Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Distorted audio when using dynamic normalisation #745

Closed
rbuch opened this issue May 13, 2021 · 9 comments · Fixed by #749
Closed

Distorted audio when using dynamic normalisation #745

rbuch opened this issue May 13, 2021 · 9 comments · Fixed by #749

Comments

@rbuch
Copy link

rbuch commented May 13, 2021

Audio sounds highly distorted and seems to be clipping when using the current default dynamic normalisation added in #660. Changing back to using basic normalisation or disabling normalisation altogether fixes the issue.

(Discovered via ncspot, the corresponding issue there is: hrkfdn/ncspot#522.)

@roderickvd
Copy link
Member

Could you please provide the following information:

  1. Complete debug logs;
  2. Whether the issue also occurs on vanilla librespot, all else being equal (same pregain, attack, threshold, knee, and so on);
  3. As above, but now also using --backend alsa or --backend rodio instead of PulseAudio or PipeWire.

Finally, please explain what its meant by "even when in-app volume is set to 0%" in that downstream issue. As I understand it, the audio is distorted even when volume is set to 0 or mute? Does the distortion differ depending on the volume setting?

@Johannesd3
Copy link
Contributor

Johannesd3 commented May 13, 2021

And if you use PipeWire, which backend? IIRC ALSA, Jack, GStreamer, Pulseaudio, or Rodio would be possible. Does it happen with other backends + PipeWire as well?

@rbuch
Copy link
Author

rbuch commented May 13, 2021

I did a bit of digging, I couldn't get this to reproduce in vanilla librespot with any of the backends or changing any other options. However, comparing debug output between librespot and ncspot uncovered the issue, the normalisation_threshold in ncspot is incorrect.

ncspot initializes librespot_playback::config::PlayerConfig with the following code:

let player_config = PlayerConfig {
    gapless: cfg.values().gapless.unwrap_or(false),
    bitrate: bitrate.unwrap_or(Bitrate::Bitrate320),
    normalisation: cfg.values().volnorm.unwrap_or(false),
    normalisation_pregain: cfg.values().volnorm_pregain.unwrap_or(0.0),
    ..Default::default()
};

Thus, it uses the default value for normalisation_threshold (which is -1.0) directly, whereas librespot passes the default value through NormalisationData::db_to_ratio when it constructs the object (resulting in ~0.8912509). Explicitly passing in this adjusted value in the ncspot constructor fixes the issue, otherwise the effective threshold after converting to dB in the ncspot case ends up being NaN.

So I suppose the question now is can the logic to convert the value from dB to ratio be pushed into an object creation function for PlayerConfig to avoid this problem?

@Johannesd3
Copy link
Contributor

Why can't ncspot use NormalisationData::db_to_ratio themselves?

@rbuch
Copy link
Author

rbuch commented May 14, 2021

Why can't ncspot use NormalisationData::db_to_ratio themselves?

It can, of course, but it feels like a leaky abstraction for an external application to have to pull a default value out, transform it, and then explicitly pass it back in when it just wants it to be default initialized.

@roderickvd
Copy link
Member

roderickvd commented May 14, 2021

I agree with @rbuch the default should just make sense. This was an oversight on my end. I'll update it later this weekend.

@roderickvd
Copy link
Member

Thanks for digging around 😅 I was getting worried.

@roderickvd
Copy link
Member

@rbuch could you please verify #749 and report back there?

@rbuch
Copy link
Author

rbuch commented May 16, 2021

@rbuch could you please verify #749 and report back there?

Building ncspot with #749 does indeed fix the default value issue and it all sounds like it should. Thanks for the quick fix!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants