关于Zebra条码打印机(EPL2语言)的条码打印在C#中的使用
最近要使用Zebra条码打印机打印一串条码,条码下方显示一串字符(此字符不是条码的字符意义,而是其他字符),采用的机器为Zebra888TT,打印机语言为EPL2,计算机编程为C#,调试环境VS2008,需打印的标签尺寸为5cm*1.2cm,计算机与打印机的连接采用串口方式。
首先介绍下EPL2语言。对此语言,我也就使用了最为基本的四个指令,N(清空image buffer)、P(开始打印)、A(打印文本)、B(打印条码)。对了,EPL2语言是区分大小写的。
下面是语法的详解,其实打印机附带光盘里的说明书《EPL2EN》更具体,不过是英文的。
以下的A,B命令的语法详解我是转载的http://blog.csdn.net/wdtking/archive/2007/05/25/1625924.aspx
A
语法 Ap1,p2,p3,p4,p5,p6,p7,“DATA”
参数 p1=以象素点为单位的水平起始位置
p2=以象素点为单位的垂直起始位置
p3=旋转
Value Description
0 No rotation
1 90 degrees
2 180 degrees
3 270 degrees
4 No rotation
5 90 degrees
6 180 degrees
7 270 degrees
4-7是针对亚洲字体的设置
p4=字体选择
Value Description
203 dpi 300 dpi
1 20.3 cpi, 6 pts, 25 cpi, 4 pts,
(8 x 12 dots) (12 x 20 dots)
2 16.9 cpi, 7 pts, 18.75 cpi, 6 pts,
(10 x 16 dots) (16 x 28 dots)
3 14.5 cpi, 10 pts, 15 cpi, 8 pts,
(12 x 20 dots) (20 x 36 dots)
4 12.7 cpi, 12 pts, 12.5 cpi, 10 pts,
(14 x 24 dots) (24 x 44 dots)
5 5.6 cpi, 24 pts, 6.25 cpi, 21 pts,
(32 x 48 dots) (48 x 80 dots)
6 Numeric Only Numeric Only
(14 x 19 dots) (14 x 19 dots)
7 Numeric Only Numeric Only
(14 x 19 dots) (14 x 19 dots)
亚洲打印机
Simplified Chinese, Japanese, Korean
8 203 dpi fonts : 24 x 24 dots
300 dpi Double-byte fonts : 36 x 36 dots
300 dpi Single-byte fonts : 24 x 36 dots
Traditional Chinese, Japanese
9 300 dpi Double-byte fonts: 36 x 36 dots
300 dpi Single-byte fonts : 24 x 36 dots
Korean - Reserved
p5=水平膨胀,值:1-6&8
p6=垂直膨胀,值:1-9
p7=N代表普通,R表示反转图象
"DATA"=数据
B
用于打印标准条码
语法:Bp1,p2,p3,p4,p5,p6,p7,p8,“DATA”
参数 p1=以象素点为单位的水平起始位置
p2=以象素点为单位的垂直起始位置
p3=旋转
Value Description
0 No rotation
1 90 degrees
2 180 degrees
3 270 degrees
p4=条码选择,参见条码表
p5=窄条的象数宽度,参见条码表
p6=宽条的象数宽度,参见条码表
p7=条码的象素高度
p8=打印可读代码,值 B=是,N=否
"DATA"=数据
条码表
Description P4 P5 P6
Value Value Value
Code 39 std. or extended 3 1-10 Y
Code 39 with check digit 3C 1-10 N
Code 93 9 1-10 N
Code 128 UCC
Serial Shipping Container Code 0 1-10 N
Code 128 auto A, B, C modes 1 1-10 N
Code 128 mode A 1A 1-10 N
Code 128 mode B 1B 1-10 N
Code 128 mode C 1C 1-10 N
Code 128 with Deutsche Post check digit4 1D 2-10 N
Codabar K 1-10 Y
EAN8 E80 2-4 N
EAN8 2 digit add-on E82 2-4 N
EAN8 5 digit add-on E85 2-4 N
EAN13 E30 2-4 N
EAN13 2 digit add-on E32 2-4 N
EAN13 5 digit add-on E35 2-4 N
German Post Code 2G 3-4 N
Interleaved 2 of 5 2 1-10 Y
Interleaved 2 of 5 with mod 10 check digit 2C 1-10 Y
Interleaved 2 of 5 with human readable
check digit 2D 1-10 Y
Postnet 5, 9, 11 & 13 digit1 P — N
Planet 11 & 13 digit1 PL — N
Japanese Postnet3 J — —
UCC/EAN 1282 1E 1-10 N
UPC A UA0 2-4 N
UPC A 2 digit add-on UA2 2-4 N
UPC A 5 digit add-on UA5 2-4 N
UPC E UE0 2-4 N
UPC E 2 digit add-on UE2 2-4 N
UPC E 5 digit add-on UE5 2-4 N
UPC Interleaved 2 of 5 2U 1-10 Y
Plessey (MSI-1) with mod. 10 check digit L — —
MSI-3 with mod. 10 check digit M — —
下面开始我的原创:
首先有3点注意:
1、说明书上说N命令开始前要先输入一行空白行,原文:Always send a Line Feed (LF) prior to the N command to ensure that previous data in the command buffer has cleared and the printer is in i tial ized and ready to ac cept com mands.
2、P命令之后也要加一个空白行,即回车,不然最后的P命令要打印的东西是不打印的,之前的P命令由于由后面的命令,间接等于换行了,所以会照打不误
3、说明书上写P命令是Pp1, [p2],其参数p1是Number of label sets,而参数p2是Number of copies of each label (used in combination with counters to print multiple copies of the same label).但我试验下来p1就是要打印的条码的重复次数,而p2无论我怎么改写都没有变换,始终打印最后一个条码。应该是我哪里写错了。但是多用几次P1,每次打一条还是可以起到同样的打印多条条码的效果的。
下面,给出我打印的条码的例子:
N
B60,5,0,1,2,3,40,N,"1234567891123"
A60,55,0,8,1,1,N,"ALP-1"
P1
B60,5,0,1,2,3,40,N,"1234567890123"
A60,55,0,8,1,1,N,"ALP-2"
P1
B60,5,0,1,2,3,40,N,"1234567890123"
A60,55,0,8,1,1,N,"ALP-3"
P1
注意N命令前的换行和最后P1后的换行。将此段代码复制到windows记事本里另存为Print.ext,文件名随便,后缀为ext。然后通过cmd控制命令行输入"copy c:\print.ext COM1”。然后就可以看到打印机开始打印了,效果不错。
那么在C#中怎么让它打印呢?我也在网上看到别人写了什么封装,老实说我也试过,但是一来老外写的东西,看到英语注释与说明就不高兴研究了,而来关键的BasePositioning这个接口的定义缺失,根本过不了编译。所以得另谋他路,我想如果通过刚才的控制命令行的模式,通过C#来发出"copy c:\print.ext COM1”,不就可以了吗?
于是乎:
System.Diagnostics.ProcessStartInfo ps = new System.Diagnostics.ProcessStartInfo("cmd");
ps.UseShellExecute = false;
ps.CreateNoWindow = true;
ps.RedirectStandardOutput = true;
ps.RedirectStandardInput = true;
System.Diagnostics.Process p = System.Diagnostics.Process.Start(ps);
p.StandardInput.WriteLine(@"copy c:\print.ext COM1");
p.StandardInput.WriteLine(@"exit");
p.WaitForExit();//之前要记住exit,否则会持续等待造成无响应的
p.Close();//释放资源
通过以上的代码就可以实现打印了,当然还是通过中间文件print.ext 。
有没有其他的不用产生中间文件的办法?
答案是有的.
因为我们是采用串口通信,所以只需要用SerialPort控件向串口里写入数据(EPL2语句)即可。当然,由于是直接写串口数据,所以请先将控制面板里的打印机属性的端口属性给改成错误的端口而非真正的端口,不然的话,当SerialPort控件打开要打开的端口时可是会异常的。下面给出我的演示,其中spPrinter为SerialPort控件:
string ToPrint;
ToPrint = Environment.NewLine + "N" + Environment.NewLine
+ "B60,5,0,1,2,3,40,N,\"1234567891123\"" + Environment.NewLine + "A60,55,0,8,1,1,N,\"ALP-5\"" + Environment.NewLine + "P1" + Environment.NewLine
+ "B60,5,0,1,2,3,40,N,\"1234567891123\"" + Environment.NewLine + "A60,55,0,8,1,1,N,\"ALP-6\"" + Environment.NewLine + "P1" + Environment.NewLine
+ "B60,5,0,1,2,3,40,N,\"1234567891123\"" + Environment.NewLine + "A60,55,0,8,1,1,N,\"ALP-7\"" + Environment.NewLine + "P1" + Environment.NewLine;
spPrinter.Open();
spPrinter.Write(ToPrint);
spPrinter.Close();
就这样,不用产生中间文件,我们也成功的打印了。
值得注意的是:换行要使用Environment.NewLine,而不是单纯的"\n"。