mirror of
https://github.com/swift-project/pilotclient.git
synced 2026-04-05 01:05:34 +08:00
Issue #100 Add slider for master output volume
This commit is contained in:
@@ -268,16 +268,14 @@ namespace BlackCore
|
||||
|
||||
bool CAfvClient::isMuted() const
|
||||
{
|
||||
const int v1 = this->getNormalizedOutputVolume(CComSystem::Com1);
|
||||
const int v2 = this->getNormalizedOutputVolume(CComSystem::Com2);
|
||||
return v1 < 1 && v2 < 1;
|
||||
const int v = this->getNormalizedMasterOutputVolume();
|
||||
return v < 1;
|
||||
}
|
||||
|
||||
void CAfvClient::setMuted(bool mute)
|
||||
{
|
||||
if (this->isMuted() == mute) { return; }
|
||||
this->setNormalizedOutputVolume(CComSystem::Com1, mute ? 0 : 50);
|
||||
this->setNormalizedOutputVolume(CComSystem::Com2, mute ? 0 : 50);
|
||||
this->setNormalizedMasterOutputVolume(mute ? 0 : 50);
|
||||
emit this->changedMute(mute);
|
||||
}
|
||||
|
||||
@@ -768,7 +766,7 @@ namespace BlackCore
|
||||
return changed;
|
||||
}
|
||||
|
||||
double CAfvClient::getOutputVolumeDb(CComSystem::ComUnit comUnit) const
|
||||
double CAfvClient::getComOutputVolumeDb(CComSystem::ComUnit comUnit) const
|
||||
{
|
||||
QMutexLocker lock(&m_mutexVolume);
|
||||
if (comUnit == CComSystem::Com1)
|
||||
@@ -798,19 +796,19 @@ namespace BlackCore
|
||||
return i;
|
||||
}
|
||||
|
||||
int CAfvClient::getNormalizedOutputVolume(CComSystem::ComUnit comUnit) const
|
||||
int CAfvClient::getNormalizedMasterOutputVolume() const
|
||||
{
|
||||
double db = this->getOutputVolumeDb(comUnit);
|
||||
double range = MaxDbOut;
|
||||
int v = 50;
|
||||
if (db < 0)
|
||||
{
|
||||
v = 0;
|
||||
db -= MinDbOut;
|
||||
range = qAbs(MinDbOut);
|
||||
}
|
||||
v += qRound(db * 50 / range);
|
||||
return v;
|
||||
QMutexLocker lock(&m_mutexVolume);
|
||||
return m_outputMasterVolumeNormalized;
|
||||
}
|
||||
|
||||
int CAfvClient::getNormalizedComOutputVolume(CComSystem::ComUnit comUnit) const
|
||||
{
|
||||
QMutexLocker lock(&m_mutexVolume);
|
||||
if (comUnit == CComSystem::Com1) { return m_outputVolumeCom1Normalized; }
|
||||
else if (comUnit == CComSystem::Com2) { return m_outputVolumeCom2Normalized; }
|
||||
qFatal("Invalid ComUnit");
|
||||
return 0;
|
||||
}
|
||||
|
||||
bool CAfvClient::setNormalizedInputVolume(int volume)
|
||||
@@ -824,11 +822,49 @@ namespace BlackCore
|
||||
return this->setInputVolumeDb(dB);
|
||||
}
|
||||
|
||||
void CAfvClient::setNormalizedOutputVolume(CComSystem::ComUnit comUnit, int volume)
|
||||
bool CAfvClient::setNormalizedMasterOutputVolume(int volume)
|
||||
{
|
||||
if (!CThreadUtils::isInThisThread(this))
|
||||
{
|
||||
// call in background thread of AFVClient to avoid lock issues
|
||||
QPointer<CAfvClient> myself(this);
|
||||
QTimer::singleShot(0, this, [ = ]
|
||||
{
|
||||
if (!myself || !CAfvClient::hasContexts()) { return; }
|
||||
myself->setNormalizedMasterOutputVolume(volume);
|
||||
});
|
||||
return true; // not exactly "true" as we do it async
|
||||
}
|
||||
|
||||
bool changed = false;
|
||||
{
|
||||
QMutexLocker lock(&m_mutexVolume);
|
||||
changed = m_outputMasterVolumeNormalized != volume;
|
||||
if (changed) { m_outputMasterVolumeNormalized = volume; }
|
||||
}
|
||||
|
||||
// Trigger update of com volumes
|
||||
int com1Normalized = getNormalizedComOutputVolume(CComSystem::Com1);
|
||||
int com2Normalized = getNormalizedComOutputVolume(CComSystem::Com2);
|
||||
setNormalizedComOutputVolume(CComSystem::Com1, com1Normalized);
|
||||
setNormalizedComOutputVolume(CComSystem::Com2, com2Normalized);
|
||||
|
||||
return changed;
|
||||
}
|
||||
|
||||
bool CAfvClient::setNormalizedComOutputVolume(CComSystem::ComUnit comUnit, int volume)
|
||||
{
|
||||
if (volume < 0) { volume = 0; }
|
||||
else if (volume > 100) { volume = 100; }
|
||||
|
||||
// Save original volume
|
||||
if (comUnit == CComSystem::Com1) { m_outputVolumeCom1Normalized = volume; }
|
||||
else if (comUnit == CComSystem::Com2) { m_outputVolumeCom2Normalized = volume; }
|
||||
else { qFatal("Invalid ComUnit"); }
|
||||
|
||||
// Calculate volume relative to master-output volume
|
||||
volume = qRound((double)volume*getNormalizedMasterOutputVolume()/100);
|
||||
|
||||
// Asymetric
|
||||
double range = MaxDbOut;
|
||||
double dB = 0;
|
||||
@@ -844,7 +880,7 @@ namespace BlackCore
|
||||
dB += (volume * range / 50.0);
|
||||
|
||||
// converted to MinDbOut-MaxDbOut
|
||||
this->setOutputVolumeDb(comUnit, dB);
|
||||
return this->setComOutputVolumeDb(comUnit, dB);
|
||||
}
|
||||
|
||||
double CAfvClient::getInputVolumePeakVU() const
|
||||
@@ -1099,12 +1135,14 @@ namespace BlackCore
|
||||
{
|
||||
const CSettings audioSettings = m_audioSettings.get();
|
||||
const int iv = audioSettings.getInVolume();
|
||||
const int ov = audioSettings.getOutVolume();
|
||||
const int ov1 = audioSettings.getOutVolumeCom1();
|
||||
const int ov2 = audioSettings.getOutVolumeCom2();
|
||||
|
||||
this->setNormalizedInputVolume(iv);
|
||||
this->setNormalizedOutputVolume(CComSystem::Com1, ov1);
|
||||
this->setNormalizedOutputVolume(CComSystem::Com2, ov2);
|
||||
this->setNormalizedMasterOutputVolume(ov);
|
||||
this->setNormalizedComOutputVolume(CComSystem::Com1, ov1);
|
||||
this->setNormalizedComOutputVolume(CComSystem::Com2, ov2);
|
||||
this->setBypassEffects(!audioSettings.isAudioEffectsEnabled());
|
||||
}
|
||||
|
||||
@@ -1160,8 +1198,8 @@ namespace BlackCore
|
||||
const int vol1 = com1.getVolumeReceive();
|
||||
const int vol2 = com2.getVolumeReceive();
|
||||
|
||||
this->setNormalizedOutputVolume(CComSystem::Com1, vol1);
|
||||
this->setNormalizedOutputVolume(CComSystem::Com2, vol2);
|
||||
this->setNormalizedComOutputVolume(CComSystem::Com1, vol1);
|
||||
this->setNormalizedComOutputVolume(CComSystem::Com2, vol2);
|
||||
|
||||
// enable, we currently treat receive as enable
|
||||
// flight sim cockpits normally use rx and tx
|
||||
@@ -1415,7 +1453,7 @@ namespace BlackCore
|
||||
return sApp && !sApp->isShuttingDown() && sApp->getIContextOwnAircraft() && sApp->getIContextNetwork() && sApp->getIContextSimulator();
|
||||
}
|
||||
|
||||
bool CAfvClient::setOutputVolumeDb(CComSystem::ComUnit comUnit, double valueDb)
|
||||
bool CAfvClient::setComOutputVolumeDb(CComSystem::ComUnit comUnit, double valueDb)
|
||||
{
|
||||
if (!CThreadUtils::isInThisThread(this))
|
||||
{
|
||||
@@ -1424,7 +1462,7 @@ namespace BlackCore
|
||||
QTimer::singleShot(0, this, [ = ]
|
||||
{
|
||||
if (!myself || !CAfvClient::hasContexts()) { return; }
|
||||
myself->setOutputVolumeDb(comUnit, valueDb);
|
||||
myself->setComOutputVolumeDb(comUnit, valueDb);
|
||||
});
|
||||
return true; // not exactly "true" as we do it async
|
||||
}
|
||||
@@ -1464,7 +1502,7 @@ namespace BlackCore
|
||||
return false;
|
||||
}
|
||||
|
||||
if (m_outputSampleProvider)
|
||||
if (m_soundcardSampleProvider)
|
||||
{
|
||||
changed = m_soundcardSampleProvider->setGainRatioForTransceiver(comUnit, gainRatio);
|
||||
}
|
||||
|
||||
@@ -234,11 +234,11 @@ namespace BlackCore
|
||||
Q_INVOKABLE bool setInputVolumeDb(double valueDb);
|
||||
//! @}
|
||||
|
||||
//! Output volume in dB, [MinDbOut, MaxDbOut]dB
|
||||
//! Output volume for each COM in dB, [MinDbOut, MaxDbOut]dB
|
||||
//! \threadsafe
|
||||
//! @{
|
||||
double getOutputVolumeDb(BlackMisc::Aviation::CComSystem::ComUnit comUnit) const;
|
||||
Q_INVOKABLE bool setOutputVolumeDb(BlackMisc::Aviation::CComSystem::ComUnit comUnit, double valueDb);
|
||||
double getComOutputVolumeDb(BlackMisc::Aviation::CComSystem::ComUnit comUnit) const;
|
||||
Q_INVOKABLE bool setComOutputVolumeDb(BlackMisc::Aviation::CComSystem::ComUnit comUnit, double valueDb);
|
||||
//! @}
|
||||
|
||||
//! Gain ratio
|
||||
@@ -249,9 +249,11 @@ namespace BlackCore
|
||||
//! \threadsafe
|
||||
//! @{
|
||||
int getNormalizedInputVolume() const;
|
||||
int getNormalizedOutputVolume(BlackMisc::Aviation::CComSystem::ComUnit comUnit) const;
|
||||
int getNormalizedComOutputVolume(BlackMisc::Aviation::CComSystem::ComUnit comUnit) const;
|
||||
int getNormalizedMasterOutputVolume() const;
|
||||
bool setNormalizedInputVolume(int volume);
|
||||
void setNormalizedOutputVolume(BlackMisc::Aviation::CComSystem::ComUnit comUnit, int volume);
|
||||
bool setNormalizedComOutputVolume(BlackMisc::Aviation::CComSystem::ComUnit comUnit, int volume);
|
||||
bool setNormalizedMasterOutputVolume(int volume);
|
||||
//! @}
|
||||
|
||||
//! VU values, 0..1
|
||||
@@ -412,6 +414,9 @@ namespace BlackCore
|
||||
QDateTime m_startDateTimeUtc;
|
||||
|
||||
double m_inputVolumeDb = 0.0;
|
||||
int m_outputMasterVolumeNormalized = 0;
|
||||
int m_outputVolumeCom1Normalized = 0;
|
||||
int m_outputVolumeCom2Normalized = 0;
|
||||
double m_outputVolumeDbCom1 = 0.0;
|
||||
double m_outputGainRatioCom1 = 1.0; //!< 0dB
|
||||
double m_outputVolumeDbCom2 = 0.0;
|
||||
|
||||
@@ -110,8 +110,7 @@ namespace BlackCore
|
||||
else if (parser.commandStartsWith("vol") && parser.countParts() > 1)
|
||||
{
|
||||
const int v = parser.toInt(1);
|
||||
this->setVoiceOutputVolume(CComSystem::Com1, v);
|
||||
this->setVoiceOutputVolume(CComSystem::Com2, v);
|
||||
this->setMasterOutputVolume(v);
|
||||
return true;
|
||||
}
|
||||
else if (afvClient() && parser.matchesCommand(".aliased") && parser.countParts() > 1)
|
||||
@@ -149,8 +148,9 @@ namespace BlackCore
|
||||
if (!myself || !sApp || sApp->isShuttingDown()) { return; }
|
||||
|
||||
const CSettings as = m_audioSettings.getThreadLocal();
|
||||
this->setVoiceOutputVolume(CComSystem::Com1, as.getOutVolumeCom1());
|
||||
this->setVoiceOutputVolume(CComSystem::Com2, as.getOutVolumeCom2());
|
||||
this->setMasterOutputVolume(as.getOutVolume());
|
||||
this->setComOutputVolume(CComSystem::Com1, as.getOutVolumeCom1());
|
||||
this->setComOutputVolume(CComSystem::Com2, as.getOutVolumeCom2());
|
||||
m_selcalPlayer = new CSelcalPlayer(CAudioDeviceInfo::getDefaultOutputDevice(), this);
|
||||
|
||||
myself->changeDeviceSettings();
|
||||
@@ -421,22 +421,20 @@ namespace BlackCore
|
||||
m_voiceClient->startAudio(inputDevice, outputDevice);
|
||||
}
|
||||
|
||||
void CContextAudioBase::setVoiceOutputVolume(CComSystem::ComUnit comUnit, int volume)
|
||||
void CContextAudioBase::setMasterOutputVolume(int volume)
|
||||
{
|
||||
if (comUnit != CComSystem::Com1 && comUnit != CComSystem::Com2) { return; }
|
||||
if (!m_voiceClient) { return; }
|
||||
|
||||
const bool wasMuted = this->isMuted();
|
||||
volume = CSettings::fixOutVolume(volume);
|
||||
|
||||
const int currentVolume = m_voiceClient->getNormalizedOutputVolume(comUnit);
|
||||
const int currentVolume = m_voiceClient->getNormalizedMasterOutputVolume();
|
||||
const bool changedVoiceOutput = (currentVolume != volume);
|
||||
if (changedVoiceOutput)
|
||||
{
|
||||
// TODO: KB 2020-05 the mute handling should entirely go to AFV client!
|
||||
m_voiceClient->setNormalizedOutputVolume(comUnit, volume);
|
||||
if (comUnit == CComSystem::Com1) { m_outVolumeBeforeMuteCom1 = volume; }
|
||||
if (comUnit == CComSystem::Com2) { m_outVolumeBeforeMuteCom2 = volume; }
|
||||
m_voiceClient->setNormalizedMasterOutputVolume(volume);
|
||||
m_outMasterVolumeBeforeMute = volume;
|
||||
|
||||
emit this->changedAudioVolume(volume);
|
||||
if ((volume > 0 && wasMuted) || (volume < 1 && !wasMuted))
|
||||
@@ -446,6 +444,29 @@ namespace BlackCore
|
||||
}
|
||||
}
|
||||
|
||||
CSettings as(m_audioSettings.getThreadLocal());
|
||||
if (as.getOutVolume() != volume)
|
||||
{
|
||||
as.setOutVolume(volume);
|
||||
m_audioSettings.set(as);
|
||||
}
|
||||
}
|
||||
|
||||
void CContextAudioBase::setComOutputVolume(CComSystem::ComUnit comUnit, int volume)
|
||||
{
|
||||
if (comUnit != CComSystem::Com1 && comUnit != CComSystem::Com2) { return; }
|
||||
if (!m_voiceClient) { return; }
|
||||
|
||||
volume = CSettings::fixOutVolume(volume);
|
||||
|
||||
const int currentVolume = m_voiceClient->getNormalizedComOutputVolume(comUnit);
|
||||
const bool changedVoiceOutput = (currentVolume != volume);
|
||||
if (changedVoiceOutput)
|
||||
{
|
||||
m_voiceClient->setNormalizedComOutputVolume(comUnit, volume);
|
||||
emit this->changedAudioVolume(volume);
|
||||
}
|
||||
|
||||
CSettings as(m_audioSettings.getThreadLocal());
|
||||
if (comUnit == CComSystem::Com1 && as.getOutVolumeCom1() != volume)
|
||||
{
|
||||
@@ -459,10 +480,16 @@ namespace BlackCore
|
||||
}
|
||||
}
|
||||
|
||||
int CContextAudioBase::getVoiceOutputVolume(CComSystem::ComUnit comUnit) const
|
||||
int CContextAudioBase::getMasterOutputVolume() const
|
||||
{
|
||||
if (!m_voiceClient) { return 0; }
|
||||
return m_voiceClient->getNormalizedOutputVolume(comUnit);
|
||||
return m_voiceClient->getNormalizedMasterOutputVolume();
|
||||
}
|
||||
|
||||
int CContextAudioBase::getComOutputVolume(CComSystem::ComUnit comUnit) const
|
||||
{
|
||||
if (!m_voiceClient) { return 0; }
|
||||
return m_voiceClient->getNormalizedComOutputVolume(comUnit);
|
||||
}
|
||||
|
||||
void CContextAudioBase::setMute(bool muted)
|
||||
@@ -470,18 +497,11 @@ namespace BlackCore
|
||||
if (!m_voiceClient) { return; }
|
||||
if (this->isMuted() == muted) { return; } // avoid roundtrips / unnecessary signals
|
||||
|
||||
if (muted)
|
||||
{
|
||||
m_outVolumeBeforeMuteCom1 = m_voiceClient->getNormalizedOutputVolume(CComSystem::Com1);
|
||||
m_outVolumeBeforeMuteCom2 = m_voiceClient->getNormalizedOutputVolume(CComSystem::Com2);
|
||||
}
|
||||
if (muted) { m_outMasterVolumeBeforeMute = m_voiceClient->getNormalizedMasterOutputVolume(); }
|
||||
|
||||
|
||||
m_voiceClient->setMuted(muted);
|
||||
if (!muted)
|
||||
{
|
||||
m_voiceClient->setNormalizedOutputVolume(CComSystem::Com1, m_outVolumeBeforeMuteCom1);
|
||||
m_voiceClient->setNormalizedOutputVolume(CComSystem::Com2, m_outVolumeBeforeMuteCom2);
|
||||
}
|
||||
if (!muted) { m_voiceClient->setNormalizedMasterOutputVolume(m_outMasterVolumeBeforeMute); }
|
||||
|
||||
// signal no longer need, signaled by m_voiceClient->setMuted
|
||||
// emit this->changedMute(muted);
|
||||
@@ -594,8 +614,9 @@ namespace BlackCore
|
||||
const CSettings s = m_audioSettings.get();
|
||||
const QString dir = s.getNotificationSoundDirectory();
|
||||
m_notificationPlayer.updateDirectory(dir);
|
||||
this->setVoiceOutputVolume(CComSystem::Com1, s.getOutVolumeCom1());
|
||||
this->setVoiceOutputVolume(CComSystem::Com2, s.getOutVolumeCom2());
|
||||
this->setMasterOutputVolume(s.getOutVolume());
|
||||
this->setComOutputVolume(CComSystem::Com1, s.getOutVolumeCom1());
|
||||
this->setComOutputVolume(CComSystem::Com2, s.getOutVolumeCom2());
|
||||
}
|
||||
|
||||
void CContextAudioBase::onChangedVoiceSettings()
|
||||
@@ -607,19 +628,15 @@ namespace BlackCore
|
||||
void CContextAudioBase::audioIncreaseVolume(bool enabled)
|
||||
{
|
||||
if (!enabled) { return; }
|
||||
const int v1 = qRound(this->getVoiceOutputVolume(CComSystem::Com1) * 1.05);
|
||||
const int v2 = qRound(this->getVoiceOutputVolume(CComSystem::Com2) * 1.05);
|
||||
this->setVoiceOutputVolume(CComSystem::Com1, v1);
|
||||
this->setVoiceOutputVolume(CComSystem::Com2, v2);
|
||||
const int v = qRound(this->getMasterOutputVolume() * 1.05);
|
||||
this->setMasterOutputVolume(v);
|
||||
}
|
||||
|
||||
void CContextAudioBase::audioDecreaseVolume(bool enabled)
|
||||
{
|
||||
if (!enabled) { return; }
|
||||
const int v1 = qRound(this->getVoiceOutputVolume(CComSystem::Com1) / 1.05);
|
||||
const int v2 = qRound(this->getVoiceOutputVolume(CComSystem::Com2) / 1.05);
|
||||
this->setVoiceOutputVolume(CComSystem::Com1, v1);
|
||||
this->setVoiceOutputVolume(CComSystem::Com2, v2);
|
||||
const int v = qRound(this->getMasterOutputVolume() / 1.05);
|
||||
this->setMasterOutputVolume(v);
|
||||
}
|
||||
|
||||
void CContextAudioBase::xCtxNetworkConnectionStatusChanged(const CConnectionStatus &from, const CConnectionStatus &to)
|
||||
|
||||
@@ -178,8 +178,10 @@ namespace BlackCore
|
||||
|
||||
//! Volume
|
||||
//! @{
|
||||
void setVoiceOutputVolume(BlackMisc::Aviation::CComSystem::ComUnit comUnit, int volume);
|
||||
int getVoiceOutputVolume(BlackMisc::Aviation::CComSystem::ComUnit comUnit) const;
|
||||
void setMasterOutputVolume(int volume);
|
||||
void setComOutputVolume(BlackMisc::Aviation::CComSystem::ComUnit comUnit, int volume);
|
||||
int getMasterOutputVolume() const;
|
||||
int getComOutputVolume(BlackMisc::Aviation::CComSystem::ComUnit comUnit) const;
|
||||
void setMute(bool muted);
|
||||
bool isMuted() const;
|
||||
//! @}
|
||||
@@ -354,8 +356,7 @@ namespace BlackCore
|
||||
CActionBind m_actionAudioVolumeIncrease { BlackMisc::Input::audioVolumeIncreaseHotkeyAction(), BlackMisc::Input::audioVolumeIncreaseHotkeyIcon(), this, &CContextAudioBase::audioIncreaseVolume };
|
||||
CActionBind m_actionAudioVolumeDecrease { BlackMisc::Input::audioVolumeDecreaseHotkeyAction(), BlackMisc::Input::audioVolumeDecreaseHotkeyIcon(), this, &CContextAudioBase::audioDecreaseVolume };
|
||||
|
||||
int m_outVolumeBeforeMuteCom1 = 90;
|
||||
int m_outVolumeBeforeMuteCom2 = 90;
|
||||
int m_outMasterVolumeBeforeMute = 50;
|
||||
static constexpr int MinUnmuteVolume = 20; //!< minimum volume when unmuted
|
||||
|
||||
//! Do we use a local core
|
||||
|
||||
Reference in New Issue
Block a user