[evince/294-cannot-select-default-option-in-form-drop-down-box] ev-view: fix ComboBoxText user selected item's logic



commit 976f74a354d6ea9b6de8b5999b65168add2c780a
Author: Nelson Benítez León <nbenitezl gmail com>
Date:   Sun Oct 28 13:01:26 2018 +0500

    ev-view: fix ComboBoxText user selected item's logic
    
    so that:
    
     - we don't force the first item as default, i.e.
       permit the user to dismiss the dialog without
       select any option.
    
     - detect when user didn't select any option or
       selected the already active option, as we also
       need to remove combobox in those cases. This both
       cases couldn't be detected with GtkComboBox "changed"
       signal, that's why we have to use "notify::popup-shown"
       for that.
    
      Fixes issue #294

 libview/ev-view.c | 61 +++++++++++++++++++++++++++++++++++++++++++++++--------
 1 file changed, 52 insertions(+), 9 deletions(-)
---
diff --git a/libview/ev-view.c b/libview/ev-view.c
index 219ee9f9..5a28ffca 100644
--- a/libview/ev-view.c
+++ b/libview/ev-view.c
@@ -2573,8 +2573,8 @@ ev_view_form_field_choice_changed (GtkWidget   *widget,
                gint item;
                
                item = gtk_combo_box_get_active (GTK_COMBO_BOX (widget));
-               if (!field_choice->selected_items ||
-                   GPOINTER_TO_INT (field_choice->selected_items->data) != item) {
+               if (item != -1 && (!field_choice->selected_items ||
+                   GPOINTER_TO_INT (field_choice->selected_items->data) != item)) {
                        g_list_free (field_choice->selected_items);
                        field_choice->selected_items = NULL;
                        field_choice->selected_items = g_list_prepend (field_choice->selected_items,
@@ -2622,6 +2622,51 @@ ev_view_form_field_choice_changed (GtkWidget   *widget,
        }
 }
 
+typedef struct _PopupShownData {
+       GtkWidget   *choice;
+       EvFormField *field;
+       EvView      *view;
+} PopupShownData;
+
+static gboolean
+ev_view_form_field_choice_popup_shown_real (PopupShownData *data)
+{
+       ev_view_form_field_choice_changed (data->choice, data->field);
+       ev_view_form_field_destroy (data->choice, data->view);
+
+       g_object_unref (data->choice);
+       g_object_unref (data->field);
+       g_free (data);
+
+       return FALSE;
+}
+
+static void
+ev_view_form_field_choice_popup_shown_cb (GObject    *self,
+                                         GParamSpec *pspec,
+                                         EvView     *view)
+{
+       EvFormField *field;
+       GtkWidget *choice;
+       gboolean shown;
+       PopupShownData *data;
+
+       g_object_get (self, "popup-shown", &shown, NULL);
+       if (shown)
+               return; /* popup is already opened */
+
+       /* Popup has been closed */
+       field = g_object_get_data (self, "form-field");
+       choice = GTK_WIDGET (self);
+
+       data = g_new0 (PopupShownData, 1);
+       data->choice = g_object_ref (choice);
+       data->field = g_object_ref (field);
+       data->view = view;
+       /* We need to use an idle here because combobox "active" item is not updated yet */
+       g_idle_add ((GSourceFunc) ev_view_form_field_choice_popup_shown_real, (gpointer) data);
+}
+
 static GtkWidget *
 ev_view_form_field_choice_create_widget (EvView      *view,
                                         EvFormField *field)
@@ -2630,7 +2675,7 @@ ev_view_form_field_choice_create_widget (EvView      *view,
        GtkWidget         *choice;
        GtkTreeModel      *model;
        gint               n_items, i;
-       gint               selected_item = 0;
+       gint               selected_item = -1;
 
        n_items = ev_document_forms_form_field_choice_get_n_items (EV_DOCUMENT_FORMS (view->document),
                                                                   field);
@@ -2729,12 +2774,10 @@ ev_view_form_field_choice_create_widget (EvView      *view,
                gtk_combo_box_set_active (GTK_COMBO_BOX (choice), selected_item);
                gtk_combo_box_popup (GTK_COMBO_BOX (choice));
                
-               g_signal_connect (choice, "changed",
-                                 G_CALLBACK (ev_view_form_field_choice_changed),
-                                 field);
-               g_signal_connect_after (choice, "changed",
-                                       G_CALLBACK (ev_view_form_field_destroy),
-                                       view);
+               /* See issue #294 for why we use this instead of "changed" signal */
+               g_signal_connect (choice, "notify::popup-shown",
+                                 G_CALLBACK (ev_view_form_field_choice_popup_shown_cb),
+                                 view);
        }
 
        g_object_unref (model);


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