102

アプリケーションに2つの選択可能なテーマが必要です。そのために、次のようないくつかの属性を定義しました。

 <attr format="color" name="item_background" />

次に、次のように両方のテーマを作成しました。

  <style name="ThemeA">
     <item name="item_background">#123456</item>
 </style>

 <style name="ThemeB">
     <item name="item_background">#ABCDEF</item>
 </style>

この方法はうまく機能し、いくつかのテーマを簡単に作成および変更できます。問題は、ビューでのみ使用でき、Drawableでは使用できないように見えることです。

たとえば、レイアウト内のビューから値を参照すると、次のように機能します。

 <TextView android:background="?item_background" />

しかし、Drawableで同じことをしても、次のことはできません。

 <shape android:shape="rectangle">
     <solid android:color="?item_background" />
 </shape>

アプリケーションを実行すると、次のエラーが発生します。

    java.lang.UnsupportedOperationException: Can't convert to color: type=0x2

ハードコードされた色を使用する代わりに?item_background、それは機能しますが、それではテーマを使用できません。私も試し?attr:item_backgroundましたが、同じことが起こります。

どうすればこれを行うことができますか?また、ビューでは機能するのにドローアブルでは機能しないのはなぜですか?この制限はドキュメントのどこにも見つかりません...

4

5 に答える 5

177

私の経験では、XMLドローアブルの属性を参照することはできません。
テーマを作成するには、次のことを行う必要があります。

  • テーマごとに1つのXMLドローアブルを作成します。
  • @colorタグまたは#RGB形式で直接描画可能な必要な色を含めます。

attrs.xmlでドローアブルの属性を作成します。

<?xml version="1.0" encoding="utf-8"?>
<resources>
   <!-- Attributes must be lowercase as we want to use them for drawables -->
   <attr name="my_drawable" format="reference" />
</resources>

ドローアブルをtheme.xmlに追加します。

<style name="MyTheme" parent="@android:style/Theme.NoTitleBar">
   <item name="my_drawable">@drawable/my_drawable</item>
</style>

属性を使用して、レイアウトでドローアブルを参照します。

<TextView android:background="?my_drawable" />
于 2012-11-20T10:55:18.877 に答える
20

lollipop(API 21)以降、この機能がサポートされています 。https://code.google.com/p/android/issues/detail?id=26251を参照してください。

ただし、ロリポップのないデバイスをターゲットにしている場合は、使用しないでください。クラッシュするため、代わりに、受け入れられた回答の回避策を使用してください。

于 2015-05-20T13:47:55.823 に答える
5

Lollipopより前のデバイスのドローアブルからスタイル属性を参照することはできませんが、カラー状態リストでは参照できます。AndroidサポートライブラリのAppCompatResources.getColorStateList(Context context、int resId)メソッドを使用できます。欠点は、これらのカラー状態リストをプログラムで設定する必要があることです。

これは非常に基本的な例です。

color / my_color_state.xml

<selector xmlns:android="http://schemas.android.com/apk/res/android">
  <item android:state_checked="true" android:color="?colorControlActivated" />
  <item android:color="?colorControlNormal" />
</selector>

カラー状態リストが必要なウィジェット:

<RadioButton
  android:id="@+id/radio_button"
  android:text="My Radio" />

そして最も重要なのは:

ColorStateList csl = AppCompatResources.getColorStateList(context, R.color.my_color_state);    
RadioButton r = (RadioButton) findViewById(R.id.radio_button);
r.setTextColor(csl);

さて、最もエレガントで最短の方法ではありませんが、これはAndroidサポートライブラリがAndroidの古いバージョン(ロリポップ以前)で動作するようにするために行うことです。

残念ながら、ドローアブルの同様の方法は、スタイル属性では機能しません。

于 2016-12-10T23:59:51.697 に答える
5

私はhttps://stackoverflow.com/a/59467269/3841352で同じ質問に答えましたが、ここにも投稿します:

同じ問題が発生しましたが、2019年の時点では解決されていないため、セレクターで属性をドローアブルとして参照することはできません。ここに投稿されていないので、問題に対して得た解決策を共有します。バグレポートの最後のコメントで見つけました。

回避策は、基本的に、属性値を参照するリソースとなる描画可能なリソースを作成することです。

あなたのケースを説明するために、解決策は次の代わりになります:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:drawable="?attr/colorPrimary" android:state_enabled="true" android:state_window_focused="false"/>
    <item android:drawable="?attr/colorPrimaryDark" android:state_pressed="true"/>
    <item android:drawable="@android:color/darker_gray" android:state_enabled="false"/>
    <item android:drawable="?attr/colorPrimary"/>
</selector>

ドローアブルリソースの?attr/*を置き換えます。

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:drawable="@drawable/colorPrimaryDrawable" android:state_enabled="true" android:state_window_focused="false"/>
    <item android:drawable="@drawable/colorPrimaryDarkDrawable" android:state_pressed="true"/>
    <item android:drawable="@android:color/darker_gray" android:state_enabled="false"/>
    <item android:drawable="@drawable/colorPrimaryDrawable"/>
</selector>

ドローアブルは次のように定義されます。

drawable / colorPrimaryDrawable

<shape xmlns:android="http://schemas.android.com/apk/res/android"android:shape="rectangle">
    <solid android:color="?attr/colorPrimary" />
</shape>

drawable / colorPrimaryDarkDrawable

<shape xmlns:android="http://schemas.android.com/apk/res/android"android:shape="rectangle">
    <solid android:color="?attr/colorPrimaryDark" />
</shape>

それが役に立てば幸い!!

于 2019-12-24T10:23:30.743 に答える
0

@marmorが述べたように、これはAPI 21でサポートされるようになりました。ただし、Androidのレガシーバージョンをサポートする必要がある場合は、この機能を使用できます。v7サポートライブラリを使用すると、SDKレベルが7までのアプリでも使用できます。

AppCompatImageViewv7 Androidサポートライブラリのには、この機能のバグのない実装があります。ImageViewの使用法をに置き換えるだけAppCompatImageViewです。

于 2016-05-11T03:51:21.757 に答える