上一篇实现了粗略的打印元素绘制协议,并且写了打印示例和导出示例,趁着空隙时间完善一下打印。
首先元素构造函数默认初始化每个字段值
package LIS.Core.Dto;
/**
* 打印约定元素
*/
public class PrintElement {
/**
* 元素类型
*/
public String PrintType;
/**
* X
*/
public String PrintX;
/**
* Y
*/
public String PrintY;
/**
* 字体
*/
public String PrintFont;
/**
* 字体大小
*/
public String PrintFontSize;
/**
* 字体样式
*/
public String PrintFontStyle;
/**
* 长度
*/
public String PrintLength;
/**
* 宽度
*/
public String PrintWidth;
/**
* 高度
*/
public String PrintHeight;
/**
* 文本
*/
public String PrintText;
/**
* 数据字段
*/
public String DataField;
/**
* 特殊标志
*/
public String PrintFlag;
/**
* 停靠
*/
public String PrintAlignment;
/**
* 图片
*/
public String PrintImageFile;
/**
* 颜色
*/
public String PrintColor;
/**
* 旋转角度
*/
public String Angle;
/**
* 垂直显示
*/
public String IsVShow;
/**
* 业务ID
*/
public String BllID;
/**
* 构造
*/
public PrintElement()
{
PrintType="";
PrintX="10";
PrintY="10";
PrintFont="宋体";
PrintFontSize="10";
PrintFontStyle="";
PrintLength="10";
PrintWidth="20";
PrintHeight="20";
PrintText="";
DataField="";
PrintFlag="";
PrintAlignment="";
PrintImageFile="";
PrintColor="";
Angle="0";
IsVShow="";
BllID="";
}
}
加强绘制元素的类型约束和检查,把换页,打印机控制等都实现
package LIS.Core.Util;
import LIS.Core.Dto.PrintElement;
import java.awt.*;
import java.util.List;
/**
* 打印元素绘制协议实现,先提供各种元素的初级api,参数类型限制比较松散,后面再包限制严格的api,避免参数错误导致的画图问题
*/
public class PrintDrawProtocol {
/**
* 打印纸张方向 Landscape:旋转 Portrait:正常
*/
public enum PrintLayout {
Landscape, Portrait
}
/**
* 打印文本的停靠方向
*/
public enum PrintAlignment {
Left, Center, Right
}
/**
* 控制打印机,在第一个输出的元素就会按输出控制打印机
*
* @param paper A4或A5等
* @param paperLayout Landscape或Portrait
* @param printerName 打印机名称,tiaoma等
* @param paperSource 送纸来源,1,2等
* @param paperWidth 纸张宽度
* @param paperHeight 纸张高度
* @return
*/
public static PrintElement ControlPrinter(String paper, PrintLayout paperLayout, String printerName, String paperSource, int paperWidth, int paperHeight) {
PrintElement ret = new PrintElement();
ret.PrintType = "PRINTER";
ret.DataField = paper;
ret.PrintAlignment = paperLayout.toString();
ret.PrintFlag = printerName;
ret.PrintFont = paperSource;
ret.PrintWidth = String.valueOf(paperWidth);
ret.PrintHeight = String.valueOf(paperHeight);
return ret;
}
/**
* 控制打印机,在第一个输出的元素就会按输出控制打印机,只会按名称选择打印机,不会控制纸张等
*
* @param printerName 打印机名称,tiaoma等
* @return
*/
public static PrintElement ControlPrinterName(String printerName) {
PrintElement ret = new PrintElement();
ret.PrintType = "PRINTERONLY";
ret.PrintFlag = printerName;
return ret;
}
/**
* 输出此元素通知打印换页
*
* @return
*/
public static PrintElement ChangePage() {
PrintElement ret = new PrintElement();
ret.PrintType = "PAGE";
return ret;
}
/**
* 让用户选择打印机并且按唯一键缓存
*
* @param uniqueFlag
* @return
*/
public static PrintElement SelectPrinter(String uniqueFlag) {
PrintElement ret = new PrintElement();
ret.PrintType = "SELECTPRINTER";
ret.PrintFlag = uniqueFlag;
return ret;
}
/**
* 绘图输出第一个元素为ImageInfo类型的元素讲按照以上属性创建位图,其他后续元素的画笔操作都在该位图上执行。
*
* @param width 图的宽度
* @param height 图的高度
* @param color 颜色
* @return
*/
public static PrintElement CreateImage(int width, int height, String color) {
PrintElement ret = new PrintElement();
ret.PrintType = "ImageInfo";
ret.PrintWidth = String.valueOf(width);
ret.PrintHeight = String.valueOf(height);
ret.PrintColor = color;
return ret;
}
/**
* 画标签
*
* @param x x坐标(*必填)
* @param y y坐标(*必填)
* @param drawStr 要绘制的文本(*必填)
* @param font 字体
* @param fontSize 字体大小
* @param fontStyle 字体样式
* @param alignment 字体靠齐方向 Center:居中 Right:靠右 Justified或者空:靠左
* @param color 颜色,html颜色 red #ffffff这种
* @param angle 旋转角度,角度数字
* @return
*/
public static PrintElement DrawLabel(int x, int y, String drawStr, String font, Integer fontSize, String fontStyle, PrintAlignment alignment, String color, String angle) {
PrintElement ret = new PrintElement();
ret.PrintX = String.valueOf(x);
ret.PrintY = String.valueOf(y);
ret.PrintText = drawStr;
ret.PrintFont = font;
if (fontSize == null) {
fontSize = 9;
}
ret.PrintFontSize = String.valueOf(fontSize);
ret.PrintFontStyle = fontStyle;
if(alignment!=null)
{
ret.PrintAlignment = alignment.toString();
}
ret.Angle = String.valueOf(angle);
ret.PrintType = "Label";
return ret;
}
/**
* 画线
*
* @param x 起点x坐标(*必填)
* @param y 起点y坐标(*必填)
* @param x1 终点x坐标(*必填)
* @param y1 终点y坐标(*必填)
* @param size 线宽度 默认1
* @param dashStyle 线样式,0、1、2、3、4
* @param color 颜色 html颜色 red #ffffff这种
* @return
*/
public static PrintElement DrawLine(int x, int y, int x1, int y1, Integer size, String dashStyle, String color) {
if (size == null) {
size = 1;
}
PrintElement ret = new PrintElement();
ret.PrintX = String.valueOf(x);
ret.PrintY = String.valueOf(y);
ret.PrintWidth = String.valueOf(x1);
ret.PrintHeight = String.valueOf(y1);
ret.PrintLength = String.valueOf(size);
ret.PrintFlag = dashStyle;
ret.PrintColor = color;
ret.PrintType = "ILineN";
return ret;
}
/**
* 画条码
*
* @param x x坐标(*必填)
* @param y y坐标(*必填)
* @param barStr 要绘制的文本(*必填)
* @param isDrawText 是否绘制条码文本 false:不画条码文本 true:画条码文本
* @param width 宽度 小于10认为使用条码本身宽度不做缩放
* @param height 高度
* @param barType 条码码制,空默认,可为A、B、C
* @param font 字体
* @param fontSize 字体大小
* @param fontStyle 字体样式
* @param alignment 字体靠齐方向 Center:居中 Right:靠右 Justified或者空:靠左
* @param color 颜色,html颜色 red #ffffff这种
* @param angle 旋转角度,角度数字
*/
public static PrintElement DrawBarCode(int x, int y, String barStr, boolean isDrawText, int width, int height, String barType, String font, Integer fontSize, String fontStyle, PrintAlignment alignment, String color, String angle) {
PrintElement ret = new PrintElement();
ret.PrintX = String.valueOf(x);
ret.PrintY = String.valueOf(y);
ret.PrintText = barStr;
ret.PrintFont = font;
if (fontSize == null) {
fontSize = 9;
}
ret.PrintFontSize = String.valueOf(fontSize);
ret.PrintFontStyle = fontStyle;
if(alignment!=null) {
ret.PrintAlignment = alignment.toString();
}
ret.Angle = String.valueOf(angle);
ret.PrintWidth = String.valueOf(width);
ret.PrintHeight = String.valueOf(height);
ret.PrintType = "Data";
String Flag = "";
if (isDrawText == false) {
Flag = "N";
}
String PrintFlag = "BarCode" + Flag + barType;
ret.PrintFlag = PrintFlag;
return ret;
}
/**
* 画二维吗
*
* @param x x坐标(*必填)
* @param y y坐标(*必填)
* @param barStr 要绘制的文本(*必填)
* @param width 宽度
* @param height 高度
* @return
*/
public static PrintElement DrawQRCode(int x, int y, String barStr, int width, int height) {
PrintElement ret = new PrintElement();
ret.PrintX = String.valueOf(x);
ret.PrintY = String.valueOf(y);
ret.PrintText = barStr;
ret.PrintWidth = String.valueOf(width);
ret.PrintHeight = String.valueOf(height);
ret.PrintType = "Data";
String PrintFlag = "QRCode";
ret.PrintFlag = PrintFlag;
return ret;
}
/**
* 画点
*
* @param x x坐标(*必填)
* @param y y坐标(*必填)
* @param width 宽度
* @param height 高度
* @param type 点类型o [] <>或者空串
* @param color 颜色,html颜色 red #ffffff这种
* @return
*/
public static PrintElement DrawPoint(int x, int y, int width, int height, String type, String color) {
PrintElement ret = new PrintElement();
ret.PrintX = String.valueOf(x);
ret.PrintY = String.valueOf(y);
ret.PrintWidth = String.valueOf(width);
ret.PrintHeight = String.valueOf(height);
ret.PrintType = "Point";
ret.PrintFlag = type;
ret.PrintColor = color;
return ret;
}
/**
* 画多边形
*
* @param pointList 点集合描述串多个点用^分割,一个点的xy用@分割 如:10@10^29@20^100@15(*必填)
* @param color 颜色,html颜色 red #ffffff这种
* @return
*/
public static PrintElement DrawPoly(List<Point> pointList, String color) {
String polyStr = "";
if (pointList != null || pointList.size() > 0) {
for (Point p : pointList) {
if (polyStr.isEmpty()) {
polyStr = p.x + "@" + p.y;
} else {
polyStr += "^" + p.x + "@" + p.y;
}
}
}
PrintElement ret = new PrintElement();
ret.PrintText = polyStr;
ret.PrintType = "Poly";
ret.PrintColor = color;
return ret;
}
/**
* 画多边形
*
* @param points 点集合描述串多个点用^分割,一个点的xy用@分割 如:10@10^29@20^100@15(*必填)
* @param color 颜色,html颜色 red #ffffff这种
* @return
*/
public static PrintElement DrawPoly(String points, String color) {
PrintElement ret = new PrintElement();
ret.PrintText = points;
ret.PrintType = "Poly";
ret.PrintColor = color;
return ret;
}
/**
* 画图片
*
* @param x x坐标(*必填)
* @param y y坐标(*必填)
* @param width 宽度(*必填)
* @param height 高度(*必填)
* @param dataField :数据,签名图片就传base64位串,否则传ftp全路径地址(*必填)
* @param isSign 是否是签名图片 默认不是
* @return
*/
public static PrintElement DrawGraph(int x, int y, int width, int height, String dataField, boolean isSign) {
PrintElement ret = new PrintElement();
ret.PrintX = String.valueOf(x);
ret.PrintY = String.valueOf(y);
ret.DataField = dataField;
ret.PrintWidth = String.valueOf(width);
ret.PrintHeight = String.valueOf(height);
ret.PrintType = "Graph";
if (isSign == true) {
ret.PrintFlag = "D";
}
return ret;
}
/**
* 画复选框
*
* @param x x坐标(*必填)
* @param y y坐标(*必填)
* @param checked 是否选择 0:不选,1:选中
* @param width 宽度
* @param height 高度
* @return
*/
public static PrintElement DrawCheckBox(int x, int y, boolean checked, int width, int height) {
PrintElement ret = new PrintElement();
ret.PrintX = String.valueOf(x);
ret.PrintY = String.valueOf(y);
if (checked == true) {
ret.PrintText = "是";
}
ret.PrintWidth = String.valueOf(width);
ret.PrintHeight = String.valueOf(height);
ret.PrintType = "CheckBox";
return ret;
}
/**
* 画单选框
*
* @param x x坐标(*必填)
* @param y y坐标(*必填)
* @param checked 是否选择 0:不选,1:选中
* @param width 宽度
* @param height 高度
* @return
*/
public static PrintElement DrawRadio(int x, int y, boolean checked, int width, int height) {
PrintElement ret = new PrintElement();
ret.PrintX = String.valueOf(x);
ret.PrintY = String.valueOf(y);
if (checked == true) {
ret.PrintText = "是";
}
ret.PrintWidth = String.valueOf(width);
ret.PrintHeight = String.valueOf(height);
ret.PrintType = "Radio";
return ret;
}
/**
* PDF文件的ftp或http全路径。用英文逗号分隔两个A5PDF路径打印会自动合并为一个A4。一个A5路径后跟个英文逗号,会把PDF转A4纸打印
*
* @param httpOrFtpPath pdf文件的下载路径
* @return
*/
public static PrintElement DrawFile(String httpOrFtpPath) {
PrintElement ret = new PrintElement();
ret.DataField = httpOrFtpPath;
ret.PrintType = "FILE";
return ret;
}
}
测试
import LIS.Core.Dto.OutParam;
import LIS.Core.Dto.PrintElement;
import LIS.Core.Util.PrintDrawProtocol;
import appcode.BaseHttpHandlerNoSession;
import appcode.Helper;
import java.awt.*;
import java.util.ArrayList;
import java.util.List;
/**
* 输出符合打印元素绘制协议的打印元素数据,来供打印执行层打印
*/
public class PrintBarCodeTest extends BaseHttpHandlerNoSession {
/**
* 按传入的RowID输出符合打印元素绘制协议的数据来实现打印控制
* @param RowID 业务主键
* @param P1
* @param P2
* @param P3
* @param P4
* @param P5
* @param P6
* @param P7
* @param P8
* @param P9
* @param P10
* @param P11
* @param P12
* @param P13
* @param Session
* @param Output
* @return
*/
public String GetData(String RowID, String P1, String P2, String P3, String P4, String P5, String P6, String P7, String P8, String P9, String P10, String P11, String P12, String P13, OutParam Session, OutParam Output) {
List<PrintElement> retList=new ArrayList<>();
//画一个文本
retList.add(PrintDrawProtocol.DrawLabel(10,10,"zhanglianzhu","宋体",12,"", null,"","0"));
//画一个条码
retList.add(PrintDrawProtocol.DrawBarCode(10,50,"0947809",true,5,30,"","宋体",12,"",null,"","0"));
//换一根横线
retList.add(PrintDrawProtocol.DrawLine(10,70,70,70,1,"",""));
//换一根竖线
retList.add(PrintDrawProtocol.DrawLine(50,10,50,470,1,"",""));
//绘制一个条码
retList.add(PrintDrawProtocol.DrawQRCode(10,90,"jbase",90,90));
//绘制一个条码
retList.add(PrintDrawProtocol.DrawLabel(10,210,"jbase打印支持","宋体",12,"",null,"","0"));
//绘制一个条码
retList.add(PrintDrawProtocol.DrawLabel(10,230,"20231118 22:49","宋体",12,"",null,"","0"));
//画一个点
retList.add(PrintDrawProtocol.DrawPoint(10,270,10,10,"o",""));
retList.add(PrintDrawProtocol.DrawPoint(100,270,10,10,"[]",""));
retList.add(PrintDrawProtocol.DrawPoint(200,270,10,10,"<>",""));
//画多边形
List<Point> pointList=new ArrayList<>();
Point p1=new Point();
p1.x=10;
p1.y=300;
pointList.add(p1);
Point p2=new Point();
p2.x=100;
p2.y=310;
pointList.add(p2);
Point p3=new Point();
p3.x=50;
p3.y=360;
pointList.add(p3);
retList.add(PrintDrawProtocol.DrawPoly(pointList,""));
//画复选框
retList.add(PrintDrawProtocol.DrawCheckBox(10,400,true,30,30));
//画单选框
retList.add(PrintDrawProtocol.DrawRadio(10,400,true,30,30));
//换页
retList.add(PrintDrawProtocol.ChangePage());
//画一个文本
retList.add(PrintDrawProtocol.DrawLabel(10,10,"这是打印的第二页","宋体",12,"", null,"","0"));
//画一个条码
retList.add(PrintDrawProtocol.DrawBarCode(10,50,"0947809",true,5,30,"","宋体",12,"",null,"","0"));
//换一根横线
retList.add(PrintDrawProtocol.DrawLine(10,70,70,70,1,"",""));
//换一根竖线
retList.add(PrintDrawProtocol.DrawLine(50,10,50,470,1,"",""));
//绘制一个条码
retList.add(PrintDrawProtocol.DrawQRCode(10,90,"jbase",90,90));
//绘制一个条码
retList.add(PrintDrawProtocol.DrawLabel(10,210,"jbase打印支持","宋体",12,"",null,"","0"));
//绘制一个条码
retList.add(PrintDrawProtocol.DrawLabel(10,230,"20231119","宋体",12,"",null,"","0"));
//先包一个打印元素绘制协议数据生成的工具类来解决元素约束问题,工具类实现了调用工具类得到标签,条码,文本等
return Helper.Object2Json(retList);
}
}
打印基础就更稳定了,业务只需要按要求控制输出数据就行了,可以结合设计器的保存数据和业务数据组装