summaryrefslogtreecommitdiffhomepage
path: root/android/src/main
diff options
context:
space:
mode:
authorAleksandr Granin <aleksandr@mullvad.net>2021-03-02 17:12:55 +0100
committerAleksandr Granin <aleksandr@mullvad.net>2021-03-19 14:42:20 +0100
commit0bbffe3fb1c04c181dfc0ac8e6391e444e363ac2 (patch)
tree86960391606085a91eece73fcbd555a8c45a5bec /android/src/main
parent53cc7b6b4d002cf83091c2d2b31defef8a1076ab (diff)
downloadmullvadvpn-0bbffe3fb1c04c181dfc0ac8e6391e444e363ac2.tar.xz
mullvadvpn-0bbffe3fb1c04c181dfc0ac8e6391e444e363ac2.zip
Create ListItemAdapter
Diffstat (limited to 'android/src/main')
-rw-r--r--android/src/main/kotlin/net/mullvad/mullvadvpn/ui/ListItemsAdapter.kt105
1 files changed, 105 insertions, 0 deletions
diff --git a/android/src/main/kotlin/net/mullvad/mullvadvpn/ui/ListItemsAdapter.kt b/android/src/main/kotlin/net/mullvad/mullvadvpn/ui/ListItemsAdapter.kt
new file mode 100644
index 0000000000..b69d2b22b9
--- /dev/null
+++ b/android/src/main/kotlin/net/mullvad/mullvadvpn/ui/ListItemsAdapter.kt
@@ -0,0 +1,105 @@
+package net.mullvad.mullvadvpn.ui
+
+import android.view.ViewGroup
+import androidx.recyclerview.widget.AsyncDifferConfig
+import androidx.recyclerview.widget.AsyncListDiffer
+import androidx.recyclerview.widget.DiffUtil
+import androidx.recyclerview.widget.ListUpdateCallback
+import androidx.recyclerview.widget.RecyclerView
+import net.mullvad.mullvadvpn.model.ListItemData
+import net.mullvad.mullvadvpn.ui.listitemview.ActionListItemView
+import net.mullvad.mullvadvpn.ui.listitemview.DividerGroupListItemView
+import net.mullvad.mullvadvpn.ui.listitemview.ListItemView
+import net.mullvad.mullvadvpn.ui.listitemview.PlainListItemView
+import net.mullvad.mullvadvpn.ui.listitemview.ProgressListItemView
+import net.mullvad.mullvadvpn.ui.listitemview.TwoActionListItemView
+
+class ListItemsAdapter : RecyclerView.Adapter<ListItemsAdapter.ViewHolder>() {
+
+ var listItemListener: ListItemListener? = null
+
+ protected var diffCallback: DiffCallback = DefaultDiffCallback()
+
+ private val listDiffer: AsyncListDiffer<ListItemData> = createDiffer(diffCallback)
+
+ fun setItems(items: List<ListItemData?>) = listDiffer.submitList(items)
+
+ override fun onCreateViewHolder(parent: ViewGroup, @ListItemData.ItemType viewType: Int):
+ ListItemsAdapter.ViewHolder {
+ return ViewHolder(
+ when (viewType) {
+ ListItemData.DIVIDER -> DividerGroupListItemView(parent.context)
+ ListItemData.PROGRESS -> ProgressListItemView(parent.context)
+ ListItemData.PLAIN -> PlainListItemView(parent.context)
+ ListItemData.ACTION -> ActionListItemView(parent.context)
+ ListItemData.DOUBLE_ACTION -> TwoActionListItemView(parent.context)
+ else ->
+ throw IllegalArgumentException("View type '$viewType' is not supported")
+ }
+ )
+ }
+
+ override fun onBindViewHolder(holder: ViewHolder, position: Int) {
+ (holder.itemView as ListItemView).update(getItem(position))
+ holder.itemView.listItemListener = listItemListener
+ }
+
+ override fun onViewRecycled(holder: ViewHolder) {
+ super.onViewRecycled(holder)
+ (holder.itemView as ListItemView).listItemListener = null
+ }
+
+ override fun getItemCount(): Int = listDiffer.currentList.size
+
+ @ListItemData.ItemType
+ override fun getItemViewType(position: Int): Int = getItem(position).type
+
+ override fun getItemId(position: Int): Long = getItem(position).identifier.hashCode().toLong()
+
+ private fun getItem(position: Int): ListItemData = listDiffer.currentList[position]
+
+ private fun createDiffer(diffCallback: DiffCallback): AsyncListDiffer<ListItemData> {
+ return AsyncListDiffer(getListUpdateCallback(), getConfig(diffCallback))
+ }
+
+ private fun getConfig(diffUtil: DiffCallback): AsyncDifferConfig<ListItemData> {
+ return AsyncDifferConfig.Builder(diffUtil).build()
+ }
+
+ protected fun getListUpdateCallback(): ListUpdateCallback {
+ return object : ListUpdateCallback {
+ override fun onInserted(position: Int, count: Int) {
+ notifyItemRangeInserted(position, count)
+ }
+
+ override fun onRemoved(position: Int, count: Int) {
+ notifyItemRangeRemoved(position, count)
+ }
+
+ override fun onMoved(fromPosition: Int, toPosition: Int) {
+ notifyItemMoved(fromPosition, toPosition)
+ }
+
+ override fun onChanged(position: Int, count: Int, payload: Any?) {
+ notifyItemRangeChanged(position, count, payload)
+ }
+ }
+ }
+
+ internal class DefaultDiffCallback : DiffCallback() {
+ override fun areItemsTheSame(oldItem: ListItemData, newItem: ListItemData): Boolean {
+ return oldItem.type == newItem.type && oldItem.identifier == newItem.identifier
+ }
+
+ override fun areContentsTheSame(oldItem: ListItemData, newItem: ListItemData): Boolean {
+ return oldItem == newItem
+ }
+
+ override fun getChangePayload(oldItem: ListItemData, newItem: ListItemData): Any {
+ return Any()
+ }
+ }
+
+ inner class ViewHolder(view: ListItemView) : RecyclerView.ViewHolder(view)
+}
+typealias DiffCallback = DiffUtil.ItemCallback<ListItemData>