Implement combobox apis for GtkFileChooserNativePortal
https://bugzilla.gnome.org/show_bug.cgi?id=768499
This commit is contained in:
		| @ -55,7 +55,6 @@ typedef struct { | ||||
|   GDBusConnection *connection; | ||||
|   char *portal_handle; | ||||
|   guint portal_response_signal_id; | ||||
|   GDBusSignalCallback signal_callback; | ||||
|   gboolean modal; | ||||
|  | ||||
|   gboolean hidden; | ||||
| @ -86,73 +85,35 @@ filechooser_portal_data_free (FilechooserPortalData *data) | ||||
| } | ||||
|  | ||||
| static void | ||||
| one_file_response (GDBusConnection  *connection, | ||||
|                    const gchar      *sender_name, | ||||
|                    const gchar      *object_path, | ||||
|                    const gchar      *interface_name, | ||||
|                    const gchar      *signal_name, | ||||
|                    GVariant         *parameters, | ||||
|                    gpointer          user_data) | ||||
| response_cb (GDBusConnection  *connection, | ||||
|              const gchar      *sender_name, | ||||
|              const gchar      *object_path, | ||||
|              const gchar      *interface_name, | ||||
|              const gchar      *signal_name, | ||||
|              GVariant         *parameters, | ||||
|              gpointer          user_data) | ||||
| { | ||||
|   GtkFileChooserNative *self = user_data; | ||||
|   FilechooserPortalData *data = self->mode_data; | ||||
|   guint32 portal_response; | ||||
|   int gtk_response; | ||||
|   char *uri, *handle; | ||||
|   GVariant *response_data; | ||||
|  | ||||
|   g_variant_get (parameters, "(&ou&s@a{sv})", &handle, &portal_response, &uri, &response_data); | ||||
|  | ||||
|   if (data->portal_handle == NULL || | ||||
|       strcmp (handle, data->portal_handle) != 0) | ||||
|     return; | ||||
|  | ||||
|   g_slist_free_full (self->custom_files, g_object_unref); | ||||
|   self->custom_files = g_slist_prepend (NULL, g_file_new_for_uri (uri)); | ||||
|  | ||||
|   switch (portal_response) | ||||
|     { | ||||
|     case 0: | ||||
|       gtk_response = GTK_RESPONSE_OK; | ||||
|       break; | ||||
|     case 1: | ||||
|       gtk_response = GTK_RESPONSE_CANCEL; | ||||
|       break; | ||||
|     case 2: | ||||
|     default: | ||||
|       gtk_response = GTK_RESPONSE_DELETE_EVENT; | ||||
|       break; | ||||
|     } | ||||
|  | ||||
|   filechooser_portal_data_free (data); | ||||
|   self->mode_data = NULL; | ||||
|  | ||||
|   _gtk_native_dialog_emit_response (GTK_NATIVE_DIALOG (self), gtk_response); | ||||
| } | ||||
|  | ||||
| static void | ||||
| multi_file_response (GDBusConnection  *connection, | ||||
|                      const gchar      *sender_name, | ||||
|                      const gchar      *object_path, | ||||
|                      const gchar      *interface_name, | ||||
|                      const gchar      *signal_name, | ||||
|                      GVariant         *parameters, | ||||
|                      gpointer          user_data) | ||||
| { | ||||
|   GtkFileChooserNative *self = user_data; | ||||
|   FilechooserPortalData *data = self->mode_data; | ||||
|   guint32 portal_response; | ||||
|   int gtk_response; | ||||
|   char *handle; | ||||
|   char **uris; | ||||
|   const char **uris; | ||||
|   int i; | ||||
|   GVariant *response_data; | ||||
|   g_autoptr (GVariant) choices = NULL; | ||||
|  | ||||
|   g_variant_get (parameters, "(&ou^a&s@a{sv})", &handle, &portal_response, &uris, &response_data); | ||||
|   g_variant_get (parameters, "(u@a{sv})", &portal_response, &response_data); | ||||
|   g_variant_lookup (response_data, "uris", "^a&s", &uris); | ||||
|  | ||||
|   if (data->portal_handle == NULL || | ||||
|       strcmp (handle, data->portal_handle) != 0) | ||||
|     return; | ||||
|   choices = g_variant_lookup_value (response_data, "choices", G_VARIANT_TYPE ("a(ss)")); | ||||
|   if (choices) | ||||
|     for (i = 0; i < g_variant_n_children (choices); i++) | ||||
|       { | ||||
|         const char *id; | ||||
|         const char *selected; | ||||
|         g_variant_get_child (choices, i, "(&s&s)", &id, &selected); | ||||
|         gtk_file_chooser_set_choice (GTK_FILE_CHOOSER (self), id, selected); | ||||
|       } | ||||
|  | ||||
|   g_slist_free_full (self->custom_files, g_object_unref); | ||||
|   self->custom_files = NULL; | ||||
| @ -250,7 +211,7 @@ open_file_msg_cb (GObject *source_object, | ||||
|                                             data->portal_handle, | ||||
|                                             NULL, | ||||
|                                             G_DBUS_SIGNAL_FLAGS_NO_MATCH_RULE, | ||||
|                                             data->signal_callback, | ||||
|                                             response_cb, | ||||
|                                             self, NULL); | ||||
|     } | ||||
|  | ||||
| @ -275,6 +236,44 @@ get_filters (GtkFileChooser *self) | ||||
|   return g_variant_builder_end (&builder); | ||||
| } | ||||
|  | ||||
| static GVariant * | ||||
| gtk_file_chooser_native_choice_to_variant (GtkFileChooserNativeChoice *choice) | ||||
| { | ||||
|   GVariantBuilder choices; | ||||
|   int i; | ||||
|  | ||||
|   g_variant_builder_init (&choices, G_VARIANT_TYPE ("a(ss)")); | ||||
|   if (choice->options) | ||||
|     { | ||||
|       for (i = 0; choice->options[i]; i++) | ||||
|         g_variant_builder_add (&choices, "(&s&s)", choice->options[i], choice->option_labels[i]); | ||||
|     } | ||||
|  | ||||
|   return g_variant_new ("(&s&s@a(ss)&s)", | ||||
|                         choice->id, | ||||
|                         choice->label, | ||||
|                         g_variant_builder_end (&choices), | ||||
|                         choice->selected ? choice->selected : ""); | ||||
| } | ||||
|  | ||||
| static GVariant * | ||||
| serialize_choices (GtkFileChooserNative *self) | ||||
| { | ||||
|   GVariantBuilder builder; | ||||
|   GSList *l; | ||||
|  | ||||
|   g_variant_builder_init (&builder, G_VARIANT_TYPE ("a(ssa(ss)s)")); | ||||
|   for (l = self->choices; l; l = l->next) | ||||
|     { | ||||
|       GtkFileChooserNativeChoice *choice = l->data; | ||||
|  | ||||
|       g_variant_builder_add (&builder, "@(ssa(ss)s)", | ||||
|                              gtk_file_chooser_native_choice_to_variant (choice)); | ||||
|     } | ||||
|  | ||||
|   return g_variant_builder_end (&builder); | ||||
| } | ||||
|  | ||||
| gboolean | ||||
| gtk_file_chooser_native_portal_show (GtkFileChooserNative *self) | ||||
| { | ||||
| @ -312,11 +311,6 @@ gtk_file_chooser_native_portal_show (GtkFileChooserNative *self) | ||||
|   data->self = g_object_ref (self); | ||||
|   data->connection = connection; | ||||
|  | ||||
|   if (strcmp (method_name, "OpenFiles") == 0) | ||||
|     data->signal_callback = multi_file_response; | ||||
|   else | ||||
|     data->signal_callback = one_file_response; | ||||
|  | ||||
|   message = g_dbus_message_new_method_call ("org.freedesktop.portal.Desktop", | ||||
|                                             "/org/freedesktop/portal/desktop", | ||||
|                                             "org.freedesktop.portal.FileChooser", | ||||
| @ -336,7 +330,7 @@ gtk_file_chooser_native_portal_show (GtkFileChooserNative *self) | ||||
|   if (gtk_native_dialog_get_modal (GTK_NATIVE_DIALOG (self))) | ||||
|     data->modal = TRUE; | ||||
|  | ||||
|   if (data->modal && transient_for) | ||||
|   if (data->modal && transient_for != NULL) | ||||
|     { | ||||
|       data->grab_widget = gtk_invisible_new_for_screen (gtk_widget_get_screen (GTK_WIDGET (transient_for))); | ||||
|       gtk_grab_add (GTK_WIDGET (data->grab_widget)); | ||||
| @ -376,6 +370,10 @@ gtk_file_chooser_native_portal_show (GtkFileChooserNative *self) | ||||
|       g_free (path); | ||||
|     } | ||||
|  | ||||
|   if (GTK_FILE_CHOOSER_NATIVE (self)->choices) | ||||
|     g_variant_builder_add (&opt_builder, "{sv}", "choices", | ||||
|                            serialize_choices (GTK_FILE_CHOOSER_NATIVE (self))); | ||||
|  | ||||
|   g_dbus_message_set_body (message, | ||||
|                            g_variant_new ("(ss@a{sv})", | ||||
|                                           parent_window_str ? parent_window_str : "", | ||||
|  | ||||
		Reference in New Issue
	
	Block a user
	 Matthias Clasen
					Matthias Clasen