fix seeking hah

This commit is contained in:
Erica Z 2024-10-16 22:24:48 +02:00
parent e1b6b19c03
commit 2fe276bfbd
3 changed files with 28 additions and 31 deletions

View file

@ -166,6 +166,10 @@ class Playbin : GLib.Object {
assert (this.playbin.query_duration (Gst.Format.TIME, out duration));
this.duration = duration;
// cancel any queued seeks
this.queued_seek = -1;
this.update_position = true;
this.position = 0;
bool continues = this.next_gapless;
@ -202,7 +206,17 @@ class Playbin : GLib.Object {
Gst.State new_state;
message.parse_state_changed (null, out new_state, null);
this.update_position = new_state == Gst.State.PLAYING;
if (new_state == Gst.State.PLAYING) {
if (queued_seek != -1) {
if (this.playbin.seek_simple (Gst.Format.TIME, Gst.SeekFlags.FLUSH | Gst.SeekFlags.ACCURATE, this.queued_seek)) {
this.queued_seek = -1;
} else {
warning ("could not reapply queued seek after state changed changed to playing, retrying later");
}
} else {
this.update_position = true;
}
}
});
bus.message["eos"].connect ((message) => {
@ -210,9 +224,14 @@ class Playbin : GLib.Object {
});
}
private int64 queued_seek = -1;
public void seek (int64 position) {
this.position = position;
this.update_position = false;
if (!this.playbin.seek_simple (Gst.Format.TIME, Gst.SeekFlags.FLUSH | Gst.SeekFlags.ACCURATE, position)) {
warning ("could not seek");
// try to queue this seek for later
queued_seek = position;
}
}

View file

@ -136,7 +136,7 @@ template $UiWindow: Adw.ApplicationWindow {
"numeric",
]
label: bind $format_timestamp (template.position) as <string>;
label: bind $format_timestamp (template.playbin as <$Playbin>.position) as <string>;
}
[center]
@ -148,7 +148,7 @@ template $UiWindow: Adw.ApplicationWindow {
adjustment: Adjustment {
lower: 0;
value: bind template.position;
value: bind template.playbin as <$Playbin>.position;
upper: bind template.playbin as <$Playbin>.duration;
};

View file

@ -10,8 +10,6 @@ class Ui.Window : Adw.ApplicationWindow {
private Setup setup;
private Subsonic.Client api;
public int64 position { get; private set; }
public double volume {
get { return this.playbin.volume; }
@ -114,13 +112,6 @@ class Ui.Window : Adw.ApplicationWindow {
});
}
});
this.playbin.notify["position"].connect (() => {
// only set if we aren't seeking
if (this.seek_timeout_id == 0) {
this.position = this.playbin.position;
}
});
}
[GtkCallback] private void on_sidebar_row_activated (Gtk.ListBoxRow row) {
@ -137,22 +128,9 @@ class Ui.Window : Adw.ApplicationWindow {
int s = (int) (ns / Gst.SECOND);
return "%02d:%02d".printf (s/60, s%60);
}
private void seek_impl (int64 position) {
this.position = position;
if (this.seek_timeout_id == 0) {
this.seek_timeout_id = Timeout.add (500, () => {
playbin.seek(this.position);
this.seek_timeout_id = 0;
return false;
});
}
}
// same timeout logic as https://code.videolan.org/videolan/npapi-vlc/blob/6eae0ffb9cbaf8f6e04423de2ff38daabdf7cae3/npapi/vlcplugin_gtk.cpp#L312
private uint seek_timeout_id = 0;
[GtkCallback] private bool on_play_position_seek (Gtk.Range range, Gtk.ScrollType scroll_type, double value) {
this.seek_impl((int64) value);
this.playbin.seek ((int64) value);
return false;
}
@ -202,16 +180,16 @@ class Ui.Window : Adw.ApplicationWindow {
[GtkCallback] private void seek_backward () {
// 10 seconds
int64 new_position = position - 10 * Gst.SECOND;
int64 new_position = playbin.position - 10 * Gst.SECOND;
if (new_position < 0) new_position = 0;
this.seek_impl (new_position);
this.playbin.seek (new_position);
}
[GtkCallback] private void seek_forward () {
// 10 seconds
int64 new_position = position + 10 * Gst.SECOND;
int64 new_position = playbin.position + 10 * Gst.SECOND;
if (new_position > this.playbin.duration) new_position = this.playbin.duration;
this.seek_impl (new_position);
this.playbin.seek (new_position);
}
[GtkCallback] private string song_title (Subsonic.Song? song) {