program ChkPrinter; {keith ball printer experiment on NEC 7710} {October 27 1982} const kbrd = 35; {keyboard unit number} printer = 6; {printer unit number} ControlZ = $1A; ControlA = $01; ControlB = $02; ControlC = $03; ControlD = $04; ControlE = $05; ControlF = $06; ControlP = $10; bs = $08; {back space} lf = $0A; {line feed} ff = $0C; {form feed} cr = $0D; {carriage return} tab = $09; {tab} esc = $1B; {escape} bell = $07; {bell} space = $20; {ascii blank char} RubberSP = $A0; {Alt space} NoLf = 1; ShdwON = $2B; {+} ShdwOFF = $2C; {,} USon = $2D; {-} USoff = $27; {'} HalfLF = $3A; {:} NHalfLF = $3B; {;} RevrsLF = $39; {9} NoEntry = -1; NormFAdv = '\1B]W'; {normal form advance distance} SubSupFAdv = '\1B]Q'; {used for Subscript and Superscript} type byte = -128..127; str3 = string[3]; str5 = string[5]; var ch,strikechar : byte; i,SendRaw,chcount,pspNumCh : integer; spNChfirst,spNChsecond,ich : integer; pspseq1,pspseq2 : str3; US,Shdw,SC,Super,Sub,PropSP,Alt : boolean; AltIndexTbl : array[1..96] of byte; AltCharSeq : array[1..96] of str5; prntr : interactive; function cnv( b : byte) : integer; Begin if b < 0 then cnv := 256 + b else cnv := b; End; {cnv} procedure display(ch: byte); var ch1 : byte; Begin if (ch>=0) and (ch<=$1F) and (NOT(ch in [bell,bs,lf,cr])) then {control character} if ch=esc then write('|Esc|') else if ch=tab then write(' ') {tab=10 spaces} else write('^',chr(ch+$40)) else if ch<0 then begin ch1 := ch+128; if (ch1>=0) and (ch1<=$1F) then write('|alt-^',chr(ch1+$40),'|') else write('|alt-',chr(ch1),'|'); end else write(chr(ch)); End; {display} procedure SendPrinter(ch : byte); begin write( prntr, chr(ch) ); end; {SendPrinter} procedure SendSeq(s : str3); Begin write(prntr,s); End; {SendSeq} procedure Overstrike; const olen = 3; var ch : array[1..4] of byte; Begin ch[2] := bs; unitread(kbrd,ch[1],1); write('|over|'); display(ch[1]); unitread(kbrd,ch[3],1); write(','); display(ch[3]); write('|'); unitwrite(printer,ch,olen,0,NoLF); chcount := chcount + 1; End; {Overstrike} procedure getsoc; var soc : char; Begin write('Enter strike out char: '); read(soc); writeln; strikechar := ord(soc); End;{getsoc} procedure PrSO; Begin SC := NOT SC; write(' *Strikeout '); if SC then begin write('ON* '); getsoc; end else begin SC := FALSE; write('OFF* '); strikechar:= space; end; End; {PrSO} procedure Underline; Begin US := NOT US; SendPrinter(esc); write(' *Underline '); if US then begin SendPrinter(USon); write('ON* '); end else begin SendPrinter(USoff); write('OFF* '); end; End; {Underline} procedure Shadow; Begin Shdw := NOT Shdw; SendPrinter(esc); write(' *Shadow '); if Shdw then begin SendPrinter(ShdwON); write('ON* '); end else begin SendPrinter(ShdwOFF); write('OFF* '); end; End; {Shadow} procedure Superscript; Begin if Sub then begin writeln('Doing Subscript'); exit(Superscript); end; Super := NOT Super; {change LF length} SendSeq(SubSupFAdv); write(' *Superscript '); if Super then {do neg 1/2 LF} begin SendPrinter(esc); SendPrinter(RevrsLF); write('ON* '); end else begin {return to line} SendPrinter(lf); write('OFF* '); end; {change LF length back} SendSeq(NormFAdv); End;{Superscript} procedure Subscript; Begin if Super then begin writeln('Doing Superscript'); exit(Subscript); end; Sub := NOT Sub; {change LF length} SendSeq(SubSupFAdv); write(' *Subscript '); if Sub then begin SendPrinter(lf); write('ON* '); end else begin {return to line} SendPrinter(esc); SendPrinter(RevrsLF); write('OFF* '); end; {change LF length back} SendSeq(NormFAdv); End;{Subscript} procedure Strikeout; var SvSub,SvSuper : boolean; Begin SvSub := Sub; {use minus sign} SvSuper := Super; if SvSub then Subscript; if SvSuper then Superscript; SendPrinter(bs); SendPrinter(strikechar); if SvSub then Subscript; if SvSuper then Superscript; End; {Strikeout} procedure PropSPOn; var NumCh,NumPads,NumExtras : integer; Begin if PropSP then begin writeln('already doing proportional spacing.'); exit(PropSPOn); end; pspNumCh := 0; spNChfirst := 0; spNchsecond := 0; write('Enter number of chars on line : '); readln(NumCh); write('Enter number of chars to pad : '); readln(NumPads); if (NumPads <= 0) then begin if (NumPads < 0) then writeln('invalid number'); exit(PropSPOn); end; {calc number of extras needed for each char} NumExtras := NumPads * 12; {number of 120th" for 10 pitch} Numch := NumCh - 1; {must have even right margin} {do case to figure out value of first and second} if ((3*NumCh) < NumExtras) then begin writeln('To many pads.'); exit(PropSPOn); end; if (NumExtras <= NumCh) then begin spNChfirst := NumExtras; pspseq1 := '\1B]M';{13/120"} pspseq2 := ''; {normal for rest} end else if (NumExtras <= (2 * NumCh)) then begin spNChfirst := NumExtras - NumCh; pspseq1 := '\1B]N';{14/120"} spNChsecond := NumCh - spNCHfirst; pspseq2 := '\1B]M';{13/120"} end else if (NumExtras <= (3 * NumCh)) then begin spNChfirst := NumExtras - (2 * NumCh); pspseq1 := '\1B]O';{15/120"} spNChsecond := NumCh - spNCHfirst; pspseq2 := '\1B]N';{14/120"} end; {send sequence for first if any} SendSeq(pspseq1); PropSP := TRUE; pspNumCh := spNChfirst; End; {PropSpOn} procedure PropSPOff; Begin if (spNChsecond <> 0) then begin pspNumCh := spNChsecond; spNChsecond := 0; {send 2nd sequence for spacing} SendSeq(pspseq2); end else begin PropSP := FALSE; {send restore sequence} SendSeq('\1B]L' {12/120"}); {10 pitch} end; End; {PropSpOff} procedure InitAltTbls; const ALTucA = $C1; {alternate upper case A} ALTlca = $E1; {alternate lower case a} var i : integer; Begin for i := 1 to 96 do AltIndexTbl[i] := NoEntry; for i := 1 to 96 do AltCharSeq[i] := ''; AltIndexTbl[ (ALTucA - RubberSP) + 1 ] := 1; AltCharSeq[1] := 'A\08"'; AltIndexTbl[ (ALTlca - RubberSP) + 1 ] := 2; AltCharSeq[2] := 'a\08"'; End; {InitAltTbls} procedure AltChar( altch : byte ); var i,k,m : integer; procedure DoAltCtl; {what about alternate control characters} Begin altch := i - 128; {remove hi bit} SendPrinter(altch); {send as control char} End; {DoAltCtl} Begin i := cnv(altch); if (i 0 then begin writeln('Cannot open /printer.'); exit(ChkPrinter); end; writeln; writeln('Echo character input from keyboard to printer and screen.'); writeln('Press CONTROL-Z to stop.'); writeln('Press CONTROL-A to do 1 overstrike.'); writeln('Press CONTROL-B to toggle strikeout.'); writeln('Press CONTROL-C to toggle Shadow.'); writeln('Press CONTROL-D to toggle Underscore.'); writeln('Press CONTROL-E to toggle Superscript.'); writeln('Press CONTROL-F to toggle Subscript.'); writeln('Press CONTROL-P to turn-on Proportional Spacing for 1 line'); writeln; Shdw := FALSE; US := FALSE; SC := FALSE; Super := FALSE; Sub := FALSE; PropSP := FALSE; chcount := 0; strikechar := space; repeat unitread(kbrd,ch,1); if ch<0 then ich := 256+ch else ich := ch; CASE ich OF ControlA : Overstrike; {normally build state machine } ControlB : PrSO; {to parse character stream. For} ControlC : Shadow; {Alt chars just alter source of } ControlD : Underline; {input stream. } ControlE : Superscript; ControlF : Subscript; ControlP : PropSPOn; RubberSP : display(ch); {show to user} Otherwise: begin display(ch); if (ch=cr) or (ch =ControlZ) then begin SendPrinter(cr); {always send cr} {turn back on enhancements printer turns off} if Shdw then write(prntr,chr(esc),chr(ShdwON)); if US then write(prntr,chr(esc),chr(USon)); spNChsecond := 0; {force it off} if PropSP then PropSPoff; chcount := 0; {last in cr processing} end else begin if ch < 0 then AltChar(ich) else begin chcount := chcount+1; SendPrinter(ch); if (SC) then Strikeout; if (PropSP) then begin pspNumCh := pspNumCh - 1; if pspNumCh = 0 then PropSPoff; end; end; end; end; end;{case} until(ch=ControlZ); writeln; END.