国产激情自拍_国产9色视频_丁香花在线电影小说观看 _久久久久国产精品嫩草影院

首頁 > 系統 > Android > 正文

Android平臺生成二維碼并實現掃描 & 識別功能

2019-10-23 20:36:57
字體:
來源:轉載
供稿:網友

1.二維碼的前世今生

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

上面是百度百科的解釋。既然有二維碼,那么肯定有一維碼。

一維碼。最為常見的就是食品 & 書本后面的條碼。

條碼起源與20世紀40年代,后來在1970年 UPC碼發明,并開始廣泛應用與食品包裝。

具體的介紹可以看百度百科 一維碼。

其實二維碼與一維碼本質上是類似的,就跟一維數組和二維數組一樣。

2.二維碼的java支持庫

為了讓java或者說android方便繼承條碼的功能,google就開發了一個zxing的庫:

https://github.com/zxing/zxing

3.生成二維碼

public class EncodeThread {public static void encode(final String url, final int width, final int height, final EncodeResult result) {if (result == null) {return;}if (TextUtils.isEmpty(url)) {result.onEncodeResult(null);return;}new Thread() {@Overridepublic void run() {try {MultiFormatWriter writer = new MultiFormatWriter();Hashtable<EncodeHintType, String> hints = new Hashtable<>();hints.put(EncodeHintType.CHARACTER_SET, "utf-8");BitMatrix bitMatrix = writer.encode(url, BarcodeFormat.QR_CODE, width, height, hints);Bitmap bitmap = parseBitMatrix(bitMatrix);result.onEncodeResult(bitmap);return;} catch (WriterException e) {e.printStackTrace();}result.onEncodeResult(null);}}.start();}/*** 生成二維碼內容<br>** @param matrix* @return*/public static Bitmap parseBitMatrix(BitMatrix matrix) {final int QR_WIDTH = matrix.getWidth();final int QR_HEIGHT = matrix.getHeight();int[] pixels = new int[QR_WIDTH * QR_HEIGHT];//this we using qrcode algorithmfor (int y = 0; y < QR_HEIGHT; y++) {for (int x = 0; x < QR_WIDTH; x++) {if (matrix.get(x, y)) {pixels[y * QR_WIDTH + x] = 0xff000000;} else {pixels[y * QR_WIDTH + x] = 0xffffffff;}}}Bitmap bitmap = Bitmap.createBitmap(QR_WIDTH, QR_HEIGHT, Bitmap.Config.ARGB_8888);bitmap.setPixels(pixels, 0, QR_WIDTH, 0, 0, QR_WIDTH, QR_HEIGHT);return bitmap;}public interface EncodeResult {void onEncodeResult(Bitmap bitmap);}} 

zxing 支持很多條碼格式:我們這里使用QR_CODE碼。也就是我們常見的微信里面的二維碼。

我們先來分析下這段代碼:

MultiFormatWriter writer = new MultiFormatWriter();

這個是一個工具類,把所有支持的幾個write寫在里面了。

public BitMatrix encode(String contents,BarcodeFormat format,int width, int height,Map<EncodeHintType,?> hints) throws WriterException {Writer writer;switch (format) {case EAN_8:writer = new EAN8Writer();break;case UPC_E:writer = new UPCEWriter();break;case EAN_13:writer = new EAN13Writer();break;case UPC_A:writer = new UPCAWriter();break;case QR_CODE:writer = new QRCodeWriter();break;case CODE_39:writer = new Code39Writer();break;case CODE_93:writer = new Code93Writer();break;case CODE_128:writer = new Code128Writer();break;case ITF:writer = new ITFWriter();break;case PDF_417:writer = new PDF417Writer();break;case CODABAR:writer = new CodaBarWriter();break;case DATA_MATRIX:writer = new DataMatrixWriter();break;case AZTEC:writer = new AztecWriter();break;default:throw new IllegalArgumentException("No encoder available for format " + format);}return writer.encode(contents, format, width, height, hints);} 

這是官方最新支持的格式,具體看引入的jar里面支持的格式。

對與bitmatrix的結果,通過摸個算法,設置每個點白色,或者黑色。

最后創建一張二維碼的圖片。

4.識別二維碼

如何從一張圖片上面,識別二維碼呢:

public class ReDecodeThread {public static void encode(final Bitmap bitmap, final ReDecodeThreadResult listener) {if (listener == null) {return;}if (bitmap == null) {listener.onReDecodeResult(null);return;}new Thread() {@Overridepublic void run() {try {MultiFormatReader multiFormatReader = new MultiFormatReader();BitmapLuminanceSource source = new BitmapLuminanceSource(bitmap);BinaryBitmap bitmap1 = new BinaryBitmap(new HybridBinarizer(source));Result result1 = multiFormatReader.decode(bitmap1);listener.onReDecodeResult(result1.getText());return;} catch (NotFoundException e) {e.printStackTrace();}listener.onReDecodeResult(null);}}.start();}public interface ReDecodeThreadResult {void onReDecodeResult(String url);}} 

過程也是很簡單,使用MultiFormatReader來分析圖片,這里不需要缺人圖片的條碼格式。

如果分析下源碼,就是依次使用每種格式的reader來分析,直到找到合適的為止。

當然回了能夠把Bitmap轉化成Bitmatrix,然后在分析。

public final class BitmapLuminanceSource extends LuminanceSource{private final byte[] luminances;public BitmapLuminanceSource(String path) throws FileNotFoundException {this(loadBitmap(path));}public BitmapLuminanceSource(Bitmap bitmap) {super(bitmap.getWidth(), bitmap.getHeight());int width = bitmap.getWidth();int height = bitmap.getHeight();int[] pixels = new int[width * height];bitmap.getPixels(pixels, 0, width, 0, 0, width, height);// In order to measure pure decoding speed, we convert the entire image// to a greyscale array// up front, which is the same as the Y channel of the// YUVLuminanceSource in the real app.luminances = new byte[width * height];for (int y = 0; y < height; y++) {int offset = y * width;for (int x = 0; x < width; x++) {int pixel = pixels[offset + x];int r = (pixel >> 16) & 0xff;int g = (pixel >> 8) & 0xff;int b = pixel & 0xff;if (r == g && g == b) {// Image is already greyscale, so pick any channel.luminances[offset + x] = (byte) r;} else {// Calculate luminance cheaply, favoring green.luminances[offset + x] = (byte) ((r + g + g + b) >> 2);}}}}@Overridepublic byte[] getRow(int y, byte[] row) {if (y < 0 || y >= getHeight()) {throw new IllegalArgumentException("Requested row is outside the image: " + y);}int width = getWidth();if (row == null || row.length < width) {row = new byte[width];}System.arraycopy(luminances, y * width, row, 0, width);return row;}// Since this class does not support cropping, the underlying byte array// already contains// exactly what the caller is asking for, so give it to them without a copy.@Overridepublic byte[] getMatrix() {return luminances;}private static Bitmap loadBitmap(String path) throws FileNotFoundException {Bitmap bitmap = BitmapFactory.decodeFile(path);if (bitmap == null) {throw new FileNotFoundException("Couldn't open " + path);}return bitmap;}} 

5.掃描二維碼

掃描二維碼,其實比上面只多了一步,就是把camera獲取的東西直接轉換,然后進行識別。

public void requestPreviewFrame(Handler handler, int message) {if (camera != null && previewing) {previewCallback.setHandler(handler, message);if (useOneShotPreviewCallback) {camera.setOneShotPreviewCallback(previewCallback);} else {camera.setPreviewCallback(previewCallback);}}} 

首先把camera預覽的數據放入previewCallback中。

final class PreviewCallback implements Camera.PreviewCallback public void onPreviewFrame(byte[] data, Camera camera) {Point cameraResolution = configManager.getCameraResolution();if (!useOneShotPreviewCallback) {camera.setPreviewCallback(null);}if (previewHandler != null) {Message message = previewHandler.obtainMessage(previewMessage, cameraResolution.x,cameraResolution.y, data);message.sendToTarget();previewHandler = null;} else {Log.d(TAG, "Got preview callback, but no handler for it");}} 

可以看到,預覽的數據data,回傳遞過來,然后handler的方式傳遞出去。

接收data的地方:

@Overridepublic void handleMessage(Message message) {switch (message.what) {case R.id.decode://Log.d(TAG, "Got decode message");decode((byte[]) message.obj, message.arg1, message.arg2);break;case R.id.quit:Looper.myLooper().quit();break;}} 

然后是decode data

private void decode(byte[] data, int width, int height) {long start = System.currentTimeMillis();Result rawResult = null;//modify herebyte[] rotatedData = new byte[data.length];for (int y = 0; y < height; y++) {for (int x = 0; x < width; x++)rotatedData[x * height + height - y - 1] = data[x + y * width];}int tmp = width; // Here we are swapping, that's the difference to #11width = height;height = tmp;PlanarYUVLuminanceSource source = CameraManager.get().buildLuminanceSource(rotatedData, width, height);BinaryBitmap bitmap = new BinaryBitmap(new HybridBinarizer(source));try {rawResult = multiFormatReader.decodeWithState(bitmap);} catch (ReaderException re) {// continue} finally {multiFormatReader.reset();}if (rawResult != null) {long end = System.currentTimeMillis();Log.d(TAG, "Found barcode (" + (end - start) + " ms):/n" + rawResult.toString());Message message = Message.obtain(activity.getHandler(), R.id.decode_succeeded, rawResult);Bundle bundle = new Bundle();bundle.putParcelable(DecodeThread.BARCODE_BITMAP, source.renderCroppedGreyscaleBitmap());message.setData(bundle);//Log.d(TAG, "Sending decode succeeded message...");message.sendToTarget();} else {Message message = Message.obtain(activity.getHandler(), R.id.decode_failed);message.sendToTarget();}} 

當把camera上的圖片轉換成BinaryBitmap以后,剩下的事情,就更直接從圖片識別是一樣的。

PlanarYUVLuminanceSource source = CameraManager.get().buildLuminanceSource(rotatedData, width, height);
BinaryBitmap bitmap = new BinaryBitmap(new HybridBinarizer(source));


注:相關教程知識閱讀請移步到Android開發頻道。
發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
国产激情自拍_国产9色视频_丁香花在线电影小说观看 _久久久久国产精品嫩草影院
国产h色视频在线观看| 青草青在线视频| 中文字幕乱在线伦视频乱在线伦视频| 午夜影院免费看| 999在线视频| 人成在线免费视频| 交视频在线观看国产| 国产三线在线| 天天操夜夜做| 国产精品被窝福利一区| 在线中文字幕视频观看| www中文字幕在线观看| www.色婷婷| 国产成人va亚洲电影| 爱福利在线视频| 国产黄在线播放| 丁香婷婷激情| 香蕉视频在线看| 国产成人高清精品| 天天干天天摸| 国产精品美女视频免费观看软件| 欧美日韩在线精品成人综合网| 国产激情在线| 最新亚洲精品国自产在线观看| a视频在线观看| 中文字幕av高清在线观看| 91av久久| 嫩草在线播放| 伊人伊人av电影| 国产区在线观看| 国产丝袜在线观看视频| 最近中文字幕mv免费高清视频8| 影音先锋在线中文字幕| 国产激情在线观看| 黄色电影网站在线观看| 欧美日韩在线视频免费观看| 色悠久久久久综合网小说| 在线免费观看你懂的| 精品一区二区三区在线成人| 国产一区二区三区福利| 91xxx在线观看| 国产精品午夜久久久久久| 超碰在线国产| 国产资源在线看| 九九热精品在线视频| 日日夜夜中文字幕| www在线视频| 黄网址在线播放免费| 久久久久久久美女| 国内自拍视频在线观看| 最近中文av字幕在线中文| 国产免费专区| 国产视频三区| 在线成人综合色一区| 性国产高清在线观看| 欧美亚洲另类在线观看| 快射av在线播放一区| 午夜免费福利在线观看| 91看片在线观看| 免费男女羞羞的视频网站中文字幕| www.国产精品.com| 99热在线免费播放| 国产高潮又爽又无遮挡又免费| 精品176二区| 四虎一区二区三区| 天天操天天艹| 99热99re6国产在线播放| 亚洲人在线播放| 天堂在线一二区| 亚洲精品白浆| 最新天堂资源在线资源| av中文天堂在线| 中文字幕一区免费| 日本片在线看| 国产视频精品久久| 白浆爆出在线观看| 国产污视频在线| 久久精品亚洲7777影院| 在线国产福利网站| 国产乱视频在线观看| 精品推荐国产麻豆剧传媒| 久久国产情侣| 亚洲精品影视在线| 国产成a人亚洲精v品| 天天操夜夜摸| 狠狠插狠狠操| 热99re久久精品这里都是免费| 国产精品伦理一区二区三区| 九九热免费在线视频| 亚洲日本伊人| 伊人222成人综合网| 国产视频一二三区| 国产在线一二三区| 人人澡人人爽| 中文在线视频观看| 69国产精品视频| 国产精品美女一区二区视频| 国产免费人人看| 国产秒拍福利视频露脸| 国产尤物一区二区三区| 黄色av网址在线免费观看| 日本h片在线观看| www.国产精| 黄色av免费在线| 91超碰国产在线| 国产一卡2卡3卡免费网站| 中文字幕日本在线| 国产一区二区三区四区尤物| 国产三级在线免费观看| 中文字幕视频在线免费| 国产亚av手机在线观看 | 国产人成高清视频观看| 国产精品探花在线| 国产三级香港三韩国三级| 国产精品视频福利一区二区| 国产黄色在线网站| 亚洲成人电视网| 国产乱人视频免费播放| 中文字幕在线观看日本| 国产高清一区二区三区视频| 99在线播放| 久草在线视频网| 国产精品国产国产aⅴ| 国产日产精品久久久久久婷婷| 精品美女在线观看视频在线观看| 在线视频中文字幕第一页| 免费日本黄色| 97一区二区三区| 国产鲁鲁视频在线观看特色| 国产白浆在线| 青青草在线播放| 国产精品美女视频免费观看软件| 一级二级在线观看| 国产精品第八页| 国产美女一区视频| 亚洲伊人网在线观看| 国产特级淫片免费看| а√资源新版在线天堂| 国产羞羞视频| 黄色国产在线| 超碰97国产精品人人cao| 国产精品福利视频一区二区三区| 牛牛热在线视频| 在线激情小视频| 国产成人天天5g影院| 最近中文字幕mv免费高清电影 | 亚洲精品成人a| 国产精品不卡一区二区三区在线观看| 亚洲日本伊人| 精品国产二区三区| 99热在线免费观看| 久久99国产视频| av在线不卡网站| 夜色资源网av在先锋网站观看| 国产三级视频| 国产精美视频| 国产h在线观看| 国产成人夜间影院在线观看| 国产三级在线免费观看| 国产精品久久久久一区二区国产| 国产一级又黄| 国产第一页在线| 国产精品区一区二| 精品偷拍激情视频在线观看| 国产一卡2卡3卡四卡网站| www.狠狠操.com| 四虎精品视频| 麻豆精品视频入口| 国产精品自拍在线观看| 成年黄网站在线观看免费| 在线天堂中文| 午夜影院在线免费观看| av天天在线| 激情丁香婷婷| 国产无遮挡又黄又爽免费网站 | 精品极品三级久久久久| 99在线欧洲视频| 全网国产福利在线播放| 国产在线麻豆精品| 国产女主播在线观看| 亚洲天堂二区| 九九视频在线播放| 国产精品人人| 免费av不卡在线观看| 国产精品国产三级国产试看| 日本久久国产| 国产精品入口免费麻豆| 四虎久久影院| 国产精品白浆视频免费观看| av色在线观看| 国产精品一区在线看| 在线免费观看黄色av| 国产美女被遭强高潮免费网站| 精品卡1卡2卡三卡免费网站| 久久综合第一页| 中文国产字幕在线观看| 国产香蕉免费精品视频| 欧美激情福利视频在线观看免费| 国产精品入口麻豆免费观看| 四虎网站在线观看|