Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/207.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
以编程方式更改Android溢出菜单图标_Android_Android Actionbar - Fatal编程技术网

以编程方式更改Android溢出菜单图标

以编程方式更改Android溢出菜单图标,android,android-actionbar,Android,Android Actionbar,我一直在寻找一种方法,以编程方式更改android中溢出菜单图标的颜色 我找到的唯一选择是通过添加自定义样式永久更改图标。 问题是,在不久的将来,我们需要在使用我们的应用程序时改变这一点 我们的应用程序是一系列在线平台的扩展,因此用户可以输入其平台的web url。它们有自己的风格,将通过对应用程序的API调用获取 这些可能要求我更改图标的颜色 目前,我更改了Actionbar中的其他图标,如下所示: if (ib != null){ Drawable resIcon =

我一直在寻找一种方法,以编程方式更改android中溢出菜单图标的颜色

我找到的唯一选择是通过添加自定义样式永久更改图标。 问题是,在不久的将来,我们需要在使用我们的应用程序时改变这一点

我们的应用程序是一系列在线平台的扩展,因此用户可以输入其平台的web url。它们有自己的风格,将通过对应用程序的API调用获取

这些可能要求我更改图标的颜色

目前,我更改了Actionbar中的其他图标,如下所示:

if (ib != null){
            Drawable resIcon = getResources().getDrawable(R.drawable.navigation_refresh);
            resIcon.mutate().setColorFilter(StyleClass.getColor("color_navigation_icon_overlay"), PorterDuff.Mode.SRC_ATOP);
            ib.setIcon(resIcon);
}

现在我必须使用样式。

实际上,您可以使用一个小技巧以编程方式更改溢出图标。下面是一个例子:

为溢出菜单创建样式并传入内容描述

<style name="Widget.ActionButton.Overflow" parent="@android:style/Widget.Holo.ActionButton.Overflow">
    <item name="android:contentDescription">@string/accessibility_overflow</item>
</style>

<style name="Your.Theme" parent="@android:style/Theme.Holo.Light.DarkActionBar">
    <item name="android:actionOverflowButtonStyle">@style/Widget.ActionButton.Overflow</item>
</style>
View.findViewsWithText
是在API级别14中添加的,因此您必须使用自己的兼容方法:

static void findViewsWithText(List<View> outViews, ViewGroup parent, String targetDescription) {
    if (parent == null || TextUtils.isEmpty(targetDescription)) {
        return;
    }
    final int count = parent.getChildCount();
    for (int i = 0; i < count; i++) {
        final View child = parent.getChildAt(i);
        final CharSequence desc = child.getContentDescription();
        if (!TextUtils.isEmpty(desc) && targetDescription.equals(desc.toString())) {
            outViews.add(child);
        } else if (child instanceof ViewGroup && child.getVisibility() == View.VISIBLE) {
            findViewsWithText(outViews, (ViewGroup) child, targetDescription);
        }
    }
}
static void findViewWithText(列表视图、视图组父视图、字符串targetDescription){
if(parent==null | | TextUtils.isEmpty(targetDescription)){
返回;
}
final int count=parent.getChildCount();
for(int i=0;i
结果


阿德尼尔的答案很好,我一直在使用它,直到最近。但后来我想让我的应用程序利用材料设计,从而
Theme.AppCompat.*
style和
android.support.v7.widget.Toolbar

是的,它停止工作了,我试图通过将.Theme
的父项设置为
@style/Widget.AppCompat.ActionButton.Overflow来修复它。它通过属性设置
contentDescription
工作,但在转换到
ImageButton
时失败。在最新的android.support.v7版本中,是从
AppCompatImageView
扩展而来的。改变铸造类足以使它与运行棒棒糖的Nexus5工具栏一起工作

然后我用KitKat在Galaxy S4上运行了它,无论我做了什么尝试,我都无法将overflow的
contentDescription
设置为我的自定义值。但在中,我发现它已经具有默认值:

<item name="android:contentDescription">@string/abc_action_menu_overflow_description</item>
并根据:

public static void removeOnGlobalLayoutListener(视图v,ViewTreeObserver.OnGlobalLayoutListener){
if(Build.VERSION.SDK\u INT
当然,您可以使用自己的颜色,而不是
Color.CYAN
activity.getResources().getColor(R.Color.black)

编辑: 添加了对最新AppCompat库(23)的支持,该库使用AppCompatImageView
对于AppCompat 22,您应该将溢出按钮强制转换为TintImageView

基于@michalbrz answer,我使用下面的更改图标本身:

public静态无效setOverflowButtonColor(最终活动){
最终字符串溢出描述=activity.getString(R.String.abc\u action\u menu\u overflow\u description);
最终视图组decorView=(视图组)activity.getWindow().getDecorView();
final ViewTreeObserver ViewTreeObserver=decorView.getViewTreeObserver();
viewTreeObserver.addOnGlobalLayoutListener(新viewTreeObserver.OnGlobalLayoutListener(){
@凌驾
公共图书馆{
最终ArrayList OutView=新ArrayList();
decorView.FindView WithText(OutView、overflowDescription、,
查看。查找带有内容描述的视图);
if(outview.isEmpty()){
返回;
}
TintImageView溢出=(TintImageView)outViews.get(0);
//overflow.setColorFilter(Color.CYAN);//更改颜色
溢出.setImageResource(R.drawable.dots);
移除LobalLayoutListener(decorView,本);
}
});

使用appcompat-v7:23.0.1没有一个@adneal或@michalbrz对我有效。我必须更改@michalbrz答案的两行代码才能使其生效。

我添加了一个答案,因为当前的两个答案对某人都很有用,但是如果您使用的是像我一样的最新appcompat版本,那么您应该使用基于@michalbrz:

private static void setOverflowButtonColor(final AppCompatActivity activity, final PorterDuffColorFilter colorFilter) {
    final String overflowDescription = activity.getString(R.string.abc_action_menu_overflow_description);
    final ViewGroup decorView = (ViewGroup) activity.getWindow().getDecorView();
    final ViewTreeObserver viewTreeObserver = decorView.getViewTreeObserver();
    viewTreeObserver.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
        @Override
        public void onGlobalLayout() {
            final ArrayList<View> outViews = new ArrayList<>();
            decorView.findViewsWithText(outViews, overflowDescription,
                    View.FIND_VIEWS_WITH_CONTENT_DESCRIPTION);
            if (outViews.isEmpty()) {
                return;
            }
            ActionMenuItemView overflow = (ActionMenuItemView)outViews.get(0);
            overflow.getCompoundDrawables()[0].setColorFilter(colorFilter);
            removeOnGlobalLayoutListener(decorView,this);
        }
    });
}

因此,在
ActionMenuItemView
的代码中挖掘了一点之后,我发现了如何获得图标的可绘制性(查看
setIcon()
),然后我将强制转换更改为
ActionMenuItemView
,对从
getCompoundDrawables()获得的左侧可绘制性应用颜色过滤器
瞧!它工作了!

从支持23.1开始,工具栏现在有了新的工具和方法,因此我们可以更轻松地完成这项工作:

public static void setOverflowButtonColor(final Toolbar toolbar, final int color) {
    Drawable drawable = toolbar.getOverflowIcon();
    if(drawable != null) {
        drawable = DrawableCompat.wrap(drawable);
        DrawableCompat.setTint(drawable.mutate(), color);
        toolbar.setOverflowIcon(drawable);
    }
}

对于更改溢出图标,有一种不太老套的解决方案。下面是一个如何更改溢出图标颜色的示例,但您可以调整它以更改图像:

 private void setOverflowIconColor(int color) {
        Drawable overflowIcon = toolbar.getOverflowIcon();

        if (overflowIcon != null) {
            Drawable newIcon = overflowIcon.mutate();
            newIcon.setColorFilter(color, PorterDuff.Mode.MULTIPLY);
            toolbar.setOverflowIcon(newIcon);
        }
    }

伙计们,我用一种简单的方式完成了这项工作,请看下面的片段:

@Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.menu_dashboard, menu);
        MenuItem item = menu.findItem(R.id.help);
        Drawable drawable = item.getIcon();
        drawable.setColorFilter(Color.RED, PorterDuff.Mode.SRC_ATOP);
        return super.onCreateOptionsMenu(menu);
    }

如果这里有更多的澄清,请告诉我。

有更好的解决方案。您可以在运行时以编程方式进行

toolbar.overflowIcon?.setColorFilter(colorInt, PorterDuff.Mode.SRC_ATOP)

Viola!

不需要创建新的样式资源,只需使用setOvewflowIcon(drawable)方法到工具栏对象,并将要用作图标的drawable传递给它

Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
       toolbar.setOverflowIcon(getResources().getDrawable(R.drawable.ic_notifications_black_24dp));

toolBar.overflowIcon?.setTint(Color.WHITE)

在科特林, 更改您想要的任何颜色:)
public static void setOverflowButtonColor(final Toolbar toolbar, final int color) {
    Drawable drawable = toolbar.getOverflowIcon();
    if(drawable != null) {
        drawable = DrawableCompat.wrap(drawable);
        DrawableCompat.setTint(drawable.mutate(), color);
        toolbar.setOverflowIcon(drawable);
    }
}
 private void setOverflowIconColor(int color) {
        Drawable overflowIcon = toolbar.getOverflowIcon();

        if (overflowIcon != null) {
            Drawable newIcon = overflowIcon.mutate();
            newIcon.setColorFilter(color, PorterDuff.Mode.MULTIPLY);
            toolbar.setOverflowIcon(newIcon);
        }
    }
@Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.menu_dashboard, menu);
        MenuItem item = menu.findItem(R.id.help);
        Drawable drawable = item.getIcon();
        drawable.setColorFilter(Color.RED, PorterDuff.Mode.SRC_ATOP);
        return super.onCreateOptionsMenu(menu);
    }
toolbar.overflowIcon?.setColorFilter(colorInt, PorterDuff.Mode.SRC_ATOP)
Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
       toolbar.setOverflowIcon(getResources().getDrawable(R.drawable.ic_notifications_black_24dp));