How to collect Viewmodel StateFlow in customView in android

54 Views Asked by At

How to collect StateFlow in customView in android

I have a ViewModel

class MyViewModel : ViewModel() {
    private val _myState = MutableStateFlow(MyState())
    val myState: StateFlow<MyState> = _myState

    fun updateMyState(newState: MyState) {
        _myState.value = newState
    }
}

data class MyState(
    val name: String = "",
    val age: Int = 0,
    val isMarried: Boolean = false
)

I am able to collect the updated data in an activity using

lifecycleScope.launchWhenStarted {
            viewModel.myState.collect { state ->
                Log.e("collected ", "tateflow: ${state.name}")
           
            }
        }

How ever we want to update a custom view based on this collected data how can we update the custom view based on this data

2

There are 2 best solutions below

0
hnxtay On

Can you please share the code for creating a viewModel in your custom view? Is your code similar to this:

 private val viewModel: ActivityViewModel by activityViewModels()
0
Iván Garza Bermea On

It really depends on the kind of 'view' you're trying to do this through.

As a failsafe, you can always try to build your own CoroutineScope wherever you need it, just make sure that you cancel/complete all jobs once you're done with it:

val job = Job()
val scope = CoroutineScope(job + Dispatchers.Main)
// do your thing
job.complete()

In the example above, I chose a to use Dispatchers.Main given that we're talking about views here, but you could go with any other of the Dispatchers depending on the kind of job you're trying to achieve.

Nevertheless, I would recommend you don't listen to your ViewModel's data directly from a custom View. Instead, consider listening from the parent container (I'd like to assume all this lives in a Fragment or Composable of sorts) and only passing in the data that is required for your given View to function properly.

This a much better pattern, as recommended by Android all around; see 'Best Practices' point #4 in the following documentation.