[gitg] Make gitg work with gtk+ 2.18 again
- From: Jesse van den Kieboom <jessevdk src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gitg] Make gitg work with gtk+ 2.18 again
- Date: Mon, 7 Jun 2010 08:13:20 +0000 (UTC)
commit b67f475d53619a67f4869bd5f1026cac045cca43
Author: Jesse van den Kieboom <jesse vandenkieboom epfl ch>
Date: Mon Jun 7 09:28:37 2010 +0200
Make gitg work with gtk+ 2.18 again
configure.ac | 19 +-
gitg/Makefile.am | 5 +
gitg/gitg-activatable.c | 35 ++-
gitg/gitg-commit-view.c | 7 +-
gitg/gitg-repository-dialog.c | 116 ++++++-
gitg/gitg-repository.ui | 9 +-
gitg/gitg-revision-panel.c | 31 ++-
gitg/gitg-spinner.c | 794 +++++++++++++++++++++++++++++++++++++++++
gitg/gitg-spinner.h | 99 +++++
gitg/gitg-stat-view.c | 1 +
gitg/gitg-utils.c | 2 +
gitg/gitg-window.c | 2 +
gitg/gitg-window.ui | 2 +-
gitg/gseal-gtk-compat.h | 2 +
14 files changed, 1094 insertions(+), 30 deletions(-)
---
diff --git a/configure.ac b/configure.ac
index db0f0ae..e8a45a1 100644
--- a/configure.ac
+++ b/configure.ac
@@ -51,7 +51,7 @@ PKG_CHECK_EXISTS([gtk+-3.0 >= 2.90],
GTK_REQUIRED_VERSION=2.90.0
],[
GTK_REQUIRED=gtk+-2.0
- GTK_REQUIRED_VERSION=2.20.0
+ GTK_REQUIRED_VERSION=2.18.0
])
PKG_CHECK_MODULES(GITG, [
@@ -86,15 +86,28 @@ AC_ARG_ENABLE(deprecations,
if test "$enable_deprecations" = "yes"; then
DISABLE_DEPRECATED_CFLAGS="\
--DGSEAL_ENABLE \
-DG_DISABLE_DEPRECATED \
-DGDK_DISABLE_DEPRECATED \
-DGTK_DISABLE_DEPRECATED \
-DGDK_PIXBUF_DISABLE_DEPRECATED \
-DGNOME_DISABLE_DEPRECATED"
- AC_SUBST(DISABLE_DEPRECATED_CFLAGS)
fi
+if $PKG_CONFIG --atleast-version 2.19.0 $GTK_REQUIRED; then
+ gtkatleast=
+else
+ gtkatleast=no
+fi
+
+AM_CONDITIONAL(BUILD_SPINNER, test "$gtkatleast" = "no")
+if test "$gtkatleast" = "no"; then
+ AC_DEFINE([BUILD_SPINNER],[1],[Whether to use GitgSpinner instead of GtkSpinner])
+else
+ DISABLE_DEPRECATED_CFLAGS="$DISABLE_DEPRECATED_CFLAGS -DGSEAL_ENABLE"
+fi
+
+AC_SUBST(DISABLE_DEPRECATED_CFLAGS)
+
AC_SUBST(PACKAGE_CFLAGS)
AC_SUBST(PACKAGE_LIBS)
diff --git a/gitg/Makefile.am b/gitg/Makefile.am
index 7ffb604..0cee607 100644
--- a/gitg/Makefile.am
+++ b/gitg/Makefile.am
@@ -63,6 +63,11 @@ gitg_SOURCES = \
gitg-window.c \
$(NOINST_H_FILES)
+if BUILD_SPINNER
+gitg_SOURCES += gitg-spinner.c
+NOINST_H_FILES += gitg-spinner.h
+endif
+
gitg_LDADD = \
$(GITG_LIBS) \
$(PACKAGE_LIBS) \
diff --git a/gitg/gitg-activatable.c b/gitg/gitg-activatable.c
index 644aaee..690deb3 100644
--- a/gitg/gitg-activatable.c
+++ b/gitg/gitg-activatable.c
@@ -1,6 +1,35 @@
#include "gitg-activatable.h"
-G_DEFINE_INTERFACE (GitgActivatable, gitg_activatable, G_TYPE_INVALID)
+static void gitg_activatable_default_init (GitgActivatableInterface *iface);
+
+GType
+gitg_activatable_get_type ()
+{
+ static GType gitg_activatable_type_id = 0;
+
+ if (!gitg_activatable_type_id)
+ {
+ static const GTypeInfo g_define_type_info =
+ {
+ sizeof (GitgActivatableInterface),
+ (GBaseInitFunc) gitg_activatable_default_init,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ 0,
+ 0,
+ NULL
+ };
+
+ gitg_activatable_type_id = g_type_register_static (G_TYPE_INTERFACE,
+ "GitgActivatable",
+ &g_define_type_info,
+ 0);
+ }
+
+ return gitg_activatable_type_id;
+}
/* Default implementation */
static gchar *
@@ -11,7 +40,7 @@ gitg_activatable_get_id_default (GitgActivatable *panel)
static gboolean
gitg_activatable_activate_default (GitgActivatable *panel,
- gchar const *cmd)
+ gchar const *cmd)
{
return FALSE;
}
@@ -40,7 +69,7 @@ gitg_activatable_get_id (GitgActivatable *panel)
gboolean
gitg_activatable_activate (GitgActivatable *panel,
- gchar const *action)
+ gchar const *action)
{
g_return_val_if_fail (GITG_IS_ACTIVATABLE (panel), FALSE);
diff --git a/gitg/gitg-commit-view.c b/gitg/gitg-commit-view.c
index f6998b1..7f53deb 100644
--- a/gitg/gitg-commit-view.c
+++ b/gitg/gitg-commit-view.c
@@ -32,6 +32,7 @@
#include "gitg-preferences.h"
#include "gitg-data-binding.h"
#include "gitg-utils.h"
+#include "gseal-gtk-compat.h"
#define GITG_COMMIT_VIEW_GET_PRIVATE(object)(G_TYPE_INSTANCE_GET_PRIVATE((object), GITG_TYPE_COMMIT_VIEW, GitgCommitViewPrivate))
#define CATEGORY_UNSTAGE_HUNK "CategoryUnstageHunk"
@@ -1677,10 +1678,14 @@ gitg_commit_view_set_repository(GitgCommitView *view, GitgRepository *repository
gtk_list_store_clear(view->priv->store_staged);
if (repository)
+ {
view->priv->repository = g_object_ref(repository);
+ }
- if (gtk_widget_get_mapped(GTK_WIDGET(view)))
+ if (gtk_widget_get_mapped (GTK_WIDGET (view)))
+ {
initialize_commit(view);
+ }
g_object_notify(G_OBJECT(view), "repository");
}
diff --git a/gitg/gitg-repository-dialog.c b/gitg/gitg-repository-dialog.c
index 2d0276a..c1dc6ac 100644
--- a/gitg/gitg-repository-dialog.c
+++ b/gitg/gitg-repository-dialog.c
@@ -28,6 +28,14 @@
#include "gitg-repository-dialog.h"
#include "gitg-utils.h"
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#ifdef BUILD_SPINNER
+#include "gitg-spinner.h"
+#endif
+
void on_button_fetch_remote_clicked (GtkButton *button,
GitgRepositoryDialog *dialog);
@@ -64,7 +72,8 @@ enum
COLUMN_NAME,
COLUMN_URL,
COLUMN_FETCH,
- COLUMN_PULSE
+ COLUMN_PULSE,
+ COLUMN_SPINNER
};
struct _GitgRepositoryDialogPrivate
@@ -93,7 +102,12 @@ typedef struct
GitgRepositoryDialog *dialog;
GitgRunner *runner;
GtkTreeRowReference *reference;
+
+#ifdef BUILD_SPINNER
+ GitgSpinner *spinner;
+#else
guint pulse_id;
+#endif
} FetchInfo;
static void
@@ -110,6 +124,13 @@ fetch_cleanup (FetchInfo *info)
&iter,
path);
+#ifdef BUILD_SPINNER
+ gtk_list_store_set (info->dialog->priv->list_store_remotes,
+ &iter,
+ COLUMN_SPINNER, NULL,
+ -1);
+#endif
+
gtk_list_store_set (info->dialog->priv->list_store_remotes,
&iter,
COLUMN_FETCH, FALSE,
@@ -118,7 +139,14 @@ fetch_cleanup (FetchInfo *info)
gtk_tree_path_free (path);
}
+#ifdef BUILD_SPINNER
+ if (info->spinner)
+ {
+ g_object_unref (info->spinner);
+ }
+#else
g_source_remove (info->pulse_id);
+#endif
gtk_tree_row_reference_free (info->reference);
g_object_unref (info->runner);
@@ -193,9 +221,10 @@ update_fetch (GitgRepositoryDialog *dialog)
{
GtkTreePath *path = (GtkTreePath *)item->data;
GtkTreeIter iter;
- gboolean fetch;
gtk_tree_model_get_iter (model, &iter, path);
+
+ gboolean fetch;
gtk_tree_model_get (model, &iter, COLUMN_FETCH, &fetch, -1);
if (!fetch)
@@ -250,15 +279,35 @@ add_remote (GitgRepositoryDialog *dialog, gchar const *name, gchar const *url, G
GtkTreeIter it;
gtk_list_store_append (dialog->priv->list_store_remotes, iter ? iter : &it);
- gtk_list_store_set (dialog->priv->list_store_remotes,
+ gtk_list_store_set (dialog->priv->list_store_remotes,
iter ? iter : &it,
COLUMN_NAME, name,
COLUMN_URL, url,
COLUMN_FETCH, FALSE,
COLUMN_PULSE, 0,
+ COLUMN_SPINNER, NULL,
-1);
}
+#ifdef BUILD_SPINNER
+static void
+on_spinner_frame (GitgSpinner *spinner, GdkPixbuf *pixbuf, FetchInfo *info)
+{
+ GtkTreeIter iter;
+ GtkTreePath *path = gtk_tree_row_reference_get_path (info->reference);
+
+ gtk_tree_model_get_iter (GTK_TREE_MODEL (info->dialog->priv->list_store_remotes),
+ &iter,
+ path);
+
+ gtk_list_store_set (info->dialog->priv->list_store_remotes,
+ &iter,
+ COLUMN_SPINNER, pixbuf,
+ -1);
+
+ gtk_tree_path_free (path);
+}
+#else
static gboolean
pulse_row (FetchInfo *info)
{
@@ -276,7 +325,7 @@ pulse_row (FetchInfo *info)
COLUMN_FETCH, &fetch,
COLUMN_PULSE, &pulse,
-1);
-
+
if (fetch)
{
gtk_list_store_set (info->dialog->priv->list_store_remotes,
@@ -284,11 +333,12 @@ pulse_row (FetchInfo *info)
COLUMN_PULSE, pulse + 1,
-1);
}
-
+
gtk_tree_path_free (path);
return fetch;
}
+#endif
static void
on_fetch_begin_loading (GitgRunner *runner, FetchInfo *info)
@@ -305,6 +355,13 @@ on_fetch_begin_loading (GitgRunner *runner, FetchInfo *info)
COLUMN_FETCH, TRUE,
-1);
+#ifdef BUILD_SPINNER
+ info->spinner = gitg_spinner_new (GTK_ICON_SIZE_MENU);
+ gitg_spinner_set_screen (info->spinner, gtk_widget_get_screen (GTK_WIDGET (info->dialog)));
+
+ g_signal_connect (info->spinner, "frame", G_CALLBACK (on_spinner_frame), info);
+ gitg_spinner_start (info->spinner);
+#else
GtkStyle *style = gtk_widget_get_style (GTK_WIDGET (info->dialog->priv->tree_view_remotes));
GValue cycle_duration = {0,};
@@ -323,9 +380,9 @@ on_fetch_begin_loading (GitgRunner *runner, FetchInfo *info)
g_value_unset (&cycle_duration);
g_value_unset (&num_steps);
+#endif
gtk_tree_path_free (path);
-
update_fetch (info->dialog);
}
@@ -359,10 +416,10 @@ fetch_remote (GitgRepositoryDialog *dialog, GtkTreeIter *iter)
info->reference = gtk_tree_row_reference_new (model, path);
info->runner = runner;
- gtk_tree_path_free (path);
+ gtk_tree_path_free (path);
- g_signal_connect (runner,
- "begin-loading",
+ g_signal_connect (runner,
+ "begin-loading",
G_CALLBACK (on_fetch_begin_loading),
info);
@@ -458,6 +515,7 @@ init_properties(GitgRepositoryDialog *dialog)
init_remotes(dialog);
}
+#ifndef BUILD_SPINNER
static void
fetch_data_spinner_cb (GtkTreeViewColumn *column,
GtkCellRenderer *cell,
@@ -479,6 +537,7 @@ fetch_data_spinner_cb (GtkTreeViewColumn *column,
"pulse", pulse,
NULL);
}
+#endif
static void
fetch_data_icon_cb (GtkTreeViewColumn *column,
@@ -487,6 +546,21 @@ fetch_data_icon_cb (GtkTreeViewColumn *column,
GtkTreeIter *iter,
GitgRepositoryDialog *dialog)
{
+#ifdef BUILD_SPINNER
+ GdkPixbuf *fetch;
+
+ gtk_tree_model_get (model, iter, COLUMN_SPINNER, &fetch, -1);
+
+ if (fetch)
+ {
+ g_object_set (cell, "pixbuf", fetch, NULL);
+ g_object_unref (fetch);
+ }
+ else
+ {
+ g_object_set (cell, "stock-id", GTK_STOCK_NETWORK, NULL);
+ }
+#else
gboolean fetch;
gtk_tree_model_get (model, iter, COLUMN_FETCH, &fetch, -1);
@@ -494,6 +568,7 @@ fetch_data_icon_cb (GtkTreeViewColumn *column,
g_object_set (G_OBJECT (cell),
"visible", !fetch,
NULL);
+#endif
}
@@ -526,13 +601,20 @@ create_repository_dialog (GitgWindow *window)
repository_dialog->priv->image_fetch_remote = GTK_IMAGE(gtk_builder_get_object(b, "image_fetch_remote"));
GtkTreeViewColumn *column = GTK_TREE_VIEW_COLUMN (gtk_builder_get_object (b, "tree_view_remotes_column_name"));
- GtkCellRenderer *spinner_renderer = GTK_CELL_RENDERER (gtk_builder_get_object (b, "tree_view_remotes_renderer_spinner"));
+
+#ifndef BUILD_SPINNER
+ GtkCellRenderer *spinner_renderer = gtk_cell_renderer_spinner_new ();
+ g_object_set (spinner_renderer, "visible", FALSE, NULL);
+
+ gtk_tree_view_column_pack_start (column, spinner_renderer, FALSE);
+ gtk_cell_layout_reorder (GTK_CELL_LAYOUT (column), spinner_renderer, 1);
gtk_tree_view_column_set_cell_data_func (column,
spinner_renderer,
(GtkTreeCellDataFunc)fetch_data_spinner_cb,
repository_dialog,
NULL);
+#endif
GtkCellRenderer *icon_renderer = GTK_CELL_RENDERER (gtk_builder_get_object (b, "tree_view_remotes_renderer_icon"));
gtk_tree_view_column_set_cell_data_func (column,
@@ -560,10 +642,12 @@ create_repository_dialog (GitgWindow *window)
}
GitgRepositoryDialog *
-gitg_repository_dialog_present(GitgWindow *window)
+gitg_repository_dialog_present (GitgWindow *window)
{
if (!repository_dialog)
+ {
create_repository_dialog(window);
+ }
gtk_window_set_transient_for(GTK_WINDOW(repository_dialog), GTK_WINDOW (window));
gtk_window_present(GTK_WINDOW(repository_dialog));
@@ -581,7 +665,8 @@ gitg_repository_dialog_close (void)
}
static void
-fetch_remote_cancel (GitgRepositoryDialog *dialog, GtkTreeIter *iter)
+fetch_remote_cancel (GitgRepositoryDialog *dialog,
+ GtkTreeIter *iter)
{
GList *item;
GtkTreePath *orig;
@@ -608,7 +693,8 @@ fetch_remote_cancel (GitgRepositoryDialog *dialog, GtkTreeIter *iter)
}
void
-on_button_fetch_remote_clicked (GtkButton *button, GitgRepositoryDialog *dialog)
+on_button_fetch_remote_clicked (GtkButton *button,
+ GitgRepositoryDialog *dialog)
{
GtkTreeSelection *selection;
GtkTreeModel *model;
@@ -809,9 +895,9 @@ on_remote_name_edited (GtkCellRendererText *renderer,
gchar *oldname;
gchar *url;
- gtk_tree_model_get (GTK_TREE_MODEL (dialog->priv->list_store_remotes),
+ gtk_tree_model_get (GTK_TREE_MODEL (dialog->priv->list_store_remotes),
&iter,
- COLUMN_NAME, &oldname,
+ COLUMN_NAME, &oldname,
COLUMN_URL, &url,
-1);
diff --git a/gitg/gitg-repository.ui b/gitg/gitg-repository.ui
index ef8f192..b619954 100644
--- a/gitg/gitg-repository.ui
+++ b/gitg/gitg-repository.ui
@@ -1,6 +1,6 @@
<?xml version="1.0"?>
<interface>
- <requires lib="gtk+" version="2.20"/>
+ <requires lib="gtk+" version="2.18"/>
<!-- interface-requires gitg 0.2 -->
<!-- interface-naming-policy toplevel-contextual -->
<object class="GtkListStore" id="list_store_remotes">
@@ -13,6 +13,8 @@
<column type="gboolean"/>
<!-- column-name pulse -->
<column type="gint"/>
+ <!-- column-name spinner -->
+ <column type="GdkPixbuf"/>
</columns>
</object>
<object class="GitgRepositoryDialog" id="dialog_repository">
@@ -58,11 +60,6 @@
</object>
</child>
<child>
- <object class="GtkCellRendererSpinner" id="tree_view_remotes_renderer_spinner">
- <property name="visible">False</property>
- </object>
- </child>
- <child>
<object class="GtkCellRendererText" id="tree_view_remotes_renderer_name">
<property name="editable">True</property>
<signal name="edited" handler="on_remote_name_edited"/>
diff --git a/gitg/gitg-revision-panel.c b/gitg/gitg-revision-panel.c
index 2812a8d..565e186 100644
--- a/gitg/gitg-revision-panel.c
+++ b/gitg/gitg-revision-panel.c
@@ -1,6 +1,35 @@
#include "gitg-revision-panel.h"
-G_DEFINE_INTERFACE (GitgRevisionPanel, gitg_revision_panel, G_TYPE_INVALID)
+static void gitg_revision_panel_default_init (GitgRevisionPanelInterface *iface);
+
+GType
+gitg_revision_panel_get_type ()
+{
+ static GType gitg_revision_panel_type_id = 0;
+
+ if (!gitg_revision_panel_type_id)
+ {
+ static const GTypeInfo g_define_type_info =
+ {
+ sizeof (GitgRevisionPanelInterface),
+ (GBaseInitFunc) gitg_revision_panel_default_init,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ 0,
+ 0,
+ NULL
+ };
+
+ gitg_revision_panel_type_id = g_type_register_static (G_TYPE_INTERFACE,
+ "GitgRevisionPanel",
+ &g_define_type_info,
+ 0);
+ }
+
+ return gitg_revision_panel_type_id;
+}
/* Default implementation */
static void
diff --git a/gitg/gitg-spinner.c b/gitg/gitg-spinner.c
new file mode 100644
index 0000000..912bc24
--- /dev/null
+++ b/gitg/gitg-spinner.c
@@ -0,0 +1,794 @@
+/*
+ * gitg-spinner.c
+ * This file is part of gitg
+ *
+ * Copyright (C) 2009 - Jesse van den kieboom
+ * Copyright (C) 2005 - Paolo Maggi
+ * Copyright (C) 2002-2004 Marco Pesenti Gritti
+ * Copyright (C) 2004 Christian Persch
+ * Copyright (C) 2000 - Eazel, Inc.
+ *
+ * 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.
+ */
+
+/*
+ * This widget was originally written by Andy Hertzfeld <andy eazel com> for
+ * Nautilus. It was then modified by Marco Pesenti Gritti and Christian Persch
+ * for Epiphany.
+ *
+ * Modified by the gitg Team, 2005. See the AUTHORS file for a
+ * list of people on the gitg Team.
+ * See the ChangeLog files for a list of changes.
+ *
+ * Modified by the gitg team, 2009.
+ *
+ * $Id$
+ */
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#include "gitg-spinner.h"
+
+#include <gdk-pixbuf/gdk-pixbuf.h>
+
+/* Spinner cache implementation */
+
+#define GITG_TYPE_SPINNER_CACHE (gitg_spinner_cache_get_type())
+#define GITG_SPINNER_CACHE(object) (G_TYPE_CHECK_INSTANCE_CAST((object), GITG_TYPE_SPINNER_CACHE, GitgSpinnerCache))
+#define GITG_SPINNER_CACHE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), GITG_TYPE_SPINNER_CACHE, GitgSpinnerCacheClass))
+#define GITG_IS_SPINNER_CACHE(object) (G_TYPE_CHECK_INSTANCE_TYPE((object), GITG_TYPE_SPINNER_CACHE))
+#define GITG_IS_SPINNER_CACHE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), GITG_TYPE_SPINNER_CACHE))
+#define GITG_SPINNER_CACHE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), GITG_TYPE_SPINNER_CACHE, GitgSpinnerCacheClass))
+
+typedef struct _GitgSpinnerCache GitgSpinnerCache;
+typedef struct _GitgSpinnerCacheClass GitgSpinnerCacheClass;
+typedef struct _GitgSpinnerCachePrivate GitgSpinnerCachePrivate;
+
+struct _GitgSpinnerCacheClass
+{
+ GObjectClass parent_class;
+};
+
+struct _GitgSpinnerCache
+{
+ GObject parent_object;
+
+ /*< private >*/
+ GitgSpinnerCachePrivate *priv;
+};
+
+#define GITG_SPINNER_CACHE_GET_PRIVATE(object)(G_TYPE_INSTANCE_GET_PRIVATE ((object), GITG_TYPE_SPINNER_CACHE, GitgSpinnerCachePrivate))
+
+struct _GitgSpinnerCachePrivate
+{
+ /* Hash table of GdkScreen -> GitgSpinnerCacheData */
+ GHashTable *hash;
+};
+
+typedef struct
+{
+ guint ref_count;
+ GtkIconSize size;
+ gint width;
+ gint height;
+ GdkPixbuf **animation_pixbufs;
+ guint n_animation_pixbufs;
+} GitgSpinnerImages;
+
+#define LAST_ICON_SIZE GTK_ICON_SIZE_DIALOG + 1
+#define SPINNER_ICON_NAME "process-working"
+#define SPINNER_FALLBACK_ICON_NAME "gnome-spinner"
+#define GITG_SPINNER_IMAGES_INVALID ((GitgSpinnerImages *) 0x1)
+
+typedef struct
+{
+ GdkScreen *screen;
+ GtkIconTheme *icon_theme;
+ GitgSpinnerImages *images[LAST_ICON_SIZE];
+} GitgSpinnerCacheData;
+
+static void gitg_spinner_cache_class_init (GitgSpinnerCacheClass *klass);
+static void gitg_spinner_cache_init (GitgSpinnerCache *cache);
+
+static GObjectClass *gitg_spinner_cache_parent_class;
+
+static GType
+gitg_spinner_cache_get_type (void)
+{
+ static GType type = 0;
+
+ if (G_UNLIKELY (type == 0))
+ {
+ const GTypeInfo our_info =
+ {
+ sizeof (GitgSpinnerCacheClass),
+ NULL,
+ NULL,
+ (GClassInitFunc) gitg_spinner_cache_class_init,
+ NULL,
+ NULL,
+ sizeof (GitgSpinnerCache),
+ 0,
+ (GInstanceInitFunc) gitg_spinner_cache_init
+ };
+
+ type = g_type_register_static (G_TYPE_OBJECT,
+ "GitgSpinnerCache",
+ &our_info, 0);
+ }
+
+ return type;
+}
+
+static GitgSpinnerImages *
+gitg_spinner_images_ref (GitgSpinnerImages *images)
+{
+ g_return_val_if_fail (images != NULL, NULL);
+
+ images->ref_count++;
+
+ return images;
+}
+
+static void
+gitg_spinner_images_unref (GitgSpinnerImages *images)
+{
+ g_return_if_fail (images != NULL);
+
+ images->ref_count--;
+
+ if (images->ref_count == 0)
+ {
+ guint i;
+
+ /* LOG ("Freeing spinner images %p for size %d", images, images->size); */
+
+ for (i = 0; i < images->n_animation_pixbufs; ++i)
+ {
+ g_object_unref (images->animation_pixbufs[i]);
+ }
+
+ g_free (images->animation_pixbufs);
+ g_free (images);
+ }
+}
+
+static void
+gitg_spinner_cache_data_unload (GitgSpinnerCacheData *data)
+{
+ GtkIconSize size;
+ GitgSpinnerImages *images;
+
+ g_return_if_fail (data != NULL);
+
+ /* LOG ("GitgSpinnerDataCache unload for screen %p", data->screen); */
+
+ for (size = GTK_ICON_SIZE_INVALID; size < LAST_ICON_SIZE; ++size)
+ {
+ images = data->images[size];
+ data->images[size] = NULL;
+
+ if (images != NULL && images != GITG_SPINNER_IMAGES_INVALID)
+ {
+ gitg_spinner_images_unref (images);
+ }
+ }
+}
+
+static GdkPixbuf *
+extract_frame (GdkPixbuf *grid_pixbuf,
+ int x,
+ int y,
+ int size)
+{
+ GdkPixbuf *pixbuf;
+
+ if (x + size > gdk_pixbuf_get_width (grid_pixbuf) ||
+ y + size > gdk_pixbuf_get_height (grid_pixbuf))
+ {
+ return NULL;
+ }
+
+ pixbuf = gdk_pixbuf_new_subpixbuf (grid_pixbuf,
+ x, y,
+ size, size);
+ g_return_val_if_fail (pixbuf != NULL, NULL);
+
+ return pixbuf;
+}
+
+static GdkPixbuf *
+scale_to_size (GdkPixbuf *pixbuf,
+ int dw,
+ int dh)
+{
+ GdkPixbuf *result;
+ int pw, ph;
+
+ g_return_val_if_fail (pixbuf != NULL, NULL);
+
+ pw = gdk_pixbuf_get_width (pixbuf);
+ ph = gdk_pixbuf_get_height (pixbuf);
+
+ if (pw != dw || ph != dh)
+ {
+ result = gdk_pixbuf_scale_simple (pixbuf, dw, dh,
+ GDK_INTERP_BILINEAR);
+ g_object_unref (pixbuf);
+ return result;
+ }
+
+ return pixbuf;
+}
+
+static GitgSpinnerImages *
+gitg_spinner_images_load (GdkScreen *screen,
+ GtkIconTheme *icon_theme,
+ GtkIconSize icon_size)
+{
+ GitgSpinnerImages *images;
+ GdkPixbuf *icon_pixbuf, *pixbuf;
+ GtkIconInfo *icon_info = NULL;
+ int grid_width, grid_height, x, y, requested_size, size, isw, ish, n;
+ const char *icon;
+ GSList *list = NULL, *l;
+
+ /* LOG ("GitgSpinnerCacheData loading for screen %p at size %d", screen, icon_size); */
+
+ /* START_PROFILER ("loading spinner animation") */
+
+ if (screen == NULL)
+ screen = gdk_screen_get_default ();
+
+ if (!gtk_icon_size_lookup_for_settings (gtk_settings_get_for_screen (screen),
+ icon_size, &isw, &ish))
+ goto loser;
+
+ requested_size = MAX (ish, isw);
+
+ /* Load the animation. The 'rest icon' is the 0th frame */
+ icon_info = gtk_icon_theme_lookup_icon (icon_theme,
+ SPINNER_ICON_NAME,
+ requested_size, 0);
+
+ if (icon_info == NULL)
+ {
+ g_warning ("Throbber animation not found");
+
+ /* If the icon naming spec compliant name wasn't found, try the old name */
+ icon_info = gtk_icon_theme_lookup_icon (icon_theme,
+ SPINNER_FALLBACK_ICON_NAME,
+ requested_size, 0);
+ if (icon_info == NULL)
+ {
+ g_warning ("Throbber fallback animation not found either");
+ goto loser;
+ }
+ }
+
+ g_assert (icon_info != NULL);
+
+ size = gtk_icon_info_get_base_size (icon_info);
+ icon = gtk_icon_info_get_filename (icon_info);
+
+ if (icon == NULL)
+ goto loser;
+
+ icon_pixbuf = gdk_pixbuf_new_from_file (icon, NULL);
+ gtk_icon_info_free (icon_info);
+ icon_info = NULL;
+
+ if (icon_pixbuf == NULL)
+ {
+ g_warning ("Could not load the spinner file");
+ goto loser;
+ }
+
+ grid_width = gdk_pixbuf_get_width (icon_pixbuf);
+ grid_height = gdk_pixbuf_get_height (icon_pixbuf);
+
+ n = 0;
+ for (y = 0; y < grid_height; y += size)
+ {
+ for (x = 0; x < grid_width ; x += size)
+ {
+ pixbuf = extract_frame (icon_pixbuf, x, y, size);
+
+ if (pixbuf)
+ {
+ list = g_slist_prepend (list, pixbuf);
+ ++n;
+ }
+ else
+ {
+ g_warning ("Cannot extract frame (%d, %d) from the grid\n", x, y);
+ }
+ }
+ }
+
+ g_object_unref (icon_pixbuf);
+
+ if (list == NULL)
+ goto loser;
+
+ /* g_assert (n > 0); */
+
+ if (size > requested_size)
+ {
+ for (l = list; l != NULL; l = l->next)
+ {
+ l->data = scale_to_size (l->data, isw, ish);
+ }
+ }
+
+ /* Now we've successfully got all the data */
+ images = g_new (GitgSpinnerImages, 1);
+ images->ref_count = 1;
+
+ images->size = icon_size;
+ images->width = images->height = requested_size;
+
+ images->n_animation_pixbufs = n;
+ images->animation_pixbufs = g_new (GdkPixbuf *, n);
+
+ for (l = list; l != NULL; l = l->next)
+ {
+ g_assert (l->data != NULL);
+ images->animation_pixbufs[--n] = l->data;
+ }
+ g_assert (n == 0);
+
+ g_slist_free (list);
+
+ /* STOP_PROFILER ("loading spinner animation") */
+ return images;
+
+loser:
+ if (icon_info)
+ {
+ gtk_icon_info_free (icon_info);
+ }
+
+ g_slist_foreach (list, (GFunc) g_object_unref, NULL);
+
+ /* STOP_PROFILER ("loading spinner animation") */
+
+ return NULL;
+}
+
+static GitgSpinnerCacheData *
+gitg_spinner_cache_data_new (GdkScreen *screen)
+{
+ GitgSpinnerCacheData *data;
+
+ data = g_new0 (GitgSpinnerCacheData, 1);
+
+ data->screen = screen;
+ data->icon_theme = gtk_icon_theme_get_for_screen (screen);
+
+ g_signal_connect_swapped (data->icon_theme,
+ "changed",
+ G_CALLBACK (gitg_spinner_cache_data_unload),
+ data);
+
+ return data;
+}
+
+static void
+gitg_spinner_cache_data_free (GitgSpinnerCacheData *data)
+{
+ g_return_if_fail (data != NULL);
+ g_return_if_fail (data->icon_theme != NULL);
+
+ g_signal_handlers_disconnect_by_func (data->icon_theme,
+ G_CALLBACK (gitg_spinner_cache_data_unload),
+ data);
+
+ gitg_spinner_cache_data_unload (data);
+
+ g_free (data);
+}
+
+static GitgSpinnerImages *
+gitg_spinner_cache_get_images (GitgSpinnerCache *cache,
+ GdkScreen *screen,
+ GtkIconSize icon_size)
+{
+ GitgSpinnerCachePrivate *priv = cache->priv;
+ GitgSpinnerCacheData *data;
+ GitgSpinnerImages *images;
+
+ g_return_val_if_fail (icon_size >= 0 && icon_size < LAST_ICON_SIZE, NULL);
+
+ data = g_hash_table_lookup (priv->hash, screen);
+
+ if (data == NULL)
+ {
+ data = gitg_spinner_cache_data_new (screen);
+
+ /* FIXME: think about what happens when the screen's display is closed later on */
+ g_hash_table_insert (priv->hash, screen, data);
+ }
+
+ images = data->images[icon_size];
+
+ if (images == GITG_SPINNER_IMAGES_INVALID)
+ {
+ /* Load failed, but don't try endlessly again! */
+ return NULL;
+ }
+
+ if (images != NULL)
+ {
+ /* Return cached data */
+ return gitg_spinner_images_ref (images);
+ }
+
+ images = gitg_spinner_images_load (screen, data->icon_theme, icon_size);
+
+ if (images == NULL)
+ {
+ /* Mark as failed-to-load */
+ data->images[icon_size] = GITG_SPINNER_IMAGES_INVALID;
+
+ return NULL;
+ }
+
+ data->images[icon_size] = images;
+
+ return gitg_spinner_images_ref (images);
+}
+
+static void
+gitg_spinner_cache_init (GitgSpinnerCache *cache)
+{
+ GitgSpinnerCachePrivate *priv;
+
+ priv = cache->priv = GITG_SPINNER_CACHE_GET_PRIVATE (cache);
+
+ /* LOG ("GitgSpinnerCache initialising"); */
+
+ priv->hash = g_hash_table_new_full (g_direct_hash,
+ g_direct_equal,
+ NULL,
+ (GDestroyNotify) gitg_spinner_cache_data_free);
+}
+
+static void
+gitg_spinner_cache_finalize (GObject *object)
+{
+ GitgSpinnerCache *cache = GITG_SPINNER_CACHE (object);
+ GitgSpinnerCachePrivate *priv = cache->priv;
+
+ g_hash_table_destroy (priv->hash);
+
+ /* LOG ("GitgSpinnerCache finalised"); */
+
+ G_OBJECT_CLASS (gitg_spinner_cache_parent_class)->finalize (object);
+}
+
+static void
+gitg_spinner_cache_class_init (GitgSpinnerCacheClass *klass)
+{
+ GObjectClass *object_class = G_OBJECT_CLASS (klass);
+
+ gitg_spinner_cache_parent_class = g_type_class_peek_parent (klass);
+
+ object_class->finalize = gitg_spinner_cache_finalize;
+
+ g_type_class_add_private (object_class, sizeof (GitgSpinnerCachePrivate));
+}
+
+static GitgSpinnerCache *spinner_cache = NULL;
+
+static GitgSpinnerCache *
+gitg_spinner_cache_ref (void)
+{
+ if (spinner_cache == NULL)
+ {
+ GitgSpinnerCache **cache_ptr;
+
+ spinner_cache = g_object_new (GITG_TYPE_SPINNER_CACHE, NULL);
+ cache_ptr = &spinner_cache;
+ g_object_add_weak_pointer (G_OBJECT (spinner_cache),
+ (gpointer *) cache_ptr);
+
+ return spinner_cache;
+ }
+
+ return g_object_ref (spinner_cache);
+}
+
+/* Spinner implementation */
+
+#define SPINNER_TIMEOUT 50 /* ms */
+
+#define GITG_SPINNER_GET_PRIVATE(object)(G_TYPE_INSTANCE_GET_PRIVATE ((object), GITG_TYPE_SPINNER, GitgSpinnerPrivate))
+
+struct _GitgSpinnerPrivate
+{
+ GdkScreen *screen;
+ GitgSpinnerCache *cache;
+ GtkIconSize size;
+ GitgSpinnerImages *images;
+ guint current_image;
+ guint timeout;
+ guint timer_task;
+ guint spinning : 1;
+ guint need_load : 1;
+};
+
+enum
+{
+ FRAME,
+ NUM_SIGNALS
+};
+
+static guint spinner_signals[NUM_SIGNALS] = {0,};
+
+static void gitg_spinner_class_init (GitgSpinnerClass *class);
+static void gitg_spinner_init (GitgSpinner *spinner);
+
+static GObjectClass *parent_class;
+
+GType
+gitg_spinner_get_type (void)
+{
+ static GType type = 0;
+
+ if (G_UNLIKELY (type == 0))
+ {
+ const GTypeInfo our_info =
+ {
+ sizeof (GitgSpinnerClass),
+ NULL, /* base_init */
+ NULL, /* base_finalize */
+ (GClassInitFunc) gitg_spinner_class_init,
+ NULL,
+ NULL, /* class_data */
+ sizeof (GitgSpinner),
+ 0, /* n_preallocs */
+ (GInstanceInitFunc) gitg_spinner_init
+ };
+
+ type = g_type_register_static (G_TYPE_OBJECT,
+ "GitgSpinner",
+ &our_info, 0);
+ }
+
+ return type;
+}
+
+static gboolean
+gitg_spinner_load_images (GitgSpinner *spinner)
+{
+ GitgSpinnerPrivate *priv = spinner->priv;
+
+ if (priv->need_load)
+ {
+ priv->images = gitg_spinner_cache_get_images (priv->cache, priv->screen, priv->size);
+
+ priv->current_image = 0; /* 'rest' icon */
+ priv->need_load = FALSE;
+ }
+
+ return priv->images != NULL;
+}
+
+static void
+gitg_spinner_unload_images (GitgSpinner *spinner)
+{
+ GitgSpinnerPrivate *priv = spinner->priv;
+
+ if (priv->images != NULL)
+ {
+ gitg_spinner_images_unref (priv->images);
+ priv->images = NULL;
+ }
+
+ priv->current_image = 0;
+ priv->need_load = TRUE;
+}
+
+static void
+gitg_spinner_init (GitgSpinner *spinner)
+{
+ spinner->priv = GITG_SPINNER_GET_PRIVATE (spinner);
+
+ spinner->priv->cache = gitg_spinner_cache_ref ();
+ spinner->priv->size = GTK_ICON_SIZE_MENU;
+ spinner->priv->timeout = SPINNER_TIMEOUT;
+ spinner->priv->need_load = TRUE;
+}
+
+static gboolean
+bump_spinner_frame_cb (GitgSpinner *spinner)
+{
+ GitgSpinnerPrivate *priv = spinner->priv;
+
+ /* This can happen when we've unloaded the images on a theme
+ * change, but haven't been in the queued size request yet.
+ * Just skip this update.
+ */
+ if (priv->images == NULL)
+ {
+ if (!gitg_spinner_load_images (spinner))
+ {
+ return FALSE;
+ }
+ }
+
+ priv->current_image++;
+
+ if (priv->current_image >= priv->images->n_animation_pixbufs)
+ {
+ /* the 0th frame is the 'rest' icon */
+ priv->current_image = MIN (1, priv->images->n_animation_pixbufs);
+ }
+
+ g_signal_emit (spinner, spinner_signals[FRAME], 0, priv->images->animation_pixbufs[priv->current_image]);
+
+ /* run again */
+ return TRUE;
+}
+
+/**
+ * gitg_spinner_start:
+ * @spinner: a #GitgSpinner
+ *
+ * Start the spinner animation.
+ **/
+void
+gitg_spinner_start (GitgSpinner *spinner)
+{
+ GitgSpinnerPrivate *priv = spinner->priv;
+
+ priv->spinning = TRUE;
+
+ if (priv->timer_task == 0 && gitg_spinner_load_images (spinner))
+ {
+ /* the 0th frame is the 'rest' icon */
+ priv->current_image = MIN (0, priv->images->n_animation_pixbufs);
+
+ priv->timer_task = g_timeout_add_full (G_PRIORITY_LOW,
+ priv->timeout,
+ (GSourceFunc) bump_spinner_frame_cb,
+ spinner,
+ NULL);
+
+ bump_spinner_frame_cb (spinner);
+ }
+}
+
+static void
+gitg_spinner_remove_update_callback (GitgSpinner *spinner)
+{
+ GitgSpinnerPrivate *priv = spinner->priv;
+
+ if (priv->timer_task != 0)
+ {
+ g_source_remove (priv->timer_task);
+ priv->timer_task = 0;
+ }
+}
+
+/**
+ * gitg_spinner_stop:
+ * @spinner: a #GitgSpinner
+ *
+ * Stop the spinner animation.
+ **/
+void
+gitg_spinner_stop (GitgSpinner *spinner)
+{
+ GitgSpinnerPrivate *priv = spinner->priv;
+
+ priv->spinning = FALSE;
+ priv->current_image = 0;
+
+ if (priv->timer_task != 0)
+ {
+ gitg_spinner_remove_update_callback (spinner);
+ }
+}
+
+void
+gitg_spinner_set_screen (GitgSpinner *spinner, GdkScreen *screen)
+{
+ g_return_if_fail (GITG_IS_SPINNER (spinner));
+ g_return_if_fail (GDK_IS_SCREEN (screen));
+
+ if (spinner->priv->screen != screen)
+ {
+ gitg_spinner_unload_images (spinner);
+
+ if (spinner->priv->screen)
+ {
+ g_object_unref (spinner->priv->screen);
+ }
+
+ spinner->priv->screen = g_object_ref (screen);
+ }
+}
+
+static void
+gitg_spinner_dispose (GObject *object)
+{
+ //GitgSpinner *spinner = GITG_SPINNER (object);
+
+ G_OBJECT_CLASS (parent_class)->dispose (object);
+}
+
+static void
+gitg_spinner_finalize (GObject *object)
+{
+ GitgSpinner *spinner = GITG_SPINNER (object);
+
+ gitg_spinner_remove_update_callback (spinner);
+ gitg_spinner_unload_images (spinner);
+
+ g_object_unref (spinner->priv->cache);
+
+ G_OBJECT_CLASS (parent_class)->finalize (object);
+}
+
+static void
+gitg_spinner_class_init (GitgSpinnerClass *class)
+{
+ GObjectClass *object_class = G_OBJECT_CLASS (class);
+
+ parent_class = g_type_class_peek_parent (class);
+
+ object_class->dispose = gitg_spinner_dispose;
+ object_class->finalize = gitg_spinner_finalize;
+
+ spinner_signals[FRAME] =
+ g_signal_new ("frame",
+ G_OBJECT_CLASS_TYPE (object_class),
+ G_SIGNAL_RUN_LAST,
+ G_STRUCT_OFFSET (GitgSpinnerClass, frame),
+ NULL, NULL,
+ g_cclosure_marshal_VOID__OBJECT,
+ G_TYPE_NONE,
+ 1,
+ GDK_TYPE_PIXBUF);
+
+ g_type_class_add_private (object_class, sizeof (GitgSpinnerPrivate));
+}
+
+GitgSpinner *
+gitg_spinner_new (GtkIconSize size)
+{
+ GitgSpinner *spinner = g_object_new (GITG_TYPE_SPINNER, NULL);
+
+ spinner->priv->size = size;
+ return spinner;
+}
+
+GdkPixbuf *
+gitg_spinner_get_pixbuf (GitgSpinner *spinner)
+{
+ g_return_val_if_fail (GITG_IS_SPINNER (spinner), NULL);
+
+ if (spinner->priv->timer_task == 0)
+ {
+ return NULL;
+ }
+
+ return g_object_ref (spinner->priv->images->animation_pixbufs[spinner->priv->current_image]);
+}
diff --git a/gitg/gitg-spinner.h b/gitg/gitg-spinner.h
new file mode 100644
index 0000000..b3d4e44
--- /dev/null
+++ b/gitg/gitg-spinner.h
@@ -0,0 +1,99 @@
+/*
+ * gitg-spinner.h
+ * This file is part of gitg
+ *
+ * Copyright (C) 2009 - Jesse van den Kieboom
+ * Copyright (C) 2005 - Paolo Maggi
+ * Copyright (C) 2000 - Eazel, Inc.
+ *
+ * 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.
+ */
+
+/*
+ * This widget was originally written by Andy Hertzfeld <andy eazel com> for
+ * Nautilus.
+ *
+ * Modified by the gitg Team, 2005. See the AUTHORS file for a
+ * list of people on the gitg Team.
+ * See the ChangeLog files for a list of changes.
+ *
+ * Modified by the gitg Team, 2009
+ *
+ * $Id$
+ */
+
+#ifndef __GITG_SPINNER_H__
+#define __GITG_SPINNER_H__
+
+#include <gtk/gtk.h>
+
+G_BEGIN_DECLS
+
+/*
+ * Type checking and casting macros
+ */
+#define GITG_TYPE_SPINNER (gitg_spinner_get_type ())
+#define GITG_SPINNER(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), GITG_TYPE_SPINNER, GitgSpinner))
+#define GITG_SPINNER_CLASS(k) (G_TYPE_CHECK_CLASS_CAST((k), GITG_TYPE_SPINNER, GitgSpinnerClass))
+#define GITG_IS_SPINNER(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), GITG_TYPE_SPINNER))
+#define GITG_IS_SPINNER_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), GITG_TYPE_SPINNER))
+#define GITG_SPINNER_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS ((o), GITG_TYPE_SPINNER, GitgSpinnerClass))
+
+
+/* Private structure type */
+typedef struct _GitgSpinnerPrivate GitgSpinnerPrivate;
+
+/*
+ * Main object structure
+ */
+typedef struct _GitgSpinner GitgSpinner;
+
+struct _GitgSpinner
+{
+ GObject parent;
+
+ /*< private >*/
+ GitgSpinnerPrivate *priv;
+};
+
+/*
+ * Class definition
+ */
+typedef struct _GitgSpinnerClass GitgSpinnerClass;
+
+struct _GitgSpinnerClass
+{
+ GObjectClass parent_class;
+
+ void (*frame)(GitgSpinner *spinner, GdkPixbuf *pixbuf);
+};
+
+/*
+ * Public methods
+ */
+GType gitg_spinner_get_type (void) G_GNUC_CONST;
+
+GitgSpinner *gitg_spinner_new (GtkIconSize size);
+void gitg_spinner_set_screen (GitgSpinner *spinner,
+ GdkScreen *screen);
+void gitg_spinner_start (GitgSpinner *spinner);
+void gitg_spinner_stop (GitgSpinner *spinner);
+
+GdkPixbuf *gitg_spinner_get_pixbuf (GitgSpinner *spinner);
+
+G_END_DECLS
+
+#endif /* __GITG_SPINNER_H__ */
diff --git a/gitg/gitg-stat-view.c b/gitg/gitg-stat-view.c
index a04f9b2..d9c54cc 100644
--- a/gitg/gitg-stat-view.c
+++ b/gitg/gitg-stat-view.c
@@ -3,6 +3,7 @@
#include "gitg-utils.h"
#include <math.h>
#include <cairo.h>
+#include "gseal-gtk-compat.h"
#define GITG_STAT_VIEW_GET_PRIVATE(object)(G_TYPE_INSTANCE_GET_PRIVATE((object), GITG_TYPE_STAT_VIEW, GitgStatViewPrivate))
diff --git a/gitg/gitg-utils.c b/gitg/gitg-utils.c
index 61df5ac..edfe6ae 100644
--- a/gitg/gitg-utils.c
+++ b/gitg/gitg-utils.c
@@ -28,6 +28,8 @@
#include <string.h>
#include <math.h>
+#include "gseal-gtk-compat.h"
+
gchar *
gitg_utils_get_content_type(GFile *file)
{
diff --git a/gitg/gitg-window.c b/gitg/gitg-window.c
index 25eed6b..a500528 100644
--- a/gitg/gitg-window.c
+++ b/gitg/gitg-window.c
@@ -50,6 +50,8 @@
#include "gitg-activatable.h"
#include "gitg-uri.h"
+#include "gseal-gtk-compat.h"
+
#define DYNAMIC_ACTION_DATA_KEY "GitgDynamicActionDataKey"
#define DYNAMIC_ACTION_DATA_REMOTE_KEY "GitgDynamicActionDataRemoteKey"
#define DYNAMIC_ACTION_DATA_BRANCH_KEY "GitgDynamicActionDataBranchKey"
diff --git a/gitg/gitg-window.ui b/gitg/gitg-window.ui
index b84e092..842de54 100644
--- a/gitg/gitg-window.ui
+++ b/gitg/gitg-window.ui
@@ -1,6 +1,6 @@
<?xml version="1.0"?>
<interface>
- <!-- interface-requires gtk+ 2.20 -->
+ <!-- interface-requires gtk+ 2.18 -->
<!-- interface-requires gitg 0.0.6 -->
<!-- interface-requires sourceview2 0.0 -->
<!-- interface-naming-policy toplevel-contextual -->
diff --git a/gitg/gseal-gtk-compat.h b/gitg/gseal-gtk-compat.h
index 789174b..8d34e62 100644
--- a/gitg/gseal-gtk-compat.h
+++ b/gitg/gseal-gtk-compat.h
@@ -25,6 +25,8 @@ G_BEGIN_DECLS
#if !GTK_CHECK_VERSION (2, 21, 0)
#define gdk_drag_context_list_targets(context) ((context)->targets)
+#define gtk_widget_get_mapped(widget) (GTK_WIDGET_MAPPED ((widget)))
+#define gtk_widget_get_realized(widget) (GTK_WIDGET_REALIZED ((widget)))
#endif /* GTK < 2.22.0 */
G_END_DECLS
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]