【问题标题】:AutoCompleteTextView dropdown height not wrapping to contentAutoCompleteTextView 下拉高度不包装到内容
【发布时间】:2023-02-01 09:02:39
【问题描述】:

我的应用程序有一个 AutoCompleteTextView,它查询 Room 数据库并在用户键入时在下拉列表中显示搜索结果。 结果显示正确,但下拉列表的高度对于项目数量来说总是太大(请参见下面的屏幕截图)。

基本上,AutoCompleteTextView 有一个 TextWatcher,它将当前文本发送到 ViewModel,ViewModel 反过来查询数据库。收到结果后,ViewModel 会更新视图状态(Flow),观察它的片段会使用新数据重新分配 AutoCompleteTextView 的适配器。

下拉项布局

<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/root"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:padding="@dimen/spacing_8">

    <GridLayout
        android:id="@+id/imageContainer"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        ... />

    <com.google.android.material.textview.MaterialTextView
        android:id="@+id/txtName"
        style="@style/TextAppearance.MaterialComponents.Body1"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        ... />
</androidx.constraintlayout.widget.ConstraintLayout>

片段布局

<com.google.android.material.textfield.TextInputLayout>
    ...
    <com.google.android.material.textfield.MaterialAutoCompleteTextView
        android:id="@+id/autoCompleteTextView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:padding="@dimen/spacing_16"/>
</com.google.android.material.textfield.TextInputLayout>

适配器

internal class StationAdapter(
    context: Context,
    private val stations: List<UiStation>
) : ArrayAdapter<String>(
    context,
    R.layout.item_station,
    stations.map { it.name }
) {

    fun getStation(position: Int): UiStation = stations[position]

    override fun getCount(): Int = stations.size

    override fun getItem(position: Int): String = stations[position].name

    override fun getView(position: Int, convertView: View?, parent: ViewGroup): View {
        return convertView ?: run {
            val inflater = LayoutInflater.from(context)
            val binding = ItemStationBinding.inflate(inflater, parent, false).apply {
                val station = stations[position]
                imageContainer.addIconsForModes(station.modes)
                txtName.text = station.name
            }

            binding.root
        }
    }

    ...
}

分段

private fun handleState(state: StationSearchViewState) = with(state) {
    ...

    stations?.let {
        val adapter = StationAdapter(
            context = requireContext(),
            stations = it
        )
        binding.autoCompleteTextView.setAdapter(adapter)
    }
}

现在这些是我也尝试过但没有用的其他东西(得到相同的结果):

  1. 将所有数据库表的结果传递给适配器并实施自定义过滤器
  2. 实现向适配器提交新数据的功能并调用notifyDataSetChanged()
  3. 将 AutoCompleteTextView 的 android:dropDownHeight 属性设置为 wrap_content

    唯一似乎有效的是当我使用 ArrayAdapterandroid.R.layout.simple_list_item_1 布局时

【问题讨论】:

  • 找到任何解决方案?

标签: android layout dropdown autocompletetextview


【解决方案1】:

经过 3 天的努力解决这个问题,我终于找到了一个解决方案,部分在this answer to an unrelated question

这是我的代码:

private const val DROPDOWN_ITEM_MAX_COUNT = 5
private const val PADDING = 34

class CustomAutoCompleteTextView(
    context: Context,
    attributeSet: AttributeSet?
) : MaterialAutoCompleteTextView(context, attributeSet) {

    override fun onFilterComplete(count: Int) {
        val itemCount = if (count > DROPDOWN_ITEM_MAX_COUNT) {
            DROPDOWN_ITEM_MAX_COUNT
        } else {
            count
        }
        val individualItemHeight = (height / 2) + PADDING

        dropDownHeight = itemCount * individualItemHeight
        super.onFilterComplete(count)
    }
}

本质上,我必须创建一个自定义的AutoCompleteTextView,一旦数据被过滤,它就会获取一个项目计数(不大于我设置的最大值)并将其乘以我的下拉列表中单个项目的高度(a)加上填充 (b) 以确保下拉视图始终包裹项目。

a:我通过反复试验达到了这个值,但它仍然适用于不同的屏幕尺寸和密度

b:不是强制性的。我只是想添加一点填充让它看起来更好

最终结果

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2020-09-06
    • 1970-01-01
    • 2015-10-26
    • 1970-01-01
    • 2020-12-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多