diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/bltGrElemBar.C | 769 | ||||
-rw-r--r-- | src/bltGrElemLine.C | 4 | ||||
-rw-r--r-- | src/bltGrElemOp.C | 1120 | ||||
-rw-r--r-- | src/bltGrPenOp.C | 422 | ||||
-rw-r--r-- | src/bltGraph.C | 6 | ||||
-rw-r--r-- | src/bltGraph.h | 5 |
6 files changed, 954 insertions, 1372 deletions
diff --git a/src/bltGrElemBar.C b/src/bltGrElemBar.C index 52cc694..9735d1c 100644 --- a/src/bltGrElemBar.C +++ b/src/bltGrElemBar.C @@ -187,6 +187,39 @@ typedef struct { int errorBarCapWidth; /* Length of cap on error bars */ } BarElement; +// Defs + +static void InitBarPen(Graph* graphPtr, BarPen* penPtr); +static void ResetBar(BarElement* elemPtr); + +static PenConfigureProc ConfigurePenProc; +static PenDestroyProc DestroyPenProc; +static ElementClosestProc ClosestBarProc; +static ElementConfigProc ConfigureBarProc; +static ElementDestroyProc DestroyBarProc; +static ElementDrawProc DrawActiveBarProc; +static ElementDrawProc DrawNormalBarProc; +static ElementDrawSymbolProc DrawSymbolProc; +static ElementExtentsProc GetBarExtentsProc; +static ElementToPostScriptProc ActiveBarToPostScriptProc; +static ElementToPostScriptProc NormalBarToPostScriptProc; +static ElementSymbolToPostScriptProc SymbolToPostScriptProc; +static ElementMapProc MapBarProc; + +static ElementProcs barProcs = { + ClosestBarProc, + ConfigureBarProc, + DestroyBarProc, + DrawActiveBarProc, + DrawNormalBarProc, + DrawSymbolProc, + GetBarExtentsProc, + ActiveBarToPostScriptProc, + NormalBarToPostScriptProc, + SymbolToPostScriptProc, + MapBarProc, +}; + // OptionSpecs static Tk_ObjCustomOption styleObjOption = @@ -301,123 +334,6 @@ static Tk_OptionSpec barElemOptionSpecs[] = { {TK_OPTION_END, NULL, NULL, NULL, NULL, -1, 0, 0, NULL, 0} }; -/* -static Blt_ConfigSpec barElemConfigSpecs[] = { - {BLT_CONFIG_CUSTOM, "-activepen", "activePen", "ActivePen", - "activeBar", Tk_Offset(BarElement, activePenPtr), - BLT_CONFIG_NULL_OK, &bltBarPenOption}, - {BLT_CONFIG_BORDER, "-background", "background", "Background", - "navyblue", Tk_Offset(BarElement, builtinPen.fill), - BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_DOUBLE, "-barwidth", "barWidth", "BarWidth", - 0, Tk_Offset(BarElement, barWidth), - BLT_CONFIG_DONT_SET_DEFAULT}, - {BLT_CONFIG_SYNONYM, "-bd", "borderWidth", (char *)NULL, - (char *)NULL, 0, 0}, - {BLT_CONFIG_SYNONYM, "-bg", "background", (char *)NULL, - (char *)NULL, 0, 0}, - {BLT_CONFIG_CUSTOM, "-bindtags", "bindTags", "BindTags", "all", - Tk_Offset(BarElement, obj.tags), BLT_CONFIG_NULL_OK, - &listOption}, - {BLT_CONFIG_PIXELS, "-borderwidth", "borderWidth", "BorderWidth", - STD_BORDERWIDTH, Tk_Offset(BarElement, builtinPen.borderWidth), 0}, - {BLT_CONFIG_SYNONYM, "-color", "background", (char *)NULL, - (char *)NULL, 0, 0}, - {BLT_CONFIG_CUSTOM, "-errorbarcolor", "errorBarColor", "ErrorBarColor", - "defcolor", - Tk_Offset(BarElement, builtinPen.errorBarColor), 0, &bltColorOption}, - {BLT_CONFIG_PIXELS,"-errorbarwidth", "errorBarWidth", "ErrorBarWidth", - "1", - Tk_Offset(BarElement, builtinPen.errorBarLineWidth), - BLT_CONFIG_DONT_SET_DEFAULT}, - {BLT_CONFIG_PIXELS, "-errorbarcap", "errorBarCap", "ErrorBarCap", - "1", - Tk_Offset(BarElement, builtinPen.errorBarCapWidth), - BLT_CONFIG_DONT_SET_DEFAULT}, - {BLT_CONFIG_SYNONYM, "-fg", "foreground", (char *)NULL, (char *)NULL, 0, 0}, - {BLT_CONFIG_CUSTOM, "-data", "data", "Data", (char *)NULL, 0, 0, - &bltValuePairsOption}, - {BLT_CONFIG_SYNONYM, "-fill", "background", (char *)NULL, - (char *)NULL, 0, 0}, - {BLT_CONFIG_COLOR, "-foreground", "foreground", "Foreground", - "bblue", Tk_Offset(BarElement, builtinPen.outlineColor), - BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_STRING, "-label", "label", "Label", (char *)NULL, - Tk_Offset(BarElement, label), BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_RELIEF, "-legendrelief", "legendRelief", "LegendRelief", - "flat", Tk_Offset(BarElement, legendRelief), - BLT_CONFIG_DONT_SET_DEFAULT}, - {BLT_CONFIG_CUSTOM, "-hide", "hide", "Hide", "no", - Tk_Offset(BarElement, flags), BLT_CONFIG_DONT_SET_DEFAULT, - &bitmaskBarElemHideOption}, - {BLT_CONFIG_CUSTOM, "-mapx", "mapX", "MapX", "x", - Tk_Offset(BarElement, axes.x), 0, &bltXAxisOption}, - {BLT_CONFIG_CUSTOM, "-mapy", "mapY", "MapY", "y", - Tk_Offset(BarElement, axes.y), 0, &bltYAxisOption}, - {BLT_CONFIG_SYNONYM, "-outline", "foreground", (char *)NULL, - (char *)NULL, 0, 0}, - {BLT_CONFIG_CUSTOM, "-pen", "pen", "Pen", (char *)NULL, - Tk_Offset(BarElement, normalPenPtr), BLT_CONFIG_NULL_OK, - &bltBarPenOption}, - {BLT_CONFIG_RELIEF, "-relief", "relief", "Relief", - "raised", Tk_Offset(BarElement, builtinPen.relief), 0}, - {BLT_CONFIG_CUSTOM, "-showerrorbars", "showErrorBars", "ShowErrorBars", - "both", Tk_Offset(BarElement, builtinPen.errorBarShow), - BLT_CONFIG_DONT_SET_DEFAULT, &fillOption}, - {BLT_CONFIG_CUSTOM, "-showvalues", "showValues", "ShowValues", - "no", Tk_Offset(BarElement, builtinPen.valueShow), - BLT_CONFIG_DONT_SET_DEFAULT, &fillOption}, - {BLT_CONFIG_STRING, "-stack", "stack", "Stack", NULL, - Tk_Offset(BarElement, groupName), BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_CUSTOM, "-state", "state", "State", "normal", - Tk_Offset(BarElement, state), BLT_CONFIG_DONT_SET_DEFAULT, &stateOption}, - {BLT_CONFIG_BITMAP, "-stipple", "stipple", "Stipple", - "", Tk_Offset(BarElement, builtinPen.stipple), - BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_CUSTOM, "-styles", "styles", "Styles", "", - Tk_Offset(BarElement, stylePalette), 0, &bltBarStylesOption}, - {BLT_CONFIG_ANCHOR, "-valueanchor", "valueAnchor", "ValueAnchor", - "s", - Tk_Offset(BarElement, builtinPen.valueStyle.anchor), 0}, - {BLT_CONFIG_COLOR, "-valuecolor", "valueColor", "ValueColor", - "black", - Tk_Offset(BarElement, builtinPen.valueStyle.color), 0}, - {BLT_CONFIG_FONT, "-valuefont", "valueFont", "ValueFont", - STD_FONT_SMALL, - Tk_Offset(BarElement, builtinPen.valueStyle.font), 0}, - {BLT_CONFIG_STRING, "-valueformat", "valueFormat", "ValueFormat", - "%g", Tk_Offset(BarElement, builtinPen.valueFormat), - BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_DOUBLE, "-valuerotate", "valueRotate", "ValueRotate", - (char *)NULL, Tk_Offset(BarElement, builtinPen.valueStyle.angle), 0}, - {BLT_CONFIG_CUSTOM, "-weights", "weights", "Weights", (char *)NULL, - Tk_Offset(BarElement, w), 0, &bltValuesOption}, - {BLT_CONFIG_CUSTOM, "-x", "xdata", "Xdata", (char *)NULL, - Tk_Offset(BarElement, x), 0, &bltValuesOption}, - {BLT_CONFIG_CUSTOM, "-y", "ydata", "Ydata", (char *)NULL, - Tk_Offset(BarElement, y), 0, &bltValuesOption}, - {BLT_CONFIG_CUSTOM, "-xdata", "xdata", "Xdata", (char *)NULL, - Tk_Offset(BarElement, x), 0, &bltValuesOption}, - {BLT_CONFIG_CUSTOM, "-ydata", "ydata", "Ydata", (char *)NULL, - Tk_Offset(BarElement, y), 0, &bltValuesOption}, - {BLT_CONFIG_CUSTOM, "-xerror", "xError", "XError", (char *)NULL, - Tk_Offset(BarElement, xError), 0, &bltValuesOption}, - {BLT_CONFIG_CUSTOM, "-xhigh", "xHigh", "XHigh", (char *)NULL, - Tk_Offset(BarElement, xHigh), 0, &bltValuesOption}, - {BLT_CONFIG_CUSTOM, "-xlow", "xLow", "XLow", (char *)NULL, - Tk_Offset(BarElement, xLow), 0, &bltValuesOption}, - {BLT_CONFIG_CUSTOM, "-yerror", "yError", "YError", (char *)NULL, - Tk_Offset(BarElement, yError), 0, &bltValuesOption}, - {BLT_CONFIG_CUSTOM, "-yhigh", "yHigh", "YHigh", (char *)NULL, - Tk_Offset(BarElement, yHigh), 0, &bltValuesOption}, - {BLT_CONFIG_CUSTOM, "-ylow", "yLow", "YLow", (char *)NULL, - Tk_Offset(BarElement, yLow), 0, &bltValuesOption}, - {BLT_CONFIG_END, NULL, NULL, NULL, NULL, 0, 0} -}; -*/ - -//*** - static Tk_OptionSpec barPenOptionSpecs[] = { {TK_OPTION_BORDER, "-background", "background", "Background", STD_NORMAL_FOREGROUND, -1, Tk_Offset(BarPen, fill), 0, NULL, 0}, @@ -459,102 +375,134 @@ static Tk_OptionSpec barPenOptionSpecs[] = { {TK_OPTION_END, NULL, NULL, NULL, NULL, -1, 0, 0, NULL, 0} }; -/* -static Blt_ConfigSpec barPenConfigSpecs[] = { - {BLT_CONFIG_BORDER, "-background", "background", "Background", - "rred", Tk_Offset(BarPen, fill), - BLT_CONFIG_NULL_OK | ACTIVE_PEN}, - {BLT_CONFIG_BORDER, "-background", "background", "Background", - "navyblue", Tk_Offset(BarPen, fill), - BLT_CONFIG_NULL_OK | NORMAL_PEN}, - {BLT_CONFIG_SYNONYM, "-bd", "borderWidth", (char *)NULL, - (char *)NULL, 0, ALL_PENS}, - {BLT_CONFIG_SYNONYM, "-bg", "background", (char *)NULL, - (char *)NULL, 0, ALL_PENS}, - {BLT_CONFIG_PIXELS, "-borderwidth", "borderWidth", "BorderWidth", - STD_BORDERWIDTH, Tk_Offset(BarPen, borderWidth), ALL_PENS}, - {BLT_CONFIG_CUSTOM, "-errorbarcolor", "errorBarColor", "ErrorBarColor", - "defcolor", Tk_Offset(BarPen, errorBarColor), ALL_PENS, - &bltColorOption}, - {BLT_CONFIG_PIXELS, "-errorbarwidth", "errorBarWidth","ErrorBarWidth", - "1", Tk_Offset(BarPen, errorBarLineWidth), - ALL_PENS | BLT_CONFIG_DONT_SET_DEFAULT}, - {BLT_CONFIG_PIXELS, "-errorbarcap", "errorBarCap", "ErrorBarCap", - "1", Tk_Offset(BarPen, errorBarCapWidth), - ALL_PENS | BLT_CONFIG_DONT_SET_DEFAULT}, - {BLT_CONFIG_SYNONYM, "-fg", "foreground", (char *)NULL, - (char *)NULL, 0, ALL_PENS}, - {BLT_CONFIG_SYNONYM, "-fill", "background", (char *)NULL, - (char *)NULL, 0, ALL_PENS}, - {BLT_CONFIG_COLOR, "-foreground", "foreground", "Foreground", - "pink", Tk_Offset(BarPen, outlineColor), - ACTIVE_PEN | BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_COLOR, "-foreground", "foreground", "Foreground", - "bblue", Tk_Offset(BarPen, outlineColor), - NORMAL_PEN | BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_SYNONYM, "-outline", "foreground", (char *)NULL, - (char *)NULL, 0, ALL_PENS}, - {BLT_CONFIG_RELIEF, "-relief", "relief", "Relief", - "raised", Tk_Offset(BarPen, relief), ALL_PENS}, - {BLT_CONFIG_CUSTOM, "-showerrorbars", "showErrorBars", "ShowErrorBars", - "both", Tk_Offset(BarPen, errorBarShow), - BLT_CONFIG_DONT_SET_DEFAULT, &fillOption}, - {BLT_CONFIG_CUSTOM, "-showvalues", "showValues", "ShowValues", - "no", Tk_Offset(BarPen, valueShow), - ALL_PENS | BLT_CONFIG_DONT_SET_DEFAULT, &fillOption}, - {BLT_CONFIG_BITMAP, "-stipple", "stipple", "Stipple", "", - Tk_Offset(BarPen, stipple), ALL_PENS | BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_STRING, "-type", (char *)NULL, (char *)NULL, "bar", - Tk_Offset(BarPen, typeId), ALL_PENS | BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_ANCHOR, "-valueanchor", "valueAnchor", "ValueAnchor", - "s", Tk_Offset(BarPen, valueStyle.anchor), - ALL_PENS}, - {BLT_CONFIG_COLOR, "-valuecolor", "valueColor", "ValueColor", - "black", Tk_Offset(BarPen, valueStyle.color), - ALL_PENS}, - {BLT_CONFIG_FONT, "-valuefont", "valueFont", "ValueFont", - STD_FONT_SMALL, Tk_Offset(BarPen, valueStyle.font), - ALL_PENS}, - {BLT_CONFIG_STRING, "-valueformat", "valueFormat", "ValueFormat", - "%g", Tk_Offset(BarPen, valueFormat), - ALL_PENS | BLT_CONFIG_NULL_OK}, - {BLT_CONFIG_DOUBLE, "-valuerotate", "valueRotate", "ValueRotate", - (char *)NULL, Tk_Offset(BarPen, valueStyle.angle), ALL_PENS}, - {BLT_CONFIG_END, NULL, NULL, NULL, NULL, 0, 0} -}; -*/ +// Create -/* Forward declarations */ -static PenConfigureProc ConfigureBarPenProc; -static PenDestroyProc DestroyBarPenProc; -static ElementClosestProc ClosestBarProc; -static ElementConfigProc ConfigureBarProc; -static ElementDestroyProc DestroyBarProc; -static ElementDrawProc DrawActiveBarProc; -static ElementDrawProc DrawNormalBarProc; -static ElementDrawSymbolProc DrawSymbolProc; -static ElementExtentsProc GetBarExtentsProc; -static ElementToPostScriptProc ActiveBarToPostScriptProc; -static ElementToPostScriptProc NormalBarToPostScriptProc; -static ElementSymbolToPostScriptProc SymbolToPostScriptProc; -static ElementMapProc MapBarProc; +Element* Blt_BarElement(Graph* graphPtr, const char* name, ClassId classId) +{ + BarElement *elemPtr = calloc(1, sizeof(BarElement)); + elemPtr->procsPtr = &barProcs; + elemPtr->legendRelief = TK_RELIEF_FLAT; + Blt_GraphSetObjectClass(&elemPtr->obj, classId); + elemPtr->obj.name = Blt_Strdup(name); + elemPtr->obj.graphPtr = graphPtr; + /* By default, an element's name and label are the same. */ + elemPtr->label = Blt_Strdup(name); + elemPtr->builtinPenPtr = &elemPtr->builtinPen; + InitBarPen(graphPtr, elemPtr->builtinPenPtr); + elemPtr->stylePalette = Blt_Chain_Create(); -static void ResetStylePalette(Blt_Chain stylePalette) + elemPtr->optionTable = + Tk_CreateOptionTable(graphPtr->interp, barElemOptionSpecs); + Tk_InitOptions(graphPtr->interp, (char*)elemPtr, elemPtr->optionTable, + graphPtr->tkwin); + + return (Element *)elemPtr; +} + +Pen* Blt_BarPen(Graph* graphPtr, const char *penName) +{ + BarPen* penPtr = calloc(1, sizeof(BarPen)); + InitBarPen(graphPtr, penPtr); + penPtr->name = Blt_Strdup(penName); + if (strcmp(penName, "activeBar") == 0) + penPtr->flags = ACTIVE_PEN; + + return (Pen*)penPtr; +} + +static void InitBarPen(Graph* graphPtr, BarPen* penPtr) { + /* Generic fields common to all pen types. */ + penPtr->configProc = ConfigurePenProc; + penPtr->destroyProc = DestroyPenProc; + penPtr->flags = NORMAL_PEN; + /* Initialize fields specific to bar pens. */ + Blt_Ts_InitStyle(penPtr->valueStyle); + penPtr->relief = TK_RELIEF_RAISED; + penPtr->valueShow = SHOW_NONE; + penPtr->borderWidth = 2; + penPtr->errorBarShow = SHOW_BOTH; + + penPtr->optionTable = + Tk_CreateOptionTable(graphPtr->interp, barPenOptionSpecs); + Tk_InitOptions(graphPtr->interp, (char*)penPtr, penPtr->optionTable, + graphPtr->tkwin); +} + +static void DestroyBarProc(Graph* graphPtr, Element* basePtr) +{ + BarElement* elemPtr = (BarElement*)basePtr; + Tk_FreeConfigOptions((char*)elemPtr, elemPtr->optionTable, graphPtr->tkwin); + Tk_DeleteOptionTable(elemPtr->optionTable); + + DestroyPenProc(graphPtr, (Pen*)&elemPtr->builtinPen); + if (elemPtr->activePenPtr != NULL) + Blt_FreePen((Pen *)elemPtr->activePenPtr); + if (elemPtr->normalPenPtr != NULL) + Blt_FreePen((Pen *)elemPtr->normalPenPtr); + + ResetBar(elemPtr); + if (elemPtr->stylePalette != NULL) { + Blt_FreeStylePalette(elemPtr->stylePalette); + Blt_Chain_Destroy(elemPtr->stylePalette); + } + if (elemPtr->activeIndices != NULL) { + free(elemPtr->activeIndices); + } +} + +static void DestroyPenProc(Graph* graphPtr, Pen* basePtr) +{ + BarPen* penPtr = (BarPen*)basePtr; + Tk_FreeConfigOptions((char*)penPtr, penPtr->optionTable, graphPtr->tkwin); + Tk_DeleteOptionTable(penPtr->optionTable); + + Blt_Ts_FreeStyle(graphPtr->display, &penPtr->valueStyle); + if (penPtr->outlineGC != NULL) { + Tk_FreeGC(graphPtr->display, penPtr->outlineGC); + } + if (penPtr->fillGC != NULL) { + Tk_FreeGC(graphPtr->display, penPtr->fillGC); + } + if (penPtr->errorBarGC != NULL) { + Tk_FreeGC(graphPtr->display, penPtr->errorBarGC); + } +} + +// Configure + +static int ConfigureBarProc(Graph *graphPtr, Element *basePtr) +{ + BarElement *elemPtr = (BarElement *)basePtr; Blt_ChainLink link; + BarStyle *stylePtr; - for (link = Blt_Chain_FirstLink(stylePalette); link != NULL; - link = Blt_Chain_NextLink(link)) { - BarStyle *stylePtr; + if (ConfigurePenProc(graphPtr, (Pen*)&elemPtr->builtinPen)!= TCL_OK) { + return TCL_ERROR; + } + /* + * Point to the static normal pen if no external pens have been selected. + */ + link = Blt_Chain_FirstLink(elemPtr->stylePalette); + if (link == NULL) { + link = Blt_Chain_AllocLink(sizeof(BarStyle)); + Blt_Chain_LinkAfter(elemPtr->stylePalette, link, NULL); + } + stylePtr = Blt_Chain_GetValue(link); + stylePtr->penPtr = NORMALPEN(elemPtr); - stylePtr = Blt_Chain_GetValue(link); - stylePtr->xeb.length = stylePtr->yeb.length = 0; - stylePtr->nBars = 0; + /* + if (Blt_ConfigModified(elemPtr->configSpecs, "-barwidth", "-*data", + "-map*", "-label", "-hide", "-x", "-y", (char *)NULL)) { + elemPtr->flags |= MAP_ITEM; } + */ + return TCL_OK; } -static int ConfigureBarPen(Graph *graphPtr, BarPen *penPtr) +static int ConfigurePenProc(Graph *graphPtr, Pen *basePtr) { + BarPen* penPtr = (BarPen*)basePtr; XGCValues gcValues; unsigned long gcMask; GC newGC; @@ -614,87 +562,30 @@ static int ConfigureBarPen(Graph *graphPtr, BarPen *penPtr) return TCL_OK; } -static void DestroyBarPen(Graph* graphPtr, BarPen* penPtr) -{ - Tk_FreeConfigOptions((char*)penPtr, penPtr->optionTable, graphPtr->tkwin); - Tk_DeleteOptionTable(penPtr->optionTable); +// Support - Blt_Ts_FreeStyle(graphPtr->display, &penPtr->valueStyle); - if (penPtr->outlineGC != NULL) { - Tk_FreeGC(graphPtr->display, penPtr->outlineGC); - } - if (penPtr->fillGC != NULL) { - Tk_FreeGC(graphPtr->display, penPtr->fillGC); - } - if (penPtr->errorBarGC != NULL) { - Tk_FreeGC(graphPtr->display, penPtr->errorBarGC); - } -} - -static int ConfigureBarPenProc(Graph *graphPtr, Pen *basePtr) -{ - return ConfigureBarPen(graphPtr, (BarPen *)basePtr); -} - -static void DestroyBarPenProc(Graph *graphPtr, Pen *basePtr) -{ - DestroyBarPen(graphPtr, (BarPen *)basePtr); -} - -static void InitBarPen(Graph* graphPtr, BarPen* penPtr) +static void ResetStylePalette(Blt_Chain stylePalette) { - /* Generic fields common to all pen types. */ - penPtr->configProc = ConfigureBarPenProc; - penPtr->destroyProc = DestroyBarPenProc; - penPtr->flags = NORMAL_PEN; - penPtr->optionTable = - Tk_CreateOptionTable(graphPtr->interp, barPenOptionSpecs); + Blt_ChainLink link; - /* Initialize fields specific to bar pens. */ - Blt_Ts_InitStyle(penPtr->valueStyle); - penPtr->relief = TK_RELIEF_RAISED; - penPtr->valueShow = SHOW_NONE; - penPtr->borderWidth = 2; - penPtr->errorBarShow = SHOW_BOTH; -} + for (link = Blt_Chain_FirstLink(stylePalette); link != NULL; + link = Blt_Chain_NextLink(link)) { + BarStyle *stylePtr; -Pen* Blt_BarPen(Graph* graphPtr, const char *penName) -{ - BarPen *penPtr = calloc(1, sizeof(BarPen)); - InitBarPen(graphPtr, penPtr); - penPtr->name = Blt_Strdup(penName); - if (strcmp(penName, "activeBar") == 0) { - penPtr->flags = ACTIVE_PEN; + stylePtr = Blt_Chain_GetValue(link); + stylePtr->xeb.length = stylePtr->yeb.length = 0; + stylePtr->nBars = 0; } - return (Pen *)penPtr; } -/* - *--------------------------------------------------------------------------- - * - * CheckBarStacks -- - * - * Check that the data limits are not superseded by the heights of - * stacked bar segments. The heights are calculated by - * Blt_ComputeStacks. - * - * Results: - * If the y-axis limits need to be adjusted for stacked segments, - * *minPtr* or *maxPtr* are updated. - * - * Side effects: - * Autoscaling of the y-axis is affected. - * - *--------------------------------------------------------------------------- - */ static void CheckBarStacks(Graph *graphPtr, Axis2d *pairPtr, double *minPtr, double *maxPtr) { BarGroup *gp, *gend; - if ((graphPtr->mode != BARS_STACKED) || (graphPtr->nBarGroups == 0)) { + if ((graphPtr->mode != BARS_STACKED) || (graphPtr->nBarGroups == 0)) return; - } + for (gp = graphPtr->barGroups, gend = gp + graphPtr->nBarGroups; gp < gend; gp++) { if ((gp->axes.x == pairPtr->x) && (gp->axes.y == pairPtr->y)) { @@ -715,55 +606,6 @@ static void CheckBarStacks(Graph *graphPtr, Axis2d *pairPtr, } } -/* - *--------------------------------------------------------------------------- - * - * ConfigureBarProc -- - * - * Sets up the appropriate configuration parameters in the GC. It is - * assumed the parameters have been previously set by a call to - * Blt_ConfigureWidget. - * - * Results: - * The return value is a standard TCL result. If TCL_ERROR is returned, - * then interp->result contains an error message. - * - * Side effects: - * Configuration information such as bar foreground/background color and - * stipple etc. get set in a new GC. - * - *--------------------------------------------------------------------------- - */ - -static int ConfigureBarProc(Graph *graphPtr, Element *basePtr) -{ - BarElement *elemPtr = (BarElement *)basePtr; - Blt_ChainLink link; - BarStyle *stylePtr; - - if (ConfigureBarPen(graphPtr, elemPtr->builtinPenPtr)!= TCL_OK) { - return TCL_ERROR; - } - /* - * Point to the static normal pen if no external pens have been selected. - */ - link = Blt_Chain_FirstLink(elemPtr->stylePalette); - if (link == NULL) { - link = Blt_Chain_AllocLink(sizeof(BarStyle)); - Blt_Chain_LinkAfter(elemPtr->stylePalette, link, NULL); - } - stylePtr = Blt_Chain_GetValue(link); - stylePtr->penPtr = NORMALPEN(elemPtr); - - /* - if (Blt_ConfigModified(elemPtr->configSpecs, "-barwidth", "-*data", - "-map*", "-label", "-hide", "-x", "-y", (char *)NULL)) { - elemPtr->flags |= MAP_ITEM; - } - */ - return TCL_OK; -} - static void GetBarExtentsProc(Element *basePtr, Region2d *regPtr) { BarElement *elemPtr = (BarElement *)basePtr; @@ -906,28 +748,8 @@ static void GetBarExtentsProc(Element *basePtr, Region2d *regPtr) } } -/* - *--------------------------------------------------------------------------- - * - * ClosestBar -- - * - * Find the bar segment closest to the window coordinates point - * specified. - * - * Note: This does not return the height of the stacked segment - * (in graph coordinates) properly. - * - * Results: - * Returns 1 if the point is width any bar segment, otherwise 0. - * - *--------------------------------------------------------------------------- - */ - -static void ClosestBarProc( - Graph *graphPtr, /* Not used. */ - Element *basePtr, /* Bar element */ - ClosestSearch *searchPtr) /* Information about closest point in - * element */ +static void ClosestBarProc(Graph *graphPtr, Element *basePtr, + ClosestSearch *searchPtr) { BarElement *elemPtr = (BarElement *)basePtr; XRectangle *bp; @@ -987,23 +809,6 @@ static void ClosestBarProc( } } -/* - *--------------------------------------------------------------------------- - * - * MergePens -- - * - * Reorders the both arrays of points and errorbars to merge pens. - * - * Results: - * None. - * - * Side effects: - * The old arrays are freed and new ones allocated containing - * the reordered points and errorbars. - * - *--------------------------------------------------------------------------- - */ - static void MergePens(BarElement *elemPtr, BarStyle **dataToStyle) { if (Blt_Chain_GetLength(elemPtr->stylePalette) < 2) { @@ -1122,22 +927,6 @@ static void MergePens(BarElement *elemPtr, BarStyle **dataToStyle) } } -/* - *--------------------------------------------------------------------------- - * - * MapActiveBars -- - * - * Creates an array of points of the active graph coordinates. - * - * Results: - * None. - * - * Side effects: - * Memory is freed and allocated for the active point array. - * - *--------------------------------------------------------------------------- - */ - static void MapActiveBars(BarElement *elemPtr) { if (elemPtr->activeRects != NULL) { @@ -1216,22 +1005,6 @@ static void ResetBar(BarElement *elemPtr) elemPtr->nBars = 0; } -/* - *--------------------------------------------------------------------------- - * - * Blt_MapErrorBars -- - * - * Creates two arrays of points and pen indices, filled with the screen - * coordinates of the visible - * - * Results: - * None. - * - * Side effects: - * Memory is freed and allocated for the index array. - * - *--------------------------------------------------------------------------- - */ static void MapErrorBars(Graph *graphPtr, BarElement *elemPtr, BarStyle **dataToStyle) { @@ -1370,30 +1143,6 @@ static void MapErrorBars(Graph *graphPtr, BarElement *elemPtr, } } - -/* - *--------------------------------------------------------------------------- - * - * MapBarProc -- - * - * Calculates the actual window coordinates of the bar element. The - * window coordinates are saved in the bar element structure. - * - * Results: - * None. - * - * Notes: - * A bar can have multiple segments (more than one x,y pairs). In this - * case, the bar can be represented as either a set of non-contiguous - * bars or a single multi-segmented (stacked) bar. - * - * The x-axis layout for a barchart may be presented in one of two ways. - * If abscissas are used, the bars are placed at those coordinates. - * Otherwise, the range will represent the number of values. - * - *--------------------------------------------------------------------------- - */ - static void MapBarProc(Graph *graphPtr, Element *basePtr) { BarElement *elemPtr = (BarElement *)basePtr; @@ -1627,23 +1376,6 @@ static void MapBarProc(Graph *graphPtr, Element *basePtr) free(dataToStyle); } -/* - *--------------------------------------------------------------------------- - * - * DrawSymbolProc -- - * - * Draw a symbol centered at the given x,y window coordinate based upon - * the element symbol type and size. - * - * Results: - * None. - * - * Problems: - * Most notable is the round-off errors generated when calculating the - * centered position of the symbol. - *--------------------------------------------------------------------------- - */ - static void DrawSymbolProc(Graph *graphPtr, Drawable drawable, Element *basePtr, int x, int y, int size) { @@ -1706,19 +1438,6 @@ static void UnsetBackgroundClipRegion(Tk_Window tkwin, Tk_3DBorder border) XSetClipMask(display, gc, None); } -/* - *--------------------------------------------------------------------------- - * - * DrawBarSegments -- - * - * Draws each of the rectangular segments for the element. - * - * Results: - * None. - * - *--------------------------------------------------------------------------- - */ - static void DrawBarSegments(Graph *graphPtr, Drawable drawable, BarPen *penPtr, XRectangle *bars, int nBars) { @@ -1779,18 +1498,6 @@ static void DrawBarSegments(Graph *graphPtr, Drawable drawable, BarPen *penPtr, TkDestroyRegion(rgn); } -/* - *--------------------------------------------------------------------------- - * - * DrawBarValues -- - * - * Draws the numeric value of the bar. - * - * Results: - * None. - * - *--------------------------------------------------------------------------- - */ static void DrawBarValues(Graph *graphPtr, Drawable drawable, BarElement *elemPtr, BarPen *penPtr, XRectangle *bars, int nBars, @@ -1841,28 +1548,6 @@ static void DrawBarValues(Graph *graphPtr, Drawable drawable, } } - -/* - *--------------------------------------------------------------------------- - * - * DrawNormalBar -- - * - * Draws the rectangle representing the bar element. If the relief - * option is set to "raised" or "sunken" and the bar borderwidth is set - * (borderwidth > 0), a 3D border is drawn around the bar. - * - * Don't draw bars that aren't visible (i.e. within the limits of the - * axis). - * - * Results: - * None. - * - * Side effects: - * X drawing commands are output. - * - *--------------------------------------------------------------------------- - */ - static void DrawNormalBarProc(Graph *graphPtr, Drawable drawable, Element *basePtr) { @@ -1899,24 +1584,6 @@ static void DrawNormalBarProc(Graph *graphPtr, Drawable drawable, } } -/* - *--------------------------------------------------------------------------- - * - * DrawActiveBar -- - * - * Draws bars representing the active segments of the bar element. If - * the -relief option is set (other than "flat") and the borderwidth is - * greater than 0, a 3D border is drawn around the each bar segment. - * - * Results: - * None. - * - * Side effects: - * X drawing commands are output. - * - *--------------------------------------------------------------------------- - */ - static void DrawActiveBarProc(Graph *graphPtr, Drawable drawable, Element *basePtr) { @@ -1947,30 +1614,8 @@ static void DrawActiveBarProc(Graph *graphPtr, Drawable drawable, } } -/* - *--------------------------------------------------------------------------- - * - * SymbolToPostScript -- - * - * Draw a symbol centered at the given x,y window coordinate based upon - * the element symbol type and size. - * - * Results: - * None. - * - * Problems: - * Most notable is the round-off errors generated when calculating the - * centered position of the symbol. - * - *--------------------------------------------------------------------------- - */ - -static void SymbolToPostScriptProc( - Graph *graphPtr, - Blt_Ps ps, - Element *basePtr, - double x, double y, - int size) +static void SymbolToPostScriptProc(Graph *graphPtr, Blt_Ps ps, Element *basePtr, + double x, double y, int size) { BarElement *elemPtr = (BarElement *)basePtr; BarPen *penPtr; @@ -2006,9 +1651,8 @@ static void SymbolToPostScriptProc( Blt_Ps_Format(ps, "%g %g %d Sq\n", x, y, size); } -static void -SegmentsToPostScript(Graph *graphPtr, Blt_Ps ps, BarPen *penPtr, - XRectangle *bars, int nBars) +static void SegmentsToPostScript(Graph *graphPtr, Blt_Ps ps, BarPen *penPtr, + XRectangle *bars, int nBars) { XRectangle *rp, *rend; @@ -2038,8 +1682,8 @@ SegmentsToPostScript(Graph *graphPtr, Blt_Ps ps, BarPen *penPtr, } if ((penPtr->fill != NULL) && (penPtr->borderWidth > 0) && (penPtr->relief != TK_RELIEF_FLAT)) { - Blt_Ps_Draw3DRectangle(ps, penPtr->fill, - (double)rp->x, (double)rp->y, (int)rp->width, (int)rp->height, + Blt_Ps_Draw3DRectangle(ps, penPtr->fill, (double)rp->x, (double)rp->y, + (int)rp->width, (int)rp->height, penPtr->borderWidth, penPtr->relief); } } @@ -2093,24 +1737,6 @@ static void BarValuesToPostScript(Graph *graphPtr, Blt_Ps ps, } } -/* - *--------------------------------------------------------------------------- - * - * ActiveBarToPostScript -- - * - * Similar to the NormalBarToPostScript procedure, generates PostScript - * commands to display the bars representing the active bar segments of - * the element. - * - * Results: - * None. - * - * Side effects: - * PostScript pen width, dashes, and color settings are changed. - * - *--------------------------------------------------------------------------- - */ - static void ActiveBarToPostScriptProc(Graph *graphPtr, Blt_Ps ps, Element *basePtr) { @@ -2185,61 +1811,6 @@ static void NormalBarToPostScriptProc(Graph *graphPtr, Blt_Ps ps, } } -static void DestroyBarProc(Graph* graphPtr, Element* basePtr) -{ - BarElement* elemPtr = (BarElement*)basePtr; - Tk_FreeConfigOptions((char*)elemPtr, elemPtr->optionTable, graphPtr->tkwin); - Tk_DeleteOptionTable(elemPtr->optionTable); - - DestroyBarPen(graphPtr, elemPtr->builtinPenPtr); - if (elemPtr->activePenPtr != NULL) - Blt_FreePen((Pen *)elemPtr->activePenPtr); - if (elemPtr->normalPenPtr != NULL) - Blt_FreePen((Pen *)elemPtr->normalPenPtr); - - ResetBar(elemPtr); - if (elemPtr->stylePalette != NULL) { - Blt_FreeStylePalette(elemPtr->stylePalette); - Blt_Chain_Destroy(elemPtr->stylePalette); - } - if (elemPtr->activeIndices != NULL) { - free(elemPtr->activeIndices); - } -} - -static ElementProcs barProcs = { - ClosestBarProc, - ConfigureBarProc, - DestroyBarProc, - DrawActiveBarProc, - DrawNormalBarProc, - DrawSymbolProc, - GetBarExtentsProc, - ActiveBarToPostScriptProc, - NormalBarToPostScriptProc, - SymbolToPostScriptProc, - MapBarProc, -}; - -Element* Blt_BarElement(Graph* graphPtr, const char* name, ClassId classId) -{ - BarElement *elemPtr = calloc(1, sizeof(BarElement)); - elemPtr->procsPtr = &barProcs; - elemPtr->optionTable = - Tk_CreateOptionTable(graphPtr->interp, barElemOptionSpecs); - elemPtr->legendRelief = TK_RELIEF_FLAT; - Blt_GraphSetObjectClass(&elemPtr->obj, classId); - elemPtr->obj.name = Blt_Strdup(name); - elemPtr->obj.graphPtr = graphPtr; - /* By default, an element's name and label are the same. */ - elemPtr->label = Blt_Strdup(name); - elemPtr->builtinPenPtr = &elemPtr->builtinPen; - InitBarPen(graphPtr, elemPtr->builtinPenPtr); - elemPtr->stylePalette = Blt_Chain_Create(); - - return (Element *)elemPtr; -} - void Blt_InitBarSetTable(Graph *graphPtr) { Blt_ChainLink link; diff --git a/src/bltGrElemLine.C b/src/bltGrElemLine.C index 50b47d2..4032f37 100644 --- a/src/bltGrElemLine.C +++ b/src/bltGrElemLine.C @@ -832,9 +832,9 @@ static int ConfigureLineProc(Graph *graphPtr, Element *basePtr) return TCL_OK; } -static int ConfigurePenProc(Graph* graphPtr, Pen* penPtr) +static int ConfigurePenProc(Graph* graphPtr, Pen* basePtr) { - LinePen* lpPtr = (LinePen*)penPtr; + LinePen* lpPtr = (LinePen*)basePtr; unsigned long gcMask; GC newGC; XGCValues gcValues; diff --git a/src/bltGrElemOp.C b/src/bltGrElemOp.C index 5e954ad..73bad98 100644 --- a/src/bltGrElemOp.C +++ b/src/bltGrElemOp.C @@ -45,28 +45,31 @@ /* Ignore elements that aren't in the display list or have been deleted. */ #define IGNORE_ELEMENT(e) (((e)->link == NULL) || ((e)->flags & DELETE_PENDING)) -static int ParseValues(Tcl_Interp *interp, Tcl_Obj *objPtr, int *nValuesPtr, - double **arrayPtr); +// Defs + +static void DestroyElement(Element *elemPtr); +static int ElementObjConfigure(Tcl_Interp *interp, Graph* graphPtr, + Element* elemPtr, + int objc, Tcl_Obj* const objv[]); static void FreeDataValues(ElemValues *valuesPtr); +static void FreeElement(char* data); static void FindRange(ElemValues *valuesPtr); +static int GetIndex(Tcl_Interp *interp, Element *elemPtr, + Tcl_Obj *objPtr, int *indexPtr); static int GetPenStyleFromObj(Tcl_Interp *interp, Graph *graphPtr, Tcl_Obj *objPtr, ClassId classId, PenStyle *stylePtr); static int GetVectorData(Tcl_Interp *interp, ElemValues *valuesPtr, const char *vecName); -static void DestroyElement(Element *elemPtr); -static int ElementObjConfigure(Tcl_Interp *interp, Graph* graphPtr, - Element* elemPtr, - int objc, Tcl_Obj* const objv[]); +static int ParseValues(Tcl_Interp *interp, Tcl_Obj *objPtr, int *nValuesPtr, + double **arrayPtr); typedef int (GraphElementProc)(Graph *graphPtr, Tcl_Interp *interp, int objc, Tcl_Obj *const *objv); // OptionSpecs -// Fill char* fillObjOption[] = {"none", "x", "y", "both", NULL}; -// Values static Tk_CustomOptionSetProc ValuesSetProc; static Tk_CustomOptionGetProc ValuesGetProc; Tk_ObjCustomOption valuesObjOption = @@ -146,7 +149,6 @@ static Tcl_Obj* ValuesGetProc(ClientData clientData, Tk_Window tkwin, } } -// Pairs static Tk_CustomOptionSetProc PairsSetProc; static Tk_CustomOptionGetProc PairsGetProc; Tk_ObjCustomOption pairsObjOption = @@ -212,7 +214,6 @@ static Tcl_Obj* PairsGetProc(ClientData clientData, Tk_Window tkwin, return listObjPtr; }; -// Style int StyleSetProc(ClientData clientData, Tcl_Interp *interp, Tk_Window tkwin, Tcl_Obj** objPtr, char* widgRec, int offset, char* save, int flags) @@ -281,31 +282,29 @@ Tcl_Obj* StyleGetProc(ClientData clientData, Tk_Window tkwin, return listObjPtr; } -// Configure - -static Blt_VectorChangedProc VectorChangedProc; +// Create static int CreateElement(Graph *graphPtr, Tcl_Interp *interp, int objc, Tcl_Obj *const *objv, ClassId classId) { - Element *elemPtr; - Tcl_HashEntry *hPtr; - int isNew; - char *string; - - string = Tcl_GetString(objv[3]); + char *string = Tcl_GetString(objv[3]); if (string[0] == '-') { Tcl_AppendResult(graphPtr->interp, "name of element \"", string, "\" can't start with a '-'", (char *)NULL); return TCL_ERROR; } - hPtr = Tcl_CreateHashEntry(&graphPtr->elements.table, string, &isNew); + + int isNew; + Tcl_HashEntry* hPtr = + Tcl_CreateHashEntry(&graphPtr->elements.table, string, &isNew); if (!isNew) { Tcl_AppendResult(interp, "element \"", string, "\" already exists in \"", Tcl_GetString(objv[0]), "\"", (char *)NULL); return TCL_ERROR; } + + Element *elemPtr; switch (classId) { case CID_ELEM_BAR: elemPtr = Blt_BarElement(graphPtr, string, classId); @@ -319,23 +318,59 @@ static int CreateElement(Graph *graphPtr, Tcl_Interp *interp, int objc, if (!elemPtr) return TCL_ERROR; - elemPtr->hashPtr = hPtr; - Tcl_SetHashValue(hPtr, elemPtr); - - if ((Tk_InitOptions(graphPtr->interp, (char*)elemPtr, elemPtr->optionTable, graphPtr->tkwin) != TCL_OK) || (ElementObjConfigure(interp, graphPtr, elemPtr, objc-4, objv+4) != TCL_OK)) { + if (ElementObjConfigure(interp,graphPtr, elemPtr, objc-4, objv+4) != TCL_OK) { DestroyElement(elemPtr); return TCL_ERROR; } + elemPtr->hashPtr = hPtr; + Tcl_SetHashValue(hPtr, elemPtr); + elemPtr->link = Blt_Chain_Append(graphPtr->elements.displayList, elemPtr); - graphPtr->flags |= CACHE_DIRTY; - Blt_EventuallyRedrawGraph(graphPtr); elemPtr->flags |= MAP_ITEM; + graphPtr->flags |= CACHE_DIRTY; graphPtr->flags |= RESET_AXES; + Blt_EventuallyRedrawGraph(graphPtr); + Tcl_SetObjResult(interp, objv[3]); return TCL_OK; } +static void DestroyElement(Element *elemPtr) +{ + Graph *graphPtr = elemPtr->obj.graphPtr; + + Blt_DeleteBindings(graphPtr->bindTable, elemPtr); + Blt_Legend_RemoveElement(graphPtr, elemPtr); + + FreeDataValues(&elemPtr->x); + FreeDataValues(&elemPtr->y); + + (*elemPtr->procsPtr->destroyProc) (graphPtr, elemPtr); + + /* Remove it also from the element display list */ + if (elemPtr->link) { + Blt_Chain_DeleteLink(graphPtr->elements.displayList, elemPtr->link); + if (!IGNORE_ELEMENT(elemPtr)) { + graphPtr->flags |= RESET_WORLD; + Blt_EventuallyRedrawGraph(graphPtr); + } + } + /* Remove the element for the graph's hash table of elements */ + if (elemPtr->hashPtr) + Tcl_DeleteHashEntry(elemPtr->hashPtr); + + if (elemPtr->obj.name) + free((void*)(elemPtr->obj.name)); + + if (elemPtr->label) + free((void*)(elemPtr->label)); + + free(elemPtr); +} + +// Configure + static int CgetOp(Graph* graphPtr, Tcl_Interp* interp, int objc, Tcl_Obj* const objv[]) { @@ -422,537 +457,6 @@ static int ElementObjConfigure(Tcl_Interp *interp, Graph* graphPtr, } } -// Support - -static int GetPenStyleFromObj(Tcl_Interp *interp, Graph *graphPtr, - Tcl_Obj *objPtr, ClassId classId, - PenStyle *stylePtr) -{ - Pen *penPtr; - Tcl_Obj **objv; - int objc; - - if (Tcl_ListObjGetElements(interp, objPtr, &objc, &objv) != TCL_OK) { - return TCL_ERROR; - } - if ((objc != 1) && (objc != 3)) { - if (interp != NULL) { - Tcl_AppendResult(interp, "bad style entry \"", - Tcl_GetString(objPtr), - "\": should be \"penName\" or \"penName min max\"", - (char *)NULL); - } - return TCL_ERROR; - } - if (Blt_GetPenFromObj(interp, graphPtr, objv[0], classId, &penPtr) - != TCL_OK) { - return TCL_ERROR; - } - if (objc == 3) { - double min, max; - - if ((Tcl_GetDoubleFromObj(interp, objv[1], &min) != TCL_OK) || - (Tcl_GetDoubleFromObj(interp, objv[2], &max) != TCL_OK)) { - return TCL_ERROR; - } - SetWeight(stylePtr->weight, min, max); - } - stylePtr->penPtr = penPtr; - return TCL_OK; -} - -static void FreeVectorSource(ElemValues *valuesPtr) -{ - if (valuesPtr->vectorSource.vector != NULL) { - Blt_SetVectorChangedProc(valuesPtr->vectorSource.vector, NULL, NULL); - Blt_FreeVectorId(valuesPtr->vectorSource.vector); - valuesPtr->vectorSource.vector = NULL; - } -} - -static int FetchVectorValues(Tcl_Interp *interp, ElemValues *valuesPtr, - Blt_Vector *vector) -{ - double *array; - - if (valuesPtr->values == NULL) { - array = malloc(Blt_VecLength(vector) * sizeof(double)); - } else { - array = realloc(valuesPtr->values, - Blt_VecLength(vector) * sizeof(double)); - } - if (array == NULL) { - if (interp != NULL) { - Tcl_AppendResult(interp, "can't allocate new vector", (char *)NULL); - } - return TCL_ERROR; - } - memcpy(array, Blt_VecData(vector), sizeof(double) * Blt_VecLength(vector)); - valuesPtr->min = Blt_VecMin(vector); - valuesPtr->max = Blt_VecMax(vector); - valuesPtr->values = array; - valuesPtr->nValues = Blt_VecLength(vector); - /* FindRange(valuesPtr); */ - return TCL_OK; -} - -static void VectorChangedProc(Tcl_Interp *interp, ClientData clientData, - Blt_VectorNotify notify) -{ - ElemValues *valuesPtr = clientData; - - if (notify == BLT_VECTOR_NOTIFY_DESTROY) { - FreeDataValues(valuesPtr); - } else { - Blt_Vector *vector; - - Blt_GetVectorById(interp, valuesPtr->vectorSource.vector, &vector); - if (FetchVectorValues(NULL, valuesPtr, vector) != TCL_OK) { - return; - } - } - { - Element *elemPtr = valuesPtr->elemPtr; - Graph *graphPtr; - - graphPtr = elemPtr->obj.graphPtr; - graphPtr->flags |= RESET_AXES; - elemPtr->flags |= MAP_ITEM; - if (!IGNORE_ELEMENT(elemPtr)) { - graphPtr->flags |= CACHE_DIRTY; - Blt_EventuallyRedrawGraph(graphPtr); - } - } -} - -static int GetVectorData(Tcl_Interp *interp, ElemValues *valuesPtr, - const char *vecName) -{ - Blt_Vector *vecPtr; - VectorDataSource *srcPtr; - - srcPtr = &valuesPtr->vectorSource; - srcPtr->vector = Blt_AllocVectorId(interp, vecName); - if (Blt_GetVectorById(interp, srcPtr->vector, &vecPtr) != TCL_OK) { - return TCL_ERROR; - } - if (FetchVectorValues(interp, valuesPtr, vecPtr) != TCL_OK) { - FreeVectorSource(valuesPtr); - return TCL_ERROR; - } - Blt_SetVectorChangedProc(srcPtr->vector, VectorChangedProc, valuesPtr); - valuesPtr->type = ELEM_SOURCE_VECTOR; - return TCL_OK; -} - -static int ParseValues(Tcl_Interp *interp, Tcl_Obj *objPtr, int *nValuesPtr, - double **arrayPtr) -{ - int objc; - Tcl_Obj **objv; - - if (Tcl_ListObjGetElements(interp, objPtr, &objc, &objv) != TCL_OK) { - return TCL_ERROR; - } - *arrayPtr = NULL; - *nValuesPtr = 0; - if (objc > 0) { - double *array; - double *p; - int i; - - array = malloc(sizeof(double) * objc); - if (array == NULL) { - Tcl_AppendResult(interp, "can't allocate new vector", (char *)NULL); - return TCL_ERROR; - } - for (p = array, i = 0; i < objc; i++, p++) { - if (Blt_ExprDoubleFromObj(interp, objv[i], p) != TCL_OK) { - free(array); - return TCL_ERROR; - } - } - *arrayPtr = array; - *nValuesPtr = objc; - } - return TCL_OK; -} - -static void FreeDataValues(ElemValues *valuesPtr) -{ - switch (valuesPtr->type) { - case ELEM_SOURCE_VECTOR: - FreeVectorSource(valuesPtr); - break; - case ELEM_SOURCE_VALUES: - break; - } - if (valuesPtr->values != NULL) { - free(valuesPtr->values); - } - valuesPtr->values = NULL; - valuesPtr->nValues = 0; - valuesPtr->type = ELEM_SOURCE_VALUES; -} - -static void FindRange(ElemValues *valuesPtr) -{ - int i; - double *x; - double min, max; - - if ((valuesPtr->nValues < 1) || (valuesPtr->values == NULL)) { - return; /* This shouldn't ever happen. */ - } - x = valuesPtr->values; - - min = DBL_MAX, max = -DBL_MAX; - for(i = 0; i < valuesPtr->nValues; i++) { - if (isfinite(x[i])) { - min = max = x[i]; - break; - } - } - /* Initialize values to track the vector range */ - for (/* empty */; i < valuesPtr->nValues; i++) { - if (isfinite(x[i])) { - if (x[i] < min) { - min = x[i]; - } else if (x[i] > max) { - max = x[i]; - } - } - } - valuesPtr->min = min, valuesPtr->max = max; -} - -double Blt_FindElemValuesMinimum(ElemValues *valuesPtr, double minLimit) -{ - int i; - double min; - - min = DBL_MAX; - for (i = 0; i < valuesPtr->nValues; i++) { - double x; - - x = valuesPtr->values[i]; - if (x < 0.0) { - /* What do you do about negative values when using log - * scale values seems like a grey area. Mirror. */ - x = -x; - } - if ((x > minLimit) && (min > x)) { - min = x; - } - } - if (min == DBL_MAX) { - min = minLimit; - } - return min; -} - -void Blt_FreeStylePalette(Blt_Chain stylePalette) -{ - Blt_ChainLink link; - - /* Skip the first slot. It contains the built-in "normal" pen of - * the element. */ - link = Blt_Chain_FirstLink(stylePalette); - if (link != NULL) { - Blt_ChainLink next; - - for (link = Blt_Chain_NextLink(link); link != NULL; link = next) { - PenStyle *stylePtr; - - next = Blt_Chain_NextLink(link); - stylePtr = Blt_Chain_GetValue(link); - Blt_FreePen(stylePtr->penPtr); - Blt_Chain_DeleteLink(stylePalette, link); - } - } -} - -PenStyle **Blt_StyleMap(Element *elemPtr) -{ - int i; - int nWeights; /* Number of weights to be examined. - * If there are more data points than - * weights, they will default to the - * normal pen. */ - - PenStyle **dataToStyle; /* Directory of styles. Each array - * element represents the style for - * the data point at that index */ - Blt_ChainLink link; - PenStyle *stylePtr; - double *w; /* Weight vector */ - int nPoints; - - nPoints = NUMBEROFPOINTS(elemPtr); - nWeights = MIN(elemPtr->w.nValues, nPoints); - w = elemPtr->w.values; - link = Blt_Chain_FirstLink(elemPtr->stylePalette); - stylePtr = Blt_Chain_GetValue(link); - - /* - * Create a style mapping array (data point index to style), - * initialized to the default style. - */ - dataToStyle = malloc(nPoints * sizeof(PenStyle *)); - for (i = 0; i < nPoints; i++) { - dataToStyle[i] = stylePtr; - } - - for (i = 0; i < nWeights; i++) { - for (link = Blt_Chain_LastLink(elemPtr->stylePalette); link != NULL; - link = Blt_Chain_PrevLink(link)) { - stylePtr = Blt_Chain_GetValue(link); - - if (stylePtr->weight.range > 0.0) { - double norm; - - norm = (w[i] - stylePtr->weight.min) / stylePtr->weight.range; - if (((norm - 1.0) <= DBL_EPSILON) && - (((1.0 - norm) - 1.0) <= DBL_EPSILON)) { - dataToStyle[i] = stylePtr; - break; /* Done: found range that matches. */ - } - } - } - } - return dataToStyle; -} - - -static int GetIndex(Tcl_Interp *interp, Element *elemPtr, - Tcl_Obj *objPtr, int *indexPtr) -{ - char *string; - - string = Tcl_GetString(objPtr); - if ((*string == 'e') && (strcmp("end", string) == 0)) { - *indexPtr = NUMBEROFPOINTS(elemPtr) - 1; - } else if (Blt_ExprIntFromObj(interp, objPtr, indexPtr) != TCL_OK) { - return TCL_ERROR; - } - return TCL_OK; -} - -int Blt_GetElement(Tcl_Interp *interp, Graph *graphPtr, Tcl_Obj *objPtr, - Element **elemPtrPtr) -{ - Tcl_HashEntry *hPtr; - char *name; - - name = Tcl_GetString(objPtr); - hPtr = Tcl_FindHashEntry(&graphPtr->elements.table, name); - if (hPtr == NULL) { - if (interp != NULL) { - Tcl_AppendResult(interp, "can't find element \"", name, - "\" in \"", Tk_PathName(graphPtr->tkwin), "\"", - (char *)NULL); - } - return TCL_ERROR; - } - *elemPtrPtr = Tcl_GetHashValue(hPtr); - return TCL_OK; -} - -static void DestroyElement(Element *elemPtr) -{ - Graph *graphPtr = elemPtr->obj.graphPtr; - - Blt_DeleteBindings(graphPtr->bindTable, elemPtr); - Blt_Legend_RemoveElement(graphPtr, elemPtr); - - FreeDataValues(&elemPtr->x); - FreeDataValues(&elemPtr->y); - - (*elemPtr->procsPtr->destroyProc) (graphPtr, elemPtr); - - /* Remove it also from the element display list */ - if (elemPtr->link != NULL) { - Blt_Chain_DeleteLink(graphPtr->elements.displayList, elemPtr->link); - if (!IGNORE_ELEMENT(elemPtr)) { - graphPtr->flags |= RESET_WORLD; - Blt_EventuallyRedrawGraph(graphPtr); - } - } - /* Remove the element for the graph's hash table of elements */ - if (elemPtr->hashPtr != NULL) - Tcl_DeleteHashEntry(elemPtr->hashPtr); - - if (elemPtr->obj.name != NULL) - free((void*)(elemPtr->obj.name)); - - if (elemPtr->label != NULL) - free((void*)(elemPtr->label)); - - free(elemPtr); -} - -static void FreeElement(char* data) -{ - Element *elemPtr = (Element *)data; - DestroyElement(elemPtr); -} - -void Blt_DestroyElements(Graph *graphPtr) -{ - Tcl_HashEntry *hPtr; - Tcl_HashSearch iter; - Element *elemPtr; - - for (hPtr = Tcl_FirstHashEntry(&graphPtr->elements.table, &iter); - hPtr != NULL; hPtr = Tcl_NextHashEntry(&iter)) { - elemPtr = Tcl_GetHashValue(hPtr); - elemPtr->hashPtr = NULL; - DestroyElement(elemPtr); - } - Tcl_DeleteHashTable(&graphPtr->elements.table); - Tcl_DeleteHashTable(&graphPtr->elements.tagTable); - Blt_Chain_Destroy(graphPtr->elements.displayList); -} - -void Blt_ConfigureElements(Graph *graphPtr) -{ - Blt_ChainLink link; - - for (link = Blt_Chain_FirstLink(graphPtr->elements.displayList); - link != NULL; link = Blt_Chain_NextLink(link)) { - Element *elemPtr; - - elemPtr = Blt_Chain_GetValue(link); - (*elemPtr->procsPtr->configProc) (graphPtr, elemPtr); - } -} - -void Blt_MapElements(Graph *graphPtr) -{ - Blt_ChainLink link; - - if (graphPtr->mode != BARS_INFRONT) { - Blt_ResetBarGroups(graphPtr); - } - for (link = Blt_Chain_FirstLink(graphPtr->elements.displayList); - link != NULL; link = Blt_Chain_NextLink(link)) { - Element *elemPtr; - - elemPtr = Blt_Chain_GetValue(link); - if (IGNORE_ELEMENT(elemPtr)) { - continue; - } - if ((graphPtr->flags & MAP_ALL) || (elemPtr->flags & MAP_ITEM)) { - (*elemPtr->procsPtr->mapProc) (graphPtr, elemPtr); - elemPtr->flags &= ~MAP_ITEM; - } - } -} - -void Blt_DrawElements(Graph *graphPtr, Drawable drawable) -{ - Blt_ChainLink link; - - /* Draw with respect to the stacking order. */ - for (link = Blt_Chain_LastLink(graphPtr->elements.displayList); - link != NULL; link = Blt_Chain_PrevLink(link)) { - Element *elemPtr; - - elemPtr = Blt_Chain_GetValue(link); - if (!(elemPtr->flags & DELETE_PENDING) && !elemPtr->hide) { - (*elemPtr->procsPtr->drawNormalProc)(graphPtr, drawable, elemPtr); - } - } -} - -void Blt_DrawActiveElements(Graph *graphPtr, Drawable drawable) -{ - Blt_ChainLink link; - - for (link = Blt_Chain_LastLink(graphPtr->elements.displayList); - link != NULL; link = Blt_Chain_PrevLink(link)) { - Element *elemPtr; - - elemPtr = Blt_Chain_GetValue(link); - if (!(elemPtr->flags & DELETE_PENDING) && - (elemPtr->flags & ACTIVE) && - !elemPtr->hide) { - (*elemPtr->procsPtr->drawActiveProc)(graphPtr, drawable, elemPtr); - } - } -} - -void Blt_ElementsToPostScript(Graph *graphPtr, Blt_Ps ps) -{ - Blt_ChainLink link; - - for (link = Blt_Chain_LastLink(graphPtr->elements.displayList); - link != NULL; link = Blt_Chain_PrevLink(link)) { - Element *elemPtr; - - elemPtr = Blt_Chain_GetValue(link); - if (!(elemPtr->flags & DELETE_PENDING) && !elemPtr->hide) { - continue; - } - /* Comment the PostScript to indicate the start of the element */ - Blt_Ps_Format(ps, "\n%% Element \"%s\"\n\n", elemPtr->obj.name); - (*elemPtr->procsPtr->printNormalProc) (graphPtr, ps, elemPtr); - } -} - -void Blt_ActiveElementsToPostScript( Graph *graphPtr, Blt_Ps ps) -{ - Blt_ChainLink link; - - for (link = Blt_Chain_LastLink(graphPtr->elements.displayList); - link != NULL; link = Blt_Chain_PrevLink(link)) { - Element *elemPtr; - - elemPtr = Blt_Chain_GetValue(link); - if (!(elemPtr->flags & DELETE_PENDING) && - (elemPtr->flags & ACTIVE) && - !elemPtr->hide) { - Blt_Ps_Format(ps, "\n%% Active Element \"%s\"\n\n", - elemPtr->obj.name); - (*elemPtr->procsPtr->printActiveProc)(graphPtr, ps, elemPtr); - } - } -} - -ClientData Blt_MakeElementTag(Graph *graphPtr, const char *tagName) -{ - Tcl_HashEntry *hPtr; - int isNew; - - hPtr = Tcl_CreateHashEntry(&graphPtr->elements.tagTable, tagName, &isNew); - return Tcl_GetHashKey(&graphPtr->elements.tagTable, hPtr); -} - -// waj -/* - if (Blt_ConfigModified(elemPtr->configSpecs, "-hide", (char *)NULL)) { - graphPtr->flags |= RESET_AXES; - elemPtr->flags |= MAP_ITEM; - } -*/ -/* If data points or axes have changed, reset the axes (may - * affect autoscaling) and recalculate the screen points of - * the element. */ - -/* - if (Blt_ConfigModified(elemPtr->configSpecs, "-*data", "-map*", "-x", - "-y", (char *)NULL)) { - graphPtr->flags |= RESET_WORLD; - elemPtr->flags |= MAP_ITEM; - } -*/ -/* The new label may change the size of the legend */ -/* - if (Blt_ConfigModified(elemPtr->configSpecs, "-label", (char *)NULL)) { - graphPtr->flags |= (MAP_WORLD | REDRAW_WORLD); - } -*/ - // Ops static int ActivateOp(Graph *graphPtr, Tcl_Interp *interp, @@ -1032,8 +536,8 @@ static int BindOp(Graph *graphPtr, Tcl_Interp *interp, return Blt_ConfigureBindingsFromObj(interp, graphPtr->bindTable, Blt_MakeElementTag(graphPtr, Tcl_GetString(objv[3])), objc - 4, objv + 4); } -static int CreateOp(Graph *graphPtr, Tcl_Interp *interp, - int objc, Tcl_Obj *const *objv, ClassId classId) +static int CreateOp(Graph* graphPtr, Tcl_Interp* interp, + int objc, Tcl_Obj* const objv[], ClassId classId) { return CreateElement(graphPtr, interp, objc, objv, classId); } @@ -1517,3 +1021,501 @@ int Blt_ElementOp(Graph *graphPtr, Tcl_Interp *interp, } return result; } +// Support + +static void FreeElement(char* data) +{ + Element *elemPtr = (Element *)data; + DestroyElement(elemPtr); +} + +static int GetPenStyleFromObj(Tcl_Interp *interp, Graph *graphPtr, + Tcl_Obj *objPtr, ClassId classId, + PenStyle *stylePtr) +{ + Pen *penPtr; + Tcl_Obj **objv; + int objc; + + if (Tcl_ListObjGetElements(interp, objPtr, &objc, &objv) != TCL_OK) { + return TCL_ERROR; + } + if ((objc != 1) && (objc != 3)) { + if (interp != NULL) { + Tcl_AppendResult(interp, "bad style entry \"", + Tcl_GetString(objPtr), + "\": should be \"penName\" or \"penName min max\"", + (char *)NULL); + } + return TCL_ERROR; + } + if (Blt_GetPenFromObj(interp, graphPtr, objv[0], classId, &penPtr) + != TCL_OK) { + return TCL_ERROR; + } + if (objc == 3) { + double min, max; + + if ((Tcl_GetDoubleFromObj(interp, objv[1], &min) != TCL_OK) || + (Tcl_GetDoubleFromObj(interp, objv[2], &max) != TCL_OK)) { + return TCL_ERROR; + } + SetWeight(stylePtr->weight, min, max); + } + stylePtr->penPtr = penPtr; + return TCL_OK; +} + +static void FreeVectorSource(ElemValues *valuesPtr) +{ + if (valuesPtr->vectorSource.vector != NULL) { + Blt_SetVectorChangedProc(valuesPtr->vectorSource.vector, NULL, NULL); + Blt_FreeVectorId(valuesPtr->vectorSource.vector); + valuesPtr->vectorSource.vector = NULL; + } +} + +static int FetchVectorValues(Tcl_Interp *interp, ElemValues *valuesPtr, + Blt_Vector *vector) +{ + double *array; + + if (valuesPtr->values == NULL) { + array = malloc(Blt_VecLength(vector) * sizeof(double)); + } else { + array = realloc(valuesPtr->values, + Blt_VecLength(vector) * sizeof(double)); + } + if (array == NULL) { + if (interp != NULL) { + Tcl_AppendResult(interp, "can't allocate new vector", (char *)NULL); + } + return TCL_ERROR; + } + memcpy(array, Blt_VecData(vector), sizeof(double) * Blt_VecLength(vector)); + valuesPtr->min = Blt_VecMin(vector); + valuesPtr->max = Blt_VecMax(vector); + valuesPtr->values = array; + valuesPtr->nValues = Blt_VecLength(vector); + /* FindRange(valuesPtr); */ + return TCL_OK; +} + +static void VectorChangedProc(Tcl_Interp *interp, ClientData clientData, + Blt_VectorNotify notify) +{ + ElemValues *valuesPtr = clientData; + + if (notify == BLT_VECTOR_NOTIFY_DESTROY) { + FreeDataValues(valuesPtr); + } else { + Blt_Vector *vector; + + Blt_GetVectorById(interp, valuesPtr->vectorSource.vector, &vector); + if (FetchVectorValues(NULL, valuesPtr, vector) != TCL_OK) { + return; + } + } + { + Element *elemPtr = valuesPtr->elemPtr; + Graph *graphPtr; + + graphPtr = elemPtr->obj.graphPtr; + graphPtr->flags |= RESET_AXES; + elemPtr->flags |= MAP_ITEM; + if (!IGNORE_ELEMENT(elemPtr)) { + graphPtr->flags |= CACHE_DIRTY; + Blt_EventuallyRedrawGraph(graphPtr); + } + } +} + +static int GetVectorData(Tcl_Interp *interp, ElemValues *valuesPtr, + const char *vecName) +{ + Blt_Vector *vecPtr; + VectorDataSource *srcPtr; + + srcPtr = &valuesPtr->vectorSource; + srcPtr->vector = Blt_AllocVectorId(interp, vecName); + if (Blt_GetVectorById(interp, srcPtr->vector, &vecPtr) != TCL_OK) { + return TCL_ERROR; + } + if (FetchVectorValues(interp, valuesPtr, vecPtr) != TCL_OK) { + FreeVectorSource(valuesPtr); + return TCL_ERROR; + } + Blt_SetVectorChangedProc(srcPtr->vector, VectorChangedProc, valuesPtr); + valuesPtr->type = ELEM_SOURCE_VECTOR; + return TCL_OK; +} + +static int ParseValues(Tcl_Interp *interp, Tcl_Obj *objPtr, int *nValuesPtr, + double **arrayPtr) +{ + int objc; + Tcl_Obj **objv; + + if (Tcl_ListObjGetElements(interp, objPtr, &objc, &objv) != TCL_OK) { + return TCL_ERROR; + } + *arrayPtr = NULL; + *nValuesPtr = 0; + if (objc > 0) { + double *array; + double *p; + int i; + + array = malloc(sizeof(double) * objc); + if (array == NULL) { + Tcl_AppendResult(interp, "can't allocate new vector", (char *)NULL); + return TCL_ERROR; + } + for (p = array, i = 0; i < objc; i++, p++) { + if (Blt_ExprDoubleFromObj(interp, objv[i], p) != TCL_OK) { + free(array); + return TCL_ERROR; + } + } + *arrayPtr = array; + *nValuesPtr = objc; + } + return TCL_OK; +} + +static void FreeDataValues(ElemValues *valuesPtr) +{ + switch (valuesPtr->type) { + case ELEM_SOURCE_VECTOR: + FreeVectorSource(valuesPtr); + break; + case ELEM_SOURCE_VALUES: + break; + } + if (valuesPtr->values != NULL) { + free(valuesPtr->values); + } + valuesPtr->values = NULL; + valuesPtr->nValues = 0; + valuesPtr->type = ELEM_SOURCE_VALUES; +} + +static void FindRange(ElemValues *valuesPtr) +{ + int i; + double *x; + double min, max; + + if ((valuesPtr->nValues < 1) || (valuesPtr->values == NULL)) { + return; /* This shouldn't ever happen. */ + } + x = valuesPtr->values; + + min = DBL_MAX, max = -DBL_MAX; + for(i = 0; i < valuesPtr->nValues; i++) { + if (isfinite(x[i])) { + min = max = x[i]; + break; + } + } + /* Initialize values to track the vector range */ + for (/* empty */; i < valuesPtr->nValues; i++) { + if (isfinite(x[i])) { + if (x[i] < min) { + min = x[i]; + } else if (x[i] > max) { + max = x[i]; + } + } + } + valuesPtr->min = min, valuesPtr->max = max; +} + +double Blt_FindElemValuesMinimum(ElemValues *valuesPtr, double minLimit) +{ + int i; + double min; + + min = DBL_MAX; + for (i = 0; i < valuesPtr->nValues; i++) { + double x; + + x = valuesPtr->values[i]; + if (x < 0.0) { + /* What do you do about negative values when using log + * scale values seems like a grey area. Mirror. */ + x = -x; + } + if ((x > minLimit) && (min > x)) { + min = x; + } + } + if (min == DBL_MAX) { + min = minLimit; + } + return min; +} + +void Blt_FreeStylePalette(Blt_Chain stylePalette) +{ + Blt_ChainLink link; + + /* Skip the first slot. It contains the built-in "normal" pen of + * the element. */ + link = Blt_Chain_FirstLink(stylePalette); + if (link != NULL) { + Blt_ChainLink next; + + for (link = Blt_Chain_NextLink(link); link != NULL; link = next) { + PenStyle *stylePtr; + + next = Blt_Chain_NextLink(link); + stylePtr = Blt_Chain_GetValue(link); + Blt_FreePen(stylePtr->penPtr); + Blt_Chain_DeleteLink(stylePalette, link); + } + } +} + +PenStyle **Blt_StyleMap(Element *elemPtr) +{ + int i; + int nWeights; /* Number of weights to be examined. + * If there are more data points than + * weights, they will default to the + * normal pen. */ + + PenStyle **dataToStyle; /* Directory of styles. Each array + * element represents the style for + * the data point at that index */ + Blt_ChainLink link; + PenStyle *stylePtr; + double *w; /* Weight vector */ + int nPoints; + + nPoints = NUMBEROFPOINTS(elemPtr); + nWeights = MIN(elemPtr->w.nValues, nPoints); + w = elemPtr->w.values; + link = Blt_Chain_FirstLink(elemPtr->stylePalette); + stylePtr = Blt_Chain_GetValue(link); + + /* + * Create a style mapping array (data point index to style), + * initialized to the default style. + */ + dataToStyle = malloc(nPoints * sizeof(PenStyle *)); + for (i = 0; i < nPoints; i++) { + dataToStyle[i] = stylePtr; + } + + for (i = 0; i < nWeights; i++) { + for (link = Blt_Chain_LastLink(elemPtr->stylePalette); link != NULL; + link = Blt_Chain_PrevLink(link)) { + stylePtr = Blt_Chain_GetValue(link); + + if (stylePtr->weight.range > 0.0) { + double norm; + + norm = (w[i] - stylePtr->weight.min) / stylePtr->weight.range; + if (((norm - 1.0) <= DBL_EPSILON) && + (((1.0 - norm) - 1.0) <= DBL_EPSILON)) { + dataToStyle[i] = stylePtr; + break; /* Done: found range that matches. */ + } + } + } + } + return dataToStyle; +} + + +static int GetIndex(Tcl_Interp *interp, Element *elemPtr, + Tcl_Obj *objPtr, int *indexPtr) +{ + char *string; + + string = Tcl_GetString(objPtr); + if ((*string == 'e') && (strcmp("end", string) == 0)) { + *indexPtr = NUMBEROFPOINTS(elemPtr) - 1; + } else if (Blt_ExprIntFromObj(interp, objPtr, indexPtr) != TCL_OK) { + return TCL_ERROR; + } + return TCL_OK; +} + +int Blt_GetElement(Tcl_Interp *interp, Graph *graphPtr, Tcl_Obj *objPtr, + Element **elemPtrPtr) +{ + Tcl_HashEntry *hPtr; + char *name; + + name = Tcl_GetString(objPtr); + hPtr = Tcl_FindHashEntry(&graphPtr->elements.table, name); + if (hPtr == NULL) { + if (interp != NULL) { + Tcl_AppendResult(interp, "can't find element \"", name, + "\" in \"", Tk_PathName(graphPtr->tkwin), "\"", + (char *)NULL); + } + return TCL_ERROR; + } + *elemPtrPtr = Tcl_GetHashValue(hPtr); + return TCL_OK; +} + +void Blt_DestroyElements(Graph *graphPtr) +{ + Tcl_HashEntry *hPtr; + Tcl_HashSearch iter; + Element *elemPtr; + + for (hPtr = Tcl_FirstHashEntry(&graphPtr->elements.table, &iter); + hPtr != NULL; hPtr = Tcl_NextHashEntry(&iter)) { + elemPtr = Tcl_GetHashValue(hPtr); + elemPtr->hashPtr = NULL; + DestroyElement(elemPtr); + } + Tcl_DeleteHashTable(&graphPtr->elements.table); + Tcl_DeleteHashTable(&graphPtr->elements.tagTable); + Blt_Chain_Destroy(graphPtr->elements.displayList); +} + +void Blt_ConfigureElements(Graph *graphPtr) +{ + Blt_ChainLink link; + + for (link = Blt_Chain_FirstLink(graphPtr->elements.displayList); + link != NULL; link = Blt_Chain_NextLink(link)) { + Element *elemPtr; + + elemPtr = Blt_Chain_GetValue(link); + (*elemPtr->procsPtr->configProc) (graphPtr, elemPtr); + } +} + +void Blt_MapElements(Graph *graphPtr) +{ + Blt_ChainLink link; + + if (graphPtr->mode != BARS_INFRONT) { + Blt_ResetBarGroups(graphPtr); + } + for (link = Blt_Chain_FirstLink(graphPtr->elements.displayList); + link != NULL; link = Blt_Chain_NextLink(link)) { + Element *elemPtr; + + elemPtr = Blt_Chain_GetValue(link); + if (IGNORE_ELEMENT(elemPtr)) { + continue; + } + if ((graphPtr->flags & MAP_ALL) || (elemPtr->flags & MAP_ITEM)) { + (*elemPtr->procsPtr->mapProc) (graphPtr, elemPtr); + elemPtr->flags &= ~MAP_ITEM; + } + } +} + +void Blt_DrawElements(Graph *graphPtr, Drawable drawable) +{ + Blt_ChainLink link; + + /* Draw with respect to the stacking order. */ + for (link = Blt_Chain_LastLink(graphPtr->elements.displayList); + link != NULL; link = Blt_Chain_PrevLink(link)) { + Element *elemPtr; + + elemPtr = Blt_Chain_GetValue(link); + if (!(elemPtr->flags & DELETE_PENDING) && !elemPtr->hide) { + (*elemPtr->procsPtr->drawNormalProc)(graphPtr, drawable, elemPtr); + } + } +} + +void Blt_DrawActiveElements(Graph *graphPtr, Drawable drawable) +{ + Blt_ChainLink link; + + for (link = Blt_Chain_LastLink(graphPtr->elements.displayList); + link != NULL; link = Blt_Chain_PrevLink(link)) { + Element *elemPtr; + + elemPtr = Blt_Chain_GetValue(link); + if (!(elemPtr->flags & DELETE_PENDING) && + (elemPtr->flags & ACTIVE) && + !elemPtr->hide) { + (*elemPtr->procsPtr->drawActiveProc)(graphPtr, drawable, elemPtr); + } + } +} + +void Blt_ElementsToPostScript(Graph *graphPtr, Blt_Ps ps) +{ + Blt_ChainLink link; + + for (link = Blt_Chain_LastLink(graphPtr->elements.displayList); + link != NULL; link = Blt_Chain_PrevLink(link)) { + Element *elemPtr; + + elemPtr = Blt_Chain_GetValue(link); + if (!(elemPtr->flags & DELETE_PENDING) && !elemPtr->hide) { + continue; + } + /* Comment the PostScript to indicate the start of the element */ + Blt_Ps_Format(ps, "\n%% Element \"%s\"\n\n", elemPtr->obj.name); + (*elemPtr->procsPtr->printNormalProc) (graphPtr, ps, elemPtr); + } +} + +void Blt_ActiveElementsToPostScript( Graph *graphPtr, Blt_Ps ps) +{ + Blt_ChainLink link; + + for (link = Blt_Chain_LastLink(graphPtr->elements.displayList); + link != NULL; link = Blt_Chain_PrevLink(link)) { + Element *elemPtr; + + elemPtr = Blt_Chain_GetValue(link); + if (!(elemPtr->flags & DELETE_PENDING) && + (elemPtr->flags & ACTIVE) && + !elemPtr->hide) { + Blt_Ps_Format(ps, "\n%% Active Element \"%s\"\n\n", + elemPtr->obj.name); + (*elemPtr->procsPtr->printActiveProc)(graphPtr, ps, elemPtr); + } + } +} + +ClientData Blt_MakeElementTag(Graph *graphPtr, const char *tagName) +{ + Tcl_HashEntry *hPtr; + int isNew; + + hPtr = Tcl_CreateHashEntry(&graphPtr->elements.tagTable, tagName, &isNew); + return Tcl_GetHashKey(&graphPtr->elements.tagTable, hPtr); +} + +// waj +/* + if (Blt_ConfigModified(elemPtr->configSpecs, "-hide", (char *)NULL)) { + graphPtr->flags |= RESET_AXES; + elemPtr->flags |= MAP_ITEM; + } +*/ +/* If data points or axes have changed, reset the axes (may + * affect autoscaling) and recalculate the screen points of + * the element. */ + +/* + if (Blt_ConfigModified(elemPtr->configSpecs, "-*data", "-map*", "-x", + "-y", (char *)NULL)) { + graphPtr->flags |= RESET_WORLD; + elemPtr->flags |= MAP_ITEM; + } +*/ +/* The new label may change the size of the legend */ +/* + if (Blt_ConfigModified(elemPtr->configSpecs, "-label", (char *)NULL)) { + graphPtr->flags |= (MAP_WORLD | REDRAW_WORLD); + } +*/ + diff --git a/src/bltGrPenOp.C b/src/bltGrPenOp.C index e1d5ec7..84a2ef0 100644 --- a/src/bltGrPenOp.C +++ b/src/bltGrPenOp.C @@ -41,6 +41,18 @@ #include "bltGrElem.h" #include "bltOp.h" +// Defs + +static void DestroyPen(Pen* penPtr); +static int GetPenFromObj(Tcl_Interp *interp, Graph *graphPtr, Tcl_Obj *objPtr, + Pen **penPtrPtr); +static int PenObjConfigure(Tcl_Interp *interp, Graph* graphPtr, Pen* penPtr, + int objc, Tcl_Obj* const objv[]); +typedef int (GraphPenProc)(Tcl_Interp *interp, Graph *graphPtr, int objc, + Tcl_Obj *const *objv); + +// OptionSpecs + static Tk_CustomOptionSetProc PenSetProc; static Tk_CustomOptionGetProc PenGetProc; Tk_ObjCustomOption barPenObjOption = @@ -92,193 +104,96 @@ static Tcl_Obj* PenGetProc(ClientData clientData, Tk_Window tkwin, return Tcl_NewStringObj(penPtr->name, -1); }; -static int PenObjConfigure(Tcl_Interp *interp, Graph* graphPtr, - Pen* penPtr, - int objc, Tcl_Obj* const objv[]); -typedef int (GraphPenProc)(Tcl_Interp *interp, Graph *graphPtr, int objc, - Tcl_Obj *const *objv); +// Create -static int GetPenFromObj(Tcl_Interp *interp, Graph *graphPtr, Tcl_Obj *objPtr, - Pen **penPtrPtr) +int Blt_CreatePen(Graph* graphPtr, Tcl_Interp* interp, + const char* penName, ClassId classId, + int objc, Tcl_Obj* const objv[]) { - Tcl_HashEntry *hPtr; - Pen *penPtr; - const char *name; - - penPtr = NULL; - name = Tcl_GetString(objPtr); - hPtr = Tcl_FindHashEntry(&graphPtr->penTable, name); - if (hPtr != NULL) { - penPtr = Tcl_GetHashValue(hPtr); - if (penPtr->flags & DELETE_PENDING) { - penPtr = NULL; - } - } - if (penPtr == NULL) { - if (interp != NULL) { - Tcl_AppendResult(interp, "can't find pen \"", name, "\" in \"", - Tk_PathName(graphPtr->tkwin), "\"", (char *)NULL); - } - return TCL_ERROR; - } - *penPtrPtr = penPtr; - return TCL_OK; -} - -static void DestroyPen(Pen* penPtr) -{ - Graph *graphPtr = penPtr->graphPtr; - - (*penPtr->destroyProc) (graphPtr, penPtr); - if ((penPtr->name != NULL) && (penPtr->name[0] != '\0')) { - free((void*)(penPtr->name)); - } - if (penPtr->hashPtr != NULL) { - Tcl_DeleteHashEntry(penPtr->hashPtr); - } - free(penPtr); -} - -void Blt_FreePen(Pen *penPtr) -{ - if (penPtr != NULL) { - penPtr->refCount--; - if ((penPtr->refCount == 0) && (penPtr->flags & DELETE_PENDING)) { - DestroyPen(penPtr); - } - } -} - -Pen* Blt_CreatePen(Graph* graphPtr, const char* penName, ClassId classId, - int objc, Tcl_Obj* const objv[]) -{ - Pen *penPtr; - Tcl_HashEntry *hPtr; - int isNew; - int i; - /* * Scan the option list for a "-type" entry. This will indicate what type * of pen we are creating. Otherwise we'll default to the suggested type. * Last -type option wins. */ - for (i = 0; i < objc; i += 2) { + for (int ii = 0; ii<objc; ii += 2) { char *string; int length; - string = Tcl_GetStringFromObj(objv[i], &length); + string = Tcl_GetStringFromObj(objv[ii], &length); if ((length > 2) && (strncmp(string, "-type", length) == 0)) { char *arg; - arg = Tcl_GetString(objv[i + 1]); - if (strcmp(arg, "bar") == 0) { + arg = Tcl_GetString(objv[ii + 1]); + if (strcmp(arg, "bar") == 0) classId = CID_ELEM_BAR; - } else if (strcmp(arg, "line") == 0) { + else if (strcmp(arg, "line") == 0) classId = CID_ELEM_LINE; - } else { - Tcl_AppendResult(graphPtr->interp, "unknown pen type \"", + else { + Tcl_AppendResult(interp, "unknown pen type \"", arg, "\" specified", (char *)NULL); - return NULL; + return TCL_ERROR; } } } - classId = CID_ELEM_LINE; - hPtr = Tcl_CreateHashEntry(&graphPtr->penTable, penName, &isNew); + + Pen *penPtr; + int isNew; + Tcl_HashEntry *hPtr = + Tcl_CreateHashEntry(&graphPtr->penTable, penName, &isNew); if (!isNew) { penPtr = Tcl_GetHashValue(hPtr); - if ((penPtr->flags & DELETE_PENDING) == 0) { - Tcl_AppendResult(graphPtr->interp, "pen \"", penName, - "\" already exists in \"", Tk_PathName(graphPtr->tkwin), "\"", - (char *)NULL); - return NULL; - } - if (penPtr->classId != classId) { - Tcl_AppendResult(graphPtr->interp, "pen \"", penName, - "\" in-use: can't change pen type from \"", - Blt_GraphClassName(penPtr->classId), "\" to \"", - Blt_GraphClassName(classId), "\"", (char *)NULL); - return NULL; - } - penPtr->flags &= ~DELETE_PENDING; /* Undelete the pen. */ - } else { - if (classId == CID_ELEM_BAR) - penPtr = Blt_BarPen(graphPtr, penName); - else - penPtr = Blt_LinePen(graphPtr, penName); - penPtr->classId = classId; - penPtr->hashPtr = hPtr; - penPtr->graphPtr = graphPtr; - Tcl_SetHashValue(hPtr, penPtr); - } + if ((penPtr->flags & DELETE_PENDING) == 0) + Tcl_AppendResult(interp, "pen \"", penName, "\" already exists in \"", Tk_PathName(graphPtr->tkwin), "\"", (char *)NULL); + else if (penPtr->classId != classId) + Tcl_AppendResult(interp, "pen \"", penName, "\" in-use: can't change pen type from \"", Blt_GraphClassName(penPtr->classId), "\" to \"", Blt_GraphClassName(classId), "\"", (char *)NULL); - /* - if ((Tk_InitOptions(graphPtr->interp, (char*)penPtr, penPtr->optionTable, graphPtr->tkwin) != TCL_OK) || (PenObjConfigure(interp, graphPtr, penPtr, objc-4, objv+4) != TCL_OK)) { - if (isNew) - DestroyElement(penPtr); return TCL_ERROR; } - */ - - // (*penPtr->configProc) (graphPtr, penPtr); - return penPtr; -} -int Blt_GetPenFromObj(Tcl_Interp *interp, Graph *graphPtr, Tcl_Obj *objPtr, - ClassId classId, Pen **penPtrPtr) -{ - Tcl_HashEntry *hPtr; - Pen *penPtr; - const char *name; - - penPtr = NULL; - name = Tcl_GetString(objPtr); - hPtr = Tcl_FindHashEntry(&graphPtr->penTable, name); - if (hPtr != NULL) { - penPtr = Tcl_GetHashValue(hPtr); - if (penPtr->flags & DELETE_PENDING) { - penPtr = NULL; - } - } - if (penPtr == NULL) { - if (interp != NULL) { - Tcl_AppendResult(interp, "can't find pen \"", name, "\" in \"", - Tk_PathName(graphPtr->tkwin), "\"", (char *)NULL); - } + if (classId == CID_ELEM_BAR) + penPtr = Blt_BarPen(graphPtr, penName); + else + penPtr = Blt_LinePen(graphPtr, penName); + if (!penPtr) return TCL_ERROR; - } - classId = CID_ELEM_LINE; - if (penPtr->classId != classId) { - if (interp != NULL) { - Tcl_AppendResult(interp, "pen \"", name, - "\" is the wrong type (is \"", - Blt_GraphClassName(penPtr->classId), "\"", ", wanted \"", - Blt_GraphClassName(classId), "\")", (char *)NULL); - } + + penPtr->graphPtr = graphPtr; + penPtr->classId = classId; + + if (PenObjConfigure(interp, graphPtr, penPtr, objc-4, objv+4) != TCL_OK) { + DestroyPen(penPtr); return TCL_ERROR; } - penPtr->refCount++; - *penPtrPtr = penPtr; + + penPtr->hashPtr = hPtr; + Tcl_SetHashValue(hPtr, penPtr); + + graphPtr->flags |= CACHE_DIRTY; + Blt_EventuallyRedrawGraph(graphPtr); + + Tcl_SetObjResult(interp, objv[3]); return TCL_OK; } -void Blt_DestroyPens(Graph *graphPtr) +static void DestroyPen(Pen* penPtr) { - Tcl_HashEntry *hPtr; - Tcl_HashSearch iter; + Graph *graphPtr = penPtr->graphPtr; - for (hPtr = Tcl_FirstHashEntry(&graphPtr->penTable, &iter); - hPtr != NULL; hPtr = Tcl_NextHashEntry(&iter)) { - Pen *penPtr; + (*penPtr->destroyProc) (graphPtr, penPtr); - penPtr = Tcl_GetHashValue(hPtr); - penPtr->hashPtr = NULL; - DestroyPen(penPtr); - } - Tcl_DeleteHashTable(&graphPtr->penTable); + if (penPtr->name) + free((void*)(penPtr->name)); + + if (penPtr->hashPtr) + Tcl_DeleteHashEntry(penPtr->hashPtr); + + free(penPtr); } -static int CgetOp(Tcl_Interp *interp, Graph *graphPtr, - int objc, Tcl_Obj *const *objv) +// Configure + +static int CgetOp(Tcl_Interp* interp, Graph* graphPtr, + int objc, Tcl_Obj* const objv[]) { if (objc != 5) { Tcl_WrongNumArgs(interp, 3, objv, "cget option"); @@ -303,78 +218,73 @@ static int CgetOp(Tcl_Interp *interp, Graph *graphPtr, static int ConfigureOp(Tcl_Interp *interp, Graph *graphPtr, int objc, Tcl_Obj *const *objv) { - Pen *penPtr; - int nNames, nOpts; - int redraw; - Tcl_Obj *const *options; - int i; - - /* Figure out where the option value pairs begin */ - objc -= 3; - objv += 3; - for (i = 0; i < objc; i++) { - char *string; + Pen* penPtr; + if (GetPenFromObj(interp, graphPtr, objv[3], &penPtr) != TCL_OK) + return TCL_ERROR; - string = Tcl_GetString(objv[i]); - if (string[0] == '-') { - break; - } - if (GetPenFromObj(interp, graphPtr, objv[i], &penPtr) != TCL_OK) { + if (objc <= 5) { + Tcl_Obj* objPtr = Tk_GetOptionInfo(graphPtr->interp, (char*)penPtr, + penPtr->optionTable, + (objc == 5) ? objv[4] : NULL, + graphPtr->tkwin); + if (objPtr == NULL) return TCL_ERROR; - } - } - nNames = i; /* Number of pen names specified */ - nOpts = objc - i; /* Number of options specified */ - options = objv + i; /* Start of options in objv */ + else + Tcl_SetObjResult(interp, objPtr); + return TCL_OK; + } + else + return PenObjConfigure(interp, graphPtr, penPtr, objc-4, objv+4); +} - redraw = 0; - for (i = 0; i < nNames; i++) { - if (GetPenFromObj(interp, graphPtr, objv[i], &penPtr) != TCL_OK) { - return TCL_ERROR; - } - /* - // waj - flags = BLT_CONFIG_OBJV_ONLY | (penPtr->flags&(ACTIVE_PEN|NORMAL_PEN)); - if (nOpts == 0) { - return Blt_ConfigureInfoFromObj(interp, graphPtr->tkwin, - penPtr->configSpecs, (char *)penPtr, (Tcl_Obj *)NULL, flags); - } else if (nOpts == 1) { - return Blt_ConfigureInfoFromObj(interp, graphPtr->tkwin, - penPtr->configSpecs, (char *)penPtr, options[0], flags); - } - if (Blt_ConfigureWidgetFromObj(interp, graphPtr->tkwin, - penPtr->configSpecs, nOpts, options, (char *)penPtr, flags) - != TCL_OK) { - break; +static int PenObjConfigure(Tcl_Interp *interp, Graph* graphPtr, Pen* penPtr, + int objc, Tcl_Obj* const objv[]) +{ + Tk_SavedOptions savedOptions; + int mask =0; + int error; + Tcl_Obj* errorResult; + + for (error=0; error<=1; error++) { + if (!error) { + if (Tk_SetOptions(interp, (char*)penPtr, penPtr->optionTable, + objc, objv, graphPtr->tkwin, &savedOptions, &mask) + != TCL_OK) + continue; } - */ - (*penPtr->configProc) (graphPtr, penPtr); - if (penPtr->refCount > 0) { - redraw++; + else { + errorResult = Tcl_GetObjResult(interp); + Tcl_IncrRefCount(errorResult); + Tk_RestoreSavedOptions(&savedOptions); } - } - if (redraw) { + + graphPtr->flags |= mask; graphPtr->flags |= CACHE_DIRTY; + if ((*penPtr->configProc) (graphPtr, penPtr) != TCL_OK) + return TCL_ERROR; Blt_EventuallyRedrawGraph(graphPtr); + + break; + } + + if (!error) { + Tk_FreeSavedOptions(&savedOptions); + return TCL_OK; } - if (i < nNames) { + else { + Tcl_SetObjResult(interp, errorResult); + Tcl_DecrRefCount(errorResult); return TCL_ERROR; } - return TCL_OK; } +// Ops + static int CreateOp(Tcl_Interp *interp, Graph *graphPtr, int objc, Tcl_Obj *const *objv) { - Pen *penPtr; - - penPtr = Blt_CreatePen(graphPtr, Tcl_GetString(objv[3]), graphPtr->classId, - objc - 4, objv + 4); - if (penPtr == NULL) - return TCL_ERROR; - - Tcl_SetObjResult(interp, objv[3]); - return TCL_OK; + return Blt_CreatePen(graphPtr, interp, Tcl_GetString(objv[3]), + graphPtr->classId, objc, objv); } static int DeleteOp(Tcl_Interp *interp, Graph *graphPtr, @@ -475,6 +385,8 @@ static Blt_OpSpec penOps[] = }; static int nPenOps = sizeof(penOps) / sizeof(Blt_OpSpec); +// Extern + int Blt_PenOp(Graph *graphPtr, Tcl_Interp *interp, int objc, Tcl_Obj *const *objv) { @@ -485,3 +397,97 @@ int Blt_PenOp(Graph *graphPtr, Tcl_Interp *interp, } return (*proc) (interp, graphPtr, objc, objv); } + +void Blt_DestroyPens(Graph *graphPtr) +{ + Tcl_HashEntry *hPtr; + Tcl_HashSearch iter; + + for (hPtr = Tcl_FirstHashEntry(&graphPtr->penTable, &iter); + hPtr != NULL; hPtr = Tcl_NextHashEntry(&iter)) { + Pen *penPtr; + + penPtr = Tcl_GetHashValue(hPtr); + penPtr->hashPtr = NULL; + DestroyPen(penPtr); + } + Tcl_DeleteHashTable(&graphPtr->penTable); +} + +void Blt_FreePen(Pen *penPtr) +{ + if (penPtr != NULL) { + penPtr->refCount--; + if ((penPtr->refCount == 0) && (penPtr->flags & DELETE_PENDING)) { + DestroyPen(penPtr); + } + } +} + +int Blt_GetPenFromObj(Tcl_Interp *interp, Graph *graphPtr, Tcl_Obj *objPtr, + ClassId classId, Pen **penPtrPtr) +{ + Tcl_HashEntry *hPtr; + Pen *penPtr; + const char *name; + + penPtr = NULL; + name = Tcl_GetString(objPtr); + hPtr = Tcl_FindHashEntry(&graphPtr->penTable, name); + if (hPtr != NULL) { + penPtr = Tcl_GetHashValue(hPtr); + if (penPtr->flags & DELETE_PENDING) { + penPtr = NULL; + } + } + if (penPtr == NULL) { + if (interp != NULL) { + Tcl_AppendResult(interp, "can't find pen \"", name, "\" in \"", + Tk_PathName(graphPtr->tkwin), "\"", (char *)NULL); + } + return TCL_ERROR; + } + classId = CID_ELEM_LINE; + if (penPtr->classId != classId) { + if (interp != NULL) { + Tcl_AppendResult(interp, "pen \"", name, + "\" is the wrong type (is \"", + Blt_GraphClassName(penPtr->classId), "\"", ", wanted \"", + Blt_GraphClassName(classId), "\")", (char *)NULL); + } + return TCL_ERROR; + } + penPtr->refCount++; + *penPtrPtr = penPtr; + return TCL_OK; +} + +// Support + +static int GetPenFromObj(Tcl_Interp *interp, Graph *graphPtr, Tcl_Obj *objPtr, + Pen **penPtrPtr) +{ + Tcl_HashEntry *hPtr; + Pen *penPtr; + const char *name; + + penPtr = NULL; + name = Tcl_GetString(objPtr); + hPtr = Tcl_FindHashEntry(&graphPtr->penTable, name); + if (hPtr != NULL) { + penPtr = Tcl_GetHashValue(hPtr); + if (penPtr->flags & DELETE_PENDING) { + penPtr = NULL; + } + } + if (penPtr == NULL) { + if (interp != NULL) { + Tcl_AppendResult(interp, "can't find pen \"", name, "\" in \"", + Tk_PathName(graphPtr->tkwin), "\"", (char *)NULL); + } + return TCL_ERROR; + } + *penPtrPtr = penPtr; + return TCL_OK; +} + diff --git a/src/bltGraph.C b/src/bltGraph.C index a02a818..50d42e1 100644 --- a/src/bltGraph.C +++ b/src/bltGraph.C @@ -301,9 +301,11 @@ static int NewGraph(ClientData clientData, Tcl_Interp*interp, goto error; if (Blt_CreateLegend(graphPtr) != TCL_OK) goto error; - if (Blt_CreatePen(graphPtr, "activeLine", CID_ELEM_LINE, 0, NULL) == NULL) + if (Blt_CreatePen(graphPtr, interp, "activeLine", CID_ELEM_LINE, 0, NULL) != + TCL_OK) goto error; - if (Blt_CreatePen(graphPtr, "activeBar", CID_ELEM_BAR, 0, NULL) == NULL) + if (Blt_CreatePen(graphPtr, interp, "activeBar", CID_ELEM_BAR, 0, NULL) != + TCL_OK) goto error; if (Blt_CreatePageSetup(graphPtr) != TCL_OK) diff --git a/src/bltGraph.h b/src/bltGraph.h index 2907965..db67c88 100644 --- a/src/bltGraph.h +++ b/src/bltGraph.h @@ -556,8 +556,9 @@ extern Pen* Blt_BarPen(Graph* graphPtr, const char* penName); extern Pen* Blt_LinePen(Graph* graphPtr, const char* penName); -extern Pen* Blt_CreatePen(Graph* graphPtr, const char* penName, - ClassId classId, int objc, Tcl_Obj* const objv[]); +extern int Blt_CreatePen(Graph* graphPtr, Tcl_Interp* interp, + const char* penName, ClassId classId, + int objc, Tcl_Obj* const objv[]); extern int Blt_InitLinePens(Graph *graphPtr); |