I have a Composable that uses a Handler to slowly update the alpha of an image inside a composable. However, I'm seeing that the screen turns off before the animation could complete.
In XML layouts, we could keep it alive using android:keepScreenOn
or window.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
Is there a way to do this using compose without using the wake lock permission?
Today, we're releasing version 1.2 of Jetpack Compose, Android's modern, native UI toolkit, continuing to build out our roadmap.
Jetpack Compose comes with all the functionality needed to build a rich and responsive application UI and features full interoperability with current Android views, making it easy for developers to implement in existing projects.
Stay organized with collections Save and categorize content based on your preferences. For the best experience developing with Jetpack Compose, download and install Android Studio.
mutableStateOf creates an observable MutableState<T> , which is an observable type integrated with the compose runtime. interface MutableState<T> : State<T> { override var value: T. } Any changes to value will schedule recomposition of any composable functions that read value .
You can use LocalContext
to get activity, and it has a window on which you can apply needed flags.
In such cases, when you need to run some code on both view appearance and disappearance, DisposableEffect
can be used:
@Composable
fun KeepScreenOn() {
val context = LocalContext.current
DisposableEffect(Unit) {
val window = context.findActivity()?.window
window?.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
onDispose {
window?.clearFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
}
}
}
fun Context.findActivity(): Activity? {
var context = this
while (context is ContextWrapper) {
if (context is Activity) return context
context = context.baseContext
}
return null
}
Usage: when screen appears flag is set to on, and when disappears - it's cleared.
@Composable
fun Screen() {
KeepScreenOn()
}
As @Louis CAD correctly pointed out, you can have problems if you use this "view" in many views: if one view appears that uses it, and then disappears previous views that also used it, it will reset the flag.
I haven't found a way of tracking flags
state to update the view, I think @Louis CAD solution is OK until Compose have some system support.
This one should be safe from any interference if you have multiple usages in the same composition:
@Composable
fun KeepScreenOn() = AndroidView({ View(it).apply { keepScreenOn = true } })
Usage is then as simple as that:
if (screenShallBeKeptOn) {
KeepScreenOn()
}
In a more Compose way:
@Composable
fun KeepScreenOn() {
val currentView = LocalView.current
DisposableEffect(Unit) {
currentView.keepScreenOn = true
onDispose {
currentView.keepScreenOn = false
}
}
}
This will be disposed of as soon as views disappear from the composition. Usage is as simple as:
@Composable
fun Screen() {
KeepScreenOn()
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With