diff options
author | Uwe Klotz <uklotz@mixxx.org> | 2021-06-19 17:37:12 +0200 |
---|---|---|
committer | Uwe Klotz <uklotz@mixxx.org> | 2021-06-19 17:39:43 +0200 |
commit | b0cb80b82724a0bc2277bdf148dd65ffdb7ba72d (patch) | |
tree | 3369f3669c80bcd5da509e12efc0a4eef77887a3 /src/sources | |
parent | b49f33b6daa86c2a88b4e096eedd18815ef25245 (diff) |
lp1933001: Preserve phase of decoded FLAC samples
Diffstat (limited to 'src/sources')
-rw-r--r-- | src/sources/soundsourceflac.cpp | 12 |
1 files changed, 9 insertions, 3 deletions
diff --git a/src/sources/soundsourceflac.cpp b/src/sources/soundsourceflac.cpp index a6624a7e82..9c0ba7a5c3 100644 --- a/src/sources/soundsourceflac.cpp +++ b/src/sources/soundsourceflac.cpp @@ -403,12 +403,18 @@ namespace { // get rid of the garbage in the most significant bits before scaling // to the range [-CSAMPLE_PEAK, CSAMPLE_PEAK - epsilon] with // epsilon = 1 / 2 ^ bitsPerSample. -constexpr CSAMPLE kSampleScaleFactor = CSAMPLE_PEAK / +// +// We have to negate the nominator to compensate for the negative denominator! +// Otherwise the phase would be inverted: https://bugs.launchpad.net/mixxx/+bug/1933001 +constexpr CSAMPLE kSampleUnshiftFactor = -CSAMPLE_PEAK / (static_cast<FLAC__int32>(1) << std::numeric_limits<FLAC__int32>::digits); inline CSAMPLE convertDecodedSample(FLAC__int32 decodedSample, int bitsPerSample) { - DEBUG_ASSERT(std::numeric_limits<FLAC__int32>::is_signed); - return (decodedSample << ((std::numeric_limits<FLAC__int32>::digits + 1) - bitsPerSample)) * kSampleScaleFactor; + static_assert(std::numeric_limits<FLAC__int32>::is_signed); + static_assert(kSampleUnshiftFactor > CSAMPLE_ZERO, "preserve phase of decoded signal"); + const auto leftShift = (std::numeric_limits<FLAC__int32>::digits + 1) - bitsPerSample; + const auto shiftedSample = decodedSample << leftShift; + return shiftedSample * kSampleUnshiftFactor; } } // anonymous namespace |