Ajuster l'image dans ImageButton sous Android

147

J'ai 6 ImageButton dans mon activité, j'y mets des images via mon code (sans utiliser de xml).

Je veux qu'ils couvrent 75% de la zone des boutons. Mais là où certaines images couvrent moins de surface, certaines sont trop grandes pour tenir dans l'imageButton. Comment les redimensionner et les afficher par programme? Ci-dessous la capture d'écran

entrez la description de l'image ici ci-dessous est le fichier xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:layout_marginBottom="5sp"
        android:layout_marginLeft="2sp"
        android:layout_marginRight="5sp"
        android:layout_marginTop="0sp"     >
   <LinearLayout
        android:layout_height="0dp"
        android:layout_width="match_parent"
        android:layout_weight="1"
        android:orientation="horizontal">
        <ImageButton          

            android:layout_height="match_parent"
            android:layout_width="0dp"
            android:layout_weight="1"
            android:id="@+id/button_topleft"
        android:layout_marginBottom="5sp"
        android:layout_marginLeft="2sp"
        android:layout_marginRight="5sp"
        android:layout_marginTop="0sp"
            />
        <ImageButton
            android:layout_height="match_parent"
            android:layout_width="0dp"
            android:layout_weight="1"
            android:id="@+id/button_topright"
    android:layout_marginBottom="5sp"
        android:layout_marginLeft="2sp"
        android:layout_marginRight="5sp"
        android:layout_marginTop="0sp"
            />
    </LinearLayout>
    <LinearLayout
        android:layout_height="0dp"
        android:layout_width="match_parent"
        android:layout_weight="1"
        android:orientation="horizontal">

        <ImageButton
            android:layout_height="match_parent"
            android:layout_width="0dp"
            android:layout_weight="1"
            android:id="@+id/button_repeat"
    android:layout_marginBottom="5sp"
        android:layout_marginLeft="2sp"
        android:layout_marginRight="5sp"
        android:layout_marginTop="0sp"     
             />

              <ImageButton
            android:layout_height="match_parent"
            android:layout_width="0dp"
            android:layout_weight="1"
            android:id="@+id/button_next"
    android:layout_marginBottom="5sp"
        android:layout_marginLeft="2sp"
        android:layout_marginRight="5sp"
        android:layout_marginTop="0sp"     
             />

    </LinearLayout>    
   <LinearLayout
        android:layout_height="0dp"
        android:layout_width="match_parent"
        android:layout_weight="1"
        android:orientation="horizontal">

        <ImageButton
            android:layout_height="match_parent"
            android:layout_width="0dp"
            android:layout_weight="1"
            android:id="@+id/button_bottomleft"
    android:layout_marginBottom="5sp"
        android:layout_marginLeft="2sp"
        android:layout_marginRight="5sp"
        android:layout_marginTop="0sp"                                 
             />
        <ImageButton
            android:layout_height="match_parent"
            android:layout_width="0dp"
            android:layout_weight="1"
            android:id="@+id/button_bottomright"
    android:layout_marginBottom="5sp"
        android:layout_marginLeft="2sp"
        android:layout_marginRight="5sp"
        android:layout_marginTop="0sp"                  
            />        
    </LinearLayout>        

</LinearLayout>

et un extrait de myClass.java:

public void addImageButtons()
    {
        iB_topleft = (ImageButton) findViewById(R.id.button_topleft);
        iB_topright = (ImageButton) findViewById(R.id.button_topright);
        iB_bottomleft = (ImageButton) findViewById(R.id.button_bottomleft);
        iB_bottomright = (ImageButton) findViewById(R.id.button_bottomright);
        iB_next = (ImageButton) findViewById(R.id.button_next);
        iB_repeat = (ImageButton) findViewById(R.id.button_repeat);
    }

    public void setImageNextAndRepeat()
    {

    iB_topleft .setImageResource(R.drawable.aa);
        iB_topright.setImageResource(R.drawable.bb);   

    iB_bottomleft.setImageResource(R.drawable.cc);
        iB_bottomright.setImageResource(R.drawable.dd);   

        iB_next.setImageResource(R.drawable.next);
        iB_repeat.setImageResource(R.drawable.repeat);      
    }
RDX
la source
2
avez-vous vérifié les méthodes de mise à l'échelle fournies par Android? developer.android.com/reference/android/widget/…
bofredo

Réponses:

393

Je veux qu'ils couvrent 75% de la zone des boutons.

Utilisez android:padding="20dp"(ajustez le rembourrage si nécessaire) pour contrôler la taille de l'image sur le bouton.

mais là où certaines images couvrent moins de surface, certaines sont trop grandes pour tenir dans l'imageButton. Comment les redimensionner et les afficher par programme?

Utilisez a android:scaleType="fitCenter"pour qu'Android redimensionne les images et android:adjustViewBounds="true"leur demande d'ajuster leurs limites en raison de la mise à l'échelle.

Tous ces attributs peuvent être définis dans le code sur chacun d'eux ImageButtonau moment de l'exécution. Cependant, il est beaucoup plus facile de définir et de prévisualiser en xml à mon avis.

Aussi, ne l' utilisez passp pour autre chose que la taille du texte, elle est mise à l'échelle en fonction de la préférence de taille du texte définie par l'utilisateur, de sorte que vos spdimensions seront plus grandes que celles prévues si l'utilisateur a un paramètre de texte «grand». À utiliser à la dpplace, car il n'est pas mis à l'échelle par la préférence de taille du texte de l'utilisateur.

Voici un extrait de ce à quoi chaque bouton devrait ressembler:

    <ImageButton
        android:id="@+id/button_topleft"
        android:layout_width="0dp"
        android:layout_height="match_parent"
        android:layout_marginBottom="5dp"
        android:layout_marginLeft="2dp"
        android:layout_marginRight="5dp"
        android:layout_marginTop="0dp"
        android:layout_weight="1"
        android:adjustViewBounds="true"
        android:padding="20dp"
        android:scaleType="fitCenter" />

Bouton échantillon

Steven Byle
la source
@Steven Byle Désolé pour la réponse tardive, mais comment puis-je appliquer la même chose mais pour une mise en page relative?
Nous sommes tous fous ici le
8
Pour ceux qui recherchent, les ImageButtonméthodes le setScaleType(ImageView.ScaleType.CENTER) setAdjustViewBounds(true)font par programme.
ps95
Merci beaucoup :)
Pankaj Nimgade
1
Faites
31

J'utilise le code suivant dans xml

android:adjustViewBounds="true"
android:scaleType="centerInside"
Pratibha Sarode
la source
2
J'ai un rectangle plutôt "plat" et cela fonctionne bien pour moi ... un hic cependant: assurez-vous d'utiliser "android: src" au lieu de "android: background". +1.
Johnny Wu
@johnny Merci mon pote pour le tuyau!
Bishan le
8

Essayez d'utiliser android:scaleType="fitXY"dans i-Imagebutton xml

Swap-IOS-Android
la source
bien que cela ait fonctionné et mis à l'échelle, mais je voulais qu'il couvre 75% de la zone pour une meilleure visibilité.
RDX
@PowerPC essaie d'utiliser framelayout pour donner une hauteur et une largeur à 75% et dans cette disposition de cadre, utilisez votre bouton d'image et définissez le type d'échelle adapté à xy
Swap-IOS-Android
framelayout pour chaque imagebutton à l'intérieur de linearlayout? can u plz clarifier
RDX
@PowerPC Je n'utilise jamais cela mais ce lien peut vous aider à stackoverflow.com/questions/9946580/…
Swap-IOS-Android
1
@StevenByle J'ai envisagé les deux approches, mais comme je voulais une couverture de 75%, votre solution a bien fonctionné. Merci.
RDX
7

J'utilise android:scaleType="fitCenter"avec satisfaction.

Séraphins
la source
3

Reportez-vous au lien ci-dessous et essayez de trouver ce que vous voulez vraiment:

ImageView.ScaleType CENTER Centrez l'image dans la vue, mais n'effectuez aucune mise à l'échelle.

ImageView.ScaleType CENTER_CROP Mettez l'image à l'échelle uniformément (conservez le rapport hauteur / largeur de l'image) afin que les deux dimensions (largeur et hauteur) de l'image soient égales ou supérieures à la dimension correspondante de la vue (moins le remplissage).

ImageView.ScaleType CENTER_INSIDE Mettez l'image à l'échelle uniformément (conservez le rapport hauteur / largeur de l'image) afin que les deux dimensions (largeur et hauteur) de l'image soient égales ou inférieures à la dimension correspondante de la vue (moins le remplissage).

ImageView.ScaleType FIT_CENTER Mettez l'image à l'échelle à l'aide de CENTER.

ImageView.ScaleType FIT_END Mettez l'image à l'échelle à l'aide de END.

ImageView.ScaleType FIT_START Mettez l'image à l'échelle à l'aide de START.

ImageView.ScaleType FIT_XY Mettez l'image à l'échelle à l'aide de FILL.

ImageView.ScaleType MATRIX Mise à l'échelle à l'aide de la matrice d'image lors du dessin.

https://developer.android.com/reference/android/widget/ImageView.ScaleType.html

Nhat Dinh
la source
1

J'ai récemment découvert par accident que puisque vous avez plus de contrôle sur un ImageView, vous pouvez définir un onclicklistener pour une image, voici un exemple de bouton d'image créé dynamiquement

private int id;
private bitmap bmp;
    LinearLayout.LayoutParams familyimagelayout = new LinearLayout.LayoutParams(
                    LinearLayout.LayoutParams.MATCH_PARENT,LinearLayout.LayoutParams.WRAP_CONTENT );

    final ImageView familyimage = new ImageView(this);
            familyimage.setBackground(null);
            familyimage.setImageBitmap(bmp);
            familyimage.setScaleType(ImageView.ScaleType.FIT_START);
            familyimage.setAdjustViewBounds(true);
            familyimage.setId(id);
            familyimage.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    //what you want to do put here
                }
            });
David
la source
Ce n'est pas une mauvaise idée. J'aime.
Boris Karloff
0

Cela a bien fonctionné dans mon cas. Tout d'abord, vous téléchargez une image et la renommez comme iconimage, la localise dans le dossier dessinable. Vous pouvez modifier la taille en définissant android:layout_widthou android:layout_height. Enfin, nous avons

 <ImageButton
        android:id="@+id/answercall"
        android:layout_width="120dp"
        android:layout_height="80dp"
        android:src="@drawable/iconimage"
        android:layout_alignParentBottom="true"
        android:layout_alignParentLeft="true"
        android:scaleType="fitCenter" />
Jame
la source
0

Vous pouvez créer votre widget ImageButton comme je l'ai fait. Dans mon cas, j'avais besoin d'un widget avec une taille d'icône fixe. Commençons par les attributs personnalisés:

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <declare-styleable name="ImageButtonFixedIconSize">
        <attr name="imageButton_icon" format="reference" />
        <attr name="imageButton_iconWidth" format="dimension" />
        <attr name="imageButton_iconHeight" format="dimension" />
    </declare-styleable>
</resources>

La classe de widget est assez simple (le point clé est les calculs de remplissage dans la méthode onLayout ):

class ImageButtonFixedIconSize
@JvmOverloads
constructor(
    context: Context,
    attrs: AttributeSet? = null,
    defStyleAttr: Int = android.R.attr.imageButtonStyle
) : ImageButton(context, attrs, defStyleAttr) {

    private lateinit var icon: Drawable

    @Px
    private var iconWidth: Int = 0
    @Px
    private var iconHeight: Int = 0

    init {
        scaleType = ScaleType.FIT_XY
        attrs?.let { retrieveAttributes(it) }
    }

    /**
     *
     */
    override fun onLayout(changed: Boolean, left: Int, top: Int, right: Int, bottom: Int) {
        val width = right - left
        val height = bottom - top

        val horizontalPadding = if(width > iconWidth) (width - iconWidth) / 2 else 0
        val verticalPadding = if(height > iconHeight) (height - iconHeight) / 2 else 0

        setPadding(horizontalPadding, verticalPadding, horizontalPadding, verticalPadding)

        setImageDrawable(icon)

        super.onLayout(changed, left, top, right, bottom)
    }

    /**
     *
     */
    private fun retrieveAttributes(attrs: AttributeSet) {
        val typedArray = context.obtainStyledAttributes(attrs, R.styleable.ImageButtonFixedIconSize)

        icon = typedArray.getDrawable(R.styleable.ImageButtonFixedIconSize_imageButton_icon)!!

        iconWidth = typedArray.getDimension(R.styleable.ImageButtonFixedIconSize_imageButton_iconWidth, 0f).toInt()
        iconHeight = typedArray.getDimension(R.styleable.ImageButtonFixedIconSize_imageButton_iconHeight, 0f).toInt()

        typedArray.recycle()
    }
}

Et enfin, vous devriez utiliser votre widget comme ceci:

<com.syleiman.gingermoney.ui.common.controls.ImageButtonFixedIconSize
    android:layout_width="90dp"
    android:layout_height="63dp"

    app:imageButton_icon="@drawable/ic_backspace"
    app:imageButton_iconWidth="20dp"
    app:imageButton_iconHeight="15dp"

    android:id="@+id/backspaceButton"
    tools:ignore="ContentDescription"
    />
Alex Shevelev
la source