android android-support-library appcompat remoteview vectordrawable

android - AppCompat 23.2 usa VectorDrawableCompat con RemoteViews(AppWidget) en la API<21



android-support-library (2)

El siguiente método convertirá el vector drawable a un mapa de bits antes, esto debería hacer el truco.

public static BitmapDrawable vectorToBitmapDrawable(Context ctx, @DrawableRes int resVector) { return new BitmapDrawable(ctx.getResources(), vectorToBitmap(ctx, resVector)); } public static Bitmap vectorToBitmap(Context ctx, @DrawableRes int resVector) { Drawable drawable = AppCompatDrawableManager.get().getDrawable(ctx, resVector); Bitmap b = Bitmap.createBitmap(drawable.getIntrinsicWidth(), drawable.getIntrinsicHeight(), Bitmap.Config.ARGB_8888); Canvas c = new Canvas(b); drawable.setBounds(0, 0, c.getWidth(), c.getHeight()); drawable.draw(c); return b; }

Tengo un AppWidget y me gustaría usar VectorDrawables también en dispositivos pre-Lollipop. VectorDrawableCompat no funcionará con las RemoteViews que creo.

Para mantener el tamaño de mi APK de la aplicación, no quiero agregar versiones PNG alternativas de mis dibujables para plataformas API más antiguas.

¿Cómo puedo hacer eso?


ACTUALIZACIÓN 22/10/2017

Como lo señaló @ user924, ahora el acceso a AppCompatDrawableManager está restringido a su propia biblioteca. ContextCompat.getDrawable (...) debería hacer el truco.

ACTUALIZACIÓN 05/09/2016

Como lo señaló @ kirill-kulakov en su respuesta, las últimas actualizaciones de la Biblioteca de soporte restringieron la visibilidad de TintContextWrapper a su propio paquete. Estoy actualizando mi respuesta para eliminar el código incorrecto, ¡pero agradezca a Kirill por la corrección!

VectorDrawable y RemoteViews pre-Lollipop

Puede evitar agregar versiones rasterizadas alternativas de sus recursos dibujables vectoriales con un simple truco : use AppCompat TintResources a través de TintContextWrapper usando AppCompatDrawableManager usando ContextCompat .

TintResources AppCompatDrawableManager ContextCompat es la clase que, entre otras cosas, en los dispositivos pre-Lollipop, analiza los archivos XML de VectorDrawable y los convierte en instancias de VectorDrawableCompat que pueden utilizarse hasta API 7.

Luego, una vez que tenga una instancia de VectorDrawableCompat , rasterícelo en un mapa de bits. Más adelante utilizará este mapa de bits en un ImageView remoto.


Antes de comenzar: AppCompat Library

Asegúrese de que está utilizando Android Studio 2.0+ y que haya configurado su aplicación build.gradle file de la siguiente manera:

android { defaultConfig { vectorDrawables.useSupportLibrary = true } } dependencies { compile ''com.android.support:appcompat-v7:23.3.0'' }


Actualice su AppWidgetProvider

En primer lugar: no configure sus recursos dibujables vectoriales dentro de su archivo de diseño de RemoteViews (ni android:src ni app:srcCompat funcionarán). Tendrás que configurarlas programáticamente.

Dentro de su clase AppWidgetProvider , establezca el recurso vectorial o una versión rasterizada según el nivel de API:

RemoteViews remoteViews = new RemoteViews(context.getPackageName(), R.layout.appwidget_layout); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { remoteViews.setImageViewResource(R.id.imageView, R.drawable.vector); } else { Drawable d = ContextCompat.getDrawable(context, R.drawable.vector); Bitmap b = Bitmap.createBitmap(d.getIntrinsicWidth(), d.getIntrinsicHeight(), Bitmap.Config.ARGB_8888); Canvas c = new Canvas(b); d.setBounds(0, 0, c.getWidth(), c.getHeight()); d.draw(c); remoteViews.setImageViewBitmap(R.id.imageView, b); }


Referencias