Estoy intentando usar elementos de diseño vectoriales en mi aplicación de Android. De http://developer.android.com/training/material/drawables.html (énfasis mío):
En Android 5.0 (API nivel 21) y superior, puede definir elementos de diseño vectoriales, que escalan sin perder definición.
Usando este dibujable:
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:height="24dp"
android:width="24dp"
android:viewportWidth="24"
android:viewportHeight="24">
<path android:fillColor="@color/colorPrimary" android:pathData="M14,20A2,2 0 0,1 12,22A2,2 0 0,1 10,20H14M12,2A1,1 0 0,1 13,3V4.08C15.84,4.56 18,7.03 18,10V16L21,19H3L6,16V10C6,7.03 8.16,4.56 11,4.08V3A1,1 0 0,1 12,2Z" />
y este ImageView:
<ImageView
android:layout_width="400dp"
android:layout_height="400dp"
android:src="@drawable/icon_bell"/>
produce esta imagen borrosa cuando se intenta mostrar el icono a 400 dp (en un dispositivo móvil de alta resolución de alrededor de 2015 que ejecuta una paleta):
Cambiar el ancho y el alto en la definición del vector dibujable a 200dp mejora significativamente la situación en el tamaño renderizado de 400dp. Sin embargo, configurar esto como un elemento de dibujo para un elemento TextView (es decir, el icono a la izquierda del texto) ahora crea un icono enorme.
Mis preguntas:
1) ¿Por qué hay una especificación de ancho / alto en el vector dibujable? Pensé que el objetivo de estos es que se escalan hacia arriba y hacia abajo sin pérdidas, lo que hace que el ancho y la altura no tengan sentido en su definición.
2) ¿Es posible usar un único elemento de dibujo vectorial que funcione como elemento de dibujo de 24 dp en un TextView pero que se amplíe bien para usar imágenes mucho más grandes también? Por ejemplo, ¿cómo evito crear varios elementos de diseño vectoriales de diferentes tamaños y, en su lugar, uso uno que se adapte a mis requisitos renderizados?
3) ¿Cómo utilizo eficazmente los atributos de ancho / alto y cuál es la diferencia con viewportWidth / Height?
Detalles adicionales:
- El dispositivo está ejecutando API 22
- Usando Android Studio v1.5.1 con Gradle versión 1.5.0
- Manifest es compilar y nivel objetivo 23, nivel mínimo 15. También intenté mover el nivel mínimo a 21, pero esto no hizo ninguna diferencia.
- La descompilación del APK (con el nivel mínimo establecido en 21) muestra un solo recurso XML en la carpeta dibujable. No se producen imágenes rasterizadas.
New -> Vector Asset
, suelta la imagen vectorial XML en mi carpeta dibujable. Sin embargo, si utilizo apktool para descomprimir el APK que se compila, veo que los archivos XML están instaladosdrawable-anydpi-v21
y escalan correctamente en dispositivos API 21+. Los archivos ráster se colocan en lasdrawable-<mdpi/hdpi/etc>-v4
carpetas y no se usan en dispositivos API 21+ (basado en el hecho de que escalan correctamente)drawable
carpeta. El ancho / alto en el archivo xml dibujable de vectores es 24 dp. Especificar un ImageView de 400dp de alto / ancho definitivamente está creando una imagen mal escalada.drawable-anydpi-v21
es porque myminSdkVersion
es menor que 21. ¿Algún cambio en el comportamiento si lo ponesminSdkVersion
en menos de 21? ¿Qué hay de mover el XML adrawable-anydpi
? No esperaría que hubiera un cambio, pero también esperaría que su imagen vectorial se escale correctamente ...drawable-anydpi-v21
con varias imágenes rasterizadas en mdi / hdpi / etc. carpetas. Sin embargo, no hay cambios en el resultado final renderizado.Respuestas:
Hay nueva información sobre este problema aquí:
https://code.google.com/p/android/issues/detail?id=202019
Parece que usarlo
android:scaleType="fitXY"
hará que se escale correctamente en Lollipop.De un ingeniero de Google:
fuente
Para las versiones de SDK inferiores a 21, donde el sistema de compilación necesita generar imágenes ráster y como tamaño predeterminado en los casos en que no especifica el ancho / alto.
No creo que esto sea posible si también necesita orientar los SDK a menos de 21.
Documentación: (en realidad no es muy útil ahora que lo releo ...)
Más documentación:
Editar: Algo extraño está sucediendo. Aquí están mis resultados en la versión 23 del SDK del emulador (el dispositivo de prueba Lollipop + está muerto en este momento ...):
Y en la versión 21 del SDK del emulador:
fuente
width
height
viewport
height
ywidth
dexml
?AppCompat 23.2 presenta elementos de diseño vectoriales para todos los dispositivos que ejecutan Android 2.1 y superior. Las imágenes se escalan correctamente, independientemente del ancho / alto especificado en el archivo XML del elemento de diseño vectorial. Desafortunadamente, esta implementación no se utiliza en el nivel de API 21 y superior (a favor de la implementación nativa).
La buena noticia es que podemos obligar a AppCompat a usar su implementación en los niveles de API 21 y 22. La mala noticia es que tenemos que usar la reflexión para hacer esto.
En primer lugar, asegúrese de que está utilizando la última versión de AppCompat y que ha habilitado la nueva implementación de vector:
Luego, llame
useCompatVectorIfNeeded();
al onCreate () de su aplicación:Finalmente, asegúrese de que está usando en
app:srcCompat
lugar deandroid:src
configurar la imagen de su ImageView:¡Sus elementos de diseño vectoriales ahora deberían escalar correctamente!
fuente
1) ¿Por qué hay una especificación de ancho / alto en el vector dibujable? Pensé que el objetivo de estos es que se escalan hacia arriba y hacia abajo sin pérdidas, lo que hace que el ancho y la altura no tengan sentido en su definición.
2) ¿Es posible utilizar un único elemento de dibujo vectorial que funcione como elemento de dibujo de 24 dp en un TextView, así como una imagen grande de ancho cerca de la pantalla?
3) ¿Cómo utilizo eficazmente los atributos de ancho / alto y cuál es la diferencia con viewportWidth / Height?
fuente
Resuelvo mi problema, solo cambio el tamaño de la imagen vectorial. Desde el principio fue un recurso como:
Y lo cambié a 150dp (tamaño de ImageView en el diseño con este recurso de vector) como:
Me está funcionando.
fuente
Probé muchas de estas formas, pero desafortunadamente, ninguna funcionó. Trato
fitXY
deImageView
, trato de usarapp:srcCompat
, pero no puedo incluso utilizarlo. pero encontré una forma engañosa:Pero el punto de esta forma son las dimensiones de Vistas. si tu
ImageView
tiene dimensiones incorrectas, el elemento dibujable se estira. debes controlarlo en versiones anteriores a la piruleta o usar algunas vistasPercentRelativeLayout
.Espero que sea de ayuda.
fuente
Primero : importe svg a drawble: (( https://www.learn2crack.com/2016/02/android-studio-svg.html ))
Segundo : si desea compatibilidad con la API de Android 7+, debe utilizar la grabación de la biblioteca de compatibilidad de Android (( https://stackoverflow.com/a/44713221/1140304 ))
1- agregar
a su archivo build.gradle.
2-Use el espacio de nombres en su diseño que tiene imageView:
Tercero : configure imageView con android: scaleType = "fitXY" y use la aplicación: srcCompat
Cuarto : si desea configurar svg en el código java, debe agregar la siguiente línea en el método oncreate
fuente
Para mí, la razón que causó que los vectores se convirtieran a png fue el
android:fillType="evenodd"
atributo en mi vector dibujable. Cuando eliminé todas las apariciones de este atributo en mi elemento de dibujo (por lo tanto, elnonzero
tipo de relleno predeterminado aplicado al vector), la próxima vez que se compiló la aplicación, todo estuvo bien.fuente