You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
923 lines
20 KiB
923 lines
20 KiB
9 months ago
|
|
||
|
let QRCode={};
|
||
|
(function(){
|
||
|
function unicodeFormat8(code){
|
||
|
var c0,c1,c2;
|
||
|
if(code<128){
|
||
|
return[code];
|
||
|
}else if(code<2048){
|
||
|
c0=192+(code>>6);
|
||
|
c1=128+(code&63);
|
||
|
return[c0,c1];
|
||
|
}else{
|
||
|
c0=224+(code>>12);
|
||
|
c1=128+(code>>6&63);
|
||
|
c2=128+(code&63);
|
||
|
return[c0,c1,c2];
|
||
|
}
|
||
|
}
|
||
|
function getUTF8Bytes(string){
|
||
|
var utf8codes=[];
|
||
|
for(var i=0;i<string.length;i++){
|
||
|
var code=string.charCodeAt(i);
|
||
|
var utf8=unicodeFormat8(code);
|
||
|
for(var j=0;j<utf8.length;j++){
|
||
|
utf8codes.push(utf8[j]);
|
||
|
}
|
||
|
}
|
||
|
return utf8codes;
|
||
|
}
|
||
|
function QRCodeAlg(data,twodimensionalcodeee5conversionmethod){
|
||
|
this.typeNumber=-1;
|
||
|
this.errorCorrectLevel=twodimensionalcodeee5conversionmethod;
|
||
|
this.modules=null;
|
||
|
this.moduleCount=0;
|
||
|
this.dataCache=null;
|
||
|
this.rsBlocks=null;
|
||
|
this.totalDataCount=-1;
|
||
|
this.data=data;
|
||
|
this.utf8bytes=getUTF8Bytes(data);
|
||
|
this.make();
|
||
|
}
|
||
|
QRCodeAlg.prototype={
|
||
|
constructor:QRCodeAlg,
|
||
|
getModuleCount:function(){
|
||
|
return this.moduleCount;
|
||
|
},
|
||
|
make:function(){
|
||
|
this.getRightType();
|
||
|
this.dataCache=this.createData();
|
||
|
this.createQrcode();
|
||
|
},
|
||
|
makeImpl:function(maskPattern){
|
||
|
this.moduleCount=this.typeNumber*4+17;
|
||
|
this.modules=new Array(this.moduleCount);
|
||
|
for(var row=0;row<this.moduleCount;row++){
|
||
|
this.modules[row]=new Array(this.moduleCount);
|
||
|
}
|
||
|
this.setupPositionProbePattern(0,0);
|
||
|
this.setupPositionProbePattern(this.moduleCount-7,0);
|
||
|
this.setupPositionProbePattern(0,this.moduleCount-7);
|
||
|
this.setupPositionAdjustPattern();
|
||
|
this.setupTimingPattern();
|
||
|
this.setupTypeInfo(true,maskPattern);
|
||
|
if(this.typeNumber>=7){
|
||
|
this.setupTypeNumber(true);
|
||
|
}
|
||
|
this.mapData(this.dataCache,maskPattern);
|
||
|
},
|
||
|
setupPositionProbePattern:function(row,col){
|
||
|
for(var r=-1;r<=7;r++){
|
||
|
if(row+r<=-1||this.moduleCount<=row+r)continue;
|
||
|
for(var c=-1;c<=7;c++){
|
||
|
if(col+c<=-1||this.moduleCount<=col+c)continue;
|
||
|
if((0<=r&&r<=6&&(c==0||c==6))||(0<=c&&c<=6&&(r==0||r==6))||(2<=r&&r<=4&&2<=c&&c<=4)){
|
||
|
this.modules[row+r][col+c]=true;
|
||
|
}else{
|
||
|
this.modules[row+r][col+c]=false;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
},
|
||
|
createQrcode:function(){
|
||
|
var minLostPoint=0;
|
||
|
var pattern=0;
|
||
|
var bestModules=null;
|
||
|
for(var i=0;i<8;i++){
|
||
|
this.makeImpl(i);
|
||
|
var lostPoint=QRUtil.getLostPoint(this);
|
||
|
if(i==0||minLostPoint>lostPoint){
|
||
|
minLostPoint=lostPoint;
|
||
|
pattern=i;
|
||
|
bestModules=this.modules;
|
||
|
}
|
||
|
}
|
||
|
this.modules=bestModules;
|
||
|
this.setupTypeInfo(false,pattern);
|
||
|
if(this.typeNumber>=7){
|
||
|
this.setupTypeNumber(false);
|
||
|
}
|
||
|
},
|
||
|
setupTimingPattern:function(){
|
||
|
for(var r=8;r<this.moduleCount-8;r++){
|
||
|
if(this.modules[r][6]!=null){
|
||
|
continue;
|
||
|
}
|
||
|
this.modules[r][6]=(r%2==0);
|
||
|
if(this.modules[6][r]!=null){
|
||
|
continue;
|
||
|
}
|
||
|
this.modules[6][r]=(r%2==0);
|
||
|
}
|
||
|
},
|
||
|
setupPositionAdjustPattern:function(){
|
||
|
var pos=QRUtil.getPatternPosition(this.typeNumber);
|
||
|
for(var i=0;i<pos.length;i++){
|
||
|
for(var j=0;j<pos.length;j++){
|
||
|
var row=pos[i];
|
||
|
var col=pos[j];
|
||
|
if(this.modules[row][col]!=null){
|
||
|
continue;
|
||
|
}
|
||
|
for(var r=-2;r<=2;r++){
|
||
|
for(var c=-2;c<=2;c++){
|
||
|
if(r==-2||r==2||c==-2||c==2||(r==0&&c==0)){
|
||
|
this.modules[row+r][col+c]=true;
|
||
|
}else{
|
||
|
this.modules[row+r][col+c]=false;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
},
|
||
|
setupTypeNumber:function(test){
|
||
|
var bits=QRUtil.getBCHTypeNumber(this.typeNumber);
|
||
|
for(var i=0;i<18;i++){
|
||
|
var mod=(!test&&((bits>>i)&1)==1);
|
||
|
this.modules[Math.floor(i/3)][i%3+this.moduleCount-8-3]=mod;
|
||
|
this.modules[i%3+this.moduleCount-8-3][Math.floor(i/3)]=mod;
|
||
|
}
|
||
|
},
|
||
|
setupTypeInfo:function(test,maskPattern){
|
||
|
var data=(QRErrorCorrectLevel[this.errorCorrectLevel]<<3)|maskPattern;
|
||
|
var bits=QRUtil.getBCHTypeInfo(data);
|
||
|
for(var i=0;i<15;i++){
|
||
|
var mod=(!test&&((bits>>i)&1)==1);
|
||
|
if(i<6){
|
||
|
this.modules[i][8]=mod;
|
||
|
}else if(i<8){
|
||
|
this.modules[i+1][8]=mod;
|
||
|
}else{
|
||
|
this.modules[this.moduleCount-15+i][8]=mod;
|
||
|
}
|
||
|
var mod=(!test&&((bits>>i)&1)==1);
|
||
|
if(i<8){
|
||
|
this.modules[8][this.moduleCount-i-1]=mod;
|
||
|
}else if(i<9){
|
||
|
this.modules[8][15-i-1+1]=mod;
|
||
|
}else{
|
||
|
this.modules[8][15-i-1]=mod;
|
||
|
}
|
||
|
}
|
||
|
this.modules[this.moduleCount-8][8]=(!test);
|
||
|
},
|
||
|
createData:function(){
|
||
|
var buffer=new QRBitBuffer();
|
||
|
var lengthBits=this.typeNumber>9?16:8;
|
||
|
buffer.put(4,4);
|
||
|
buffer.put(this.utf8bytes.length,lengthBits);
|
||
|
for(var i=0,l=this.utf8bytes.length;i<l;i++){
|
||
|
buffer.put(this.utf8bytes[i],8);
|
||
|
}
|
||
|
if(buffer.length+4<=this.totalDataCount*8){
|
||
|
buffer.put(0,4);
|
||
|
}
|
||
|
while(buffer.length%8!=0){
|
||
|
buffer.putBit(false);
|
||
|
}
|
||
|
while(true){
|
||
|
if(buffer.length>=this.totalDataCount*8){
|
||
|
break;
|
||
|
}
|
||
|
buffer.put(QRCodeAlg.PAD0,8);
|
||
|
if(buffer.length>=this.totalDataCount*8){
|
||
|
break;
|
||
|
}
|
||
|
buffer.put(QRCodeAlg.PAD1,8);
|
||
|
}
|
||
|
return this.createBytes(buffer);
|
||
|
},
|
||
|
createBytes:function(buffer){
|
||
|
var offset=0;
|
||
|
var maxDcCount=0;
|
||
|
var maxEcCount=0;
|
||
|
var length=this.rsBlock.length/3;
|
||
|
var rsBlocks=new Array();
|
||
|
for(var i=0;i<length;i++){
|
||
|
var count=this.rsBlock[i*3+0];
|
||
|
var totalCount=this.rsBlock[i*3+1];
|
||
|
var dataCount=this.rsBlock[i*3+2];
|
||
|
for(var j=0;j<count;j++){
|
||
|
rsBlocks.push([dataCount,totalCount]);
|
||
|
}
|
||
|
}
|
||
|
var dcdata=new Array(rsBlocks.length);
|
||
|
var ecdata=new Array(rsBlocks.length);
|
||
|
for(var r=0;r<rsBlocks.length;r++){
|
||
|
var dcCount=rsBlocks[r][0];
|
||
|
var ecCount=rsBlocks[r][1]-dcCount;
|
||
|
maxDcCount=Math.max(maxDcCount,dcCount);
|
||
|
maxEcCount=Math.max(maxEcCount,ecCount);
|
||
|
dcdata[r]=new Array(dcCount);
|
||
|
for(var i=0;i<dcdata[r].length;i++){
|
||
|
dcdata[r][i]=0xff&buffer.buffer[i+offset];
|
||
|
}
|
||
|
offset+=dcCount;
|
||
|
var rsPoly=QRUtil.getErrorCorrectPolynomial(ecCount);
|
||
|
var rawPoly=new QRPolynomial(dcdata[r],rsPoly.getLength()-1);
|
||
|
var modPoly=rawPoly.mod(rsPoly);
|
||
|
ecdata[r]=new Array(rsPoly.getLength()-1);
|
||
|
for(var i=0;i<ecdata[r].length;i++){
|
||
|
var modIndex=i+modPoly.getLength()-ecdata[r].length;
|
||
|
ecdata[r][i]=(modIndex>=0)?modPoly.get(modIndex):0;
|
||
|
}
|
||
|
}
|
||
|
var data=new Array(this.totalDataCount);
|
||
|
var index=0;
|
||
|
for(var i=0;i<maxDcCount;i++){
|
||
|
for(var r=0;r<rsBlocks.length;r++){
|
||
|
if(i<dcdata[r].length){
|
||
|
data[index++]=dcdata[r][i];
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
for(var i=0;i<maxEcCount;i++){
|
||
|
for(var r=0;r<rsBlocks.length;r++){
|
||
|
if(i<ecdata[r].length){
|
||
|
data[index++]=ecdata[r][i];
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
return data;
|
||
|
},
|
||
|
mapData:function(data,maskPattern){
|
||
|
var inc=-1;
|
||
|
var row=this.moduleCount-1;
|
||
|
var bitIndex=7;
|
||
|
var byteIndex=0;
|
||
|
for(var col=this.moduleCount-1;col>0;col-=2){
|
||
|
if(col==6)col--;
|
||
|
while(true){
|
||
|
for(var c=0;c<2;c++){
|
||
|
if(this.modules[row][col-c]==null){
|
||
|
var dark=false;
|
||
|
if(byteIndex<data.length){
|
||
|
dark=(((data[byteIndex]>>>bitIndex)&1)==1);
|
||
|
}
|
||
|
var mask=QRUtil.getMask(maskPattern,row,col-c);
|
||
|
if(mask){
|
||
|
dark=!dark;
|
||
|
}
|
||
|
this.modules[row][col-c]=dark;
|
||
|
bitIndex--;
|
||
|
if(bitIndex==-1){
|
||
|
byteIndex++;
|
||
|
bitIndex=7;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
row+=inc;
|
||
|
if(row<0||this.moduleCount<=row){
|
||
|
row-=inc;
|
||
|
inc=-inc;
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
};
|
||
|
QRCodeAlg.PAD0=0xEC;
|
||
|
QRCodeAlg.PAD1=0x11;
|
||
|
var QRErrorCorrectLevel=[1,0,3,2];
|
||
|
var QRMaskPattern={
|
||
|
PATTERN000:0,
|
||
|
PATTERN001:1,
|
||
|
PATTERN010:2,
|
||
|
PATTERN011:3,
|
||
|
PATTERN100:4,
|
||
|
PATTERN101:5,
|
||
|
PATTERN110:6,
|
||
|
PATTERN111:7
|
||
|
};
|
||
|
var QRUtil={
|
||
|
PATTERN_POSITION_TABLE:[
|
||
|
[],
|
||
|
[6,18],
|
||
|
[6,22],
|
||
|
[6,26],
|
||
|
[6,30],
|
||
|
[6,34],
|
||
|
[6,22,38],
|
||
|
[6,24,42],
|
||
|
[6,26,46],
|
||
|
[6,28,50],
|
||
|
[6,30,54],
|
||
|
[6,32,58],
|
||
|
[6,34,62],
|
||
|
[6,26,46,66],
|
||
|
[6,26,48,70],
|
||
|
[6,26,50,74],
|
||
|
[6,30,54,78],
|
||
|
[6,30,56,82],
|
||
|
[6,30,58,86],
|
||
|
[6,34,62,90],
|
||
|
[6,28,50,72,94],
|
||
|
[6,26,50,74,98],
|
||
|
[6,30,54,78,102],
|
||
|
[6,28,54,80,106],
|
||
|
[6,32,58,84,110],
|
||
|
[6,30,58,86,114],
|
||
|
[6,34,62,90,118],
|
||
|
[6,26,50,74,98,122],
|
||
|
[6,30,54,78,102,126],
|
||
|
[6,26,52,78,104,130],
|
||
|
[6,30,56,82,108,134],
|
||
|
[6,34,60,86,112,138],
|
||
|
[6,30,58,86,114,142],
|
||
|
[6,34,62,90,118,146],
|
||
|
[6,30,54,78,102,126,150],
|
||
|
[6,24,50,76,102,128,154],
|
||
|
[6,28,54,80,106,132,158],
|
||
|
[6,32,58,84,110,136,162],
|
||
|
[6,26,54,82,110,138,166],
|
||
|
[6,30,58,86,114,142,170]
|
||
|
],
|
||
|
G15:(1<<10)|(1<<8)|(1<<5)|(1<<4)|(1<<2)|(1<<1)|(1<<0),
|
||
|
G18:(1<<12)|(1<<11)|(1<<10)|(1<<9)|(1<<8)|(1<<5)|(1<<2)|(1<<0),
|
||
|
G15_MASK:(1<<14)|(1<<12)|(1<<10)|(1<<4)|(1<<1),
|
||
|
getBCHTypeInfo:function(data){
|
||
|
var d=data<<10;
|
||
|
while(QRUtil.getBCHDigit(d)-QRUtil.getBCHDigit(QRUtil.G15)>=0){
|
||
|
d^=(QRUtil.G15<<(QRUtil.getBCHDigit(d)-QRUtil.getBCHDigit(QRUtil.G15)));
|
||
|
}
|
||
|
return((data<<10)|d)^QRUtil.G15_MASK;
|
||
|
},
|
||
|
getBCHTypeNumber:function(data){
|
||
|
var d=data<<12;
|
||
|
while(QRUtil.getBCHDigit(d)-QRUtil.getBCHDigit(QRUtil.G18)>=0){
|
||
|
d^=(QRUtil.G18<<(QRUtil.getBCHDigit(d)-QRUtil.getBCHDigit(QRUtil.G18)));
|
||
|
}
|
||
|
return(data<<12)|d;
|
||
|
},
|
||
|
getBCHDigit:function(data){
|
||
|
var digit=0;
|
||
|
while(data!=0){
|
||
|
digit++;
|
||
|
data>>>=1;
|
||
|
}
|
||
|
return digit;
|
||
|
},
|
||
|
getPatternPosition:function(typeNumber){
|
||
|
return QRUtil.PATTERN_POSITION_TABLE[typeNumber-1];
|
||
|
},
|
||
|
getMask:function(maskPattern,i,j){
|
||
|
switch(maskPattern){
|
||
|
case QRMaskPattern.PATTERN000:
|
||
|
return(i+j)%2==0;
|
||
|
case QRMaskPattern.PATTERN001:
|
||
|
return i%2==0;
|
||
|
case QRMaskPattern.PATTERN010:
|
||
|
return j%3==0;
|
||
|
case QRMaskPattern.PATTERN011:
|
||
|
return(i+j)%3==0;
|
||
|
case QRMaskPattern.PATTERN100:
|
||
|
return(Math.floor(i/2)+Math.floor(j/3))%2==0;
|
||
|
case QRMaskPattern.PATTERN101:
|
||
|
return(i*j)%2+(i*j)%3==0;
|
||
|
case QRMaskPattern.PATTERN110:
|
||
|
return((i*j)%2+(i*j)%3)%2==0;
|
||
|
case QRMaskPattern.PATTERN111:
|
||
|
return((i*j)%3+(i+j)%2)%2==0;
|
||
|
default:
|
||
|
throw new Error("bad maskPattern:"+maskPattern);
|
||
|
}
|
||
|
},
|
||
|
getErrorCorrectPolynomial:function(errorCorrectLength){
|
||
|
var a=new QRPolynomial([1],0);
|
||
|
for(var i=0;i<errorCorrectLength;i++){
|
||
|
a=a.multiply(new QRPolynomial([1,QRMath.gexp(i)],0));
|
||
|
}
|
||
|
return a;
|
||
|
},
|
||
|
getLostPoint:function(qrCode){
|
||
|
var moduleCount=qrCode.getModuleCount(),
|
||
|
lostPoint=0,
|
||
|
darkCount=0;
|
||
|
for(var row=0;row<moduleCount;row++){
|
||
|
var sameCount=0;
|
||
|
var head=qrCode.modules[row][0];
|
||
|
for(var col=0;col<moduleCount;col++){
|
||
|
var current=qrCode.modules[row][col];
|
||
|
if(col<moduleCount-6){
|
||
|
if(current&&!qrCode.modules[row][col+1]&&qrCode.modules[row][col+2]&&qrCode.modules[row][col+3]&&qrCode.modules[row][col+4]&&!qrCode.modules[row][col+5]&&qrCode.modules[row][col+6]){
|
||
|
if(col<moduleCount-10){
|
||
|
if(qrCode.modules[row][col+7]&&qrCode.modules[row][col+8]&&qrCode.modules[row][col+9]&&qrCode.modules[row][col+10]){
|
||
|
lostPoint+=40;
|
||
|
}
|
||
|
}else if(col>3){
|
||
|
if(qrCode.modules[row][col-1]&&qrCode.modules[row][col-2]&&qrCode.modules[row][col-3]&&qrCode.modules[row][col-4]){
|
||
|
lostPoint+=40;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
if((row<moduleCount-1)&&(col<moduleCount-1)){
|
||
|
var count=0;
|
||
|
if(current)count++;
|
||
|
if(qrCode.modules[row+1][col])count++;
|
||
|
if(qrCode.modules[row][col+1])count++;
|
||
|
if(qrCode.modules[row+1][col+1])count++;
|
||
|
if(count==0||count==4){
|
||
|
lostPoint+=3;
|
||
|
}
|
||
|
}
|
||
|
if(head^current){
|
||
|
sameCount++;
|
||
|
}else{
|
||
|
head=current;
|
||
|
if(sameCount>=5){
|
||
|
lostPoint+=(3+sameCount-5);
|
||
|
}
|
||
|
sameCount=1;
|
||
|
}
|
||
|
if(current){
|
||
|
darkCount++;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
for(var col=0;col<moduleCount;col++){
|
||
|
var sameCount=0;
|
||
|
var head=qrCode.modules[0][col];
|
||
|
for(var row=0;row<moduleCount;row++){
|
||
|
var current=qrCode.modules[row][col];
|
||
|
if(row<moduleCount-6){
|
||
|
if(current&&!qrCode.modules[row+1][col]&&qrCode.modules[row+2][col]&&qrCode.modules[row+3][col]&&qrCode.modules[row+4][col]&&!qrCode.modules[row+5][col]&&qrCode.modules[row+6][col]){
|
||
|
if(row<moduleCount-10){
|
||
|
if(qrCode.modules[row+7][col]&&qrCode.modules[row+8][col]&&qrCode.modules[row+9][col]&&qrCode.modules[row+10][col]){
|
||
|
lostPoint+=40;
|
||
|
}
|
||
|
}else if(row>3){
|
||
|
if(qrCode.modules[row-1][col]&&qrCode.modules[row-2][col]&&qrCode.modules[row-3][col]&&qrCode.modules[row-4][col]){
|
||
|
lostPoint+=40;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
if(head^current){
|
||
|
sameCount++;
|
||
|
}else{
|
||
|
head=current;
|
||
|
if(sameCount>=5){
|
||
|
lostPoint+=(3+sameCount-5);
|
||
|
}
|
||
|
sameCount=1;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
var ratio=Math.abs(100*darkCount/moduleCount/moduleCount-50)/5;
|
||
|
lostPoint+=ratio*10;
|
||
|
return lostPoint;
|
||
|
}
|
||
|
};
|
||
|
var QRMath={
|
||
|
glog:function(n){
|
||
|
if(n<1){
|
||
|
throw new Error("glog("+n+")");
|
||
|
}
|
||
|
return QRMath.LOG_TABLE[n];
|
||
|
},
|
||
|
gexp:function(n){
|
||
|
while(n<0){
|
||
|
n+=255;
|
||
|
}
|
||
|
while(n>=256){
|
||
|
n-=255;
|
||
|
}
|
||
|
return QRMath.EXP_TABLE[n];
|
||
|
},
|
||
|
EXP_TABLE:new Array(256),
|
||
|
LOG_TABLE:new Array(256)
|
||
|
};
|
||
|
for(var i=0;i<8;i++){
|
||
|
QRMath.EXP_TABLE[i]=1<<i;
|
||
|
}
|
||
|
for(var i=8;i<256;i++){
|
||
|
QRMath.EXP_TABLE[i]=QRMath.EXP_TABLE[i-4]^QRMath.EXP_TABLE[i-5]^QRMath.EXP_TABLE[i-6]^QRMath.EXP_TABLE[i-8];
|
||
|
}
|
||
|
for(var i=0;i<255;i++){
|
||
|
QRMath.LOG_TABLE[QRMath.EXP_TABLE[i]]=i;
|
||
|
}
|
||
|
function QRPolynomial(num,shift){
|
||
|
if(num.length==undefined){
|
||
|
throw new Error(num.length+"/"+shift);
|
||
|
}
|
||
|
var offset=0;
|
||
|
while(offset<num.length&&num[offset]==0){
|
||
|
offset++;
|
||
|
}
|
||
|
this.num=new Array(num.length-offset+shift);
|
||
|
for(var i=0;i<num.length-offset;i++){
|
||
|
this.num[i]=num[i+offset];
|
||
|
}
|
||
|
}
|
||
|
QRPolynomial.prototype={
|
||
|
get:function(index){
|
||
|
return this.num[index];
|
||
|
},
|
||
|
getLength:function(){
|
||
|
return this.num.length;
|
||
|
},
|
||
|
multiply:function(e){
|
||
|
var num=new Array(this.getLength()+e.getLength()-1);
|
||
|
for(var i=0;i<this.getLength();i++){
|
||
|
for(var j=0;j<e.getLength();j++){
|
||
|
num[i+j]^=QRMath.gexp(QRMath.glog(this.get(i))+QRMath.glog(e.get(j)));
|
||
|
}
|
||
|
}
|
||
|
return new QRPolynomial(num,0);
|
||
|
},
|
||
|
mod:function(e){
|
||
|
var tl=this.getLength(),
|
||
|
el=e.getLength();
|
||
|
if(tl-el<0){
|
||
|
return this;
|
||
|
}
|
||
|
var num=new Array(tl);
|
||
|
for(var i=0;i<tl;i++){
|
||
|
num[i]=this.get(i);
|
||
|
}
|
||
|
while(num.length>=el){
|
||
|
var ratio=QRMath.glog(num[0])-QRMath.glog(e.get(0));
|
||
|
for(var i=0;i<e.getLength();i++){
|
||
|
num[i]^=QRMath.gexp(QRMath.glog(e.get(i))+ratio);
|
||
|
}
|
||
|
while(num[0]==0){
|
||
|
num.shift();
|
||
|
}
|
||
|
}
|
||
|
return new QRPolynomial(num,0);
|
||
|
}
|
||
|
};
|
||
|
var RS_BLOCK_TABLE=[
|
||
|
[1,26,19],
|
||
|
[1,26,16],
|
||
|
[1,26,13],
|
||
|
[1,26,9],
|
||
|
[1,44,34],
|
||
|
[1,44,28],
|
||
|
[1,44,22],
|
||
|
[1,44,16],
|
||
|
[1,70,55],
|
||
|
[1,70,44],
|
||
|
[2,35,17],
|
||
|
[2,35,13],
|
||
|
[1,100,80],
|
||
|
[2,50,32],
|
||
|
[2,50,24],
|
||
|
[4,25,9],
|
||
|
[1,134,108],
|
||
|
[2,67,43],
|
||
|
[2,33,15,2,34,16],
|
||
|
[2,33,11,2,34,12],
|
||
|
[2,86,68],
|
||
|
[4,43,27],
|
||
|
[4,43,19],
|
||
|
[4,43,15],
|
||
|
[2,98,78],
|
||
|
[4,49,31],
|
||
|
[2,32,14,4,33,15],
|
||
|
[4,39,13,1,40,14],
|
||
|
[2,121,97],
|
||
|
[2,60,38,2,61,39],
|
||
|
[4,40,18,2,41,19],
|
||
|
[4,40,14,2,41,15],
|
||
|
[2,146,116],
|
||
|
[3,58,36,2,59,37],
|
||
|
[4,36,16,4,37,17],
|
||
|
[4,36,12,4,37,13],
|
||
|
[2,86,68,2,87,69],
|
||
|
[4,69,43,1,70,44],
|
||
|
[6,43,19,2,44,20],
|
||
|
[6,43,15,2,44,16],
|
||
|
[4,101,81],
|
||
|
[1,80,50,4,81,51],
|
||
|
[4,50,22,4,51,23],
|
||
|
[3,36,12,8,37,13],
|
||
|
[2,116,92,2,117,93],
|
||
|
[6,58,36,2,59,37],
|
||
|
[4,46,20,6,47,21],
|
||
|
[7,42,14,4,43,15],
|
||
|
[4,133,107],
|
||
|
[8,59,37,1,60,38],
|
||
|
[8,44,20,4,45,21],
|
||
|
[12,33,11,4,34,12],
|
||
|
[3,145,115,1,146,116],
|
||
|
[4,64,40,5,65,41],
|
||
|
[11,36,16,5,37,17],
|
||
|
[11,36,12,5,37,13],
|
||
|
[5,109,87,1,110,88],
|
||
|
[5,65,41,5,66,42],
|
||
|
[5,54,24,7,55,25],
|
||
|
[11,36,12],
|
||
|
[5,122,98,1,123,99],
|
||
|
[7,73,45,3,74,46],
|
||
|
[15,43,19,2,44,20],
|
||
|
[3,45,15,13,46,16],
|
||
|
[1,135,107,5,136,108],
|
||
|
[10,74,46,1,75,47],
|
||
|
[1,50,22,15,51,23],
|
||
|
[2,42,14,17,43,15],
|
||
|
[5,150,120,1,151,121],
|
||
|
[9,69,43,4,70,44],
|
||
|
[17,50,22,1,51,23],
|
||
|
[2,42,14,19,43,15],
|
||
|
[3,141,113,4,142,114],
|
||
|
[3,70,44,11,71,45],
|
||
|
[17,47,21,4,48,22],
|
||
|
[9,39,13,16,40,14],
|
||
|
[3,135,107,5,136,108],
|
||
|
[3,67,41,13,68,42],
|
||
|
[15,54,24,5,55,25],
|
||
|
[15,43,15,10,44,16],
|
||
|
[4,144,116,4,145,117],
|
||
|
[17,68,42],
|
||
|
[17,50,22,6,51,23],
|
||
|
[19,46,16,6,47,17],
|
||
|
[2,139,111,7,140,112],
|
||
|
[17,74,46],
|
||
|
[7,54,24,16,55,25],
|
||
|
[34,37,13],
|
||
|
[4,151,121,5,152,122],
|
||
|
[4,75,47,14,76,48],
|
||
|
[11,54,24,14,55,25],
|
||
|
[16,45,15,14,46,16],
|
||
|
[6,147,117,4,148,118],
|
||
|
[6,73,45,14,74,46],
|
||
|
[11,54,24,16,55,25],
|
||
|
[30,46,16,2,47,17],
|
||
|
[8,132,106,4,133,107],
|
||
|
[8,75,47,13,76,48],
|
||
|
[7,54,24,22,55,25],
|
||
|
[22,45,15,13,46,16],
|
||
|
[10,142,114,2,143,115],
|
||
|
[19,74,46,4,75,47],
|
||
|
[28,50,22,6,51,23],
|
||
|
[33,46,16,4,47,17],
|
||
|
[8,152,122,4,153,123],
|
||
|
[22,73,45,3,74,46],
|
||
|
[8,53,23,26,54,24],
|
||
|
[12,45,15,28,46,16],
|
||
|
[3,147,117,10,148,118],
|
||
|
[3,73,45,23,74,46],
|
||
|
[4,54,24,31,55,25],
|
||
|
[11,45,15,31,46,16],
|
||
|
[7,146,116,7,147,117],
|
||
|
[21,73,45,7,74,46],
|
||
|
[1,53,23,37,54,24],
|
||
|
[19,45,15,26,46,16],
|
||
|
[5,145,115,10,146,116],
|
||
|
[19,75,47,10,76,48],
|
||
|
[15,54,24,25,55,25],
|
||
|
[23,45,15,25,46,16],
|
||
|
[13,145,115,3,146,116],
|
||
|
[2,74,46,29,75,47],
|
||
|
[42,54,24,1,55,25],
|
||
|
[23,45,15,28,46,16],
|
||
|
[17,145,115],
|
||
|
[10,74,46,23,75,47],
|
||
|
[10,54,24,35,55,25],
|
||
|
[19,45,15,35,46,16],
|
||
|
[17,145,115,1,146,116],
|
||
|
[14,74,46,21,75,47],
|
||
|
[29,54,24,19,55,25],
|
||
|
[11,45,15,46,46,16],
|
||
|
[13,145,115,6,146,116],
|
||
|
[14,74,46,23,75,47],
|
||
|
[44,54,24,7,55,25],
|
||
|
[59,46,16,1,47,17],
|
||
|
[12,151,121,7,152,122],
|
||
|
[12,75,47,26,76,48],
|
||
|
[39,54,24,14,55,25],
|
||
|
[22,45,15,41,46,16],
|
||
|
[6,151,121,14,152,122],
|
||
|
[6,75,47,34,76,48],
|
||
|
[46,54,24,10,55,25],
|
||
|
[2,45,15,64,46,16],
|
||
|
[17,152,122,4,153,123],
|
||
|
[29,74,46,14,75,47],
|
||
|
[49,54,24,10,55,25],
|
||
|
[24,45,15,46,46,16],
|
||
|
[4,152,122,18,153,123],
|
||
|
[13,74,46,32,75,47],
|
||
|
[48,54,24,14,55,25],
|
||
|
[42,45,15,32,46,16],
|
||
|
[20,147,117,4,148,118],
|
||
|
[40,75,47,7,76,48],
|
||
|
[43,54,24,22,55,25],
|
||
|
[10,45,15,67,46,16],
|
||
|
[19,148,118,6,149,119],
|
||
|
[18,75,47,31,76,48],
|
||
|
[34,54,24,34,55,25],
|
||
|
[20,45,15,61,46,16]
|
||
|
];
|
||
|
QRCodeAlg.prototype.getRightType=function(){
|
||
|
for(var typeNumber=1;typeNumber<41;typeNumber++){
|
||
|
var rsBlock=RS_BLOCK_TABLE[(typeNumber-1)*4+this.errorCorrectLevel];
|
||
|
if(rsBlock==undefined){
|
||
|
throw new Error("bad rs block @ typeNumber:"+typeNumber+"/errorCorrectLevel:"+this.errorCorrectLevel);
|
||
|
}
|
||
|
var length=rsBlock.length/3;
|
||
|
var totalDataCount=0;
|
||
|
for(var i=0;i<length;i++){
|
||
|
var count=rsBlock[i*3+0];
|
||
|
var dataCount=rsBlock[i*3+2];
|
||
|
totalDataCount+=dataCount*count;
|
||
|
}
|
||
|
var lengthBytes=typeNumber>9?2:1;
|
||
|
if(this.utf8bytes.length+lengthBytes<totalDataCount||typeNumber==40){
|
||
|
this.typeNumber=typeNumber;
|
||
|
this.rsBlock=rsBlock;
|
||
|
this.totalDataCount=totalDataCount;
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
};
|
||
|
function QRBitBuffer(){
|
||
|
this.buffer=new Array();
|
||
|
this.length=0;
|
||
|
}
|
||
|
QRBitBuffer.prototype={
|
||
|
get:function(index){
|
||
|
var bufIndex=Math.floor(index/8);
|
||
|
return((this.buffer[bufIndex]>>>(7-index%8))&1);
|
||
|
},
|
||
|
put:function(num,length){
|
||
|
for(var i=0;i<length;i++){
|
||
|
this.putBit(((num>>>(length-i-1))&1));
|
||
|
}
|
||
|
},
|
||
|
putBit:function(bit){
|
||
|
var bufIndex=Math.floor(this.length/8);
|
||
|
if(this.buffer.length<=bufIndex){
|
||
|
this.buffer.push(0);
|
||
|
}
|
||
|
if(bit){
|
||
|
this.buffer[bufIndex]|=(0x80>>>(this.length%8));
|
||
|
}
|
||
|
this.length++;
|
||
|
}
|
||
|
};
|
||
|
let qrcodeAlgObjCache=[];
|
||
|
QRCode=function(opt){
|
||
|
this.options={
|
||
|
text:'',
|
||
|
size:256,
|
||
|
correctLevel:3,
|
||
|
background:'#ffffff',
|
||
|
foreground:'#000000',
|
||
|
pdground:'#000000',
|
||
|
image:'',
|
||
|
imageSize:30,
|
||
|
canvasId:opt.canvasId,
|
||
|
context:opt.context,
|
||
|
usingComponents:opt.usingComponents,
|
||
|
showLoading:opt.showLoading,
|
||
|
loadingText:opt.loadingText,
|
||
|
};
|
||
|
if(typeof opt==='string'){
|
||
|
opt={
|
||
|
text:opt
|
||
|
};
|
||
|
}
|
||
|
if(opt){
|
||
|
for(var i in opt){
|
||
|
this.options[i]=opt[i];
|
||
|
}
|
||
|
}
|
||
|
var qrCodeAlg=null;
|
||
|
for(var i=0,l=qrcodeAlgObjCache.length;i<l;i++){
|
||
|
if(qrcodeAlgObjCache[i].text==this.options.text&&qrcodeAlgObjCache[i].text.correctLevel==this.options.correctLevel){
|
||
|
qrCodeAlg=qrcodeAlgObjCache[i].obj;
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
if(i==l){
|
||
|
qrCodeAlg=new QRCodeAlg(this.options.text,this.options.correctLevel);
|
||
|
qrcodeAlgObjCache.push({
|
||
|
text:this.options.text,
|
||
|
correctLevel:this.options.correctLevel,
|
||
|
obj:qrCodeAlg
|
||
|
});
|
||
|
}
|
||
|
let getForeGround=function(config){
|
||
|
var options=config.options;
|
||
|
if(options.pdground&&(
|
||
|
(config.row>1&&config.row<5&&config.col>1&&config.col<5)||
|
||
|
(config.row>(config.count-6)&&config.row<(config.count-2)&&config.col>1&&config.col<5)||
|
||
|
(config.row>1&&config.row<5&&config.col>(config.count-6)&&config.col<(config.count-2))
|
||
|
)){
|
||
|
return options.pdground;
|
||
|
}
|
||
|
return options.foreground;
|
||
|
}
|
||
|
let createCanvas=function(options){
|
||
|
if(options.showLoading){
|
||
|
uni.showLoading({
|
||
|
title:options.loadingText,
|
||
|
mask:true
|
||
|
});
|
||
|
}
|
||
|
var ctx=uni.createCanvasContext(options.canvasId,options.context);
|
||
|
var count=qrCodeAlg.getModuleCount();
|
||
|
var ratioSize=options.size;
|
||
|
var ratioImgSize=options.imageSize;
|
||
|
var tileW=(ratioSize/count).toPrecision(4);
|
||
|
var tileH=(ratioSize/count).toPrecision(4);
|
||
|
for(var row=0;row<count;row++){
|
||
|
for(var col=0;col<count;col++){
|
||
|
var w=(Math.ceil((col+1)*tileW)-Math.floor(col*tileW));
|
||
|
var h=(Math.ceil((row+1)*tileW)-Math.floor(row*tileW));
|
||
|
var foreground=getForeGround({
|
||
|
row:row,
|
||
|
col:col,
|
||
|
count:count,
|
||
|
options:options
|
||
|
});
|
||
|
ctx.setFillStyle(qrCodeAlg.modules[row][col]?foreground:options.background);
|
||
|
ctx.fillRect(Math.round(col*tileW),Math.round(row*tileH),w,h);
|
||
|
}
|
||
|
}
|
||
|
if(options.image){
|
||
|
var x=Number(((ratioSize-ratioImgSize)/2).toFixed(2));
|
||
|
var y=Number(((ratioSize-ratioImgSize)/2).toFixed(2));
|
||
|
drawRoundedRect(ctx,x,y,ratioImgSize,ratioImgSize,2,6,true,true)
|
||
|
ctx.drawImage(options.image,x,y,ratioImgSize,ratioImgSize);
|
||
|
function drawRoundedRect(ctxi,x,y,width,height,r,lineWidth,fill,stroke){
|
||
|
ctxi.setLineWidth(lineWidth);
|
||
|
ctxi.setFillStyle(options.background);
|
||
|
ctxi.setStrokeStyle(options.background);
|
||
|
ctxi.beginPath();
|
||
|
ctxi.moveTo(x+r,y);
|
||
|
ctxi.arcTo(x+width,y,x+width,y+r,r);
|
||
|
ctxi.arcTo(x+width,y+height,x+width-r,y+height,r);
|
||
|
ctxi.arcTo(x,y+height,x,y+height-r,r);
|
||
|
ctxi.arcTo(x,y,x+r,y,r);
|
||
|
ctxi.closePath();
|
||
|
if(fill){
|
||
|
ctxi.fill();
|
||
|
}
|
||
|
if(stroke){
|
||
|
ctxi.stroke();
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
setTimeout(()=>{
|
||
|
ctx.draw(true,()=>{
|
||
|
setTimeout(()=>{
|
||
|
uni.canvasToTempFilePath({
|
||
|
width:options.width,
|
||
|
height:options.height,
|
||
|
destWidth:options.width,
|
||
|
destHeight:options.height,
|
||
|
canvasId:options.canvasId,
|
||
|
quality:Number(1),
|
||
|
success:function(res){
|
||
|
if(options.cbResult){
|
||
|
options.cbResult(res.tempFilePath)
|
||
|
}
|
||
|
},
|
||
|
fail:function(res){
|
||
|
if(options.cbResult){
|
||
|
options.cbResult(res)
|
||
|
}
|
||
|
},
|
||
|
complete:function(){
|
||
|
if(options.showLoading){
|
||
|
uni.hideLoading();
|
||
|
}
|
||
|
},
|
||
|
},options.context);
|
||
|
},options.text.length+100);
|
||
|
});
|
||
|
},options.usingComponents?0:150);
|
||
|
}
|
||
|
createCanvas(this.options);
|
||
|
let empty=function(v){
|
||
|
let tp=typeof v,
|
||
|
rt=false;
|
||
|
if(tp=="number"&&String(v)==""){
|
||
|
rt=true
|
||
|
}else if(tp=="undefined"){
|
||
|
rt=true
|
||
|
}else if(tp=="object"){
|
||
|
if(JSON.stringify(v)=="{}"||JSON.stringify(v)=="[]"||v==null)rt=true
|
||
|
}else if(tp=="string"){
|
||
|
if(v==""||v=="undefined"||v=="null"||v=="{}"||v=="[]")rt=true
|
||
|
}else if(tp=="function"){
|
||
|
rt=false
|
||
|
}
|
||
|
return rt
|
||
|
}
|
||
|
};
|
||
|
QRCode.prototype.clear=function(fn){
|
||
|
var ctx=uni.createCanvasContext(this.options.canvasId,this.options.context)
|
||
|
ctx.clearRect(0,0,this.options.size,this.options.size)
|
||
|
ctx.draw(false,()=>{
|
||
|
if(fn){
|
||
|
fn()
|
||
|
}
|
||
|
})
|
||
|
};
|
||
|
})()
|
||
|
export default QRCode
|