tracklist: Add a SortFieldWidget
This Widget is intended to be used as the child widget in a Gtk.ListView to display and change the sort order of the current playlist. I use arrow buttons from the icon library to represent sort order Signed-off-by: Anna Schumaker <Anna@NoWheyCreamery.com>
This commit is contained in:
parent
83355f7e96
commit
ed4a484a31
|
@ -3,6 +3,7 @@
|
|||
from gi.repository import GObject
|
||||
from gi.repository import Gio
|
||||
from gi.repository import Gtk
|
||||
from . import sorter
|
||||
from .. import buttons
|
||||
from .. import factory
|
||||
|
||||
|
@ -99,3 +100,65 @@ class ShuffleButton(buttons.ImageToggle):
|
|||
def do_toggled(self):
|
||||
"""Adjust opacity when active state toggles."""
|
||||
self.icon_opacity = 1.0 if self.active else 0.5
|
||||
|
||||
|
||||
class SortFieldWidget(Gtk.Box):
|
||||
"""A Widget to display in the Sort Order button popover."""
|
||||
|
||||
sort_field = GObject.Property(type=sorter.SortField)
|
||||
|
||||
def __init__(self) -> None:
|
||||
"""Initialize a SortField Widget."""
|
||||
super().__init__(spacing=6)
|
||||
self._enabled = Gtk.Switch(valign=Gtk.Align.CENTER)
|
||||
self._name = Gtk.Label(hexpand=True, sensitive=False)
|
||||
self._reverse = buttons.ImageToggle("arrow1-up", "arrow1-down",
|
||||
icon_size=Gtk.IconSize.NORMAL,
|
||||
sensitive=False)
|
||||
self._box = Gtk.Box(sensitive=False)
|
||||
self._move_up = Gtk.Button(icon_name="go-up-symbolic")
|
||||
self._move_down = Gtk.Button(icon_name="go-down-symbolic")
|
||||
|
||||
self._enabled.bind_property("active", self._name, "sensitive")
|
||||
self._enabled.bind_property("active", self._reverse, "sensitive")
|
||||
self._enabled.bind_property("active", self._box, "sensitive")
|
||||
|
||||
self._enabled.connect("notify::active", self.__notify_enabled)
|
||||
self._reverse.connect("clicked", self.__reverse)
|
||||
self._move_up.connect("clicked", self.__move_item_up)
|
||||
self._move_down.connect("clicked", self.__move_item_down)
|
||||
|
||||
self.append(self._enabled)
|
||||
self.append(self._name)
|
||||
self.append(self._reverse)
|
||||
self.append(self._box)
|
||||
|
||||
self._box.append(self._move_up)
|
||||
self._box.append(self._move_down)
|
||||
self._box.add_css_class("linked")
|
||||
|
||||
def __move_item_down(self, button: Gtk.Button) -> None:
|
||||
if self.sort_field is not None:
|
||||
self.sort_field.move_down()
|
||||
|
||||
def __move_item_up(self, button: Gtk.Button) -> None:
|
||||
if self.sort_field is not None:
|
||||
self.sort_field.move_up()
|
||||
|
||||
def __notify_enabled(self, switch: Gtk.Switch, param) -> None:
|
||||
if self.sort_field is not None:
|
||||
if switch.get_active():
|
||||
self.sort_field.enable()
|
||||
else:
|
||||
self.sort_field.disable()
|
||||
|
||||
def __reverse(self, button: buttons.ImageToggle) -> None:
|
||||
if self.sort_field is not None:
|
||||
self.sort_field.reverse()
|
||||
|
||||
def set_sort_field(self, field: sorter.SortField | None) -> None:
|
||||
"""Set the Sort Field displayed by this Widget."""
|
||||
self.sort_field = field
|
||||
self._name.set_text(field.name if field is not None else "")
|
||||
self._enabled.set_active(field is not None and field.enabled)
|
||||
self._reverse.active = field is not None and field.reversed
|
||||
|
|
|
@ -0,0 +1,2 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" height="16px" viewBox="0 0 16 16" width="16px"><path d="m 12 7 h -1 c -0.257812 0 -0.53125 0.128906 -0.71875 0.3125 l -1.28125 1.28125 v -8.59375 h -2 v 8.59375 l -1.28125 -1.28125 c -0.191406 -0.183594 -0.460938 -0.3125 -0.71875 -0.3125 h -1 v 1 c 0 0.308594 0.089844 0.550781 0.28125 0.75 l 3.71875 3.65625 l 3.71875 -3.65625 c 0.191406 -0.199219 0.28125 -0.441406 0.28125 -0.75 z m 0 0" fill="#222222"/></svg>
|
After Width: | Height: | Size: 492 B |
|
@ -0,0 +1,2 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" height="16px" viewBox="0 0 16 16" width="16px"><path d="m 12 9 h -1 c -0.257812 0 -0.53125 -0.128906 -0.71875 -0.3125 l -1.28125 -1.28125 v 8.59375 h -2 v -8.59375 l -1.28125 1.28125 c -0.191406 0.183594 -0.460938 0.3125 -0.71875 0.3125 h -1 v -1 c 0 -0.308594 0.089844 -0.550781 0.28125 -0.75 l 3.71875 -3.65625 l 3.71875 3.65625 c 0.191406 0.199219 0.28125 0.441406 0.28125 0.75 z m 0 0" fill="#222222"/></svg>
|
After Width: | Height: | Size: 492 B |
|
@ -157,3 +157,121 @@ class TestShuffleButtons(unittest.TestCase):
|
|||
self.assertEqual(self.shuffle.icon_opacity, 1.0)
|
||||
self.shuffle.active = False
|
||||
self.assertEqual(self.shuffle.icon_opacity, 0.5)
|
||||
|
||||
|
||||
class TestSortFieldWidget(unittest.TestCase):
|
||||
"""Test the Sort Field widget."""
|
||||
|
||||
def setUp(self):
|
||||
"""Set up common variables."""
|
||||
self.sort = emmental.tracklist.buttons.SortFieldWidget()
|
||||
self.model = emmental.tracklist.sorter.SortOrderModel()
|
||||
self.model[0].enable()
|
||||
self.model[0].reverse()
|
||||
|
||||
def test_init(self):
|
||||
"""Test that the Sort Field Widget is configured correctly."""
|
||||
self.assertIsInstance(self.sort, Gtk.Box)
|
||||
self.assertIsInstance(self.sort._box, Gtk.Box)
|
||||
self.assertIsInstance(self.sort._name, Gtk.Label)
|
||||
|
||||
self.assertTrue(self.sort._name.get_hexpand())
|
||||
|
||||
self.assertEqual(self.sort.get_spacing(), 6)
|
||||
self.assertEqual(self.sort._enabled.get_next_sibling(),
|
||||
self.sort._name)
|
||||
self.assertEqual(self.sort._reverse.get_next_sibling(),
|
||||
self.sort._box)
|
||||
self.assertTrue(self.sort._box.has_css_class("linked"))
|
||||
|
||||
def test_set_sort_field(self):
|
||||
"""Test setting a sort field to the Sort Field Widget."""
|
||||
self.assertIsNone(self.sort.sort_field)
|
||||
|
||||
self.sort.set_sort_field(self.model[0])
|
||||
self.assertEqual(self.sort.sort_field, self.model[0])
|
||||
self.assertEqual(self.sort._name.get_text(), self.model[0].name)
|
||||
self.assertTrue(self.sort._enabled.get_active())
|
||||
self.assertTrue(self.sort._reverse.active)
|
||||
|
||||
self.sort.set_sort_field(None)
|
||||
self.assertIsNone(self.sort.sort_field)
|
||||
self.assertEqual(self.sort._name.get_text(), "")
|
||||
self.assertFalse(self.sort._enabled.get_active())
|
||||
self.assertFalse(self.sort._reverse.active)
|
||||
|
||||
def test_enabled(self):
|
||||
"""Test enabling and disabling a sort field."""
|
||||
self.assertIsInstance(self.sort._enabled, Gtk.Switch)
|
||||
self.assertEqual(self.sort._enabled.get_valign(), Gtk.Align.CENTER)
|
||||
self.assertEqual(self.sort.get_first_child(), self.sort._enabled)
|
||||
|
||||
self.sort._enabled.set_active(True)
|
||||
|
||||
self.sort.set_sort_field(self.model[1])
|
||||
self.assertFalse(self.sort._name.get_sensitive())
|
||||
self.assertFalse(self.sort._box.get_sensitive())
|
||||
self.assertFalse(self.sort._reverse.get_sensitive())
|
||||
|
||||
self.sort._enabled.set_active(True)
|
||||
self.assertTrue(self.model[1].enabled)
|
||||
self.assertTrue(self.sort._name.get_sensitive())
|
||||
self.assertTrue(self.sort._box.get_sensitive())
|
||||
self.assertTrue(self.sort._reverse.get_sensitive())
|
||||
|
||||
self.sort._enabled.set_active(False)
|
||||
self.assertFalse(self.model[1].enabled)
|
||||
self.assertFalse(self.sort._name.get_sensitive())
|
||||
self.assertFalse(self.sort._box.get_sensitive())
|
||||
self.assertFalse(self.sort._reverse.get_sensitive())
|
||||
|
||||
def test_move_down(self):
|
||||
"""Test the moving a sort field down."""
|
||||
self.assertIsInstance(self.sort._move_down, Gtk.Button)
|
||||
self.assertEqual(self.sort._move_down.get_icon_name(),
|
||||
"go-down-symbolic")
|
||||
self.assertEqual(self.sort._move_up.get_next_sibling(),
|
||||
self.sort._move_down)
|
||||
|
||||
self.sort._move_down.emit("clicked")
|
||||
|
||||
(field := self.model[0]).enable()
|
||||
self.model[1].enable()
|
||||
self.sort.set_sort_field(field)
|
||||
|
||||
self.sort._move_down.emit("clicked")
|
||||
self.assertEqual(self.model.index(field), 1)
|
||||
|
||||
def test_move_up(self):
|
||||
"""Test the moving a sort field."""
|
||||
self.assertIsInstance(self.sort._move_up, Gtk.Button)
|
||||
self.assertEqual(self.sort._move_up.get_icon_name(), "go-up-symbolic")
|
||||
|
||||
self.assertEqual(self.sort._box.get_first_child(),
|
||||
self.sort._move_up)
|
||||
|
||||
self.sort._move_up.emit("clicked")
|
||||
|
||||
self.model[0].enable()
|
||||
(field := self.model[1]).enable()
|
||||
self.sort.set_sort_field(field)
|
||||
|
||||
self.sort._move_up.emit("clicked")
|
||||
self.assertEqual(self.model.index(field), 0)
|
||||
|
||||
def test_reverse(self):
|
||||
"""Test reversing a sort field."""
|
||||
self.assertIsInstance(self.sort._reverse, emmental.buttons.ImageToggle)
|
||||
self.assertEqual(self.sort._reverse.active_icon_name, "arrow1-up")
|
||||
self.assertEqual(self.sort._reverse.inactive_icon_name, "arrow1-down")
|
||||
self.assertEqual(self.sort._reverse.icon_size, Gtk.IconSize.NORMAL)
|
||||
self.assertEqual(self.sort._name.get_next_sibling(),
|
||||
self.sort._reverse)
|
||||
|
||||
self.sort._reverse.emit("clicked")
|
||||
|
||||
self.sort.set_sort_field(self.model[0])
|
||||
self.sort._reverse.emit("clicked")
|
||||
self.assertFalse(self.model[0].reversed)
|
||||
self.sort._reverse.emit("clicked")
|
||||
self.assertTrue(self.model[0].reversed)
|
||||
|
|
Loading…
Reference in New Issue