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

yelp-base.c

/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
/*
 * Copyright (C) 2001-2002 Mikael Hallendal <micke@imendio.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.
 *
 * Author: Mikael Hallendal <micke@imendio.com>
 */

#include <config.h>

#include <bonobo/bonobo-main.h>
#include <libgnomevfs/gnome-vfs.h>
#include <gdk/gdkx.h>
#define SN_API_NOT_YET_FROZEN
#include <libsn/sn-launchee.h>

#include <string.h>

#include "yelp-window.h"
#include "yelp-settings.h"
#include "yelp-pager.h"
#include "yelp-toc-pager.h"
#include "yelp-base.h"
#include "yelp-bookmarks.h"

gboolean main_running;

#define YELP_BASE_GET_PRIVATE(object)(G_TYPE_INSTANCE_GET_PRIVATE ((object), YELP_TYPE_BASE, YelpBasePriv))

struct _YelpBasePriv {
      GNode  *toc_tree;

      GList  *index;
      GSList *windows;
};

static void           yelp_base_init                (YelpBase       *base);
static void           yelp_base_class_init          (YelpBaseClass  *klass);
static void           yelp_base_new_window_cb       (YelpWindow     *window,
                                         const gchar    *uri,
                                         YelpBase       *base);
static void           yelp_base_window_finalized_cb (YelpBase       *base,
                                         YelpWindow     *window);


#define PARENT_TYPE BONOBO_OBJECT_TYPE
static BonoboObjectClass *parent_class;

static void
impl_Yelp_newWindow (PortableServer_Servant  servant,
                 const CORBA_char       *url,
                 const CORBA_char       *time,
                 CORBA_Environment      *ev)
{
      YelpBase  *yelp_base;

      yelp_base = YELP_BASE (bonobo_object (servant));
      yelp_base_new_window (yelp_base, url, time);
}

static GNOME_Yelp_WindowList *
impl_Yelp_getWindows (PortableServer_Servant  servant,
                  CORBA_Environment      *ev)
{
      YelpBase              *base;
      YelpBasePriv          *priv;
      GNOME_Yelp_WindowList *list;
      gint                   len, i;
      GSList                *node;
      YelpDocInfo           *doc_info;
      gchar                 *uri;
      
      base = YELP_BASE (bonobo_object (servant));
      priv = base->priv;

      len  = g_slist_length (priv->windows);
      
      list = GNOME_Yelp_WindowList__alloc ();
      list->_buffer = CORBA_sequence_CORBA_string_allocbuf (len);
      list->_length = len;
      list->_maximum = len;
      CORBA_sequence_set_release (list, CORBA_TRUE);
      
      for (node = priv->windows, i = 0; node; node = node->next, i++) {
            doc_info = yelp_window_get_doc_info (YELP_WINDOW (node->data));
            uri = yelp_doc_info_get_uri (doc_info, NULL, YELP_URI_TYPE_ANY);
            list->_buffer[i] = CORBA_string_dup (uri);
            g_free (uri);
      }
      
      return list;
}

static void
yelp_base_init (YelpBase *base)
{
        YelpBasePriv *priv;

        base->priv = priv = YELP_BASE_GET_PRIVATE (base);
        
      priv->toc_tree = g_node_new (NULL);
      priv->index    = NULL;
      priv->windows  = NULL;

      yelp_bookmarks_init ();
      yelp_settings_init ();
}

static void
yelp_base_class_init (YelpBaseClass *klass)
{
      POA_GNOME_Yelp__epv *epv = &klass->epv;

      parent_class = gtk_type_class (PARENT_TYPE);

      epv->newWindow  = impl_Yelp_newWindow;
      epv->getWindows = impl_Yelp_getWindows;

      main_running = TRUE;

      g_type_class_add_private (klass, sizeof (YelpBasePriv));
}

static void
yelp_base_new_window_cb (YelpWindow *window, const gchar *uri,
                   YelpBase *base)
{
      GtkWidget *new_window;
      
      g_return_if_fail (YELP_IS_WINDOW (window));
      g_return_if_fail (YELP_IS_BASE (base));
      
      new_window = yelp_base_new_window (base, uri, NULL);

      gtk_widget_show (new_window);
}

static void
yelp_base_window_finalized_cb (YelpBase *base, YelpWindow *window)
{
      YelpBasePriv *priv;
      
      g_return_if_fail (YELP_IS_BASE (base));

      priv = base->priv;
      
      priv->windows = g_slist_remove (priv->windows, window);

      if (g_slist_length (priv->windows) == 0) {
            main_running = FALSE;
            bonobo_main_quit ();
      }
}

YelpBase *
yelp_base_new (void)
{
        YelpBase     *base;
      
        base = g_object_new (YELP_TYPE_BASE, NULL);
      
      yelp_toc_pager_init ();

        return base;
}

static void
sn_error_trap_push (SnDisplay *display,
                Display *xdisplay)
{
      gdk_error_trap_push ();
}

static void
sn_error_trap_pop (SnDisplay *display,
               Display *xdisplay)
{
      gdk_error_trap_pop ();
}

GtkWidget *
yelp_base_new_window (YelpBase *base, const gchar *uri, const gchar *startup_id)
{
      YelpBasePriv *priv;
      GtkWidget    *window;
      SnDisplay *sn_display = NULL;
      GdkScreen *screen = NULL;
      GdkDisplay *display = NULL;
      SnLauncheeContext *context = NULL;

        g_return_val_if_fail (YELP_IS_BASE (base), NULL);

      priv = base->priv;
        
        window = yelp_window_new (priv->toc_tree, priv->index);
      gtk_widget_realize (GTK_WIDGET (window));

      if (startup_id) {
            screen = gtk_window_get_screen (GTK_WINDOW (window));
            display = gdk_screen_get_display (screen);
            
            sn_display = 
                  sn_display_new (gdk_x11_display_get_xdisplay (display),
                              sn_error_trap_push, sn_error_trap_pop);
            context = sn_launchee_context_new (sn_display,
                                 gdk_screen_get_number (screen),
                                       startup_id);
            if (strncmp (sn_launchee_context_get_startup_id (context), 
                       "_TIME", 5) != 0)
                  sn_launchee_context_setup_window (context,
                               GDK_WINDOW_XWINDOW (window->window));

            if (sn_launchee_context_get_id_has_timestamp (context)) {
                  gulong time;

                  time = sn_launchee_context_get_timestamp (context);
                  gdk_x11_window_set_user_time (window->window, time);
            }           
      }
              
      priv->windows = g_slist_prepend (priv->windows, window);

      g_object_weak_ref (G_OBJECT (window),
                     (GWeakNotify) yelp_base_window_finalized_cb,
                     base);
      
      g_signal_connect (window, "new_window_requested",
                    G_CALLBACK (yelp_base_new_window_cb),
                    base);

      gtk_widget_show (window);

      if (uri && uri[0] != '\0')
            yelp_window_load (YELP_WINDOW (window), uri);
      else
            yelp_window_load (YELP_WINDOW (window), "x-yelp-toc:");

      if (context) {
            sn_launchee_context_complete (context);
            sn_launchee_context_unref (context);
            sn_display_unref (sn_display);            
      }

      return window;
}

BONOBO_TYPE_FUNC_FULL (YelpBase, GNOME_Yelp, PARENT_TYPE, yelp_base)

Generated by  Doxygen 1.6.0   Back to index