25

私の Android プロジェクトでは、Drawableリソースのコレクション全体をループ処理したいと考えています。通常、次のような ID を使用して特定のリソースのみを取得できます。

InputStream is = Resources.getSystem().openRawResource(resourceId)

ただし、事前に ID がわからないDrawableすべてのリソースを取得したいと考えています。ループできるコレクションや、プロジェクト内のリソースからリソース ID のリストを取得する方法はありますか?

または、Java でR.drawable静的クラスからすべてのプロパティ値を抽出する方法はありますか?

4

11 に答える 11

34

ちょっとハックっぽい感じですが、リフレクションで思いついたのがこれです。resources(は class のインスタンスであることに注意してくださいandroid.content.res.Resources。)

final R.drawable drawableResources = new R.drawable();
final Class<R.drawable> c = R.drawable.class;
final Field[] fields = c.getDeclaredFields();

for (int i = 0, max = fields.length; i < max; i++) {
    final int resourceId;
    try {
        resourceId = fields[i].getInt(drawableResources);
    } catch (Exception e) {
        continue;
    }
    /* make use of resourceId for accessing Drawables here */
}

私が気付いていない可能性のある Android 呼び出しをより有効に活用するためのより良い解決策を誰かが持っている場合は、ぜひ見てみたいと思います!

于 2010-07-11T03:48:46.723 に答える
8

私は Matt Huggins の素晴らしい回答を受け取り、それをリファクタリングしてより一般的なものにしました。

public static void loadDrawables(Class<?> clz){
    final Field[] fields = clz.getDeclaredFields();
    for (Field field : fields) {
        final int drawableId;
        try {
            drawableId = field.getInt(clz);
        } catch (Exception e) {
            continue;
        }
        /* make use of drawableId for accessing Drawables here */
    }   
}

使用法:

loadDrawables(R.drawable.class);
于 2013-03-06T20:39:35.417 に答える
8

getResources().getIdentifier を使用して、リソース フォルダー内の順番に名前が付けられた画像をスキャンしました。安全のために、アクティビティが初めて作成されたときにイメージ ID をキャッシュすることにしました。

    private void getImagesIdentifiers() {

    int resID=0;        
    int imgnum=1;
    images = new ArrayList<Integer>();

    do {            
        resID=getResources().getIdentifier("img_"+imgnum, "drawable", "InsertappPackageNameHere");
        if (resID!=0)
            images.add(resID);
        imgnum++;
    }
    while (resID!=0);

    imageMaxNumber=images.size();
}
于 2010-10-16T18:47:19.693 に答える
7

Raw フォルダーと AssetManager を使用する必要があります。

JPG ドローアブルの非常に長いファイル リストがあり、1 つずつ取得する手間をかけずにすべてのリソース ID を取得したいとします (R.drawable.pic1、R.drawable.pic2 など)。

//first we create an array list to hold all the resources ids
ArrayList<Integer> imageListId = new ArrayList<Integer>();

//we iterate through all the items in the drawable folder
Field[] drawables = R.drawable.class.getFields();
for (Field f : drawables) {
    //if the drawable name contains "pic" in the filename...
    if (f.getName().contains("image"))
        imageListId.add(getResources().getIdentifier(f.getName(), "drawable", getPackageName()));
}

//now the ArrayList "imageListId" holds all ours image resource ids
for (int imgResourceId : imageListId) {
     //do whatever you want here
}
于 2017-03-17T11:38:51.043 に答える
6

aaaa という名前の画像と zzzz という名前の別の画像を追加してから、次の手順を繰り返します。

public static void loadDrawables() {
  for(long identifier = (R.drawable.aaaa + 1);
      identifier <= (R.drawable.zzzz - 1);
      identifier++) {
    String name = getResources().getResourceEntryName(identifier);
    //name is the file name without the extension, indentifier is the resource ID
  }
}

これは私にとってはうまくいきました。

于 2013-10-02T07:04:41.340 に答える
4

If you find yourself wanting to do this you're probably misusing the resource system. Take a look at assets and AssetManager if you want to iterate over files included in your .apk.

于 2010-07-11T20:14:32.917 に答える
3

リフレクション コードは機能すると思いますが、なぜこれが必要なのかわかりません。

Android のリソースは、アプリケーションがインストールされると静的になるため、リソースのリストまたは配列を取得できます。何かのようなもの:

<string-array name="drawables_list">
    <item>drawable1</item>
    <item>drawable2</item>
    <item>drawable3</item>
</string-array>

そして、あなたは次のActivityようにしてそれを得ることができます:

getResources().getStringArray(R.array.drawables_list);
于 2010-07-11T13:20:11.440 に答える
0

OPにはドローアブルが必要で、レイアウトが必要でした。これが私がレイアウトのために思いついたものです。ビジネスではname.startsWith、システム生成のレイアウトを無視できるので、少し調整する必要があるかもしれません. これは、 の値を変更することで、どのリソース タイプでも機能するはずですclz

public static Map<String,Integer> loadLayouts(){
    final Class<?> clz = R.layout.class;
    Map<String,Integer> layouts = new HashMap<>();
    final Field[] fields = clz.getDeclaredFields();
    for (Field field : fields) {
        String name = field.getName();
        if (
                !name.startsWith("abc_")
                && !name.startsWith("design_")
                && !name.startsWith("notification_")
                && !name.startsWith("select_dialog_")
                && !name.startsWith("support_")
        ) {
            try {
                layouts.put(field.getName(), field.getInt(clz));
            } catch (Exception e) {
                continue;
            }
        }
    }
    return layouts;
}
于 2016-04-06T16:33:12.117 に答える