I have a simple class Person, defined as follow
data class User(
val id: String = "",
val name: String = "",
val surname: String = "",
...
)
Then I have a ProfileViewModel class which has two methods
getUserById()
and updateUser()
class ProfileViewModel(private val id: String): ViewModel() {
var user: User = User()
fun getUserById() { ... }
fun updateUser() { ... }
}
afterwards I have a composable function with a form, that should be able to initialize the user data into the form field, and then update them
@Composable
fun ProfileView(profileViewModel: ProfileViewModel() = viewModel()) {
Column () {
...
}
}
I could create some variable into the composable function and then pass them when I perform the userUpdate, but How can I perform theese operations using the user variable into the profileViewModel class with a clean and structured code?
I see a couple of ways of doing this. Your initial code does not look like it can progress in a good direction. However, consider the following changes:
Avoid the string dependency in the ViewModel
. The entire class is not dependent on the string. Even if it is, it should not be passed a constructor parameter. Consider using technologies like compose State
your ViewModel
and properly encapsulate it.
class ProfileViewModel(): ViewModel() {
val user = mutableStateOf<User>(User.dummy()) // initial value
fun getUserById(id: String) { /* Fetch user and set user */ }
fun updateUser() { /* Send the user object to the domain layer */ }
}
You can now load the current values of user
into your composable function. As the client is changing his details, the information is synced with the ViewModel
.
When you are comfortable with this, think about how you can encapsulate the mutable state. Mutable objects and variables should not be exposed since other parts of your code can modify it without considering its consequences.