Blog Infos
Author
Published
Topics
,
Published
Topics
,
ViewModel
class MainActivityViewModel : ViewModel() {
private val _counterLiveData = MutableLiveData(0)
val counterLiveData: LiveData<Int> = _counterLiveData
fun incrementByOne() {
_counterLiveData.value = _counterLiveData.value?.plus(1)
}
}

2. Now we will declare an instance of ViewModel in our Fragment. Now many of you, who are new to this concept of ViewModels might be wondering, as ViewModel is just a class, we can simply declare an instance of the ViewModel and access public variables in our Activity/Fragment.
Something like -:

val viewModel = MainActivityViewModel()
findViewById<Button>(R.id.btn_increment).setOnClickListener {
viewModel.incrementByOne()
}
viewModel.counterLiveData.observe(this) { counter ->
findViewById<TextView>(R.id.tv_counter).text = "$counter"
}

Cool and easy right? NOOO. This will not throw an error, but it will not fill our purpose of retaining counter value on configuration changes. That’s not how ViewModel works. We need something called a ViewModelProvider to create a ViewModel. The correct way to create a ViewModel is -:

val viewModel = ViewModelProvider(this)[MainActivityViewModel::class.java]
findViewById<Button>(R.id.btn_increment).setOnClickListener {
viewModel.incrementByOne()
}
viewModel.counterLiveData.observe(this) { counter ->
findViewById<TextView>(R.id.tv_counter).text = "$counter"
}

Job Offers

Job Offers

There are currently no vacancies.

OUR VIDEO RECOMMENDATION

Jobs

ViewModelProvider
1. Activity lifecycle on Configuration changes
2. ViewModelProvider not destroyed by configuration change??????
public constructor(
owner: ViewModelStoreOwner
) : this(owner.viewModelStore, defaultFactory(owner))

Here you can see that we pass something called ViewModelStoreOwner. But in our Activity, we pass this while instantiating our ViewModelProvider.

ViewModelProvider(this)[MainActivityViewModel::class.java]

But from where did this ViewModelStoreOwner come from in our Activity? If we check the source code of Activity class, it can be noticed that the Activity class implements the ViewModelStoreOwner interface.

public class ComponentActivity extends androidx.core.app.ComponentActivity implements
        ContextAware,
        LifecycleOwner,
        ViewModelStoreOwner,
        HasDefaultViewModelProviderFactory,
        SavedStateRegistryOwner,
        OnBackPressedDispatcherOwner,
        ActivityResultRegistryOwner,
        ActivityResultCaller
public interface ViewModelStoreOwner {
    /**
     * Returns owned {@link ViewModelStore}
     *
     * @return a {@code ViewModelStore}
     */
    @NonNull
    ViewModelStore getViewModelStore();
}

Let’s dig further deep into the implementation of the getViewModelStore()in our Activity and see what it does.

@NonNull
@Override
public ViewModelStore getViewModelStore() {
    if (getApplication() == null) {
        throw new IllegalStateException("Your activity is not yet attached to the "
                + "Application instance. You can't request ViewModel before onCreate call.");
    }
    ensureViewModelStore();
    return mViewModelStore;
}

If the activity is not created, it returns throwing an error, but if it is it called the ensureViewModelStore() method.

void ensureViewModelStore() {
    if (mViewModelStore == null) {
        NonConfigurationInstances nc =
                (NonConfigurationInstances) getLastNonConfigurationInstance();
        if (nc != null) {
            // Restore the ViewModelStore from NonConfigurationInstances
            mViewModelStore = nc.viewModelStore;
        }
        if (mViewModelStore == null) {
            mViewModelStore = new ViewModelStore();
        }
    }
}
if (nc != null) {
            // Restore the ViewModelStore from NonConfigurationInstances
            mViewModelStore = nc.viewModelStore;
        }
static final class NonConfigurationInstances {
    Object custom;
    ViewModelStore viewModelStore;
}
getLifecycle().addObserver(new LifecycleEventObserver() {
    @Override
    public void onStateChanged(@NonNull LifecycleOwner source,
            @NonNull Lifecycle.Event event) {
        if (event == Lifecycle.Event.ON_DESTROY) {
            // Clear out the available context
            mContextAwareHelper.clearAvailableContext();
            // And clear the ViewModelStore
            if (!isChangingConfigurations()) {
                getViewModelStore().clear();
            }
        }
    }
});

YOU MAY BE INTERESTED IN

YOU MAY BE INTERESTED IN

blog
It’s one of the common UX across apps to provide swipe to dismiss so…
READ MORE
blog
Hi, today I come to you with a quick tip on how to update…
READ MORE
blog
Automation is a key point of Software Testing once it make possible to reproduce…
READ MORE
blog
Drag and Drop reordering in Recyclerview can be achieved with ItemTouchHelper (checkout implementation reference).…
READ MORE
Menu