Mercurial > pidgin.yaz
diff pidgin/pidgintooltip.c @ 21947:c6b408d16011
merge of '791803b6696dd26a5193ad76f80dbc7c6cb2687a'
and 'e7dd3b30ece9f95dd95249583812659312c457e6'
author | Stu Tomlinson <stu@nosnilmot.com> |
---|---|
date | Fri, 28 Dec 2007 02:49:23 +0000 |
parents | 3fc5862b834a |
children | c38d72677c8a |
line wrap: on
line diff
--- a/pidgin/pidgintooltip.c Fri Dec 28 02:49:10 2007 +0000 +++ b/pidgin/pidgintooltip.c Fri Dec 28 02:49:23 2007 +0000 @@ -43,15 +43,22 @@ { GtkWidget *widget; gpointer userdata; - PidginTooltipCreateForTree create_tooltip; PidginTooltipPaint paint_tooltip; - GtkTreePath *path; + union { + struct { + PidginTooltipCreateForTree create_tooltip; + GtkTreePath *path; + } treeview; + struct { + PidginTooltipCreate create_tooltip; + } widget; + } common; } PidginTooltipData; static void destroy_tooltip_data(PidginTooltipData *data) { - gtk_tree_path_free(data->path); + gtk_tree_path_free(data->common.treeview.path); g_free(data); } @@ -70,8 +77,11 @@ static gboolean pidgin_tooltip_expose_event(GtkWidget *widget, GdkEventExpose *event, gpointer data) { - if (pidgin_tooltip.paint_tooltip) + if (pidgin_tooltip.paint_tooltip) { + gtk_paint_flat_box(widget->style, widget->window, GTK_STATE_NORMAL, GTK_SHADOW_OUT, + NULL, widget, "tooltip", 0, 0, -1, -1); pidgin_tooltip.paint_tooltip(widget, data); + } return FALSE; } @@ -184,14 +194,35 @@ static void reset_data_treepath(PidginTooltipData *data) { - gtk_tree_path_free(data->path); - data->path = NULL; + gtk_tree_path_free(data->common.treeview.path); + data->common.treeview.path = NULL; } static void pidgin_tooltip_draw(PidginTooltipData *data) { GtkWidget *tipwindow; + int w, h; + + pidgin_tooltip_destroy(); + + pidgin_tooltip.widget = gtk_widget_get_toplevel(data->widget); + pidgin_tooltip.tipwindow = tipwindow = setup_tooltip_window(); + pidgin_tooltip.paint_tooltip = data->paint_tooltip; + + if (!data->common.widget.create_tooltip(tipwindow, data->userdata, &w, &h)) { + if (tipwindow == pidgin_tooltip.tipwindow) + pidgin_tooltip_destroy(); + return; + } + + setup_tooltip_window_position(data->userdata, w, h); +} + +static void +pidgin_tooltip_draw_tree(PidginTooltipData *data) +{ + GtkWidget *tipwindow; GtkTreePath *path = NULL; int w, h; @@ -203,13 +234,13 @@ return; } - if (data->path) { - if (gtk_tree_path_compare(data->path, path) == 0) { + if (data->common.treeview.path) { + if (gtk_tree_path_compare(data->common.treeview.path, path) == 0) { gtk_tree_path_free(path); return; } - gtk_tree_path_free(data->path); - data->path = NULL; + gtk_tree_path_free(data->common.treeview.path); + data->common.treeview.path = NULL; } pidgin_tooltip_destroy(); @@ -218,24 +249,29 @@ pidgin_tooltip.tipwindow = tipwindow = setup_tooltip_window(); pidgin_tooltip.paint_tooltip = data->paint_tooltip; - if (!data->create_tooltip(tipwindow, path, data->userdata, &w, &h)) { - pidgin_tooltip_destroy(); + if (!data->common.treeview.create_tooltip(tipwindow, path, data->userdata, &w, &h)) { + if (tipwindow == pidgin_tooltip.tipwindow) + pidgin_tooltip_destroy(); gtk_tree_path_free(path); return; } setup_tooltip_window_position(data->userdata, w, h); - data->path = path; - g_signal_connect_swapped(G_OBJECT(tipwindow), "destroy", + data->common.treeview.path = path; + g_signal_connect_swapped(G_OBJECT(pidgin_tooltip.tipwindow), "destroy", G_CALLBACK(reset_data_treepath), data); } static gboolean pidgin_tooltip_timeout(gpointer data) { + PidginTooltipData *tdata = data; pidgin_tooltip.timeout = 0; - pidgin_tooltip_draw(data); + if (GTK_IS_TREE_VIEW(tdata->widget)) + pidgin_tooltip_draw_tree(data); + else + pidgin_tooltip_draw(data); return FALSE; } @@ -276,7 +312,7 @@ } static gboolean -row_leave_cb(GtkWidget *tv, GdkEvent *event, gpointer userdata) +widget_leave_cb(GtkWidget *tv, GdkEvent *event, gpointer userdata) { pidgin_tooltip_destroy(); return FALSE; @@ -288,12 +324,40 @@ PidginTooltipData *tdata = g_new0(PidginTooltipData, 1); tdata->widget = tree; tdata->userdata = userdata; - tdata->create_tooltip = create_tooltip; + tdata->common.treeview.create_tooltip = create_tooltip; tdata->paint_tooltip = paint_tooltip; g_signal_connect(G_OBJECT(tree), "motion-notify-event", G_CALLBACK(row_motion_cb), tdata); - g_signal_connect(G_OBJECT(tree), "leave-notify-event", G_CALLBACK(row_leave_cb), NULL); + g_signal_connect(G_OBJECT(tree), "leave-notify-event", G_CALLBACK(widget_leave_cb), NULL); g_signal_connect_swapped(G_OBJECT(tree), "destroy", G_CALLBACK(destroy_tooltip_data), tdata); return TRUE; } +static gboolean +widget_motion_cb(GtkWidget *widget, GdkEvent *event, gpointer data) +{ + int delay = purple_prefs_get_int(PIDGIN_PREFS_ROOT "/blist/tooltip_delay"); + + pidgin_tooltip_destroy(); + if (delay == 0) + return FALSE; + + pidgin_tooltip.timeout = g_timeout_add(delay, (GSourceFunc)pidgin_tooltip_timeout, data); + return FALSE; +} + +gboolean pidgin_tooltip_setup_for_widget(GtkWidget *widget, gpointer userdata, + PidginTooltipCreate create_tooltip, PidginTooltipPaint paint_tooltip) +{ + PidginTooltipData *wdata = g_new0(PidginTooltipData, 1); + wdata->widget = widget; + wdata->userdata = userdata; + wdata->common.widget.create_tooltip = create_tooltip; + wdata->paint_tooltip = paint_tooltip; + + g_signal_connect(G_OBJECT(widget), "motion-notify-event", G_CALLBACK(widget_motion_cb), wdata); + g_signal_connect(G_OBJECT(widget), "leave-notify-event", G_CALLBACK(widget_leave_cb), NULL); + g_signal_connect_swapped(G_OBJECT(widget), "destroy", G_CALLBACK(g_free), wdata); + return TRUE; +} +