Window in Klassen Kapseln
-
Hallo
Ich packe grad die WinAPI Funktionen für ein Grundfenster in eine Klasse, und wollt Fragen, ob etwas dagegen spricht, und ob es schonmal jemand gemacht hat.
Denn ich hab Probleme die WndProc einzubinden.Ich hab die WinMain so gestaltet (bei Borland abgeguggt
)
main.cpp:#include "globals.h" // Entrypoint int APIENTRY WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmdLine, int CmdShow ) { WPARAM exitcode = 0; WinApp application( hInstance ); try { // Initialize application.init(); // Run exitcode = application.run(); } catch (...) { // TODO: exitcode = ( Exception ID ) // Show Message( Exception Text ) } // Finalize application.clear(); return exitcode; }die Globalen defines und includes..
globals.h#pragma once #define STRICT #define WIN32_LEAN_AND_MEAN #include <windows.h> #include <tchar.h>und meine Fensterklasse
winapp.h#include "globals.h" class WinApp { public: WinApp( HINSTANCE hInst ); ~WinApp(); LRESULT CALLBACK WndProc( HWND hWnd_, UINT msg_, WPARAM wParam_, LPARAM lParam_ ); void init(); WPARAM run(); void clear(); HINSTANCE hinstance; HWND hwnd; MSG msg; WNDCLASSEX window; LPCTSTR classname; };winapp.cpp
WinApp::WinApp( HINSTANCE hInst ) { hinstance = hInst; hwnd = 0; ZeroMemory( &msg, sizeof(msg) ); ZeroMemory( &window, sizeof(window) ); classname = _T("classname does not matter"); } WinApp::~WinApp(void) { clear(); } LRESULT CALLBACK WinApp::WndProc( HWND hWnd_, UINT msg_, WPARAM wParam_, LPARAM lParam_ ) { switch( msg_ ) { case WM_DESTROY: { PostQuitMessage( 0 ); return 0; } default: return DefWindowProc( hWnd_, msg_, wParam_, lParam_ ); } } void WinApp::init() { window.cbSize = sizeof( WNDCLASSEX ); window.style = CS_CLASSDC; window.lpfnWndProc = WndProc; // <---HIER!!! // window.cbClsExtra = 0; // window.cbWndExtra = 0; window.hInstance = hinstance; // window.hIcon = 0; // window.hCursor = 0; window.hbrBackground= (HBRUSH)GetStockObject(WHITE_BRUSH); // window.lpszMenuName = 0; window.lpszClassName= classname; // window.hIconSm = 0; if( !RegisterClassEx( &window ) ) // TODO Throw return; hwnd = CreateWindowEx( 0, classname, _T(""), WS_POPUPWINDOW | WS_VISIBLE, 10, 10, 400, 400, GetDesktopWindow(), 0, hinstance, 0 ); if( !hwnd ) // TODO Throw return; ShowWindow( hwnd, SW_SHOWDEFAULT ); UpdateWindow( hwnd ); return; } WPARAM WinApp::run() { while( msg.message != WM_QUIT ) { if( PeekMessage( &msg, 0, 0, 0, PM_REMOVE ) ) { TranslateMessage( &msg ); DispatchMessage( &msg ); } else { // TODO Application Goes Here } } return msg.wParam; } void WinApp::clear() { if( GetClassInfoEx( hinstance, classname, &window ) ) UnregisterClass( classname, hinstance ); }Das ergibt folgende Fehler:
...error C3867: 'WinApp::WndProc': function call missing argument list; use '&WinApp::WndProc' to create a pointer to member
...error C2440: '=' : cannot convert from 'LRESULT (__stdcall WinApp::* )(HWND,UINT,WPARAM,LPARAM)' to 'WNDPROC'
There is no context in which this conversion is possibleHab nun allso ein & vor WndProc gesetzt, dann kam dies:
...error C2276: '&' : illegal operation on bound member function expression
Kann die WndProc demzufolge keine Memberfunktion sein?
Ich probiers nun schon den zweiten Abend in Folge,
und wär um jede Hilfe frohDanke im voraus..
-
this pointer -> etc etc
wenn du näheres wissen willst winapi faq lesen
http://www.c-plusplus.net/forum/viewtopic-var-t-is-148410.html
-
danke für die links, die forensuche ergab irgendwie nichts.
also wenn ichs static mach gehts.
und da es das hauptfenster ist, brauch ich nur eins.
sollt ich dann ein singleton draus machen?
-
Hmm ich find Vertexwahns umsetzung nicht sooo schlecht. d.h. : http://turing.fh-landshut.de/~jamann/IMB/IMB.html
-
hmm auf der Seite find ich nichts, was hier helfen könnte

-
(D)Evil schrieb:
Hmm ich find Vertexwahns umsetzung nicht sooo schlecht. d.h. : http://turing.fh-landshut.de/~jamann/IMB/IMB.html
ist für seine zwecke vollkommen überzogen und bei dem ganzen overhead da krieg ich kopfschmerzen da wird für eine winow message das ganze durch 10 funktionen durchgereicht die ganzen jmps machen das auch ned gerade schneller...
-
Lol... du sollst dir einfach nur mal angucken wie Vertex es gemacht hat... also die kapselung... mehr nciht... daran kannst du dein konzept evt. anpassen.. manman man
-
this pointer -> etc etc
wenn du näheres wissen willst winapi faq lesen
http://www.c-plusplus.net/forum/viewtopic-var-t-is-148410.html
this pointer -> etc etc
wenn du näheres wissen willst winapi faq lesen
http://www.c-plusplus.net/forum/viewtopic-var-t-is-148410.html
this pointer -> etc etc
wenn du näheres wissen willst winapi faq lesen
http://www.c-plusplus.net/forum/viewtopic-var-t-is-148410.html
-
Warum verwendest Du nicht MFC oder sonstige "Frameworks". Die haben genau das gemacht was Du auch machen willst...
-
Weil ich ein armer Student und Hobbyprogrammierer bin und nur die Express Editition habe.
Ausserdem brauch ich den ganzen Overhead nicht, sondern einfach eine simple Anwendung mit weissem Fenster ohne Titelleiste, Menu, Buttons, etc pp
-
Windows-User schrieb:
Windows-User schrieb:
danke für die links, die forensuche ergab irgendwie nichts.
also wenn ichs static mach gehts. //<--- OK! Erledigt!
und da es das hauptfenster ist, brauch ich nur eins.
sollt ich dann ein singleton draus machen? ??? ??? ???@fae: fast so hilfsbereit wie tggc

hm komm ja vergleich mich nicht mit irgendeinem dummen forum troll...meine antwort war doch hilfreich...bot 1 gute lösunghsmöglichkeit zum direkten copy & paste an und einen link z ueiner 4 seitigen diskussion mit mehreren anderen lösungsmöglichkeiten an....aber wenn dir noch was unklar ist kannst du ja gerne fragen

-
Ok sorry, war unfair dich mit dem grössenwahnsinnigen spiele progger zu vergleichen
Also, wenn ich nur ein Grundfenster hab..brauch ich dann die Methode mit den this Zeigern?
Oder kann ich ein Singleton machen?
Oder wie mach ichs am "besten", nicht im Sinn von elegannt. Es soll ja nicht auf die Performance drücken..
Sonst mach ich einfach eine lokale Proc ohne Scope, so wie ich das Problem am Anfang umging.
-
ok danke
ich habs jetzt abgetippt, und sogar geschnallt, mit dem this, pointer GetWindowLongPtr etc.
Funzt auch!Aber ich bin sicher, TGGC hat in seinen brillianten Codes eine elegantere Lösung!
-
Back2Topic: PLEAZZZE HELP MEEE!!!!¨¨¨
Ok ich hab gedacht es geht, aber falsch gedacht.
folgendes geht ned:LRESULT CALLBACK mainwin::WndProc( HWND hWnd_, UINT msg_, WPARAM wParam_, LPARAM lParam_ ) { mainwin* this_ = (mainwin*) GetWindowLongPtr( hWnd_, GWL_USERDATA ); switch( msg_ ) { case WM_CREATE: { this_ = (mainwin*) ( (LPCREATESTRUCT)lParam_)->lpCreateParams; SetWindowLongPtr( hWnd_, GWL_USERDATA, (LONG)this_ ); break; } case WM_PAINT: { PAINTSTRUCT ps; HDC hDC; LPCWSTR text = "blabla"; if( hDC = BeginPaint( this_->hwnd, &ps ) ) { ///<---Hier //TextOut( hDC, 0, 0, text, sizeof(text) ); EndPaint( this_->hwnd, &ps ); }es kompiliert zwar einwandfrei, aber steigt aus mit
Unhandled exception at 0x00411914 in WinApp.exe: 0xC0000005: Access violation reading location 0x0000003c.
und zwar beim ersten EInsatz von this_
[emotionen]Je m'enerve! Püree!![/emotionen]
Vorhin gings, was mach ich falsch???
*zwerveifel*
-
Windows-User schrieb:
Weil ich ein armer Student und Hobbyprogrammierer bin und nur die Express Editition habe.
Das ist ja kein Grund...
1. Mit der Express-Version kann man WTL und sonstige Frameworks verwenden (wxWidgeds)
2. Als Student bekommst Du von Deiner Uni/FH ein vollständiges VS Academic kostenlos gestellt (musst nur fragen)
-
Hast Du es mal durchdebuggt? Kommst Du durch WM_CREATE durch? Was soll den das viele casten?
Warum willst Du das Rad neu erfinden?
-
Ja, die WM_CREATE wird aufgerufen. Die Variblen sind aber alle unused=??? Auch hWnd_ .

Hab das casten abgetippt von da: http://www.c-plusplus.net/forum/viewtopic-var-t-is-148410-and-start-is-0-and-postdays-is-0-and-postorder-is-asc-and-highlight-is-.html Mein VS motzt auch deswegen.
Wieso Rad neu erfinden? Ich will doch nur mein eintes einzigstes Fenster auslagern, damit ich es wiederverwenden kann, und die WinMain aufgeräumter aussieht. Und jetzt ist es auch eine Frage des Ehrgeizes, dass ich das schaffen möcht.
-
Hast Du das Beispiel dort verstanden??? Wie sieht DEIN CreateWindow(Ex) aus??? In Deinem ersten Beispiel hast Du da was komplett falsch gemacht (this fehlt)...
Aber wie gesagt, wenn Du das (simple) Beispiel nicht verstanden hast, dann solltest Du dich da mal zuerst reindenken, bevor Du was eigenes machst...
-
Huch
ich hab inzwischen folgendes in der MSDN rausgefunden
bei GetWindowLongPtr:
Remarks
Reserve extra window memory by specifying a nonzero value in the cbWndExtra member of the WNDCLASSEX structure used with the RegisterClassEx function.
also bei cbWndExtra sollte man bytes reservieren, geht aber auch ohne (?)
bei CreateWindowEx:
lpParam
[in] Pointer to a value to be passed to the window through the CREATESTRUCT structure passed in the lParam member of the WM_CREATE message sent to the created window by this function before it returns. May be NULL if no additional data is needed.also das this im Beispiel hab ich nun zugefügt. jetzt geht es!
Ich habs jetzt geschnallt.
Ich hab mich doch auch gewundert, woher der Pointer im lParam des WM_CREATE kommen sollte. *kling* der Groschen ist nun gefallen.
Wenn ich nun noch die Casts wegkriege, bin ich glücklich.
Danke vielmals, du hast mir sehr geholfen.
-
Windows-User schrieb:
Wenn ich nun noch die Casts wegkriege, bin ich glücklich.
DIe bekommst Du nicht weg... sollten aber auch alle korrekt sein...