记录在项目中遇到的问题,主要是想在注册的虚拟打印机,在网页打印或文档打印中调整一些打印属性比如打印份数,打印颜色,打印纸张大小,但是想要获取从网页中调整的参数需要如何获取呢,
上网找了好久也没有找到,倒是有些方法但是获取的都是一些打印机首选项中的值,没办法动态获取手动调整的属性:
1、发现可以使用PrintTicket类方式获取打印机参数,但是发现只能获取打印机的首选项中设置的参数无法获取用户输入的参数
2、发现使用PrintDialog类结合PrintDocument.PrinterSettings类和PrintDocument.DefaultPageSettings可以获取打印机参数,但是会再次创建一个打印会话框然后才能获取到输入的打印参数
3、发现可以使用打印后台处理程序中的API,DocumentProperties来获取到DEVMODE中的打印参数,但是发现获取的仍是打印机的首选项中设置的参数
最后终于发现了一种方法可以获取到手动调整的打印属性,展示:
可以看到,可以实现获取用户在网页中使用虚拟打印机所设置的属性:打印份数,打印颜色,打印纸张大小等等都可以获取到。
目前我只能获取到这些,其他的应该也都能获取到,还没有试我觉得应该能获取到,然后分享一下我的方法,有不对的或者有问题的地方欢迎指教,
具体方法如下:
在属性获取之前首先要导入一些Windows的Print Spooler API如下:
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]internal struct structPrinterDefaults{[MarshalAs(UnmanagedType.LPTStr)]public String pDatatype;public IntPtr pDevMode;[MarshalAs(UnmanagedType.I4)]public int DesiredAccess;};[DllImport("winspool.Drv", EntryPoint = "OpenPrinter", SetLastError = true, CharSet = CharSet.Unicode, ExactSpelling = false, CallingConvention = CallingConvention.StdCall),SuppressUnmanagedCodeSecurityAttribute()]internal static extern bool OpenPrinter([MarshalAs(UnmanagedType.LPTStr)] string printerName, out IntPtr phPrinter, ref structPrinterDefaults pd);[DllImport("winspool.drv", CharSet = CharSet.Auto)]static extern bool ClosePrinter(IntPtr hPrinter);[DllImport("winspool.drv", EntryPoint = "GetJob", SetLastError = true, ExactSpelling = false, CallingConvention = CallingConvention.StdCall)]private static extern bool GetJob([InAttribute()] IntPtr hPrinter, [InAttribute()] UInt32 JobId, [InAttribute()] UInt32 Level, [OutAttribute()] IntPtr pJob, [InAttribute()] UInt32 cbBuf, [OutAttribute()] out UInt32 pcbNeeded);
OpenPrinter用于打开注册的虚拟打印机,通过传入填充过的structPrinterDefaults获取打印机句柄phPrinter,其中defaults.DesiredAccess = 0x00008;需要与注册时使用的地址x相符合
ClosePrinter就是通过OpenPrinter获取到的打印机句柄进行关闭打开的虚拟打印机
GetJob函数用于检索有关指定打印作业的信息,也是此模块的核心函数,用于获取打印机属性,其主要包含两个结构体如下需要自己定义然后获取:
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]private struct JOB_INFO_2[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]public struct DEVMODE
在这三个结构体中用于保存打印机属性的结构体就是DEVMODE结构体,其中主要用的的一些打印属性如下:
打印份数:dmCopies
打印颜色模式:dmColor
打印纸张大小:dmPaperSize
打印分辨率:dmYResolution
打印单双面:dmDuplex
整体代码如下:
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]internal struct structPrinterDefaults{[MarshalAs(UnmanagedType.LPTStr)]public String pDatatype;public IntPtr pDevMode;[MarshalAs(UnmanagedType.I4)]public int DesiredAccess;};[DllImport("winspool.Drv", EntryPoint = "OpenPrinter", SetLastError = true, CharSet = CharSet.Unicode, ExactSpelling = false, CallingConvention = CallingConvention.