android - setscaletype - ImageView adjustViewBounds no funciona
setimageresource (4)
Además de la answer @ RomanNurik
here puede encontrar una solución de trabajo, ya sea copiar o pegar el código o simplemente agregar la dependencia de Gradle
dependencies {
compile ''com.inthecheesefactory.thecheeselibrary:adjustable-imageview:1.0.1''
}
La solución PS proporcionada por @Nilzor no funcionó para mí
Tengo un ImageView con android:layout_width=100dp
, android:layout_height=wrap_content
y android:adjustViewBounds=true
Su fuente es una imagen de 50 x 50 px. Pero la relación de aspecto no se conserva: la altura de ImageView es 50px, no 100px (es decir, adjustViewBounds
no funciona). Si tengo una imagen de 200x200px, funciona: el ancho y la altura son 100 píxeles. Este código da como resultado una imagen de 100 px de ancho y 50 px de alto, pero la imagen de src es cuadrada:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<ImageView
android:id="@+id/photo"
android:src="@drawable/icon"
android:layout_width="100dp"
android:layout_height="wrap_content"
android:scaleType="fitXY"
android:adjustViewBounds="true" />
</LinearLayout>
El problema es que adjustViewBounds
no aumentará el tamaño de ImageView
más allá de las dimensiones naturales del dibujable. Solo reducirá la vista para mantener la relación de aspecto; si proporciona una imagen de 500x500 en lugar de una imagen de 50x50, esto debería funcionar.
Si está interesado en el lugar donde se implementa este comportamiento, consulte la implementación onMeasure de ImageView.java .
Una solución alternativa es implementar un ImageView
personalizado que cambie este comportamiento en onMeasure
.
Hay una manera más simple. Haga su ImageView así:
<ImageView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:scaleType="fitCenter"
android:adjustViewBounds="true"/>
De esta forma, drawable se estirará para caber en el centro de ImageView conservando la relación de aspecto. Solo tenemos que calcular la altura correcta para que sea proporcional, por lo que no tenemos ningún espacio en blanco:
private void setImageBitmap(Bitmap bitmap, ImageView imageView){
float i = ((float)imageWidth)/((float)bitmap.getWidth());
float imageHeight = i * (bitmap.getHeight());
imageView.setLayoutParams(new RelativeLayout.LayoutParams(imageWidth, (int) imageHeight));
imageView.setImageBitmap(bitmap);
}
Tenía un requisito similar; en mi caso, quería que la imagen fuera cuadrada, y quería que el ImageView coincidiera con la relación de aspecto para poder usar su fondo y relleno para dibujar un borde.
Leí las respuestas aquí, pero en lugar de anular ImageView, decidí hacer un diseño que garantice que su contenido (debe ser solo una vista) sea cuadrado. De esa manera podría usar un ImageView estándar dentro de él. (Y nunca se sabe, podría querer hacer algo más cuadrado más tarde, aunque probablemente no).
En caso de que sea útil para cualquier otra persona, aquí está el código (no dude en copiarlo). Probablemente haya errores ya que solo lo hice funcionar para mi aplicación y luego me detuve. :)
public class SquareLayout extends ViewGroup
{
public SquareLayout(Context context, AttributeSet attrs, int defStyle)
{
super(context, attrs, defStyle);
}
public SquareLayout(Context context, AttributeSet attrs)
{
super(context, attrs);
}
public SquareLayout(Context context)
{
super(context);
}
@Override
protected void onLayout(boolean changed, int l, int t, int r, int b)
{
// Work out width and height, and square size.
int width = r - l;
int height = b - t;
int size, xOffset, yOffset;
if(width < height)
{
size = width;
xOffset = 0;
yOffset = (height - size) / 2;
}
else
{
size = height;
xOffset = (width - size) / 2;
yOffset = 0;
}
for(int i = 0; i < getChildCount(); i++)
{
View child = getChildAt(i);
child.layout(xOffset, yOffset, size + xOffset, size + yOffset);
}
}
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec)
{
// Get width and height.
int w = -1, h = -1;
switch(MeasureSpec.getMode(widthMeasureSpec))
{
case MeasureSpec.AT_MOST:
case MeasureSpec.EXACTLY:
w = MeasureSpec.getSize(widthMeasureSpec);
break;
case MeasureSpec.UNSPECIFIED:
break;
}
switch(MeasureSpec.getMode(heightMeasureSpec))
{
case MeasureSpec.AT_MOST:
case MeasureSpec.EXACTLY:
h = MeasureSpec.getSize(heightMeasureSpec);
break;
case MeasureSpec.UNSPECIFIED:
break;
}
// If only one of width/height is unspecified, set them both the same.
if(w == -1 && h != -1)
{
w = h;
}
else if(h == -1 && w != -1)
{
h = w;
}
// Either they''re both specified or both unspecified.
int childMeasureSpec;
if(w == -1)
{
childMeasureSpec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED);
}
else
{
childMeasureSpec = MeasureSpec.makeMeasureSpec(w, MeasureSpec.EXACTLY);
}
// Pass through to children.
int maxDimension = 1;
for(int i = 0; i < getChildCount(); i++)
{
View child = getChildAt(i);
child.measure(childMeasureSpec, childMeasureSpec);
maxDimension = Math.max(maxDimension, child.getMeasuredWidth());
maxDimension = Math.max(maxDimension, child.getMeasuredHeight());
}
if(w == -1)
{
w = maxDimension;
h = maxDimension;
}
setMeasuredDimension(w, h);
}
}