Last active
August 29, 2015 14:16
-
-
Save getchenge/a69fe38cdb8c2a46b84d to your computer and use it in GitHub Desktop.
a qrcode-service by nodejs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
//npm install qrcode | |
"use strict"; | |
var _ = require('lodash'); | |
var aid = require(__base + 'lib/aid'); | |
var defaultNumber = aid.defaultNumber(); | |
function resample_hermite(canvas, W, H, W2, H2) { | |
var time1 = Date.now(); | |
W2 = Math.round(W2); | |
H2 = Math.round(H2); | |
var img = canvas.getContext("2d").getImageData(0, 0, W, H); | |
var img2 = canvas.getContext("2d").getImageData(0, 0, W2, H2); | |
var data = img.data; | |
var data2 = img2.data; | |
var ratio_w = W / W2; | |
var ratio_h = H / H2; | |
var ratio_w_half = Math.ceil(ratio_w / 2); | |
var ratio_h_half = Math.ceil(ratio_h / 2); | |
for (var j = 0; j < H2; j++) { | |
for (var i = 0; i < W2; i++) { | |
var x2 = (i + j * W2) * 4; | |
var weight = 0; | |
var weights = 0; | |
var weights_alpha = 0; | |
var gx_g, gx_b, gx_a; | |
var gx_r = gx_g = gx_b = gx_a = 0; | |
var center_y = (j + 0.5) * ratio_h; | |
for (var yy = Math.floor(j * ratio_h); yy < (j + 1) * ratio_h; yy++) { | |
var dy = Math.abs(center_y - (yy + 0.5)) / ratio_h_half; | |
var center_x = (i + 0.5) * ratio_w; | |
var w0 = dy * dy //pre-calc part of w | |
for (var xx = Math.floor(i * ratio_w); xx < (i + 1) * ratio_w; xx++) { | |
var dx = Math.abs(center_x - (xx + 0.5)) / ratio_w_half; | |
var w = Math.sqrt(w0 + dx * dx); | |
if (w >= -1 && w <= 1) { | |
//hermite filter | |
weight = 2 * w * w * w - 3 * w * w + 1; | |
if (weight > 0) { | |
dx = 4 * (xx + yy * W); | |
//alpha | |
gx_a += weight * data[dx + 3]; | |
weights_alpha += weight; | |
//colors | |
if (data[dx + 3] < 255) | |
weight = weight * data[dx + 3] / 250; | |
gx_r += weight * data[dx]; | |
gx_g += weight * data[dx + 1]; | |
gx_b += weight * data[dx + 2]; | |
weights += weight; | |
} | |
} | |
} | |
} | |
data2[x2] = gx_r / weights; | |
data2[x2 + 1] = gx_g / weights; | |
data2[x2 + 2] = gx_b / weights; | |
data2[x2 + 3] = gx_a / weights_alpha; | |
} | |
} | |
//console.log("hermite = " + (Math.round(Date.now() - time1) / 1000) + " s"); | |
canvas.getContext("2d").clearRect(0, 0, Math.max(W, W2), Math.max(H, H2)); | |
canvas.width = W2; | |
canvas.height = H2; | |
canvas.getContext("2d").putImageData(img2, 0, 0); | |
return canvas; | |
} | |
function defaultNumber(val, default_val) { | |
val = +val; | |
if (typeof val == 'number' && !isNaN(val)) { | |
return val; | |
} else { | |
return default_val; | |
} | |
} | |
module.exports = function (req, res) { | |
var params = req.query || {}; | |
var QRCode = require('qrcode'); | |
var draw = new QRCode.QRCodeDraw(); | |
var Canvas = QRCode.canvas; | |
var content = params['content'] || 'hello'; | |
var width = params['width']; | |
var errorLevelObj = {//容错率等级 L M Q H | |
L: 1, | |
M: 0, | |
Q: 3, | |
H: 2 | |
}; | |
var errorlevel = params['errorlevel'] && params['errorlevel'].toUpperCase(); | |
var margin = +params['margin']; | |
//draw.color = { | |
// dark: '#333', | |
// light: '#efefef' | |
//}; | |
draw.scale = defaultNumber(params['scale'], 10);//黑点尺寸 | |
draw.defaultErrorCorrectLevel = typeof errorLevelObj[errorlevel] == 'number' ? errorLevelObj[errorlevel] : 1; | |
draw.marginScaleFactor = 0;//边距点个数 | |
draw.defaultMargin = defaultNumber(params['margin'], 10); | |
//if (_.isNumber(margin) && !_.isNaN(margin)) {//边距大小,像素 | |
// draw.defaultMargin = margin; | |
//} else { | |
// draw.defaultMargin = 10; | |
//} | |
//draw.draw(new Canvas(200, 200), content, {version: +params['level'] || 10}, function (error, canvas) {//設置容量等級 | |
draw.draw(new Canvas(200, 200), content, function (error, canvas) { | |
if (width) { | |
canvas = resample_hermite(canvas, canvas.width, canvas.height, width, width);//重置canvas大小 | |
} | |
canvas.toDataURL(function (err, url) {//转换为二进制以图片格式输出 | |
url = url.replace('data:image/png;base64,', ''); | |
url = new Buffer(url, 'base64'); | |
res.type('png'); | |
res.end(url, 'binary'); | |
}); | |
}); | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment