Improve branch selection
parent
e69964d1f5
commit
6d0cd49db3
@ -0,0 +1,93 @@
|
|||||||
|
package org.koitharu.kotatsu.base.ui.dialog
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import android.content.DialogInterface
|
||||||
|
import androidx.annotation.DrawableRes
|
||||||
|
import androidx.annotation.StringRes
|
||||||
|
import androidx.appcompat.app.AlertDialog
|
||||||
|
import androidx.core.view.updatePadding
|
||||||
|
import androidx.recyclerview.widget.LinearLayoutManager
|
||||||
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
|
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
||||||
|
import com.hannesdorfmann.adapterdelegates4.AdapterDelegate
|
||||||
|
import com.hannesdorfmann.adapterdelegates4.AdapterDelegatesManager
|
||||||
|
import com.hannesdorfmann.adapterdelegates4.ListDelegationAdapter
|
||||||
|
import org.koitharu.kotatsu.R
|
||||||
|
|
||||||
|
class RecyclerViewAlertDialog private constructor(
|
||||||
|
private val delegate: AlertDialog
|
||||||
|
) : DialogInterface by delegate {
|
||||||
|
|
||||||
|
fun show() = delegate.show()
|
||||||
|
|
||||||
|
class Builder<T>(context: Context) {
|
||||||
|
|
||||||
|
private val recyclerView = RecyclerView(context)
|
||||||
|
private val delegatesManager = AdapterDelegatesManager<List<T>>()
|
||||||
|
private var items: List<T>? = null
|
||||||
|
|
||||||
|
private val delegate = MaterialAlertDialogBuilder(context)
|
||||||
|
.setView(recyclerView)
|
||||||
|
|
||||||
|
init {
|
||||||
|
recyclerView.layoutManager = LinearLayoutManager(context)
|
||||||
|
recyclerView.updatePadding(
|
||||||
|
top = context.resources.getDimensionPixelOffset(R.dimen.list_spacing),
|
||||||
|
)
|
||||||
|
recyclerView.clipToPadding = false
|
||||||
|
}
|
||||||
|
|
||||||
|
fun setTitle(@StringRes titleResId: Int): Builder<T> {
|
||||||
|
delegate.setTitle(titleResId)
|
||||||
|
return this
|
||||||
|
}
|
||||||
|
|
||||||
|
fun setTitle(title: CharSequence): Builder<T> {
|
||||||
|
delegate.setTitle(title)
|
||||||
|
return this
|
||||||
|
}
|
||||||
|
|
||||||
|
fun setIcon(@DrawableRes iconId: Int): Builder<T> {
|
||||||
|
delegate.setIcon(iconId)
|
||||||
|
return this
|
||||||
|
}
|
||||||
|
|
||||||
|
fun setPositiveButton(
|
||||||
|
@StringRes textId: Int,
|
||||||
|
listener: DialogInterface.OnClickListener,
|
||||||
|
): Builder<T> {
|
||||||
|
delegate.setPositiveButton(textId, listener)
|
||||||
|
return this
|
||||||
|
}
|
||||||
|
|
||||||
|
fun setNegativeButton(
|
||||||
|
@StringRes textId: Int,
|
||||||
|
listener: DialogInterface.OnClickListener? = null
|
||||||
|
): Builder<T> {
|
||||||
|
delegate.setNegativeButton(textId, listener)
|
||||||
|
return this
|
||||||
|
}
|
||||||
|
|
||||||
|
fun setCancelable(isCancelable: Boolean): Builder<T> {
|
||||||
|
delegate.setCancelable(isCancelable)
|
||||||
|
return this
|
||||||
|
}
|
||||||
|
|
||||||
|
fun addAdapterDelegate(subject: AdapterDelegate<List<T>>): Builder<T> {
|
||||||
|
delegatesManager.addDelegate(subject)
|
||||||
|
return this
|
||||||
|
}
|
||||||
|
|
||||||
|
fun setItems(list: List<T>): Builder<T> {
|
||||||
|
items = list
|
||||||
|
return this
|
||||||
|
}
|
||||||
|
|
||||||
|
fun create(): RecyclerViewAlertDialog {
|
||||||
|
recyclerView.adapter = ListDelegationAdapter(delegatesManager).also {
|
||||||
|
it.items = items
|
||||||
|
}
|
||||||
|
return RecyclerViewAlertDialog(delegate.create())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -1,6 +1,8 @@
|
|||||||
package org.koitharu.kotatsu.details.domain
|
package org.koitharu.kotatsu.details.domain
|
||||||
|
|
||||||
class BranchComparator : Comparator<String?> {
|
import org.koitharu.kotatsu.details.ui.model.MangaBranch
|
||||||
|
|
||||||
override fun compare(o1: String?, o2: String?): Int = compareValues(o1, o2)
|
class BranchComparator : Comparator<MangaBranch> {
|
||||||
|
|
||||||
|
override fun compare(o1: MangaBranch, o2: MangaBranch): Int = compareValues(o1.name, o2.name)
|
||||||
}
|
}
|
||||||
@ -0,0 +1,39 @@
|
|||||||
|
package org.koitharu.kotatsu.details.ui.adapter
|
||||||
|
|
||||||
|
import android.graphics.Color
|
||||||
|
import android.text.Spannable
|
||||||
|
import android.text.style.ForegroundColorSpan
|
||||||
|
import android.text.style.RelativeSizeSpan
|
||||||
|
import androidx.core.text.buildSpannedString
|
||||||
|
import com.hannesdorfmann.adapterdelegates4.dsl.adapterDelegateViewBinding
|
||||||
|
import org.koitharu.kotatsu.R
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.AdapterDelegateClickListenerAdapter
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.OnListItemClickListener
|
||||||
|
import org.koitharu.kotatsu.databinding.ItemCheckableNewBinding
|
||||||
|
import org.koitharu.kotatsu.details.ui.model.MangaBranch
|
||||||
|
import org.koitharu.kotatsu.utils.ext.getThemeColor
|
||||||
|
|
||||||
|
fun branchAD(
|
||||||
|
clickListener: OnListItemClickListener<MangaBranch>,
|
||||||
|
) = adapterDelegateViewBinding<MangaBranch, MangaBranch, ItemCheckableNewBinding>(
|
||||||
|
{ inflater, parent -> ItemCheckableNewBinding.inflate(inflater, parent, false) },
|
||||||
|
) {
|
||||||
|
|
||||||
|
val clickAdapter = AdapterDelegateClickListenerAdapter(this, clickListener)
|
||||||
|
itemView.setOnClickListener(clickAdapter)
|
||||||
|
val counterColorSpan = ForegroundColorSpan(context.getThemeColor(android.R.attr.textColorSecondary, Color.LTGRAY))
|
||||||
|
val counterSizeSpan = RelativeSizeSpan(0.86f)
|
||||||
|
|
||||||
|
bind {
|
||||||
|
binding.root.text = buildSpannedString {
|
||||||
|
append(item.name ?: getString(R.string.system_default))
|
||||||
|
append(' ')
|
||||||
|
append(' ')
|
||||||
|
val start = length
|
||||||
|
append(item.count.toString())
|
||||||
|
setSpan(counterColorSpan, start, length, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE)
|
||||||
|
setSpan(counterSizeSpan, start, length, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE)
|
||||||
|
}
|
||||||
|
binding.root.isChecked = item.isSelected
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -1,45 +1,16 @@
|
|||||||
package org.koitharu.kotatsu.details.ui.adapter
|
package org.koitharu.kotatsu.details.ui.adapter
|
||||||
|
|
||||||
import android.view.LayoutInflater
|
import com.hannesdorfmann.adapterdelegates4.ListDelegationAdapter
|
||||||
import android.view.View
|
import org.koitharu.kotatsu.base.ui.list.OnListItemClickListener
|
||||||
import android.view.ViewGroup
|
import org.koitharu.kotatsu.details.ui.model.MangaBranch
|
||||||
import android.widget.BaseAdapter
|
|
||||||
import android.widget.TextView
|
class BranchesAdapter(
|
||||||
import org.koitharu.kotatsu.R
|
list: List<MangaBranch>,
|
||||||
import org.koitharu.kotatsu.parsers.util.replaceWith
|
listener: OnListItemClickListener<MangaBranch>,
|
||||||
|
) : ListDelegationAdapter<List<MangaBranch>>() {
|
||||||
class BranchesAdapter : BaseAdapter() {
|
|
||||||
|
init {
|
||||||
private val dataSet = ArrayList<String?>()
|
delegatesManager.addDelegate(branchAD(listener))
|
||||||
|
items = list
|
||||||
override fun getCount(): Int {
|
|
||||||
return dataSet.size
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun getItem(position: Int): Any? {
|
|
||||||
return dataSet[position]
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun getItemId(position: Int): Long {
|
|
||||||
return dataSet[position].hashCode().toLong()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun getView(position: Int, convertView: View?, parent: ViewGroup): View {
|
|
||||||
val view = convertView ?: LayoutInflater.from(parent.context)
|
|
||||||
.inflate(R.layout.item_branch, parent, false)
|
|
||||||
(view as TextView).text = dataSet[position]
|
|
||||||
return view
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun getDropDownView(position: Int, convertView: View?, parent: ViewGroup): View {
|
|
||||||
val view = convertView ?: LayoutInflater.from(parent.context)
|
|
||||||
.inflate(R.layout.item_branch_dropdown, parent, false)
|
|
||||||
(view as TextView).text = dataSet[position]
|
|
||||||
return view
|
|
||||||
}
|
|
||||||
|
|
||||||
fun setItems(items: Collection<String?>) {
|
|
||||||
dataSet.replaceWith(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -0,0 +1,32 @@
|
|||||||
|
package org.koitharu.kotatsu.details.ui.model
|
||||||
|
|
||||||
|
import org.koitharu.kotatsu.list.ui.model.ListModel
|
||||||
|
|
||||||
|
class MangaBranch(
|
||||||
|
val name: String?,
|
||||||
|
val count: Int,
|
||||||
|
val isSelected: Boolean,
|
||||||
|
) : ListModel {
|
||||||
|
|
||||||
|
override fun equals(other: Any?): Boolean {
|
||||||
|
if (this === other) return true
|
||||||
|
if (javaClass != other?.javaClass) return false
|
||||||
|
|
||||||
|
other as MangaBranch
|
||||||
|
|
||||||
|
if (name != other.name) return false
|
||||||
|
if (count != other.count) return false
|
||||||
|
return isSelected == other.isSelected
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun hashCode(): Int {
|
||||||
|
var result = name.hashCode()
|
||||||
|
result = 31 * result + count
|
||||||
|
result = 31 * result + isSelected.hashCode()
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun toString(): String {
|
||||||
|
return "$name: $count"
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -1,22 +0,0 @@
|
|||||||
package org.koitharu.kotatsu.utils
|
|
||||||
|
|
||||||
import android.graphics.drawable.Drawable
|
|
||||||
import androidx.preference.Preference
|
|
||||||
import coil.target.Target
|
|
||||||
|
|
||||||
class PreferenceIconTarget(
|
|
||||||
private val preference: Preference,
|
|
||||||
) : Target {
|
|
||||||
|
|
||||||
override fun onError(error: Drawable?) {
|
|
||||||
preference.icon = error
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onStart(placeholder: Drawable?) {
|
|
||||||
preference.icon = placeholder
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onSuccess(result: Drawable) {
|
|
||||||
preference.icon = result
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@ -1,9 +0,0 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<CheckedTextView
|
|
||||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
|
||||||
style="?android:attr/spinnerItemStyle"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="?android:attr/listPreferredItemHeightSmall"
|
|
||||||
android:gravity="center_vertical"
|
|
||||||
android:singleLine="true"
|
|
||||||
android:textAppearance="?attr/textAppearanceBodyLarge" />
|
|
||||||
@ -1,11 +0,0 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<CheckedTextView
|
|
||||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
|
||||||
xmlns:tools="http://schemas.android.com/tools"
|
|
||||||
style="?android:attr/spinnerDropDownItemStyle"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="?android:attr/listPreferredItemHeightSmall"
|
|
||||||
android:drawableEnd="?android:listChoiceIndicatorSingle"
|
|
||||||
android:singleLine="true"
|
|
||||||
android:textAppearance="?attr/textAppearanceBodyLarge"
|
|
||||||
tools:text="Scanlator" />
|
|
||||||
Loading…
Reference in New Issue