home *** CD-ROM | disk | FTP | other *** search
-
- {*******************************************************}
- { }
- { Turbo Pascal Version 6.0 }
- { Turbo Vision Unit }
- { }
- { Copyright (c) 1990 Borland International }
- { }
- {*******************************************************}
-
- unit App;
-
- {$F+,O+,S-,X+,D-}
-
- interface
-
- uses Objects, Drivers, Memory, HistList, Views, Menus;
-
- const
-
- { TApplication palette entries }
-
- apColor = 0;
- apBlackWhite = 1;
- apMonochrome = 2;
-
- { TApplication palettes }
-
- CColor =
- #$71#$70#$78#$74#$20#$28#$24#$17#$1F#$1A#$31#$31#$1E#$71#$00 +
- #$37#$3F#$3A#$13#$13#$3E#$21#$00#$70#$7F#$7A#$13#$13#$70#$7F#$00 +
- #$70#$7F#$7A#$13#$13#$70#$70#$7F#$7E#$20#$2B#$2F#$78#$2E#$70#$30 +
- #$3F#$3E#$1F#$2F#$1A#$20#$72#$31#$31#$30#$2F#$3E#$31#$13#$00#$00;
-
- CBlackWhite =
- #$70#$70#$78#$7F#$07#$07#$0F#$07#$0F#$07#$70#$70#$07#$70#$00 +
- #$07#$0F#$07#$70#$70#$07#$70#$00#$70#$7F#$7F#$70#$07#$70#$07#$00 +
- #$70#$7F#$7F#$70#$07#$70#$70#$7F#$7F#$07#$0F#$0F#$78#$0F#$78#$07 +
- #$0F#$0F#$0F#$70#$0F#$07#$70#$70#$70#$07#$70#$0F#$07#$07#$00#$00;
-
- CMonochrome =
- #$70#$07#$07#$0F#$70#$70#$70#$07#$0F#$07#$70#$70#$07#$70#$00 +
- #$07#$0F#$07#$70#$70#$07#$70#$00#$70#$70#$70#$07#$07#$70#$07#$00 +
- #$70#$70#$70#$07#$07#$70#$70#$70#$0F#$07#$07#$0F#$70#$0F#$70#$07 +
- #$0F#$0F#$07#$70#$07#$07#$70#$07#$07#$07#$70#$0F#$07#$07#$00#$00;
-
-
- { TBackground palette }
-
- CBackground = #1;
-
- type
-
- { TBackground object }
-
- PBackground = ^TBackground;
- TBackground = object(TView)
- Pattern: Char;
- constructor Init(var Bounds: TRect; APattern: Char);
- constructor Load(var S: TStream);
- procedure Draw; virtual;
- function GetPalette: PPalette; virtual;
- procedure Store(var S: TStream);
- end;
-
- { TDeskTop object }
-
- PDeskTop = ^TDeskTop;
- TDeskTop = object(TGroup)
- Background: PBackground;
- constructor Init(var Bounds: TRect);
- procedure Cascade(var R: TRect);
- procedure HandleEvent(var Event: TEvent); virtual;
- procedure InitBackground; virtual;
- procedure Tile(var R: TRect);
- procedure TileError; virtual;
- end;
-
- { TProgram object }
-
- { Palette layout }
- { 1 = TBackground }
- { 2- 7 = TMenuView and TStatusLine }
- { 8-15 = TWindow(Blue) }
- { 16-23 = TWindow(Cyan) }
- { 24-31 = TWindow(Gray) }
- { 32-63 = TDialog }
-
- PProgram = ^TProgram;
- TProgram = object(TGroup)
- constructor Init;
- destructor Done; virtual;
- procedure GetEvent(var Event: TEvent); virtual;
- function GetPalette: PPalette; virtual;
- procedure HandleEvent(var Event: TEvent); virtual;
- procedure Idle; virtual;
- procedure InitDeskTop; virtual;
- procedure InitMenuBar; virtual;
- procedure InitScreen; virtual;
- procedure InitStatusLine; virtual;
- procedure OutOfMemory; virtual;
- procedure PutEvent(var Event: TEvent); virtual;
- procedure Run; virtual;
- procedure SetScreenMode(Mode: Word);
- function ValidView(P: PView): PView;
- end;
-
- { TApplication object }
-
- PApplication = ^TApplication;
- TApplication = object(TProgram)
- constructor Init;
- destructor Done; virtual;
- end;
-
- { App registration procedure }
-
- procedure RegisterApp;
-
- const
-
- { Public variables }
-
- Application: PProgram = nil;
- DeskTop: PDeskTop = nil;
- StatusLine: PStatusLine = nil;
- MenuBar: PMenuView = nil;
- AppPalette: Integer = apColor;
-
- { Stream registration records }
-
- RBackground: TStreamRec = (
- ObjType: 30;
- VmtLink: Ofs(TypeOf(TBackground)^);
- Load: @TBackground.Load;
- Store: @TBackground.Store);
-
- RDeskTop: TStreamRec = (
- ObjType: 31;
- VmtLink: Ofs(TypeOf(TDeskTop)^);
- Load: @TDeskTop.Load;
- Store: @TDeskTop.Store);
-
- implementation
-
- const
-
- { Private variables }
-
- Pending: TEvent = (What: evNothing);
-
- { TBackground }
-
- constructor TBackground.Init(var Bounds: TRect; APattern: Char);
- begin
- TView.Init(Bounds);
- GrowMode := gfGrowHiX + gfGrowHiY;
- Pattern := APattern;
- end;
-
- constructor TBackground.Load(var S: TStream);
- begin
- TView.Load(S);
- S.Read(Pattern, SizeOf(Pattern));
- end;
-
- procedure TBackground.Draw;
- var
- B: TDrawBuffer;
- begin
- MoveChar(B, Pattern, GetColor($01), Size.X);
- WriteLine(0, 0, Size.X, Size.Y, B);
- end;
-
- function TBackground.GetPalette: PPalette;
- const
- P: string[Length(CBackground)] = CBackground;
- begin
- GetPalette := @P;
- end;
-
- procedure TBackground.Store(var S: TStream);
- begin
- TView.Store(S);
- S.Write(Pattern, SizeOf(Pattern));
- end;
-
- { TDeskTop object }
-
- constructor TDeskTop.Init(var Bounds: TRect);
- begin
- TGroup.Init(Bounds);
- GrowMode := gfGrowHiX + gfGrowHiY;
- InitBackground;
- if Background <> nil then Insert(Background);
- end;
-
- function Tileable(P: PView): Boolean;
- begin
- Tileable := (P^.Options and ofTileable <> 0) and
- (P^.State and sfVisible <> 0);
- end;
-
- procedure TDeskTop.Cascade(var R: TRect);
- var
- CascadeNum: Integer;
- LastView: PView;
- Min, Max: TPoint;
-
-
- procedure DoCount(P: PView); far;
- begin
- if Tileable(P) then
- begin
- Inc(CascadeNum);
- LastView := P;
- end;
- end;
-
- procedure DoCascade(P: PView); far;
- var
- NR: TRect;
- begin
- if Tileable(P) and (CascadeNum >= 0) then
- begin
- NR.Copy(R);
- Inc(NR.A.X, CascadeNum); Inc(NR.A.Y, CascadeNum);
- P^.Locate(NR);
- Dec(CascadeNum);
- end;
- end;
-
- begin
- CascadeNum := 0;
- ForEach(@DoCount);
- if CascadeNum > 0 then
- begin
- LastView^.SizeLimits(Min, Max);
- if (Min.X > R.B.X - R.A.X - CascadeNum) or
- (Min.Y > R.B.Y - R.A.Y - CascadeNum) then TileError
- else
- begin
- Dec(CascadeNum);
- Lock;
- ForEach(@DoCascade);
- Unlock;
- end;
- end;
- end;
-
- procedure TDeskTop.HandleEvent(var Event: TEvent);
- begin
- TGroup.HandleEvent(Event);
- if Event.What = evCommand then
- begin
- case Event.Command of
- cmNext: SelectNext(False);
- cmPrev: Current^.PutInFrontOf(Background);
- else
- Exit;
- end;
- ClearEvent(Event);
- end;
- end;
-
- procedure TDeskTop.InitBackground;
- var
- R: TRect;
- begin
- GetExtent(R);
- New(Background, Init(R, #176));
- end;
-
- function ISqr(X: Integer): Integer; assembler;
- asm
- MOV CX,X
- MOV BX,0
- @@1: INC BX
- MOV AX,BX
- IMUL AX
- CMP AX,CX
- JLE @@1
- MOV AX,BX
- DEC AX
- end;
-
- procedure MostEqualDivisors(N: Integer; var X, Y: Integer);
- var
- I: Integer;
- begin
- I := ISqr(N);
- if ((N mod I) <> 0) then
- if (N mod (I+1)) = 0 then Inc(I);
- if I < (N div I) then I := N div I;
- X := N div I;
- Y := I;
- end;
-
- procedure TDeskTop.Tile(var R: TRect);
- var
- NumCols, NumRows, NumTileable, LeftOver, TileNum: Integer;
-
- procedure DoCountTileable(P: PView); far;
- begin
- if Tileable(P) then Inc(NumTileable);
- end;
-
- function DividerLoc(Lo, Hi, Num, Pos: Integer): Integer;
- begin
- DividerLoc := LongDiv(LongMul(Hi - Lo, Pos), Num) + Lo;
- end;
-
- procedure CalcTileRect(Pos: Integer; var NR: TRect);
- var
- X,Y,D: Integer;
- begin
- D := (NumCols - LeftOver) * NumRows;
- if Pos < D then
- begin
- X := Pos div NumRows;
- Y := Pos mod NumRows;
- end else
- begin
- X := (Pos - D) div (NumRows + 1) + (NumCols - LeftOver);
- Y := (Pos - D) mod (NumRows + 1);
- end;
- NR.A.X := DividerLoc(R.A.X, R.B.X, NumCols, X);
- NR.B.X := DividerLoc(R.A.X, R.B.X, NumCols, X+1);
- if Pos >= D then
- begin
- NR.A.Y := DividerLoc(R.A.Y, R.B.Y, NumRows+1, Y);
- NR.B.Y := DividerLoc(R.A.Y, R.B.Y, NumRows+1, Y+1);
- end else
- begin
- NR.A.Y := DividerLoc(R.A.Y, R.B.Y, NumRows, Y);
- NR.B.Y := DividerLoc(R.A.Y, R.B.Y, NumRows, Y+1);
- end;
- end;
-
- procedure DoTile(P: PView); far;
- var
- R: TRect;
- begin
- if Tileable(P) then
- begin
- CalcTileRect(TileNum, R);
- P^.Locate(R);
- Dec(TileNum);
- end;
- end;
-
- begin
- NumTileable := 0;
- ForEach(@DoCountTileable);
- if NumTileable > 0 then
- begin
- MostEqualDivisors(NumTileable, NumCols, NumRows);
- if ((R.B.X - R.A.X) div NumCols = 0) or
- ((R.B.Y - R.A.Y) div NumRows = 0) then TileError
- else
- begin
- LeftOver := NumTileable mod NumCols;
- TileNum := NumTileable-1;
- Lock;
- ForEach(@DoTile);
- Unlock;
- end;
- end;
- end;
-
- procedure TDesktop.TileError;
- begin
- end;
-
- { TProgram }
-
- constructor TProgram.Init;
- var
- R: TRect;
- begin
- Application := @Self;
- InitScreen;
- R.Assign(0, 0, ScreenWidth, ScreenHeight);
- TGroup.Init(R);
- State := sfVisible + sfSelected + sfFocused + sfModal + sfExposed;
- Options := 0;
- Buffer := ScreenBuffer;
- InitDeskTop;
- InitStatusLine;
- InitMenuBar;
- if DeskTop <> nil then Insert(DeskTop);
- if StatusLine <> nil then Insert(StatusLine);
- if MenuBar <> nil then Insert(MenuBar);
- end;
-
- destructor TProgram.Done;
- begin
- if DeskTop <> nil then Dispose(DeskTop, Done);
- if MenuBar <> nil then Dispose(MenuBar, Done);
- if StatusLine <> nil then Dispose(StatusLine, Done);
- Application := nil;
- end;
-
- procedure TProgram.GetEvent(var Event: TEvent);
- var
- R: TRect;
-
- function ContainsMouse(P: PView): Boolean; far;
- begin
- ContainsMouse := (P^.State and sfVisible <> 0) and
- P^.MouseInView(Event.Where);
- end;
-
- begin
- if Pending.What <> evNothing then
- begin
- Event := Pending;
- Pending.What := evNothing;
- end else
- begin
- GetMouseEvent(Event);
- if Event.What = evNothing then
- begin
- GetKeyEvent(Event);
- if Event.What = evNothing then Idle;
- end;
- end;
- if StatusLine <> nil then
- if (Event.What and evKeyDown <> 0) or
- (Event.What and evMouseDown <> 0) and
- (FirstThat(@ContainsMouse) = PView(StatusLine)) then
- StatusLine^.HandleEvent(Event);
- end;
-
- function TProgram.GetPalette: PPalette;
- const
- P: array[apColor..apMonochrome] of string[Length(CColor)] =
- (CColor, CBlackWhite, CMonochrome);
- begin
- GetPalette := @P[AppPalette];
- end;
-
- procedure TProgram.HandleEvent(var Event: TEvent);
- var
- I: Word;
- C: Char;
- begin
- if Event.What = evKeyDown then
- begin
- C := GetAltChar(Event.KeyCode);
- if (C >= '1') and (C <= '9') then
- if Message(DeskTop, evBroadCast, cmSelectWindowNum,
- Pointer(Byte(C) - $30)) <> nil then ClearEvent(Event);
- end;
- TGroup.HandleEvent(Event);
- if Event.What = evCommand then
- if Event.Command = cmQuit then
- begin
- EndModal(cmQuit);
- ClearEvent(Event);
- end;
- end;
-
- procedure TProgram.Idle;
- begin
- if StatusLine <> nil then StatusLine^.Update;
- if CommandSetChanged then
- begin
- Message(@Self, evBroadcast, cmCommandSetChanged, nil);
- CommandSetChanged := False;
- end;
- end;
-
- procedure TProgram.InitDeskTop;
- var
- R: TRect;
- begin
- GetExtent(R);
- Inc(R.A.Y);
- Dec(R.B.Y);
- New(DeskTop, Init(R));
- end;
-
- procedure TProgram.InitMenuBar;
- var
- R: TRect;
- begin
- GetExtent(R);
- R.B.Y := R.A.Y + 1;
- MenuBar := New(PMenuBar, Init(R, nil));
- end;
-
- procedure TProgram.InitScreen;
- begin
- if Lo(ScreenMode) <> smMono then
- begin
- if ScreenMode and smFont8x8 <> 0 then
- ShadowSize.X := 1 else
- ShadowSize.X := 2;
- ShadowSize.Y := 1;
- ShowMarkers := False;
- if Lo(ScreenMode) = smBW80 then
- AppPalette := apBlackWhite else
- AppPalette := apColor;
- end else
- begin
- ShadowSize.X := 0;
- ShadowSize.Y := 0;
- ShowMarkers := True;
- AppPalette := apMonochrome;
- end;
- end;
-
- procedure TProgram.InitStatusLine;
- var
- R: TRect;
- begin
- GetExtent(R);
- R.A.Y := R.B.Y - 1;
- New(StatusLine, Init(R,
- NewStatusDef(0, $FFFF,
- NewStatusKey('~Alt-X~ Exit', kbAltX, cmQuit,
- NewStatusKey('', kbF10, cmMenu,
- NewStatusKey('', kbAltF3, cmClose,
- NewStatusKey('', kbF5, cmZoom,
- NewStatusKey('', kbCtrlF5, cmResize,
- NewStatusKey('', kbF6, cmNext, nil)))))), nil)));
- end;
-
- procedure TProgram.OutOfMemory;
- begin
- end;
-
- procedure TProgram.PutEvent(var Event: TEvent);
- begin
- Pending := Event;
- end;
-
- procedure TProgram.Run;
- begin
- Execute;
- end;
-
- procedure TProgram.SetScreenMode(Mode: Word);
- var
- R: TRect;
- begin
- HideMouse;
- SetVideoMode(Mode);
- DoneMemory;
- InitScreen;
- Buffer := ScreenBuffer;
- R.Assign(0, 0, ScreenWidth, ScreenHeight);
- ChangeBounds(R);
- ShowMouse;
- end;
-
- function TProgram.ValidView(P: PView): PView;
- begin
- ValidView := nil;
- if P <> nil then
- begin
- if LowMemory then
- begin
- Dispose(P, Done);
- OutOfMemory;
- Exit;
- end;
- if not P^.Valid(cmValid) then
- begin
- Dispose(P, Done);
- Exit;
- end;
- ValidView := P;
- end;
- end;
-
- { TApplication }
-
- constructor TApplication.Init;
- begin
- InitMemory;
- InitVideo;
- InitEvents;
- InitSysError;
- InitHistory;
- TProgram.Init;
- end;
-
- destructor TApplication.Done;
- begin
- TProgram.Done;
- DoneHistory;
- DoneSysError;
- DoneEvents;
- DoneVideo;
- DoneMemory;
- end;
-
- { App registration procedure }
-
- procedure RegisterApp;
- begin
- RegisterType(RBackground);
- RegisterType(RDeskTop);
- end;
-
- end.
-