|
|
DataMuseum.dkPresents historical artifacts from the history of: DKUUG/EUUG Conference tapes |
This is an automatic "excavation" of a thematic subset of
See our Wiki for more about DKUUG/EUUG Conference tapes Excavated with: AutoArchaeologist - Free & Open Source Software. |
top - metrics - downloadIndex: T v
Length: 10147 (0x27a3)
Types: TextFile
Names: »vt220vdu.mod«
└─⟦060c9c824⟧ Bits:30007080 DKUUG TeX 2/12/89
└─⟦this⟧ »./DVIware/crt-viewers/others/dvitovdu/src/vt220vdu.mod«
└─⟦52210d11f⟧ Bits:30007239 EUUGD2: TeX 3 1992-12
└─⟦af5ba6c8e⟧ »unix3.0/DVIWARE.tar.Z«
└─⟦ca79c7339⟧
└─⟦this⟧ »DVIware/crt-viewers/others/dvitovdu/src/vt220vdu.mod«
IMPLEMENTATION MODULE vt220vdu;
(* Author: John Mann & Andrew Trevorrow
Implementation: Modula-2 under VAX/UNIX 4.2 BSD
Date Started: June, 1986
This module was the idea of John Mann (Monash University).
Chunky bitmap graphics are used in ShowRectangle.
VT220 is switched to 132 column mode and is assumed to
be in VT200 mode with 7 bit controls.
Description:
Implements the InitVT220 procedure that initializes the generic VDU routines
and parameters used in DVItoVDU.
DVItoVDU assumes text lines start at 1 and increase down the screen.
When updating the window in graphics mode (using ShowChar and ShowRectangle),
DVItoVDU assumes the top left screen pixel is (0,0); h coordinates increase
to the right and v coordinates increase down.
The VT220 coordinate scheme for graphics is exactly the same.
The bottom 20 rows in Bitmap represent a 132 by 20 character window region.
Each character is made up of 5 vertical "pixels" and so 32 (=2^5) characters
can be down-loaded and used to draw all possible 1 by 5 pixel rectangles.
*)
FROM vduinterface IMPORT
DVIstatusl, windowstatusl, messagel, commandl, bottoml,
windowh, windowv, windowwd, windowht,
TeXtoASCII,
StartText, MoveToTextLine, ClearTextLine, ClearScreen,
StartGraphics, LoadFont, ShowChar, ShowRectangle,
ResetVDU;
FROM screenio IMPORT
Write, WriteString, WriteCard, WriteBuffer;
FROM ansivdu IMPORT
MoveAbs, ANSIMoveToTextLine, ANSIClearTextLine, ANSILoadFont;
CONST
ESC = 33C;
SO = 16C;
SI = 17C;
VAR
cursrow, curscol : CARDINAL; (* VT220ShowChar remembers cursor location *)
CONST
hpixels = 1; (* horizontal pixels per char position *)
vpixels = 5; (* vertical pixels per char position *)
flag = 7; (* SYSDEP: to overcome a compiler limitation *)
hscreenmax = 131; (* max horizontal char coordinate *)
vscreenmax = 23; (* max vertical char coordinate *)
TYPE
BitValue = [0..flag];
(* SYSDEP: was 0..vpixels but compiler seemed to have trouble
with an array element size of 6 bits!!!
*)
ByteSet = SET OF BitValue;
VAR
rectcount : CARDINAL; (* keeps a count of ShowRectangle calls;
reset in ShowBitmap *)
Bitmap : ARRAY [0..hscreenmax],[0..vscreenmax] OF ByteSet;
(******************************************************************************)
PROCEDURE InitVT220;
(* The dialogue region is the top 4 lines.
The window region is the remaining area of the screen
(the bottom 20 rows in Bitmap).
*)
BEGIN
DVIstatusl := 1;
windowstatusl := 2;
messagel := 3;
commandl := 4;
bottoml := vscreenmax + 1;
(* DVItoVDU's coordinate scheme is the same as the VT220 scheme. *)
windowh := 0;
windowv := 4 * vpixels; (* = height of 4 dialogue lines *)
windowwd := (hscreenmax + 1) * hpixels;
windowht := (vscreenmax + 1) * vpixels - windowv;
StartText := ShowBitmap; (* flush the graphics Bitmap *)
MoveToTextLine := ANSIMoveToTextLine;
ClearTextLine := ANSIClearTextLine;
ClearScreen := VT220ClearScreen;
StartGraphics := VT220StartGraphics;
LoadFont := ANSILoadFont;
ShowChar := VT220ShowChar;
ShowRectangle := VT220ShowRectangle;
ResetVDU := VT220ResetVDU;
LoadPixels;
Write(ESC); WriteString('[?3h'); (* 132 column mode *)
END InitVT220;
(******************************************************************************)
PROCEDURE LoadPixels;
(* Down-load the chunky graphics character set into the VT220. *)
BEGIN
Write(ESC); Write('P');
WriteString('1;1;2;3;2;1{&%C');
WriteString('BBBBBBBB/????????;');
WriteString('KKKKKKKK/????????;');
WriteString('NNNNNNNN/????????;');
WriteString('oooooooo/????????;');
WriteString('rrrrrrrr/????????;');
WriteString('{{{{{{{{/????????;');
WriteString('~~~~~~~~/????????;');
WriteString('????????/BBBBBBBB;');
WriteString('BBBBBBBB/BBBBBBBB;');
WriteString('KKKKKKKK/BBBBBBBB;');
WriteString('NNNNNNNN/BBBBBBBB;');
WriteString('oooooooo/BBBBBBBB;');
WriteString('rrrrrrrr/BBBBBBBB;');
WriteString('{{{{{{{{/BBBBBBBB;');
WriteString('~~~~~~~~/BBBBBBBB;');
WriteString('????????/KKKKKKKK;');
WriteString('BBBBBBBB/KKKKKKKK;');
WriteString('KKKKKKKK/KKKKKKKK;');
WriteString('NNNNNNNN/KKKKKKKK;');
WriteString('oooooooo/KKKKKKKK;');
WriteString('rrrrrrrr/KKKKKKKK;');
WriteString('{{{{{{{{/KKKKKKKK;');
WriteString('~~~~~~~~/KKKKKKKK;');
WriteString('????????/NNNNNNNN;');
WriteString('BBBBBBBB/NNNNNNNN;');
WriteString('KKKKKKKK/NNNNNNNN;');
WriteString('NNNNNNNN/NNNNNNNN;');
WriteString('oooooooo/NNNNNNNN;');
WriteString('rrrrrrrr/NNNNNNNN;');
WriteString('{{{{{{{{/NNNNNNNN;');
WriteString('~~~~~~~~/NNNNNNNN');
(* SYSDEP: compiler did not like '\' !!! *)
Write(ESC); Write(134C);
Write(ESC); WriteString(')&%C'); (* set as G1 character set *)
END LoadPixels;
(******************************************************************************)
PROCEDURE ClearBitmap;
(* Clear the Bitmap. *)
VAR h,v : CARDINAL;
BEGIN
FOR v := 4 TO vscreenmax DO (* ignore dialogue lines 0..3 *)
FOR h := 0 TO hscreenmax DO
Bitmap [h,v] := ByteSet {};
END;
END;
END ClearBitmap;
(******************************************************************************)
PROCEDURE ShowBitmap;
(* Display only the flagged characters in the Bitmap. *)
VAR h, v : CARDINAL;
BEGIN
Write(SO); (* assume only working over 7 bit comm lines *)
FOR v := 4 TO vscreenmax DO (* ignore dialogue lines *)
FOR h := 0 TO hscreenmax DO
IF flag IN Bitmap[h,v] THEN (* send flagged character *)
EXCL (Bitmap[h,v], flag); (* clear flag *)
MoveQuick(h,v);
Write(CHAR(CARDINAL(Bitmap[h,v]) + 32));
END;
END;
END;
Write(SI); (* assume only working over 7 bit comm lines *)
WriteBuffer;
rectcount := 0;
END ShowBitmap;
(******************************************************************************)
PROCEDURE VT220ClearScreen;
BEGIN
Write(ESC);
WriteString('[2J'); (* erase entire screen *)
ClearBitmap; (* reset Bitmap *)
END VT220ClearScreen;
(******************************************************************************)
PROCEDURE VT220StartGraphics;
(* Note that DVItoVDU will only call LoadFont, ShowChar and ShowRectangle
while in graphics mode.
*)
BEGIN
rectcount := 0;
cursrow := 0; (* for MoveQuick *)
END VT220StartGraphics;
(******************************************************************************)
PROCEDURE MoveQuick (screenh, screenv : CARDINAL);
(* Move cursor to given screen position.
We remember the cursor position (cursrow,curscol) so we can reduce the
output bytes needed to do the next MoveQuick.
StartGraphics resets the position to an undefined state (cursrow = 0).
We also reset when the cursor reaches the right edge (= windowwd) to
avoid possibility of any auto wrap.
*)
VAR amount : CARDINAL;
BEGIN
(* first translate DVItoVDU coordinates into actual screen location *)
INC(screenh);
INC(screenv);
IF cursrow = screenv THEN
(* The cursor is on the same line as in previous MoveQuick call so we only
need to move left or right, and probably just a small amount (if at all).
*)
IF screenh = curscol THEN (* cursor in correct location *)
INC(curscol); (* cursor will move right when ch written *)
ELSIF screenh < curscol THEN (* move cursor left *)
amount := curscol - screenh;
Write(ESC); Write('[');
IF amount > 1 THEN (* default is 1 col *)
WriteCard(amount);
DEC(curscol,amount-1); (* no need to do this if amount = 1 *)
END;
Write('D');
ELSE (* move cursor right *)
amount := screenh - curscol;
Write(ESC); Write('[');
IF amount > 1 THEN WriteCard(amount) END; (* default is 1 col *)
INC(curscol,amount+1);
Write('C');
END;
ELSE (* cursrow undefined or ch on a new line *)
MoveAbs(screenv,screenh);
cursrow := screenv;
curscol := screenh + 1; (* cursor will move right when ch written *)
END;
IF screenh = CARDINAL(windowwd) THEN (* ch will be written at right edge *)
cursrow := 0; (* so avoid auto wrap next time around *)
END;
END MoveQuick;
(******************************************************************************)
PROCEDURE VT220ShowChar (screenh, screenv : CARDINAL; ch : CHAR);
(* Show the given Terse character (mapped to ASCII) at the given position. *)
BEGIN
IF rectcount > 0 THEN (* flush Bitmap if ShowRectangle/s are pending *)
ShowBitmap;
END;
MoveQuick(screenh, screenv DIV vpixels);
Write(TeXtoASCII[ch]);
END VT220ShowChar;
(******************************************************************************)
PROCEDURE VT220ShowRectangle (screenh, screenv, (* top left pixel *)
width, height : CARDINAL; (* size of rectangle *)
ch : CHAR); (* black pixel *)
(* Set the given rectangular Bitmap region.
DVItoVDU ensures the top left position is visible and the given
dimensions do not go beyond the window edges.
*)
VAR h, v, vrow : CARDINAL;
BEGIN
FOR v := screenv TO screenv + height - 1 DO
FOR h := screenh TO screenh + width - 1 DO
(* set bit h,v in Bitmap *)
vrow := v DIV vpixels;
INCL (Bitmap [h,vrow], v MOD vpixels);
INCL (Bitmap [h,vrow], flag); (* flag so char will be sent *)
END;
END;
INC(rectcount);
IF rectcount = 400 THEN (* avoid too much of a pause before flushing Bitmap *)
ShowBitmap;
END;
END VT220ShowRectangle;
(******************************************************************************)
PROCEDURE VT220ResetVDU;
(* We don't do a hardware reset, but leave VDU in 80 column mode. *)
BEGIN
(* we should really save the state in InitVT220 and restore it here *)
Write(ESC); WriteString('[?3l'); (* 80 column mode *)
END VT220ResetVDU;
(******************************************************************************)
BEGIN
END vt220vdu.