I am printing the output of a text box in C#. To do that, I use raw printing.
However, before sending the text to print using WritePrinter
[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);
I would like to modify the device structure to landscape mode.
I can perform the first DocumentProperties call, because that returns the size of the device structure that will be pointed to by pDevMode
.
IntPtr pDevMode;
.
.
.
int dwNeeded = DocumentProperties(GetForegroundWindow(),
hPrinter, /* Handle to our printer. */
szPrinterName, /* Name of the printer. */
IntPtr.Zero, /* Asking for size, so */
IntPtr.Zero, /* these are not used. */
0); /* Zero returns buffer size. */
pDevMode = new IntPtr(dwNeeded);
However, the second call to DocumentProperties requires a both a pointer to a device information block as well as the constant DM_OUT_BUFFER
to tell the function to write the device information into the device information block, pointed to by pDevMode
.
How can I access the value of DM_OUT_BUFFER
from C#? I have read a lot of articles, but haven't come across anything that spells this out.
Most of the full raw printing function is listed below, without the DLL includes that are needed for the WinAPI
functions not directly accessible from C#.
And this example works fine, except it sends the document portrait mode, even if the printer is defaulted to landscape mode.
static extern int GetWindowText(IntPtr hWnd, StringBuilder text, int count);
// 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.
public static bool SendBytesToPrinter(string szPrinterName, IntPtr pBytes, Int32 dwCount)
{
Int32 dwError = 0, dwWritten = 0;
IntPtr hPrinter = new IntPtr(0);
DOCINFOA di = new DOCINFOA();
IntPtr pDevMode;
bool bSuccess = false; // Assume failure unless you specifically succeed.
di.pDocName = "My C#.NET RAW Document";
di.pDataType = "RAW";
// Open the printer.
if (OpenPrinter(szPrinterName.Normalize(), out hPrinter, IntPtr.Zero))
{
if (StartDocPrinter(hPrinter, 1, 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;
}