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);
 }