You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何分离使用remember与mutableStateOf解决Compose状态丢失问题

Jetpack Compose 状态持有与编译代码查看相关问题

常规实现写法

通常情况下,Compose代码写法如下:

@Preview
@Composable
fun BuildMyView() {
    val counter = rememberSaveable { mutableStateOf(1) }

    Text(
        modifier = Modifier
            .fillMaxSize()
            .wrapContentSize(align = Alignment.Center)
            .clickable { counter.value++ },// 点击后文本数值自增
        text = "${counter.value}"
    )
}

自定义状态封装的异常问题

为了将所有视图数据聚合封装为统一状态类,编写了如下形式的代码:

data class MyState(
    val data: MutableState<String>
)

val stateTemp = MyState(mutableStateOf("hello"))

@Preview
@Composable
fun BuildMyView() {
    val counter = rememberSaveable { stateTemp.data}

    Text(
        modifier = Modifier
            .fillMaxSize()
            .wrapContentSize(align = Alignment.Center)
            .clickable { stateTemp.data.value += "-1" },
        text = counter.value
    )
}

第二种写法点击文本时可正常触发内容更新,但跳转到新页面再返回时,所有修改的状态都会丢失,第一种写法则不会出现该问题。查阅Compose相关代码后未找到remember订阅可变状态的具体实现位置,存在两个待解决的疑问:

  • 是否有方法可以让定义在Compose作用域外的mutableState正常工作,避免页面返回时状态丢失?
  • 是否可以在Gradle构建目录或其他位置找到Compose编译生成的代码(dex文件除外,其可读性过差)?Compose功能十分强大,但无法直接查看实际运行的对应代码对新手入门造成了较大阻碍。

2022年6月15日更新

目前找到了合适的解决方案:使用ViewModel替代普通状态持有类,在ViewModel中定义mutableState,在Composable视图层中订阅状态,该方式可以避免ViewModel搭配LiveData的复杂语法,希望能为其他开发者提供参考。


内容的提问来源于stack exchange,提问作者michael

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.30 23:12:24