Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
449 changes: 404 additions & 45 deletions src/client.cpp

Large diffs are not rendered by default.

44 changes: 28 additions & 16 deletions src/client.h
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,8 @@
#include <QString>
#include <QDateTime>
#include <QMutex>
#include <atomic>
#include <memory>
#ifdef USE_OPUS_SHARED_LIB
# include "opus/opus_custom.h"
#else
Expand Down Expand Up @@ -142,6 +144,7 @@ class CClientChannel
};

class CClientSettings;
class CAuxiliaryMonoSender;

class CClient : public QObject
{
Expand Down Expand Up @@ -185,6 +188,13 @@ class CClient : public QObject
EAudChanConf GetAudioChannels() const { return eAudioChannelConf; }
void SetAudioChannels ( const EAudChanConf eNAudChanConf );

bool IsAuxiliaryMonoSenderEnabled() const { return eAudioChannelConf == CC_TWO_IN_STEREO_OUT; }
void SetAuxiliaryMonoSenderEnabled ( const bool bEnable );
bool CanUseAuxiliaryMonoSender();

bool IsAuxiliaryPrimaryOnLeft() const { return bAuxiliaryPrimaryOnLeft.load(); }
void SetAuxiliaryPrimaryOnLeft ( const bool bPrimaryOnLeft ) { bAuxiliaryPrimaryOnLeft.store ( bPrimaryOnLeft ); }

int GetAudioInFader() const { return iAudioInFader; }
void SetAudioInFader ( const int iNV ) { iAudioInFader = iNV; }

Expand All @@ -201,20 +211,11 @@ class CClient : public QObject
void SetDoAutoSockBufSize ( const bool bValue );
bool GetDoAutoSockBufSize() const { return Channel.GetDoAutoSockBufSize(); }

void SetSockBufNumFrames ( const int iNumBlocks, const bool bPreserve = false ) { Channel.SetSockBufNumFrames ( iNumBlocks, bPreserve ); }
void SetSockBufNumFrames ( const int iNumBlocks, const bool bPreserve = false );
int GetSockBufNumFrames() { return Channel.GetSockBufNumFrames(); }

void SetServerSockBufNumFrames ( const int iNumBlocks )
{
iServerSockBufNumFrames = iNumBlocks;

// if auto setting is disabled, inform the server about the new size
if ( !GetDoAutoSockBufSize() )
{
Channel.CreateJitBufMes ( iServerSockBufNumFrames );
}
}
int GetServerSockBufNumFrames() { return iServerSockBufNumFrames; }
void SetServerSockBufNumFrames ( const int iNumBlocks );
int GetServerSockBufNumFrames() { return iServerSockBufNumFrames; }

int GetUploadRateKbps() { return Channel.GetUploadRateKbps(); }

Expand Down Expand Up @@ -289,7 +290,7 @@ class CClient : public QObject

void SetInputBoost ( const int iNewBoost ) { iInputBoost = iNewBoost; }

void SetRemoteInfo() { Channel.SetRemoteInfo ( ChannelInfo ); }
void SetRemoteInfo();

void CreateChatTextMes ( const QString& strChatText ) { Channel.CreateChatTextMes ( strChatText ); }

Expand Down Expand Up @@ -340,9 +341,14 @@ class CClient : public QObject
// callback function must be static, otherwise it does not work
static void AudioCallback ( CVector<short>& psData, void* arg );

void Init();
void ProcessSndCrdAudioData ( CVector<short>& vecsStereoSndCrd );
void ProcessAudioDataIntern ( CVector<short>& vecsStereoSndCrd );
void Init();
EAudChanConf GetEffectiveAudioChannels() const;
void ConfigureAuxiliaryMonoSender();
void StartAuxiliaryMonoSender();
void StopAuxiliaryMonoSender();
CChannelCoreInfo GetAuxiliaryChannelInfo() const;
void ProcessSndCrdAudioData ( CVector<short>& vecsStereoSndCrd );
void ProcessAudioDataIntern ( CVector<short>& vecsStereoSndCrd );

int PreparePingMessage();
int EvaluatePingMessage ( const int iMs );
Expand Down Expand Up @@ -389,13 +395,18 @@ class CClient : public QObject
EAudChanConf eAudioChannelConf;
int iNumAudioChannels;
bool bIsInitializationPhase;
std::atomic<bool> bAuxiliaryPrimaryOnLeft;
bool bMuteOutStream;
float fMuteOutStreamGain;
CVector<unsigned char> vecCeltData;

bool bIPv6Available; // must be before Socket - passed by reference to Socket
const quint16 iSocketQosNumber;
const bool bDisableIPv6;
CHighPrioSocket Socket;

std::unique_ptr<CAuxiliaryMonoSender> pAuxiliaryMonoSender;

CSound Sound;
CStereoSignalLevelMeter SignalLevelMeter;

Expand All @@ -416,6 +427,7 @@ class CClient : public QObject
CBuffer<int16_t> SndCrdConversionBufferOut;
CVector<int16_t> vecDataConvBuf;
CVector<int16_t> vecsStereoSndCrdMuteStream;
CVector<int16_t> vecAuxiliaryMonoInput;
CVector<int16_t> vecZeros;

bool bFraSiFactPrefSupported;
Expand Down
57 changes: 57 additions & 0 deletions src/clientdlg.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -693,6 +693,39 @@ void CClientDlg::ManageDragNDrop ( QDropEvent* Event, const bool bCheckAccept )

void CClientDlg::UpdateRevSelection()
{
if ( pClient->IsAuxiliaryMonoSenderEnabled() )
{
const QString strPrimaryInput = "<b>" + tr ( "Primary Input" ) + ":</b> " +
tr ( "Selects which mapped input is sent by the visible client. "
"The other input is sent by the auxiliary client." );

lblAudioReverb->setText ( tr ( "Primary Input" ) );
lblAudioReverb->setWhatsThis ( strPrimaryInput );
sldAudioReverb->setVisible ( false );
sldAudioReverb->setEnabled ( false );
rbtReverbSelL->setVisible ( true );
rbtReverbSelR->setVisible ( true );
rbtReverbSelL->setWhatsThis ( strPrimaryInput );
rbtReverbSelR->setWhatsThis ( strPrimaryInput );
rbtReverbSelL->setAccessibleName ( tr ( "Left primary input" ) );
rbtReverbSelR->setAccessibleName ( tr ( "Right primary input" ) );
rbtReverbSelL->setChecked ( pClient->IsAuxiliaryPrimaryOnLeft() );
rbtReverbSelR->setChecked ( !pClient->IsAuxiliaryPrimaryOnLeft() );

MainMixerBoard->SetDisplayPans ( false );
return;
}

const QString strReverbChannelSelection =
"<b>" + tr ( "Reverb Channel Selection" ) + ":</b> " + tr ( "Selects the input channel to which reverb is applied." );
lblAudioReverb->setText ( tr ( "Reverb" ) );
sldAudioReverb->setVisible ( true );
sldAudioReverb->setEnabled ( true );
rbtReverbSelL->setWhatsThis ( strReverbChannelSelection );
rbtReverbSelR->setWhatsThis ( strReverbChannelSelection );
rbtReverbSelL->setAccessibleName ( tr ( "Left channel selection for reverb" ) );
rbtReverbSelR->setAccessibleName ( tr ( "Right channel selection for reverb" ) );

if ( pClient->GetAudioChannels() == CC_STEREO )
{
// for stereo make channel selection invisible since
Expand Down Expand Up @@ -721,6 +754,30 @@ void CClientDlg::UpdateRevSelection()
MainMixerBoard->SetDisplayPans ( pClient->GetAudioChannels() != CC_MONO );
}

void CClientDlg::OnReverbSelLClicked()
{
if ( pClient->IsAuxiliaryMonoSenderEnabled() )
{
pClient->SetAuxiliaryPrimaryOnLeft ( true );
}
else
{
pClient->SetReverbOnLeftChan ( true );
}
}

void CClientDlg::OnReverbSelRClicked()
{
if ( pClient->IsAuxiliaryMonoSenderEnabled() )
{
pClient->SetAuxiliaryPrimaryOnLeft ( false );
}
else
{
pClient->SetReverbOnLeftChan ( false );
}
}

void CClientDlg::OnConnectDlgAccepted()
{
// We had an issue that the accepted signal was emit twice if a list item was double
Expand Down
4 changes: 2 additions & 2 deletions src/clientdlg.h
Original file line number Diff line number Diff line change
Expand Up @@ -204,9 +204,9 @@ public slots:

void OnAudioReverbValueChanged ( int value ) { pClient->SetReverbLevel ( value ); }

void OnReverbSelLClicked() { pClient->SetReverbOnLeftChan ( true ); }
void OnReverbSelLClicked();

void OnReverbSelRClicked() { pClient->SetReverbOnLeftChan ( false ); }
void OnReverbSelRClicked();

void OnFeedbackDetectionChanged ( int state ) { ClientSettingsDlg.SetEnableFeedbackDetection ( state == Qt::Checked ); }

Expand Down
16 changes: 16 additions & 0 deletions src/clientsettingsdlg.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -509,6 +509,7 @@ CClientSettingsDlg::CClientSettingsDlg ( CClient* pNCliP, CClientSettings* pNSet
cbxAudioChannels->addItem ( tr ( "Mono" ) ); // CC_MONO
cbxAudioChannels->addItem ( tr ( "Mono-in/Stereo-out" ) ); // CC_MONO_IN_STEREO_OUT
cbxAudioChannels->addItem ( tr ( "Stereo" ) ); // CC_STEREO
cbxAudioChannels->addItem ( tr ( "Two-in/Stereo-out" ) ); // CC_TWO_IN_STEREO_OUT
cbxAudioChannels->setCurrentIndex ( static_cast<int> ( pClient->GetAudioChannels() ) );

// Audio Quality combo box
Expand Down Expand Up @@ -1226,12 +1227,14 @@ void CClientSettingsDlg::OnLInChanActivated ( int iChanIdx )
{
pClient->SetSndCrdLeftInputChannel ( iChanIdx );
UpdateSoundDeviceChannelSelectionFrame();
UpdateAuxiliaryMonoSender();
}

void CClientSettingsDlg::OnRInChanActivated ( int iChanIdx )
{
pClient->SetSndCrdRightInputChannel ( iChanIdx );
UpdateSoundDeviceChannelSelectionFrame();
UpdateAuxiliaryMonoSender();
}

void CClientSettingsDlg::OnLOutChanActivated ( int iChanIdx )
Expand All @@ -1249,6 +1252,7 @@ void CClientSettingsDlg::OnROutChanActivated ( int iChanIdx )
void CClientSettingsDlg::OnAudioChannelsActivated ( int iChanIdx )
{
pClient->SetAudioChannels ( static_cast<EAudChanConf> ( iChanIdx ) );
cbxAudioChannels->setCurrentIndex ( static_cast<int> ( pClient->GetAudioChannels() ) );
emit AudioChannelsChanged();
UpdateDisplay(); // upload rate will be changed
}
Expand Down Expand Up @@ -1365,6 +1369,18 @@ void CClientSettingsDlg::UpdateDisplay()
UpdateJitterBufferFrame();
UpdateSoundCardFrame();
UpdateUploadRate();
UpdateAuxiliaryMonoSender();
}

void CClientSettingsDlg::UpdateAuxiliaryMonoSender()
{
const bool bAuxiliaryMonoSenderEnabled = pClient->IsAuxiliaryMonoSenderEnabled();

cbxAudioChannels->setEnabled ( !pClient->IsRunning() );
cbxAudioQuality->setEnabled ( !bAuxiliaryMonoSenderEnabled );
sldAudioPan->setEnabled ( !bAuxiliaryMonoSenderEnabled );
lblAudioPan->setEnabled ( !bAuxiliaryMonoSenderEnabled );
lblAudioPanValue->setEnabled ( !bAuxiliaryMonoSenderEnabled );
}

void CClientSettingsDlg::UpdateDirectoryComboBox()
Expand Down
1 change: 1 addition & 0 deletions src/clientsettingsdlg.h
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,7 @@ class CClientSettingsDlg : public CBaseDlg, private Ui_CClientSettingsDlgBase
void UpdateSoundCardFrame();
void UpdateDirectoryComboBox();
void UpdateAudioFaderSlider();
void UpdateAuxiliaryMonoSender();
QString GenSndCrdBufferDelayString ( const int iFrameSize, const QString strAddText = "" );

virtual void showEvent ( QShowEvent* ) override;
Expand Down
10 changes: 9 additions & 1 deletion src/settings.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -621,7 +621,7 @@ void CClientSettings::ReadSettingsFromXML ( const QDomDocument& IniXMLDocument,
}

// audio channels
if ( GetNumericIniSet ( IniXMLDocument, "client", "audiochannels", 0, 2 /* CC_STEREO */, iValue ) )
if ( GetNumericIniSet ( IniXMLDocument, "client", "audiochannels", 0, 3 /* CC_TWO_IN_STEREO_OUT */, iValue ) )
{
pClient->SetAudioChannels ( static_cast<EAudChanConf> ( iValue ) );
}
Expand All @@ -632,6 +632,11 @@ void CClientSettings::ReadSettingsFromXML ( const QDomDocument& IniXMLDocument,
pClient->SetAudioQuality ( static_cast<EAudioQuality> ( iValue ) );
}

if ( GetFlagIniSet ( IniXMLDocument, "client", "auxiliaryprimaryleft", bValue ) )
{
pClient->SetAuxiliaryPrimaryOnLeft ( bValue );
}

// MIDI settings: Always read from XML first to preserve values
if ( GetNumericIniSet ( IniXMLDocument, "client", "midichannel", 0, 16, iValue ) )
iMidiChannel = iValue;
Expand Down Expand Up @@ -993,6 +998,9 @@ void CClientSettings::WriteSettingsToXML ( QDomDocument& IniXMLDocument, bool is
// audio quality
SetNumericIniSet ( IniXMLDocument, "client", "audioquality", static_cast<int> ( pClient->GetAudioQuality() ) );

// primary input for Two-in/Stereo-out mode
SetFlagIniSet ( IniXMLDocument, "client", "auxiliaryprimaryleft", pClient->IsAuxiliaryPrimaryOnLeft() );

// custom directories
for ( iIdx = 0; iIdx < MAX_NUM_SERVER_ADDR_ITEMS; iIdx++ )
{
Expand Down
4 changes: 3 additions & 1 deletion src/util.h
Original file line number Diff line number Diff line change
Expand Up @@ -504,7 +504,8 @@ enum EAudChanConf
// used for settings -> enum values should be fixed
CC_MONO = 0,
CC_MONO_IN_STEREO_OUT = 1,
CC_STEREO = 2
CC_STEREO = 2,
CC_TWO_IN_STEREO_OUT = 3

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd say stereo already covers this. This should rather tell the server to treat a stereo signal as two mono signals and have the client display two channels instead of one.

};

// Audio compression type enum -------------------------------------------------
Expand Down Expand Up @@ -844,6 +845,7 @@ class CInstPictures

// per definition: the very first instrument is the "not used" instrument
static int GetNotUsedInstrument() { return 0; }
static int GetVocalInstrument() { return 10; }
static bool IsNotUsedInstrument ( const int iInstrument ) { return iInstrument == 0; }

static int GetNumAvailableInst() { return GetTable().Size(); }
Expand Down
Loading