Posted to tcl by patthoyts at Sun Apr 19 23:46:58 GMT 2009view pretty
Index: generic/tkSquare.c =================================================================== RCS file: /cvsroot/tktoolkit/tk/generic/tkSquare.c,v retrieving revision 1.5 diff -u -u -r1.5 tkSquare.c --- generic/tkSquare.c 17 Jan 2002 23:33:53 -0000 1.5 +++ generic/tkSquare.c 13 Aug 2003 23:37:42 -0000 @@ -34,6 +34,7 @@ Tcl_Command widgetCmd; /* Token for square's widget command. */ Tk_OptionTable optionTable; /* Token representing the configuration * specifications. */ + Tk_Style style; /* Style currently applied. */ Tcl_Obj *xPtr, *yPtr; /* Position of square's upper-left corner * within widget. */ int x, y; @@ -85,6 +86,8 @@ "raised", Tk_Offset(Square, reliefPtr), -1}, {TK_OPTION_PIXELS, "-size", "size", "Size", "20", Tk_Offset(Square, sizeObjPtr), -1}, + {TK_OPTION_STYLE, "-style", "style", "Style", + "", -1, Tk_Offset(Square, style)}, {TK_OPTION_END} }; @@ -106,6 +109,95 @@ XEvent *eventPtr)); static int SquareWidgetObjCmd _ANSI_ARGS_((ClientData clientData, Tcl_Interp *, int objc, Tcl_Obj * CONST objv[])); + +/* + * Square element. + */ + +Tk_GetElementSizeProc SquareElementGetSize; +Tk_GetElementBoxProc SquareElementGetBox; +Tk_GetElementBorderWidthProc SquareElementGetBorderWidth; +Tk_DrawElementProc SquareElementDraw; + +enum { + SQUARE_ELEMENT_FOREGROUND, + SQUARE_ELEMENT_BORDERWIDTH, + SQUARE_ELEMENT_POSX, + SQUARE_ELEMENT_POSY, + SQUARE_ELEMENT_SIZE +} squareElementOption; + +Tk_ElementOptionSpec squareElementOptions[] = { + {"-foreground", TK_OPTION_BORDER}, + {"-borderwidth", TK_OPTION_PIXELS}, + {"-posx", TK_OPTION_PIXELS}, + {"-posy", TK_OPTION_PIXELS}, + {"-size", TK_OPTION_PIXELS}, + {NULL} +}; +Tk_ElementSpec squareElementSpec = { + /* Version */ + TK_STYLE_VERSION_1, + + /* Name of the element */ + "Square.square", + + /* Options. */ + squareElementOptions, + + /* Hooks. */ + SquareElementGetSize, /* getSize */ + SquareElementGetBox, /* getBox */ + SquareElementGetBorderWidth, /* getBorderWidth */ + SquareElementDraw /* draw */ +}; + +int squareElementId; + + +/* + * Variant of square element with fixed border width (used by instances of the + * "fixedborder" engine). + */ + +Tk_GetElementSizeProc FSquareElementGetSize; +Tk_GetElementBoxProc FSquareElementGetBox; +Tk_GetElementBorderWidthProc FSquareElementGetBorderWidth; +Tk_DrawElementProc FSquareElementDraw; + +enum { + FIXED_SQUARE_ELEMENT_FOREGROUND, + FIXED_SQUARE_ELEMENT_POSX, + FIXED_SQUARE_ELEMENT_POSY, + FIXED_SQUARE_ELEMENT_SIZE +} fSquareElementOption; + +Tk_ElementOptionSpec fSquareElementOptions[] = { + {"-foreground", TK_OPTION_BORDER}, + {"-posx", TK_OPTION_PIXELS}, + {"-posy", TK_OPTION_PIXELS}, + {"-size", TK_OPTION_PIXELS}, + {NULL} +}; +Tk_ElementSpec fSquareElementSpec = { + /* Version */ + TK_STYLE_VERSION_1, + + /* Name of the element */ + "Square.square", + + /* Options. */ + fSquareElementOptions, + + /* Hooks. */ + FSquareElementGetSize, /* getSize */ + FSquareElementGetBox, /* getBox */ + FSquareElementGetBorderWidth, /* getBorderWidth */ + FSquareElementDraw /* draw */ +}; + + + /* *-------------------------------------------------------------- @@ -173,6 +265,7 @@ (ClientData) squarePtr, SquareDeletedProc); squarePtr->gc = None; squarePtr->optionTable = optionTable; + squarePtr->style = NULL; if (Tk_InitOptions(interp, (char *) squarePtr, optionTable, tkwin) != TCL_OK) { @@ -484,8 +577,9 @@ Pixmap pm = None; Drawable d; int borderWidth, size, relief; - Tk_3DBorder bgBorder, fgBorder; + Tk_3DBorder bgBorder; int doubleBuffer; + Tk_StyledElement squareElement; squarePtr->updatePending = 0; if (!Tk_IsMapped(tkwin)) { @@ -523,10 +617,10 @@ */ Tk_GetPixelsFromObj(NULL, squarePtr->tkwin, squarePtr->sizeObjPtr, &size); - fgBorder = Tk_Get3DBorderFromObj(squarePtr->tkwin, - squarePtr->fgBorderPtr); - Tk_Fill3DRectangle(tkwin, d, fgBorder, squarePtr->x, squarePtr->y, size, - size, borderWidth, TK_RELIEF_RAISED); + squareElement = Tk_GetStyledElement(squarePtr->style, squareElementId, + squarePtr->optionTable); + Tk_DrawElement(squarePtr->style, squareElement, (char *) squarePtr, + squarePtr->tkwin, d, squarePtr->x, squarePtr->y, size, size, 0); /* * If double-buffered, copy to the screen and release the pixmap. @@ -618,4 +712,236 @@ if (squarePtr->y < bd) { squarePtr->y = bd; } +} + +int +GetPixelsFromWidget(tkwin, recordPtr, specPtr, intPtr) + Tk_Window tkwin; + char *recordPtr; + CONST Tk_OptionSpec *specPtr; + int *intPtr; +{ + if (specPtr) { + if (specPtr->internalOffset != -1) { + *intPtr = *(int *) (recordPtr+specPtr->internalOffset); + return TCL_OK; + } else if (specPtr->objOffset != -1) { + return Tk_GetPixelsFromObj(NULL, tkwin, + *(Tcl_Obj **) (recordPtr+specPtr->objOffset), + intPtr); + } + } + return TCL_ERROR; +} + +int +Get3DBorderFromWidget(tkwin, recordPtr, specPtr, borderPtr) + Tk_Window tkwin; + char *recordPtr; + CONST Tk_OptionSpec *specPtr; + Tk_3DBorder *borderPtr; +{ + if (specPtr) { + if (specPtr->internalOffset != -1) { + *borderPtr = *(Tk_3DBorder *) (recordPtr+specPtr->internalOffset); + return TCL_OK; + } else if (specPtr->objOffset != -1) { + *borderPtr = Tk_Get3DBorderFromObj(tkwin, + *(Tcl_Obj **) (recordPtr+specPtr->objOffset)); + return TCL_OK; + } + } + return TCL_ERROR; +} + + + +void +SquareInit(interp) + Tcl_Interp *interp; +{ + Tk_StyleEngine engine; + + /* + * Register the default square element implementation. + */ + + squareElementId = Tk_RegisterStyledElement(NULL, &squareElementSpec); + + /* + * Create a new "flat" style engine derived from the default engine, and + * register a new square element implementation. + */ + + engine = Tk_RegisterStyleEngine("fixedborder", NULL); + Tk_RegisterStyledElement(engine, &fSquareElementSpec); + + /* + * Create various instances of the "fixedborder" engine. The client data + * gives the fixed border width in pixels. + */ + + Tk_CreateStyle("flat", engine, (ClientData) 0); + Tk_CreateStyle("border2", engine, (ClientData) 2); + Tk_CreateStyle("border4", engine, (ClientData) 4); + Tk_CreateStyle("border8", engine, (ClientData) 8); +} + +void +SquareElementGetSize(clientData, recordPtr, optionsPtr, tkwin, width, height, + inner, widthPtr, heightPtr) + ClientData clientData; + char *recordPtr; + CONST Tk_OptionSpec **optionsPtr; + Tk_Window tkwin; + int width, height; + int inner; + int *widthPtr, *heightPtr; +{ +} + +void +SquareElementGetBox(clientData, recordPtr, optionsPtr, tkwin, x, y, width, + height, inner, xPtr, yPtr, widthPtr, heightPtr) + ClientData clientData; + char *recordPtr; + CONST Tk_OptionSpec **optionsPtr; + Tk_Window tkwin; + int x, y; + int width, height; + int inner; + int *xPtr, *yPtr; + int *widthPtr, *heightPtr; +{ +} + +int +SquareElementGetBorderWidth(clientData, recordPtr, optionsPtr, tkwin) + ClientData clientData; + char *recordPtr; + CONST Tk_OptionSpec **optionsPtr; + Tk_Window tkwin; +{ + int borderWidth = 0; + + /* TODO: quick shortcut % optionTable. */ + GetPixelsFromWidget(tkwin, recordPtr, + optionsPtr[SQUARE_ELEMENT_BORDERWIDTH], &borderWidth); + return borderWidth; +} + +void +SquareElementDraw(clientData, recordPtr, optionsPtr, tkwin, d, x, y, width, + height, state) + ClientData clientData; + char *recordPtr; + CONST Tk_OptionSpec **optionsPtr; + Tk_Window tkwin; + Drawable d; + int x, y; + int width, height; + int state; +{ + int borderWidth = 0; + Tk_3DBorder fgBorder = NULL; + + /* TODO: quick shortcut % optionTable. */ + + /* + * Get option values. + */ + + /* Foreground border. */ + Get3DBorderFromWidget(tkwin, recordPtr, + optionsPtr[SQUARE_ELEMENT_FOREGROUND], &fgBorder); + if (!fgBorder) { + /* + * No border to draw. + */ + + return; + } + + /* Border width. */ + GetPixelsFromWidget(tkwin, recordPtr, + optionsPtr[SQUARE_ELEMENT_BORDERWIDTH], &borderWidth); + + Tk_Fill3DRectangle(tkwin, d, fgBorder, x, y, width, height, borderWidth, + TK_RELIEF_RAISED); +} + +void +FSquareElementGetSize(clientData, recordPtr, optionsPtr, tkwin, width, height, + inner, widthPtr, heightPtr) + ClientData clientData; + char *recordPtr; + CONST Tk_OptionSpec **optionsPtr; + Tk_Window tkwin; + int width, height; + int inner; + int *widthPtr, *heightPtr; +{ +} + +void +FSquareElementGetBox(clientData, recordPtr, optionsPtr, tkwin, x, y, width, + height, inner, xPtr, yPtr, widthPtr, heightPtr) + ClientData clientData; + char *recordPtr; + CONST Tk_OptionSpec **optionsPtr; + Tk_Window tkwin; + int x, y; + int width, height; + int inner; + int *xPtr, *yPtr; + int *widthPtr, *heightPtr; +{ +} + +int +FSquareElementGetBorderWidth(clientData, recordPtr, optionsPtr, tkwin) + ClientData clientData; + char *recordPtr; + CONST Tk_OptionSpec **optionsPtr; + Tk_Window tkwin; +{ + int borderWidth = (int) clientData; + + return borderWidth; +} + +void +FSquareElementDraw(clientData, recordPtr, optionsPtr, tkwin, d, x, y, width, + height, state) + ClientData clientData; + char *recordPtr; + CONST Tk_OptionSpec **optionsPtr; + Tk_Window tkwin; + Drawable d; + int x, y; + int width, height; + int state; +{ + int borderWidth = (int) clientData; + Tk_3DBorder fgBorder = NULL; + + /* TODO: quick shortcut % optionTable. */ + + /* + * Get option values. + */ + + /* Foreground border. */ + Get3DBorderFromWidget(tkwin, recordPtr, + optionsPtr[FIXED_SQUARE_ELEMENT_FOREGROUND], &fgBorder); + if (!fgBorder) { + /* + * No border to draw. + */ + + return; + } + + Tk_Fill3DRectangle(tkwin, d, fgBorder, x, y, width, height, borderWidth, + TK_RELIEF_RAISED); }