本文用于推荐一款很好用的二维码生成插件QRCode.js,测试使用方便且简单。
其实官方就有很好的文档,这里只是做一个我工作的记录和总结。
@version1.0——2018-11-22——创建《前端QRCode.js生成二维码插件》
@version1.1——2019-01-20——修改《前端QRCode.js生成二维码插件(解决长字符串显示模糊问题)》
- 将注意事项提出不可忽略的问题
- 添加长字符串显示模糊,手机二维码不能识别的问题
- 添加解决小米8手机不显示二维码的问题
©burning_韵七七
- 目录
- 介绍
- 使用
- 1.引入js文件
- 2.定义承载二维码标签
- 3.js调用
- 4.页面预览
- 参数API
- QRCode参数
- Option参数
- API接口
- 实践
- 生成二维码,微信QQ识别打开网页
- 不可忽略的问题(踩坑)
- url的中文编码问题
- 长字符串的显示模糊问题
- 问题分析
- 解决思路
- 实践真知
- 二维码难以识别
- 观察生成的结构
- 放大倍数
- css缩小倍数
- 解决小米8手机不显示二维码的问题
- 此案例完整代码
介绍
- 这个插件主要使用canvas实现的。
- 原生代码不需要依赖jquery,或者zepto。
- 兼容性也很好,IE6~10, Chrome, Firefox, Safari, Opera, Mobile Safari, Android, Windows Mobile, ETC.
- 前端开发者仓库官网
- GitHub地址
使用
1.引入js文件
<script src="qrcode.js"></script>
2.定义承载二维码标签
<div id="qrcode"></div>
3.js调用
简单调用
new QRCode(document.getElementById('qrcode'), 'your content');
设置参数调用
下面会有参数详解
var qrcode = new QRCode('qrcode', {
text: 'your content',
width: 256,
height: 256,
colorDark: '#000000',
colorLight: '#ffffff',
correctLevel: QRCode.CorrectLevel.H
});
4.页面预览
这样就很简单的生成了一个二维码
参数API
QRCode参数
new QRCode(element, option)
名称 | 默认值 | 说明 |
---|---|---|
element | - | 承载二维码的DOM元素的ID |
option | - | 参数设置 |
Option参数
名称 | 默认值 | 说明 | 备注 |
---|---|---|---|
text | - | 二维码承载的信息 | 如果是string那没有什么好说的。 如果是url的话,为了微信和QQ可以识别,连接中的中文使用encodeURIComponent进行编码 |
width | 256 | 二维码宽度 | 单位像素(百分比不行) |
height | 256 | 二维码高度 | 单位像素(百分比不行) |
colorDark | '#000000' | 二维码前景色 | 英文\十六进制\rgb\rgba\transparent都可以 |
colorLight | '#ffffff' | 二维码背景色 | 英文\十六进制\rgb\rgba\transparent都可以 |
correctLevel | QRCode.CorrectLevel.L | 容错级别 | 由低到高 QRCode.CorrectLevel.L QRCode.CorrectLevel.M QRCode.CorrectLevel.Q QRCode.CorrectLevel.H |
API接口
名称 | 参数 | 说明 | 使用 |
---|---|---|---|
clear | - | 清除二维码 | qrcode.clear() |
makeCode | string | 替换二维码(参数里面是新的二维码内容) | qrcode.makeCode('new content') |
var qrcode = new QRCode('qrcode',{
'text':'content',
'width':256,
'height':256,
'colorDark':'red',
'colorLoght':'transparent',
'correctLevel':QRCode.CorrectLevel.H
})
qrcode.clear();
qrcode.madkCode('new content');
实践
生成二维码,微信QQ识别打开网页
需求
- 前端根据传的不同的参数,在页面生成一个二维码
- 由端分享到QQ、QQ空间、微信、朋友圈的时候,截屏成图片
- 长按图片,识别其中的二维码,打开网页链接。
思路
- 和端交互的网页a.html后面加query参数,如:
http://www.test.html/a.html?code=123
- a.html中调用QRCode.js生成一个二维码,二维码中的信息是
http://www.test.html/b.html?code=123
- 分享出去的页面是截屏是a.html的,识别图中的二维码打开b.html
实现
由于很简单,所以就不贴代码了。
但是下面有几个踩的坑,不可忽略的问题,必看。
不可忽略的问题(踩坑)
url的中文编码问题
如果传的是url,但是打开的时候只是一堆字符串让手动复制,那么说明url的地址不正确。
如果是微信,传的url的地址中有中文是可以识别的,但是在QQ中是不行的
所以其中的中文要进行encodeURIComponent编码,但是不要整体都编码,只是中文的部分编码即可。
长字符串的显示模糊问题
问题分析
显示模糊的问题,应该是canvas的问题。由于字符串比较长,尤其是需要传一个连接地址,后面还加一些参数的时候,就会加大二维码的像素复杂度,而本身canvas在绘制的时候,就一直有像素模糊的问题,尤其是在手机上的时候。
解决思路
所以可以利用这个问题,不动源码去解决因为长字符串导致的二维码模糊,手机无法识别的问题——先将生成的二维码进行倍数扩大,然后在css上面固定其显示宽高,这样就可以扩大显示像素精度。
实践真知
1. 二维码难以识别
下面二维码的识别难度:
- QQ > weChat(相同长度的二维码,微信的识别程度比QQ的要好)
- 微信中在大部分安卓手机上面是可以长按识别的,小部分安卓手机比如小米、oppo是无法识别的。还有苹果手机大部分也不能识别,更别说QQ了,所以这个问题需要解决。
2. 观察生成的结构
生成的页面结构可以看到是这样的。通过canvas生成二维码图片,然后canvas隐藏显示img。所以只要确保生成的canvas和img的宽高是100%即可。
3. 放大倍数
//显示二维码
var qrcode = new QRCode(document.getElementById("qrcodeConIn"), {
text: `${location.origin}/codesearch/activity/broadcastgroup?requestAct=openview&openId=${data.openId}&random=${data.random}`,
width: fontSize * 1.92 * 4, //这里是根据rem进行了换算,后面的4指的就是四倍
height: fontSize * 1.92 * 4, //这里是根据rem进行了换算,后面的4指的就是四倍
colorDark : '#000',
colorLight : "transparent",
correctLevel : QRCode.CorrectLevel.H
});
看一下放大倍数的图片(为了效果展示的是3倍的图片)
4. css缩小倍数
/*固定宽高*/
.qrcodeCon{
width: 2.2rem;
height: 2.2rem;
padding: 0.15rem;
}
/*内容自适应*/
.qrcodeConIn{
width: 100%;
height: 100%;
}
/*生成的二维码里面的img标签宽高自适应*/
.qrcodeConIn img{
width: 100%;
height: 100%;
}
/*一开始生成的canvas也要进行宽高自适应*/
.qrcodeConIn canvas{
width: 100%;
height: 100%;
}
这样就可以看到生成的效果了。
下面这个二维码,几乎所有手机的QQ和微信都可以识别了,如果还不能识别,那就继续加大倍数。
5. 解决小米8手机不显示二维码的问题
先说我只是在测试的时候,发现小米8手机并不能生成二维码,我觉得肯定是有一些代码不兼容。但是目前没有时间去研究源码,留下一个坑。
但是是知道,小米8在生成二维码之后的img标签中的src为空。
根据这个现象后面做了一个planB,待以后有时间研究了再完善。
//把代码放到事件队列后面
setTimeout(function(){
//检测一下如果img标签里面的src没有base64就进行下面操作
if(!$("#qrcodeConIn img").attr("src")){
$("#qrcodeConIn img").show();
$("#qrcodeConIn canvas").hide();
var canvas = $("#qrcodeConIn canvas")[0];
var dataURL = canvas.toDataURL("image/png");
$("#qrcodeConIn img").attr("src",dataURL);
}
},0);
此案例完整代码
html
<div class="codeCon">
<!--撑开的后面背景-->
<div class="inlineBlock qrcode">
<!--白色部分占位-->
<div id="qrcodeCon" class="qrcodeCon">
<!--二维码显示范围-->
<div id="qrcodeConIn" class="qrcodeConIn"></div>
</div>
</div>
<div class="inlineBlock">
<h3>长按识别</h3>
<h3>扫码免费领</h3>
<p>仅限今日</p>
</div>
</div>
css
.codeCon{
margin: 0 auto;
width: 6.6rem;
padding: 0.35rem 0;
border-radius: 0.2rem;
background-color: #eee;
}
.inlineBlock{
display: inline-block;
vertical-align: middle;
}
.qrcode{
background-color: #fff;
border-radius: 0.2rem;
border: 1px solid #eee;
}
/*固定宽高*/
.qrcodeCon{
width: 2.2rem;
height: 2.2rem;
padding: 0.15rem;
}
/*内容自适应*/
.qrcodeConIn{
width: 100%;
height: 100%;
}
h3{
font-size: 0.4rem;
margin-bottom: 0.15rem;
letter-spacing: 0.04rem;
text-indent: 0.04rem;
}
p{
font-size: 0.32rem;
letter-spacing: 0.2rem;
text-indent: 0.2rem;
}
/*生成的二维码里面的img标签宽高自适应*/
.qrcodeConIn img{
width: 100%;
height: 100%;
}
/*一开始生成的canvas也要进行宽高自适应*/
.qrcodeConIn canvas{
width: 100%;
height: 100%;
}
js
//显示二维码
var qrcode = new QRCode(document.getElementById("qrcodeConIn"), {
text: `${location.origin}/codesearch/activity/broadcastgroup?requestAct=openview&openId=${data.openId}&random=${data.random}`,
width: fontSize * 1.92 * 4,
height: fontSize * 1.92 * 4,
colorDark : '#000',
colorLight : "transparent",
correctLevel : QRCode.CorrectLevel.H
});
setTimeout(function(){
if(!$("#qrcodeConIn img").attr("src")){
$("#qrcodeConIn img").show();
$("#qrcodeConIn canvas").hide();
var canvas = $("#qrcodeConIn canvas")[0];
var dataURL = canvas.toDataURL("image/png");
$("#qrcodeConIn img").attr("src",dataURL);
}
},0);