Last updated: 15. 2.1998, 17:38
<*/NOWARN:F*>
MODULE PoePoem;
(*-------------------------------------------------
POEPOEM.C --- Demonstrates User-Defined Resource
(c) Charles Petzold, 1996
PoePoem.mod --- translation to Stony Brook Modula-2
(c) Peter Stadler, 1997
-------------------------------------------------*)
%IF WIN32 %THEN
<*/Resource:PoePoem.RES*>
%ELSE
%END
IMPORT h2d_PoePoem;
IMPORT WIN32;
IMPORT WINGDI;
IMPORT WINUSER;
IMPORT WINX;
IMPORT SYSTEM;
TYPE
TEXT = ARRAY[0..4000] OF CHAR;
PTEXT = POINTER TO TEXT;
VAR
szAppName : ARRAY[0..9] OF CHAR;
szCaption : ARRAY[0..34] OF CHAR;
hInst : WIN32.HINSTANCE;
hwnd : WIN32.HWND;
msg : WINUSER.MSG;
wc : WINUSER.WNDCLASSEX;
pText : PTEXT;
hResource : WIN32.HGLOBAL;
hScroll : WIN32.HWND;
iPosition : INTEGER;
cxChar : INTEGER;
cyChar : INTEGER;
cyClient : INTEGER;
iNumLines : INTEGER;
xScroll : INTEGER;
(*++++*****************************************************************)
PROCEDURE MaxInt (a,b : INTEGER) : INTEGER;
(**********************************************************************)
BEGIN
IF(a>b) THEN
RETURN a;
ELSE
RETURN b;
END;
END MaxInt;
(*++++*****************************************************************)
PROCEDURE MinInt (a,b : INTEGER) : INTEGER;
(**********************************************************************)
BEGIN
IF(a>b) THEN
RETURN b;
ELSE
RETURN a;
END;
END MinInt;
<*/PUSH*>
%IF WIN32 %THEN
<*/CALLS:WIN32SYSTEM*>
%ELSE
<*/CALLS:WINSYSTEM*>
%END
(*++++*****************************************************************)
PROCEDURE WndProc (hwnd : WIN32.HWND;
(**********************************************************************)
iMsg : WIN32.UINT;
wParam : WIN32.WPARAM;
lParam : WIN32.LPARAM) : WIN32.LRESULT [EXPORT];
VAR
szPoemRes : ARRAY[0..14] OF CHAR;
hdc : WIN32.HDC;
ps : WINUSER.PAINTSTRUCT;
rect : WIN32.RECT;
tm : WINGDI.TEXTMETRIC;
nH : INTEGER;
i : CARDINAL;
BEGIN
CASE (iMsg) OF
| WINUSER.WM_CREATE :
hdc := WINUSER.GetDC (hwnd);
WINGDI.GetTextMetrics (hdc, tm);
cxChar := tm.tmAveCharWidth;
cyChar := tm.tmHeight + tm.tmExternalLeading;
WINUSER.ReleaseDC (hwnd, hdc);
xScroll := WINUSER.GetSystemMetrics (WINUSER.SM_CXVSCROLL);
hScroll := WINUSER.CreateWindow ("scrollbar", "",
WINUSER.WS_CHILD BOR WINUSER.WS_VISIBLE BOR WINUSER.SBS_VERT,
0, 0, 0, 0,
hwnd, SYSTEM.CAST(WIN32.HMENU,1), hInst, NIL);
WINUSER.LoadString (hInst, h2d_PoePoem.IDS_POEMRES, szPoemRes, SIZE (szPoemRes));
hResource := WIN32.LoadResource (hInst,
WIN32.FindResource (hInst, szPoemRes, "TEXT"));
pText := SYSTEM.CAST(PTEXT,WIN32.LockResource (hResource));
iNumLines := 0;
FOR i := 0 TO LENGTH(pText^) DO
IF(pText^[i] = CHR(13)) AND(pText^[i+1]= CHR(10)) THEN
INC(iNumLines);
END;
END;
WINUSER.SetScrollRange (hScroll, WINUSER.SB_CTL, 0, iNumLines, FALSE);
WINUSER.SetScrollPos (hScroll, WINUSER.SB_CTL, 0, FALSE);
RETURN 0;
| WINUSER.WM_SIZE :
IF(cyClient = VAL(INTEGER,WINUSER.HIWORD(lParam))) THEN
nH := 1;
ELSE
nH := 0;
END;
WINUSER.MoveWindow (hScroll, VAL(INTEGER,WINUSER.LOWORD (lParam)) - xScroll, 0,
xScroll, nH, TRUE);
WINUSER.SetFocus (hwnd);
RETURN 0;
| WINUSER.WM_SETFOCUS :
WINUSER.SetFocus (hScroll);
RETURN 0;
| WINUSER.WM_VSCROLL :
CASE (wParam) OF
| WINUSER.SB_TOP :
iPosition := 0;
| WINUSER.SB_BOTTOM :
iPosition := iNumLines;
| WINUSER.SB_LINEUP :
iPosition := iPosition - 1;
| WINUSER.SB_LINEDOWN :
iPosition := iPosition + 1;
| WINUSER.SB_PAGEUP :
iPosition := iPosition - cyClient DIV cyChar;
| WINUSER.SB_PAGEDOWN :
iPosition := iPosition + cyClient DIV cyChar;
| WINUSER.SB_THUMBPOSITION :
iPosition := WINUSER.LOWORD (lParam);
ELSE
END;
iPosition := MaxInt (0, MinInt (iPosition, iNumLines));
IF (iPosition # WINUSER.GetScrollPos (hScroll, WINUSER.SB_CTL)) THEN
WINUSER.SetScrollPos (hScroll, WINUSER.SB_CTL, iPosition, TRUE);
WINUSER.InvalidateRect (hwnd, WINX.NIL_RECT, TRUE);
END;
RETURN 0;
| WINUSER.WM_PAINT :
hdc := WINUSER.BeginPaint (hwnd, ps);
pText := SYSTEM.CAST(PTEXT, WIN32.LockResource (hResource));
WINUSER.GetClientRect (hwnd, rect);
rect.left := rect.left + cxChar;
rect.top := rect.top + cyChar * (1 - iPosition);
WINUSER.DrawText (hdc, pText^, -1, rect, WINUSER.DT_EXTERNALLEADING);
WINUSER.EndPaint (hwnd, ps);
RETURN 0;
| WINUSER.WM_DESTROY :
WIN32.FreeResource (hResource);
WINUSER.PostQuitMessage (0);
RETURN 0;
ELSE
RETURN WINUSER.DefWindowProc (hwnd, iMsg, wParam, lParam);
END;
END WndProc;
<*/POP*>
(*++++*****************************************************************)
PROCEDURE InitApplication () : BOOLEAN;
(**********************************************************************)
BEGIN
WINUSER.LoadString (WINX.Instance, h2d_PoePoem.IDS_APPNAME, szAppName, SIZE(szAppName));
WINUSER.LoadString (WINX.Instance, h2d_PoePoem.IDS_CAPTION, szCaption, SIZE(szCaption));
wc.cbSize := SIZE(wc);
wc.style := WINUSER.CS_HREDRAW BOR WINUSER.CS_VREDRAW;
wc.lpfnWndProc := WndProc;
wc.cbClsExtra := 0;
wc.cbWndExtra := 0;
wc.hInstance := WINX.Instance;
wc.hIcon := WINUSER.LoadIcon (WINX.Instance, szAppName);
wc.hCursor := WINUSER.LoadCursor (NIL, WINUSER.IDC_ARROW^);
wc.hbrBackground := SYSTEM.CAST(WIN32.HBRUSH, WINGDI.GetStockObject(WINGDI.WHITE_BRUSH));
wc.lpszMenuName := NIL;
wc.lpszClassName := SYSTEM.ADR(szAppName);
wc.hIconSm := WINUSER.LoadIcon (WINX.Instance, szAppName);
RETURN WINUSER.RegisterClassEx(wc)#0;
END InitApplication;
(*++++*****************************************************************)
PROCEDURE InitMainWindow () : BOOLEAN;
(**********************************************************************)
BEGIN
hInst := WINX.Instance;
hwnd := WINUSER.CreateWindow (szAppName,
szCaption,
WINUSER.WS_OVERLAPPEDWINDOW BOR WINUSER.WS_CLIPCHILDREN,
WINUSER.CW_USEDEFAULT,
WINUSER.CW_USEDEFAULT,
WINUSER.CW_USEDEFAULT,
WINUSER.CW_USEDEFAULT,
NIL,
NIL,
WINX.Instance,
NIL);
WINUSER.ShowWindow (hwnd, WINUSER.SW_SHOWDEFAULT);
WINUSER.UpdateWindow (hwnd);
RETURN TRUE;
END InitMainWindow;
BEGIN
IF InitApplication() AND InitMainWindow() THEN
WHILE (WINUSER.GetMessage(msg,NIL,0,0)) DO
WINUSER.TranslateMessage(msg);
WINUSER.DispatchMessage(msg);
END;
END;
END PoePoem.