summaryrefslogtreecommitdiffstats
path: root/player/audio.c
diff options
context:
space:
mode:
Diffstat (limited to 'player/audio.c')
-rw-r--r--player/audio.c71
1 files changed, 39 insertions, 32 deletions
diff --git a/player/audio.c b/player/audio.c
index 96423151e7..f1dfe66784 100644
--- a/player/audio.c
+++ b/player/audio.c
@@ -60,47 +60,54 @@ static int try_filter(struct MPContext *mpctx,
return 1;
}
-static int recreate_audio_filters(struct MPContext *mpctx)
+static int update_playback_speed_filters(struct MPContext *mpctx)
{
- assert(mpctx->d_audio);
-
struct MPOpts *opts = mpctx->opts;
+ double speed = opts->playback_speed;
struct af_stream *afs = mpctx->d_audio->afilter;
- double speed = opts->playback_speed;
+ // Make sure only exactly one filter changes speed; resetting them all
+ // and setting 1 filter is the easiest way to achieve this.
+ af_control_all(afs, AF_CONTROL_SET_PLAYBACK_SPEED, &(double){1});
+ af_control_all(afs, AF_CONTROL_SET_PLAYBACK_SPEED_RESAMPLE, &(double){1});
- if (speed != 1.0) {
- int method = AF_CONTROL_SET_PLAYBACK_SPEED_RESAMPLE;
- if (opts->pitch_correction)
- method = AF_CONTROL_SET_PLAYBACK_SPEED;
- if (!af_control_any_rev(afs, method, &speed)) {
- if (af_remove_by_label(afs, "playback-speed") < 0)
- return -1;
-
- // Compatibility: if the user uses --af=scaletempo, always use
- // this filter to change speed. Don't insert a second "scaletempo"
- // filter either.
- if (!af_control_any_rev(afs, AF_CONTROL_SET_PLAYBACK_SPEED, &speed))
- {
- char *filter = method == AF_CONTROL_SET_PLAYBACK_SPEED
- ? "scaletempo" : "lavrresample";
- if (try_filter(mpctx, filter, "playback-speed", NULL) < 0)
- return -1;
- // Try again.
- if (!af_control_any_rev(afs, method, &speed))
- return -1;
- } else {
- method = AF_CONTROL_SET_PLAYBACK_SPEED;
- }
- }
- } else {
+ if (speed == 1.0)
+ return af_remove_by_label(afs, "playback-speed");
+
+ // Compatibility: if the user uses --af=scaletempo, always use this
+ // filter to change speed. Don't insert a second filter (any) either.
+ if (!af_find_by_label(afs, "playback-speed") &&
+ af_control_any_rev(afs, AF_CONTROL_SET_PLAYBACK_SPEED, &speed))
+ return 0;
+
+ int method = AF_CONTROL_SET_PLAYBACK_SPEED_RESAMPLE;
+ if (opts->pitch_correction)
+ method = AF_CONTROL_SET_PLAYBACK_SPEED;
+
+ if (!af_control_any_rev(afs, method, &speed)) {
if (af_remove_by_label(afs, "playback-speed") < 0)
return -1;
- // The filters could be inserted by the user (we don't remove them).
- af_control_any_rev(afs, AF_CONTROL_SET_PLAYBACK_SPEED, &speed);
- af_control_any_rev(afs, AF_CONTROL_SET_PLAYBACK_SPEED_RESAMPLE, &speed);
+
+ char *filter = method == AF_CONTROL_SET_PLAYBACK_SPEED
+ ? "scaletempo" : "lavrresample";
+ if (try_filter(mpctx, filter, "playback-speed", NULL) < 0)
+ return -1;
+ // Try again.
+ if (!af_control_any_rev(afs, method, &speed))
+ return -1;
}
+ return 0;
+}
+
+static int recreate_audio_filters(struct MPContext *mpctx)
+{
+ assert(mpctx->d_audio);
+
+ if (update_playback_speed_filters(mpctx) < 0)
+ return -1;
+
+ struct af_stream *afs = mpctx->d_audio->afilter;
if (afs->initialized < 1 && af_init(afs) < 0) {
MP_ERR(mpctx, "Couldn't find matching filter/ao format!\n");
return -1;