In this tutorial, we’ll go through the LiveData android architectural component in our Android application. Take a brief whirl to ViewModel for a better understanding of this tutorial.
Contents
What is LiveData?
LiveData is a class that holds observable data. Unlike a regular observable, LiveData is lifecycle-aware, which means that it respects the lifecycle of other app components such as activities, fragments, or services. This awareness ensures that only app component observers in an active lifecycle state are updated by LiveData.
LiveData is simply a data type that notifies its observer when the data changes. LiveData looks similar to a data change notifier. |
LiveData is a pattern in the architecture. It’s essentially a data holder for primitive/collection types. When it is active, it is used for observing changes in the view and updating the view. As a result, it is aware of the lifecycle.
- ViewModels, as we know, are used to communicate data to the View. Using ViewModels alone can be a time-consuming and expensive process because we must make multiple calls each time the data changes the View. In addition, we must store the data Model in different locations.
- LiveData, which is based on the Observer Pattern, helps to communicate between the ViewModel and the View.
Advantages:
- LiveData can be used with libraries such as Room Persistent Library, Coroutines, and others.
- When a set of data is modified or changed, the observers are notified. However, before notifying the observers, LiveData will check if the observer is live or not. If it is active, the notification will be sent, otherwise, it will not. As a result, the crash caused by disrupted activities will be prevented.
- You don’t have to worry about unsubscribing any observers when using LiveData.
- If an inactive observer is reactivated in the future, the most recent data will be sent to that observer.
- It is based on the observer pattern and ensures that your UI matches your data state. As a result, rather than requesting the data from ViewModel each time, we will be notified whenever the data changes.
- Prevent memory leaks — Observers are bound by the life cycle, and when the lifecycle is destroyed, the LiveData object is also destroyed.
- No more crashes as a result of stopped activities- If the observer’s lifecycle is inactive, such as in the case of a back stack activity, it does not receive any LiveData events.
- There will be no more manual lifecycle management – UI components will simply observe relevant data and will not stop or resume observation. Because LiveData is aware of relevant lifecycle status changes, it manages all of this automatically.
- Data that is always up to date — If a lifecycle becomes inactive, it receives the most recent data when it becomes active again. For example, when a background activity returns to the foreground, it receives the most recent data.
- Manage all configuration changes —When an activity or fragment is recreated as a result of a configuration change, such as device rotation, it receives the most recent available data right away.
What is the difference between livedata and MutableLiveData?
We can only observe the data with LiveData and cannot change it. MutableLiveData is a subclass of LiveData that is mutable. In MutableLiveData, we can observe and set values using the postValue() and setValue() methods (the former of which is thread-safe), allowing us to send values to any live or active observers.
LiveData is immutable, MutableLiveData is mutable & thread-safe. So yes, the difference comes only by making postValue and setValue public.
- setValue() runs on the main thread.
- postValue() runs on the background thread.
Why we need LiveData?
It handles admirably in resolving mainly 2 issues.
- It removed the leaks caused by interfaces/callbacks that send results to the UI thread. This is a fundamental feature of an MVVM model in which callbacks are sent from the ViewModel to the activity/fragment.
- It decouples the data, mediator, and UI layers from one another.
- Consider an application built using the MVP pattern. If we want to update the UI based on the result of a network call, we can call a method from the View layer to the Presentation layer to perform a network request and then write an AsyncTask to do the work. As a result, we can use the Interface to communicate this response to the Main thread, which will allow us to update the UI.
LiveData Example:
Get Started:
Step 1: Create a New Android Studio Project
Create a new project in AndroidStudio with the EmptyActivity template named LiveData. Simply add a dependency to the app/build.gradle file given below:
// ViewModel implementation(“androidx.lifecycle:lifecycle-viewmodel-ktx:2.4.0-alpha03”) // LiveData implementation(“androidx.lifecycle:lifecycle-livedata-ktx:2.4.0-alpha03”) |
We also use lambda expression in this project so set compile option 1.8 inside the android tag in app/build.gradle.
compileOptions { sourceCompatibility JavaVersion.VERSION_1_8 targetCompatibility JavaVersion.VERSION_1_8 } |
Step 2: Create a layout for application- In activity_main.xml add TextView and Button as given below.
<?xml version="1.0" encoding="utf-8"?> <androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".MainActivity"> <TextView android:id="@+id/textView" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="Hello World!" android:textSize="30sp" app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintLeft_toLeftOf="parent" app:layout_constraintRight_toRightOf="parent" app:layout_constraintTop_toTopOf="parent" app:layout_constraintVertical_bias="0.199" /> <Button android:id="@+id/button" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginBottom="176dp" android:text="UpdateData" app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintStart_toStartOf="parent" /> </androidx.constraintlayout.widget.ConstraintLayout>
Step :3 Create a new class, named it MainViewModel inside this define a livedata and MutableLiveData as shown below:
package com.sagar.livedata import androidx.lifecycle.LiveData import androidx.lifecycle.MutableLiveData import androidx.lifecycle.ViewModel class MainViewModel: ViewModel() { private val _firstLiveData = MutableLiveData<String>("LiveData Example Developers Dome") val firstLiveData: LiveData<String> get() = _firstLiveData fun updateLiveData(){ _firstLiveData.value = "Android Development" } }
Step 4: In the MainActivity file initialize textview, button, and handle event listener in this class.
package com.sagar.livedata import android.os.Bundle import android.widget.Button import android.widget.TextView import androidx.appcompat.app.AppCompatActivity import androidx.lifecycle.Observer import androidx.lifecycle.ViewModelProvider class MainActivity : AppCompatActivity() { lateinit var mainViewModel: MainViewModel private val firstTextView: TextView get() = findViewById(R.id.textView) private val btnUpdate: Button get() = findViewById(R.id.button) override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) mainViewModel = ViewModelProvider(this)[MainViewModel::class.java] mainViewModel.firstLiveData.observe(this, Observer { firstTextView.text = it }) btnUpdate.setOnClickListener { mainViewModel.updateLiveData() } } }
Output:
Run the application now. You will get the output shown in the output section.
That’s all about the Android LiveData.
If you are interested in learning Data binding and View Binding, you can go through Data Binding in Android with Example, and View Binding in Android with Example here I have explained Data Binding, One-way, and Two-way Data Binding, @BindingAdapter, View Binding in detail with suitable Examples in Android, and several scenarios in which data and view binding can be useful. and I assure you that till the end, you will have a clear understanding of this commonly used library.
- We hope that this guide will assist you in understanding all the concepts of LiveData and MutableLiveData in android. We have concentrated on making a basic, meaningful, and easy-to-learn guide to the concepts of LiveData with suitable examples. Still, if you have any problems regarding it, please post them in the comments section, we will be glad to assist you.
Pingback: Introduction to Android Architecture Components with Example