[gnome-music] First code for the playlist class



commit 9c8eea4b05dea386bb1fb521280837f0caf4a754
Author: CÃsar GarcÃa Tapia <cesar garcia tapia openshine com>
Date:   Mon Oct 29 22:01:36 2012 +0100

    First code for the playlist class

 src/Makefile.am                |    3 +-
 src/music-app.vala             |   30 +++++----
 src/music-clickable-label.vala |    8 +++
 src/music-playlist-songs.vala  |  129 ++++++++++++----------------------------
 src/music-playlist-view.vala   |   14 ++--
 src/music-playlist.vala        |  130 ++++++++++++++++++++++++++++++++++++++++
 6 files changed, 202 insertions(+), 112 deletions(-)
---
diff --git a/src/Makefile.am b/src/Makefile.am
index 5c016a8..fad167b 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -27,9 +27,10 @@ vala_sources = \
         music-player.vala       	\
 		music-collection-view.vala	\
 		music-list-store.vala		\
+		music-playlist.vala 		\
 		music-playlist-view.vala	\
-		music-album-info-box.vala	\
 		music-playlist-songs.vala	\
+		music-album-info-box.vala	\
 		music-browse-history.vala	\
 		music-clickable-label.vala 	\
 		music-utils.vala			\
diff --git a/src/music-app.vala b/src/music-app.vala
index 59da043..39968bc 100644
--- a/src/music-app.vala
+++ b/src/music-app.vala
@@ -45,6 +45,8 @@ private class Music.App {
     public Music.PlaylistView playlistView;
     public Gtk.Notebook notebook;
 
+    public Music.Playlist playlist;
+
     private Gtk.Application application;
 
     public Music.BrowseHistory browse_history;
@@ -76,15 +78,8 @@ private class Music.App {
         browse_history.changed.connect (on_browse_history_changed);
 
         application.startup.connect_after ((app) => {
-            var menu = new GLib.Menu ();
-            menu.append (_("New"), "app.new");
-            menu.append (_("About Music"), "app.about");
-            menu.append (_("Quit"), "app.quit");
-
-            application.set_app_menu (menu);
-
             setup_menu ();
-            setup_ui (); 
+            setup_app (); 
         });
 
         application.activate.connect_after ((app) => {
@@ -99,6 +94,13 @@ private class Music.App {
     }
 
     private void setup_menu () {
+        var menu = new GLib.Menu ();
+        menu.append (_("New"), "app.new");
+        menu.append (_("About Music"), "app.about");
+        menu.append (_("Quit"), "app.quit");
+
+        application.set_app_menu (menu);
+
         var action = new GLib.SimpleAction ("quit", null);
         action.activate.connect (() => { quit (); });
         application.add_action (action);
@@ -116,7 +118,7 @@ private class Music.App {
                                    "authors", authors,
                                    "translator-credits", _("translator-credits"),
                                    "comments", _("A GNOME 3 application to listen and manage music playlists"),
-                                   "copyright", "Copyright 2012 OpenShine SL.",
+                                   "copyright", "Copyright 2012 CÃsar GarcÃa Tapia",
                                    "license-type", Gtk.License.LGPL_2_1,
                                    "logo-icon-name", "gnome-music",
                                    "version", Config.PACKAGE_VERSION,
@@ -126,7 +128,7 @@ private class Music.App {
         application.add_action (action);
     }
 
-    private void setup_ui () {
+    private void setup_app () {
         window = new Gtk.ApplicationWindow (application);
         window.show_menubar = false;
         window.hide_titlebar_when_maximized = true;
@@ -184,8 +186,10 @@ private class Music.App {
         collectionView.item_selected.connect (on_collectionview_selected_item);
         notebook.append_page (collectionView.actor, null);
 
-        playlistView = new Music.PlaylistView ();
-        playlistView.song_selected.connect (on_playlistview_song_selected);
+        playlist = new Music.Playlist();
+        playlist.song_selected.connect (on_playlist_song_selected);
+
+        playlistView = new Music.PlaylistView (playlist);
         notebook.append_page (playlistView.actor, null);
 
         player = new Music.Player ();
@@ -224,7 +228,7 @@ private class Music.App {
         }
     }
 
-    private void on_playlistview_song_selected (Grl.Media media) {
+    private void on_playlist_song_selected (Grl.Media media, int index) {
         player.load (media);
     }
 
diff --git a/src/music-clickable-label.vala b/src/music-clickable-label.vala
index e99fbaf..02672d9 100644
--- a/src/music-clickable-label.vala
+++ b/src/music-clickable-label.vala
@@ -51,6 +51,14 @@ private class Music.ClickableLabel : Gtk.EventBox {
  		label.set_label (text);
  	}
 
+ 	public string get_label () {
+ 		return label.get_label ();
+ 	}
+
+ 	public void show () {
+ 		this.show_all();
+ 	}
+
  	public void set_style (string style) {
  		label.get_style_context ().add_class (style);
  	}
diff --git a/src/music-playlist-songs.vala b/src/music-playlist-songs.vala
index 213f7ec..05aad0b 100644
--- a/src/music-playlist-songs.vala
+++ b/src/music-playlist-songs.vala
@@ -16,78 +16,33 @@
  */
 
 using Gtk;
-using Gee;
 
 private class Music.PlaylistSongs {
     public Gtk.Widget actor { get { return alignment; } }
 
-    public signal void song_selected (Grl.Media media);
+    private Music.Playlist playlist;
 
     private Gtk.Alignment alignment;
     private Gtk.Grid grid;
 
-    private HashMap<string, Grl.Source> source_list = new HashMap<string, Grl.Source> ();
+    private int current_song = 0;
 
-    public PlaylistSongs () {
-        set_grl ();
+    public PlaylistSongs (Music.Playlist playlist) {
+        this.playlist = playlist;
+        this.playlist.changed.connect (on_playlist_changed);
+        this.playlist.song_selected.connect (on_playlist_song_selected);
 
         alignment = new Gtk.Alignment ((float)0.5, (float)0.5, 0, 0);
         alignment.show_all ();
     }
 
-    public void load (Grl.Media media) {
-        grid = new Gtk.Grid ();
-        grid.set_column_spacing (10);
-        grid.set_row_spacing (10);
-        grid.show();
+    private void on_playlist_changed () {
+        clear_grid ();
 
-        var child = alignment.get_child ();
-        if (child != null) {
-            alignment.remove (child);
-        }
-        alignment.add (grid);
-
-        if (media is Grl.MediaBox) {
-            unowned GLib.List keys = Grl.MetadataKey.list_new (Grl.MetadataKey.ID,
-                                                               Grl.MetadataKey.TITLE,
-                                                               Grl.MetadataKey.URL);
-
-            Grl.Caps caps = null;
-            Grl.OperationOptions options = new Grl.OperationOptions(caps);
-            options.set_skip (0);
-            options.set_count (1000000);
-            options.set_flags (Grl.ResolutionFlags.NORMAL);
-
-            var id = media.get_id ();
-
-            var query = @"SELECT rdf:type (?song)
-                                 ?song
-                                 tracker:id(?song) AS id
-                                 nie:title(?song) AS title
-                                 ?duration
-                                 ?url
-                                 tracker:coalesce (nie:title(?album), '') AS site
-                                 tracker:coalesce (nmm:artistName(?artist), '') AS author
-                          WHERE { ?song a nmm:MusicPiece;
-                                        nfo:duration ?duration;
-                                        nie:url ?url;
-                                        nmm:musicAlbum ?album FILTER (tracker:id (?album) = $id ) .
-                                  OPTIONAL { ?song nmm:musicAlbum ?album } .
-                                  OPTIONAL { ?album nmm:albumArtist ?artist }
-                          }";
-            debug (query);
-
-            foreach (var source in source_list.values) {
-                source.query (query, keys, options, (source, query_id, media, remaining, error) => {
-                    load_item_cb (media, remaining);
-                });
-            }
-        }
-    }
+        foreach (Grl.Media media in playlist) {
+            var image = new Gtk.Image.from_icon_name ("media-playback-start-symbolic", IconSize.BUTTON);
+            image.hide();
 
-    private void load_item_cb (Grl.Media? media,
-                               uint remaining) {
-        if (media != null) {
             var title = new Music.ClickableLabel (media.get_title());
             title.set_alignment (0, (float)0.5);
             title.clicked.connect (() => {
@@ -99,50 +54,42 @@ private class Music.PlaylistSongs {
             length.set_alignment (1, (float)0.5);
             length.get_style_context ().add_class ("dim-label");
 
-            grid.attach_next_to (title, null, Gtk.PositionType.BOTTOM, 1, 1);
+            grid.attach_next_to (image, null, Gtk.PositionType.BOTTOM, 1, 1);
+            grid.attach_next_to (title, image, Gtk.PositionType.RIGHT, 1, 1);
             grid.attach_next_to (length, title, Gtk.PositionType.RIGHT, 1, 1);
 
-            grid.show_all ();
+            image.hide();
+            title.show();
+            length.show();
+        }
+    }
+    public void clear_grid () {
+        var child = alignment.get_child ();
+        if (child != null) {
+            alignment.remove (child);
         }
+        
+        grid = new Gtk.Grid ();
+        grid.set_column_spacing (10);
+        grid.set_row_spacing (10);
+        alignment.add (grid);
+        grid.show_all ();
     }
 
     private void on_title_clicked (Grl.Media media) {
-        song_selected (media);
-
+        playlist.select (media);
     }
 
-    private void set_grl () {
-        var registry = Grl.Registry.get_default ();
+    private void on_playlist_song_selected (Grl.Media media, int index) {
+        debug (current_song.to_string());
+        var image = grid.get_child_at(0, current_song);
+        if (image != null) {
+            image.hide();
+        }
 
-		registry.source_added.connect (source_added_cb);
-		registry.source_removed.connect (source_removed_cb);
+        image = grid.get_child_at(0, index);
+        image.show();
 
-		if (registry.load_all_plugins () == false) {
-			error ("Failed to load plugins.");
-		}
+        current_song = index;
     }
-
-    private void source_added_cb (Grl.Source source) {
-        // FIXME: We're only handling Tracker by now
-        if (source.get_id() != "grl-tracker-source") {
-            return;
-        }
-
-        debug ("Checking source: %s", source.get_id());
-
-		var ops = source.supported_operations ();
-		if ((ops & Grl.SupportedOps.QUERY) != 0) {
-			debug ("Detected new source availabe: '%s' and it supports queries", source.get_name ());
-			source_list.set (source.get_id(), source as Grl.Source);
-		}
-	}
-
-	private void source_removed_cb (Grl.Source source) {
-        foreach (var id in source_list.keys) {
-            if (id == source.get_id()) {
-		        debug ("Source '%s' is gone", source.get_name ());
-                source_list.unset (id);
-            }
-        }
-	}
 }
diff --git a/src/music-playlist-view.vala b/src/music-playlist-view.vala
index ba0ef0e..896e7e3 100644
--- a/src/music-playlist-view.vala
+++ b/src/music-playlist-view.vala
@@ -21,13 +21,15 @@ using Gee;
 private class Music.PlaylistView {
     public Gtk.Widget actor { get { return scrolled_window; } }
 
-    public signal void song_selected (Grl.Media media);
+    private Music.Playlist playlist;
 
     private Gtk.ScrolledWindow scrolled_window;
     private Music.AlbumInfoBox album_info_box;
     private Music.PlaylistSongs playlist_songs;
 
-    public PlaylistView () {
+    public PlaylistView (Music.Playlist playlist) {
+        this.playlist = playlist;
+
         setup_view ();
     }
 
@@ -43,10 +45,7 @@ private class Music.PlaylistView {
         layout.pack_start (album_info_box.actor, false, false);
 
         /* Playlist songs Box */
-        playlist_songs = new Music.PlaylistSongs ();
-        playlist_songs.song_selected.connect ((media) => {
-            song_selected (media);
-        });
+        playlist_songs = new Music.PlaylistSongs (playlist);
         layout.pack_start (playlist_songs.actor, false, false);
 
         scrolled_window = new Gtk.ScrolledWindow (null, null);
@@ -59,6 +58,7 @@ private class Music.PlaylistView {
 
     public void load (Grl.Media media) {
         album_info_box.load (media);
-        playlist_songs.load (media);
+
+        playlist.load_album (media);
     }
 }
diff --git a/src/music-playlist.vala b/src/music-playlist.vala
new file mode 100644
index 0000000..71bfbc2
--- /dev/null
+++ b/src/music-playlist.vala
@@ -0,0 +1,130 @@
+/*
+ * Copyright (C) 2012 Cesar Garcia Tapia <tapia openshine com>
+ *
+ * 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; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * 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 <http://www.gnu.org/licenses/>.
+ */
+
+private class Music.Playlist: Object, Gee.Iterable<Grl.Media> {
+	public signal void song_selected (Grl.Media media, int index);
+	public signal void changed ();
+
+	private Gee.ArrayList<Grl.Media> list;
+	private int current_index = 0;
+
+	private Gee.HashMap<string, Grl.Source> source_list = new Gee.HashMap<string, Grl.Source> ();
+
+	public Playlist () {
+        set_grl ();
+        list = new Gee.ArrayList<Grl.Media> ();
+	}
+
+	public void select (Grl.Media media) {
+		if (media in list) {
+			current_index = list.index_of (media);
+			song_selected (media, current_index);
+		}
+	}
+
+	public void load_album (Grl.Media media) {
+		if (media is Grl.MediaBox) {
+			list.clear();
+
+            unowned GLib.List keys = Grl.MetadataKey.list_new (Grl.MetadataKey.ID,
+                                                               Grl.MetadataKey.TITLE,
+                                                               Grl.MetadataKey.URL);
+
+            Grl.Caps caps = null;
+            Grl.OperationOptions options = new Grl.OperationOptions(caps);
+            options.set_skip (0);
+            options.set_count (1000000);
+            options.set_flags (Grl.ResolutionFlags.NORMAL);
+
+            var id = media.get_id ();
+
+            var query = @"SELECT rdf:type (?song)
+                                 ?song
+                                 tracker:id(?song) AS id
+                                 tracker:coalesce (nie:title(?song), nfo:fileName(?song)) AS title
+                                 ?duration
+                                 nie:url(?song) AS url
+                                 tracker:coalesce (nie:title(?album), '') AS site
+                                 tracker:coalesce (nmm:artistName(?artist), '') AS author
+                          WHERE { ?song a nmm:MusicPiece;
+                                        nfo:duration ?duration;
+                                        nmm:musicAlbum ?album FILTER (tracker:id (?album) = $id ) .
+                                  OPTIONAL { ?song nmm:musicAlbum ?album } .
+                                  OPTIONAL { ?album nmm:albumArtist ?artist }
+                          }";
+            debug (query);
+
+            foreach (var source in source_list.values) {
+                source.query (query, keys, options, (source, query_id, media, remaining, error) => {
+                    load_item_cb (media, remaining);
+                });
+            }
+        }
+	}
+
+	private void load_item_cb (Grl.Media? media,
+                               uint remaining) {
+        if (media != null) {
+        	list.add (media);
+        }
+
+        if (remaining == 0) {
+        	changed();
+        }
+    }
+
+	private void set_grl () {
+        var registry = Grl.Registry.get_default ();
+
+		registry.source_added.connect (source_added_cb);
+		registry.source_removed.connect (source_removed_cb);
+    }
+
+    private void source_added_cb (Grl.Source source) {
+        // FIXME: We're only handling Tracker by now
+        if (source.get_id() != "grl-tracker-source") {
+            return;
+        }
+
+        debug ("Checking source: %s", source.get_id());
+
+		var ops = source.supported_operations ();
+		if ((ops & Grl.SupportedOps.QUERY) != 0) {
+			debug ("Detected new source availabe: '%s' and it supports queries", source.get_name ());
+			source_list.set (source.get_id(), source as Grl.Source);
+		}
+	}
+
+	private void source_removed_cb (Grl.Source source) {
+        foreach (var id in source_list.keys) {
+            if (id == source.get_id()) {
+		        debug ("Source '%s' is gone", source.get_name ());
+                source_list.unset (id);
+            }
+        }
+	}
+
+	//Iterator methods
+
+	public Type element_type {
+        get { return typeof (Grl.Media); }
+    }
+
+    public Gee.Iterator<Grl.Media> iterator () {
+        return list.iterator();
+    }
+}
\ No newline at end of file



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