Help needed on line printing

Posted on 2002-06-03
Last Modified: 2010-08-05
Anyone knows how to stop advancing to the next page in line printing? Meaning the printer will print a portion of the paper (if it does not use up the whole page) and wait for the next print.

Currently this is the coding I am using for the printing part:

// p points to the start of the buffer, pSize holds the number of characters
void PrintString(char *p, DWORD pSize)
    CDC             dc;
    CPrintDialog    printDlg(FALSE);
    CRect           r;
    int             nHeight;
    // ask the user to select a printer
    if (printDlg.DoModal() == IDCANCEL)
    // Attach a printer DC
    dc.m_bPrinting = TRUE;

    // use Textmappingmode, that's easiest to map the fontsize
    // setup font specifics
    LOGFONT LogFont;
    CFont     aFont, *oldFont;
    LogFont.lfHeight = -MulDiv(10, GetDeviceCaps(dc, LOGPIXELSY), 72);
    LogFont.lfWidth = 0;
    LogFont.lfEscapement = 0;
    LogFont.lfOrientation = 0;
    LogFont.lfWeight = 0;
    LogFont.lfItalic = false;
    LogFont.lfUnderline = 0;
    LogFont.lfStrikeOut = 0;
    LogFont.lfCharSet = ANSI_CHARSET;
    LogFont.lfOutPrecision = OUT_TT_PRECIS;
    LogFont.lfClipPrecision = CLIP_DEFAULT_PRECIS;
    LogFont.lfQuality = DEFAULT_QUALITY;
    LogFont.lfPitchAndFamily = DEFAULT_PITCH | FF_SWISS;
    lstrcpy (LogFont.lfFaceName, "MS Sans Serif");
    aFont.CreateFontIndirect ( &LogFont );
    // ok, we've build the font, now use it
    oldFont = dc.SelectObject( &aFont );        
    // Get the application title
    CString strTitle;
    // Initialise print document details
    DOCINFO di;
    ::ZeroMemory (di, sizeof (DOCINFO));
    di.cbSize = sizeof (DOCINFO);
    // application title appears in the spooler view
    di.lpszDocName = strTitle;
    // Begin a new print job
    BOOL bPrintingOK = dc.StartDoc( &di );
    // Get the printing extents and store in the m_rectDraw field of a
    // CPrintInfo object
    CPrintInfo Info;
    int w = dc.GetDeviceCaps(HORZRES);
    int h = dc.GetDeviceCaps(VERTRES);
    Info.m_rectDraw.SetRect(0,0, w, h);
    char *startAt = p;
    int totalDone = 0;
    int lengthToGo = pSize;
    for (UINT page = Info.GetMinPage();
    bPrintingOK & totalDone < lengthToGo; page++)
        // begin new page
        Info.m_nCurPage = page;
        // calc how much text fits on one page
        r = Info.m_rectDraw;
        r.bottom =;
        int i = 0;
        while (r.bottom < Info.m_rectDraw.bottom & totalDone + i < lengthToGo)
            r.right = Info.m_rectDraw.right;
            nHeight = dc.DrawText(startAt, i++, r,
        // go one back to assure correct height
        if (r.bottom >= Info.m_rectDraw.bottom)
        // print that text
        dc.DrawText(startAt, i, r, DT_WORDBREAK|DT_NOCLIP|DT_EXPANDTABS);
        // go to next page
        startAt += i;
        totalDone += i;
        // end page
        bPrintingOK = (dc.EndPage() > 0);
    // end a print job
    if (bPrintingOK)
        // abort job.
    // restore font
    // free font memory
    // detach the printer DC

Question by:cytay
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 3
  • 3
LVL 49

Expert Comment

ID: 7053254
If you never call
then it won't eject the page.  

But this sounds very odd.  You really can't leave the printer and the spooler 'dangling' with a half page.  

The only reason you might want to do this is because you expect to print some more data on the bottom part of the page.  In that case, the normal procedure would be to go ahead and print that data -- make it part of the same print job.

Can you explain your goal?  There may be other, better ways to accomplish it.

-- Dan

Author Comment

ID: 7053266
Hi Dan,

Even if I commented out dc.EndPage(), it will still eject the page.

I am developing a program which uses dot matrix printer. Everytime the user places any purchase on sth then the program will print out the purchase detail. I need them to be printed on the same paper.

It doesn't make sense for me to eject out all the paper in this case right?

LVL 49

Expert Comment

ID: 7053318
dc.EndPage() is called twice.

For dot-matrix output of partial page, it is probably best to use old style printing, where you open LPT1 as a file and dump text to it.

Windows output is page-oriented.  It is best to accumulate a full page, then print it all at once.

One outside-the-box idea is to define a short page (custom paper size) ... say about the length of 10 lines of text.  Then each output is a single page.  You would need to set up the printer so that it knows to advance only 10 lines for each page.  This will be printer-dependant.  Check all of the settings for the printer driver, there may be some help there.

-- Dan

Modern healthcare requires a modern cloud. View this brief video to understand how the Concerto Cloud for Healthcare can help your organization.


Author Comment

ID: 7053388
Hi Dan,

Still can't work out for this time...
the old method of open
FILE *ptr = fopen("LPT1","w");
should close by this

I am facing problem that it only print once...
LVL 49

Accepted Solution

DanRollins earned 300 total points
ID: 7053415
>>I am facing problem that it only print once...

What do you mean? How many times do you want it to print?  

-- Dan
LVL 22

Expert Comment

ID: 7053624
>> For dot-matrix output of partial page, it is probably best to use old style printing,
>> where you open  LPT1 as a file and dump text to it.
>> Windows output is page-oriented.  It is best to accumulate a full page, then print it all at once.
to continue this thought...  windows output is page-oriented because most new printers are "page printers" as opposed to "line printers".  A page printer does not physically print until it has an entire page of information to print.  It cannot print partial pages.  

Theoretically you could leave a page partially "used" in the printer and then print to the rest of the page at a later time.  But windows will never let you do this.  Whenever you stopp printing to it, windows will assume the last page printed is a full page and will finsih cause the page to be printed.  It has to do this.    It is very reasonable to assume that programs want to print to whole pages.  Image what would happen if it didn't make this assumption.  If a program is printing and crashes it might leave a page 1/2 done.  Then the next program to print would have its output mixed with the previous program's output.   Windows won't allow this.

Your best bet is to rethink your entire approach.

Write the information to a log file and when you have a full page worth, then print the info.  (We write point-of-sales systems and this is precisely what we do.)  There are many advantages to this.

For example, consider what you will do now if the printer jams?   You can reprint the 2nd part of the page since you are generatig that "currently" but the 1st part of the page was generated earlier, could you regenerate it?  probably not.   By keeping a log you can regenerate all the necessary info to perform a reprint.

Author Comment

ID: 7055310

Thanks for your suggestions and comments. I have solved the problem by using the old method of printing.


Thanks to you too. Unfortunately I have to give the points to Dan becoz he was here first. :)


Featured Post

What does it mean to be "Always On"?

Is your cloud always on? With an Always On cloud you won't have to worry about downtime for maintenance or software application code updates, ensuring that your bottom line isn't affected.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Errors will happen. It is a fact of life for the programmer. How and when errors are detected have a great impact on quality and cost of a product. It is better to detect errors at compile time, when possible and practical. Errors that make their wa…
IntroductionThis article is the second in a three part article series on the Visual Studio 2008 Debugger.  It provides tips in setting and using breakpoints. If not familiar with this debugger, you can find a basic introduction in the EE article loc…
The viewer will learn how to pass data into a function in C++. This is one step further in using functions. Instead of only printing text onto the console, the function will be able to perform calculations with argumentents given by the user.
The viewer will learn how to use the return statement in functions in C++. The video will also teach the user how to pass data to a function and have the function return data back for further processing.

630 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question