;TYPRINTER v.3.0 3/6/86 ; by Richard Mack ; ; ;Typrinter is a deluxe "use-your-printer-as-a-typewriter" program. Use your ; word processor to modify the customizing block (found at the end of the ; program). Just change the "escape codes" to be appropriate to your ; printer and install your own return address. Don't forget to put a '$' ; at the end of each string as shown below. The codes in this distribution ; version are correct for the Panasonic KX-P1091 printer. ; ;To assemble with ASM.COM: ; ; A>ASM TYPRINT3 ; ;Then using LOAD.COM: ; ; A>LOAD TYPRINT3 ; ;The resulting TYPRINT3.COM file occupies just 2K and will prove handy for ; everything from addressing envelopes to writing notes and letters. ; ; conin equ 1h conout equ 2h lstout equ 5h direct equ 6h prints equ 9h bdos equ 5h plus equ 2bh minus equ 2dh bs equ 8h ht equ 9h lf equ 0ah ff equ 0ch cr equ 0dh ctrlz equ 1ah ;clear screen spc equ 20h rub equ 7fh screen equ 50h ;crt display width tbwdth equ 8h ;TAB width no equ 0 yes equ 0ffh ; org 100h ; ;set up local stack ; lxi h,0 ;clear HL dad sp ;get current stack pointer shld oldsp ;save it lxi sp,staktop ;set new stack pointer ; call clrscr ; ;print sign on message ; mvi c,prints lxi d,sinon call bdos call response ; ;xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx ; ;routine to set up printer type options ; ;print menu of type styles ; start call clrscr mvi a,yes ;initialize to sta itals ; allow italics ; lxi h,prst ;initialize printer call escout ; mvi c,prints ;setup to print menu string lxi d,typesel call bdos ; call response ;make selection of type style cpi 'C' jz cmprsd cpi 'L' jz lqual cpi 'P' jz pica cpi 'E' jz elite cpi 'O' jz prpnl cpi 1bh jz exitchoice mvi c,prints lxi d,nochange ;print "No change" message call bdos ; call response cpi 'Y' ;'Y' means use as is jnz exitchoice ; cmprsd mvi a,137d ;maximum char/line printer allows sta prntwdth ; in this mode - store it here lxi h,cprint ;point to location of first char in ; string commanding COMPRESSED print call escout ;send out escape sequence jmp dblnor ;go choose DOUBLE or NORMAL print ; lqual mvi a,80d sta prntwdth lxi h,lprint call escout jmp empnor ;EMPHASIS or NORMAL print ; pica mvi a,80d sta prntwdth lxi h,pprint call escout jmp dblempnor ;DOUBLE, EMPHASIS or NORMAL print ; elite mvi a,96d sta prntwdth lxi h,eprint call escout jmp dblempnor ; prpnl mvi a,86d ;this is data dependent - ; just a guess based on averages sta prntwdth lxi h,oprint call escout mvi a,no ;"no" means "no italics allowed" sta itals ; so set flag to skip them jmp dblempnor ; ;select print darkness ; dblnor mvi c,prints ;set up to print dbl/nor print menu lxi d,dnmess call bdos ; lxi h,nprnt ;initialize with NORMAL call escout ; print ESC sequence call response cpi 1bh jz exitchoice lxi h,dblprnt ;set up to send DOUBLE print ESC sequence cpi 'D' cz escout ;is a "D" so overwrite with DOUBLE print ; ESC sequence jmp widnor ; dblempnor mvi c,prints lxi d,denmess call bdos ; lxi h,nprnt call escout call response cpi 1bh jz exitchoice lxi h,dblprnt cpi 'D' cz escout lxi h,emprnt cpi 'M' cz escout jmp widnor ; empnor mvi c,prints lxi d,enmess call bdos ; lxi h,nprnt call escout call response cpi 1bh jz exitchoice lxi h,emprnt cpi 'M' cz escout ; ;fall thru to double/normal width choice ; widnor mvi c,prints ;set up to print width menu lxi d,wnmess call bdos ; lxi h,norwid ;initialize with NORMAL width call escout mvi a,screen ;set up for normal sta scrnwdth ; ruler line width call response cpi 1bh jz exitchoice lxi h,dblwid cpi 'D' jnz italnor call escout lda prntwdth ;get normal printer line length rrc ;divide by 2 ani 7fh ;mask MSB sta scrnwdth ;value to use for ruler line when double ; width print is selected sta prntwdth ;only half as many fit on printer now ; ;select italics or normal print ; italnor lda itals ;check to see if ora a ; italics are allowed jz papdet ; no, so skip to next choice ; mvi c,prints lxi d,inmess call bdos ; lxi h,rstital call escout call response cpi 1bh jz exitchoice lxi h,setital cpi 'I' cz escout ; ;fall thru to paper detector enable/disable ; papdet mvi c,prints lxi d,dispapdet call bdos ; lxi h,onpapdet call escout call response cpi 1bh jz exitchoice lxi h,offpapdet cpi 'Y' cz escout ; ;fall thru to return address choice ; retaddr mvi c,prints lxi d,rtnaddr call bdos ; mvi a,no ;initialize to "NO" sta prntaddr ; and store call response cpi 1bh jz exitchoice cpi 'Y' jnz scale mvi a,yes ;if "Y" then overwrite sta prntaddr ; and store ; ;print envelope reminder ; reminder mvi c,prints lxi d,envmess call bdos ; call response cpi 1bh jz exitchoice ; ;print numbers over ruler line ; scale call clrscr mvi c,prints lxi d,rulenum call bdos ; ;draw ruler line ; lda scrnwdth ;get appropriate ruler line width mov h,a ;let H hold this value inr h ; and add 1 to make comparison ok modfn mvi b,1h ;start rule width count at 1 mov a,b ;load value of width into A loop1 sui 5h ;subtract modulus (5 in this case) jp loop1 ;continue looping while residue is positive jz prntline ;residue is zero, so we're done, answer ; is in A adi 5h ;residue was negative, we overshot - so ; add modulus back in - and we're done, ; answer is in A ; ;if NmodM=0, print "+", else print "-" ; prntline push h! push b ;save the current value of desired and ; actual ruler line length mvi e,plus ;load a "+", but overwrite a "-" ; if NmodM is not 0 cz pchar ;zero flag still represents state of A mvi e,minus cnz pchar pop b ;restore B (length printed so far) inr b ;advance the ruleline count mov a,b ;get ready to take mod of count pop h cmp h ;is ruler line = desired length? jnz loop1 ;not done, so go do mod function again ; lda scrnwdth ;check if rule line = screen (usually 80d) cpi screen jz raddress ;is = to max screen width so jump to ; next function mvi c,prints ;need lf and a cr lxi d,lfcr ; when ruler is < screen call bdos ; raddress lda prntaddr cpi yes jnz text mvi c,prints lxi d,address call bdos ;send return address to printer lxi h,address call escout ;used above to send escape sequences ; but works for other characters too ; ;xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx ; ;routine to put text on screen and out to printer text xra a sta len ;initialize letter counter nextc mvi c,direct ;get next character mvi e,0ffh ;flag this as an call as input call call bdos cpi 0h ;no char entered, so loop until one is jz nextc cpi 1bh ;escape? yes, then jz exitchoice ; go choose exit or restart cpi cr ;carrage return? yes, so add lf, jz crlf ; and start new line cpi rub ;change rub to backspace jz eras ; and make it also erase last char cpi bs ;make backspace also jz eras ; erase last character cpi ht ;tab? yes, so enter jz tab ; tab expansion routine ; call line ;none of above, so it ; must be a regular ; character so add to string in memory mvi c,direct ;none of above, so it mov e,a ; must be a regular character, call bdos ; so print it on the screen lxi h,len ;increment letter counter inr m ; by 1 lda prntwdth ;get allowed printer line length mov b,a lda len ;get current string length (char count) cmp b ;is printer line full? jz crlf ; yes, start new line jmp nextc ; no, get next character ret ; line mvi d,0 ;initialize upper half of DE lxi h,len ;point at current string length (char cnt) mov e,m ;put current length lower half of DE lxi h,strbuf ;put addr of string buffer in HL dad d ;add to get addr (in HL) where current char ; will be put in string buffer mov m,a ;put current char in string buffer ret ; eras lda len ora a jz nextc ;if string length = 0 then do nothing mvi c,direct mvi e,bs ;backup call bdos mvi c,direct mvi e,spc ;erase call bdos mvi c,direct mvi e,bs ;and backup again call bdos lxi h,len dcr m ;and reduce the char count by one jmp nextc ; tab lda len ;get current line length (char count) loop2 sui tbwdth ;find line length mod tabwidth jp loop2 ; jz tabmod ; adi tbwdth ; tabmod sui tbwdth ;subtraction order reversed, so cma ; complement and add 1 to get positive inr a ; result (no. of spaces tab should add) jz nextc ;no spaces needed, so get next char push a ;store no. of spaces to be added loop3 mvi c,direct ;set up to print a space mvi e,spc ; call bdos ; mvi a,spc ;make space = current char, then add space call line ; to string buffer for TAB function lxi h,len ;setup to increment char count inr m ; when a space is added pop a ;a space is printed, so reduce dcr a ; the balance needed by 1 jz nextc ;balance=0? yes, so get next char push a ; no, then add jmp loop3 ; another space ; crlf mvi c,direct ;add a carrage return and mvi e,lf ; linefeed automatically when call bdos ; max line length is exceeded mvi c,direct mvi e,cr call bdos mvi a,lf ;setup to print a linefeed in call line ; the string buffer lxi h,len ;setup and increment inr m ; the character counter mvi a,cr ;setup to print a carriage return in call line ; the string buffer lxi h,len ;increment the character counter inr m ; one last time ; ;routine to have the printer dump the string buffer ; lxi h,strbuf ;point at beginning of buffer loop4 push h ;save current location mvi c,lstout ;set up to print a single character mov e,m ;load ASCII char from buffer call bdos lxi h,len ;reduce the character dcr m ; count by 1 pop h ;get back addr of current character inx h ; and bump the addr up by 1 jz text ;done? (i.e., did M set zero flag)? ; yes, then start the next line. jmp loop4 ; no? move to next character ; in buffer and set up to print it. ; ;xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx ; exit lhld oldsp ;restore old sphl ; stack pointer ret ;end of program - back to CP/M ; pchar mvi c,conout ;print ASCII character call bdos ret ; ; ;select either quit or restart at the top ; exitchoice mvi c,prints lxi d,exitmess call bdos ; call response cpi 'Q' jz eject ;last choice - eject paper? jmp start ; eject mvi c,prints lxi d,ejmess call bdos ; call response cpi 'Y' jnz exit mvi c,lstout mvi e,ff call bdos jmp exit ; response mvi c,direct ;setup to get response from kbrd using ; "direct console I/O" to surpress echo mvi e,0ffh ;ff flags this call as an "I", not an "O" call bdos ora a ;if 0, then no kbrd input yet, jz response ; so loop until keypressed ani 0dfh ;mask to upper case ret ; escout mov a,m ;load next character, compare with cpi '$' ; end-of-string marker rz ;return if string is done push h ;save current position in string mvi c,lstout ;set up to send character to printer mov e,a ;transfer character to be printed to E call bdos ;send it out pop h ;restore H (current position in string) inx h ;move index to next character in string jmp escout ;repeat until string done ; clrscr mvi e,ctrlz ;setup to clear screen mvi c,conout call bdos ret ; itals db yes sinon db ht,ht,ht,' ->>> TYPRINTER <<<-',lf,cr db ht,ht,' written by Richard Mack 6Mar86',lf,cr db lf,lf,ht,' Use at any time to quit or return ' db 'to the top of the Menu',lf,cr db lf,lf,lf,lf,lf,'Press any key to begin:',lf,cr,'$' rulenum db ' 10 20 30 40' db ' 50 60 70 80$' typesel db 'Select type style: (L)etter quality',lf,cr db ' (P)ica',lf,cr db ' (E)lite',lf,cr db ' (C)ompressed',lf,cr db ' pr(O)portional',lf,lf,lf,cr,'$' ; nochange db 'No change entered - will use current printer ' db 'setup - O.K.? (Y/N)',lf,lf,lf,cr,'$' ; dnmess db '(D)ouble print or (N)ormal?',lf,lf,lf,cr,'$' denmess db '(D)ouble print, e(M)phasis or (N)ormal?',lf,lf,lf,cr,'$' enmess db 'e(M)mphasis or (N)ormal?',lf,lf,lf,cr,'$' wnmess db '(D)ouble width or (N)ormal?',lf,lf,lf,cr,'$' inmess db '(I)talic or (N)ormal?',lf,lf,lf,cr,'$' dispapdet db 'Disable paper-end detector? (Y/N)',lf,lf,lf,cr,'$' rtnaddr db 'Type home address? (Y/N)',lf,lf,lf,cr,'$' envmess db 'Is printer set for envelope thickness? ' db '(Y/N)',lf,lf,lf,cr,'$' ; exitmess db lf,'(Q)uit or (B)egin new document/page or change ' db 'type style?',lf,lf,lf,cr,'$' ejmess db 'Eject paper? (Y/N)',lf,lf,lf,cr,'$' ; scrnwdth db screen ;actual width of screen prntaddr db no ;print ret addr -false initially ; ;xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx; ; ; ; CUSTOMIZE THIS SECTION TO YOUR REQUIREMENTS ; ; (don't forget to end each string with '$') ; ; ; ;install your return address: ; ; ; address db 'Richard F. Mack',lf,cr ; db '3407A Courtleigh Drive',lf,cr ; db 'Baltimore, MD 21207',lf,cr,'$' ; ; ; ;install the following sequences for your printer: ; ; ; ;print style escape sequences ; ; ; cprint db 0fh ;compressed ; db 1bh,'Q',89h,cr,'$' ;set right margin to 137d ; lprint db 1bh,'n',cr,'$' ;near-letter quality ; pprint db 1bh,'P',cr,'$' ;pica ; eprint db 1bh,'M',cr,'$' ;elite ; oprint db 1bh,'o',cr,'$' ;proportional ; ; ; dblprnt db 1bh,'G',cr,'$' ;double print ; emprnt db 1bh,'E',cr,'$' ;emphasis print ; nprnt db 1bh,'H',cr,'$' ;normal print ; ; ; dblwid db 1bh,'W','1',cr,'$' ;double width ; norwid db 1bh,'W','0',cr,'$' ;normal width ; ; ; setital db 1bh,'4',cr,'$' ;italic ; rstital db 1bh,'5',cr,'$' ;release italic ; ; ; onpapdet db 1bh,'9',cr,'$' ;enable paper detector ; offpapdet db 1bh,'8',cr,'$' ;disable paper detector ; ; ; prst db 1bh,'@',cr,'$' ;printer reset string ; ; ; ;xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx; ; lfcr db lf,cr,'$' ;line terminator for short ruler line ; len db 0 ;initial line length (char count) prntwdth db 0 ;initial value for printer line width strbuf ds 8eh ;string buffer (allow 140 characters, ; a linefeed and a carriage return) oldsp ds 2 ;old stack pointer value stkspace ds 20h staktop dw 0h ;top of stack ; end