Correct problems with earlier fix for bug #480065

Initialize event_last_[xy] to out of range coordinates and also update
these values in enter and leave notify.  Fix up calls to
update_prelight() from size allocate.  Unconditionally doing these calls
caused problems with hover selection.  Now we only do this call when
the "width before the expander column" has changed.  (Which might be
awkward, but it is the best heuristic I could come up with so far).
This commit is contained in:
Kristian Rietveld 2009-12-21 22:33:59 +01:00
parent f223577a88
commit f59294fd93
2 changed files with 67 additions and 15 deletions

View File

@ -175,6 +175,8 @@ struct _GtkTreeViewPrivate
GList *column_drag_info;
GtkTreeViewColumnReorder *cur_reorder;
gint prev_width_before_expander;
/* Interactive Header reordering */
GdkWindow *drag_window;
GdkWindow *drag_highlight_window;

View File

@ -1378,6 +1378,9 @@ gtk_tree_view_init (GtkTreeView *tree_view)
tree_view->priv->last_button_x = -1;
tree_view->priv->last_button_y = -1;
tree_view->priv->event_last_x = -10000;
tree_view->priv->event_last_y = -10000;
}
@ -2052,6 +2055,25 @@ gtk_tree_view_size_request (GtkWidget *widget,
}
}
static int
gtk_tree_view_calculate_width_before_expander (GtkTreeView *tree_view)
{
int width = 0;
GList *list;
gboolean rtl;
rtl = (gtk_widget_get_direction (GTK_WIDGET (tree_view)) == GTK_TEXT_DIR_RTL);
for (list = (rtl ? g_list_last (tree_view->priv->columns) : g_list_first (tree_view->priv->columns));
list->data != tree_view->priv->expander_column;
list = (rtl ? list->prev : list->next))
{
GtkTreeViewColumn *column = list->data;
width += column->width;
}
return width;
}
static void
invalidate_column (GtkTreeView *tree_view,
@ -2438,14 +2460,30 @@ gtk_tree_view_size_allocate (GtkWidget *widget,
}
}
if (width_changed && tree_view->priv->expander_column)
{
/* Might seem awkward, but is the best heuristic I could come up
* with. Only if the width of the columns before the expander
* changes, we will update the prelight status. It is this
* width that makes the expander move vertically. Always updating
* prelight status causes trouble with hover selections.
*/
gint width_before_expander;
width_before_expander = gtk_tree_view_calculate_width_before_expander (tree_view);
if (tree_view->priv->prev_width_before_expander
!= width_before_expander)
update_prelight (tree_view,
-tree_view->priv->event_last_x,
-tree_view->priv->event_last_y);
tree_view->priv->prev_width_before_expander = width_before_expander;
}
/* This little hack only works if we have an LTR locale, and no column has the */
if (width_changed)
{
if (tree_view->priv->tree)
update_prelight (tree_view,
tree_view->priv->event_last_x,
tree_view->priv->event_last_y);
if (gtk_widget_get_direction (GTK_WIDGET (tree_view)) == GTK_TEXT_DIR_LTR &&
! has_expand_column)
invalidate_last_column (tree_view);
@ -3264,6 +3302,16 @@ prelight_or_select (GtkTreeView *tree_view,
do_prelight (tree_view, tree, node, x, y);
}
static void
ensure_unprelighted (GtkTreeView *tree_view)
{
do_prelight (tree_view,
NULL, NULL,
-1000, -1000); /* coords not possibly over an arrow */
g_assert (tree_view->priv->prelight_node == NULL);
}
static void
update_prelight (GtkTreeView *tree_view,
gint x,
@ -3273,6 +3321,12 @@ update_prelight (GtkTreeView *tree_view,
GtkRBTree *tree;
GtkRBNode *node;
if (x == -10000)
{
ensure_unprelighted (tree_view);
return;
}
new_y = TREE_WINDOW_Y_TO_RBTREE_Y (tree_view, y);
if (new_y < 0)
new_y = 0;
@ -3284,16 +3338,6 @@ update_prelight (GtkTreeView *tree_view,
prelight_or_select (tree_view, tree, node, x, y);
}
static void
ensure_unprelighted (GtkTreeView *tree_view)
{
do_prelight (tree_view,
NULL, NULL,
-1000, -1000); /* coords not possibly over an arrow */
g_assert (tree_view->priv->prelight_node == NULL);
}
@ -5507,6 +5551,9 @@ gtk_tree_view_enter_notify (GtkWidget *widget,
new_y = 0;
_gtk_rbtree_find_offset (tree_view->priv->tree, new_y, &tree, &node);
tree_view->priv->event_last_x = event->x;
tree_view->priv->event_last_y = event->y;
if ((tree_view->priv->button_pressed_node == NULL) ||
(tree_view->priv->button_pressed_node == node))
prelight_or_select (tree_view, tree, node, event->x, event->y);
@ -5531,6 +5578,9 @@ gtk_tree_view_leave_notify (GtkWidget *widget,
tree_view->priv->prelight_node,
NULL);
tree_view->priv->event_last_x = -10000;
tree_view->priv->event_last_y = -10000;
prelight_or_select (tree_view,
NULL, NULL,
-1000, -1000); /* coords not possibly over an arrow */