Android ViewModel Save State (Kotlin)
March 5, 2020NOTE:
- ViewModel can survive configuration change (screen rotation)
- To handle system-initiazted process death, you probably need to implement
onSaveInstanceState / onRestoreInstanceState
or use Saved State module for ViewModel.
NOTE: Save state will not function when the application exit via back button or kill by user via other means.
Dependencies
dependencies {
def activity_version = "1.1.0"
implementation "androidx.activity:activity-ktx:$activity_version"
def fragment_version = "1.2.2"
implementation "androidx.fragment:fragment-ktx:$fragment_version"
def lifecycle_version = '2.2.0'
// implementation "androidx.lifecycle:lifecycle-extensions:$lifecycle_version"
// ViewModel
implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:$lifecycle_version"
// LiveData
implementation "androidx.lifecycle:lifecycle-livedata-ktx:$lifecycle_version"
// Lifecycles only (without ViewModel or LiveData)
implementation "androidx.lifecycle:lifecycle-runtime-ktx:$lifecycle_version"
// Saved state module for ViewModel
implementation "androidx.lifecycle:lifecycle-viewmodel-savedstate:$lifecycle_version"
}
Code
class MainActivity : AppCompatActivity() {
private val viewModel by viewModels<MainViewModel>()
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.main)
setSupportActionBar(toolbar)
viewModel.getTestData().observer(this) {
textView.text = it
}
button.setOnClickListener {
viewModel.saveState()
}
}
}
NOTE: SavedStateViewModelFactory
(previosly known as SavedStateVMFactory
) automatically configured when using Activity 1.1.0,
or Fragment 1.2.0
.
class MainViewModel(val state: SavedStateHandle) : ViewModel() {
fun saveState() {
state.set("test", "TEST")
}
fun getTestData(): MutableLiveData<String> {
return state.getLiveData<String>("test")
}
}
Testing
In order to test if ViewModel Save State works, we need to simulate system-initialized process death.
One way of doing it is
Run app (Shift + F10)
from Android Studio- Click home button on device to put into background
- Click
Stop (F2)
from Android Studio
NOTE: There are other methods which I have yet to try.
On the device, find the app icon and launch again, the state value shall be restored.
The following method will not simulate system-initialized process death (thus state shall not be restored)
- Click back button to exit app
- Kill app on device via
Overview
button (Square icon) - Kill app via
adb shell am force-stop APPLICATION_ID
References:
- algo-trading
- algolia
- analytics
- android
- android-ktx
- android-permission
- android-studio
- apps-script
- bash
- binance
- bootstrap
- bootstrapvue
- chartjs
- chrome
- cloud-functions
- coding-interview
- contentresolver
- coroutines
- crashlytics
- crypto
- css
- dagger2
- datastore
- datetime
- docker
- eslint
- firebase
- firebase-auth
- firebase-hosting
- firestore
- firestore-security-rules
- flask
- fontawesome
- fresco
- git
- github
- glide
- godot
- google-app-engine
- google-cloud-storage
- google-colab
- google-drive
- google-maps
- google-places
- google-play
- google-sheets
- gradle
- html
- hugo
- inkscape
- java
- java-time
- javascript
- jetpack-compose
- jetson-nano
- kotlin
- kotlin-serialization
- layout
- lets-encrypt
- lifecycle
- linux
- logging
- lubuntu
- markdown
- mate
- material-design
- matplotlib
- md5
- mongodb
- moshi
- mplfinance
- mysql
- navigation
- nginx
- nodejs
- npm
- nuxtjs
- nvm
- pandas
- payment
- pip
- pwa
- pyenv
- python
- recylerview
- regex
- room
- rxjava
- scoped-storage
- selenium
- social-media
- ssh
- ssl
- static-site-generator
- static-website-hosting
- sublime-text
- ubuntu
- unit-test
- uwsgi
- viewmodel
- viewpager2
- virtualbox
- vue-chartjs
- vue-cli
- vue-router
- vuejs
- vuelidate
- vuepress
- web-development
- web-hosting
- webpack
- windows
- workmanager
- wsl
- yarn