标题和摘要中都提到,本文的一个目的就是生成定宽的二维码图片(还有一个很特别的要求,打印出来得图片需要被条码枪识别),用的第三方工具类库是itext,版本是2.0。
为了实现二维码的指定宽高,我的第一个想法是“先用itext生成图片,然后通过缩放或者剪裁来指定图片的宽高”,代码可以参考 http://my.oschina.net/psuyun/blog/228908 ,这种做法,达到了生成指定宽高的效果,让人遗憾的一点是,用此法打印出来的二维码不能被条码枪识别,无奈之下,只能寻求他法。
其实针对第一个想法的失败,我一直有个担心是,生成的图片dpi不够,这个说法可以参考http://blog.csdn.net/chenweionline/article/details/2026855
回到正题,这次我的思路是研究itext的源码,看看是怎么生成图片的,很遗憾,这次让我成功了。下面给出关键代码和说明(有兴趣的同学,可以去研究下他的源码):
//BarcodePDF417 为itext中生成二维码图片的工具类
BarcodePDF417 barcodePDF417 = new BarcodePDF417();
//下面两行很重要,用于定宽
barcodePDF417.setOptions(BarcodePDF417.PDF417_FIXED_COLUMNS);
//设置codeColumns,主要用于指定生成二维码图片的长度,他的计算公式为: (17 * codeColumns +3)+ 18,得到的这个值,正是二维码图片的宽度,公文二维码的宽度一般是188,所以我的codeColumns=7
barcodePDF417.setCodeColumns(7);
//下面两行动态决定二维码图片的高度,分别说明如下:
//1、setText方法用于设置二维码图片的内容,也是动态高的由来,因为图片保存的内容有多有少(有上限,string.length < 926, 一个大概值 ),相对 codeColumns,还有一个概念 codeRows,codeRows跟二维码的高度有关系。
//关于codeRows值的计算,codeRows = (tot - 1) / codeColumns + 1; 这行代码能给我们一个说法,codeRows跟tot 和 codeColumns 有关系,其中tot的重要组成部分就是二维码的内容也就是setText的值,内容越多,codeRows就会大一些
//所以说二维码的高其实是一个动态的高
//2、再来看看yHeight这个东西有什么用
//int h = (int)yHeight;
//java.awt.Image img = canvas.createImage(new MemoryImageSource(bitColumns, codeRows * h, pix, 0, bitColumns));
//对于二维码图片的高,相信不用我在多说了,额外补充一点,bitColumns其实就是188
barcodePDF417.setText(strInfo.getBytes());
barcodePDF417.setYHeight(2);
//生成图片
Image pdfImg = barcodePDF417.createAwtImage(Color.black, Color.white);
相关的说明,在示例代码中都有说明了,还有什么不清楚,可以找到我的qq进行交流。
好在功夫不负有心人,这个问题就这么OK了。