android 圖片二維碼識別和保存(一)


   最新業務開發二維碼識別的功能,這個功能,在很多應用上都有,比如微信長按圖片識別二維碼,如果圖片中存在可以識別的二維碼時,可以增加一個選項 識別二維碼。那么如何去實現這個功能呢。這里其實也非常簡單,首先對圖片進行二維碼識別,識別結果返回的時候判斷是否有二維碼,有則增加識別二維碼選項。

   對於識別二維碼,目前主流的就是zxing和zbar,對於這兩者的選型,一般來說移動智能手機更多選擇zxing,因為zxing更適合,zbar適合嵌入式硬件,兩者對於QR圖形碼能力相差無幾,但是zxing的資料明顯更多一些。各位根據自己的情況進行調整。

    二維條碼/二維碼(2-dimensional bar code)是用某種特定的幾何圖形按一定規律在平面(二維方向上)分布的黑白相間的圖形記錄數據符號信息的。
 在代碼編制上巧妙地利用構成計算機內部邏輯基礎的“0”、“1”比特流的概念,使用若干個與二進制相對應的幾何形體來表示文字數值信息,通過圖象輸入設備或光電掃描設備自動識讀以實現信息自動處理:它具有條碼技術的一些共性:每種碼制有其特定的字符集。
 每個字符占有一定的寬度;具有一定的校驗功能等。同時還具有對不同行的信息自動識別功能、及處理圖形旋轉變化點。

  對於信息量越大的二維碼圖形點越多,多到一定程度識別就困難了,二維碼有一定的糾錯能力,但是不是萬能的。

 

  首先給出識別二維碼的實現,二維碼識別一組數據。

 /**
     * 對二維碼圖片解碼結果進行編碼
     *
     * @param str
     * @return
     */
    public static String recode(String str) {
        String formart = "";

        try {
            boolean ISO = Charset.forName("ISO-8859-1").newEncoder()
                    .canEncode(str);
            if (ISO) {
                formart = new String(str.getBytes("ISO-8859-1"), "UTF-8");
            } else {
                formart = str;
            }
        } catch (UnsupportedEncodingException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (Exception e){

        }
        return formart;
    }

其次,二維碼生成的代碼如下:

public static Result handleQRCodeFormBitmap(Bitmap bitmap) {

        Map<DecodeHintType, Object> hints = new EnumMap<>(DecodeHintType.class);
        hints.put(DecodeHintType.CHARACTER_SET, "utf-8");
        hints.put(DecodeHintType.TRY_HARDER, Boolean.TRUE);
        hints.put(DecodeHintType.POSSIBLE_FORMATS, BarcodeFormat.QR_CODE);

        RGBLuminanceSource source = new RGBLuminanceSource(bitmap);
        BinaryBitmap bitmap1 = new BinaryBitmap(new HybridBinarizer(source)); 
        QRCodeReader reader2 = new QRCodeReader();
        Result result = null;
        try {
            result = reader2.decode(bitmap1, hints);
        } catch (Exception e) {
            e.printStackTrace();
            if (source != null) {
                BinaryBitmap bitmap2 = new BinaryBitmap(new GlobalHistogramBinarizer(source)); 
                try {
                    result = reader2.decode(bitmap2, hints);
                } catch (Exception e1) {
                    e1.printStackTrace();
                }
            }
        }
        return result;
    }

對返回的result進行處理,如果未能識別,彈框中則無識別二維碼選項。

而對於圖片會有保存的功能,圖片手進行進行命名,然后設定保存路徑,創建好路徑,最后將圖片存入文件,根據需要是否需要進行壓縮,可以設定相關參數。保存以后通知系統更新圖片庫。

保存圖片的代碼如下:

public static void saveImageToGallery(Context context, Bitmap bmp) {
        String fileName = System.currentTimeMillis() + ".jpg";
        String filePath = FileUtils.getFilePath(context, "/pictures/qrcode/");
        // 首先保存圖片
        File appDir = new File(filePath);
        if (!appDir.exists()) {
            appDir.mkdir();
        }
        File file = new File(appDir, fileName);
        try {
            FileOutputStream fos = new FileOutputStream(file);
            bmp.compress(Bitmap.CompressFormat.JPEG, 100, fos);
            fos.flush();
            fos.close();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } catch (Exception e){

        }

        // 其次把文件插入到系統圖庫
        ContentValues values = new ContentValues();
        values.put(MediaStore.Images.Media.DATA, file.getAbsolutePath());
        values.put(MediaStore.Images.Media.MIME_TYPE, "image/jpeg");
        Uri uri = context.getContentResolver().insert(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values);
        // 最后通知圖庫更新
        context.sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, Uri.fromFile(file)));
    }

到這里二維碼識別和圖片保存的功能就算基本完成了。

但是,經過實際的測試發現,這種方式只管功能,沒有兼顧性能,進行多次操作導致內存使用增加30%,下一篇將描述分析過程和解決方法。

 

 

 

 

 

 

 

 

 

  


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM