home *** CD-ROM | disk | FTP | other *** search
- /* parseline.c -- (part of efr) Copyright © 1989 by William F. Hammond */
- /* -- breaks a string into LineParts */
- #ifndef TDM_H
- #include "tdm.h"
- #endif
- /*********************************************************************/
- struct LinePart *parseline(lpstr, lpp)
- UBYTE *lpstr;
- struct LinePart *lpp; /* address of previous LinePart */
- {
- struct LinePart *lp, *lpn; /* lp points to the LinePart herein */
- /* allocated; it is the return */
- /* lpn points to the successor of lp */
- register USHORT i;
- SHORT lastclear, lpl, controlcount;
- int isl;
- UBYTE *nstr; /* for recursive call to self */
- USHORT clearcount, lnctlseq, ctladj;
- UBYTE drawflag, fontflag;
- if(lpstr == NULL) return NULL;
- if(strlen(lpstr) == 0) return NULL;
- lp = (struct LinePart *)AllocMem(LPSZ, MEMF_CLEAR);
- if (lp == NULL)
- {
- fputs("parseline: Insufficient memory for LinePart\xa", stderr);
- if(lpp != NULL)
- {
- lp = lpp;
- while (lp)
- {
- lpn = lp->lp_Prev;
- FreeMem(lp, LPSZ);
- lp = lpn;
- }
- }
- return NULL;
- }
- lp->lp_Address = (ULONG)lpstr;
- lp->lp_Length = NULB;
- lp->lp_Move = NULB;
- lp->lp_FontStyle = NULB;
- lp->lp_DrawStyle = NULB;
- lp->lp_Next = (struct LinePart *)NULL;
- lp->lp_Prev = lpp;
- lp->lp_Trans = 0L;
- /* Examine the characters in lpstr; */
- isl = strlen(lpstr);
- if(lpstr[isl-1] == '\n')
- {
- lpstr[isl-1] = '\0';
- isl --;
- }
- lastclear = -1;
- i = 0;
- /****************** controlcount is the offset to lpstr for lp->lp_Address
- * lnctlseq detects the controlcount contribution of the current character
- * clearcount is the number of clear characters including accessory controls
- * ctladj is the number of accessory controls
- * clearcount and ctladj are used to set lp->lp_Length *******************/
- clearcount = 0; controlcount = 0; lnctlseq = 0, ctladj = 0;
- drawflag = NULB; fontflag = NULB;
- while (i < isl)
- {
- switch (lpstr[i])
- {
- case 0x08:
- {
- lnctlseq = 1;
- if(lastclear <0)
- {
- lp->lp_Trans -- ;
- controlcount += lnctlseq;
- ctladj += (lnctlseq -1);
- }
- break;
- }
- case 0x09:
- {
- lnctlseq = 1;
- if(lastclear <0)
- {
- lp->lp_Trans += 3;
- controlcount += lnctlseq;
- ctladj += (lnctlseq -1);
- }
- break;
- }
- case 0x1B:
- {
- if((lpstr[i+1] == '[') && (lpstr[i+3] == 'm'))
- {
- switch (lpstr[i+2])
- {
- case '0': /* plain font style and drawing style */
- {
- lnctlseq = 4;
- if(lastclear <0)
- {
- fontflag = 1;
- lp->lp_FontStyle = FS_NORMAL;
- drawflag = 1;
- lp->lp_DrawStyle = JAMX;
- controlcount += lnctlseq;
- ctladj += (lnctlseq -1);
- }
- break;
- }
- case '1': /* boldface font style */
- {
- lnctlseq = 4;
- if(lastclear <0)
- {
- fontflag = 1;
- lp->lp_FontStyle = lp->lp_FontStyle | FSF_BOLD;
- controlcount += lnctlseq;
- ctladj += (lnctlseq -1);
- }
- break;
- }
- case '3': /* italic font style */
- {
- lnctlseq = 4;
- if(lastclear <0)
- {
- fontflag = 1;
- lp->lp_FontStyle = lp->lp_FontStyle | FSF_ITALIC;
- controlcount += lnctlseq;
- ctladj += (lnctlseq -1);
- }
- break;
- }
- case '4': /* underlined font style */
- {
- lnctlseq = 4;
- if(lastclear <0)
- {
- fontflag = 1;
- lp->lp_FontStyle = lp->lp_FontStyle | FSF_UNDERLINED;
- controlcount += lnctlseq;
- ctladj += (lnctlseq -1);
- }
- break;
- }
- case '7': /* inverse video drawing style */
- {
- lnctlseq = 4;
- if(lastclear <0)
- {
- drawflag = 1;
- lp->lp_DrawStyle = (JAMX|INVERSVID);
- controlcount += lnctlseq;
- ctladj += (lnctlseq -1);
- }
- break;
- }
- default:
- {
- lnctlseq = 0; lastclear = i; clearcount ++; break;
- }
- }
- }
- else
- {
- lnctlseq = 0; lastclear = i; clearcount ++; break;
- }
- break;
- }
- case 0x86: /* move down */
- case 0x88:
- {
- lnctlseq = 1;
- if(lastclear <0)
- {
- lp->lp_Move = lp->lp_Move + 1;
- controlcount += lnctlseq;
- ctladj += (lnctlseq -1);
- }
- break;
- }
- case 0x87: /* move up */
- case 0x8A:
- {
- lnctlseq = 1;
- if(lastclear <0)
- {
- lp->lp_Move = lp->lp_Move - 1;
- controlcount += lnctlseq;
- ctladj += (lnctlseq -1);
- }
- break;
- }
- default:
- {
- lnctlseq = 0; lastclear = i; clearcount ++; break;
- }
- } /*** switch end ***/
- if( (lnctlseq) && (lastclear >= 0) ) break;
- i ++;
- } /*** loop (i < strlen(lpstr)) ***/
- lpl = lastclear + 1; /* offset of first char. in next LinePart */
- lp->lp_Address = (ULONG)lpstr + (ULONG)controlcount;
- if(controlcount > 0) clearcount = clearcount - ctladj;
- lp->lp_Length = (UBYTE)(clearcount);
- if(drawflag) lp->lp_DrawStyle ++;
- if(fontflag) lp->lp_FontStyle ++;
- if (lpl < isl)
- {
- if (lastclear >=0)
- { /* At least one more LinePart required */
- nstr = &lpstr[lpl];
- lp->lp_Next = parseline(nstr, lp);
- }
- else /* Nothing but control chars in lpstr, thus lpl = 0 */
- {
- lp->lp_Length = NULB; /* Signals "control changes only" */
- }
- }
- return lp;
- }
-