[gnome-software] Add a selection bar



commit e955a493e021b0030f09193bfd5efaaa80013bad
Author: Matthias Clasen <mclasen redhat com>
Date:   Wed Nov 13 20:39:29 2013 -0500

    Add a selection bar
    
    When the installed list is in selection mode, show a bottom bar
    that allows to bring up the app folder dialog.

 src/gnome-software.ui    |   92 ++++++++++++++++++++++++++++++-----
 src/gs-shell-installed.c |  122 ++++++++++++++++++++++++++++++++++++++++++++-
 2 files changed, 199 insertions(+), 15 deletions(-)
---
diff --git a/src/gnome-software.ui b/src/gnome-software.ui
index a5410d8..c2ac09b 100644
--- a/src/gnome-software.ui
+++ b/src/gnome-software.ui
@@ -2,10 +2,25 @@
 <!-- Generated with glade 3.15.2 on Thu Aug 15 17:13:59 2013 -->
 <interface>
   <!-- interface-requires gtk+ 3.10 -->
+  <object class="GtkMenu" id="header_selection_menu">
+    <property name="visible">True</property>
+    <child>
+      <object class="GtkMenuItem" id="select_all_menuitem">
+        <property name="visible">True</property>
+        <property name="label" translatable="yes">Select All</property>
+      </object>
+    </child>
+    <child>
+      <object class="GtkMenuItem" id="select_none_menuitem">
+        <property name="visible">True</property>
+        <property name="label" translatable="yes">Select None</property>
+      </object>
+    </child>
+  </object>
   <object class="GtkImage" id="button_select_image">
     <property name="visible">True</property>
-    <property name="icon_name">object-select-symbolic</property>
     <property name="icon_size">0</property>
+    <property name="icon_name">object-select-symbolic</property> 
   </object>
   <object class="GtkApplicationWindow" id="window_software">
     <property name="can_focus">False</property>
@@ -130,6 +145,36 @@
                     <property name="position">1</property>
                   </packing>
                 </child>
+                <child>
+                  <object class="GtkMenuButton" id="header_selection_menu_button">
+                   <property name="popup">header_selection_menu</property>
+                   <style>
+                      <class name="selection-menu"/>
+                    </style>
+                    <child>
+                      <object class="GtkBox" id="header_selection_box">
+                        <property name="visible">True</property>
+                        <property name="spacing">6</property>
+                        <child>
+                          <object class="GtkLabel" id="header_selection_label">
+                            <property name="visible">True</property>
+                          </object>
+                        </child>
+                        <child>
+                          <object class="GtkArrow" id="header_selection_arrow">
+                            <property name="visible">True</property>
+                            <property name="arrow_type">down</property>
+                          </object>
+                        </child>
+                      </object>
+                    </child>
+                  </object>
+                  <packing>
+                    <property name="expand">False</property>
+                    <property name="fill">True</property>
+                    <property name="position">2</property>
+                  </packing>
+                </child>
               </object>
             </child>
             <child>
@@ -188,7 +233,7 @@
               </packing>
             </child>
             <child>
-              <object class="GtkToggleButton" id="button_select">
+              <object class="GtkButton" id="button_select">
                 <property name="image">button_select_image</property>
                 <property name="can_focus">True</property>
               </object>
@@ -509,20 +554,43 @@
                   </packing>
                 </child>
                 <child>
-                  <object class="GtkScrolledWindow" id="scrolledwindow_install">
+                  <object class="GtkBox" id="box_install">
                     <property name="visible">True</property>
-                    <property name="can_focus">True</property>
-                    <property name="hscrollbar_policy">never</property>
-                    <property name="vscrollbar_policy">automatic</property>
-                    <property name="shadow_type">none</property>
-                    <style>
-                      <class name="main-scrolled-software"/>
-                    </style>
+                    <property name="orientation">vertical</property>
                     <child>
-                      <object class="GtkListBox" id="list_box_install">
+                      <object class="GtkScrolledWindow" id="scrolledwindow_install">
                         <property name="visible">True</property>
                         <property name="can_focus">True</property>
-                        <property name="selection_mode">none</property>
+                        <property name="hscrollbar_policy">never</property>
+                        <property name="vscrollbar_policy">automatic</property>
+                        <property name="vexpand">True</property>
+                        <property name="shadow_type">none</property>
+                        <style>
+                          <class name="main-scrolled-software"/>
+                        </style>
+                        <child>
+                          <object class="GtkListBox" id="list_box_install">
+                            <property name="visible">True</property>
+                            <property name="can_focus">True</property>
+                            <property name="selection_mode">none</property>
+                          </object>
+                        </child>
+                      </object>
+                    </child>
+                    <child>
+                      <object class="GtkRevealer" id="bottom_install">
+                        <property name="visible">True</property>
+                        <property name="transition-type">4</property>
+                        <child>
+                          <object class="GtkButton" id="button_folder_install">
+                            <property name="visible">True</property>
+                            <property name="label" translatable="yes">Application _Folders</property>
+                            <property name="use_underline">True</property>
+                            <property name="hexpand">True</property>
+                            <property name="halign">center</property>
+                            <property name="margin">10</property>
+                          </object>
+                        </child>
                       </object>
                     </child>
                   </object>
diff --git a/src/gs-shell-installed.c b/src/gs-shell-installed.c
index ad272bf..0dd95ba 100644
--- a/src/gs-shell-installed.c
+++ b/src/gs-shell-installed.c
@@ -30,6 +30,7 @@
 #include "gs-app.h"
 #include "gs-utils.h"
 #include "gs-app-widget.h"
+#include "gs-app-folder-dialog.h"
 
 #define INSTALL_DATE_QUEUED     (G_MAXUINT - 1)
 #define INSTALL_DATE_INSTALLING (G_MAXUINT - 2)
@@ -46,6 +47,7 @@ struct GsShellInstalledPrivate
        GtkBuilder              *builder;
        GCancellable            *cancellable;
        GtkListBox              *list_box_installed;
+       GtkRevealer             *bottom_bar;
        GtkSizeGroup            *sizegroup_image;
        GtkSizeGroup            *sizegroup_name;
        gboolean                 cache_valid;
@@ -558,14 +560,45 @@ gs_shell_installed_pending_apps_changed_cb (GsPluginLoader *plugin_loader,
 }
 
 static void
-selection_mode_cb (GtkToggleButton *button, GsShellInstalled *shell_installed)
+selection_mode_cb (GtkButton *button, GsShellInstalled *shell_installed)
 {
        GsShellInstalledPrivate *priv = shell_installed->priv;
        GList *children, *l;
        GtkWidget *row;
        GtkWidget *app_widget;
+       GtkWidget *header;
+       GtkWidget *widget;
+       GtkStyleContext *context;
        
-       priv->selection_mode = gtk_toggle_button_get_active (button);
+       priv->selection_mode = !priv->selection_mode;
+
+       header = GTK_WIDGET (gtk_builder_get_object (priv->builder, "header"));
+       context = gtk_widget_get_style_context (header);
+       if (priv->selection_mode) {
+               gtk_header_bar_set_show_close_button (GTK_HEADER_BAR (header), FALSE);
+               gtk_style_context_add_class (context, "selection-mode");
+               widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "button_select"));
+               gtk_button_set_image (GTK_BUTTON (widget), NULL);
+               gtk_button_set_label (GTK_BUTTON (widget), _("Cancel"));
+               gtk_widget_show (widget);
+               widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "buttonbox_main"));
+               gtk_widget_hide (widget);
+               widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "header_selection_menu_button"));
+               gtk_widget_show (widget);
+               widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "header_selection_label"));
+               gtk_label_set_label (GTK_LABEL (widget), _("Click on items to select them"));
+       } else {
+               gtk_header_bar_set_show_close_button (GTK_HEADER_BAR (header), TRUE);
+               gtk_style_context_remove_class (context, "selection-mode");
+               widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "button_select"));
+               gtk_button_set_image (GTK_BUTTON (widget), gtk_image_new_from_icon_name 
("object-select-symbolic", GTK_ICON_SIZE_MENU));
+               gtk_button_set_label (GTK_BUTTON (widget), NULL);
+               gtk_widget_show (widget);
+               widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "buttonbox_main"));
+               gtk_widget_show (widget);
+               widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "header_selection_menu_button"));
+               gtk_widget_hide (widget);
+       }
 
        children = gtk_container_get_children (GTK_CONTAINER (priv->list_box_installed));
        for (l = children; l; l = l->next) {
@@ -575,6 +608,72 @@ selection_mode_cb (GtkToggleButton *button, GsShellInstalled *shell_installed)
                                              priv->selection_mode);
        }
        g_list_free (children);
+
+       gtk_revealer_set_reveal_child (priv->bottom_bar, priv->selection_mode);
+}
+
+static GList *
+get_selected_apps (GsShellInstalled *shell_installed)
+{
+       GsShellInstalledPrivate *priv = shell_installed->priv;
+       GList *children, *l, *list;
+
+       list = NULL;
+       children = gtk_container_get_children (GTK_CONTAINER (priv->list_box_installed));
+       for (l = children; l; l = l->next) {
+               GtkListBoxRow *row = l->data;
+               GsAppWidget *app_widget = GS_APP_WIDGET (gtk_bin_get_child (GTK_BIN (row)));
+               if (gs_app_widget_get_selected (app_widget)) {
+                       list = g_list_prepend (list, gs_app_widget_get_app (app_widget));       
+               }
+       }
+       g_list_free (children);
+
+       return list;
+}
+
+static void
+show_folder_dialog (GtkButton *button, GsShellInstalled *shell_installed)
+{
+       GtkWidget *toplevel;
+       GtkWidget *dialog;
+       GList *apps;
+
+       toplevel = gtk_widget_get_toplevel (GTK_WIDGET (button));
+       apps = get_selected_apps (shell_installed);
+       dialog = gs_app_folder_dialog_new (GTK_WINDOW (toplevel), apps);
+       g_list_free (apps);
+       gtk_window_present (GTK_WINDOW (dialog));
+}
+
+static void
+select_all_cb (GtkMenuItem *item, GsShellInstalled *shell_installed)
+{
+       GsShellInstalledPrivate *priv = shell_installed->priv;
+       GList *children, *l;
+
+       children = gtk_container_get_children (GTK_CONTAINER (priv->list_box_installed));
+       for (l = children; l; l = l->next) {
+               GtkListBoxRow *row = l->data;
+               GsAppWidget *app_widget = GS_APP_WIDGET (gtk_bin_get_child (GTK_BIN (row)));
+               gs_app_widget_set_selected (app_widget, TRUE);
+       }
+       g_list_free (children);
+}
+
+static void
+select_none_cb (GtkMenuItem *item, GsShellInstalled *shell_installed)
+{
+       GsShellInstalledPrivate *priv = shell_installed->priv;
+       GList *children, *l;
+
+       children = gtk_container_get_children (GTK_CONTAINER (priv->list_box_installed));
+       for (l = children; l; l = l->next) {
+               GtkListBoxRow *row = l->data;
+               GsAppWidget *app_widget = GS_APP_WIDGET (gtk_bin_get_child (GTK_BIN (row)));
+               gs_app_widget_set_selected (app_widget, FALSE);
+       }
+       g_list_free (children);
 }
 
 /**
@@ -611,10 +710,27 @@ gs_shell_installed_setup (GsShellInstalled *shell_installed,
        gtk_list_box_set_sort_func (priv->list_box_installed,
                                    gs_shell_installed_sort_func,
                                    shell_installed, NULL);
+
+       priv->bottom_bar = GTK_REVEALER (gtk_builder_get_object (priv->builder, "bottom_install"));
+
+       widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "button_folder_install"));
+       g_signal_connect (widget, "clicked",
+                         G_CALLBACK (show_folder_dialog), shell_installed);
        
        widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "button_select"));
-       g_signal_connect (widget, "toggled",
+       g_signal_connect (widget, "clicked",
                          G_CALLBACK (selection_mode_cb), shell_installed);
+
+       widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "button_select"));
+       gtk_button_set_image (GTK_BUTTON (widget), gtk_image_new_from_icon_name ("object-select-symbolic", 
GTK_ICON_SIZE_MENU));
+       gtk_button_set_label (GTK_BUTTON (widget), NULL);
+
+       widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "select_all_menuitem"));
+       g_signal_connect (widget, "activate",
+                         G_CALLBACK (select_all_cb), shell_installed);
+       widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, "select_none_menuitem"));
+       g_signal_connect (widget, "activate",
+                         G_CALLBACK (select_none_cb), shell_installed);
 }
 
 /**


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