[gnome-software] update dialog: Show a spinner while loading update history
- From: Kalev Lember <klember src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-software] update dialog: Show a spinner while loading update history
- Date: Sun, 24 May 2015 14:18:02 +0000 (UTC)
commit 3fe41213058ed8fc9d632edb63ba79cc88fb2577
Author: Kalev Lember <kalevlember gmail com>
Date: Sun May 24 13:20:53 2015 +0200
update dialog: Show a spinner while loading update history
This moves the async update history loading from GsShell to
GsUpdateDidalog, in order to make it possible to show a spinner in the
dialog itself while the data is loading.
src/gs-shell-updates.c | 2 +-
src/gs-shell.c | 51 ++----------------------
src/gs-update-dialog.c | 98 ++++++++++++++++++++++++++++++++++++++++------
src/gs-update-dialog.h | 6 +-
src/gs-update-dialog.ui | 28 +++++++++++++
5 files changed, 121 insertions(+), 64 deletions(-)
---
diff --git a/src/gs-shell-updates.c b/src/gs-shell-updates.c
index ac05db0..4d11e3b 100644
--- a/src/gs-shell-updates.c
+++ b/src/gs-shell-updates.c
@@ -570,7 +570,7 @@ show_update_details (GsApp *app, GsShellUpdates *shell_updates)
GsShellUpdatesPrivate *priv = shell_updates->priv;
GtkWidget *dialog;
- dialog = gs_update_dialog_new ();
+ dialog = gs_update_dialog_new (priv->plugin_loader);
gs_update_dialog_show_update_details (GS_UPDATE_DIALOG (dialog), app);
gtk_window_set_transient_for (GTK_WINDOW (dialog), gs_shell_get_window (priv->shell));
diff --git a/src/gs-shell.c b/src/gs-shell.c
index f04812d..d2a3898 100644
--- a/src/gs-shell.c
+++ b/src/gs-shell.c
@@ -677,60 +677,17 @@ gs_shell_get_mode_string (GsShell *shell)
return page_name[priv->mode];
}
-static void
-gs_shell_get_installed_updates_cb (GsPluginLoader *plugin_loader,
- GAsyncResult *res,
- GsShell *shell)
+void
+gs_shell_show_installed_updates (GsShell *shell)
{
GsShellPrivate *priv = shell->priv;
- GList *list;
GtkWidget *dialog;
- _cleanup_error_free_ GError *error = NULL;
-
- /* get the results */
- list = gs_plugin_loader_get_updates_finish (plugin_loader, res, &error);
- if (list == NULL) {
- if (g_error_matches (error,
- GS_PLUGIN_LOADER_ERROR,
- GS_PLUGIN_LOADER_ERROR_NO_RESULTS)) {
- g_debug ("no updates to show");
- } else if (g_error_matches (error,
- G_IO_ERROR,
- G_IO_ERROR_CANCELLED)) {
- g_debug ("get updates cancelled");
- } else {
- g_warning ("failed to get updates: %s", error->message);
- }
- goto out;
- }
- dialog = gs_update_dialog_new ();
- gs_update_dialog_show_installed_updates (GS_UPDATE_DIALOG (dialog), list);
+ dialog = gs_update_dialog_new (priv->plugin_loader);
+ gs_update_dialog_show_installed_updates (GS_UPDATE_DIALOG (dialog));
gtk_window_set_transient_for (GTK_WINDOW (dialog), priv->main_window);
gtk_window_present (GTK_WINDOW (dialog));
-
-out:
- gs_plugin_list_free (list);
-}
-
-
-void
-gs_shell_show_installed_updates (GsShell *shell)
-{
- GsShellPrivate *priv = shell->priv;
- guint64 refine_flags;
-
- refine_flags = GS_PLUGIN_REFINE_FLAGS_DEFAULT |
- GS_PLUGIN_REFINE_FLAGS_REQUIRE_UPDATE_DETAILS |
- GS_PLUGIN_REFINE_FLAGS_REQUIRE_VERSION |
- GS_PLUGIN_REFINE_FLAGS_USE_HISTORY;
-
- gs_plugin_loader_get_updates_async (priv->plugin_loader,
- refine_flags,
- priv->cancellable,
- (GAsyncReadyCallback) gs_shell_get_installed_updates_cb,
- shell);
}
void
diff --git a/src/gs-update-dialog.c b/src/gs-update-dialog.c
index eed2774..874a0ff 100644
--- a/src/gs-update-dialog.c
+++ b/src/gs-update-dialog.c
@@ -42,6 +42,8 @@ typedef struct {
struct _GsUpdateDialogPrivate
{
GQueue *back_entry_stack;
+ GCancellable *cancellable;
+ GsPluginLoader *plugin_loader;
GtkWidget *box_header;
GtkWidget *button_back;
GtkWidget *image_icon;
@@ -52,6 +54,7 @@ struct _GsUpdateDialogPrivate
GtkWidget *list_box_installed_updates;
GtkWidget *scrolledwindow;
GtkWidget *scrolledwindow_details;
+ GtkWidget *spinner;
GtkWidget *stack;
};
@@ -166,11 +169,52 @@ installed_updates_row_activated_cb (GtkListBox *list_box,
gs_update_dialog_show_update_details (dialog, app);
}
-void
-gs_update_dialog_show_installed_updates (GsUpdateDialog *dialog, GList *installed_updates)
+static void
+get_installed_updates_cb (GsPluginLoader *plugin_loader,
+ GAsyncResult *res,
+ GsUpdateDialog *dialog)
{
GsUpdateDialogPrivate *priv = gs_update_dialog_get_instance_private (dialog);
GList *l;
+ _cleanup_plugin_list_free_ GList *list = NULL;
+ _cleanup_error_free_ GError *error = NULL;
+
+ gs_stop_spinner (GTK_SPINNER (priv->spinner));
+
+ /* get the results */
+ list = gs_plugin_loader_get_updates_finish (plugin_loader, res, &error);
+ if (list == NULL) {
+ if (g_error_matches (error,
+ GS_PLUGIN_LOADER_ERROR,
+ GS_PLUGIN_LOADER_ERROR_NO_RESULTS)) {
+ g_debug ("no installed updates to show");
+ return;
+ } else if (g_error_matches (error,
+ G_IO_ERROR,
+ G_IO_ERROR_CANCELLED)) {
+ /* This should only ever happen while the dialog is being closed */
+ g_debug ("get installed updates cancelled");
+ return;
+ }
+
+ g_warning ("failed to get installed updates: %s", error->message);
+ return;
+ }
+
+ gtk_stack_set_visible_child_name (GTK_STACK (priv->stack), "installed-updates-list");
+
+ gs_container_remove_all (GTK_CONTAINER (priv->list_box_installed_updates));
+ for (l = list; l != NULL; l = l->next) {
+ gs_update_list_add_app (GS_UPDATE_LIST (priv->list_box_installed_updates),
+ GS_APP (l->data));
+ }
+}
+
+void
+gs_update_dialog_show_installed_updates (GsUpdateDialog *dialog)
+{
+ GsUpdateDialogPrivate *priv = gs_update_dialog_get_instance_private (dialog);
+ guint64 refine_flags;
guint64 time_updates_installed;
/* TRANSLATORS: this is the title of the installed updates dialog window */
@@ -193,13 +237,19 @@ gs_update_dialog_show_installed_updates (GsUpdateDialog *dialog, GList *installe
}
gtk_widget_set_visible (priv->button_back, !g_queue_is_empty (priv->back_entry_stack));
- gtk_stack_set_visible_child_name (GTK_STACK (priv->stack), "installed-updates-list");
-
- gs_container_remove_all (GTK_CONTAINER (priv->list_box_installed_updates));
- for (l = installed_updates; l != NULL; l = l->next) {
- gs_update_list_add_app (GS_UPDATE_LIST (priv->list_box_installed_updates),
- GS_APP (l->data));
- }
+ gs_start_spinner (GTK_SPINNER (priv->spinner));
+ gtk_stack_set_visible_child_name (GTK_STACK (priv->stack), "spinner");
+
+ refine_flags = GS_PLUGIN_REFINE_FLAGS_DEFAULT |
+ GS_PLUGIN_REFINE_FLAGS_REQUIRE_UPDATE_DETAILS |
+ GS_PLUGIN_REFINE_FLAGS_REQUIRE_VERSION |
+ GS_PLUGIN_REFINE_FLAGS_USE_HISTORY;
+
+ gs_plugin_loader_get_updates_async (priv->plugin_loader,
+ refine_flags,
+ priv->cancellable,
+ (GAsyncReadyCallback) get_installed_updates_cb,
+ dialog);
}
void
@@ -336,6 +386,14 @@ unset_focus (GtkWidget *widget)
}
static void
+set_plugin_loader (GsUpdateDialog *dialog, GsPluginLoader *plugin_loader)
+{
+ GsUpdateDialogPrivate *priv = gs_update_dialog_get_instance_private (dialog);
+
+ priv->plugin_loader = g_object_ref (plugin_loader);
+}
+
+static void
gs_update_dialog_finalize (GObject *object)
{
GsUpdateDialog *dialog = GS_UPDATE_DIALOG (object);
@@ -346,6 +404,13 @@ gs_update_dialog_finalize (GObject *object)
priv->back_entry_stack = NULL;
}
+ if (priv->cancellable != NULL) {
+ g_cancellable_cancel (priv->cancellable);
+ g_clear_object (&priv->cancellable);
+ }
+
+ g_clear_object (&priv->plugin_loader);
+
G_OBJECT_CLASS (gs_update_dialog_parent_class)->finalize (object);
}
@@ -358,6 +423,7 @@ gs_update_dialog_init (GsUpdateDialog *dialog)
gtk_widget_init_template (GTK_WIDGET (dialog));
priv->back_entry_stack = g_queue_new ();
+ priv->cancellable = g_cancellable_new ();
g_signal_connect (GTK_LIST_BOX (priv->list_box), "row-activated",
G_CALLBACK (row_activated_cb), dialog);
@@ -406,15 +472,21 @@ gs_update_dialog_class_init (GsUpdateDialogClass *klass)
gtk_widget_class_bind_template_child_private (widget_class, GsUpdateDialog,
list_box_installed_updates);
gtk_widget_class_bind_template_child_private (widget_class, GsUpdateDialog, scrolledwindow);
gtk_widget_class_bind_template_child_private (widget_class, GsUpdateDialog, scrolledwindow_details);
+ gtk_widget_class_bind_template_child_private (widget_class, GsUpdateDialog, spinner);
gtk_widget_class_bind_template_child_private (widget_class, GsUpdateDialog, stack);
}
GtkWidget *
-gs_update_dialog_new (void)
+gs_update_dialog_new (GsPluginLoader *plugin_loader)
{
- return GTK_WIDGET (g_object_new (GS_TYPE_UPDATE_DIALOG,
- "use-header-bar", TRUE,
- NULL));
+ GsUpdateDialog *dialog;
+
+ dialog = g_object_new (GS_TYPE_UPDATE_DIALOG,
+ "use-header-bar", TRUE,
+ NULL);
+ set_plugin_loader (dialog, plugin_loader);
+
+ return GTK_WIDGET (dialog);
}
/* vim: set noexpandtab: */
diff --git a/src/gs-update-dialog.h b/src/gs-update-dialog.h
index d6ffd44..fd7a68e 100644
--- a/src/gs-update-dialog.h
+++ b/src/gs-update-dialog.h
@@ -25,6 +25,7 @@
#include <gtk/gtk.h>
#include "gs-app.h"
+#include "gs-plugin-loader.h"
#define GS_TYPE_UPDATE_DIALOG (gs_update_dialog_get_type())
#define GS_UPDATE_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), GS_TYPE_UPDATE_DIALOG,
GsUpdateDialog))
@@ -50,9 +51,8 @@ struct _GsUpdateDialogClass
};
GType gs_update_dialog_get_type (void);
-GtkWidget *gs_update_dialog_new (void);
-void gs_update_dialog_show_installed_updates (GsUpdateDialog *dialog,
- GList *installed_updates);
+GtkWidget *gs_update_dialog_new (GsPluginLoader *plugin_loader);
+void gs_update_dialog_show_installed_updates (GsUpdateDialog *dialog);
void gs_update_dialog_show_update_details (GsUpdateDialog *dialog,
GsApp *app);
diff --git a/src/gs-update-dialog.ui b/src/gs-update-dialog.ui
index af8c998..cfc6276 100644
--- a/src/gs-update-dialog.ui
+++ b/src/gs-update-dialog.ui
@@ -53,6 +53,34 @@
<property name="visible">True</property>
<property name="can_focus">False</property>
<child>
+ <object class="GtkBox" id="box_spinner">
+ <property name="visible">True</property>
+ <property name="orientation">vertical</property>
+ <property name="spacing">12</property>
+ <property name="halign">center</property>
+ <property name="valign">center</property>
+ <property name="hexpand">True</property>
+ <property name="vexpand">True</property>
+ <style>
+ <class name="dim-label"/>
+ </style>
+ <child>
+ <object class="GtkSpinner" id="spinner">
+ <property name="visible">True</property>
+ <property name="width_request">32</property>
+ <property name="height_request">32</property>
+ <property name="halign">center</property>
+ <property name="valign">center</property>
+ <property name="hexpand">True</property>
+ <property name="vexpand">True</property>
+ </object>
+ </child>
+ </object>
+ <packing>
+ <property name="name">spinner</property>
+ </packing>
+ </child>
+ <child>
<object class="GtkBox" id="box7">
<property name="visible">True</property>
<property name="can_focus">False</property>
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]