home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Current Shareware 1994 January
/
SHAR194.ISO
/
dos_util
/
pcmcvt.zip
/
PCMASM.ZIP
/
WORDWRAP.INC
< prev
next >
Wrap
Text File
|
1993-04-22
|
7KB
|
210 lines
;WORDWRAP.INC
;Copyright (c) 1993 Jay Munro
;First Published in PC Magazine June 29 1993
;Word wrap function for PCMCVT.COM
;
;Variables used by for Word wrap
LastSpc DW 0
LastLen DW 0
KeepCX DW 0
WriteCount DW 0
CurLine DW 0
WordWrap Proc Near Uses BX DI SI CX, WBuffer:Word, WBLen:Word
;-----------------------------------------------------------------------
;get address of buffer, and length
Mov DI, WBuffer ;get addr of write buffer
Mov SI, DI
Mov BX, WBLen ;save length of buffer in BX
Mov CX, BX ;use CX as a counter
Mov DX, MaxWidth ;value for width
Or DX,DX ;is it 0?
Jnz @F
Mov DX,78 ;force 78 characters
Mov MaxWidth,DX ;save it too
@@:
Cld ;forward direction
Cmp DX,LastLen ;check last len for bogus size
Jg CRLFLoop1
Mov Word Ptr LastLen, 0 ;clear it
;-----------------------------------------------------------------------
CRLFLoop1: ;checks first for CRLF's
Mov KeepCX,CX ;store CX for a moment
Mov AL, 13 ;check for that CRLF
RepNe ScaSb ;scan for that CRLF
Mov AX,BX ;get len
Sub AX,CX ;ax = length now
Mov CurLine,AX ;save size
Cmp Byte Ptr [DI],10 ;is the next character a lf?
Jnz @F ;nope, skip it
Inc CurLine ;bump count
@@:
Add AX,LastLen ;if last length was anything...
Cmp AX,DX ;check its length
Jg PreScanLoop
Call WriteCurLine
Mov AX,CurLine ;get last position
Add SI,AX ;add it to our address
Mov DI,SI ;set DI for Scan
Sub BX,AX ;adjust BX (length of buffer)
Jcxz WWDoneLp2 ;if we're out of bytes
Mov Word Ptr LastLen,0 ;clear last len
Jmp CRLFLoop1
PreScanLoop:
Mov DX, MaxWidth ;retread DX
Mov CX,KeepCX
Mov DI,SI ;reset DI
;-----------------------------------------------------------------------
ScanLoop:
Mov AL, 32 ;load AL with space character
RepNe ScaSb ;look for that first space
Mov AX, BX ;get length
Sub AX, CX ;see difference
Mov CurLine,AX ;save current length
Add AX, LastLen ;add in the last length
Cmp AX, DX ;check line length against width
Jg Decision2Make ;if it's greater, exit
Mov AX,CurLine ;otherwise get current position
Mov LastSpc,AX ;and save it as last space
Jmp ScanLoop ;go back for more
WWDoneLeap:
Call WriteCurLine ;write it
WWDoneLp2:
Mov AX,CurLine ;get last length
Mov LastLen,AX
Jmp WWDone
Decision2Make: ;decide where to break
;at this point, DI points to the next character, AX = number of chars
;since last write crlf and BX contains starting point
Cmp Word Ptr LastSpc,0 ;ok, do we have at least some characters?
Jz @F
Jmp WritePartial
@@:
Cmp Word Ptr CurLine,0 ;how about Curline
Jz @F
Mov AX,CurLine ;set last space
Mov LastSpc,AX
Jmp WritePartial
@@:
Cmp Word Ptr LastLen,0 ;was last length something?
Jz @F
Sub DX,LastLen ;adjust what we write
@@:
Mov CurLine,DX ;adjust current line
Call WriteCurLine
PushF ;preserve flags through sub
Sub BX,DX
PopF
Mov CX,BX ;retread counter
Jnc BackForMore ;check carry and write CRLF
Jmp WWExit ;error exit
SetCRLF DB 0 ;send crlf flag
WritePartial:
Cmp Word Ptr LastLen,0
Jz @F
Mov Word Ptr LastLen,0 ;reset LastLen
@@:
Push BX
Push DX
Push CX
Push SI ;save pointer
Mov CX, LastSpc ;put size into CX
PartialCut:
Cmp CX, MaxWidth
Jle DoPartial
Call CutLoop
Jmp PartialCut
DoPartial:
Call CheckNextChar ;check for leading space
Invoke Write, DHandle, SI, CX
Pop SI
Pop CX
Pop DX
Pop BX
Sub BX,LastSpc
Mov CX,BX
BackForMore: ;Set crlf into file
Push BX
Push DX
Push CX
Invoke Write, DHandle, Addr CRLF,2 ;print a crlf
Pop CX
Pop DX
Pop BX
Mov byte Ptr SetCRLF,-1
Add SI,LastSpc ;bring us up to the current location
Mov DI,SI ;
Mov AX,LastSpc ;
Mov Word Ptr LastSpc, 0
Mov Word Ptr LastLen,AX ;preserve last length of line
Jcxz WWDone
Mov Word Ptr LastLen,0
Jmp CRLFLoop1
WWDone:
WWExit:
Ret
WriteCurLine:
Push BX ;preserve our registers too
Push CX ; ditto
Push DX
Push SI
Mov CX, CurLine ;put size into CX
CheckMWidth:
Cmp CX, MaxWidth ;if current spot is greater than max width
Jle FineLine ;then cut it up
Call CutLoop
Jmp CheckMWidth ;go back and check again
FineLine:
Call CheckNextChar
Invoke Write, DHandle, SI, CX ;write it
PopOut:
Pop SI
Pop DX ;retrieve regs
Pop CX
Pop BX
RetN
CheckNextChar: ;trims leading spaces from word wrapped
;lines
Cmp Byte Ptr SetCRLF,-1 ;ok, did we send a crlf last time?
Jnz @F ;nope, just print it.
CheckNSpace: ;this clips leading spaces after CRLF
Cmp Byte Ptr [SI], 32 ;is the next character a space?
Jnz @F ;no, skip
Inc SI ;ok point to the next one
Loop CheckNSpace ;bump back
@@:
Mov Byte Ptr SetCRLF,0 ;ok, did we send a crlf last time?
RetN
CutLoop:
Sub CX,MaxWidth ;deduct maxwidth
Push CX ;save CX
Invoke Write, DHandle, SI, MaxWidth ;write only maxwidth # of char's
Invoke Write, DHandle, Addr CRLF,2 ;print a crlf
Pop CX ;retrieve CX
Add SI,MaxWidth ;adjust pointer to buffer
RetN
WordWrap EndP