15 мая 2023 года "Исходники.РУ" отмечают своё 23-летие!
Поздравляем всех причастных и неравнодушных с этим событием!
И огромное спасибо всем, кто был и остаётся с нами все эти годы!

Главная Форум Журнал Wiki DRKB Discuz!ML Помощь проекту


Cancel Print Leaks Windows

Jeffrey T. Kouzmanoff -- jtk@prairienet.org
Friday, February 23, 1996


Hello MFC fans.
I have a print function in my application that simply starts printing 
upon the click of the OK button in the "Print What" dialog.
(Please, no "that's not standard" comments. This is for an "appliance")

When the application prints and is ultimately terminated, Debug Windows
does not report any leaks.

When the user clicks the CANCEL button and the job is aborted, somewhere,
somehow, 3 windows become reported as not being deleted upon app 
termination.

By SPYing, I have found that the reported window handles do not match
1) the main app window, the MDIFrame
2) the MDI client
3) the layer 1 dialog
4) the layer 2 dialog (called from dialog 1 when "Print..." selected)
5) the layer 3 dialog (called from 2, asking "print what?")
6) any of the layer 3 dialog controls
7) the "Printing..." modeless dialog
8) any of the "Printing..." dialog's controls

So, where did these windows come from, and why are they undeleted?

Here is a sample of the print code:

NOTE: this is a good piece of code to squirrel away if you want to 
implement a "hands off" print task with MFC... IF IT WORKED, that is.
I noticed that the printer abort procedure isn't here, which is necessary.
E-mail me if you'd like complete code.
PrintInfo is an instance of a class that is used to store the printer
device context, etc., for other print routines to access.
.........

    // Get the default printer info
    CPrintDialog dlgPrint (FALSE);
 
    if (!App.GetPrinterDeviceDefaults (&dlgPrint.m_pd)) {
        AfxMessageBox (IDP_ErrGetPrintDefs);
        return;
    }
 
    // Create a printer device context in which to draw things
    HDC hdcPrint = dlgPrint.CreatePrinterDC ();
    if (hdcPrint == NULL) {
        AfxMessageBox (IDP_ErrCreatePrintDC);
        return;
    }
 
    // Attach the handle to the printer context to an object of type CDC so
    // that this class' members may be used.
    PrintInfo.m_DC.Attach (hdcPrint);

    // Create the modeless dialog that has the "Printing..." message and
    // Cancel button. This sets m_bUserAbortPrint to TRUE when clicked. 
    CPrintingDlg *pdlgPrinting = new CPrintingDlg (this);

    // Abort Proc has message loop. E-MAIL me for more complete code
    PrintInfo.m_DC.SetAbortProc (AbortProc);
 
    // Set up DOCINFO structure with which to start the
    // print job.    
    DOCINFO DocInfo;
    DocInfo.cbSize = sizeof (DocInfo);
    DocInfo.lpszOutput = NULL;  // output to go to device, not file
    static char BASED_CODE JobName[] = "Whatever";
    DocInfo.lpszDocName = JobName;
 
    if (PrintInfo.m_DC.StartDoc (&DocInfo) == SP_ERROR) {
        ... handle error, e.g., AfxMessage something
        goto UglyGoto999;
    }
 
    //// Start of Print Job
     ... startpage / endpage blah blah blah

    //// End of print job
    ////
 
    if (m_bUserAbortPrint) {
        // user wants to abort the print job
        if (PrintInfo.m_DC.AbortDoc () < 0)
            TRACE0 ("AbortDoc error\n");
    }
    else {
        if (PrintInfo.m_DC.EndDoc () < 0)
            TRACE0 ("EndDoc error\n");
    }
    
 UglyGoto999:

    // clean up
    pdlgPrinting->DestroyWindow (); // get rid of modeless "printing" dlg
    PrintInfo.m_DC.Detach ();    // detach the printer DC from the CDC obj.
    ::DeleteDC (hdcPrint);          // delete the DC
    


-Jeff




Jeffrey T. Kouzmanoff -- jtk@prairienet.org
Monday, February 26, 1996

On Mon, 26 Feb 1996, Chong Zhang wrote:

> The problem seems like happened in 
> 
>  ...start page/end page blah blah blah
> 
> section!
> 
> If the printing process creates some temprary windows, who knows why, and 
> the abort procedure breaks the process, these temprary windows can be 
> left behind. 

But my printing code is just a bunch of StartPage, EndPage and GDI calls.
Can GDI calls create such windows? How am I supposed to Cancel a print
cleanly? Can GDI objects be misreported as windows rather than fonts by the
debugging version of windows?

-Jeff




Chong Zhang -- cz@dana.ucc.nau.edu
Thursday, February 29, 1996

On Mon, 26 Feb 1996, Jeffrey T. Kouzmanoff wrote:

> On Mon, 26 Feb 1996, Chong Zhang wrote:
> 
> > The problem seems like happened in 
> > 
> >  ...start page/end page blah blah blah
> > 
> > section!
> > 
> > If the printing process creates some temprary windows, who knows why, and 
> > the abort procedure breaks the process, these temprary windows can be 
> > left behind. 
> 
> But my printing code is just a bunch of StartPage, EndPage and GDI calls.
> Can GDI calls create such windows? How am I supposed to Cancel a print
> cleanly? Can GDI objects be misreported as windows rather than fonts by the
> debugging version of windows?
> 
> -Jeff
> 
> 

The debug windows should not misreport GDI objects as windows object 
because they belong to different segment ( you know that a HANDLE is 
actually an offset address within a segment ).

If you sure that no windows are created during startpage and endpage 
section, than these windows must be created outside of it and must be 
destroied by the standard end printing process which is skiped by the 
abort procedure. 

Microsoft provides a good sample of printing abort procedure in 
VIEWPRNT.CPP which does not jump to anywhere but records the abort 
indication within the dialogbox so that the printing routine can exit 
from the loop clean.

I wish it helps.




| Вернуться в корень Архива |