/*********************************************************************** * * TITLE: * rectlist.c * * AUTHOR: * Kevin J. Miller * * DESCRIPTION: * This is a set of routines to manage rectangle lists that * are part of standard screen objects. * * CHANGE HISTORY * * $Log: rectlist.c,v $ * Revision 1.8 1997/01/01 01:06:59 kevin * fixed compiler warnings * * Revision 1.7 1994/05/19 22:36:04 kevin * renamed add_expose_event to AddExposeEvent * * Revision 1.6 1994/04/30 02:44:04 kevin * port to ANSI * * Revision 1.5 1993/10/08 21:07:23 chester * update message functions * * Revision 1.4 1991/12/05 23:20:12 chester * added getSenseRect function. * * Revision 1.3 1991/09/04 22:34:32 kevin * added new functions from Chester * * Revision 1.2 1991/08/12 23:28:06 kevin * added background sense * * Revision 1.1 1991/08/12 21:41:08 kevin * Initial revision * *********************************************************************** * * WARNINGS: * * EXTERNAL CALLABLE COMPONENTS (PUBLIC): * * GLOBALS: * * WAIVERS: * * NOTES: * * MANPAGE: * ***********************************************************************/ #ifndef lint static const char rcsid[] = "$Id: rectlist.c,v 1.8 1997/01/01 01:06:59 kevin OEL $"; #endif #include #include "rectlist.h" #include "message.h" /* * external function prototype */ extern AddExposeEvent(int, XRectangle *); static XRectangle *moverects[16]; static int bg_sense; /*********************************************************************** * * FUNCTION: * newRectList() * * INPUTS: * count - (int) count of rectangles * rval - (XRectangle *) pointer to a rectangle * type - (int) flags to assign to this rectangle * : - more (rval, type) pairs * * OUTPUTS: * * RETURNS: * rlist - (RectList *) pointer to new rectangle list * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * * DESCRIPTION: * This function creates, assembles, and returns a new rectangle * list, which is generally part of the screen object structure. */ RectList * newRectList(int count, ...) { va_list ap; /* variable argument list */ RectList *rlist; /* pointer to list of rectangles */ int i; /* local index */ va_start(ap, count); rlist = XtNew(RectList); rlist->avail = rlist->count = count; if (rlist->count) { rlist->rects = (RectElem (*)[])XtCalloc((Cardinal)rlist->count, (Cardinal)sizeof(RectElem)); for (i = 0; i < rlist->count; ++i) { (*(rlist->rects))[i].rvals = *va_arg(ap, XRectangle *); (*(rlist->rects))[i].type = va_arg(ap, int); } } else { rlist->rects = NULL; } va_end(ap); return rlist; } /*********************************************************************** * * FUNCTION: * setRectList() * * INPUTS: * rlist - (RectList *) pointer to existing structure * count - (int) count of rectangles * rval - (XRectangle *) pointer to a rectangle * type - (int) flags to assign to this rectangle * : - more (rval, type) pairs * * OUTPUTS: * * RETURNS: * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * * DESCRIPTION: * This sets an existing rectangle list to the new values. */ void setRectList(RectList *rlist, ...) { va_list ap; /* variable argument list */ int i; /* local index */ va_start(ap, rlist); if (rlist == NULL) { Message("Internal editor error - fail at setRectList()"); } else { rlist->count = va_arg(ap, int); if (rlist->count > rlist->avail) { if (rlist->rects != NULL) XtFree((char *)(rlist->rects)); rlist->rects = (RectElem (*)[])XtCalloc((Cardinal)rlist->count, sizeof(RectElem)); rlist->avail = rlist->count; } for (i = 0; i < rlist->count; ++i) { (*(rlist->rects))[i].rvals = *va_arg(ap, XRectangle *); (*(rlist->rects))[i].type = va_arg(ap, int); } } va_end(ap); } /*********************************************************************** * * FUNCTION: * freeRectList() * * INPUTS: * rlist - (RectList *) pointer to existing rectangle list * * OUTPUTS: * * RETURNS: * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * * DESCRIPTION: * This function frees up memory used by an rectangle list. */ void freeRectList(RectList *rlist) { if (rlist != NULL) { if (rlist->rects != NULL) XtFree((char *)(rlist->rects)); XtFree((char *)(rlist)); } } /*********************************************************************** * * FUNCTION: * copyRectList() * * INPUTS: * rlist - (RectList *) pointer to existing rectangle list * * OUTPUTS: * * RETURNS: * rlistcpy - (RectList *) pointer to copy of above * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * * DESCRIPTION: * This function returns a copy of an existing RectList. */ RectList * copyRectList(RectList *rlist) { RectList *rlistcpy; int i; if (rlist != NULL) { rlistcpy = XtNew(RectList); rlistcpy->count = rlist->count; rlistcpy->avail = rlist->avail; if (rlistcpy->avail) { rlistcpy->rects = (RectElem (*)[])XtCalloc( (Cardinal)rlistcpy->avail, (Cardinal)sizeof(RectElem)); for (i = 0; i < rlist->count; ++i) { (*(rlistcpy->rects))[i].rvals = (*(rlist->rects))[i].rvals; (*(rlistcpy->rects))[i].type = (*(rlist->rects))[i].type; } } else { rlistcpy->rects = NULL; } } else { rlistcpy = NULL; } return rlistcpy; } /*********************************************************************** * * FUNCTION: * getMoveRect() * * INPUTS: * rlist - (RectList *) pointer to existing rectangle list * * OUTPUTS: * * RETURNS: * moverects - (XRectangle *(*)[]) pointer to MOVE rectangle * array * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * moverects - (static XRectangle *[]) set to all movables * * DESCRIPTION: * This function returns the a pointer to a static array of all * movable rectangles from the rectangle list. */ XRectangle *(* getMoveRect(RectList *rlist))[] { int i, j; j = 0; if (rlist != NULL) { for (i = 0; i < rlist->count; ++i) { if ((*(rlist->rects))[i].type & RL_MOVER) { moverects[j++] = &((*(rlist->rects))[i].rvals); } } } moverects[j] = NULL; return (XRectangle *(*)[])moverects; } /*********************************************************************** * * FUNCTION: * getSenseRect() * * INPUTS: * rlist - (RectList *) pointer to existing rectangle list * * OUTPUTS: * * RETURNS: * moverects - (XRectangle *(*)[]) pointer to MOVE rectangle * array * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * moverects - (static XRectangle *[]) set to all movables * * DESCRIPTION: * This function returns the a pointer to a static array of all * movable rectangles from the rectangle list. */ XRectangle *(* getSenseRect(RectList *rlist))[] { int i, j; j = 0; if (rlist != NULL) { for (i = 0; i < rlist->count; ++i) { if ((*(rlist->rects))[i].type & RL_SENSE) { moverects[j++] = &((*(rlist->rects))[i].rvals); } } } moverects[j] = NULL; return (XRectangle *(*)[])moverects; } /*********************************************************************** * * FUNCTION: * getSecondaryRect() * * INPUTS: * rlist - (RectList *) pointer to existing rectangle list * * OUTPUTS: * * RETURNS: * moverects - (XRectangle *(*)[]) pointer to MOVE rectangle * array * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * moverects - (static XRectangle *[]) set to all movables * * DESCRIPTION: * This function returns the a pointer to a static array of all * secondary rectangles from the rectangle list. */ XRectangle *(* getSecondaryRect(RectList *rlist))[] { int i, j; j = 0; if (rlist != NULL) { for (i = 0; i < rlist->count; ++i) { if ((*(rlist->rects))[i].type == RL_SECONDARY) { moverects[j++] = &((*(rlist->rects))[i].rvals); } } } moverects[j] = NULL; return (XRectangle *(*)[])moverects; } /*********************************************************************** * * FUNCTION: * getExposeRect() * * INPUTS: * rlist - (RectList *) pointer to existing rectangle list * * OUTPUTS: * * RETURNS: * moverects - (XRectangle *(*)[]) pointer to MOVE rectangle * array * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * moverects - (static XRectangle *[]) set to all movables * * DESCRIPTION: * This function returns the a pointer to a static array of all * the EXPOSE rectangles from the rectangle list. */ XRectangle *(* getExposeRect(RectList *rlist))[] { int i, j; j = 0; if (rlist != NULL) { for (i = 0; i < rlist->count; ++i) { if ((*(rlist->rects))[i].type == RL_EXPOSE) { moverects[j++] = &((*(rlist->rects))[i].rvals); } } } moverects[j] = NULL; return (XRectangle *(*)[])moverects; } /*********************************************************************** * * FUNCTION: * exposeRectList() * * INPUTS: * notlast - (int) this number is 0 on the last expose event * rlist - (RectList *) pointer to existing rectangle list * * OUTPUTS: * * RETURNS: * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * * DESCRIPTION: * This function returns the primary rectangle from the rectangle * list. */ void exposeRectList(int notlast, RectList *rlist) { int i; if (rlist != NULL) { /* * count down so we can test for (i == 0) */ for (i = rlist->count - 1; i >= 0; --i) { if ((*(rlist->rects))[i].type & RL_EXPOSE) { /* * if (notlast == 0) and (i == 0) then we actually do the * expose */ AddExposeEvent((notlast || i), &((*(rlist->rects))[i].rvals)); } } } } /*********************************************************************** * * FUNCTION: * cliptestRectList() * * INPUTS: * clip_region - (Region) clip region to test list against * rlist - (RectList *) pointer to existing rectangle list * * OUTPUTS: * * RETURNS: * TRUE - if rlist intersects clip_region * FALSE - otherwise * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * * DESCRIPTION: * This function checks a rectangle list against a clip region. */ int cliptestRectList(Region clip_region, RectList *rlist) { int i; int code; code = FALSE; if (rlist != NULL) { for (i = 0; i < rlist->count; ++i) { if ((*(rlist->rects))[i].type & RL_EXPOSE) { if (XRectInRegion(clip_region, ((*(rlist->rects))[i].rvals).x, ((*(rlist->rects))[i].rvals).y, (unsigned int)((*(rlist->rects))[i].rvals).width, (unsigned int)((*(rlist->rects))[i].rvals).height) != RectangleOut) { code = TRUE; break; } } } } return code; } /*********************************************************************** * * FUNCTION: * pointinRectList() * * INPUTS: * x, y - (int, int) coordinates of point * rlist - (RectList *) pointer to existing rectangle list * * OUTPUTS: * * RETURNS: * TRUE - if rectangle list contains point * FALSE - otherwise * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * * DESCRIPTION: * This function checks a point against a rectangle list. */ int pointinRectList(int x, int y, RectList *rlist) { int i; int code; code = FALSE; if (rlist != NULL) { for (i = 0; i < rlist->count; ++i) { if (((*(rlist->rects))[i].type & RL_SENSE) || (bg_sense && ((*(rlist->rects))[i].type & RL_BG_SENSE))) { if ((x >= ((*(rlist->rects))[i].rvals).x) && (y >= ((*(rlist->rects))[i].rvals).y) && (x <= ((*(rlist->rects))[i].rvals).x + ((*(rlist->rects))[i].rvals).width) && (y <= ((*(rlist->rects))[i].rvals).y + ((*(rlist->rects))[i].rvals).height)) { code = TRUE; break; } } } } return code; } /*********************************************************************** * * FUNCTION: * setBackgroundSense() * * INPUTS: * val - (int) TRUE or FALSE * * OUTPUTS: * * RETURNS: * * EXTERNALLY READ: * * EXTERNALLY MODIFIED: * bg_sense - (int) set to val * * DESCRIPTION: * This function sets the background sense flag. */ void setBackgroundSense(int val) { bg_sense = val; }