将位图缩放至80%

7
我正在尝试使用options.inSampleSize来缩放位图,但据我所知,缩放比例如下:
  • 如果inSampleSize为1,则结果图像为100%

  • 如果inSampleSize为2,则结果图像为50%

  • 如果inSampleSize为3,则结果图像为33%

  • 如果inSampleSize为4,则结果图像为25%

  • 如果inSampleSize为5,则结果图像为20%

但我想要的是一个缩放为80%的结果图像。我该怎么做?

3个回答

18

你能不能不使用Bitmap.createScaledBitmap方法?

int srcWidth = srcBitmap.getWidth();
int srcHeight = srcBitmap.getHeight();
int dstWidth = (int)(srcWidth*0.8f);
int dstHeight = (int)(srcHeight*0.8f);
Bitmap dstBitmap = Bitmap.createScaledBitmap(srcBitmap, dstWidth, dstHeight, true);

最佳答案在这里 :) - CandleCoder
请注意,此操作不会保留原始位图的纵横比。 - Nima GT

2
你可以使用这个类中的calculateSampleSize函数,它完全基于计算。
package com.abhan.example.util;

import android.content.res.Resources;
import android.graphics.Bitmap;
import android.graphics.Bitmap.Config;
import android.graphics.BitmapFactory;
import android.graphics.BitmapFactory.Options;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.Rect;

public class ScalingUtilities {

    public static Bitmap decodeResource(Resources res, int resId, int dstWidth,
            int dstHeight, ScalingLogic scalingLogic) {
        Options options = new Options();
        options.inJustDecodeBounds = true;
        BitmapFactory.decodeResource(res, resId, options);
        options.inJustDecodeBounds = false;
        options.inSampleSize = calculateSampleSize(options.outWidth,
                options.outHeight, dstWidth, dstHeight, scalingLogic);
        Bitmap unscaledBitmap = BitmapFactory.decodeResource(res, resId,
                options);

        return unscaledBitmap;
    }

    public static Bitmap createScaledBitmap(Bitmap unscaledBitmap,
            int dstWidth, int dstHeight, ScalingLogic scalingLogic) {
        Rect srcRect = calculateSrcRect(unscaledBitmap.getWidth(),
                unscaledBitmap.getHeight(), dstWidth, dstHeight, scalingLogic);
        Rect dstRect = calculateDstRect(unscaledBitmap.getWidth(),
                unscaledBitmap.getHeight(), dstWidth, dstHeight, scalingLogic);
        Bitmap scaledBitmap = Bitmap.createBitmap(dstRect.width(),
                dstRect.height(), Config.ARGB_8888);
        Canvas canvas = new Canvas(scaledBitmap);
        canvas.drawBitmap(unscaledBitmap, srcRect, dstRect, new Paint(
                Paint.FILTER_BITMAP_FLAG));

        return scaledBitmap;
    }

    public static enum ScalingLogic {
        CROP, FIT
    }

    public static int calculateSampleSize(int srcWidth, int srcHeight,
            int dstWidth, int dstHeight, ScalingLogic scalingLogic) {
        if (scalingLogic == ScalingLogic.FIT) {
            final float srcAspect = (float) srcWidth / (float) srcHeight;
            final float dstAspect = (float) dstWidth / (float) dstHeight;

            if (srcAspect > dstAspect) {
                return srcWidth / dstWidth;
            } else {
                return srcHeight / dstHeight;
            }
        } else {
            final float srcAspect = (float) srcWidth / (float) srcHeight;
            final float dstAspect = (float) dstWidth / (float) dstHeight;

            if (srcAspect > dstAspect) {
                return srcHeight / dstHeight;
            } else {
                return srcWidth / dstWidth;
            }
        }
    }

    public static Rect calculateSrcRect(int srcWidth, int srcHeight,
            int dstWidth, int dstHeight, ScalingLogic scalingLogic) {
        if (scalingLogic == ScalingLogic.CROP) {
            final float srcAspect = (float) srcWidth / (float) srcHeight;
            final float dstAspect = (float) dstWidth / (float) dstHeight;

            if (srcAspect > dstAspect) {
                final int srcRectWidth = (int) (srcHeight * dstAspect);
                final int srcRectLeft = (srcWidth - srcRectWidth) / 2;
                return new Rect(srcRectLeft, 0, srcRectLeft + srcRectWidth,
                        srcHeight);
            } else {
                final int srcRectHeight = (int) (srcWidth / dstAspect);
                final int scrRectTop = (int) (srcHeight - srcRectHeight) / 2;
                return new Rect(0, scrRectTop, srcWidth, scrRectTop
                        + srcRectHeight);
            }
        } else {
            return new Rect(0, 0, srcWidth, srcHeight);
        }
    }

    public static Rect calculateDstRect(int srcWidth, int srcHeight,
            int dstWidth, int dstHeight, ScalingLogic scalingLogic) {
        if (scalingLogic == ScalingLogic.FIT) {
            final float srcAspect = (float) srcWidth / (float) srcHeight;
            final float dstAspect = (float) dstWidth / (float) dstHeight;

            if (srcAspect > dstAspect) {
                return new Rect(0, 0, dstWidth, (int) (dstWidth / srcAspect));
            } else {
                return new Rect(0, 0, (int) (dstHeight * srcAspect), dstHeight);
            }
        } else {
            return new Rect(0, 0, dstWidth, dstHeight);
        }
    }

}

希望这能对你有所帮助。

谢谢。


-1

我认为你可能误解了inSampleSize的作用。它是为了节省内存而设计的。如果你只是想将图像缩小到80%,那么你可以在将文件读入内存后使用矩阵将其缩小(或放大)。


调整大小是否按比例缩放? - Pouton Gerald
如果您使用矩阵来缩放图像,并且在缩放调用中使用相同的浮点数参数,则它将按比例缩放。以下是一个示例... https://dev59.com/Emoy5IYBdhLWcg3wL7H1 - csamsonrun
感谢您与我分享您的知识,我也点赞了。 - Pouton Gerald

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接