src/notification.c (-set_scaled_pixbuf, +zenity_notification_icon_update,
2006-07-27 Lucas Rocha <lucasr@gnome.org> * src/notification.c (-set_scaled_pixbuf, +zenity_notification_icon_update, -zenity_notification_icon_press_callback, +zenity_notification_icon_size_changed_cb, -zenity_notification_icon_expose_callback, -zenity_notification_icon_destroy_callback, +zenity_notification_icon_activate_cb, zenity_notification_handle_stdin, zenity_notification), src/util.[ch] (+zenity_util_stock_from_filename, zenity_util_pixbuf_new_from_file), Makefile.am, configure.in: Migration to gtk_status_icon (Fixes bug #341451). Patch from Christian Persch <chpe@gnome.org>. * src/eggtrayicon.[ch]: removed.
This commit is contained in:
parent
e46814b46a
commit
d373b3f3ce
18
ChangeLog
18
ChangeLog
@ -1,3 +1,21 @@
|
|||||||
|
2006-07-27 Lucas Rocha <lucasr@gnome.org>
|
||||||
|
|
||||||
|
* src/notification.c (-set_scaled_pixbuf,
|
||||||
|
+zenity_notification_icon_update,
|
||||||
|
-zenity_notification_icon_press_callback,
|
||||||
|
+zenity_notification_icon_size_changed_cb,
|
||||||
|
-zenity_notification_icon_expose_callback,
|
||||||
|
-zenity_notification_icon_destroy_callback,
|
||||||
|
+zenity_notification_icon_activate_cb,
|
||||||
|
zenity_notification_handle_stdin, zenity_notification),
|
||||||
|
src/util.[ch] (+zenity_util_stock_from_filename,
|
||||||
|
zenity_util_pixbuf_new_from_file), Makefile.am, configure.in:
|
||||||
|
|
||||||
|
Migration to gtk_status_icon (Fixes bug #341451). Patch from
|
||||||
|
Christian Persch <chpe@gnome.org>.
|
||||||
|
|
||||||
|
* src/eggtrayicon.[ch]: removed.
|
||||||
|
|
||||||
2006-07-27 Lucas Rocha <lucasr@gnome.org>
|
2006-07-27 Lucas Rocha <lucasr@gnome.org>
|
||||||
|
|
||||||
* src/text.c (zenity_text_handle_stdin): correctly stdin input for
|
* src/text.c (zenity_text_handle_stdin): correctly stdin input for
|
||||||
|
@ -16,7 +16,7 @@ IT_PROG_INTLTOOL([0.34.90])
|
|||||||
|
|
||||||
AC_PROG_CC
|
AC_PROG_CC
|
||||||
|
|
||||||
GTK_REQUIRED=2.9.0
|
GTK_REQUIRED=2.9.2
|
||||||
|
|
||||||
PKG_CHECK_MODULES([ZENITY],[gtk+-2.0 >= $GTK_REQUIRED libglade-2.0 libgnomecanvas-2.0 glib-2.0])
|
PKG_CHECK_MODULES([ZENITY],[gtk+-2.0 >= $GTK_REQUIRED libglade-2.0 libgnomecanvas-2.0 glib-2.0])
|
||||||
AC_SUBST([ZENITY_CFLAGS])
|
AC_SUBST([ZENITY_CFLAGS])
|
||||||
@ -32,7 +32,7 @@ AC_PATH_PROG([PERL],[perl],)
|
|||||||
# libnotify check
|
# libnotify check
|
||||||
# *******************************
|
# *******************************
|
||||||
|
|
||||||
LIBNOTIFY_REQUIRED=0.3.2
|
LIBNOTIFY_REQUIRED=0.4.1
|
||||||
PKG_CHECK_MODULES([LIBNOTIFY],[libnotify >= $LIBNOTIFY_REQUIRED],
|
PKG_CHECK_MODULES([LIBNOTIFY],[libnotify >= $LIBNOTIFY_REQUIRED],
|
||||||
[HAVE_LIBNOTIFY="yes"],[HAVE_LIBNOTIFY="no"])
|
[HAVE_LIBNOTIFY="yes"],[HAVE_LIBNOTIFY="no"])
|
||||||
AC_SUBST([LIBNOTIFY_CFLAGS])
|
AC_SUBST([LIBNOTIFY_CFLAGS])
|
||||||
|
@ -3,24 +3,22 @@ bin_PROGRAMS = zenity
|
|||||||
bin_SCRIPTS = gdialog
|
bin_SCRIPTS = gdialog
|
||||||
|
|
||||||
zenity_SOURCES = \
|
zenity_SOURCES = \
|
||||||
|
about.c \
|
||||||
|
calendar.c \
|
||||||
|
entry.c \
|
||||||
|
fileselection.c \
|
||||||
main.c \
|
main.c \
|
||||||
|
msg.c \
|
||||||
|
notification.c \
|
||||||
option.c \
|
option.c \
|
||||||
option.h \
|
option.h \
|
||||||
zenity.h \
|
|
||||||
calendar.c \
|
|
||||||
msg.c \
|
|
||||||
scale.c \
|
|
||||||
fileselection.c \
|
|
||||||
entry.c \
|
|
||||||
text.c \
|
|
||||||
progress.c \
|
progress.c \
|
||||||
|
scale.c \
|
||||||
|
text.c \
|
||||||
tree.c \
|
tree.c \
|
||||||
eggtrayicon.h \
|
util.c \
|
||||||
eggtrayicon.c \
|
|
||||||
notification.c \
|
|
||||||
about.c \
|
|
||||||
util.h \
|
util.h \
|
||||||
util.c
|
zenity.h
|
||||||
|
|
||||||
zenity_CPPFLAGS = \
|
zenity_CPPFLAGS = \
|
||||||
-I$(includedir) \
|
-I$(includedir) \
|
||||||
|
@ -1,468 +0,0 @@
|
|||||||
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
|
|
||||||
/* eggtrayicon.c
|
|
||||||
* Copyright (C) 2002 Anders Carlsson <andersca@gnu.org>
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the
|
|
||||||
* Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
|
|
||||||
* Boston, MA 02110-1301, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include <config.h>
|
|
||||||
#include <string.h>
|
|
||||||
#include <libintl.h>
|
|
||||||
|
|
||||||
#include "eggtrayicon.h"
|
|
||||||
|
|
||||||
#include <gdk/gdkx.h>
|
|
||||||
#include <X11/Xatom.h>
|
|
||||||
|
|
||||||
#ifndef EGG_COMPILATION
|
|
||||||
#ifndef _
|
|
||||||
#define _(x) dgettext (GETTEXT_PACKAGE, x)
|
|
||||||
#define N_(x) x
|
|
||||||
#endif
|
|
||||||
#else
|
|
||||||
#define _(x) x
|
|
||||||
#define N_(x) x
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define SYSTEM_TRAY_REQUEST_DOCK 0
|
|
||||||
#define SYSTEM_TRAY_BEGIN_MESSAGE 1
|
|
||||||
#define SYSTEM_TRAY_CANCEL_MESSAGE 2
|
|
||||||
|
|
||||||
#define SYSTEM_TRAY_ORIENTATION_HORZ 0
|
|
||||||
#define SYSTEM_TRAY_ORIENTATION_VERT 1
|
|
||||||
|
|
||||||
enum {
|
|
||||||
PROP_0,
|
|
||||||
PROP_ORIENTATION
|
|
||||||
};
|
|
||||||
|
|
||||||
static GtkPlugClass *parent_class = NULL;
|
|
||||||
|
|
||||||
static void egg_tray_icon_init (EggTrayIcon *icon);
|
|
||||||
static void egg_tray_icon_class_init (EggTrayIconClass *klass);
|
|
||||||
|
|
||||||
static void egg_tray_icon_get_property (GObject *object,
|
|
||||||
guint prop_id,
|
|
||||||
GValue *value,
|
|
||||||
GParamSpec *pspec);
|
|
||||||
|
|
||||||
static void egg_tray_icon_realize (GtkWidget *widget);
|
|
||||||
static void egg_tray_icon_unrealize (GtkWidget *widget);
|
|
||||||
|
|
||||||
static void egg_tray_icon_update_manager_window (EggTrayIcon *icon);
|
|
||||||
|
|
||||||
GType
|
|
||||||
egg_tray_icon_get_type (void)
|
|
||||||
{
|
|
||||||
static GType our_type = 0;
|
|
||||||
|
|
||||||
if (our_type == 0)
|
|
||||||
{
|
|
||||||
static const GTypeInfo our_info =
|
|
||||||
{
|
|
||||||
sizeof (EggTrayIconClass),
|
|
||||||
(GBaseInitFunc) NULL,
|
|
||||||
(GBaseFinalizeFunc) NULL,
|
|
||||||
(GClassInitFunc) egg_tray_icon_class_init,
|
|
||||||
NULL, /* class_finalize */
|
|
||||||
NULL, /* class_data */
|
|
||||||
sizeof (EggTrayIcon),
|
|
||||||
0, /* n_preallocs */
|
|
||||||
(GInstanceInitFunc) egg_tray_icon_init
|
|
||||||
};
|
|
||||||
|
|
||||||
our_type = g_type_register_static (GTK_TYPE_PLUG, "EggTrayIcon", &our_info, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
return our_type;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
egg_tray_icon_init (EggTrayIcon *icon)
|
|
||||||
{
|
|
||||||
icon->stamp = 1;
|
|
||||||
icon->orientation = GTK_ORIENTATION_HORIZONTAL;
|
|
||||||
|
|
||||||
gtk_widget_add_events (GTK_WIDGET (icon), GDK_PROPERTY_CHANGE_MASK);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
egg_tray_icon_class_init (EggTrayIconClass *klass)
|
|
||||||
{
|
|
||||||
GObjectClass *gobject_class = (GObjectClass *)klass;
|
|
||||||
GtkWidgetClass *widget_class = (GtkWidgetClass *)klass;
|
|
||||||
|
|
||||||
parent_class = g_type_class_peek_parent (klass);
|
|
||||||
|
|
||||||
gobject_class->get_property = egg_tray_icon_get_property;
|
|
||||||
|
|
||||||
widget_class->realize = egg_tray_icon_realize;
|
|
||||||
widget_class->unrealize = egg_tray_icon_unrealize;
|
|
||||||
|
|
||||||
g_object_class_install_property (gobject_class,
|
|
||||||
PROP_ORIENTATION,
|
|
||||||
g_param_spec_enum ("orientation",
|
|
||||||
_("Orientation"),
|
|
||||||
_("The orientation of the tray."),
|
|
||||||
GTK_TYPE_ORIENTATION,
|
|
||||||
GTK_ORIENTATION_HORIZONTAL,
|
|
||||||
G_PARAM_READABLE));
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
egg_tray_icon_get_property (GObject *object,
|
|
||||||
guint prop_id,
|
|
||||||
GValue *value,
|
|
||||||
GParamSpec *pspec)
|
|
||||||
{
|
|
||||||
EggTrayIcon *icon = EGG_TRAY_ICON (object);
|
|
||||||
|
|
||||||
switch (prop_id)
|
|
||||||
{
|
|
||||||
case PROP_ORIENTATION:
|
|
||||||
g_value_set_enum (value, icon->orientation);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
egg_tray_icon_get_orientation_property (EggTrayIcon *icon)
|
|
||||||
{
|
|
||||||
Display *xdisplay;
|
|
||||||
Atom type;
|
|
||||||
int format;
|
|
||||||
union {
|
|
||||||
gulong *prop;
|
|
||||||
guchar *prop_ch;
|
|
||||||
} prop = { NULL };
|
|
||||||
gulong nitems;
|
|
||||||
gulong bytes_after;
|
|
||||||
int error, result;
|
|
||||||
|
|
||||||
g_assert (icon->manager_window != None);
|
|
||||||
|
|
||||||
xdisplay = GDK_DISPLAY_XDISPLAY (gtk_widget_get_display (GTK_WIDGET (icon)));
|
|
||||||
|
|
||||||
gdk_error_trap_push ();
|
|
||||||
type = None;
|
|
||||||
result = XGetWindowProperty (xdisplay,
|
|
||||||
icon->manager_window,
|
|
||||||
icon->orientation_atom,
|
|
||||||
0, G_MAXLONG, FALSE,
|
|
||||||
XA_CARDINAL,
|
|
||||||
&type, &format, &nitems,
|
|
||||||
&bytes_after, &(prop.prop_ch));
|
|
||||||
error = gdk_error_trap_pop ();
|
|
||||||
|
|
||||||
if (error || result != Success)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (type == XA_CARDINAL)
|
|
||||||
{
|
|
||||||
GtkOrientation orientation;
|
|
||||||
|
|
||||||
orientation = (prop.prop [0] == SYSTEM_TRAY_ORIENTATION_HORZ) ?
|
|
||||||
GTK_ORIENTATION_HORIZONTAL :
|
|
||||||
GTK_ORIENTATION_VERTICAL;
|
|
||||||
|
|
||||||
if (icon->orientation != orientation)
|
|
||||||
{
|
|
||||||
icon->orientation = orientation;
|
|
||||||
|
|
||||||
g_object_notify (G_OBJECT (icon), "orientation");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (prop.prop)
|
|
||||||
XFree (prop.prop);
|
|
||||||
}
|
|
||||||
|
|
||||||
static GdkFilterReturn
|
|
||||||
egg_tray_icon_manager_filter (GdkXEvent *xevent, GdkEvent *event, gpointer user_data)
|
|
||||||
{
|
|
||||||
EggTrayIcon *icon = user_data;
|
|
||||||
XEvent *xev = (XEvent *)xevent;
|
|
||||||
|
|
||||||
if (xev->xany.type == ClientMessage &&
|
|
||||||
xev->xclient.message_type == icon->manager_atom &&
|
|
||||||
xev->xclient.data.l[1] == icon->selection_atom)
|
|
||||||
{
|
|
||||||
egg_tray_icon_update_manager_window (icon);
|
|
||||||
}
|
|
||||||
else if (xev->xany.window == icon->manager_window)
|
|
||||||
{
|
|
||||||
if (xev->xany.type == PropertyNotify &&
|
|
||||||
xev->xproperty.atom == icon->orientation_atom)
|
|
||||||
{
|
|
||||||
egg_tray_icon_get_orientation_property (icon);
|
|
||||||
}
|
|
||||||
if (xev->xany.type == DestroyNotify)
|
|
||||||
{
|
|
||||||
egg_tray_icon_update_manager_window (icon);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return GDK_FILTER_CONTINUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
egg_tray_icon_unrealize (GtkWidget *widget)
|
|
||||||
{
|
|
||||||
EggTrayIcon *icon = EGG_TRAY_ICON (widget);
|
|
||||||
GdkWindow *root_window;
|
|
||||||
|
|
||||||
if (icon->manager_window != None)
|
|
||||||
{
|
|
||||||
GdkWindow *gdkwin;
|
|
||||||
|
|
||||||
gdkwin = gdk_window_lookup_for_display (gtk_widget_get_display (widget),
|
|
||||||
icon->manager_window);
|
|
||||||
|
|
||||||
gdk_window_remove_filter (gdkwin, egg_tray_icon_manager_filter, icon);
|
|
||||||
}
|
|
||||||
|
|
||||||
root_window = gdk_screen_get_root_window (gtk_widget_get_screen (widget));
|
|
||||||
|
|
||||||
gdk_window_remove_filter (root_window, egg_tray_icon_manager_filter, icon);
|
|
||||||
|
|
||||||
if (GTK_WIDGET_CLASS (parent_class)->unrealize)
|
|
||||||
(* GTK_WIDGET_CLASS (parent_class)->unrealize) (widget);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
egg_tray_icon_send_manager_message (EggTrayIcon *icon,
|
|
||||||
long message,
|
|
||||||
Window window,
|
|
||||||
long data1,
|
|
||||||
long data2,
|
|
||||||
long data3)
|
|
||||||
{
|
|
||||||
XClientMessageEvent ev;
|
|
||||||
Display *display;
|
|
||||||
|
|
||||||
ev.type = ClientMessage;
|
|
||||||
ev.window = window;
|
|
||||||
ev.message_type = icon->system_tray_opcode_atom;
|
|
||||||
ev.format = 32;
|
|
||||||
ev.data.l[0] = gdk_x11_get_server_time (GTK_WIDGET (icon)->window);
|
|
||||||
ev.data.l[1] = message;
|
|
||||||
ev.data.l[2] = data1;
|
|
||||||
ev.data.l[3] = data2;
|
|
||||||
ev.data.l[4] = data3;
|
|
||||||
|
|
||||||
display = GDK_DISPLAY_XDISPLAY (gtk_widget_get_display (GTK_WIDGET (icon)));
|
|
||||||
|
|
||||||
gdk_error_trap_push ();
|
|
||||||
XSendEvent (display,
|
|
||||||
icon->manager_window, False, NoEventMask, (XEvent *)&ev);
|
|
||||||
XSync (display, False);
|
|
||||||
gdk_error_trap_pop ();
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
egg_tray_icon_send_dock_request (EggTrayIcon *icon)
|
|
||||||
{
|
|
||||||
egg_tray_icon_send_manager_message (icon,
|
|
||||||
SYSTEM_TRAY_REQUEST_DOCK,
|
|
||||||
icon->manager_window,
|
|
||||||
gtk_plug_get_id (GTK_PLUG (icon)),
|
|
||||||
0, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
egg_tray_icon_update_manager_window (EggTrayIcon *icon)
|
|
||||||
{
|
|
||||||
Display *xdisplay;
|
|
||||||
|
|
||||||
xdisplay = GDK_DISPLAY_XDISPLAY (gtk_widget_get_display (GTK_WIDGET (icon)));
|
|
||||||
|
|
||||||
if (icon->manager_window != None)
|
|
||||||
{
|
|
||||||
GdkWindow *gdkwin;
|
|
||||||
|
|
||||||
gdkwin = gdk_window_lookup_for_display (gtk_widget_get_display (GTK_WIDGET (icon)),
|
|
||||||
icon->manager_window);
|
|
||||||
|
|
||||||
gdk_window_remove_filter (gdkwin, egg_tray_icon_manager_filter, icon);
|
|
||||||
}
|
|
||||||
|
|
||||||
XGrabServer (xdisplay);
|
|
||||||
|
|
||||||
icon->manager_window = XGetSelectionOwner (xdisplay,
|
|
||||||
icon->selection_atom);
|
|
||||||
|
|
||||||
if (icon->manager_window != None)
|
|
||||||
XSelectInput (xdisplay,
|
|
||||||
icon->manager_window, StructureNotifyMask|PropertyChangeMask);
|
|
||||||
|
|
||||||
XUngrabServer (xdisplay);
|
|
||||||
XFlush (xdisplay);
|
|
||||||
|
|
||||||
if (icon->manager_window != None)
|
|
||||||
{
|
|
||||||
GdkWindow *gdkwin;
|
|
||||||
|
|
||||||
gdkwin = gdk_window_lookup_for_display (gtk_widget_get_display (GTK_WIDGET (icon)),
|
|
||||||
icon->manager_window);
|
|
||||||
|
|
||||||
gdk_window_add_filter (gdkwin, egg_tray_icon_manager_filter, icon);
|
|
||||||
|
|
||||||
/* Send a request that we'd like to dock */
|
|
||||||
egg_tray_icon_send_dock_request (icon);
|
|
||||||
|
|
||||||
egg_tray_icon_get_orientation_property (icon);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
egg_tray_icon_realize (GtkWidget *widget)
|
|
||||||
{
|
|
||||||
EggTrayIcon *icon = EGG_TRAY_ICON (widget);
|
|
||||||
GdkScreen *screen;
|
|
||||||
GdkDisplay *display;
|
|
||||||
Display *xdisplay;
|
|
||||||
char buffer[256];
|
|
||||||
GdkWindow *root_window;
|
|
||||||
|
|
||||||
if (GTK_WIDGET_CLASS (parent_class)->realize)
|
|
||||||
GTK_WIDGET_CLASS (parent_class)->realize (widget);
|
|
||||||
|
|
||||||
screen = gtk_widget_get_screen (widget);
|
|
||||||
display = gdk_screen_get_display (screen);
|
|
||||||
xdisplay = gdk_x11_display_get_xdisplay (display);
|
|
||||||
|
|
||||||
/* Now see if there's a manager window around */
|
|
||||||
g_snprintf (buffer, sizeof (buffer),
|
|
||||||
"_NET_SYSTEM_TRAY_S%d",
|
|
||||||
gdk_screen_get_number (screen));
|
|
||||||
|
|
||||||
icon->selection_atom = XInternAtom (xdisplay, buffer, False);
|
|
||||||
|
|
||||||
icon->manager_atom = XInternAtom (xdisplay, "MANAGER", False);
|
|
||||||
|
|
||||||
icon->system_tray_opcode_atom = XInternAtom (xdisplay,
|
|
||||||
"_NET_SYSTEM_TRAY_OPCODE",
|
|
||||||
False);
|
|
||||||
|
|
||||||
icon->orientation_atom = XInternAtom (xdisplay,
|
|
||||||
"_NET_SYSTEM_TRAY_ORIENTATION",
|
|
||||||
False);
|
|
||||||
|
|
||||||
egg_tray_icon_update_manager_window (icon);
|
|
||||||
|
|
||||||
root_window = gdk_screen_get_root_window (screen);
|
|
||||||
|
|
||||||
/* Add a root window filter so that we get changes on MANAGER */
|
|
||||||
gdk_window_add_filter (root_window,
|
|
||||||
egg_tray_icon_manager_filter, icon);
|
|
||||||
}
|
|
||||||
|
|
||||||
EggTrayIcon *
|
|
||||||
egg_tray_icon_new_for_screen (GdkScreen *screen, const char *name)
|
|
||||||
{
|
|
||||||
g_return_val_if_fail (GDK_IS_SCREEN (screen), NULL);
|
|
||||||
|
|
||||||
return g_object_new (EGG_TYPE_TRAY_ICON, "screen", screen, "title", name, NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
EggTrayIcon*
|
|
||||||
egg_tray_icon_new (const gchar *name)
|
|
||||||
{
|
|
||||||
return g_object_new (EGG_TYPE_TRAY_ICON, "title", name, NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
guint
|
|
||||||
egg_tray_icon_send_message (EggTrayIcon *icon,
|
|
||||||
gint timeout,
|
|
||||||
const gchar *message,
|
|
||||||
gint len)
|
|
||||||
{
|
|
||||||
guint stamp;
|
|
||||||
|
|
||||||
g_return_val_if_fail (EGG_IS_TRAY_ICON (icon), 0);
|
|
||||||
g_return_val_if_fail (timeout >= 0, 0);
|
|
||||||
g_return_val_if_fail (message != NULL, 0);
|
|
||||||
|
|
||||||
if (icon->manager_window == None)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if (len < 0)
|
|
||||||
len = strlen (message);
|
|
||||||
|
|
||||||
stamp = icon->stamp++;
|
|
||||||
|
|
||||||
/* Get ready to send the message */
|
|
||||||
egg_tray_icon_send_manager_message (icon, SYSTEM_TRAY_BEGIN_MESSAGE,
|
|
||||||
(Window)gtk_plug_get_id (GTK_PLUG (icon)),
|
|
||||||
timeout, len, stamp);
|
|
||||||
|
|
||||||
/* Now to send the actual message */
|
|
||||||
gdk_error_trap_push ();
|
|
||||||
while (len > 0)
|
|
||||||
{
|
|
||||||
XClientMessageEvent ev;
|
|
||||||
Display *xdisplay;
|
|
||||||
|
|
||||||
xdisplay = GDK_DISPLAY_XDISPLAY (gtk_widget_get_display (GTK_WIDGET (icon)));
|
|
||||||
|
|
||||||
ev.type = ClientMessage;
|
|
||||||
ev.window = (Window)gtk_plug_get_id (GTK_PLUG (icon));
|
|
||||||
ev.format = 8;
|
|
||||||
ev.message_type = XInternAtom (xdisplay,
|
|
||||||
"_NET_SYSTEM_TRAY_MESSAGE_DATA", False);
|
|
||||||
if (len > 20)
|
|
||||||
{
|
|
||||||
memcpy (&ev.data, message, 20);
|
|
||||||
len -= 20;
|
|
||||||
message += 20;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
memcpy (&ev.data, message, len);
|
|
||||||
len = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
XSendEvent (xdisplay,
|
|
||||||
icon->manager_window, False, StructureNotifyMask, (XEvent *)&ev);
|
|
||||||
XSync (xdisplay, False);
|
|
||||||
}
|
|
||||||
gdk_error_trap_pop ();
|
|
||||||
|
|
||||||
return stamp;
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
egg_tray_icon_cancel_message (EggTrayIcon *icon,
|
|
||||||
guint id)
|
|
||||||
{
|
|
||||||
g_return_if_fail (EGG_IS_TRAY_ICON (icon));
|
|
||||||
g_return_if_fail (id > 0);
|
|
||||||
|
|
||||||
egg_tray_icon_send_manager_message (icon, SYSTEM_TRAY_CANCEL_MESSAGE,
|
|
||||||
(Window)gtk_plug_get_id (GTK_PLUG (icon)),
|
|
||||||
id, 0, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
GtkOrientation
|
|
||||||
egg_tray_icon_get_orientation (EggTrayIcon *icon)
|
|
||||||
{
|
|
||||||
g_return_val_if_fail (EGG_IS_TRAY_ICON (icon), GTK_ORIENTATION_HORIZONTAL);
|
|
||||||
|
|
||||||
return icon->orientation;
|
|
||||||
}
|
|
@ -1,77 +0,0 @@
|
|||||||
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
|
|
||||||
/* eggtrayicon.h
|
|
||||||
* Copyright (C) 2002 Anders Carlsson <andersca@gnu.org>
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the
|
|
||||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
|
||||||
* Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef __EGG_TRAY_ICON_H__
|
|
||||||
#define __EGG_TRAY_ICON_H__
|
|
||||||
|
|
||||||
#include <gtk/gtkplug.h>
|
|
||||||
#include <gdk/gdkx.h>
|
|
||||||
|
|
||||||
G_BEGIN_DECLS
|
|
||||||
|
|
||||||
#define EGG_TYPE_TRAY_ICON (egg_tray_icon_get_type ())
|
|
||||||
#define EGG_TRAY_ICON(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), EGG_TYPE_TRAY_ICON, EggTrayIcon))
|
|
||||||
#define EGG_TRAY_ICON_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), EGG_TYPE_TRAY_ICON, EggTrayIconClass))
|
|
||||||
#define EGG_IS_TRAY_ICON(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), EGG_TYPE_TRAY_ICON))
|
|
||||||
#define EGG_IS_TRAY_ICON_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), EGG_TYPE_TRAY_ICON))
|
|
||||||
#define EGG_TRAY_ICON_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), EGG_TYPE_TRAY_ICON, EggTrayIconClass))
|
|
||||||
|
|
||||||
typedef struct _EggTrayIcon EggTrayIcon;
|
|
||||||
typedef struct _EggTrayIconClass EggTrayIconClass;
|
|
||||||
|
|
||||||
struct _EggTrayIcon
|
|
||||||
{
|
|
||||||
GtkPlug parent_instance;
|
|
||||||
|
|
||||||
guint stamp;
|
|
||||||
|
|
||||||
Atom selection_atom;
|
|
||||||
Atom manager_atom;
|
|
||||||
Atom system_tray_opcode_atom;
|
|
||||||
Atom orientation_atom;
|
|
||||||
Window manager_window;
|
|
||||||
|
|
||||||
GtkOrientation orientation;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct _EggTrayIconClass
|
|
||||||
{
|
|
||||||
GtkPlugClass parent_class;
|
|
||||||
};
|
|
||||||
|
|
||||||
GType egg_tray_icon_get_type (void);
|
|
||||||
|
|
||||||
EggTrayIcon *egg_tray_icon_new_for_screen (GdkScreen *screen,
|
|
||||||
const gchar *name);
|
|
||||||
|
|
||||||
EggTrayIcon *egg_tray_icon_new (const gchar *name);
|
|
||||||
|
|
||||||
guint egg_tray_icon_send_message (EggTrayIcon *icon,
|
|
||||||
gint timeout,
|
|
||||||
const char *message,
|
|
||||||
gint len);
|
|
||||||
void egg_tray_icon_cancel_message (EggTrayIcon *icon,
|
|
||||||
guint id);
|
|
||||||
|
|
||||||
GtkOrientation egg_tray_icon_get_orientation (EggTrayIcon *icon);
|
|
||||||
|
|
||||||
G_END_DECLS
|
|
||||||
|
|
||||||
#endif /* __EGG_TRAY_ICON_H__ */
|
|
@ -2,6 +2,7 @@
|
|||||||
* notification.c
|
* notification.c
|
||||||
*
|
*
|
||||||
* Copyright (C) 2002 Sun Microsystems, Inc.
|
* Copyright (C) 2002 Sun Microsystems, Inc.
|
||||||
|
* Copyright (C) 2006 Christian Persch
|
||||||
*
|
*
|
||||||
* This library is free software; you can redistribute it and/or
|
* This library is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Library General Public
|
* modify it under the terms of the GNU Library General Public
|
||||||
@ -23,6 +24,7 @@
|
|||||||
|
|
||||||
#include <config.h>
|
#include <config.h>
|
||||||
|
|
||||||
|
#include <gtk/gtk.h>
|
||||||
#include <glade/glade.h>
|
#include <glade/glade.h>
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
@ -32,101 +34,71 @@
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include "zenity.h"
|
#include "zenity.h"
|
||||||
#include "eggtrayicon.h"
|
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
|
|
||||||
static EggTrayIcon *tray_icon;
|
static GtkStatusIcon *status_icon;
|
||||||
static GtkWidget *icon_image;
|
static gchar *icon_file;
|
||||||
static GtkWidget *icon_event_box;
|
static const gchar *icon_stock;
|
||||||
static GtkTooltips *tooltips;
|
static gint icon_size;
|
||||||
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
set_scaled_pixbuf (GtkImage *image, GdkPixbuf *pixbuf, GtkIconSize icon_size)
|
zenity_notification_icon_update (void)
|
||||||
{
|
{
|
||||||
GdkScreen *screen;
|
GdkPixbuf *pixbuf;
|
||||||
GtkSettings *settings;
|
GError *error = NULL;
|
||||||
int width, height, desired_width, desired_height;
|
|
||||||
GdkPixbuf *new_pixbuf;
|
|
||||||
|
|
||||||
screen = gtk_widget_get_screen (GTK_WIDGET (image));
|
pixbuf = gdk_pixbuf_new_from_file_at_scale (icon_file, icon_size, icon_size, TRUE, &error);
|
||||||
settings = gtk_settings_get_for_screen (screen);
|
if (error) {
|
||||||
if (!gtk_icon_size_lookup_for_settings (settings, icon_size,
|
g_warning ("Could not load notification icon '%s': %s",
|
||||||
&desired_width, &desired_height))
|
icon_file, error->message);
|
||||||
return;
|
g_clear_error (&error);
|
||||||
|
}
|
||||||
|
if (!pixbuf) {
|
||||||
|
pixbuf = gdk_pixbuf_new_from_file_at_scale (ZENITY_IMAGE_FULLPATH ("zenity-notification.png"),
|
||||||
|
icon_size, icon_size, TRUE, NULL);
|
||||||
|
}
|
||||||
|
|
||||||
width = gdk_pixbuf_get_width (pixbuf);
|
gtk_status_icon_set_from_pixbuf (status_icon, pixbuf);
|
||||||
height = gdk_pixbuf_get_height (pixbuf);
|
|
||||||
if (height > desired_height || width > desired_width) {
|
|
||||||
if (width * desired_height / height > desired_width)
|
|
||||||
desired_height = height * desired_width / width;
|
|
||||||
else
|
|
||||||
desired_width = width * desired_height / height;
|
|
||||||
|
|
||||||
new_pixbuf = gdk_pixbuf_scale_simple (pixbuf,
|
if (pixbuf) {
|
||||||
desired_width,
|
g_object_unref (pixbuf);
|
||||||
desired_height,
|
|
||||||
GDK_INTERP_BILINEAR);
|
|
||||||
gtk_image_set_from_pixbuf (image, new_pixbuf);
|
|
||||||
g_object_unref (new_pixbuf);
|
|
||||||
} else {
|
|
||||||
gtk_image_set_from_pixbuf (image, pixbuf);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
zenity_notification_icon_press_callback (GtkWidget *widget, GdkEventButton *event, gpointer data)
|
zenity_notification_icon_size_changed_cb (GtkStatusIcon *icon,
|
||||||
|
gint size,
|
||||||
|
gpointer user_data)
|
||||||
{
|
{
|
||||||
ZenityData *zen_data;
|
icon_size = size;
|
||||||
|
|
||||||
zen_data = data;
|
/* If we're displaying not a stock icon but a custom pixbuf,
|
||||||
|
* we need to update the icon for the new size.
|
||||||
|
*/
|
||||||
|
if (!icon_stock) {
|
||||||
|
zenity_notification_icon_update ();
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
zenity_notification_icon_activate_cb (GtkWidget *widget,
|
||||||
|
ZenityData *data)
|
||||||
|
{
|
||||||
|
data->exit_code = zenity_util_return_exit_code (ZENITY_OK);
|
||||||
|
|
||||||
zen_data->exit_code = zenity_util_return_exit_code (ZENITY_OK);
|
|
||||||
gtk_main_quit ();
|
gtk_main_quit ();
|
||||||
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
zenity_notification_icon_expose_callback (GtkWidget *widget, GdkEventExpose *event, gpointer data)
|
zenity_notification_handle_stdin (GIOChannel *channel,
|
||||||
{
|
|
||||||
if (GTK_WIDGET_HAS_FOCUS (widget)) {
|
|
||||||
gint focus_width, focus_pad;
|
|
||||||
gint x, y, width, height;
|
|
||||||
|
|
||||||
gtk_widget_style_get (widget,
|
|
||||||
"focus-line-width", &focus_width,
|
|
||||||
"focus-padding", &focus_pad,
|
|
||||||
NULL);
|
|
||||||
x = widget->allocation.x + focus_pad;
|
|
||||||
y = widget->allocation.y + focus_pad;
|
|
||||||
width = widget->allocation.width - 2 * focus_pad;
|
|
||||||
height = widget->allocation.height - 2 * focus_pad;
|
|
||||||
|
|
||||||
gtk_paint_focus (widget->style, widget->window,
|
|
||||||
GTK_WIDGET_STATE (widget),
|
|
||||||
&event->area, widget, "button",
|
|
||||||
x, y, width, height);
|
|
||||||
}
|
|
||||||
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
zenity_notification_icon_destroy_callback (GtkWidget *widget, gpointer data)
|
|
||||||
{
|
|
||||||
ZenityData *zen_data;
|
|
||||||
|
|
||||||
zen_data = data;
|
|
||||||
gtk_widget_destroy (GTK_WIDGET (tray_icon));
|
|
||||||
|
|
||||||
zen_data->exit_code = zenity_util_return_exit_code (ZENITY_ESC);
|
|
||||||
gtk_main_quit ();
|
|
||||||
}
|
|
||||||
|
|
||||||
static gboolean
|
|
||||||
zenity_notification_handle_stdin (GIOChannel *channel,
|
|
||||||
GIOCondition condition,
|
GIOCondition condition,
|
||||||
gpointer user_data)
|
gpointer user_data)
|
||||||
{
|
{
|
||||||
ZenityData *zen_data;
|
ZenityData *zen_data;
|
||||||
|
|
||||||
@ -137,7 +109,7 @@ zenity_notification_handle_stdin (GIOChannel *channel,
|
|||||||
GError *error = NULL;
|
GError *error = NULL;
|
||||||
|
|
||||||
string = g_string_new (NULL);
|
string = g_string_new (NULL);
|
||||||
while (channel->is_readable != TRUE)
|
while (channel->is_readable == FALSE)
|
||||||
;
|
;
|
||||||
do {
|
do {
|
||||||
gint status;
|
gint status;
|
||||||
@ -167,60 +139,72 @@ zenity_notification_handle_stdin (GIOChannel *channel,
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
/* split off the command and value */
|
/* split off the command and value */
|
||||||
command = g_strndup (string->str, colon - string->str);
|
command = g_strstrip (g_strndup (string->str, colon - string->str));
|
||||||
command = g_strstrip (command);
|
|
||||||
g_strdown (command);
|
|
||||||
|
|
||||||
value = colon + 1;
|
value = colon + 1;
|
||||||
while (*value && g_ascii_isspace (*value)) value++;
|
while (*value && g_ascii_isspace (*value)) value++;
|
||||||
|
|
||||||
if (!strcmp (command, "icon")) {
|
if (!g_ascii_strcasecmp (command, "icon")) {
|
||||||
GdkPixbuf *pixbuf;
|
icon_stock = zenity_util_stock_from_filename (value);
|
||||||
|
|
||||||
pixbuf = zenity_util_pixbuf_new_from_file (GTK_WIDGET (tray_icon),
|
g_free (icon_file);
|
||||||
value);
|
icon_file = g_strdup (value);
|
||||||
if (pixbuf != NULL) {
|
|
||||||
set_scaled_pixbuf (GTK_IMAGE (icon_image), pixbuf,
|
if (icon_stock) {
|
||||||
GTK_ICON_SIZE_BUTTON);
|
gtk_status_icon_set_from_stock (status_icon, icon_stock);
|
||||||
gdk_pixbuf_unref (pixbuf);
|
} else if (gtk_status_icon_get_visible (status_icon) &&
|
||||||
} else {
|
gtk_status_icon_is_embedded (status_icon)) {
|
||||||
g_warning ("Could not load notification icon : %s", value);
|
zenity_notification_icon_update ();
|
||||||
}
|
}
|
||||||
} else if (!strcmp (command, "message")) {
|
} else if (!g_ascii_strcasecmp (command, "message")) {
|
||||||
#ifdef HAVE_LIBNOTIFY
|
#ifdef HAVE_LIBNOTIFY
|
||||||
/* display a notification bubble */
|
/* display a notification bubble */
|
||||||
if (notify_is_initted ()) {
|
if (!g_utf8_validate (value, -1, NULL)) {
|
||||||
GError *error = NULL;
|
g_warning ("Invalid UTF-8 in input!");
|
||||||
NotifyNotification *n;
|
} else if (notify_is_initted ()) {
|
||||||
GdkPixbuf *icon;
|
GError *error = NULL;
|
||||||
|
NotifyNotification *notif;
|
||||||
|
const gchar *icon = NULL;
|
||||||
|
gchar *freeme = NULL;
|
||||||
|
gchar *message;
|
||||||
|
|
||||||
n = notify_notification_new (g_strcompress (value), NULL, NULL,
|
message = g_strcompress (value);
|
||||||
GTK_WIDGET (tray_icon));
|
|
||||||
|
|
||||||
icon = gtk_image_get_pixbuf (GTK_IMAGE (icon_image));
|
if (icon_stock) {
|
||||||
|
icon = icon_stock;
|
||||||
|
} else if (icon_file) {
|
||||||
|
icon = freeme = g_filename_to_uri (icon_file, NULL, NULL);
|
||||||
|
}
|
||||||
|
|
||||||
notify_notification_set_icon_from_pixbuf (n, icon);
|
notif = notify_notification_new_with_status_icon (message, NULL /* summary */,
|
||||||
|
icon, status_icon);
|
||||||
|
g_free (message);
|
||||||
|
g_free (freeme);
|
||||||
|
|
||||||
notify_notification_show (n, &error);
|
notify_notification_show (notif, &error);
|
||||||
if (error) {
|
if (error) {
|
||||||
g_warning (error->message);
|
g_warning ("Error showing notification: %s", error->message);
|
||||||
g_error_free (error);
|
g_error_free (error);
|
||||||
}
|
}
|
||||||
|
|
||||||
g_object_unref (G_OBJECT (n));
|
g_object_unref (notif);
|
||||||
} else {
|
} else {
|
||||||
#else
|
#else
|
||||||
{ /* this brace is for balance */
|
{ /* this brace is for balance */
|
||||||
#endif
|
#endif
|
||||||
g_warning ("Notification framework not available");
|
g_warning ("Notification framework not available");
|
||||||
}
|
}
|
||||||
} else if (!strcmp (command, "tooltip")) {
|
} else if (!g_ascii_strcasecmp (command, "tooltip")) {
|
||||||
gtk_tooltips_set_tip (tooltips, icon_event_box, value, value);
|
if (g_utf8_validate (value, -1, NULL)) {
|
||||||
} else if (!strcmp (command, "visible")) {
|
gtk_status_icon_set_tooltip (status_icon, value);
|
||||||
if (!strcasecmp (value, "false")) {
|
} else {
|
||||||
gtk_widget_hide (GTK_WIDGET (tray_icon));
|
g_warning ("Invalid UTF-8 in input!");
|
||||||
} else {
|
}
|
||||||
gtk_widget_show (GTK_WIDGET (tray_icon));
|
} else if (!g_ascii_strcasecmp (command, "visible")) {
|
||||||
|
if (!g_ascii_strcasecmp (value, "false")) {
|
||||||
|
gtk_status_icon_set_visible (status_icon, FALSE);
|
||||||
|
} else {
|
||||||
|
gtk_status_icon_set_visible (status_icon, TRUE);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
g_warning ("Unknown command '%s'", command);
|
g_warning ("Unknown command '%s'", command);
|
||||||
@ -256,64 +240,47 @@ zenity_notification_listen_on_stdin (ZenityData *data)
|
|||||||
void
|
void
|
||||||
zenity_notification (ZenityData *data, ZenityNotificationData *notification_data)
|
zenity_notification (ZenityData *data, ZenityNotificationData *notification_data)
|
||||||
{
|
{
|
||||||
GdkPixbuf *pixbuf = NULL;
|
status_icon = gtk_status_icon_new ();
|
||||||
|
g_signal_connect (status_icon, "size-changed",
|
||||||
|
G_CALLBACK (zenity_notification_icon_size_changed_cb), data);
|
||||||
|
|
||||||
tray_icon = egg_tray_icon_new (_("Zenity notification"));
|
if (notification_data->notification_text) {
|
||||||
tooltips = gtk_tooltips_new ();
|
gtk_status_icon_set_tooltip (status_icon, notification_data->notification_text);
|
||||||
|
|
||||||
if (data->window_icon != NULL)
|
|
||||||
pixbuf = zenity_util_pixbuf_new_from_file (GTK_WIDGET (tray_icon), data->window_icon);
|
|
||||||
else
|
|
||||||
pixbuf = gdk_pixbuf_new_from_file (ZENITY_IMAGE_FULLPATH ("zenity-notification.png"), NULL);
|
|
||||||
|
|
||||||
icon_event_box = gtk_event_box_new ();
|
|
||||||
icon_image = gtk_image_new ();
|
|
||||||
|
|
||||||
if (pixbuf) {
|
|
||||||
set_scaled_pixbuf (GTK_IMAGE (icon_image), pixbuf,
|
|
||||||
GTK_ICON_SIZE_BUTTON);
|
|
||||||
gdk_pixbuf_unref (pixbuf);
|
|
||||||
} else {
|
} else {
|
||||||
if (data->window_icon != NULL) {
|
gtk_status_icon_set_tooltip (status_icon, _("Zenity notification"));
|
||||||
g_warning ("Could not load notification icon : %s", data->window_icon);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
g_warning ("Could not load notification icon : %s", ZENITY_IMAGE_FULLPATH ("zenity-notification.png"));
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
gtk_container_add (GTK_CONTAINER (icon_event_box), icon_image);
|
icon_file = g_strdup (data->window_icon);
|
||||||
|
icon_stock = zenity_util_stock_from_filename (data->window_icon);
|
||||||
|
|
||||||
if (notification_data->notification_text)
|
/* Only set the stock icon here; if we're going to display a
|
||||||
gtk_tooltips_set_tip (tooltips, icon_event_box, notification_data->notification_text, notification_data->notification_text);
|
* custom pixbuf we wait for the size-changed signal to load
|
||||||
else
|
* it at the right size.
|
||||||
gtk_tooltips_set_tip (tooltips, icon_event_box, _("Zenity notification"), _("Zenity notification"));
|
*/
|
||||||
|
if (icon_stock) {
|
||||||
gtk_widget_add_events (GTK_WIDGET (tray_icon), GDK_BUTTON_PRESS_MASK | GDK_FOCUS_CHANGE_MASK);
|
gtk_status_icon_set_from_stock (status_icon, icon_stock);
|
||||||
gtk_container_add (GTK_CONTAINER (tray_icon), icon_event_box);
|
|
||||||
|
|
||||||
g_signal_connect (tray_icon, "destroy",
|
|
||||||
G_CALLBACK (zenity_notification_icon_destroy_callback), data);
|
|
||||||
|
|
||||||
g_signal_connect (tray_icon, "expose_event",
|
|
||||||
G_CALLBACK (zenity_notification_icon_expose_callback), data);
|
|
||||||
|
|
||||||
if (notification_data->listen) {
|
|
||||||
zenity_notification_listen_on_stdin (data);
|
|
||||||
} else {
|
|
||||||
/* if we aren't listening for changes, then close on button_press */
|
|
||||||
g_signal_connect (tray_icon, "button_press_event",
|
|
||||||
G_CALLBACK (zenity_notification_icon_press_callback), data);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef HAVE_LIBNOTIFY
|
#ifdef HAVE_LIBNOTIFY
|
||||||
/* create the notification widget */
|
/* create the notification widget */
|
||||||
if (!notify_is_initted ())
|
if (!notify_is_initted ()) {
|
||||||
notify_init (_("Zenity notification"));
|
notify_init (_("Zenity notification"));
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
gtk_widget_show_all (GTK_WIDGET (tray_icon));
|
if (notification_data->listen) {
|
||||||
|
zenity_notification_listen_on_stdin (data);
|
||||||
/* Does nothing at the moment */
|
} else {
|
||||||
|
/* if we aren't listening for changes, then close on activate (left-click) */
|
||||||
|
g_signal_connect (status_icon, "activate",
|
||||||
|
G_CALLBACK (zenity_notification_icon_activate_cb), data);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Show icon and wait */
|
||||||
|
gtk_status_icon_set_visible (status_icon, TRUE);
|
||||||
gtk_main ();
|
gtk_main ();
|
||||||
|
|
||||||
|
/* Cleanup */
|
||||||
|
g_object_unref (status_icon);
|
||||||
|
g_free (icon_file);
|
||||||
}
|
}
|
||||||
|
38
src/util.c
38
src/util.c
@ -145,19 +145,33 @@ zenity_util_fill_file_buffer (GtkTextBuffer *buffer, const gchar *filename)
|
|||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
GdkPixbuf *
|
const gchar *
|
||||||
zenity_util_pixbuf_new_from_file (GtkWidget *widget, gchar *filename)
|
zenity_util_stock_from_filename (const gchar *filename)
|
||||||
{
|
{
|
||||||
if (!strcasecmp (filename, "warning"))
|
if (!filename || !filename[0])
|
||||||
return gtk_widget_render_icon (widget, GTK_STOCK_DIALOG_WARNING, GTK_ICON_SIZE_BUTTON, NULL);
|
return GTK_STOCK_DIALOG_WARNING; /* default */
|
||||||
if (!strcasecmp (filename, "info"))
|
|
||||||
return gtk_widget_render_icon (widget, GTK_STOCK_DIALOG_INFO, GTK_ICON_SIZE_BUTTON, NULL);
|
if (!g_ascii_strcasecmp (filename, "warning"))
|
||||||
if (!strcasecmp (filename, "question"))
|
return GTK_STOCK_DIALOG_WARNING;
|
||||||
return gtk_widget_render_icon (widget, GTK_STOCK_DIALOG_QUESTION, GTK_ICON_SIZE_BUTTON, NULL);
|
if (!g_ascii_strcasecmp (filename, "info"))
|
||||||
if (!strcasecmp (filename, "error"))
|
return GTK_STOCK_DIALOG_INFO;
|
||||||
return gtk_widget_render_icon (widget, GTK_STOCK_DIALOG_ERROR, GTK_ICON_SIZE_BUTTON, NULL);
|
if (!g_ascii_strcasecmp (filename, "question"))
|
||||||
else
|
return GTK_STOCK_DIALOG_QUESTION;
|
||||||
return gdk_pixbuf_new_from_file (filename, NULL);
|
if (!g_ascii_strcasecmp (filename, "error"))
|
||||||
|
return GTK_STOCK_DIALOG_ERROR;
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
GdkPixbuf *
|
||||||
|
zenity_util_pixbuf_new_from_file (GtkWidget *widget, const gchar *filename)
|
||||||
|
{
|
||||||
|
const gchar *stock;
|
||||||
|
|
||||||
|
stock = zenity_util_stock_from_filename (filename);
|
||||||
|
if (stock)
|
||||||
|
return gtk_widget_render_icon (widget, stock, GTK_ICON_SIZE_BUTTON, NULL);
|
||||||
|
|
||||||
|
return gdk_pixbuf_new_from_file (filename, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -15,6 +15,7 @@ GladeXML* zenity_util_load_glade_file (const gchar *widge
|
|||||||
gchar * zenity_util_strip_newline (gchar *string);
|
gchar * zenity_util_strip_newline (gchar *string);
|
||||||
gboolean zenity_util_fill_file_buffer (GtkTextBuffer *buffer,
|
gboolean zenity_util_fill_file_buffer (GtkTextBuffer *buffer,
|
||||||
const gchar *filename);
|
const gchar *filename);
|
||||||
|
const gchar * zenity_util_stock_from_filename (const gchar *filename);
|
||||||
void zenity_util_set_window_icon (GtkWidget *widget,
|
void zenity_util_set_window_icon (GtkWidget *widget,
|
||||||
const gchar *filename,
|
const gchar *filename,
|
||||||
const gchar *default_file);
|
const gchar *default_file);
|
||||||
@ -22,7 +23,7 @@ void zenity_util_set_window_icon_from_stock (GtkWidget *widge
|
|||||||
const gchar *filename,
|
const gchar *filename,
|
||||||
const gchar *default_stock_id);
|
const gchar *default_stock_id);
|
||||||
GdkPixbuf * zenity_util_pixbuf_new_from_file (GtkWidget *widget,
|
GdkPixbuf * zenity_util_pixbuf_new_from_file (GtkWidget *widget,
|
||||||
gchar *filename);
|
const gchar *filename);
|
||||||
void zenity_util_show_help (GError **error);
|
void zenity_util_show_help (GError **error);
|
||||||
gint zenity_util_return_exit_code (ZenityExitCode value);
|
gint zenity_util_return_exit_code (ZenityExitCode value);
|
||||||
void zenity_util_show_dialog (GtkWidget *widget);
|
void zenity_util_show_dialog (GtkWidget *widget);
|
||||||
|
Reference in New Issue
Block a user