直接上代码,以后有时间再添加说明
二维码的基本信息,包括要二维码内包含的文字,嵌入的图片,加到二维码下边的文字
/**
*
*/
package com.tong.util.code;
import java.io.File;
/**
* @author zxm
*
*/
public class CodeModel {
private String contents;
private int width = 400;
private int height = 400;
private String format = "gif";
private String character_set = "utf-8";
private int fontSize = 12;
private File logoFile;
private float logoRatio = 0.20f;
private String desc;
private int whiteWidth;//白边的宽度
private int[] bottomStart;//二维码最下边的开始坐标
private int[] bottomEnd;//二维码最下边的结束坐标
public String getContents() {
return contents;
}
public void setContents(String contents) {
this.contents = contents;
}
public int getWidth() {
return width;
}
public void setWidth(int width) {
this.width = width;
}
public int getHeight() {
return height;
}
public void setHeight(int height) {
this.height = height;
}
public String getFormat() {
return format;
}
public void setFormat(String format) {
this.format = format;
}
public String getCharacter_set() {
return character_set;
}
public void setCharacter_set(String character_set) {
this.character_set = character_set;
}
public int getFontSize() {
return fontSize;
}
public void setFontSize(int fontSize) {
this.fontSize = fontSize;
}
public File getLogoFile() {
return logoFile;
}
public void setLogoFile(File logoFile) {
this.logoFile = logoFile;
}
public float getLogoRatio() {
return logoRatio;
}
public void setLogoRatio(float logoRatio) {
this.logoRatio = logoRatio;
}
public String getDesc() {
return desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
public int getWhiteWidth() {
return whiteWidth;
}
public void setWhiteWidth(int whiteWidth) {
this.whiteWidth = whiteWidth;
}
public int[] getBottomStart() {
return bottomStart;
}
public void setBottomStart(int[] bottomStart) {
this.bottomStart = bottomStart;
}
public int[] getBottomEnd() {
return bottomEnd;
}
public void setBottomEnd(int[] bottomEnd) {
this.bottomEnd = bottomEnd;
}
}
生成二维码
/**
*
*/
package com.tong.util.code;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.image.BufferedImage;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.util.HashMap;
import java.util.Map;
import javax.imageio.ImageIO;
import org.springframework.util.StringUtils;
import com.google.zxing.BarcodeFormat;
import com.google.zxing.EncodeHintType;
import com.google.zxing.MultiFormatWriter;
import com.google.zxing.WriterException;
import com.google.zxing.common.BitMatrix;
import com.google.zxing.qrcode.decoder.ErrorCorrectionLevel;
/**
* @author zxm
*
*/
public class CodeCreator {
private static int BLACK = 0x000000;
private static int WHITE = 0xFFFFFF;
private BufferedImage createCodeImage(CodeModel info){
String contents = info.getContents();
int width = info.getWidth();
int height = info.getHeight();
Map<EncodeHintType, Object> hint = new HashMap<>();
hint.put(EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.H);
hint.put(EncodeHintType.CHARACTER_SET, info.getCharacter_set());
hint.put(EncodeHintType.MARGIN, 0);
MultiFormatWriter writer = new MultiFormatWriter();
BufferedImage img = null;
try {
BitMatrix bm = writer.encode(contents, BarcodeFormat.QR_CODE, width, height, hint);
int[] locationTopLeft = bm.getTopLeftOnBit();
int[] locationBottomRight = bm.getBottomRightOnBit();
info.setBottomStart(new int[]{locationTopLeft[0], locationBottomRight[1]});
info.setBottomEnd(locationBottomRight);
int w = bm.getWidth();
int h = bm.getHeight();
img = new BufferedImage(w, h, BufferedImage.TYPE_INT_RGB);
for(int x=0;x<w;x++){
for(int y=0;y<h;y++){
img.setRGB(x, y, bm.get(x, y) ? BLACK : WHITE);
}
}
} catch (WriterException e) {
e.printStackTrace();
}
return img;
}
public void createCodeImage(CodeModel info, OutputStream output){
BufferedImage bm = createCodeImage(info);
File logoFile = info.getLogoFile();
if(logoFile!=null && logoFile.exists()){
try{
BufferedImage logoImg = ImageIO.read(logoFile);
int logoWidth = logoImg.getWidth();
int logoHeight = logoImg.getHeight();
int width = bm.getWidth();
int height = bm.getHeight();
float ratio = info.getLogoRatio();
if(ratio>0){
logoWidth = logoWidth>width*ratio ? (int)(width*ratio) : logoWidth;
logoHeight = logoHeight>height*ratio ? (int)(height*ratio) : logoHeight;
}
int x = (width-logoWidth)/2;
int y = (height-logoHeight)/2;
Graphics g = bm.getGraphics();
g.drawImage(logoImg, x, y, logoWidth, logoHeight, null);
String desc = info.getDesc();
//int whiteWidth = 8;
if(!StringUtils.isEmpty(desc)){
int whiteWidth = info.getHeight()-info.getBottomEnd()[1];
// width = info.getBottomEnd()[0]-info.getBottomStart()[0];
// height = info.getBottomEnd()[1]+1;
Font font = new Font("黑体", Font.BOLD, info.getFontSize());
int fontHeight = g.getFontMetrics(font).getHeight();
//计算需要多少行
int lineNum = 1;
int currentLineLen = 0;
for(int i=0;i<desc.length();i++){
char c = desc.charAt(i);
int charWidth = g.getFontMetrics(font).charWidth(c);
if(currentLineLen+charWidth>width){
lineNum++;
currentLineLen = 0;
continue;
}
currentLineLen += charWidth;
}
int totalFontHeight = fontHeight*lineNum;
int wordTopMargin = 4;
BufferedImage bm1 = new BufferedImage(width, height+totalFontHeight+wordTopMargin-whiteWidth, BufferedImage.TYPE_INT_RGB);
Graphics g1 = bm1.getGraphics();
if(totalFontHeight+wordTopMargin-whiteWidth>0){
g1.setColor(Color.WHITE);
g1.fillRect(0, height, width, totalFontHeight+wordTopMargin-whiteWidth);
}
g1.setColor(new Color(BLACK));
g1.setFont(font);
g1.drawImage(bm, 0, 0, null);
width = info.getBottomEnd()[0]-info.getBottomStart()[0];
height = info.getBottomEnd()[1]+1;
currentLineLen = 0;
int currentLineIndex = 0;
int baseLo = g1.getFontMetrics().getAscent();
for(int i=0;i<desc.length();i++){
String c = desc.substring(i, i+1);
int charWidth = g.getFontMetrics(font).stringWidth(c);
if(currentLineLen+charWidth>width){
currentLineIndex++;
currentLineLen = 0;
g1.drawString(c, currentLineLen + whiteWidth, height+baseLo+fontHeight*(currentLineIndex)+wordTopMargin);
currentLineLen = charWidth;
continue;
}
g1.drawString(c, currentLineLen+whiteWidth, height+baseLo+fontHeight*(currentLineIndex) + wordTopMargin);
currentLineLen += charWidth;
}
g1.dispose();
bm = bm1;
}
}catch(Exception e){
e.printStackTrace();
}
}
try{
ImageIO.write(bm, StringUtils.isEmpty(info.getFormat()) ? info.getFormat() : info.getFormat(), output);
}catch(Exception e){
e.printStackTrace();
}
}
public void createCodeImage(CodeModel info, File file){
File parent = file.getParentFile();
if(!parent.exists())parent.mkdirs();
OutputStream output = null;
try{
output = new BufferedOutputStream(new FileOutputStream(file));
createCodeImage(info, output);
output.flush();
}catch(Exception e){
e.printStackTrace();
}finally{
try {
output.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
public void createCodeImage(CodeModel info, String filePath){
createCodeImage(info, new File(filePath));
}
}
二维码读取
/**
*
*/
package com.tong.util.code;
import java.awt.image.BufferedImage;
import java.io.InputStream;
import java.util.HashMap;
import java.util.Map;
import javax.imageio.ImageIO;
import com.google.zxing.BarcodeFormat;
import com.google.zxing.BinaryBitmap;
import com.google.zxing.DecodeHintType;
import com.google.zxing.LuminanceSource;
import com.google.zxing.RGBLuminanceSource;
import com.google.zxing.Result;
import com.google.zxing.common.HybridBinarizer;
import com.google.zxing.qrcode.QRCodeReader;
/**
* @author zxm
*
*/
public class CodeDecoder {
public String decode(InputStream input){
Map<DecodeHintType, Object> hint = new HashMap<DecodeHintType, Object>();
hint.put(DecodeHintType.POSSIBLE_FORMATS, BarcodeFormat.QR_CODE);
String result = "";
try{
BufferedImage img = ImageIO.read(input);
int[] pixels = img.getRGB(0, 0, img.getWidth(), img.getHeight(), null, 0, img.getWidth());
LuminanceSource source = new RGBLuminanceSource(img.getWidth(), img.getHeight(), pixels);
BinaryBitmap bitmap = new BinaryBitmap(new HybridBinarizer(source));
QRCodeReader reader = new QRCodeReader();
Result r = reader.decode(bitmap, hint);
result = r.getText();
}catch(Exception e){
result="读取错误";
}
return result;
}
}
测试代码
/**
*
*/
package com.tong.util;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.HashMap;
import java.util.Map;
import javax.imageio.ImageIO;
import com.google.zxing.BarcodeFormat;
import com.google.zxing.EncodeHintType;
import com.google.zxing.MultiFormatWriter;
import com.google.zxing.WriterException;
import com.google.zxing.common.BitMatrix;
import com.google.zxing.qrcode.decoder.ErrorCorrectionLevel;
import com.tong.util.code.CodeCreator;
import com.tong.util.code.CodeDecoder;
import com.tong.util.code.CodeModel;
/**
* @author zxm
*
*/
public class QRCodeMain{
private static void encode() {
CodeCreator creator = new CodeCreator();
CodeModel info = new CodeModel();
info.setWidth(400);
info.setHeight(400);
info.setFontSize(24);
info.setContents("<a href='http://www.sohu.com'>人生就是拼搏</a>");
//info.setContents("http://www.sohu.com");
info.setContents("万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新\n万水千山只等闲\n小荷才楼尖尖角\n谁家新燕啄春泥\n无边光景一时新");
info.setLogoFile(new File("D:/workspaces/workspace1/tong3/WebContent/img/girl3.jpg"));
info.setDesc("你怎么会知道我的苦,我是一页孤舟,漂流在尘世中asdfsaf33333abCD1234567890");
//info.setLogoDesc("一叶浮萍归大海,adsasfbhtjg人生何处不相逢");
//info.setLogoDesc("一叶浮萍");
creator.createCodeImage(info, "D:/2Dcode/dest." + info.getFormat());
}
static public void decode(InputStream input){
CodeDecoder decoder = new CodeDecoder();
String result = decoder.decode(input);
System.out.println(result);
}
public static void main(String[] args) throws Exception{
encode();
//decode(new FileInputStream(new File("D:/2Dcode/dest.gif")));
}
}

本文展示了如何利用ZXing库在二维码中添加图片和文字,并提供了生成及读取二维码的代码示例。
1525

被折叠的 条评论
为什么被折叠?



