Subversion Repositories planix.SVN

Rev

Rev 2 | Blame | Compare with Previous | Last modification | View Log | RSS feed

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include "grap.h"
#include "y.tab.h"

int     nnum    = 0;    /* number of saved numbers */
double  num[MAXNUM];

int     just;           /* current justification mode (RJUST, etc.) */
int     sizeop;         /* current optional operator for size change */
double  sizexpr;        /* current size change expression */

void savenum(int n, double f)   /* save f in num[n] */
{
        num[n] = f;
        nnum = n+1;
        if (nnum >= MAXNUM)
                ERROR "too many numbers" WARNING;
}

void setjust(int j)
{
        just |= j;
}

void setsize(int op, double expr)
{
        sizeop = op;
        sizexpr = expr;
}

char *tostring(char *s)
{
        register char *p;

        p = malloc(strlen(s)+1);
        if (p == NULL)
                ERROR "out of space in tostring on %s", s FATAL;
        strcpy(p, s);
        return(p);
}

void range(Point pt)    /* update the range for point pt */
{
        Obj *p = pt.obj;

        if (!(p->coord & XFLAG)) {
                if (pt.x > p->pt1.x)
                        p->pt1.x = pt.x;
                if (pt.x < p->pt.x)
                        p->pt.x = pt.x;
        }
        if (!(p->coord & YFLAG)) {
                if (pt.y > p->pt1.y)
                        p->pt1.y = pt.y;
                if (pt.y < p->pt.y)
                        p->pt.y = pt.y;
        }
}

void halfrange(Obj *p, int side, double val)    /* record max and min for one direction */
{
        if (!(p->coord&XFLAG) && (side == LEFT || side == RIGHT)) {
                if (val < p->pt.y)
                        p->pt.y = val;
                if (val > p->pt1.y)
                        p->pt1.y = val;
        } else if (!(p->coord&YFLAG) && (side == TOP || side == BOT)) {
                if (val < p->pt.x)
                        p->pt.x = val;
                if (val > p->pt1.x)
                        p->pt1.x = val;
        }
}


Obj *lookup(char *s, int inst)  /* find s in objlist, install if inst */
{
        Obj *p;
        int found = 0;

        for (p = objlist; p; p = p->next){
                if (strcmp(s, p->name) == 0) {
                        found = 1;
                        break;
                }
        }
        if (p == NULL && inst != 0) {
                p = (Obj *) calloc(1, sizeof(Obj));
                if (p == NULL)
                        ERROR "out of space in lookup" FATAL;
                p->name = tostring(s);
                p->type = NAME;
                p->pt = ptmax;
                p->pt1 = ptmin;
                p->fval = 0.0;
                p->next = objlist;
                objlist = p;
        }
        dprintf("lookup(%s,%d) = %d\n", s, inst, found);
        return p;
}

double getvar(Obj *p)   /* return value of variable */
{
        return p->fval;
}

double setvar(Obj *p, double f) /* set value of variable to f */
{
        if (strcmp(p->name, "pointsize") == 0) {        /* kludge */
                pointsize = f;
                ps_set = 1;
        }
        p->type = VARNAME;
        return p->fval = f;
}

Point makepoint(Obj *s, double x, double y)     /* make a Point */
{
        Point p;
        
        dprintf("makepoint: %s, %g,%g\n", s->name, x, y);
        p.obj = s;
        p.x = x;
        p.y = y;
        return p;
}

Attr *makefattr(int type, double fval)  /* set double in attribute */
{
        return makeattr(type, fval, (char *) 0, 0, 0);
}

Attr *makesattr(char *s)                /* make an Attr cell containing s */
{
        Attr *ap = makeattr(STRING, sizexpr, s, just, sizeop);
        just = sizeop = 0;
        sizexpr = 0.0;
        return ap;
}

Attr *makeattr(int type, double fval, char *sval, int just, int op)
{
        Attr *a;

        a = (Attr *) malloc(sizeof(Attr));
        if (a == NULL)
                ERROR "out of space in makeattr" FATAL;
        a->type = type;
        a->fval = fval;
        a->sval = sval;
        a->just = just;
        a->op = op;
        a->next = NULL;
        return a;
}

Attr *addattr(Attr *a1, Attr *ap)       /* add attr ap to end of list a1 */
{
        Attr *p;

        if (a1 == 0)
                return ap;
        if (ap == 0)
                return a1;
        for (p = a1; p->next; p = p->next)
                ;
        p->next = ap;
        return a1;
}

void freeattr(Attr *ap) /* free an attribute list */
{
        Attr *p;

        while (ap) {
                p = ap->next;   /* save next */
                if (ap->sval)
                        free(ap->sval);
                free((char *) ap);
                ap = p;
        }
}

char *slprint(Attr *stringlist) /* print strings from stringlist */
{
        int ntext, n, last_op, last_just;
        double last_fval;
        static char buf[1000];
        Attr *ap;

        buf[0] = '\0';
        last_op = last_just = 0;
        last_fval = 0.0;
        for (ntext = 0, ap = stringlist; ap != NULL; ap = ap->next)
                ntext++;
        sprintf(buf, "box invis wid 0 ht %d*textht", ntext);
        n = strlen(buf);
        for (ap = stringlist; ap != NULL; ap = ap->next) {
                if (ap->op == 0) {      /* propagate last value */
                        ap->op = last_op;
                        ap->fval = last_fval;
                } else {
                        last_op = ap->op;
                        last_fval = ap->fval;
                }
                sprintf(buf+n, " \"%s\"", ps_set || ap->op ? sizeit(ap) : ap->sval);
                if (ap->just)
                        last_just = ap->just;
                if (last_just)
                        strcat(buf+n, juststr(last_just));
                n = strlen(buf);
        }
        return buf;     /* watch it:  static */
}

char *juststr(int j)    /* convert RJUST, etc., into string */
{
        static char buf[50];

        buf[0] = '\0';
        if (j & RJUST)
                strcat(buf, " rjust");
        if (j & LJUST)
                strcat(buf, " ljust");
        if (j & ABOVE)
                strcat(buf, " above");
        if (j & BELOW)
                strcat(buf, " below");
        return buf;     /* watch it:  static */
}

char *sprntf(char *s, Attr *ap) /* sprintf(s, attrlist ap) */
{
        char buf[500];
        int n;
        Attr *p;

        for (n = 0, p = ap; p; p = p->next)
                n++;
        switch (n) {
        case 0:
                return s;
        case 1:
                sprintf(buf, s, ap->fval);
                break;
        case 2:
                sprintf(buf, s, ap->fval, ap->next->fval);
                break;
        case 3:
                sprintf(buf, s, ap->fval, ap->next->fval, ap->next->next->fval);
                break;
        case 5:
                ERROR "too many expressions in sprintf" WARNING;
        case 4:
                sprintf(buf, s, ap->fval, ap->next->fval, ap->next->next->fval, ap->next->next->next->fval);
                break;
        }
        free(s);
        return tostring(buf);
}