From 1a561e0efb8d40f2ff9e8216b3f38a26105752bb Mon Sep 17 00:00:00 2001 From: lecoanet Date: Fri, 28 Nov 2003 13:27:48 +0000 Subject: * The smooth method incorrectly reported bezier curve segments instead of straight line segments. * Added a configuration option -followpointer to try some optimizations of motion event processing under application control. The motion events are still emitted but the enter leave processing is suspended when this option is set to zero. --- generic/tkZinc.c | 70 ++++++++++++++++++++++++++++++++++++++++++-------------- 1 file changed, 53 insertions(+), 17 deletions(-) (limited to 'generic/tkZinc.c') diff --git a/generic/tkZinc.c b/generic/tkZinc.c index 73ed985..c016b9b 100644 --- a/generic/tkZinc.c +++ b/generic/tkZinc.c @@ -127,6 +127,7 @@ static Tk_Uid neg_tag_val_uid; static Tk_Uid dot_uid; static Tk_Uid star_uid; +static void PickCurrentItem _ANSI_ARGS_((ZnWInfo *wi, XEvent *event)); static int ZnReliefParse _ANSI_ARGS_((ClientData client_data, Tcl_Interp *interp, Tk_Window tkwin, Tcl_Obj *ovalue, char *widget_rec, int offset)); @@ -270,6 +271,8 @@ static Tk_ConfigSpec config_specs[] = { "Pink", Tk_Offset(ZnWInfo, bbox_color), 0, &gradientOption}, {TK_CONFIG_INT, "-lightangle", "lightAngle", "LightAngle", "120", Tk_Offset(ZnWInfo, light_angle), 0, NULL}, + {TK_CONFIG_BOOLEAN, "-followpointer", "followPointer", + "FollowPointer", "1", Tk_Offset(ZnWInfo, follow_pointer), 0, NULL}, {TK_CONFIG_END, NULL, NULL, NULL, NULL, 0, 0, NULL} }; @@ -315,6 +318,7 @@ static Tk_ConfigSpec config_specs[] = { #define BBOXES_SPEC 35 #define BBOXES_COLOR_SPEC 36 #define LIGHT_ANGLE_SPEC 37 +#define FOLLOW_POINTER_SPEC 38 static void CmdDeleted _ANSI_ARGS_((ClientData client_data)); @@ -724,6 +728,7 @@ ZincObjCmd(ClientData client_data, /* Main window associated with wi->bbox_color = NULL; wi->draw_bboxes = 0; wi->light_angle = 120; + wi->follow_pointer = 0; wi->border_width = 0; wi->relief = ZN_RELIEF_FLAT; wi->opt_width = None; @@ -5059,14 +5064,8 @@ WidgetObjCmd(ClientData client_data, /* Information about the widget. */ for (i = 0; i < num_points; i++, points++) { entries[0] = Tcl_NewDoubleObj(points->x); entries[1] = Tcl_NewDoubleObj(points->y); - if (i % 3) { - entries[2] = Tcl_NewStringObj(c, -1); - Tcl_ListObjAppendElement(interp, l, Tcl_NewListObj(3, entries)); - } - else { - Tcl_ListObjAppendElement(interp, l, Tcl_NewListObj(2, entries)); - } - } + Tcl_ListObjAppendElement(interp, l, Tcl_NewListObj(2, entries)); + } ZnListFree(to_points); } break; @@ -5701,7 +5700,7 @@ Configure(Tcl_Interp *interp,/* Used for error reporting. */ } } } - + if (CONFIG_PROBE(SCROLL_REGION_SPEC) || CONFIG_PROBE(CONFINE_SPEC)) { SetOrigin(wi, wi->origin.x, wi->origin.y); @@ -5709,6 +5708,27 @@ Configure(Tcl_Interp *interp,/* Used for error reporting. */ } return TCL_OK; + + if (CONFIG_PROBE(FOLLOW_POINTER_SPEC)) { + if (wi->follow_pointer) { + /* Flag has just been turned on, process + * the last known positional event to update + * the item under pointer. + */ + if (wi->pick_event.type == ButtonPress || + wi->pick_event.type == ButtonRelease || + wi->pick_event.type == MotionNotify || + wi->pick_event.type == EnterNotify || + wi->pick_event.type == LeaveNotify) { + Tcl_Preserve((ClientData) wi); + CLEAR(wi->flags, ZN_INTERNAL_NEED_REPICK); + PickCurrentItem(wi, &wi->pick_event); + Tcl_Release((ClientData) wi); + } + } + } + + return TCL_OK; } @@ -6518,7 +6538,15 @@ Bind(ClientData client_data, /* Information about widget. */ else if (event->type == MotionNotify) { wi->state = event->xmotion.state; - PickCurrentItem(wi, event); + if (wi->follow_pointer) { + PickCurrentItem(wi, event); + } + else { + /* Copy the event for later processing + * and skip the picking phase. + */ + wi->pick_event = *event; + } } DoEvent(wi, event, True, True); @@ -7337,13 +7365,21 @@ Redisplay(ClientData client_data) /* Information about the widget. */ if (ISSET(wi->flags, ZN_INTERNAL_NEED_REPICK)) { Tk_Window tkwin; - Tcl_Preserve((ClientData) wi); - CLEAR(wi->flags, ZN_INTERNAL_NEED_REPICK); - PickCurrentItem(wi, &wi->pick_event); - tkwin = wi->win; - Tcl_Release((ClientData) wi); - if (tkwin == NULL) { - return; + if (wi->follow_pointer) { + Tcl_Preserve((ClientData) wi); + CLEAR(wi->flags, ZN_INTERNAL_NEED_REPICK); + PickCurrentItem(wi, &wi->pick_event); + tkwin = wi->win; + Tcl_Release((ClientData) wi); + if (tkwin == NULL) { + return; + } + } + else if (ISCLEAR(wi->top_group->inv_flags, ZN_COORDS_FLAG) && + ISCLEAR(wi->top_group->inv_flags, ZN_TRANSFO_FLAG)) { + /* Don't repick now but escape the loop if + * the geometry is updated. */ + break; } } } -- cgit v1.1