c# 在进行小票打印时大致有三种方法。

1. 使用水晶报表进行打印。可以参考:https://www.cnblogs.com/aitong/p/10717786.html

2. 在 PrintDocument 对象上进行绘图,然后使用其打印方法直接打印。

using CrystalDecisions.CrystalReports.Engine;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Drawing.Printing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms; namespace CrTest
{
public partial class Form1 : Form
{
string title = "标题标题标题标题标题标题标题标题标题标题标题";
public Form1()
{
InitializeComponent();
} private void button1_Click(object sender, EventArgs e)
{
//打印预览
PrintPreviewDialog ppd = new PrintPreviewDialog();
PrintDocument pd = new PrintDocument();
//设置边距
Margins margin = new Margins(, , , );
pd.DefaultPageSettings.Margins = margin;
int height = ;
if (title.Length > )
{
height = ;
}
//纸张设置默认
PaperSize pageSize = new PaperSize("First custom size", (int)( * / 25.4), height);//58mm 转绘图宽度
pd.DefaultPageSettings.PaperSize = pageSize;
//打印事件设置
pd.PrintPage += new PrintPageEventHandler(pd_PrintPage);
ppd.Document = pd;
ppd.ShowDialog();
//try
//{
// pd.Print();
//}
//catch (Exception ex)
//{
// MessageBox.Show(ex.Message, "打印出错", MessageBoxButtons.OK, MessageBoxIcon.Error);
// pd.PrintController.OnEndPrint(pd, new PrintEventArgs());
//}
} private void pd_PrintPage(object sender, PrintPageEventArgs e)
{
Font font = new Font("Arial", , System.Drawing.FontStyle.Regular);
string text = title;
int yLocation = e.MarginBounds.Y;
int center = e.PageSettings.PaperSize.Width / ;
int heightStep = ;
while (text.Length > )
{
string printStr;
if (text.Length > )
{
printStr = text.Substring(, );
text = text.Substring();
}
else
{
printStr = text;
text = "";
}
SizeF size = e.Graphics.MeasureString(printStr, font);
heightStep =Convert.ToInt32( size.Height * 1.3);
e.Graphics.DrawString(printStr, font, System.Drawing.Brushes.Black, center - size.Width / , yLocation);
yLocation += heightStep;
}
}
}
}

3. 使用 ESC/POS 控制指令

注意 SendStringToPrinter 这个接口。

using System;
using System.Collections.Generic;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
//https://www.cnblogs.com/QiuTianBaBa/p/6730829.html
//https://blog.csdn.net/andrewniu/article/details/80353655
namespace Evet2Basic.Model.Print.Report
{
public class RawPrint
{
// Structure and API declarions:
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)]
public class DOCINFOA
{
[MarshalAs(UnmanagedType.LPStr)]
public string pDocName;
[MarshalAs(UnmanagedType.LPStr)]
public string pOutputFile;
[MarshalAs(UnmanagedType.LPStr)]
public string pDataType;
}
[DllImport("winspool.Drv", EntryPoint = "OpenPrinterA", SetLastError = true, CharSet = CharSet.Ansi, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
public static extern bool OpenPrinter([MarshalAs(UnmanagedType.LPStr)] string szPrinter, out IntPtr hPrinter, IntPtr pd); [DllImport("winspool.Drv", EntryPoint = "ClosePrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
public static extern bool ClosePrinter(IntPtr hPrinter); [DllImport("winspool.Drv", EntryPoint = "StartDocPrinterA", SetLastError = true, CharSet = CharSet.Ansi, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
public static extern bool StartDocPrinter(IntPtr hPrinter, Int32 level, [In, MarshalAs(UnmanagedType.LPStruct)] DOCINFOA di); [DllImport("winspool.Drv", EntryPoint = "EndDocPrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
public static extern bool EndDocPrinter(IntPtr hPrinter); [DllImport("winspool.Drv", EntryPoint = "StartPagePrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
public static extern bool StartPagePrinter(IntPtr hPrinter); [DllImport("winspool.Drv", EntryPoint = "EndPagePrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
public static extern bool EndPagePrinter(IntPtr hPrinter); [DllImport("winspool.Drv", EntryPoint = "WritePrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
public static extern bool WritePrinter(IntPtr hPrinter, IntPtr pBytes, Int32 dwCount, out Int32 dwWritten); // SendBytesToPrinter()
// When the function is given a printer name and an unmanaged array
// of bytes, the function sends those bytes to the print queue.
// Returns true on success, false on failure.
private static bool SendBytesToPrinter(string szPrinterName, IntPtr pBytes, Int32 dwCount)
{
Int32 dwError = , dwWritten = ;
IntPtr hPrinter = new IntPtr();
DOCINFOA di = new DOCINFOA();
bool bSuccess = false; // Assume failure unless you specifically succeed. di.pDocName = "XiaoPiao";
di.pDataType = "RAW"; // Open the printer.
if (OpenPrinter(szPrinterName.Normalize(), out hPrinter, IntPtr.Zero))
{
// Start a document.
if (StartDocPrinter(hPrinter, , di))
{
// Start a page.
if (StartPagePrinter(hPrinter))
{
// Write your bytes.
bSuccess = WritePrinter(hPrinter, pBytes, dwCount, out dwWritten);
EndPagePrinter(hPrinter);
}
EndDocPrinter(hPrinter);
}
ClosePrinter(hPrinter);
}
// If you did not succeed, GetLastError may give more information
// about why not.
if (bSuccess == false)
{
dwError = Marshal.GetLastWin32Error();
}
return bSuccess;
} private static bool SendFileToPrinter(string szPrinterName, string szFileName)
{
// Open the file.
FileStream fs = new FileStream(szFileName, FileMode.Open);
// Create a BinaryReader on the file.
BinaryReader br = new BinaryReader(fs);
// Dim an array of bytes big enough to hold the file's contents.
Byte[] bytes = new Byte[fs.Length];
bool bSuccess = false;
// Your unmanaged pointer.
IntPtr pUnmanagedBytes = new IntPtr();
int nLength; nLength = Convert.ToInt32(fs.Length);
// Read the contents of the file into the array.
bytes = br.ReadBytes(nLength);
// Allocate some unmanaged memory for those bytes.
pUnmanagedBytes = Marshal.AllocCoTaskMem(nLength);
// Copy the managed byte array into the unmanaged array.
Marshal.Copy(bytes, , pUnmanagedBytes, nLength);
// Send the unmanaged bytes to the printer.
bSuccess = SendBytesToPrinter(szPrinterName, pUnmanagedBytes, nLength);
// Free the unmanaged memory that you allocated earlier.
Marshal.FreeCoTaskMem(pUnmanagedBytes);
return bSuccess;
} public static bool SendBytesToPrinter(string szPrinterName, byte[] buf)
{
bool bSuccess = false;
// Your unmanaged pointer.
IntPtr pUnmanagedBytes = new IntPtr();
// Allocate some unmanaged memory for those bytes.
pUnmanagedBytes = Marshal.AllocCoTaskMem(buf.Length);
// Copy the managed byte array into the unmanaged array.
Marshal.Copy(buf, , pUnmanagedBytes, buf.Length);
// Send the unmanaged bytes to the printer.
bSuccess = SendBytesToPrinter(szPrinterName, pUnmanagedBytes, buf.Length);
// Free the unmanaged memory that you allocated earlier.
Marshal.FreeCoTaskMem(pUnmanagedBytes);
return bSuccess;
} /// <summary>
/// 切纸
/// </summary>
/// <param name="szPrinterName">打印机名</param>
/// <returns></returns>
public static bool Cut(string szPrinterName)
{
bool bSuccess = false; IntPtr pUnmanagedBytes = new IntPtr(); byte[] data = new byte[] { 0x1B, 0x69 };
pUnmanagedBytes = Marshal.AllocCoTaskMem(data.Length);
Marshal.Copy(data, , pUnmanagedBytes, data.Length);
bSuccess = SendBytesToPrinter(szPrinterName, pUnmanagedBytes, data.Length);
Marshal.FreeCoTaskMem(pUnmanagedBytes);
return true;
} public static bool SendBytesToPrinterImg(string szPrinterName, Bitmap bmp, bool needWarning)
{
bool bSuccess = false; //Byte[] byte_send = Encoding.GetEncoding("GB2312").GetBytes("\x1b\x40");
IntPtr pUnmanagedBytes = new IntPtr();
//pUnmanagedBytes = Marshal.AllocCoTaskMem(byte_send.Length);
//Marshal.Copy(byte_send, 0, pUnmanagedBytes, byte_send.Length);
//bSuccess = SendBytesToPrinter(szPrinterName, pUnmanagedBytes, byte_send.Length);
//Marshal.FreeCoTaskMem(pUnmanagedBytes); byte[] data = new byte[] { 0x1B, 0x33, 0x00 };
//pUnmanagedBytes = new IntPtr(0);
pUnmanagedBytes = Marshal.AllocCoTaskMem(data.Length);
Marshal.Copy(data, , pUnmanagedBytes, data.Length);
bSuccess = SendBytesToPrinter(szPrinterName, pUnmanagedBytes, data.Length);
Marshal.FreeCoTaskMem(pUnmanagedBytes);
data[] = (byte)'\x00';
data[] = (byte)'\x00';
data[] = (byte)'\x00'; Color pixelColor; // ESC * m nL nH 点阵图
byte[] escBmp = new byte[] { 0x1B, 0x2A, 0x00, 0x00, 0x00 };
escBmp[] = (byte)'\x21';
//nL, nH
escBmp[] = (byte)(bmp.Width % );
escBmp[] = (byte)(bmp.Width / ); // data
for (int i = ; i < (bmp.Height / ) + ; i++)
{
//pUnmanagedBytes = new IntPtr(0);
pUnmanagedBytes = Marshal.AllocCoTaskMem(escBmp.Length);
Marshal.Copy(escBmp, , pUnmanagedBytes, escBmp.Length);
bSuccess = SendBytesToPrinter(szPrinterName, pUnmanagedBytes, escBmp.Length);
Marshal.FreeCoTaskMem(pUnmanagedBytes); byte[] temptype = new byte[bmp.Width * ];
int lengthNow = ;
for (int j = ; j < bmp.Width; j++)
{
for (int k = ; k < ; k++)
{
if (((i * ) + k) < bmp.Height) // if within the BMP size
{
pixelColor = bmp.GetPixel(j, (i * ) + k);
if (pixelColor.R == )
{
data[k / ] += (byte)( >> (k % ));
}
}
}
data.CopyTo(temptype, lengthNow);
lengthNow += ; data[] = (byte)'\x00';
data[] = (byte)'\x00';
data[] = (byte)'\x00';
} //pUnmanagedBytes = new IntPtr(0);
pUnmanagedBytes = Marshal.AllocCoTaskMem(temptype.Length);
Marshal.Copy(temptype, , pUnmanagedBytes, temptype.Length);
bSuccess = SendBytesToPrinter(szPrinterName, pUnmanagedBytes, temptype.Length);
Marshal.FreeCoTaskMem(pUnmanagedBytes);
System.Threading.Thread.Sleep();
}
byte[] dataClear = new byte[] { 0x1B, 0x40 };
pUnmanagedBytes = Marshal.AllocCoTaskMem(dataClear.Length);
Marshal.Copy(dataClear, , pUnmanagedBytes, dataClear.Length);
bSuccess = SendBytesToPrinter(szPrinterName, pUnmanagedBytes, dataClear.Length);
Marshal.FreeCoTaskMem(pUnmanagedBytes);
return bSuccess;
} public static bool SendStringToPrinter(string szPrinterName, string szString)
{
try
{
//指令见打印机官方文档 http://www.xprinter.net/index.php/Server/index/cid/3
byte[] smallArray = new byte[] { , , };
List<byte> list = new List<byte>(); list.AddRange(smallArray);
while (szString.Contains("<B>") || szString.Contains("<A>"))
{
if (!szString.Contains("<B>"))
{
ReplaceAB(ref szString, ref list, );
}
else if (!szString.Contains("<A>"))
{
ReplaceAB(ref szString, ref list, );
}
else
{
int indexA = szString.IndexOf("<A>");
int indexB = szString.IndexOf("<B>");
if (indexA < indexB)
{
ReplaceAB(ref szString, ref list, );
}
else
{
ReplaceAB(ref szString, ref list, );
}
}
}
Encoding enc = Encoding.GetEncoding("gb2312");
list.AddRange(enc.GetBytes(szString));
return RawPrint.SendBytesToPrinter(szPrinterName, list.ToArray());
}
catch (Exception)
{
return false;
}
} private static void ReplaceAB(ref string szString, ref List<byte> list, int mul)
{
//指令见打印机官方文档 http://www.xprinter.net/index.php/Server/index/cid/3
string replaceStr1 = "<B>";
string replaceStr2 = "</B>";
byte[] smallArray = new byte[] { , , };
byte[] bigArray = new byte[] { , , }; //放大三倍 //29, 33字体放大指令 34放大倍数 ( 0一倍 17两倍 34三倍 51四倍 68五倍 85六倍)
if (mul == )
{
replaceStr1 = "<A>";
replaceStr2 = "</A>";
bigArray = new byte[] { , , }; //放大两倍
}
Encoding enc = Encoding.GetEncoding("gb2312");
int index = szString.IndexOf(replaceStr1);
string first = szString.Substring(, index);
list.AddRange(enc.GetBytes(first));//第一段
list.AddRange(bigArray);//变成大写
szString = szString.Substring(index + );
int index2 = szString.IndexOf(replaceStr2);
string second = szString.Substring(, index2);
list.AddRange(enc.GetBytes(second));//大写段
list.AddRange(smallArray);//变小写
szString = szString.Substring(index2 + );
}
}
}

最新文章

  1. xcode8.0升级之后公司项目遇到的问题
  2. C++中的private/protected/public
  3. 原生js实现滚动条
  4. js与php转换时间戳
  5. MarkDown 语法
  6. Mobile data
  7. extjs表格下的分页条——Ext.grid.Panel 的 pagingtoolbar
  8. 让progressDialog不会触摸消失
  9. qt中如果用qDebug输出彩色调试信息
  10. JSONP技术原理及实现
  11. HTML5 Canvas实现刮刮卡效果实例
  12. javaWeb之自动发送邮件生日祝福(ServletContextListener监听)
  13. [HNOI2004]L语言
  14. bootstrap4 Reboot details summary 美化(点选禁止选中文本,单行隐藏角标,多行后移)
  15. Select2 4.0.5 API
  16. Guitar Pro怎样可以快速打出三连音?
  17. NB-IoT移远BC95使用小结
  18. 选择、操作web元素-3
  19. Java8简明指南
  20. 13.4SolrCloud集群使用手册之CRUD

热门文章

  1. Spring框架总结(二)
  2. UVALive 7749 Convex Contour (计算几何)
  3. HDU 4714 Tree2cycle (树形DP)
  4. 9.29学习的js基础
  5. Android colorAccent、colorPrimary、colorPrimaryDark actionbar toolbar navigationbar
  6. 理解Javascript中的事件绑定与事件委托
  7. web项目不能链接数据库
  8. BlockingCollection 集合随记
  9. C#线程和异步
  10. BJ2011集训/BZOJ2321 星器