颜色/可绘制更改应用于具有相同背景(颜色)的所有视图[棉花糖]

Mdl*_*dlc 12 android

我最近将手机更新为Android Marshmallow并在其上运行我现有的应用程序,但注意到颜色行为的差异:当将更改应用于视图的背景(可绘制)时,所有共享相同背景的视图(参考)将也适用相同的变化.以前,情况并非如此.

示例
在此示例中,我有两个具有相同背景颜色的视图,我想更改其中一个视图的alpha级别.

首先我们在布局中定义视图:

    <LinearLayout
        android:id="@+id/test1"
        android:orientation="horizontal"
        android:layout_width="50dp"
        android:layout_height="50dp"
        android:background="@color/testColor2">

    </LinearLayout>

    <LinearLayout
        android:id="@+id/test2"
        android:orientation="horizontal"
        android:layout_width="50dp"
        android:layout_height="50dp"
        android:background="@color/testColor1"
        android:layout_marginLeft="5dp">
    </LinearLayout>
Run Code Online (Sandbox Code Playgroud)

两个视图共享相同的背景颜色或drawable:

<color name="testColor1">#3F51B5</color>
<color name="testColor2">#3F51B5</color>
Run Code Online (Sandbox Code Playgroud)

结果如下:
在此输入图像描述

现在我们要改变两个背景中的一个,如下所示:

    LinearLayout test1 = (LinearLayout) findViewById(R.id.test1);
    LinearLayout test2 = (LinearLayout) findViewById(R.id.test2);
    test1.getBackground().setAlpha(80);
Run Code Online (Sandbox Code Playgroud)

结果如下:
在此输入图像描述

然而,期望和预期的结果显然是这样的:
在此输入图像描述

此处下载示例项目.

一些但是:

  • 通过XML设置Alpha级别时,此行为不适用.
  • 如果两个视图在colors.xml中引用不同的颜色定义并不重要(如示例中所示),请在视图的xml文件中直接引用两者的相同颜色定义具有相同的颜色(十六进制).

问题
如何在不影响共享相同背景的其他视图的情况下更改视图的背景.优选地,同时仍然能够使用直接引用颜色的xml文件中定义的颜色的背景

Mdl*_*dlc 17

很可能每个视图的背景和constantstate的类都是同一个对象.似乎两个颜色资源已经在某处"合并" - 这意味着它们共享了ConstantState.也许在Resources类的缓存中?我会期望它们保持分离,因为它们是不同的资源(虽然具有相同的颜色值),但显然不是.

- Snild Dolkow

ColorDrawable的状态存储alpha,因此对one的任何更改都将更改其他.为了防止这种情况,你可以先在drawable上调用mutate(),将两个drawable分开(通过制作一个状态的副本).

在该示例中,这将导致使用test1.getBackground().mutate().setAlpha(80);而不是直接应用alpha.