The*_*awd 14 android kotlin kotlin-coroutines android-jetpack-compose kotlin-flow
我的应用程序中有一个 UserStateModel(数据类)类型的 StateFlow。
private val _userStateFlow: MutableStateFlow<UserStateModel?> = MutableStateFlow(UserStateModel())
val userStateFlow: StateFlow<UserStateModel?> = _userStateFlow
Run Code Online (Sandbox Code Playgroud)
这是用户状态模型
data class UserStateModel(
val uid: String? = null,
val username: String? = null,
val profileImageUrl: String? = null,
var isLoggedIn: Boolean = false,
val isPremiumUser: Boolean = false,
val posts: List<Post>? = listOf()
)
Run Code Online (Sandbox Code Playgroud)
当我使用新的用户名更新 StateFlow 时,它会将更改发送给收集器并更新 UI。但是当我更改帖子内的属性时:列表?列表它不会发出更改。当我更改列表的大小时,它会更改,而当我更改索引 0 处的帖子的 name 属性时,它不会更改。如何检测 Data 类的子属性的更改?
现在我使用一个丑陋的解决方法,我补充道
val updateErrorWorkaround: Int = 0
Run Code Online (Sandbox Code Playgroud)
到 UserStateModel 数据类并将其加一以便收集器收到通知
PS我正在使用 MVVM + Clean Architecture 和 Jeptack Compose
编辑 这是我的帖子模型:
data class Post(
val id: Int,
val name: String,
val tags: MutableList<Tag>? = null
)
Run Code Online (Sandbox Code Playgroud)
以下是我更新 MutableList 的方法:
val posts = userStateFlow.value?.posts
posts.get(index).tags?.add(myNewTag)
_userStateFlow.value = userStateFlow.value?.copy(posts = posts)
Run Code Online (Sandbox Code Playgroud)
这些更改不会发送给收集器
bro*_*oot 56
StateFlow仅当它检测到值的更改时才发出,它会忽略用相同数据替换该值。为此,它将前一个值与新值进行比较。因此,我们不应该修改已经提供给 的数据StateFlow,因为它将无法检测到更改。
例如,我们设置value为User(name=John). name然后,我们通过将其修改为来改变同一个用户对象James,并将其设置value为这个“新”用户对象。StateFlow将“new”User(name=James)与其存储的值进行比较,该值现在也是User(name=James),因此它看不到任何变化。
在您的示例中,您创建了 的副本UserStateModel,但在内部重复使用相同的对象并对它们进行变异。在这种情况下,您添加了一个新项目,tags并且此更改也会影响旧项目UserStateModel,因此StateFlow不会检测到该更改。
要解决该问题,您需要复制所有已更改的数据,并且不要就地更改任何内容。使所有数据不可变会更安全,因此,val这样List您就被迫制作副本。我更改tags为val tags: List<Tag> = listOf(),那么您的代码可能如下所示:
val posts = userStateFlow.value?.posts!!.toMutableList()
posts[index] = posts[index].copy(tags = posts[index].tags + myNewTag)
userStateFlow.value = userStateFlow.value?.copy(posts = posts)
Run Code Online (Sandbox Code Playgroud)
这里我们不仅创建了一个副本UserStateModel。我们还复制posts列表、Post我们修改的列表以及标签列表。
或者,如果 的这种行为对StateFlow您来说更烦人而不是有帮助,您可以使用SharedFlow它不比较值,而只是发出。
| 归档时间: |
|
| 查看次数: |
17961 次 |
| 最近记录: |