envbvs@epb2.lbl.gov (Brian V. Smith) (07/04/90)
Submitted-by: envbvs@epb2.lbl.gov (Brian V. Smith) Posting-number: Volume 8, Issue 22 Archive-name: xfig2.8/part13 #! /bin/sh # This is a shell archive. Remove anything before this line, then unpack # it by saving it into a file and typing "sh file". To overwrite existing # files, type "sh file -c". You can also feed this as standard input via # unshar, or by typing "sh <file", e.g.. If this archive is complete, you # will see the following message at the end: # "End of archive 13 (of 21)." # Contents: f2hp.c movept.c read.c # Wrapped by envbvs@epb2.lbl.gov on Thu Jun 28 08:52:45 1990 PATH=/bin:/usr/bin:/usr/ucb ; export PATH if test -f 'f2hp.c' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'f2hp.c'\" else echo shar: Extracting \"'f2hp.c'\" \(18027 characters\) sed "s/^X//" >'f2hp.c' <<'END_OF_FILE' X/* X * f2hp : Fig-to-HPGL translator X * X * Original Copyright (c) 1986 by Supoj Sutanthavibul (supoj@sally.UTEXAS.EDU) X * X * Created from f2ps by B.V. Smith 5/90 X * X * %W% %G% X*/ X#include "fig.h" X#include "object.h" X#include "resources.h" X X#define PAGE_WIDTH (10.250-0.250) /* 10" X plot area (7475A) */ X#define PAGE_HEIGHT (7.796-0.596) /* 7.2" Y plot area */ X#define POINT_PER_INCH 72 /* text ppi */ X#define MAX_COLORS 6 /* number of pens */ X#define DEFAULT_COLOR 0 /* black */ X#define UP 0 X#define DOWN 1 X X#define TRANSF_X(x) (x)*scalex X#define TRANSF_Y(y) (coord_system==2? (ury-(y))*scaley: (y)*scaley) X Xchar Usage[] = "Usage: %s [-P][-L][-debug][-e scale] [input [output]]\n"; Xchar *prog; Xint cur_thickness; Xint cur_color= -9; Xint cur_areafill=0; Xint debug = 0; Xint landscape = 1; Xint pen=UP; Xextern int num_object; Xchar *from = NULL, *to = NULL; XFILE *tfp = NULL; Xchar Err_incomp[] = "Incomplete %s object at line %d."; Xchar Err_mem[] = "Running out of memory."; Xdouble scale = 1.0; Xdouble scalex, scaley; Xint coord_system; Xint ppi; Xint llx, lly, urx, ury; X Xint fill_type[NUMFILLPATS] = {4, 3, 4, 3, 4, 3, 4, 3, 4, 3, X 4, 3, 4, 3, 4, 3, 4, 3, 4, 3, 1}; Xint fill_spacing[NUMFILLPATS] = {8, 8, 8, 8, 8, 6, 6, 6, 6, 6, 6, 6, X 4, 4, 4, 4, 4, 4, 2, 2, 0}; Xint fill_angle[NUMFILLPATS] = {0, 0, 45, 45, 90, 90, 0, 0, 45, 45, X 90, 90, 0, 0, 45, 45, 90, 90, 0, 0, 0}; Xint line_thickness; /* not needed for f2ps, arrow.c needs it for fig */ X Xget_args(argc, argv) Xint argc; Xchar *argv[]; X{ X char *a; X int first = 1; X X prog = *argv; X while (--argc) { X a = *++argv; X if (*a == '-') { X if (*++a == 'l' || *a == 'L') { /* Landscape */ X landscape = 1; X } X else if (*a == 'p' || *a == 'P') { /* Portrait */ X landscape = 0; X } X else if (*a == 'd') /* debug printing */ X debug = 1; X else if (*a == 'e') { /* Enlarging factor followed */ X if (--argc) X scale = atof(*++argv); X else X goto error_exit; X } X else X goto error_exit; X } X else if (first) { X from = a; /* from file */ X first = 0; X } X else if (first == 0) { X to = a; /* to file */ X first = -1; X } X else X goto error_exit; X } X return; X X error_exit: X fprintf(stderr, Usage, prog); X exit(1); X } X Xmain(argc, argv) Xint argc; Xchar *argv[]; X{ X F_compound objects; X int status; X X get_args(argc, argv); X X if (to == NULL) X tfp = stdout; X else if ((tfp = fopen(to, "w")) == NULL) { X fprintf(stderr, "%s: Couldn't open %s", prog, to); X fprintf(stderr, Usage, prog); X exit(1); X } X X if (from) X status = read_fig(from, &objects); X else /* read from stdin */ X status = readfp_fig(stdin, &objects); X X if (status != 0) { X if (from) read_fail_message(from, status); X fprintf(stderr,"\n"); X exit(1); X } X genhp_objects(&objects); X if (tfp != stdout) X (void)fclose(tfp); X exit(0); X } X Xprolog(objects) XF_compound *objects; X { X plotter_on(); X fprintf(tfp, "\033.I80;;17:"); /* set x-on/x-off */ X fprintf(tfp, "\033.N;19:"); X /* **** rotate for portrait mode **** */ X if (!landscape) /* must reset clip window and plotter limits with rotaton */ X fprintf(tfp, "RO 90;IW;IP;\n"); X fprintf(tfp, "SC %d %d %d %d;\n", llx, urx, lly, ury); X } X Xepilog() X { X penup(); X fprintf(tfp,"PA %d %d; ",urx,ury); X fprintf(tfp, "SP;\n"); X plotter_off(); X } X Xplotter_on() X { X fprintf(tfp,"\033.(\n"); X } X Xplotter_off() X { X fprintf(tfp,"\033.)\n"); X } X Xgenhp_objects(objects) XF_compound *objects; X{ X F_arc *a; X F_compound *c; X F_ellipse *e; X F_line *l; X F_spline *s; X F_text *t; X int itmp; X int color; X X /* Compute bounding box of objects */ X compound_bound(objects, &llx, &lly, &urx, &ury); X if (llx > urx) { X fprintf(stderr, "%s: No object",prog); X return; X } X X ppi = objects->nwcorner.x; /* ppi */ X coord_system = objects->nwcorner.y; /* 1=y normal, 2=y flipped */ X X scalex = scaley = scale; /* user enlarging factor */ X X /*************************************************************************/ X /* we will just set llx lly etc to plotter area */ X /*************************************************************************/ X X llx = lly = 0; /* lower left */ X urx = PAGE_WIDTH*ppi; X ury = PAGE_HEIGHT*ppi; X X if (!landscape) /* swap x,y */ X { X itmp = llx; llx = lly; lly = itmp; X itmp = urx; urx = ury; ury = itmp; X } X X prolog(objects); X X /* plot color 0 first then 1, ... */ X for (color=-1; color < MAX_COLORS; color++) X { X for (a = objects->arcs; a != NULL; a = a->next) X genhp_arc(a,color); X for (c = objects->compounds; c != NULL; c = c->next) X genhp_compound(c,color); X for (e = objects->ellipses; e != NULL; e = e->next) X genhp_ellipse(e,color); X for (l = objects->lines; l != NULL; l = l->next) X genhp_line(l,color); X for (s = objects->splines; s != NULL; s = s->next) X genhp_spline(s,color); X for (t = objects->texts; t != NULL; t = t->next) X genhp_text(t,color); X } X epilog(); X } X Xset_style(s, v) Xint s; Xdouble v; X{ X if (s == DASH_LINE) { X if (v > 0.0) fprintf(tfp, "LT 2;\n"); X } X else if (s == DOTTED_LINE) { X if (v > 0.0) fprintf(tfp, "LT 1;\n"); X } X } X Xreset_style(s, v) Xint s; Xdouble v; X{ X if (s == DASH_LINE) { X if (v > 0.0) fprintf(tfp, "LT;\n"); X } X else if (s == DOTTED_LINE) { X if (v > 0.0) fprintf(tfp, "LT;\n"); X } X } X Xset_areafill(a) Xint a; X { X if (cur_areafill == a) X return; X cur_areafill = a; X fprintf(tfp, "FT %d %d %d;\n", X fill_type[a-1],fill_spacing[a-1],fill_angle[a-1]); X } X Xset_linewidth(w) Xint w; X { X cur_thickness = w; X } X Xset_color(c) Xint c; X { X if (c < 0) X c = DEFAULT_COLOR; X if (cur_color == c) X return; X cur_color = c; X fprintf(tfp,"SP %d;\n",c+1); X } X Xmoveto(x,y) Xint x,y; X { X penup(); X fprintf(tfp,"PA %.2f %.2f;\n",TRANSF_X(x),TRANSF_Y(y)); X } X Xdrawto(x,y) Xint x,y; X { X pendown(); X fprintf(tfp,"PA %.2f %.2f;\n",TRANSF_X(x),TRANSF_Y(y)); X } X Xf_moveto(x,y) Xdouble x,y; X { X penup(); X fprintf(tfp,"PA %.2lf %.2lf;\n",TRANSF_X(x),TRANSF_Y(y)); X } X Xf_drawto(x,y) Xdouble x,y; X { X pendown(); X fprintf(tfp,"PA %.2lf %.2lf;\n",TRANSF_X(x),TRANSF_Y(y)); X } X Xpenup() X { X if (pen != UP) X fprintf(tfp,"PU; "); X pen = UP; X } X Xpendown() X { X if (pen != DOWN) X fprintf(tfp,"PD; "); X pen = DOWN; X } X Xgenhp_compound(com,color) XF_compound *com; Xint color; X{ X F_arc *a; X F_compound *c; X F_ellipse *e; X F_line *l; X F_spline *s; X F_text *t; X X for (a = com->arcs; a != NULL; a = a->next) X genhp_arc(a,color); X for (c = com->compounds; c != NULL; c = c->next) X genhp_compound(c,color); X for (e = com->ellipses; e != NULL; e = e->next) X genhp_ellipse(e,color); X for (l = com->lines; l != NULL; l = l->next) X genhp_line(l,color); X for (s = com->splines; s != NULL; s = s->next) X genhp_spline(s,color); X for (t = com->texts; t != NULL; t = t->next) X genhp_text(t,color); X } X X#define FILL_RECT(x,y) fprintf(tfp,"RA %.2f %.2f; ",TRANSF_X((x)),TRANSF_Y((y))) X#define EDGE_RECT(x,y) fprintf(tfp,"EA %.2f %.2f; ",TRANSF_X((x)),TRANSF_Y((y))) X#define FILL_WEDGE(r,angle,sweep) fprintf(tfp,"WG %.2f %d %d; ", \ X TRANSF_X(r),(angle),(sweep)) X#define ARC_TO(x,y,angle) fprintf(tfp,"AA %.2f %.2f %d; ", \ X TRANSF_X((x)),TRANSF_Y((y)),(angle)) X#define F_FILL_WEDGE(r,angle,sweep) fprintf(tfp,"WG %.2lf %d %d; ", \ X TRANSF_X(r),(angle),(sweep)) X#define F_ARC_TO(x,y,angle) fprintf(tfp,"AA %.2lf %.2lf %d; ", \ X TRANSF_X((x)),TRANSF_Y((y)),(angle)) X#define CIRCLE(r) fprintf(tfp,"CI %.2f;",TRANSF_X(r)) X Xgenhp_line(l,color) XF_line *l; Xint color; X { X F_point *p, *q; X int radius,tmp; X int xmin,xmax,ymin,ymax; X X if (color != l->color) X return; X X set_linewidth(l->thickness); X set_color(l->color); X radius = l->radius; /* radius of rounded-corner boxes */ X p = l->points; X q = p->next; X if (q == NULL) { /* A single point line */ X if (l->thickness > 0) X { X moveto(p->x,p->y); X pendown(); X penup(); X } X return; X } X if (l->back_arrow) X draw_arrow_head((double)q->x, (double)q->y, (double)p->x, X (double)p->y, l->back_arrow->ht, l->back_arrow->wid); X set_style(l->style, l->style_val); X if (l->area_fill) X set_areafill(l->area_fill); X xmin = xmax = p->x; X ymin = ymax = p->y; X X while ((l->type == T_BOX || l->type == T_ARC_BOX) && X p->next != NULL) /* find lower left and upper right corners */ X { X p=p->next; X if (xmin > p->x) X xmin = p->x; X else if (xmax < p->x) X xmax = p->x; X if (ymin > p->y) X ymin = p->y; X else if (ymax < p->y) X ymax = p->y; X } X if (l->type == T_ARC_BOX) /* rounded-corner box */ X { X if (l->area_fill) X { X moveto(xmin+radius,ymin); X FILL_RECT(xmax-radius,ymin+radius); X moveto(xmin,ymin+radius); X FILL_RECT(xmax,ymax-radius); X moveto(xmin+radius,ymax-radius); X FILL_RECT(xmax-radius,ymax); X X /* now do the corner wedges */ X moveto(xmin+radius,ymin+radius); X FILL_WEDGE(radius,90,90); X moveto(xmin+radius,ymax-radius); X FILL_WEDGE(radius,180,90); X moveto(xmax-radius,ymax-radius); X FILL_WEDGE(radius,270,90); X moveto(xmax-radius,ymin+radius); X FILL_WEDGE(radius,0,90); X } X /* draw the outline of the box */ X moveto(xmin+radius,ymin); X pendown(); X ARC_TO(xmin+radius,ymin+radius,90); X drawto(xmin,ymax-radius); X ARC_TO(xmin+radius,ymax-radius,90); X drawto(xmax-radius,ymax); X ARC_TO(xmax-radius,ymax-radius,90); X drawto(xmax,ymin+radius); X ARC_TO(xmax-radius,ymin+radius,90); X drawto(xmin+radius,ymin); X } /* T_ARC_BOX */ X else if (l->type == T_BOX) X { X moveto(xmin,ymin); X if (l->area_fill) X FILL_RECT(xmax,ymax); X EDGE_RECT(xmax,ymax); X } X else /* POLYGON or POLYLINE */ X { X moveto(p->x, p->y); X while (q->next != NULL) X { X p = q; X q = q->next; X drawto(p->x, p->y); X } X drawto(q->x, q->y); X } X penup(); X X reset_style(l->style, l->style_val); X if (l->for_arrow && l->thickness > 0) X draw_arrow_head((double)p->x, (double)p->y, (double)q->x, X (double)q->y, l->for_arrow->ht, l->for_arrow->wid); X } X Xgenhp_spline(s,color) XF_spline *s; Xint color; X{ X if (color != s->color) X return; X X set_color(s->color); X#ifndef notdef X fprintf(stderr,"No spline yet\n"); X#else X if (int_spline(s)) X genhp_itp_spline(s); X else X genhp_ctl_spline(s); X#endif X } X Xgenhp_itp_spline(s) XF_spline *s; X{ X F_point *p, *q; X F_control *a, *b; X X set_linewidth(s->thickness); X a = s->controls; X b = a->next; X p = s->points; X if (s->back_arrow && s->thickness > 0) X draw_arrow_head(b->lx, b->ly, (double)p->x, X (double)p->y, s->back_arrow->ht, s->back_arrow->wid); X X set_style(s->style, s->style_val); X fprintf(tfp, "%% Interpolated spline\n"); X fprintf(tfp, "newpath %d %d moveto\n", p->x, p->y); X for (q = p->next; q != NULL; p = q, q = q->next) { X b = a->next; X fprintf(tfp, "\t%.3f %.3f %.3f %.3f %d %d curveto\n", X a->rx, a->ry, b->lx, b->ly, q->x, q->y); X a = b; X } X if (closed_spline(s)) X { X fprintf(tfp, " closepath "); X if (s->area_fill) X { X set_areafill(s->area_fill); X fprintf(tfp, " gsave fill grestore "); X set_areafill(NUMFILLPATS); /* back to black for line */ X } X } X if (s->thickness > 0) X fprintf(tfp, " stroke\n"); X reset_style(s->style, s->style_val); X X if (s->for_arrow && s->thickness > 0) X draw_arrow_head(a->lx, a->ly, (double)p->x, X (double)p->y, s->for_arrow->ht, s->for_arrow->wid); X } X Xgenhp_ctl_spline(s) XF_spline *s; X{ X double a, b, c, d, x1, y1, x2, y2, x3, y3; X F_point *p, *q; X X p = s->points; X x1 = p->x; y1 = p->y; X p = p->next; X c = p->x; d = p->y; X set_linewidth(s->thickness); X x3 = a = (x1 + c) / 2; X y3 = b = (y1 + d) / 2; X if (s->back_arrow && s->thickness > 0) { X draw_arrow_head(c, d, x1, y1, s->back_arrow->ht, s->back_arrow->wid); X } X set_style(s->style, s->style_val); X if (! closed_spline(s)) { X fprintf(tfp, "%% Open spline\n"); X fprintf(tfp, "newpath %.3f %.3f moveto %.3f %.3f lineto\n", X x1, y1, x3, y3); X } X else { X fprintf(tfp, "%% Closed spline\n"); X fprintf(tfp, "newpath %.3f %.3f moveto\n", a, b); X } X for (q = p->next; q != NULL; q = q->next) { X x1 = x3; y1 = y3; X x2 = c; y2 = d; X c = q->x; d = q->y; X x3 = (x2 + c) / 2; X y3 = (y2 + d) / 2; X fprintf(tfp, "\t%.3f %.3f %.3f %.3f %.3f %.3f DrawSplineSection\n", X x1, y1, x2, y2, x3, y3); X } X /* X * At this point, (x2,y2) and (c,d) are the position of the X * next-to-last and last point respectively, in the point list X */ X if (closed_spline(s)) { X fprintf(tfp, "\t%.3f %.3f %.3f %.3f %.3f %.3f DrawSplineSection closepath ", X x3, y3, c, d, a, b); X if (s->area_fill) X { X set_areafill(s->area_fill); X fprintf(tfp, " gsave fill grestore\n"); X set_areafill(NUMFILLPATS); /* back to black for line */ X } X if (s->thickness > 0) X fprintf(tfp, " stroke\n"); X } X else { X if (s->thickness > 0) X fprintf(tfp, "\t%.3f %.3f lineto stroke\n", c, d); X else X fprintf(tfp, "\t%.3f %.3f lineto\n", c, d); X } X reset_style(s->style, s->style_val); X if (s->for_arrow && s->thickness > 0) X { X draw_arrow_head(x2, y2, c, d, s->for_arrow->ht, X s->for_arrow->wid); X } X } X Xgenhp_ellipse(e,color) XF_ellipse *e; Xint color; X { X int rx,ry,cx,cy; X double x,y; X int npts; X double theta,inc; X X if (color != e->color) X return; X X set_linewidth(e->thickness); X set_color(e->color); X set_style(e->style, e->style_val); X if (e->area_fill) X set_areafill(e->area_fill); X rx = e->radiuses.x; X ry = e->radiuses.y; X cx = e->center.x; X cy = e->center.y; X if (rx == ry) X { /* CIRCLE */ X moveto(cx, cy); X if (e->area_fill) X FILL_WEDGE(rx, 0, 360); X /* outline the circle */ X CIRCLE(rx); X } X else /* ellipse */ X { X npts = (rx+ry)*2; /* pick some number of points proportional X to the size of the ellipse to plot */ X inc = 2.0*M_PI/npts; X moveto(cx+rx,cy); X for (theta = 0.0; theta <= 2*M_PI; theta += inc) X { X x = cx + rx*cos(theta); X y = cy + ry*sin(theta); X f_drawto(x,y); X } X drawto(cx+rx, cy); X } X penup(); X reset_style(e->style, e->style_val); X } X X X#define IS_ITALICS(f) ((f)&1) X Xgenhp_text(t,color) XF_text *t; Xint color; X { X double height; X int len; X X if (color != t->color) X return; X X set_color(t->color); X height = (double) t->size/POINT_PER_INCH*2.54; /* height in cm */ X X height = height*scale; X height = height/1.5; /* kludge for now */ X fprintf(tfp,"SI %.2lf %.2lf;",height/2.54,height); X len = strlen(t->cstring); X if (IS_ITALICS(t->font)) /* slant for Italics font */ X fprintf(tfp,"SL %.2f;",tan((double)30.0*M_PI/180.0)); /* 30 degrees */ X moveto(t->base_x,t->base_y); X if (t->type == T_RIGHT_JUSTIFIED) X fprintf(tfp,"CP %d 0; ",-len); X else if (t->type == T_CENTER_JUSTIFIED) X fprintf(tfp,"CP %.1f 0; ",-len/2.0); X fprintf(tfp,"LB%s\003;\n",t->cstring); X if (IS_ITALICS(t->font)) X fprintf(tfp,"SL;"); X } X Xgenhp_arc(a,color) XF_arc *a; Xint color; X{ X double angle1, angle2, dx, dy, radius, x, y; X double cx, cy, sx, sy, ex, ey; X int sweep; X int direction; X X if (color != a->color) X return; X X cx = a->center.x; cy = a->center.y; X sx = a->point[0].x; sy = a->point[0].y; X ex = a->point[2].x; ey = a->point[2].y; X X if (coord_system == 2) X direction = !a->direction; X else X direction = a->direction; X set_linewidth(a->thickness); X set_color(a->color); X if (a->for_arrow && a->thickness > 0) { X arc_tangent(cx, cy, ex, ey, direction, &x, &y); X draw_arrow_head(x, y, ex, ey, a->for_arrow->ht, a->for_arrow->wid); X } X if (a->back_arrow && a->thickness > 0) { X arc_tangent(cx, cy, sx, sy, !direction, &x, &y); X draw_arrow_head(x, y, sx, sy, a->back_arrow->ht, a->back_arrow->wid); X } X dx = cx - sx; X dy = cy - sy; X radius = sqrt(dx*dx + dy*dy); X angle1 = atan2(sy-cy, sx-cx) * 180 / M_PI; X angle2 = atan2(ey-cy, ex-cx) * 180 / M_PI; X /* make the angles go from 0 to 2PI */ X if (angle1 < 0.0) X angle1 += 360.0; X if (angle2 < 0.0) X angle2 += 360.0; X /* direction 1 -> Counter-Clockwise */ X if (direction == 1) /* ccw */ X { X if (angle1 > angle2) X sweep = 360.0 - angle1 + angle2; X else X sweep = angle2 - angle1; X } X else /* cw */ X { X if (angle1 > angle2) X sweep = - (angle1 - angle2); X else X sweep = - (360.0 - angle2 + angle1); X } X if (debug) X fprintf(stderr,"#%d: dir=%s, a1 = %.1f, a2 = %.1f, sweep = %d\n", X a->thickness,direction==0?"cw ":"ccw",cx,cy,angle1,angle2,sweep); X set_style(a->style, a->style_val); X if (a->area_fill) X { X set_areafill(a->area_fill); X f_moveto(cx,cy); X F_FILL_WEDGE(radius,(int)angle1,sweep); X } X f_moveto(ex,ey); X pendown(); X F_ARC_TO(cx,cy,sweep); X penup(); X X reset_style(a->style, a->style_val); X } X Xarc_tangent(x1, y1, x2, y2, direction, x, y) Xdouble x1, y1, x2, y2, *x, *y; Xint direction; X{ X if (direction) { /* counter clockwise */ X *x = x2 + (y2 - y1); X *y = y2 - (x2 - x1); X } X else { X *x = x2 - (y2 - y1); X *y = y2 + (x2 - x1); X } X } X X/* draw arrow heading from (x1, y1) to (x2, y2) */ X Xdraw_arrow_head(x1, y1, x2, y2, arrowht, arrowwid) Xdouble x1, y1, x2, y2, arrowht, arrowwid; X{ X double x, y, xb, yb, dx, dy, l, sina, cosa; X double xc, yc, xd, yd; X X dx = x2 - x1; dy = y1 - y2; X l = sqrt((double)(dx*dx + dy*dy)); /* length of line */ X sina = dy / l; cosa = dx / l; X xb = x2*cosa - y2*sina; X yb = x2*sina + y2*cosa; X x = xb - arrowht; X y = yb - arrowwid / 2; X xc = x*cosa + y*sina; /* one tail of arrow */ X yc = -x*sina + y*cosa; X y = yb + arrowwid / 2; X xd = x*cosa + y*sina; /* other tail of arrow */ X yd = -x*sina + y*cosa; X f_moveto(xc,yc); X f_drawto(x2,y2); X f_drawto(xd,yd); X penup(); X } X Xellipse_exist(ob) XF_compound *ob; X{ X F_compound *c; X X if (NULL != ob->ellipses) return(1); X X for (c = ob->compounds; c != NULL; c = c->next) { X if (ellipse_exist(c)) return(1); X } X X return(0); X } X Xnormal_spline_exist(ob) XF_compound *ob; X{ X F_spline *s; X F_compound *c; X X for (s = ob->splines; s != NULL; s = s->next) { X if (normal_spline(s)) return(1); X } X X for (c = ob->compounds; c != NULL; c = c->next) { X if (normal_spline_exist(c)) return(1); X } X X return(0); X } X X/*VARARGS1*/ Xput_msg(format, arg1, arg2, arg3, arg4, arg5) X char *format; X int arg1, arg2, arg3, arg4, arg5; X{ X fprintf(stderr, format, arg1, arg2, arg3, arg4, arg5); X} END_OF_FILE if test 18027 -ne `wc -c <'f2hp.c'`; then echo shar: \"'f2hp.c'\" unpacked with wrong size! fi # end of 'f2hp.c' fi if test -f 'movept.c' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'movept.c'\" else echo shar: Extracting \"'movept.c'\" \(17045 characters\) sed "s/^X//" >'movept.c' <<'END_OF_FILE' X/* X * FIG : Facility for Interactive Generation of figures X * X * Copyright (c) 1985 by Supoj Sutanthavibul (supoj@sally.UTEXAS.EDU) X * January 1985. X * 1st revision : Aug 1985. X * X * %W% %G% X*/ X#include "fig.h" X#include "resources.h" X#include "func.h" X#include "object.h" X#include "paintop.h" X X#define TOLERANCE 3 Xextern int latexline_mode, latexarrow_mode; Xextern int magnet_mode; X Xextern (*canvas_kbd_proc)(); Xextern (*canvas_locmove_proc)(); Xextern (*canvas_leftbut_proc)(); Xextern (*canvas_middlebut_proc)(); Xextern (*canvas_rightbut_proc)(); Xextern null_proc(); Xextern set_popupmenu(); XF_line *line_point_search(); XF_spline *spline_point_search(); XF_ellipse *ellipse_point_search(); XF_arc *arc_point_search(); X Xextern F_compound objects; X Xextern F_point *moved_point, *left_point; Xextern F_pos last_position, new_position; Xextern int movedpoint_num; Xextern int last_object; Xextern int fix_x, fix_y, cur_x, cur_y; Xextern int pointmarker_shown; Xextern int foreground_color, background_color; X Xextern elastic_box(), move_ebrbox(), move_ebdbox(); Xextern move_cbrbox(), move_cbdbox(); X Xextern int init_move_point(); Xextern int move_linepoint(), fix_movedlinepoint(); Xextern int move_latexlinepoint(), fix_movedlatexlinepoint(); Xextern int fix_box(); Xextern int fix_movedsplinepoint(); Xextern int move_arcpoint(), fix_movedarcpoint(); Xextern int fix_movedellipsepoint(); X Xstatic F_line *line; Xstatic F_spline *spline; Xstatic F_ellipse *ellipse; Xstatic F_arc *arc; X Xstatic int latex_fix_x, latex_fix_y; XCURSOR cur_latexcursor; XBoolean init_ellipsepointmoving(); X Xmove_point_selected() X{ X canvas_kbd_proc = null_proc; X canvas_locmove_proc = null_proc; X canvas_leftbut_proc = init_move_point; X canvas_middlebut_proc = null_proc; X canvas_rightbut_proc = set_popupmenu; X set_cursor(&pick9_cursor); X reset_action_on(); X } X Xinit_move_point(x, y) Xint x, y; X{ X Boolean Ok=True; X X if ((line = line_point_search(x, y, TOLERANCE, X &left_point, &moved_point)) != NULL) { X init_linepointmoving(line); X } X else if ((spline = spline_point_search(x, y, X TOLERANCE, &left_point, &moved_point)) != NULL){ X init_splinepointmoving(spline); X } X else if ((ellipse = ellipse_point_search(x, y, TOLERANCE, X &movedpoint_num)) != NULL) { X if (!init_ellipsepointmoving(ellipse)) /* selected center, ignore */ X Ok=False; X } X else if ((arc = arc_point_search(x, y, TOLERANCE, X &movedpoint_num)) != NULL) { X init_arcpointmoving(arc); X } X else { X return; X } X if (Ok) /* movepoint went ok */ X { X canvas_leftbut_proc = canvas_rightbut_proc = null_proc; X erase_pointmarker(); X } X } X Xwrapup_movepoint() X{ X show_pointmarker(); X move_point_selected(); X } X X/************************* ellipse *******************************/ X XF_ellipse * Xellipse_point_search(x, y, tol, point_num) Xint x, y, tol, *point_num; X{ X F_ellipse *e; X X for (e = objects.ellipses; e != NULL; e = e->next) { X if (abs(e->start.x - x) <= tol && abs(e->start.y - y) <= tol) { X *point_num = 0; X return(e); X } X if (abs(e->end.x - x) <= tol && abs(e->end.y - y) <= tol) { X *point_num = 1; X return(e); X } X } X return(NULL); X } X Xstatic F_ellipse *cur_e; X XBoolean Xinit_ellipsepointmoving(ellipse) XF_ellipse *ellipse; X{ X if (movedpoint_num == 0) { /* center point is selected - disallow */ X if (ellipse->type == T_ELLIPSE_BY_RAD || X ellipse->type == T_CIRCLE_BY_RAD) { X return False; /* don't erase point_marker etc */ X } X last_position.x = cur_x = ellipse->start.x; X last_position.y = cur_y = ellipse->start.y; X fix_x = ellipse->end.x; fix_y = ellipse->end.y; X switch (ellipse->type) { X case T_ELLIPSE_BY_DIA : X canvas_locmove_proc = move_ebdbox; X ellipsebydia_box(INV_PAINT); X break; X case T_CIRCLE_BY_DIA : X canvas_locmove_proc = move_cbdbox; X circlebydia_box(INV_PAINT); X break; X } X } X else { X last_position.x = cur_x = ellipse->end.x; X last_position.y = cur_y = ellipse->end.y; X fix_x = ellipse->start.x; fix_y = ellipse->start.y; X switch (ellipse->type) { X case T_ELLIPSE_BY_RAD : X canvas_locmove_proc = move_ebrbox; X ellipsebyrad_box(INV_PAINT); X break; X case T_CIRCLE_BY_RAD : X canvas_locmove_proc = move_cbrbox; X circlebyrad_box(INV_PAINT); X break; X case T_ELLIPSE_BY_DIA : X canvas_locmove_proc = move_ebdbox; X ellipsebydia_box(INV_PAINT); X break; X case T_CIRCLE_BY_DIA : X canvas_locmove_proc = move_cbdbox; X circlebydia_box(INV_PAINT); X break; X } X } X cur_e = ellipse; X set_temp_cursor(&crosshair_cursor); X win_setmouseposition(canvas_win, cur_x, cur_y); X canvas_middlebut_proc = fix_movedellipsepoint; X canvas_leftbut_proc = null_proc; X return True; /* all is Ok */ X } X Xfix_movedellipsepoint(x, y) Xint x, y; X{ X switch (cur_e->type) { X case T_ELLIPSE_BY_RAD : X ellipsebyrad_box(INV_PAINT); X break; X case T_CIRCLE_BY_RAD : X circlebyrad_box(INV_PAINT); X break; X case T_ELLIPSE_BY_DIA : X ellipsebydia_box(INV_PAINT); X break; X case T_CIRCLE_BY_DIA : X circlebydia_box(INV_PAINT); X break; X } X new_position.x = x; X new_position.y = y; X clean_up(); X set_action_object(F_MOVE_POINT, O_ELLIPSE); X set_latestellipse(cur_e); X relocate_ellipsepoint(cur_e, x, y, movedpoint_num); X wrapup_movepoint(); X } X Xrelocate_ellipsepoint(ellipse, x, y, point_num) XF_ellipse *ellipse; Xint x, y, point_num; X{ X int dx, dy; X X set_temp_cursor(&wait_cursor); X if (pointmarker_shown) toggle_ellipsepointmarker(ellipse); X draw_ellipse(ellipse, background_color); X if (point_num == 0) { /* starting point is selected */ X fix_x = ellipse->end.x; fix_y = ellipse->end.y; X ellipse->start.x = x; ellipse->start.y = y; X } X else { X fix_x = ellipse->start.x; fix_y = ellipse->start.y; X ellipse->end.x = x; ellipse->end.y = y; X } X switch (ellipse->type) { X case T_ELLIPSE_BY_RAD : X ellipse->radiuses.x = abs(x - fix_x) + 1; X ellipse->radiuses.y = abs(y - fix_y) + 1; X break; X case T_CIRCLE_BY_RAD : X dx = fix_x - x; dy = fix_y - y; X ellipse->radiuses.x = sqrt((double)(dx*dx + dy*dy)) + .5; X ellipse->radiuses.y = ellipse->radiuses.x; X break; X case T_ELLIPSE_BY_DIA : X ellipse->center.x = (fix_x + x) / 2; X ellipse->center.y = (fix_y + y) / 2; X ellipse->radiuses.x = abs(ellipse->center.x - fix_x); X ellipse->radiuses.y = abs(ellipse->center.y - fix_y); X break; X case T_CIRCLE_BY_DIA : X dx = ellipse->center.x = (fix_x + x) / 2 +.5; X dy = ellipse->center.y = (fix_y + y) / 2 +.5; X dx -= x; dy -= y; X ellipse->radiuses.x = sqrt((double)(dx*dx + dy*dy)) + .5; X ellipse->radiuses.y = ellipse->radiuses.x; X break; X } X draw_ellipse(ellipse, foreground_color); X if (pointmarker_shown) toggle_ellipsepointmarker(ellipse); X reset_cursor(); X set_modifiedflag(); X } X X/*************************** arc *********************************/ X Xstatic F_arc *cur_a; X XF_arc * Xarc_point_search(x, y, tol, point_num) Xint x, y, tol, *point_num; X{ X F_arc *a; X int i; X X for(a = objects.arcs; a != NULL; a = a->next) { X for (i = 0; i < 3; i++) { X if (abs(a->point[i].x - x) <= tol && X abs(a->point[i].y - y) <= tol) { X *point_num = i; X return(a); X } X } X } X return(NULL); X } X Xinit_arcpointmoving(arc) XF_arc *arc; X{ X cur_a = arc; X last_position.x = cur_x = arc->point[movedpoint_num].x; X last_position.y = cur_y = arc->point[movedpoint_num].y; X set_temp_cursor(&crosshair_cursor); X win_setmouseposition(canvas_win, cur_x, cur_y); X draw_arclink(INV_PAINT); X canvas_locmove_proc = move_arcpoint; X canvas_middlebut_proc = fix_movedarcpoint; X canvas_leftbut_proc = null_proc; X } X Xmove_arcpoint(x, y) Xint x, y; X{ X draw_arclink(INV_PAINT); X cur_x = x; cur_y = y; X draw_arclink(INV_PAINT); X } X Xdraw_arclink(op) Xint op; X{ X switch (movedpoint_num) { X case 0 : X pw_vector(canvas_win, cur_x, cur_y, X arc->point[1].x, arc->point[1].y, op, 1, SOLID_LINE, 0.0); X break; X case 1 : X pw_vector(canvas_win, arc->point[0].x, arc->point[0].y, X cur_x, cur_y, op, 1, SOLID_LINE, 0.0); X pw_vector(canvas_win, arc->point[2].x, arc->point[2].y, X cur_x, cur_y, op, 1, SOLID_LINE, 0.0); X break; X default : X pw_vector(canvas_win, arc->point[2].x, arc->point[2].y, X cur_x, cur_y, op, 1, SOLID_LINE, 0.0); X } X } X Xfix_movedarcpoint(x, y) Xint x, y; X{ X draw_arclink(INV_PAINT); X new_position.x = x; X new_position.y = y; X clean_up(); X set_action_object(F_MOVE_POINT, O_ARC); X set_latestarc(cur_a); X relocate_arcpoint(cur_a, x, y, movedpoint_num); X wrapup_movepoint(); X } X Xrelocate_arcpoint(arc, x, y, movedpoint_num) XF_arc *arc; Xint x, y, movedpoint_num; X{ X float xx, yy; X F_pos p[3]; X X p[0] = arc->point[0]; X p[1] = arc->point[1]; X p[2] = arc->point[2]; X p[movedpoint_num].x = x; X p[movedpoint_num].y = y; X if (compute_arccenter(p[0], p[1], p[2], &xx, &yy)) { X set_temp_cursor(&wait_cursor); X if (pointmarker_shown) toggle_arcpointmarker(arc); X draw_arc(arc, background_color); /* erase old arc */ X arc->point[movedpoint_num].x = x; X arc->point[movedpoint_num].y = y; X arc->center.x = xx; X arc->center.y = yy; X arc->direction = compute_direction(p[0], p[1], p[2]); X draw_arc(arc, foreground_color); /* draw new arc */ X if (pointmarker_shown) toggle_arcpointmarker(arc); X reset_cursor(); X set_modifiedflag(); X } X } X X/************************** spline *******************************/ X Xstatic F_spline *cur_s; X Xinit_splinepointmoving(s) XF_spline *s; X{ X F_point *p; X X cur_s = s; X last_position.x = cur_x = moved_point->x; X last_position.y = cur_y = moved_point->y; X set_temp_cursor(&crosshair_cursor); X win_setmouseposition(canvas_win, cur_x, cur_y); X if (closed_spline(s) && left_point == NULL) { X for (left_point = moved_point->next, X p = left_point->next; X p->next != NULL; X left_point = p, p = p->next); X } X draw_pointlink(INV_PAINT); X canvas_locmove_proc = move_linepoint; X canvas_middlebut_proc = fix_movedsplinepoint; X canvas_leftbut_proc = null_proc; X } X XF_spline * Xspline_point_search(x, y, tol, p, q) Xint x, y, tol; XF_point **p, **q; X{ X F_spline *s; X X for (s = objects.splines; s != NULL; s= s->next) { X *p = NULL; X for (*q = s->points; *q != NULL; *p = *q, *q = (*q)->next) { X if (abs((*q)->x - x) <= tol && abs((*q)->y - y) <= tol) X return(s); X } X } X return(NULL); X } X Xfix_movedsplinepoint(x, y) Xint x, y; X{ X draw_pointlink(INV_PAINT); X new_position.x = x; X new_position.y = y; X clean_up(); X set_action_object(F_MOVE_POINT, O_SPLINE); X set_latestspline(cur_s); X relocate_splinepoint(cur_s, x, y, moved_point); X wrapup_movepoint(); X } X Xrelocate_splinepoint(s, x, y, moved_point) XF_spline *s; Xint x, y; XF_point *moved_point; X{ X set_temp_cursor(&wait_cursor); X if (pointmarker_shown) toggle_splinepointmarker(s); X draw_spline(s, ERASE); /* erase old spline */ X moved_point->x = x; X moved_point->y = y; X if (closed_spline(s)) { X left_point->next->x = x; X left_point->next->y = y; X } X if (int_spline(s)) remake_control_points(s); X draw_spline(s, PAINT); /* draw spline with moved point */ X if (pointmarker_shown) toggle_splinepointmarker(s); X reset_cursor(); X set_modifiedflag(); X } X X/*************************** line ********************************/ X Xstatic F_line *cur_l; X Xinit_linepointmoving(line) XF_line *line; X{ X int box_case; X int latex_case; X F_point *p; X X cur_l = line; X box_case = 0; X latex_case = 0; X last_position.x = cur_x = moved_point->x; X last_position.y = cur_y = moved_point->y; X set_temp_cursor(&crosshair_cursor); X win_setmouseposition(canvas_win, cur_x, cur_y); X switch (line->type) { X case T_POLYGON : X if (left_point == NULL) X for (left_point = moved_point->next, X p = left_point->next; X p->next != NULL; X left_point = p, p = p->next); X break; X case T_BOX : X case T_ARC_BOX : X if (moved_point->next->next == NULL) { /* point 4 */ X fix_x = line->points->next->x; X fix_y = line->points->next->y; X } X else { X fix_x = moved_point->next->next->x; X fix_y = moved_point->next->next->y; X } X if (line->type == T_ARC_BOX) X draw_arc_box(line, ERASE); X else X draw_line(line, ERASE); X box_case = 1; X break; X case T_POLYLINE : X if (left_point != NULL) { X if (left_point == line->points) { X if (line->back_arrow) /* backward arrow */ X draw_arrow(cur_x, cur_y, X left_point->x, left_point->y, X line->back_arrow, ERASE); X } X } X else if (line->back_arrow) /* backward arrow */ X draw_arrow(moved_point->next->x, moved_point->next->y, X cur_x, cur_y, line->back_arrow, ERASE); X p = moved_point->next; X if (p != NULL) { X if (line->for_arrow && p->next == NULL) X draw_arrow(cur_x, cur_y, p->x, p->y, X line->for_arrow, ERASE); X } X else if (line->for_arrow)/* f arrow */ X draw_arrow(left_point->x, left_point->y, X cur_x, cur_y, line->for_arrow, ERASE); X if (latexline_mode || latexarrow_mode) { X if (left_point != NULL) { X latex_fix_x = left_point->x; X latex_fix_y = left_point->y; X latex_case = 1; X } X else if (p != NULL) { X latex_fix_x = p->x; X latex_fix_y = p->y; X latex_case = 1; X } X } X } X if (box_case) { X draw_rectbox(fix_x, fix_y, cur_x, cur_y, INV_PAINT); X canvas_locmove_proc = elastic_box; X canvas_middlebut_proc = fix_box; X } X else if (latex_case) { X draw_pointlink(INV_PAINT); X canvas_locmove_proc = move_latexlinepoint; X canvas_middlebut_proc = fix_movedlatexlinepoint; X cur_latexcursor = &crosshair_cursor; X } X else { X draw_pointlink(INV_PAINT); X canvas_locmove_proc = move_linepoint; X canvas_middlebut_proc = fix_movedlinepoint; X } X canvas_leftbut_proc = null_proc; X } X Xmove_linepoint(x, y) Xint x, y; X{ X draw_pointlink(INV_PAINT); X cur_x = x; X cur_y = y; X draw_pointlink(INV_PAINT); X } X Xmove_latexlinepoint(x, y) Xint x, y; X{ X CURSOR c; X X draw_pointlink(INV_PAINT); X latex_endpoint(latex_fix_x, latex_fix_y, x, y, &cur_x, &cur_y, X latexarrow_mode, (magnet_mode)? 5: 1); X draw_pointlink(INV_PAINT); X c = (x == cur_x && y == cur_y)? &null_cursor: &crosshair_cursor; X if (c != cur_latexcursor) { X set_temp_cursor(c); X cur_latexcursor = c; X } X } X Xfix_box(x, y) Xint x, y; X{ X draw_rectbox(fix_x, fix_y, cur_x, cur_y, INV_PAINT); X new_position.x = x; X new_position.y = y; X clean_up(); X set_action_object(F_MOVE_POINT, O_POLYLINE); X set_latestline(line); X relocate_linepoint(line, x, y, fix_x, fix_y, moved_point, X left_point); X wrapup_movepoint(); X } X Xassign_newboxpoint(b, x1, y1, x2, y2) XF_line *b; Xint x1, y1, x2, y2; X{ X F_point *p; X register int tmp; X X p = b->points; X if (x1 > x2) /* sort them so that lower left is first */ X { X tmp = x1; x1 = x2; x2 = tmp; X } X if (y1 > y2) X { X tmp = y1; y1 = y2; y2 = tmp; X } X p->x = x1; p->y = y1; p = p->next; X p->x = x1; p->y = y2; p = p->next; X p->x = x2; p->y = y2; p = p->next; X p->x = x2; p->y = y1; p = p->next; X p->x = x1; p->y = y1; p = p->next; X } X Xfix_movedlinepoint(x, y) Xint x, y; X{ X draw_pointlink(INV_PAINT); X new_position.x = x; X new_position.y = y; X clean_up(); X set_action_object(F_MOVE_POINT, O_POLYLINE); X set_latestline(cur_l); X relocate_linepoint(cur_l, x, y, fix_x, fix_y, moved_point, left_point); X wrapup_movepoint(); X } X Xfix_movedlatexlinepoint(x, y) Xint x, y; X{ X draw_pointlink(INV_PAINT); X latex_endpoint(latex_fix_x, latex_fix_y, x, y, &x, &y, X latexarrow_mode, (magnet_mode)? 5: 1); X if (cur_latexcursor != &crosshair_cursor) X set_temp_cursor(&crosshair_cursor); X win_setmouseposition(canvas_win, x, y); X new_position.x = x; X new_position.y = y; X clean_up(); X set_action_object(F_MOVE_POINT, O_POLYLINE); X set_latestline(cur_l); X relocate_linepoint(cur_l, x, y, fix_x, fix_y, moved_point, left_point); X wrapup_movepoint(); X } X Xrelocate_linepoint(line, x, y, fix_x, fix_y, moved_point, left_point) XF_line *line; Xint x, y; XF_point *moved_point, *left_point; X{ X if (pointmarker_shown) toggle_linepointmarker(line); X draw_line(line, ERASE); X switch (line->type) { X case T_BOX : X case T_ARC_BOX: X assign_newboxpoint(line, fix_x, fix_y, x, y); X break; X case T_POLYGON : X if (line->points == moved_point) { X left_point->next->x = x; X left_point->next->y = y; X } X default : X moved_point->x = x; X moved_point->y = y; X } X draw_line(line, PAINT); X if (pointmarker_shown) toggle_linepointmarker(line); X set_modifiedflag(); X } X Xdraw_pointlink(op) Xint op; X{ X F_point *p; X X if (left_point != NULL) { X pw_vector(canvas_win, left_point->x, left_point->y, X cur_x, cur_y, op, 1, SOLID_LINE, 0.0); X } X if ((p = moved_point->next) != NULL) { X pw_vector(canvas_win, p->x, p->y, cur_x, cur_y, op, 1, SOLID_LINE, 0.0); X } X } X XF_line * Xline_point_search(x, y, tol, p, q) Xint x, y, tol; XF_point **p, **q; X{ X F_line *l; X F_point *a, *b; X X for (l = objects.lines; l != NULL; l= l->next) { X for (a = NULL, b = l->points; b != NULL; a = b, b = b->next) { X if (abs(b->x - x) <= tol && abs(b->y - y) <= tol) { X *p = a; X *q = b; X return(l); X } X } X } X return(NULL); X } END_OF_FILE if test 17045 -ne `wc -c <'movept.c'`; then echo shar: \"'movept.c'\" unpacked with wrong size! fi # end of 'movept.c' fi if test -f 'read.c' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'read.c'\" else echo shar: Extracting \"'read.c'\" \(16741 characters\) sed "s/^X//" >'read.c' <<'END_OF_FILE' X/* X * FIG : Facility for Interactive Generation of figures X * X * Copyright (c) 1985, 1988 by Supoj Sutanthavibul (supoj@sally.UTEXAS.EDU) X * January 1985. X * 1st revision : August 1985. X * 2nd revision : March 1988. X * X * %W% %G% X*/ X#include "fig.h" X#include "alloc.h" X#include "object.h" X#include "psfonts.h" X Xextern F_arrow *make_arrow(); Xextern char *calloc(); Xextern int errno; X Xstatic F_ellipse *read_ellipseobject(); Xstatic F_line *read_lineobject(); Xstatic F_text *read_textobject(); Xstatic F_spline *read_splineobject(); Xstatic F_arc *read_arcobject(); Xstatic F_compound *read_compoundobject(); X X#define BUF_SIZE 1024 X Xchar buf[BUF_SIZE]; Xint line_no; Xint num_object; Xint proto; /* file protocol*10 */ X Xread_fail_message(file, err) Xchar *file; Xint err; X{ X extern char *sys_errlist[]; X X if (err == 0) /* Successful read */ X return; X#ifdef ENAMETOOLONG X else if (err == ENAMETOOLONG) X put_msg("File name \"%s\" is too long", file); X#endif X else if (err == ENOENT) X put_msg("File \"%s\" does not exist", file); X else if (err == ENOTDIR) X put_msg("A name in the path \"%s\" is not a directory", file); X else if (err == EACCES) X put_msg("Read access to file \"%s\" is blocked", file); X else if (err == EISDIR) X put_msg("File \"%s\" is a directory", file); X else if (err == -2) { X put_msg("File \"%s\" is empty", file); X } X else if (err == -1) { X /* Format error; relevant error message is already delivered */ X } X else X put_msg("File \"%s\" is not accessable; %s", file, sys_errlist[err]); X } X X/********************************************************** XRead_fig returns : X X 0 : successful read. X -1 : File is in incorrect format X -2 : File is empty Xerr_no : if file can not be read for various reasons X XThe resolution (ppi) and the coordinate system (coord_sys) are Xstored in obj->nwcorner.x and obj->nwcorner.y respectively. XThe coordinate system is 1 for lower left at 0,0 and X2 for upper left at 0,0 X>>> xfig only uses 2 for the coordinate system. <<< X**********************************************************/ X Xread_fig(file_name, obj) Xchar *file_name; XF_compound *obj; X{ X FILE *fp; X X line_no = 0; X if ((fp = fopen(file_name, "r")) == NULL) X return(errno); X else X return(readfp_fig(fp, obj)); X } X Xreadfp_fig(fp, obj) XFILE *fp; XF_compound *obj; X{ X int status; X float fproto; X X num_object = 0; X bzero((char*)obj, COMOBJ_SIZE); X if (fgets(buf,BUF_SIZE,fp)==0) /* version */ X return -2; X if (strncmp(buf,"#FIG",4)==0) /* versions 1.4/later have #FIG in first line */ X { X if ((sscanf(index(buf,' ')+1,"%f",&fproto))==0) /* assume 1.4 */ X proto=14; X else X proto = (fproto+.01)*10; /* protocol version*10 */ X status = read_objects(fp, obj); X } X else X { X proto = 13; X status = read_1_3_objects(fp, obj); X } X X fclose(fp); X return(status); X } X Xint Xread_objects(fp, obj) XFILE *fp; XF_compound *obj; X{ X F_ellipse *e, *le = NULL; X F_line *l, *ll = NULL; X F_text *t, *lt = NULL; X F_spline *s, *ls = NULL; X F_arc *a, *la = NULL; X F_compound *c, *lc = NULL; X int object, ppi, coord_sys; X X line_no++; X if (get_line(fp) < 0) { X put_msg("File is truncated"); X return(-1); X } X if (2 != sscanf(buf,"%d%d\n", &ppi, &coord_sys)) { X put_msg("Incomplete data at line %d", line_no); X return(-1); X } X X obj->nwcorner.x = ppi; X obj->nwcorner.y = coord_sys; X while (get_line(fp) > 0) { X if (1 != sscanf(buf, "%d", &object)) { X put_msg("Incorrect format at line %d", line_no); X return(-1); X } X switch (object) { X case O_POLYLINE : X if ((l = read_lineobject(fp)) == NULL) return(-1); X if (ll) X ll = (ll->next = l); X else X ll = obj->lines = l; X num_object++; X break; X case O_SPLINE : X if ((s = read_splineobject(fp)) == NULL) return(-1); X if (ls) X ls = (ls->next = s); X else X ls = obj->splines = s; X num_object++; X break; X case O_ELLIPSE : X if ((e = read_ellipseobject()) == NULL) return(-1); X if (le) X le = (le->next = e); X else X le = obj->ellipses = e; X num_object++; X break; X case O_ARC : X if ((a = read_arcobject(fp)) == NULL) return(-1); X if (la) X la = (la->next = a); X else X la = obj->arcs = a; X num_object++; X break; X case O_TEXT : X if ((t = read_textobject(fp)) == NULL) return(-1); X if (lt) X lt = (lt->next = t); X else X lt = obj->texts = t; X num_object++; X break; X case O_COMPOUND : X if ((c = read_compoundobject(fp)) == NULL) return(-1); X if (lc) X lc = (lc->next = c); X else X lc = obj->compounds = c; X num_object++; X break; X default : X put_msg("Incorrect object code at line %d", line_no); X return(-1); X } /* switch */ X } /* while */ X if (feof(fp)) X return(0); X else X return(errno); X } /* read_objects */ X Xstatic F_arc * Xread_arcobject(fp) XFILE *fp; X{ X F_arc *a; X int n, fa, ba; X int type, style; X float thickness, wid, ht; X X if (NULL == (Arc_malloc(a))) { X put_msg(Err_mem); X return(NULL); X } X a->next = NULL; X a->for_arrow = a->back_arrow = NULL; /* added 8/23/89 B.V.Smith */ X n = sscanf(buf, "%*d%d%d%d%d%d%d%d%f%d%d%d%f%f%d%d%d%d%d%d\n", X &a->type, &a->style, &a->thickness, X &a->color, &a->depth, X &a->pen, &a->area_fill, X &a->style_val, &a->direction, &fa, &ba, X &a->center.x, &a->center.y, X &a->point[0].x, &a->point[0].y, X &a->point[1].x, &a->point[1].y, X &a->point[2].x, &a->point[2].y); X if (n != 19) { X put_msg(Err_incomp, "arc", line_no); X free((char*)a); X return(NULL); X } X X skip_comment(fp); X if (fa) { X line_no++; X if (5 != fscanf(fp, "%d%d%f%f%f", &type, &style, &thickness, &wid, &ht)) { X fprintf(stderr, Err_incomp, "arc", line_no); X return(NULL); X } X skip_line(fp); X a->for_arrow = make_arrow(type, style, thickness, wid, ht); X skip_comment(fp); X } X skip_comment(fp); X if (ba) { X line_no++; X if (5 != fscanf(fp, "%d%d%f%f%f", &type, &style, &thickness, &wid, &ht)) { X fprintf(stderr, Err_incomp, "arc", line_no); X return(NULL); X } X skip_line(fp); X a->back_arrow = make_arrow(type, style, thickness, wid, ht); X } X return(a); X } X Xstatic F_compound * Xread_compoundobject(fp) XFILE *fp; X{ X F_arc *a, *la = NULL; X F_ellipse *e, *le = NULL; X F_line *l, *ll = NULL; X F_spline *s, *ls = NULL; X F_text *t, *lt = NULL; X F_compound *com, *c, *lc = NULL; X int n, object; X X if (NULL == (Compound_malloc(com))) { X put_msg(Err_mem); X return(NULL); X } X com->arcs = NULL; X com->ellipses = NULL; X com->lines = NULL; X com->splines = NULL; X com->texts = NULL; X com->compounds = NULL; X com->next = NULL; X n = sscanf(buf, "%*d%d%d%d%d\n", &com->nwcorner.x, &com->nwcorner.y, X &com->secorner.x, &com->secorner.y); X if (4 != n) { X put_msg(Err_incomp, "compound", line_no); X free((char*)com); X return(NULL); X } X while (get_line(fp) > 0) { X if (1 != sscanf(buf, "%d", &object)) { X put_msg(Err_incomp, "compound", line_no); X free_compound(&com); X return(NULL); X } X switch (object) { X case O_POLYLINE : X if ((l = read_lineobject(fp)) == NULL) { X free_line(&l); X return(NULL); X } X if (ll) X ll = (ll->next = l); X else X ll = com->lines = l; X break; X case O_SPLINE : X if ((s = read_splineobject(fp)) == NULL) { X free_spline(&s); X return(NULL); X } X if (ls) X ls = (ls->next = s); X else X ls = com->splines = s; X break; X case O_ELLIPSE : X if ((e = read_ellipseobject()) == NULL) { X free_ellipse(&e); X return(NULL); X } X if (le) X le = (le->next = e); X else X le = com->ellipses = e; X break; X case O_ARC : X if ((a = read_arcobject(fp)) == NULL) { X free_arc(&a); X return(NULL); X } X if (la) X la = (la->next = a); X else X la = com->arcs = a; X break; X case O_TEXT : X if ((t = read_textobject(fp)) == NULL) { X free_text(&t); X return(NULL); X } X if (lt) X lt = (lt->next = t); X else X lt = com->texts = t; X break; X case O_COMPOUND : X if ((c = read_compoundobject(fp)) == NULL) { X free_compound(&c); X return(NULL); X } X if (lc) X lc = (lc->next = c); X else X lc = com->compounds = c; X break; X case O_END_COMPOUND : X return(com); X default : X put_msg("Wrong object code at line %d", line_no); X return(NULL); X } /* switch */ X } X if (feof(fp)) X return(com); X else X return(NULL); X } X Xstatic F_ellipse * Xread_ellipseobject() X{ X F_ellipse *e; X int n; X X if (NULL == (Ellipse_malloc(e))) { X put_msg(Err_mem); X return(NULL); X } X e->next = NULL; X n = sscanf(buf, "%*d%d%d%d%d%d%d%d%f%d%f%d%d%d%d%d%d%d%d\n", X &e->type, &e->style, &e->thickness, X &e->color, &e->depth, &e->pen, &e->area_fill, X &e->style_val, &e->direction, &e->angle, X &e->center.x, &e->center.y, X &e->radiuses.x, &e->radiuses.y, X &e->start.x, &e->start.y, X &e->end.x, &e->end.y); X if (n != 18) { X put_msg(Err_incomp, "ellipse", line_no); X free((char*)e); X return(NULL); X } X return(e); X } X Xstatic F_line * Xread_lineobject(fp) XFILE *fp; X{ X F_line *l; X F_point *p, *q; X int n, x, y, fa, ba; X int type, style; X float thickness, wid, ht; X X if (NULL == (Line_malloc(l))) { X put_msg(Err_mem); X return(NULL); X } X l->points = NULL; X l->for_arrow = l->back_arrow = NULL; X l->next = NULL; X X sscanf(buf,"%*d%d",&l->type); X#ifndef TFX X /* 2.0 or later; has separate radius parm for arc-box corners */ X if (l->type == T_ARC_BOX && proto >= 20) X { X n = sscanf(buf, "%*d%d%d%d%d%d%d%d%f%d%d%d", X &l->type, &l->style, &l->thickness, &l->color, X &l->depth, &l->pen, &l->area_fill, &l->style_val, &l->radius, X &fa, &ba); X } X /* old format uses pen for radius of arc-box corners */ X else X#endif TFX X { X n = sscanf(buf, "%*d%d%d%d%d%d%d%d%f%d%d", X &l->type, &l->style, &l->thickness, &l->color, X &l->depth, &l->pen, &l->area_fill, &l->style_val, &fa, &ba); X#ifndef TFX X if (l->type == T_ARC_BOX) X { X l->radius = l->pen; X l->pen = 0; X } X else X#endif TFX X l->radius = 0; X } X X#ifdef TFX X if (n != 10) X#else X if ((proto==14 && n != 10) || X (proto==20 && (l->type == T_ARC_BOX && n != 11) || X (l->type != T_ARC_BOX && n != 10))) { X#endif TFX X put_msg(Err_incomp, "line", line_no); X free((char*)l); X return(NULL); X } X skip_comment(fp); X if (fa) { X line_no++; X if (5 != fscanf(fp, "%d%d%f%f%f", &type, &style, &thickness, &wid, &ht)) { X fprintf(stderr, Err_incomp, "line", line_no); X return(NULL); X } X skip_line(fp); X l->for_arrow = make_arrow(type, style, thickness, wid, ht); X skip_comment(fp); X } X if (ba) { X line_no++; X if (5 != fscanf(fp, "%d%d%f%f%f", &type, &style, &thickness, &wid, &ht)) { X fprintf(stderr, Err_incomp, "line", line_no); X return(NULL); X } X skip_line(fp); X l->back_arrow = make_arrow(type, style, thickness, wid, ht); X skip_comment(fp); X } X X if (NULL == (l->points = Point_malloc(p))) { X put_msg(Err_mem); X return(NULL); X } X p->next = NULL; X X /* points start on new line */ X line_no++; X X /* read first point */ X if (fscanf(fp, "%d%d", &p->x, &p->y) != 2) { X put_msg(Err_incomp, "line", line_no); X free_linestorage(l); X return(NULL); X } X /* read subsequent points */ X for (;;) { X if (fscanf(fp, "%d%d", &x, &y) != 2) { X put_msg(Err_incomp, "line", line_no); X free_linestorage(l); X return(NULL); X } X if (x == 9999) break; X if (NULL == (Point_malloc(q))) { X put_msg(Err_mem); X free_linestorage(l); X return(NULL); X } X q->x = x; X q->y = y; X q->next = NULL; X p->next = q; X p = q; X } X skip_line(fp); X return(l); X } X Xstatic F_spline * Xread_splineobject(fp) XFILE *fp; X{ X F_spline *s; X F_point *p, *q; X F_control *cp, *cq; X int c, n, x, y, fa, ba; X int type, style; X float thickness, wid, ht; X float lx, ly, rx, ry; X X if (NULL == (Spline_malloc(s))) { X put_msg(Err_mem); X return(NULL); X } X s->points = NULL; X s->controls = NULL; X s->for_arrow = s->back_arrow = NULL; X s->next = NULL; X X n = sscanf(buf, "%*d%d%d%d%d%d%d%d%f%d%d%d%d%d%d", X &s->type, &s->style, &s->thickness, &s->color, X &s->depth, &s->pen, &s->area_fill, &s->style_val, &fa, &ba); X if (n != 10) { X put_msg(Err_incomp, "spline", line_no); X free((char*)s); X return(NULL); X } X skip_comment(fp); X if (fa) { X line_no++; X if (5 != fscanf(fp, "%d%d%f%f%f", &type, &style, &thickness, &wid, &ht)) { X fprintf(stderr, Err_incomp, "spline", line_no); X return(NULL); X } X skip_line(fp); X s->for_arrow = make_arrow(type, style, thickness, wid, ht); X skip_comment(fp); X } X if (ba) { X line_no++; X if (5 != fscanf(fp, "%d%d%f%f%f", &type, &style, &thickness, &wid, &ht)) { X fprintf(stderr, Err_incomp, "spline", line_no); X return(NULL); X } X skip_line(fp); X s->back_arrow = make_arrow(type, style, thickness, wid, ht); X skip_comment(fp); X } X X line_no++; X X /* Read points */ X if ((n = fscanf(fp, "%d%d", &x, &y)) != 2) { X put_msg(Err_incomp, "spline", line_no); X free_splinestorage(s); X return(NULL); X }; X if (NULL == (s->points = Point_malloc(p))) { X put_msg(Err_mem); X free_splinestorage(s); X return(NULL); X } X p->x = x; p->y = y; X for (c = 1;;) { X if (fscanf(fp, "%d%d", &x, &y) != 2) { X put_msg(Err_incomp, "spline", line_no); X p->next = NULL; X free_splinestorage(s); X return(NULL); X }; X if (x == 9999) break; X if (NULL == (Point_malloc(q))) { X put_msg(Err_mem); X free_splinestorage(s); X return(NULL); X } X q->x = x; X q->y = y; X p->next = q; X p = q; X c++; X } X p->next = NULL; X skip_line(fp); X X if (normal_spline(s)) return(s); X X line_no++; X skip_comment(fp); X /* Read controls */ X if ((n = fscanf(fp, "%f%f%f%f", &lx, &ly, &rx, &ry)) != 4) { X put_msg(Err_incomp, "spline", line_no); X free_splinestorage(s); X return(NULL); X }; X if (NULL == (s->controls = Control_malloc(cp))) { X put_msg(Err_mem); X free_splinestorage(s); X return(NULL); X } X cp->lx = lx; cp->ly = ly; X cp->rx = rx; cp->ry = ry; X while (--c) { X if (fscanf(fp, "%f%f%f%f", &lx, &ly, &rx, &ry) != 4) { X put_msg(Err_incomp, "spline", line_no); X cp->next = NULL; X free_splinestorage(s); X return(NULL); X }; X if (NULL == (Control_malloc(cq))) { X put_msg(Err_mem); X cp->next = NULL; X free_splinestorage(s); X return(NULL); X } X cq->lx = lx; cq->ly = ly; X cq->rx = rx; cq->ry = ry; X cp->next = cq; X cp = cq; X } X cp->next = NULL; X X skip_line(fp); X return(s); X } X Xstatic F_text * Xread_textobject(fp) XFILE *fp; X{ X F_text *t; X int n; X int ignore = 0; X char s[BUF_SIZE], s_temp[BUF_SIZE], junk[2]; X X if (NULL == (Text_malloc(t))) { X put_msg(Err_mem); X return(NULL); X } X t->next = NULL; X /* The text object is terminated by a CONTROL-A, so we read X everything up to the CONTROL-A and then read that character. X If we do not find the CONTROL-A on this line then this must X be a multi-line text object and we will have to read more. */ X n = sscanf(buf,"%*d%d%d%d%d%d%d%f%d%d%d%d%d %[^\1]%[\1]", X &t->type, &t->font, &t->size, &t->pen, X &t->color, &t->depth, &t->angle, X &t->style, &t->height, &t->length, X &t->base_x, &t->base_y, s, junk); X if (n != 13 && n != 14) { X put_msg(Err_incomp, "text", line_no); X free((char*)t); X /* return(NULL); */ X } X if (n == 13) { X /* Read in the remainder of the text object. */ X do { X fgets(buf, BUF_SIZE, fp); X line_no++; /* As is done in get_line */ X n = sscanf(buf,"%[^\1]%[\1]", s_temp, junk); X /* Safety check */ X if (strlen(s)+1 + strlen(s_temp)+1 > BUF_SIZE) { X /* Too many characters. Ignore the rest. */ X ignore = 1; X } X if (!ignore) X strcat(s, s_temp); X } while (n == 1); X } X if (t->type > T_RIGHT_JUSTIFIED) X { X put_msg("Invalid text justification at line %d.",line_no); X return(NULL); X } X if (t->font >= NUMFONTS) X { X put_msg("Invalid text font (%d) at line %d.",t->font,line_no); X return(NULL); X } X if (strlen(s) == 0) X (void) strcpy(s," "); X t->cstring = (char*)calloc((unsigned)(strlen(s)+1), sizeof(char)); X if (NULL == t->cstring) { X put_msg(Err_mem); X free((char*)t); X return(NULL); X } X (void) strcpy(t->cstring, s); X return(t); X } X Xget_line(fp) XFILE *fp; X{ X while (1) { X if (NULL == fgets(buf, BUF_SIZE, fp)) { X return(-1); X } X line_no++; X if (*buf != '\n' && *buf != '#') /* Skip empty and comment lines */ X return(1); X } X } X Xskip_comment(fp) XFILE *fp; X{ X char c; X X while ((c = fgetc(fp)) == '#') skip_line(fp); X if (c != '#') ungetc(c, fp); X } X Xskip_line(fp) XFILE *fp; X{ X while (fgetc(fp) != '\n') { X if (feof(fp)) return; X } X } END_OF_FILE if test 16741 -ne `wc -c <'read.c'`; then echo shar: \"'read.c'\" unpacked with wrong size! fi # end of 'read.c' fi echo shar: End of archive 13 \(of 21\). cp /dev/null ark13isdone MISSING="" for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 ; do if test ! -f ark${I}isdone ; then MISSING="${MISSING} ${I}" fi done if test "${MISSING}" = "" ; then echo You have unpacked all 21 archives. rm -f ark[1-9]isdone ark[1-9][0-9]isdone else echo You still need to unpack the following archives: echo " " ${MISSING} fi ## End of shell archive. exit 0 dan ---------------------------------------------------- O'Reilly && Associates argv@sun.com / argv@ora.com Opinions expressed reflect those of the author only.