today I'm trying about Jetpack compose and the ViewModel class. Everything seems to be logic but I got some problems understanding the encapsulation.
// ViewModel
class MyViewModel: ViewModel() {
var uiStateList = mutableStateListOf(1,2,3)
privat set
private var _uiStateList2 = mutableStateListOf(11,22,33)
val uiState2 List<Int>
get() = _uiStateList2
fun addToUiStateList2() {
_uiStateList2.add(_uiStateList2.last() 11)
}
}
The first var is like in the Compose tutorials. The construction of the second var looks like using MutableLiveData.
// Activity
@Composable
fun MyComposable(
modifier: Modifier = Modifier,
myViewModel: MyViewModel= viewModel()
) {
val uiStateList = myViewModel.uiStateList
val uiStateList2 = myViewModel.uiStateList2
Column {
uiStateList.forEach {
Text(it.toString())
}
Button(
onclick = {uiStateList.add(uiStateList.last() 1)},
content = {text( 1)}
)
uiStateList2.forEach {
Text(it.toString())
}
Button(
onclick = {
// uiStateList2.add(uiStateList2.last() 11) // not possible because of type List<Int>
myViewModel.addToUiStateList2() // possible, changing indirectly the value of uiStateList2
},
content = {text( 11)}
)
}
}
In the first case it's possible to modify the mutableStateList inside of the ViewModel by running just a simple function in the composable. Consequently it is possible to change the value from outside of the class directly.
In the second case I got no chance to change the data in the viewmodel. The var uiStateList2 is a imutable list which reflects the data from the private val from the viewmodel. If the function addToUiStateList2() is triggered, the original list changes and the composable will be recompositioned and everything is fine.
Why can I change the data of the var uiStateList inside the Composable, although the setter is set to private inside the ViewModel class? In the documentation I read, that private setters could just be used inside the owning class. Do I think too complicated, or is this the usually aproach how everything is build?
Thanks for help Guys!
CodePudding user response:
Private setter doesn't allow to set the value i.e myViewModel.uiStateList= //something
. But you can still modify the list because it is mutable. If you want to restrict changing the state from outside viewModel second approach is preferred.