在 C# 中读取打印机设备上下文
我能够将屏幕设备显示并保存到 DIB 位图,并且我想对打印机设备上下文执行相同的操作。我可以获得非空位图,但它始终是纯黑色。
这是允许我处理屏幕设备上下文的代码。
//In size variable we shall keep the size of the window.
SIZE size;
//Win32 API functions are imported in classes
//PlatformInvokeGDI32
//PlatformInvokeUSER32
//Get handle of calc.exe window.
IntPtr hwnd = PlatformInvokeUSER32.FindWindow("SciCalc", "Calculator");
//Get window dimensions
PlatformInvokeUSER32.RECT rect;
PlatformInvokeUSER32.GetWindowRect(hwnd, out rect);
size.cx = rect._Right - rect._Left;
size.cy = rect._Bottom - rect._Top;
//Get the device context of Calculator.
IntPtr hDC = PlatformInvokeUSER32.GetDC(hwnd);
//Draw on the Calculator surface.
Graphics CalculatorGraphics = Graphics.FromHdc(hDC);
Color colorRed = Color.FromName("Red");
Pen penRed = new Pen(colorRed);
CalculatorGraphics.DrawEllipse(penRed, 50, 50, 50, 50);
CalculatorGraphics.Save();
//Here we make a compatible device context in memory for screen device context.
IntPtr hMemDC = PlatformInvokeGDI32.CreateCompatibleDC(hDC);
//Create a compatible bitmap of window size and using screen device context.
m_HBitmap = PlatformInvokeGDI32.CreateCompatibleBitmap(hDC, size.cx, size.cy);
//As m_HBitmap is IntPtr we can not check it against null. For this purspose IntPtr.Zero is used.
if (m_HBitmap != IntPtr.Zero)
{
//Here we select the compatible bitmap in memeory device context and keeps the refrence to Old bitmap.
IntPtr hOld = (IntPtr)PlatformInvokeGDI32.SelectObject(hMemDC, m_HBitmap);
//We copy the Bitmap to the memory device context.
PlatformInvokeGDI32.BitBlt(hMemDC, 0, 0, size.cx, size.cy, hDC, 0, 0, PlatformInvokeGDI32.SRCCOPY);
//We select the old bitmap back to the memory device context.
PlatformInvokeGDI32.SelectObject(hMemDC, hOld);
//We delete the memory device context.
PlatformInvokeGDI32.DeleteDC(hMemDC);
//We release the screen device context.
PlatformInvokeUSER32.ReleaseDC(hwnd, hDC);
//Image is created by Image bitmap handle and returned.
return System.Drawing.Image.FromHbitmap(m_HBitmap);
}
//If m_HBitmap is null retunrn null.
return null;
以下是获取打印机设备上下文的方法:
//In size variable we shall keep the size of the window.
SIZE size;
size.cx = 1000;
size.cy = 1000;
//Get Printer Handle
IntPtr PrinterHandle;
PlatformInvokeGDI32.PRINTER_DEFAULTSW defaults = new PlatformInvokeGDI32.PRINTER_DEFAULTSW();
PlatformInvokeGDI32.OpenPrinterW("Bullzip PDF Printer", out PrinterHandle, defaults);
//Get Printer Device context
IntPtr PrinterHDC = PlatformInvokeGDI32.CreateDCW("", "Bullzip PDF Printer", "", IntPtr.Zero);
//Initialize DocInfo structure.
PlatformInvokeGDI32.DOCINFOW docInfo = new PlatformInvokeGDI32.DOCINFOW();
//Start printing.
PlatformInvokeGDI32.StartDocW(PrinterHDC, ref docInfo);
PlatformInvokeGDI32.StartPage(PrinterHDC);
Graphics graphics = Graphics.FromHdc(PrinterHDC, PrinterHandle);
Color theColor = Color.FromName("Red");
Pen pen = new Pen(theColor);
graphics.DrawRectangle(pen, 50, 50, 50, 50);
graphics.DrawEllipse(pen, 50, 50, 50, 50);
graphics.Save();
//Here we make a compatible device context in memory for screen device context.
IntPtr hMemDC = PlatformInvokeGDI32.CreateCompatibleDC(PrinterHDC);
//Create a compatible bitmap of window size and using screen device context.
m_HBitmap = PlatformInvokeGDI32.CreateCompatibleBitmap(PrinterHDC, size.cx, size.cy);
//As m_HBitmap is IntPtr we can not check it against null. For this purspose IntPtr.Zero is used.
if (m_HBitmap != IntPtr.Zero)
{
//Here we select the compatible bitmap in memeory device context and keeps the refrence to Old bitmap.
IntPtr hOld = (IntPtr)PlatformInvokeGDI32.SelectObject(hMemDC, m_HBitmap);
//We copy the Bitmap to the memory device context.
PlatformInvokeGDI32.BitBlt(hMemDC, 0, 0, size.cx, size.cy, PrinterHDC, 0, 0, PlatformInvokeGDI32.SRCCOPY);
//We select the old bitmap back to the memory device context.
PlatformInvokeGDI32.SelectObject(hMemDC, hOld);
//We delete the memory device context.
PlatformInvokeGDI32.DeleteDC(hMemDC);
//We release the screen device context.
//PlatformInvokeUSER32.ReleaseDC(hwnd, PrinterHDC);
//Image is created by Image bitmap handle and returned.
PlatformInvokeGDI32.EndPage(PrinterHDC);
PlatformInvokeGDI32.EndDoc(PrinterHDC);
PlatformInvokeGDI32.ClosePrinter(PrinterHandle);
pen.Dispose();
graphics.Dispose();
return System.Drawing.Image.FromHbitmap(m_HBitmap);
}
//If m_HBitmap is null retunrn null.
return null;
How can I Draw on the Printer device context? 如何将打印机设备上下文保存到DIB?
谢谢你,
雅各布
I am able to display and save a screen device to DIB bitmap, and I would like to do the same with a printer device context. I can get a non-null bitmap, but it is always solid black.
Here is the code that allows me to handle a screen device context.
//In size variable we shall keep the size of the window.
SIZE size;
//Win32 API functions are imported in classes
//PlatformInvokeGDI32
//PlatformInvokeUSER32
//Get handle of calc.exe window.
IntPtr hwnd = PlatformInvokeUSER32.FindWindow("SciCalc", "Calculator");
//Get window dimensions
PlatformInvokeUSER32.RECT rect;
PlatformInvokeUSER32.GetWindowRect(hwnd, out rect);
size.cx = rect._Right - rect._Left;
size.cy = rect._Bottom - rect._Top;
//Get the device context of Calculator.
IntPtr hDC = PlatformInvokeUSER32.GetDC(hwnd);
//Draw on the Calculator surface.
Graphics CalculatorGraphics = Graphics.FromHdc(hDC);
Color colorRed = Color.FromName("Red");
Pen penRed = new Pen(colorRed);
CalculatorGraphics.DrawEllipse(penRed, 50, 50, 50, 50);
CalculatorGraphics.Save();
//Here we make a compatible device context in memory for screen device context.
IntPtr hMemDC = PlatformInvokeGDI32.CreateCompatibleDC(hDC);
//Create a compatible bitmap of window size and using screen device context.
m_HBitmap = PlatformInvokeGDI32.CreateCompatibleBitmap(hDC, size.cx, size.cy);
//As m_HBitmap is IntPtr we can not check it against null. For this purspose IntPtr.Zero is used.
if (m_HBitmap != IntPtr.Zero)
{
//Here we select the compatible bitmap in memeory device context and keeps the refrence to Old bitmap.
IntPtr hOld = (IntPtr)PlatformInvokeGDI32.SelectObject(hMemDC, m_HBitmap);
//We copy the Bitmap to the memory device context.
PlatformInvokeGDI32.BitBlt(hMemDC, 0, 0, size.cx, size.cy, hDC, 0, 0, PlatformInvokeGDI32.SRCCOPY);
//We select the old bitmap back to the memory device context.
PlatformInvokeGDI32.SelectObject(hMemDC, hOld);
//We delete the memory device context.
PlatformInvokeGDI32.DeleteDC(hMemDC);
//We release the screen device context.
PlatformInvokeUSER32.ReleaseDC(hwnd, hDC);
//Image is created by Image bitmap handle and returned.
return System.Drawing.Image.FromHbitmap(m_HBitmap);
}
//If m_HBitmap is null retunrn null.
return null;
Here is how I get a printer device context:
//In size variable we shall keep the size of the window.
SIZE size;
size.cx = 1000;
size.cy = 1000;
//Get Printer Handle
IntPtr PrinterHandle;
PlatformInvokeGDI32.PRINTER_DEFAULTSW defaults = new PlatformInvokeGDI32.PRINTER_DEFAULTSW();
PlatformInvokeGDI32.OpenPrinterW("Bullzip PDF Printer", out PrinterHandle, defaults);
//Get Printer Device context
IntPtr PrinterHDC = PlatformInvokeGDI32.CreateDCW("", "Bullzip PDF Printer", "", IntPtr.Zero);
//Initialize DocInfo structure.
PlatformInvokeGDI32.DOCINFOW docInfo = new PlatformInvokeGDI32.DOCINFOW();
//Start printing.
PlatformInvokeGDI32.StartDocW(PrinterHDC, ref docInfo);
PlatformInvokeGDI32.StartPage(PrinterHDC);
Graphics graphics = Graphics.FromHdc(PrinterHDC, PrinterHandle);
Color theColor = Color.FromName("Red");
Pen pen = new Pen(theColor);
graphics.DrawRectangle(pen, 50, 50, 50, 50);
graphics.DrawEllipse(pen, 50, 50, 50, 50);
graphics.Save();
//Here we make a compatible device context in memory for screen device context.
IntPtr hMemDC = PlatformInvokeGDI32.CreateCompatibleDC(PrinterHDC);
//Create a compatible bitmap of window size and using screen device context.
m_HBitmap = PlatformInvokeGDI32.CreateCompatibleBitmap(PrinterHDC, size.cx, size.cy);
//As m_HBitmap is IntPtr we can not check it against null. For this purspose IntPtr.Zero is used.
if (m_HBitmap != IntPtr.Zero)
{
//Here we select the compatible bitmap in memeory device context and keeps the refrence to Old bitmap.
IntPtr hOld = (IntPtr)PlatformInvokeGDI32.SelectObject(hMemDC, m_HBitmap);
//We copy the Bitmap to the memory device context.
PlatformInvokeGDI32.BitBlt(hMemDC, 0, 0, size.cx, size.cy, PrinterHDC, 0, 0, PlatformInvokeGDI32.SRCCOPY);
//We select the old bitmap back to the memory device context.
PlatformInvokeGDI32.SelectObject(hMemDC, hOld);
//We delete the memory device context.
PlatformInvokeGDI32.DeleteDC(hMemDC);
//We release the screen device context.
//PlatformInvokeUSER32.ReleaseDC(hwnd, PrinterHDC);
//Image is created by Image bitmap handle and returned.
PlatformInvokeGDI32.EndPage(PrinterHDC);
PlatformInvokeGDI32.EndDoc(PrinterHDC);
PlatformInvokeGDI32.ClosePrinter(PrinterHandle);
pen.Dispose();
graphics.Dispose();
return System.Drawing.Image.FromHbitmap(m_HBitmap);
}
//If m_HBitmap is null retunrn null.
return null;
How can I draw on the printer device context?
How can I save the printer device context to DIB?
Thank you,
Jacob
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
打印机设备上下文是只写的。
例如,假设您正在打印到 PostScript 打印机。您创建一个打印机设备上下文并在其上绘制一些文本。打印机设备驱动程序不会呈现包含文本的位图。相反,它创建一系列 PostScript 命令来绘制文本并将命令发送到打印机。换句话说,没有要复制的位图。
你想达到什么目的?
Printer device contexts are write-only.
For example, suppose you are printing to a PostScript printer. You create a printer device context and draw some text on it. The printer device driver does not render a bitmap containing your text. Rather, it creates a sequence of PostScript commands to draw the text and sends the commands to the printer. In other words, there is no bitmap to be copied.
What are you trying to achieve?