Ticket #28069: patch-pidgin-gtkdocklet-gtk.c.diff

File patch-pidgin-gtkdocklet-gtk.c.diff, 6.3 KB (added by jemaltz@…, 13 years ago)
  • pidgin/gtkdocklet-gtk.c

    old new  
    22 * System tray icon (aka docklet) plugin for Purple
    33 *
    44 * Copyright (C) 2007 Anders Hasselqvist
    5  *
     5 * 
    66 * This program is free software; you can redistribute it and/or
    77 * modify it under the terms of the GNU General Public License as
    88 * published by the Free Software Foundation; either version 2 of the
     
    1212 * WITHOUT ANY WARRANTY; without even the implied warranty of
    1313 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    1414 * General Public License for more details.
    15  *
     15 * 
    1616 * You should have received a copy of the GNU General Public License
    1717 * along with this program; if not, write to the Free Software
    1818 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
     
    2626#include "pidginstock.h"
    2727#include "gtkdocklet.h"
    2828
    29 #define SHORT_EMBED_TIMEOUT 5
    30 #define LONG_EMBED_TIMEOUT 15
    31 
    3229/* globals */
    33 static GtkStatusIcon *docklet = NULL;
    34 static guint embed_timeout = 0;
    35 
    36 /* protos */
    37 static void docklet_gtk_status_create(gboolean);
    38 
    39 static gboolean
    40 docklet_gtk_recreate_cb(gpointer data)
    41 {
    42         docklet_gtk_status_create(TRUE);
    43 
    44         return FALSE;
    45 }
    46 
    47 static gboolean
    48 docklet_gtk_embed_timeout_cb(gpointer data)
    49 {
    50 #if !GTK_CHECK_VERSION(2,12,0)
    51         if (gtk_status_icon_is_embedded(docklet)) {
    52                 /* Older GTK+ (<2.12) don't implement the embedded signal, but the
    53                    information is still accessable through the above function. */
    54                 purple_debug_info("docklet", "embedded\n");
    55 
    56                 pidgin_docklet_embedded();
    57                 purple_prefs_set_bool(PIDGIN_PREFS_ROOT "/docklet/gtk/embedded", TRUE);
    58         }
    59         else
    60 #endif
    61         {
    62                 /* The docklet was not embedded within the timeout.
    63                  * Remove it as a visibility manager, but leave the plugin
    64                  * loaded so that it can embed automatically if/when a notification
    65                  * area becomes available.
    66                  */
    67                 purple_debug_info("docklet", "failed to embed within timeout\n");
    68                 pidgin_docklet_remove();
    69                 purple_prefs_set_bool(PIDGIN_PREFS_ROOT "/docklet/gtk/embedded", FALSE);
    70         }
    71 
    72 #if GTK_CHECK_VERSION(2,12,0)
    73         embed_timeout = 0;
    74         return FALSE;
    75 #else
    76         return TRUE;
    77 #endif
    78 }
    79 
    80 #if GTK_CHECK_VERSION(2,12,0)
    81 static gboolean
    82 docklet_gtk_embedded_cb(GtkWidget *widget, gpointer data)
    83 {
    84         if (embed_timeout) {
    85                 purple_timeout_remove(embed_timeout);
    86                 embed_timeout = 0;
    87         }
    88 
    89         if (gtk_status_icon_is_embedded(docklet)) {
    90                 purple_debug_info("docklet", "embedded\n");
    91 
    92                 pidgin_docklet_embedded();
    93                 purple_prefs_set_bool(PIDGIN_PREFS_ROOT "/docklet/gtk/embedded", TRUE);
    94         } else {
    95                 purple_debug_info("docklet", "detached\n");
    96 
    97                 pidgin_docklet_remove();
    98                 purple_prefs_set_bool(PIDGIN_PREFS_ROOT "/docklet/gtk/embedded", FALSE);
    99         }
    100 
    101         return TRUE;
    102 }
    103 #endif
    104 
    105 static void
    106 docklet_gtk_destroyed_cb(GtkWidget *widget, gpointer data)
    107 {
    108         purple_debug_info("docklet", "destroyed\n");
    109 
    110         pidgin_docklet_remove();
    111 
    112         g_object_unref(G_OBJECT(docklet));
    113         docklet = NULL;
    114 
    115         g_idle_add(docklet_gtk_recreate_cb, NULL);
    116 }
     30GtkStatusIcon *docklet = NULL;
    11731
    11832static void
    11933docklet_gtk_status_activated_cb(GtkStatusIcon *status_icon, gpointer user_data)
    12034{
    121         pidgin_docklet_clicked(1);
     35        pidgin_docklet_clicked(1); 
    12236}
    12337
    12438static void
     
    17892static void
    17993docklet_gtk_status_set_tooltip(gchar *tooltip)
    18094{
    181         gtk_status_icon_set_tooltip(docklet, tooltip);
     95        if (tooltip) {
     96                gtk_status_icon_set_tooltip(docklet, tooltip);
     97        } else {
     98                gtk_status_icon_set_tooltip(docklet, NULL);
     99        }
    182100}
    183101
    184102static void
     
    196114
    197115        pidgin_docklet_remove();
    198116
    199         if (embed_timeout) {
    200                 purple_timeout_remove(embed_timeout);
    201                 embed_timeout = 0;
    202         }
    203 
    204117        gtk_status_icon_set_visible(docklet, FALSE);
    205         g_signal_handlers_disconnect_by_func(G_OBJECT(docklet), G_CALLBACK(docklet_gtk_destroyed_cb), NULL);
    206118        g_object_unref(G_OBJECT(docklet));
    207119        docklet = NULL;
    208120
     
    225137
    226138        g_signal_connect(G_OBJECT(docklet), "activate", G_CALLBACK(docklet_gtk_status_activated_cb), NULL);
    227139        g_signal_connect(G_OBJECT(docklet), "popup-menu", G_CALLBACK(docklet_gtk_status_clicked_cb), NULL);
    228 #if GTK_CHECK_VERSION(2,12,0)
    229         g_signal_connect(G_OBJECT(docklet), "notify::embedded", G_CALLBACK(docklet_gtk_embedded_cb), NULL);
    230 #endif
    231         g_signal_connect(G_OBJECT(docklet), "destroy", G_CALLBACK(docklet_gtk_destroyed_cb), NULL);
    232140
     141        pidgin_docklet_embedded();
    233142        gtk_status_icon_set_visible(docklet, TRUE);
    234 
    235         /* This is a hack to avoid a race condition between the docklet getting
    236          * embedded in the notification area and the gtkblist restoring its
    237          * previous visibility state.  If the docklet does not get embedded within
    238          * the timeout, it will be removed as a visibility manager until it does
    239          * get embedded.  Ideally, we would only call docklet_embedded() when the
    240          * icon was actually embedded. This only happens when the docklet is first
    241          * created, not when being recreated.
    242          *
    243          * The gtk docklet tracks whether it successfully embedded in a pref and
    244          * allows for a longer timeout period if it successfully embedded the last
    245          * time it was run. This should hopefully solve problems with the buddy
    246          * list not properly starting hidden when Pidgin is started on login.
    247          */
    248         if (!recreate) {
    249                 pidgin_docklet_embedded();
    250 #if GTK_CHECK_VERSION(2,12,0)
    251                 if (purple_prefs_get_bool(PIDGIN_PREFS_ROOT "/docklet/gtk/embedded")) {
    252                         embed_timeout = purple_timeout_add_seconds(LONG_EMBED_TIMEOUT, docklet_gtk_embed_timeout_cb, NULL);
    253                 } else {
    254                         embed_timeout = purple_timeout_add_seconds(SHORT_EMBED_TIMEOUT, docklet_gtk_embed_timeout_cb, NULL);
    255                 }
    256 #else
    257                 embed_timeout = purple_timeout_add_seconds(SHORT_EMBED_TIMEOUT, docklet_gtk_embed_timeout_cb, NULL);
    258 #endif
    259         }
    260 
    261143        purple_debug_info("docklet", "GTK+ created\n");
    262144}
    263145
     
    281163docklet_ui_init(void)
    282164{
    283165        pidgin_docklet_set_ui_ops(&ui_ops);
    284 
    285         purple_prefs_add_none(PIDGIN_PREFS_ROOT "/docklet/gtk");
    286         if (purple_prefs_get_bool(PIDGIN_PREFS_ROOT "/docklet/x11/embedded")) {
    287                 purple_prefs_add_bool(PIDGIN_PREFS_ROOT "/docklet/gtk/embedded", TRUE);
    288                 purple_prefs_remove(PIDGIN_PREFS_ROOT "/docklet/x11/embedded");
    289         } else {
    290                 purple_prefs_add_bool(PIDGIN_PREFS_ROOT "/docklet/gtk/embedded", FALSE);
    291         }
    292 
    293166        gtk_icon_theme_append_search_path(gtk_icon_theme_get_default(),
    294167                DATADIR G_DIR_SEPARATOR_S "pixmaps" G_DIR_SEPARATOR_S "pidgin" G_DIR_SEPARATOR_S "tray");
    295168}
    296