• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /**
2  * Copyright (C) 2022 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
5  * in compliance with the License. You may obtain a copy of the License at
6  *
7  *      http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software distributed under the License
10  * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
11  * or implied. See the License for the specific language governing permissions and limitations under
12  * the License.
13  */
14 package com.android.healthconnect.controller.shared.recyclerview
15 
16 import android.view.View
17 import android.view.ViewGroup
18 import androidx.recyclerview.widget.RecyclerView
19 
20 /**
21  * {@link RecyclerView.Adapter} that handles binding objects of different classes to a corresponding
22  * {@link View}.
23  */
24 class RecyclerViewAdapter
25 private constructor(
26     private val itemClassToItemViewTypeMap: Map<Class<*>, Int>,
27     private val itemViewTypeToViewBinderMap: Map<Int, ViewBinder<*, out View>>
28 ) : RecyclerView.Adapter<RecyclerViewAdapter.ViewHolder>() {
29 
30     class Builder {
31         companion object {
32             // Base item view type to use when setting a view binder for objects of a specific class
33             private const val BASE_ITEM_VIEW_TYPE = 100
34         }
35 
36         private var nextItemType = BASE_ITEM_VIEW_TYPE
37         private val itemClassToItemViewTypeMap: MutableMap<Class<*>, Int> = mutableMapOf()
38         private val itemViewTypeToViewBinderMap: MutableMap<Int, ViewBinder<*, out View>> =
39             mutableMapOf()
40 
setViewBindernull41         fun <T> setViewBinder(clazz: Class<T>, viewBinder: ViewBinder<T, out View>): Builder {
42             itemClassToItemViewTypeMap[clazz] = nextItemType
43             itemViewTypeToViewBinderMap[nextItemType] = viewBinder
44             nextItemType++
45             return this
46         }
47 
buildnull48         fun build() = RecyclerViewAdapter(itemClassToItemViewTypeMap, itemViewTypeToViewBinderMap)
49     }
50 
51     class ViewHolder(view: View) : RecyclerView.ViewHolder(view)
52 
53     private var data: List<Any> = emptyList()
54 
55     fun updateData(entries: List<Any>) {
56         this.data = entries
57         notifyDataSetChanged()
58     }
59 
onCreateViewHoldernull60     override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
61         val viewBinder = checkNotNull(itemViewTypeToViewBinderMap[viewType])
62         return ViewHolder(viewBinder.newView(parent))
63     }
64 
onBindViewHoldernull65     override fun onBindViewHolder(holder: ViewHolder, position: Int) {
66         val viewBinder: ViewBinder<Any, View> =
67             checkNotNull(itemViewTypeToViewBinderMap[getItemViewType(position)])
68                 as ViewBinder<Any, View>
69         val item = data[position]
70         viewBinder.bind(holder.itemView, item, position)
71     }
72 
getItemViewTypenull73     override fun getItemViewType(position: Int): Int {
74         val clazz = data[position].javaClass
75         return checkNotNull(itemClassToItemViewTypeMap[clazz])
76     }
77 
getItemCountnull78     override fun getItemCount(): Int {
79         return data.size
80     }
81 }
82