/* H/Z19 window terminal driver (16 Oct 1983 ACT) */ /* Copyright (c) 1983 University of Maryland Computer Science Department */ /* With thanks to Carl Binding at Univ of Washington, who did the orignal version and determined the padding requirements */ /* This driver runs the H/Z19 in either Heath/Zenith Mode or ANSI Mode, depending on the environment TERM setting. An 'a' in $TERM indicates that we should use ANSI mode. This tends to be faster at low baud rates since we can insert or delete many lines, and delete many characters, with one sequence, rather than one for each line or character. However, since the way the H19 does this is stupid, it requires much more padding. I haven't tested the ANSI mode at > 300 baud; it probably doesn't work. */ /* NOTE: If the bell rings, the 128 character input FIFO overflowed, which means there's not enough padding someplace. */ #include #include "Trm.h" #include "win.h" #include "cm.h" static int Ansi, curIns, curHL, desHL, curGraph; static modes (m) { desHL = m & WINVERSE; /* Only capable of inverse video */ } static setHL () { if (curHL != desHL) { if (Ansi) printf (desHL ? "\033[7m" : "\033[m"); else printf (desHL ? "\033p" : "\033q"); curHL = desHL; } } static INSmode (n) { if (curIns == n) return; if (Ansi) printf ("\033[4%c", n ? 'h' : 'l'); else printf ("\033%c", n ? '@' : 'O'); curIns = n; } static inslines (n) register n; { if (Ansi) { printf (n == 1 ? "\033[L" : "\033[%dL", n); cmpad (24 - curY - n, 1.0); } else { while (--n >= 0) { printf ("\033L"); cmpad (23 - curY, 1.0); } } } static dellines (n) register n; { if (Ansi) { printf (n == 1 ? "\033[M" : "\033[%dM", n); cmpad (24 - curY - n, 1.0); } else { while (--n >= 0) { printf ("\033M"); cmpad (23 - curY, 1.0); } } } static delchars (n) register n; { if (Ansi) { printf (n == 1 ? "\033[P" : "\033[%dP", n); cmpad (80 - curX - n, 1.0); } else { while (--n >= 0) { printf ("\033N"); cmpad (80 - curX, 1.0); } } } static writechars (start, end) register char *start, *end; { setHL (); cmplus (end-start+1); while (start <= end) { if (*start & 0x80) { if (curGraph == 0) { printf (Ansi ? "\033[10m" : "\033F"); curGraph++; } putchar (*start++ & 0x7f); } else { /* 0x5e-0x7e are the only graphics chars */ if (curGraph && *start >= 0x5e) { printf (Ansi ? "\033[11m" : "\033G"); curGraph = 0; } putchar (*start++); } if (curIns) cmpad (1, 2.0); } } static blanks (n) register n; { setHL (); cmplus (n); while (--n >= 0) { putchar (' '); if (curIns) cmpad (1, 2.0); } } static topos (row, col) { cmgoto (row-1, col-1); /* let cm routines handle it */ } static init (BaudRate) { float BaudFactor = BaudRate/10000.; cmcostinit (); W_tt.t_ILmf = Ansi ? 0 : 2 + BaudFactor*5.;/* approx */ W_tt.t_ILov = Ansi ? 3 + BaudFactor*5. : 0;/* " */ W_tt.t_DCmf = Ansi ? 0 : 2 + BaudFactor*5.;/* " */ W_tt.t_DCov = Ansi ? 3 + BaudFactor*5. : 0;/* " */ W_tt.t_ICov = Ansi ? 4 : 2; W_tt.t_ICmf = BaudFactor*2.; return 0; } static reset () { /* Clear screen, out of graphics mode, no autowrap, block cursor, overwrite mode, normal video */ if (Ansi) printf ("\033[2J\033[0;11m\033[?7l\033[>4h\033[4l"); else printf ("\033E\033G\033w\033x4\033O\033q"); cmat (0, 0); cmpad (1, 10.0); curIns = 0, curGraph = 0, curHL = 0; } static cleanup () { desHL = 0; setHL (); INSmode (0); if (curGraph) printf (Ansi ? "\033[11m" : "\033G"); printf (Ansi ? "\033[?7h" : "\033v");/* autowrap back on */ /* SHOULD DO SOMETHING ABOUT SWITCHING TO UNDERSCORE CURSOR IF THAT IS PREFERRED */ } static wipeline () { printf (Ansi ? "\033[K" : "\033K"); cmpad (80 - curX, 0.1); } static wipescreen () { printf (Ansi ? "\033[2J" : "\033E"); cmat (0, 0); cmpad (1, 2.5); /* so why 10.0 in reset()? */ } static donerefresh () { if (curGraph) { printf (Ansi ? "\033[11m" : "\033G"); curGraph = 0; } } TrmH19 (term) register char *term; { Ansi = 0; while (*term) if (*term++ == 'a') Ansi++; W_tt.t_INSmode = INSmode; W_tt.t_modes = modes; W_tt.t_inslines = inslines; W_tt.t_dellines = dellines; W_tt.t_blanks = blanks; W_tt.t_init = init; W_tt.t_cleanup = cleanup; W_tt.t_wipeline = wipeline; W_tt.t_wipescreen = wipescreen; W_tt.t_topos = topos; W_tt.t_reset = reset; W_tt.t_delchars = delchars; W_tt.t_writechars = writechars; W_tt.t_donerefresh = donerefresh; W_tt.t_length = 24; W_tt.t_width = 80; W_tt.t_frames[0] = 'f' | 0x80;/* ulc */ W_tt.t_frames[1] = W_tt.t_frames[6] = 'a' | 0x80;/* top, bottom */ W_tt.t_frames[2] = 'c' | 0x80;/* urc */ W_tt.t_frames[3] = W_tt.t_frames[4] = '`' | 0x80;/* left, right sides */ W_tt.t_frames[5] = 'e' | 0x80;/* llc */ W_tt.t_frames[7] = 'd' | 0x80;/* lrc */ Up = Ansi ? "\033M" : "\033A"; Down = "\n"; Left = "\b"; Right = Ansi ? "\033[C" : "\033C"; Home = Ansi ? "\033[H" : "\033H"; CR = "\r"; Tab = "\t"; TabWidth = 8; AbsPosition = Ansi ? "\033[%i%d;%dH" : "\033Y%+ %+ "; UseTabs = 1; ScreenRows = W_tt.t_length; ScreenCols = W_tt.t_width; Wcm_init (0); return 0; }