Stilllegung des Forums
Das Forum wurde am 05.06.2023 nach über 20 Jahren stillgelegt (weitere Informationen und ein kleiner Rückblick).
Registrierungen, Anmeldungen und Postings sind nicht mehr möglich. Öffentliche Inhalte sind weiterhin zugänglich.
Das Team von spieleprogrammierer.de bedankt sich bei der Community für die vielen schönen Jahre.
Wenn du eine deutschsprachige Spieleentwickler-Community suchst, schau doch mal im Discord und auf ZFX vorbei!
Werbeanzeige
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 |
include <windows.h> LRESULT CALLBACK WindowProc (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam); HWND ErstelleHauptfenster (HINSTANCE hInst); void ErstelleSteuerelemente (HWND hWnd, HINSTANCE hInst); #define ID_STATICTEXT 4000 #define ID_EDITBOX 4001 #define ID_BTN_UEBERNEHMEN 4002 #define ID_BTN_BEENDEN 4003 // Globale Variablen // Don't do this at home! // //Wie kireg ich die hier Weg? HWND hText; // Handle für den statischen Text HWND hEditBox; // Handle für die Editbox HWND hUebernehmen; // Handle für Button "Übernehmen" HWND hBeenden; // Handle für Button "Beenden" int WINAPI WinMain (HINSTANCE hInst, HINSTANCE hPrevInst, LPSTR lpcmdline, int ncmdshow) { HWND hWnd; // Fenster-Handle MSG message; // Nachricht hWnd = ErstelleHauptfenster (hInst); if (hWnd == NULL) return (0); ErstelleSteuerelemente (hWnd, hInst); while (GetMessage (&message, NULL, 0, 0) ) { TranslateMessage (&message); DispatchMessage (&message); } return (int)(message.wParam); } HWND ErstelleHauptfenster (HINSTANCE hInst) { HWND hWnd; // Fenster-Handle WNDCLASSEX windowclass; // Nachricht // Der Klassenname des Fensters ist frei wählbar const char szClassName[] = "Zweites Fenster"; windowclass.cbSize = sizeof (WNDCLASSEX); windowclass.style = CS_HREDRAW | CS_VREDRAW; //Wie übergebe ich hier die Handles? // // windowclass.lpfnWndProc = WindowProc; windowclass.cbClsExtra = 0; windowclass.cbWndExtra = 0; windowclass.hInstance = hInst; windowclass.hIcon = LoadIcon (NULL, IDI_APPLICATION); windowclass.hIconSm = LoadIcon (NULL, IDI_APPLICATION); windowclass.hCursor = LoadCursor (NULL, IDC_ARROW); windowclass.hbrBackground = (HBRUSH)COLOR_BACKGROUND+1; windowclass.lpszMenuName = NULL; windowclass.lpszClassName = szClassName; if (!RegisterClassEx (&windowclass) ) return (NULL); hWnd = CreateWindowEx (NULL, szClassName, "Eine kleine Anwendung", WS_OVERLAPPEDWINDOW | WS_VISIBLE, CW_USEDEFAULT, CW_USEDEFAULT, 300, 135, NULL, NULL, hInst, NULL); return (hWnd); } LRESULT CALLBACK WindowProc (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) { switch (message) { case WM_DESTROY: { PostQuitMessage (0); return (0); } case WM_COMMAND: { switch (wParam) { case ID_BTN_UEBERNEHMEN: { char szText[256]; GetWindowText (hEditBox, szText, 256);//Wie zeige ich dem Programm, was hEditbox ist? // // SetWindowText (hText, szText); SetWindowText (hEditBox, ""); return (0); } case ID_BTN_BEENDEN: { int Resultat; // Rückgabewert der Messagebox Resultat = MessageBox (hWnd, "Wirklich beenden?", "Programm beenden", MB_YESNO | MB_ICONQUESTION); if (Resultat == IDYES) { PostQuitMessage (0); return (0); } return (0); } } break; } break; } return (DefWindowProc (hWnd, message, wParam, lParam) ); } // WindowProc |
Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von »dot« (31.07.2011, 00:09)
Dass mit WM_CREATE hab ich schon einigermaßen verstanden, allerdings bleibt mir eine Frage noch offen:
Die Childwindows rufen ja auch jeweils die Nachricht auf, wie verhindere ich, dass dann neue Fenster erstellt werden, oder es einen Fehler gibt?
Zu GetDlgItem, nun gut. Ich kriege hier also ein Handle zu einer ID und noch etwas anderem ( in meinem Fall dem Parentwindow?).
Dieses Handle könnt ich mir theoretisch doch auch so in der WM_CREATE erzeugen, oder?
Wie benutze ich denn dieses Handle weiter?
Ich muss es ja irgendwie sichern.
Zum Schluss noch SetWindowLongPtr:
Ich kann hier also diverse Sachen verändern.
Allerdings bin ich mir nicht sicher was denn jezt genau.
Und vorallem was brauch ich hierfür?
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 |
class MyWindow { private: HWND hwnd; // Unsere Nachrichtenprozedur ist eine Memberfunktion LRESULT WndProc(UINT msg, WPARAM wParam, LPARAM lParam) { // Hier hast du Zugriff auf sämtliche Member switch (msg) { ... } ... } // Dummyfunktion die die Methode aufruft static LRESULT CALLBACK WndProcThunk(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) { MyWindow* obj = reinterpret_cast<MyWindow*>(GetWindowLongPtr(hWnd, GWLP_USERDATA)); return obj->WndProc(msg, wParam, lParam); } // Fenster wird mit dieser WndProc erzeugt static LRESULT CALLBACK BootstrapWndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) { if (msg == WM_CREATE) { MyWindow* obj = reinterpret_cast<MyWindow*>(reinterpret_cast<CREATESTRUCT*>(lParam)->lpCreateParams); // Den this-Pointer in GLWP_USERDATA stecken SetWindowLongPtr(hWnd, GWLP_USERDATA, reinterpret_cast<LONG_PTR>(obj)); // Neue WndProc setzen die alle Nachrichten ab jetzt an unser Objekt weiterleitet SetWindowLongPtr(hWnd, GWLP_WNDPROC, reinterpret_cast<LONG_PTR>(&WndProcThunk)); return obj->WndProc(msg, wParam, lParam); } return DefWindowProc(hWnd, msg, wParam, lParam); } public: MyWindow() : hwnd(CreateWindowEx(0, TEXT("MyWindowClass"), TEXT("hello world"), WM_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, 800, 600, 0, 0, hInstance, this)) { } }; |
Nun gut, das wäre dann schon geklärtZitat
Die Childwindows rufen nicht das WM_CREATE deines Fenster auf, das Problem das du da siehst existiert nicht
Heißt, ich nutze jetzt immer diese Funktion mit der ID als Parameter wenn ich das Handle benötige?Zitat
Ja nein, eben genau nicht. Anstatt es zu sichern kannst du es damit einfach immer wenn dus brauchst abfragen.
Hm, also erstmal brauch ich keine neue Nachrichten Funktion mehr zu erstellen, wenn ich dies in einer Klasse bereits getan habe?Zitat
SetWindowLongPtr() erlaubt es dir über GWLP_USERDATA einen beliebigen Pointer an das Fenster anzuhängen den du über GetWindowLongPtr() auch wieder abfragen kannst. Damit kannst du beispielsweise ein Fenster durch ein C++ Objekt repräsentieren
Heißt, ich nutze jetzt immer diese Funktion mit der ID als Parameter wenn ich das Handle benötige?Zitat
Ja nein, eben genau nicht. Anstatt es zu sichern kannst du es damit einfach immer wenn dus brauchst abfragen.
Hm, also erstmal brauch ich keine neue Nachrichten Funktion mehr zu erstellen, wenn ich dies in einer Klasse bereits getan habe?Zitat
SetWindowLongPtr() erlaubt es dir über GWLP_USERDATA einen beliebigen Pointer an das Fenster anzuhängen den du über GetWindowLongPtr() auch wieder abfragen kannst. Damit kannst du beispielsweise ein Fenster durch ein C++ Objekt repräsentieren
In deinem Beispiel wird also ein Zeiger erstellt, mit dem dem Fenster die ThunkProc Funktion zugewiesen wird.
Glaube ich zumindest
Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von »dot« (09.08.2011, 00:05)
Werbeanzeige