[gnome-packagekit/glib2: 64/79] moo



commit 86da6588948dff849cfba29c72a328c1a6f0e617
Author: Richard Hughes <richard hughsie com>
Date:   Sat Oct 3 21:44:42 2009 +0100

    moo

 src/gpk-update-viewer.c | 1367 +++++++++++++++++++++++------------------------
 1 files changed, 671 insertions(+), 696 deletions(-)
---
diff --git a/src/gpk-update-viewer.c b/src/gpk-update-viewer.c
index b67f4da..19c6e29 100644
--- a/src/gpk-update-viewer.c
+++ b/src/gpk-update-viewer.c
@@ -200,68 +200,148 @@ gpk_update_viewer_undisable_packages ()
 }
 
 /**
- * gpk_update_viewer_button_check_connection:
+ * gpk_update_viewer_auto_shutdown:
+ **/
+static gboolean
+gpk_update_viewer_auto_shutdown (GtkDialog *dialog)
+{
+	gtk_dialog_response (dialog, GTK_RESPONSE_CANCEL);
+	auto_shutdown_id = 0;
+	return FALSE;
+}
+
+/**
+ * gpk_update_viewer_check_restart:
  **/
 static gboolean
-gpk_update_viewer_button_check_connection (guint size)
+gpk_update_viewer_check_restart (PkRestartEnum restart)
 {
 	GtkWindow *window;
 	GtkWidget *dialog;
-	gboolean ret = TRUE;
-	gchar *text_size = NULL;
-	gchar *message = NULL;
+	gboolean ret = FALSE;
+	const gchar *title;
+	const gchar *message;
+	const gchar *button;
 	GtkResponseType response;
-	GError *error = NULL;
-	PkNetworkEnum state;
+	gboolean show_button = TRUE;
 
-	/* get network state */
-	state = pk_control_get_network_state (control, &error);
-	if (error != NULL) {
-		egg_warning ("failed to get network state: %s", error->message);
-		g_error_free (error);
-		goto out;
-	}
+	/* get the text */
+	title = gpk_restart_enum_to_localised_text (restart);
+	if (restart == PK_RESTART_ENUM_SYSTEM) {
+		/* TRANSLATORS: the message text for the restart */
+		message = _("Some of the updates that were installed require the computer to be restarted before the changes will be applied.");
+		/* TRANSLATORS: the button text for the restart */
+		button = _("Restart Computer");
 
-	/* not on wireless mobile */
-	if (state != PK_NETWORK_ENUM_MOBILE)
-		goto out;
+	} else if (restart == PK_RESTART_ENUM_SECURITY_SYSTEM) {
+		/* TRANSLATORS: the message text for the restart */
+		message = _("Some of the updates that were installed require the computer to be restarted to remain secure.");
+		/* TRANSLATORS: the button text for the restart */
+		button = _("Restart Computer");
 
-	/* not when small */
-	if (size < GPK_UPDATE_VIEWER_MOBILE_SMALL_SIZE)
-		goto out;
+	} else if (restart == PK_RESTART_ENUM_SESSION) {
+		/* TRANSLATORS: the message text for the logout */
+		message = _("Some of the updates that were installed require you to log out and back in before the changes will be applied.");
+		/* TRANSLATORS: the button text for the logout */
+		button = _("Log Out");
 
-	/* not when ignored */
-	ret = gconf_client_get_bool (gconf_client, GPK_CONF_UPDATE_VIEWER_MOBILE_BBAND, NULL);
-	if (!ret)
+	} else if (restart == PK_RESTART_ENUM_SECURITY_SESSION) {
+		/* TRANSLATORS: the message text for the logout */
+		message = _("Some of the updates that were installed require you to log out and back in to remain secure.");
+		/* TRANSLATORS: the button text for the logout */
+		button = _("Log Out");
+
+	} else {
+		egg_warning ("unknown restart enum");
 		goto out;
+	}
 
 	/* show modal dialog */
 	window = GTK_WINDOW (gtk_builder_get_object (builder, "dialog_updates"));
 	dialog = gtk_message_dialog_new (window, GTK_DIALOG_MODAL,
-					 GTK_MESSAGE_INFO, GTK_BUTTONS_CANCEL,
-					 "%s", _("Detected wireless broadband connection"));
+					 GTK_MESSAGE_INFO, GTK_BUTTONS_CLOSE,
+					 "%s", title);
 
-	/* TRANSLATORS: this is the button text when we check if it's okay to download */
-	gtk_dialog_add_button (GTK_DIALOG (dialog), _("Update anyway"), GTK_RESPONSE_OK);
-	text_size = g_format_size_for_display (size_total);
+	/* check to see if restart is possible */
+	if (restart == PK_RESTART_ENUM_SYSTEM ||
+	    restart == PK_RESTART_ENUM_SECURITY_SYSTEM) {
+		egg_console_kit_can_restart (console, &show_button, NULL);
+	}
 
-	/* TRANSLATORS, the %s is a size, e.g. 13.3Mb */
-	message = g_strdup_printf (_("Connectivity is being provided by wireless broadband, and it may be expensive to download %s."), text_size);
+	/* only show the button if we can do the action */
+	if (show_button)
+		gtk_dialog_add_button (GTK_DIALOG (dialog), button, GTK_RESPONSE_OK);
 	gtk_message_dialog_format_secondary_text (GTK_MESSAGE_DIALOG(dialog), "%s", message);
-	gpk_dialog_embed_do_not_show_widget (GTK_DIALOG (dialog), GPK_CONF_UPDATE_VIEWER_MOBILE_BBAND);
 	gtk_window_set_icon_name (GTK_WINDOW(dialog), GPK_ICON_SOFTWARE_INSTALLER);
+
+	/* setup a callback so we autoclose */
+	auto_shutdown_id = g_timeout_add_seconds (GPK_UPDATE_VIEWER_AUTO_RESTART_TIMEOUT, (GSourceFunc) gpk_update_viewer_auto_shutdown, dialog);
+
 	response = gtk_dialog_run (GTK_DIALOG(dialog));
 	gtk_widget_destroy (dialog);
 
+	/* cancel */
 	if (response != GTK_RESPONSE_OK)
-		ret = FALSE;
+		goto out;
+
+	/* doing the action, return success */
+	ret = TRUE;
+
+	/* do the action */
+	if (restart == PK_RESTART_ENUM_SYSTEM)
+		gpk_update_viewer_shutdown ();
+	else if (restart == PK_RESTART_ENUM_SESSION)
+		gpk_update_viewer_logout ();
 out:
-	g_free (text_size);
-	g_free (message);
 	return ret;
 }
 
 /**
+ * gpk_update_viewer_check_blocked_packages:
+ **/
+static void
+gpk_update_viewer_check_blocked_packages (GPtrArray *array)
+{
+	guint i;
+	const PkItemPackage *item;
+	GString *string;
+	gboolean exists = FALSE;
+	gchar *text;
+	GtkWindow *window;
+
+	string = g_string_new ("");
+
+	/* find any that are blocked */
+	for (i=0;i<array->len;i++) {
+		item = g_ptr_array_index (array, i);
+		if (item->info == PK_INFO_ENUM_BLOCKED) {
+			text = gpk_package_id_format_oneline (item->package_id, item->summary);
+			g_string_append_printf (string, "%s\n", text);
+			g_free (text);
+			exists = TRUE;
+		}
+	}
+
+	/* trim off extra newlines */
+	if (string->len != 0)
+		g_string_set_size (string, string->len-1);
+
+	/* convert to a normal gchar */
+	text = g_string_free (string, FALSE);
+
+	/* nothing of interest */
+	if (!exists)
+		goto out;
+
+	/* throw up dialog */
+	window = GTK_WINDOW (gtk_builder_get_object (builder, "dialog_updates"));
+	/* TRANSLATORS: we failed to install all the updates we requested */
+	gpk_error_dialog_modal (window, _("Some updates were not installed"), text, NULL);
+out:
+	g_free (text);
+}
+
+/**
  * gpk_update_viewer_update_packages_cb:
  **/
 static void
@@ -272,6 +352,10 @@ gpk_update_viewer_update_packages_cb (PkTask *_task, GAsyncResult *res, GMainLoo
 	GPtrArray *array = NULL;
 	PkItemPackage *item;
 	guint i;
+	GtkWidget *dialog;
+	GtkWidget *widget;
+	PkRestartEnum restart;
+	gchar *text;
 
 	/* get the results */
 	results = pk_task_generic_finish (task, res, &error);
@@ -281,12 +365,84 @@ gpk_update_viewer_update_packages_cb (PkTask *_task, GAsyncResult *res, GMainLoo
 		goto out;
 	}
 
+	/* TODO: failed sound */
+	/* play the sound, using sounds from the naming spec */
+	ca_context_play (ca_gtk_context_get (), 0,
+			 CA_PROP_EVENT_ID, "dialog-warning",
+			 /* TRANSLATORS: this is the application name for libcanberra */
+			 CA_PROP_APPLICATION_NAME, _("GNOME PackageKit Update Viewer"),
+			 /* TRANSLATORS: this is the sound description */
+			 CA_PROP_EVENT_DESCRIPTION, _("Failed to update"), NULL);
+
+	gpk_update_viewer_undisable_packages ();
+
 	/* get data */
 	array = pk_results_get_package_array (results);
 	for (i=0; i<array->len; i++) {
 		item = g_ptr_array_index (array, i);
 	}
 
+	/* TODO: use ca_gtk_context_get_for_screen to allow use of GDK_MULTIHEAD_SAFE */
+
+	/* play the sound, using sounds from the naming spec */
+	ca_context_play (ca_gtk_context_get (), 0,
+			 /* TODO: add a new sound to the spec */
+			 CA_PROP_EVENT_ID, "complete-download",
+			 /* TRANSLATORS: this is the application name for libcanberra */
+			 CA_PROP_APPLICATION_NAME, _("GNOME PackageKit Update Viewer"),
+			 /* TRANSLATORS: this is the sound description */
+			 CA_PROP_EVENT_DESCRIPTION, _("Updated successfully"), NULL);
+
+	/* get the worst restart case */
+	restart = pk_results_get_require_restart_worst (results);
+	if (restart > restart_update)
+		restart_update = restart;
+
+	/* check blocked */
+	array = pk_results_get_package_array (results);
+	gpk_update_viewer_check_blocked_packages (array);
+	g_ptr_array_unref (array);
+
+	/* check restart */
+	if (restart_update == PK_RESTART_ENUM_SYSTEM ||
+	    restart_update == PK_RESTART_ENUM_SESSION ||
+	    restart_update == PK_RESTART_ENUM_SECURITY_SESSION ||
+	    restart_update == PK_RESTART_ENUM_SECURITY_SYSTEM) {
+		gpk_update_viewer_check_restart (restart_update);
+		g_main_loop_quit (loop);
+	}
+
+	/* hide close button */
+	widget = GTK_WIDGET (gtk_builder_get_object (builder, "button_quit"));
+	gtk_widget_hide (widget);
+
+	/* show a new title */
+	widget = GTK_WIDGET (gtk_builder_get_object (builder, "label_header_title"));
+	/* TRANSLATORS: completed all updates */
+	text = g_strdup_printf ("<big><b>%s</b></big>", _("All selected updates installed..."));
+	gtk_label_set_label (GTK_LABEL (widget), text);
+	g_free (text);
+
+	/* show modal dialog */
+	widget = GTK_WIDGET (gtk_builder_get_object (builder, "dialog_updates"));
+	dialog = gtk_message_dialog_new (GTK_WINDOW (widget), GTK_DIALOG_MODAL,
+					 GTK_MESSAGE_INFO, GTK_BUTTONS_OK,
+					 /* TRANSLATORS: title: all updates installed okay */
+					 "%s", _("All selected updates installed"));
+	gtk_message_dialog_format_secondary_text (GTK_MESSAGE_DIALOG(dialog),
+						  "%s",
+						  /* TRANSLATORS: software updates installed okay */
+						  _("All selected updates were successfully installed."));
+	gtk_window_set_icon_name (GTK_WINDOW(dialog), GPK_ICON_SOFTWARE_INSTALLER);
+
+	/* setup a callback so we autoclose */
+	auto_shutdown_id = g_timeout_add_seconds (GPK_UPDATE_VIEWER_AUTO_RESTART_TIMEOUT, (GSourceFunc) gpk_update_viewer_auto_shutdown, dialog);
+
+	gtk_dialog_run (GTK_DIALOG(dialog));
+	gtk_widget_destroy (dialog);
+
+	/* quit after we successfully updated */
+	g_main_loop_quit (loop);
 out:
 	if (array != NULL)
 		g_ptr_array_unref (array);
@@ -294,130 +450,107 @@ out:
 		g_object_unref (results);
 }
 
+
+static GSList *active_rows = NULL;
+static guint active_row_timeout = 0;
+
 /**
- * gpk_update_viewer_button_install_cb:
+ * gpk_update_viewer_compare_refs:
  **/
-static void
-gpk_update_viewer_button_install_cb (GtkWidget *widget, gpointer data)
+static gint
+gpk_update_viewer_compare_refs (GtkTreeRowReference *a, GtkTreeRowReference *b)
 {
-	GtkWindow *window;
-	GtkTreeView *treeview;
-	GtkTreeModel *model;
-	GtkTreeIter iter;
-	GtkTreeSelection *selection;
-	gboolean ret;
-	gboolean valid;
-	gboolean update;
-	gboolean selected_any = FALSE;
-	gchar *package_id;
-	GPtrArray *array = NULL;
-	gchar **package_ids = NULL;
-	PkInfoEnum info;
-
-	/* check connection */
-	ret = gpk_update_viewer_button_check_connection (size_total);
-	if (!ret)
-		goto out;
-
-	/* hide the upgrade viewbox from now on */
-	widget = GTK_WIDGET (gtk_builder_get_object (builder, "viewport_upgrade"));
-	gtk_widget_hide (widget);
+	GtkTreeModel *am, *bm;
+	GtkTreePath *ap, *bp;
+	gint res;
 
-	egg_debug ("Doing the package updates");
-	array = g_ptr_array_new ();
+	am = gtk_tree_row_reference_get_model (a);
+	bm = gtk_tree_row_reference_get_model (b);
 
-	treeview = GTK_TREE_VIEW (gtk_builder_get_object (builder, "treeview_updates"));
-	model = gtk_tree_view_get_model (treeview);
+	res = 1;
+	if (am == bm) {
+		ap = gtk_tree_row_reference_get_path (a);
+		bp = gtk_tree_row_reference_get_path (b);
 
-	/* get the first iter in the array */
-	valid = gtk_tree_model_get_iter_first (model, &iter);
+		res = gtk_tree_path_compare (ap, bp);
 
-	/* find out how many we should update */
-	while (valid) {
-		gtk_tree_model_get (model, &iter,
-				    GPK_UPDATES_COLUMN_INFO, &info,
-				    GPK_UPDATES_COLUMN_SELECT, &update,
-				    GPK_UPDATES_COLUMN_ID, &package_id, -1);
+		gtk_tree_path_free (ap);
+		gtk_tree_path_free (bp);
+	}
 
-		/* set all the checkboxes insensitive */
-		gtk_list_store_set (array_store_updates, &iter,
-				    GPK_UPDATES_COLUMN_CLICKABLE, FALSE,
-				    GPK_UPDATES_COLUMN_SENSITIVE, FALSE, -1);
+	return res;
+}
 
-		/* any selected? */
-		if (update)
-			selected_any = TRUE;
+/**
+ * gpk_update_viewer_pulse_active_rows:
+ **/
+static gboolean
+gpk_update_viewer_pulse_active_rows (void)
+{
+	GSList *l;
+	GtkTreeRowReference *ref;
+	GtkTreeModel *model;
+	GtkTreePath *path;
+	GtkTreeIter iter;
+	gint val;
 
-		/* if selected, and not added previously because of deps */
-		if (update && info != PK_INFO_ENUM_AVAILABLE) {
-			g_ptr_array_add (array, package_id);
-		} else {
-			/* need to free the one in the array later */
-			g_free (package_id);
+	for (l = active_rows; l; l = l->next) {
+		ref = l->data;
+		model = gtk_tree_row_reference_get_model (ref);
+		path = gtk_tree_row_reference_get_path (ref);
+		if (path) {
+			gtk_tree_model_get_iter (model, &iter, path);
+			gtk_tree_model_get (model, &iter, GPK_UPDATES_COLUMN_PULSE, &val, -1);
+			gtk_list_store_set (GTK_LIST_STORE (model), &iter, GPK_UPDATES_COLUMN_PULSE, val + 1, -1);
+			gtk_tree_path_free (path);
 		}
-		valid = gtk_tree_model_iter_next (model, &iter);
 	}
 
-	/* we have no checkboxes selected */
-	if (!selected_any) {
-		window = GTK_WINDOW (gtk_builder_get_object (builder, "dialog_updates"));
-		gpk_error_dialog_modal (window,
-					/* TRANSLATORS: we clicked apply, but had no packages selected */
-					_("No updates selected"),
-					_("No updates are selected"), NULL);
-		return;
-	}
-
-	/* disable button */
-	widget = GTK_WIDGET (gtk_builder_get_object (builder, "button_install"));
-	gtk_widget_set_sensitive (widget, FALSE);
-
-	/* clear the selection */
-	selection = gtk_tree_view_get_selection (treeview);
-	gtk_tree_selection_unselect_all (selection);
-
-	/* save for finished */
-	package_ids = pk_ptr_array_to_strv (array);
-	g_strfreev (install_package_ids);
-	install_package_ids = g_strdupv (package_ids);
-
-	/* get packages that also have to be updated */
-	pk_task_update_packages (task, package_ids, cancellable,
-				 NULL, NULL,
-				 (GAsyncReadyCallback) gpk_update_viewer_update_packages_cb, loop);
-out:
-	g_strfreev (package_ids);
-
-	/* get rid of the array, and free the contents */
-	if (array != NULL) {
-		g_ptr_array_unref (array);
-	}
+	return TRUE;
 }
 
 /**
- * gpk_update_viewer_button_upgrade_cb:
+ * gpk_update_viewer_add_active_row:
  **/
 static void
-gpk_update_viewer_button_upgrade_cb (GtkWidget *widget, gpointer data)
+gpk_update_viewer_add_active_row (GtkTreeModel *model, GtkTreePath *path)
 {
-	gboolean ret;
-	GError *error = NULL;
+	GtkTreeRowReference *ref;
 
-	ret = g_spawn_command_line_async ("/usr/share/PackageKit/pk-upgrade-distro.sh", NULL);
-	if (!ret) {
-		egg_warning ("Failure launching pk-upgrade-distro.sh: %s", error->message);
-		g_error_free (error);
+	if (!active_row_timeout) {
+		active_row_timeout = g_timeout_add (60, (GSourceFunc)gpk_update_viewer_pulse_active_rows, NULL);
 	}
+
+	ref = gtk_tree_row_reference_new (model, path);
+	active_rows = g_slist_prepend (active_rows, ref);
 }
 
 /**
- * gpk_update_viewer_button_delete_event_cb:
+ * gpk_update_viewer_remove_active_row:
  **/
-static gboolean
-gpk_update_viewer_button_delete_event_cb (GtkWidget *widget, GdkEvent *event, gpointer data)
+static void
+gpk_update_viewer_remove_active_row (GtkTreeModel *model, GtkTreePath *path)
 {
-	gpk_update_viewer_quit ();
-	return TRUE;
+	GSList *link;
+	GtkTreeRowReference *ref;
+	GtkTreeIter iter;
+
+	gtk_tree_model_get_iter (model, &iter, path);
+	gtk_list_store_set (GTK_LIST_STORE (model), &iter, GPK_UPDATES_COLUMN_PULSE, -1, -1);
+
+	ref = gtk_tree_row_reference_new (model, path);
+	link = g_slist_find_custom (active_rows, (gconstpointer)ref, (GCompareFunc)gpk_update_viewer_compare_refs);
+	gtk_tree_row_reference_free (ref);
+	g_assert (link);
+
+	active_rows = g_slist_remove_link (active_rows, link);
+	gtk_tree_row_reference_free (link->data);
+	g_slist_free (link);
+
+	if (active_rows == NULL) {
+		g_source_remove (active_row_timeout);
+		active_row_timeout = 0;
+	}
 }
 
 /**
@@ -464,134 +597,307 @@ gpk_update_viewer_model_get_path (GtkTreeModel *model, const gchar *id)
 }
 
 /**
- * gpk_update_viewer_details_cb:
+ * gpk_update_viewer_progress_cb:
  **/
 static void
-gpk_update_viewer_details_cb (PkClient *client, const PkItemDetails *item, gpointer data)
+gpk_update_viewer_progress_cb (PkProgress *progress, PkProgressType type, GMainLoop *_loop)
 {
-	GtkTreeView *treeview;
-	GtkTreeModel *model;
-	GtkTreeIter iter;
-	GtkTreePath *path;
+	PkStatusEnum status;
+	gint percentage;
+	gint subpercentage;
+	gboolean allow_cancel;
+	gchar *package_id;
+	GtkWidget *widget;
+	PkInfoEnum info = PK_INFO_ENUM_UNKNOWN;
+
+	g_object_get (progress,
+		      "status", &status,
+		      "percentage", &percentage,
+		      "subpercentage", &subpercentage,
+		      "package-id", &package_id,
+		      "allow-cancel", &allow_cancel,
+		      NULL);
 
-	treeview = GTK_TREE_VIEW (gtk_builder_get_object (builder, "treeview_updates"));
-	model = gtk_tree_view_get_model (treeview);
+	if (type == PK_PROGRESS_TYPE_PACKAGE_ID) {
 
-	path = gpk_update_viewer_model_get_path (model, item->package_id);
-	if (path == NULL) {
-		egg_debug ("not found ID for details");
-		return;
-	}
+		GtkTreeView *treeview;
+		GtkTreeIter iter;
+		GtkTreeModel *model;
+		GtkTreeViewColumn *column;
+		GtkTreePath *path;
+		gboolean scroll;
 
-	gtk_tree_model_get_iter (model, &iter, path);
-	gtk_tree_path_free (path);
-	gtk_list_store_set (array_store_updates, &iter,
-			    GPK_UPDATES_COLUMN_DETAILS_OBJ, (gpointer) pk_details_item_copy (item),
-			    GPK_UPDATES_COLUMN_SIZE, (gint)item->size,
-			    GPK_UPDATES_COLUMN_SIZE_DISPLAY, (gint)item->size,
-			    -1);
-	/* in cache */
-	if (item->size == 0)
+		/* used for progress */
+		g_free (package_id_last);
+		package_id_last = g_strdup (package_id);
+
+		/* find model */
+		treeview = GTK_TREE_VIEW (gtk_builder_get_object (builder, "treeview_updates"));
+		model = gtk_tree_view_get_model (treeview);
+
+		/* update icon */
+		path = gpk_update_viewer_model_get_path (model, package_id);
+		if (path == NULL) {
+			egg_debug ("not found ID for package");
+			goto out;
+		}
+
+		gtk_tree_model_get_iter (model, &iter, path);
+
+		/* scroll to the active cell */
+		scroll = gconf_client_get_bool (gconf_client, GPK_CONF_UPDATE_VIEWER_SCROLL_ACTIVE, NULL);
+		if (scroll) {
+			column = gtk_tree_view_get_column (treeview, 3);
+			gtk_tree_view_scroll_to_cell (treeview, path, column, FALSE, 0.0f, 0.0f);
+		}
+
+		/* if the info is finished, change the status to past tense */
+		if (info == PK_INFO_ENUM_FINISHED) {
+			gtk_tree_model_get (model, &iter,
+					    GPK_UPDATES_COLUMN_STATUS, &info, -1);
+			/* promote to past tense if present tense */
+			if (info < PK_INFO_ENUM_UNKNOWN)
+				info += PK_INFO_ENUM_UNKNOWN;
+		}
 		gtk_list_store_set (array_store_updates, &iter,
-				    GPK_UPDATES_COLUMN_STATUS, GPK_INFO_ENUM_DOWNLOADED, -1);
+				    GPK_UPDATES_COLUMN_STATUS, info, -1);
+
+		gtk_tree_path_free (path);
+
+		/* set package description */
+		//widget = GTK_WIDGET (gtk_builder_get_object (builder, "label_package"));
+		//gtk_label_set_label (GTK_LABEL (widget), item->summary);
+
+
+	} else if (type == PK_PROGRESS_TYPE_STATUS) {
+
+		GdkWindow *window;
+		const gchar *text;
+		GdkDisplay *display;
+		GdkCursor *cursor;
+
+		egg_debug ("status %s", pk_status_enum_to_text (status));
+
+		/* use correct status pane */
+		widget = GTK_WIDGET (gtk_builder_get_object (builder, "hbox_status"));
+		gtk_widget_show (widget);
+		widget = GTK_WIDGET (gtk_builder_get_object (builder, "hbox_info"));
+		gtk_widget_hide (widget);
+
+		/* set cursor back to normal */
+		window = gtk_widget_get_window (widget);
+		if (status == PK_STATUS_ENUM_FINISHED) {
+			gdk_window_set_cursor (window, NULL);
+		} else {
+			display = gdk_display_get_default ();
+			cursor = gdk_cursor_new_for_display (display, GDK_WATCH);
+			gdk_window_set_cursor (window, cursor);
+			gdk_cursor_unref (cursor);
+		}
+
+		/* clear package */
+		if (status == PK_STATUS_ENUM_WAIT) {
+			widget = GTK_WIDGET (gtk_builder_get_object (builder, "label_package"));
+			gtk_label_set_label (GTK_LABEL (widget), "");
+		}
+
+		/* set status */
+		widget = GTK_WIDGET (gtk_builder_get_object (builder, "label_status"));
+		if (status == PK_STATUS_ENUM_FINISHED) {
+			gtk_label_set_label (GTK_LABEL (widget), "");
+			widget = GTK_WIDGET (gtk_builder_get_object (builder, "image_progress"));
+			gtk_widget_hide (widget);
+			goto out;
+		}
+		if (status == PK_STATUS_ENUM_QUERY || status == PK_STATUS_ENUM_SETUP) {
+			/* TRANSLATORS: querying update array */
+			text = _("Getting the array of updates");
+		} else {
+			text = gpk_status_enum_to_localised_text (status);
+		}
+
+		/* set label */
+		gtk_label_set_label (GTK_LABEL (widget), text);
+		widget = GTK_WIDGET (gtk_builder_get_object (builder, "image_progress"));
+
+		/* set icon */
+		gtk_image_set_from_icon_name (GTK_IMAGE (widget), gpk_status_enum_to_icon_name (status), GTK_ICON_SIZE_BUTTON);
+		gtk_widget_show (widget);
+
+	} else if (type == PK_PROGRESS_TYPE_PERCENTAGE) {
+
+//		GtkWidget *widget;
+		GtkTreeView *treeview;
+		GtkTreeModel *model;
+		GtkTreeIter iter;
+		GtkTreePath *path;
+		guint oldval;
+		guint size;
+		guint size_display;
+
+		widget = GTK_WIDGET (gtk_builder_get_object (builder, "progressbar_progress"));
+		gtk_widget_show (widget);
+		if (percentage != -1)
+			gtk_progress_bar_set_fraction (GTK_PROGRESS_BAR (widget), (gfloat) percentage / 100.0);
+
+		treeview = GTK_TREE_VIEW (gtk_builder_get_object (builder, "treeview_updates"));
+		model = gtk_tree_view_get_model (treeview);
+
+		if (package_id_last == NULL) {
+			egg_debug ("no last package");
+			return;
+		}
+
+		path = gpk_update_viewer_model_get_path (model, package_id_last);
+		if (path == NULL) {
+			egg_debug ("not found ID for package");
+			return;
+		}
+
+		gtk_tree_model_get_iter (model, &iter, path);
+		gtk_tree_model_get (model, &iter,
+				    GPK_UPDATES_COLUMN_PERCENTAGE, &oldval,
+				    GPK_UPDATES_COLUMN_SIZE, &size,
+				    -1);
+		if ((oldval > 0 && oldval < 100) != (subpercentage > 0 && subpercentage < 100)) {
+			if (oldval > 0 && oldval < 100)
+				gpk_update_viewer_remove_active_row (model, path);
+			else
+				gpk_update_viewer_add_active_row (model, path);
+		}
+
+		size_display = size - ((size * subpercentage) / 100);
+		gtk_list_store_set (array_store_updates, &iter,
+				    GPK_UPDATES_COLUMN_PERCENTAGE, subpercentage,
+				    GPK_UPDATES_COLUMN_SIZE_DISPLAY, size_display,
+				    -1);
+
+		gtk_tree_path_free (path);
+
+	} else if (type == PK_PROGRESS_TYPE_ALLOW_CANCEL) {
+		widget = GTK_WIDGET (gtk_builder_get_object (builder, "button_quit"));
+		gtk_widget_set_sensitive (widget, allow_cancel);
+	}
+out:
+	g_free (package_id);
 }
 
 /**
- * gpk_update_viewer_package_cb:
+ * gpk_update_viewer_button_install_cb:
  **/
 static void
-gpk_update_viewer_package_cb (PkClient *client, const PkItemPackage *item, gpointer data)
+gpk_update_viewer_button_install_cb (GtkWidget *widget, gpointer data)
 {
-	PkInfoEnum info;
+	GtkWindow *window;
 	GtkTreeView *treeview;
-	GtkTreeIter iter;
 	GtkTreeModel *model;
-	GtkTreeViewColumn *column;
-	GtkTreePath *path;
-	gboolean scroll;
+	GtkTreeIter iter;
+	GtkTreeSelection *selection;
+	gboolean valid;
+	gboolean update;
+	gboolean selected_any = FALSE;
+	gchar *package_id;
+	GPtrArray *array = NULL;
+	gchar **package_ids = NULL;
+	PkInfoEnum info;
 
-	/* used for progress */
-	g_free (package_id_last);
-	package_id_last = pk_package_id_copy (item->package_id);
+	/* hide the upgrade viewbox from now on */
+	widget = GTK_WIDGET (gtk_builder_get_object (builder, "viewport_upgrade"));
+	gtk_widget_hide (widget);
+
+	egg_debug ("Doing the package updates");
+	array = g_ptr_array_new ();
 
-	/* find model */
 	treeview = GTK_TREE_VIEW (gtk_builder_get_object (builder, "treeview_updates"));
 	model = gtk_tree_view_get_model (treeview);
 
-	/* update icon */
-	path = gpk_update_viewer_model_get_path (model, item->package_id);
-	if (path == NULL) {
-		egg_debug ("not found ID for package");
-		goto out;
-	}
+	/* get the first iter in the array */
+	valid = gtk_tree_model_get_iter_first (model, &iter);
 
-	gtk_tree_model_get_iter (model, &iter, path);
+	/* find out how many we should update */
+	while (valid) {
+		gtk_tree_model_get (model, &iter,
+				    GPK_UPDATES_COLUMN_INFO, &info,
+				    GPK_UPDATES_COLUMN_SELECT, &update,
+				    GPK_UPDATES_COLUMN_ID, &package_id, -1);
+
+		/* set all the checkboxes insensitive */
+		gtk_list_store_set (array_store_updates, &iter,
+				    GPK_UPDATES_COLUMN_CLICKABLE, FALSE,
+				    GPK_UPDATES_COLUMN_SENSITIVE, FALSE, -1);
 
-	/* scroll to the active cell */
-	scroll = gconf_client_get_bool (gconf_client, GPK_CONF_UPDATE_VIEWER_SCROLL_ACTIVE, NULL);
-	if (scroll) {
-		column = gtk_tree_view_get_column (treeview, 3);
-		gtk_tree_view_scroll_to_cell (treeview, path, column, FALSE, 0.0f, 0.0f);
+		/* any selected? */
+		if (update)
+			selected_any = TRUE;
+
+		/* if selected, and not added previously because of deps */
+		if (update && info != PK_INFO_ENUM_AVAILABLE) {
+			g_ptr_array_add (array, package_id);
+		} else {
+			/* need to free the one in the array later */
+			g_free (package_id);
+		}
+		valid = gtk_tree_model_iter_next (model, &iter);
 	}
 
-	/* if the info is finished, change the status to past tense */
-	if (item->info == PK_INFO_ENUM_FINISHED) {
-		gtk_tree_model_get (model, &iter,
-				    GPK_UPDATES_COLUMN_STATUS, &info, -1);
-		/* promote to past tense if present tense */
-		if (info < PK_INFO_ENUM_UNKNOWN)
-			info += PK_INFO_ENUM_UNKNOWN;
-	} else {
-		info = item->info;
+	/* we have no checkboxes selected */
+	if (!selected_any) {
+		window = GTK_WINDOW (gtk_builder_get_object (builder, "dialog_updates"));
+		gpk_error_dialog_modal (window,
+					/* TRANSLATORS: we clicked apply, but had no packages selected */
+					_("No updates selected"),
+					_("No updates are selected"), NULL);
+		return;
 	}
-	gtk_list_store_set (array_store_updates, &iter,
-			    GPK_UPDATES_COLUMN_STATUS, info, -1);
 
-	gtk_tree_path_free (path);
+	/* disable button */
+	widget = GTK_WIDGET (gtk_builder_get_object (builder, "button_install"));
+	gtk_widget_set_sensitive (widget, FALSE);
 
-	/* set package description */
-	//widget = GTK_WIDGET (gtk_builder_get_object (builder, "label_package"));
-	//gtk_label_set_label (GTK_LABEL (widget), item->summary);
-out:
-	return;
+	/* clear the selection */
+	selection = gtk_tree_view_get_selection (treeview);
+	gtk_tree_selection_unselect_all (selection);
+
+	/* save for finished */
+	package_ids = pk_ptr_array_to_strv (array);
+	g_strfreev (install_package_ids);
+	install_package_ids = g_strdupv (package_ids);
+
+	/* get packages that also have to be updated */
+	pk_task_update_packages_async (task, package_ids, cancellable,
+				       (PkProgressCallback) gpk_update_viewer_progress_cb, NULL,
+				       (GAsyncReadyCallback) gpk_update_viewer_update_packages_cb, loop);
+	g_strfreev (package_ids);
+
+	/* get rid of the array, and free the contents */
+	if (array != NULL)
+		g_ptr_array_unref (array);
 }
 
 /**
- * gpk_update_viewer_update_detail_cb:
+ * gpk_update_viewer_button_upgrade_cb:
  **/
 static void
-gpk_update_viewer_update_detail_cb (PkClient *client, const PkItemUpdateDetail *item, gpointer data)
+gpk_update_viewer_button_upgrade_cb (GtkWidget *widget, gpointer data)
 {
-	GtkTreeView *treeview;
-	GtkTreeModel *model;
-	GtkTreeIter iter;
-	GtkTreePath *path;
-
-	treeview = GTK_TREE_VIEW (gtk_builder_get_object (builder, "treeview_updates"));
-	model = gtk_tree_view_get_model (treeview);
+	gboolean ret;
+	GError *error = NULL;
 
-	path = gpk_update_viewer_model_get_path (model, item->package_id);
-	if (path == NULL) {
-		egg_warning ("not found ID for update detail");
-		return;
+	ret = g_spawn_command_line_async ("/usr/share/PackageKit/pk-upgrade-distro.sh", NULL);
+	if (!ret) {
+		egg_warning ("Failure launching pk-upgrade-distro.sh: %s", error->message);
+		g_error_free (error);
 	}
-
-	gtk_tree_model_get_iter (model, &iter, path);
-	gtk_tree_path_free (path);
-	gtk_list_store_set (array_store_updates, &iter,
-			    GPK_UPDATES_COLUMN_UPDATE_DETAIL_OBJ, (gpointer) pk_update_detail_item_copy (item),
-			    GPK_UPDATES_COLUMN_RESTART, item->restart, -1);
 }
 
 /**
- * gpk_update_viewer_auto_shutdown:
+ * gpk_update_viewer_button_delete_event_cb:
  **/
 static gboolean
-gpk_update_viewer_auto_shutdown (GtkDialog *dialog)
+gpk_update_viewer_button_delete_event_cb (GtkWidget *widget, GdkEvent *event, gpointer data)
 {
-	gtk_dialog_response (dialog, GTK_RESPONSE_CANCEL);
-	auto_shutdown_id = 0;
-	return FALSE;
+	gpk_update_viewer_quit ();
+	return TRUE;
 }
 
 /**
@@ -751,69 +1057,6 @@ out:
 }
 
 /**
- * gpk_update_viewer_status_changed_cb:
- **/
-static void
-gpk_update_viewer_status_changed_cb (PkClient *client, PkStatusEnum status, gpointer data)
-{
-	GtkWidget *widget;
-	GdkWindow *window;
-	const gchar *text;
-	GdkDisplay *display;
-	GdkCursor *cursor;
-
-	egg_debug ("status %s", pk_status_enum_to_text (status));
-
-	/* use correct status pane */
-	widget = GTK_WIDGET (gtk_builder_get_object (builder, "hbox_status"));
-	gtk_widget_show (widget);
-	widget = GTK_WIDGET (gtk_builder_get_object (builder, "hbox_info"));
-	gtk_widget_hide (widget);
-
-	/* set cursor back to normal */
-	window = gtk_widget_get_window (widget);
-	if (status == PK_STATUS_ENUM_FINISHED) {
-		gdk_window_set_cursor (window, NULL);
-	} else {
-		display = gdk_display_get_default ();
-		cursor = gdk_cursor_new_for_display (display, GDK_WATCH);
-		gdk_window_set_cursor (window, cursor);
-		gdk_cursor_unref (cursor);
-	}
-
-	/* clear package */
-	if (status == PK_STATUS_ENUM_WAIT) {
-		widget = GTK_WIDGET (gtk_builder_get_object (builder, "label_package"));
-		gtk_label_set_label (GTK_LABEL (widget), "");
-	}
-
-	/* set status */
-	widget = GTK_WIDGET (gtk_builder_get_object (builder, "label_status"));
-	if (status == PK_STATUS_ENUM_FINISHED) {
-		gtk_label_set_label (GTK_LABEL (widget), "");
-		widget = GTK_WIDGET (gtk_builder_get_object (builder, "image_progress"));
-		gtk_widget_hide (widget);
-		goto out;
-	}
-	if (status == PK_STATUS_ENUM_QUERY || status == PK_STATUS_ENUM_SETUP) {
-		/* TRANSLATORS: querying update array */
-		text = _("Getting the array of updates");
-	} else {
-		text = gpk_status_enum_to_localised_text (status);
-	}
-
-	/* set label */
-	gtk_label_set_label (GTK_LABEL (widget), text);
-	widget = GTK_WIDGET (gtk_builder_get_object (builder, "image_progress"));
-
-	/* set icon */
-	gtk_image_set_from_icon_name (GTK_IMAGE (widget), gpk_status_enum_to_icon_name (status), GTK_ICON_SIZE_BUTTON);
-	gtk_widget_show (widget);
-out:
-	return;
-}
-
-/**
  * gpk_update_viewer_treeview_update_toggled:
  **/
 static void
@@ -1281,52 +1524,6 @@ gpk_packages_treeview_clicked_cb (GtkTreeSelection *selection, gpointer data)
 }
 
 /**
- * gpk_update_viewer_check_blocked_packages:
- **/
-static void
-gpk_update_viewer_check_blocked_packages (GPtrArray *array)
-{
-	guint i;
-	guint length;
-	const PkItemPackage *item;
-	GString *string;
-	gboolean exists = FALSE;
-	gchar *text;
-	GtkWindow *window;
-
-	string = g_string_new ("");
-
-	/* find any that are blocked */
-	for (i=0;i<array->len;i++) {
-		item = g_ptr_array_index (array, i);
-		if (item->info == PK_INFO_ENUM_BLOCKED) {
-			text = gpk_package_id_format_oneline (item->package_id, item->summary);
-			g_string_append_printf (string, "%s\n", text);
-			g_free (text);
-			exists = TRUE;
-		}
-	}
-
-	/* trim off extra newlines */
-	if (string->len != 0)
-		g_string_set_size (string, string->len-1);
-
-	/* convert to a normal gchar */
-	text = g_string_free (string, FALSE);
-
-	/* nothing of interest */
-	if (!exists)
-		goto out;
-
-	/* throw up dialog */
-	window = GTK_WINDOW (gtk_builder_get_object (builder, "dialog_updates"));
-	/* TRANSLATORS: we failed to install all the updates we requested */
-	gpk_error_dialog_modal (window, _("Some updates were not installed"), text, NULL);
-out:
-	g_free (text);
-}
-
-/**
  * gpk_update_viewer_get_details_cb:
  **/
 static void
@@ -1341,6 +1538,8 @@ gpk_update_viewer_get_details_cb (PkClient *client, GAsyncResult *res, GMainLoop
 	GtkTreePath *path;
 	GtkTreeModel *model;
 	GtkTreeSelection *selection;
+	GtkTreeView *treeview;
+	GtkTreeIter iter;
 
 	/* get the results */
 	results = pk_client_generic_finish (client, res, &error);
@@ -1350,10 +1549,31 @@ gpk_update_viewer_get_details_cb (PkClient *client, GAsyncResult *res, GMainLoop
 		goto out;
 	}
 
+	treeview = GTK_TREE_VIEW (gtk_builder_get_object (builder, "treeview_updates"));
+	model = gtk_tree_view_get_model (treeview);
+
 	/* get data */
 	array = pk_results_get_details_array (results);
 	for (i=0; i<array->len; i++) {
 		item = g_ptr_array_index (array, i);
+
+		path = gpk_update_viewer_model_get_path (model, item->package_id);
+		if (path == NULL) {
+			egg_debug ("not found ID for details");
+			return;
+		}
+
+		gtk_tree_model_get_iter (model, &iter, path);
+		gtk_tree_path_free (path);
+		gtk_list_store_set (array_store_updates, &iter,
+				    GPK_UPDATES_COLUMN_DETAILS_OBJ, (gpointer) pk_item_details_ref (item),
+				    GPK_UPDATES_COLUMN_SIZE, (gint)item->size,
+				    GPK_UPDATES_COLUMN_SIZE_DISPLAY, (gint)item->size,
+				    -1);
+		/* in cache */
+		if (item->size == 0)
+			gtk_list_store_set (array_store_updates, &iter,
+					    GPK_UPDATES_COLUMN_STATUS, GPK_INFO_ENUM_DOWNLOADED, -1);
 	}
 
 	/* select the first entry in the updates array now we've got data */
@@ -1374,16 +1594,20 @@ out:
 }
 
 /**
- * gpk_update_viewer_get_update_details_cb:
+ * gpk_update_viewer_get_update_detail_cb:
  **/
 static void
-gpk_update_viewer_get_update_details_cb (PkClient *client, GAsyncResult *res, GMainLoop *_loop)
+gpk_update_viewer_get_update_detail_cb (PkClient *client, GAsyncResult *res, GMainLoop *_loop)
 {
 	PkResults *results;
 	GError *error = NULL;
 	GPtrArray *array = NULL;
 	PkItemUpdateDetail *item;
 	guint i;
+	GtkTreeView *treeview;
+	GtkTreeModel *model;
+	GtkTreeIter iter;
+	GtkTreePath *path;
 
 	/* get the results */
 	results = pk_client_generic_finish (client, res, &error);
@@ -1394,11 +1618,23 @@ gpk_update_viewer_get_update_details_cb (PkClient *client, GAsyncResult *res, GM
 	}
 
 	/* get data */
+	treeview = GTK_TREE_VIEW (gtk_builder_get_object (builder, "treeview_updates"));
+	model = gtk_tree_view_get_model (treeview);
 	array = pk_results_get_update_detail_array (results);
 	for (i=0; i<array->len; i++) {
 		item = g_ptr_array_index (array, i);
-	}
+		path = gpk_update_viewer_model_get_path (model, item->package_id);
+		if (path == NULL) {
+			egg_warning ("not found ID for update detail");
+			continue;
+		}
 
+		gtk_tree_model_get_iter (model, &iter, path);
+		gtk_tree_path_free (path);
+		gtk_list_store_set (array_store_updates, &iter,
+				    GPK_UPDATES_COLUMN_UPDATE_DETAIL_OBJ, (gpointer) pk_item_update_detail_ref (item),
+				    GPK_UPDATES_COLUMN_RESTART, item->restart, -1);
+	}
 out:
 	if (array != NULL)
 		g_ptr_array_unref (array);
@@ -1406,100 +1642,13 @@ out:
 		g_object_unref (results);
 }
 
-/**
- * gpk_update_viewer_check_restart:
- **/
-static gboolean
-gpk_update_viewer_check_restart (PkRestartEnum restart)
-{
-	GtkWindow *window;
-	GtkWidget *dialog;
-	gboolean ret = FALSE;
-	const gchar *title;
-	const gchar *message;
-	const gchar *button;
-	GtkResponseType response;
-	gboolean show_button = TRUE;
-
-	/* get the text */
-	title = gpk_restart_enum_to_localised_text (restart);
-	if (restart == PK_RESTART_ENUM_SYSTEM) {
-		/* TRANSLATORS: the message text for the restart */
-		message = _("Some of the updates that were installed require the computer to be restarted before the changes will be applied.");
-		/* TRANSLATORS: the button text for the restart */
-		button = _("Restart Computer");
-
-	} else if (restart == PK_RESTART_ENUM_SECURITY_SYSTEM) {
-		/* TRANSLATORS: the message text for the restart */
-		message = _("Some of the updates that were installed require the computer to be restarted to remain secure.");
-		/* TRANSLATORS: the button text for the restart */
-		button = _("Restart Computer");
-
-	} else if (restart == PK_RESTART_ENUM_SESSION) {
-		/* TRANSLATORS: the message text for the logout */
-		message = _("Some of the updates that were installed require you to log out and back in before the changes will be applied.");
-		/* TRANSLATORS: the button text for the logout */
-		button = _("Log Out");
-
-	} else if (restart == PK_RESTART_ENUM_SECURITY_SESSION) {
-		/* TRANSLATORS: the message text for the logout */
-		message = _("Some of the updates that were installed require you to log out and back in to remain secure.");
-		/* TRANSLATORS: the button text for the logout */
-		button = _("Log Out");
-
-	} else {
-		egg_warning ("unknown restart enum");
-		goto out;
-	}
-
-	/* show modal dialog */
-	window = GTK_WINDOW (gtk_builder_get_object (builder, "dialog_updates"));
-	dialog = gtk_message_dialog_new (window, GTK_DIALOG_MODAL,
-					 GTK_MESSAGE_INFO, GTK_BUTTONS_CLOSE,
-					 "%s", title);
-
-	/* check to see if restart is possible */
-	if (restart == PK_RESTART_ENUM_SYSTEM ||
-	    restart == PK_RESTART_ENUM_SECURITY_SYSTEM) {
-		egg_console_kit_can_restart (console, &show_button, NULL);
-	}
-
-	/* only show the button if we can do the action */
-	if (show_button)
-		gtk_dialog_add_button (GTK_DIALOG (dialog), button, GTK_RESPONSE_OK);
-	gtk_message_dialog_format_secondary_text (GTK_MESSAGE_DIALOG(dialog), "%s", message);
-	gtk_window_set_icon_name (GTK_WINDOW(dialog), GPK_ICON_SOFTWARE_INSTALLER);
-
-	/* setup a callback so we autoclose */
-	auto_shutdown_id = g_timeout_add_seconds (GPK_UPDATE_VIEWER_AUTO_RESTART_TIMEOUT, (GSourceFunc) gpk_update_viewer_auto_shutdown, dialog);
-
-	response = gtk_dialog_run (GTK_DIALOG(dialog));
-	gtk_widget_destroy (dialog);
-
-	/* cancel */
-	if (response != GTK_RESPONSE_OK)
-		goto out;
-
-	/* doing the action, return success */
-	ret = TRUE;
-
-	/* do the action */
-	if (restart == PK_RESTART_ENUM_SYSTEM)
-		gpk_update_viewer_shutdown ();
-	else if (restart == PK_RESTART_ENUM_SESSION)
-		gpk_update_viewer_logout ();
-out:
-	return ret;
-}
-
+#if 0
 /**
  * gpk_update_viewer_deps_update_event_cb:
  **/
 static void
 gpk_update_viewer_deps_update_event_cb (gpointer *helper, GtkResponseType type, GPtrArray *deps_array, gpointer data)
 {
-	gboolean ret;
-	GError *error = NULL;
 	GtkTreeView *treeview;
 	GtkTreeModel *model;
 	gboolean valid;
@@ -1536,7 +1685,7 @@ gpk_update_viewer_deps_update_event_cb (gpointer *helper, GtkResponseType type,
 
 			/* we found a match */
 			if (g_strcmp0 (package_id_temp, item->package_id)) {
-				egg_debug ("selecting %s", id->name);
+				egg_debug ("selecting %s", item->package_id);
 				gtk_list_store_set (GTK_LIST_STORE (model), &iter,
 						    GPK_UPDATES_COLUMN_SELECT, TRUE, -1);
 				found = TRUE;
@@ -1575,12 +1724,14 @@ gpk_update_viewer_deps_update_event_cb (gpointer *helper, GtkResponseType type,
 
 	/* actually install packages this time */
 	pk_task_update_packages_async (task, install_package_ids, cancellable,
-					 NULL, NULL,
-					(GAsyncReadyCallback) gpk_update_viewer_update_packages_cb, loop);
+				       (PkProgressCallback) gpk_update_viewer_progress_cb, NULL,
+				       (GAsyncReadyCallback) gpk_update_viewer_update_packages_cb, loop);
 out:
 	return;
 }
+#endif
 
+#if 0
 /**
  * gpk_update_viewer_finished_cb:
  **/
@@ -1588,13 +1739,9 @@ static void
 gpk_update_viewer_finished_cb (PkClient *client, PkExitEnum exit, guint runtime, gpointer data)
 {
 	GtkWidget *widget;
-	GtkWidget *dialog;
 	GtkTreeView *treeview;
 	GtkTreeModel *model;
 	PkRoleEnum role;
-	GPtrArray *array;
-	PkRestartEnum restart;
-	gchar *text;
 
 	/* clear package */
 	widget = GTK_WIDGET (gtk_builder_get_object (builder, "label_package"));
@@ -1624,88 +1771,6 @@ gpk_update_viewer_finished_cb (PkClient *client, PkExitEnum exit, guint runtime,
 			gpk_update_viewer_undisable_packages ();
 	}
 
-	/* check if we need to display infomation about blocked packages */
-	if (exit == PK_EXIT_ENUM_SUCCESS &&
-	    (role == PK_ROLE_ENUM_UPDATE_SYSTEM ||
-	     role == PK_ROLE_ENUM_UPDATE_PACKAGES)) {
-
-		/* TODO: use ca_gtk_context_get_for_screen to allow use of GDK_MULTIHEAD_SAFE */
-
-		/* play the sound, using sounds from the naming spec */
-		ca_context_play (ca_gtk_context_get (), 0,
-				 /* TODO: add a new sound to the spec */
-				 CA_PROP_EVENT_ID, "complete-download",
-				 /* TRANSLATORS: this is the application name for libcanberra */
-				 CA_PROP_APPLICATION_NAME, _("GNOME PackageKit Update Viewer"),
-				 /* TRANSLATORS: this is the sound description */
-				 CA_PROP_EVENT_DESCRIPTION, _("Updated successfully"), NULL);
-
-		/* get the worst restart case */
-		restart = pk_client_get_require_restart (PK_CLIENT(task));
-		if (restart > restart_update)
-			restart_update = restart;
-
-		/* check blocked */
-		array = pk_results_get_package_array (results);
-		gpk_update_viewer_check_blocked_packages (array);
-		g_ptr_array_unref (array);
-
-		/* check restart */
-		if (restart_update == PK_RESTART_ENUM_SYSTEM ||
-		    restart_update == PK_RESTART_ENUM_SESSION ||
-		    restart_update == PK_RESTART_ENUM_SECURITY_SESSION ||
-		    restart_update == PK_RESTART_ENUM_SECURITY_SYSTEM) {
-			gpk_update_viewer_check_restart (restart_update);
-			g_main_loop_quit (loop);
-		}
-
-		/* hide close button */
-		widget = GTK_WIDGET (gtk_builder_get_object (builder, "button_quit"));
-		gtk_widget_hide (widget);
-
-		/* show a new title */
-		widget = GTK_WIDGET (gtk_builder_get_object (builder, "label_header_title"));
-		/* TRANSLATORS: completed all updates */
-		text = g_strdup_printf ("<big><b>%s</b></big>", _("All selected updates installed..."));
-		gtk_label_set_label (GTK_LABEL (widget), text);
-		g_free (text);
-
-		/* show modal dialog */
-		widget = GTK_WIDGET (gtk_builder_get_object (builder, "dialog_updates"));
-		dialog = gtk_message_dialog_new (GTK_WINDOW (widget), GTK_DIALOG_MODAL,
-						 GTK_MESSAGE_INFO, GTK_BUTTONS_OK,
-						 /* TRANSLATORS: title: all updates installed okay */
-						 "%s", _("All selected updates installed"));
-		gtk_message_dialog_format_secondary_text (GTK_MESSAGE_DIALOG(dialog),
-							  "%s",
-							  /* TRANSLATORS: software updates installed okay */
-							  _("All selected updates were successfully installed."));
-		gtk_window_set_icon_name (GTK_WINDOW(dialog), GPK_ICON_SOFTWARE_INSTALLER);
-
-		/* setup a callback so we autoclose */
-		auto_shutdown_id = g_timeout_add_seconds (GPK_UPDATE_VIEWER_AUTO_RESTART_TIMEOUT, (GSourceFunc) gpk_update_viewer_auto_shutdown, dialog);
-
-		gtk_dialog_run (GTK_DIALOG(dialog));
-		gtk_widget_destroy (dialog);
-
-		/* quit after we successfully updated */
-		g_main_loop_quit (loop);
-	}
-
-	/* failed sound */
-	if (exit != PK_EXIT_ENUM_SUCCESS &&
-	    (role == PK_ROLE_ENUM_UPDATE_SYSTEM ||
-	     role == PK_ROLE_ENUM_UPDATE_PACKAGES)) {
-
-		/* play the sound, using sounds from the naming spec */
-		ca_context_play (ca_gtk_context_get (), 0,
-				 CA_PROP_EVENT_ID, "dialog-warning",
-				 /* TRANSLATORS: this is the application name for libcanberra */
-				 CA_PROP_APPLICATION_NAME, _("GNOME PackageKit Update Viewer"),
-				 /* TRANSLATORS: this is the sound description */
-				 CA_PROP_EVENT_DESCRIPTION, _("Failed to update"), NULL);
-	}
-
 	/* we pressed cancel */
 	if (exit != PK_EXIT_ENUM_SUCCESS) {
 		gpk_update_viewer_undisable_packages ();
@@ -1713,165 +1778,9 @@ gpk_update_viewer_finished_cb (PkClient *client, PkExitEnum exit, guint runtime,
 		gtk_widget_set_sensitive (widget, TRUE);
 	}
 }
+#endif
 
-static GSList *active_rows = NULL;
-static guint active_row_timeout = 0;
-
-/**
- * gpk_update_viewer_compare_refs:
- **/
-static gint
-gpk_update_viewer_compare_refs (GtkTreeRowReference *a, GtkTreeRowReference *b)
-{
-	GtkTreeModel *am, *bm;
-	GtkTreePath *ap, *bp;
-	gint res;
-
-	am = gtk_tree_row_reference_get_model (a);
-	bm = gtk_tree_row_reference_get_model (b);
-
-	res = 1;
-	if (am == bm) {
-		ap = gtk_tree_row_reference_get_path (a);
-		bp = gtk_tree_row_reference_get_path (b);
-
-		res = gtk_tree_path_compare (ap, bp);
-
-		gtk_tree_path_free (ap);
-		gtk_tree_path_free (bp);
-	}
-
-	return res;
-}
-
-/**
- * gpk_update_viewer_pulse_active_rows:
- **/
-static gboolean
-gpk_update_viewer_pulse_active_rows (void)
-{
-	GSList *l;
-	GtkTreeRowReference *ref;
-	GtkTreeModel *model;
-	GtkTreePath *path;
-	GtkTreeIter iter;
-	gint val;
-
-	for (l = active_rows; l; l = l->next) {
-		ref = l->data;
-		model = gtk_tree_row_reference_get_model (ref);
-		path = gtk_tree_row_reference_get_path (ref);
-		if (path) {
-			gtk_tree_model_get_iter (model, &iter, path);
-			gtk_tree_model_get (model, &iter, GPK_UPDATES_COLUMN_PULSE, &val, -1);
-			gtk_list_store_set (GTK_LIST_STORE (model), &iter, GPK_UPDATES_COLUMN_PULSE, val + 1, -1);
-			gtk_tree_path_free (path);
-		}
-	}
-
-	return TRUE;
-}
-
-/**
- * gpk_update_viewer_add_active_row:
- **/
-static void
-gpk_update_viewer_add_active_row (GtkTreeModel *model, GtkTreePath *path)
-{
-	GtkTreeRowReference *ref;
-
-	if (!active_row_timeout) {
-		active_row_timeout = g_timeout_add (60, (GSourceFunc)gpk_update_viewer_pulse_active_rows, NULL);
-	}
-
-	ref = gtk_tree_row_reference_new (model, path);
-	active_rows = g_slist_prepend (active_rows, ref);
-}
-
-/**
- * gpk_update_viewer_remove_active_row:
- **/
-static void
-gpk_update_viewer_remove_active_row (GtkTreeModel *model, GtkTreePath *path)
-{
-	GSList *link;
-	GtkTreeRowReference *ref;
-	GtkTreeIter iter;
-
-	gtk_tree_model_get_iter (model, &iter, path);
-	gtk_list_store_set (GTK_LIST_STORE (model), &iter, GPK_UPDATES_COLUMN_PULSE, -1, -1);
-
-	ref = gtk_tree_row_reference_new (model, path);
-	link = g_slist_find_custom (active_rows, (gconstpointer)ref, (GCompareFunc)gpk_update_viewer_compare_refs);
-	gtk_tree_row_reference_free (ref);
-	g_assert (link);
-
-	active_rows = g_slist_remove_link (active_rows, link);
-	gtk_tree_row_reference_free (link->data);
-	g_slist_free (link);
-
-	if (active_rows == NULL) {
-		g_source_remove (active_row_timeout);
-		active_row_timeout = 0;
-	}
-}
-
-/**
- * gpk_update_viewer_progress_changed_cb:
- **/
-static void
-gpk_update_viewer_progress_changed_cb (PkClient *client, guint percentage, guint subpercentage,
-				       guint elapsed, guint remaining, gpointer data)
-{
-	GtkWidget *widget;
-	GtkTreeView *treeview;
-	GtkTreeModel *model;
-	GtkTreeIter iter;
-	GtkTreePath *path;
-	guint oldval;
-	guint size;
-	guint size_display;
-
-	widget = GTK_WIDGET (gtk_builder_get_object (builder, "progressbar_progress"));
-	gtk_widget_show (widget);
-	if (percentage != -1)
-		gtk_progress_bar_set_fraction (GTK_PROGRESS_BAR (widget), (gfloat) percentage / 100.0);
-
-	treeview = GTK_TREE_VIEW (gtk_builder_get_object (builder, "treeview_updates"));
-	model = gtk_tree_view_get_model (treeview);
-
-	if (package_id_last == NULL) {
-		egg_debug ("no last package");
-		return;
-	}
-
-	path = gpk_update_viewer_model_get_path (model, package_id_last);
-	if (path == NULL) {
-		egg_debug ("not found ID for package");
-		return;
-	}
-
-	gtk_tree_model_get_iter (model, &iter, path);
-	gtk_tree_model_get (model, &iter,
-			    GPK_UPDATES_COLUMN_PERCENTAGE, &oldval,
-			    GPK_UPDATES_COLUMN_SIZE, &size,
-			    -1);
-	if ((oldval > 0 && oldval < 100) != (subpercentage > 0 && subpercentage < 100)) {
-		if (oldval > 0 && oldval < 100)
-			gpk_update_viewer_remove_active_row (model, path);
-		else
-			gpk_update_viewer_add_active_row (model, path);
-	}
-
-	size_display = size - ((size * subpercentage) / 100);
-	gtk_list_store_set (array_store_updates, &iter,
-			    GPK_UPDATES_COLUMN_PERCENTAGE, subpercentage,
-			    GPK_UPDATES_COLUMN_SIZE_DISPLAY, size_display,
-			    -1);
-
-	gtk_tree_path_free (path);
-}
-
+#if 0
 /**
  * gpk_update_viewer_error_code_cb:
  **/
@@ -1880,23 +1789,11 @@ gpk_update_viewer_error_code_cb (PkClient *client, PkErrorCodeEnum code, const g
 {
 	GtkWindow *window;
 
-	/* ignore some errors */
-	if (code == PK_ERROR_ENUM_PROCESS_KILL ||
-	    code == PK_ERROR_ENUM_TRANSACTION_CANCELLED) {
-		egg_debug ("error ignored %s: %s", pk_error_enum_to_text (code), details);
-		return;
-	}
-
-	/* ignore not authorised, which seems odd but this will happen if the user clicks cancel */
-	if (code == PK_ERROR_ENUM_NOT_AUTHORIZED) {
-		egg_debug ("auth failure '%s' ignored: %s", pk_error_enum_to_text (code), details);
-		return;
-	}
-
 	window = GTK_WINDOW (gtk_builder_get_object (builder, "dialog_updates"));
 	gpk_error_dialog_modal (window, gpk_error_enum_to_localised_text (code),
 				gpk_error_enum_to_localised_message (code), details);
 }
+#endif
 
 /**
  * gpk_update_viewer_repo_array_changed_cb:
@@ -2134,6 +2031,24 @@ gpk_update_viewer_message_received_cb (UniqueApp *app, UniqueCommand command, Un
 }
 
 /**
+ * gpk_update_viewer_packages_to_ids:
+ **/
+static gchar **
+gpk_update_viewer_packages_to_ids (GPtrArray *array)
+{
+	guint i;
+	gchar **value;
+	PkItemPackage *item;
+
+	value = g_new0 (gchar *, array->len + 1);
+	for (i=0; i<array->len; i++) {
+		item = g_ptr_array_index (array, i);
+		value[i] = g_strdup (item->package_id);
+	}
+	return value;
+}
+
+/**
  * gpk_update_viewer_get_updates_cb:
  **/
 static void
@@ -2196,16 +2111,16 @@ gpk_update_viewer_get_updates_cb (PkClient *client, GAsyncResult *res, GMainLoop
 
 	/* get the download sizes */
 	if (update_array->len > 0) {
-		package_ids = pk_package_sack_get_ids (array);
+		package_ids = gpk_update_viewer_packages_to_ids (array);
 
 		/* get the details of all the packages */
 		pk_client_get_update_detail_async (PK_CLIENT(task), package_ids, cancellable,
-						   NULL, NULL,
-						   (GAsyncReadyCallback) gpk_update_viewer_get_details_cb, loop);
+						   (PkProgressCallback) gpk_update_viewer_progress_cb, NULL,
+						   (GAsyncReadyCallback) gpk_update_viewer_get_update_detail_cb, loop);
 
 		/* get the details of all the packages */
 		pk_client_get_details_async (PK_CLIENT(task), package_ids, cancellable,
-					     NULL, NULL,
+					     (PkProgressCallback) gpk_update_viewer_progress_cb, NULL,
 					     (GAsyncReadyCallback) gpk_update_viewer_get_details_cb, loop);
 
 		g_strfreev (package_ids);
@@ -2256,24 +2171,13 @@ gpk_update_viewer_get_new_update_array (void)
 
 	/* get new array */
 	pk_client_get_updates_async (PK_CLIENT(task), filter, cancellable,
-				     NULL, NULL,
+				     (PkProgressCallback) gpk_update_viewer_progress_cb, NULL,
 				     (GAsyncReadyCallback) gpk_update_viewer_get_updates_cb, loop);
 	g_free (text);
 	return ret;
 }
 
 /**
- * gpk_update_viewer_allow_cancel_cb:
- **/
-static void
-gpk_update_viewer_allow_cancel_cb (PkClient *client, gboolean allow_cancel, gpointer data)
-{
-	GtkWidget *widget;
-	widget = GTK_WIDGET (gtk_builder_get_object (builder, "button_quit"));
-	gtk_widget_set_sensitive (widget, allow_cancel);
-}
-
-/**
  * gpk_update_viewer_textview_follow_link:
  *
  * Looks at all tags covering the position of iter in the text view,
@@ -2561,6 +2465,56 @@ out:
 	if (results != NULL)
 		g_object_unref (results);
 }
+
+/**
+ * gpk_update_viewer_set_network_state:
+ **/
+static void
+gpk_update_viewer_set_network_state (PkNetworkEnum state)
+{
+	GtkWindow *window;
+	GtkWidget *dialog;
+	gboolean ret = TRUE;
+	gchar *text_size = NULL;
+	gchar *message = NULL;
+	GtkResponseType response;
+	guint size = 0;
+
+	/* not on wireless mobile */
+	if (state != PK_NETWORK_ENUM_MOBILE)
+		goto out;
+
+	/* not when small */
+	if (size < GPK_UPDATE_VIEWER_MOBILE_SMALL_SIZE)
+		goto out;
+
+	/* not when ignored */
+	ret = gconf_client_get_bool (gconf_client, GPK_CONF_UPDATE_VIEWER_MOBILE_BBAND, NULL);
+	if (!ret)
+		goto out;
+
+	/* show modal dialog */
+	window = GTK_WINDOW (gtk_builder_get_object (builder, "dialog_updates"));
+	dialog = gtk_message_dialog_new (window, GTK_DIALOG_MODAL,
+					 GTK_MESSAGE_INFO, GTK_BUTTONS_CANCEL,
+					 "%s", _("Detected wireless broadband connection"));
+
+	/* TRANSLATORS: this is the button text when we check if it's okay to download */
+	gtk_dialog_add_button (GTK_DIALOG (dialog), _("Update anyway"), GTK_RESPONSE_OK);
+	text_size = g_format_size_for_display (size_total);
+
+	/* TRANSLATORS, the %s is a size, e.g. 13.3Mb */
+	message = g_strdup_printf (_("Connectivity is being provided by wireless broadband, and it may be expensive to download %s."), text_size);
+	gtk_message_dialog_format_secondary_text (GTK_MESSAGE_DIALOG(dialog), "%s", message);
+	gpk_dialog_embed_do_not_show_widget (GTK_DIALOG (dialog), GPK_CONF_UPDATE_VIEWER_MOBILE_BBAND);
+	gtk_window_set_icon_name (GTK_WINDOW(dialog), GPK_ICON_SOFTWARE_INSTALLER);
+	response = gtk_dialog_run (GTK_DIALOG(dialog));
+	gtk_widget_destroy (dialog);
+out:
+	g_free (text_size);
+	g_free (message);
+}
+
 /**
  * gpk_update_viewer_get_properties_cb:
  **/
@@ -2571,6 +2525,7 @@ gpk_update_viewer_get_properties_cb (PkControl *_control, GAsyncResult *res, GMa
 	GError *error = NULL;
 	gboolean ret;
 	PkBitfield roles;
+	PkNetworkEnum state;
 
 	/* get the result */
 	ret = pk_control_get_properties_finish (control, res, &error);
@@ -2585,12 +2540,15 @@ gpk_update_viewer_get_properties_cb (PkControl *_control, GAsyncResult *res, GMa
 	/* get values */
 	g_object_get (control,
 		      "roles", &roles,
+		      "network-state", &state,
 		      NULL);
 
+	gpk_update_viewer_set_network_state (state);
+
 	/* get the distro-upgrades if we support it */
 	if (pk_bitfield_contain (roles, PK_ROLE_ENUM_GET_DISTRO_UPGRADES)) {
 		pk_client_get_distro_upgrades_async (PK_CLIENT(task), cancellable,
-						     NULL, NULL,
+						     (PkProgressCallback) gpk_update_viewer_progress_cb, NULL,
 						     (GAsyncReadyCallback) gpk_update_viewer_get_distro_upgrades_cb, loop);
 	}
 out:
@@ -2598,6 +2556,21 @@ out:
 }
 
 /**
+ * gpk_update_viewer_notify_network_state_cb:
+ **/
+static void
+gpk_update_viewer_notify_network_state_cb (PkControl *control_, GParamSpec *pspec, gpointer user_data)
+{
+	PkNetworkEnum state;
+
+	/* show icon? */
+	g_object_get (control,
+		      "network-state", &state,
+		      NULL);
+	gpk_update_viewer_set_network_state (state);
+}
+
+/**
  * main:
  **/
 int
@@ -2683,6 +2656,8 @@ main (int argc, char *argv[])
 			  G_CALLBACK (gpk_update_viewer_repo_array_changed_cb), NULL);
 	g_signal_connect (control, "updates-changed",
 			  G_CALLBACK (gpk_update_viewer_updates_changed_cb), NULL);
+	g_signal_connect (control, "notify::network-state",
+			  G_CALLBACK (gpk_update_viewer_notify_network_state_cb), NULL);
 
 	/* this is what we use mainly */
 	task = PK_TASK(gpk_task_new ());



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]