40 votes

ImageView adjustViewBounds ne fonctionne pas

J'ai une ImageView avec width = 100px, height = wrap_content et adjustViewBounds = true. src est une image 50x50px. Mais le rapport hauteur / largeur n'est pas conservé - la hauteur de l'ImageView est de 50 pixels, pas de 100 pixels (c'est-à-dire que adjustViewBounds ne fonctionne pas). Si j'ai une image de 200 x 200 pixels, cela fonctionne - la largeur et la hauteur sont de 100 pixels. Ce code donne une image de 100 pixels de large et de 50 pixels de haut, mais l'image src est carrée:

 <?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>
 

68voto

Roman Nurik Points 18632

Le problème est qu' adjustViewBounds ne sera pas augmenter la taille de l' ImageView - delà les dimensions naturelles de la drawable. Il ne se rétrécir le point de vue de maintenir le ratio d'aspect; si vous fournissez un 500x500 image au lieu d'une 50x50 image, cela devrait fonctionner.

Si vous êtes intéressé par l'endroit où ce comportement est mis en œuvre, voir ImageView.java's onMeasure mise en œuvre.

Une solution de contournement consiste à mettre en œuvre une coutume ImageView qui change ce comportement en onMeasure.

12voto

vladexologija Points 1644

Il existe un moyen plus simple. Faites votre ImageView comme ceci:

 <ImageView
  android:layout_width="match_parent"
  android:layout_height="match_parent"
  android:scaleType="fitCenter"
  android:adjustViewBounds="true"/>
 

De cette façon, le dessin peut s'étirer pour s'adapter au centre ImageView en préservant le rapport d'aspect. Il suffit de calculer la bonne hauteur pour la rendre proportionnelle afin de ne pas avoir d'espace vide:

 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);
}
 

0voto

sam Points 378

J'ai eu une demande similaire, dans mon cas, je voulais que l'image soit carré, et je voulais l'ImageView fonction des proportions si je pouvais utiliser son arrière-plan et du remplissage de tracer une frontière.

J'ai lu les réponses ici, mais au lieu de l'annulation de la ImageView, j'ai décidé de faire une Mise en page qui garantit son contenu (ce qui devrait être une seule vue) sont de forme carrée. De cette façon, je pourrais utiliser un standard ImageView à l'intérieur. (Et on ne sait jamais, je pourrais avoir besoin de faire quelque chose de carré plus tard. Bien que probablement pas.)

Dans le cas où il est utile pour quelqu'un d'autre, voici le code (n'hésitez pas à copier). Il y a probablement des bugs que j'ai juste fait le travail pour mon application est ensuite arrêté. :)

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);
    }
}

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X