diff --git a/src/ui/window.rs b/src/ui/window.rs index 6d747b5..809bdc9 100644 --- a/src/ui/window.rs +++ b/src/ui/window.rs @@ -54,8 +54,6 @@ mod imp { #[property(type = u32, get = Self::playlist_count)] _playlist_count: (), - tick_callback: Cell>, - pub(super) queued_seek: Cell>, pub(crate) initial_setup_handle: RefCell>>, @@ -63,6 +61,9 @@ mod imp { zbus_executor_loop_handle: RefCell>>, // same loading_cover_handle: RefCell>>, + + buffering_timeout: Cell>, + time_pos_notify_timeout: Cell>, } impl Default for Window { @@ -78,7 +79,6 @@ mod imp { mpv.observe_property(2, "pause").unwrap(); mpv.observe_property(3, "playlist-pos").unwrap(); mpv.observe_property(4, "idle-active").unwrap(); - mpv.observe_property(5, "time-pos").unwrap(); mpv.observe_property(6, "playlist-count").unwrap(); mpv.observe_property(7, "duration").unwrap(); mpv.observe_property(8, "path").unwrap(); @@ -106,8 +106,6 @@ mod imp { _idle_active: (), _playlist_count: (), - tick_callback: Default::default(), - queued_seek: Default::default(), initial_setup_handle: Default::default(), @@ -115,6 +113,9 @@ mod imp { zbus_executor_loop_handle: Default::default(), loading_cover_handle: Default::default(), + + buffering_timeout: Default::default(), + time_pos_notify_timeout: Default::default(), } } } @@ -140,6 +141,22 @@ mod imp { fn constructed(&self) { self.parent_constructed(); + // update time-pos every 100 ms + let window = self.obj().downgrade(); + self.time_pos_notify_timeout + .replace(Some(glib::timeout_add_local( + std::time::Duration::from_millis(100), + move || match window.upgrade() { + None => glib::ControlFlow::Break, + Some(window) => { + if !window.idle_active() && !window.pause() { + window.notify("time-pos"); + } + glib::ControlFlow::Continue + } + }, + ))); + let window = self.obj().downgrade(); let mpv_event_loop_handle = glib::spawn_future_local(async move { loop { @@ -175,11 +192,6 @@ mod imp { window.notify("idle-active"); } - 5 => { - assert_eq!(event.name, "time-pos"); - window.notify("time-pos"); - } - 6 => { assert_eq!(event.name, "playlist-count"); window.notify("playlist-count"); @@ -234,6 +246,9 @@ mod imp { } }))) .map(|handle| handle.abort()); + + // make sure this is reported as 0 + window.notify("time-pos"); } Event::Hook(event) => match event.reply_userdata { @@ -316,6 +331,9 @@ mod imp { window.imp().queued_seek.set(None); window.set_playing_cover_art(None::); + + // make sure the seekbar looks full + window.notify("time-pos"); } _ => event!(Level::DEBUG, "unhandled {event:?}"), @@ -516,20 +534,29 @@ mod imp { fn buffering_start(&self) { let started_buffering = std::time::Instant::now(); - self.tick_callback - .replace(Some(self.obj().add_tick_callback(move |window, _| { - // 3 second period from gnome hig - if started_buffering.elapsed() > std::time::Duration::from_secs(3) { - window.imp().playbar.set_show_pulse_bar(true); - window.imp().playbar.pulse_bar().pulse(); - } - glib::ControlFlow::Continue - }))) - .map(gtk::TickCallbackId::remove); + let window = self.obj().downgrade(); + self.buffering_timeout + .replace(Some(glib::timeout_add_local( + std::time::Duration::from_millis(100), + move || { + match window.upgrade() { + None => glib::ControlFlow::Break, + Some(window) => { + // 3 second period from gnome hig + if started_buffering.elapsed() > std::time::Duration::from_secs(3) { + window.imp().playbar.set_show_pulse_bar(true); + window.imp().playbar.pulse_bar().pulse(); + } + glib::ControlFlow::Continue + } + } + }, + ))) + .map(|source| source.remove()); } fn buffering_end(&self) { - self.tick_callback.take().map(gtk::TickCallbackId::remove); + self.buffering_timeout.take().map(|source| source.remove()); self.playbar.set_show_pulse_bar(false); } } @@ -540,6 +567,11 @@ mod imp { self.mpv_event_loop_handle.take().unwrap().abort(); self.zbus_executor_loop_handle.take().unwrap().abort(); + + self.time_pos_notify_timeout + .take() + .map(|source| source.remove()); + self.buffering_timeout.take().map(|source| source.remove()); } } }