[C] WINAPI: Fenster mit fixer Größe

Micha1701

Cadet 4th Year
Registriert
März 2007
Beiträge
113
Hallo zusammen,

ich fang gerade an mich mit der WIN API zu beschäftigen und daher gibts für mich natürlich in den Anfängen viel neues zu erforschen... :-)

Nun ja, auf jeden Fall möchte ich ein Anwendungsfenster mit einer fixen Größe von 800x600 Pixeln im Anwendungsbereich öffnen. Bis jetzt hab ich noch nicht rausgefunden, wie man denn elegant ein Fenster mit einem Anwendungsbereich von 800x600 öffnen kann. Man gibt ja nur die äußeren Maßen an. GetSystemMetrics() war ein guter Kandidat um mir bei der Größenermittlung zu helfen, aber anscheinend ist das Fenster immnoch ein paar Pixel zu klein um tatsächlich 800x600 Pixel zu haben.

Code:
für die Breite: 800 + (GetSystemMetrics(SM_CXBORDER) * 2);
für die Höhe:  600 + GetSystemMetrics(SM_CYBORDER) + GetSystemMetrics(SM_CYSIZE);

wie kann man das besser machen?

Ach ja, welchen Style oder welche Klasse muß das Fenster haben um in der Größe nicht veränderbar zu sein?

Vielen dank für die Hilfe!
 
Hallo,

das ist kein Problem :) Wie du schon vermutest, gibt es einen (wenn man es so nennen will) eleganten Weg. Die Lösung lautet: AdjustWindowRectEx()

Diese Funktion erwartet als ersten Parameter die Adresse einer RECT-Struktur, in der du vorher die gewünschten Koordinaten des Clientbereichs einträgst. Als zweiten und vierten Parameter musst du die Styleflags deines Fensters angeben, damit die Funktion auch weiß, ob dein Fenster z.B. einen Rahmen hat, um die richtigen Werte entsprechend berechnen zu können. Wenn dein Fenster kein Menü hat (sehr wahrscheinlich, da du ja noch in den Anfängen bist), kannst du als dritten Parameter einfach 0 eintragen.

Nach Rückkehr der Funktion stehen in der RECT-Struktur, deren Adresse du am Anfang übergeben hast, die richtigen Werte, also die Größen, die der gesamte Anwendungsbereich haben muss, damit der Clientbereich anschließend die gewünschte Größe hat :p

Du könntest diese Berechnung in der WinMain machen, bevor du CreateWindow(Ex) aufrufst, und die neuen Werte dann dieser Funktion übergeben, oder aber du lässt das Fenster erst normal erstellen und änderst seine Größe anschließend z.B. als Reaktion auf WM_CREATE. Letzteres könnte ungefähr so aussehen:


Code:
[COLOR="Green"]//Fensterrechteck mit den gewünschten Werten[/COLOR]
RECT rc = {0, 0, 800, 600};
 
[COLOR="Green"]//Styleflags des Fensters abfragen[/COLOR]
DWORD style    = GetWindowLongPtrW(hWnd, GWL_STYLE);  
DWORD styleEx  = GetWindowLongPtrW(hWnd, GWL_EXSTYLE);     
 
[COLOR="green"]//korrekte Fenstergröße berechnen und in rc speichern[/COLOR]
AdjustWindowRectEx(&rc, style, 0, styleEx);  
 
[COLOR="green"]//Die nächsten beiden Zeilen sind optional. Sie bewirken eine Zentrierung des Fensters
//in der Bildschirmmitte, da es sich sonst in der obersten linken Ecke befindet[/COLOR]
int centerX = GetSystemMetrics(SM_CXFULLSCREEN)/2 - (rc.right-rc.left)/2;
int centerY = GetSystemMetrics(SM_CYFULLSCREEN)/2 - (rc.bottom-rc.top)/2;
 
[COLOR="green"]//Anschließend das Fenster anhand der errechneten Koordinaten neu positionieren[/COLOR]
MoveWindow(hWnd, centerX, centerY, rc.right-rc.left, rc.bottom-rc.top, true);
 
ShowWindow(hWnd, SW_SHOWNORMAL);

Falls du Fragen hast oder etwas nicht funktioniert, melde dich bitte wieder ;)

ph4nt0m
 
Danke!

Das hat super funktioniert.

Weißt Du auch, wie man das vergößern/verkleinern eines Fensters verhindern kann? Es soll halt eine fixe Größe von 800x600 Pixeln haben und nicht verändert werden...
 
Also das Styleflag, welches das vergrößern ermöglicht, lautet WS_THICKFRAME. Da WS_OVERLAPPEDWINDOW dieses beinhaltet, ist die Größe deines Fensters wohl veränderbar. Du könntest daher z.B. einfach alle Flags, die WS_OVERLAPPEDWINDOW beinhaltet, manuell kombinieren und dabei WS_THICKFRAME weglassen:
Code:
WS_OVERLAPPED | WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX | WS_MAXIMIZEBOX

ph4nt0m
 
Vielen Dank!

Kaum macht mans richtig schon funktionierts...

Hab noch WS_MAXIMIZEBOX entfernt, damit mans nicht auf Fullscreen vergrößern kann.
Jetzt ist das Fenster genau so, wie ichs haben wollte.

Hätt mir ja auch mal einfallen könne die Styleflags durchzulesen... :freak:
 
Das ist doch kein Problem. Deine Fragen waren präzise und du hast alle nötigen Angaben gemacht, damit man dir schnell weiterhelfen konnte. Und den Umgang mit der MSDN Library lernt man mit der Zeit :)

ph4nt0m
 
Zurück
Oben