[gnome-shell] Adjust to gtk/mutter changes for Application API
- From: Ryan Lortie <ryanl src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-shell] Adjust to gtk/mutter changes for Application API
- Date: Wed, 18 Jan 2012 22:25:48 +0000 (UTC)
commit c5932c0f070a8969c7beafa420b2ebb58c3ee21f
Author: Ryan Lortie <desrt desrt ca>
Date: Tue Jan 17 15:13:47 2012 -0500
Adjust to gtk/mutter changes for Application API
https://bugzilla.gnome.org/show_bug.cgi?id=668118
src/shell-app.c | 263 ++++++++++---------------------------------------------
src/shell-app.h | 2 -
2 files changed, 47 insertions(+), 218 deletions(-)
---
diff --git a/src/shell-app.c b/src/shell-app.c
index a96b062..cc86091 100644
--- a/src/shell-app.c
+++ b/src/shell-app.c
@@ -40,13 +40,8 @@ typedef struct {
gboolean window_sort_stale : 1;
/* See GApplication documentation */
- gint name_watcher_id;
- gchar *dbus_name;
- GDBusProxy *app_proxy;
- GActionGroup *remote_actions;
- GMenuModel *remote_menu;
+ GDBusMenuModel *remote_menu;
GActionMuxer *muxer;
- GCancellable *dbus_cancellable;
} ShellAppRunningState;
/**
@@ -99,14 +94,8 @@ enum {
static guint shell_app_signals[LAST_SIGNAL] = { 0 };
static void create_running_state (ShellApp *app);
+static void setup_running_state (ShellApp *app, MetaWindow *window);
static void unref_running_state (ShellAppRunningState *state);
-static void on_dbus_name_appeared (GDBusConnection *bus,
- const gchar *name,
- const gchar *name_owner,
- gpointer user_data);
-static void on_dbus_name_disappeared (GDBusConnection *bus,
- const gchar *name,
- gpointer user_data);
G_DEFINE_TYPE (ShellApp, shell_app, G_TYPE_OBJECT)
@@ -126,9 +115,6 @@ shell_app_get_property (GObject *gobject,
case PROP_ID:
g_value_set_string (value, shell_app_get_id (app));
break;
- case PROP_DBUS_ID:
- g_value_set_string (value, shell_app_get_dbus_id (app));
- break;
case PROP_ACTION_GROUP:
if (app->running_state)
g_value_set_object (value, app->running_state->muxer);
@@ -186,15 +172,6 @@ window_backed_app_get_icon (ShellApp *app,
return actor;
}
-const char *
-shell_app_get_dbus_id (ShellApp *app)
-{
- if (app->running_state)
- return app->running_state->dbus_name;
- else
- return NULL;
-}
-
/**
* shell_app_create_icon_texture:
*
@@ -563,7 +540,7 @@ shell_app_update_window_actions (ShellApp *app, MetaWindow *window)
{
const char *object_path;
- object_path = meta_window_get_dbus_object_path (window);
+ object_path = meta_window_get_gtk_window_object_path (window);
if (object_path != NULL)
{
GActionGroup *actions;
@@ -572,7 +549,7 @@ shell_app_update_window_actions (ShellApp *app, MetaWindow *window)
if (actions == NULL)
{
actions = G_ACTION_GROUP (g_dbus_action_group_get (g_bus_get_sync (G_BUS_TYPE_SESSION, NULL, NULL),
- meta_window_get_dbus_unique_name (window),
+ meta_window_get_gtk_unique_bus_name (window),
object_path));
g_object_set_data_full (G_OBJECT (window), "actions", actions, g_object_unref);
}
@@ -975,34 +952,6 @@ shell_app_on_ws_switch (MetaScreen *screen,
g_signal_emit (app, shell_app_signals[WINDOWS_CHANGED], 0);
}
-static void
-on_dbus_application_id_changed (MetaWindow *window,
- GParamSpec *pspec,
- gpointer user_data)
-{
- const char *appid;
- ShellApp *app = SHELL_APP (user_data);
-
- /* Ignore changes in the appid after it's set, shouldn't happen */
- if (app->running_state->dbus_name != NULL)
- return;
-
- appid = meta_window_get_dbus_application_id (window);
-
- if (!appid)
- return;
-
- g_assert (app->running_state != NULL);
- app->running_state->dbus_name = g_strdup (appid);
- app->running_state->name_watcher_id = g_bus_watch_name (G_BUS_TYPE_SESSION,
- appid,
- G_BUS_NAME_WATCHER_FLAGS_NONE,
- on_dbus_name_appeared,
- on_dbus_name_disappeared,
- g_object_ref (app),
- g_object_unref);
-}
-
void
_shell_app_add_window (ShellApp *app,
MetaWindow *window)
@@ -1020,12 +969,11 @@ _shell_app_add_window (ShellApp *app,
g_signal_connect (window, "unmanaged", G_CALLBACK(shell_app_on_unmanaged), app);
g_signal_connect (window, "notify::user-time", G_CALLBACK(shell_app_on_user_time_changed), app);
+ setup_running_state (app, window);
+
if (app->state != SHELL_APP_STATE_STARTING)
shell_app_state_transition (app, SHELL_APP_STATE_RUNNING);
- g_signal_connect (window, "notify::dbus-application-id", G_CALLBACK(on_dbus_application_id_changed), app);
- on_dbus_application_id_changed (window, NULL, app);
-
g_object_thaw_notify (G_OBJECT (app));
g_signal_emit (app, shell_app_signals[WINDOWS_CHANGED], 0);
@@ -1042,7 +990,6 @@ _shell_app_remove_window (ShellApp *app,
g_signal_handlers_disconnect_by_func (window, G_CALLBACK(shell_app_on_unmanaged), app);
g_signal_handlers_disconnect_by_func (window, G_CALLBACK(shell_app_on_user_time_changed), app);
- g_signal_handlers_disconnect_by_func (window, G_CALLBACK(on_dbus_application_id_changed), app);
g_object_unref (window);
app->running_state->windows = g_slist_remove (app->running_state->windows, window);
@@ -1052,137 +999,6 @@ _shell_app_remove_window (ShellApp *app,
g_signal_emit (app, shell_app_signals[WINDOWS_CHANGED], 0);
}
-static void
-on_dbus_proxy_gotten (GObject *initable,
- GAsyncResult *result,
- gpointer user_data)
-{
- ShellApp *self = SHELL_APP (user_data);
- ShellAppRunningState *state = self->running_state;
- GError *error = NULL;
- GVariant *menu_property;
-
- state->app_proxy = g_dbus_proxy_new_finish (result,
- &error);
-
- if (error)
- {
- if (!g_error_matches (error, G_IO_ERROR, G_IO_ERROR_CANCELLED) &&
- !g_error_matches (error, G_DBUS_ERROR, G_DBUS_ERROR_UNKNOWN_METHOD))
- {
- g_warning ("Unexpected error while creating application proxy: %s", error->message);
- }
-
- g_clear_error (&error);
- g_clear_object (&state->dbus_cancellable);
-
- if (state->name_watcher_id)
- {
- g_bus_unwatch_name (state->name_watcher_id);
- state->name_watcher_id = 0;
- }
-
- g_free (state->dbus_name);
- state->dbus_name = NULL;
-
- g_object_unref (self);
- return;
- }
-
- /* on to the second step, the primary action group */
-
- state->remote_actions = (GActionGroup*)g_dbus_action_group_get (
- g_dbus_proxy_get_connection (state->app_proxy),
- g_dbus_proxy_get_name (state->app_proxy),
- g_dbus_proxy_get_object_path (state->app_proxy));
-
- if (!state->muxer)
- state->muxer = g_action_muxer_new ();
-
- g_action_muxer_insert (state->muxer, "app", state->remote_actions);
- g_strfreev (g_action_group_list_actions (state->remote_actions));
-
- g_object_notify (G_OBJECT (self), "action-group");
-
- menu_property = g_dbus_proxy_get_cached_property (state->app_proxy, "AppMenu");
-
- if (menu_property && g_variant_n_children (menu_property) > 0)
- {
- const gchar *object_path;
-
- g_variant_get_child (menu_property, 0, "&o", &object_path);
-
- state->remote_menu = G_MENU_MODEL (g_dbus_menu_model_get (g_dbus_proxy_get_connection (state->app_proxy),
- g_dbus_proxy_get_name (state->app_proxy),
- object_path));
-
- g_object_notify (G_OBJECT (self), "menu");
- }
-}
-
-static void
-on_dbus_name_appeared (GDBusConnection *bus,
- const gchar *name,
- const gchar *name_owner,
- gpointer user_data)
-{
- ShellApp *self = SHELL_APP (user_data);
- ShellAppRunningState *state = self->running_state;
- char *object_path;
-
- g_assert (state != NULL);
-
- object_path = g_strconcat ("/", name, NULL);
- g_strdelimit (object_path, ".", '/');
-
- if (!state->dbus_cancellable)
- state->dbus_cancellable = g_cancellable_new ();
-
- /* first step: the application proxy */
-
- g_dbus_proxy_new (bus,
- G_DBUS_PROXY_FLAGS_NONE,
- NULL, /* interface info */
- name_owner,
- object_path,
- "org.gtk.Application",
- state->dbus_cancellable,
- on_dbus_proxy_gotten,
- g_object_ref (self));
-
- g_object_notify (G_OBJECT (self), "dbus-id");
-
- g_free (object_path);
-}
-
-static void
-on_dbus_name_disappeared (GDBusConnection *bus,
- const gchar *name,
- gpointer user_data)
-{
- ShellApp *self = SHELL_APP (user_data);
- ShellAppRunningState *state = self->running_state;
-
- g_assert (state != NULL);
-
- if (state->dbus_cancellable)
- {
- g_cancellable_cancel (state->dbus_cancellable);
- g_clear_object (&state->dbus_cancellable);
- }
-
- g_clear_object (&state->app_proxy);
- g_clear_object (&state->remote_actions);
- g_clear_object (&state->remote_menu);
- g_clear_object (&state->muxer);
-
- g_free (state->dbus_name);
- state->dbus_name = NULL;
-
- g_bus_unwatch_name (state->name_watcher_id);
- state->name_watcher_id = 0;
-}
-
/**
* shell_app_get_pids:
* @app: a #ShellApp
@@ -1395,6 +1211,47 @@ create_running_state (ShellApp *app)
app->running_state->refcount = 1;
app->running_state->workspace_switch_id =
g_signal_connect (screen, "workspace-switched", G_CALLBACK(shell_app_on_ws_switch), app);
+
+ app->running_state->muxer = g_action_muxer_new ();
+}
+
+static void
+setup_running_state (ShellApp *app,
+ MetaWindow *window)
+{
+ /* We assume that 'gtk-unique-bus-name', gtk-application-object-path'
+ * and 'gtk-app-menu-object-path' are the same for all windows which
+ * have it set.
+ *
+ * It could be possible, however, that the first window we see
+ * belonging to the app didn't have them set. For this reason, we
+ * take the values from the first window that has them set and ignore
+ * all the rest (until the app is stopped and restarted).
+ */
+
+ if (app->running_state->remote_menu == NULL)
+ {
+ const gchar *application_object_path;
+ const gchar *app_menu_object_path;
+ const gchar *unique_bus_name;
+ GDBusConnection *session;
+ GDBusActionGroup *actions;
+
+ application_object_path = meta_window_get_gtk_application_object_path (window);
+ app_menu_object_path = meta_window_get_gtk_app_menu_object_path (window);
+ unique_bus_name = meta_window_get_gtk_unique_bus_name (window);
+
+ if (application_object_path == NULL || app_menu_object_path == NULL || unique_bus_name == NULL)
+ return;
+
+ session = g_bus_get_sync (G_BUS_TYPE_SESSION, NULL, NULL);
+ g_assert (session != NULL);
+ app->running_state->remote_menu = g_dbus_menu_model_get (session, unique_bus_name, app_menu_object_path);
+ actions = g_dbus_action_group_get (session, unique_bus_name, application_object_path);
+ g_action_muxer_insert (app->running_state->muxer, "app", G_ACTION_GROUP (actions));
+ g_object_unref (actions);
+ g_object_unref (session);
+ }
}
static void
@@ -1411,20 +1268,8 @@ unref_running_state (ShellAppRunningState *state)
screen = shell_global_get_screen (shell_global_get ());
g_signal_handler_disconnect (screen, state->workspace_switch_id);
- if (state->dbus_cancellable)
- {
- g_cancellable_cancel (state->dbus_cancellable);
- g_object_unref (state->dbus_cancellable);
- }
-
- g_clear_object (&state->app_proxy);
- g_clear_object (&state->remote_actions);
g_clear_object (&state->remote_menu);
g_clear_object (&state->muxer);
- g_free (state->dbus_name);
-
- if (state->name_watcher_id)
- g_bus_unwatch_name (state->name_watcher_id);
g_slice_free (ShellAppRunningState, state);
}
@@ -1670,20 +1515,6 @@ shell_app_class_init(ShellAppClass *klass)
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS));
/**
- * ShellApp:dbus-id:
- *
- * The DBus well-known name of the application, if one can be associated
- * to this ShellApp (it means that the application is using GApplication)
- */
- g_object_class_install_property (gobject_class,
- PROP_DBUS_ID,
- g_param_spec_string ("dbus-id",
- "Application DBus Id",
- "The DBus well-known name of the application",
- NULL,
- G_PARAM_READABLE | G_PARAM_STATIC_STRINGS));
-
- /**
* ShellApp:action-group:
*
* The #GDBusActionGroup associated with this ShellApp, if any. See the
diff --git a/src/shell-app.h b/src/shell-app.h
index 4fa6686..7e14c69 100644
--- a/src/shell-app.h
+++ b/src/shell-app.h
@@ -41,8 +41,6 @@ const char *shell_app_get_id (ShellApp *app);
GMenuTreeEntry *shell_app_get_tree_entry (ShellApp *app);
GDesktopAppInfo *shell_app_get_app_info (ShellApp *app);
-const char *shell_app_get_dbus_id (ShellApp *app);
-
ClutterActor *shell_app_create_icon_texture (ShellApp *app, int size);
ClutterActor *shell_app_get_faded_icon (ShellApp *app, int size);
const char *shell_app_get_name (ShellApp *app);
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]