gpt4 book ai didi

android - 如何让工具栏中只有操作项,并尽可能多地使用它的空间?

转载 作者:行者123 更新时间:2023-11-29 18:26:19 24 4
gpt4 key购买 nike

背景

我正在尝试让工具栏只显示操作项。无题。我希望它们尽可能多地填充空间,如果没有空间容纳一些空间,请将它们放在溢出菜单项上。

这可以包括所有类型的操作项(包括具有自定义操作 View 的操作项)。

问题

出于某种原因,即使我在工具栏上设置了所有填充/间距,即使我为每个操作项设置了 SHOW_AS_ACTION_IF_ROOM,它也不会发生。

它最多显示大约 2 个项目,即使还有很多剩余空间:

enter image description here

我尝试过的

我尝试为工具栏设置各种填充/间距重置:

    <androidx.appcompat.widget.Toolbar
android:id="@+id/toolbar" android:layout_width="match_parent" android:layout_height="?attr/actionBarSize"
android:padding="0px" app:contentInsetEnd="0px" app:contentInsetEndWithActions="0px" app:contentInsetLeft="0px"
app:contentInsetRight="0px" app:contentInsetStart="0px" app:contentInsetStartWithNavigation="0px"
app:layout_constraintEnd_toEndOf="parent" app:logo="@null" app:title="@null" app:titleMargin="0px"
tools:background="#ffcc0000" />

为了测试它,我使用了:

        for (i in 0..10) 
toolbar.menu.add("item $i").setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM)

遗憾的是,正如我所说,这没有帮助。

我还尝试使用 ActionMenuView 而不是 Toolbar 编写一些代码,但是它有太多只能从库中调用并依赖于它的函数。我找不到使它看起来与工具栏相似的方法,并且在某些情况下它还有一些奇怪的点击效果问题。

问题

只要有足够的空间,我如何设置工具栏让所有项目自行查看,如果有些放不下,让它们出现在溢出菜单中?

有没有办法覆盖工具栏的行为?这种行为甚至写在哪里?

最佳答案

好的,我有办法解决它,但它有一些重要的注释和假设。我认为通过一些调整,它也可以解决我过去问过的类似问题 to have the action items on the left 。全部写在这里的代码中:

ToolbarAdjuster.kt

object ToolbarAdjuster {
/**
* a special behavior for Toolbar, to put all of its menu items that can fit - to actually fit, and the rest to be in overflow menu
* Important notes and assumptions:
* 1. You should call it each time you reset the menu items
* 2. Toolbar has a size. You can use in `onCreateOptionsMenu` if it's the actionBar, or `doOnPreDraw` otherwise.
* 3. Only action items that have actionView can be on the toolbar. The rest should always be in the overflow menu
* 4. Toolbar should consist only of action items. No spacing, no padding, no title, ... Otherwise the calculation will be incorrect.
* Meaning:
* android:padding="0px" app:contentInsetEnd="0px" app:contentInsetEndWithActions="0px" app:contentInsetLeft="0px"
* app:contentInsetRight="0px" app:contentInsetStart="0px" app:contentInsetStartWithNavigation="0px"
* app:layout_constraintEnd_toEndOf="parent" app:logo="@null" app:title="@null" app:titleMargin="0px"
*/
fun adjustToolbar(context: Context, toolbar: Toolbar, menu: Menu) {
val toolbarWidth = toolbar.width
val indexToWidthMap = HashMap<Int, Int>()
val menuItemsCount = menu.size
var sizeSoFar = 0
var foundNeedForOverflowItem = false
//first find if we will need an overflow menu item:
for (i in 0 until menuItemsCount) {
val menuItem = menu[i]
val menuItemView = menuItem.actionView
if (!menuItem.isVisible)
continue
if (menuItemView == null) {
foundNeedForOverflowItem = true
continue
}
menuItemView.measure(View.MeasureSpec.UNSPECIFIED, View.MeasureSpec.UNSPECIFIED)
val menuItemViewWidth = menuItemView.measuredWidth
indexToWidthMap[i] = menuItemViewWidth
if (menuItemViewWidth + sizeSoFar > toolbarWidth) {
foundNeedForOverflowItem = true
break
}
sizeSoFar += menuItemViewWidth
}
//now we know if we need an overflow menu or not, so go over again, and set each menu item to how it will be shown
var spaceLeft = if (foundNeedForOverflowItem) toolbarWidth - getDefaultOverflowWidth(context) else toolbarWidth
for (i in 0 until menuItemsCount) {
val menuItem = menu[i]
val menuItemView = menuItem.actionView
if (!menuItem.isVisible)
continue
if (menuItemView == null || spaceLeft <= 0) {
menuItem.setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER)
continue
}
val measuredAItemViewWidth = indexToWidthMap[i]!!
if (spaceLeft - measuredAItemViewWidth < 0) {
//this item's view can't fit into the space we have left, so none of the next ones will fit
spaceLeft = 0
menuItem.setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER)
} else {
//this item's view can still fit
spaceLeft -= measuredAItemViewWidth
menuItem.setShowAsAction(MenuItem.SHOW_AS_ACTION_ALWAYS)
}
}
}

private fun getDefaultOverflowWidth(context: Context): Int {
val overflowMenuButton = OverflowMenuButton(context)
overflowMenuButton.measure(View.MeasureSpec.UNSPECIFIED, View.MeasureSpec.UNSPECIFIED)
val overflowCellSize = overflowMenuButton.measuredWidth
return if (overflowCellSize > 0) overflowCellSize else TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 40f, context.resources.displayMetrics).toInt()
}

/**fake view, copied from ActionMenuPresenter, which is used only to get its width*/
private class OverflowMenuButton @JvmOverloads constructor(context: Context, attrs: AttributeSet? = null, defStyleAttr: Int = R.attr.actionOverflowButtonStyle) : AppCompatImageView(context, attrs, defStyleAttr)
}

示例用法:

MainActivity.kt

class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
title = null
setSupportActionBar(toolbar)
}

override fun onCreateOptionsMenu(menu: Menu): Boolean {
for (i in 0..10) {
val actionView = LayoutInflater.from(this).inflate(R.layout.action_item, toolbar, false)
actionView.textView.text = "item $i"
menu.add("item $i").setActionView(actionView).setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM)
}
for (i in 0..10)
menu.add("item $i").setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM)
ToolbarAdjuster.adjustToolbar(this, toolbar, menu)
return super.onCreateOptionsMenu(menu)
}

}

action_item.xml

<androidx.appcompat.widget.AppCompatTextView
android:id="@+id/textView" xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools" android:layout_width="wrap_content" android:layout_height="match_parent"
android:background="?attr/selectableItemBackground" android:clickable="true" android:drawableLeft="@android:drawable/ic_dialog_email"
android:drawablePadding="8dp" android:focusable="true" android:focusableInTouchMode="false"
android:gravity="center_vertical|start" android:paddingLeft="15dp" android:paddingRight="15dp"
android:text="text" tools:background="#11ff0000"
tools:layout_gravity="center" tools:layout_height="?attr/actionBarSize" />

activity_main.xml

<FrameLayout
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:layout_width="match_parent"
android:layout_height="match_parent" tools:context=".MainActivity">

<androidx.appcompat.widget.Toolbar
android:id="@+id/toolbar" android:layout_width="match_parent" android:layout_height="?attr/actionBarSize"
android:padding="0px" app:contentInsetEnd="0px" app:contentInsetEndWithActions="0px" app:contentInsetLeft="0px"
app:contentInsetRight="0px" app:contentInsetStart="0px" app:contentInsetStartWithNavigation="0px"
app:layout_constraintEnd_toEndOf="parent" app:logo="@null" app:title="@null" app:titleMargin="0px"
tools:background="#ffcc0000" />

</FrameLayout>

结果如下:

enter image description here

关于android - 如何让工具栏中只有操作项,并尽可能多地使用它的空间?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58838220/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com