私はこれらの2つのAPIと少し混同しています。
ResourcesCompat.getDrawable(Resources res、int id、Resources.Theme theme)
特定のリソースIDに関連付けられ、指定されたテーマのスタイルが設定された描画可能なオブジェクトを返します。基になるリソースに応じて、さまざまなタイプのオブジェクトが返されます。たとえば、単色、PNG画像、スケーラブル画像などです。
APIレベル21より前は、テーマは適用されず、このメソッドは単にgetDrawable(int)を呼び出します。
AppCompatResources.getDrawable(Context context、int resId)
特定のリソースIDに関連付けられた描画可能なオブジェクトを返します。
このメソッドは、デバイス上のvectorおよびanimated-vectorリソースのインフレーションをサポートします。プラットフォームのサポートは利用できません。
2つのメソッドのソースコードを見ると、非常に似ているように見えます。ベクトルがない場合は、おそらくどちらか一方を使用して逃げることができます。
ResourcesCompat.getDrawable()
は、API 21以降でResources#getDrawable(int, theme)
を呼び出します。また、Android API 4+。をサポートしています。これ以上の機能はありません。
_public Drawable getDrawable(Resources res, int id, Theme theme)
throws NotFoundException {
final int version = Build.VERSION.SDK_INT;
if (version >= 21) {
return ResourcesCompatApi21.getDrawable(res, id, theme);
} else {
return res.getDrawable(id);
}
}
_
Where-in _ResourcesCompatApi21
_は、単にres.getDrawable(id, theme)
を呼び出します。これは、デバイスがベクトルドロアブルをサポートしていない場合、ベクトルドロアブルを描画できるようにするnotを意味します。ただし、テーマを渡すことはできます。
一方、 AppCompatResources.getDrawable(Context context, int resId)
のコード変更は、最終的に次のようになります。
_ Drawable getDrawable(@NonNull Context context, @DrawableRes int resId, boolean failIfNotKnown) {
checkVectorDrawableSetup(context);
Drawable drawable = loadDrawableFromDelegates(context, resId);
if (drawable == null) {
drawable = createDrawableIfNeeded(context, resId);
}
if (drawable == null) {
drawable = ContextCompat.getDrawable(context, resId);
}
if (drawable != null) {
// Tint it if needed
drawable = tintDrawable(context, resId, failIfNotKnown, drawable);
}
if (drawable != null) {
// See if we need to 'fix' the drawable
DrawableUtils.fixDrawable(drawable);
}
return drawable;
}
_
したがって、このインスタンスは、可能な場合はリソースを描画しようとします。そうでない場合は、ContextCompat
バージョンを検索してリソースを取得します。その後、必要に応じて色合いを調整します。ただし、このメソッドはAPI 7+のみをサポートします。
だから、どちらを使うべきかを決めると思います。
API 4、5、または6をサポートする必要がありますか?
ResourcesCompat
またはContextCompat
を使用する以外に選択肢はありません。カスタムテーマを提供する必要がありますか?
ResourcesCompat
を使用する以外に選択肢はありませんAppCompatResources
を使用しますここにいくつかのテストの後、私の理解があります
_ContextCompat.getDrawable(@NonNull Context context, @DrawableRes int resId)
ResourcesCompat.getDrawable(@NonNull Resources res, @DrawableRes int id, @Nullable Theme theme)
AppCompatResources.getDrawable(@NonNull Context context, @DrawableRes int resId)
VectorDrawableCompat.create(@NonNull Resources res, @DrawableRes int resId, @Nullable Theme theme
_
最初に表示されるのは、VectorDrawableCompat
およびResourcesCompat
が特定のテーマに対応していることです
ApplicationクラスのonCreated
のAppCompatDelegate.setCompatVectorFromResourcesEnabled(true);
1)ベクター画像の場合
API> = 21
ContextCompat
はうまく機能しますResourcesCompat
はうまく機能しますAppCompatResources
はうまく機能しますVectorDrawableCompat
はうまく機能しますAPI <21
ContextCompat
クラッシュResourcesCompat
クラッシュAppCompatResources
はうまく機能しますVectorDrawableCompat
はうまく機能します2)通常の画像の場合
ContextCompat
はうまく機能しますResourcesCompat
はうまく機能しますAppCompatResources
はうまく機能しますVectorDrawableCompat
クラッシュApplicationクラスのonCreated
のAppCompatDelegate.setCompatVectorFromResourcesEnabled(true);
1)ベクター画像の場合
ContextCompat
はうまく機能しますResourcesCompat
はうまく機能しますAppCompatResources
はうまく機能しますVectorDrawableCompat
はうまく機能します2)通常の画像の場合
ContextCompat
はうまく機能しますResourcesCompat
はうまく機能しますAppCompatResources
はうまく機能しますVectorDrawableCompat
クラッシュResourcesCompat
、ContextCompat
、およびCompat
で終わるsupport-v4のほとんどすべてのクラスにより、if (Build.VERSION.SDK_INT >= X)
チェックをどこからでも作成できます。それでおしまい。たとえば
final Drawable d;
if (Build.VERSION.SDK_INT < 21) {
// Old method, drawables cannot contain theme references.
d = context.getResources().getDrawable(R.drawable.some_image);
} else {
// Drawables on API 21 can contain theme attribute references.
// Context#getDrawable only exists since API 21.
d = context.getDrawable(R.drawable.some_image);
}
あなたは書ける
final Drawable d = ContextCompat.getDrawable(context, R.drawable.some_image);
たとえば、コメントで説明されている制限が適用されます
// This line is effectively equivalent to the above.
ResourcesCompat.getDrawable(context.getResources(), R.drawable.some_image, context.getTheme());
lollipopの前にテーマ属性を実際に適用することはありません(これはドキュメントで説明されています)。ただし、実際に新しいAPIを使用していないので、古いデバイスでチェックとコードがクラッシュしない場合は、書く必要はありません。
一方、AppCompatResources
は、実際に古いプラットフォームに新しい機能を追加するのに役立ちます(サポートベクター、カラー状態リストのテーマ参照)。
どちらを優先するべきか、またその理由は何ですか?
AppCompatResources
を使用して、残りのappcompat-v7ライブラリと一貫した結果を取得します。あなたが取得します:
Android:alpha="?android:disabledAlpha"
など)で色を解決できるgetColorStateList
、getDrawable
は、すべてのプラットフォームでベクトルの膨張をサポートし、これらのベクトルドロウアブルはテーマ属性参照も理解します(例:Android:tint="?colorControlNormal"
)、ContextCompat
にフォールバックします。