169 lines
4.2 KiB
Kotlin
169 lines
4.2 KiB
Kotlin
package jp.juggler.subwaytooter.dialog
|
|
|
|
import android.annotation.SuppressLint
|
|
import android.app.AlertDialog
|
|
import android.content.Intent
|
|
import android.content.pm.PackageManager
|
|
import android.content.pm.ResolveInfo
|
|
import android.graphics.drawable.Drawable
|
|
import android.os.Build
|
|
import android.view.View
|
|
import android.view.ViewGroup
|
|
import android.view.WindowManager
|
|
import android.widget.*
|
|
import android.app.Activity
|
|
import jp.juggler.subwaytooter.R
|
|
import jp.juggler.subwaytooter.util.CustomShare
|
|
import jp.juggler.subwaytooter.util.cn
|
|
import jp.juggler.util.*
|
|
|
|
class DlgAppPicker(
|
|
val activity : Activity,
|
|
val intent : Intent,
|
|
val autoSelect : Boolean = false,
|
|
val filter : (ResolveInfo) -> Boolean = { true },
|
|
val callback : (String) -> Unit
|
|
) {
|
|
|
|
companion object {
|
|
|
|
fun Char.isAlpha() = ('A' <= this && this <= 'Z') || ('a' <= this && this <= 'z')
|
|
}
|
|
|
|
class ListItem(
|
|
val icon : Drawable?,
|
|
val text : String,
|
|
val componentName : String
|
|
)
|
|
|
|
val list = ArrayList<ListItem>().apply {
|
|
|
|
val pm = activity.packageManager
|
|
val listResolveInfo = pm.queryIntentActivities(
|
|
intent,
|
|
if(Build.VERSION.SDK_INT >= 23) {
|
|
PackageManager.MATCH_ALL
|
|
} else {
|
|
0
|
|
}
|
|
)
|
|
|
|
for(it in listResolveInfo) {
|
|
if(! filter(it)) continue
|
|
val cn = "${it.activityInfo.packageName}/${it.activityInfo.name}"
|
|
add(
|
|
ListItem(
|
|
it.loadIcon(pm),
|
|
(it.loadLabel(pm)?.notEmpty() ?: cn).toString(),
|
|
cn
|
|
)
|
|
)
|
|
}
|
|
|
|
if(! autoSelect) {
|
|
val (label, icon) = CustomShare.getInfo(activity, CustomShare.CN_CLIPBOARD.cn())
|
|
add(ListItem(icon, label.toString(), CustomShare.CN_CLIPBOARD))
|
|
}
|
|
sortWith { a, b ->
|
|
val a1 = a.text.firstOrNull() ?: '\u0000'
|
|
val b1 = b.text.firstOrNull() ?: '\u0000'
|
|
when {
|
|
! a1.isAlpha() && b1.isAlpha() -> - 1
|
|
a1.isAlpha() && ! b1.isAlpha() -> 1
|
|
else -> a.text.compareTo(b.text, ignoreCase = true)
|
|
}
|
|
}
|
|
}
|
|
|
|
val dialog : AlertDialog?
|
|
|
|
init {
|
|
if(autoSelect && list.size == 1) {
|
|
callback(list.first().componentName)
|
|
dialog = null
|
|
} else {
|
|
@SuppressLint("InflateParams")
|
|
val listView : ListView =
|
|
activity.layoutInflater.inflate(R.layout.dlg_app_picker, null, false).cast() !!
|
|
val adapter = MyAdapter()
|
|
listView.adapter = adapter
|
|
listView.onItemClickListener = adapter
|
|
|
|
|
|
dialog = AlertDialog.Builder(activity)
|
|
.setView(listView)
|
|
.setNegativeButton(R.string.cancel, null)
|
|
.create()
|
|
}
|
|
}
|
|
|
|
// returns false if list is empty
|
|
@SuppressLint("InflateParams")
|
|
fun show() =
|
|
if(list.isEmpty()) {
|
|
dialog?.dismissSafe()
|
|
false
|
|
} else {
|
|
dialog?.run {
|
|
window?.setLayout(
|
|
WindowManager.LayoutParams.MATCH_PARENT,
|
|
WindowManager.LayoutParams.WRAP_CONTENT
|
|
)
|
|
this.show()
|
|
}
|
|
true
|
|
}
|
|
|
|
private inner class MyAdapter : BaseAdapter(), AdapterView.OnItemClickListener {
|
|
|
|
override fun getCount() : Int = list.size
|
|
override fun getItem(idx : Int) = list[idx]
|
|
override fun getItemId(p0 : Int) = 0L
|
|
|
|
override fun getView(idx : Int, convertView : View?, parent : ViewGroup?) : View {
|
|
val view : View
|
|
val holder : MyViewHolder
|
|
if(convertView != null) {
|
|
view = convertView
|
|
holder = view.tag?.cast() !!
|
|
} else {
|
|
view = activity.layoutInflater.inflate(R.layout.lv_app_picker, parent, false)
|
|
holder = MyViewHolder(view)
|
|
view.tag = holder
|
|
}
|
|
holder.bind(list[idx])
|
|
return view
|
|
}
|
|
|
|
override fun onItemClick(parent : AdapterView<*>?, view : View?, idx : Int, id : Long) {
|
|
dialog?.dismissSafe()
|
|
callback(list[idx].componentName)
|
|
}
|
|
}
|
|
|
|
private inner class MyViewHolder(viewRoot : View) {
|
|
|
|
val ivImage : ImageView = viewRoot.findViewById(R.id.ivImage)
|
|
val tvText : TextView = viewRoot.findViewById(R.id.tvText)
|
|
var item : ListItem? = null
|
|
|
|
fun bind(item : ListItem) {
|
|
this.item = item
|
|
if(item.icon != null) {
|
|
ivImage.setImageDrawable(item.icon)
|
|
} else {
|
|
setIconDrawableId(
|
|
activity,
|
|
ivImage,
|
|
R.drawable.ic_question,
|
|
color = activity.getAttributeColor(R.attr.colorVectorDrawable),
|
|
alphaMultiplier = 1f
|
|
)
|
|
}
|
|
tvText.text = item.text
|
|
}
|
|
}
|
|
}
|
|
|
|
|