I hope to set _isRecording
inside SoundViewModel
class, and I hope to expose isRecording
to UI.
But the Code A is wrong, how can I fix it?
Code A
class SoundViewModel @Inject constructor(): ViewModel() {
private var _isRecording by mutableStateOf(false)
val isRecording: State<Boolean> by _isRecording //It's wrong
//val isRecording: State<Boolean> = _isRecording //It's wrong
..
}
Add content:
To nglauber: Thanks!
I think Code B will work well.
Which is better between your code and Code B?
Code B
class SoundViewModel @Inject constructor(): ViewModel() {
var isRecording by mutableStateOf(false)
private set
}
@Composable
fun YourComposable(soundViewModel: SoundViewModel) {
//I can use soundViewModel.isRecording directly
}
CodePudding user response:
When you use the keyword by
, it's basically an alias to getValue
/setValue
. Therefore:
// _isRecording is a Boolean
private var _isRecording by mutableStateOf(false)
// _isRecording is a State<Boolean>
private var _isRecording = mutableStateOf(false)
This is why you're getting this error.
You should expose like this:
class SoundViewModel @Inject constructor(): ViewModel() {
private var _isRecording = mutableStateOf(false)
val isRecording: State<Boolean> = _isRecording
}
and consume like this:
@Composable
fun YourComposable(soundViewModel: SoundViewModel) {
val isRecording by soundViewModel.isRecording
CodePudding user response:
CLEARLY -- Code B is the best option. That's exactly what official Compose Docs recommend. The method with the underscore was adopted for LiveData
objects, but when you shift to the Compose-compatible MutableState<T>
, it is simply de-efficiencizing(?) your code, if you add that extra underscore step.
Check out the State-in-Compose for full insights.
Go with the simplest approach that gets the job done, always the rule of thumb.