diff --git a/emmental/__init__.py b/emmental/__init__.py index 7a485d1..6e24739 100644 --- a/emmental/__init__.py +++ b/emmental/__init__.py @@ -66,7 +66,13 @@ class Application(Adw.Application): def build_now_playing(self) -> nowplaying.Card: """Build a new now playing card.""" - return nowplaying.Card() + playing = nowplaying.Card() + for prop in ["title", "album", "artist", "album-artist"]: + self.player.bind_property(prop, playing, prop) + self.db.settings.bind_setting("now-playing.prefer-artist", + playing, "prefer-artist") + + return playing def build_window(self) -> window.Window: """Build a new window instance.""" diff --git a/emmental/nowplaying/__init__.py b/emmental/nowplaying/__init__.py index 5bb9345..f177360 100644 --- a/emmental/nowplaying/__init__.py +++ b/emmental/nowplaying/__init__.py @@ -1,15 +1,31 @@ # Copyright 2022 (c) Anna Schumaker. """A card for displaying information about the currently playing track.""" +from gi.repository import GObject from gi.repository import Gtk +from . import tags class Card(Gtk.Box): """The Now Playing information card.""" + title = GObject.Property(type=str) + album = GObject.Property(type=str) + artist = GObject.Property(type=str) + album_artist = GObject.Property(type=str) + prefer_artist = GObject.Property(type=bool, default=True) + def __init__(self): """Initialize a Now Playing Card.""" super().__init__() self._grid = Gtk.Grid() + self._tags = tags.TagInfo() + + for prop in ["title", "album", "artist", "album-artist"]: + self.bind_property(prop, self._tags, prop) + self.bind_property("prefer-artist", self._tags, "prefer-artist", + GObject.BindingFlags.BIDIRECTIONAL) + + self._grid.attach(self._tags, 0, 0, 1, 1) self.append(self._grid) self.add_css_class("card") diff --git a/tests/nowplaying/test_nowplaying.py b/tests/nowplaying/test_nowplaying.py index 69221f2..abb8ade 100644 --- a/tests/nowplaying/test_nowplaying.py +++ b/tests/nowplaying/test_nowplaying.py @@ -19,3 +19,28 @@ class TestNowPlaying(unittest.TestCase): self.assertEqual(self.card.get_last_child(), self.card._grid) self.assertTrue(self.card.has_css_class("card")) + + def test_prefer_artist(self): + """Test the 'prefer-artist' property.""" + self.assertTrue(self.card.prefer_artist) + + self.card.prefer_artist = False + self.assertFalse(self.card.prefer_artist) + self.assertFalse(self.card._tags.prefer_artist) + + self.card._tags.prefer_artist = True + self.assertTrue(self.card.prefer_artist) + self.assertTrue(self.card._tags.prefer_artist) + + def test_tags(self): + """Test tag properties.""" + self.assertIsInstance(self.card._tags, + emmental.nowplaying.tags.TagInfo) + self.assertEqual(self.card._grid.get_child_at(0, 0), self.card._tags) + + for tag in ["title", "album", "artist", "album-artist"]: + with self.subTest(tag=tag): + self.card.set_property(tag, f"test {tag}") + self.assertEqual(self.card.get_property(tag), f"test {tag}") + self.assertEqual(self.card._tags.get_property(tag), + f"test {tag}") diff --git a/tests/test_emmental.py b/tests/test_emmental.py index d7e6154..ac8a97c 100644 --- a/tests/test_emmental.py +++ b/tests/test_emmental.py @@ -103,6 +103,19 @@ class TestEmmental(unittest.TestCase): self.assertEqual(win.header.title, emmental.VERSION_STRING) + @unittest.mock.patch("sys.stdout", new_callable=io.StringIO) + def test_nowplaying(self, mock_stdout: io.StringIO): + """Check that the nowplaying widget is wired up properly.""" + self.application.db = emmental.db.Connection() + self.application.player = emmental.audio.Player() + win = self.application.build_window() + + for tag in ["title", "album", "artist", "album-artist"]: + with self.subTest(tag=tag): + self.assertEqual(win.now_playing.get_property(tag), "") + self.application.player.set_property(tag, "Test Tag") + self.assertEqual(win.now_playing.get_property(tag), "Test Tag") + @unittest.mock.patch("sys.stdout", new_callable=io.StringIO) def test_replaygain(self, mock_stdout: io.StringIO): """Test setting replaygain modes.""" diff --git a/tests/test_settings.py b/tests/test_settings.py index 4948087..e4a7a3d 100644 --- a/tests/test_settings.py +++ b/tests/test_settings.py @@ -88,3 +88,13 @@ class TestSettings(unittest.TestCase): self.assertEqual(self.settings["now-playing.size"], 400) self.assertEqual(self.app.build_window().now_playing_size, 400) + + def test_save_nowplaying_prefer_artist(self, mock_stdout: io.StringIO): + """Check saving and loading the prefer-artist setting.""" + self.assertTrue(self.win.now_playing.prefer_artist) + self.assertTrue(self.settings["now-playing.prefer-artist"]) + + self.win.now_playing.prefer_artist = False + self.assertFalse(self.settings["now-playing.prefer-artist"]) + + self.assertFalse(self.app.build_window().now_playing.prefer_artist)