Android BitmapUtils工具類

来源:https://www.cnblogs.com/94xiyang/archive/2018/07/26/9373165.html
-Advertisement-
Play Games

public final class BitmapUtils { public static final String TAG = "BitmapUtil"; private static int sShotScreenWidth = 480; private static int sShotScr... ...


public final class BitmapUtils {
    public static final String TAG = "BitmapUtil";
    private static int sShotScreenWidth = 480;
    private static int sShotScreenHeight = 720;
    private static int sShotScreenSize = sShotScreenWidth * sShotScreenHeight;

    @SuppressLint("StaticFieldLeak")
    private static  Context mContext;
    @SuppressLint("StaticFieldLeak")
    private static Activity mActivity;

    public void init(Context context,Activity ac) {
        mContext=context;
        mActivity=ac;

        DisplayMetrics dm = new DisplayMetrics();
        ac.getWindowManager().getDefaultDisplay().getMetrics(dm);
        //獲取屏幕解析度
        sShotScreenWidth = dm.widthPixels;
        sShotScreenHeight = dm.heightPixels;
        sShotScreenSize = sShotScreenWidth * sShotScreenHeight;
    }

    /**
     * 圖片合成
     * 
     * @param bitmap 點陣圖1
     * @param mark 點陣圖2
     * @return Bitmap
     */
    public static Bitmap createBitmap(Bitmap bitmap, Bitmap mark) {
        int w = bitmap.getWidth();
        int h = bitmap.getHeight();
        int mW = mark.getWidth();
        int mH = mark.getHeight();
        Bitmap newbitmap = Bitmap.createBitmap(w, h, Config.ARGB_8888);// 創建一個長寬一樣的點陣圖

        Canvas cv = new Canvas(newbitmap);
        cv.drawBitmap(bitmap, 0, 0, null);// 在 0,0坐標開始畫入bitmap
        cv.drawBitmap(mark, w - mW , h - mH , null);// 在右下角畫入水印mark
        cv.save(Canvas.ALL_SAVE_FLAG);// 保存
        cv.restore();// 存儲
        return newbitmap;
    }

    /**
     * 放大縮小圖片
     * @param bitmap 點陣圖
     * @param w 新的寬度
     * @param h 新的高度
     * @return Bitmap
     */
    public static Bitmap zoomBitmap(Bitmap bitmap, int w, int h) {
        int width = bitmap.getWidth();
        int height = bitmap.getHeight();
        Matrix matrix = new Matrix();
        float scaleWidht = ((float) w / width);
        float scaleHeight = ((float) h / height);
        matrix.postScale(scaleWidht, scaleHeight);
        return Bitmap.createBitmap(bitmap, 0, 0, width, height, matrix, true);
    }

    /**
     * 旋轉圖片
     * @param bitmap 要旋轉的圖片
     * @param angle 旋轉角度
     * @return bitmap
     */
    public static Bitmap rotate(Bitmap bitmap,int angle) {
        Matrix matrix = new Matrix();
        matrix.postRotate(angle);
        return Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(),
                bitmap.getHeight(), matrix, true);
    }

    /**
     * 圓形圖片
     *@param source 點陣圖
     * @param strokeWidth 裁剪範圍 0表示最大
     * @param bl 是否需要描邊
     * @param bl 畫筆粗細
     * @param bl 顏色代碼
     *  @return bitmap
     */
    public static Bitmap createCircleBitmap(Bitmap source, int strokeWidth, boolean bl,int edge,int color) {

        int diameter = source.getWidth() < source.getHeight() ? source.getWidth() : source.getHeight();
        Bitmap target = Bitmap.createBitmap(diameter, diameter, Config.ARGB_8888);
        Canvas canvas = new Canvas(target);//創建畫布

        Paint paint = new Paint();
        paint.setAntiAlias(true);
        canvas.drawCircle(diameter / 2, diameter / 2, diameter / 2, paint);//繪製圓形
        paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));//取相交裁剪
        canvas.drawBitmap(source, strokeWidth, strokeWidth, paint);
        if(bl) {
            if (color == 0) color = 0xFFFEA248;//預設橘黃色
            paint.setColor(color);
            paint.setStyle(Paint.Style.STROKE);//描邊
            paint.setStrokeWidth(edge);
            canvas.drawCircle(diameter / 2, diameter / 2, diameter / 2, paint);
        }
        return target;
    }

    /**
     * 圓角圖片
     * @param bitmap 點陣圖
     * @param rx x方向上的圓角半徑
     * @param ry y方向上的圓角半徑
     * @param bl 是否需要描邊
     * @param bl 畫筆粗細
     * @param bl 顏色代碼
     * @return bitmap
     */
    public static Bitmap createCornerBitmap(Bitmap bitmap,int rx,int ry,boolean bl,int edge,int color) {
        Bitmap output = Bitmap.createBitmap(bitmap.getWidth(), bitmap.getHeight(), Config.ARGB_8888);
        Canvas canvas = new Canvas(output);//創建畫布

        Paint paint = new Paint();
        paint.setAntiAlias(true);
        Rect rect = new Rect(0, 0, bitmap.getWidth(), bitmap.getHeight());
        RectF rectF = new RectF(rect);
        canvas.drawRoundRect(rectF, rx, ry, paint);//繪製圓角矩形
        paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN));//取相交裁剪
        canvas.drawBitmap(bitmap, rect, rect, paint);
        if(bl) {
            if (color == 0) color = 0xFFFEA248;//預設橘黃色
            paint.setColor(color);
            paint.setColor(color);
            paint.setStyle(Paint.Style.STROKE);//描邊
            paint.setStrokeWidth(edge);
            canvas.drawRoundRect(rectF, rx, ry, paint);
        }
        return output;
    }

    /**
     *  按比例裁剪圖片
     *  @param bitmap 點陣圖
     *  @param wScale 裁剪寬 0~100%
     *  @param hScale 裁剪高 0~100%
      * @return bitmap
     */
    public static Bitmap cropBitmap(Bitmap bitmap, float wScale, float hScale) {
        int w = bitmap.getWidth();
        int h = bitmap.getHeight();

        int wh = (int) (w * wScale);
        int hw = (int) (h * hScale);

        int retX = (int) (w * (1 - wScale) / 2);
        int retY = (int) (h * (1 - hScale) / 2);

        return Bitmap.createBitmap(bitmap, retX, retY, wh, hw, null, false);
    }

    /**
     * 獲得帶倒影的圖片方法
     * @param bitmap 點陣圖
     * @param region 倒影區域 0.1~1
     * @return bitmap
     */
    public static Bitmap createReflectionBitmap(Bitmap bitmap,float region) {

        int width = bitmap.getWidth();
        int height = bitmap.getHeight();
        Matrix matrix = new Matrix();
        matrix.preScale(1, -1);//鏡像縮放
        Bitmap reflectionBitmap = Bitmap.createBitmap(
                                                  bitmap,0
                                                , (int)(height*(1-region))//從哪個點開始繪製
                                                , width
                                                ,(int) (height*region)//繪製多高
                                                , matrix, false);

        Bitmap reflectionWithBitmap = Bitmap.createBitmap(width,height+ (int) (height*region),
                                                            Config.ARGB_8888);
        Canvas canvas = new Canvas(reflectionWithBitmap);
        canvas.drawBitmap(bitmap, 0, 0, null);
        canvas.drawBitmap(reflectionBitmap, 0, height , null);

        LinearGradient shader = new LinearGradient(0, bitmap.getHeight(), 0,
                                                reflectionWithBitmap.getHeight()
                                                , 0x70ffffff, 0x00ffffff, TileMode.CLAMP);

        Paint paint = new Paint();
        paint.setShader(shader);
        paint.setXfermode(new PorterDuffXfermode(Mode.DST_IN));//取兩層繪製交集。顯示下層。
        canvas.drawRect(0, height, width, reflectionWithBitmap.getHeight() , paint);
        return reflectionWithBitmap;
    }

    /**
     * 圖片質量壓縮
     * @param bitmap
     * @param many 百分比
     * @return
     */
    public static Bitmap compressBitmap(Bitmap bitmap, float many){
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        bitmap.compress(Bitmap.CompressFormat.JPEG, (int)many*100, baos);
        ByteArrayInputStream isBm = new ByteArrayInputStream(baos.toByteArray());
        return BitmapFactory.decodeStream(isBm, null, null);
    }

    /**
     * 高級圖片質量壓縮
     *@param bitmap 點陣圖
     * @param maxSize 壓縮後的大小,單位kb
     */
    public static Bitmap imageZoom(Bitmap bitmap, double maxSize) {
        // 將bitmap放至數組中,意在獲得bitmap的大小(與實際讀取的原文件要大)
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        // 格式、質量、輸出流
        bitmap.compress(Bitmap.CompressFormat.PNG, 70, baos);
        byte[] b = baos.toByteArray();
        // 將位元組換成KB
        double mid = b.length / 1024;
        // 獲取bitmap大小 是允許最大大小的多少倍
        double i = mid / maxSize;
        // 判斷bitmap占用空間是否大於允許最大空間 如果大於則壓縮 小於則不壓縮
        doRecycledIfNot(bitmap);
        if (i > 1) {
            // 縮放圖片 此處用到平方根 將寬頻和高度壓縮掉對應的平方根倍
            // (保持寬高不變,縮放後也達到了最大占用空間的大小)
            return scaleWithWH(bitmap,bitmap.getWidth() / Math.sqrt(i),
                            bitmap.getHeight() / Math.sqrt(i));
        }
        return null;
    }

    /***
     * 圖片縮放
     *@param bitmap 點陣圖
     * @param w 新的寬度
     * @param h 新的高度
     * @return Bitmap
     */
    public static Bitmap scaleWithWH(Bitmap bitmap, double w, double h) {
        if (w == 0 || h == 0 || bitmap == null) {
            return bitmap;
        } else {
            int width = bitmap.getWidth();
            int height = bitmap.getHeight();

            Matrix matrix = new Matrix();
            float scaleWidth = (float) (w / width);
            float scaleHeight = (float) (h / height);
            
            matrix.postScale(scaleWidth, scaleHeight);
            return Bitmap.createBitmap(bitmap, 0, 0, width, height,
                    matrix, true);
        }
    }

    /**
     * YUV視頻流格式轉bitmap
     * @param data YUV視頻流格式
     * @return width 設置寬度
     * @return width 設置高度
     */
    public static Bitmap getBitmap(byte[] data, int width, int height) {
        Bitmap bitmap;
        YuvImage yuvimage = new YuvImage(data, ImageFormat.NV21, width, height, null);
        //data是onPreviewFrame參數提供
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        yuvimage.compressToJpeg(new Rect(0, 0, yuvimage.getWidth(), yuvimage.getHeight()), 100, baos);//
        // 80--JPG圖片的質量[0-100],100最高
        byte[] rawImage = baos.toByteArray();
        BitmapFactory.Options options = new BitmapFactory.Options();
        SoftReference<Bitmap> softRef = new SoftReference<Bitmap>(BitmapFactory.decodeByteArray(rawImage, 0, rawImage
                .length, options));
        bitmap = softRef.get();
        return bitmap;
    }

    /**
     * 圖片路徑轉bitmap
     * @param file 圖片的絕對路徑
     * @return bitmap
     */
    public static Bitmap getAssetImage(String file) {
        Bitmap bitmap = null;
        AssetManager am = mActivity.getAssets();
        try {
            InputStream is = am.open(file);
            bitmap = BitmapFactory.decodeStream(is);
            is.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
        return bitmap;
    }

    /**
     * bitmap保存到指定路徑
     * @param file 圖片的絕對路徑
     * @param file 點陣圖
     * @return bitmap
     */
    public static  boolean saveFile(String file, Bitmap bmp) {
        if(TextUtils.isEmpty(file) || bmp == null) return false;
        
        File f = new File(file);
        if (f.exists()) {
            f.delete();
        }else {
            File p = f.getParentFile();
            if(!p.exists()) {
                p.mkdirs();
            }
        }
        try {
            FileOutputStream out = new FileOutputStream(f);
            bmp.compress(Bitmap.CompressFormat.JPEG, 100, out);
            out.flush();
            out.close();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
            return false;
        }
        return true;
    }

    /**
     * 回收一個未被回收的Bitmap
     *@param bitmap
     */
    public static void doRecycledIfNot(Bitmap bitmap) {
        if (!bitmap.isRecycled()) {
            bitmap.recycle();
        }
    }
}

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 創建Execl、寫入Execl數據、導入U盤 發送帶附件的郵件 ...
  • 2018年6月5日蘋果`WWDC`開發者大會之後,蘋果已經永久暫停`4006701855`中文開發者電話支持。 現在需要電話支持的話,只能被動要求,讓蘋果客服打電話給你。那怎麼獲得蘋果開發者咨詢服務呢? 請參照博文~ ...
  • 有時候後臺json數據返回的欄位含有“id”,也有可能是有時候為了減少代碼的冗餘,兩頁面之間只是數據模型個別屬性的區別,所以這時候最好是用到模型屬性的替換,用新的屬性替換返回的json數據的欄位。這裡主要總結了兩種使用方法,都是在項目已經集成別人封裝好的解析json數據的庫的基礎上。 以常見Yima ...
  • Instruments 使用Xcode自帶的 Instruments 檢測工具對App進行檢測,它可以檢測程式在運行時的記憶體泄漏。這是與靜態記憶體檢測的最大不同。 Open Instruments 打開Instruments的兩種方式: 第一種: 打開Xcode,點擊 Product -> profi ...
  • "RetrofitUtils" "GitHub地址,幫忙給個Star" 項目介紹 Retrofit+Okhttp輔助類的簡單封裝,vesion 1.0.X 實現了Get,Post Form、Post Json 三種形式的網路請求,後續版本會實現文件上傳下載and各類raw的請求方式。 功能 1. G ...
  • (1).場景一:外部滑動方向跟內部滑動方向不一致,比如外部左右滑動,內部上下滑動 ViewPager+Fragment配合使用,會有滑動衝突,但是ViewPager內部處理了這種滑動衝突 如果採用的不是ViewPager而是ScrollView就必須手動處理滑動事件 上下滑動時,需要上一級view把 ...
  • 雲之聲離線Jar包和so文件下載地址 下載地址 Android SoundPool語音播放類 ...
  • iOS學習——核心動畫 1、什麼是核心動畫 Core Animation(核心動畫)是一組功能強大、效果華麗的動畫API,無論在iOS系統或者在你開發的App中,都有大量應用。核心動畫所在的位置如下圖所示,可以看到,核心動畫位於UIKit的下一層,相比UIView動畫,它可以實現更複雜的動畫效果。 ...
一周排行
    -Advertisement-
    Play Games
  • 示例項目結構 在 Visual Studio 中創建一個 WinForms 應用程式後,項目結構如下所示: MyWinFormsApp/ │ ├───Properties/ │ └───Settings.settings │ ├───bin/ │ ├───Debug/ │ └───Release/ ...
  • [STAThread] 特性用於需要與 COM 組件交互的應用程式,尤其是依賴單線程模型(如 Windows Forms 應用程式)的組件。在 STA 模式下,線程擁有自己的消息迴圈,這對於處理用戶界面和某些 COM 組件是必要的。 [STAThread] static void Main(stri ...
  • 在WinForm中使用全局異常捕獲處理 在WinForm應用程式中,全局異常捕獲是確保程式穩定性的關鍵。通過在Program類的Main方法中設置全局異常處理,可以有效地捕獲並處理未預見的異常,從而避免程式崩潰。 註冊全局異常事件 [STAThread] static void Main() { / ...
  • 前言 給大家推薦一款開源的 Winform 控制項庫,可以幫助我們開發更加美觀、漂亮的 WinForm 界面。 項目介紹 SunnyUI.NET 是一個基於 .NET Framework 4.0+、.NET 6、.NET 7 和 .NET 8 的 WinForm 開源控制項庫,同時也提供了工具類庫、擴展 ...
  • 說明 該文章是屬於OverallAuth2.0系列文章,每周更新一篇該系列文章(從0到1完成系統開發)。 該系統文章,我會儘量說的非常詳細,做到不管新手、老手都能看懂。 說明:OverallAuth2.0 是一個簡單、易懂、功能強大的許可權+可視化流程管理系統。 有興趣的朋友,請關註我吧(*^▽^*) ...
  • 一、下載安裝 1.下載git 必須先下載並安裝git,再TortoiseGit下載安裝 git安裝參考教程:https://blog.csdn.net/mukes/article/details/115693833 2.TortoiseGit下載與安裝 TortoiseGit,Git客戶端,32/6 ...
  • 前言 在項目開發過程中,理解數據結構和演算法如同掌握蓋房子的秘訣。演算法不僅能幫助我們編寫高效、優質的代碼,還能解決項目中遇到的各種難題。 給大家推薦一個支持C#的開源免費、新手友好的數據結構與演算法入門教程:Hello演算法。 項目介紹 《Hello Algo》是一本開源免費、新手友好的數據結構與演算法入門 ...
  • 1.生成單個Proto.bat內容 @rem Copyright 2016, Google Inc. @rem All rights reserved. @rem @rem Redistribution and use in source and binary forms, with or with ...
  • 一:背景 1. 講故事 前段時間有位朋友找到我,說他的窗體程式在客戶這邊出現了卡死,讓我幫忙看下怎麼回事?dump也生成了,既然有dump了那就上 windbg 分析吧。 二:WinDbg 分析 1. 為什麼會卡死 窗體程式的卡死,入口門檻很低,後續往下分析就不一定了,不管怎麼說先用 !clrsta ...
  • 前言 人工智慧時代,人臉識別技術已成為安全驗證、身份識別和用戶交互的關鍵工具。 給大家推薦一款.NET 開源提供了強大的人臉識別 API,工具不僅易於集成,還具備高效處理能力。 本文將介紹一款如何利用這些API,為我們的項目添加智能識別的亮點。 項目介紹 GitHub 上擁有 1.2k 星標的 C# ...