diff options
author | hobbs <hobbs> | 2006-10-31 01:42:25 (GMT) |
---|---|---|
committer | hobbs <hobbs> | 2006-10-31 01:42:25 (GMT) |
commit | 397a2c9832bf618f26be267501cf49ab06a562ec (patch) | |
tree | 61d5e957eccfcba57b0dd27ebc73db085385834e /generic/ttk/ttkTrace.c | |
parent | 18d330543869e240c2bd12fc9fbb8d5027f5cad6 (diff) | |
download | tk-397a2c9832bf618f26be267501cf49ab06a562ec.zip tk-397a2c9832bf618f26be267501cf49ab06a562ec.tar.gz tk-397a2c9832bf618f26be267501cf49ab06a562ec.tar.bz2 |
* doc/ttk_Geometry.3, doc/ttk_Theme.3, doc/ttk_button.n:
* doc/ttk_checkbutton.n, doc/ttk_combobox.n, doc/ttk_dialog.n:
* doc/ttk_entry.n, doc/ttk_frame.n, doc/ttk_image.n:
* doc/ttk_intro.n, doc/ttk_label.n, doc/ttk_labelframe.n:
* doc/ttk_menubutton.n, doc/ttk_notebook.n, doc/ttk_panedwindow.n:
* doc/ttk_progressbar.n, doc/ttk_radiobutton.n, doc/ttk_scrollbar.n:
* doc/ttk_separator.n, doc/ttk_sizegrip.n, doc/ttk_style.n:
* doc/ttk_treeview.n, doc/ttk_widget.n,:
* generic/ttk/ttk.decls, generic/ttk/ttkBlink.c:
* generic/ttk/ttkButton.c, generic/ttk/ttkCache.c:
* generic/ttk/ttkClamTheme.c, generic/ttk/ttkClassicTheme.c:
* generic/ttk/ttkDecls.h, generic/ttk/ttkDefaultTheme.c:
* generic/ttk/ttkElements.c, generic/ttk/ttkEntry.c:
* generic/ttk/ttkFrame.c, generic/ttk/ttkImage.c:
* generic/ttk/ttkInit.c, generic/ttk/ttkLabel.c:
* generic/ttk/ttkLayout.c, generic/ttk/ttkManager.c:
* generic/ttk/ttkManager.h, generic/ttk/ttkNotebook.c:
* generic/ttk/ttkPanedwindow.c, generic/ttk/ttkProgress.c:
* generic/ttk/ttkScale.c, generic/ttk/ttkScroll.c:
* generic/ttk/ttkScrollbar.c, generic/ttk/ttkSeparator.c:
* generic/ttk/ttkSquare.c, generic/ttk/ttkState.c:
* generic/ttk/ttkStubInit.c, generic/ttk/ttkStubLib.c:
* generic/ttk/ttkTagSet.c, generic/ttk/ttkTheme.c:
* generic/ttk/ttkTheme.h, generic/ttk/ttkThemeInt.h:
* generic/ttk/ttkTrace.c, generic/ttk/ttkTrack.c:
* generic/ttk/ttkTreeview.c, generic/ttk/ttkWidget.c:
* generic/ttk/ttkWidget.h:
* library/demos/ttk_demo.tcl, library/demos/ttk_iconlib.tcl:
* library/demos/ttk_repeater.tcl:
* library/ttk/altTheme.tcl, library/ttk/aquaTheme.tcl:
* library/ttk/button.tcl, library/ttk/clamTheme.tcl:
* library/ttk/classicTheme.tcl, library/ttk/combobox.tcl:
* library/ttk/cursors.tcl, library/ttk/defaults.tcl:
* library/ttk/dialog.tcl, library/ttk/entry.tcl:
* library/ttk/fonts.tcl, library/ttk/icons.tcl:
* library/ttk/keynav.tcl, library/ttk/menubutton.tcl:
* library/ttk/notebook.tcl, library/ttk/panedwindow.tcl:
* library/ttk/progress.tcl, library/ttk/scale.tcl:
* library/ttk/scrollbar.tcl, library/ttk/sizegrip.tcl:
* library/ttk/treeview.tcl, library/ttk/ttk.tcl:
* library/ttk/utils.tcl, library/ttk/winTheme.tcl:
* library/ttk/xpTheme.tcl:
* macosx/ttkMacOSXTheme.c:
* tests/ttk/all.tcl, tests/ttk/bwidget.test, tests/ttk/combobox.test:
* tests/ttk/entry.test, tests/ttk/image.test:
* tests/ttk/labelframe.test, tests/ttk/layout.test:
* tests/ttk/misc.test, tests/ttk/notebook.test:
* tests/ttk/panedwindow.test, tests/ttk/progressbar.test:
* tests/ttk/scrollbar.test, tests/ttk/treetags.test:
* tests/ttk/treeview.test, tests/ttk/ttk.test, tests/ttk/validate.test:
* win/ttkWinMonitor.c, win/ttkWinTheme.c, win/ttkWinXPTheme.c:
First import of Ttk themed Tk widgets as branched from tile 0.7.8
* generic/tkInt.h, generic/tkWindow.c: add Ttk_Init call, copy
tk classic widgets to ::tk namespace.
* library/tk.tcl: add source of ttk/ttk.tcl, define $::ttk::library.
* unix/Makefile.in, win/Makefile.in: add Ttk build bits
* win/configure, win/configure.in: check for uxtheme.h (XP theme).
Diffstat (limited to 'generic/ttk/ttkTrace.c')
-rw-r--r-- | generic/ttk/ttkTrace.c | 145 |
1 files changed, 145 insertions, 0 deletions
diff --git a/generic/ttk/ttkTrace.c b/generic/ttk/ttkTrace.c new file mode 100644 index 0000000..37a319b --- /dev/null +++ b/generic/ttk/ttkTrace.c @@ -0,0 +1,145 @@ +/* $Id: ttkTrace.c,v 1.1 2006/10/31 01:42:26 hobbs Exp $ + * + * Copyright 2003, Joe English + * + * Simplified interface to Tcl_TraceVariable. + * + * PROBLEM: Can't distinguish "variable does not exist" (which is OK) + * from other errors (which are not). + */ + +#include <tk.h> +#include "ttkTheme.h" +#include "ttkWidget.h" + +struct TtkTraceHandle_ +{ + Tcl_Interp *interp; /* Containing interpreter */ + Tcl_Obj *varnameObj; /* Name of variable being traced */ + Ttk_TraceProc callback; /* Callback procedure */ + void *clientData; /* Data to pass to callback */ +}; + +/* + * Tcl_VarTraceProc for trace handles. + */ +static char * +VarTraceProc( + ClientData clientData, /* Widget record pointer */ + Tcl_Interp *interp, /* Interpreter containing variable. */ + CONST char *name1, /* (unused) */ + CONST char *name2, /* (unused) */ + int flags) /* Information about what happened. */ +{ + Ttk_TraceHandle *tracePtr = clientData; + const char *name, *value; + Tcl_Obj *valuePtr; + + if (flags & TCL_INTERP_DESTROYED) { + return NULL; + } + + name = Tcl_GetString(tracePtr->varnameObj); + + /* + * If the variable is being unset, then re-establish the trace: + */ + if (flags & TCL_TRACE_DESTROYED) { + Tcl_TraceVar(interp, name, + TCL_GLOBAL_ONLY|TCL_TRACE_WRITES|TCL_TRACE_UNSETS, + VarTraceProc, clientData); + tracePtr->callback(tracePtr->clientData, NULL); + return NULL; + } + + /* + * Call the callback: + */ + valuePtr = Tcl_GetVar2Ex(interp, name, NULL, TCL_GLOBAL_ONLY); + value = valuePtr ? Tcl_GetString(valuePtr) : NULL; + tracePtr->callback(tracePtr->clientData, value); + + return NULL; +} + +/* Ttk_TraceVariable(interp, varNameObj, callback, clientdata) -- + * Attach a write trace to the specified variable, + * which will pass the variable's value to 'callback' + * whenever the variable is set. + * + * When the variable is unset, passes NULL to the callback + * and reattaches the trace. + */ +Ttk_TraceHandle *Ttk_TraceVariable( + Tcl_Interp *interp, + Tcl_Obj *varnameObj, + Ttk_TraceProc callback, + void *clientData) +{ + Ttk_TraceHandle *h = (Ttk_TraceHandle*)ckalloc(sizeof(*h)); + int status; + + h->interp = interp; + h->varnameObj = Tcl_DuplicateObj(varnameObj); + Tcl_IncrRefCount(h->varnameObj); + h->clientData = clientData; + h->callback = callback; + + status = Tcl_TraceVar(interp, Tcl_GetString(varnameObj), + TCL_GLOBAL_ONLY|TCL_TRACE_WRITES|TCL_TRACE_UNSETS, + VarTraceProc, (ClientData)h); + + if (status != TCL_OK) { + Tcl_DecrRefCount(h->varnameObj); + ckfree((ClientData)h); + return NULL; + } + + return h; +} + +/* + * Ttk_UntraceVariable -- + * Remove previously-registered trace and free the handle. + */ +void Ttk_UntraceVariable(Ttk_TraceHandle *h) +{ + if (h) { + Tcl_UntraceVar(h->interp, Tcl_GetString(h->varnameObj), + TCL_GLOBAL_ONLY|TCL_TRACE_WRITES|TCL_TRACE_UNSETS, + VarTraceProc, (ClientData)h); + Tcl_DecrRefCount(h->varnameObj); + ckfree((ClientData)h); + } +} + +/* + * Ttk_FireTrace -- + * Executes a trace handle as if the variable has been written. + * + * Note: may reenter the interpreter. + */ +int Ttk_FireTrace(Ttk_TraceHandle *tracePtr) +{ + Tcl_Interp *interp = tracePtr->interp; + void *clientData = tracePtr->clientData; + const char *name = Tcl_GetString(tracePtr->varnameObj); + Ttk_TraceProc callback = tracePtr->callback; + Tcl_Obj *valuePtr; + const char *value; + + /* Read the variable. + * Note that this can reenter the interpreter, and anything can happen -- + * including the current trace handle being freed! + */ + valuePtr = Tcl_GetVar2Ex(interp, name, NULL, TCL_GLOBAL_ONLY); + value = valuePtr ? Tcl_GetString(valuePtr) : NULL; + + /* Call callback. + */ + callback(clientData, value); + + return TCL_OK; +} + +/*EOF*/ |