4 * This file contains the Tk_ConfigureWidget procedure. THIS FILE
5 * IS HERE FOR BACKWARD COMPATIBILITY; THE NEW CONFIGURATION
6 * PACKAGE SHOULD BE USED FOR NEW PROJECTS.
8 * Copyright (c) 1990-1994 The Regents of the University of California.
9 * Copyright (c) 1994-1997 Sun Microsystems, Inc.
11 * See the file "license.terms" for information on usage and redistribution
12 * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
14 * RCS: @(#) $Id: bltObjConfig.c,v 1.4 2009/10/25 04:30:52 pcmacdon Exp $
18 #if (TK_VERSION_NUMBER >= _VERSION(8,0,0))
24 #include "bltObjConfig.h"
27 static Blt_ConfigSpec * GetCachedBltSpecs _ANSI_ARGS_((Tcl_Interp *interp,
28 const Blt_ConfigSpec *staticSpecs));
29 static void DeleteSpecCacheTable _ANSI_ARGS_((
30 ClientData clientData, Tcl_Interp *interp));
32 #if (TK_VERSION_NUMBER < _VERSION(8,1,0))
34 *----------------------------------------------------------------------
36 * Tk_GetAnchorFromObj --
38 * Return a Tk_Anchor value based on the value of the objPtr.
41 * The return value is a standard Tcl result. If an error occurs during
42 * conversion, an error message is left in the interpreter's result
43 * unless "interp" is NULL.
46 * The object gets converted by Tcl_GetIndexFromObj.
48 *----------------------------------------------------------------------
51 Tk_GetAnchorFromObj(interp, objPtr, anchorPtr)
52 Tcl_Interp *interp; /* Used for error reporting. */
53 Tcl_Obj *objPtr; /* The object we are trying to get the
55 Tk_Anchor *anchorPtr; /* Where to place the Tk_Anchor that
56 * corresponds to the string value of
59 return Tk_GetAnchor(interp, Tcl_GetString(objPtr), anchorPtr);
63 *----------------------------------------------------------------------
65 * Tk_GetJustifyFromObj --
67 * Return a Tk_Justify value based on the value of the objPtr.
70 * The return value is a standard Tcl result. If an error occurs during
71 * conversion, an error message is left in the interpreter's result
72 * unless "interp" is NULL.
75 * The object gets converted by Tcl_GetIndexFromObj.
77 *----------------------------------------------------------------------
80 Tk_GetJustifyFromObj(interp, objPtr, justifyPtr)
81 Tcl_Interp *interp; /* Used for error reporting. */
82 Tcl_Obj *objPtr; /* The object we are trying to get the
84 Tk_Justify *justifyPtr; /* Where to place the Tk_Justify that
85 * corresponds to the string value of
88 return Tk_GetJustify(interp, Tcl_GetString(objPtr), justifyPtr);
91 *----------------------------------------------------------------------
93 * Tk_GetReliefFromObj --
95 * Return an integer value based on the value of the objPtr.
98 * The return value is a standard Tcl result. If an error occurs during
99 * conversion, an error message is left in the interpreter's result
100 * unless "interp" is NULL.
103 * The object gets converted by Tcl_GetIndexFromObj.
105 *----------------------------------------------------------------------
108 Tk_GetReliefFromObj(interp, objPtr, reliefPtr)
109 Tcl_Interp *interp; /* Used for error reporting. */
110 Tcl_Obj *objPtr; /* The object we are trying to get the
112 int *reliefPtr; /* Where to place the answer. */
114 return Tk_GetRelief(interp, Tcl_GetString(objPtr), reliefPtr);
117 *----------------------------------------------------------------------
121 * Attempt to return an mm value from the Tcl object "objPtr". If the
122 * object is not already an mm value, an attempt will be made to convert
126 * The return value is a standard Tcl object result. If an error occurs
127 * during conversion, an error message is left in the interpreter's
128 * result unless "interp" is NULL.
131 * If the object is not already a pixel, the conversion will free
132 * any old internal representation.
134 *----------------------------------------------------------------------
137 Tk_GetMMFromObj(interp, tkwin, objPtr, doublePtr)
138 Tcl_Interp *interp; /* Used for error reporting if not NULL. */
140 Tcl_Obj *objPtr; /* The object from which to get mms. */
141 double *doublePtr; /* Place to store resulting millimeters. */
143 return Tk_GetScreenMM(interp, tkwin, Tcl_GetString(objPtr), doublePtr);
146 *----------------------------------------------------------------------
148 * Tk_GetPixelsFromObj --
150 * Attempt to return a pixel value from the Tcl object "objPtr". If the
151 * object is not already a pixel value, an attempt will be made to convert
155 * The return value is a standard Tcl object result. If an error occurs
156 * during conversion, an error message is left in the interpreter's
157 * result unless "interp" is NULL.
160 * If the object is not already a pixel, the conversion will free
161 * any old internal representation.
163 *----------------------------------------------------------------------
166 Tk_GetPixelsFromObj(interp, tkwin, objPtr, intPtr)
167 Tcl_Interp *interp; /* Used for error reporting if not NULL. */
169 Tcl_Obj *objPtr; /* The object from which to get pixels. */
170 int *intPtr; /* Place to store resulting pixels. */
172 return Tk_GetPixels(interp, tkwin, Tcl_GetString(objPtr), intPtr);
176 *----------------------------------------------------------------------
178 * Tk_Alloc3DBorderFromObj --
180 * Given a Tcl_Obj *, map the value to a corresponding
181 * Tk_3DBorder structure based on the tkwin given.
184 * The return value is a token for a data structure describing a
185 * 3-D border. This token may be passed to procedures such as
186 * Blt_Draw3DRectangle and Tk_Free3DBorder. If an error prevented
187 * the border from being created then NULL is returned and an error
188 * message will be left in the interp's result.
191 * The border is added to an internal database with a reference
192 * count. For each call to this procedure, there should eventually
193 * be a call to FreeBorderObjProc so that the database is
194 * cleaned up when borders aren't in use anymore.
196 *----------------------------------------------------------------------
199 Tk_Alloc3DBorderFromObj(interp, tkwin, objPtr)
200 Tcl_Interp *interp; /* Interp for error results. */
201 Tk_Window tkwin; /* Need the screen the border is used on.*/
202 Tcl_Obj *objPtr; /* Object giving name of color for window
205 return Tk_Get3DBorder(interp, tkwin, Tcl_GetString(objPtr));
208 *----------------------------------------------------------------------
210 * Tk_AllocBitmapFromObj --
212 * Given a Tcl_Obj *, map the value to a corresponding
213 * Pixmap structure based on the tkwin given.
216 * The return value is the X identifer for the desired bitmap
217 * (i.e. a Pixmap with a single plane), unless string couldn't be
218 * parsed correctly. In this case, None is returned and an error
219 * message is left in the interp's result. The caller should never
220 * modify the bitmap that is returned, and should eventually call
221 * Tk_FreeBitmapFromObj when the bitmap is no longer needed.
224 * The bitmap is added to an internal database with a reference count.
225 * For each call to this procedure, there should eventually be a call
226 * to Tk_FreeBitmapFromObj, so that the database can be cleaned up
227 * when bitmaps aren't needed anymore.
229 *----------------------------------------------------------------------
232 Tk_AllocBitmapFromObj(interp, tkwin, objPtr)
233 Tcl_Interp *interp; /* Interp for error results. This may
235 Tk_Window tkwin; /* Need the screen the bitmap is used on.*/
236 Tcl_Obj *objPtr; /* Object describing bitmap; see manual
237 * entry for legal syntax of string value. */
239 return Tk_GetBitmap(interp, tkwin, Tcl_GetString(objPtr));
243 *---------------------------------------------------------------------------
245 * Tk_AllocFontFromObj --
247 * Given a string description of a font, map the description to a
248 * corresponding Tk_Font that represents the font.
251 * The return value is token for the font, or NULL if an error
252 * prevented the font from being created. If NULL is returned, an
253 * error message will be left in interp's result object.
256 * The font is added to an internal database with a reference
257 * count. For each call to this procedure, there should eventually
258 * be a call to Tk_FreeFont() or Tk_FreeFontFromObj() so that the
259 * database is cleaned up when fonts aren't in use anymore.
261 *---------------------------------------------------------------------------
264 Tk_AllocFontFromObj(interp, tkwin, objPtr)
265 Tcl_Interp *interp; /* Interp for database and error return. */
266 Tk_Window tkwin; /* For screen on which font will be used. */
267 Tcl_Obj *objPtr; /* Object describing font, as: named font,
268 * native format, or parseable string. */
270 return Tk_GetFont(interp, tkwin, Tcl_GetString(objPtr));
274 *----------------------------------------------------------------------
276 * Tk_AllocCursorFromObj --
278 * Given a Tcl_Obj *, map the value to a corresponding
279 * Tk_Cursor structure based on the tkwin given.
282 * The return value is the X identifer for the desired cursor,
283 * unless objPtr couldn't be parsed correctly. In this case,
284 * None is returned and an error message is left in the interp's result.
285 * The caller should never modify the cursor that is returned, and
286 * should eventually call Tk_FreeCursorFromObj when the cursor is no
290 * The cursor is added to an internal database with a reference count.
291 * For each call to this procedure, there should eventually be a call
292 * to Tk_FreeCursorFromObj, so that the database can be cleaned up
293 * when cursors aren't needed anymore.
295 *----------------------------------------------------------------------
298 Tk_AllocCursorFromObj(interp, tkwin, objPtr)
299 Tcl_Interp *interp; /* Interp for error results. */
300 Tk_Window tkwin; /* Window in which the cursor will be used.*/
301 Tcl_Obj *objPtr; /* Object describing cursor; see manual
302 * entry for description of legal
303 * syntax of this obj's string rep. */
305 return Tk_GetCursor(interp, tkwin, Tcl_GetString(objPtr));
309 *----------------------------------------------------------------------
311 * Tk_AllocColorFromObj --
313 * Given a Tcl_Obj *, map the value to a corresponding
314 * XColor structure based on the tkwin given.
317 * The return value is a pointer to an XColor structure that
318 * indicates the red, blue, and green intensities for the color
319 * given by the string in objPtr, and also specifies a pixel value
320 * to use to draw in that color. If an error occurs, NULL is
321 * returned and an error message will be left in interp's result
322 * (unless interp is NULL).
325 * The color is added to an internal database with a reference count.
326 * For each call to this procedure, there should eventually be a call
327 * to Tk_FreeColorFromObj so that the database is cleaned up when colors
328 * aren't in use anymore.
330 *----------------------------------------------------------------------
333 Tk_AllocColorFromObj(interp, tkwin, objPtr)
334 Tcl_Interp *interp; /* Used only for error reporting. If NULL,
335 * then no messages are provided. */
336 Tk_Window tkwin; /* Window in which the color will be used.*/
337 Tcl_Obj *objPtr; /* Object that describes the color; string
338 * value is a color name such as "red" or
343 string = Tcl_GetString(objPtr);
344 return Tk_GetColor(interp, tkwin, Tk_GetUid(string));
350 *--------------------------------------------------------------
354 * Convert a string representing a numeric position.
355 * A position can be in one of the following forms.
357 * number - number of the item in the hierarchy, indexed
359 * "end" - last position in the hierarchy.
362 * A standard Tcl result. If "string" is a valid index, then
363 * *indexPtr is filled with the corresponding numeric index.
364 * If "end" was selected then *indexPtr is set to -1.
365 * Otherwise an error message is left in interp->result.
370 *--------------------------------------------------------------
373 Blt_GetPositionFromObj(interp, objPtr, indexPtr)
374 Tcl_Interp *interp; /* Interpreter to report results back
376 Tcl_Obj *objPtr; /* Tcl_Obj representation of the index.
377 * Can be an integer or "end" to refer
378 * to the last index. */
379 int *indexPtr; /* Holds the converted index. */
383 string = Tcl_GetString(objPtr);
384 if ((string[0] == 'e') && (strcmp(string, "end") == 0)) {
385 *indexPtr = -1; /* Indicates last position in hierarchy. */
389 if (Tcl_GetIntFromObj(interp, objPtr, &position) != TCL_OK) {
393 Tcl_AppendResult(interp, "bad position \"", string, "\"",
397 *indexPtr = position;
402 Blt_GetPositionSizeFromObj(interp, objPtr, size, indexPtr)
403 Tcl_Interp *interp; /* Interpreter to report results back
405 Tcl_Obj *objPtr; /* Tcl_Obj representation of the index.
406 * Can be an integer or "end" to refer
407 * to the last index. */
409 int *indexPtr; /* Holds the converted index. */
414 string = Tcl_GetString(objPtr);
415 if ((string[0] == 'e') && (strcmp(string, "end") == 0)) {
416 *indexPtr = -1; /* Indicates last position in hierarchy. */
419 if ((string[0] == 'e') && (strncmp(string, "end-", 4) == 0) &&
420 Tcl_GetInt(NULL, string+4, &n) == TCL_OK && n>=0 && n<=size) {
421 position = size-n; /* Indicates last position in hierarchy. */
423 if (Tcl_GetIntFromObj(interp, objPtr, &position) != TCL_OK) {
427 if (position < 0 || position >= size) {
428 Tcl_AppendResult(interp, "bad position \"", string, "\"",
432 *indexPtr = position;
437 *----------------------------------------------------------------------
439 * Blt_GetPixelsFromObj --
441 * Like Tk_GetPixelsFromObj, but checks for negative, zero.
444 * A standard Tcl result.
446 *----------------------------------------------------------------------
449 Blt_GetPixelsFromObj(interp, tkwin, objPtr, check, valuePtr)
453 int check; /* Can be PIXELS_POSITIVE, PIXELS_NONNEGATIVE,
459 if (Tk_GetPixelsFromObj(interp, tkwin, objPtr, &length) != TCL_OK) {
462 if (length >= SHRT_MAX) {
463 Tcl_AppendResult(interp, "bad distance \"", Tcl_GetString(objPtr),
464 "\": too big to represent", (char *)NULL);
468 case PIXELS_NONNEGATIVE:
470 Tcl_AppendResult(interp, "bad distance \"", Tcl_GetString(objPtr),
471 "\": can't be negative", (char *)NULL);
476 case PIXELS_POSITIVE:
478 Tcl_AppendResult(interp, "bad distance \"", Tcl_GetString(objPtr),
479 "\": must be positive", (char *)NULL);
492 Blt_GetPadFromObj(interp, tkwin, objPtr, padPtr)
493 Tcl_Interp *interp; /* Interpreter to send results back to */
494 Tk_Window tkwin; /* Window */
495 Tcl_Obj *objPtr; /* Pixel value string */
502 if (Tcl_ListObjGetElements(interp, objPtr, &objc, &objv) != TCL_OK) {
505 if ((objc < 1) || (objc > 2)) {
506 Tcl_AppendResult(interp, "wrong # elements in padding list",
510 if (Blt_GetPixelsFromObj(interp, tkwin, objv[0], PIXELS_NONNEGATIVE,
516 (Blt_GetPixelsFromObj(interp, tkwin, objv[1], PIXELS_NONNEGATIVE,
517 &side2) != TCL_OK)) {
520 /* Don't update the pad structure until we know both values are okay. */
521 padPtr->side1 = side1;
522 padPtr->side2 = side2;
527 Blt_GetShadowFromObj(interp, tkwin, objPtr, shadowPtr)
528 Tcl_Interp *interp; /* Interpreter to send results back to */
529 Tk_Window tkwin; /* Window */
530 Tcl_Obj *objPtr; /* Pixel value string */
538 if (Tcl_ListObjGetElements(interp, objPtr, &objc, &objv) != TCL_OK) {
542 Tcl_AppendResult(interp, "wrong # elements in drop shadow value",
549 colorPtr = Tk_AllocColorFromObj(interp, tkwin, objv[0]);
550 if (colorPtr == NULL) {
555 if (Blt_GetPixelsFromObj(interp, tkwin, objv[1], PIXELS_NONNEGATIVE,
556 &dropOffset) != TCL_OK) {
557 Tk_FreeColor(colorPtr);
562 if (shadowPtr->color != NULL) {
563 Tk_FreeColor(shadowPtr->color);
565 shadowPtr->color = colorPtr;
566 shadowPtr->offset = dropOffset;
571 Blt_GetStateFromObj(interp, objPtr, statePtr)
572 Tcl_Interp *interp; /* Interpreter to send results back to */
573 Tcl_Obj *objPtr; /* Pixel value string */
578 string = Tcl_GetString(objPtr);
579 if (strcmp(string, "normal") == 0) {
580 *statePtr = STATE_NORMAL;
581 } else if (strcmp(string, "disabled") == 0) {
582 *statePtr = STATE_DISABLED;
583 } else if (strcmp(string, "active") == 0) {
584 *statePtr = STATE_ACTIVE;
586 Tcl_AppendResult(interp, "bad state \"", string,
587 "\": should be normal, active, or disabled", (char *)NULL);
594 Blt_NameOfState(state)
609 #ifdef notdef /* Replace this routine when Tcl_Obj-based
610 * configuration comes on-line */
613 *----------------------------------------------------------------------
617 * Converts the integer representing the fill style into a string.
619 *----------------------------------------------------------------------
635 return "unknown value";
641 *----------------------------------------------------------------------
643 * Blt_GetFillFromObj --
645 * Converts the fill style string into its numeric representation.
647 * Valid style strings are:
649 * "none" Use neither plane.
650 * "x" X-coordinate plane.
651 * "y" Y-coordinate plane.
652 * "both" Use both coordinate planes.
654 *----------------------------------------------------------------------
658 Blt_GetFillFromObj(interp, objPtr, fillPtr)
659 Tcl_Interp *interp; /* Interpreter to send results back to */
660 Tcl_Obj *objPtr; /* Fill style string */
667 string = Tcl_GetStringFromObj(objPtr, &length);
669 if ((c == 'n') && (strncmp(string, "none", length) == 0)) {
670 *fillPtr = FILL_NONE;
671 } else if ((c == 'x') && (strncmp(string, "x", length) == 0)) {
673 } else if ((c == 'y') && (strncmp(string, "y", length) == 0)) {
675 } else if ((c == 'b') && (strncmp(string, "both", length) == 0)) {
676 *fillPtr = FILL_BOTH;
678 Tcl_AppendResult(interp, "bad argument \"", string,
679 "\": should be \"none\", \"x\", \"y\", or \"both\"", (char *)NULL);
686 *----------------------------------------------------------------------
688 * Blt_GetDashesFromObj --
690 * Converts a Tcl list of dash values into a dash list ready for
691 * use with XSetDashes.
693 * A valid list dash values can have zero through 11 elements
694 * (PostScript limit). Values must be between 1 and 255. Although
695 * a list of 0 (like the empty string) means no dashes.
698 * A standard Tcl result. If the list represented a valid dash
699 * list TCL_OK is returned and *dashesPtr* will contain the
700 * valid dash list. Otherwise, TCL_ERROR is returned and
701 * interp->result will contain an error message.
704 *----------------------------------------------------------------------
707 Blt_GetDashesFromObj(interp, objPtr, dashesPtr)
710 Blt_Dashes *dashesPtr;
714 string = Tcl_GetString(objPtr);
715 if ((string == NULL) || (*string == '\0')) {
716 dashesPtr->values[0] = 0;
717 } else if (strcmp(string, "dash") == 0) { /* 5 2 */
718 dashesPtr->values[0] = 5;
719 dashesPtr->values[1] = 2;
720 dashesPtr->values[2] = 0;
721 } else if (strcmp(string, "dot") == 0) { /* 1 */
722 dashesPtr->values[0] = 1;
723 dashesPtr->values[1] = 0;
724 } else if (strcmp(string, "dashdot") == 0) { /* 2 4 2 */
725 dashesPtr->values[0] = 2;
726 dashesPtr->values[1] = 4;
727 dashesPtr->values[2] = 2;
728 dashesPtr->values[3] = 0;
729 } else if (strcmp(string, "dashdotdot") == 0) { /* 2 4 2 2 */
730 dashesPtr->values[0] = 2;
731 dashesPtr->values[1] = 4;
732 dashesPtr->values[2] = 2;
733 dashesPtr->values[3] = 2;
734 dashesPtr->values[4] = 0;
741 if (Tcl_ListObjGetElements(interp, objPtr, &objc, &objv) != TCL_OK) {
744 if (objc > 11) { /* This is the postscript limit */
745 Tcl_AppendResult(interp, "too many values in dash list \"",
746 string, "\"", (char *)NULL);
749 for (i = 0; i < objc; i++) {
750 if (Tcl_GetIntFromObj(interp, objv[i], &value) != TCL_OK) {
754 * Backward compatibility:
755 * Allow list of 0 to turn off dashes
757 if ((value == 0) && (objc == 1)) {
760 if ((value < 1) || (value > 255)) {
761 Tcl_AppendResult(interp, "dash value \"",
762 Tcl_GetString(objv[i]), "\" is out of range",
766 dashesPtr->values[i] = (unsigned char)value;
768 /* Make sure the array ends with a NUL byte */
769 dashesPtr->values[i] = 0;
788 return "unknown side value";
792 *----------------------------------------------------------------------
794 * Blt_GetSideFromObj --
796 * Converts the fill style string into its numeric representation.
798 * Valid style strings are "left", "right", "top", or "bottom".
800 *----------------------------------------------------------------------
804 Blt_GetSideFromObj(interp, objPtr, sidePtr)
805 Tcl_Interp *interp; /* Interpreter to send results back to */
806 Tcl_Obj *objPtr; /* Value string */
807 int *sidePtr; /* (out) Token representing side:
808 * either SIDE_LEFT, SIDE_RIGHT,
809 * SIDE_TOP, or SIDE_BOTTOM. */
815 string = Tcl_GetStringFromObj(objPtr, &length);
817 if ((c == 'l') && (strncmp(string, "left", length) == 0)) {
818 *sidePtr = SIDE_LEFT;
819 } else if ((c == 'r') && (strncmp(string, "right", length) == 0)) {
820 *sidePtr = SIDE_RIGHT;
821 } else if ((c == 't') && (strncmp(string, "top", length) == 0)) {
823 } else if ((c == 'b') && (strncmp(string, "bottom", length) == 0)) {
824 *sidePtr = SIDE_BOTTOM;
826 Tcl_AppendResult(interp, "bad side \"", string,
827 "\": should be left, right, top, or bottom", (char *)NULL);
834 Blt_NameOfArrow(side)
849 return "unknown arow value";
853 *----------------------------------------------------------------------
855 * Blt_GetDirFromObj --
857 * Converts the fill style string into its numeric representation.
859 * Valid style strings are "left", "right", "up", or "down".
861 *----------------------------------------------------------------------
865 Blt_GetArrowFromObj(interp, objPtr, sidePtr)
866 Tcl_Interp *interp; /* Interpreter to send results back to */
867 Tcl_Obj *objPtr; /* Value string */
868 int *sidePtr; /* (out) Token representing arrow:
869 * either ARROW_LEFT, ARROW_RIGHT,
870 * ARROW_TOP, or ARROW_BOTTOM. */
876 string = Tcl_GetStringFromObj(objPtr, &length);
878 if ((c == 'l') && (strncmp(string, "left", length) == 0)) {
879 *sidePtr = ARROW_LEFT;
880 } else if ((c == 'r') && (strncmp(string, "right", length) == 0)) {
881 *sidePtr = ARROW_RIGHT;
882 } else if ((c == 'u') && (strncmp(string, "up", length) == 0)) {
884 } else if ((c == 'd') && (strncmp(string, "down", length) == 0)) {
885 *sidePtr = ARROW_DOWN;
886 } else if ((c == 'n') && (strncmp(string, "none", length) == 0)) {
887 *sidePtr = ARROW_NONE;
889 Tcl_AppendResult(interp, "bad arrow \"", string,
890 "\": should be none, left, right, up, or down", (char *)NULL);
897 *----------------------------------------------------------------------
899 * Blt_StringToEnum --
901 * Converts the string into its enumerated type.
903 *----------------------------------------------------------------------
907 Blt_ObjToEnum(clientData, interp, tkwin, objPtr, widgRec, offset)
908 ClientData clientData; /* Vectors of valid strings. */
909 Tcl_Interp *interp; /* Interpreter to send results back to */
910 Tk_Window tkwin; /* Not used. */
912 char *widgRec; /* Widget record. */
913 int offset; /* Offset of field in record */
915 int *enumPtr = (int *)(widgRec + offset);
922 string = Tcl_GetString(objPtr);
925 for (p = (char **)clientData; *p != NULL; p++) {
926 if ((c == p[0][0]) && (strcmp(string, *p) == 0)) {
934 Tcl_AppendResult(interp, "bad value \"", string, "\": should be ",
936 p = (char **)clientData;
938 Tcl_AppendResult(interp, p[0], (char *)NULL);
940 for (i = 1; i < (count - 1); i++) {
941 Tcl_AppendResult(interp, " ", p[i], ", ", (char *)NULL);
944 Tcl_AppendResult(interp, " or ", p[count - 1], ".", (char *)NULL);
950 *----------------------------------------------------------------------
954 * Returns the string associated with the enumerated type.
956 *----------------------------------------------------------------------
960 Blt_EnumToObj(clientData, interp, tkwin, widgRec, offset)
961 ClientData clientData; /* List of strings. */
963 Tk_Window tkwin; /* Not used. */
964 char *widgRec; /* Widget record */
965 int offset; /* Offset of field in widget record */
967 int value = *(int *)(widgRec + offset);
968 char **strings = (char **)clientData;
973 for (p = strings; *p != NULL; p++) {
974 if (value == count) {
975 return Tcl_NewStringObj(*p, -1);
979 return Tcl_NewStringObj("unknown value", -1);
982 /* Configuration option helper routines */
985 *--------------------------------------------------------------
989 * This procedure applies a single configuration option
990 * to a widget record.
993 * A standard Tcl return value.
996 * WidgRec is modified as indicated by specPtr and value.
997 * The old value is recycled, if that is appropriate for
1000 *--------------------------------------------------------------
1003 DoConfig(interp, tkwin, specPtr, objPtr, widgRec)
1004 Tcl_Interp *interp; /* Interpreter for error reporting. */
1005 Tk_Window tkwin; /* Window containing widget (needed to
1006 * set up X resources). */
1007 Blt_ConfigSpec *specPtr; /* Specifier to apply. */
1008 Tcl_Obj *objPtr; /* Value to use to fill in widgRec. */
1009 char *widgRec; /* Record whose fields are to be
1010 * modified. Values must be properly
1017 if (objPtr == NULL) {
1019 } else if (specPtr->specFlags & BLT_CONFIG_NULL_OK) {
1022 if (objPtr->bytes != NULL) {
1023 length = objPtr->length;
1025 Tcl_GetStringFromObj(objPtr, &length);
1027 objIsEmpty = (length == 0);
1030 ptr = widgRec + specPtr->offset;
1031 switch (specPtr->type) {
1032 case BLT_CONFIG_ANCHOR:
1038 } else if (Tk_GetAnchorFromObj(interp, objPtr, &anchor) != TCL_OK) {
1041 *(Tk_Anchor *)ptr = anchor;
1045 case BLT_CONFIG_BITMAP:
1047 Pixmap newBitmap, oldBitmap;
1052 newBitmap = Tk_AllocBitmapFromObj(interp, tkwin, objPtr);
1053 if (newBitmap == None) {
1057 oldBitmap = *(Pixmap *)ptr;
1058 if (oldBitmap != None) {
1059 Tk_FreeBitmap(Tk_Display(tkwin), oldBitmap);
1061 *(Pixmap *)ptr = newBitmap;
1065 case BLT_CONFIG_BOOLEAN:
1069 if (Tcl_GetBooleanFromObj(interp, objPtr, &newBool)
1073 *(int *)ptr = newBool;
1077 case BLT_CONFIG_BORDER:
1079 Tk_3DBorder newBorder, oldBorder;
1084 newBorder = Tk_Alloc3DBorderFromObj(interp, tkwin, objPtr);
1085 if (newBorder == NULL) {
1089 oldBorder = *(Tk_3DBorder *)ptr;
1090 if (oldBorder != NULL) {
1091 Tk_Free3DBorder(oldBorder);
1093 *(Tk_3DBorder *)ptr = newBorder;
1097 case BLT_CONFIG_CAP_STYLE:
1102 value = Tk_GetUid(Tcl_GetString(objPtr));
1103 if (Tk_GetCapStyle(interp, (char*)value, &cap) != TCL_OK) {
1110 case BLT_CONFIG_COLOR:
1112 XColor *newColor, *oldColor;
1117 newColor = Tk_AllocColorFromObj(interp, tkwin, objPtr);
1118 if (newColor == NULL) {
1122 oldColor = *(XColor **)ptr;
1123 if (oldColor != NULL) {
1124 Tk_FreeColor(oldColor);
1126 *(XColor **)ptr = newColor;
1130 case BLT_CONFIG_CURSOR:
1131 case BLT_CONFIG_ACTIVE_CURSOR:
1133 Tk_Cursor newCursor, oldCursor;
1138 newCursor = Tk_AllocCursorFromObj(interp, tkwin, objPtr);
1139 if (newCursor == None) {
1143 oldCursor = *(Tk_Cursor *)ptr;
1144 if (oldCursor != None) {
1145 Tk_FreeCursor(Tk_Display(tkwin), oldCursor);
1147 *(Tk_Cursor *)ptr = newCursor;
1148 if (specPtr->type == BLT_CONFIG_ACTIVE_CURSOR) {
1149 Tk_DefineCursor(tkwin, newCursor);
1154 case BLT_CONFIG_CUSTOM:
1156 /* Note: defers freeProc call till after success from parseProc */
1158 oldPtr = (*(char **)ptr);
1160 if ((oldPtr != NULL) &&
1161 (specPtr->customPtr->freeProc != NULL)) {
1162 (*specPtr->customPtr->freeProc)
1163 (specPtr->customPtr->clientData, Tk_Display(tkwin),
1164 widgRec, specPtr->offset, oldPtr);
1166 *(char **)ptr = NULL;
1170 result = (*specPtr->customPtr->parseProc)
1171 (specPtr->customPtr->clientData, interp, tkwin, objPtr,
1172 widgRec, specPtr->offset);
1173 if (result != TCL_OK) {
1174 *(char **)ptr = oldPtr;
1177 if ((oldPtr != NULL) &&
1178 (specPtr->customPtr->freeProc != NULL)) {
1179 (*specPtr->customPtr->freeProc)
1180 (specPtr->customPtr->clientData, Tk_Display(tkwin),
1181 widgRec, specPtr->offset, oldPtr);
1187 case BLT_CONFIG_DOUBLE:
1191 if (Tcl_GetDoubleFromObj(interp, objPtr, &newDouble)
1195 *(double *)ptr = newDouble;
1199 case BLT_CONFIG_FONT:
1201 Tk_Font newFont, oldFont;
1206 newFont = Tk_AllocFontFromObj(interp, tkwin, objPtr);
1207 if (newFont == NULL) {
1211 oldFont = *(Tk_Font *)ptr;
1212 if (oldFont != NULL) {
1213 Tk_FreeFont(oldFont);
1215 *(Tk_Font *)ptr = newFont;
1219 case BLT_CONFIG_INT:
1223 if (Tcl_GetIntFromObj(interp, objPtr, &newInt) != TCL_OK) {
1226 *(int *)ptr = newInt;
1230 case BLT_CONFIG_JOIN_STYLE:
1235 value = Tk_GetUid(Tcl_GetString(objPtr));
1236 if (Tk_GetJoinStyle(interp, (char*)value, &join) != TCL_OK) {
1243 case BLT_CONFIG_JUSTIFY:
1247 if (Tk_GetJustifyFromObj(interp, objPtr, &justify) != TCL_OK) {
1250 *(Tk_Justify *)ptr = justify;
1258 if (Tk_GetMMFromObj(interp, tkwin, objPtr, &mm) != TCL_OK) {
1261 *(double *)ptr = mm;
1265 case BLT_CONFIG_PIXELS:
1269 if (Tk_GetPixelsFromObj(interp, tkwin, objPtr, &pixels)
1273 *(int *)ptr = pixels;
1277 case BLT_CONFIG_RELIEF:
1281 if (Tk_GetReliefFromObj(interp, objPtr, &relief) != TCL_OK) {
1284 *(int *)ptr = relief;
1288 case BLT_CONFIG_STRING:
1290 char *oldString, *newString;
1295 newString = (char *)Blt_Strdup(Tcl_GetString(objPtr));
1297 oldString = *(char **)ptr;
1298 if (oldString != NULL) {
1299 Blt_Free(oldString);
1301 *(char **)ptr = newString;
1305 case BLT_CONFIG_UID:
1307 *(Tk_Uid *)ptr = NULL;
1309 *(Tk_Uid *)ptr = Tk_GetUid(Tcl_GetString(objPtr));
1313 case BLT_CONFIG_WINDOW:
1322 path = Tcl_GetString(objPtr);
1323 tkwin2 = Tk_NameToWindow(interp, path, tkwin);
1324 if (tkwin2 == NULL) {
1328 *(Tk_Window *)ptr = tkwin2;
1332 case BLT_CONFIG_BITFLAG:
1338 if (Tcl_GetBooleanFromObj(interp, objPtr, &bool) != TCL_OK) {
1341 flag = (unsigned int)specPtr->customPtr;
1342 *(int *)ptr &= ~flag;
1344 *(int *)ptr |= flag;
1349 case BLT_CONFIG_DASHES:
1350 if (Blt_GetDashesFromObj(interp, objPtr, (Blt_Dashes *)ptr)
1356 case BLT_CONFIG_DISTANCE:
1360 if (Blt_GetPixelsFromObj(interp, tkwin, objPtr,
1361 PIXELS_NONNEGATIVE, &newPixels) != TCL_OK) {
1364 *(int *)ptr = newPixels;
1368 case BLT_CONFIG_FILL:
1369 if (Blt_GetFillFromObj(interp, objPtr, (int *)ptr) != TCL_OK) {
1374 case BLT_CONFIG_FLOAT:
1378 if (Tcl_GetDoubleFromObj(interp, objPtr, &newDouble)
1382 *(float *)ptr = (float)newDouble;
1386 case BLT_CONFIG_LIST:
1391 if (Tcl_SplitList(interp, Tcl_GetString(objPtr), &argc, &argv)
1395 *(char ***)ptr = argv;
1399 case BLT_CONFIG_OBJCMD:
1400 case BLT_CONFIG_LISTOBJ:
1403 Tcl_Obj *listObjPtr, *oldObjPtr;
1406 if (Tcl_ListObjGetElements(interp, objPtr, &objc, &objv)
1410 if (objc >= 1 && specPtr->type == BLT_CONFIG_OBJCMD) {
1411 /* Precharge to a command object if possible. */
1412 Tcl_GetCommandFromObj(interp, objv[0]);
1414 oldObjPtr = *(Tcl_Obj **)ptr;
1415 if (oldObjPtr != NULL) {
1416 Tcl_DecrRefCount(oldObjPtr);
1418 listObjPtr = Tcl_NewListObj(objc, objv);
1419 Tcl_IncrRefCount(listObjPtr);
1420 *(Tcl_Obj **)ptr = listObjPtr;
1424 case BLT_CONFIG_OBJ:
1427 oldObjPtr = *(Tcl_Obj **)ptr;
1428 if (oldObjPtr != NULL) {
1429 Tcl_DecrRefCount(oldObjPtr);
1431 Tcl_IncrRefCount(objPtr);
1432 *(Tcl_Obj **)ptr = objPtr;
1436 case BLT_CONFIG_PAD:
1437 if (Blt_GetPadFromObj(interp, tkwin, objPtr, (Blt_Pad *)ptr)
1443 case BLT_CONFIG_POS_DISTANCE:
1447 if (Blt_GetPixelsFromObj(interp, tkwin, objPtr,
1448 PIXELS_POSITIVE, &newPixels) != TCL_OK) {
1451 *(int *)ptr = newPixels;
1455 case BLT_CONFIG_SHADOW:
1457 Shadow *shadowPtr = (Shadow *)ptr;
1459 if (Blt_GetShadowFromObj(interp, tkwin, objPtr, shadowPtr)
1466 case BLT_CONFIG_STATE:
1468 if (Blt_GetStateFromObj(interp, objPtr, (int *)ptr)
1475 case BLT_CONFIG_TILE:
1477 Blt_Tile newTile, oldTile;
1482 if (Blt_GetTile(interp, tkwin, Tcl_GetString(objPtr),
1483 &newTile) != TCL_OK) {
1487 oldTile = *(Blt_Tile *)ptr;
1488 if (oldTile != NULL) {
1489 Blt_FreeTile(oldTile);
1491 *(Blt_Tile *)ptr = newTile;
1495 case BLT_CONFIG_SIDE:
1496 if (Blt_GetSideFromObj(interp, objPtr, (int *)ptr) != TCL_OK) {
1501 case BLT_CONFIG_ARROW:
1502 if (Blt_GetArrowFromObj(interp, objPtr, (int *)ptr) != TCL_OK) {
1511 sprintf(buf, "bad config table: unknown type %d",
1513 Tcl_SetResult(interp, buf, TCL_VOLATILE);
1518 } while ((specPtr->switchName == NULL) &&
1519 (specPtr->type != BLT_CONFIG_END));
1524 *----------------------------------------------------------------------
1526 * FormatConfigValue --
1528 * This procedure formats the current value of a configuration
1532 * The return value is the formatted value of the option given
1533 * by specPtr and widgRec. If the value is static, so that it
1534 * need not be freed, *freeProcPtr will be set to NULL; otherwise
1535 * *freeProcPtr will be set to the address of a procedure to
1536 * free the result, and the caller must invoke this procedure
1537 * when it is finished with the result.
1542 *----------------------------------------------------------------------
1545 FormatConfigValue(interp, tkwin, specPtr, widgRec)
1546 Tcl_Interp *interp; /* Interpreter for use in real conversions. */
1547 Tk_Window tkwin; /* Window corresponding to widget. */
1548 Blt_ConfigSpec *specPtr; /* Pointer to information describing option.
1549 * Must not point to a synonym option. */
1550 char *widgRec; /* Pointer to record holding current
1551 * values of info for widget. */
1556 ptr = widgRec + specPtr->offset;
1558 switch (specPtr->type) {
1559 case BLT_CONFIG_ANCHOR:
1560 if ((*(int *)ptr)>=0) {
1561 string = Tk_NameOfAnchor(*(Tk_Anchor *)ptr);
1565 case BLT_CONFIG_BITMAP:
1566 if (*(Pixmap *)ptr != None) {
1567 string = Tk_NameOfBitmap(Tk_Display(tkwin), *(Pixmap *)ptr);
1571 case BLT_CONFIG_BOOLEAN:
1572 return Tcl_NewBooleanObj(*(int *)ptr);
1574 case BLT_CONFIG_BORDER:
1575 if (*(Tk_3DBorder *)ptr != NULL) {
1576 string = Tk_NameOf3DBorder(*(Tk_3DBorder *)ptr);
1580 case BLT_CONFIG_CAP_STYLE:
1581 string = Tk_NameOfCapStyle(*(int *)ptr);
1584 case BLT_CONFIG_COLOR:
1585 if (*(XColor **)ptr != NULL) {
1586 string = Tk_NameOfColor(*(XColor **)ptr);
1590 case BLT_CONFIG_CURSOR:
1591 case BLT_CONFIG_ACTIVE_CURSOR:
1592 if (*(Tk_Cursor *)ptr != None) {
1593 string = Tk_NameOfCursor(Tk_Display(tkwin), *(Tk_Cursor *)ptr);
1597 case BLT_CONFIG_CUSTOM:
1598 return (*specPtr->customPtr->printProc)(specPtr->customPtr->clientData,
1599 interp, tkwin, widgRec, specPtr->offset);
1601 case BLT_CONFIG_DOUBLE:
1602 return Tcl_NewDoubleObj(*(double *)ptr);
1604 case BLT_CONFIG_FONT:
1605 if (*(Tk_Font *)ptr != NULL) {
1606 string = Tk_NameOfFont(*(Tk_Font *)ptr);
1610 case BLT_CONFIG_INT:
1611 return Tcl_NewIntObj(*(int *)ptr);
1613 case BLT_CONFIG_JOIN_STYLE:
1614 string = Tk_NameOfJoinStyle(*(int *)ptr);
1617 case BLT_CONFIG_JUSTIFY:
1618 string = Tk_NameOfJustify(*(Tk_Justify *)ptr);
1622 return Tcl_NewDoubleObj(*(double *)ptr);
1624 case BLT_CONFIG_PIXELS:
1625 return Tcl_NewIntObj(*(int *)ptr);
1627 case BLT_CONFIG_RELIEF:
1628 string = Tk_NameOfRelief(*(int *)ptr);
1631 case BLT_CONFIG_STRING:
1632 case BLT_CONFIG_UID:
1633 if (*(char **)ptr != NULL) {
1634 string = *(char **)ptr;
1638 case BLT_CONFIG_BITFLAG:
1642 flag = (*(int *)ptr) & (unsigned int)specPtr->customPtr;
1643 return Tcl_NewBooleanObj((flag != 0));
1646 case BLT_CONFIG_DASHES:
1649 Tcl_Obj *listObjPtr;
1650 Blt_Dashes *dashesPtr = (Blt_Dashes *)ptr;
1652 listObjPtr = Tcl_NewListObj(0, (Tcl_Obj **)NULL);
1653 for(p = dashesPtr->values; *p != 0; p++) {
1654 Tcl_ListObjAppendElement(interp, listObjPtr, Tcl_NewIntObj(*p));
1659 case BLT_CONFIG_DISTANCE:
1660 case BLT_CONFIG_POS_DISTANCE:
1661 return Tcl_NewIntObj(*(int *)ptr);
1663 case BLT_CONFIG_FILL:
1664 string = Blt_NameOfFill(*(int *)ptr);
1667 case BLT_CONFIG_FLOAT:
1669 double x = *(double *)ptr;
1670 return Tcl_NewDoubleObj(x);
1673 case BLT_CONFIG_LIST:
1675 Tcl_Obj *objPtr, *listObjPtr;
1678 listObjPtr = Tcl_NewListObj(0, (Tcl_Obj **)NULL);
1679 for (p = *(char ***)ptr; *p != NULL; p++) {
1680 objPtr = Tcl_NewStringObj(*p, -1);
1681 Tcl_ListObjAppendElement(interp, listObjPtr, objPtr);
1686 case BLT_CONFIG_OBJCMD:
1687 case BLT_CONFIG_OBJ:
1688 case BLT_CONFIG_LISTOBJ:
1689 if (*(Tcl_Obj **)ptr) {
1690 return *(Tcl_Obj **)ptr;
1692 return Tcl_NewStringObj("", -1);
1694 case BLT_CONFIG_PAD:
1696 Blt_Pad *padPtr = (Blt_Pad *)ptr;
1697 Tcl_Obj *objPtr, *listObjPtr;
1699 listObjPtr = Tcl_NewListObj(0, (Tcl_Obj **)NULL);
1700 objPtr = Tcl_NewIntObj(padPtr->side1);
1701 Tcl_ListObjAppendElement(interp, listObjPtr, objPtr);
1702 objPtr = Tcl_NewIntObj(padPtr->side2);
1703 Tcl_ListObjAppendElement(interp, listObjPtr, objPtr);
1707 case BLT_CONFIG_SHADOW:
1709 Shadow *shadowPtr = (Shadow *)ptr;
1710 Tcl_Obj *objPtr, *listObjPtr;
1712 if (shadowPtr->color != NULL) {
1713 listObjPtr = Tcl_NewListObj(0, (Tcl_Obj **)NULL);
1714 objPtr = Tcl_NewStringObj(Tk_NameOfColor(shadowPtr->color), -1);
1715 Tcl_ListObjAppendElement(interp, listObjPtr, objPtr);
1716 objPtr = Tcl_NewIntObj(shadowPtr->offset);
1717 Tcl_ListObjAppendElement(interp, listObjPtr, objPtr);
1723 case BLT_CONFIG_STATE:
1724 string = Blt_NameOfState(*(int *)ptr);
1727 case BLT_CONFIG_TILE:
1728 string = Blt_NameOfTile(*(Blt_Tile*)ptr);
1731 case BLT_CONFIG_SIDE:
1732 string = Blt_NameOfSide(*(int *)ptr);
1735 case BLT_CONFIG_ARROW:
1736 string = Blt_NameOfArrow(*(int *)ptr);
1740 string = "?? unknown type ??";
1742 return Tcl_NewStringObj(string, -1);
1746 *--------------------------------------------------------------
1748 * FormatConfigInfo --
1750 * Create a valid Tcl list holding the configuration information
1751 * for a single configuration option.
1754 * A Tcl list, dynamically allocated. The caller is expected to
1755 * arrange for this list to be freed eventually.
1758 * Memory is allocated.
1760 *--------------------------------------------------------------
1763 FormatConfigInfo(interp, tkwin, specPtr, widgRec)
1764 Tcl_Interp *interp; /* Interpreter to use for things
1765 * like floating-point precision. */
1766 Tk_Window tkwin; /* Window corresponding to widget. */
1767 register Blt_ConfigSpec *specPtr; /* Pointer to information describing
1769 char *widgRec; /* Pointer to record holding current
1770 * values of info for widget. */
1773 Tcl_Obj *listObjPtr;
1776 objv[0] = Tcl_NewStringObj(specPtr->switchName?specPtr->switchName:"", -1);
1777 if (specPtr->type == BLT_CONFIG_SYNONYM) {
1778 objv[1] = Tcl_NewStringObj(specPtr->customPtr?(char*)specPtr->customPtr:"", -1);
1779 listObjPtr = Tcl_NewListObj(0, (Tcl_Obj **)NULL);
1780 Tcl_ListObjAppendElement(interp, listObjPtr, objv[0]);
1781 Tcl_ListObjAppendElement(interp, listObjPtr, objv[1]);
1784 objv[1] = Tcl_NewStringObj(specPtr->dbName?(char*)specPtr->dbName:"", -1);
1785 objv[2] = Tcl_NewStringObj(specPtr->dbClass?(char*)specPtr->dbClass:"", -1);
1786 objv[3] = Tcl_NewStringObj(specPtr->defValue?(char*)specPtr->defValue:"", -1);
1787 objv[4] = FormatConfigValue(interp, tkwin, specPtr, widgRec);
1789 if (strstr(Tk_PathName(tkwin), ".__##") &&
1790 specPtr->type < BLT_CONFIG_END && specPtr->type >=0) {
1791 int stype = specPtr->type;
1792 static char *conftypes[BLT_CONFIG_END+10] = {
1793 "cursor", "anchor", "bitmap", "bool", "border", "cap", "color",
1794 "activecursor", "custom", "double", "font", "int", "join",
1795 "justify", "mm", "pixels", "relief", "string", "syn", "uid",
1796 "window", "bitflag", "dashes", "distance", "fill", "float",
1797 "list", "listobj", "pad", "paddistance", "shadow", "side",
1798 "state", "tile", "obj", "objcmd", "arrow",
1801 if (conftypes[BLT_CONFIG_END] == 0 ||
1802 strcmp(conftypes[BLT_CONFIG_END],"END")) {
1803 fprintf(stderr, "Blt_ConfigTypes changed\n");
1805 if (stype == BLT_CONFIG_CUSTOM) {
1806 extern Blt_CustomOption bltDistanceOption;
1807 extern Blt_CustomOption bltPositiveDistanceOption;
1809 if (specPtr->customPtr == &bltDistanceOption ||
1810 specPtr->customPtr == &bltPositiveDistanceOption
1812 stype = BLT_CONFIG_PIXELS;
1816 objv[5] = Tcl_NewStringObj(conftypes[stype], -1);
1820 return Tcl_NewListObj(size, objv);
1824 *--------------------------------------------------------------
1828 * Search through a table of configuration specs, looking for
1829 * one that matches a given switchName.
1832 * The return value is a pointer to the matching entry, or NULL
1833 * if nothing matched. In that case an error message is left
1834 * in the interp's result.
1839 *--------------------------------------------------------------
1841 static Blt_ConfigSpec *
1842 FindConfigSpec(interp, specs, objPtr, needFlags, hateFlags)
1843 Tcl_Interp *interp; /* Used for reporting errors. */
1844 Blt_ConfigSpec *specs; /* Pointer to table of configuration
1845 * specifications for a widget. */
1846 Tcl_Obj *objPtr; /* Name (suitable for use in a "config"
1847 * command) identifying particular option. */
1848 int needFlags; /* Flags that must be present in matching
1850 int hateFlags; /* Flags that must NOT be present in
1851 * matching entry. */
1853 register Blt_ConfigSpec *specPtr;
1854 register char c; /* First character of current argument. */
1855 Blt_ConfigSpec *matchPtr; /* Matching spec, or NULL. */
1859 string = Tcl_GetStringFromObj(objPtr, &length);
1862 for (specPtr = specs; specPtr->type != BLT_CONFIG_END; specPtr++) {
1863 if (specPtr->switchName == NULL) {
1866 if ((specPtr->switchName[1] != c) ||
1867 (strncmp(specPtr->switchName, string, length) != 0)) {
1870 if (((specPtr->specFlags & needFlags) != needFlags) ||
1871 (specPtr->specFlags & hateFlags)) {
1874 if (specPtr->switchName[length] == 0) {
1878 if (matchPtr != NULL) {
1879 if (interp != NULL) {
1880 Tcl_AppendResult(interp, "ambiguous option \"", string, "\"",
1883 return (Blt_ConfigSpec *)NULL;
1888 if (matchPtr == NULL) {
1889 if (interp != NULL) {
1890 Tcl_AppendResult(interp, "unknown option \"", string, "\"",
1893 return (Blt_ConfigSpec *)NULL;
1897 * Found a matching entry. If it's a synonym, then find the
1898 * entry that it's a synonym for.
1903 if (specPtr->type == BLT_CONFIG_SYNONYM) {
1904 for (specPtr = specs; ; specPtr++) {
1905 if (specPtr->type == BLT_CONFIG_END) {
1906 if (interp != NULL) {
1907 Tcl_AppendResult(interp,
1908 "couldn't find synonym for option \"", string,
1909 "\"", (char *) NULL);
1911 return (Blt_ConfigSpec *) NULL;
1913 if ((specPtr->type != BLT_CONFIG_SYNONYM) &&
1914 ((specPtr->specFlags & needFlags) == needFlags) &&
1915 (specPtr->specFlags & hateFlags) == 0 &&
1916 (strcmp(specPtr->switchName, (char*)matchPtr->customPtr)==0)) {
1924 /* Public routines */
1927 *--------------------------------------------------------------
1929 * Blt_ConfigureWidgetFromObj --
1931 * Process command-line options and database options to
1932 * fill in fields of a widget record with resources and
1936 * A standard Tcl return value. In case of an error,
1937 * the interp's result will hold an error message.
1940 * The fields of widgRec get filled in with information
1941 * from argc/argv and the option database. Old information
1942 * in widgRec's fields gets recycled.
1944 *--------------------------------------------------------------
1947 Blt_ConfigureWidgetFromObj(interp, tkwin, specs, objc, objv, widgRec, flags, subwin)
1948 Tcl_Interp *interp; /* Interpreter for error reporting. */
1949 Tk_Window tkwin; /* Window containing widget (needed to
1950 * set up X resources). */
1951 Blt_ConfigSpec *specs; /* Describes legal options. */
1952 int objc; /* Number of elements in argv. */
1953 Tcl_Obj *CONST *objv; /* Command-line options. */
1954 char *widgRec; /* Record whose fields are to be
1955 * modified. Values must be properly
1957 int flags; /* Used to specify additional flags
1958 * that must be present in config specs
1959 * for them to be considered. Also,
1960 * may have BLT_CONFIG_ARGV_ONLY set. */
1961 Tk_Window subwin; /* Child window for components. */
1963 register Blt_ConfigSpec *specPtr;
1964 int needFlags; /* Specs must contain this set of flags
1965 * or else they are not considered. */
1966 int hateFlags; /* If a spec contains any bits here, it's
1967 * not considered. */
1969 if (tkwin == NULL) {
1971 * Either we're not really in Tk, or the main window was destroyed and
1972 * we're on our way out of the application
1974 Tcl_AppendResult(interp, "NULL main window", (char *)NULL);
1978 if (subwin == NULL) {
1982 needFlags = flags & ~(BLT_CONFIG_USER_BIT - 1);
1983 if (Tk_Depth(tkwin) <= 1) {
1984 hateFlags = BLT_CONFIG_COLOR_ONLY;
1986 hateFlags = BLT_CONFIG_MONO_ONLY;
1990 * Pass one: scan through all the option specs, replacing strings
1991 * with Tk_Uid structs (if this hasn't been done already) and
1992 * clearing the BLT_CONFIG_OPTION_SPECIFIED flags.
1995 specs = Blt_GetCachedBltSpecs(interp, specs);
1996 for (specPtr = specs; specPtr->type != BLT_CONFIG_END; specPtr++) {
1997 if (!(specPtr->specFlags & INIT) && (specPtr->switchName != NULL)) {
1998 if (specPtr->dbName != NULL) {
1999 specPtr->dbName = Tk_GetUid((char*)specPtr->dbName);
2001 if (specPtr->dbClass != NULL) {
2002 specPtr->dbClass = Tk_GetUid((char*)specPtr->dbClass);
2004 if (specPtr->defValue != NULL) {
2005 specPtr->defValue = Tk_GetUid((char*)specPtr->defValue);
2008 specPtr->specFlags =
2009 (specPtr->specFlags & ~BLT_CONFIG_OPTION_SPECIFIED) | INIT;
2013 * Pass two: scan through all of the arguments, processing those
2014 * that match entries in the specs.
2017 specPtr = FindConfigSpec(interp, specs, objv[0], needFlags, hateFlags);
2018 if (specPtr == NULL) {
2022 /* Process the entry. */
2024 Tcl_AppendResult(interp, "value for \"", Tcl_GetString(objv[0]),
2025 "\" missing", (char *) NULL);
2028 if (DoConfig(interp, tkwin, specPtr, objv[1], widgRec) != TCL_OK) {
2031 sprintf(msg, "\n (processing \"%.40s\" option)",
2032 specPtr->switchName);
2033 Tcl_AddErrorInfo(interp, msg);
2036 specPtr->specFlags |= BLT_CONFIG_OPTION_SPECIFIED;
2037 objc -= 2, objv += 2;
2041 * Pass three: scan through all of the specs again; if no
2042 * command-line argument matched a spec, then check for info
2043 * in the option database. If there was nothing in the
2044 * database, then use the default.
2047 if (!(flags & BLT_CONFIG_OBJV_ONLY)) {
2050 for (specPtr = specs; specPtr->type != BLT_CONFIG_END; specPtr++) {
2051 if ((specPtr->specFlags & BLT_CONFIG_OPTION_SPECIFIED) ||
2052 (specPtr->switchName == NULL) ||
2053 (specPtr->type == BLT_CONFIG_SYNONYM)) {
2056 if (((specPtr->specFlags & needFlags) != needFlags) ||
2057 (specPtr->specFlags & hateFlags)) {
2061 if (specPtr->dbName != NULL) {
2064 value = Tk_GetOption(subwin, (char*)specPtr->dbName, (char*)specPtr->dbClass);
2065 if (value != NULL) {
2066 objPtr = Tcl_NewStringObj((char*)value, -1);
2067 Tcl_IncrRefCount(objPtr);
2070 if (objPtr != NULL) {
2071 if (DoConfig(interp, tkwin, specPtr, objPtr, widgRec)
2075 sprintf(msg, "\n (%s \"%.50s\" in widget \"%.50s\")",
2076 "database entry for",
2077 specPtr->dbName, Tk_PathName(tkwin));
2078 if (getenv("TCL_BADOPTS") == NULL) {
2079 fprintf(stderr, "%s%s\n", Tcl_GetStringResult(interp), msg);
2080 Tcl_DecrRefCount(objPtr);
2084 Tcl_AddErrorInfo(interp, msg);
2085 Tcl_DecrRefCount(objPtr);
2088 Tcl_DecrRefCount(objPtr);
2091 if (specPtr->defValue != NULL) {
2092 objPtr = Tcl_NewStringObj((char*)specPtr->defValue, -1);
2093 Tcl_IncrRefCount(objPtr);
2097 if ((objPtr != NULL) && !(specPtr->specFlags
2098 & BLT_CONFIG_DONT_SET_DEFAULT)) {
2099 if (DoConfig(interp, tkwin, specPtr, objPtr, widgRec)
2103 Tcl_DecrRefCount(objPtr);
2105 "\n (%s \"%.50s\" in widget \"%.50s\")",
2106 "default value for",
2107 specPtr->dbName, Tk_PathName(tkwin));
2108 Tcl_AddErrorInfo(interp, msg);
2112 if ((objPtr != NULL)) {
2113 Tcl_DecrRefCount(objPtr);
2123 *--------------------------------------------------------------
2125 * Blt_ConfigureInfoFromObj --
2127 * Return information about the configuration options
2128 * for a window, and their current values.
2131 * Always returns TCL_OK. The interp's result will be modified
2132 * hold a description of either a single configuration option
2133 * available for "widgRec" via "specs", or all the configuration
2134 * options available. In the "all" case, the result will
2135 * available for "widgRec" via "specs". The result will
2136 * be a list, each of whose entries describes one option.
2137 * Each entry will itself be a list containing the option's
2138 * name for use on command lines, database name, database
2139 * class, default value, and current value (empty string
2140 * if none). For options that are synonyms, the list will
2141 * contain only two values: name and synonym name. If the
2142 * "name" argument is non-NULL, then the only information
2143 * returned is that for the named argument (i.e. the corresponding
2144 * entry in the overall list is returned).
2149 *--------------------------------------------------------------
2153 Blt_ConfigureInfoFromObj(interp, tkwin, specs, widgRec, objPtr, flags)
2154 Tcl_Interp *interp; /* Interpreter for error reporting. */
2155 Tk_Window tkwin; /* Window corresponding to widgRec. */
2156 Blt_ConfigSpec *specs; /* Describes legal options. */
2157 char *widgRec; /* Record whose fields contain current
2158 * values for options. */
2159 Tcl_Obj *objPtr; /* If non-NULL, indicates a single option
2160 * whose info is to be returned. Otherwise
2161 * info is returned for all options. */
2162 int flags; /* Used to specify additional flags
2163 * that must be present in config specs
2164 * for them to be considered. */
2166 register Blt_ConfigSpec *specPtr;
2167 int needFlags, hateFlags;
2169 Tcl_Obj *listObjPtr, *valueObjPtr;
2171 needFlags = flags & ~(BLT_CONFIG_USER_BIT - 1);
2172 if (Tk_Depth(tkwin) <= 1) {
2173 hateFlags = BLT_CONFIG_COLOR_ONLY;
2175 hateFlags = BLT_CONFIG_MONO_ONLY;
2179 * If information is only wanted for a single configuration
2180 * spec, then handle that one spec specially.
2183 Tcl_SetResult(interp, (char *)NULL, TCL_STATIC);
2184 specs = Blt_GetCachedBltSpecs(interp, specs);
2185 if (objPtr != NULL) {
2186 specPtr = FindConfigSpec(interp, specs, objPtr, needFlags, hateFlags);
2187 if (specPtr == NULL) {
2190 valueObjPtr = FormatConfigInfo(interp, tkwin, specPtr, widgRec);
2191 Tcl_SetObjResult(interp, valueObjPtr);
2196 * Loop through all the specs, creating a big list with all
2197 * their information.
2199 string = NULL; /* Suppress compiler warning. */
2200 if (objPtr != NULL) {
2201 string = Tcl_GetString(objPtr);
2203 listObjPtr = Tcl_NewListObj(0, (Tcl_Obj **)NULL);
2204 for (specPtr = specs; specPtr->type != BLT_CONFIG_END; specPtr++) {
2205 if ((objPtr != NULL) && (specPtr->switchName != string)) {
2208 if (((specPtr->specFlags & needFlags) != needFlags) ||
2209 (specPtr->specFlags & hateFlags)) {
2212 if (specPtr->switchName == NULL) {
2215 valueObjPtr = FormatConfigInfo(interp, tkwin, specPtr, widgRec);
2216 Tcl_ListObjAppendElement(interp, listObjPtr, valueObjPtr);
2218 Tcl_SetObjResult(interp, listObjPtr);
2222 /* Format expected arguments into interp. */
2224 Blt_FormatSpecOptions(interp, specs)
2225 Tcl_Interp *interp; /* Interpreter for error reporting. */
2226 Blt_ConfigSpec *specs; /* Describes legal options. */
2228 Blt_ConfigSpec *specPtr;
2230 for (specPtr = specs; specPtr->type != BLT_CONFIG_END; specPtr++) {
2231 Tcl_AppendResult(interp, (cnt?", ":""), specPtr->switchName, 0);
2239 *----------------------------------------------------------------------
2241 * Blt_ConfigureValueFromObj --
2243 * This procedure returns the current value of a configuration
2244 * option for a widget.
2247 * The return value is a standard Tcl completion code (TCL_OK or
2248 * TCL_ERROR). The interp's result will be set to hold either the value
2249 * of the option given by objPtr (if TCL_OK is returned) or
2250 * an error message (if TCL_ERROR is returned).
2255 *----------------------------------------------------------------------
2258 Blt_ConfigureValueFromObj(interp, tkwin, specs, widgRec, objPtr, flags)
2259 Tcl_Interp *interp; /* Interpreter for error reporting. */
2260 Tk_Window tkwin; /* Window corresponding to widgRec. */
2261 Blt_ConfigSpec *specs; /* Describes legal options. */
2262 char *widgRec; /* Record whose fields contain current
2263 * values for options. */
2264 Tcl_Obj *objPtr; /* Gives the command-line name for the
2265 * option whose value is to be returned. */
2266 int flags; /* Used to specify additional flags
2267 * that must be present in config specs
2268 * for them to be considered. */
2270 Blt_ConfigSpec *specPtr;
2271 int needFlags, hateFlags;
2273 needFlags = flags & ~(BLT_CONFIG_USER_BIT - 1);
2274 if (Tk_Depth(tkwin) <= 1) {
2275 hateFlags = BLT_CONFIG_COLOR_ONLY;
2277 hateFlags = BLT_CONFIG_MONO_ONLY;
2279 specs = Blt_GetCachedBltSpecs(interp, specs);
2280 specPtr = FindConfigSpec(interp, specs, objPtr, needFlags, hateFlags);
2281 if (specPtr == NULL) {
2284 objPtr = FormatConfigValue(interp, tkwin, specPtr, widgRec);
2285 Tcl_SetObjResult(interp, objPtr);
2290 *----------------------------------------------------------------------
2292 * Blt_FreeObjOptions --
2294 * Free up all resources associated with configuration options.
2300 * Any resource in widgRec that is controlled by a configuration
2301 * option (e.g. a Tk_3DBorder or XColor) is freed in the appropriate
2304 *----------------------------------------------------------------------
2307 Blt_FreeObjOptions(interp, specs, widgRec, display, needFlags)
2308 Tcl_Interp *interp; /* Interpreter for error reporting. */
2309 Blt_ConfigSpec *specs; /* Describes legal options. */
2310 char *widgRec; /* Record whose fields contain current
2311 * values for options. */
2312 Display *display; /* X display; needed for freeing some
2314 int needFlags; /* Used to specify additional flags
2315 * that must be present in config specs
2316 * for them to be considered. */
2318 register Blt_ConfigSpec *specPtr;
2321 specs = Blt_GetCachedBltSpecs(interp, specs);
2322 for (specPtr = specs; specPtr->type != BLT_CONFIG_END; specPtr++) {
2323 if ((specPtr->specFlags & needFlags) != needFlags) {
2326 ptr = widgRec + specPtr->offset;
2327 switch (specPtr->type) {
2328 case BLT_CONFIG_STRING:
2329 if (*((char **) ptr) != NULL) {
2330 Blt_Free(*((char **) ptr));
2331 *((char **) ptr) = NULL;
2335 case BLT_CONFIG_SHADOW: {
2336 Shadow *shadPtr = (Shadow*)ptr;
2337 if (shadPtr->color != NULL) {
2338 Tk_FreeColor(shadPtr->color);
2339 shadPtr->color = NULL;
2341 shadPtr->offset = 0;
2345 case BLT_CONFIG_COLOR:
2346 if (*((XColor **) ptr) != NULL) {
2347 Tk_FreeColor(*((XColor **) ptr));
2348 *((XColor **) ptr) = NULL;
2352 case BLT_CONFIG_FONT:
2353 Tk_FreeFont(*((Tk_Font *) ptr));
2354 *((Tk_Font *) ptr) = NULL;
2357 case BLT_CONFIG_BITMAP:
2358 if (*((Pixmap *) ptr) != None) {
2359 Tk_FreeBitmap(display, *((Pixmap *) ptr));
2360 *((Pixmap *) ptr) = None;
2364 case BLT_CONFIG_BORDER:
2365 if (*((Tk_3DBorder *) ptr) != NULL) {
2366 Tk_Free3DBorder(*((Tk_3DBorder *) ptr));
2367 *((Tk_3DBorder *) ptr) = NULL;
2371 case BLT_CONFIG_CURSOR:
2372 case BLT_CONFIG_ACTIVE_CURSOR:
2373 if (*((Tk_Cursor *) ptr) != None) {
2374 Tk_FreeCursor(display, *((Tk_Cursor *) ptr));
2375 *((Tk_Cursor *) ptr) = None;
2379 case BLT_CONFIG_OBJCMD:
2380 case BLT_CONFIG_OBJ:
2381 case BLT_CONFIG_LISTOBJ:
2382 if ((*(Tcl_Obj **)ptr) != NULL) {
2383 Tcl_DecrRefCount(*(Tcl_Obj **)ptr);
2384 *((Tcl_Obj **) ptr) = NULL;
2388 case BLT_CONFIG_LIST:
2392 argv = *(char ***)ptr;
2395 *(char ***)ptr = NULL;
2401 case BLT_CONFIG_TILE:
2402 if (*(Blt_Tile*)ptr != NULL) {
2403 Blt_FreeTile(*(Blt_Tile*)ptr);
2404 *(Blt_Tile *)ptr = NULL;
2408 case BLT_CONFIG_CUSTOM:
2409 if ((*(char **)ptr != NULL) &&
2410 (specPtr->customPtr->freeProc != NULL)) {
2411 (*specPtr->customPtr->freeProc)(specPtr->customPtr->clientData,
2412 display, widgRec, specPtr->offset, *(char **)ptr);
2413 *(char **)ptr = NULL;
2421 *----------------------------------------------------------------------
2423 * Blt_ObjConfigModified --
2425 * Given the configuration specifications and one or more option
2426 * patterns (terminated by a NULL), indicate if any of the matching
2427 * configuration options has been reset.
2430 * Returns 1 if one of the options has changed, 0 otherwise.
2431 * If no options specified, clears all modified flags.
2433 *----------------------------------------------------------------------
2436 Blt_ObjConfigModified TCL_VARARGS_DEF(Blt_ConfigSpec *, arg1)
2439 Blt_ConfigSpec *specs;
2440 register Blt_ConfigSpec *specPtr;
2441 register char *option;
2445 specs = TCL_VARARGS_START(Blt_ConfigSpec *, arg1, argList);
2446 interp = va_arg(argList, Tcl_Interp *);
2447 specs = Blt_GetCachedBltSpecs(interp, specs);
2448 while ((option = va_arg(argList, char *)) != NULL) {
2450 for (specPtr = specs; specPtr->type != BLT_CONFIG_END; specPtr++) {
2451 if ((Tcl_StringMatch(specPtr->switchName, option)) &&
2452 (specPtr->specFlags & BLT_CONFIG_OPTION_SPECIFIED)) {
2460 for (specPtr = specs; specPtr->type != BLT_CONFIG_END; specPtr++) {
2461 specPtr->specFlags &= ~BLT_CONFIG_OPTION_SPECIFIED;
2468 *----------------------------------------------------------------------
2470 * Blt_ConfigureComponentFromObj --
2472 * Configures a component of a widget. This is useful for
2473 * widgets that have multiple components which aren't uniquely
2474 * identified by a Tk_Window. It allows us, for example, set
2475 * resources for axes of the graph widget. The graph really has
2476 * only one window, but its convenient to specify components in a
2477 * hierarchy of options.
2479 * *graph.x.logScale yes
2480 * *graph.Axis.logScale yes
2481 * *graph.temperature.scaleSymbols yes
2482 * *graph.Element.scaleSymbols yes
2484 * This is really a hack to work around the limitations of the Tk
2485 * resource database. It creates a temporary window, needed to
2486 * call Tk_ConfigureWidget, using the name of the component.
2489 * A standard Tcl result.
2492 * A temporary window is created merely to pass to Tk_ConfigureWidget.
2494 *----------------------------------------------------------------------
2497 Blt_ConfigureComponentFromObj(interp, parent, name, className, specsPtr,
2498 objc, objv, widgRec, flags)
2500 Tk_Window parent; /* Window to associate with component */
2501 char *name; /* Name of component */
2503 Blt_ConfigSpec *specsPtr;
2505 Tcl_Obj *CONST *objv;
2512 int isTemporary = FALSE;
2514 tmpName = Blt_Strdup(name);
2516 /* Window name can't start with an upper case letter */
2517 tmpName[0] = tolower(name[0]);
2520 * Create component if a child window by the component's name
2521 * doesn't already exist.
2523 tkwin = Blt_FindChild(parent, tmpName);
2524 if (tkwin == NULL) {
2525 tkwin = Tk_CreateWindow(interp, parent, tmpName, (char *)NULL);
2528 if (tkwin == NULL) {
2529 Tcl_AppendResult(interp, "can't find window in \"",
2530 Tk_PathName(parent), "\"", (char *)NULL);
2533 assert(Tk_Depth(tkwin) == Tk_Depth(parent));
2536 Tk_SetClass(tkwin, className);
2537 result = Blt_ConfigureWidgetFromObj(interp, parent, specsPtr, objc, objv,
2538 widgRec, flags, tkwin);
2540 Tk_DestroyWindow(tkwin);
2546 *--------------------------------------------------------------
2548 * Blt_ObjIsOption --
2550 * Indicates whether objPtr is a valid configuration option
2551 * such as -background.
2554 * Returns 1 is a matching option is found and 0 otherwise.
2556 *--------------------------------------------------------------
2559 Blt_ObjIsOption(interp, specs, objPtr, flags)
2561 Blt_ConfigSpec *specs; /* Describes legal options. */
2562 Tcl_Obj *objPtr; /* Command-line option name. */
2563 int flags; /* Used to specify additional flags
2564 * that must be present in config specs
2565 * for them to be considered. Also,
2566 * may have BLT_CONFIG_ARGV_ONLY set. */
2568 register Blt_ConfigSpec *specPtr;
2569 int needFlags; /* Specs must contain this set of flags
2570 * or else they are not considered. */
2571 specs = Blt_GetCachedBltSpecs(interp, specs);
2572 needFlags = flags & ~(BLT_CONFIG_USER_BIT - 1);
2573 specPtr = FindConfigSpec((Tcl_Interp *)NULL, specs, objPtr, needFlags, 0);
2574 return (specPtr != NULL);
2578 *--------------------------------------------------------------
2580 * DeleteSpecCacheTable --
2582 * Delete the per-interpreter copy of all the Blt_ConfigSpec tables which
2583 * were stored in the interpreter's assoc-data store.
2591 *--------------------------------------------------------------
2595 DeleteSpecCacheTable(clientData, interp)
2596 ClientData clientData;
2599 Tcl_HashTable *tablePtr = (Tcl_HashTable *) clientData;
2600 Tcl_HashEntry *entryPtr;
2601 Tcl_HashSearch search;
2603 for (entryPtr = Tcl_FirstHashEntry(tablePtr,&search); entryPtr != NULL;
2604 entryPtr = Tcl_NextHashEntry(&search)) {
2606 * Someone else deallocates the Tk_Uids themselves.
2609 ckfree((char *) Tcl_GetHashValue(entryPtr));
2611 Tcl_DeleteHashTable(tablePtr);
2612 ckfree((char *) tablePtr);
2617 Blt_GetCachedBltSpecs(interp, staticSpecs)
2619 const Blt_ConfigSpec *staticSpecs;
2621 return GetCachedBltSpecs(interp, staticSpecs);
2624 static Blt_ConfigSpec *
2625 GetCachedBltSpecs(interp, staticSpecs)
2626 Tcl_Interp *interp; /* Interpreter in which to store the cache. */
2627 const Blt_ConfigSpec *staticSpecs;
2628 /* Value to cache a copy of; it is also used
2629 * as a key into the cache. */
2631 Blt_ConfigSpec *cachedSpecs;
2632 Tcl_HashTable *specCacheTablePtr;
2633 Tcl_HashEntry *entryPtr;
2637 * Get (or allocate if it doesn't exist) the hash table that the writable
2638 * copies of the widget specs are stored in. In effect, this is
2639 * self-initializing code.
2642 specCacheTablePtr = (Tcl_HashTable *)
2643 Tcl_GetAssocData(interp, "bltConfigSpec.threadTable", NULL);
2644 if (specCacheTablePtr == NULL) {
2645 specCacheTablePtr = (Tcl_HashTable *) ckalloc(sizeof(Tcl_HashTable));
2646 Tcl_InitHashTable(specCacheTablePtr, TCL_ONE_WORD_KEYS);
2647 Tcl_SetAssocData(interp, "bltConfigSpec.threadTable",
2648 DeleteSpecCacheTable, (ClientData) specCacheTablePtr);
2652 * Look up or create the hash entry that the constant specs are mapped to,
2653 * which will have the writable specs as its associated value.
2656 entryPtr = Tcl_CreateHashEntry(specCacheTablePtr, (char *) staticSpecs,
2659 unsigned int entrySpace = sizeof(Blt_ConfigSpec);
2660 const Blt_ConfigSpec *staticSpecPtr;
2661 Blt_ConfigSpec *specPtr;
2664 * OK, no working copy in this interpreter so copy. Need to work out
2665 * how much space to allocate first.
2668 for (staticSpecPtr=staticSpecs; staticSpecPtr->type!=BLT_CONFIG_END;
2670 entrySpace += sizeof(Blt_ConfigSpec);
2674 * Now allocate our working copy's space and copy over the contents
2675 * from the master copy.
2678 cachedSpecs = (Blt_ConfigSpec *) ckalloc(entrySpace);
2679 memcpy((void *) cachedSpecs, (void *) staticSpecs, entrySpace);
2680 Tcl_SetHashValue(entryPtr, (ClientData) cachedSpecs);
2683 * Finally, go through and replace database names, database classes
2684 * and default values with Tk_Uids. This is the bit that has to be
2688 for (specPtr=cachedSpecs; specPtr->type!=BLT_CONFIG_END; specPtr++) {
2689 if (specPtr->switchName != NULL) {
2690 if (specPtr->dbName != NULL) {
2691 specPtr->dbName = Tk_GetUid((char*)specPtr->dbName);
2693 if (specPtr->dbClass != NULL) {
2694 specPtr->dbClass = Tk_GetUid((char*)specPtr->dbClass);
2696 if (specPtr->defValue != NULL) {
2697 specPtr->defValue = Tk_GetUid((char*)specPtr->defValue);
2702 cachedSpecs = (Blt_ConfigSpec *) Tcl_GetHashValue(entryPtr);
2709 #endif /* TK_VERSION_NUMBER >= 8.1.0 */