/* Hist 1/19/84 SR Removed two buffer flushes in openwork 3/07/84 SR Index 1 is pen 1 3/08/84 SR Cleaned up text to output a whole string */ #include "ratdef.h"; #define MAXxHIxBUFFER 80 #define MOVE 1 #define DRAW 2 #define YES 1 #define NO 0 #define UNSUCCESSFUL 0 /* Unsuccessful GIN operation */ #define SUCCESSFUL 1 /* Unsuccessful GIN operation */ #define DEFAULT 1 /* Default GIN device number */ #define PLOTTER 6 /* Plotter device number for GIN */ int max0(), min0(); unsigned int wxmin, wymin, wxmax, wymax; int x_fetch(), y_fetch(); #include "ddcom.h" int pens[9], clrred[9], clrgrn[9], clrblu[9]; int conoff, iinoff, pinoff, ioutoff, poutoff, LFETCH(); int conseg, iinseg, pinseg, ioutseg, poutseg; DDHI29 (paraseg,paraoff) int paraoff,paraseg; { /************************************************************************ * * * Function: Device Driver for Houston Instruments DM29 plotter * * * * Input Parameters: * * paraseg - parameter segment * * paraoff - parameter offset * * * * Output Parameters: * * none * * * * Routines Called: * * Dbufhi - buffered output for HI plotter * * Gznfpl - prompt the user for a new sheet of paper * * DrDMPx - move/draw for HI plotter * * DpDMPx - Change pens on the HI DMPx plotter * * DtDMPx - Set text size on HI DMPx plotter * * Gitoch - convert integer to characters * * Gchtoi - convert character string to integer * * Gimnmx - Function to place integer value in a range * * * ************************************************************************/ int i2; int opcode; int i, j, gimnmx(), ierror, ival, istop, tries, ginok, icnvt[6], ibuf[90]; unsigned int xy[2], savexy[2]; int temp, gitoch(), length; unsigned int x1, y1, x2, y2; unsigned int hlfsiz, fulsiz; static penstring[] = {BIGE, BIGN, BIGT, BIGE, BIGR, SP, BIGT, BIGH, BIGE, SP, BIGN, BIGU, BIGM, BIGB, BIGE, BIGR, SP, BIGO, BIGF, SP, BIGP, BIGE, BIGN, BIGS, SP, BIGO, BIGN, SP, BIGY, BIGO, BIGU, BIGR, SP, BIGP, BIGL, BIGO, BIGT, BIGT, BIGE, BIGR, COLON, SP, -1}; /* Start arc definition /CA */ static int arcstart[] = {BIGC, BIGA, SP}; /* Set label(text) font /S(NI,G) / */ static int setfnt[] = {BIGS, LPAREN, BIGN, BIGI, COMMA, BIGG, 0, RPAREN, ETX, SP}; /* four possible rotation commands: 0 degrees - /S(X0,Y-1)ETX / 90 degrees - /S(X1,Y0)ETX / 180 degrees - /S(X0,Y1)ETX / 270 degrees - /S(X-1,Y0)ETX / */ static int rot0[] = {BIGS, LPAREN, BIGX, DIG0, COMMA, BIGY, MINUS, DIG1, RPAREN, ETX, SP}; static int rot90[] = {BIGS, LPAREN, BIGX, DIG1, COMMA, BIGY, DIG0, RPAREN, ETX, SP}; static int rot180[] = {BIGS, LPAREN, BIGX, DIG0, COMMA, BIGY, DIG1, RPAREN, ETX, SP}; static int rot270[] = {BIGS, LPAREN, BIGX, MINUS, DIG1, COMMA, BIGY, DIG0, RPAREN, ETX, SP}; int *rotstr[4]; static int rotleng[] = {11, 10, 10, 11}; /* Text output set up /S()/ */ static int txtout[] = {BIGS, LPAREN, RPAREN}; /* Text termination /etx / */ static int txtstop[] = {ETX, SP}; /* Marker size, output /M / */ static int mrkout[] = {BIGM}; /* Line style /L<0> / */ static int lstyle[] ={BIGL, 0, SP}; /* Set line style to solid /L0 / */ static int solid[] = {BIGL, DIG0, SP }; /* Set up - Turn plotter on ;: Set handshake mode 2 I0D 10 */ static int setup[] = {SEMICOL, COLON, SP, SEMICOL, COLON, BIGI, DIG0, BIGD, SP, DIG1, DIG0, SP }; /* Initialize plotter - Text S() Text terminator ET03 0.005 addressing EC5 */ static int setup2[] = { BIGE, BIGT, DIG0, DIG3, SP, BIGS, LPAREN, RPAREN, ETX, BIGE, BIGC, DIG5,SP }; /* Set text slope S(S4,X0,Y-1)ETX */ static int setslpe[] = {BIGS, LPAREN, BIGS, DIG3, COMMA, BIGX ,DIG0, COMMA, BIGY, MINUS, DIG1, RPAREN, ETX }; static int mrktbl[] = {4, 0, 0, 3, 1, 2, 5}; static int mrksize[] = {8, 16, 32, 64, 128}; static int mrkszext[] = {12, 24, 48, 96, 20000}; static int inqsta[] = {BIGE, BIGR, SP}; static int getgin[] = {BIGE, BIGD, SP}; static int penzero[] = {BIGP, DIG0}; static int comma = COMMA; static int endtxt = ETX; static int space = SP; static int home[2] = {0, 420}; static int iniino[45] = { /* initial intout array for open workstation*/ 0,0, METERS, /* Device coordinates are meters */ 127, /* Step size in micrometers on x axis */ 127, /* Step size in micrometers on y axis */ 253, /* Number of character heights (continuous) */ 11, /* Number of line types */ 1, /* Number of line widths */ 8, /* Number of marker types */ 9, /* Number of marker sizes (continuous) */ 16, /* Number of text fonts */ 0, /* Number of patterns */ 6, /* Number of hatch styles */ 0, /* Number of predefined colors */ 2, /* Number of GDPs */ 1,1,-1,-1,-1, /* Bars and Arcs */ -1,-1,-1,-1,-1,3,0,-1,0,-1,-1,-1,-1,-1,-1, 1, /* Device is capable of color */ 1, /* Device is capable of text rotation */ 1, /* Device is capable of filled area */ 0, /* Device is not capable of pixel operations*/ 0, /* Number of colors available (continuous */ /* pen colors) */ 1, /* Number of locator devices available */ 0, /* Number of valuator devices available */ 0, /* Number of choice devices available */ 0, /* Number of string devices available */ 2}; /* Workstation type (input/output) */ static int inipto[12] = { /* initial ptsout array for open workstation */ 0, 21, /* Minimum character height in DC space */ 0, 1785, /* Maximum character height in DC space */ 1, /* Minimum line width in DC space */ 0, 1, /* Maximum line width in DC space */ 0, 0, 8, /* Minimum marker height in DC space */ 0, 128 /* Maximum marker height in DC space */ }; int mrkextra; conoff=LFETCH(paraseg,paraoff,0); conseg=LFETCH(paraseg,paraoff,1); iinoff=LFETCH(paraseg,paraoff,2); iinseg=LFETCH(paraseg,paraoff,3); pinoff=LFETCH(paraseg,paraoff,4); pinseg=LFETCH(paraseg,paraoff,5); ioutoff=LFETCH(paraseg,paraoff,6); ioutseg=LFETCH(paraseg,paraoff,7); poutoff=LFETCH(paraseg,paraoff,8); poutseg=LFETCH(paraseg,paraoff,9); rotstr[0]=rot0; rotstr[1]=rot90; rotstr[2]=rot180; rotstr[3]=rot270; opcode=LFETCH(conseg,conoff,OPCODE); LSTORE(conseg,conoff,2,0); /*Assume no vertices are being passed back*/ /* opcode open workstation */ switch (opcode) { case OPENxWORKSTATION: LSTORE(conseg,conoff,2,6); /* Set to number of output vertices */ LSTORE(conseg,conoff,4,45); /* Length of array intout */ /* set up output capability array */ for (i=0;i<45;++i) LSTORE(ioutseg,ioutoff,i,iniino[i]); for (i=0;i<12;++i) LSTORE(poutseg,poutoff,i,inipto[i]); ndlntp = max0 (LFETCH(iinseg,iinoff,1)-1, 0); /*Set current device line style*/ if (ndlntp > 6) ndlntp = 0; ndclrl = max0 (LFETCH(iinseg,iinoff,2), 1); /*Set current polyline color index*/ ndmktp = LFETCH(iinseg,iinoff,3); /*Set current marker type*/ if (ndmktp < 1 | ndmktp > 7) ndmktp=3; ndclrm = max0 (LFETCH(iinseg,iinoff,4), 1); /*Set current polymarker color index*/ /*Set current text font*/ ndclrt = max0 (LFETCH(iinseg,iinoff,6), 1); /*Set current text color index*/ ndclrf = max0 (LFETCH(iinseg,iinoff,9),1); /*Set current fill area color index*/ ndstyf = max0 (LFETCH(iinseg,iinoff,8),1); /*Set current fill style index*/ if (ndstyf > 6)ndstyf = 1; ndistyf = max0 (LFETCH(iinseg,iinoff,7),0); /*Set current fill interior style*/ if (ndistyf > 3)ndistyf = 0; ndmkht = 0; mrkextra = 0; /*Set default marker height */ ndtysz = 8; /*Set default character height 8*/ ndtxrt = 0; /*Set default rotation to 0 degrees*/ ndclrp = -1; /*Set current device color */ /*Prompt for number of pens*/ i=0; do TTYOUT(penstring[i]); while (penstring[++i]>=0); TTYIN(&i); TTYOUT(i); TTYOUT(CR); TTYOUT(LF); nmbrpens = gimnmx(i-DIG0, 1, 8); LSTORE (ioutseg,ioutoff,13,nmbrpens); /*initialize plotter */ ndotkt = 0; /*Initialize the plotter ouput counter. This */ /* counter is used by the routine 'dbufhi' */ dbufhi (12, setup); /*Must use outstr because block mode is set */ /*in initialization sequence. */ dbufhi (13, setup2); if (nmbrpens != 8) { PCHOUT(CR); PCHOUT(CR); for (i=0; i<32760; ++i) j=i-i; LSTORE (ioutseg, ioutoff, 40, 0); /*DMP 40 cannot locate */ } /*Set line type to initial value */ dbufhi (2,penzero); /* put pen down */ lstyle[1] = ndlntp+DIG0; dbufhi (3, lstyle); dtDMPx (ndtysz); /*Set initial text size */ dbufhi (3, inqsta); /*Get the current window size*/ instr (90,ibuf,&i); for (i=24;(i<28) && (ibuf[i]<'0' || ibuf[i]>'9');++i); gchtoi (ibuf,i,&wxmin,&i); gchtoi (ibuf,i+2,&wymin,&i); gchtoi (ibuf,i+2,&wxmax,&i); gchtoi (ibuf,i+2,&wymax,&i); LSTORE (ioutseg,ioutoff,1,wxmax-wxmin); LSTORE (ioutseg,ioutoff,0,wymax-wymin); dbufhi (13, setslpe); nmbrfonts = 16; i = max0 (LFETCH(iinseg,iinoff,5), 1); if (i>nmbrfonts) i=1; --i; if (i>7) { i -= 8; setfnt[2]=SP; } else setfnt[2]=BIGN; setfnt[6] = i + DIG0; dbufhi (10, setfnt); /*Output command */ for (i=0; i<=nmbrpens; ++i) pens[i] = i; /*Station 1 holds index 1 */ clrred[0] = 0; /*Define color index 0 to black */ clrgrn[0] = 0; clrblu[0] = 0; for (i=1;i<=nmbrpens;++i) { clrred[i] = 1000; /*Define color index 1 to white */ clrgrn[i] = 1000; clrblu[i] = 1000; } break; /* opcode close workstation */ case CLOSExWORKSTATION: drDMPx (MOVE, home); dbufhi(2,penzero); break; /* opcode clear workstation */ case CLEARxWORKSTATION: dbufhi(2,penzero); drDMPx (MOVE, home); /*Home the plotter */ dbufhi (-1, home); /*Dump buffer */ gznfpl(); /*prompt user for new paper (new frame on plotter) */ ndclrp = -1; /*Force plotter to pick up pen again */ break; /* opcode update workstation */ case UPDATExWORKSTATION: dbufhi (-1, home); break; /* opcode escape */ case ESCAPE: if (LFETCH(conseg,conoff,5) == INQxADDRESSABLExCELLS) { LSTORE(ioutseg,ioutoff,0,-1); LSTORE(ioutseg,ioutoff,1,-1); } break; /* opcode polyline */ case POLYLINE: dpDMPx (ndclrl); /*Change color to line color */ xy[0]=x_fetch(0); xy[1]=y_fetch(0); drDMPx (MOVE, xy); /*Move to first point */ j = 2; for (i=2; i<=LFETCH(conseg,conoff,1); ++i) {/*Draw between subsequent pts */ xy[0]=x_fetch(j); xy[1]=y_fetch(j); drDMPx (DRAW, xy); j += 2; } j -= 2; xy[0]=x_fetch(j); xy[1]=y_fetch(j); drDMPx (MOVE, xy); /*Move to pick up the pen */ break; /* opcode polymarker */ case POLYMARKER: dpDMPx (ndclrm); /*Change color if necessary */ xy[0]=x_fetch(0); xy[1]=y_fetch(0); drDMPx (MOVE, xy); /*Move to center point */ /* Set sizes used for marker clipping */ fulsiz = mrksize[ndmkht] + mrkextra*mrkszext[ndmkht]; hlfsiz = fulsiz/2; j = 0; for (i=1; i<=LFETCH(conseg,conoff,1); ++i) {/*Output marker at each point */ xy[0] = x_fetch(j); xy[1] = y_fetch(j); /*Clip marker to device limits */ x1 = xy[0] - hlfsiz; x2 = x1 + fulsiz; y1 = xy[1] - hlfsiz; y2 = y1 + fulsiz; if ((min0(x1,y1) >= 0) && (x2 <= wxmax) && /* watch out for portrait mode changes*/ (y2 <= wymax)) { /*Marker fits on device */ drDMPx (MOVE, xy); /*Move to center point and display */ dbufhi(1, mrkout); savexy[0]=ndmkht+1 + DIG0; savexy[1]=PLUS; dbufhi(1,savexy); if (mrkextra==1) dbufhi(1,&savexy[1]); savexy[0]=mrktbl[ndmktp-1]+DIG0; dbufhi(1,savexy); dbufhi(1,&space); if (ndmktp==3) { drDMPx (MOVE, xy); /*Move to center point and display */ dbufhi(1, mrkout); savexy[0]=ndmkht+1 + DIG0; dbufhi(1,savexy); if (mrkextra==1) dbufhi(1,&savexy[1]); savexy[0]=DIG1; dbufhi(1,savexy); dbufhi(1,&space); } } j += 2; /*Increment ptr to coords */ } break; /* opcode text */ case TEXT: dpDMPx (ndclrt); /*Change color to text color */ xy[0]=x_fetch(0); xy[1]=y_fetch(0); drDMPx (MOVE, xy); /*Move to start point */ j = LFETCH(conseg,conoff,INTEGERxINxLENGTH);/*Get the string length */ j = min0(MAXxHIxBUFFER - 6,j); /* 75 chars fill up the buffer */ dbufhi (-1,txtout); /* flush that buffer for the whole string */ dbufhi (3,txtout); /* Start text */ for (i = 0; i < j; ++i) { /*Loop to keep buffer from overflowing*/ xy[0]=LFETCH(iinseg,iinoff,i); dbufhi (1, xy); } dbufhi (2, txtstop); /*terminate string */ break; /* opcode fill area */ case FILLxAREA: dpDMPx (ndclrf); /*Change color to fill color */ dbufhi (3,solid); /*Ensure a solid line type */ i = LFETCH (conseg,conoff,1); gsxfill (ndistyf, ndstyf, ndlntp, i); if (ndlntp != DIG0) { /*restore line type if not solid */ lstyle[1] = ndlntp + DIG0; dbufhi (3, lstyle); } break; /* opcode cell array */ case CELLxARRAY: savexy[0] = x_fetch(0); /*Save boundary points */ savexy[1] = y_fetch(0); x2 = x_fetch(2); y2 = y_fetch(2); dpDMPx (ndclrl); /*Change color to line color */ dbufhi (3,solid); /*Ensure a solid line type */ drDMPx (MOVE, savexy); /*Move to first point */ xy[0] = x2; /*Draw boundary around area */ xy[1] = savexy[1]; drDMPx (DRAW, xy); xy[1] = y2; drDMPx (DRAW, xy); xy[0] = savexy[0]; drDMPx (DRAW, xy); drDMPx (DRAW, savexy); if (ndlntp != DIG0) { /*restore line type if not solid */ lstyle[1] = ndlntp + DIG0; dbufhi (3, lstyle); } break; /* opcode GDP's */ case GENERALIZEDxDRAWINGxPRIMITIVE: i=LFETCH(conseg,conoff,5); if(i==1) { /* BARS - supported by all plotters */ dpDMPx (ndclrf); /*Change color to fill color */ dbufhi (3,solid); /*Ensure a solid line type */ for (j=2; j<8; ++j) ibuf[j-2] = LFETCH(pinseg,pinoff,j); x1 = LFETCH(pinseg,pinoff,0); y1 = LFETCH(pinseg,pinoff,1); x2 = LFETCH(pinseg,pinoff,2); y2 = LFETCH(pinseg,pinoff,3); LSTORE(pinseg,pinoff,2,x2); LSTORE(pinseg,pinoff,3,y1); LSTORE(pinseg,pinoff,4,x2); LSTORE(pinseg,pinoff,5,y2); LSTORE(pinseg,pinoff,6,x1); LSTORE(pinseg,pinoff,7,y2); gsxfill(ndistyf,ndstyf,ndlntp,4); if (ndlntp != DIG0) { /*restore line type if not solid */ lstyle[1] = ndlntp + DIG0; dbufhi (3, lstyle); } for (j=2; j<8; ++j) LSTORE(pinseg,pinoff,j,ibuf[j-2]); } if (i==2) { /* ARCs */ dpDMPx (ndclrl); /*Change color to line color */ dbufhi (3, solid); /*Ensure a solid line type */ xy[0] = x_fetch(2); xy[1] = y_fetch(2); drDMPx (MOVE, xy); /*Move to first point of arc */ dbufhi (3,arcstart); length = gitoch(x_fetch(0), icnvt, 6, &ierror); dbufhi (length,icnvt); dbufhi (1, &comma); length = gitoch(y_fetch(0), icnvt, 6, &ierror); dbufhi (length,icnvt); dbufhi (1, &comma); length = gitoch((LFETCH(iinseg,iinoff,1)-LFETCH(iinseg,iinoff,0))/10, icnvt, 6, &ierror); dbufhi (length,icnvt); dbufhi (1, &space); if (ndlntp != DIG0) { /*restore line type if not solid */ lstyle[1] = ndlntp + DIG0; dbufhi (3, lstyle); } } break; /* opcode set character height */ case SxCHxHEIGHT: /*The input parameters represent the text height of a character */ /*cell excluding gap. */ /*Make sure not too small and not too large */ ndtysz = gimnmx (LFETCH(pinseg,pinoff,1), inipto[1], inipto[3])/7; dtDMPx (ndtysz); /*Set the text size */ LSTORE(conseg,conoff,2,2); /*One output coordinate pair*/ LSTORE(poutseg,poutoff,0,((savexy[0] = ndtysz * 6)*8)/10); LSTORE(poutseg,poutoff,1,savexy[1] = ndtysz * 7); LSTORE(poutseg,poutoff,2,savexy[0]); LSTORE(poutseg,poutoff,3,(savexy[1]*3)/2); break; /* opcode set character up vector */ case SxCHxUPxVECTOR: ndtxrt = ((((LFETCH(iinseg,iinoff,0)/10) % 360) + 45) / 90) % 4; dbufhi (rotleng[ndtxrt],rotstr[ndtxrt]); LSTORE(ioutseg,ioutoff,0,ndtxrt*90); /*Inform upper level of angle */ break; /* opcode set color */ case SxCOLORxREPRESENTATION: /*Save 2 or 6 color indices, 1 for each pen station. The requested */ /*value is the same as the realized value */ i = gimnmx (LFETCH(iinseg,iinoff,0)-1, 0, nmbrpens-1); /*Get color index in range */ clrred[i] = LFETCH(iinseg,iinoff,1); clrgrn[i] = LFETCH(iinseg,iinoff,2); clrblu[i] = LFETCH(iinseg,iinoff,3); break; /* opcode set line type */ case SxPLxLINETYPE: ndlntp = LFETCH(iinseg,iinoff,0); if (ndlntp < 1 | ndlntp > 11) ndlntp = 1; LSTORE(ioutseg,ioutoff,0,ndlntp); /*Return linetype selected */ --ndlntp; lstyle[1] = ndlntp+DIG0; dbufhi(3, lstyle); break; /* opcode polyline color index */ case SxPLxCOLORxINDEX: ndclrl = max0 ( 0, LFETCH(iinseg,iinoff,0)); LSTORE(ioutseg,ioutoff,ndclrl); /*Return color index selected */ break; /* opcode set marker type */ case SxPMxTYPE: ndmktp = LFETCH(iinseg,iinoff,0); if (ndmktp < 1 | ndmktp > 7) ndmktp = 3; /*Marker type 3 is default */ LSTORE(ioutseg,ioutoff,ndmktp); /*Return type selected */ break; /* opcode polymarker scale */ case SxPMxSCALE: i = gimnmx (LFETCH(pinseg,pinoff,1), inipto[9], inipto[11]);/*Make sure size not too */ /*small or too large */ LSTORE(conseg,conoff,2,1); /*Return 1 coordinate pair */ LSTORE(poutseg,poutoff,0,0); for (ndmkht=0; ndmkht<5; ++ndmkht) { if (mrksize[ndmkht]==i) break; if (mrksize[ndmkht]>i) {--ndmkht; break;} } mrkextra = (i>=mrkszext[ndmkht]) ? 1 : 0; LSTORE(poutseg,poutoff,1,mrksize[ndmkht]+mrkextra*mrkszext[ndmkht]); /*Return size selected */ break; /* opcode polymarker color index */ case SxPMxCOLORxINDEX: LSTORE(ioutseg,ioutoff,0,ndclrm = max0 ( 0, LFETCH(iinseg,iinoff,0))); break; /* opcode set text font */ case SxTXxFONT: i = max0 (LFETCH(iinseg,iinoff,0), 1); if (i>nmbrfonts) i=1; --i; j=i; if (i>7) { i -= 8; setfnt[2]=SP; } else setfnt[2]=BIGN; setfnt[6] = i + DIG0; dbufhi (10, setfnt); /*Output command */ LSTORE(ioutseg,ioutoff,0,j+1); /*Return actual font selected */ break; /* opcode text color index */ case SxTXxCOLORxINDEX: LSTORE(ioutseg,ioutoff,0,ndclrt = max0(0,LFETCH(iinseg,iinoff,0))); break; /* opcode set fill color index */ case SxFxCOLORxINDEX: LSTORE(ioutseg,ioutoff,0,ndclrf = max0(0,LFETCH(iinseg,iinoff,0))); break; /* opcode set fill interior sytle index */ case SxFxINTERIORxSTYLE: ndistyf = max0(LFETCH(iinseg,iinoff,0),0); if (ndistyf > 3) ndistyf = 0; LSTORE(ioutseg,ioutoff,0,ndistyf); break; /* opcode set fill style index */ case SxFxSTYLExINDEX: ndstyf = max0(LFETCH(iinseg,iinoff,0),1); if (ndstyf > 6) ndstyf = 1; LSTORE(ioutseg,ioutoff,0,ndstyf); break; /* opcode inquire color representation */ case INQxCOLORxREPRESENTATION: i = gimnmx (LFETCH(iinseg,iinoff,0)-1, 0, nmbrpens-1); /*Map index 0-5 to 1-6 */ LSTORE(ioutseg,ioutoff,0,i + 1); /*Color index selected */ LSTORE(ioutseg,ioutoff,1,clrred[i]); /*Set values are same as realized */ LSTORE(ioutseg,ioutoff,2,clrgrn[i]); LSTORE(ioutseg,ioutoff,3,clrblu[i]); break; /* opcode input locator */ case INPxLOCATOR: LSTORE(poutseg,poutoff,0,0); LSTORE(poutseg,poutoff,1,0); LSTORE(conseg,conoff,4,UNSUCCESSFUL); i = LFETCH(iinseg,iinoff,0); /*check input device number */ if ((i != DEFAULT && i != PLOTTER) || (nmbrpens != 8)) break; xy[0]=x_fetch(0); xy[1]=y_fetch(0); drDMPx (MOVE, xy); /*move to initial point*/ dbufhi (-1, home); /*First flush the buffer */ outstr (3, getgin); /*Ask for the gin report */ do RDRIN (&temp); while (temp!=LPAREN); instr (15, ibuf, &temp); /*Get the gin report */ LSTORE(conseg,conoff,4,SUCCESSFUL); /*Request was successful */ LSTORE(conseg,conoff,2,1); /*Output 1 coordinate pair */ gchtoi (ibuf, 2, &i, &istop); LSTORE(poutseg,poutoff,1,i-wxmin); gchtoi (ibuf, istop+2, &i, &istop); LSTORE(poutseg,poutoff,0,wymax-i); LSTORE(ioutseg,ioutoff,0,SP); /*Cannot inquire pen status */ break; /* opcode set input mode */ case SxINPUTxMODE: LSTORE(ioutseg,ioutoff,0,1); /*Default mode is request */ break; } } drDMPx (opcode, xy) int opcode, xy[]; { /*********************************************************************** * * * Function: Device Driver move/draw for H I - DM 29 * * * * Input Parameters: * * opcode - driver function, either move/draw * * xy - coordinates to move or draw to * * xy [0] = x-coordinate * * xy [1] = y-coordinate * * * * Output Parameters: none * * * * Routines Called: * * dbufhi - output a string to the plotter * * gitoch - convert integer to character string * * * ************************************************************************/ int length, iconvt[10], ierror, gitoch(); static int movdrw[3] = {BIGA, BIGU, SP}; static int space[1] = {SP}; static int comma[1] = {COMMA}; movdrw[1] = BIGU; /*Always prepare to do a move */ if (opcode == DRAW) movdrw[1] = BIGD; /*Change it for a draw */ dbufhi (3, movdrw); length = gitoch (xy[0],iconvt,5,&ierror); dbufhi (length,iconvt); dbufhi (1,comma); length = gitoch (xy[1],iconvt,5,&ierror); dbufhi (length,iconvt); dbufhi (1,space); } dtDMPx (hgt) unsigned int hgt; { /*********************************************************************** * * * Function: Set text size on HI DM 29 * * * * Input Parameters: * * hgt - height of character in device char units * * Output Parameters: * * none * * * * Routines Called: * * gitoch - convert integer to character string * * dbufhi - output a command to a hi plotter * ***********************************************************************/ int ierror, i, icnvt[10], length; int gitoch(); /* Set label(text) size /S(S/ */ static int txtsiz[] = {BIGS, LPAREN, BIGS}; static int txtend[] = {SP, RPAREN, ETX, SP}; dbufhi (3, txtsiz); /*Put out text size command */ length = gitoch (hgt, icnvt, 6, &ierror); dbufhi (length, icnvt); dbufhi (4, txtend); } dpDMPx (color) int color; { /*********************************************************************** * * * Function: Change the color on the HI DM29 plotter * * * * Input Parameters: * * color - color to change to * * Output Parameters: * * none * * * * Routines Called: * * gznppl - prompt for new pen on plotter * * dbufhi - output a command to a plotter * ***********************************************************************/ int newsta; extern int pens[], clrred[], clrgrn[], clrblu[]; /* Change pens */ static int penclr[] = { BIGP, DIG0, SP }; /* /P0 / */ if (ndclrp != color) { /*prompt for new pen on plotter if necessary */ gznppl (color, nmbrpens, pens, &newsta); ndclrp = color; /*Set the current color */ penclr[1] = newsta + DIG0; /*Load this pen station */ dbufhi (3, penclr); } } dbufhi (icount, iarray) int icount, iarray[]; { /*********************************************************************** * * * Function: HIDMPx buffered output handler * * * * Input Parameters: * * icount - number of characters in iarray to be output * * -1 flushes the buffer * * * * iarray - Array of characters to be output * * * * Output Parameters: none * * * * Routines Called: * * RDRIN - get a character from the plotter * * PCHOUT - output a character to the plotter * * outstr - output a string to the plotter * * * ***********************************************************************/ int adechar, k, tries; k = icount; if (k < 0) k = 0; if (((ndotkt+k) > MAXxHIxBUFFER) || (icount < 0)) { ndotkt = 0; /*Reset the plotter buffer counter */ /*Wait for prompt response from device. The prompt should be the */ /* carriage return (13) character. */ do { PCHOUT (SP); PCHOUT (CR); /*Output buffer terminating character */ RDRIN (&adechar); } while ((adechar & 127) != CR); } outstr (k, iarray); ndotkt = ndotkt + k; /*Update the plotter buffer counter */ } gznfpl() { /*********************************************************************** * * * Function: Issue prompt to change paper and wait for input * * * * Input Parameters: * * none * * Output Parameters: * * none * * * * Routines Called: * * TTYIN - get keyboard input * * TTYOUT - output text to console * ***********************************************************************/ int i; static int string[] = { BIGC,BIGH,BIGA,BIGN,BIGG,BIGE,SP,BIGP,BIGA,BIGP,BIGE,BIGR,COMMA, SP,BIGT,BIGH,BIGE,BIGN,SP,BIGP,BIGR,BIGE,BIGS,BIGS,SP,BIGR,BIGE, BIGT,BIGU,BIGR,BIGN,CR,LF }; i=0; do TTYOUT(string[i]); while (string[i++]!=LF); TTYIN(&i); } gznppl(color, npens, pens, newstat) int color, npens, pens[], *newstat; { /*********************************************************************** * * * Function: Issue prompt to change pens and wait for input * * * * Input Parameters: * * color - new color * * npens - number of pens on plotter * * pens - pen station array * * * * Output Parameters: * * newstat - new station * * * * Routines Called: * * TTYIN - get keyboard input * * TTYOUT - output text to console * ***********************************************************************/ int i,j; static string[] = { BIGP,BIGL,BIGA,BIGC,BIGE,SP,BIGP,BIGE,BIGN,SP,SP,SP,SP,SP,SP,SP,BIGI,BIGN,SP,BIGD,BIGE, BIGS,BIGI,BIGR,BIGE,BIGD,SP,BIGP,BIGE,BIGN,SP,BIGS,BIGT,BIGA,BIGT,BIGI, BIGO,BIGN,COMMA,SP,BIGT,BIGH,BIGE,BIGN,SP,BIGE,BIGN,BIGT,BIGE,BIGR,SP, BIGS,BIGT,BIGA,BIGT,BIGI,BIGO,BIGN,SP,BIGN,BIGU,BIGM,BIGB,BIGE,BIGR,COLON, SP,-1 }; static string2[] = { BIGL,BIGO,BIGA,BIGD,SP,BIGP,BIGE,BIGN,SP,SP,SP,SP,SP,SP,SP,BIGA,BIGN,BIGD, SP,BIGP,BIGR,BIGE,BIGS,BIGS,SP,BIGR,BIGE,BIGT,BIGU,BIGR,BIGN,-1 }; *newstat=-1; for (i=0; i<=npens; ++i) if (pens[i]==color) *newstat=i; if (*newstat==-1) { if (npens>1) { for (i=10;i<14;++i) string[i]=SP; gitoch(color,&string[10],5,&i); i=0; do TTYOUT(string[i]); while (string[++i]>=0); } else { for (i=9;i<13;++i) string2[i]=SP; gitoch(color,&string2[9],5,&i); i=0; do TTYOUT(string2[i]); while (string2[++i]>=0); } TTYIN(&i); TTYOUT(i); TTYOUT(CR); TTYOUT(LF); *newstat = gimnmx(i-'0',0,npens); pens[*newstat]=color; } } instr (lenin,string,lenout) int lenin, string[], *lenout; { /*********************************************************************** * * * Function: Input a string from the plotter * * * * Input Parameters: * * lenin - maximum length of string * * * * Output Parameters: * * string - array of ADE values received from plotter * * lenout - actual length of string * * * * Routines Called: * * RDRIN - get plotter input * ***********************************************************************/ int i, tmplen; /* check for valid length */ *lenout = 1; if (lenin>0) { tmplen = min0(lenin,81); i=-1; do { RDRIN(&(string[++i])); *lenout = i; } while (imax)) return(0); else {*ierror=0; return(l);} } int gimnmx (value, min, max) int value, min, max; { /********************************************************************* * * * FUNCTION: CHECK THAT AN INTEGER IS WITHIN A GIVEN RANGE * * * * INPUT PARAMETERS: * * VALUE - INTEGER TO CHECK * * MIN - MINIMUM LEGAL VALUE * * MAX - MAXIMUM LEGAL VALUE * * * * OUTPUT PARAMETERS: * * GIMNMX - VALUE RETURNED * * * * ROUTINES CALLED: * * NONE * *********************************************************************/ return (min0(max0(min,value),max)); } nb2ade(number,chars,number_char) int number,*number_char; int *chars; /*********************************************************************** * * * Function: Convert a number to an ade-string * * * * Input Parameters: * * number - value to convert * * * * Output Parameters: * * chars - array of ade values * * number_char - length of chars * * * * Routines Called: * * none * ***********************************************************************/ { int digit,i,first,tens[5]; tens[0]=10000; tens[1]=1000; tens[2]=100; tens[3]=10; tens[4]=1; if (number==0) { *number_char=1; *(chars++)='0'; } else { *number_char=0; first=0; if (number<0) { *number_char=1; *(chars++)='-'; number*=-1; } for (i=0;i<=4;++i) { digit=number/tens[i]; if (digit>0 || first!=0) { *(chars++)=digit + '0'; ++*number_char; number-=digit*tens[i]; first=1; } } } } gchtoi (string, start, value, stop) int string[], start, *value, *stop; { /********************************************************************* * * * FUNCTION: CONVERT AN ADE STRING TO AN INTEGER * * * * INPUT PARAMETERS: * * STRING - ARRAY CONTAINING THE STRING * * START - POSITION IN STRING TO START CONVERSION * * * * OUTPUT PARAMETERS: * * VALUE - THE INTEGER VALUE * * STOP - THE LAST POSITION OF THE STRING IN THE ARRAY * * * * ROUTINES CALLED: * * NONE * *********************************************************************/ int sign; sign = 1; for (*stop=start; string[*stop]==' '; *stop++); if (string[*stop] == '+' || string[*stop] == '-' ) /* sign */ sign = (string[(*stop)++]=='+') ? 1 : -1; for (*value = 0; string[*stop] >= '0' && string[*stop] <= '9'; (*stop)++) *value = 10 * *value + string[*stop] - '0'; *value = sign * *value; } int min0 (a,b) int a,b; { /********************************************************************* * * * FUNCTION: RETURN THE MINIMUM OF A AND B * * * * INPUT PARAMETERS: * * A, B - VALUES TO FIND THE MINIMUM OF * * * * OUTPUT PARAMETERS: * * MIN0 - FUNCTION VALUE RETURNED * * * * ROUTINES CALLED: * * NONE * *********************************************************************/ return((ab) ? a : b); } gsxfill (int_style, style_index, line_style, length) int int_style, style_index, length; /*********************************************************************** * * * Function: Prepare data for polygon-fill routine * * * * Input Parameters: * * int_style - interior style * * style_index - interior style index * * line_style - current line style * * length - number of points in polygon * * * * Output Parameters: * * none * * * * Routines Called: * * LSTORE - long store * * LFETCH - long fetch * * plyfill - polygon fill * * drDMPx - move/draw on plotter * * dbufhi - send string to plotter * ***********************************************************************/ { int savexy[2], xy[2], ival, i, j, distance; if (ndistyf==1 || ndistyf==3) { savexy[0]=LFETCH(pinseg,pinoff,2*length); savexy[1]=LFETCH(pinseg,pinoff,2*length+1); i = LFETCH (pinseg, pinoff, 0); LSTORE(pinseg,pinoff,2*length,i); i = LFETCH (pinseg, pinoff, 1); LSTORE(pinseg,pinoff,2*length+1,i); distance = (ndistyf==1) ? 2 : 20; if (ndistyf==1) ival = 2; else { ival = ndstyf; if (ndstyf > 4) ival -= 3; } plyfill (ival, distance, length+1); if (ndistyf==3 && ndstyf>4) { ival = (ndstyf==5) ? 1 : 4; plyfill (ival, distance, length+1); } LSTORE(pinseg,pinoff,2*length,savexy[0]); LSTORE(pinseg,pinoff,2*length+1,savexy[1]); } xy[0]=x_fetch(0); xy[1]=y_fetch(0); drDMPx (MOVE, xy); /*Move to first point */ j = 2; for (i=2; i<=length; ++i) { /*draw between subsequent points */ xy[0]=x_fetch(j); xy[1]=y_fetch(j); drDMPx (DRAW, xy); j += 2; } xy[0]=x_fetch(0); xy[1]=y_fetch(0); drDMPx (DRAW, xy); /*draw to first point to make sure */ /*polygon closed */ drDMPx (MOVE, xy); /*Move to the point to pick the pen up */ } int x_fetch(position) {return(LFETCH(pinseg,pinoff,position+1)+wxmin);} int y_fetch(position) {return(wymax-LFETCH(pinseg,pinoff,position));} plyfill(pattern,distance,length) int pattern, distance, length; /*********************************************************************** * * * Function: Fill a polygon * * * * Input Parameters: * * pattern - fill pattern * * distance - distance between fill lines * * length - number of points in polygon * * * * Output Parameters: * * none * * * * Routines Called: * * LSTORE - long store * * LFETCH - long fetch * * MULDIV - muliply and divide using 32-bits * * INTERCPT - calculate intercept formula in 32 bits * * dr2x0 - move/draw on plotter * ***********************************************************************/ { int incr, i, j, raster, intx[50], LFETCH(), MULDIV(), INTERCPT(), wmin, wmax; int x1, x2, y1, y2, j2, xy[2], temp, oldx, oldy; int oxmin, oxmax, oymin, oymax, intercept, sign, evenodd; int x_fetch(),y_fetch(); incr = distance; if (pattern > 2) incr = (distance*7)/5; sign = (pattern == 4) ? -1 : 1; oxmax = oymax = -1; oxmin = oymin = 32767; x1 = x_fetch(0); y1 = y_fetch(0); for (i=2*length-4; i>0; i-=2) { oldx = x_fetch(i); oldy = y_fetch(i); if (pattern==1 && oldy!=y1) break; if (pattern==2 && oldx!=x1) break; if (pattern>2 && (oldx-oldy)!=(-1*sign*(x1-y1))) break; } for (i=0; i<2*length; i+=2) { x1 = x_fetch(i); y1 = y_fetch(i); if (oxmax < x1) oxmax = x1; if (oxmin > x1) oxmin = x1; if (oymax < y1) oymax = y1; if (oymin > y1) oymin = y1; } switch (pattern) { case 2: wmin = oxmin; wmax = oxmax; break; case 1: wmin = oymin; wmax = oymax; break; case 4: wmin = oymin - oxmax; wmax = oymax - oxmin; break; case 3: wmax = oxmax + oymax; wmin = oxmin + oymin; break; } evenodd=0; for (raster=wmax; raster>=wmin; raster-=incr) { j = 0; evenodd = (++evenodd)%2; for (i=0; i<(2*length-2); i+=2) { x1 = x_fetch(i); y1 = y_fetch(i); x2 = x_fetch(i+2); y2 = y_fetch(i+2); intercept = -1; switch (pattern) { case 2: if ((x1<=raster && x2>=raster) || (x1>=raster && x2<=raster)) if (x1!=x2) { intercept = y1 + MULDIV(raster-x1,y1-y2,x1-x2); if ((x1==raster) && ((x2raster) || (x2>raster && oldx=raster) || (y1>=raster && y2<=raster)) if (y1!=y2) { intercept = x1 + MULDIV(raster-y1,x1-x2,y1-y2); if ((y1==raster) && ((y2raster) || (y2>raster && oldy=raster) || ((sign*x1+y1)>=raster && (sign*x2+y2)<=raster)) if (((x1!=x2) || (y1!=y2)) && (((y1-y2)+sign*(x1-x2))!=0)) { intercept = INTERCPT(raster,sign,x1,y1,x2,y2); if (((sign*x1+y1)==raster) && (((sign*x2+y2)raster) || ((sign*x2+y2)>raster && (sign*oldx+oldy)=0) { intx[j++]=intercept; l_insert(intx,j-1,intx[j-1],evenodd); } } i = 0; for (j2=0; j2 value && evenodd==0) || (array[j] < value && evenodd!=0)) { for (j2=length-1; j2>=j; --j2) array[j2+1]=array[j2]; array[j]=value; break; } }