Logo Search packages:      
Sourcecode: eggcups version File versions  Download package

main.c

/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
/*
 * Copyright (C) 2002 CodeFactory AB
 * Copyright (C) 2002 Richard Hult <rhult@codefactory.se>
 * Copyright (C) 2002, 2003 Tim Waugh <twaugh@redhat.com>
 * Copyright (C) 2004 Red Hat, Inc.
 * Rewritten by Colin Walters <walters@redhat.com>
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as
 * published by the Free Software Foundation; either version 2 of the
 * License, or (at your option) any later version.
 *
 * This program 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
 * General Public License for more details.
 *
 * You should have received a copy of the GNU General Public
 * License along with this program; if not, write to the
 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
 * Boston, MA 02111-1307, USA.
 */

#include <config.h>
#include <signal.h>
#include <string.h>
#include <sys/wait.h>
#include <gtk/gtk.h>
#include <gconf/gconf.h>
#include <gconf/gconf-client.h>
#include <libgnomeui/libgnomeui.h>
#include <libgnome/gnome-i18n.h>
#include <libgnomecups/gnome-cups-init.h>
#include "ec-tray-icon.h"
#include "rb-debug.h"
#include <dbus/dbus.h>
#include <dbus/dbus-glib-lowlevel.h>

gboolean debug = 0;
gboolean show = 0;
static ECTrayIcon *icon;

static gboolean tray_destroy_cb (GtkWidget *win, GdkEventAny *event, gpointer unused);

static void
destroy_icon (void)
{
      if (icon) {
            rb_debug ("destroying icon!");
            gtk_widget_destroy (GTK_WIDGET (icon));
            icon = NULL;
      }
}

static gboolean
session_die (GnomeClient *client, gpointer client_data)
{
      destroy_icon ();
      gtk_main_quit ();

      return TRUE;
}

static gboolean
session_save (GnomeClient *client, gpointer client_data)
{
      return TRUE;
}

static int die_fds[2];
static GIOChannel *die_io_channel;

static void
handle_signal (int signum)
{
      write(die_fds[1], "!", 1);
}

static gboolean
handle_die_signal (GIOChannel *src,
               GIOCondition condition,
               gpointer data)
{
      char buf[1];
      gsize read;

      rb_debug ("got die input");
      g_io_channel_read_chars (src, buf, 1, &read, NULL);

      destroy_icon ();
      gtk_main_quit ();

      return TRUE;
}

int
main (int argc, char *argv[])
{
      GnomeClient *client;
      GPtrArray *restart_argv;
      char *dotdir;
      struct sigaction action;
      sigset_t block_mask;
      DBusConnection *dbus = NULL;
      dbus_uint32_t acquisition_result;
      DBusError error;

      const struct poptOption popt_options[] =
      {
            { "debug", 'd', POPT_ARG_NONE, &debug, 0, N_("Enable debugging information"), NULL },
            { "show", 's', POPT_ARG_NONE, &show, 0, N_("Show icon by default"), NULL },
            POPT_TABLEEND
      };

      bindtextdomain (GETTEXT_PACKAGE, EGGCUPS_LOCALEDIR);  
        bind_textdomain_codeset (GETTEXT_PACKAGE, "UTF-8");
      textdomain (GETTEXT_PACKAGE);

      gnome_program_init (PACKAGE, VERSION, LIBGNOMEUI_MODULE, 
                      argc, argv, 
                      GNOME_PARAM_POPT_TABLE, popt_options,
                      GNOME_PARAM_HUMAN_READABLE_NAME, _("Print Notifier"),
                      NULL);

      rb_debug_init (debug);

      client = gnome_master_client ();

      action.sa_handler = SIG_IGN;
      sigemptyset (&block_mask);
      action.sa_mask = block_mask;
      action.sa_flags = 0;
      sigaction (SIGHUP, &action, NULL);

      if (pipe(die_fds) < 0) {
            g_critical ("Couldn't create pipe: %s",
                      g_strerror (errno));
            goto lose;
      }
      action.sa_handler = handle_signal;
      sigemptyset (&block_mask);
      action.sa_mask = block_mask;
      action.sa_flags = 0;
      sigaction (SIGINT, &action, NULL);
      sigaction (SIGTERM, &action, NULL);
      
      rb_debug ("getting session bus");
      dbus_error_init (&error);
      dbus = dbus_bus_get (DBUS_BUS_SESSION, &error);
      if (dbus == NULL) {
            g_critical ("couldn't connect to session bus: %s", error.message);
            goto lose;
      }
      acquisition_result = dbus_bus_request_name (dbus,
                                        "com.redhat.PrinterManager",
                                        0,
                                        &error);
      rb_debug ("acquisition reply: %u error: %s",
              acquisition_result,
              dbus_error_is_set (&error) ? "YES" : "NO");
      if (dbus_error_is_set (&error)) {
            g_critical ("Couldn't check service: %s %s", error.name, error.message);
            goto lose;
      }     
      dbus_error_free (&error);
      if (acquisition_result == DBUS_REQUEST_NAME_REPLY_EXISTS) {
            g_message ("already active");
            goto lose;
      }

      rb_debug ("activated, starting up");
      dotdir = g_build_filename (g_get_home_dir (), ".eggcups", NULL);
      if (!g_file_test (dotdir, G_FILE_TEST_EXISTS | G_FILE_TEST_IS_DIR)) {
            if (mkdir (dotdir, 0750) < 0) {
                  g_critical ("Couldn't create .eggcups directory");
                  exit (1);
            }
      }
      g_free (dotdir);

      gnome_cups_init (NULL);

      g_signal_connect (client,
                    "save_yourself",
                    G_CALLBACK (session_save),
                    NULL);

      g_signal_connect (client,
                    "die",
                    G_CALLBACK (session_die),
                    NULL);

      restart_argv = g_ptr_array_new ();
      g_ptr_array_add (restart_argv, g_get_prgname ());
      gnome_client_set_restart_command (client, restart_argv->len, (char**) restart_argv->pdata);
      g_ptr_array_free (restart_argv, TRUE);
      gnome_client_set_restart_style (client, GNOME_RESTART_IMMEDIATELY);

      tray_destroy_cb (NULL, NULL, NULL);

      die_io_channel = g_io_channel_unix_new (die_fds[0]);
      g_io_add_watch (die_io_channel, G_IO_IN | G_IO_ERR,
                  handle_die_signal, NULL);

      gtk_main ();

      exit (0);
 lose:
      gnome_client_set_restart_style (client, GNOME_RESTART_NEVER);
      exit (1);
}

static gboolean
tray_destroy_cb (GtkWidget *win, GdkEventAny *event, gpointer unused)
{
      icon = NULL;

      if (icon) {
            rb_debug ("caught delete_event for tray icon");
            gtk_widget_destroy (GTK_WIDGET (icon));
      }

      rb_debug ("creating new tray icon");
      icon = ec_tray_icon_new ();
      gtk_object_sink (GTK_OBJECT (icon));
      g_signal_connect_object (G_OBJECT (icon), "destroy-event",
                         G_CALLBACK (tray_destroy_cb), NULL, 0);
      if (show) {
            gtk_widget_show_all (GTK_WIDGET (icon));
      }
 
      return TRUE;
}


Generated by  Doxygen 1.6.0   Back to index