Proper way of sending large amount of data from View to ViewModel
The problem
I am working on a simple drawing app for Android. I have a custom view on which the user can draw. This means that a lot of data (a list of points) is generated in this View.
I want to store this data in the ViewModel
.
If I need to update a View
after something changes in the ViewModel
, I can just use LiveData
in the ViewModel
and put an observer in the View
.
However, what I need is the other direction: changes in the View
should lead to an update of the data in the ViewModel
.
What I've learnt so far
I can use MutableLiveData
for this, however, it is unclear to me what the right way is to give the View
access to the MutableLiveData
.
I can access a ViewModel
from an Activity
, by calling:
viewModel = new ViewModelProvider(this).get(MyViewModel.class);
But, I cannot access the ViewModel
from the View. ViewModelProvider
takes a ViewModelStoreOwner
as its parameter. An Activity
is a ViewModelStoreOwner
, but a View
is not.
I believe this is intentional, otherwise the View
would be a ViewModelStoreOwner
itself. I could pass a reference to the Activity
or the ViewModel
itself to the View
, but this feels wrong.
It seems that I need to use MutableLiveData
. I could then use setValue
or postValue
on the MutableLiveData
whenever the View
has more data to send.
However, that just shifts the problem: how should the View
get access to the MutableLiveData
?
What I've tried
For now, I have a workaround.
I have created an interface ListOfPoints
that is implemented by the Activity
. The View
has a method setPointsOwner(ListOfPoints)
. So, effectively, the View
still gets a reference to the Activity
, but can only use it to manipulate the data. The implementation of the interface, inside the Activity
, then updates the MutableLiveData
it gets from the ViewModel
.
This works, but still feels wrong.
The question
How can I send a lot of data from a View
to a ViewModel
?
Is it proper coding style to give the View
access to MutableLiveData
from the owning Activity
?
Or is there a way in which I can make the ViewModel
observe the View
, without letting it have a direct reference to the View
?
3 comments
I have also added [binding] tag as the concept seems to be used (bind view to viewmodel). Very good question btw. — Alexei 5 months ago
@Alexei Thanks! "Binding" seems a rather broad tag. But I'll let the community decide about that. — FractionalRadix 5 months ago
@FractionalRadix Yes, [binding] is very general, but it is what I heard being used for frameworks such a Windows Forms. WPF, Angular and Xamarin. Maybe something like [android-viewbinding] is more appropriate, but I am not sure if this is what you are using (never programmed directly with Java in Android). — Alexei 5 months ago