使用 ReadPrinter 读取打印机数据 Winspool.Drv
Reading printer data using ReadPrinter Winspool.Drv
我通过 USB 连接了 Zebra 打印机,我正在尝试使用命令 ^XA^HWR:^XZ
读取打印机的内存。该命令适用于 TCP/IP。
我什至不确定我的方法header是否正确。
[DllImport("winspool.Drv", EntryPoint = "ReadPrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
static extern bool ReadPrinter(IntPtr hPrinter, IntPtr pBuf, int cbBuf, out int pNoBytesRead);
方法ReadPrinter
总是returns false 和 0 个读取字节。当我尝试获取 LastWin32Error
时,我得到的是各种 0、6 或 63(ERROR_SUCCESS
- 尽管它 returns 为假且没有数据,ERROR_INVALID_HANDLE
或ERROR_PRINT_CANCELLED
),这取决于我正在尝试的。我尝试了几种方法 headers 和不同的方法,但其中 none 导致成功读取数据。我启用了 'bidirectional support' 并安装了打印机驱动程序。它可能看起来像其他线程的副本,但我已经通过它们并且 none 其中有帮助。
代码片段:
private static void SendBytesToPrinter(string printerName, IntPtr pointerBytes, int bytesCount)
{
int written = 0;
PrintResult printResult = new PrintResult();
IntPtr pointerPrinter = new IntPtr(0);
DOCINFOA docInfo = new DOCINFOA();
bool success = false;
docInfo.DocName = "RAW Document";
docInfo.DataType = "RAW";
try
{
if (OpenPrinter(printerName.Normalize(), out pointerPrinter, IntPtr.Zero))
{
if (StartDocPrinter(pointerPrinter, 1, docInfo))
{
if (StartPagePrinter(pointerPrinter))
{
success = WritePrinter(pointerPrinter, pointerBytes, bytesCount, out written);
EndPagePrinter(pointerPrinter);
}
EndDocPrinter(pointerPrinter);
}
// READ HERE
Int32 bufLen = 32;
IntPtr pStatus = Marshal.AllocCoTaskMem(bufLen);
Int32 statusLen = 0;
bool bSuccess = ReadPrinter(hPrintJob, pStatus, bufLen, out statusLen);
ClosePrinter(pointerPrinter);
}
} catch (Exception ex) { }
}
我使用 Visual Basic 示例解决了它,使用 FileStreams
和 StreamReaders
。感谢@kunif 指出示例代码。
kernel32.dll
是代替 winspool.Drv
的方法
[DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)]
private static extern SafeFileHandle CreateFile(string lpFileName, EFileAccess dwDesiredAccess,
EFileShare dwShareMode, IntPtr lpSecurityAttributes,
ECreationDisposition dwCreationDisposition,
EFileAttributes dwFlagsAndAttributes,
IntPtr hTemplateFile);
private static string ReadUsbPort(StreamReader sr)
{
string readResult = string.Empty;
if (sr != null && sr.BaseStream != null)
{
do
{
readResult += sr.ReadLine();
readResult += "\r";
}
while (sr.EndOfStream == false);
}
return readResult;
}
非常有用的组合
GUID_DEVINTERFACE_USB_DEVICE and WinUSBNet
我通过 USB 连接了 Zebra 打印机,我正在尝试使用命令 ^XA^HWR:^XZ
读取打印机的内存。该命令适用于 TCP/IP。
我什至不确定我的方法header是否正确。
[DllImport("winspool.Drv", EntryPoint = "ReadPrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
static extern bool ReadPrinter(IntPtr hPrinter, IntPtr pBuf, int cbBuf, out int pNoBytesRead);
方法ReadPrinter
总是returns false 和 0 个读取字节。当我尝试获取 LastWin32Error
时,我得到的是各种 0、6 或 63(ERROR_SUCCESS
- 尽管它 returns 为假且没有数据,ERROR_INVALID_HANDLE
或ERROR_PRINT_CANCELLED
),这取决于我正在尝试的。我尝试了几种方法 headers 和不同的方法,但其中 none 导致成功读取数据。我启用了 'bidirectional support' 并安装了打印机驱动程序。它可能看起来像其他线程的副本,但我已经通过它们并且 none 其中有帮助。
代码片段:
private static void SendBytesToPrinter(string printerName, IntPtr pointerBytes, int bytesCount)
{
int written = 0;
PrintResult printResult = new PrintResult();
IntPtr pointerPrinter = new IntPtr(0);
DOCINFOA docInfo = new DOCINFOA();
bool success = false;
docInfo.DocName = "RAW Document";
docInfo.DataType = "RAW";
try
{
if (OpenPrinter(printerName.Normalize(), out pointerPrinter, IntPtr.Zero))
{
if (StartDocPrinter(pointerPrinter, 1, docInfo))
{
if (StartPagePrinter(pointerPrinter))
{
success = WritePrinter(pointerPrinter, pointerBytes, bytesCount, out written);
EndPagePrinter(pointerPrinter);
}
EndDocPrinter(pointerPrinter);
}
// READ HERE
Int32 bufLen = 32;
IntPtr pStatus = Marshal.AllocCoTaskMem(bufLen);
Int32 statusLen = 0;
bool bSuccess = ReadPrinter(hPrintJob, pStatus, bufLen, out statusLen);
ClosePrinter(pointerPrinter);
}
} catch (Exception ex) { }
}
我使用 Visual Basic 示例解决了它,使用 FileStreams
和 StreamReaders
。感谢@kunif 指出示例代码。
kernel32.dll
是代替 winspool.Drv
[DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)]
private static extern SafeFileHandle CreateFile(string lpFileName, EFileAccess dwDesiredAccess,
EFileShare dwShareMode, IntPtr lpSecurityAttributes,
ECreationDisposition dwCreationDisposition,
EFileAttributes dwFlagsAndAttributes,
IntPtr hTemplateFile);
private static string ReadUsbPort(StreamReader sr)
{
string readResult = string.Empty;
if (sr != null && sr.BaseStream != null)
{
do
{
readResult += sr.ReadLine();
readResult += "\r";
}
while (sr.EndOfStream == false);
}
return readResult;
}
非常有用的组合 GUID_DEVINTERFACE_USB_DEVICE and WinUSBNet