Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

When using MVVM on Android, should each Activity have one (and only one) ViewModel?

Tags:

android

mvvm

On MVVM pattern, the ViewModel contains business logic and notifies the View when it needs to be updated. It is also notified by the view about user events.

As I understood it, each Model should have an associated ViewModel. So, if we have the following models:

  • User
  • Account

We would have the following ViewModels:

  • UserViewModel
  • AccountViewModel

However, all examples I find about data binding with MVVM, use a single ViewModel for a layout. And recently, Google has introduced the ViewModel class within Architecture Components. This leads me to believe an Activity would have a single ViewModel that would connect to all related Models:

User / Account --> ActivityViewModel

This gets even more complicated if we think of a RecyclerView. Each adapter item could be a ViewModel itself, so an Activity with a RecyclerView would have multiple ViewModels within the list and plus a master one for the remaining view contents (assuming they require information from a ViewModel). For instance:

enter image description here

In this example, we have a list of Account ViewModels and one UserViewModel. How would this be embedded into a single ActivityViewModel?

like image 324
fhsilva Avatar asked Jun 05 '17 18:06

fhsilva


People also ask

Can two activities have same ViewModel?

In android, we can use ViewModel to share data between various fragments or activities by sharing the same ViewModel among all the fragments and they can access everything defined in the ViewModel. This is one way to have communication between fragments or activities.

Can one fragment have multiple Viewmodels?

In fact you can have multiple view models for a single fragments doing different things for you.

Should every view have a ViewModel?

For a best mvvm pattern implementation each view must have the own viewmodel, and don't share anythings with other.

Can a ViewModel have multiple models?

ViewModel is nothing but a single class that may have multiple models. It contains multiple models as a property. It should not contain any method. In the above example, we have the required View model with two properties.


4 Answers

You should have one ViewModel per View (Activity, Fragment or Custom View), with multiple LiveData, one for each logical unit. In the image one logical unit would be the user data, another logical unit would be the settings data, so you would have two LiveData exposed in the ViewModel.

View with multiple LiveData

These concepts can also be visible in the recommended app architecture google presented in the last Google I/O, where an Activity/Fragment has 1 ViewModel with multiple LiveData:

enter image description here

like image 50
Eduardo Avatar answered Oct 23 '22 14:10

Eduardo


Google suggests that you use 1 ViewModel per View (i.e., Activity or Fragment) (see https://youtu.be/Ts-uxYiBEQ8?t=8m40s), and then inside each ViewModel you can have more than 1 type of Model. However, the MVVM principle is to have only 1 Model type per ViewModel, so Google's presentation contradicts that :/. I guess you'll have to decide what approach works better for your app.

About the list example you mentioned, that is not how you'd do it, for lists you'd use the paging library. You can see details on how to use this at the end of the video I linked above.

like image 28
Franco Avatar answered Oct 23 '22 14:10

Franco


One view model is standard. However, even google suggests that you may have more than one view model. That comes quite convenient when you mitgrate a phone app towards a tablet app. When you combind more than one phone views on a single tab view, then it is convenient re-using the models.

If you have the SOLID principles in mind when coding, then the S (single responsibitly of a class) may cause you to use more than one view model.

However, one per view is pretty much standard and you shold have reasons, as metioned above, to use more than one.

like image 9
Hermann Klecker Avatar answered Oct 23 '22 14:10

Hermann Klecker


What is the relationship between Users and Accounts? If these are two separate, unrelated models, then they should each have their own views and view models. Remember the single responsibility principle: each module should be responsible for only a single part of your logic. That way, any changes to your domain logic or models will only affect that part, and that part only.

like image 1
Omar Silva Avatar answered Oct 23 '22 15:10

Omar Silva