¿Cómo configurar el tamaño del vector dibujable dentro de un botón en Android?

Las herramientas de Android Studio Vector Assets convierten los dibujos vectoriales a PNG-s para los dispositivos pre-Lollipop, pero me sale muy mal calidad PNG-s como se puede ver aquí . Lo que es más es que el fondo del botón de color sólido se supone que es esta luz verde que se ve a la izquierda, pero el dibujable lo sobrescribe:

<item android:state_checked="true" android:drawable="@drawable/show"> <shape android:shape="rectangle"> <corners android:bottomRightRadius="8dp"/> <solid android:color="@color/waveComponentGreen"/> </shape> </item> <item android:state_checked="false" android:drawable="@drawable/hide"> <shape android:shape="rectangle"> <corners android:bottomRightRadius="8dp"/> <solid android:color="@color/waveComponentGreen"/> </shape> </item> 

El xml para el dibujable es (el predeterminado de los iconos de material):

 <vector xmlns:android="http://schemas.android.com/apk/res/android" android:width="24dp" android:height="24dp" android:viewportWidth="24.0" android:viewportHeight="24.0"> <path android:fillColor="#FF000000" android:pathData="M8.59,16.34l4.58,-4.59 -4.58,-4.59L10,5.75l6,6 -6,6z"/> 

También quería hacer que el icono aparezca un poco más pequeño ajustando los valores y noté que el aumento de las dimensiones de la ventana disminuye el icono pero no estoy seguro de entender por qué.

Entonces: ¿Cómo puedo hacer que el icono y el PNG generado parezcan más pequeños, menos borrosos y con el color de fondo establecido en el archivo de recursos? Gracias.

EDIT : Me las arreglé para obtener el fondo de color sólido con el icono mediante la combinación de ellos en un archivo xml separado con capas de listas:

 <layer-list xmlns:android="http://schemas.android.com/apk/res/android" > <item> <shape android:shape="rectangle"> <corners android:bottomRightRadius="10dp"/> <solid android:color="@color/waveComponentGreen"/> </shape> </item> <item android:drawable="@drawable/show" android:top="10dp" android:bottom="10dp" android:left="10dp" android:right="10dp" /> 

El resultado está aquí . Me las arreglé para reducir el desenfoque mediante el aumento de la anchura y la altura del vector drawable.However sin el androide: top | bottom | left | derecho etiquetas el dibujable se extiende a través de todo el área del botón. El segundo botón no necesita tener un color sólido de fondo por lo que no estoy usando las etiquetas de la lista de capas => no hay forma de establecer un margen superior | inferior | izquierdo | derecho para el dibujable. Si reduzco el tamaño del botón, lo que estoy haciendo es reducir el área de clic del botón.

Mi pregunta actualizada es cómo establecer el tamaño del vector dibujable dentro de un botón / botón de conmutación / botón de radio sin reducir el tamaño del botón en sí?

ACTUALIZACIÓN No pude encontrar una forma de cambiar el tamaño del vector dibujable en dispositivos pre-API 21. Así que en su lugar he hecho los botones en sí más pequeños y aumentó el área táctil de cada botón.

El enfoque correcto para escalar cualquier dibujable sería usar vectorDrawable.setBounds(left,top,right,bottom) , pero desafortunadamente eso no funciona para drawables de vectores (¿por qué Google?).

Por lo tanto, como una solución, yo cargar mi vector drawables, convertirlos en mapa de bits dibujable y que nos permitirá utilizar el método setBounds en el mapa de bits dibujable. Ten en cuenta que estás escalando mapas de bits aquí, por lo que puedes perder algo de nitidez de la imagen. Utilizo principalmente esos métodos cuando necesito utilizar mi drawable como un compuesto drawable de una opinión del texto o de un botón por ejemplo.

Terminé escribiendo una clase del ayudante que cargará un vector drawable fijó un tinte a él y devuelvo un mapa de bits drawable que usted puede realmente escala y tinte como usted desea. Lo he probado para niveles API de 19 hasta 23, y funciona.

No te olvides de usar vectorDrawables.useSupportLibrary = true en tu build.gradle .

 public class VectorDrawableUtils { /** * Gets a Bitmap from provided Vector Drawable image * * @param vd VectorDrawable * @return Bitmap */ public static Optional<Bitmap> createBitmapFromVectorDrawable(final @NonNull Drawable vd) { try { Bitmap bitmap; bitmap = Bitmap.createBitmap(vd.getIntrinsicWidth(), vd.getIntrinsicHeight(), Bitmap.Config.ARGB_8888); Canvas canvas = new Canvas(bitmap); vd.setBounds(0, 0, canvas.getWidth(), canvas.getHeight()); vd.draw(canvas); return Optional.of(bitmap); } catch (OutOfMemoryError e) { Injector.getDependency(getContext(), IEventTracker.class).logHandledException(e); return Optional.empty(); } } /** * Loads vector drawable and apply tint color on it. */ public static Drawable loadVectorDrawableWithTintColor(final @DrawableRes int vdRes, final @ColorRes int clrRes,final Context context) { Drawable drawable = ContextCompat.getDrawable(context, vdRes); DrawableCompat.setTint(drawable, getContext().getResources().getColor(clrRes)); return drawable; } /** * Converts given vector drawable to Bitmap drawable */ public static BitmapDrawable convertVectorDrawableToBitmapDrawable(final @NonNull Drawable vd) { //it is safe to create empty bitmap drawable from null source return new BitmapDrawable(createBitmapFromVectorDrawable(vd).get()); } /** * Loads vector drawable , aplys tint on it and returns a wrapped bitmap drawable. * Bitmap drawable can be resized using setBounds method (unlike the VectorDrawable) * @param context Requires view context ! */ public static Drawable loadVectorDrawableWithTint( final @DrawableRes int vectorDrawableRes, final @ColorRes int colorRes,final Context context) { Drawable vd = VectorDrawableUtils.loadVectorDrawableWithTintColor(vectorDrawableRes, colorRes, context); final BitmapDrawable bitmapDrawable = VectorDrawableUtils.convertVectorDrawableToBitmapDrawable(vd); ColorStateList tint = ContextCompat.getColorStateList(context,colorRes); final Drawable wrappedDrawable = DrawableCompat.wrap(bitmapDrawable); DrawableCompat.setTintList(wrappedDrawable,tint); return wrappedDrawable; } } 

Ahora usaría esta clase de ayuda como esto:

  Drawable bd = VectorDrawableUtils.loadVectorDrawableWithTint( R.drawable.ic_dropdown, R.color.black,getContext()); bd.setBounds(0, 0, textView.getMeasuredHeight(), textView.getMeasuredHeight()); textView.setCompoundDrawablesWithIntrinsicBounds(null, null, bd, null); 

¡Es importante usar un Contexto de una Vista o Actividad, no el contexto de la Aplicación! Espero que resuelva su problema, o ayudar a otra persona. Y si alguien tiene una solución mejor y más limpia, me interesa saber también.

  • Solución automática de laberinto
  • La vista de desplazamiento de Android es demasiado larga
  • LinearLayout no se puede convertir en android.widget.Button
  • Android Diseño de materiales Navegación Vista -> Elemento
  • La elevación no se muestra en la barra de herramientas de los dispositivos pre-pirulí
  • ¿Definir el logotipo personalizado para ActionBar (diferente de Logo) en XML?
  • Archivo de preferencias del usuario vs Archivo de preferencias de la aplicación
  • Cómo analizar el XML de SimpleXML
  • Error de Eclipse: Error al analizar ... \ android-22 \ android-wear \ armeabi-v7a \ devices.xml
  • ¿Cajón de la navegación sobre la barra de estado en turrón?
  • Hacer texto en negrita y cursiva
  • FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.