From 2d9d89bb932174f6b54e6ba6586deafe511a685b Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Wed, 12 Feb 2014 16:47:26 -0600 Subject: Putting an abstract MediaPlayerList class in the middle of the Mpris implementation --- src/CMakeLists.txt | 6 ++ src/media-player-list-mpris.vala | 133 ++++++++++++++++++++++++++++++++++++++ src/media-player-list.vala | 136 --------------------------------------- 3 files changed, 139 insertions(+), 136 deletions(-) create mode 100644 src/media-player-list-mpris.vala delete mode 100644 src/media-player-list.vala (limited to 'src') diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 7d58afb..3efe14e 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -63,6 +63,12 @@ vala_add(indicator-sound-service media-player-list.vala DEPENDS media-player +) +vala_add(indicator-sound-service + media-player-list-mpris.vala + DEPENDS + media-player-list + media-player media-player-mpris mpris2-interfaces ) diff --git a/src/media-player-list-mpris.vala b/src/media-player-list-mpris.vala new file mode 100644 index 0000000..0ed3c72 --- /dev/null +++ b/src/media-player-list-mpris.vala @@ -0,0 +1,133 @@ +/* + * Copyright 2013 Canonical Ltd. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 3. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + * + * Authors: + * Lars Uebernickel + */ + +/** + * MediaPlayerList is a list of media players that should appear in the sound menu. Its main responsibility is + * to listen for MPRIS players on the bus and attach them to the corresponding %Player objects. + */ +public class MediaPlayerListMpris : MediaPlayerList { + + public MediaPlayerListMpris () { + this._players = new HashTable (str_hash, str_equal); + + BusWatcher.watch_namespace (BusType.SESSION, "org.mpris.MediaPlayer2", this.player_appeared, this.player_disappeared); + } + + /* only valid while the list is not changed */ + public class Iterator : MediaPlayerList.Iterator { + HashTableIter iter; + + public Iterator (MediaPlayerListMpris list) { + this.iter = HashTableIter (list._players); + } + + public override MediaPlayer? next_value () { + MediaPlayerMpris? player; + + if (this.iter.next (null, out player)) + return player as MediaPlayer; + else + return null; + } + } + + public override MediaPlayerList.Iterator iterator () { + return new Iterator (this) as MediaPlayerList.Iterator; + } + + /** + * Adds the player associated with @desktop_id. Does nothing if such a player already exists. + */ + MediaPlayerMpris? insert (string desktop_id) { + var id = desktop_id.has_suffix (".desktop") ? desktop_id : desktop_id + ".desktop"; + MediaPlayerMpris? player = this._players.lookup (id); + + if (player == null) { + var appinfo = new DesktopAppInfo (id); + if (appinfo == null) { + warning ("unable to find application '%s'", id); + return null; + } + + player = new MediaPlayerMpris (appinfo); + this._players.insert (player.id, player); + this.player_added (player); + } + + return player; + } + + /** + * Removes the player associated with @desktop_id, unless it is currently running. + */ + void remove (string desktop_id) { + MediaPlayer? player = this._players.lookup (desktop_id); + + if (player != null && !player.is_running) { + this._players.remove (desktop_id); + this.player_removed (player); + } + } + + /** + * Synchronizes the player list with @desktop_ids. After this call, this list will only contain the players + * in @desktop_ids. Players that were running but are not in @desktop_ids will remain in the list. + */ + public override void sync (string[] desktop_ids) { + + /* hash desktop_ids for faster lookup */ + var hash = new HashTable (str_hash, str_equal); + foreach (var id in desktop_ids) + hash.add (id); + + /* remove players that are not desktop_ids */ + foreach (var id in this._players.get_keys ()) { + if (!hash.contains (id)) + this.remove (id); + } + + /* insert all players (insert() takes care of not adding a player twice */ + foreach (var id in desktop_ids) + this.insert (id); + } + + HashTable _players; + + void player_appeared (DBusConnection connection, string name, string owner) { + try { + MprisRoot mpris2_root = Bus.get_proxy_sync (BusType.SESSION, name, MPRIS_MEDIA_PLAYER_PATH); + + var player = this.insert (mpris2_root.DesktopEntry); + if (player != null) + player.attach (mpris2_root, name); + } + catch (Error e) { + warning ("unable to create mpris proxy for '%s': %s", name, e.message); + } + } + + void player_disappeared (DBusConnection connection, string dbus_name) { + MediaPlayerMpris? player = this._players.find ( (name, player) => { + return player.dbus_name == dbus_name; + }); + + if (player != null) + player.detach (); + } +} diff --git a/src/media-player-list.vala b/src/media-player-list.vala deleted file mode 100644 index 87ca1f0..0000000 --- a/src/media-player-list.vala +++ /dev/null @@ -1,136 +0,0 @@ -/* - * Copyright 2013 Canonical Ltd. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; version 3. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see . - * - * Authors: - * Lars Uebernickel - */ - -/** - * MediaPlayerList is a list of media players that should appear in the sound menu. Its main responsibility is - * to listen for MPRIS players on the bus and attach them to the corresponding %Player objects. - */ -public class MediaPlayerList { - - public MediaPlayerList () { - this._players = new HashTable (str_hash, str_equal); - - BusWatcher.watch_namespace (BusType.SESSION, "org.mpris.MediaPlayer2", this.player_appeared, this.player_disappeared); - } - - /* only valid while the list is not changed */ - public class Iterator { - HashTableIter iter; - - public Iterator (MediaPlayerList list) { - this.iter = HashTableIter (list._players); - } - - public MediaPlayer? next_value () { - MediaPlayerMpris? player; - - if (this.iter.next (null, out player)) - return player as MediaPlayer; - else - return null; - } - } - - public Iterator iterator () { - return new Iterator (this); - } - - /** - * Adds the player associated with @desktop_id. Does nothing if such a player already exists. - */ - MediaPlayerMpris? insert (string desktop_id) { - var id = desktop_id.has_suffix (".desktop") ? desktop_id : desktop_id + ".desktop"; - MediaPlayerMpris? player = this._players.lookup (id); - - if (player == null) { - var appinfo = new DesktopAppInfo (id); - if (appinfo == null) { - warning ("unable to find application '%s'", id); - return null; - } - - player = new MediaPlayerMpris (appinfo); - this._players.insert (player.id, player); - this.player_added (player); - } - - return player; - } - - /** - * Removes the player associated with @desktop_id, unless it is currently running. - */ - void remove (string desktop_id) { - MediaPlayer? player = this._players.lookup (desktop_id); - - if (player != null && !player.is_running) { - this._players.remove (desktop_id); - this.player_removed (player); - } - } - - /** - * Synchronizes the player list with @desktop_ids. After this call, this list will only contain the players - * in @desktop_ids. Players that were running but are not in @desktop_ids will remain in the list. - */ - public void sync (string[] desktop_ids) { - - /* hash desktop_ids for faster lookup */ - var hash = new HashTable (str_hash, str_equal); - foreach (var id in desktop_ids) - hash.add (id); - - /* remove players that are not desktop_ids */ - foreach (var id in this._players.get_keys ()) { - if (!hash.contains (id)) - this.remove (id); - } - - /* insert all players (insert() takes care of not adding a player twice */ - foreach (var id in desktop_ids) - this.insert (id); - } - - public signal void player_added (MediaPlayer player); - public signal void player_removed (MediaPlayer player); - - HashTable _players; - - void player_appeared (DBusConnection connection, string name, string owner) { - try { - MprisRoot mpris2_root = Bus.get_proxy_sync (BusType.SESSION, name, MPRIS_MEDIA_PLAYER_PATH); - - var player = this.insert (mpris2_root.DesktopEntry); - if (player != null) - player.attach (mpris2_root, name); - } - catch (Error e) { - warning ("unable to create mpris proxy for '%s': %s", name, e.message); - } - } - - void player_disappeared (DBusConnection connection, string dbus_name) { - MediaPlayerMpris? player = this._players.find ( (name, player) => { - return player.dbus_name == dbus_name; - }); - - if (player != null) - player.detach (); - } -} -- cgit v1.2.3 From 537e5b2988815287e6bb3da35189e5c65c5ac4b2 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Wed, 12 Feb 2014 16:49:31 -0600 Subject: Move the player list outside of the service creation --- src/main.c | 5 ++++- src/service.vala | 4 ++-- 2 files changed, 6 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/main.c b/src/main.c index f8635c8..0a893b3 100644 --- a/src/main.c +++ b/src/main.c @@ -21,9 +21,12 @@ main (int argc, char ** argv) { /* Initialize libnotify */ notify_init ("indicator-sound"); + MediaPlayerList * playerlist = MEDIA_PLAYER_LIST(media_player_list_mpris_new()); - service = indicator_sound_service_new (); + service = indicator_sound_service_new (playerlist); result = indicator_sound_service_run (service); + + g_object_unref(playerlist); g_object_unref(service); return result; diff --git a/src/service.vala b/src/service.vala index 25f3011..7b88e1b 100644 --- a/src/service.vala +++ b/src/service.vala @@ -18,12 +18,12 @@ */ public class IndicatorSound.Service { - public Service () { + public Service (MediaPlayerList playerlist) { this.settings = new Settings ("com.canonical.indicator.sound"); this.volume_control = new VolumeControl (); - this.players = new MediaPlayerList (); + this.players = playerlist; this.players.player_added.connect (this.player_added); this.players.player_removed.connect (this.player_removed); -- cgit v1.2.3 From 11105537ec91c601fdf0012ed69dc2d64aeea3d4 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Wed, 12 Feb 2014 16:54:12 -0600 Subject: Adding a stub object for the greeter list --- src/CMakeLists.txt | 6 ++++++ src/media-player-list-greeter.vala | 23 +++++++++++++++++++++++ 2 files changed, 29 insertions(+) create mode 100644 src/media-player-list-greeter.vala (limited to 'src') diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 3efe14e..15133f0 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -72,6 +72,12 @@ vala_add(indicator-sound-service media-player-mpris mpris2-interfaces ) +vala_add(indicator-sound-service + media-player-list-greeter.vala + DEPENDS + media-player-list + media-player +) vala_add(indicator-sound-service mpris2-interfaces.vala ) diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala new file mode 100644 index 0000000..6bcf270 --- /dev/null +++ b/src/media-player-list-greeter.vala @@ -0,0 +1,23 @@ +/* + * Copyright © 2014 Canonical Ltd. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 3. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + * + * Authors: + * Ted Gould + */ + +public class MediaPlayerListGreeter : MediaPlayerList { + + +} -- cgit v1.2.3 From 0b76536b27f57db75a101e8ce7e3f75b7cddf57c Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Wed, 12 Feb 2014 17:07:33 -0600 Subject: Detect which player list we need at startup --- src/main.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/main.c b/src/main.c index 0a893b3..a14bdea 100644 --- a/src/main.c +++ b/src/main.c @@ -21,7 +21,13 @@ main (int argc, char ** argv) { /* Initialize libnotify */ notify_init ("indicator-sound"); - MediaPlayerList * playerlist = MEDIA_PLAYER_LIST(media_player_list_mpris_new()); + MediaPlayerList * playerlist = NULL; + + if (g_strcmp0("lightdm", g_get_user_name())) { + playerlist = MEDIA_PLAYER_LIST(media_player_list_greeter_new()); + } else { + playerlist = MEDIA_PLAYER_LIST(media_player_list_mpris_new()); + } service = indicator_sound_service_new (playerlist); result = indicator_sound_service_run (service); -- cgit v1.2.3 From d89688f426996bbfccdab0713bbe47f09c14483b Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 21 Feb 2014 15:58:53 -0600 Subject: A media player per-user --- src/CMakeLists.txt | 5 +++ src/media-player-user.vala | 90 ++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 95 insertions(+) create mode 100644 src/media-player-user.vala (limited to 'src') diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 15133f0..e80da32 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -59,6 +59,11 @@ vala_add(indicator-sound-service media-player mpris2-interfaces ) +vala_add(indicator-sound-service + media-player-user.vala + DEPENDS + media-player +) vala_add(indicator-sound-service media-player-list.vala DEPENDS diff --git a/src/media-player-user.vala b/src/media-player-user.vala new file mode 100644 index 0000000..be2dee8 --- /dev/null +++ b/src/media-player-user.vala @@ -0,0 +1,90 @@ +/* + * Copyright © 2014 Canonical Ltd. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 3. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + * + * Authors: + * Ted Gould + */ + +public abstract class MediaPlayerUser : MediaPlayer { + string username; + + MediaPlayerUser(string user) { + username = user; + } + + public override string id { + get { return username; } + } + + public override string name { + get { + /* TODO */ + return ""; + } + } + public override string state { + get { + /* TODO */ + return ""; + } + set { } + } + public override Icon? icon { + get { + /* TODO */ + return null; + } + } + public override string dbus_name { get { return ""; } } + + public override bool is_running { get { return true; } } + public override bool can_raise { get { return false; } } + + public override MediaPlayer.Track? current_track { + get { + /* TODO: */ + return null; + } + set { } + } + + /* Control functions through unity-greeter-session-broadcast */ + public override void activate () { + /* TODO: */ + } + public override void play_pause () { + /* TODO: */ + } + public override void next () { + /* TODO: */ + } + public override void previous () { + /* TODO: */ + } + + /* Play list functions are all null as we don't support the + playlist feature on the greeter */ + public override uint get_n_playlists() { + return 0; + } + public override string get_playlist_id (int index) { + return ""; + } + public override string get_playlist_name (int index) { + return ""; + } + public override void activate_playlist_by_name (string playlist) { + } +} -- cgit v1.2.3 From 946e20203b946ee9d11885ad759eec45bfee65a2 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 21 Feb 2014 16:06:47 -0600 Subject: Connect to getting the proxy and the settings --- src/CMakeLists.txt | 1 + src/media-player-user.vala | 28 ++++++++++++++++++++++++++++ 2 files changed, 29 insertions(+) (limited to 'src') diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index ac6437c..f134954 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -63,6 +63,7 @@ vala_add(indicator-sound-service media-player-user.vala DEPENDS media-player + accounts-service-sound-settings ) vala_add(indicator-sound-service media-player-list.vala diff --git a/src/media-player-user.vala b/src/media-player-user.vala index be2dee8..bb00b07 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -18,10 +18,38 @@ */ public abstract class MediaPlayerUser : MediaPlayer { + Act.UserManager accounts_manager = Act.UserManager.get_default(); string username; + Act.User? actuser = null; + AccountsServiceSoundSettings? proxy = null; MediaPlayerUser(string user) { username = user; + + actuser = accounts_manager.get_user(user); + actuser.notify["is-loaded"].connect(() => { + debug("User loaded"); + + this.proxy = null; + + Bus.get_proxy.begin ( + BusType.SYSTEM, + "org.freedesktop.Accounts", + actuser.get_object_path(), + DBusProxyFlags.GET_INVALIDATED_PROPERTIES, + null, + new_proxy); + }); + } + + void new_proxy (GLib.Object? obj, AsyncResult res) { + try { + this.proxy = Bus.get_proxy.end (res); + /* TODO: Update settings */ + } catch (Error e) { + this.proxy = null; + warning("Unable to get proxy to user '%s' sound settings: %s", username, e.message); + } } public override string id { -- cgit v1.2.3 From ceab1b92d76d4cf28fecd0f1858a628ec85ff21e Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 21 Feb 2014 16:20:39 -0600 Subject: Get the proxy values out --- src/media-player-user.vala | 41 +++++++++++++++++++++++++++++++++-------- 1 file changed, 33 insertions(+), 8 deletions(-) (limited to 'src') diff --git a/src/media-player-user.vala b/src/media-player-user.vala index bb00b07..ac73138 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -56,23 +56,38 @@ public abstract class MediaPlayerUser : MediaPlayer { get { return username; } } + string name_cache; public override string name { get { - /* TODO */ - return ""; + if (this.proxy != null) { + name_cache = this.proxy.player_name; + return name_cache; + } else { + return ""; + } } } + string state_cache; public override string state { get { - /* TODO */ - return ""; + if (this.proxy != null) { + state_cache = this.proxy.state; + return state_cache; + } else { + return ""; + } } set { } } + Icon icon_cache; public override Icon? icon { get { - /* TODO */ - return null; + if (this.proxy != null) { + icon_cache = Icon.deserialize(this.proxy.player_icon); + return icon_cache; + } else { + return null; + } } } public override string dbus_name { get { return ""; } } @@ -80,10 +95,20 @@ public abstract class MediaPlayerUser : MediaPlayer { public override bool is_running { get { return true; } } public override bool can_raise { get { return false; } } + MediaPlayer.Track track_cache; public override MediaPlayer.Track? current_track { get { - /* TODO: */ - return null; + if (this.proxy != null) { + track_cache = new MediaPlayer.Track( + this.proxy.artist, + this.proxy.title, + this.proxy.album, + this.proxy.art_url + ); + return track_cache; + } else { + return null; + } } set { } } -- cgit v1.2.3 From b8e644e88161501bce35b6d866c58bcc147abd94 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 21 Feb 2014 16:47:28 -0600 Subject: Check the timestamp as well --- src/media-player-user.vala | 21 +++++++++++++++++---- 1 file changed, 17 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/media-player-user.vala b/src/media-player-user.vala index ac73138..658b466 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -52,6 +52,19 @@ public abstract class MediaPlayerUser : MediaPlayer { } } + bool proxy_is_valid () { + if (this.proxy == null) { + return false; + } + + /* More than 10 minutes old */ + if (this.proxy.timestamp < GLib.get_monotonic_time() - 10 * 60 * 1000 * 1000) { + return false; + } + + return true; + } + public override string id { get { return username; } } @@ -59,7 +72,7 @@ public abstract class MediaPlayerUser : MediaPlayer { string name_cache; public override string name { get { - if (this.proxy != null) { + if (proxy_is_valid()) { name_cache = this.proxy.player_name; return name_cache; } else { @@ -70,7 +83,7 @@ public abstract class MediaPlayerUser : MediaPlayer { string state_cache; public override string state { get { - if (this.proxy != null) { + if (proxy_is_valid()) { state_cache = this.proxy.state; return state_cache; } else { @@ -82,7 +95,7 @@ public abstract class MediaPlayerUser : MediaPlayer { Icon icon_cache; public override Icon? icon { get { - if (this.proxy != null) { + if (proxy_is_valid()) { icon_cache = Icon.deserialize(this.proxy.player_icon); return icon_cache; } else { @@ -98,7 +111,7 @@ public abstract class MediaPlayerUser : MediaPlayer { MediaPlayer.Track track_cache; public override MediaPlayer.Track? current_track { get { - if (this.proxy != null) { + if (proxy_is_valid()) { track_cache = new MediaPlayer.Track( this.proxy.artist, this.proxy.title, -- cgit v1.2.3 From d42cb160a6823f34b478aab7c50a8b2247be0cf4 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 21 Feb 2014 16:57:59 -0600 Subject: Add a todo and adjust running --- src/media-player-user.vala | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/media-player-user.vala b/src/media-player-user.vala index 658b466..6c948ad 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -46,6 +46,7 @@ public abstract class MediaPlayerUser : MediaPlayer { try { this.proxy = Bus.get_proxy.end (res); /* TODO: Update settings */ + /* TODO: Setup setting notification */ } catch (Error e) { this.proxy = null; warning("Unable to get proxy to user '%s' sound settings: %s", username, e.message); @@ -105,7 +106,7 @@ public abstract class MediaPlayerUser : MediaPlayer { } public override string dbus_name { get { return ""; } } - public override bool is_running { get { return true; } } + public override bool is_running { get { return proxy_is_valid(); } } public override bool can_raise { get { return false; } } MediaPlayer.Track track_cache; -- cgit v1.2.3 From a758202c3799256ddded7ee790744d6fe3c1c4a7 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 24 Feb 2014 15:36:48 -0600 Subject: Build up our list of media players from the greeter list --- src/CMakeLists.txt | 1 + src/media-player-list-greeter.vala | 62 ++++++++++++++++++++++++++++++++++++++ src/media-player-user.vala | 4 +-- 3 files changed, 65 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index f134954..436a154 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -82,6 +82,7 @@ vala_add(indicator-sound-service media-player-list-greeter.vala DEPENDS media-player-list + media-player-user media-player ) vala_add(indicator-sound-service diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala index 6bcf270..c07663a 100644 --- a/src/media-player-list-greeter.vala +++ b/src/media-player-list-greeter.vala @@ -17,7 +17,69 @@ * Ted Gould */ +[DBus (name="com.canonical.UnityGreeter.List")] +public interface UnityGreeterList : Object { + public abstract async string get_active_entry () throws IOError; + public signal void entry_selected (string entry_name); +} + public class MediaPlayerListGreeter : MediaPlayerList { + string? selected_user = null; + UnityGreeterList? proxy = null; + HashTable players = new HashTable(str_hash, str_equal); + + public MediaPlayerListGreeter () { + Bus.get_proxy.begin ( + BusType.SESSION, + "com.canonical.Unity", + "/list", + DBusProxyFlags.NONE, + null, + new_proxy); + } + + void new_proxy (GLib.Object? obj, AsyncResult res) { + try { + this.proxy = Bus.get_proxy.end(res); + + this.proxy.entry_selected.connect(active_user_changed); + this.proxy.get_active_entry.begin ((obj, res) => { + try { + var value = (obj as UnityGreeterList).get_active_entry.end(res); + active_user_changed(value); + } catch (Error e) { + warning("Unable to get active entry: %s", e.message); + } + }); + } catch (Error e) { + this.proxy = null; + warning("Unable to create proxy to the greeter: %s", e.message); + } + } + + void active_user_changed (string active_user) { + /* No change, move along */ + if (selected_user == active_user) { + return; + } + + var old_user = selected_user; + selected_user = active_user; + + if (selected_user != null && !players.contains(selected_user)) { + players.insert(selected_user, new MediaPlayerUser(selected_user)); + } + + if (old_user != null) { + var old_player = players.lookup(old_user); + player_removed(old_player); + } + + if (selected_user != null) { + var new_player = players.lookup(selected_user); + player_added(new_player); + } + } } diff --git a/src/media-player-user.vala b/src/media-player-user.vala index 6c948ad..bd9bc92 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -17,13 +17,13 @@ * Ted Gould */ -public abstract class MediaPlayerUser : MediaPlayer { +public class MediaPlayerUser : MediaPlayer { Act.UserManager accounts_manager = Act.UserManager.get_default(); string username; Act.User? actuser = null; AccountsServiceSoundSettings? proxy = null; - MediaPlayerUser(string user) { + public MediaPlayerUser(string user) { username = user; actuser = accounts_manager.get_user(user); -- cgit v1.2.3 From faa10b31c7868206156c33fc3bc0b2d6c726e63d Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 24 Feb 2014 15:55:33 -0600 Subject: Add in the iterator support --- src/media-player-list-greeter.vala | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) (limited to 'src') diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala index c07663a..2488c07 100644 --- a/src/media-player-list-greeter.vala +++ b/src/media-player-list-greeter.vala @@ -81,5 +81,29 @@ public class MediaPlayerListGreeter : MediaPlayerList { } } + /* We need to have an iterator for the interface, but eh, we can + only ever have one player for the current user */ + public class Iterator : MediaPlayerList.Iterator { + int i = 0; + MediaPlayerListGreeter list; + public Iterator (MediaPlayerListGreeter in_list) { + list = in_list; + } + + public override MediaPlayer? next_value () { + MediaPlayer? retval = null; + + if (i == 0) { + retval = list.players.lookup(list.selected_user); + } + i++; + + return retval; + } + } + + public override MediaPlayerList.Iterator iterator() { + return new Iterator(this) as MediaPlayerList.Iterator; + } } -- cgit v1.2.3 From abe2227e7dfecdec4c28c9447e2b2d298ba8eb89 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 24 Feb 2014 16:30:49 -0600 Subject: Get out the dbus properties --- src/media-player-user.vala | 46 +++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 45 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/media-player-user.vala b/src/media-player-user.vala index bd9bc92..c4d0e42 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -23,6 +23,8 @@ public class MediaPlayerUser : MediaPlayer { Act.User? actuser = null; AccountsServiceSoundSettings? proxy = null; + /* Grab the user from the Accounts service and, when it is loaded then + set up a proxy to its sound settings */ public MediaPlayerUser(string user) { username = user; @@ -42,11 +44,47 @@ public class MediaPlayerUser : MediaPlayer { }); } + void queue_property_notification (string dbus_property_name) { + switch (dbus_property_name) { + case "Timestamp": + break; + case "PlayerName": + break; + case "PlayerIcon": + break; + case "State": + break; + case "Title": + break; + case "Artist": + break; + case "Album": + break; + case "ArtUrl": + break; + } + } + void new_proxy (GLib.Object? obj, AsyncResult res) { try { this.proxy = Bus.get_proxy.end (res); + + var gproxy = this.proxy as DBusProxy; + gproxy.g_properties_changed.connect ((proxy, changed, invalidated) => { + string key = ""; + Variant value; + VariantIter iter = new VariantIter(changed); + + while (iter.next("{sv}", &key, &value)) { + queue_property_notification(key); + } + + foreach (var invalid in invalidated) { + queue_property_notification(invalid); + } + }); + /* TODO: Update settings */ - /* TODO: Setup setting notification */ } catch (Error e) { this.proxy = null; warning("Unable to get proxy to user '%s' sound settings: %s", username, e.message); @@ -70,6 +108,7 @@ public class MediaPlayerUser : MediaPlayer { get { return username; } } + /* These values come from the proxy */ string name_cache; public override string name { get { @@ -104,11 +143,16 @@ public class MediaPlayerUser : MediaPlayer { } } } + + /* Placeholder */ public override string dbus_name { get { return ""; } } + /* If it's shown externally it's running */ public override bool is_running { get { return proxy_is_valid(); } } + /* A bit weird. Not sure how we should handle this. */ public override bool can_raise { get { return false; } } + /* Fill out the track based on the values in the proxy */ MediaPlayer.Track track_cache; public override MediaPlayer.Track? current_track { get { -- cgit v1.2.3 From 19fd5a77a5a820f320d71ffa364b978a69345317 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 24 Feb 2014 16:46:33 -0600 Subject: Signalling some properties! --- src/media-player-user.vala | 42 ++++++++++++++++++++++++++++++++++++++---- 1 file changed, 38 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/media-player-user.vala b/src/media-player-user.vala index c4d0e42..798c8c8 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -23,6 +23,9 @@ public class MediaPlayerUser : MediaPlayer { Act.User? actuser = null; AccountsServiceSoundSettings? proxy = null; + HashTable properties_queued = new HashTable(str_hash, str_equal); + uint properties_timeout = 0; + /* Grab the user from the Accounts service and, when it is loaded then set up a proxy to its sound settings */ public MediaPlayerUser(string user) { @@ -44,23 +47,53 @@ public class MediaPlayerUser : MediaPlayer { }); } + ~MediaPlayerUser () { + if (properties_timeout != 0) { + Source.remove(properties_timeout); + properties_timeout = 0; + } + } + + /* Ensure that we've collected all the changes so that we only signal + once for variables like 'track' */ + bool properties_idle () { + properties_timeout = 0; + + properties_queued.@foreach((key, value) => { + this.notify_property(key); + }); + + /* Remove source */ + return false; + } + + /* Turns the DBus names into the object properties */ void queue_property_notification (string dbus_property_name) { + if (properties_timeout == 0) { + properties_timeout = Idle.add(properties_idle); + } + switch (dbus_property_name) { case "Timestamp": + properties_queued.insert("name", true); + properties_queued.insert("icon", true); + properties_queued.insert("state", true); + properties_queued.insert("current-track", true); break; case "PlayerName": + properties_queued.insert("name", true); break; case "PlayerIcon": + properties_queued.insert("icon", true); break; case "State": + properties_queued.insert("state", true); break; case "Title": - break; case "Artist": - break; case "Album": - break; case "ArtUrl": + properties_queued.insert("current-track", true); break; } } @@ -84,7 +117,8 @@ public class MediaPlayerUser : MediaPlayer { } }); - /* TODO: Update settings */ + /* Update all of them -- we've got a proxy! */ + queue_property_notification("Timestamp"); } catch (Error e) { this.proxy = null; warning("Unable to get proxy to user '%s' sound settings: %s", username, e.message); -- cgit v1.2.3 From 0b93aa745830a32185f4383ba3813fbbd307bdf2 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 24 Feb 2014 16:47:50 -0600 Subject: Hmm, we totally need this --- src/media-player-list.vala | 33 +++++++++++++++++++++++++++++++++ 1 file changed, 33 insertions(+) create mode 100644 src/media-player-list.vala (limited to 'src') diff --git a/src/media-player-list.vala b/src/media-player-list.vala new file mode 100644 index 0000000..fadbf63 --- /dev/null +++ b/src/media-player-list.vala @@ -0,0 +1,33 @@ +/* + * Copyright © 2014 Canonical Ltd. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 3. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + * + * Authors: + * Ted Gould + */ + +public class MediaPlayerList { + public class Iterator { + public virtual MediaPlayer? next_value() { + return null; + } + } + public virtual Iterator iterator () { return new Iterator(); } + + public virtual void sync (string[] ids) { return; } + + public signal void player_added (MediaPlayer player); + public signal void player_removed (MediaPlayer player); +} + -- cgit v1.2.3 From e9216681e8644d91d8efc2aff76810d9172e48a6 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Tue, 25 Feb 2014 16:47:45 -0600 Subject: Truth is difficult --- src/main.c | 2 +- src/media-player-list-mpris.vala | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/main.c b/src/main.c index a14bdea..e9a148e 100644 --- a/src/main.c +++ b/src/main.c @@ -23,7 +23,7 @@ main (int argc, char ** argv) { MediaPlayerList * playerlist = NULL; - if (g_strcmp0("lightdm", g_get_user_name())) { + if (g_strcmp0("lightdm", g_get_user_name()) == 0) { playerlist = MEDIA_PLAYER_LIST(media_player_list_greeter_new()); } else { playerlist = MEDIA_PLAYER_LIST(media_player_list_mpris_new()); diff --git a/src/media-player-list-mpris.vala b/src/media-player-list-mpris.vala index 0ed3c72..65fb886 100644 --- a/src/media-player-list-mpris.vala +++ b/src/media-player-list-mpris.vala @@ -55,6 +55,8 @@ public class MediaPlayerListMpris : MediaPlayerList { * Adds the player associated with @desktop_id. Does nothing if such a player already exists. */ MediaPlayerMpris? insert (string desktop_id) { + debug("Inserting player: %s", desktop_id); + var id = desktop_id.has_suffix (".desktop") ? desktop_id : desktop_id + ".desktop"; MediaPlayerMpris? player = this._players.lookup (id); -- cgit v1.2.3 From c362b97968c8732773057905193762063880cd8e Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 13:57:38 -0600 Subject: Null user protection --- src/media-player-list-greeter.vala | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala index 2488c07..2f1962e 100644 --- a/src/media-player-list-greeter.vala +++ b/src/media-player-list-greeter.vala @@ -64,7 +64,13 @@ public class MediaPlayerListGreeter : MediaPlayerList { } var old_user = selected_user; - selected_user = active_user; + + /* Protect against a null user */ + if (active_user != "") { + selected_user = active_user; + } else { + selected_user = null; + } if (selected_user != null && !players.contains(selected_user)) { players.insert(selected_user, new MediaPlayerUser(selected_user)); -- cgit v1.2.3 From 8dea058491a3ca351853df4e85f6c69a4d788944 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 15:41:43 -0600 Subject: Remove the properties we just signaled --- src/media-player-user.vala | 2 ++ 1 file changed, 2 insertions(+) (limited to 'src') diff --git a/src/media-player-user.vala b/src/media-player-user.vala index 798c8c8..3a3feaf 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -63,6 +63,8 @@ public class MediaPlayerUser : MediaPlayer { this.notify_property(key); }); + properties_queued.remove_all(); + /* Remove source */ return false; } -- cgit v1.2.3 From 3847d2c622e3cd838bd485403c1c4378aa57a637 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 15:43:52 -0600 Subject: Debug message on property change --- src/media-player-user.vala | 1 + 1 file changed, 1 insertion(+) (limited to 'src') diff --git a/src/media-player-user.vala b/src/media-player-user.vala index 3a3feaf..28ec5ae 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -60,6 +60,7 @@ public class MediaPlayerUser : MediaPlayer { properties_timeout = 0; properties_queued.@foreach((key, value) => { + debug("Notifying '%s' changed", key); this.notify_property(key); }); -- cgit v1.2.3 From dd42fb51e44d1a1233e6a803a997af7c20b8dc56 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 16:25:09 -0600 Subject: Wait until we have data before saying that we can add the player --- src/media-player-list-greeter.vala | 14 ++++++++++++-- src/media-player-user.vala | 4 ++-- 2 files changed, 14 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala index 2f1962e..101211d 100644 --- a/src/media-player-list-greeter.vala +++ b/src/media-player-list-greeter.vala @@ -73,7 +73,15 @@ public class MediaPlayerListGreeter : MediaPlayerList { } if (selected_user != null && !players.contains(selected_user)) { - players.insert(selected_user, new MediaPlayerUser(selected_user)); + var newplayer = new MediaPlayerUser(selected_user); + newplayer.notify["is-running"].connect((obj, prop) => { + MediaPlayerUser? player = obj as MediaPlayerUser; + if (player == null) return; + if (player.is_running && player.id == this.selected_user) + this.player_added(player); + }); + + players.insert(selected_user, newplayer); } if (old_user != null) { @@ -83,7 +91,9 @@ public class MediaPlayerListGreeter : MediaPlayerList { if (selected_user != null) { var new_player = players.lookup(selected_user); - player_added(new_player); + + if (new_player.is_running) + player_added(new_player); } } diff --git a/src/media-player-user.vala b/src/media-player-user.vala index 28ec5ae..a4b75c3 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -120,8 +120,8 @@ public class MediaPlayerUser : MediaPlayer { } }); - /* Update all of them -- we've got a proxy! */ - queue_property_notification("Timestamp"); + debug("Notifying player is ready for user: %s", this.username); + this.notify_property("is-running"); } catch (Error e) { this.proxy = null; warning("Unable to get proxy to user '%s' sound settings: %s", username, e.message); -- cgit v1.2.3 From 386d973866817541a904198865d49ec040d4755d Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 16:42:24 -0600 Subject: Use the standard code for only showing ready players --- src/media-player-list-greeter.vala | 12 ++---------- src/service.vala | 2 +- 2 files changed, 3 insertions(+), 11 deletions(-) (limited to 'src') diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala index 101211d..541fe3e 100644 --- a/src/media-player-list-greeter.vala +++ b/src/media-player-list-greeter.vala @@ -73,15 +73,7 @@ public class MediaPlayerListGreeter : MediaPlayerList { } if (selected_user != null && !players.contains(selected_user)) { - var newplayer = new MediaPlayerUser(selected_user); - newplayer.notify["is-running"].connect((obj, prop) => { - MediaPlayerUser? player = obj as MediaPlayerUser; - if (player == null) return; - if (player.is_running && player.id == this.selected_user) - this.player_added(player); - }); - - players.insert(selected_user, newplayer); + players.insert(selected_user, new MediaPlayerUser(selected_user)); } if (old_user != null) { @@ -92,7 +84,7 @@ public class MediaPlayerListGreeter : MediaPlayerList { if (selected_user != null) { var new_player = players.lookup(selected_user); - if (new_player.is_running) + if (new_player != null) player_added(new_player); } } diff --git a/src/service.vala b/src/service.vala index be0164d..f1a002f 100644 --- a/src/service.vala +++ b/src/service.vala @@ -35,7 +35,7 @@ public class IndicatorSound.Service: Object { this.actions.add_action (this.create_mic_volume_action ()); this.menus = new HashTable (str_hash, str_equal); - this.menus.insert ("desktop_greeter", new SoundMenu (null, SoundMenu.DisplayFlags.SHOW_MUTE)); + this.menus.insert ("desktop_greeter", new SoundMenu (null, SoundMenu.DisplayFlags.SHOW_MUTE | SoundMenu.DisplayFlags.HIDE_INACTIVE_PLAYERS)); this.menus.insert ("desktop", new SoundMenu ("indicator.desktop-settings", SoundMenu.DisplayFlags.SHOW_MUTE)); this.menus.insert ("phone", new SoundMenu ("indicator.phone-settings", SoundMenu.DisplayFlags.HIDE_INACTIVE_PLAYERS)); -- cgit v1.2.3 From 5a9752b71c90d82342dff8138b25f6af2dcb6b28 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 17:01:11 -0600 Subject: Some debugging information --- src/sound-menu.vala | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'src') diff --git a/src/sound-menu.vala b/src/sound-menu.vala index 480e1cf..62f510d 100644 --- a/src/sound-menu.vala +++ b/src/sound-menu.vala @@ -123,16 +123,20 @@ class SoundMenu: Object /* returns the position in this.menu of the section that's associated with @player */ int find_player_section (MediaPlayer player) { + debug("Looking for player: %s", player.id); string action_name = @"indicator.$(player.id)"; int n = this.menu.get_n_items () -1; for (int i = 1; i < n; i++) { var section = this.menu.get_item_link (i, Menu.LINK_SECTION); + if (section == null) continue; + string action; section.get_item_attribute (0, "action", "s", out action); if (action == action_name) return i; } + debug("Unable to find section for player: %s", player.id); return -1; } @@ -140,6 +144,8 @@ class SoundMenu: Object var section = new Menu (); Icon icon; + debug("Adding section for player: %s", player.id); + icon = player.icon; if (icon == null) icon = new ThemedIcon.with_default_fallbacks ("application-default-icon"); -- cgit v1.2.3 From db8f59aa75d57bed2dd74c40507d6db2481b5b0c Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 17:08:50 -0600 Subject: More debugging --- src/media-player-list-greeter.vala | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala index 541fe3e..6dd5eb9 100644 --- a/src/media-player-list-greeter.vala +++ b/src/media-player-list-greeter.vala @@ -78,14 +78,17 @@ public class MediaPlayerListGreeter : MediaPlayerList { if (old_user != null) { var old_player = players.lookup(old_user); + debug("Removing player for user: %s", old_user); player_removed(old_player); } if (selected_user != null) { var new_player = players.lookup(selected_user); - if (new_player != null) + if (new_player != null) { + debug("Adding player for user: %s", selected_user); player_added(new_player); + } } } -- cgit v1.2.3 From 4d6c4f5a4c6bcb16843b936175988261f2699688 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 17:08:59 -0600 Subject: Block the guest account --- src/media-player-list-greeter.vala | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala index 6dd5eb9..5acfe16 100644 --- a/src/media-player-list-greeter.vala +++ b/src/media-player-list-greeter.vala @@ -66,7 +66,7 @@ public class MediaPlayerListGreeter : MediaPlayerList { var old_user = selected_user; /* Protect against a null user */ - if (active_user != "") { + if (active_user != "" && active_user != "*guest") { selected_user = active_user; } else { selected_user = null; -- cgit v1.2.3 From 3664e8f90eabc8ca2b1b7752f9faf56a9d6664d6 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 21:05:12 -0600 Subject: Restructuring to ensure we're doing what we want on an update --- src/sound-menu.vala | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) (limited to 'src') diff --git a/src/sound-menu.vala b/src/sound-menu.vala index 62f510d..edb72d1 100644 --- a/src/sound-menu.vala +++ b/src/sound-menu.vala @@ -95,12 +95,11 @@ class SoundMenu: Object this.update_playlists (player); var handler_id = player.notify["is-running"].connect ( () => { - if (this.hide_inactive) { - if (player.is_running) + if (player.is_running || !this.hide_inactive) + if (this.find_player_section(player) == -1) this.insert_player_section (player); - else - this.remove_player_section (player); - } + else + this.remove_player_section (player); this.update_playlists (player); }); this.notify_handlers.insert (player, handler_id); -- cgit v1.2.3 From d67a230f9271bdc43441868cfa0012309a7c8967 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 21:06:18 -0600 Subject: The running state could also be effect the is-running variable --- src/media-player-user.vala | 1 + 1 file changed, 1 insertion(+) (limited to 'src') diff --git a/src/media-player-user.vala b/src/media-player-user.vala index a4b75c3..37f54a9 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -82,6 +82,7 @@ public class MediaPlayerUser : MediaPlayer { properties_queued.insert("icon", true); properties_queued.insert("state", true); properties_queued.insert("current-track", true); + properties_queued.insert("is-running", true); break; case "PlayerName": properties_queued.insert("name", true); -- cgit v1.2.3 From 37b28dc5427415f3fc69b1c6a2229301314e59ed Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 21:27:08 -0600 Subject: Reshuffle the status of the players --- src/sound-menu.vala | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/sound-menu.vala b/src/sound-menu.vala index edb72d1..6d36731 100644 --- a/src/sound-menu.vala +++ b/src/sound-menu.vala @@ -95,11 +95,13 @@ class SoundMenu: Object this.update_playlists (player); var handler_id = player.notify["is-running"].connect ( () => { - if (player.is_running || !this.hide_inactive) + if (player.is_running) if (this.find_player_section(player) == -1) this.insert_player_section (player); else - this.remove_player_section (player); + if (this.hide_inactive) + this.remove_player_section (player); + this.update_playlists (player); }); this.notify_handlers.insert (player, handler_id); -- cgit v1.2.3 From 8b43adebc047ac432f38296eec2e9b2dd7a5f051 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 21:47:44 -0600 Subject: When removing disconnect as well --- src/sound-menu.vala | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/sound-menu.vala b/src/sound-menu.vala index 6d36731..701930e 100644 --- a/src/sound-menu.vala +++ b/src/sound-menu.vala @@ -111,7 +111,12 @@ class SoundMenu: Object public void remove_player (MediaPlayer player) { this.remove_player_section (player); - this.notify_handlers.remove (player); + + var id = this.notify_handlers.lookup(player); + if (id != 0) { + player.disconnect(id); + this.notify_handlers.remove (player); + } } Menu root; -- cgit v1.2.3 From 76d1861936ae2a7acb8291321bb1c86bb96f064e Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Fri, 28 Feb 2014 21:49:20 -0600 Subject: Drop a connection to playlist event as well --- src/sound-menu.vala | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/sound-menu.vala b/src/sound-menu.vala index 701930e..2df1a52 100644 --- a/src/sound-menu.vala +++ b/src/sound-menu.vala @@ -115,8 +115,12 @@ class SoundMenu: Object var id = this.notify_handlers.lookup(player); if (id != 0) { player.disconnect(id); - this.notify_handlers.remove (player); } + + player.playlists_changed.disconnect (this.update_playlists); + + /* this'll drop our ref to it */ + this.notify_handlers.remove (player); } Menu root; -- cgit v1.2.3 From 3c07d07d3ce971d9abcc19ab58429353384cbeb4 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Sun, 2 Mar 2014 20:05:00 -0600 Subject: Disconnect notify when removing the player --- src/service.vala | 2 ++ 1 file changed, 2 insertions(+) (limited to 'src') diff --git a/src/service.vala b/src/service.vala index f1a002f..490e242 100644 --- a/src/service.vala +++ b/src/service.vala @@ -401,6 +401,8 @@ public class IndicatorSound.Service: Object { this.actions.remove_action ("previous." + player.id); this.actions.remove_action ("play-playlist." + player.id); + player.notify.disconnect (this.eventually_update_player_actions); + this.menus.@foreach ( (profile, menu) => menu.remove_player (player)); this.update_preferred_players (); -- cgit v1.2.3 From bb6dabf8052f9f9f5ed57a0a73ab4be29d9da020 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Sun, 2 Mar 2014 20:23:30 -0600 Subject: Making it so that we can raise the player, which should make it enabled --- src/media-player-user.vala | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/media-player-user.vala b/src/media-player-user.vala index 37f54a9..dfe6229 100644 --- a/src/media-player-user.vala +++ b/src/media-player-user.vala @@ -188,7 +188,7 @@ public class MediaPlayerUser : MediaPlayer { /* If it's shown externally it's running */ public override bool is_running { get { return proxy_is_valid(); } } /* A bit weird. Not sure how we should handle this. */ - public override bool can_raise { get { return false; } } + public override bool can_raise { get { return true; } } /* Fill out the track based on the values in the proxy */ MediaPlayer.Track track_cache; -- cgit v1.2.3 From 0d6e0d7dc3c4213cb6fc265b427b8d871fc45bf4 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Sun, 2 Mar 2014 20:36:40 -0600 Subject: Make enabled work the same was when the properties get updated --- src/service.vala | 1 + 1 file changed, 1 insertion(+) (limited to 'src') diff --git a/src/service.vala b/src/service.vala index 490e242..a35d465 100644 --- a/src/service.vala +++ b/src/service.vala @@ -366,6 +366,7 @@ public class IndicatorSound.Service: Object { this.menus.@foreach ( (profile, menu) => menu.add_player (player)); SimpleAction action = new SimpleAction.stateful (player.id, null, this.action_state_for_player (player)); + action.set_enabled (player.can_raise); action.activate.connect ( () => { player.activate (); }); this.actions.add_action (action); -- cgit v1.2.3 From c046c8f4bf047668341745a0d573a2b9ce4f1964 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Sun, 2 Mar 2014 20:39:27 -0600 Subject: Use the detail to make this a little cleaner --- src/service.vala | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/service.vala b/src/service.vala index a35d465..075c6df 100644 --- a/src/service.vala +++ b/src/service.vala @@ -373,9 +373,8 @@ public class IndicatorSound.Service: Object { var play_action = new SimpleAction.stateful ("play." + player.id, null, player.state); play_action.activate.connect ( () => player.play_pause () ); this.actions.add_action (play_action); - player.notify.connect ( (object, pspec) => { - if (pspec.name == "state") - play_action.set_state (player.state); + player.notify["state"].connect ( (object, pspec) => { + play_action.set_state (player.state); }); var next_action = new SimpleAction ("next." + player.id, null); -- cgit v1.2.3 From a78e8bd5d95b4da3d6ae70d4fd280f61adee6fef Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Sun, 2 Mar 2014 21:38:36 -0600 Subject: More debug information --- src/sound-menu.vala | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/sound-menu.vala b/src/sound-menu.vala index 2df1a52..4b33543 100644 --- a/src/sound-menu.vala +++ b/src/sound-menu.vala @@ -154,7 +154,7 @@ class SoundMenu: Object var section = new Menu (); Icon icon; - debug("Adding section for player: %s", player.id); + debug("Adding section for player: %s (%s)", player.id, player.is_running ? "running" : "not running"); icon = player.icon; if (icon == null) -- cgit v1.2.3 From 778db7d1a428bbdbaa17ca271da76ddeb3ee978a Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 3 Mar 2014 09:02:59 -0600 Subject: Sound menu doesn't need MPRIS, that's all in the player --- src/CMakeLists.txt | 1 - 1 file changed, 1 deletion(-) (limited to 'src') diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 436a154..f2c6cec 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -95,7 +95,6 @@ vala_add(indicator-sound-service sound-menu.vala DEPENDS media-player - mpris2-interfaces ) vala_add(indicator-sound-service accounts-service-user.vala -- cgit v1.2.3 From e2e27b5e147d08e150eefd9d64dcb504594f86b8 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 3 Mar 2014 10:43:31 -0600 Subject: Setting up a basic sound menu test --- src/sound-menu.vala | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/sound-menu.vala b/src/sound-menu.vala index 4b33543..74da887 100644 --- a/src/sound-menu.vala +++ b/src/sound-menu.vala @@ -17,7 +17,7 @@ * Lars Uebernickel */ -class SoundMenu: Object +public class SoundMenu: Object { public enum DisplayFlags { NONE = 0, -- cgit v1.2.3 From cc8600927594dcdfcba74813788d90c999156468 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 3 Mar 2014 11:11:32 -0600 Subject: Test the number of entries in the menu --- src/sound-menu.vala | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/sound-menu.vala b/src/sound-menu.vala index 74da887..8c087bc 100644 --- a/src/sound-menu.vala +++ b/src/sound-menu.vala @@ -123,8 +123,8 @@ public class SoundMenu: Object this.notify_handlers.remove (player); } - Menu root; - Menu menu; + public Menu root; + public Menu menu; Menu volume_section; bool mic_volume_shown; bool settings_shown = false; -- cgit v1.2.3 From 621efbb8d9728da645aa1c9aeac6068f395c8dc2 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 3 Mar 2014 11:34:58 -0600 Subject: Check all the menu items, that way we don't have to handle all the exceptions --- src/sound-menu.vala | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/sound-menu.vala b/src/sound-menu.vala index 8c087bc..e4b8ad1 100644 --- a/src/sound-menu.vala +++ b/src/sound-menu.vala @@ -135,8 +135,8 @@ public class SoundMenu: Object int find_player_section (MediaPlayer player) { debug("Looking for player: %s", player.id); string action_name = @"indicator.$(player.id)"; - int n = this.menu.get_n_items () -1; - for (int i = 1; i < n; i++) { + int n = this.menu.get_n_items (); + for (int i = 0; i < n; i++) { var section = this.menu.get_item_link (i, Menu.LINK_SECTION); if (section == null) continue; -- cgit v1.2.3 From b26ca3dc5f4aa49584b402d98cfea976f0966eb9 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 3 Mar 2014 12:46:48 -0600 Subject: Blocking all '*' users --- src/media-player-list-greeter.vala | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala index 5acfe16..33bf1d6 100644 --- a/src/media-player-list-greeter.vala +++ b/src/media-player-list-greeter.vala @@ -66,7 +66,7 @@ public class MediaPlayerListGreeter : MediaPlayerList { var old_user = selected_user; /* Protect against a null user */ - if (active_user != "" && active_user != "*guest") { + if (active_user != "" && active_user[0] != '*') { selected_user = active_user; } else { selected_user = null; -- cgit v1.2.3 From 72e697f81e37c2fb5a08cf037ca550d7650bf827 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 3 Mar 2014 12:48:00 -0600 Subject: Print a debug message when the active user changes --- src/media-player-list-greeter.vala | 2 ++ 1 file changed, 2 insertions(+) (limited to 'src') diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala index 33bf1d6..fce3266 100644 --- a/src/media-player-list-greeter.vala +++ b/src/media-player-list-greeter.vala @@ -63,6 +63,8 @@ public class MediaPlayerListGreeter : MediaPlayerList { return; } + debug(@"Active user changed to: $active_user"); + var old_user = selected_user; /* Protect against a null user */ -- cgit v1.2.3 From aaabe3c2c523f07e2d9e7ac1b549a53bbfdd0ef1 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Mon, 3 Mar 2014 13:28:24 -0600 Subject: Debug message for the blocked user --- src/media-player-list-greeter.vala | 1 + 1 file changed, 1 insertion(+) (limited to 'src') diff --git a/src/media-player-list-greeter.vala b/src/media-player-list-greeter.vala index fce3266..15e4c55 100644 --- a/src/media-player-list-greeter.vala +++ b/src/media-player-list-greeter.vala @@ -71,6 +71,7 @@ public class MediaPlayerListGreeter : MediaPlayerList { if (active_user != "" && active_user[0] != '*') { selected_user = active_user; } else { + debug(@"Blocking active user change for '$active_user'"); selected_user = null; } -- cgit v1.2.3 From 8c23ea52648f4555403acf42a096e83853ff7e08 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Tue, 4 Mar 2014 15:29:57 -0600 Subject: Make it so the desktop greeter doesn't have any players on it --- src/service.vala | 2 +- src/sound-menu.vala | 8 +++++++- 2 files changed, 8 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/service.vala b/src/service.vala index 075c6df..b4dae65 100644 --- a/src/service.vala +++ b/src/service.vala @@ -35,7 +35,7 @@ public class IndicatorSound.Service: Object { this.actions.add_action (this.create_mic_volume_action ()); this.menus = new HashTable (str_hash, str_equal); - this.menus.insert ("desktop_greeter", new SoundMenu (null, SoundMenu.DisplayFlags.SHOW_MUTE | SoundMenu.DisplayFlags.HIDE_INACTIVE_PLAYERS)); + this.menus.insert ("desktop_greeter", new SoundMenu (null, SoundMenu.DisplayFlags.SHOW_MUTE | SoundMenu.DisplayFlags.DONT_SHOW_PLAYERS)); this.menus.insert ("desktop", new SoundMenu ("indicator.desktop-settings", SoundMenu.DisplayFlags.SHOW_MUTE)); this.menus.insert ("phone", new SoundMenu ("indicator.phone-settings", SoundMenu.DisplayFlags.HIDE_INACTIVE_PLAYERS)); diff --git a/src/sound-menu.vala b/src/sound-menu.vala index e4b8ad1..ebb7632 100644 --- a/src/sound-menu.vala +++ b/src/sound-menu.vala @@ -22,7 +22,8 @@ public class SoundMenu: Object public enum DisplayFlags { NONE = 0, SHOW_MUTE = 1, - HIDE_INACTIVE_PLAYERS = 2 + HIDE_INACTIVE_PLAYERS = 2, + DONT_SHOW_PLAYERS = 4 } public SoundMenu (string? settings_action, DisplayFlags flags) { @@ -31,6 +32,8 @@ public class SoundMenu: Object * it has a dynamic amount of player sections, one for each registered player. */ + this.no_players = ((flags & DisplayFlags.DONT_SHOW_PLAYERS) != 0); + this.volume_section = new Menu (); if ((flags & DisplayFlags.SHOW_MUTE) != 0) volume_section.append (_("Mute"), "indicator.mute"); @@ -87,6 +90,8 @@ public class SoundMenu: Object } public void add_player (MediaPlayer player) { + if (this.no_players) + return; if (this.notify_handlers.contains (player)) return; @@ -129,6 +134,7 @@ public class SoundMenu: Object bool mic_volume_shown; bool settings_shown = false; bool hide_inactive; + bool no_players; HashTable notify_handlers; /* returns the position in this.menu of the section that's associated with @player */ -- cgit v1.2.3 From e9f0b68ab8b9afec9466011b8a8bae3b202b4bf9 Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Tue, 4 Mar 2014 15:38:07 -0600 Subject: Adding a specific phone_greeter profile --- src/service.vala | 1 + 1 file changed, 1 insertion(+) (limited to 'src') diff --git a/src/service.vala b/src/service.vala index b4dae65..ca00caa 100644 --- a/src/service.vala +++ b/src/service.vala @@ -36,6 +36,7 @@ public class IndicatorSound.Service: Object { this.menus = new HashTable (str_hash, str_equal); this.menus.insert ("desktop_greeter", new SoundMenu (null, SoundMenu.DisplayFlags.SHOW_MUTE | SoundMenu.DisplayFlags.DONT_SHOW_PLAYERS)); + this.menus.insert ("phone_greeter", new SoundMenu (null, SoundMenu.DisplayFlags.SHOW_MUTE | SoundMenu.DisplayFlags.HIDE_INACTIVE_PLAYERS)); this.menus.insert ("desktop", new SoundMenu ("indicator.desktop-settings", SoundMenu.DisplayFlags.SHOW_MUTE)); this.menus.insert ("phone", new SoundMenu ("indicator.phone-settings", SoundMenu.DisplayFlags.HIDE_INACTIVE_PLAYERS)); -- cgit v1.2.3 From 1a857591cec4d3d47080732c3703ca57e037db0c Mon Sep 17 00:00:00 2001 From: Ted Gould Date: Thu, 13 Mar 2014 13:57:22 -0500 Subject: Make sure to clean up the timer --- src/accounts-service-user.vala | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'src') diff --git a/src/accounts-service-user.vala b/src/accounts-service-user.vala index f021764..052c7a0 100644 --- a/src/accounts-service-user.vala +++ b/src/accounts-service-user.vala @@ -101,6 +101,11 @@ public class AccountsServiceUser : Object { ~AccountsServiceUser () { this.player = null; + + if (this.timer != 0) { + GLib.Source.remove(this.timer); + this.timer = 0; + } } void new_proxy (GLib.Object? obj, AsyncResult res) { -- cgit v1.2.3