mirror of
https://github.com/overte-org/overte.git
synced 2025-04-14 07:47:30 +02:00
Add manual mode to noise reduction + add noise reduction threshold
This commit is contained in:
parent
69e5d1261b
commit
d2875c2c4f
4 changed files with 119 additions and 1 deletions
|
@ -25,6 +25,8 @@ QString Audio::DESKTOP { "Desktop" };
|
||||||
QString Audio::HMD { "VR" };
|
QString Audio::HMD { "VR" };
|
||||||
|
|
||||||
Setting::Handle<bool> enableNoiseReductionSetting { QStringList { Audio::AUDIO, "NoiseReduction" }, true };
|
Setting::Handle<bool> enableNoiseReductionSetting { QStringList { Audio::AUDIO, "NoiseReduction" }, true };
|
||||||
|
Setting::Handle<bool> enableNoiseReductionAutomaticSetting { QStringList { Audio::AUDIO, "NoiseReductionAutomatic" }, false };
|
||||||
|
Setting::Handle<float> setNoiseReductionThresholdSetting { QStringList { Audio::AUDIO, "NoiseReductionThreshold" }, 0.2f };
|
||||||
Setting::Handle<bool> enableWarnWhenMutedSetting { QStringList { Audio::AUDIO, "WarnWhenMuted" }, true };
|
Setting::Handle<bool> enableWarnWhenMutedSetting { QStringList { Audio::AUDIO, "WarnWhenMuted" }, true };
|
||||||
Setting::Handle<bool> enableAcousticEchoCancellationSetting { QStringList { Audio::AUDIO, "AcousticEchoCancellation" }, true };
|
Setting::Handle<bool> enableAcousticEchoCancellationSetting { QStringList { Audio::AUDIO, "AcousticEchoCancellation" }, true };
|
||||||
|
|
||||||
|
@ -40,6 +42,8 @@ Audio::Audio() : _devices(_contextIsHMD) {
|
||||||
auto client = DependencyManager::get<AudioClient>().data();
|
auto client = DependencyManager::get<AudioClient>().data();
|
||||||
connect(client, &AudioClient::muteToggled, this, &Audio::setMuted);
|
connect(client, &AudioClient::muteToggled, this, &Audio::setMuted);
|
||||||
connect(client, &AudioClient::noiseReductionChanged, this, &Audio::enableNoiseReduction);
|
connect(client, &AudioClient::noiseReductionChanged, this, &Audio::enableNoiseReduction);
|
||||||
|
connect(client, &AudioClient::noiseReductionAutomaticChanged, this, &Audio::enableNoiseReductionAutomatic);
|
||||||
|
connect(client, &AudioClient::noiseReductionThresholdChanged, this, &Audio::setNoiseReductionThreshold);
|
||||||
connect(client, &AudioClient::warnWhenMutedChanged, this, &Audio::enableWarnWhenMuted);
|
connect(client, &AudioClient::warnWhenMutedChanged, this, &Audio::enableWarnWhenMuted);
|
||||||
connect(client, &AudioClient::acousticEchoCancellationChanged, this, &Audio::enableAcousticEchoCancellation);
|
connect(client, &AudioClient::acousticEchoCancellationChanged, this, &Audio::enableAcousticEchoCancellation);
|
||||||
connect(client, &AudioClient::inputLoudnessChanged, this, &Audio::onInputLoudnessChanged);
|
connect(client, &AudioClient::inputLoudnessChanged, this, &Audio::onInputLoudnessChanged);
|
||||||
|
@ -47,6 +51,8 @@ Audio::Audio() : _devices(_contextIsHMD) {
|
||||||
connect(this, &Audio::contextChanged, &_devices, &AudioDevices::onContextChanged);
|
connect(this, &Audio::contextChanged, &_devices, &AudioDevices::onContextChanged);
|
||||||
connect(this, &Audio::pushingToTalkChanged, this, &Audio::handlePushedToTalk);
|
connect(this, &Audio::pushingToTalkChanged, this, &Audio::handlePushedToTalk);
|
||||||
enableNoiseReduction(enableNoiseReductionSetting.get());
|
enableNoiseReduction(enableNoiseReductionSetting.get());
|
||||||
|
enableNoiseReductionAutomatic(enableNoiseReductionAutomaticSetting.get());
|
||||||
|
setNoiseReductionThreshold(setNoiseReductionThresholdSetting.get());
|
||||||
enableWarnWhenMuted(enableWarnWhenMutedSetting.get());
|
enableWarnWhenMuted(enableWarnWhenMutedSetting.get());
|
||||||
enableAcousticEchoCancellation(enableAcousticEchoCancellationSetting.get());
|
enableAcousticEchoCancellation(enableAcousticEchoCancellationSetting.get());
|
||||||
onContextChanged();
|
onContextChanged();
|
||||||
|
@ -286,6 +292,50 @@ void Audio::enableNoiseReduction(bool enable) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool Audio::noiseReductionAutomatic() const {
|
||||||
|
return resultWithReadLock<bool>([&] {
|
||||||
|
return _noiseReductionAutomatic;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
void Audio::enableNoiseReductionAutomatic(bool enable) {
|
||||||
|
bool changed = false;
|
||||||
|
withWriteLock([&] {
|
||||||
|
if (_noiseReductionAutomatic != enable) {
|
||||||
|
_noiseReductionAutomatic = enable;
|
||||||
|
auto client = DependencyManager::get<AudioClient>().data();
|
||||||
|
QMetaObject::invokeMethod(client, "setNoiseReductionAutomatic", Q_ARG(bool, enable), Q_ARG(bool, false));
|
||||||
|
enableNoiseReductionAutomaticSetting.set(enable);
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
if (changed) {
|
||||||
|
emit noiseReductionAutomaticChanged(enable);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
float Audio::getNoiseReductionThreshold() const {
|
||||||
|
return resultWithReadLock<float>([&] {
|
||||||
|
return _noiseReductionThreshold;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
void Audio::setNoiseReductionThreshold(float threshold) {
|
||||||
|
bool changed = false;
|
||||||
|
withWriteLock([&] {
|
||||||
|
if (_noiseReductionThreshold != threshold) {
|
||||||
|
_noiseReductionThreshold = threshold;
|
||||||
|
auto client = DependencyManager::get<AudioClient>().data();
|
||||||
|
QMetaObject::invokeMethod(client, "setNoiseReductionThreshold", Q_ARG(float, threshold), Q_ARG(bool, false));
|
||||||
|
setNoiseReductionThresholdSetting.set(threshold);
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
if (changed) {
|
||||||
|
emit noiseReductionAutomaticChanged(threshold);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool Audio::warnWhenMutedEnabled() const {
|
bool Audio::warnWhenMutedEnabled() const {
|
||||||
return resultWithReadLock<bool>([&] {
|
return resultWithReadLock<bool>([&] {
|
||||||
return _enableWarnWhenMuted;
|
return _enableWarnWhenMuted;
|
||||||
|
|
|
@ -92,6 +92,8 @@ class Audio : public AudioScriptingInterface, protected ReadWriteLockable {
|
||||||
|
|
||||||
Q_PROPERTY(bool muted READ isMuted WRITE setMuted NOTIFY mutedChanged)
|
Q_PROPERTY(bool muted READ isMuted WRITE setMuted NOTIFY mutedChanged)
|
||||||
Q_PROPERTY(bool noiseReduction READ noiseReductionEnabled WRITE enableNoiseReduction NOTIFY noiseReductionChanged)
|
Q_PROPERTY(bool noiseReduction READ noiseReductionEnabled WRITE enableNoiseReduction NOTIFY noiseReductionChanged)
|
||||||
|
Q_PROPERTY(bool noiseReductionAutomatic READ noiseReductionAutomatic WRITE enableNoiseReductionAutomatic NOTIFY noiseReductionAutomaticChanged)
|
||||||
|
Q_PROPERTY(float noiseReductionThreshold READ getNoiseReductionThreshold WRITE setNoiseReductionThreshold NOTIFY noiseReductionThresholdChanged)
|
||||||
Q_PROPERTY(bool warnWhenMuted READ warnWhenMutedEnabled WRITE enableWarnWhenMuted NOTIFY warnWhenMutedChanged)
|
Q_PROPERTY(bool warnWhenMuted READ warnWhenMutedEnabled WRITE enableWarnWhenMuted NOTIFY warnWhenMutedChanged)
|
||||||
Q_PROPERTY(bool acousticEchoCancellation
|
Q_PROPERTY(bool acousticEchoCancellation
|
||||||
READ acousticEchoCancellationEnabled WRITE enableAcousticEchoCancellation NOTIFY acousticEchoCancellationChanged)
|
READ acousticEchoCancellationEnabled WRITE enableAcousticEchoCancellation NOTIFY acousticEchoCancellationChanged)
|
||||||
|
@ -124,6 +126,8 @@ public:
|
||||||
|
|
||||||
bool isMuted() const;
|
bool isMuted() const;
|
||||||
bool noiseReductionEnabled() const;
|
bool noiseReductionEnabled() const;
|
||||||
|
bool noiseReductionAutomatic() const;
|
||||||
|
float getNoiseReductionThreshold() const;
|
||||||
bool warnWhenMutedEnabled() const;
|
bool warnWhenMutedEnabled() const;
|
||||||
bool acousticEchoCancellationEnabled() const;
|
bool acousticEchoCancellationEnabled() const;
|
||||||
float getInputVolume() const;
|
float getInputVolume() const;
|
||||||
|
@ -398,6 +402,24 @@ signals:
|
||||||
* @returns {Signal}
|
* @returns {Signal}
|
||||||
*/
|
*/
|
||||||
void noiseReductionChanged(bool isEnabled);
|
void noiseReductionChanged(bool isEnabled);
|
||||||
|
|
||||||
|
/**jsdoc
|
||||||
|
* Triggered when the audio input noise reduction mode is changed.
|
||||||
|
* @function Audio.noiseReductionAutomaticChanged
|
||||||
|
* @param {boolean} isEnabled - <code>true</code> if audio input noise reduction automatic mode is enabled, otherwise <code>false</code>.
|
||||||
|
* This means the mode is set to 'manual'.
|
||||||
|
* @returns {Signal}
|
||||||
|
*/
|
||||||
|
void noiseReductionAutomaticChanged(bool isEnabled);
|
||||||
|
|
||||||
|
/**jsdoc
|
||||||
|
* Triggered when audio input noise reduction threshold is changed.
|
||||||
|
* @function Audio.noiseReductionThresholdChanged
|
||||||
|
* @param {number} threshold - The threshold for the audio input noise reduction, range <code>0.0</code> (open the gate completely) – <code>1.0</code>
|
||||||
|
* (close the gate completely).
|
||||||
|
* @returns {Signal}
|
||||||
|
*/
|
||||||
|
void noiseReductionThresholdChanged(float threshold);
|
||||||
|
|
||||||
/**jsdoc
|
/**jsdoc
|
||||||
* Triggered when "warn when muted" is enabled or disabled.
|
* Triggered when "warn when muted" is enabled or disabled.
|
||||||
|
@ -512,6 +534,8 @@ public slots:
|
||||||
private slots:
|
private slots:
|
||||||
void setMuted(bool muted);
|
void setMuted(bool muted);
|
||||||
void enableNoiseReduction(bool enable);
|
void enableNoiseReduction(bool enable);
|
||||||
|
void enableNoiseReductionAutomatic(bool enable);
|
||||||
|
void setNoiseReductionThreshold(float threshold);
|
||||||
void enableWarnWhenMuted(bool enable);
|
void enableWarnWhenMuted(bool enable);
|
||||||
void enableAcousticEchoCancellation(bool enable);
|
void enableAcousticEchoCancellation(bool enable);
|
||||||
void setInputVolume(float volume);
|
void setInputVolume(float volume);
|
||||||
|
@ -533,8 +557,10 @@ private:
|
||||||
float _localInjectorGain { 0.0f }; // in dB
|
float _localInjectorGain { 0.0f }; // in dB
|
||||||
float _systemInjectorGain { 0.0f }; // in dB
|
float _systemInjectorGain { 0.0f }; // in dB
|
||||||
float _pttOutputGainDesktop { 0.0f }; // in dB
|
float _pttOutputGainDesktop { 0.0f }; // in dB
|
||||||
|
float _noiseReductionThreshold { 0.2f }; // Match default value of AudioClient::_noiseReductionThreshold.
|
||||||
bool _isClipping { false };
|
bool _isClipping { false };
|
||||||
bool _enableNoiseReduction { true }; // Match default value of AudioClient::_isNoiseGateEnabled.
|
bool _enableNoiseReduction { true }; // Match default value of AudioClient::_isNoiseGateEnabled.
|
||||||
|
bool _noiseReductionAutomatic { true }; // Match default value of AudioClient::_noiseReductionAutomatic.
|
||||||
bool _enableWarnWhenMuted { true };
|
bool _enableWarnWhenMuted { true };
|
||||||
bool _enableAcousticEchoCancellation { true }; // AudioClient::_isAECEnabled
|
bool _enableAcousticEchoCancellation { true }; // AudioClient::_isAECEnabled
|
||||||
bool _contextIsHMD { false };
|
bool _contextIsHMD { false };
|
||||||
|
|
|
@ -1342,6 +1342,13 @@ void AudioClient::handleLocalEchoAndReverb(QByteArray& inputByteArray) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
float AudioClient::loudnessToLevel(float loudness) {
|
||||||
|
float level = loudness * (1 / 32768.0f); // level in [0, 1]
|
||||||
|
level = 6.02059991f * fastLog2f(level); // convert to dBFS
|
||||||
|
level = (level + 48.0f) * (1 / 42.0f); // map [-48, -6] dBFS to [0, 1]
|
||||||
|
return glm::clamp(level, 0.0f, 1.0f);
|
||||||
|
}
|
||||||
|
|
||||||
void AudioClient::handleAudioInput(QByteArray& audioBuffer) {
|
void AudioClient::handleAudioInput(QByteArray& audioBuffer) {
|
||||||
if (!_audioPaused) {
|
if (!_audioPaused) {
|
||||||
|
|
||||||
|
@ -1352,9 +1359,14 @@ void AudioClient::handleAudioInput(QByteArray& audioBuffer) {
|
||||||
int numSamples = audioBuffer.size() / AudioConstants::SAMPLE_SIZE;
|
int numSamples = audioBuffer.size() / AudioConstants::SAMPLE_SIZE;
|
||||||
int numFrames = numSamples / (_isStereoInput ? AudioConstants::STEREO : AudioConstants::MONO);
|
int numFrames = numSamples / (_isStereoInput ? AudioConstants::STEREO : AudioConstants::MONO);
|
||||||
|
|
||||||
if (_isNoiseGateEnabled) {
|
if (_isNoiseGateEnabled && _isNoiseReductionAutomatic) {
|
||||||
// The audio gate includes DC removal
|
// The audio gate includes DC removal
|
||||||
audioGateOpen = _audioGate->render(samples, samples, numFrames);
|
audioGateOpen = _audioGate->render(samples, samples, numFrames);
|
||||||
|
} else if (_isNoiseGateEnabled && !_isNoiseReductionAutomatic &&
|
||||||
|
loudnessToLevel(_lastSmoothedRawInputLoudness) >= _noiseReductionThreshold) {
|
||||||
|
audioGateOpen = _audioGate->removeDC(samples, samples, numFrames);
|
||||||
|
} else if (_isNoiseGateEnabled && !_isNoiseReductionAutomatic) {
|
||||||
|
audioGateOpen = false;
|
||||||
} else {
|
} else {
|
||||||
audioGateOpen = _audioGate->removeDC(samples, samples, numFrames);
|
audioGateOpen = _audioGate->removeDC(samples, samples, numFrames);
|
||||||
}
|
}
|
||||||
|
@ -1750,6 +1762,24 @@ void AudioClient::setNoiseReduction(bool enable, bool emitSignal) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AudioClient::setNoiseReductionAutomatic(bool enable, bool emitSignal) {
|
||||||
|
if (_isNoiseReductionAutomatic != enable) {
|
||||||
|
_isNoiseReductionAutomatic = enable;
|
||||||
|
if (emitSignal) {
|
||||||
|
emit noiseReductionAutomaticChanged(_isNoiseReductionAutomatic);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void AudioClient::setNoiseReductionThreshold(float threshold, bool emitSignal) {
|
||||||
|
if (_noiseReductionThreshold != threshold) {
|
||||||
|
_noiseReductionThreshold = threshold;
|
||||||
|
if (emitSignal) {
|
||||||
|
emit noiseReductionThresholdChanged(_noiseReductionThreshold);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void AudioClient::setWarnWhenMuted(bool enable, bool emitSignal) {
|
void AudioClient::setWarnWhenMuted(bool enable, bool emitSignal) {
|
||||||
if (_warnWhenMuted != enable) {
|
if (_warnWhenMuted != enable) {
|
||||||
_warnWhenMuted = enable;
|
_warnWhenMuted = enable;
|
||||||
|
|
|
@ -217,6 +217,12 @@ public slots:
|
||||||
|
|
||||||
void setNoiseReduction(bool isNoiseGateEnabled, bool emitSignal = true);
|
void setNoiseReduction(bool isNoiseGateEnabled, bool emitSignal = true);
|
||||||
bool isNoiseReductionEnabled() const { return _isNoiseGateEnabled; }
|
bool isNoiseReductionEnabled() const { return _isNoiseGateEnabled; }
|
||||||
|
|
||||||
|
void setNoiseReductionAutomatic(bool isNoiseGateAutomatic, bool emitSignal = true);
|
||||||
|
bool isNoiseReductionAutomatic() const { return _isNoiseReductionAutomatic; }
|
||||||
|
|
||||||
|
void setNoiseReductionThreshold(float noiseReductionThreshold, bool emitSignal = true);
|
||||||
|
float noiseReductionThreshold() const { return _noiseReductionThreshold; }
|
||||||
|
|
||||||
void setWarnWhenMuted(bool isNoiseGateEnabled, bool emitSignal = true);
|
void setWarnWhenMuted(bool isNoiseGateEnabled, bool emitSignal = true);
|
||||||
bool isWarnWhenMutedEnabled() const { return _warnWhenMuted; }
|
bool isWarnWhenMutedEnabled() const { return _warnWhenMuted; }
|
||||||
|
@ -265,6 +271,8 @@ signals:
|
||||||
void inputVolumeChanged(float volume);
|
void inputVolumeChanged(float volume);
|
||||||
void muteToggled(bool muted);
|
void muteToggled(bool muted);
|
||||||
void noiseReductionChanged(bool noiseReductionEnabled);
|
void noiseReductionChanged(bool noiseReductionEnabled);
|
||||||
|
void noiseReductionAutomaticChanged(bool noiseReductionAutomatic);
|
||||||
|
void noiseReductionThresholdChanged(bool noiseReductionThreshold);
|
||||||
void warnWhenMutedChanged(bool warnWhenMutedEnabled);
|
void warnWhenMutedChanged(bool warnWhenMutedEnabled);
|
||||||
void acousticEchoCancellationChanged(bool acousticEchoCancellationEnabled);
|
void acousticEchoCancellationChanged(bool acousticEchoCancellationEnabled);
|
||||||
void mutedByMixer();
|
void mutedByMixer();
|
||||||
|
@ -310,6 +318,8 @@ private:
|
||||||
friend class CheckDevicesThread;
|
friend class CheckDevicesThread;
|
||||||
friend class LocalInjectorsThread;
|
friend class LocalInjectorsThread;
|
||||||
|
|
||||||
|
float loudnessToLevel(float loudness);
|
||||||
|
|
||||||
// background tasks
|
// background tasks
|
||||||
void checkDevices();
|
void checkDevices();
|
||||||
void checkPeakValues();
|
void checkPeakValues();
|
||||||
|
@ -397,6 +407,8 @@ private:
|
||||||
bool _shouldEchoLocally{ false };
|
bool _shouldEchoLocally{ false };
|
||||||
bool _shouldEchoToServer{ false };
|
bool _shouldEchoToServer{ false };
|
||||||
bool _isNoiseGateEnabled{ true };
|
bool _isNoiseGateEnabled{ true };
|
||||||
|
bool _isNoiseReductionAutomatic{ true };
|
||||||
|
float _noiseReductionThreshold{ 0.2f };
|
||||||
bool _warnWhenMuted;
|
bool _warnWhenMuted;
|
||||||
bool _isAECEnabled{ true };
|
bool _isAECEnabled{ true };
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue