LiveData
LiveData
는 액티비티나 프래그먼트의Lifecycle
을 고려한 옵저버 패턴을 이용해 구현된 데이터 홀더 클래스이다.- 액티비티나 프래그먼트의 생명주기인
STARTED
,RESUMED
상태에서만 데이터의 변경사항을 관찰자에게 알려주며, 그 외의 상태에서는 변경사항을 알리지 않는다.- 즉, Active 상태에서만 변경사항을 관찰자에게 알려준다.
액티비티나 프래그먼트에서
LiveData
를observe
메소드를 이용해 관찰한다.- 대체로 LiveData는
ViewModel
에서 자주 사용된다.- 화면 회전과 같은 변경사항이 발생했을 경우 액티비티는 Destory 됐다가 다시 Create되는데 이때 UI를 다시 그리게 되어 이전에 작성된 사항들이 사라지기 때문에 ViewModel 객체에서 UI의 데이터(텍스트 뷰 내용 등)를 관리한다.
- 액티비티나 프래그먼트에서 LiveData를 observe하고 있고 비활성 상태(홈버튼을 눌러 화면을 나갔을 때 등)에서 활성 상태로 변경될 때 LiveData의 최신 데이터값을 가져와 UI에 표현한다.
- 액티비티나 프래그먼트의 생명주기를 따르므로 화면이 Destory될 때 LiveData를 관찰하는 관찰자를 제거해주게 되어 메모리 누수에 대한 부작용을 제거할 수 있다.
예제 1
- class를 이용한 LiveData 예제
activity_main.xml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
<?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">
<EditText
android:id="@+id/username_edittext"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:gravity="center"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent"
tools:text="가나다" />
<Button
android:id="@+id/add_user_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="추가"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/username_edittext" />
</androidx.constraintlayout.widget.ConstraintLayout>
MainActivity.kt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.util.Log
import android.widget.Button
import android.widget.EditText
import androidx.fragment.app.Fragment
import androidx.lifecycle.LiveData
import androidx.lifecycle.MutableLiveData
import androidx.lifecycle.Observer
const val TAG = "MainActivity"
class MainActivity : AppCompatActivity() {
private lateinit var usernameEditText: EditText
private lateinit var addUserButton: Button
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val userList = UserList()
usernameEditText = findViewById(R.id.username_edittext)
addUserButton = findViewById<Button?>(R.id.add_user_button).apply {
setOnClickListener {
userList.addUser(usernameEditText.text.toString())
}
}
userList.userList.observe(this, Observer { users ->
Log.d(TAG, "================================")
users.forEach { user ->
Log.d(TAG, "user info : $user")
}
Log.d(TAG, "================================")
})
}
}
data class User(val username: String)
class UserList {
private val totalUserList = mutableListOf<User>()
private var _userList = MutableLiveData<List<User>>()
val userList: LiveData<List<User>>
get() = _userList
fun addUser(username: String) {
totalUserList.add(User(username))
_userList.value = totalUserList
}
}
예제 2
- ViewModel과 LiveData를 이용한 예제
- 예제 1과 동일한 xml
UserListViewModel.kt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import androidx.lifecycle.LiveData
import androidx.lifecycle.MutableLiveData
import androidx.lifecycle.ViewModel
class UserListViewModel : ViewModel() {
private val totalUserList = mutableListOf<User>()
private var _userList = MutableLiveData<List<User>>()
val userList: LiveData<List<User>>
get() = _userList
fun addUser(username: String) {
totalUserList.add(User(username))
_userList.value = totalUserList
}
}
data class User(val username: String)
MainActivity.kt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.util.Log
import android.widget.Button
import android.widget.EditText
import androidx.lifecycle.Observer
import androidx.lifecycle.ViewModelProvider
const val TAG = "MainActivity"
class MainActivity : AppCompatActivity() {
private lateinit var usernameEditText: EditText
private lateinit var addUserButton: Button
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val userListViewModel = ViewModelProvider(this).get(UserListViewModel::class.java)
usernameEditText = findViewById(R.id.username_edittext)
addUserButton = findViewById<Button>(R.id.add_user_button).apply {
setOnClickListener {
userListViewModel.addUser(usernameEditText.text.toString())
}
}
userListViewModel.userList.observe(this, Observer { users ->
Log.d(TAG, "================================")
users.forEach { user ->
Log.d(TAG, "user info : $user")
}
Log.d(TAG, "================================")
})
}
}
Comments powered by Disqus.