3

I've ran into a problem that is a very foreign topic to me: printing to a printer.

Through scouring the internet I have found a way to print to my printer, but only simple text.

see here:

#include <stdio.h>
#include <windows.h>
#include <string.h>

int main () 
{
TCHAR   szDriver[16] = _T("WINSPOOL");
TCHAR   szPrinter[256];
DWORD   cchBuffer = 255;
HDC     hdcPrint = NULL;
HANDLE  hPrinter = NULL;
PRINTER_INFO_2  *pPrinterData;
BYTE    pdBuffer[16384];
BOOL    bReturn = FALSE;

DWORD   cbBuf = sizeof (pdBuffer);
DWORD   cbNeeded = 0;
pPrinterData = (PRINTER_INFO_2 *)&pdBuffer[0];

// get the default printer name
bReturn = GetDefaultPrinter(
    szPrinter,
    &cchBuffer);

if (bReturn) {
    // open the default printer
    bReturn = OpenPrinter(
        szPrinter,
        &hPrinter,
        NULL);
}

if (bReturn) {
    // get the printer port name
    bReturn =  GetPrinter(
        hPrinter,
        2,
        &pdBuffer[0],
        cbBuf,
        &cbNeeded);

       // this handle is no longer needed
    ClosePrinter(hPrinter);
}

if (bReturn) {
   // create the Print DC
   hdcPrint = CreateDC(szDriver, szPrinter, 
        pPrinterData->pPortName, NULL); 
}

if (hdcPrint) {
    // Print a test page that contains the string  
    // "PRINTER TEST" in the upper left corner.  

    Escape(hdcPrint, STARTDOC, 8, "Test-Doc", NULL); 
    TextOut(hdcPrint, 50, 50, _T("PRINTER TEST"), 12); 
    Escape(hdcPrint, NEWFRAME, 0, NULL, NULL); 
    Escape(hdcPrint, ENDDOC, 0, NULL, NULL); 

    // Delete the printer DC.  
    DeleteDC(hdcPrint); 
}

This successfully prints "PRINTER TEXT" to my printer. What I'm looking for is how to specify a path to a BMP file, and then print that BMP file. Though I've found some information using Google, all efforts have provided nothing. I appreciate any help.

Current update:

#include "stdafx.h"
#include <stdio.h>
#include <windows.h>
#include <string.h>

int main () 
{
TCHAR   szDriver[16] = _T("WINSPOOL");
TCHAR   szPrinter[256];
DWORD   cchBuffer = 255;
HDC     hdcPrint = NULL;
HDC     hdcPrintImg = NULL;
HANDLE  hPrinter = NULL;
PRINTER_INFO_2  *pPrinterData;
BYTE    pdBuffer[16384];
BOOL    bReturn = FALSE;

DWORD   cbBuf = sizeof (pdBuffer);
DWORD   cbNeeded = 0;
pPrinterData = (PRINTER_INFO_2 *)&pdBuffer[0];

// get the default printer name
bReturn = GetDefaultPrinter(
    szPrinter,
    &cchBuffer);

if (bReturn) {
    // open the default printer
    bReturn = OpenPrinter(
        szPrinter,
        &hPrinter,
        NULL);
}

if (bReturn) {
    // get the printer port name
    bReturn =  GetPrinter(
        hPrinter,
        2,
        &pdBuffer[0],
        cbBuf,
        &cbNeeded);

       // this handle is no longer needed
    ClosePrinter(hPrinter);
}

if (bReturn) {
    // create the Print DC
    HBITMAP bmp = (HBITMAP)LoadImage(0, L"print_file.bmp", IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE);
    HBITMAP CreatCompatibleBitmap(bmp);
    hdcPrintImg = bmp;
    hdcPrint = CreateDC(szDriver, szPrinter, 
        pPrinterData->pPortName, NULL); 
}

if (hdcPrint) {
    // Print a test page that contains the string  
    // "PRINTER TEST" in the upper left corner.  
    //Escape(hdcPrint, STARTDOC, 8, "Test-Doc", NULL); 
    //TextOut(hdcPrint, 50, 50, _T("PRINTER TEST"), 12); 
    BitBlt(hdcPrint, 0, 0, 3300, 2550, hdcPrintImg, 0, 0, SRCCOPY);
    //Escape(hdcPrint, NEWFRAME, 0, NULL, NULL); 
    //Escape(hdcPrint, ENDDOC, 0, NULL, NULL); 

    // Delete the printer DC.  
    DeleteDC(hdcPrint); 
}

}

user3419168
  • 1,135
  • 2
  • 8
  • 16

1 Answers1

2

Printing to a printer isn't much different from printing to the screen. You've already handled all the "stuff" that's different about a printer.

Your hdcPrint is basically just a normal handle to a normal DC. You can print a BMP to it just about the way you'd display a BMP on the screen:

  1. Load the BMP
  2. Create a DC compatible with your destination DC
  3. Select that BMP into a compatible DC
  4. Blit from the compatible DC to the DC for the printer.

The big difference is that a screen typically has around 100 DPI, where a printer typically has at least 300 DPI. As such, a picture that sized to look reasonable on-screen will generally look minuscule on a printer. Depending on its dimensions, you may well want to scale the picture up when printing to a printer.

As an aside: there are also a few printers that aren't compatible with Bit Blitting. You may want to use GetDeviceCaps(RC_BITBLT) or GetDeviceCaps(RC_STRETCHBLT) before writing your data. At one time, you ran into this pretty often, but I haven't seen it in quite a while.

Jerry Coffin
  • 476,176
  • 80
  • 629
  • 1,111
  • Thanks for the reply Jerry. Unfortunately, I think I'm way over my head here. I understand what you've written, but I haven't the slightest clue on how to implement it. I imagine step one is a large task alone, so I doubt you could easily show me an example. I may be a lost cause in regards to all of this. – user3419168 Jun 02 '14 at 20:21
  • I'm attempting to give it a shot, I've found this: http://stackoverflow.com/a/2654860/3419168 so I'm starting there. – user3419168 Jun 02 '14 at 20:32
  • That's for writing a bitmap (more difficult because Windows does less to support it). Loading one is pretty easy: http://stackoverflow.com/a/15940441/179910 – Jerry Coffin Jun 02 '14 at 20:33
  • Oh, I see. It seems easy enough, but I'm confused on "bmp". Shouldn't it be created as some data type? simply dropping that line into my code does give me a "identifier undefined". I appreciate the help here, I'm sure my noviceness is showing. – user3419168 Jun 02 '14 at 21:42
  • Oh--it should be an `HBITMAP`. – Jerry Coffin Jun 02 '14 at 21:50
  • and I specify the file name this way?: (0, "print_file.bmp", IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE); It seems to not like it whether I put the quotations or not. – user3419168 Jun 02 '14 at 22:04
  • Update: HBITMAP bmp = (HBITMAP)LoadImage(0, L"print_file.bmp", IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE); I think works. Now for step 2. – user3419168 Jun 02 '14 at 22:21
  • I just update the original post with what I have so far. It's horrendously out of whack, but I would be extremely appreciative if you could point out all that I'm doing wrong. Thanks so much. – user3419168 Jun 02 '14 at 22:49