play queue now works again (sort of)
This commit is contained in:
parent
0a5f8a9162
commit
ec0992ce54
8 changed files with 121 additions and 34 deletions
|
@ -5,7 +5,7 @@ template $AudreyUiPlayQueue: Adw.Bin {
|
|||
name: "play-queue";
|
||||
|
||||
child: Stack {
|
||||
visible-child-name: bind $visible_child_name (template.playbin as <$AudreyPlaybin>.play-queue-length) as <string>;
|
||||
visible-child-name: bind $visible_child_name (template.model as <$GListStore>.n-items) as <string>;
|
||||
|
||||
StackPage {
|
||||
name: "empty";
|
||||
|
@ -31,7 +31,7 @@ template $AudreyUiPlayQueue: Adw.Bin {
|
|||
activate => $on_row_activated () swapped;
|
||||
|
||||
model: NoSelection {
|
||||
model: bind template.playbin as <$AudreyPlaybin>.play_queue;
|
||||
model: bind template.model;
|
||||
};
|
||||
|
||||
factory: SignalListItemFactory {
|
||||
|
|
|
@ -35,7 +35,7 @@ template $AudreyUiPlayQueueSong: Box {
|
|||
margin-top: 1;
|
||||
margin-bottom: 1;
|
||||
pixel-size: 50;
|
||||
paintable: bind template.song as <$AudreyPlaybinSong>.thumbnail;
|
||||
//paintable: bind template.song as <$AudreyPlaybinSong>.thumbnail;
|
||||
}
|
||||
|
||||
Box title_box {
|
||||
|
|
|
@ -119,7 +119,7 @@ template $AudreyUiWindow: Adw.ApplicationWindow {
|
|||
margin-end: 24;
|
||||
|
||||
styles [ "frame" ]
|
||||
playbin: bind template.playbin;
|
||||
//playbin: bind template.playbin;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
|
|
@ -163,7 +163,9 @@ where
|
|||
|
||||
pub fn remove_entry(&self, index: usize) {
|
||||
let mut entries = self.entries.borrow_mut();
|
||||
self.mpv.command(["remove", &index.to_string()]).unwrap();
|
||||
self.mpv
|
||||
.command(["playlist-remove", &index.to_string()])
|
||||
.unwrap();
|
||||
entries.remove(index as usize);
|
||||
|
||||
drop(entries);
|
||||
|
@ -241,6 +243,22 @@ where
|
|||
self.muted_changed.signal()
|
||||
}
|
||||
|
||||
pub fn current_entry_changed(&self) -> Signal<'_, Self, ()> {
|
||||
self.current_entry_changed.signal()
|
||||
}
|
||||
|
||||
pub fn entry_inserted(&self) -> Signal<'_, Self, usize> {
|
||||
self.entry_inserted.signal()
|
||||
}
|
||||
|
||||
pub fn stopped(&self) -> Signal<'_, Self, ()> {
|
||||
self.stopped.signal()
|
||||
}
|
||||
|
||||
pub fn entry_removed(&self) -> Signal<'_, Self, usize> {
|
||||
self.entry_removed.signal()
|
||||
}
|
||||
|
||||
pub fn file_started(&self) -> Signal<'_, Self, ()> {
|
||||
self.file_started.signal()
|
||||
}
|
||||
|
|
|
@ -25,7 +25,7 @@ pub struct Signal<'a, E, T> {
|
|||
just_connected: &'a RefCell<Vec<SignalHandlerBox<E, T>>>,
|
||||
}
|
||||
|
||||
#[derive(Clone)]
|
||||
#[derive(Clone, Default)]
|
||||
pub struct SignalHandler(Weak<Cell<bool>>);
|
||||
|
||||
impl SignalHandler {
|
||||
|
|
|
@ -2,15 +2,22 @@ pub mod song;
|
|||
pub use song::Song;
|
||||
|
||||
mod imp {
|
||||
use adw::{glib, prelude::*, subclass::prelude::*};
|
||||
use crate::playbin::Song as PlaybinSong;
|
||||
use adw::{gio, glib, prelude::*, subclass::prelude::*};
|
||||
use glib::{subclass::InitializingObject, WeakRef};
|
||||
use std::cell::{Cell, RefCell};
|
||||
use std::rc::Rc;
|
||||
|
||||
type Playbin = crate::playbin2::Playbin<PlaybinSong>;
|
||||
|
||||
#[derive(gtk::CompositeTemplate, glib::Properties, Default)]
|
||||
#[template(resource = "/eu/callcc/audrey/play_queue.ui")]
|
||||
#[properties(wrapper_type = super::PlayQueue)]
|
||||
pub struct PlayQueue {
|
||||
#[property(get, set)]
|
||||
playbin: WeakRef<crate::Playbin>,
|
||||
pub(super) model: RefCell<Option<gio::ListStore>>,
|
||||
|
||||
pub(super) playbin: RefCell<Option<Rc<Playbin>>>,
|
||||
}
|
||||
|
||||
#[glib::object_subclass]
|
||||
|
@ -30,7 +37,13 @@ mod imp {
|
|||
}
|
||||
|
||||
#[glib::derived_properties]
|
||||
impl ObjectImpl for PlayQueue {}
|
||||
impl ObjectImpl for PlayQueue {
|
||||
fn constructed(&self) {
|
||||
self.parent_constructed();
|
||||
|
||||
self.obj().set_model(gio::ListStore::new::<PlaybinSong>());
|
||||
}
|
||||
}
|
||||
|
||||
impl WidgetImpl for PlayQueue {}
|
||||
|
||||
|
@ -49,7 +62,7 @@ mod imp {
|
|||
|
||||
#[template_callback]
|
||||
fn on_song_list_setup(&self, item: >k::ListItem, _factory: >k::SignalListItemFactory) {
|
||||
let child = super::Song::new(&self.playbin.upgrade().unwrap());
|
||||
let child = super::Song::new(self.playbin.borrow().as_ref().unwrap());
|
||||
|
||||
child.set_draggable(true);
|
||||
child.set_show_position(true);
|
||||
|
@ -81,7 +94,11 @@ mod imp {
|
|||
|
||||
#[template_callback]
|
||||
fn on_row_activated(&self, position: u32) {
|
||||
self.obj().playbin().unwrap().select_track(position);
|
||||
self.playbin
|
||||
.borrow()
|
||||
.as_ref()
|
||||
.unwrap()
|
||||
.play_entry(position as usize);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -92,10 +109,47 @@ mod imp {
|
|||
}
|
||||
}
|
||||
|
||||
use crate::playbin::Song as PlaybinSong;
|
||||
use adw::subclass::prelude::*;
|
||||
use gtk::glib;
|
||||
use std::rc::Rc;
|
||||
|
||||
type Playbin = crate::playbin2::Playbin<PlaybinSong>;
|
||||
|
||||
glib::wrapper! {
|
||||
pub struct PlayQueue(ObjectSubclass<imp::PlayQueue>)
|
||||
@extends adw::Bin, gtk::Widget,
|
||||
@implements gtk::Accessible, gtk::Buildable, gtk::ConstraintTarget;
|
||||
}
|
||||
|
||||
impl PlayQueue {
|
||||
pub fn set_playbin(&self, playbin: &Rc<Playbin>) {
|
||||
assert!(self
|
||||
.imp()
|
||||
.playbin
|
||||
.replace(Some(Rc::clone(playbin)))
|
||||
.is_none()); // only set once
|
||||
|
||||
playbin
|
||||
.entry_inserted()
|
||||
.connect_object(self, |playbin, play_queue, index| {
|
||||
play_queue
|
||||
.model()
|
||||
.unwrap()
|
||||
.insert(index as u32, &playbin.entries()[index]);
|
||||
true
|
||||
});
|
||||
playbin
|
||||
.stopped()
|
||||
.connect_object(self, |playbin, play_queue, ()| {
|
||||
play_queue.model().unwrap().remove_all();
|
||||
true
|
||||
});
|
||||
playbin
|
||||
.entry_removed()
|
||||
.connect_object(self, |playbin, play_queue, index| {
|
||||
play_queue.model().unwrap().remove(index as u32);
|
||||
true
|
||||
});
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,14 +1,17 @@
|
|||
mod imp {
|
||||
use crate::playbin::Song as PlaybinSong;
|
||||
use crate::signal::SignalHandler;
|
||||
use glib::{subclass::InitializingObject, WeakRef};
|
||||
use gtk::{gdk, gio, glib, prelude::*, subclass::prelude::*};
|
||||
use std::cell::{Cell, RefCell};
|
||||
use std::rc::Rc;
|
||||
|
||||
type Playbin = crate::playbin2::Playbin<PlaybinSong>;
|
||||
|
||||
#[derive(gtk::CompositeTemplate, glib::Properties, Default)]
|
||||
#[template(resource = "/eu/callcc/audrey/play_queue_song.ui")]
|
||||
#[properties(wrapper_type = super::Song)]
|
||||
pub struct Song {
|
||||
pub(super) playbin: WeakRef<crate::Playbin>,
|
||||
|
||||
#[property(set, get)]
|
||||
draggable: Cell<bool>,
|
||||
#[property(set, get)]
|
||||
|
@ -24,12 +27,13 @@ mod imp {
|
|||
#[property(set, get)]
|
||||
displayed_position: Cell<u32>,
|
||||
#[property(get, set)]
|
||||
song: RefCell<Option<crate::playbin::Song>>,
|
||||
|
||||
pub(super) connection: Cell<Option<glib::SignalHandlerId>>,
|
||||
song: RefCell<Option<PlaybinSong>>,
|
||||
|
||||
drag_pos: Cell<(i32, i32)>,
|
||||
drag_widget: Cell<Option<gtk::ListBox>>,
|
||||
|
||||
pub(super) playbin: RefCell<Option<Rc<Playbin>>>,
|
||||
pub(super) connection: Cell<SignalHandler>,
|
||||
}
|
||||
|
||||
#[glib::object_subclass]
|
||||
|
@ -61,7 +65,7 @@ mod imp {
|
|||
self_
|
||||
.obj()
|
||||
.playbin()
|
||||
.remove_track(self_.obj().displayed_position() - 1)
|
||||
.remove_entry(self_.obj().displayed_position() as usize - 1)
|
||||
}
|
||||
))
|
||||
.build();
|
||||
|
@ -169,10 +173,14 @@ mod imp {
|
|||
}
|
||||
}
|
||||
|
||||
use crate::playbin::Song as PlaybinSong;
|
||||
use adw::prelude::*;
|
||||
use adw::subclass::prelude::*;
|
||||
use glib::Object;
|
||||
use gtk::glib;
|
||||
use std::rc::Rc;
|
||||
|
||||
type Playbin = crate::playbin2::Playbin<PlaybinSong>;
|
||||
|
||||
glib::wrapper! {
|
||||
pub struct Song(ObjectSubclass<imp::Song>)
|
||||
|
@ -181,36 +189,38 @@ glib::wrapper! {
|
|||
}
|
||||
|
||||
impl Song {
|
||||
pub fn new(playbin: &crate::Playbin) -> Self {
|
||||
pub fn new(playbin: &Rc<Playbin>) -> Self {
|
||||
let song: Self = Object::new();
|
||||
song.imp().playbin.set(Some(playbin));
|
||||
|
||||
assert!(song
|
||||
.imp()
|
||||
.playbin
|
||||
.replace(Some(Rc::clone(playbin)))
|
||||
.is_none()); // only set once
|
||||
|
||||
song
|
||||
}
|
||||
|
||||
fn playbin(&self) -> crate::Playbin {
|
||||
self.imp().playbin.upgrade().unwrap()
|
||||
fn playbin(&self) -> Rc<Playbin> {
|
||||
Rc::clone(self.imp().playbin.borrow().as_ref().unwrap())
|
||||
}
|
||||
|
||||
pub fn bind(&self, position: u32, song: &crate::playbin::Song) {
|
||||
self.set_displayed_position(position + 1);
|
||||
self.set_song(song);
|
||||
self.set_current(self.playbin().play_queue_position() == position);
|
||||
self.set_current(self.playbin().current_entry() == Some(position as usize));
|
||||
self.imp()
|
||||
.connection
|
||||
.replace(Some(self.playbin().connect_notify_local(
|
||||
Some("play-queue-position"),
|
||||
glib::clone!(
|
||||
#[weak(rename_to = self_)]
|
||||
.replace(self.playbin().current_entry_changed().connect_object(
|
||||
self,
|
||||
move |playbin: &crate::Playbin, _| {
|
||||
self_.set_current(playbin.play_queue_position() == position)
|
||||
}
|
||||
),
|
||||
)));
|
||||
move |playbin, song, ()| {
|
||||
song.set_current(playbin.current_entry() == Some(position as usize));
|
||||
true
|
||||
},
|
||||
));
|
||||
}
|
||||
|
||||
pub fn unbind(&self) {
|
||||
self.playbin()
|
||||
.disconnect(self.imp().connection.take().unwrap());
|
||||
self.imp().connection.take().disconnect();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -19,6 +19,9 @@ mod imp {
|
|||
#[template_child]
|
||||
pub(super) playbar: TemplateChild<crate::ui::Playbar>,
|
||||
|
||||
#[template_child]
|
||||
pub(super) play_queue: TemplateChild<crate::ui::PlayQueue>,
|
||||
|
||||
#[property(get, set)]
|
||||
playbin: RefCell<crate::Playbin>,
|
||||
|
||||
|
@ -72,6 +75,8 @@ mod imp {
|
|||
}
|
||||
}));
|
||||
|
||||
self.play_queue.set_playbin(&self.playbin2);
|
||||
|
||||
// set up mpris
|
||||
let window = self.obj().clone();
|
||||
glib::spawn_future_local(async move {
|
||||
|
|
Loading…
Reference in a new issue