二维码扫描的相关知识
1.二维码扫描
二维码,是一种采用黑白相间的平面几何图形通过相应的编码算法来记录文字、图片、网址等信息的条码图片。如下图
二维码的特点:
1. 高密度编码,信息容量大
可容纳多达1850个大写字母或2710个数字或1108个字节,或500多个汉字,比普通条码信息容量约高几十倍。
2. 编码范围广
该条码可以把图片、声音、文字、签字、指纹等可以数字化的信息进行编码,用条码表示出来;可以表示多种语言文字;可表示图像数据。
3. 容错能力强,具有纠错功能
这使得二维条码因穿孔、污损等引起局部损坏时,照样可以正确得到识读,损毁面积达50%仍可恢复信息。
4. 译码可靠性高
它比普通条码译码错误率百万分之二要低得多,误码率不超过千万分之一。
5. 可引入加密措施
保密性、防伪性好。
6. 成本低,易制作,持久耐用
正因为以上这些特点,二维码现在越来越流行,应用也是越来越广(详细了解请见百度百科,介绍不是本篇重点),所以掌握如何开发二维码是非常不错的知识储备,因此本篇博文将为大家讲解如何生成、解析二维码。
所需jar包:QRCode.jar
http://download.csdn.net/detail/wangpeng047/4008532
TwoDimensionCode类:二维码操作核心类
1 package qrcode; 2 3 import java.awt.Color; 4 import java.awt.Graphics2D; 5 import java.awt.image.BufferedImage; 6 import java.io.File; 7 import java.io.IOException; 8 import java.io.InputStream; 9 import java.io.OutputStream; 10 11 import javax.imageio.ImageIO; 12 13 import jp.sourceforge.qrcode.QRCodeDecoder; 14 import jp.sourceforge.qrcode.exception.DecodingFailedException; 15 16 import com.swetake.util.Qrcode; 17 18 public class TwoDimensionCode { 19 20 /** 21 * 生成二维码(QRCode)图片 22 * @param content 存储内容 23 * @param imgPath 图片路径 24 */ 25 public void encoderQRCode(String content, String imgPath) { 26 this.encoderQRCode(content, imgPath, "png", 7); 27 } 28 29 /** 30 * 生成二维码(QRCode)图片 31 * @param content 存储内容 32 * @param output 输出流 33 */ 34 public void encoderQRCode(String content, OutputStream output) { 35 this.encoderQRCode(content, output, "png", 7); 36 } 37 38 /** 39 * 生成二维码(QRCode)图片 40 * @param content 存储内容 41 * @param imgPath 图片路径 42 * @param imgType 图片类型 43 */ 44 public void encoderQRCode(String content, String imgPath, String imgType) { 45 this.encoderQRCode(content, imgPath, imgType, 7); 46 } 47 48 /** 49 * 生成二维码(QRCode)图片 50 * @param content 存储内容 51 * @param output 输出流 52 * @param imgType 图片类型 53 */ 54 public void encoderQRCode(String content, OutputStream output, String imgType) { 55 this.encoderQRCode(content, output, imgType, 7); 56 } 57 58 /** 59 * 生成二维码(QRCode)图片 60 * @param content 存储内容 61 * @param imgPath 图片路径 62 * @param imgType 图片类型 63 * @param size 二维码尺寸 64 */ 65 public void encoderQRCode(String content, String imgPath, String imgType, int size) { 66 try { 67 BufferedImage bufImg = this.qRCodeCommon(content, imgType, size); 68 69 File imgFile = new File(imgPath); 70 // 生成二维码QRCode图片 71 ImageIO.write(bufImg, imgType, imgFile); 72 } catch (Exception e) { 73 e.printStackTrace(); 74 } 75 } 76 77 /** 78 * 生成二维码(QRCode)图片 79 * @param content 存储内容 80 * @param output 输出流 81 * @param imgType 图片类型 82 * @param size 二维码尺寸 83 */ 84 public void encoderQRCode(String content, OutputStream output, String imgType, int size) { 85 try { 86 BufferedImage bufImg = this.qRCodeCommon(content, imgType, size); 87 // 生成二维码QRCode图片 88 ImageIO.write(bufImg, imgType, output); 89 } catch (Exception e) { 90 e.printStackTrace(); 91 } 92 } 93 94 /** 95 * 生成二维码(QRCode)图片的公共方法 96 * @param content 存储内容 97 * @param imgType 图片类型 98 * @param size 二维码尺寸 99 * @return 100 */ 101 private BufferedImage qRCodeCommon(String content, String imgType, int size) { 102 BufferedImage bufImg = null; 103 try { 104 Qrcode qrcodeHandler = new Qrcode(); 105 // 设置二维码排错率,可选L(7%)、M(15%)、Q(25%)、H(30%),排错率越高可存储的信息越少,但对二维码清晰度的要求越小 106 qrcodeHandler.setQrcodeErrorCorrect('M'); 107 qrcodeHandler.setQrcodeEncodeMode('B'); 108 // 设置设置二维码尺寸,取值范围1-40,值越大尺寸越大,可存储的信息越大 109 qrcodeHandler.setQrcodeVersion(size); 110 // 获得内容的字节数组,设置编码格式 111 byte[] contentBytes = content.getBytes("utf-8"); 112 // 图片尺寸 113 int imgSize = 67 + 12 * (size - 1); 114 bufImg = new BufferedImage(imgSize, imgSize, BufferedImage.TYPE_INT_RGB); 115 Graphics2D gs = bufImg.createGraphics(); 116 // 设置背景颜色 117 gs.setBackground(Color.WHITE); 118 gs.clearRect(0, 0, imgSize, imgSize); 119 120 // 设定图像颜色> BLACK 121 gs.setColor(Color.BLACK); 122 // 设置偏移量,不设置可能导致解析出错 123 int pixoff = 2; 124 // 输出内容> 二维码 125 if (contentBytes.length > 0 && contentBytes.length < 800) { 126 boolean[][] codeOut = qrcodeHandler.calQrcode(contentBytes); 127 for (int i = 0; i < codeOut.length; i++) { 128 for (int j = 0; j < codeOut.length; j++) { 129 if (codeOut[j][i]) { 130 gs.fillRect(j * 3 + pixoff, i * 3 + pixoff, 3, 3); 131 } 132 } 133 } 134 } else { 135 throw new Exception("QRCode content bytes length = " + contentBytes.length + " not in [0, 800]."); 136 } 137 gs.dispose(); 138 bufImg.flush(); 139 } catch (Exception e) { 140 e.printStackTrace(); 141 } 142 return bufImg; 143 } 144 145 /** 146 * 解析二维码(QRCode) 147 * @param imgPath 图片路径 148 * @return 149 */ 150 public String decoderQRCode(String imgPath) { 151 // QRCode 二维码图片的文件 152 File imageFile = new File(imgPath); 153 BufferedImage bufImg = null; 154 String content = null; 155 try { 156 bufImg = ImageIO.read(imageFile); 157 QRCodeDecoder decoder = new QRCodeDecoder(); 158 content = new String(decoder.decode(new TwoDimensionCodeImage(bufImg)), "utf-8"); 159 } catch (IOException e) { 160 System.out.println("Error: " + e.getMessage()); 161 e.printStackTrace(); 162 } catch (DecodingFailedException dfe) { 163 System.out.println("Error: " + dfe.getMessage()); 164 dfe.printStackTrace(); 165 } 166 return content; 167 } 168 169 /** 170 * 解析二维码(QRCode) 171 * @param input 输入流 172 * @return 173 */ 174 public String decoderQRCode(InputStream input) { 175 BufferedImage bufImg = null; 176 String content = null; 177 try { 178 bufImg = ImageIO.read(input); 179 QRCodeDecoder decoder = new QRCodeDecoder(); 180 content = new String(decoder.decode(new TwoDimensionCodeImage(bufImg)), "utf-8"); 181 } catch (IOException e) { 182 System.out.println("Error: " + e.getMessage()); 183 e.printStackTrace(); 184 } catch (DecodingFailedException dfe) { 185 System.out.println("Error: " + dfe.getMessage()); 186 dfe.printStackTrace(); 187 } 188 return content; 189 } 190 191 public static void main(String[] args) { 192 String imgPath = "G:/TDDOWNLOAD/Michael_QRCode.png"; 193 String encoderContent = "Hello 大大、小小,welcome to QRCode!" + "\nMyblog [ http://sjsky.iteye.com ]" + "\nEMail [ sjsky007@gmail.com ]"; 194 TwoDimensionCode handler = new TwoDimensionCode(); 195 handler.encoderQRCode(encoderContent, imgPath, "png"); 196 // try { 197 // OutputStream output = new FileOutputStream(imgPath); 198 // handler.encoderQRCode(content, output); 199 // } catch (Exception e) { 200 // e.printStackTrace(); 201 // } 202 System.out.println("========encoder success"); 203 204 205 String decoderContent = handler.decoderQRCode(imgPath); 206 System.out.println("解析结果如下:"); 207 System.out.println(decoderContent); 208 System.out.println("========decoder success!!!"); 209 } 210 }
TwoDimensionCodeImage 类:二维码图片对象
1 package qrcode; 2 3 import java.awt.image.BufferedImage; 4 5 import jp.sourceforge.qrcode.data.QRCodeImage; 6 7 public class TwoDimensionCodeImage implements QRCodeImage { 8 9 BufferedImage bufImg; 10 11 public TwoDimensionCodeImage(BufferedImage bufImg) { 12 this.bufImg = bufImg; 13 } 14 15 @Override 16 public int getHeight() { 17 return bufImg.getHeight(); 18 } 19 20 @Override 21 public int getPixel(int x, int y) { 22 return bufImg.getRGB(x, y); 23 } 24 25 @Override 26 public int getWidth() { 27 return bufImg.getWidth(); 28 } 29 30 }
转载于:https://www.cnblogs.com/xuanyuanzhuo-blog/p/3984552.html
二维码扫描的相关知识相关推荐
- iOS原生实现二维码扫描
iOS原生实现二维码扫描 最近项目上需要开发扫描二维码进行签到的功能,主要用于开会签到的场景,所以为了避免作弊,我们再开发时只采用直接扫描的方式,并且要屏蔽从相册读取图片,此外还在二维码扫描成功签到时 ...
- Android 基于Zxing二维码扫描的光速实现
Android 十分钟光速实现二维码扫描 前言 在项目中要使用到二维码的相关内容,我们第一时间想到的是使用大名鼎鼎的zxing或者ZBar开源框架: github-zxing官方库的地址 github ...
- QML QZXing 二维码扫描
QML QZXing 二维码.条形码扫描 QML QZXing 二维码.条形码扫描 QZXing.QML变化 QZXing使用方式 详解 引用 Qml6 采用识别图像方式 Qt 5.15.2 采用视频 ...
- Android开发之google Zxing实现二维码扫描的代码分析
1.技术简介 在Android中实现二维码的扫描主要是通过第三方框架来实现的,主要框架是google的Zxing.现在就用该框架来实现二维码及条形码的扫描及识别,同时对于手机中存储的图片也进行识 ...
- 二维码扫描和应用跳转
转载自: http://sindrilin.com/ios-dev/2015/11/01/二维码扫描和应用跳转.html 前面我们已经调到过怎么制作二维码,在我们能够生成二维码之后,如何对二维码进行扫 ...
- uniapp中qrcode生成二维码后传的参数不见了_二维码扫描登录,你必须知道的 3 件事...
作者 | 互联网平头哥 本文经授权转载自互联网平头哥(ID:it_pingtouge) 扫二维码登录现在比较常见,比如微信.支付宝等 PC 端登录,并且好像每款 APP 都支持扫码登录,不搞个扫码登录 ...
- 二维码扫描开源库ZXing定制化【转】
转自:http://www.cnblogs.com/sickworm/p/4562081.html 最近在用ZXing这个开源库做二维码的扫描模块,开发过程的一些代码修改和裁剪的经验和大家分享一下. ...
- 二维码扫描ZXing简化
最近项目中有需要用到二维码扫描功能,于是查了相关资料,也没有过多地研究ZXing源码,只是有了最简单的功能,因为下载大牛的demo已经完全实现了功能,只是对其中的扫描线做了更改,需要的朋友可以直接使用 ...
- 基于MUI框架的使用HTML5+实现的二维码扫描功能
Barcode的一个实现案例 一.简介 Barco ...
最新文章
- oracle rodm包,由重启引起的Oracle RAC节点宕机分析及追根溯源
- 基于用户的协同过滤和皮尔逊相关系数
- win7 'IIS APPPOOL\Classic .NET AppPool' 登录失败
- Spring Boot笔记-@PathVariable的使用
- 142.4. Gearman
- 如何使用Docker Swarm管理更多容器
- python生成范围内随机数_如何使用Python中的pareto分布在specyfic范围内生成随机数...
- javascript Nested functions
- BA-风阀水阀执行器接线图
- eeprom和编程器固件 k2_斐讯K1K2新版固件v22.4.xx.xx简单刷机教程
- chrome内核 用h5调用高拍仪(摄像图)实现拍证件照
- 王慧文:当下社会最稀缺的是“π型人才”
- Linux 部署开源WAF模块 ModSecurity
- 修改内核参数 dad_transmits
- java获取时间的各种风格_各种获取时间的方法包含各类时间格式
- Nodejs+Koa2+云服务ECS 开发微信公众号(一)之环境配置
- @ConfigrationProperties + @EnableConfigrationProperties
- MFC Windows 程序设计[315]之磁盘文件列举器(附源码)
- Delphi/C#之父Anders Hejlsberg
- vue打包后dist目录直接打开index资源路径错误和css样式背景图路径问题
热门文章
- 如何搭建一套个性化推荐系统?
- 5个超经典实验,老杨带你高效进阶OSPF
- 自动驾驶基础知识(一)——英文缩写(持续更新...)
- Toolbar与DrawerLayout
- 前端开发第三方分享/登录功能备忘(facebook、weibo、QQ、weixin微信好友或者朋友圈)
- 从《青云志》看完美世界如何玩转影游联动,打造S级手游
- 开源一个中国象棋 alpha zero 程序
- 无穷小微积分,入门三道坎儿
- 时间序列论文: NeuralProphet: Explainable Forecasting at Scale
- psv型号版本怎么看的