|

Grundlagen der Grafikprogrammierung - Teil 3 - by Delax
Jetzt steigen wir tiefer in die Windows Programmierung ein und schauen uns
die Windows Klassen an.
Jedes Fenster egal ob Dialog Box, Message Box oder Vollbild benötigt eine Windows Klasse. Eine Klasse definiert das Fenster und seine Attribute. Also das Aussehen, das Verhalten und sonst alles Mögliche. Natürlich gibt es (wie bei fast allem in Windows) Standard-Klassen, aber im wirklichen Leben werdet ihr wohl für jede Applikation eine eigene Klasse definieren.
Ich will jetzt nicht lang und breit über Windows Klassen und deren Möglichkeiten reden. Erstens Mal ist das Thema sehr umfangreich und zweitens Mal braucht ihr nicht wirklich alles über sie zu wissen. Im Grunde werden wir nur mal darauf eingehen, das ihr wisst, was ihr da eigentlich macht.
Wir hatten das letzte Mal ein kurzes und kleines "Hello World" Programm - bei FPC liegt
ein etwas umfangreicheres "Hello World" bei und das schauen wir uns jetzt einmal genauer an:
{
$Id: winhello.pp,v 1.1 1998/12/20 22:23:54 peter Exp $
Copyright (c) 1996 by Charlie Calvert
Modifications by Florian Klaempfl
Standard Windows API application written in Object Pascal.
No VCL code included. This is all done on the Windows API
level.
}
{$APPTYPE GUI}
{$MODE DELPHI}
program WinHello;
uses
Strings, Windows;
const
AppName = 'WinHello';
function WindowProc(Window: HWnd; AMessage, WParam,
LParam: Longint): Longint; stdcall; export;
var
dc : hdc;
ps : paintstruct;
r : rect;
begin
WindowProc := 0;
case AMessage of
wm_paint:
begin
dc:=BeginPaint(Window,@ps);
GetClientRect(Window,@r);
DrawText(dc,'Hello world by Free Pascal',-1,@r,
DT_SINGLELINE or DT_CENTER or DT_VCENTER);
EndPaint(Window,ps);
Exit;
end;
wm_Destroy:
begin
PostQuitMessage(0);
Exit;
end;
end;
WindowProc := DefWindowProc(Window, AMessage, WParam, LParam);
end;
{ Register the Window Class }
function WinRegister: Boolean;
var
WindowClass: WndClass;
begin
WindowClass.Style := cs_hRedraw or cs_vRedraw;
WindowClass.lpfnWndProc := WndProc(@WindowProc);
WindowClass.cbClsExtra := 0;
WindowClass.cbWndExtra := 0;
WindowClass.hInstance := system.MainInstance;
WindowClass.hIcon := LoadIcon(0, idi_Application);
WindowClass.hCursor := LoadCursor(0, idc_Arrow);
WindowClass.hbrBackground := GetStockObject(WHITE_BRUSH);
WindowClass.lpszMenuName := nil;
WindowClass.lpszClassName := AppName;
Result := RegisterClass(WindowClass) <> 0;
end;
{ Create the Window Class }
function WinCreate: HWnd;
var
hWindow: HWnd;
begin
hWindow := CreateWindow(AppName, 'Hello world program',
ws_OverlappedWindow, cw_UseDefault, cw_UseDefault,
cw_UseDefault, cw_UseDefault, 0, 0, system.MainInstance, nil);
if hWindow <> 0 then begin
ShowWindow(hWindow, CmdShow);
UpdateWindow(hWindow);
end;
Result := hWindow;
end;
var
AMessage: Msg;
hWindow: HWnd;
begin
if not WinRegister then begin
MessageBox(0, 'Register failed', nil, mb_Ok);
Exit;
end;
hWindow := WinCreate;
if longint(hWindow) = 0 then begin
MessageBox(0, 'WinCreate failed', nil, mb_Ok);
Exit;
end;
while GetMessage(@AMessage, 0, 0, 0) do begin
TranslateMessage(AMessage);
DispatchMessage(AMessage);
end;
Halt(AMessage.wParam);
end.
{
$Log: winhello.pp,v $
Revision 1.1 1998/12/20 22:23:54 peter
* new name
}
Hier als Datei zum download
So. Keine Panik, schaut euch erst einmal nur den Part mit der Überschrift "Register the Windows
Class" an. Dort seht ihr wie die Struktur WindowClass mit Werten versorgt wird. Gehen wir die
einzelnen Punkte einmal durch:
style: Dieses Feld hat Tonnen von Flags, die durch ein OR verbunden werden können. Ein paar Beispiele: CS_REDRAW (zeichnet das Fenster neu, wenn es der Nutzer bewegt); CS_VREDRAW / CS_HREDRAW (zeichnet das Fenster neu, wenn der Nutzer seine Größe verändert hat); CS_OWNDC (wichtig, bindet einen eigenen Device Context an unser Fenster - mehr dazu später); CS_NOCLOSE (deaktiviert das "schließen" Feld am Fenster); CS_DBLCLKS (sendet eine Nachricht wenn der User in unserem Fenster doppelklickt). Das sind nur einige, wenn ihr mehr wollt: nachschlagen ;).
lpfnWndProc: Das ist ein Pointer zu unserer WndProc Routine. Erinnert ihr euch noch? Im zweiten Teil sagte ich Windows sei Event Driven und jene Nachrichten würden auch an euer Programm geschickt und ihr bräuchtet eine Schnittstelle? Nun, diese Schnittstelle ist WndProc. Dort werdet ihr auf jene Events reagieren, doch jene Prozedur nehmen wir uns irgendwann vor ;) Im Moment genügt es zu wissen, daß man hier folgendes einträgt: WindowClass.lpfnWndProc := WndProc(@WindowProc);
cbClsExtra und cbWndExtra: brauchen wir nicht, setzen wir auf 0: winclass.cbClsExtra := 0; und winclass.cbWndExtra := 0;.
hInstance: siehe zweiter Teil. WindowClass.hInstance := system.MainInstance;
hIcon: Juchu, unser Icon ;) Wir nehmen erst mal das 0815 Icon: WindowClass.hIcon := LoadIcon(0, idi_Application);
hCursor: Unser Cursor. Auch hier Standart WindowClass.hCursor := LoadCursor(0, idc_Arrow);
hbrBackground: Das ist die Hintergrundfarbe eurer Applikation. Wäre aber zu einfach nur eine Farbe zu definieren, nein, da das GDI (Graphics Device Interfae) kompliziert ist, müssen wir auch die Art eintragen mit der wir sie haben wollen. WindowClass.hbrBackground := GetStockObject(WHITE_BRUSH);
lpszMenuName: Das ist der Name unseres Menus (falls wir eins wollen). Im Moment nicht, also: WindowClass.lpszMenuName := nil;
lpszClassName: So, jetzt benennen wir unsere soeben definierte Klasse. WindowClass.lpszClassName := AppName;. Und damit taufe ich dich auf den Namen "WinHello"...oder so ;)
Und das ist es! Das ist unsere Windows Klasse! Hier noch einmal im ganzen:
WindowClass.Style := cs_hRedraw or cs_vRedraw;
WindowClass.lpfnWndProc := WndProc(@WindowProc);
WindowClass.cbClsExtra := 0;
WindowClass.cbWndExtra := 0;
WindowClass.hInstance := system.MainInstance;
WindowClass.hIcon := LoadIcon(0, idi_Application);
WindowClass.hCursor := LoadCursor(0, idc_Arrow);
WindowClass.hbrBackground := GetStockObject(WHITE_BRUSH);
WindowClass.lpszMenuName := nil;
WindowClass.lpszClassName := AppName;
Jaja, schon klar, das ist trockenes Material, man kann nicht damit herumspielen und wenn es alleine da steht kompiliert es sich nicht, aber das ist wichtig zu wissen! Kein Windows Programm ohne diesen Kram! Also, zieht euch eine Fanta 'rein und versucht zumindest zu erahnen worum es hier geht. Das nächste Mal erfahrt ihr, was ihr mit der eben definierten Struktur anfangen könnt.
Bis done!
Delax/ Sundancer Inc.
[delax@sundancerinc.de]
Back to previous page
|