繁体   English   中英

在 Jetpack Compose 中保持可组合娱乐状态的最佳方式是什么?

[英]What is the best way to persist state in composable recreation in Jetpack Compose?

考虑我们在切换实现场景中具有以下结构:

@Composable
fun RootComposable() {
  var someAuxToggle by remember { mutableStateOf(false) }

  if (someAuxToggle) {
    FirstComposable { someAuxToggle = !someAuxToggle }
  } else {
    SecondComposable { someAuxToggle = !someAuxToggle }
  }
}

@Composable
fun FirstComposable(auxCallback: () -> Unit) {
  val myRandomNumber by remember { mutableStateOf(Random.nextInt(100)) }
  Button(onClick = { auxCallback() }) {
    Text(text = "I'm the FirstComposable.\nMy random is: $myRandomNumber")
  }
}

@Composable
fun SecondComposable(auxCallback: () -> Unit) {
  val myRandomNumber by remember { mutableStateOf(Random.nextInt(100)) }
  Button(onClick = { auxCallback() }) {
    Text(text = "I'm the SecondComposable.\nMy random is: $myRandomNumber")
  }
}

这样做,切换工作,可组合物被正确调用,但是一旦我“重新创建”它们自己的状态就会改变。 如果这些按钮被放置在其他顶级可组合项中并且这些顶级可组合项被调用,这也是有效的。

现在,如果我们以一种有点老套的方式实现它,状态就会保持活跃(随机数不会重新生成):

@Composable
fun RootComposable() {
  var someAuxToggle by remember { mutableStateOf(false) }

  Box(
    if (someAuxToggle)
      Modifier.wrapContentSize()
    else
      Modifier.size(0.dp)
  ) {
    FirstComposable { someAuxToggle = !someAuxToggle }
  }

  Box(
    if (someAuxToggle)
      Modifier.size(0.dp)
    else
      Modifier.wrapContentSize()
  ) {
    SecondComposable { someAuxToggle = !someAuxToggle }
  }
}

@Composable
fun FirstComposable(auxCallback: () -> Unit) {
  val myRandomNumber by remember { mutableStateOf(Random.nextInt(100)) }
  Button(onClick = { auxCallback() }) {
    Text(text = "I'm the FirstComposable.\nMy random is: $myRandomNumber")
  }
}

@Composable
fun SecondComposable(auxCallback: () -> Unit) {
  val myRandomNumber by remember { mutableStateOf(Random.nextInt(100)) }
  Button(onClick = { auxCallback() }) {
    Text(text = "I'm the SecondComposable.\nMy random is: $myRandomNumber")
  }
}

请注意,在此实现中,两个按钮都在 root 内部调用,但切换是通过设置它们的大小来切换它们的“可见性”来进行的。

另请注意,可组合的按钮实际上是相同的组件,但我的想法只是演示状态行为。

我的问题是,如果我们再次调用可组合对象,保持状态的最佳方式,就像在第一个代码中一样; 如果有一种简单的方法可以做到这一点,或者我们真的需要将这些状态存储在一些顶级字段或类似的东西中。

另外,就性能而言,第二种方法是否过于昂贵? 我认为是的,因为这两个可组合组件一直都在“打开”,那么如果我们有使工作很辛苦的可组合组件(例如,通过副作用甚至后台任务),那么性能可能会降低。

无论如何,我希望我们能找到解决方案。

这取决于您要如何recreaterestore状态的范围,您可以在状态取决于其生命周期的viewmodel中提升它,或者在必须定义SaversaverestorerememberSaveable中提升它国家。 到目前为止,当我只想在配置更改期间生存恢复状态(即从亮到暗,屏幕旋转)时,我只考虑使用rememberSaveable ,另一方面,当composable的功能依赖于更深层次的功能时,我通过ViewModel提升状态(即存储库/网络调用,繁重的业务用例

此外,这两个实现都将触发RootComposable的整个重新组合,因为它观察到一个mutableState

 if (someAuxToggle) 
 ...
 ...

我不太确定第二个是否会对性能造成重大影响,假设这只是您实际代码的范围。

我建议在做出hoisting决定时不时观看此内容作为复习A Compose 的心态:使用 Jetpack Compose 的自动状态观察

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM