3 /* Copyright (C) 1994 Free Software Foundation, Inc.
4 Written by Francisco Andrés Verdú <pandres@dragonet.es>
6 groff is free software; you can redistribute it and/or modify it under
7 the terms of the GNU General Public License as published by the Free
8 Software Foundation; either version 2, or (at your option) any later
11 groff is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 You should have received a copy of the GNU General Public License along
17 with groff; see the file COPYING. If not, write to the Free Software
18 Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
20 /* This file contains a set of utility functions to use canon CAPSL printers
21 * (lbp-4 and lbp-8 series printers) */
29 static FILE *lbpoutput
= NULL
;
30 static FILE *vdmoutput
= NULL
;
33 lbpinit(FILE *outfile
)
40 lbpprintf(char *format
, ... )
41 { /* Taken from cjet */
44 va_start(stuff
, format
);
45 vfprintf(lbpoutput
, format
, stuff
);
52 fputs(data
,lbpoutput
);
63 lbpsavestatus(int index
)
65 fprintf(lbpoutput
,"\033[%d%%y",index
);
69 lbprestorestatus(int index
)
71 fprintf(lbpoutput
,"\033[%d%cz",index
,'%');
77 fprintf(lbpoutput
,"\033[1;%d;0x",index
);
81 lbprestorepos(int index
)
83 fprintf(lbpoutput
,"\033[0;%d;0x",index
);
87 lbprestoreposx(int index
)
89 fprintf(lbpoutput
,"\033[0;%d;1x",index
);
93 lbpmoverel(int despl
, char direction
)
95 fprintf(lbpoutput
,"\033[%d%c",despl
,direction
);
99 lbplinerel(int width
,int despl
,char direction
)
101 fprintf(lbpoutput
,"\033[%d;0;9{\033[%d%c\033[9}",width
,despl
,direction
);
105 lbpmoveabs(int x
, int y
)
107 fprintf(lbpoutput
,"\033[%d;%df",y
,x
);
111 lbplineto(int x
,int y
, int width
)
113 fprintf(lbpoutput
,"\033[%d;0;9{",width
);
115 fprintf(lbpoutput
,"\033[9}\n");
119 lbpruleabs(int x
, int y
, int hsize
, int vsize
)
122 fprintf(lbpoutput
,"\033[0;9;000s");
123 lbpmoveabs(x
+hsize
,y
+vsize
);
124 fprintf(lbpoutput
,"\033[9r");
127 static inline void vdmprintf(char *format
, ... );
130 vdmnum(int num
,char *result
)
137 /* First byte 1024 - 32768 */
138 b1
= ((nm
>> 10) & 0x3F);
139 if (b1
) *p
++ = b1
| 0x40;
141 /* Second Byte 16 - 1024 */
142 b2
= ((nm
>> 4) & 0x3F);
143 if ( b1
|| b2
) *p
++= b2
| 0x40;
145 /* Third byte 0 - 15 */
146 b3
= ((nm
& 0x0F) | 32);
147 if (num
>= 0) b3
|= 16;
149 *p
= 0x00; /* End of the resulting string */
154 vdmorigin(int newx
, int newy
)
158 vdmprintf("}\"%s%s\x1e",vdmnum(newx
,nx
),vdmnum(newy
,ny
));
163 vdminit(FILE *vdmfile
)
165 char scale
[4],size
[4],lineend
[4];
167 /* vdmoutput = tmpfile();*/
169 /* Initialize the VDM mode */
170 vdmprintf("\033[0&}#GROLBP\x1e!0%s%s\x1e$\x1e}F%s\x1e",\
171 vdmnum(-3,scale
),vdmnum(1,size
),vdmnum(1,lineend
));
183 vdmprintf(char *format
, ... )
184 { /* Taken from cjet */
187 if (vdmoutput
== NULL
) vdminit(tmpfile());
188 va_start(stuff
, format
);
189 vfprintf(vdmoutput
, format
, stuff
);
194 vdmsetfillmode(int pattern
,int perimeter
, int inverted
)
196 char patt
[4],perim
[4],
197 rot
[4], /* rotation */
198 espejo
[4], /* espejo */
199 inv
[4]; /* Inverted */
201 vdmprintf("I%s%s%s%s%s\x1e",vdmnum(pattern
,patt
),\
202 vdmnum(perimeter
,perim
),vdmnum(0,rot
),
203 vdmnum(0,espejo
),vdmnum(inverted
,inv
));
207 vdmcircle(int centerx
, int centery
, int radius
)
209 char x
[4],y
[4],rad
[4];
211 vdmprintf("5%s%s%s\x1e",vdmnum(centerx
,x
),vdmnum(centery
,y
),\
216 vdmaarc(int centerx
, int centery
, int radius
,int startangle
,int angle
,int style
,int arcopen
)
218 char x
[4],y
[4],rad
[4],stx
[4],sty
[4],styl
[4],op
[4];
220 vdmprintf("}6%s%s%s%s%s%s%s\x1e",vdmnum(arcopen
,op
),\
221 vdmnum(centerx
,x
),vdmnum(centery
,y
),\
222 vdmnum(radius
,rad
),vdmnum(startangle
,stx
),vdmnum(angle
,sty
),\
227 vdmvarc(int centerx
, int centery
,int radius
, int startx
, int starty
, int endx
, int endy
,\
228 int style
,int arcopen
)
230 char x
[4],y
[4],rad
[4],stx
[4],sty
[4],enx
[4],eny
[4],styl
[4],op
[4];
232 vdmprintf("}6%s%s%s%s%s%s%s%s\x1e",vdmnum(arcopen
,op
),\
233 vdmnum(centerx
,x
),vdmnum(centery
,y
),\
234 vdmnum(radius
,rad
),vdmnum(startx
,stx
),vdmnum(starty
,sty
),\
235 vdmnum(endx
,enx
),vdmnum(endy
,eny
),vdmnum(style
,styl
));
239 vdmellipse(int centerx
, int centery
, int radiusx
, int radiusy
,int rotation
)
241 char x
[4],y
[4],radx
[4],rady
[4],rotat
[4];
243 vdmprintf("}7%s%s%s%s%s\x1e\n",vdmnum(centerx
,x
),vdmnum(centery
,y
),\
244 vdmnum(radiusx
,radx
),vdmnum(radiusy
,rady
),\
245 vdmnum(rotation
,rotat
));
249 vdmsetlinetype(int lintype
)
251 char ltyp
[4], expfact
[4];
253 vdmprintf("E1%s%s\x1e",vdmnum(lintype
,ltyp
),vdmnum(1,expfact
));
258 vdmsetlinestyle(int lintype
, int pattern
,int unionstyle
)
260 char patt
[4],ltip
[4],
261 rot
[4], /* rotation */
262 espejo
[4], /* espejo */
263 in
[4]; /* Inverted */
265 vdmprintf("}G%s%s%s%s%s\x1e",vdmnum(lintype
,ltip
),\
266 vdmnum(pattern
,patt
),vdmnum(0,rot
),
267 vdmnum(0,espejo
),vdmnum(0,in
));
268 vdmprintf("}F%s",vdmnum(unionstyle
,rot
));
272 vdmlinewidth(int width
)
276 vdmprintf("F1%s\x1e",vdmnum(width
,wh
));
280 vdmrectangle(int origx
, int origy
,int dstx
, int dsty
)
282 char xcoord
[4],ycoord
[4],sdstx
[4],sdsty
[4];
284 vdmprintf("}:%s%s%s%s\x1e\n",vdmnum(origx
,xcoord
),vdmnum(dstx
,sdstx
),\
285 vdmnum(origy
,ycoord
),vdmnum(dsty
,sdsty
));
289 vdmpolyline(int numpoints
, int *points
)
292 char xcoord
[4],ycoord
[4];
294 if (numpoints
< 2) return;
295 vdmprintf("1%s%s",vdmnum(*p
,xcoord
),vdmnum(*(p
+1),ycoord
));
297 for (i
= 1; i
< numpoints
; i
++) {
298 vdmprintf("%s%s",vdmnum(*p
,xcoord
),vdmnum(*(p
+1),ycoord
));
305 vdmpolygon(int numpoints
, int *points
)
308 char xcoord
[4],ycoord
[4];
310 if (numpoints
< 2) return;
311 vdmprintf("2%s%s",vdmnum(*p
,xcoord
),vdmnum(*(p
+1),ycoord
));
313 for (i
= 1; i
< numpoints
; i
++) {
314 vdmprintf("%s%s",vdmnum(*p
,xcoord
),vdmnum(*(p
+1),ycoord
));
322 /************************************************************************
323 * Highter level auxiliary functions *
324 ************************************************************************/
328 return (vdmoutput
!= NULL
);
333 vdmline(int startx
, int starty
, int sizex
, int sizey
)
342 vdmpolyline(2,points
);
346 /*#define THRESHOLD .05 */ /* inch */
347 #define THRESHOLD 1 /* points (1/300 inch) */
349 splinerel(double px
,double py
,int flush
)
351 static int lx
= 0 ,ly
= 0;
352 static float pend
= 0.0;
353 static int dx
= 0,dy
= 0, despx
= 0, despy
= 0, sigpend
= 0;
354 int dxnew
,dynew
, sg
;
355 char xcoord
[4],ycoord
[4];
358 if (flush
== -1) {lx
= (int)px
; ly
= (int)py
; return;};
363 if ((dxnew
== 0) && (dynew
== 0)) return;
364 sg
= (dxnew
< 0)? -1 : 0;
365 /* fprintf(stderr,"s (%d,%d) (%d,%d)\n",dxnew,dynew,despx,despy);*/
368 if ((sg
== sigpend
) && (dy
== 0)){
375 npend
= (1.0*dxnew
)/dynew
;
376 if (( npend
== pend
) && (sigpend
== sg
))
377 { despy
= dynew
; despx
= dxnew
; return; }
381 }; /* else (( npend == pend) && ... */
382 }; /* else (if (dynew == 0)) */
383 }; /* if (!flush ) */
385 /* if we've changed direction we must draw the line */
386 /* fprintf(stderr," (%d) %.2f,%.2f\n",flush,(float)px,(float)py);*/
387 if ((despx
!= 0) || (despy
!= 0)) vdmprintf("%s%s",vdmnum(despx
,xcoord
),\
388 vdmnum(despy
,ycoord
));
389 /*if ((despx != 0) || (despy != 0)) fprintf(stderr,"2
390 *%d,%d\n",despx,despy);*/
392 dx
= dxnew
= dy
= despx
= despy
= 0;
397 if ((dxnew
!= 0) || (dynew
!= 0)) vdmprintf("%s%s",vdmnum(dxnew
,xcoord
),\
398 vdmnum(dynew
,ycoord
));
400 /* if ((dxnew != 0) || (dynew != 0)) fprintf(stderr,"3
401 * %d,%d\n",dxnew,dynew);*/
402 lx
= (int)px
; ly
= (int)py
;
403 dx
= dxnew
= dy
= despx
= despy
= 0;
407 /**********************************************************************
408 * The following code to draw splines is adapted from the transfig package
411 quadratic_spline(double a1
,double b1
, double a2
, double b2
, \
412 double a3
, double b3
, double a4
, double b4
)
414 double x1
, y1
, x4
, y4
;
419 xmid
= (a2
+ a3
)/2.0;
420 ymid
= (b2
+ b3
)/2.0;
421 if ((fabs(x1
- xmid
) < THRESHOLD
) && (fabs(y1
- ymid
) < THRESHOLD
)) {
422 splinerel(xmid
,ymid
,0);
423 /* fprintf(tfp, "PA%.4f,%.4f;\n", xmid, ymid);*/
426 quadratic_spline(x1
, y1
, ((x1
+a2
)/2.0), ((y1
+b2
)/2.0),
427 ((3.0*a2
+a3
)/4.0), ((3.0*b2
+b3
)/4.0), xmid
, ymid
);
430 if ((fabs(xmid
- x4
) < THRESHOLD
) && (fabs(ymid
- y4
) < THRESHOLD
)) {
432 /* fprintf(tfp, "PA%.4f,%.4f;\n", x4, y4);*/
435 quadratic_spline(xmid
, ymid
, ((a2
+3.0*a3
)/4.0), ((b2
+3.0*b3
)/4.0),
436 ((a3
+x4
)/2.0), ((b3
+y4
)/2.0), x4
, y4
);
438 }; /* quadratic_spline */
440 #define XCOORD(i) numbers[(2*i)]
441 #define YCOORD(i) numbers[(2*i)+1]
443 vdmspline(int numpoints
, int ox
,int oy
, int *numbers
)
445 double cx1
, cy1
, cx2
, cy2
, cx3
, cy3
, cx4
, cy4
;
446 double x1
, y1
, x2
, y2
;
447 char xcoord
[4],ycoord
[4];
461 cx2
= (x1
+ 3.0*x2
)/4.0;
462 cy2
= (y1
+ 3.0*y2
)/4.0;
464 /* fprintf(stderr,"Spline %d (%d,%d)\n",numpoints,(int)x1,(int)y1);*/
465 vdmprintf("1%s%s",vdmnum((int)x1
,xcoord
),vdmnum((int)y1
,ycoord
));
467 splinerel(cx1
,cy1
,0);
468 /* fprintf(tfp, "PA%.4f,%.4f;PD%.4f,%.4f;\n",
471 /*for (p = p->next; p != NULL; p = p->next) {*/
472 for (i
= 1; i
< (numpoints
); i
++) {
479 cx3
= (3.0*x1
+ x2
)/4.0;
480 cy3
= (3.0*y1
+ y2
)/4.0;
483 /* fprintf(stderr,"Point (%d,%d) - (%d,%d)\n",(int)x1,(int)(y1),(int)x2,(int)y2);*/
484 quadratic_spline(cx1
, cy1
, cx2
, cy2
, cx3
, cy3
, cx4
, cy4
);
487 cx2
= (x1
+ 3.0*x2
)/4.0;
488 cy2
= (y1
+ 3.0*y2
)/4.0;
492 /* p = s->points->next;
497 cx3
= (3.0*x1
+ x2
)/4.0;
498 cy3
= (3.0*y1
+ y2
)/4.0;
503 /*vdmprintf("%s%s",vdmnum((int)(x1-lx),xcoord),\
504 vdmnum((int)(y1-ly),ycoord));*/
506 /* fprintf(tfp, "PA%.4f,%.4f;PU;\n", x1, y1);*/