web-dev-qa-db-fra.com

Android Centre de recadrage de Bitmap

J'ai des bitmaps qui sont des carrés ou des rectangles. Je prends le côté le plus court et fais quelque chose comme ça:

int value = 0;
if (bitmap.getHeight() <= bitmap.getWidth()) {
    value = bitmap.getHeight();
} else {
    value = bitmap.getWidth();
}

Bitmap finalBitmap = null;
finalBitmap = Bitmap.createBitmap(bitmap, 0, 0, value, value);

Ensuite, je l'adapte à un bitmap 144 x 144 en utilisant ceci:

Bitmap lastBitmap = null;
lastBitmap = Bitmap.createScaledBitmap(finalBitmap, 144, 144, true);

Le problème est qu'il recadre le coin supérieur gauche du bitmap d'origine. Quelqu'un a-t-il le code pour recadrer le centre du bitmap?

139
Maurice

enter image description here

Ceci peut être réalisé avec: Bitmap.createBitmap (source, x, y, largeur, hauteur)

if (srcBmp.getWidth() >= srcBmp.getHeight()){

  dstBmp = Bitmap.createBitmap(
     srcBmp, 
     srcBmp.getWidth()/2 - srcBmp.getHeight()/2,
     0,
     srcBmp.getHeight(), 
     srcBmp.getHeight()
     );

}else{

  dstBmp = Bitmap.createBitmap(
     srcBmp,
     0, 
     srcBmp.getHeight()/2 - srcBmp.getWidth()/2,
     srcBmp.getWidth(),
     srcBmp.getWidth() 
     );
}
334
Lumis

Bien que la plupart des réponses ci-dessus fournissent un moyen de le faire, il existe déjà un moyen intégré pour le faire et il s’agit d’une ligne de code (ThumbnailUtils.extractThumbnail())

int dimension = getSquareCropDimensionForBitmap(bitmap);
bitmap = ThumbnailUtils.extractThumbnail(bitmap, dimension, dimension);

...

//I added this method because people keep asking how 
//to calculate the dimensions of the bitmap...see comments below
public int getSquareCropDimensionForBitmap(Bitmap bitmap)
{
    //use the smallest dimension of the image to crop to
    return Math.min(bitmap.getWidth(), bitmap.getHeight());
}

Si vous souhaitez que l'objet bitmap soit recyclé, vous pouvez transmettre les options qui le rendent ainsi:

bitmap = ThumbnailUtils.extractThumbnail(bitmap, dimension, dimension, ThumbnailUtils.OPTIONS_RECYCLE_INPUT);

De: Documentation ThumbnailUtils

public statique Bitmap extractThumbnail (source Bitmap, largeur int, hauteur hauteur)

Ajouté dans l'API de niveau 8 Crée une image bitmap centrée de la taille souhaitée.

Paramètres source source image source largeur cible largeur hauteur hauteur visée

J'avais parfois des erreurs de mémoire lorsque j'utilisais la réponse acceptée, et ThumbnailUtils résolvait ces problèmes pour moi. De plus, c'est beaucoup plus propre et plus réutilisable.

295
DiscDev

Avez-vous envisagé de le faire depuis le layout.xml? Vous pouvez définir pour votre ImageView le ScaleType à Android:scaleType="centerCrop" et définissez les dimensions de l’image dans le ImageView à l’intérieur du layout.xml.

12
Ovidiu Latcu

Voici un extrait plus complet qui délimite le centre d'un [bitmap] de dimensions arbitraires et adapte le résultat au résultat souhaité [IMAGE_SIZE]. Ainsi, vous obtiendrez toujours un carré [croppedBitmap] du centre de l’image avec une taille fixe. idéal pour les vignettes et autres.

C'est une combinaison plus complète des autres solutions.

final int IMAGE_SIZE = 255;
boolean landscape = bitmap.getWidth() > bitmap.getHeight();

float scale_factor;
if (landscape) scale_factor = (float)IMAGE_SIZE / bitmap.getHeight();
else scale_factor = (float)IMAGE_SIZE / bitmap.getWidth();
Matrix matrix = new Matrix();
matrix.postScale(scale_factor, scale_factor);

Bitmap croppedBitmap;
if (landscape){
    int start = (tempBitmap.getWidth() - tempBitmap.getHeight()) / 2;
    croppedBitmap = Bitmap.createBitmap(tempBitmap, start, 0, tempBitmap.getHeight(), tempBitmap.getHeight(), matrix, true);
} else {
    int start = (tempBitmap.getHeight() - tempBitmap.getWidth()) / 2;
    croppedBitmap = Bitmap.createBitmap(tempBitmap, 0, start, tempBitmap.getWidth(), tempBitmap.getWidth(), matrix, true);
}
9
mschmoock

Vous pouvez utiliser le code suivant qui peut résoudre votre problème.

Matrix matrix = new Matrix();
matrix.postScale(0.5f, 0.5f);
Bitmap croppedBitmap = Bitmap.createBitmap(bitmapOriginal, 100, 100,100, 100, matrix, true);

La méthode ci-dessus consiste à effectuer un post-appel de l'image avant le rognage afin d'obtenir le meilleur résultat possible avec une image rognée sans erreur OOM.

Pour plus de détails, vous pouvez vous référer ce blog

9
Hitesh Patel

Probablement la solution la plus simple à ce jour:

public static Bitmap cropCenter(Bitmap bmp) {
    int dimension = Math.min(bmp.getWidth(), bmp.getHeight());
    return ThumbnailUtils.extractThumbnail(bmp, dimension, dimension);
}

importations:

import Android.media.ThumbnailUtils;
import Java.lang.Math;
import Android.graphics.Bitmap;
6
Kirill Kulakov

Pour corriger la solution @willsteel:

if (landscape){
                int start = (tempBitmap.getWidth() - tempBitmap.getHeight()) / 2;
                croppedBitmap = Bitmap.createBitmap(tempBitmap, start, 0, tempBitmap.getHeight(), tempBitmap.getHeight(), matrix, true);
            } else {
                int start = (tempBitmap.getHeight() - tempBitmap.getWidth()) / 2;
                croppedBitmap = Bitmap.createBitmap(tempBitmap, 0, start, tempBitmap.getWidth(), tempBitmap.getWidth(), matrix, true);
            }
3
Yman
public static Bitmap resizeAndCropCenter(Bitmap bitmap, int size, boolean recycle) {
    int w = bitmap.getWidth();
    int h = bitmap.getHeight();
    if (w == size && h == size) return bitmap;
    // scale the image so that the shorter side equals to the target;
    // the longer side will be center-cropped.
    float scale = (float) size / Math.min(w,  h);
    Bitmap target = Bitmap.createBitmap(size, size, getConfig(bitmap));
    int width = Math.round(scale * bitmap.getWidth());
    int height = Math.round(scale * bitmap.getHeight());
    Canvas canvas = new Canvas(target);
    canvas.translate((size - width) / 2f, (size - height) / 2f);
    canvas.scale(scale, scale);
    Paint paint = new Paint(Paint.FILTER_BITMAP_FLAG | Paint.DITHER_FLAG);
    canvas.drawBitmap(bitmap, 0, 0, Paint);
    if (recycle) bitmap.recycle();
    return target;
}

private static Bitmap.Config getConfig(Bitmap bitmap) {
    Bitmap.Config config = bitmap.getConfig();
    if (config == null) {
        config = Bitmap.Config.ARGB_8888;
    }
    return config;
}
1
kakopappa
public Bitmap getResizedBitmap(Bitmap bm) {
    int width = bm.getWidth();
    int height = bm.getHeight();

    int narrowSize = Math.min(width, height);
    int differ = (int)Math.abs((bm.getHeight() - bm.getWidth())/2.0f);
    width  = (width  == narrowSize) ? 0 : differ;
    height = (width == 0) ? differ : 0;

    Bitmap resizedBitmap = Bitmap.createBitmap(bm, width, height, narrowSize, narrowSize);
    bm.recycle();
    return resizedBitmap;
}
1
Vahe Gharibyan