Composable Debug Drawer for Jetpack Compose apps
Add mirror for maven repository:
repositories {
//...
maven {
url = uri("https://effective-android.bytesafe.dev/maven/drawer/")
}
}
Add dependencies to build.gradle.kts
of app:
dependencies{
debugImplementation("effective.band:drawer:$version")
debugImplementation("effective.band:drawer-modules:$version")
debugImplementation("effective.band:drawer-location:$version")
}
Wrap your content with DebugDrawerLayout
:
DebugDrawerLayout(
drawerModules = {
TODO()
}
) {
// TODO Add your APP Content here
}
If you don't want DebugDrawer layout code in release you can wrap it on a custom function:
src/debug/...
@Composable
fun ConfigureScreen(bodyContent: @Composable () -> Unit) {
DebugDrawerLayout(
drawerModules = { ... },
bodyContent = { bodyContent() },
)
}
src/release/...
@Composable
fun ConfigureScreen(bodyContent: @Composable () -> Unit) {
bodyContent()
}
Add modules as a list of DebugModule
s
DebugDrawerLayout(
debug = { BuildConfig.DEBUG },
drawerModules = {
DeviceModule()
BuildModule()
}
) {
// TODO Add your APP Content here
}
This module has a composable slot.
You can build any of the provided actions, or build your own.
Actions
-
ButtonAction: Shows a
Button
with given text, and register a lambda to receive its click -
SwitchAction: Shows a
Switch
and register a lambda to receive its changes
Shows information about the app: Version code, Version name and Package
Shows information about device running the app such as model and manufacturer
Allows to show a Grid layer as overlay of your content, to help align content to grid
var debugGridLayerConfig: DebugGridStateConfig by remember {
mutableStateOf(DebugGridStateConfig())
}
DebugDrawerLayout(
drawerModules = {
//...
DesignModule(config = debugGridLayerConfig) {
debugGridLayerConfig = it
}
//...
},
bodyContent = { drawerState ->
Box {
// Body of your app
DebugGridLayer(debugGridLayerConfig)
}
},
)
Configuring Retrofit endpoints and mock network behaviour
To begin, you must create a list of
Endpoints
.
This list might include entries such as staging
, or mock
.
Next, create an instance of
DebugRetrofitConfig
.
This class takes care of persisting settings between app launches, and forwarding any runtime
modifications to NetworkBehavior
. It also ensures that when you select a new Endpoint
your
entire app process is restarted.
Finally, you can add
RetrofitModule
var debugGridLayerConfig: DebugGridStateConfig by remember {
mutableStateOf(DebugGridStateConfig())
}
DebugDrawerLayout(
drawerModules = {
//...
RetrofitModule(
modifier = modulesModifier,
config = debugRetrofitConfig
)
//...
},
bodyContent = { drawerState ->
Box {
// Body of your app
DebugGridLayer(debugGridLayerConfig)
}
},
)
It can be incredibly useful to view HTTP requests and results when debugging your app. This module provides a dropdown menu in the drawer to select what level of logging you'd like to see for your HTTP requests. It relies on you using OkHttp as your HTTP client, and pipes its output into Timber.
To use it, first add
HttpLogger.interceptor
as an interceptor to your OkHttpClient
. Then pass HttpLogger
on to
OkHttpLoggerModule.
Providing a more convenient entry into LeakCanary LeakCanary is a fantastic tool for detecting memory leaks in your app. The only problem with it is how it adds a launcher icon for each app you have installed that uses it. This module takes care of removing that launcher icon and cages LeakCanary in the debug drawer. It also provides a handy switch for toggling heap dumps on and off.
Shows common location information (requires extra dependency)
Debug drawer can show any @Composable
function.
If you want to provide a custom module that looks like the ones provided by the library:
@Composable
fun CustomModule(
modifier: Modifier = Modifier,
icon: @Composable (() -> Unit)? = null,
title: String,
showBadge: Boolean = false,
items: List<Pair<String, String>>
) {
DebugDrawerModule(
modifier = modifier,
icon = icon,
title = title,
showBadge = showBadge,
) {
// Module content
}
}
Use drawerColors
to customize drawer theme colors.
DebugDrawerLayout(
drawerColors = YourColorScheme, // darkColors() or lightColors()
)
If you want to modify the drawer colors, use DebugDrawerDefaults.colors.copy(...)
Update each module's UI by passing a Modifier
DebugDrawerLayout(
drawerModules = {
val modulesModifier = Modifier
.padding(4.dp)
.clip(shape = MaterialTheme.shapes.medium)
.background(color = MaterialTheme.colors.surface)
DeviceModule(modulesModifier)
BuildModule(modulesModifier)
}
)
Or configure the whole contents by specifying a drawerContentModifier
DebugDrawerLayout(
drawerContentModifier = Modifier.padding(16.dp),
drawerModules = {
DeviceModule()
BuildModule()
}
)
Add publish credentials to local.properties
:
myMavenRepoWriteUrl=https://effective-android.bytesafe.dev/maven/drawer/
username=username
password=password
Update the version in buildSrc/src/main/kotlin/PublishConfig.kt
:
object PublishConfig {
const val drawerVersion = "1.0.0"
//...
}
Run publish
task