Delen via


Afdrukken van bureaublad-app

In deze sectie wordt beschreven hoe u afdrukt vanuit een systeemeigen Windows-bureaubladprogramma.

Overzicht

Om de beste gebruikerservaring te bieden wanneer u afdrukt vanuit een systeemeigen Windows-programma, moet het programma zijn ontworpen om af te drukken vanuit een toegewezen thread. In een systeemeigen Windows-programma is het programma verantwoordelijk voor het beheren van gebeurtenissen en berichten van de gebruikersinterface. Afdrukbewerkingen kunnen perioden van intensieve berekening vereisen omdat de toepassingsinhoud wordt weergegeven voor de printer, waardoor het programma niet kan reageren op gebruikersinteractie als deze verwerking wordt uitgevoerd in dezelfde thread als de gebeurtenisverwerking van de gebruikersinteractie.

Als u al bekend bent met het schrijven van een systeemeigen Windows-programma met meerdere threads, gaat u rechtstreeks naar Afdrukken vanuit een Windows-toepassing en leert u hoe u afdrukfunctionaliteit toevoegt aan uw programma.

Basisvereisten voor Windows-programma's

Voor de beste prestaties en reactiesnelheid van het programma moet u de afdruktaakverwerking van een programma niet uitvoeren in de thread die gebruikersinteractie verwerkt.

Deze scheiding van afdrukken van gebruikersinteractie heeft invloed op de wijze waarop het programma de toepassingsgegevens beheert. U moet deze implicaties grondig begrijpen voordat u begint met het schrijven van de toepassing. In de volgende onderwerpen worden de basisvereisten beschreven voor het verwerken van afdrukken in een afzonderlijke thread van een programma.

Basisbeginselen van Windows-programma's

Een systeemeigen Windows-programma moet de hoofdvensterprocedure opgeven voor het verwerken van de vensterberichten die het ontvangt van het besturingssysteem. Elk venster in een Windows-programma heeft een bijbehorende WndProc--functie waarmee deze vensterberichten worden verwerkt. De thread waarin deze functie wordt uitgevoerd, wordt de gebruikersinterface of ui, thread genoemd.

Resources gebruiken voor tekenreeksen.
Gebruik tekenreeksresources uit het resourcebestand van het programma in plaats van tekenreeksconstanten voor tekenreeksen die mogelijk moeten worden gewijzigd wanneer u een andere taal ondersteunt. Voordat een programma een tekenreeksresource als een tekenreeks kan gebruiken, moet het programma de resource ophalen uit het resourcebestand en deze kopiëren naar een lokale geheugenbuffer. Hiervoor is enige extra programmering in het begin vereist, maar is het mogelijk om het programma in de toekomst eenvoudiger te wijzigen, te vertalen en te lokaliseren.
Gegevens verwerken in stappen.
Verwerk de afdruktaak in stappen die kunnen worden onderbroken. Dit ontwerp maakt het mogelijk dat de gebruiker een lange verwerkingsbewerking annuleert voordat deze is voltooid en voorkomt dat het programma andere programma's blokkeert die mogelijk tegelijkertijd worden uitgevoerd.
Venstergebruikersgegevens gebruiken.
Afdruktoepassingen hebben vaak verschillende vensters en threads. Als u de gegevens beschikbaar wilt houden tussen threads en verwerkingsstappen zonder statische, globale variabelen te gebruiken, verwijst u naar de gegevensstructuren door een gegevenspointer die deel uitmaakt van het venster waarin ze worden gebruikt.

In het volgende codevoorbeeld ziet u een hoofdinvoerpunt voor een afdruktoepassing. In dit voorbeeld ziet u hoe u tekenreeksbronnen gebruikt in plaats van tekenreeksconstanten en ook de hoofdberichtlus ziet die de vensterberichten van het programma verwerkt.

int APIENTRY 
wWinMain(
        HINSTANCE hInstance, 
        HINSTANCE hPrevInstance, 
        LPWSTR lpCmdLine, 
        int nCmdShow
)
{
    UNREFERENCED_PARAMETER(hPrevInstance);
    UNREFERENCED_PARAMETER(lpCmdLine);

    MSG msg;
    HACCEL hAccelTable;
    HRESULT hr = S_OK;

    // Register the main window class name
    WCHAR szWindowClass[MAXIMUM_RESOURCE_STRING_LENGTH];            
    LoadString(
        hInstance, 
        IDC_PRINTSAMPLE, 
        szWindowClass, 
        MAXIMUM_RESOURCE_STRING_LENGTH);
    MyRegisterClass(hInstance, szWindowClass);

    // Perform application initialization:
    if (!InitInstance (hInstance, nCmdShow))
    {
        // Unable to initialize this instance of the application
        //  so display error message and exit
        MessageBoxWithResourceString (
            hInstance, 
            GetDesktopWindow(), 
            IDS_ERROR_INSTINITFAIL, 
            IDS_CAPTION_ERROR, 
            (MB_OK | MB_ICONEXCLAMATION));
        return FALSE;
    }    
    
    // Init COM for printing interfaces
    if (FAILED(hr = CoInitializeEx(0, COINIT_MULTITHREADED)))
    {
        // Unable to initialize COM
        //  so display error message and exit
        MessageBoxWithResourceString (
            hInstance, 
            GetDesktopWindow(), 
            IDS_ERROR_COMINITFAIL, 
            IDS_CAPTION_ERROR, 
            (MB_OK | MB_ICONEXCLAMATION));
        return FALSE;
    }

    hAccelTable = LoadAccelerators(
                    hInstance, 
                    MAKEINTRESOURCE(IDC_PRINTSAMPLE));

    // Main message handling loop
    while (GetMessage(&msg, NULL, 0, 0))
    {
        if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg))
        {
            TranslateMessage(&msg);
            DispatchMessage(&msg);
        }
    }

    // Uninitialize (close) the COM interface
    CoUninitialize();

    return (int) msg.wParam;
}

Documentgegevens

Systeemeigen Windows-programma's die afdrukken moeten worden ontworpen voor verwerking met meerdere threads. Een van de vereisten van een ontwerp met meerdere threads is om de gegevenselementen van het programma te beveiligen, zodat ze veilig zijn voor meerdere threads die tegelijkertijd kunnen worden gebruikt. U kunt gegevenselementen beveiligen met behulp van synchronisatieobjecten en de gegevens ordenen om conflicten tussen de threads te voorkomen. Tegelijkertijd moet het programma voorkomen dat de programmagegevens worden gewijzigd terwijl deze worden afgedrukt. Het voorbeeldprogramma maakt gebruik van verschillende programmeertechnieken met meerdere threads.

synchronisatiegebeurtenissen
Het voorbeeldprogramma maakt gebruik van gebeurtenissen, thread-ingangen en wachtfuncties om de verwerking tussen de afdrukthread en het hoofdprogramma te synchroniseren en om aan te geven dat de gegevens in gebruik zijn.
Application-Specific Windows-berichten
Het voorbeeldprogramma maakt gebruik van toepassingsspecifieke vensterberichten om het programma compatibeler te maken met andere systeemeigen Windows-programma's. Als u de verwerking in kleinere stappen opsplitst en deze stappen in de berichtenlus van het venster in de wachtrij plaatst, is het voor Windows eenvoudiger om de verwerking te beheren zonder andere toepassingen te blokkeren die mogelijk ook op de computer worden uitgevoerd.
gegevensstructuren
Het voorbeeldprogramma is niet geschreven in een objectgeoriënteerde stijl met behulp van objecten en klassen, hoewel het wel gegevenselementen in gegevensstructuren groepeert. In het voorbeeld wordt geen objectgerichte benadering gebruikt om te voorkomen dat de ene benadering beter of slechter is dan een andere.
U kunt de functies en gegevensstructuren van het voorbeeldprogramma als uitgangspunt gebruiken wanneer u uw programma ontwerpt. Of u nu besluit om een objectgeoriënteerd programma te ontwerpen of niet, de belangrijke ontwerpoverweging die u moet onthouden, is het groeperen van de gerelateerde gegevenselementen, zodat u ze indien nodig veilig in verschillende threads kunt gebruiken.

Apparaatcontext van de printer

Wanneer u afdrukt, wilt u mogelijk de inhoud weergeven die moet worden afgedrukt naar een apparaatcontext. Procedure: Een printerapparaatcontext ophalen beschrijft de verschillende manieren waarop u een printerapparaatcontext kunt verkrijgen.

Afdrukken vanuit een Windows-toepassing