117292Sopcode /*
2*17651Sopcode * @(#)point.c 1.2 01/03/85
317292Sopcode *
417292Sopcode * Routines for manipulating the point data structures of the
517292Sopcode * SUN Gremlin picture editor.
617292Sopcode *
717292Sopcode * Mark Opperman (opcode@monet.BERKELEY)
817292Sopcode *
917292Sopcode */
1017292Sopcode
1117292Sopcode #include "gremlin.h"
1217292Sopcode
1317292Sopcode /* imports from graphics.c */
1417292Sopcode
1517292Sopcode extern GRFontStrlen();
1617292Sopcode
1717292Sopcode /* imports from C */
1817292Sopcode
1917292Sopcode extern char *malloc();
2017292Sopcode
2117292Sopcode
2217292Sopcode /*
2317292Sopcode * This routine creates a new point with coordinates x and y and
2417292Sopcode * links it into the pointlist.
2517292Sopcode */
2617292Sopcode POINT *
PTMakePoint(x,y,pplist)2717292Sopcode PTMakePoint(x, y, pplist)
2817292Sopcode float x, y;
2917292Sopcode POINT **pplist;
3017292Sopcode {
3117292Sopcode register POINT *point;
3217292Sopcode
3317292Sopcode if (Nullpoint(point = *pplist)) { /* empty list */
3417292Sopcode *pplist = (POINT *) malloc(sizeof(POINT));
3517292Sopcode point = *pplist;
3617292Sopcode }
3717292Sopcode else {
3817292Sopcode while (!Nullpoint(point->nextpt))
3917292Sopcode point = point->nextpt;
4017292Sopcode point->nextpt = (POINT *) malloc(sizeof(POINT));
4117292Sopcode point = point->nextpt;
4217292Sopcode }
4317292Sopcode
4417292Sopcode point->x = x;
4517292Sopcode point->y = y;
4617292Sopcode point->nextpt = PTInit();
4717292Sopcode return(point);
4817292Sopcode } /* end PTMakePoint */
4917292Sopcode
5017292Sopcode
5117292Sopcode /*
5217292Sopcode * This routine removes the specified point from the pointlist and
5317292Sopcode * returns it to free storage. Deletion is done in place by copying the
5417292Sopcode * next point over the one to be deleted and then removing the (previously)
5517292Sopcode * next point.
5617292Sopcode *
5717292Sopcode * It is up to the caller to ensure that, if a list contains only one POINT,
5817292Sopcode * any pointers to that list are set to NULL after this call.
5917292Sopcode */
PTDeletePoint(pt,plist)6017292Sopcode PTDeletePoint(pt, plist)
6117292Sopcode register POINT *pt; /* the point to deleted */
6217292Sopcode register POINT **plist; /* the address of the list from
6317292Sopcode which it is to be deleted */
6417292Sopcode {
6517292Sopcode register POINT *tempt;
6617292Sopcode
6717292Sopcode if (Nullpoint(pt->nextpt)) { /* last POINT in list */
6817292Sopcode if (*plist == pt) /* only POINT in list */
6917292Sopcode *plist = (POINT *) NULL;
7017292Sopcode else { /* search for previous point */
7117292Sopcode tempt = *plist;
7217292Sopcode while (tempt->nextpt != pt)
7317292Sopcode tempt = tempt->nextpt;
7417292Sopcode tempt->nextpt = (POINT *) NULL;
7517292Sopcode }
7617292Sopcode free((char *) pt);
7717292Sopcode }
7817292Sopcode else { /* copy over */
7917292Sopcode tempt = PTNextPoint(pt);
8017292Sopcode pt->x = tempt->x;
8117292Sopcode pt->y = tempt->y;
8217292Sopcode pt->nextpt = tempt->nextpt;
8317292Sopcode free((char *) tempt);
8417292Sopcode }
8517292Sopcode } /* end PTDeletePoint */
8617292Sopcode
8717292Sopcode
8817292Sopcode /*
8917292Sopcode * This routine makes the four positioning points required for text
9017292Sopcode * elements: (1) the point layed down by the user, (2) the bottom left
9117292Sopcode * corner of the text display, (3) the midpoint of the bottom edge of
9217292Sopcode * the text display, and (4) the bottom right corner of the text display.
9317292Sopcode * A pointer to this list is returned.
9417292Sopcode */
9517292Sopcode POINT *
PTMakeTextPoints(text,font,size,point,pos)9617292Sopcode PTMakeTextPoints(text, font, size, point, pos)
9717292Sopcode char *text;
9817292Sopcode int font, size;
9917292Sopcode register POINT *point; /* point layed down by user */
10017292Sopcode register POINT *pos; /* bottom left corner of text display */
10117292Sopcode {
10217292Sopcode register length;
10317292Sopcode POINT *pt;
10417292Sopcode
10517292Sopcode length = GRFontStrlen(text, font, size);
10617292Sopcode
10717292Sopcode pt = PTInit();
10817292Sopcode (void) PTMakePoint(point->x, point->y, &pt); /* user's point */
10917292Sopcode (void) PTMakePoint(pos->x, pos->y, &pt); /* bottom left */
11017292Sopcode (void) PTMakePoint(pos->x + (length / 2), pos->y, &pt); /* bottom midpt */
11117292Sopcode (void) PTMakePoint(pos->x + length, pos->y, &pt); /* bottom right */
11217292Sopcode
11317292Sopcode return(pt);
11417292Sopcode }
11517292Sopcode
11617292Sopcode
11717292Sopcode /*
11817292Sopcode * Change the text points to reflect the current justification,
11917292Sopcode * font and size of a text element.
12017292Sopcode */
PTModifyTextPoints(elt)12117292Sopcode PTModifyTextPoints(elt)
12217292Sopcode register ELT *elt;
12317292Sopcode {
12417292Sopcode register length;
12517292Sopcode register POINT *pos, *point;
12617292Sopcode
12717292Sopcode length = GRFontStrlen(elt->textpt, elt->brushf, elt->size);
12817292Sopcode pos = PTNextPoint(elt->ptlist); /* bottom left */
12917292Sopcode
13017292Sopcode GRSetTextPos(elt->textpt, elt->type, elt->brushf, elt->size,
13117292Sopcode elt->ptlist, pos);
13217292Sopcode
13317292Sopcode point = PTNextPoint(pos); /* bottom midpoint */
13417292Sopcode point->x = pos->x + (length / 2);
13517292Sopcode point->y = pos->y;
13617292Sopcode point = PTNextPoint(point); /* bottom right */
13717292Sopcode point->x = pos->x + length;
13817292Sopcode point->y = pos->y;
13917292Sopcode }
14017292Sopcode
14117292Sopcode
14217292Sopcode /*
14317292Sopcode * Return number of POINTs in an element.
14417292Sopcode */
PTListLength(elt)14517292Sopcode PTListLength(elt)
14617292Sopcode register ELT *elt;
14717292Sopcode {
14817292Sopcode register POINT *point;
14917292Sopcode register length = 1;
15017292Sopcode
15117292Sopcode if (Nullpoint(point = elt->ptlist)) {
15217292Sopcode printf("PTListLength: empty point list\n");
15317292Sopcode return(0);
15417292Sopcode }
15517292Sopcode
15617292Sopcode while (!Nullpoint(point->nextpt)) {
15717292Sopcode length++;
15817292Sopcode point = point->nextpt;
15917292Sopcode }
16017292Sopcode
16117292Sopcode return(length);
16217292Sopcode }
163