Herzlich Willkommen, lieber Gast!
  Sie befinden sich hier:

  Forum » FAQ C / C++ (WinAPI, Konsole) » Modale Dialoge

Forum | Hilfe | Team | Links | Impressum | > Suche < | Mitglieder | Registrieren | Einloggen
  Quicklinks: MSDN-Online || STL || clib Reference Grundlagen || Literatur || E-Books || Zubehör || > F.A.Q. < || Downloads   

Autor Thread - Seiten: > 1 <
000
10.01.2003, 16:22 Uhr
void*
Generic Pointer
(Operator)


Erstellt von Uwe

Bis zu diesem Zeitpunkt haben wir uns (eigentlich) nur der Erzeugung einer Anwendung und der Behandlung von Ereignissen beschäftigt. Was wäre aber eine Windowsanwendung ohne Dialoge? Nicht viel, denn bieten sie uns nicht die Möglichkeit Informationen abzufragen? Bisher haben wir uns nur den Informationsfenstern (MessageBox()) bedient. Das wird sich jedoch ab sofort ändern.
Wir unterscheiden zwei Gruppen von Dialogen: modale- und nichtmodale Dialoge. Die erste Gruppe ermöglicht dem Benutzer nach deren Aufruf auch weiterhin auf das Hauptfenster zuzugreifen. Ein Beispiel hierfür ist der "Suchen- und Ersetzendialog". Modale Dialog verlangen einen expliziten Abschluß des Dialoges, meist über die Buttons "OK" oder "Abbrechen" realisiert. In diesem Teil unseres Kurses beschäftigen wir uns hier mit den modalen Dialogen. Ein typischer Verteter ist hier das berühmte Info- oder Aboutfenster. Das anlegen der Menüs und der Umgang mit der Resourcendatei war bereits Bestandteil von
API Teil 3 - Menüs, Icons und wird hier nicht nochmals behandelt.
Wir öffnen als erstes unsere Resourcen Datei und definieren den Dialogprototyp.

C++:

#include "resource.h"

DialogMenu MENU DISCARDABLE
BEGIN
        POPUP "&Datei"
        BEGIN
                MENUITEM "B&eenden", IDM_BEENDEN
        END
        POPUP "&Hilfe"
        BEGIN
                MENUITEM "&nichtmodaler Dialog", IDM_NMD
        END
END

IDD_NMD DIALOG 16, 28, 119, 86
STYLE DS_MODALFRAME | DS_CENTER | DS_CENTERMOUSE | WS_POPUP | WS_VISIBLE | WS_CAPTION
CAPTION "Mein erster Dialog"
FONT 10, "MS Sans Serif"
BEGIN
    PUSHBUTTON      "OK", IDOK, 30, 60, 40, 14
    LTEXT           "Unser erster nichtmodaler Dialog", IDC_STATIC, 5, 15, 110, 10
END



Als erstes wird der Bezeichner für den Dialog festgelegt. Danach folgt das Schlüsselwort DIALOG. Jetzt kommen die Angaben für die Position des Dialogs relativ zum zum Anwendungsbereich des Hauptfensters in Form von x- und y-Koordinaten, Breite und Höhe. Diese vier Werte basieren nicht auf der Einheit Pixel, sondern haben die Dimensionen des verwendeten Font zur Gundlage. Hier bleibt uns nichts weiter als rechnen:
Umrechnung in Pixel:
x-Koordinaten und Breitenangaben: Pixel = Wert * durchschnittliche Breite der Schrift / 4
y-Koordinaten und Höhenangaben : Pixel = Wert * Höhe der Schrift / 8


Es folgen die Elemente des Dialoges, welche vom Grundsatzt her immer wie folgt angegeben werden: Typ "Beschriftung", ID, xPos, yPos, xWidth, yHeigh,...

Die nachfolgenden Bezeichner PUSHBUTTON und LTEXT definieren Steuerelemente innerhalb des Dialoges.
Um den auf Ereignisse im Dialog zu reagieren benötigt dieser eine eigene Callbackfunktion, welche vom Typ BOOL sein muß. Für bearbeitete Nachrichten etwa WM_INITDIALOG wird TRUE und für nicht bearbeitete FALSE zurück gegeben.
Unsere Dialogprozedur kümmert sich nicht um Nachrichten, welche das Hauptfenster betreffen (WM_PAINT WM_DESTROY). An die Stelle von WM_CREATE tritt in dieser Funktion WM_INITDIALOG. WM_INITDIALOG gibt es nur für Dialoge. Wird für diese Nachricht TRUE geliefert, erhält automatisch das erste Element, welches mit dem Flag WS_TABSTOP im Fensterstil erzeugt wurde, den Eingabefokus.
Was wir brauchen ist eine Behandlung für WM_COMMAND. Dort wird auf die Aktivierung der in der Resourcendatei zugewiesenen IDOK reagiert und der Dialog mit EndDialog(hDlg, 0);

geschlossen. Um den Dialog noch mit der "ESC" - Taste schließen zu können (was eigentlich nach den Richtlinien Standard ist, aber viele es nicht haben wollen) fangen wir das auch noch ab. Es foglt das gesamte Beispiel mit dem Header der Resourcendatei:

C++:
// resource.h
#include < windows.h >

#define IDM_BEENDEN            1001
#define IDM_NMD                1002
#define IDC_STATIC             3001



Und nun die Dialog.c:

C++:
// Dialog.c
#include < windows.h >
#include "resource.h"
#include < tchar.h >

LRESULT CALLBACK WfFu(HWND hWnd, UINT message,WPARAM wParam, LPARAM lParam);
BOOL CALLBACK NmDProc(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam);

int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine,
int nCmdShow)
{
    WNDCLASSEX wc = {0};
    wc.cbSize =  sizeof(WNDCLASSEX);
    static TCHAR szAppName[] =
    _T("Fenster");
    wc.style = CS_HREDRAW | CS_VREDRAW;
    wc.lpfnWndProc = WfFu;
    wc.cbClsExtra = 0;
    wc.cbWndExtra = 0;
    wc.hInstance = hInstance;
    wc.hIcon = LoadIcon(NULL,IDI_APPLICATION);
    wc.hCursor = LoadCursor(NULL,IDC_ARROW);
    wc.hbrBackground = reinterpret_cast(COLOR_WINDOW + 1);
    wc.lpszMenuName = "DialogMenu";
    wc.lpszClassName = szAppName;
    wc.hIconSm = LoadIcon(NULL, IDI_APPLICATION);

    RegisterClassEx(&wc);

    HWND hWnd = CreateWindowEx(
        WS_EX_CLIENTEDGE,
        szAppName,
        _T("nichtmodaler Dialog"),
        WS_OVERLAPPEDWINDOW,
        CW_USEDEFAULT,
        CW_USEDEFAULT,
        CW_USEDEFAULT,
        CW_USEDEFAULT,
        NULL,
        NULL,
        hInstance,
        NULL);

    ShowWindow(hWnd, nCmdShow);
    UpdateWindow(hWnd);

    MSG msg;
    while (GetMessage(&msg,NULL, 0, 0) == TRUE)
    {
        TranslateMessage(&msg);
        DispatchMessage(&msg);
    }
    return msg.wParam;
}

LRESULT CALLBACK WfFu(HWND hWnd, UINT message,WPARAM wParam, LPARAM lParam)
{
        static HINSTANCE hInstance;
        switch(message)
        {
        case WM_CREATE:
                hInstance = (HINSTANCE)GetWindowLong(hWnd, GWL_HINSTANCE);
                return 0;
        case WM_COMMAND:
                switch(LOWORD(wParam))
                {
                        case IDM_NMD:
                                DialogBox(hInstance, "IDD_NMD", hWnd, NmDProc);
                                return 0;
                        case IDM_BEENDEN:
                                SendMessage(hWnd, WM_DESTROY, 0, 0);
                                return 0;
                }
                return 0;


                case WM_DESTROY:
                        PostQuitMessage(0);
                        return 0;

                default:
                        return DefWindowProc(hWnd, message, wParam, lParam);
    }
}

BOOL CALLBACK NmDProc(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{
        switch(message)
        {
        case WM_INITDIALOG:
                return TRUE;

        case WM_COMMAND:
                switch(LOWORD(wParam))
                {
                case IDOK:
                case IDCANCEL:
                        EndDialog(hDlg, 0);
                        return TRUE;
                }
                break;
        }
        return FALSE;
}




Der eigentliche Aufruf des Dialoges erfolgt mit
DialogBox(hInstance, "IDD_NMD", hWnd, NmDProc); in der Callbackfunktion der Anwendung. Der erste Parameter ist eigentlich nur ein Zähler (das Programm kann ja mehrmals gestartet werden). Der zweite Parameter ist der Name für die Resource gefolgt von dem Handle des Hauptfensters. Schließlich wird noch unsere Dialogprozedur übergeben.
--
Gruß
void*
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
Seiten: > 1 <     [ FAQ C / C++ (WinAPI, Konsole) ]  


ThWBoard 2.73 FloSoft-Edition
© by Paul Baecher & Felix Gonschorek (www.thwboard.de)

Anpassungen des Forums
© by Flo-Soft (www.flo-soft.de)

Sie sind Besucher: