This module provides an interface for a vt100 terminal which implements the escape sequences for controlling the special features of this terminal. The most generally used escape sequences are implemented using specific procedures. The module has no intelligence, and only performs a direct conversion of the calls into vt100 escape sequences. Note that a zero argument in some places in the escape sequence represents a default value of one. For example "<ESC>[0B" is equivalent to "<ESC>[B", which moves the cursor one line down. Calling certain procedures with a zero argument can lead to an unexpected result.
This module makes use of a file of characters for the standard output file, which is normally connected to the terminal. A consequence of this is that all output to the terminal should make use of procedures of this module.
All references in this description are to the operation manual for the video display terminal model va120. The va120 did not behave according to the description in the manual in all situations.
The type dec mnemonic is the enumeration of the kinds of terminal setting that can be used. The type is defined by:
dec_mnemonic = (dec_cursor_key_mode, #14A/B p65,80 dec_ansi_mode, #2 p62,78; B(2-3) p38 dec_column_mode, #7A/B p37,64,79 dec_scroll_mode, #3A/B p62,78; B(1-1) p38 dec_screen_mode, #9A/B p64,79; B(1-3) p38 dec_origin_mode, #5A/B p78 dec_auto_wrap_mode, #8A/B p64,79; B(3-1) p38 dec_auto_repeat, #12A/B p65,79; B(1-2) p38 dec_editing_mode, #23A/B p70,83; C(A-1) p42 dec_line_transmit, #30A/B p72,84; C(B-1) p43 dec_sp_com_fl_del_mode, #32A/B p73,85; C(A-4) p43 dec_transmit_execution, #27A/B p71,84; C(B-4) p43 dec_edit_key_execution, #24A/B p70,84; C(A-2) p42 dec_guarded_area, #33A/B p73,85; C(A-3) p42 dec_kbd_locked, #11A/B p79 dec_insert_mode, #22A/B p83 dec_erase_mode, #26A/B p84 dec_local_echo_off, #13A/B p65,80; B(3-4) p39 dec_transfer_term, #31A/B p72,85; C(B-2) p43 dec_line_feed_mode #10A p64,79; B(3-3) p39 );
On the right-hand side of each line is a number that refers to Table 6-5 "ANSI-compatible sequences" in the operator manual. If this terminal setting can be changed in the set-up of the terminal, it is followed by the set-up field code as in Table 4-1 p37 (the first letter refers to the set-up screen, and between brackets the switch to operate on that set-up screen is given).
These terminal settings can be changed by using the following procedure:
PROCEDURE set_term_setting(setting : dec_mnemonic; on : boolean := TRUE);
The first parameter setting contains the required setting to be changed. The other parameter on determines whether the setting is switched on whenever it is equal to TRUE, or switched off otherwise.
The following procedures can be used to save and restore the current terminal settings:
PROCEDURE save_terminal_setting; PROCEDURE restore_terminal_setting;
The procedure save terminal setting operates according to Table 6-5 #6L p64. The procedure restore terminal setting operates according to Table 6-5 #6M p64.
Using the following procedure the scroll region can be changed:
PROCEDURE set_scroll_region (t : range_screen := 1; b : range_screen := max_screen_length);
If the scroll region is legal it is set from the line number of the first parameter t until the line number of the second parameter b. See Table 6-5 #4 "Scrolling region" p62,78.
The following procedure can be used to move the cursor absolutely:
PROCEDURE set_cursor_at_pos(x : range_screen := 1; y : range_line := 1);
The first parameter x determines the new column position and the second parameter y the new line position of the cursor. See Table 6-5 #6G "Cursor Positioning" p63,78.
The relative movements of the cursor are represented by the following enumeration type:
cursor_rel_dir = (cursor_up, cursor_down, cursor_forward, cursor_backward);
The following procedure can be used to move the cursor without scrolling if the border of the current scrolling region is reached:
PROCEDURE move_cursor_rel(s : integer := 1; dir : cursor_rel_dir);
The first parameter s determines the number of positions the cursor has to be moved, and the second parameter dir determines the direction. See Table 6-5 #6A/D "Cursor Positioning" p62,78
The relative cursor scroll movements are represented by the following enumeration type:
cursor_scroll = (cursor_index, cursor_reverse, cursor_next_line);
The index cursor movement, as represented by cursor index moves the cursor down one line (same column position). If bottom margin is encountered, a scroll up is performed. The reverse cursor movement, as represented by cursor reverse moves the cursor up one line (same column position). If the top margin is encountered, a scroll down is performed. The next line cursor movement, as represented by cursor reverse moves the cursor to the start of the next line. If bottom margin is encountered, a scroll up is performed. See Table 6-5 #6I/K "Cursor Positioning" p63,78.
The following procedure performs the required cursor operation for cursor scroll movements:
PROCEDURE move_cursor_scroll (dir : cursor_scroll := cursor_next_line);
The argument dir determines the kind of operation that is performed.
There are three erasing kinds as represented by the following enumeration type:
erasure_kind = (erase_from_cursor, erase_to_cursor, erase_all);
The following procedure can be used to erase a line:
PROCEDURE erase_line (kind : erasure_kind := erase_from_cursor);
This procedure performs the erasure action on the current line, determined by the parameter kind with the current cursor position. See Table 6-5 #20A/D "Erasing" p68,83.
The following procedure can be used to erase the screen:
PROCEDURE erase_screen (kind : erasure_kind := erase_from_cursor);
This procedure performs the erasure action on the whole screen, determined by the parameter kind with the current cursor position. See Table 6-5 #20E/H "Erasing" p69,83
The following procedure can be used to delete characters:
PROCEDURE delete_character(nr : integer := 1);
This procedure deletes a number of characters equal to the parameter nr from the current cursor position. See Table 6-5 #21A "Computer Editing" p69,83.
The following procedures can be used to insert or delete a line:
PROCEDURE insert_line(nr : integer := 1); PROCEDURE delete_line(nr : integer := 1);
The procedure insert line inserts a number of lines, equal to the value of the parameter nr, on the current cursor line position. See Table 6-5 #21B "Computer Editing" p69,83. The procedure delete line deletes a number of lines, equal to the value of the parameter nr, from the current cursor line position. See Table 6-5 #21C "Computer Editing" p 70,83.
The different kinds of lines are represented by the following enumeration type:
kind_of_line = (line_single_width, line_double_width, line_double_height_top_half, line_double_height_down_half );
With the following procedure the line kind can be set:
PROCEDURE set_kind_of_line (kind : kind_of_line := line_single_width);
This procedure sets the current line with the line kind determined by the parameter kind. See Table 6-5 #19A/C "Line Attributes" p68,83
The different kinds of character sets are defined by the following enumeration type:
character_sets = (char_set_normal_UK, char_set_normal_US, char_set_special, char_set_EPROM1, char_set_EPROM2 );
Using the following procedure the current writing character set can be changed:
PROCEDURE set_character_sets (g : integer; kind : character_sets := char_set_normal_US);
The procedure sets the character bank, determined by the first parameter g to the character set, specified by the second parameter kind. See Table 6-5 #16A/J "Character Sets and Selection" p66,82.
The different kinds of character attributes are defined by the following enumeration and set types:
character_attr = (char_attr_none, char_attr_bold, char_attr_under, char_attr_blink, char_attr_reverse ); set_of_char_attr = SET OF character_attr;
The following procedure sets the current writing character attributes:
PROCEDURE set_character_attr (kind : set_of_char_attr := [char_attr_none]);
The procedure sets the character attributes as described by the parameter kind. See Table 6-5 #17A/F "Character Attribute" p67,83.
The following procedure sets the current writing protection character attributes:
PROCEDURE set_protection_attr (kind : set_of_char_attr := [char_attr_none]);
The procedure sets the protection character attributes as described by the parameter kind. See Table 6-5 #25A/E "Character Protection" p71,84.
The following procedures should be used to write text to the terminal:
PROCEDURE write_scr_chr(ch : char); PROCEDURE write_scr(txt : VARYING [s] OF CHAR);
The procedure write scr chr writes the character, represented by the parameter ch on the terminal. The procedure write scr writes the text represented by the parameter txt on the terminal.
The following procedure allows the user to write all other escape sequences to the terminal that are not generated by one of the other procedures:
PROCEDURE special_command(com : VARYING [s] OF CHAR);
The parameter com is written to the terminal as an escape sequence. This is done by adding the escape character as the first character before the text is written.
[ENVIRONMENT ('vt100.pen')] MODULE low_level_vt100_interface; CONST esc_char = chr(27); max_screen_length = 24; max_line_length = 132; TYPE range_screen = 1..max_screen_length; range_line = 1..max_line_length; character_attr = (char_attr_none, char_attr_bold, char_attr_under, char_attr_blink, char_attr_reverse ); set_of_char_attr = SET OF character_attr; (* table 6.5 page | setup page *) dec_mnemonic = (dec_cursor_key_mode, (* #14A/B 80 | *) dec_ansi_mode, (* #2 78 | B(2-3) 38 *) dec_column_mode, (* #7A/B 79 | 37 *) dec_scroll_mode, (* #3A/B 78 | B(1-1) 38 *) dec_screen_mode, (* #9A/B 79 | B(1-3) 38 *) dec_origin_mode, (* #5A/B 78 | *) dec_auto_wrap_mode, (* #8A/B 79 | B(3-1) 38 *) dec_auto_repeat, (* #12A/B 79 | B(1-2) 38 *) dec_xx9xx_mode, (* | *) dec_editing_mode, (* #23A/B 83 | C(A-1) 42 *) dec_line_transmit, (* #30A/B 84 | C(B-1) 43 *) dec_xx12xx_mode, (* | *) dec_sp_com_fl_del_mode, (* #32A/B 85 | C(A-4) 43 *) dec_transmit_execution, (* #27A/B 84 | C(B-4) 43 *) dec_xx15xx_mode, (* | *) dec_edit_key_execution, (* #24A/B 84 | C(A-2) 42 *) dec_guarded_area, (* #33A/B 85 | C(A-3) 42 *) dec_kbd_locked, (* #11A/B 79 | *) dec_insert_mode, (* #22A/B 83 | *) dec_erase_mode, (* #26A/B 84 | *) dec_local_echo_off, (* #13A/B 80 | B(3-4) 39 *) dec_transfer_term, (* #31A/B 85 | C(B-2) 43 *) dec_line_feed_mode (* #10A 79 | B(3-3) 39 *) ); cursor_rel_dir = (cursor_up, cursor_down, cursor_forward, cursor_backward); cursor_scroll = (cursor_index, cursor_reverse, cursor_next_line); character_sets = (char_set_normal_UK, char_set_normal_US, char_set_special, char_set_EPROM1, char_set_EPROM2 ); kind_of_line = (line_single_width, line_double_width, line_double_height_top_half, line_double_height_down_half ); erasure_kind = (erase_from_cursor, erase_to_cursor, erase_all ); VAR screen : [HIDDEN] FILE OF CHAR; |
[INITIALIZE,HIDDEN] PROCEDURE init_screen; (* This procedure takes care for the opening of the screen file, when *) (* this module is used. No explicit call is needed, and even would lead to *) (* a runtime error. (see introduction for more detail) *) BEGIN open(screen, 'sys$output'); rewrite(screen) END; [HIDDEN] PROCEDURE write_nr_wh(i : integer); BEGIN IF i >= 10 THEN write(screen, chr((i DIV 10)MOD 10 + ord('0'))); write(screen, chr(i MOD 10 + ord('0'))) END; [HIDDEN] PROCEDURE write_nr(i : integer); BEGIN IF i >= 100 THEN write(screen, '1'); IF i >= 10 THEN write(screen, chr((i DIV 10)MOD 10 + ord('0'))); IF i > 1 THEN write(screen, chr(i MOD 10 + ord('0'))) END; |
This page contains all procedures to manipulate the terminal settings.
PROCEDURE set_term_setting(setting : dec_mnemonic; on : boolean := TRUE); BEGIN write(screen, esc_char,'['); IF setting < dec_guarded_area THEN BEGIN write(screen, '?'); write_nr_wh(succ(ord(setting))) END ELSE CASE setting OF dec_guarded_area : write(screen, '1'); dec_kbd_locked : write(screen, '2'); dec_insert_mode : write(screen, '4'); dec_erase_mode : write(screen, '6'); dec_local_echo_off : write(screen, '1','2'); dec_transfer_term : write(screen, '1','6'); dec_line_feed_mode : write(screen, '2','0') END; IF on THEN write(screen, 'h') ELSE write(screen, 'l') END; PROCEDURE save_terminal_setting; (* Table 6.5 #6L, page 64 *) BEGIN write(screen, esc_char, '7') END; PROCEDURE restore_terminal_setting; (* Table 6.5 #6M, page 64 *) BEGIN write(screen, esc_char, '8') END; |
PROCEDURE set_scroll_region(t : range_screen := 1; b : range_screen := max_screen_length); (* Table 6.5 #4 Scrolling region, page 78 *) BEGIN write(screen, esc_char,'['); write_nr(t); write(screen, ';'); write_nr(b); write(screen, 'r') END; PROCEDURE set_cursor_at_pos(x : range_screen := 1; y : range_line := 1); (* Table 6.5 #6G, page 63 *) BEGIN write(screen, esc_char,'['); write_nr(x); write(screen, ';'); write_nr(y); write(screen, 'f'); END; PROCEDURE move_cursor_rel(s : integer := 1; dir : cursor_rel_dir); (* Table 6.5 #6A/D Cursor Positioning, page 62, 78 *) BEGIN write(screen, esc_char,'['); write_nr(s); CASE dir OF cursor_up : write(screen, 'A'); cursor_down : write(screen, 'B'); cursor_forward : write(screen, 'C'); cursor_backward : write(screen, 'D') END END; PROCEDURE move_cursor_scroll(dir : cursor_scroll := cursor_next_line); (* Table 6.5 #6I/K Cursor Positioning, page 63, 78 *) BEGIN write(screen, esc_char); CASE dir OF cursor_index : write(screen, 'D'); cursor_reverse : write(screen, 'M'); cursor_next_line : write(screen, 'E') END END; |
PROCEDURE erase_line(kind : erasure_kind := erase_from_cursor); (* Table 6.5 #20A/D Erasing, page 68, 83 *) BEGIN write(screen, esc_char, '['); CASE kind OF erase_from_cursor : write(screen, 'K'); erase_to_cursor : write(screen, '1','K'); erase_all : write(screen, '2','K') END END; PROCEDURE erase_screen(kind : erasure_kind := erase_from_cursor); (* Table 6.5 #20E/H Erasing, page 69, 83 *) BEGIN write(screen, esc_char, '['); CASE kind OF erase_from_cursor : write(screen, 'J'); erase_to_cursor : write(screen, '1','J'); erase_all : write(screen, '2','J') END END; PROCEDURE delete_character(nr : integer := 1); (* Table 6.5 #21A Computer Editing, page 69, 83 *) BEGIN write(screen, esc_char, '['); write_nr(nr); write(screen, 'P') END; PROCEDURE insert_line(nr : integer := 1); (* Table 6.5 #21B Compute Editing, page 69, 83 *) BEGIN write(screen, esc_char, '['); write_nr(nr); write(screen, 'L') END; PROCEDURE delete_line(nr : integer := 1); (* Table 6.5 #21C Computer Editing, page 70, 83 *) BEGIN write(screen, esc_char, '['); write_nr(nr); write(screen, 'M') END; |
PROCEDURE set_kind_of_line(kind : kind_of_line := line_single_width); (* Table 6.5 #19A/C Line Attributes, page 68, 83 *) BEGIN write(screen, esc_char, '#'); CASE kind OF line_single_width : write(screen, '5'); line_double_width : write(screen, '6'); line_double_height_top_half : write(screen, '3'); line_double_height_down_half : write(screen, '4') END END; |
PROCEDURE set_character_sets(g : integer; kind : character_sets := char_set_normal_US); (* Table 6.5 #16A/J Character Sets and Selection, page 66, 82 *) BEGIN write(screen, esc_char); IF g = 0 THEN write(screen, '(') ELSE write(screen, ')'); CASE kind OF char_set_normal_UK : write(screen, 'A'); char_set_normal_US : write(screen, 'B'); char_set_special : write(screen, '0'); char_set_EPROM1 : write(screen, '1'); char_set_EPROM2 : write(screen, '2') END END; PROCEDURE set_character_attr(kind : set_of_char_attr := [char_attr_none]); (* Table 6.5 #17A/F Character Attribute, page 67, 83 *) BEGIN IF char_attr_none IN kind THEN write(screen, esc_char, '[','0','m'); IF char_attr_bold IN kind THEN write(screen, esc_char, '[','1','m'); IF char_attr_under IN kind THEN write(screen, esc_char, '[','4','m'); IF char_attr_blink IN kind THEN write(screen, esc_char, '[','5','m'); IF char_attr_reverse IN kind THEN write(screen, esc_char, '[','7','m') END; PROCEDURE set_protection_attr(kind : set_of_char_attr := [char_attr_none]); (* Table 6.5 #25A/E Character Protection, page 71, 84 *) BEGIN IF char_attr_none IN kind THEN write(screen, esc_char, '[','0','}'); IF char_attr_bold IN kind THEN write(screen, esc_char, '[','1','}'); IF char_attr_under IN kind THEN write(screen, esc_char, '[','4','}'); IF char_attr_blink IN kind THEN write(screen, esc_char, '[','5','}'); IF char_attr_reverse IN kind THEN write(screen, esc_char, '[','7','}') END; |
PROCEDURE special_command(com : VARYING [s] OF CHAR); VAR i : integer; BEGIN write(screen, esc_char); FOR i := 1 TO com.length DO write(screen, com[i]) END; PROCEDURE write_scr_chr(ch : char); BEGIN write(screen, ch) END; PROCEDURE write_scr(txt : VARYING [s] OF CHAR); VAR i : integer; BEGIN FOR i := 1 TO txt.length DO write(screen, txt[i]) END; END. |
My life as a hacker | My home page