aboutsummaryrefslogtreecommitdiffstats
path: root/shell
diff options
context:
space:
mode:
Diffstat (limited to 'shell')
-rw-r--r--shell/e-shell-backend.c21
-rw-r--r--shell/e-shell-taskbar.c76
-rw-r--r--shell/e-shell-view.c2
-rw-r--r--shell/e-shell.c12
-rw-r--r--shell/test/e-test-shell-view.c2
5 files changed, 63 insertions, 50 deletions
diff --git a/shell/e-shell-backend.c b/shell/e-shell-backend.c
index 0d7ff020c7..c2abb470a2 100644
--- a/shell/e-shell-backend.c
+++ b/shell/e-shell-backend.c
@@ -398,19 +398,30 @@ void
e_shell_backend_add_activity (EShellBackend *shell_backend,
EActivity *activity)
{
- GCancellable *cancellable;
+ EActivityState state;
g_return_if_fail (E_IS_SHELL_BACKEND (shell_backend));
g_return_if_fail (E_IS_ACTIVITY (activity));
- cancellable = e_activity_get_cancellable (activity);
+ state = e_activity_get_state (activity);
- /* Skip cancelled activities. */
- if (g_cancellable_is_cancelled (cancellable))
+ /* Disregard cancelled or completed activities. */
+
+ if (state == E_ACTIVITY_CANCELLED)
+ return;
+
+ if (state == E_ACTIVITY_COMPLETED)
return;
g_queue_push_tail (shell_backend->priv->activities, activity);
+ /* Emit the "activity-added" signal before adding a weak reference
+ * to the EActivity because EShellTaskbar's signal handler also adds
+ * a weak reference to the EActivity, and we want its GWeakNotify
+ * to run before ours, since ours may destroy the EShellTaskbar
+ * during application shutdown. */
+ g_signal_emit (shell_backend, signals[ACTIVITY_ADDED], 0, activity);
+
/* We reference the backend on every activity to
* guarantee the backend outlives the activity. */
g_object_weak_ref (
@@ -418,8 +429,6 @@ e_shell_backend_add_activity (EShellBackend *shell_backend,
shell_backend_activity_finalized_cb,
g_object_ref (shell_backend));
- g_signal_emit (shell_backend, signals[ACTIVITY_ADDED], 0, activity);
-
/* Only emit "notify::busy" when switching from idle to busy. */
if (g_queue_get_length (shell_backend->priv->activities) == 1)
g_object_notify (G_OBJECT (shell_backend), "busy");
diff --git a/shell/e-shell-taskbar.c b/shell/e-shell-taskbar.c
index 47f900ae3e..9be7c1564e 100644
--- a/shell/e-shell-taskbar.c
+++ b/shell/e-shell-taskbar.c
@@ -64,8 +64,8 @@ G_DEFINE_TYPE_WITH_CODE (
E_TYPE_EXTENSIBLE, NULL))
static void
-shell_taskbar_activity_remove (EShellTaskbar *shell_taskbar,
- EActivity *activity)
+shell_taskbar_weak_notify_cb (EShellTaskbar *shell_taskbar,
+ GObject *where_the_activity_was)
{
GtkWidget *proxy;
GtkContainer *container;
@@ -73,11 +73,10 @@ shell_taskbar_activity_remove (EShellTaskbar *shell_taskbar,
GList *children;
proxy_table = shell_taskbar->priv->proxy_table;
- proxy = g_hash_table_lookup (proxy_table, activity);
+ proxy = g_hash_table_lookup (proxy_table, where_the_activity_was);
+ g_hash_table_remove (proxy_table, where_the_activity_was);
g_return_if_fail (proxy != NULL);
- g_hash_table_remove (proxy_table, activity);
-
container = GTK_CONTAINER (shell_taskbar->priv->hbox);
gtk_container_remove (container, proxy);
@@ -95,6 +94,17 @@ shell_taskbar_activity_add (EShellTaskbar *shell_taskbar,
{
GtkBox *box;
GtkWidget *proxy;
+ EActivityState state;
+ GHashTable *proxy_table;
+
+ /* Sanity check the activity state. */
+ state = e_activity_get_state (activity);
+ g_return_if_fail (state == E_ACTIVITY_RUNNING);
+
+ /* Make sure it hasn't already been added. */
+ proxy_table = shell_taskbar->priv->proxy_table;
+ proxy = g_hash_table_lookup (proxy_table, activity);
+ g_return_if_fail (proxy == NULL);
/* Proxy widgets manage their own visibility.
* Don't call gtk_widget_show() on it here. */
@@ -104,17 +114,28 @@ shell_taskbar_activity_add (EShellTaskbar *shell_taskbar,
gtk_box_reorder_child (box, proxy, 0);
gtk_widget_show (GTK_WIDGET (box));
- g_hash_table_insert (
- shell_taskbar->priv->proxy_table,
- g_object_ref (activity), g_object_ref (proxy));
+ /* The proxy widget also holds a weak reference to the activity,
+ * so the activity should get finalized in the normal course of
+ * operation. When that happens we remove the corresponding
+ * proxy widget from the taskbar. */
- g_signal_connect_swapped (
- activity, "cancelled",
- G_CALLBACK (shell_taskbar_activity_remove), shell_taskbar);
+ g_object_weak_ref (
+ G_OBJECT (activity), (GWeakNotify)
+ shell_taskbar_weak_notify_cb, shell_taskbar);
- g_signal_connect_swapped (
- activity, "completed",
- G_CALLBACK (shell_taskbar_activity_remove), shell_taskbar);
+ g_hash_table_insert (proxy_table, activity, proxy);
+}
+
+static gboolean
+shell_taskbar_weak_unref (EActivity *activity,
+ EActivityProxy *proxy,
+ EShellTaskbar *shell_taskbar)
+{
+ g_object_weak_unref (
+ G_OBJECT (activity), (GWeakNotify)
+ shell_taskbar_weak_notify_cb, shell_taskbar);
+
+ return TRUE;
}
static void
@@ -176,18 +197,6 @@ shell_taskbar_get_property (GObject *object,
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
}
-static gboolean
-disconnect_remove (EActivity *activity,
- EActivityProxy *proxy,
- EShellTaskbar *shell_taskbar)
-{
- g_signal_handlers_disconnect_matched (
- activity, G_SIGNAL_MATCH_DATA,
- 0, 0, NULL, NULL, shell_taskbar);
-
- return TRUE;
-}
-
static void
shell_taskbar_dispose (GObject *object)
{
@@ -195,6 +204,10 @@ shell_taskbar_dispose (GObject *object)
priv = E_SHELL_TASKBAR_GET_PRIVATE (object);
+ g_hash_table_foreach_remove (
+ priv->proxy_table, (GHRFunc)
+ shell_taskbar_weak_unref, object);
+
if (priv->shell_view != NULL) {
g_object_remove_weak_pointer (
G_OBJECT (priv->shell_view), &priv->shell_view);
@@ -219,9 +232,6 @@ shell_taskbar_dispose (GObject *object)
priv->hbox = NULL;
}
- g_hash_table_foreach_remove (
- priv->proxy_table, (GHRFunc) disconnect_remove, object);
-
/* Chain up to parent's dispose() method. */
G_OBJECT_CLASS (e_shell_taskbar_parent_class)->dispose (object);
}
@@ -315,16 +325,10 @@ static void
e_shell_taskbar_init (EShellTaskbar *shell_taskbar)
{
GtkWidget *widget;
- GHashTable *proxy_table;
gint height;
- proxy_table = g_hash_table_new_full (
- g_direct_hash, g_direct_equal,
- (GDestroyNotify) g_object_unref,
- (GDestroyNotify) g_object_unref);
-
shell_taskbar->priv = E_SHELL_TASKBAR_GET_PRIVATE (shell_taskbar);
- shell_taskbar->priv->proxy_table = proxy_table;
+ shell_taskbar->priv->proxy_table = g_hash_table_new (NULL, NULL);
gtk_box_set_spacing (GTK_BOX (shell_taskbar), 12);
diff --git a/shell/e-shell-view.c b/shell/e-shell-view.c
index 18300c4672..e07b76213a 100644
--- a/shell/e-shell-view.c
+++ b/shell/e-shell-view.c
@@ -293,7 +293,7 @@ shell_view_save_state (EShellView *shell_view)
FALSE, G_FILE_CREATE_PRIVATE, (GAsyncReadyCallback)
shell_view_save_state_done_cb, data);
- e_activity_set_primary_text (
+ e_activity_set_text (
activity, (_("Saving user interface state")));
e_shell_backend_add_activity (shell_backend, activity);
diff --git a/shell/e-shell.c b/shell/e-shell.c
index 62cae09cfc..b983b18403 100644
--- a/shell/e-shell.c
+++ b/shell/e-shell.c
@@ -221,7 +221,7 @@ shell_ready_for_offline (EShell *shell,
* a signal without triggering the toggle reference. */
g_object_ref (activity);
- e_activity_complete (activity);
+ e_activity_set_state (activity, E_ACTIVITY_COMPLETED);
g_object_remove_toggle_ref (
G_OBJECT (activity), (GToggleNotify)
@@ -243,7 +243,7 @@ shell_prepare_for_offline (EShell *shell)
shell->priv->preparing_for_line_change = e_activity_new ();
- e_activity_set_primary_text (
+ e_activity_set_text (
shell->priv->preparing_for_line_change,
_("Preparing to go offline..."));
@@ -274,7 +274,7 @@ shell_ready_for_online (EShell *shell,
* a signal without triggering the toggle reference. */
g_object_ref (activity);
- e_activity_complete (activity);
+ e_activity_set_state (activity, E_ACTIVITY_COMPLETED);
g_object_remove_toggle_ref (
G_OBJECT (activity), (GToggleNotify)
@@ -296,7 +296,7 @@ shell_prepare_for_online (EShell *shell)
shell->priv->preparing_for_line_change = e_activity_new ();
- e_activity_set_primary_text (
+ e_activity_set_text (
shell->priv->preparing_for_line_change,
_("Preparing to go online..."));
@@ -329,7 +329,7 @@ shell_ready_for_quit (EShell *shell,
* a signal without triggering the toggle reference. */
g_object_ref (activity);
- e_activity_complete (activity);
+ e_activity_set_state (activity, E_ACTIVITY_COMPLETED);
g_object_remove_toggle_ref (
G_OBJECT (activity), (GToggleNotify)
@@ -358,7 +358,7 @@ shell_prepare_for_quit (EShell *shell)
shell->priv->preparing_for_quit = e_activity_new ();
- e_activity_set_primary_text (
+ e_activity_set_text (
shell->priv->preparing_for_quit,
_("Preparing to quit..."));
diff --git a/shell/test/e-test-shell-view.c b/shell/test/e-test-shell-view.c
index 4ecda3035c..924f9891f4 100644
--- a/shell/test/e-test-shell-view.c
+++ b/shell/test/e-test-shell-view.c
@@ -98,7 +98,7 @@ test_shell_view_constructed (GObject *object)
activity = e_activity_new ();
cancellable = g_cancellable_new ();
e_activity_set_cancellable (activity, cancellable);
- e_activity_set_primary_text (activity, "Test Activity");
+ e_activity_set_text (activity, "Test Activity");
e_shell_backend_add_activity (shell_backend, activity);
g_object_unref (cancellable);
priv->activity = activity;