diff options
Diffstat (limited to 'generic/tkPanedWindow.c')
-rw-r--r-- | generic/tkPanedWindow.c | 1900 |
1 files changed, 1006 insertions, 894 deletions
diff --git a/generic/tkPanedWindow.c b/generic/tkPanedWindow.c index 57670ba..68d62d7 100644 --- a/generic/tkPanedWindow.c +++ b/generic/tkPanedWindow.c @@ -1,23 +1,23 @@ -/* +/* * tkPanedWindow.c -- * - * This module implements "paned window" widgets that are object - * based. A "paned window" is a widget that manages the geometry for - * some number of other widgets, placing a movable "sash" between them, - * which can be used to alter the relative sizes of adjacent widgets. + * This module implements "paned window" widgets that are object based. A + * "paned window" is a widget that manages the geometry for some number + * of other widgets, placing a movable "sash" between them, which can be + * used to alter the relative sizes of adjacent widgets. * * Copyright (c) 1997 Sun Microsystems, Inc. * Copyright (c) 2000 Ajuba Solutions. * - * See the file "license.terms" for information on usage and redistribution - * of this file, and for a DISCLAIMER OF ALL WARRANTIES. + * See the file "license.terms" for information on usage and redistribution of + * this file, and for a DISCLAIMER OF ALL WARRANTIES. */ -#include "tkPort.h" #include "default.h" #include "tkInt.h" -/* Flag values for "sticky"ness The 16 combinations subsume the packer's +/* + * Flag values for "sticky"ness. The 16 combinations subsume the packer's * notion of anchor and fill. * * STICK_NORTH This window sticks to the top of its cavity. @@ -30,16 +30,44 @@ #define STICK_EAST 2 #define STICK_SOUTH 4 #define STICK_WEST 8 + /* * The following table defines the legal values for the -orient option. */ static char *orientStrings[] = { - "horizontal", "vertical", (char *) NULL + "horizontal", "vertical", NULL }; enum orient { ORIENT_HORIZONTAL, ORIENT_VERTICAL }; +/* + * The following table defines the legal values for the -stretch option. + */ + +static char *stretchStrings[] = { + "always", "first", "last", "middle", "never", NULL +}; + +enum stretch { + STRETCH_ALWAYS, /* Always give extra space to this pane. */ + STRETCH_FIRST, /* Give extra space to pane if it is first. */ + STRETCH_LAST, /* Give extra space to pane if it is last. */ + STRETCH_MIDDLE, /* Give extra space to pane only if it is + * neither first nor last. */ + STRETCH_NEVER /* Never give extra space to this pane. */ +}; + +/* + * Codify the stretchiness rule in one place. + */ + +#define IsStretchable(stretch,index,first,last) \ + (((stretch) == STRETCH_ALWAYS) || \ + ((stretch) == STRETCH_FIRST && (index) == (first)) || \ + ((stretch) == STRETCH_LAST && (index) == (last)) || \ + ((stretch) == STRETCH_MIDDLE && (index) != (first) && (index) != (last))) + typedef struct { Tk_OptionTable pwOptions; /* Token for paned window option table. */ Tk_OptionTable slaveOpts; /* Token for slave cget option table. */ @@ -51,35 +79,38 @@ typedef struct { */ typedef struct Slave { - Tk_Window tkwin; /* Window being managed. */ - - int minSize; /* Minimum size of this pane, on the - * relevant axis, in pixels. */ - int padx; /* Additional padding requested for - * slave, in the x dimension. */ - int pady; /* Additional padding requested for - * slave, in the y dimension. */ - Tcl_Obj *widthPtr, *heightPtr; /* Tcl_Obj rep's of slave width/height, - * to allow for null values. */ - int width; /* Slave width. */ - int height; /* Slave height. */ - int sticky; /* Sticky string. */ - int x, y; /* Coordinates of the widget. */ - int paneWidth, paneHeight; /* Pane dimensions (may be different - * from slave width/height). */ - int sashx, sashy; /* Coordinates of the sash of the - * right or bottom of this pane. */ - int markx, marky; /* Coordinates of the last mark set - * for the sash. */ - int handlex, handley; /* Coordinates of the sash handle. */ - struct PanedWindow *masterPtr; /* Paned window managing the window. */ - Tk_Window after; /* Placeholder for parsing options. */ - Tk_Window before; /* Placeholder for parsing options. */ + Tk_Window tkwin; /* Window being managed. */ + int minSize; /* Minimum size of this pane, on the relevant + * axis, in pixels. */ + int padx; /* Additional padding requested for slave, in + * the x dimension. */ + int pady; /* Additional padding requested for slave, in + * the y dimension. */ + Tcl_Obj *widthPtr, *heightPtr; + /* Tcl_Obj rep's of slave width/height, to + * allow for null values. */ + int width; /* Slave width. */ + int height; /* Slave height. */ + int sticky; /* Sticky string. */ + int x, y; /* Coordinates of the widget. */ + int paneWidth, paneHeight; /* Pane dimensions (may be different from + * slave width/height). */ + int sashx, sashy; /* Coordinates of the sash of the right or + * bottom of this pane. */ + int markx, marky; /* Coordinates of the last mark set for the + * sash. */ + int handlex, handley; /* Coordinates of the sash handle. */ + enum stretch stretch; /* Controls how slave grows/shrinks */ + int hide; /* Controls visibility of pane */ + struct PanedWindow *masterPtr; + /* Paned window managing the window. */ + Tk_Window after; /* Placeholder for parsing options. */ + Tk_Window before; /* Placeholder for parsing options. */ } Slave; /* - * A data structure of the following type is kept for each paned window - * widget managed by this file: + * A data structure of the following type is kept for each paned window widget + * managed by this file: */ typedef struct PanedWindow { @@ -101,7 +132,6 @@ typedef struct PanedWindow { Tk_Cursor cursor; /* Current cursor for window, or None. */ int resizeOpaque; /* Boolean indicating whether resize should be * opaque or rubberband style. */ - int sashRelief; /* Relief used to draw sash. */ int sashWidth; /* Width of each sash, in pixels. */ Tcl_Obj *sashWidthPtr; /* Tcl_Obj rep for sash width. */ @@ -114,7 +144,6 @@ typedef struct PanedWindow { int handlePad; /* Distance from border to draw handle. */ Tcl_Obj *handleSizePtr; /* Tcl_Obj rep for handle size. */ Tk_Cursor sashCursor; /* Cursor used when mouse is above a sash. */ - GC gc; /* Graphics context for copying from * off-screen pixmap onto screen. */ int proxyx, proxyy; /* Proxy x,y coordinates. */ @@ -127,11 +156,11 @@ typedef struct PanedWindow { /* * Flags used for paned windows: * - * REDRAW_PENDING: Non-zero means a DoWhenIdle handler has - * been queued to redraw this window. + * REDRAW_PENDING: Non-zero means a DoWhenIdle handler has been + * queued to redraw this window. * - * WIDGET_DELETED: Non-zero means that the paned window has - * been, or is in the process of being, deleted. + * WIDGET_DELETED: Non-zero means that the paned window has been, + * or is in the process of being, deleted. * * RESIZE_PENDING: Non-zero means that the window might need to * change its size (or the size of its panes) @@ -147,59 +176,63 @@ typedef struct PanedWindow { #define RESIZE_PENDING 0x0020 /* - * Forward declarations for procedures defined later in this file: + * Forward declarations for functions defined later in this file: */ -int Tk_PanedWindowObjCmd _ANSI_ARGS_((ClientData clientData, - Tcl_Interp *interp, int objc, Tcl_Obj * CONST objv[])); -static void PanedWindowCmdDeletedProc _ANSI_ARGS_((ClientData clientData)); -static int ConfigurePanedWindow _ANSI_ARGS_((Tcl_Interp *interp, - PanedWindow *pwPtr, int objc, Tcl_Obj *CONST objv[])); -static void DestroyPanedWindow _ANSI_ARGS_((PanedWindow *pwPtr)); -static void DisplayPanedWindow _ANSI_ARGS_((ClientData clientData)); -static void PanedWindowEventProc _ANSI_ARGS_((ClientData clientData, - XEvent *eventPtr)); -static void ProxyWindowEventProc _ANSI_ARGS_((ClientData clientData, - XEvent *eventPtr)); -static void DisplayProxyWindow _ANSI_ARGS_((ClientData clientData)); -static void PanedWindowWorldChanged _ANSI_ARGS_((ClientData instanceData)); -static int PanedWindowWidgetObjCmd _ANSI_ARGS_((ClientData clientData, - Tcl_Interp *, int objc, Tcl_Obj * CONST objv[])); -static void PanedWindowLostSlaveProc _ANSI_ARGS_((ClientData clientData, - Tk_Window tkwin)); -static void PanedWindowReqProc _ANSI_ARGS_((ClientData clientData, - Tk_Window tkwin)); -static void ArrangePanes _ANSI_ARGS_((ClientData clientData)); -static void Unlink _ANSI_ARGS_((Slave *slavePtr)); -static Slave * GetPane _ANSI_ARGS_((PanedWindow *pwPtr, Tk_Window tkwin)); -static void SlaveStructureProc _ANSI_ARGS_((ClientData clientData, - XEvent *eventPtr)); -static int PanedWindowSashCommand _ANSI_ARGS_((PanedWindow *pwPtr, - Tcl_Interp *interp, int objc, Tcl_Obj * CONST objv[])); -static int PanedWindowProxyCommand _ANSI_ARGS_((PanedWindow *pwPtr, - Tcl_Interp *interp, int objc, Tcl_Obj * CONST objv[])); -static void ComputeGeometry _ANSI_ARGS_((PanedWindow *pwPtr)); -static int ConfigureSlaves _ANSI_ARGS_((PanedWindow *pwPtr, - Tcl_Interp *interp, int objc, Tcl_Obj * CONST objv[])); -static void DestroyOptionTables _ANSI_ARGS_((ClientData clientData, - Tcl_Interp *interp)); -static int SetSticky _ANSI_ARGS_((ClientData clientData, - Tcl_Interp *interp, Tk_Window tkwin, - Tcl_Obj **value, char *recordPtr, int internalOffset, - char *oldInternalPtr, int flags)); -static Tcl_Obj *GetSticky _ANSI_ARGS_((ClientData clientData, Tk_Window tkwin, - char *recordPtr, int internalOffset)); -static void RestoreSticky _ANSI_ARGS_((ClientData clientData, - Tk_Window tkwin, char *internalPtr, - char *oldInternalPtr)); -static void AdjustForSticky _ANSI_ARGS_((int sticky, int cavityWidth, - int cavityHeight, int *xPtr, int *yPtr, - int *slaveWidthPtr, int *slaveHeightPtr)); -static void MoveSash _ANSI_ARGS_((PanedWindow *pwPtr, int sash, int diff)); -static int ObjectIsEmpty _ANSI_ARGS_((Tcl_Obj *objPtr)); -static char * ComputeSlotAddress _ANSI_ARGS_((char *recordPtr, int offset)); -static int PanedWindowIdentifyCoords _ANSI_ARGS_((PanedWindow *pwPtr, - Tcl_Interp *interp, int x, int y)); +int Tk_PanedWindowObjCmd(ClientData clientData, + Tcl_Interp *interp, int objc, + Tcl_Obj *CONST objv[]); +static void PanedWindowCmdDeletedProc(ClientData clientData); +static int ConfigurePanedWindow(Tcl_Interp *interp, + PanedWindow *pwPtr, int objc, + Tcl_Obj *CONST objv[]); +static void DestroyPanedWindow(PanedWindow *pwPtr); +static void DisplayPanedWindow(ClientData clientData); +static void PanedWindowEventProc(ClientData clientData, + XEvent *eventPtr); +static void ProxyWindowEventProc(ClientData clientData, + XEvent *eventPtr); +static void DisplayProxyWindow(ClientData clientData); +static void PanedWindowWorldChanged(ClientData instanceData); +static int PanedWindowWidgetObjCmd(ClientData clientData, + Tcl_Interp *, int objc, Tcl_Obj * CONST objv[]); +static void PanedWindowLostSlaveProc(ClientData clientData, + Tk_Window tkwin); +static void PanedWindowReqProc(ClientData clientData, + Tk_Window tkwin); +static void ArrangePanes(ClientData clientData); +static void Unlink(Slave *slavePtr); +static Slave * GetPane(PanedWindow *pwPtr, Tk_Window tkwin); +static void SlaveStructureProc(ClientData clientData, + XEvent *eventPtr); +static int PanedWindowSashCommand(PanedWindow *pwPtr, + Tcl_Interp *interp, int objc, + Tcl_Obj * CONST objv[]); +static int PanedWindowProxyCommand(PanedWindow *pwPtr, + Tcl_Interp *interp, int objc, + Tcl_Obj * CONST objv[]); +static void ComputeGeometry(PanedWindow *pwPtr); +static int ConfigureSlaves(PanedWindow *pwPtr, + Tcl_Interp *interp, int objc, + Tcl_Obj * CONST objv[]); +static void DestroyOptionTables(ClientData clientData, + Tcl_Interp *interp); +static int SetSticky(ClientData clientData, Tcl_Interp *interp, + Tk_Window tkwin, Tcl_Obj **value, char *recordPtr, + int internalOffset, char *oldInternalPtr, + int flags); +static Tcl_Obj * GetSticky(ClientData clientData, Tk_Window tkwin, + char *recordPtr, int internalOffset); +static void RestoreSticky(ClientData clientData, Tk_Window tkwin, + char *internalPtr, char *oldInternalPtr); +static void AdjustForSticky(int sticky, int cavityWidth, + int cavityHeight, int *xPtr, int *yPtr, + int *slaveWidthPtr, int *slaveHeightPtr); +static void MoveSash(PanedWindow *pwPtr, int sash, int diff); +static int ObjectIsEmpty(Tcl_Obj *objPtr); +static char * ComputeSlotAddress(char *recordPtr, int offset); +static int PanedWindowIdentifyCoords(PanedWindow *pwPtr, + Tcl_Interp *interp, int x, int y); /* * Sashes are between panes only, so there is one less sash than slaves @@ -208,7 +241,7 @@ static int PanedWindowIdentifyCoords _ANSI_ARGS_((PanedWindow *pwPtr, #define ValidSashIndex(pwPtr, sash) \ (((sash) >= 0) && ((sash) < ((pwPtr)->numSlaves-1))) -static Tk_GeomMgr panedWindowMgrType = { +static const Tk_GeomMgr panedWindowMgrType = { "panedwindow", /* name */ PanedWindowReqProc, /* requestProc */ PanedWindowLostSlaveProc, /* lostSlaveProc */ @@ -226,31 +259,31 @@ static Tk_GeomMgr panedWindowMgrType = { */ static Tk_ObjCustomOption stickyOption = { - "sticky", /* name */ - SetSticky, /* setProc */ - GetSticky, /* getProc */ - RestoreSticky, /* restoreProc */ - (Tk_CustomOptionFreeProc *)NULL, /* freeProc */ + "sticky", /* name */ + SetSticky, /* setProc */ + GetSticky, /* getProc */ + RestoreSticky, /* restoreProc */ + NULL, /* freeProc */ 0 }; -static Tk_OptionSpec optionSpecs[] = { +static const Tk_OptionSpec optionSpecs[] = { {TK_OPTION_BORDER, "-background", "background", "Background", DEF_PANEDWINDOW_BG_COLOR, -1, Tk_Offset(PanedWindow, background), 0, (ClientData) DEF_PANEDWINDOW_BG_MONO}, - {TK_OPTION_SYNONYM, "-bd", (char *) NULL, (char *) NULL, - (char *) NULL, 0, -1, 0, (ClientData) "-borderwidth"}, - {TK_OPTION_SYNONYM, "-bg", (char *) NULL, (char *) NULL, - (char *) NULL, 0, -1, 0, (ClientData) "-background"}, + {TK_OPTION_SYNONYM, "-bd", NULL, NULL, + NULL, 0, -1, 0, (ClientData) "-borderwidth"}, + {TK_OPTION_SYNONYM, "-bg", NULL, NULL, + NULL, 0, -1, 0, (ClientData) "-background"}, {TK_OPTION_PIXELS, "-borderwidth", "borderWidth", "BorderWidth", DEF_PANEDWINDOW_BORDERWIDTH, -1, Tk_Offset(PanedWindow, borderWidth), - 0, 0, GEOMETRY}, + 0, 0, GEOMETRY}, {TK_OPTION_CURSOR, "-cursor", "cursor", "Cursor", DEF_PANEDWINDOW_CURSOR, -1, Tk_Offset(PanedWindow, cursor), TK_OPTION_NULL_OK, 0, 0}, {TK_OPTION_PIXELS, "-handlepad", "handlePad", "HandlePad", DEF_PANEDWINDOW_HANDLEPAD, -1, Tk_Offset(PanedWindow, handlePad), - 0, 0, GEOMETRY}, + 0, 0, GEOMETRY}, {TK_OPTION_PIXELS, "-handlesize", "handleSize", "HandleSize", DEF_PANEDWINDOW_HANDLESIZE, Tk_Offset(PanedWindow, handleSizePtr), Tk_Offset(PanedWindow, handleSize), 0, 0, GEOMETRY}, @@ -259,9 +292,9 @@ static Tk_OptionSpec optionSpecs[] = { Tk_Offset(PanedWindow, height), TK_OPTION_NULL_OK, 0, GEOMETRY}, {TK_OPTION_BOOLEAN, "-opaqueresize", "opaqueResize", "OpaqueResize", DEF_PANEDWINDOW_OPAQUERESIZE, -1, - Tk_Offset(PanedWindow, resizeOpaque), 0, 0, 0}, + Tk_Offset(PanedWindow, resizeOpaque), 0, 0, 0}, {TK_OPTION_STRING_TABLE, "-orient", "orient", "Orient", - DEF_PANEDWINDOW_ORIENT, -1, Tk_Offset(PanedWindow, orient), + DEF_PANEDWINDOW_ORIENT, -1, Tk_Offset(PanedWindow, orient), 0, (ClientData) orientStrings, GEOMETRY}, {TK_OPTION_RELIEF, "-relief", "relief", "Relief", DEF_PANEDWINDOW_RELIEF, -1, Tk_Offset(PanedWindow, relief), 0, 0, 0}, @@ -270,55 +303,59 @@ static Tk_OptionSpec optionSpecs[] = { TK_OPTION_NULL_OK, 0, 0}, {TK_OPTION_PIXELS, "-sashpad", "sashPad", "SashPad", DEF_PANEDWINDOW_SASHPAD, -1, Tk_Offset(PanedWindow, sashPad), - 0, 0, GEOMETRY}, + 0, 0, GEOMETRY}, {TK_OPTION_RELIEF, "-sashrelief", "sashRelief", "Relief", DEF_PANEDWINDOW_SASHRELIEF, -1, Tk_Offset(PanedWindow, sashRelief), - 0, 0, 0}, + 0, 0, 0}, {TK_OPTION_PIXELS, "-sashwidth", "sashWidth", "Width", DEF_PANEDWINDOW_SASHWIDTH, Tk_Offset(PanedWindow, sashWidthPtr), Tk_Offset(PanedWindow, sashWidth), 0, 0, GEOMETRY}, {TK_OPTION_BOOLEAN, "-showhandle", "showHandle", "ShowHandle", DEF_PANEDWINDOW_SHOWHANDLE, -1, Tk_Offset(PanedWindow, showHandle), - 0, 0, GEOMETRY}, + 0, 0, GEOMETRY}, {TK_OPTION_PIXELS, "-width", "width", "Width", DEF_PANEDWINDOW_WIDTH, Tk_Offset(PanedWindow, widthPtr), Tk_Offset(PanedWindow, width), TK_OPTION_NULL_OK, 0, GEOMETRY}, {TK_OPTION_END} }; -static Tk_OptionSpec slaveOptionSpecs[] = { - {TK_OPTION_WINDOW, "-after", (char *) NULL, (char *) NULL, +static const Tk_OptionSpec slaveOptionSpecs[] = { + {TK_OPTION_WINDOW, "-after", NULL, NULL, DEF_PANEDWINDOW_PANE_AFTER, -1, Tk_Offset(Slave, after), - TK_OPTION_NULL_OK, 0, 0}, - {TK_OPTION_WINDOW, "-before", (char *) NULL, (char *) NULL, - DEF_PANEDWINDOW_PANE_BEFORE, -1, Tk_Offset(Slave, before), - TK_OPTION_NULL_OK, 0, 0}, - {TK_OPTION_PIXELS, "-height", (char *) NULL, (char *) NULL, + TK_OPTION_NULL_OK, 0, 0}, + {TK_OPTION_WINDOW, "-before", NULL, NULL, + DEF_PANEDWINDOW_PANE_BEFORE, -1, Tk_Offset(Slave, before), + TK_OPTION_NULL_OK, 0, 0}, + {TK_OPTION_PIXELS, "-height", NULL, NULL, DEF_PANEDWINDOW_PANE_HEIGHT, Tk_Offset(Slave, heightPtr), - Tk_Offset(Slave, height), TK_OPTION_NULL_OK, 0, 0}, - {TK_OPTION_PIXELS, "-minsize", (char *) NULL, (char *) NULL, + Tk_Offset(Slave, height), TK_OPTION_NULL_OK, 0, 0}, + {TK_OPTION_BOOLEAN, "-hide", "hide", "Hide", + DEF_PANEDWINDOW_PANE_HIDE, -1, Tk_Offset(Slave, hide), 0,0,GEOMETRY}, + {TK_OPTION_PIXELS, "-minsize", NULL, NULL, DEF_PANEDWINDOW_PANE_MINSIZE, -1, Tk_Offset(Slave, minSize), 0, 0, 0}, - {TK_OPTION_PIXELS, "-padx", (char *) NULL, (char *) NULL, + {TK_OPTION_PIXELS, "-padx", NULL, NULL, DEF_PANEDWINDOW_PANE_PADX, -1, Tk_Offset(Slave, padx), 0, 0, 0}, - {TK_OPTION_PIXELS, "-pady", (char *) NULL, (char *) NULL, + {TK_OPTION_PIXELS, "-pady", NULL, NULL, DEF_PANEDWINDOW_PANE_PADY, -1, Tk_Offset(Slave, pady), 0, 0, 0}, - {TK_OPTION_CUSTOM, "-sticky", (char *) NULL, (char *) NULL, + {TK_OPTION_CUSTOM, "-sticky", NULL, NULL, DEF_PANEDWINDOW_PANE_STICKY, -1, Tk_Offset(Slave, sticky), 0, - (ClientData) &stickyOption, 0}, - {TK_OPTION_PIXELS, "-width", (char *) NULL, (char *) NULL, + (ClientData) &stickyOption, 0}, + {TK_OPTION_STRING_TABLE, "-stretch", "stretch", "Stretch", + DEF_PANEDWINDOW_PANE_STRETCH, -1, Tk_Offset(Slave, stretch), 0, + (ClientData) stretchStrings, 0}, + {TK_OPTION_PIXELS, "-width", NULL, NULL, DEF_PANEDWINDOW_PANE_WIDTH, Tk_Offset(Slave, widthPtr), - Tk_Offset(Slave, width), TK_OPTION_NULL_OK, 0, 0}, + Tk_Offset(Slave, width), TK_OPTION_NULL_OK, 0, 0}, {TK_OPTION_END} }; - /* *-------------------------------------------------------------- * * Tk_PanedWindowObjCmd -- * - * This procedure is invoked to process the "panedwindow" Tcl - * command. It creates a new "panedwindow" widget. + * This function is invoked to process the "panedwindow" Tcl command. It + * creates a new "panedwindow" widget. * * Results: * A standard Tcl result. @@ -330,11 +367,11 @@ static Tk_OptionSpec slaveOptionSpecs[] = { */ int -Tk_PanedWindowObjCmd(clientData, interp, objc, objv) - ClientData clientData; /* NULL. */ - Tcl_Interp *interp; /* Current interpreter. */ - int objc; /* Number of arguments. */ - Tcl_Obj * CONST objv[]; /* Argument objects. */ +Tk_PanedWindowObjCmd( + ClientData clientData, /* NULL. */ + Tcl_Interp *interp, /* Current interpreter. */ + int objc, /* Number of arguments. */ + Tcl_Obj * CONST objv[]) /* Argument objects. */ { PanedWindow *pwPtr; Tk_Window tkwin, parent; @@ -346,27 +383,35 @@ Tk_PanedWindowObjCmd(clientData, interp, objc, objv) return TCL_ERROR; } - tkwin = Tk_CreateWindowFromPath(interp, Tk_MainWindow(interp), + tkwin = Tk_CreateWindowFromPath(interp, Tk_MainWindow(interp), Tcl_GetStringFromObj(objv[1], NULL), NULL); if (tkwin == NULL) { return TCL_ERROR; } pwOpts = (OptionTables *) - Tcl_GetAssocData(interp, "PanedWindowOptionTables", NULL); + Tcl_GetAssocData(interp, "PanedWindowOptionTables", NULL); if (pwOpts == NULL) { /* - * The first time this procedure is invoked, the option tables will - * be NULL. We then create the option tables from the templates - * and store a pointer to the tables as the command's clinical so - * we'll have easy access to it in the future. + * The first time this function is invoked, the option tables will be + * NULL. We then create the option tables from the templates and store + * a pointer to the tables as the command's clinical so we'll have + * easy access to it in the future. */ + pwOpts = (OptionTables *) ckalloc(sizeof(OptionTables)); - /* Set up an exit handler to free the optionTables struct */ + + /* + * Set up an exit handler to free the optionTables struct. + */ + Tcl_SetAssocData(interp, "PanedWindowOptionTables", DestroyOptionTables, (ClientData) pwOpts); - /* Create the paned window option tables. */ + /* + * Create the paned window option tables. + */ + pwOpts->pwOptions = Tk_CreateOptionTable(interp, optionSpecs); pwOpts->slaveOpts = Tk_CreateOptionTable(interp, slaveOptionSpecs); } @@ -379,18 +424,18 @@ Tk_PanedWindowObjCmd(clientData, interp, objc, objv) pwPtr = (PanedWindow *) ckalloc(sizeof(PanedWindow)); memset((void *)pwPtr, 0, (sizeof(PanedWindow))); - pwPtr->tkwin = tkwin; - pwPtr->display = Tk_Display(tkwin); - pwPtr->interp = interp; - pwPtr->widgetCmd = Tcl_CreateObjCommand(interp, + pwPtr->tkwin = tkwin; + pwPtr->display = Tk_Display(tkwin); + pwPtr->interp = interp; + pwPtr->widgetCmd = Tcl_CreateObjCommand(interp, Tk_PathName(pwPtr->tkwin), PanedWindowWidgetObjCmd, (ClientData) pwPtr, PanedWindowCmdDeletedProc); - pwPtr->optionTable = pwOpts->pwOptions; - pwPtr->slaveOpts = pwOpts->slaveOpts; - pwPtr->relief = TK_RELIEF_RAISED; - pwPtr->gc = None; - pwPtr->cursor = None; - pwPtr->sashCursor = None; + pwPtr->optionTable = pwOpts->pwOptions; + pwPtr->slaveOpts = pwOpts->slaveOpts; + pwPtr->relief = TK_RELIEF_RAISED; + pwPtr->gc = None; + pwPtr->cursor = None; + pwPtr->sashCursor = None; /* * Keep a hold of the associated tkwin until we destroy the widget, @@ -409,10 +454,11 @@ Tk_PanedWindowObjCmd(clientData, interp, objc, objv) PanedWindowEventProc, (ClientData) pwPtr); /* - * Find the toplevel ancestor of the panedwindow, and make a proxy - * win as a child of that window; this way the proxy can always float - * above slaves in the panedwindow. + * Find the toplevel ancestor of the panedwindow, and make a proxy win as + * a child of that window; this way the proxy can always float above + * slaves in the panedwindow. */ + parent = Tk_Parent(pwPtr->tkwin); while (!(Tk_IsTopLevel(parent))) { parent = Tk_Parent(parent); @@ -422,15 +468,16 @@ Tk_PanedWindowObjCmd(clientData, interp, objc, objv) } } - pwPtr->proxywin = Tk_CreateAnonymousWindow(interp, parent, (char *) NULL); + pwPtr->proxywin = Tk_CreateAnonymousWindow(interp, parent, NULL); + /* - * The proxy window has to be able to share GCs with the main - * panedwindow despite being children of windows with potentially - * different characteristics, and it looks better that way too. - * [Bug 702230] - * Also Set the X window save under attribute to avoid expose events as - * the proxy sash is dragged across the panes. [Bug 1036963] + * The proxy window has to be able to share GCs with the main panedwindow + * despite being children of windows with potentially different + * characteristics, and it looks better that way too. [Bug 702230] Also + * set the X window save under attribute to avoid expose events as the + * proxy sash is dragged across the panes. [Bug 1036963] */ + Tk_SetWindowVisual(pwPtr->proxywin, Tk_Visual(tkwin), Tk_Depth(tkwin), Tk_Colormap(tkwin)); Tk_CreateEventHandler(pwPtr->proxywin, ExposureMask, ProxyWindowEventProc, @@ -453,9 +500,9 @@ Tk_PanedWindowObjCmd(clientData, interp, objc, objv) * * PanedWindowWidgetObjCmd -- * - * This procedure is invoked to process the Tcl command - * that corresponds to a widget managed by this module. - * See the user documentation for details on what it does. + * This function is invoked to process the Tcl command that corresponds + * to a widget managed by this module. See the user documentation for + * details on what it does. * * Results: * A standard Tcl result. @@ -467,26 +514,27 @@ Tk_PanedWindowObjCmd(clientData, interp, objc, objv) */ static int -PanedWindowWidgetObjCmd(clientData, interp, objc, objv) - ClientData clientData; /* Information about square widget. */ - Tcl_Interp *interp; /* Current interpreter. */ - int objc; /* Number of arguments. */ - Tcl_Obj * CONST objv[]; /* Argument objects. */ +PanedWindowWidgetObjCmd( + ClientData clientData, /* Information about square widget. */ + Tcl_Interp *interp, /* Current interpreter. */ + int objc, /* Number of arguments. */ + Tcl_Obj * CONST objv[]) /* Argument objects. */ { PanedWindow *pwPtr = (PanedWindow *) clientData; int result = TCL_OK; - static CONST char *optionStrings[] = {"add", "cget", "configure", "forget", - "identify", "panecget", - "paneconfigure", "panes", - "proxy", "sash", (char *) NULL}; - enum options { PW_ADD, PW_CGET, PW_CONFIGURE, PW_FORGET, PW_IDENTIFY, - PW_PANECGET, PW_PANECONFIGURE, PW_PANES, PW_PROXY, - PW_SASH }; + static CONST char *optionStrings[] = { + "add", "cget", "configure", "forget", "identify", "panecget", + "paneconfigure", "panes", "proxy", "sash", NULL + }; + enum options { + PW_ADD, PW_CGET, PW_CONFIGURE, PW_FORGET, PW_IDENTIFY, PW_PANECGET, + PW_PANECONFIGURE, PW_PANES, PW_PROXY, PW_SASH + }; Tcl_Obj *resultObj; int index, count, i, x, y; Tk_Window tkwin; Slave *slavePtr; - + if (objc < 2) { Tcl_WrongNumArgs(interp, 1, objv, "option ?arg arg...?"); return TCL_ERROR; @@ -498,196 +546,177 @@ PanedWindowWidgetObjCmd(clientData, interp, objc, objv) } Tcl_Preserve((ClientData) pwPtr); - + switch ((enum options) index) { - case PW_ADD: { - if (objc < 3) { - Tcl_WrongNumArgs(interp, 2, objv, "widget ?widget ...?"); - result = TCL_ERROR; - break; - } - - result = ConfigureSlaves(pwPtr, interp, objc, objv); + case PW_ADD: + if (objc < 3) { + Tcl_WrongNumArgs(interp, 2, objv, "widget ?widget ...?"); + result = TCL_ERROR; break; } - - case PW_CGET: { - if (objc != 3) { - Tcl_WrongNumArgs(interp, 2, objv, "option"); - result = TCL_ERROR; - break; - } - resultObj = Tk_GetOptionValue(interp, (char *) pwPtr, - pwPtr->optionTable, objv[2], pwPtr->tkwin); + result = ConfigureSlaves(pwPtr, interp, objc, objv); + break; + + case PW_CGET: + if (objc != 3) { + Tcl_WrongNumArgs(interp, 2, objv, "option"); + result = TCL_ERROR; + break; + } + resultObj = Tk_GetOptionValue(interp, (char *) pwPtr, + pwPtr->optionTable, objv[2], pwPtr->tkwin); + if (resultObj == NULL) { + result = TCL_ERROR; + } else { + Tcl_SetObjResult(interp, resultObj); + } + break; + + case PW_CONFIGURE: + resultObj = NULL; + if (objc <= 3) { + resultObj = Tk_GetOptionInfo(interp, (char *) pwPtr, + pwPtr->optionTable, + (objc == 3) ? objv[2] : NULL, pwPtr->tkwin); if (resultObj == NULL) { result = TCL_ERROR; } else { Tcl_SetObjResult(interp, resultObj); } + } else { + result = ConfigurePanedWindow(interp, pwPtr, objc - 2, objv + 2); + } + break; + + case PW_FORGET: { + int i; + + if (objc < 3) { + Tcl_WrongNumArgs(interp, 2, objv, "widget ?widget ...?"); + result = TCL_ERROR; break; } - - case PW_CONFIGURE: { - resultObj = NULL; - if (objc <= 3) { - resultObj = Tk_GetOptionInfo(interp, (char *) pwPtr, - pwPtr->optionTable, - (objc == 3) ? objv[2] : (Tcl_Obj *) NULL, - pwPtr->tkwin); - if (resultObj == NULL) { - result = TCL_ERROR; - } else { - Tcl_SetObjResult(interp, resultObj); - } - } else { - result = ConfigurePanedWindow(interp, pwPtr, objc - 2, - objv + 2); + + /* + * Clean up each window named in the arg list. + */ + for (count = 0, i = 2; i < objc; i++) { + Tk_Window slave = Tk_NameToWindow(interp, Tcl_GetString(objv[i]), + pwPtr->tkwin); + if (slave == NULL) { + continue; + } + slavePtr = GetPane(pwPtr, slave); + if ((slavePtr != NULL) && (slavePtr->masterPtr != NULL)) { + count++; + Tk_ManageGeometry(slave, NULL, (ClientData)NULL); + Tk_UnmaintainGeometry(slavePtr->tkwin, pwPtr->tkwin); + Tk_DeleteEventHandler(slavePtr->tkwin, StructureNotifyMask, + SlaveStructureProc, (ClientData) slavePtr); + Tk_UnmapWindow(slavePtr->tkwin); + Unlink(slavePtr); + } + if (count != 0) { + ComputeGeometry(pwPtr); } + } + break; + } + + case PW_IDENTIFY: + if (objc != 4) { + Tcl_WrongNumArgs(interp, 2, objv, "x y"); + result = TCL_ERROR; break; } - - case PW_FORGET: { - Tk_Window slave; - int i; - - if (objc < 3) { - Tcl_WrongNumArgs(interp, 2, objv, "widget ?widget ...?"); - result = TCL_ERROR; - break; - } - /* - * Clean up each window named in the arg list. - */ - for (count = 0, i = 2; i < objc; i++) { - slave = Tk_NameToWindow(interp, Tcl_GetString(objv[i]), - pwPtr->tkwin); - if (slave == NULL) { - continue; - } - slavePtr = GetPane(pwPtr, slave); - if ((slavePtr != NULL) && (slavePtr->masterPtr != NULL)) { - count++; - Tk_ManageGeometry(slave, (Tk_GeomMgr *) NULL, - (ClientData) NULL); - Tk_UnmaintainGeometry(slavePtr->tkwin, pwPtr->tkwin); - Tk_DeleteEventHandler(slavePtr->tkwin, StructureNotifyMask, - SlaveStructureProc, (ClientData) slavePtr); - Tk_UnmapWindow(slavePtr->tkwin); - Unlink(slavePtr); - } - if (count != 0) { - ComputeGeometry(pwPtr); - } - } + if ((Tcl_GetIntFromObj(interp, objv[2], &x) != TCL_OK) + || (Tcl_GetIntFromObj(interp, objv[3], &y) != TCL_OK)) { + result = TCL_ERROR; break; } + result = PanedWindowIdentifyCoords(pwPtr, interp, x, y); + break; - case PW_IDENTIFY: { - if (objc != 4) { - Tcl_WrongNumArgs(interp, 2, objv, "x y"); - result = TCL_ERROR; - break; + case PW_PANECGET: + if (objc != 4) { + Tcl_WrongNumArgs(interp, 2, objv, "pane option"); + result = TCL_ERROR; + break; + } + tkwin = Tk_NameToWindow(interp, Tcl_GetString(objv[2]), pwPtr->tkwin); + if (tkwin == NULL) { + result = TCL_ERROR; + break; + } + resultObj = NULL; + for (i = 0; i < pwPtr->numSlaves; i++) { + if (pwPtr->slaves[i]->tkwin == tkwin) { + resultObj = Tk_GetOptionValue(interp, + (char *) pwPtr->slaves[i], pwPtr->slaveOpts, + objv[3], tkwin); } + } + if (i == pwPtr->numSlaves) { + Tcl_SetResult(interp, "not managed by this window", TCL_STATIC); + } + if (resultObj == NULL) { + result = TCL_ERROR; + } else { + Tcl_SetObjResult(interp, resultObj); + } + break; - if ((Tcl_GetIntFromObj(interp, objv[2], &x) != TCL_OK) - || (Tcl_GetIntFromObj(interp, objv[3], &y) != TCL_OK)) { - result = TCL_ERROR; - break; - } - - result = PanedWindowIdentifyCoords(pwPtr, interp, x, y); + case PW_PANECONFIGURE: + if (objc < 3) { + Tcl_WrongNumArgs(interp, 2, objv, + "pane ?option? ?value option value ...?"); + result = TCL_ERROR; break; } - - case PW_PANECGET: { - if (objc != 4) { - Tcl_WrongNumArgs(interp, 2, objv, "pane option"); - result = TCL_ERROR; - break; - } + resultObj = NULL; + if (objc <= 4) { tkwin = Tk_NameToWindow(interp, Tcl_GetString(objv[2]), pwPtr->tkwin); - if (tkwin == NULL) { - result = TCL_ERROR; - break; - } - resultObj = NULL; for (i = 0; i < pwPtr->numSlaves; i++) { if (pwPtr->slaves[i]->tkwin == tkwin) { - resultObj = Tk_GetOptionValue(interp, + resultObj = Tk_GetOptionInfo(interp, (char *) pwPtr->slaves[i], pwPtr->slaveOpts, - objv[3], tkwin); - } - } - if (i == pwPtr->numSlaves) { - Tcl_SetResult(interp, "not managed by this window", - TCL_STATIC); - } - if (resultObj == NULL) { - result = TCL_ERROR; - } else { - Tcl_SetObjResult(interp, resultObj); - } - break; - } - - case PW_PANECONFIGURE: { - if (objc < 3) { - Tcl_WrongNumArgs(interp, 2, objv, - "pane ?option? ?value option value ...?"); - result = TCL_ERROR; - break; - } - resultObj = NULL; - if (objc <= 4) { - tkwin = Tk_NameToWindow(interp, Tcl_GetString(objv[2]), - pwPtr->tkwin); - for (i = 0; i < pwPtr->numSlaves; i++) { - if (pwPtr->slaves[i]->tkwin == tkwin) { - resultObj = Tk_GetOptionInfo(interp, - (char *) pwPtr->slaves[i], - pwPtr->slaveOpts, - (objc == 4) ? objv[3] : (Tcl_Obj *) NULL, - pwPtr->tkwin); - if (resultObj == NULL) { - result = TCL_ERROR; - } else { - Tcl_SetObjResult(interp, resultObj); - } - break; + (objc == 4) ? objv[3] : NULL, + pwPtr->tkwin); + if (resultObj == NULL) { + result = TCL_ERROR; + } else { + Tcl_SetObjResult(interp, resultObj); } + break; } - } else { - result = ConfigureSlaves(pwPtr, interp, objc, objv); } - break; + } else { + result = ConfigureSlaves(pwPtr, interp, objc, objv); } - - case PW_PANES: { - resultObj = Tcl_NewObj(); + break; - Tcl_IncrRefCount(resultObj); + case PW_PANES: + resultObj = Tcl_NewObj(); - for (i = 0; i < pwPtr->numSlaves; i++) { - Tcl_ListObjAppendElement(interp, resultObj, - Tcl_NewStringObj(Tk_PathName(pwPtr->slaves[i]->tkwin), - -1)); - } - Tcl_SetObjResult(interp, resultObj); - Tcl_DecrRefCount(resultObj); - break; - } + Tcl_IncrRefCount(resultObj); - case PW_PROXY: { - result = PanedWindowProxyCommand(pwPtr, interp, objc, objv); - break; + for (i = 0; i < pwPtr->numSlaves; i++) { + Tcl_ListObjAppendElement(interp, resultObj, + Tcl_NewStringObj(Tk_PathName(pwPtr->slaves[i]->tkwin),-1)); } + Tcl_SetObjResult(interp, resultObj); + Tcl_DecrRefCount(resultObj); + break; - case PW_SASH: { - result = PanedWindowSashCommand(pwPtr, interp, objc, objv); - break; - } + case PW_PROXY: + result = PanedWindowProxyCommand(pwPtr, interp, objc, objv); + break; + + case PW_SASH: + result = PanedWindowSashCommand(pwPtr, interp, objc, objv); + break; } Tcl_Release((ClientData) pwPtr); return result; @@ -698,39 +727,38 @@ PanedWindowWidgetObjCmd(clientData, interp, objc, objv) * * ConfigureSlaves -- * - * Add or alter the configuration options of a slave in a paned - * window. + * Add or alter the configuration options of a slave in a paned window. * * Results: * Standard Tcl result. * * Side effects: - * Depends on options; may add a slave to the paned window, may - * alter the geometry management options of a slave. + * Depends on options; may add a slave to the paned window, may alter the + * geometry management options of a slave. * *---------------------------------------------------------------------- */ static int -ConfigureSlaves(pwPtr, interp, objc, objv) - PanedWindow *pwPtr; /* Information about paned window. */ - Tcl_Interp *interp; /* Current interpreter. */ - int objc; /* Number of arguments. */ - Tcl_Obj * CONST objv[]; /* Argument objects. */ +ConfigureSlaves( + PanedWindow *pwPtr, /* Information about paned window. */ + Tcl_Interp *interp, /* Current interpreter. */ + int objc, /* Number of arguments. */ + Tcl_Obj *CONST objv[]) /* Argument objects. */ { int i, firstOptionArg, j, found, doubleBw, index, numNewSlaves, haveLoc; int insertIndex; Tk_Window tkwin = NULL, ancestor, parent; - Slave *slavePtr, **inserts, **new; + Slave *slavePtr, **inserts, **newSlaves; Slave options; char *arg; - + /* - * Find the non-window name arguments; these are the configure options - * for the slaves. Also validate that the window names given are - * legitimate (ie, they are real windows, they are not the panedwindow - * itself, etc.). + * Find the non-window name arguments; these are the configure options for + * the slaves. Also validate that the window names given are legitimate + * (ie, they are real windows, they are not the panedwindow itself, etc.). */ + for (i = 2; i < objc; i++) { arg = Tcl_GetString(objv[i]); if (arg[0] == '-') { @@ -742,28 +770,32 @@ ConfigureSlaves(pwPtr, interp, objc, objv) * Just a plain old bad window; Tk_NameToWindow filled in an * error message for us. */ + return TCL_ERROR; } else if (tkwin == pwPtr->tkwin) { /* * A panedwindow cannot manage itself. */ + Tcl_ResetResult(interp); Tcl_AppendResult(interp, "can't add ", arg, " to itself", - (char *) NULL); + NULL); return TCL_ERROR; } else if (Tk_IsTopLevel(tkwin)) { /* * A panedwindow cannot manage a toplevel. */ + Tcl_ResetResult(interp); Tcl_AppendResult(interp, "can't add toplevel ", arg, " to ", - Tk_PathName(pwPtr->tkwin), (char *) NULL); + Tk_PathName(pwPtr->tkwin), NULL); return TCL_ERROR; } else { /* * Make sure the panedwindow is the parent of the slave, * or a descendant of the slave's parent. */ + parent = Tk_Parent(tkwin); for (ancestor = pwPtr->tkwin;;ancestor = Tk_Parent(ancestor)) { if (ancestor == parent) { @@ -771,9 +803,8 @@ ConfigureSlaves(pwPtr, interp, objc, objv) } if (Tk_IsTopLevel(ancestor)) { Tcl_ResetResult(interp); - Tcl_AppendResult(interp, "can't add ", arg, - " to ", Tk_PathName(pwPtr->tkwin), - (char *) NULL); + Tcl_AppendResult(interp, "can't add ", arg, " to ", + Tk_PathName(pwPtr->tkwin), NULL); return TCL_ERROR; } } @@ -784,10 +815,11 @@ ConfigureSlaves(pwPtr, interp, objc, objv) /* * Pre-parse the configuration options, to get the before/after specifiers - * into an easy-to-find location (a local variable). Also, check the + * into an easy-to-find location (a local variable). Also, check the * return from Tk_SetOptions once, here, so we can save a little bit of * extra testing in the for loop below. */ + memset((void *)&options, 0, sizeof(Slave)); if (Tk_SetOptions(interp, (char *) &options, pwPtr->slaveOpts, objc - firstOptionArg, objv + firstOptionArg, @@ -797,9 +829,10 @@ ConfigureSlaves(pwPtr, interp, objc, objv) /* * If either -after or -before was given, find the numerical index that - * corresponds to the given window. If both -after and -before are - * given, the option precedence is: -after, then -before. + * corresponds to the given window. If both -after and -before are given, + * the option precedence is: -after, then -before. */ + index = -1; haveLoc = 0; if (options.after != None) { @@ -823,14 +856,14 @@ ConfigureSlaves(pwPtr, interp, objc, objv) } /* - * If a window was given for -after/-before, but it's not a window - * managed by the panedwindow, throw an error + * If a window was given for -after/-before, but it's not a window managed + * by the panedwindow, throw an error */ + if (haveLoc && index == -1) { Tcl_ResetResult(interp); Tcl_AppendResult(interp, "window \"", Tk_PathName(tkwin), - "\" is not managed by ", Tk_PathName(pwPtr->tkwin), - (char *) NULL); + "\" is not managed by ", Tk_PathName(pwPtr->tkwin), NULL); Tk_FreeConfigOptions((char *) &options, pwPtr->slaveOpts, pwPtr->tkwin); return TCL_ERROR; @@ -838,23 +871,26 @@ ConfigureSlaves(pwPtr, interp, objc, objv) /* * Allocate an array to hold, in order, the pointers to the slave - * structures corresponding to the windows specified. Some of those + * structures corresponding to the windows specified. Some of those * structures may already have existed, some may be new. */ + inserts = (Slave **)ckalloc(sizeof(Slave *) * (firstOptionArg - 2)); insertIndex = 0; - + /* * Populate the inserts array, creating new slave structures as necessary, * applying the options to each structure as we go, and, if necessary, - * marking the spot in the original slaves array as empty (for pre-existing - * slave structures). + * marking the spot in the original slaves array as empty (for + * pre-existing slave structures). */ + for (i = 0, numNewSlaves = 0; i < firstOptionArg - 2; i++) { /* * We don't check that tkwin is NULL here, because the pre-pass above * guarantees that the input at this stage is good. */ + tkwin = Tk_NameToWindow(interp, Tcl_GetString(objv[i + 2]), pwPtr->tkwin); @@ -888,8 +924,8 @@ ConfigureSlaves(pwPtr, interp, objc, objv) /* * Make sure this slave wasn't already put into the inserts array, - * ie, when the user specifies the same window multiple times in - * a single add commaned. + * i.e., when the user specifies the same window multiple times in a + * single add commaned. */ for (j = 0; j < insertIndex; j++) { if (inserts[j]->tkwin == tkwin) { @@ -900,12 +936,12 @@ ConfigureSlaves(pwPtr, interp, objc, objv) if (found) { continue; } - + /* - * Create a new slave structure and initialize it. All slaves - * start out with their "natural" dimensions. + * Create a new slave structure and initialize it. All slaves start + * out with their "natural" dimensions. */ - + slavePtr = (Slave *) ckalloc(sizeof(Slave)); memset(slavePtr, 0, sizeof(Slave)); Tk_InitOptions(interp, (char *)slavePtr, pwPtr->slaveOpts, @@ -913,8 +949,8 @@ ConfigureSlaves(pwPtr, interp, objc, objv) Tk_SetOptions(interp, (char *)slavePtr, pwPtr->slaveOpts, objc - firstOptionArg, objv + firstOptionArg, pwPtr->tkwin, NULL, NULL); - slavePtr->tkwin = tkwin; - slavePtr->masterPtr = pwPtr; + slavePtr->tkwin = tkwin; + slavePtr->masterPtr = pwPtr; doubleBw = 2 * Tk_Changes(slavePtr->tkwin)->border_width; if (slavePtr->width > 0) { slavePtr->paneWidth = slavePtr->width; @@ -943,43 +979,44 @@ ConfigureSlaves(pwPtr, interp, objc, objv) } /* - * Allocate the new slaves array, then copy the slaves into it, in - * order. + * Allocate the new slaves array, then copy the slaves into it, in order. */ + i = sizeof(Slave *) * (pwPtr->numSlaves+numNewSlaves); - new = (Slave **)ckalloc((unsigned) i); - memset(new, 0, (size_t) i); + newSlaves = (Slave **)ckalloc((unsigned) i); + memset(newSlaves, 0, (size_t) i); if (index == -1) { /* * If none of the existing slaves have to be moved, just copy the old * and append the new. */ - memcpy((void *)&(new[0]), pwPtr->slaves, + memcpy((void *)&(newSlaves[0]), pwPtr->slaves, sizeof(Slave *) * pwPtr->numSlaves); - memcpy((void *)&(new[pwPtr->numSlaves]), inserts, + memcpy((void *)&(newSlaves[pwPtr->numSlaves]), inserts, sizeof(Slave *) * numNewSlaves); } else { /* * If some of the existing slaves were moved, the old slaves array * will be partially populated, with some valid and some invalid - * entries. Walk through it, copying valid entries to the new slaves + * entries. Walk through it, copying valid entries to the new slaves * array as we go; when we get to the insert location for the new * slaves, copy the inserts array over, then finish off the old slaves * array. */ + for (i = 0, j = 0; i < index; i++) { if (pwPtr->slaves[i] != NULL) { - new[j] = pwPtr->slaves[i]; + newSlaves[j] = pwPtr->slaves[i]; j++; } } - - memcpy((void *)&(new[j]), inserts, sizeof(Slave *) * (insertIndex)); + + memcpy((void *)&(newSlaves[j]), inserts, sizeof(Slave *)*insertIndex); j += firstOptionArg - 2; - + for (i = index; i < pwPtr->numSlaves; i++) { if (pwPtr->slaves[i] != NULL) { - new[j] = pwPtr->slaves[i]; + newSlaves[j] = pwPtr->slaves[i]; j++; } } @@ -988,17 +1025,19 @@ ConfigureSlaves(pwPtr, interp, objc, objv) /* * Make the new slaves array the paned window's slave array, and clean up. */ + ckfree((void *)pwPtr->slaves); ckfree((void *)inserts); - pwPtr->slaves = new; + pwPtr->slaves = newSlaves; /* * Set the paned window's slave count to the new value. */ + pwPtr->numSlaves += numNewSlaves; Tk_FreeConfigOptions((char *) &options, pwPtr->slaveOpts, pwPtr->tkwin); - + ComputeGeometry(pwPtr); return TCL_OK; } @@ -1008,7 +1047,7 @@ ConfigureSlaves(pwPtr, interp, objc, objv) * * PanedWindowSashCommand -- * - * Implementation of the panedwindow sash subcommand. See the user + * Implementation of the panedwindow sash subcommand. See the user * documentation for details on what it does. * * Results: @@ -1021,133 +1060,132 @@ ConfigureSlaves(pwPtr, interp, objc, objv) */ static int -PanedWindowSashCommand(pwPtr, interp, objc, objv) - PanedWindow *pwPtr; /* Pointer to paned window information. */ - Tcl_Interp *interp; /* Current interpreter. */ - int objc; /* Number of arguments. */ - Tcl_Obj * CONST objv[]; /* Argument objects. */ +PanedWindowSashCommand( + PanedWindow *pwPtr, /* Pointer to paned window information. */ + Tcl_Interp *interp, /* Current interpreter. */ + int objc, /* Number of arguments. */ + Tcl_Obj *CONST objv[]) /* Argument objects. */ { - static CONST char *sashOptionStrings[] = { "coord", "dragto", "mark", - "place", (char *) NULL }; - enum sashOptions { SASH_COORD, SASH_DRAGTO, SASH_MARK, SASH_PLACE }; + static CONST char *sashOptionStrings[] = { + "coord", "dragto", "mark", "place", NULL + }; + enum sashOptions { + SASH_COORD, SASH_DRAGTO, SASH_MARK, SASH_PLACE + }; int index, sash, x, y, diff; Tcl_Obj *coords[2]; Slave *slavePtr; - + if (objc < 3) { Tcl_WrongNumArgs(interp, 2, objv, "option ?arg ...?"); return TCL_ERROR; } - if (Tcl_GetIndexFromObj(interp, objv[2], sashOptionStrings, - "option", 0, &index) != TCL_OK) { + if (Tcl_GetIndexFromObj(interp, objv[2], sashOptionStrings, "option", 0, + &index) != TCL_OK) { return TCL_ERROR; } Tcl_ResetResult(interp); switch ((enum sashOptions) index) { - case SASH_COORD: { - if (objc != 4) { - Tcl_WrongNumArgs(interp, 3, objv, "index"); - return TCL_ERROR; - } + case SASH_COORD: + if (objc != 4) { + Tcl_WrongNumArgs(interp, 3, objv, "index"); + return TCL_ERROR; + } - if (Tcl_GetIntFromObj(interp, objv[3], &sash) != TCL_OK) { - return TCL_ERROR; - } + if (Tcl_GetIntFromObj(interp, objv[3], &sash) != TCL_OK) { + return TCL_ERROR; + } - if (!ValidSashIndex(pwPtr, sash)) { - Tcl_ResetResult(interp); - Tcl_SetResult(interp, "invalid sash index", TCL_STATIC); - return TCL_ERROR; - } - slavePtr = pwPtr->slaves[sash]; - - coords[0] = Tcl_NewIntObj(slavePtr->sashx); - coords[1] = Tcl_NewIntObj(slavePtr->sashy); - Tcl_SetListObj(Tcl_GetObjResult(interp), 2, coords); - break; + if (!ValidSashIndex(pwPtr, sash)) { + Tcl_ResetResult(interp); + Tcl_SetResult(interp, "invalid sash index", TCL_STATIC); + return TCL_ERROR; } + slavePtr = pwPtr->slaves[sash]; - case SASH_MARK: { - if (objc != 6 && objc != 4) { - Tcl_WrongNumArgs(interp, 3, objv, "index ?x y?"); - return TCL_ERROR; - } - - if (Tcl_GetIntFromObj(interp, objv[3], &sash) != TCL_OK) { + coords[0] = Tcl_NewIntObj(slavePtr->sashx); + coords[1] = Tcl_NewIntObj(slavePtr->sashy); + Tcl_SetListObj(Tcl_GetObjResult(interp), 2, coords); + break; + + case SASH_MARK: + if (objc != 6 && objc != 4) { + Tcl_WrongNumArgs(interp, 3, objv, "index ?x y?"); + return TCL_ERROR; + } + + if (Tcl_GetIntFromObj(interp, objv[3], &sash) != TCL_OK) { + return TCL_ERROR; + } + + if (!ValidSashIndex(pwPtr, sash)) { + Tcl_ResetResult(interp); + Tcl_SetResult(interp, "invalid sash index", TCL_STATIC); + return TCL_ERROR; + } + + if (objc == 6) { + if (Tcl_GetIntFromObj(interp, objv[4], &x) != TCL_OK) { return TCL_ERROR; } - if (!ValidSashIndex(pwPtr, sash)) { - Tcl_ResetResult(interp); - Tcl_SetResult(interp, "invalid sash index", TCL_STATIC); + if (Tcl_GetIntFromObj(interp, objv[5], &y) != TCL_OK) { return TCL_ERROR; } - if (objc == 6) { - if (Tcl_GetIntFromObj(interp, objv[4], &x) != TCL_OK) { - return TCL_ERROR; - } - - if (Tcl_GetIntFromObj(interp, objv[5], &y) != TCL_OK) { - return TCL_ERROR; - } + pwPtr->slaves[sash]->markx = x; + pwPtr->slaves[sash]->marky = y; + } else { + coords[0] = Tcl_NewIntObj(pwPtr->slaves[sash]->markx); + coords[1] = Tcl_NewIntObj(pwPtr->slaves[sash]->marky); + Tcl_SetListObj(Tcl_GetObjResult(interp), 2, coords); + } + break; - pwPtr->slaves[sash]->markx = x; - pwPtr->slaves[sash]->marky = y; - } else { - coords[0] = Tcl_NewIntObj(pwPtr->slaves[sash]->markx); - coords[1] = Tcl_NewIntObj(pwPtr->slaves[sash]->marky); - Tcl_SetListObj(Tcl_GetObjResult(interp), 2, coords); - } + case SASH_DRAGTO: + case SASH_PLACE: + if (objc != 6) { + Tcl_WrongNumArgs(interp, 3, objv, "index x y"); + return TCL_ERROR; + } - break; + if (Tcl_GetIntFromObj(interp, objv[3], &sash) != TCL_OK) { + return TCL_ERROR; } - - case SASH_DRAGTO: - case SASH_PLACE: { - if (objc != 6) { - Tcl_WrongNumArgs(interp, 3, objv, "index x y"); - return TCL_ERROR; - } - - if (Tcl_GetIntFromObj(interp, objv[3], &sash) != TCL_OK) { - return TCL_ERROR; - } - if (!ValidSashIndex(pwPtr, sash)) { - Tcl_ResetResult(interp); - Tcl_SetResult(interp, "invalid sash index", TCL_STATIC); - return TCL_ERROR; - } + if (!ValidSashIndex(pwPtr, sash)) { + Tcl_ResetResult(interp); + Tcl_SetResult(interp, "invalid sash index", TCL_STATIC); + return TCL_ERROR; + } - if (Tcl_GetIntFromObj(interp, objv[4], &x) != TCL_OK) { - return TCL_ERROR; - } + if (Tcl_GetIntFromObj(interp, objv[4], &x) != TCL_OK) { + return TCL_ERROR; + } - if (Tcl_GetIntFromObj(interp, objv[5], &y) != TCL_OK) { - return TCL_ERROR; + if (Tcl_GetIntFromObj(interp, objv[5], &y) != TCL_OK) { + return TCL_ERROR; + } + + slavePtr = pwPtr->slaves[sash]; + if (pwPtr->orient == ORIENT_HORIZONTAL) { + if (index == SASH_PLACE) { + diff = x - pwPtr->slaves[sash]->sashx; + } else { + diff = x - pwPtr->slaves[sash]->markx; } - - slavePtr = pwPtr->slaves[sash]; - if (pwPtr->orient == ORIENT_HORIZONTAL) { - if (index == SASH_PLACE) { - diff = x - pwPtr->slaves[sash]->sashx; - } else { - diff = x - pwPtr->slaves[sash]->markx; - } + } else { + if (index == SASH_PLACE) { + diff = y - pwPtr->slaves[sash]->sashy; } else { - if (index == SASH_PLACE) { - diff = y - pwPtr->slaves[sash]->sashy; - } else { - diff = y - pwPtr->slaves[sash]->marky; - } + diff = y - pwPtr->slaves[sash]->marky; } - - MoveSash(pwPtr, sash, diff); - ComputeGeometry(pwPtr); } + + MoveSash(pwPtr, sash, diff); + ComputeGeometry(pwPtr); } return TCL_OK; } @@ -1157,32 +1195,31 @@ PanedWindowSashCommand(pwPtr, interp, objc, objv) * * ConfigurePanedWindow -- * - * This procedure is called to process an argv/argc list in - * conjunction with the Tk option database to configure (or - * reconfigure) a paned window widget. + * This function is called to process an argv/argc list in conjunction + * with the Tk option database to configure (or reconfigure) a paned + * window widget. * * Results: - * The return value is a standard Tcl result. If TCL_ERROR is - * returned, then the interp's result contains an error message. + * The return value is a standard Tcl result. If TCL_ERROR is returned, + * then the interp's result contains an error message. * * Side effects: - * Configuration information, such as colors, border width, - * etc. get set for pwPtr; old resources get freed, - * if there were any. + * Configuration information, such as colors, border width, etc. get set + * for pwPtr; old resources get freed, if there were any. * *---------------------------------------------------------------------- */ static int -ConfigurePanedWindow(interp, pwPtr, objc, objv) - Tcl_Interp *interp; /* Used for error reporting. */ - PanedWindow *pwPtr; /* Information about widget. */ - int objc; /* Number of arguments. */ - Tcl_Obj *CONST objv[]; /* Argument values. */ +ConfigurePanedWindow( + Tcl_Interp *interp, /* Used for error reporting. */ + PanedWindow *pwPtr, /* Information about widget. */ + int objc, /* Number of arguments. */ + Tcl_Obj *CONST objv[]) /* Argument values. */ { Tk_SavedOptions savedOptions; int typemask = 0; - + if (Tk_SetOptions(interp, (char *) pwPtr, pwPtr->optionTable, objc, objv, pwPtr->tkwin, &savedOptions, &typemask) != TCL_OK) { Tk_RestoreSavedOptions(&savedOptions); @@ -1194,14 +1231,14 @@ ConfigurePanedWindow(interp, pwPtr, objc, objv) PanedWindowWorldChanged((ClientData) pwPtr); /* - * If an option that affects geometry has changed, make a relayout + * If an option that affects geometry has changed, make a re-layout * request. */ if (typemask & GEOMETRY) { ComputeGeometry(pwPtr); } - + return TCL_OK; } @@ -1210,9 +1247,9 @@ ConfigurePanedWindow(interp, pwPtr, objc, objv) * * PanedWindowWorldChanged -- * - * This procedure is invoked anytime a paned window's world has - * changed in some way that causes the widget to have to recompute - * graphics contexts and geometry. + * This function is invoked anytime a paned window's world has changed in + * some way that causes the widget to have to recompute graphics contexts + * and geometry. * * Results: * None. @@ -1224,8 +1261,8 @@ ConfigurePanedWindow(interp, pwPtr, objc, objv) */ static void -PanedWindowWorldChanged(instanceData) - ClientData instanceData; /* Information about the paned window. */ +PanedWindowWorldChanged( + ClientData instanceData) /* Information about the paned window. */ { XGCValues gcValues; GC newGC; @@ -1235,7 +1272,7 @@ PanedWindowWorldChanged(instanceData) * Allocated a graphics context for drawing the paned window widget * elements (background, sashes, etc.) and set the window background. */ - + gcValues.background = Tk_3DBorderColor(pwPtr->background)->pixel; newGC = Tk_GetGC(pwPtr->tkwin, GCBackground, &gcValues); if (pwPtr->gc != None) { @@ -1268,23 +1305,23 @@ PanedWindowWorldChanged(instanceData) * * PanedWindowEventProc -- * - * This procedure is invoked by the Tk dispatcher for various - * events on paned windows. + * This function is invoked by the Tk dispatcher for various events on + * paned windows. * * Results: * None. * * Side effects: - * When the window gets deleted, internal structures get - * cleaned up. When it gets exposed, it is redisplayed. + * When the window gets deleted, internal structures get cleaned up. When + * it gets exposed, it is redisplayed. * *-------------------------------------------------------------- */ static void -PanedWindowEventProc(clientData, eventPtr) - ClientData clientData; /* Information about window. */ - XEvent *eventPtr; /* Information about event. */ +PanedWindowEventProc( + ClientData clientData, /* Information about window. */ + XEvent *eventPtr) /* Information about event. */ { PanedWindow *pwPtr = (PanedWindow *) clientData; @@ -1309,9 +1346,9 @@ PanedWindowEventProc(clientData, eventPtr) * * PanedWindowCmdDeletedProc -- * - * This procedure is invoked when a widget command is deleted. If - * the widget isn't already in the process of being destroyed, - * this command destroys it. + * This function is invoked when a widget command is deleted. If the + * widget isn't already in the process of being destroyed, this command + * destroys it. * * Results: * None. @@ -1323,16 +1360,16 @@ PanedWindowEventProc(clientData, eventPtr) */ static void -PanedWindowCmdDeletedProc(clientData) - ClientData clientData; /* Pointer to widget record for widget. */ +PanedWindowCmdDeletedProc( + ClientData clientData) /* Pointer to widget record for widget. */ { PanedWindow *pwPtr = (PanedWindow *) clientData; /* - * This procedure could be invoked either because the window was - * destroyed and the command was then deleted or because the command was - * deleted, and then this procedure destroys the widget. The - * WIDGET_DELETED flag distinguishes these cases. + * This function could be invoked either because the window was destroyed + * and the command was then deleted or because the command was deleted, + * and then this function destroys the widget. The WIDGET_DELETED flag + * distinguishes these cases. */ if (!(pwPtr->flags & WIDGET_DELETED)) { @@ -1346,9 +1383,9 @@ PanedWindowCmdDeletedProc(clientData) * * DisplayPanedWindow -- * - * This procedure redraws the contents of a paned window widget. - * It is invoked as a do-when-idle handler, so it only runs - * when there's nothing else for the application to do. + * This function redraws the contents of a paned window widget. It is + * invoked as a do-when-idle handler, so it only runs when there's + * nothing else for the application to do. * * Results: * None. @@ -1360,8 +1397,8 @@ PanedWindowCmdDeletedProc(clientData) */ static void -DisplayPanedWindow(clientData) - ClientData clientData; /* Information about window. */ +DisplayPanedWindow( + ClientData clientData) /* Information about window. */ { PanedWindow *pwPtr = (PanedWindow *) clientData; Slave *slavePtr; @@ -1417,9 +1454,14 @@ DisplayPanedWindow(clientData) for (i = 0; i < pwPtr->numSlaves - 1; i++) { slavePtr = pwPtr->slaves[i]; - Tk_Fill3DRectangle(tkwin, pixmap, pwPtr->background, - slavePtr->sashx, slavePtr->sashy, - sashWidth, sashHeight, 1, pwPtr->sashRelief); + if (slavePtr->hide) { + continue; + } + if (sashWidth > 0 && sashHeight > 0) { + Tk_Fill3DRectangle(tkwin, pixmap, pwPtr->background, + slavePtr->sashx, slavePtr->sashy, sashWidth, sashHeight, + 1, pwPtr->sashRelief); + } if (pwPtr->showHandle) { Tk_Fill3DRectangle(tkwin, pixmap, pwPtr->background, slavePtr->handlex, slavePtr->handley, @@ -1430,13 +1472,12 @@ DisplayPanedWindow(clientData) #ifndef TK_NO_DOUBLE_BUFFERING /* - * Copy the information from the off-screen pixmap onto the screen, - * then delete the pixmap. + * Copy the information from the off-screen pixmap onto the screen, then + * delete the pixmap. */ - XCopyArea(Tk_Display(tkwin), pixmap, Tk_WindowId(tkwin), pwPtr->gc, - 0, 0, (unsigned) Tk_Width(tkwin), (unsigned) Tk_Height(tkwin), - 0, 0); + XCopyArea(Tk_Display(tkwin), pixmap, Tk_WindowId(tkwin), pwPtr->gc, 0, 0, + (unsigned) Tk_Width(tkwin), (unsigned) Tk_Height(tkwin), 0, 0); Tk_FreePixmap(Tk_Display(tkwin), pixmap); #endif /* TK_NO_DOUBLE_BUFFERING */ } @@ -1446,8 +1487,8 @@ DisplayPanedWindow(clientData) * * DestroyPanedWindow -- * - * This procedure is invoked by PanedWindowEventProc to free the - * internal structure of a paned window. + * This function is invoked by PanedWindowEventProc to free the internal + * structure of a paned window. * * Results: * None. @@ -1459,23 +1500,23 @@ DisplayPanedWindow(clientData) */ static void -DestroyPanedWindow(pwPtr) - PanedWindow *pwPtr; /* Info about paned window widget. */ +DestroyPanedWindow( + PanedWindow *pwPtr) /* Info about paned window widget. */ { int i; - + /* - * First mark the widget as in the process of being deleted, - * so that any code that causes calls to other paned window procedures - * will abort. + * First mark the widget as in the process of being deleted, so that any + * code that causes calls to other paned window functions will abort. */ pwPtr->flags |= WIDGET_DELETED; /* - * Cancel idle callbacks for redrawing the widget and for rearranging - * the panes. + * Cancel idle callbacks for redrawing the widget and for rearranging the + * panes. */ + if (pwPtr->flags & REDRAW_PENDING) { Tcl_CancelIdleCall(DisplayPanedWindow, (ClientData) pwPtr); } @@ -1489,7 +1530,7 @@ DestroyPanedWindow(pwPtr) * o Cancel geometry management for the slave. * o Free memory for the slave */ - + for (i = 0; i < pwPtr->numSlaves; i++) { Tk_DeleteEventHandler(pwPtr->slaves[i]->tkwin, StructureNotifyMask, SlaveStructureProc, (ClientData) pwPtr->slaves[i]); @@ -1525,26 +1566,25 @@ DestroyPanedWindow(pwPtr) * * PanedWindowReqProc -- * - * This procedure is invoked by Tk_GeometryRequest for - * windows managed by a paned window. + * This function is invoked by Tk_GeometryRequest for windows managed by + * a paned window. * * Results: * None. * * Side effects: - * Arranges for tkwin, and all its managed siblings, to - * be re-arranged at the next idle point. + * Arranges for tkwin, and all its managed siblings, to be re-arranged at + * the next idle point. * *-------------------------------------------------------------- */ static void -PanedWindowReqProc(clientData, tkwin) - ClientData clientData; /* Paned window's information about - * window that got new preferred - * geometry. */ - Tk_Window tkwin; /* Other Tk-related information - * about the window. */ +PanedWindowReqProc( + ClientData clientData, /* Paned window's information about window + * that got new preferred geometry. */ + Tk_Window tkwin) /* Other Tk-related information about the + * window. */ { Slave *slavePtr = (Slave *) clientData; PanedWindow *pwPtr = (PanedWindow *) (slavePtr->masterPtr); @@ -1555,6 +1595,7 @@ PanedWindowReqProc(clientData, tkwin) } } else { int doubleBw = 2 * Tk_Changes(slavePtr->tkwin)->border_width; + if (slavePtr->width <= 0) { slavePtr->paneWidth = Tk_ReqWidth(slavePtr->tkwin) + doubleBw; } @@ -1570,27 +1611,28 @@ PanedWindowReqProc(clientData, tkwin) * * PanedWindowLostSlaveProc -- * - * This procedure is invoked by Tk whenever some other geometry - * claims control over a slave that used to be managed by us. + * This function is invoked by Tk whenever some other geometry claims + * control over a slave that used to be managed by us. * * Results: * None. * * Side effects: - * Forgets all information about the slave. Causes geometry to - * be recomputed for the panedwindow. + * Forgets all information about the slave. Causes geometry to be + * recomputed for the panedwindow. * *-------------------------------------------------------------- */ static void -PanedWindowLostSlaveProc(clientData, tkwin) - ClientData clientData; /* Grid structure for slave window that - * was stolen away. */ - Tk_Window tkwin; /* Tk's handle for the slave window. */ +PanedWindowLostSlaveProc( + ClientData clientData, /* Grid structure for slave window that was + * stolen away. */ + Tk_Window tkwin) /* Tk's handle for the slave window. */ { register Slave *slavePtr = (Slave *) clientData; PanedWindow *pwPtr = (PanedWindow *) (slavePtr->masterPtr); + if (pwPtr->tkwin != Tk_Parent(slavePtr->tkwin)) { Tk_UnmaintainGeometry(slavePtr->tkwin, pwPtr->tkwin); } @@ -1608,11 +1650,10 @@ PanedWindowLostSlaveProc(clientData, tkwin) * * ArrangePanes -- * - * This procedure is invoked (using the Tcl_DoWhenIdle - * mechanism) to re-layout a set of windows managed by - * a paned window. It is invoked at idle time so that a - * series of pane requests can be merged into a single - * layout operation. + * This function is invoked (using the Tcl_DoWhenIdle mechanism) to + * re-layout a set of windows managed by a paned window. It is invoked at + * idle time so that a series of pane requests can be merged into a + * single layout operation. * * Results: * None. @@ -1624,8 +1665,8 @@ PanedWindowLostSlaveProc(clientData, tkwin) */ static void -ArrangePanes(clientData) - ClientData clientData; /* Structure describing parent whose slaves +ArrangePanes( + ClientData clientData) /* Structure describing parent whose slaves * are to be re-layed out. */ { register PanedWindow *pwPtr = (PanedWindow *) clientData; @@ -1638,16 +1679,17 @@ ArrangePanes(clientData) int sashReserve, sxReserve, syReserve; int internalBW; int paneDynSize, paneDynMinSize, pwHeight, pwWidth, pwSize; + int first, last; int stretchReserve, stretchAmount; const int horizontal = (pwPtr->orient == ORIENT_HORIZONTAL); pwPtr->flags &= ~(REQUESTED_RELAYOUT|RESIZE_PENDING); /* - * If the parent has no slaves anymore, then don't do anything - * at all: just leave the parent's size as-is. Otherwise there is - * no way to "relinquish" control over the parent so another geometry - * manager can take over. + * If the parent has no slaves anymore, then don't do anything at all: + * just leave the parent's size as-is. Otherwise there is no way to + * "relinquish" control over the parent so another geometry manager can + * take over. */ if (pwPtr->numSlaves == 0) { @@ -1657,6 +1699,19 @@ ArrangePanes(clientData) Tcl_Preserve((ClientData) pwPtr); /* + * Find index of last visible pane. + */ + + for (i = 0, last = 0, first = -1; i < pwPtr->numSlaves; i++) { + if (pwPtr->slaves[i]->hide == 0) { + if (first < 0) { + first = i; + } + last = i; + } + } + + /* * First pass; compute sizes */ @@ -1668,8 +1723,8 @@ ArrangePanes(clientData) stretchReserve = (horizontal ? pwWidth : pwHeight); /* - * Calculate the sash width, including handle and padding, - * and the sash and handle offsets. + * Calculate the sash width, including handle and padding, and the sash + * and handle offsets. */ sashOffset = handleOffset = pwPtr->sashPad; @@ -1682,14 +1737,17 @@ ArrangePanes(clientData) handleOffset = ((pwPtr->sashWidth - pwPtr->handleSize) / 2) + pwPtr->sashPad; } - sashCount = pwPtr->numSlaves - 1; - for (i = 0; i < pwPtr->numSlaves; i++) { + for (i = sashCount = 0; i < pwPtr->numSlaves; i++) { slavePtr = pwPtr->slaves[i]; + if (slavePtr->hide) { + continue; + } + /* - * Compute the total size needed by all the slaves and the - * left-over, or shortage of space available. + * Compute the total size needed by all the slaves and the left-over, + * or shortage of space available. */ if (horizontal) { @@ -1699,11 +1757,14 @@ ArrangePanes(clientData) paneSize = slavePtr->paneHeight; stretchReserve -= paneSize + (2 * slavePtr->pady); } - if (i == sashCount) { + if (IsStretchable(slavePtr->stretch,i,first,last) + && Tk_IsMapped(pwPtr->tkwin)) { paneDynSize += paneSize; paneDynMinSize += slavePtr->minSize; - } else { + } + if (i != last) { stretchReserve -= sashWidth; + sashCount++; } } @@ -1714,16 +1775,21 @@ ArrangePanes(clientData) for (i = 0; i < pwPtr->numSlaves; i++) { slavePtr = pwPtr->slaves[i]; + if (slavePtr->hide) { + Tk_UnmaintainGeometry(slavePtr->tkwin, pwPtr->tkwin); + Tk_UnmapWindow(slavePtr->tkwin); + continue; + } + /* - * Compute the size of this slave. The algorithm (assuming a + * Compute the size of this slave. The algorithm (assuming a * horizontal paned window) is: * - * 1. Get "base" dimensions. If a width or height is specified - * for this slave, use those values; else use the - * ReqWidth/ReqHeight. + * 1. Get "base" dimensions. If a width or height is specified for + * this slave, use those values; else use the ReqWidth/ReqHeight. * 2. Using base dimensions, pane dimensions, and sticky values, - * determine the x and y, and actual width and height of the - * widget. + * determine the x and y, and actual width and height of the + * widget. */ doubleBw = 2 * Tk_Changes(slavePtr->tkwin)->border_width; @@ -1744,37 +1810,37 @@ ArrangePanes(clientData) paneSize = slavePtr->paneHeight; pwSize = pwHeight; } - if (Tk_IsMapped(pwPtr->tkwin)) { - if (i == pwPtr->numSlaves - 1) { - double frac; - if (paneDynSize > 0) { - frac = (double)paneSize / (double)paneDynSize; - } else { - frac = (double)paneSize / (double)pwSize; - } - paneDynSize -= paneSize; - paneDynMinSize -= slavePtr->minSize; - stretchAmount = (int) (frac * stretchReserve); - if (paneSize + stretchAmount >= paneMinSize) { - stretchReserve -= stretchAmount; - paneSize += stretchAmount; - } else { - stretchReserve += paneSize - paneMinSize; - paneSize = paneMinSize; - } - if (stretchReserve > 0) { - paneSize += stretchReserve; - stretchReserve = 0; - } - } else if (paneDynSize - paneDynMinSize + stretchReserve < 0) { - if (paneSize + paneDynSize - paneDynMinSize + stretchReserve - <= paneMinSize) { - stretchReserve += paneSize - paneMinSize; - paneSize = paneMinSize; - } else { - paneSize += paneDynSize - paneDynMinSize + stretchReserve; - stretchReserve = paneDynMinSize - paneDynSize; - } + if (IsStretchable(slavePtr->stretch, i, first, last)) { + double frac; + + if (paneDynSize > 0) { + frac = (double)paneSize / (double)paneDynSize; + } else { + frac = (double)paneSize / (double)pwSize; + } + + paneDynSize -= paneSize; + paneDynMinSize -= slavePtr->minSize; + stretchAmount = (int) (frac * stretchReserve); + if (paneSize + stretchAmount >= paneMinSize) { + stretchReserve -= stretchAmount; + paneSize += stretchAmount; + } else { + stretchReserve += paneSize - paneMinSize; + paneSize = paneMinSize; + } + if (i == last && stretchReserve > 0) { + paneSize += stretchReserve; + stretchReserve = 0; + } + } else if (paneDynSize - paneDynMinSize + stretchReserve < 0) { + if (paneSize + paneDynSize - paneDynMinSize + stretchReserve + <= paneMinSize) { + stretchReserve += paneSize - paneMinSize; + paneSize = paneMinSize; + } else { + paneSize += paneDynSize - paneDynMinSize + stretchReserve; + stretchReserve = paneDynMinSize - paneDynSize; } } if (horizontal) { @@ -1829,8 +1895,8 @@ ArrangePanes(clientData) if (x < internalBW) { x = internalBW; } - slavePtr->sashx = x + sashOffset; - slavePtr->sashy = y; + slavePtr->sashx = x + sashOffset; + slavePtr->sashy = y; slavePtr->handlex = x + handleOffset; slavePtr->handley = y + pwPtr->handlePad; x += sashWidth; @@ -1839,8 +1905,8 @@ ArrangePanes(clientData) if (y < internalBW) { y = internalBW; } - slavePtr->sashx = x; - slavePtr->sashy = y + sashOffset; + slavePtr->sashx = x; + slavePtr->sashy = y + sashOffset; slavePtr->handlex = x + pwPtr->handlePad; slavePtr->handley = y + handleOffset; y += sashWidth; @@ -1893,12 +1959,12 @@ ArrangePanes(clientData) */ static void -Unlink(slavePtr) - register Slave *slavePtr; /* Window to unlink. */ +Unlink( + register Slave *slavePtr) /* Window to unlink. */ { register PanedWindow *masterPtr; int i, j; - + masterPtr = slavePtr->masterPtr; if (masterPtr == NULL) { return; @@ -1921,6 +1987,7 @@ Unlink(slavePtr) /* * Clean out any -after or -before references to this slave */ + for (i = 0; i < masterPtr->numSlaves; i++) { if (masterPtr->slaves[i]->before == slavePtr->tkwin) { masterPtr->slaves[i]->before = None; @@ -1937,9 +2004,10 @@ Unlink(slavePtr) } /* - * Set the slave's masterPtr to NULL, so that we can tell that the - * slave is no longer attached to any panedwindow. + * Set the slave's masterPtr to NULL, so that we can tell that the slave + * is no longer attached to any panedwindow. */ + slavePtr->masterPtr = NULL; masterPtr->numSlaves--; @@ -1950,12 +2018,12 @@ Unlink(slavePtr) * * GetPane -- * - * Given a token to a Tk window, find the pane that corresponds to - * that token in a given paned window. + * Given a token to a Tk window, find the pane that corresponds to that + * token in a given paned window. * * Results: - * Pointer to the slave structure, or NULL if the window is not - * managed by this paned window. + * Pointer to the slave structure, or NULL if the window is not managed + * by this paned window. * * Side effects: * None. @@ -1964,11 +2032,12 @@ Unlink(slavePtr) */ static Slave * -GetPane(pwPtr, tkwin) - PanedWindow *pwPtr; /* Pointer to the paned window info. */ - Tk_Window tkwin; /* Window to search for. */ +GetPane( + PanedWindow *pwPtr, /* Pointer to the paned window info. */ + Tk_Window tkwin) /* Window to search for. */ { int i; + for (i = 0; i < pwPtr->numSlaves; i++) { if (pwPtr->slaves[i]->tkwin == tkwin) { return pwPtr->slaves[i]; @@ -1982,10 +2051,9 @@ GetPane(pwPtr, tkwin) * * SlaveStructureProc -- * - * This procedure is invoked whenever StructureNotify events - * occur for a window that's managed by a paned window. This - * procedure's only purpose is to clean up when windows are - * deleted. + * This function is invoked whenever StructureNotify events occur for a + * window that's managed by a paned window. This function's only purpose + * is to clean up when windows are deleted. * * Results: * None. @@ -1999,13 +2067,13 @@ GetPane(pwPtr, tkwin) */ static void -SlaveStructureProc(clientData, eventPtr) - ClientData clientData; /* Pointer to record describing window item. */ - XEvent *eventPtr; /* Describes what just happened. */ +SlaveStructureProc( + ClientData clientData, /* Pointer to record describing window item. */ + XEvent *eventPtr) /* Describes what just happened. */ { Slave *slavePtr = (Slave *) clientData; PanedWindow *pwPtr = slavePtr->masterPtr; - + if (eventPtr->type == DestroyNotify) { Unlink(slavePtr); slavePtr->tkwin = NULL; @@ -2019,8 +2087,8 @@ SlaveStructureProc(clientData, eventPtr) * * ComputeGeometry -- * - * Compute geometry for the paned window, including coordinates of - * all slave windows and each sash. + * Compute geometry for the paned window, including coordinates of all + * slave windows and each sash. * * Results: * None. @@ -2032,8 +2100,8 @@ SlaveStructureProc(clientData, eventPtr) */ static void -ComputeGeometry(pwPtr) - PanedWindow *pwPtr; /* Pointer to the Paned Window structure. */ +ComputeGeometry( + PanedWindow *pwPtr) /* Pointer to the Paned Window structure. */ { int i, x, y, doubleBw, internalBw; int sashWidth, sashOffset, handleOffset; @@ -2047,10 +2115,10 @@ ComputeGeometry(pwPtr) reqWidth = reqHeight = 0; /* - * Sashes and handles share space on the display. To simplify - * processing below, precompute the x and y offsets of the handles and - * sashes within the space occupied by their combination; later, just add - * those offsets blindly (avoiding the extra showHandle, etc, checks). + * Sashes and handles share space on the display. To simplify processing + * below, precompute the x and y offsets of the handles and sashes within + * the space occupied by their combination; later, just add those offsets + * blindly (avoiding the extra showHandle, etc, checks). */ sashOffset = handleOffset = pwPtr->sashPad; @@ -2067,6 +2135,10 @@ ComputeGeometry(pwPtr) for (i = 0; i < pwPtr->numSlaves; i++) { slavePtr = pwPtr->slaves[i]; + if (slavePtr->hide) { + continue; + } + /* * First set the coordinates for the top left corner of the slave's * parcel. @@ -2076,9 +2148,9 @@ ComputeGeometry(pwPtr) slavePtr->y = y; /* - * Make sure the pane's paned dimension is at least minsize. - * This check may be redundant, since the only way to change a pane's - * size is by moving a sash, and that code checks the minsize. + * Make sure the pane's paned dimension is at least minsize. This + * check may be redundant, since the only way to change a pane's size + * is by moving a sash, and that code checks the minsize. */ if (horizontal) { @@ -2098,15 +2170,15 @@ ComputeGeometry(pwPtr) if (horizontal) { x += slavePtr->paneWidth + (2 * slavePtr->padx); - slavePtr->sashx = x + sashOffset; - slavePtr->sashy = y; + slavePtr->sashx = x + sashOffset; + slavePtr->sashy = y; slavePtr->handlex = x + handleOffset; slavePtr->handley = y + pwPtr->handlePad; x += sashWidth; } else { y += slavePtr->paneHeight + (2 * slavePtr->pady); - slavePtr->sashx = x; - slavePtr->sashy = y + sashOffset; + slavePtr->sashx = x; + slavePtr->sashy = y + sashOffset; slavePtr->handlex = x + pwPtr->handlePad; slavePtr->handley = y + handleOffset; y += sashWidth; @@ -2118,7 +2190,6 @@ ComputeGeometry(pwPtr) */ if (horizontal) { - /* * If the slave has an explicit height set, use that; otherwise, * use the slave's requested height. @@ -2135,10 +2206,9 @@ ComputeGeometry(pwPtr) reqHeight = dim; } } else { - /* - * If the slave has an explicit width set use that; otherwise, - * use the slave's requested width. + * If the slave has an explicit width set use that; otherwise, use + * the slave's requested width. */ if (slavePtr->width > 0) { @@ -2155,21 +2225,21 @@ ComputeGeometry(pwPtr) } /* - * The loop above should have left x (or y) equal to the sum of the - * widths (or heights) of the widgets, plus the size of one sash and - * the sash padding for each widget, plus the width of the left (or top) - * border of the paned window. + * The loop above should have left x (or y) equal to the sum of the widths + * (or heights) of the widgets, plus the size of one sash and the sash + * padding for each widget, plus the width of the left (or top) border of + * the paned window. * * The requested width (or height) is therefore x (or y) minus the size of - * one sash and padding, plus the width of the right (or bottom) border - * of the paned window. + * one sash and padding, plus the width of the right (or bottom) border of + * the paned window. * - * The height (or width) is equal to the maximum height (or width) of - * the slaves, plus the width of the border of the top and bottom (or left - * and right) of the paned window. + * The height (or width) is equal to the maximum height (or width) of the + * slaves, plus the width of the border of the top and bottom (or left and + * right) of the paned window. * - * If the panedwindow has an explicit width/height set use that; otherwise, - * use the requested width/height. + * If the panedwindow has an explicit width/height set use that; + * otherwise, use the requested width/height. */ if (horizontal) { @@ -2195,8 +2265,8 @@ ComputeGeometry(pwPtr) * * DestroyOptionTables -- * - * This procedure is registered as an exit callback when the paned window - * command is first called. It cleans up the OptionTables structure + * This function is registered as an exit callback when the paned window + * command is first called. It cleans up the OptionTables structure * allocated by that command. * * Results: @@ -2209,9 +2279,9 @@ ComputeGeometry(pwPtr) */ static void -DestroyOptionTables(clientData, interp) - ClientData clientData; /* Pointer to the OptionTables struct */ - Tcl_Interp *interp; /* Pointer to the calling interp */ +DestroyOptionTables( + ClientData clientData, /* Pointer to the OptionTables struct */ + Tcl_Interp *interp) /* Pointer to the calling interp */ { ckfree((char *)clientData); return; @@ -2222,8 +2292,8 @@ DestroyOptionTables(clientData, interp) * * GetSticky - * - * Converts an internal boolean combination of "sticky" bits into a - * a Tcl string obj containing zero or mor of n, s, e, or w. + * Converts an internal boolean combination of "sticky" bits into a Tcl + * string obj containing zero or more of n, s, e, or w. * * Results: * Tcl_Obj containing the string representation of the sticky value. @@ -2235,11 +2305,11 @@ DestroyOptionTables(clientData, interp) */ static Tcl_Obj * -GetSticky(clientData, tkwin, recordPtr, internalOffset) - ClientData clientData; - Tk_Window tkwin; - char *recordPtr; /* Pointer to widget record. */ - int internalOffset; /* Offset within *recordPtr containing the +GetSticky( + ClientData clientData, + Tk_Window tkwin, + char *recordPtr, /* Pointer to widget record. */ + int internalOffset) /* Offset within *recordPtr containing the * sticky value. */ { int sticky = *(int *)(recordPtr + internalOffset); @@ -2247,16 +2317,16 @@ GetSticky(clientData, tkwin, recordPtr, internalOffset) int count = 0; if (sticky & STICK_NORTH) { - buffer[count++] = 'n'; + buffer[count++] = 'n'; } if (sticky & STICK_EAST) { - buffer[count++] = 'e'; + buffer[count++] = 'e'; } if (sticky & STICK_SOUTH) { - buffer[count++] = 's'; + buffer[count++] = 's'; } if (sticky & STICK_WEST) { - buffer[count++] = 'w'; + buffer[count++] = 'w'; } buffer[count] = '\0'; @@ -2268,64 +2338,70 @@ GetSticky(clientData, tkwin, recordPtr, internalOffset) * * SetSticky -- * - * Converts a Tcl_Obj representing a widgets stickyness into an - * integer value. + * Converts a Tcl_Obj representing a widgets stickyness into an integer + * value. * * Results: * Standard Tcl result. * * Side effects: - * May store the integer value into the internal representation - * pointer. May change the pointer to the Tcl_Obj to NULL to indicate - * that the specified string was empty and that is acceptable. + * May store the integer value into the internal representation pointer. + * May change the pointer to the Tcl_Obj to NULL to indicate that the + * specified string was empty and that is acceptable. * *---------------------------------------------------------------------- */ static int -SetSticky(clientData, interp, tkwin, value, recordPtr, internalOffset, - oldInternalPtr, flags) - ClientData clientData; - Tcl_Interp *interp; /* Current interp; may be used for errors. */ - Tk_Window tkwin; /* Window for which option is being set. */ - Tcl_Obj **value; /* Pointer to the pointer to the value object. - * We use a pointer to the pointer because - * we may need to return a value (NULL). */ - char *recordPtr; /* Pointer to storage for the widget record. */ - int internalOffset; /* Offset within *recordPtr at which the - internal value is to be stored. */ - char *oldInternalPtr; /* Pointer to storage for the old value. */ - int flags; /* Flags for the option, set Tk_SetOptions. */ +SetSticky( + ClientData clientData, + Tcl_Interp *interp, /* Current interp; may be used for errors. */ + Tk_Window tkwin, /* Window for which option is being set. */ + Tcl_Obj **value, /* Pointer to the pointer to the value object. + * We use a pointer to the pointer because we + * may need to return a value (NULL). */ + char *recordPtr, /* Pointer to storage for the widget record. */ + int internalOffset, /* Offset within *recordPtr at which the + * internal value is to be stored. */ + char *oldInternalPtr, /* Pointer to storage for the old value. */ + int flags) /* Flags for the option, set Tk_SetOptions. */ { int sticky = 0; char c, *string, *internalPtr; internalPtr = ComputeSlotAddress(recordPtr, internalOffset); - + if (flags & TK_OPTION_NULL_OK && ObjectIsEmpty(*value)) { *value = NULL; } else { /* * Convert the sticky specifier into an integer value. */ - + string = Tcl_GetString(*value); - + while ((c = *string++) != '\0') { switch (c) { - case 'n': case 'N': sticky |= STICK_NORTH; break; - case 'e': case 'E': sticky |= STICK_EAST; break; - case 's': case 'S': sticky |= STICK_SOUTH; break; - case 'w': case 'W': sticky |= STICK_WEST; break; - case ' ': case ',': case '\t': case '\r': case '\n': break; - default: { - Tcl_ResetResult(interp); - Tcl_AppendResult(interp, "bad stickyness value \"", - Tcl_GetString(*value), "\": must be a string ", - "containing zero or more of n, e, s, and w", - (char *)NULL); - return TCL_ERROR; - } + case 'n': case 'N': + sticky |= STICK_NORTH; + break; + case 'e': case 'E': + sticky |= STICK_EAST; + break; + case 's': case 'S': + sticky |= STICK_SOUTH; + break; + case 'w': case 'W': + sticky |= STICK_WEST; + break; + case ' ': case ',': case '\t': case '\r': case '\n': + break; + default: + Tcl_ResetResult(interp); + Tcl_AppendResult(interp, "bad stickyness value \"", + Tcl_GetString(*value), "\": must be a string ", + "containing zero or more of n, e, s, and w", NULL); + return TCL_ERROR; } } } @@ -2335,7 +2411,7 @@ SetSticky(clientData, interp, tkwin, value, recordPtr, internalOffset, *((int *) internalPtr) = sticky; } return TCL_OK; -} +} /* *---------------------------------------------------------------------- @@ -2354,11 +2430,11 @@ SetSticky(clientData, interp, tkwin, value, recordPtr, internalOffset, */ static void -RestoreSticky(clientData, tkwin, internalPtr, oldInternalPtr) - ClientData clientData; - Tk_Window tkwin; - char *internalPtr; /* Pointer to storage for value. */ - char *oldInternalPtr; /* Pointer to old value. */ +RestoreSticky( + ClientData clientData, + Tk_Window tkwin, + char *internalPtr, /* Pointer to storage for value. */ + char *oldInternalPtr) /* Pointer to old value. */ { *(int *)internalPtr = *(int *)oldInternalPtr; } @@ -2368,14 +2444,13 @@ RestoreSticky(clientData, tkwin, internalPtr, oldInternalPtr) * * AdjustForSticky -- * - * Given the x,y coords of the top-left corner of a pane, the - * dimensions of that pane, and the dimensions of a slave, compute - * the x,y coords and actual dimensions of the slave based on the slave's - * sticky value. + * Given the x,y coords of the top-left corner of a pane, the dimensions + * of that pane, and the dimensions of a slave, compute the x,y coords + * and actual dimensions of the slave based on the slave's sticky value. * * Results: - * No direct return; sets the x, y, slaveWidth and slaveHeight to - * correct values. + * No direct return; sets the x, y, slaveWidth and slaveHeight to correct + * values. * * Side effects: * None. @@ -2384,19 +2459,19 @@ RestoreSticky(clientData, tkwin, internalPtr, oldInternalPtr) */ static void -AdjustForSticky(sticky, cavityWidth, cavityHeight, xPtr, yPtr, - slaveWidthPtr, slaveHeightPtr) - int sticky; /* Sticky value; see top of file for definition. */ - int cavityWidth; /* Width of the cavity. */ - int cavityHeight; /* Height of the cavity. */ - int *xPtr, *yPtr; /* Initially, coordinates of the top-left +AdjustForSticky( + int sticky, /* Sticky value; see top of file for + * definition. */ + int cavityWidth, /* Width of the cavity. */ + int cavityHeight, /* Height of the cavity. */ + int *xPtr, int *yPtr, /* Initially, coordinates of the top-left * corner of cavity; also return values for * actual x, y coords of slave. */ - int *slaveWidthPtr; /* Slave width. */ - int *slaveHeightPtr; /* Slave height. */ + int *slaveWidthPtr, /* Slave width. */ + int *slaveHeightPtr) /* Slave height. */ { - int diffx=0; /* Cavity width - slave width. */ - int diffy=0; /* Cavity hight - slave height. */ + int diffx = 0; /* Cavity width - slave width. */ + int diffy = 0; /* Cavity hight - slave height. */ if (cavityWidth > *slaveWidthPtr) { diffx = cavityWidth - *slaveWidthPtr; @@ -2413,10 +2488,10 @@ AdjustForSticky(sticky, cavityWidth, cavityHeight, xPtr, yPtr, *slaveHeightPtr += diffy; } if (!(sticky & STICK_WEST)) { - *xPtr += (sticky & STICK_EAST) ? diffx : diffx/2; + *xPtr += (sticky & STICK_EAST) ? diffx : diffx/2; } if (!(sticky & STICK_NORTH)) { - *yPtr += (sticky & STICK_SOUTH) ? diffy : diffy/2; + *yPtr += (sticky & STICK_SOUTH) ? diffy : diffy/2; } } @@ -2437,10 +2512,10 @@ AdjustForSticky(sticky, cavityWidth, cavityHeight, xPtr, yPtr, */ static void -MoveSash(pwPtr, sash, diff) - PanedWindow *pwPtr; - int sash; - int diff; +MoveSash( + PanedWindow *pwPtr, + int sash, + int diff) { int i; int expandPane, reduceFirst, reduceLast, reduceIncr, slaveSize, sashOffset; @@ -2464,6 +2539,9 @@ MoveSash(pwPtr, sash, diff) } for (i = 0; i < pwPtr->numSlaves; i++) { slavePtr = pwPtr->slaves[i]; + if (slavePtr->hide) { + continue; + } if (horizontal) { slavePtr->paneWidth = slavePtr->width = slavePtr->sashx - sashOffset - slavePtr->x - (2 * slavePtr->padx); @@ -2474,6 +2552,16 @@ MoveSash(pwPtr, sash, diff) } /* + * There must be a next sash since it is only possible to enter this + * routine when moving an actual sash which implies there exists a visible + * pane to either side of the sash. + */ + + while (nextSash < pwPtr->numSlaves-1 && pwPtr->slaves[nextSash]->hide) { + nextSash++; + } + + /* * Consolidate +/-diff variables to reduce duplicate code. */ @@ -2491,12 +2579,15 @@ MoveSash(pwPtr, sash, diff) } /* - * Calculate how much room we have to stretch in - * and adjust diff value accordingly. + * Calculate how much room we have to stretch in and adjust diff value + * accordingly. */ for (i = reduceFirst; i != reduceLast; i += reduceIncr) { slavePtr = pwPtr->slaves[i]; + if (slavePtr->hide) { + continue; + } if (horizontal) { stretchReserve += slavePtr->width - slavePtr->minSize; } else { @@ -2527,6 +2618,9 @@ MoveSash(pwPtr, sash, diff) for (i = reduceFirst; i != reduceLast; i += reduceIncr) { slavePtr = pwPtr->slaves[i]; + if (slavePtr->hide) { + continue; + } if (horizontal) { slaveSize = slavePtr->width; } else { @@ -2552,23 +2646,23 @@ MoveSash(pwPtr, sash, diff) * * ProxyWindowEventProc -- * - * This procedure is invoked by the Tk dispatcher for various - * events on paned window proxy windows. + * This function is invoked by the Tk dispatcher for various events on + * paned window proxy windows. * * Results: * None. * * Side effects: - * When the window gets deleted, internal structures get - * cleaned up. When it gets exposed, it is redisplayed. + * When the window gets deleted, internal structures get cleaned up. Whena + * it gets exposed, it is redisplayed. * *-------------------------------------------------------------- */ static void -ProxyWindowEventProc(clientData, eventPtr) - ClientData clientData; /* Information about window. */ - XEvent *eventPtr; /* Information about event. */ +ProxyWindowEventProc( + ClientData clientData, /* Information about window. */ + XEvent *eventPtr) /* Information about event. */ { PanedWindow *pwPtr = (PanedWindow *) clientData; @@ -2585,9 +2679,9 @@ ProxyWindowEventProc(clientData, eventPtr) * * DisplayProxyWindow -- * - * This procedure redraws a paned window proxy window. - * It is invoked as a do-when-idle handler, so it only runs - * when there's nothing else for the application to do. + * This function redraws a paned window proxy window. It is invoked as a + * do-when-idle handler, so it only runs when there's nothing else for + * the application to do. * * Results: * None. @@ -2599,8 +2693,8 @@ ProxyWindowEventProc(clientData, eventPtr) */ static void -DisplayProxyWindow(clientData) - ClientData clientData; /* Information about window. */ +DisplayProxyWindow( + ClientData clientData) /* Information about window. */ { PanedWindow *pwPtr = (PanedWindow *) clientData; Pixmap pixmap; @@ -2624,6 +2718,7 @@ DisplayProxyWindow(clientData) /* * Redraw the widget's background and border. */ + Tk_Fill3DRectangle(tkwin, pixmap, pwPtr->background, 0, 0, Tk_Width(tkwin), Tk_Height(tkwin), 2, pwPtr->sashRelief); @@ -2631,9 +2726,9 @@ DisplayProxyWindow(clientData) /* * Copy the pixmap to the display. */ - XCopyArea(Tk_Display(tkwin), pixmap, Tk_WindowId(tkwin), pwPtr->gc, - 0, 0, (unsigned) Tk_Width(tkwin), (unsigned) Tk_Height(tkwin), - 0, 0); + + XCopyArea(Tk_Display(tkwin), pixmap, Tk_WindowId(tkwin), pwPtr->gc, 0, 0, + (unsigned) Tk_Width(tkwin), (unsigned) Tk_Height(tkwin), 0, 0); Tk_FreePixmap(Tk_Display(tkwin), pixmap); #endif /* TK_NO_DOUBLE_BUFFERING */ } @@ -2643,8 +2738,8 @@ DisplayProxyWindow(clientData) * * PanedWindowProxyCommand -- * - * Handles the panedwindow proxy subcommand. See the user - * documentation for details. + * Handles the panedwindow proxy subcommand. See the user documentation + * for details. * * Results: * Standard Tcl result. @@ -2656,18 +2751,21 @@ DisplayProxyWindow(clientData) */ static int -PanedWindowProxyCommand(pwPtr, interp, objc, objv) - PanedWindow *pwPtr; /* Pointer to paned window information. */ - Tcl_Interp *interp; /* Current interpreter. */ - int objc; /* Number of arguments. */ - Tcl_Obj * CONST objv[]; /* Argument objects. */ +PanedWindowProxyCommand( + PanedWindow *pwPtr, /* Pointer to paned window information. */ + Tcl_Interp *interp, /* Current interpreter. */ + int objc, /* Number of arguments. */ + Tcl_Obj *CONST objv[]) /* Argument objects. */ { - static CONST char *optionStrings[] = { "coord", "forget", "place", - (char *) NULL }; - enum options { PROXY_COORD, PROXY_FORGET, PROXY_PLACE }; + static CONST char *optionStrings[] = { + "coord", "forget", "place", NULL + }; + enum options { + PROXY_COORD, PROXY_FORGET, PROXY_PLACE + }; int index, x, y, sashWidth, sashHeight; Tcl_Obj *coords[2]; - + if (objc < 3) { Tcl_WrongNumArgs(interp, 2, objv, "option ?arg ...?"); return TCL_ERROR; @@ -2679,85 +2777,92 @@ PanedWindowProxyCommand(pwPtr, interp, objc, objv) } switch ((enum options) index) { - case PROXY_COORD: - if (objc != 3) { - Tcl_WrongNumArgs(interp, 3, objv, NULL); - return TCL_ERROR; - } + case PROXY_COORD: + if (objc != 3) { + Tcl_WrongNumArgs(interp, 3, objv, NULL); + return TCL_ERROR; + } - coords[0] = Tcl_NewIntObj(pwPtr->proxyx); - coords[1] = Tcl_NewIntObj(pwPtr->proxyy); - Tcl_SetListObj(Tcl_GetObjResult(interp), 2, coords); - break; + coords[0] = Tcl_NewIntObj(pwPtr->proxyx); + coords[1] = Tcl_NewIntObj(pwPtr->proxyy); + Tcl_SetListObj(Tcl_GetObjResult(interp), 2, coords); + break; - case PROXY_FORGET: - if (objc != 3) { - Tcl_WrongNumArgs(interp, 3, objv, NULL); - return TCL_ERROR; - } - if (Tk_IsMapped(pwPtr->proxywin)) { - Tk_UnmapWindow(pwPtr->proxywin); - Tk_UnmaintainGeometry(pwPtr->proxywin, pwPtr->tkwin); - } - break; + case PROXY_FORGET: + if (objc != 3) { + Tcl_WrongNumArgs(interp, 3, objv, NULL); + return TCL_ERROR; + } + if (Tk_IsMapped(pwPtr->proxywin)) { + Tk_UnmapWindow(pwPtr->proxywin); + Tk_UnmaintainGeometry(pwPtr->proxywin, pwPtr->tkwin); + } + break; - case PROXY_PLACE: { - if (objc != 5) { - Tcl_WrongNumArgs(interp, 3, objv, "x y"); - return TCL_ERROR; - } + case PROXY_PLACE: + if (objc != 5) { + Tcl_WrongNumArgs(interp, 3, objv, "x y"); + return TCL_ERROR; + } - if (Tcl_GetIntFromObj(interp, objv[3], &x) != TCL_OK) { - return TCL_ERROR; - } + if (Tcl_GetIntFromObj(interp, objv[3], &x) != TCL_OK) { + return TCL_ERROR; + } - if (Tcl_GetIntFromObj(interp, objv[4], &y) != TCL_OK) { - return TCL_ERROR; - } + if (Tcl_GetIntFromObj(interp, objv[4], &y) != TCL_OK) { + return TCL_ERROR; + } - if (pwPtr->orient == ORIENT_HORIZONTAL) { - if (x < 0) { - x = 0; - } - y = Tk_InternalBorderWidth(pwPtr->tkwin); - sashWidth = pwPtr->sashWidth; - sashHeight = Tk_Height(pwPtr->tkwin) - - (2 * Tk_InternalBorderWidth(pwPtr->tkwin)); - } else { - if (y < 0) { - y = 0; - } - x = Tk_InternalBorderWidth(pwPtr->tkwin); - sashHeight = pwPtr->sashWidth; - sashWidth = Tk_Width(pwPtr->tkwin) - + if (pwPtr->orient == ORIENT_HORIZONTAL) { + if (x < 0) { + x = 0; + } + y = Tk_InternalBorderWidth(pwPtr->tkwin); + sashWidth = pwPtr->sashWidth; + sashHeight = Tk_Height(pwPtr->tkwin) - (2 * Tk_InternalBorderWidth(pwPtr->tkwin)); + } else { + if (y < 0) { + y = 0; } + x = Tk_InternalBorderWidth(pwPtr->tkwin); + sashHeight = pwPtr->sashWidth; + sashWidth = Tk_Width(pwPtr->tkwin) - + (2 * Tk_InternalBorderWidth(pwPtr->tkwin)); + } - /* - * Stash the proxy coordinates for future "proxy coord" calls. - */ + if (sashWidth < 1) { + sashWidth = 1; + } + if (sashHeight < 1) { + sashHeight = 1; + } - pwPtr->proxyx = x; - pwPtr->proxyy = y; - - /* - * Make sure the proxy window is higher in the stacking order - * than the slaves, so that it will be visible when drawn. - * It would be more correct to push the proxy window just high - * enough to appear above the highest slave, but it's much easier - * to just force it all the way to the top of the stacking order. - */ - - Tk_RestackWindow(pwPtr->proxywin, Above, NULL); - - /* - * Let Tk_MaintainGeometry take care of placing the window at - * the right coordinates. - */ - Tk_MaintainGeometry(pwPtr->proxywin, pwPtr->tkwin, - x, y, sashWidth, sashHeight); - break; - } + /* + * Stash the proxy coordinates for future "proxy coord" calls. + */ + + pwPtr->proxyx = x; + pwPtr->proxyy = y; + + /* + * Make sure the proxy window is higher in the stacking order than the + * slaves, so that it will be visible when drawn. It would be more + * correct to push the proxy window just high enough to appear above + * the highest slave, but it's much easier to just force it all the + * way to the top of the stacking order. + */ + + Tk_RestackWindow(pwPtr->proxywin, Above, NULL); + + /* + * Let Tk_MaintainGeometry take care of placing the window at the + * right coordinates. + */ + + Tk_MaintainGeometry(pwPtr->proxywin, pwPtr->tkwin, x, y, + sashWidth, sashHeight); + break; } return TCL_OK; @@ -2768,12 +2873,11 @@ PanedWindowProxyCommand(pwPtr, interp, objc, objv) * * ObjectIsEmpty -- * - * This procedure tests whether the string value of an object is - * empty. + * This function tests whether the string value of an object is empty. * * Results: - * The return value is 1 if the string value of objPtr has length - * zero, and 0 otherwise. + * The return value is 1 if the string value of objPtr has length zero, + * and 0 otherwise. * * Side effects: * May cause object shimmering, since this function can force a @@ -2783,8 +2887,8 @@ PanedWindowProxyCommand(pwPtr, interp, objc, objv) */ static int -ObjectIsEmpty(objPtr) - Tcl_Obj *objPtr; /* Object to test. May be NULL. */ +ObjectIsEmpty( + Tcl_Obj *objPtr) /* Object to test. May be NULL. */ { int length; @@ -2807,8 +2911,8 @@ ObjectIsEmpty(objPtr) * within that record, compute the address of that slot. * * Results: - * If offset is non-negative, returns the computed address; else, - * returns NULL. + * If offset is non-negative, returns the computed address; else, returns + * NULL. * * Side effects: * None. @@ -2817,9 +2921,9 @@ ObjectIsEmpty(objPtr) */ static char * -ComputeSlotAddress(recordPtr, offset) - char *recordPtr; /* Pointer to the start of a record. */ - int offset; /* Offset of a slot within that record; may be < 0. */ +ComputeSlotAddress( + char *recordPtr, /* Pointer to the start of a record. */ + int offset) /* Offset of a slot within that record; may be < 0. */ { if (offset >= 0) { return recordPtr + offset; @@ -2833,25 +2937,25 @@ ComputeSlotAddress(recordPtr, offset) * * PanedWindowIdentifyCoords -- * - * Given a pair of x,y coordinates, identify the panedwindow component - * at that point, if any. + * Given a pair of x,y coordinates, identify the panedwindow component at + * that point, if any. * * Results: * Standard Tcl result. * * Side effects: - * Modifies the interpreter's result to contain either an empty list, - * or a two element list of the form {sash n} or {handle n} to indicate - * that the point lies within the n'th sash or handle. + * Modifies the interpreter's result to contain either an empty list, or + * a two element list of the form {sash n} or {handle n} to indicate that + * the point lies within the n'th sash or handle. * *---------------------------------------------------------------------- */ static int -PanedWindowIdentifyCoords(pwPtr, interp, x, y) - PanedWindow *pwPtr; /* Information about the widget. */ - Tcl_Interp *interp; /* Interpreter in which to store result. */ - int x, y; /* Coordinates of the point to identify. */ +PanedWindowIdentifyCoords( + PanedWindow *pwPtr, /* Information about the widget. */ + Tcl_Interp *interp, /* Interpreter in which to store result. */ + int x, int y) /* Coordinates of the point to identify. */ { Tcl_Obj *list; int i, sashHeight, sashWidth, thisx, thisy; @@ -2860,45 +2964,48 @@ PanedWindowIdentifyCoords(pwPtr, interp, x, y) if (pwPtr->orient == ORIENT_HORIZONTAL) { if (Tk_IsMapped(pwPtr->tkwin)) { - sashHeight = Tk_Height(pwPtr->tkwin); + sashHeight = Tk_Height(pwPtr->tkwin); } else { - sashHeight = Tk_ReqHeight(pwPtr->tkwin); + sashHeight = Tk_ReqHeight(pwPtr->tkwin); } - sashHeight -= 2 * Tk_InternalBorderWidth(pwPtr->tkwin); + sashHeight -= 2 * Tk_InternalBorderWidth(pwPtr->tkwin); if (pwPtr->showHandle && pwPtr->handleSize > pwPtr->sashWidth) { - sashWidth = pwPtr->handleSize; - lpad = (pwPtr->handleSize - pwPtr->sashWidth) / 2; - rpad = pwPtr->handleSize - lpad; - lpad += pwPtr->sashPad; - rpad += pwPtr->sashPad; + sashWidth = pwPtr->handleSize; + lpad = (pwPtr->handleSize - pwPtr->sashWidth) / 2; + rpad = pwPtr->handleSize - lpad; + lpad += pwPtr->sashPad; + rpad += pwPtr->sashPad; } else { - sashWidth = pwPtr->sashWidth; + sashWidth = pwPtr->sashWidth; lpad = rpad = pwPtr->sashPad; } - tpad = bpad = 0; + tpad = bpad = 0; } else { if (pwPtr->showHandle && pwPtr->handleSize > pwPtr->sashWidth) { - sashHeight = pwPtr->handleSize; - tpad = (pwPtr->handleSize - pwPtr->sashWidth) / 2; - bpad = pwPtr->handleSize - tpad; - tpad += pwPtr->sashPad; - bpad += pwPtr->sashPad; + sashHeight = pwPtr->handleSize; + tpad = (pwPtr->handleSize - pwPtr->sashWidth) / 2; + bpad = pwPtr->handleSize - tpad; + tpad += pwPtr->sashPad; + bpad += pwPtr->sashPad; } else { - sashHeight = pwPtr->sashWidth; + sashHeight = pwPtr->sashWidth; tpad = bpad = pwPtr->sashPad; } if (Tk_IsMapped(pwPtr->tkwin)) { - sashWidth = Tk_Width(pwPtr->tkwin); + sashWidth = Tk_Width(pwPtr->tkwin); } else { - sashWidth = Tk_ReqWidth(pwPtr->tkwin); + sashWidth = Tk_ReqWidth(pwPtr->tkwin); } - sashWidth -= 2 * Tk_InternalBorderWidth(pwPtr->tkwin); - lpad = rpad = 0; + sashWidth -= 2 * Tk_InternalBorderWidth(pwPtr->tkwin); + lpad = rpad = 0; } - + isHandle = 0; found = -1; for (i = 0; i < pwPtr->numSlaves - 1; i++) { + if (pwPtr->slaves[i]->hide) { + continue; + } thisx = pwPtr->slaves[i]->sashx; thisy = pwPtr->slaves[i]->sashy; @@ -2909,6 +3016,7 @@ PanedWindowIdentifyCoords(pwPtr, interp, x, y) /* * Determine if the point is over the handle or the sash. */ + if (pwPtr->showHandle) { thisx = pwPtr->slaves[i]->handlex; thisy = pwPtr->slaves[i]->handley; @@ -2929,17 +3037,21 @@ PanedWindowIdentifyCoords(pwPtr, interp, x, y) /* * Set results. */ + if (found != -1) { Tcl_ListObjAppendElement(interp, list, Tcl_NewIntObj(found)); - if (isHandle) { - Tcl_ListObjAppendElement(interp, list, - Tcl_NewStringObj("handle", -1)); - } else { - Tcl_ListObjAppendElement(interp, list, - Tcl_NewStringObj("sash", -1)); - } + Tcl_ListObjAppendElement(interp, list, Tcl_NewStringObj( + (isHandle ? "handle" : "sash"), -1)); } - + Tcl_SetObjResult(interp, list); return TCL_OK; } + +/* + * Local Variables: + * mode: c + * c-basic-offset: 4 + * fill-column: 78 + * End: + */ |