home *** CD-ROM | disk | FTP | other *** search
- (*-----------------------------------------------------------------*)
- (* PIBSCREN.PAS --- Screen Handling Routines for Turbo Pascal*)
- (*-----------------------------------------------------------------*)
- (* *)
- (* Author: Philip R. Burns *)
- (* *)
- (* Date: Version 1.0: January, 1985 (Part of PibMenus) *)
- (* Version 1.1: March, 1985 (Part of PibMenus) *)
- (* Version 1.2: May, 1985 (Part of PibMenus) *)
- (* Version 2.0: June, 1985 (Split from PibMenus) *)
- (* Version 3.0: October, 1985 *)
- (* Version 3.1: October, 1985 *)
- (* Version 3.2: November, 1985 *)
- (* *)
- (* Systems: For MS-DOS on IBM PCs and close compatibles only. *)
- (* Note: I have checked these on Zenith 151s under *)
- (* MSDOS 2.1 and IBM PCs under PCDOS 2.0. *)
- (* *)
- (* History: These routines provide a simple windowing facility for*)
- (* Turbo Pascal as well as routines for direct access to *)
- (* screen memory area. *)
- (* *)
- (* The windowing facility provides windows similar to tho*)
- (* implemented in QMODEM by John Friel III. *)
- (* *)
- (* Version 1.0 of these routines formed part of the *)
- (* PIBMENUS.PAS include file. These routines were split *)
- (* into a separate PIBSCREN.PAS file at version 2.0. *)
- (* *)
- (* Starting with version 3.2, PibScren uses a (hopefully)*)
- (* version-independent method for ascertaining the size *)
- (* of the current window. The method relies on the 1-pas*)
- (* construction of Turbo, so that the standard built-in *)
- (* procedure WINDOW can be replaced by one defined here, *)
- (* the built-in version then referred to by the name *)
- (* TurboWindow. *)
- (* *)
- (* Suggestions for improvements or corrections are welcom*)
- (* Please leave messages on Gene Plantz's BBS(312)8824145*)
- (* or Ron Fox's BBS (312) 940 6496. *)
- (* *)
- (* If you use this code in your own programs, please be *)
- (* and give all of us credit. *)
- (* *)
- (*----------------------------------------------------------------*)
- (* *)
- (* Needs: These routines need the include files MINMAX.PAS, *)
- (* GLOBTYPE.PAS, ASCII.PAS, and INT24.PAS. *)
- (* *)
- (*----------------------------------------------------------------*)
- (* *)
- (* Note that code for stacked windows is available here. You may*)
- (* want to modify this to use compile-time window spaces,or remove*)
- (* the current push-down stack structure. *)
- (* *)
- (*----------------------------------------------------------------*)
-
- (*----------------------------------------------------------------*)
- (* Constants, Types, and Variables for Screen Access *)
- (*----------------------------------------------------------------*)
-
- CONST
- Color_Screen_Address = $B800; (* Address of color screen *)
- Mono_Screen_Address = $B000; (* Address of mono screen *)
- Screen_Length = 4000; (* 80 x 25 x 2 = screen area *)
- Max_Saved_Screen = 1; (* Maximum no. saved screens *)
-
- TYPE
- (* A screen image *)
-
- Screen_Type = ARRAY[ 1 .. Screen_Length ] OF BYTE;
-
- Screen_Ptr = ^Screen_Image_Type;
-
- Screen_Image_Type = RECORD
- Screen_Image: Screen_Type;
- END;
-
- (* Screen stack entries *)
- Saved_Screen_Ptr = ^Saved_Screen_Type;
-
- Saved_Screen_Type = RECORD
- Screen_Image : Screen_Type;
- Screen_Row : INTEGER;
- Screen_Column : INTEGER;
- Screen_X1 : INTEGER;
- Screen_Y1 : INTEGER;
- Screen_X2 : INTEGER;
- Screen_Y2 : INTEGER;
- END;
-
- VAR
- (* Memory-mapped screen area *)
- Actual_Screen : Screen_Ptr;
- (* Saves screen behind menus *)
-
- Saved_Screen : Saved_Screen_Ptr;
-
- (* Stack of saved screens *)
-
- Saved_Screen_List : ARRAY[ 1 .. Max_Saved_Screen ] OF Saved_Screen_Ptr;
-
- (* STRUCTURED *) CONST
- (* Depth of saved screen stack *)
- Current_Saved_Screen : 0 .. Max_Saved_Screen = 0;
-
- (* Upper left corner of *)
- (* current TURBO window *)
- CONST
- Upper_Left_Column : Byte = 1;
- Upper_Left_Row : Byte = 1;
-
- (* Lower right corner of *)
- (* current TURBO window *)
- CONST
- Lower_Right_Column : Byte = 80;
- Lower_Right_Row : Byte = 25;
-
- (*-----------------------------------------------------------------*)
- (* Turbo_Window --- allow access to built-in WINDOW procedure*)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Turbo_Window( X1, Y1, X2, Y2 : INTEGER );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: Turbo_Window *)
- (* *)
- (* Purpose: Allows access to built-in Turbo procedure WINDOW*)
- (* after Window is re-defined below. *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- BEGIN (* Turbo_Window *)
-
- Window( X1, Y1, X2, Y2 );
-
- END (* Turbo_Window *);
-
- (*-----------------------------------------------------------------*)
- (* Window --- Redefines Turbo's built-in WINDOW procedure *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Window( X1, Y1, X2, Y2 : INTEGER );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: Window *)
- (* *)
- (* Purpose: Redefines built-in Turbo procedure WINDOW so tha*)
- (* we can keep track of window boundaries. *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- BEGIN (* Window *)
-
- Turbo_Window( X1, Y1, X2, Y2 );
-
- Upper_Left_Column := X1;
- Upper_Left_Row := Y1;
- Lower_Right_Column := X2;
- Lower_Right_Row := Y2;
-
- END (* Window *);
-
- (*-----------------------------------------------------------------*)
- (* Color_Screen_Active --- Determine if color or mono screen *)
- (*-----------------------------------------------------------------*)
-
- FUNCTION Color_Screen_Active : BOOLEAN;
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Function: Color_Screen_Active *)
- (* *)
- (* Purpose: Determines if color or mono screen active *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* Color_Active := Color_Screen_Active : BOOLEAN; *)
- (* *)
- (* Color_Active --- set to TRUE if the color screen is *)
- (* active, FALSE if the mono screen is *)
- (* active. *)
- (* *)
- (* Calls: INTR *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- VAR
- Regs : RegPack;
-
- BEGIN (* Color_Screen_Active *)
-
- Regs.Ax := 15 SHL 8;
-
- INTR( $10 , Regs );
-
- Color_Screen_Active := ( Regs.Al <> 7 );
-
- End (* Color_Screen_Active *);
-
- (*-----------------------------------------------------------------*)
- (* Current_Video_Mode --- Determine current video mode setting *)
- (*-----------------------------------------------------------------*)
-
- FUNCTION Current_Video_Mode: INTEGER;
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Function: Current_Video_Mode *)
- (* *)
- (* Purpose: Gets current video mode setting from system *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* Current_Mode := Current_Video_Mode : INTEGER; *)
- (* *)
- (* Current_Mode --- set to integer representing current *)
- (* video mode inherited from system. *)
- (* *)
- (* Calls: INTR *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- VAR
- Regs : RegPack;
-
- BEGIN (* Current_Video_Mode *)
-
- Regs.Ax := 15 SHL 8;
-
- INTR( $10 , Regs );
-
- Current_Video_Mode := Regs.Al;
-
- End (* Current_Video_Mode *);
-
- (*-----------------------------------------------------------------*)
- (* Get_Screen_Address --- Get address of current screen *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Get_Screen_Address( VAR Actual_Screen : Screen_Ptr );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: Get_Screen_Address *)
- (* *)
- (* Purpose: Gets screen address for current type of display *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* Get_Screen_Address( Var Actual_Screen : Screen_Ptr ); *)
- (* *)
- (* Actual_Screen --- pointer whose value receives the *)
- (* current screen address. *)
- (* *)
- (* Calls: Color_Screen_Active *)
- (* PTR *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- BEGIN (* Get_Screen_Address *)
-
- IF Color_Screen_Active THEN
- Actual_Screen := PTR( Color_Screen_Address , 0 )
- ELSE
- Actual_Screen := PTR( Mono_Screen_Address , 0 );
-
- END (* Get_Screen_Address *);
-
- (*-----------------------------------------------------------------*)
- (* Video Display Control Routines *)
- (*-----------------------------------------------------------------*)
- (* *)
- (* RvsVideoOn --- Turn On Reverse Video *)
- (* RvsVideoOff --- Turn Off Reverse Video *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE RvsVideoOn( Foreground_Color, Background_Color : INTEGER );
-
- BEGIN (* RvsVideoOn *)
-
- TextColor ( Background_color );
- TextBackGround( Foreground_color );
-
- END (* RvsVideoOn *);
-
- (*-----------------------------------------------------------------*)
-
- PROCEDURE RvsVideoOff( Foreground_Color, Background_Color : INTEGER );
-
- BEGIN (* RvsVideoOff *)
-
- TextColor ( Foreground_color );
- TextBackGround( Background_color );
-
- END (* RvsVideoOff *);
-
- (*-----------------------------------------------------------------*)
- (* Upper_Left --- Upper Position of current window *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Upper_Left( VAR X1, Y1 : INTEGER );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: Upper_Left *)
- (* *)
- (* Purpose: Returns upper position of current TURBO window *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* Upper_Left( VAR X1, Y1 : INTEGER ); *)
- (* *)
- (* X1 --- returned upper left column *)
- (* Y1 --- returned upper left row *)
- (* *)
- (* Calls: None *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- BEGIN (* Upper_Left *)
-
- Y1 := Upper_Left_Row; (* get Row *)
- X1 := Upper_Left_Column (* get Column *)
-
- END (* Upper_Left *);
-
-
- (*-----------------------------------------------------------------*)
- (* Set/Reset Text Color Routines *)
- (*-----------------------------------------------------------------*)
- (* *)
- (* These routines set and reset the global text foreground and *)
- (* background colors. *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- (* Global Text Color Variables *)
-
- VAR
- Global_ForeGround_Color : INTEGER;
- Global_BackGround_Color : INTEGER;
-
- (*-----------------------------------------------------------------*)
- (* Set_Global_Colors --- Reset global foreground, background cols.*)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Set_Global_Colors( ForeGround, BackGround : INTEGER );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: Set_Global_Colors *)
- (* *)
- (* Purpose: Sets global text foreground, background colors. *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* Set_Global_Colors( ForeGround, BackGround : INTEGER ); *)
- (* *)
- (* ForeGround --- Default foreground color *)
- (* BackGround --- Default background color *)
- (* *)
- (* Calls: TextColor *)
- (* TextBackGround *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- BEGIN (* Set_Global_Colors *)
-
- Global_ForeGround_Color := ForeGround;
- GLobal_BackGround_Color := BackGround;
-
- TextColor ( Global_ForeGround_Color );
- TextBackground( Global_BackGround_Color );
-
- END (* Set_Global_Colors *);
-
- (*-----------------------------------------------------------------*)
- (*Reset_Global_Colors --- Reset global foreground, background cols.*)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Reset_Global_Colors;
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: Reset_Global_Colors *)
- (* *)
- (* Purpose:Resets text foreground, background colors to global *)
- (* defaults. *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* Reset_Global_Colors; *)
- (* *)
- (* Calls: TextColor *)
- (* TextBackGround *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- BEGIN (* Reset_Global_Colors *)
-
- TextColor ( Global_ForeGround_Color );
- TextBackground( Global_BackGround_Color );
-
- END (* Reset_Global_Colors *);
-
- (*-----------------------------------------------------------------*)
- (* Screen Manipulation Routines *)
- (*-----------------------------------------------------------------*)
- (* *)
- (*These routines save and restore screen images in support of the *)
- (*windowing facility. Also, the current screen image can be printed*)
- (*and text extracted from the screen memory. *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- (*-----------------------------------------------------------------*)
- (* Get_Screen_Text_Line --- Extract text from screen image *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Get_Screen_Text_Line( VAR Text_Line : AnyStr;
- Screen_Line : INTEGER;
- Screen_Column : INTEGER );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: Get_Screen_Text_Line *)
- (* *)
- (* Purpose: Extracts text from current screen image *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* Get_Screen_Text_Line( Var Text_Line : AnyStr; *)
- (* Screen_Line : INTEGER; *)
- (* Screen_Column : INTEGER ); *)
- (* *)
- (* Text_Line --- receives text extracted from scrn*)
- (* Screen_Line --- line on screen to extract *)
- (* Screen_Column --- starting column to extract *)
- (* *)
- (* Calls: None *)
- (* *)
- (* Remarks: *)
- (* *)
- (* Only the text -- not attributes -- from the screen is *)
- (* returned. *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- VAR
- First_Pos : INTEGER;
- Last_Pos : INTEGER;
- I : INTEGER;
-
- BEGIN (* Get_Screen_Text_Line *)
-
- Screen_Line := Max( Min( Screen_Line , 25 ) , 1 );
- Screen_Column := Max( Min( Screen_Column , 80 ) , 1 );
-
- Text_Line := '';
- First_Pos := ( ( Screen_Line - 1 ) * 80 + Screen_Column ) * 2 - 1;
- Last_Pos := First_Pos + ( 80 - Screen_Column ) * 2 + 1;
-
- REPEAT
- Text_Line := Text_Line + CHR( Actual_Screen^.Screen_Image[ First_Pos ] );
- First_Pos := First_Pos + 2;
- UNTIL ( First_Pos > Last_Pos );
-
- END (* Get_Screen_Text_Line *);
-
- (*-----------------------------------------------------------------*)
- (* Print_Screen --- Print current screen image *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Print_Screen;
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: Print_Screen *)
- (* *)
- (* Purpose: Prints current screen image (memory mapped area)*)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* Print_Screen; *)
- (* *)
- (* Calls: None *)
- (* *)
- (* Remarks: *)
- (* *)
- (* Only the text from the screen is printed, not the attributes. *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- VAR
- I : INTEGER;
- Text_Line : AnyStr;
-
- BEGIN (* Print_Screen *)
-
- FOR I := 1 TO 25 DO
- BEGIN
- Get_Screen_Text_Line( Text_Line, I, 1 );
- WRITELN( Lst , Text_Line );
- END;
- Writeln(Lst,chr(12));
- END (* Print_Screen *);
-
- (*-----------------------------------------------------------------*)
- (* Write_Screen --- Write current screen image to file *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Write_Screen( Fname : AnyStr );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: Write_Screen *)
- (* *)
- (* Purpose: Write current screen image (memory mapped area) *)
- (* a file. *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* Write_Screen( Fname : AnyStr ); *)
- (* *)
- (* Fname --- Name of file to write screen to *)
- (* *)
- (* Calls: None *)
- (* *)
- (* Remarks: *)
- (* *)
- (* Only the text from the screen is written, not the attributes. *)
- (* If the file already exists, then the new screen is appended *)
- (* to the end of the file. *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- VAR
- I : INTEGER;
- Text_Line : STRING[80];
- F : TEXT [512];
-
- BEGIN (* Write_Screen *)
-
- (*$I-*)
- ASSIGN( F , Fname );
- RESET ( F );
-
- IF Int24Result = 0 THEN
- BEGIN
- CLOSE( F );
- APPEND( F );
- END
- ELSE
- BEGIN
- CLOSE ( F );
- REWRITE( F );
- END;
-
- FOR I := 1 TO 25 DO
- BEGIN
- Get_Screen_Text_Line( Text_Line, I, 1 );
- WRITELN( F , Text_Line );
- END;
-
- CLOSE( F );
- (*$I+*)
-
- END (* Write_Screen *);
-
- (*-----------------------------------------------------------------*)
- (* WriteSLin --- Write text string to screen *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE WriteSLin( S: AnyStr; Color: INTEGER );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: WriteSLin *)
- (* *)
- (*Purpose: Writes text string to current line in screen memory *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* WriteSLin( S: AnyStr; Color: INTEGER ); *)
- (* *)
- (* S --- String to be written *)
- (* Color --- Color in which to write string *)
- (* *)
- (* Calls: None *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- VAR
- Length_S : INTEGER;
- S_Column : INTEGER;
- S_Row : INTEGER;
- I : INTEGER;
- Regs : RegPack;
-
- BEGIN (* WriteSLin *)
-
- Length_S := LENGTH( S );
-
- IF ( NOT Write_Screen_Memory ) THEN
- BEGIN
-
- S_Row := WhereY;
-
- FOR I := 1 TO Length_S DO
- BEGIN
-
- GoToXY( I , S_Row );
-
- Regs.AH := 9;
- Regs.AL := ORD( S[I] );
- Regs.BH := 0;
- Regs.BL := Color;
- Regs.CX := 1;
-
- INTR( $10 , Regs );
-
- END
-
- END
- ELSE
- BEGIN
-
- S_Column := 1;
- S_Row := ( WhereY - 1 ) * 160;
-
- FOR I := 1 TO Length_S DO
- WITH Actual_Screen^ DO
- BEGIN
- Screen_Image[ S_Column + S_Row ] := ORD( COPY( S, I, 1 ) );
- Screen_Image[ S_Column + S_Row + 1 ] := Color;
- S_Column := S_Column + 2;
- END;
-
- S_Row := S_Row + 160;
-
- IF S_Row > 3800 THEN
- InsLine;
-
- END;
-
- END (* WriteSLin *);
-
- (*-----------------------------------------------------------------*)
- (* WriteSXY --- Write text string to specified row/column *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE WriteSXY( S: AnyStr; X: INTEGER; Y: INTEGER; Color: INTEGER );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: WriteSXY *)
- (* *)
- (* Purpose: Writes text string at specified row and column *)
- (* position on screen. *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* WriteSXY( S: AnyStr; X: INTEGER; Y: INTEGER; Color: INTEGER );*)
- (* *)
- (* S --- String to be written *)
- (* X --- Column position to write string *)
- (* Y --- Column position to write string *)
- (* Color --- Color in which to write string *)
- (* *)
- (* Calls: None *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- VAR
- Length_S : INTEGER;
- S_Column : INTEGER;
- S_Row : INTEGER;
- I : INTEGER;
- S_Pos : INTEGER;
- Regs : RegPack;
-
- BEGIN (* WriteSXY *)
-
- Length_S := LENGTH( S );
- S_Pos := 0;
-
- IF ( NOT Write_Screen_Memory ) THEN
- FOR I := 1 TO Length_S DO
- BEGIN
-
- GoToXY( X + I - 1 , Y );
-
- Regs.AH := 9;
- Regs.AL := ORD( S[I] );
- Regs.BH := 0;
- Regs.BL := Color;
- Regs.CX := 1;
-
- INTR( $10 , Regs );
-
- END
- ELSE
- FOR I := 1 TO Length_S DO
- WITH Actual_Screen^ DO
- IF S_Pos < 4001 THEN
- BEGIN
- S_Pos := ( ( Y - 1 ) * 80 + X ) * 2 - 1;
- Screen_Image[ S_Pos ] := ORD( COPY( S, I, 1 ) );
- Screen_Image[ S_Pos + 1 ] := Color;
- X := X + 1;
- END;
-
- END (* WriteSXY *);
-
- (*-----------------------------------------------------------------*)
- (* WriteCXY --- Write character to screen at specified row/column*)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE WriteCXY( C: CHAR; X: INTEGER; Y: INTEGER; Color: INTEGER );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (* Procedure: WriteCXY *)
- (* *)
- (* Purpose: Writes a character at specified row and column *)
- (* position on screen. *)
- (* *)
- (* Calling Sequence: *)
- (* *)
- (* WriteCXY( C: CHAR; X: INTEGER; Y: INTEGER; Color: INTEGER ); *)
- (* *)
- (* C --- Character to be written *)
- (* X --- Column position to write character *)
- (* Y --- Column position to write character *)
- (* Color --- Color in which to write character *)
- (* *)
- (* Calls: INTR *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- VAR
- S_Pos : INTEGER;
- Regs : RegPack;
-
- BEGIN (* WriteCXY *)
-
- IF ( NOT Write_Screen_Memory ) THEN
- BEGIN
-
- GoToXY( X , Y );
-
- Regs.AH := 9;
- Regs.AL := ORD( C );
- Regs.BH := 0;
- Regs.BL := Color;
- Regs.CX := 1;
-
- INTR( $10 , Regs );
-
- END
- ELSE
- WITH Actual_Screen^ DO
- BEGIN
- S_Pos := ( ( Y - 1 ) * 80 + X ) * 2 - 1;
- Screen_Image[ S_Pos ] := ORD( C );
- Screen_Image[ S_Pos + 1 ] := Color;
- END;
-
- END (* WriteCXY *);
-
- (*-----------------------------------------------------------------*)
- (* Save_Screen --- Save current screen image *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Save_Screen( VAR Saved_Screen_Pointer : Saved_Screen_Ptr );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (*Procedure: Save_Screen *)
- (* *)
- (*Purpose: Saves current screen image (memory mapped area) *)
- (* *)
- (*Calling Sequence: *)
- (* *)
- (* Save_Screen( Var Saved_Screen_Pointer : Saved_Screen_Ptr ); *)
- (* *)
- (* Saved_Screen_Pointer --- pointer to record receiving *)
- (* screen image, window location, *)
- (* and current cursor location. *)
- (* *)
- (*Calls: Move *)
- (* Upper_Left *)
- (* *)
- (*Remarks: *)
- (* *)
- (* This version checks for stack overflow. *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- BEGIN (* Save_Screen *)
- (* Overwrite last screen if no room *)
-
- IF Current_Saved_Screen >= Max_Saved_Screen THEN
- Saved_Screen_Pointer := Saved_Screen_List[ Max_Saved_Screen ]
- ELSE
- BEGIN
- Current_Saved_Screen := Current_Saved_Screen + 1;
- NEW( Saved_Screen_Pointer );
- Saved_Screen_List[ Current_Saved_Screen ] := Saved_Screen_Pointer;
- END;
-
- WITH Saved_Screen_Pointer^ DO
- BEGIN
-
- Upper_Left( Screen_X1, Screen_Y1 );
-
- Screen_X2 := Lower_Right_Column;
- Screen_Y2 := Lower_Right_Row;
-
- Screen_Row := WhereY;
- Screen_Column := WhereX;
-
- MOVE( Actual_Screen^.Screen_Image, Screen_Image, Screen_Length );
-
- END;
-
- END (* Save_Screen *);
-
- (*-----------------------------------------------------------------*)
- (* Restore_Screen --- Restore saved screen image *)
- (*-----------------------------------------------------------------*)
-
- PROCEDURE Restore_Screen( VAR Saved_Screen_Pointer : Saved_Screen_Ptr );
-
- (*-----------------------------------------------------------------*)
- (* *)
- (*Procedure: Restore_Screen *)
- (* *)
- (*Purpose: Restores previously saved screen image. *)
- (* *)
- (*Calling Sequence: *)
- (* *)
- (* Restore_Screen( Var Saved_Screen_Pointer: Saved_Screen_Ptr ); *)
- (* *)
- (* Saved_Screen_Pointer --- pointer to record with saved *)
- (* screen image, window location, *)
- (* and cursor location. *)
- (* *)
- (*Calls: Window *)
- (* Move *)
- (* GoToXY *)
- (* WriteCXY *)
- (* *)
- (*Remarks: *)
- (* *)
- (* All saved screen pointers from the last saved down to the *)
- (* argument pointer are popped from the saved screen list. *)
- (* *)
- (*-----------------------------------------------------------------*)
-
- VAR
- X: BYTE;
- Y: BYTE;
- I: INTEGER;
-
- BEGIN (* Restore_Screen *)
-
- WITH Saved_Screen_Pointer^ DO
- BEGIN
-
- Window( 1, 1, 80, 25 );
-
- IF Write_Screen_Memory THEN
- MOVE( Screen_Image, Actual_Screen^.Screen_Image, Screen_Length )
- ELSE
- BEGIN
- I := 1;
- FOR Y := 1 TO 25 DO
- FOR X := 1 TO 80 DO
- BEGIN
- WriteCXY( CHR(Screen_Image[I]), X, Y, Screen_Image[I+1] );
- I := I + 2;
- END;
- END;
-
- Window( Screen_X1, Screen_Y1, Screen_X2, Screen_Y2 );
- GoToXY( Screen_Column, Screen_Row );
-
- END;
-
-
- WHILE( Saved_Screen_List[ Current_Saved_Screen ] <> Saved_Screen_Pointer ) DO
- BEGIN
- DISPOSE( Saved_Screen_List[ Current_Saved_Screen ] );
- Current_Saved_Screen := Current_Saved_Screen - 1;
- END;
-
- IF Current_Saved_Screen > 0 THEN
- Current_Saved_Screen := Current_Saved_Screen - 1;
-
- DISPOSE( Saved_Screen_Pointer );
-
- Saved_Screen_Pointer := NIL;
-
- END (* Restore_Screen *);