Notice
Recent Posts
Recent Comments
Link
«   2025/06   »
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
Archives
Today
Total
관리 메뉴

일기장

Android MVVM, RecyclerView + Livedata + databinding (Kotlin) 본문

카테고리 없음

Android MVVM, RecyclerView + Livedata + databinding (Kotlin)

Hemulen 2020. 7. 5. 14:15

1. app gradle에 databinding 추가

    buildFeatures{
        dataBinding = true
    }

 

2. 기본적인 ViewModel과 Data Class 작성

class MainViewModel: ViewModel() {
    private val _postList = ListLiveData<PostModel>()
    
    val postList: LiveData<ArrayList<PostModel>>
    get() = _postList
    
    …
}

 

data class PostModel (
    val postId: String
)

 

3. RecyclerView에 databinding (posts 속성은 아래 BindingAdapter로 추가)

<androidx.recyclerview.widget.RecyclerView
  android:id="@+id/post_list"
  …
  posts="@{vm.postList}"
  …
  />

 

4. RecyclerView에 사용될 Item xml 작성

<layout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto">

    <data>
        <variable
            name="postItem"
            type="com.example.test.api.model.PostModel" />
    </data>

    …
    
</layout>

 

5. Binding된 변수의 변화를 RecyclerViewAdapter에게 알리는 Custom Binding Adapter 작성

@JvmStatic
    @BindingAdapter("posts")
    fun setBindPost(view: RecyclerView, posts: LiveData<ArrayList<PostModel>>) {
        view.adapter?.run {
            if(this is PostListAdapter) {
                posts.value?.let { this.posts = it } ?: { this.posts = arrayListOf() }()
                this.notifyDataSetChanged()
            }
        }
    }
    
    …

 

6. RecyclerViewAdapter 작성

class PostListAdapter(val vm: MainViewModel): RecyclerView.Adapter<PostListAdapter.PostHolder>() {
    var posts = ArrayList<PostModel>()
        set(value) {
            posts.clear()
            posts.addAll(value)
        }

    inner class PostHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
        private val binding: PostItemBinding? = DataBindingUtil.bind(itemView)

        fun bind(item: PostModel) {
            binding?.setVariable(BR.postItem, item)

            // post item click listener
            itemView.setOnClickListener {
                vm.onPostClick(item)
            }
        }
    }

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = PostHolder(
        LayoutInflater.from(parent.context).inflate(
            R.layout.post_item,
            parent,
            false
        )
    )

    override fun getItemCount() = posts.size

    override fun onBindViewHolder(holder: PostHolder, position: Int) {
        holder.bind(posts[position])
    }

}

 

7. Activity혹은 Fragment에서 Adapter 선언

val mViewModel: MainViewModel by activityViewModels()
post_list.adapter = PostListAdapter(mViewModel)
…