なんか、いろんな方法があるんだなあ、と。
👉 Lifecycle を Compose と統合する | App architecture | Android Developers
👉 ComposeでLifecycleを監視する(2023年9月バージョン) - Kenji Abe - Medium
いろいろ試しながらどこから使っていくのがいいか。を考える。
🤔 参考になるコードたち
調べてみると、
DisposableEffect を中心に考えるのがいいだろう、
と思える。
@Composable
fun LifecycleEffect(
onCreate: () -> Unit = { },
onStart: () -> Unit = { },
onResume: () -> Unit = { },
onPause: () -> Unit = { },
onStop: () -> Unit = { },
onDestroy: () -> Unit = { },
onAny: () -> Unit = { }
) {
val lifecycleOwner = LocalLifecycleOwner.current
DisposableEffect(lifecycleOwner) {
val observer = LifecycleEventObserver { _, event ->
when (event) {
Event.ON_CREATE -> onCreate()
Event.ON_START -> onStart()
Event.ON_RESUME -> onResume()
Event.ON_PAUSE -> onPause()
Event.ON_STOP -> onStop()
Event.ON_DESTROY -> onDestroy()
Event.ON_ANY -> onAny()
}
}
lifecycleOwner.lifecycle.addObserver(observer)
onDispose {
lifecycleOwner.lifecycle.removeObserver(observer)
}
}
}
@Composable
fun LifecycleEffect(
lifecycleOwner: LifecycleOwner = LocalLifecycleOwner.current,
onStart: (suspend () -> Unit)? = null,
onPause: (suspend () -> Unit)? = null,
onStop: (suspend () -> Unit)? = null
) {
val scope = rememberCoroutineScope()
val currentOnStart by rememberUpdatedState(onStart)
val currentOnPause by rememberUpdatedState(onPause)
val currentOnStop by rememberUpdatedState(onStop)
DisposableEffect(lifecycleOwner) {
val observer = LifecycleEventObserver { _, event ->
scope.launch {
when (event) {
Lifecycle.Event.ON_START -> currentOnStart?.invoke()
Lifecycle.Event.ON_PAUSE -> currentOnPause?.invoke()
Lifecycle.Event.ON_STOP -> currentOnStop?.invoke()
else -> {}
}
}
}
lifecycleOwner.lifecycle.addObserver(observer)
onDispose {
lifecycleOwner.lifecycle.removeObserver(observer)
}
}
}
@Immutable
enum class LifecycleEvent {
OnStop
}
@Immutable
data class LifecycleHandler(
val id: String,
val event: LifecycleEvent,
val onEvent: () -> Unit
)
@Composable
fun <R : Any> DestinationScope<R>.LifecycleEffect(
event: LifecycleEvent,
onEvent: () -> Unit
) {
val id = remember { randomUUID() }
DisposableEffect(this, id, event, onEvent) {
navigator.update {
it.copy(lifecycleHandlers = it.lifecycleHandlers + LifecycleHandler(
id = id,
event = event,
onEvent = onEvent
))
}
onDispose {
navigator.update { dest ->
dest.copy(lifecycleHandlers = dest.lifecycleHandlers.filter { it.id != id })
}
}
}
}
🤔 まとめ
まずは、ここらから記述していくのがいいのではないか。
@Composable
@NonRestartableComposable
fun DisposableLifecycleEffect(
lifecycle: Lifecycle = LocalLifecycleOwner.current.lifecycle,
onResume: () -> Unit,
onPause: () -> Unit,
) {
DisposableEffect(lifecycle) {
val observer = LifecycleEventObserver { _, event ->
when (event) {
Lifecycle.Event.ON_RESUME -> onResume()
Lifecycle.Event.ON_PAUSE -> onPause()
else -> { }
}
}
lifecycle.addObserver(observer)
onDispose {
lifecycle.removeObserver(observer)
}
}
}
記述位置は Screen。
@NonRestartableComposable の意味を考えながら書く。
フォアグラウンド、バックグラウンドの切り分けにも使えるか。
関連ワード: Android・AndroidStudio・GitHub・IDEA・Kotlin・おすすめ・今さら聞けない・初心者・開発