start work for supporting CELT codec, code does not compile at the moment (backup checkin)
This commit is contained in:
parent
4642431103
commit
034530474c
21 changed files with 499 additions and 583 deletions
150
src/buffer.cpp
150
src/buffer.cpp
|
@ -35,40 +35,14 @@ void CNetBuf::Init ( const int iNewBlockSize, const int iNewNumBlocks )
|
|||
iBlockSize = iNewBlockSize;
|
||||
iMemSize = iNewBlockSize * iNewNumBlocks;
|
||||
|
||||
// fade in first block added to the buffer
|
||||
bFadeInNewPutData = true;
|
||||
|
||||
// allocate and clear memory for actual data buffer
|
||||
vecdMemory.Init ( iMemSize );
|
||||
vecbyMemory.Init ( iMemSize );
|
||||
|
||||
// use the "get" flag to make sure the buffer is cleared
|
||||
Clear ( CT_GET );
|
||||
|
||||
// initialize number of samples for fading effect
|
||||
if ( FADE_IN_OUT_NUM_SAM < iBlockSize )
|
||||
{
|
||||
iNumSamFading = iBlockSize;
|
||||
}
|
||||
else
|
||||
{
|
||||
iNumSamFading = FADE_IN_OUT_NUM_SAM;
|
||||
}
|
||||
|
||||
if ( FADE_IN_OUT_NUM_SAM_EXTRA > iBlockSize )
|
||||
{
|
||||
iNumSamFadingExtra = iBlockSize;
|
||||
}
|
||||
else
|
||||
{
|
||||
iNumSamFadingExtra = FADE_IN_OUT_NUM_SAM_EXTRA;
|
||||
}
|
||||
|
||||
// init variables for extrapolation (in case a fade out is needed)
|
||||
dExPDiff = 0.0;
|
||||
dExPLastV = 0.0;
|
||||
}
|
||||
|
||||
bool CNetBuf::Put ( CVector<double>& vecdData )
|
||||
bool CNetBuf::Put ( const CVector<uint8_t>& vecbyData )
|
||||
{
|
||||
#ifdef _DEBUG_
|
||||
static FILE* pFileBI = fopen("bufferin.dat", "w");
|
||||
|
@ -79,7 +53,7 @@ fflush(pFileBI);
|
|||
bool bPutOK = true;
|
||||
|
||||
// get size of data to be added to the buffer
|
||||
const int iInSize = vecdData.Size();
|
||||
const int iInSize = vecbyData.Size();
|
||||
|
||||
// Check if there is not enough space available -> correct
|
||||
if ( GetAvailSpace() < iInSize )
|
||||
|
@ -88,9 +62,6 @@ fflush(pFileBI);
|
|||
// prepare for new data
|
||||
Clear ( CT_PUT );
|
||||
|
||||
// set flag to fade in new block to avoid clicks
|
||||
bFadeInNewPutData = true;
|
||||
|
||||
bPutOK = false; // return error flag
|
||||
|
||||
// check for special case: buffer memory is not sufficient
|
||||
|
@ -101,12 +72,6 @@ fflush(pFileBI);
|
|||
}
|
||||
}
|
||||
|
||||
// fade in new block if required
|
||||
if ( bFadeInNewPutData )
|
||||
{
|
||||
FadeInAudioDataBlock ( vecdData );
|
||||
}
|
||||
|
||||
// copy new data in internal buffer
|
||||
int iCurPos = 0;
|
||||
if ( iPutPos + iInSize > iMemSize )
|
||||
|
@ -117,12 +82,12 @@ fflush(pFileBI);
|
|||
// data must be written in two steps because of wrap around
|
||||
while ( iPutPos < iMemSize )
|
||||
{
|
||||
vecdMemory[iPutPos++] = vecdData[iCurPos++];
|
||||
vecbyMemory[iPutPos++] = vecbyData[iCurPos++];
|
||||
}
|
||||
|
||||
for ( iPutPos = 0; iPutPos < iRemSpace; iPutPos++ )
|
||||
{
|
||||
vecdMemory[iPutPos] = vecdData[iCurPos++];
|
||||
vecbyMemory[iPutPos] = vecbyData[iCurPos++];
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -131,7 +96,7 @@ fflush(pFileBI);
|
|||
const int iEnd = iPutPos + iInSize;
|
||||
while ( iPutPos < iEnd )
|
||||
{
|
||||
vecdMemory[iPutPos++] = vecdData[iCurPos++];
|
||||
vecbyMemory[iPutPos++] = vecbyData[iCurPos++];
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -148,13 +113,12 @@ fflush(pFileBI);
|
|||
return bPutOK;
|
||||
}
|
||||
|
||||
bool CNetBuf::Get ( CVector<double>& vecdData )
|
||||
bool CNetBuf::Get ( CVector<uint8_t>& vecbyData )
|
||||
{
|
||||
bool bGetOK = true; // init return value
|
||||
bool bFadeOutExtrap = false;
|
||||
bool bGetOK = true; // init return value
|
||||
|
||||
// get size of data to be get from the buffer
|
||||
const int iInSize = vecdData.Size();
|
||||
const int iInSize = vecbyData.Size();
|
||||
|
||||
// Check if there is not enough data available -> correct
|
||||
if ( GetAvailData() < iInSize )
|
||||
|
@ -163,11 +127,6 @@ bool CNetBuf::Get ( CVector<double>& vecdData )
|
|||
// prepare for getting data
|
||||
Clear ( CT_GET );
|
||||
|
||||
// set flag to fade in next new block in buffer and fade out last
|
||||
// block by extrapolation to avoid clicks
|
||||
bFadeInNewPutData = true;
|
||||
bFadeOutExtrap = true;
|
||||
|
||||
bGetOK = false; // return error flag
|
||||
|
||||
// check for special case: buffer memory is not sufficient
|
||||
|
@ -188,12 +147,12 @@ bool CNetBuf::Get ( CVector<double>& vecdData )
|
|||
// data must be read in two steps because of wrap around
|
||||
while ( iGetPos < iMemSize )
|
||||
{
|
||||
vecdData[iCurPos++] = vecdMemory[iGetPos++];
|
||||
vecbyData[iCurPos++] = vecbyMemory[iGetPos++];
|
||||
}
|
||||
|
||||
for ( iGetPos = 0; iGetPos < iRemData; iGetPos++ )
|
||||
{
|
||||
vecdData[iCurPos++] = vecdMemory[iGetPos];
|
||||
vecbyData[iCurPos++] = vecbyMemory[iGetPos];
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -202,7 +161,7 @@ bool CNetBuf::Get ( CVector<double>& vecdData )
|
|||
const int iEnd = iGetPos + iInSize;
|
||||
while ( iGetPos < iEnd )
|
||||
{
|
||||
vecdData[iCurPos++] = vecdMemory[iGetPos++];
|
||||
vecbyData[iCurPos++] = vecbyMemory[iGetPos++];
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -216,23 +175,6 @@ bool CNetBuf::Get ( CVector<double>& vecdData )
|
|||
eBufState = CNetBuf::BS_OK;
|
||||
}
|
||||
|
||||
|
||||
/* extrapolate data from old block to avoid "clicks"
|
||||
we have to do this method since we cannot fade out the old block
|
||||
anymore since it is already gone (processed or send through the
|
||||
network) */
|
||||
if ( bFadeOutExtrap )
|
||||
{
|
||||
FadeOutExtrapolateAudioDataBlock ( vecdData, dExPDiff, dExPLastV );
|
||||
}
|
||||
|
||||
/* save some paramters from last block which is needed in case we do not
|
||||
have enough data for next "get" operation and need to extrapolate the
|
||||
signal to avoid "clicks"
|
||||
we assume here that "iBlockSize" is larger than 1! */
|
||||
dExPDiff = vecdData[iInSize - 1] - vecdData[iInSize - 2];
|
||||
dExPLastV = vecdData[iInSize - 1];
|
||||
|
||||
return bGetOK;
|
||||
}
|
||||
|
||||
|
@ -303,7 +245,7 @@ void CNetBuf::Clear ( const EClearType eClearType )
|
|||
if ( eClearType == CT_GET )
|
||||
{
|
||||
// clear buffer
|
||||
vecdMemory.Reset ( 0.0 );
|
||||
vecbyMemory.Reset ( 0 );
|
||||
|
||||
// correct buffer so that after the current get operation the pointer
|
||||
// are at maximum distance
|
||||
|
@ -334,38 +276,6 @@ void CNetBuf::Clear ( const EClearType eClearType )
|
|||
iPutPos -= iMemSize;
|
||||
}
|
||||
|
||||
// fade out old data right before new put pointer
|
||||
int iCurPos = iPutPos - iNumSamFading;
|
||||
int i = iNumSamFading;
|
||||
|
||||
if ( iCurPos < 0 )
|
||||
{
|
||||
// wrap around
|
||||
iCurPos += iMemSize;
|
||||
|
||||
// data must be processed in two steps because of wrap around
|
||||
while ( iCurPos < iMemSize )
|
||||
{
|
||||
vecdMemory[iCurPos++] *= ( (double) i / iNumSamFading );
|
||||
i--;
|
||||
}
|
||||
|
||||
for ( iCurPos = 0; iCurPos < iPutPos; iCurPos++ )
|
||||
{
|
||||
vecdMemory[iCurPos] *= ( (double) i / iNumSamFading );
|
||||
i--;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// data can be processed in one step
|
||||
while ( iCurPos < iPutPos )
|
||||
{
|
||||
vecdMemory[iCurPos++] *= ( (double) i / iNumSamFading );
|
||||
i--;
|
||||
}
|
||||
}
|
||||
|
||||
// check for special case
|
||||
if ( iPutPos == iGetPos )
|
||||
{
|
||||
|
@ -378,40 +288,6 @@ void CNetBuf::Clear ( const EClearType eClearType )
|
|||
}
|
||||
}
|
||||
|
||||
void CNetBuf::FadeInAudioDataBlock ( CVector<double>& vecdData )
|
||||
{
|
||||
// correct fading length if necessary
|
||||
const int iCurFadingLen = min ( vecdData.Size(), iNumSamFading );
|
||||
|
||||
// apply linear fading
|
||||
for ( int i = 0; i < iCurFadingLen; i++ )
|
||||
{
|
||||
vecdData[i] *= ( (double) i / iCurFadingLen );
|
||||
}
|
||||
|
||||
// reset flag
|
||||
bFadeInNewPutData = false;
|
||||
}
|
||||
|
||||
void CNetBuf::FadeOutExtrapolateAudioDataBlock ( CVector<double>& vecdData,
|
||||
const double dExPDiff,
|
||||
const double dExPLastV )
|
||||
{
|
||||
// correct fading length if necessary
|
||||
const int iCurFadingLenExtra = min ( vecdData.Size(), iNumSamFadingExtra );
|
||||
|
||||
// apply linear extrapolation and linear fading
|
||||
for ( int i = 0; i < iCurFadingLenExtra; i++ )
|
||||
{
|
||||
// calculate extrapolated value
|
||||
vecdData[i] = ( ( i + 1 ) * dExPDiff + dExPLastV );
|
||||
|
||||
// linear fading
|
||||
vecdData[i] *= ( (double) ( iCurFadingLenExtra - i ) / iCurFadingLenExtra );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* conversion buffer implementation *******************************************/
|
||||
void CConvBuf::Init ( const int iNewMemSize )
|
||||
|
|
33
src/buffer.h
33
src/buffer.h
|
@ -29,15 +29,6 @@
|
|||
#include "global.h"
|
||||
|
||||
|
||||
/* Definitions ****************************************************************/
|
||||
// time for fading effect for masking drop outs
|
||||
#define FADE_IN_OUT_TIME ( (double) 2 ) // ms
|
||||
#define FADE_IN_OUT_NUM_SAM ( (int) ( SYSTEM_SAMPLE_RATE * FADE_IN_OUT_TIME ) / 1000 )
|
||||
|
||||
// for extrapolation a shorter time for fading
|
||||
#define FADE_IN_OUT_NUM_SAM_EXTRA 10 // samples
|
||||
|
||||
|
||||
/* Classes ********************************************************************/
|
||||
class CNetBuf
|
||||
{
|
||||
|
@ -48,8 +39,8 @@ public:
|
|||
void Init ( const int iNewBlockSize, const int iNewNumBlocks );
|
||||
int GetSize() { return iMemSize / iBlockSize; }
|
||||
|
||||
bool Put ( CVector<double>& vecdData );
|
||||
bool Get ( CVector<double>& vecdData );
|
||||
bool Put ( const CVector<uint8_t>& vecbyData );
|
||||
bool Get ( CVector<uint8_t>& vecbyData );
|
||||
|
||||
protected:
|
||||
enum EBufState { BS_OK, BS_FULL, BS_EMPTY };
|
||||
|
@ -57,22 +48,12 @@ protected:
|
|||
void Clear ( const EClearType eClearType );
|
||||
int GetAvailSpace() const;
|
||||
int GetAvailData() const;
|
||||
void FadeInAudioDataBlock ( CVector<double>& vecdData );
|
||||
void FadeOutExtrapolateAudioDataBlock ( CVector<double>& vecdData,
|
||||
const double dExPDiff, const double dExPLastV );
|
||||
|
||||
CVector<double> vecdMemory;
|
||||
int iMemSize;
|
||||
int iBlockSize;
|
||||
int iGetPos, iPutPos;
|
||||
EBufState eBufState;
|
||||
bool bFadeInNewPutData;
|
||||
int iNumSamFading;
|
||||
int iNumSamFadingExtra;
|
||||
|
||||
// extrapolation parameters
|
||||
double dExPDiff;
|
||||
double dExPLastV;
|
||||
CVector<uint8_t> vecbyMemory;
|
||||
int iMemSize;
|
||||
int iBlockSize;
|
||||
int iGetPos, iPutPos;
|
||||
EBufState eBufState;
|
||||
};
|
||||
|
||||
|
||||
|
|
227
src/channel.cpp
227
src/channel.cpp
|
@ -28,9 +28,8 @@
|
|||
/******************************************************************************\
|
||||
* CChannelSet *
|
||||
\******************************************************************************/
|
||||
CChannelSet::CChannelSet ( const int iNewUploadRateLimitKbps ) :
|
||||
bWriteStatusHTMLFile ( false ),
|
||||
iUploadRateLimitKbps ( iNewUploadRateLimitKbps )
|
||||
CChannelSet::CChannelSet() :
|
||||
bWriteStatusHTMLFile ( false )
|
||||
{
|
||||
// enable all channels (for the server all channel must be enabled the
|
||||
// entire life time of the software
|
||||
|
@ -492,7 +491,8 @@ void CChannelSet::GetBlockAllConC ( CVector<int>& vecChanID,
|
|||
{
|
||||
// read out all input buffers to decrease timeout counter on
|
||||
// disconnected channels
|
||||
const EGetDataStat eGetStat = vecChannels[i].GetData ( vecdData );
|
||||
// const EGetDataStat eGetStat = vecChannels[i].GetData ( vecdData );
|
||||
const EGetDataStat eGetStat=GS_BUFFER_OK;//TEST
|
||||
|
||||
// if channel was just disconnected, set flag that connected
|
||||
// client list is sent to all other clients
|
||||
|
@ -668,56 +668,9 @@ CChannel::CChannel ( const bool bNIsServer ) :
|
|||
bIsEnabled ( false ),
|
||||
iCurNetwOutBlSiFact ( DEF_NET_BLOCK_SIZE_FACTOR )
|
||||
{
|
||||
// query all possible network in buffer sizes for determining if an
|
||||
// audio packet was received (the following code only works if all
|
||||
// possible network buffer sizes are different!)
|
||||
// we add a special entry for network modes which are managed via the
|
||||
// protocol -> "+ 1"
|
||||
const int iNumSupportedAudComprTypes = 3;
|
||||
vecNetwBufferInProps.Init ( iNumSupportedAudComprTypes *
|
||||
MAX_NET_BLOCK_SIZE_FACTOR + 1 );
|
||||
|
||||
// init special mode (with invalid data)
|
||||
vecNetwBufferInProps[0].iAudioBlockSize = 0;
|
||||
vecNetwBufferInProps[0].eAudComprType = CT_NONE;
|
||||
vecNetwBufferInProps[0].iNetwInBufSize = 0;
|
||||
|
||||
for ( int i = 0; i < MAX_NET_BLOCK_SIZE_FACTOR; i++ )
|
||||
{
|
||||
// (consider the special mode -> "1 +")
|
||||
const int iNoneIdx = 1 + iNumSupportedAudComprTypes * i;
|
||||
const int iIMAIdx = 1 + iNumSupportedAudComprTypes * i + 1;
|
||||
const int iMSIdx = 1 + iNumSupportedAudComprTypes * i + 2;
|
||||
|
||||
// network block size factor must start from 1 -> i + 1
|
||||
const int iCurNetBlockSizeFact = i + 1;
|
||||
vecNetwBufferInProps[iNoneIdx].iAudioBlockSize =
|
||||
iCurNetBlockSizeFact * MIN_SERVER_BLOCK_SIZE_SAMPLES;
|
||||
|
||||
vecNetwBufferInProps[iIMAIdx].iAudioBlockSize =
|
||||
iCurNetBlockSizeFact * MIN_SERVER_BLOCK_SIZE_SAMPLES;
|
||||
|
||||
vecNetwBufferInProps[iMSIdx].iAudioBlockSize =
|
||||
iCurNetBlockSizeFact * MIN_SERVER_BLOCK_SIZE_SAMPLES;
|
||||
|
||||
// None (no audio compression)
|
||||
vecNetwBufferInProps[iNoneIdx].eAudComprType = CT_NONE;
|
||||
vecNetwBufferInProps[iNoneIdx].iNetwInBufSize = AudioCompressionIn.Init (
|
||||
vecNetwBufferInProps[iNoneIdx].iAudioBlockSize,
|
||||
vecNetwBufferInProps[iNoneIdx].eAudComprType );
|
||||
|
||||
// IMA ADPCM
|
||||
vecNetwBufferInProps[iIMAIdx].eAudComprType = CT_IMAADPCM;
|
||||
vecNetwBufferInProps[iIMAIdx].iNetwInBufSize = AudioCompressionIn.Init (
|
||||
vecNetwBufferInProps[iIMAIdx].iAudioBlockSize,
|
||||
vecNetwBufferInProps[iIMAIdx].eAudComprType );
|
||||
|
||||
// MS ADPCM
|
||||
vecNetwBufferInProps[iMSIdx].eAudComprType = CT_MSADPCM;
|
||||
vecNetwBufferInProps[iMSIdx].iNetwInBufSize = AudioCompressionIn.Init (
|
||||
vecNetwBufferInProps[iMSIdx].iAudioBlockSize,
|
||||
vecNetwBufferInProps[iMSIdx].eAudComprType );
|
||||
}
|
||||
// init network input properties
|
||||
NetwBufferInProps.iAudioBlockSize = 0;
|
||||
NetwBufferInProps.iNetwInBufSize = 0;
|
||||
|
||||
// initial value for connection time out counter, we calculate the total
|
||||
// number of samples here and subtract the number of samples of the block
|
||||
|
@ -730,11 +683,7 @@ CChannel::CChannel ( const bool bNIsServer ) :
|
|||
// init the socket buffer
|
||||
SetSockBufSize ( DEF_NET_BUF_SIZE_NUM_BL );
|
||||
|
||||
// set initial input and output block size factors
|
||||
SetAudioBlockSizeAndComprIn (
|
||||
MIN_SERVER_BLOCK_SIZE_SAMPLES * DEF_NET_BLOCK_SIZE_FACTOR,
|
||||
CT_MSADPCM );
|
||||
|
||||
// set initial output block size factors
|
||||
if ( bIsServer )
|
||||
{
|
||||
SetNetwBufSizeFactOut ( DEF_NET_BLOCK_SIZE_FACTOR );
|
||||
|
@ -824,53 +773,20 @@ void CChannel::SetEnable ( const bool bNEnStat )
|
|||
}
|
||||
}
|
||||
|
||||
void CChannel::SetAudioBlockSizeAndComprIn ( const int iNewBlockSize,
|
||||
const EAudComprType eNewAudComprType )
|
||||
{
|
||||
QMutexLocker locker ( &Mutex );
|
||||
|
||||
// store block size value
|
||||
iCurAudioBlockSizeIn = iNewBlockSize;
|
||||
|
||||
// init audio compression unit
|
||||
AudioCompressionIn.Init ( iNewBlockSize, eNewAudComprType );
|
||||
}
|
||||
|
||||
void CChannel::SetNetwBufSizeOut ( const int iNewAudioBlockSizeOut )
|
||||
{
|
||||
// this function is intended for the client (not the server)
|
||||
QMutexLocker locker ( &Mutex );
|
||||
|
||||
// direct setting of audio buffer (without buffer size factor) is
|
||||
// right now only intendet for the client, not the server
|
||||
if ( !bIsServer )
|
||||
{
|
||||
// store new value
|
||||
iCurAudioBlockSizeOut = iNewAudioBlockSizeOut;
|
||||
|
||||
iAudComprSizeOut =
|
||||
AudioCompressionOut.Init ( iNewAudioBlockSizeOut, eAudComprTypeOut );
|
||||
}
|
||||
}
|
||||
|
||||
void CChannel::SetNetwBufSizeFactOut ( const int iNewNetwBlSiFactOut )
|
||||
{
|
||||
// this function is intended for the server (not the client)
|
||||
QMutexLocker locker ( &Mutex );
|
||||
|
||||
// use the network block size factor only for the server
|
||||
if ( bIsServer )
|
||||
{
|
||||
// store new value
|
||||
iCurNetwOutBlSiFact = iNewNetwBlSiFactOut;
|
||||
// store new value
|
||||
iCurNetwOutBlSiFact = iNewNetwBlSiFactOut;
|
||||
|
||||
// init audio compression and get audio compression block size
|
||||
iAudComprSizeOut = AudioCompressionOut.Init (
|
||||
iNewNetwBlSiFactOut * MIN_SERVER_BLOCK_SIZE_SAMPLES, eAudComprTypeOut );
|
||||
// init audio compression and get audio compression block size
|
||||
iAudComprSizeOut = AudioCompressionOut.Init (
|
||||
iNewNetwBlSiFactOut * MIN_SERVER_BLOCK_SIZE_SAMPLES, eAudComprTypeOut );
|
||||
|
||||
// init conversion buffer
|
||||
ConvBuf.Init ( iNewNetwBlSiFactOut * MIN_SERVER_BLOCK_SIZE_SAMPLES );
|
||||
}
|
||||
// init conversion buffer
|
||||
ConvBuf.Init ( iNewNetwBlSiFactOut * MIN_SERVER_BLOCK_SIZE_SAMPLES );
|
||||
}
|
||||
|
||||
void CChannel::SetAudioCompressionOut ( const EAudComprType eNewAudComprTypeOut )
|
||||
|
@ -1021,11 +937,22 @@ void CChannel::OnNetTranspPropsReceived ( CNetworkTransportProps NetworkTranspor
|
|||
QMutexLocker locker ( &Mutex );
|
||||
|
||||
// apply received parameters to internal data struct
|
||||
vecNetwBufferInProps[0].iAudioBlockSize = NetworkTransportProps.iMonoAudioBlockSize;
|
||||
vecNetwBufferInProps[0].eAudComprType = NetworkTransportProps.eAudioCodingType;
|
||||
vecNetwBufferInProps[0].iNetwInBufSize = AudioCompressionIn.Init (
|
||||
vecNetwBufferInProps[0].iAudioBlockSize,
|
||||
vecNetwBufferInProps[0].eAudComprType );
|
||||
NetwBufferInProps.iAudioBlockSize = NetworkTransportProps.iMonoAudioBlockSize;
|
||||
NetwBufferInProps.eAudComprType = NetworkTransportProps.eAudioCodingType;
|
||||
NetwBufferInProps.iNetwInBufSize = NetworkTransportProps.iNetworkPacketSize;
|
||||
|
||||
// re-initialize cycle time variance measurement if necessary
|
||||
if ( NetwBufferInProps.iAudioBlockSize != CycleTimeVariance.GetBlockLength() )
|
||||
{
|
||||
// re-init (we have to use the buffer size which works
|
||||
// on the system sample rate, therefore we use the
|
||||
// decompressed audio buffer size instead of the network
|
||||
// buffer size)
|
||||
CycleTimeVariance.Init ( NetwBufferInProps.iAudioBlockSize,
|
||||
SYSTEM_SAMPLE_RATE, TIME_MOV_AV_RESPONSE );
|
||||
|
||||
CycleTimeVariance.Reset();
|
||||
}
|
||||
}
|
||||
|
||||
void CChannel::OnReqNetTranspProps()
|
||||
|
@ -1040,7 +967,7 @@ void CChannel::CreateNetTranspPropsMessFromCurrentSettings()
|
|||
iCurAudioBlockSizeOut,
|
||||
1, // right now we only use mono
|
||||
SYSTEM_SAMPLE_RATE, // right now only one sample rate is supported
|
||||
AudioCompressionOut.GetType(),
|
||||
CT_CELT, // always CELT coding
|
||||
0 );
|
||||
|
||||
// send current network transport properties
|
||||
|
@ -1064,11 +991,6 @@ EPutDataStat CChannel::PutData ( const CVector<uint8_t>& vecbyData,
|
|||
bool bIsProtocolPacket = false;
|
||||
bool bIsAudioPacket = false;
|
||||
bool bNewConnection = false;
|
||||
bool bReinitializeIn = false;
|
||||
|
||||
// intermediate storage for new parameters
|
||||
int iNewAudioBlockSize;
|
||||
EAudComprType eNewAudComprType;
|
||||
|
||||
if ( bIsEnabled )
|
||||
{
|
||||
|
@ -1088,62 +1010,16 @@ EPutDataStat CChannel::PutData ( const CVector<uint8_t>& vecbyData,
|
|||
// only try to parse audio if it was not a protocol packet
|
||||
if ( !bIsProtocolPacket )
|
||||
{
|
||||
Mutex.lock();
|
||||
{
|
||||
// check if this is an audio packet by checking all possible lengths
|
||||
const int iPossNetwSizes = vecNetwBufferInProps.Size();
|
||||
|
||||
for ( int i = 0; i < iPossNetwSizes; i++ )
|
||||
{
|
||||
// check for low/high quality audio packets and set flags
|
||||
if ( iNumBytes == vecNetwBufferInProps[i].iNetwInBufSize )
|
||||
{
|
||||
bIsAudioPacket = true;
|
||||
|
||||
// check if we are correctly initialized
|
||||
iNewAudioBlockSize =
|
||||
vecNetwBufferInProps[i].iAudioBlockSize;
|
||||
|
||||
eNewAudComprType =
|
||||
vecNetwBufferInProps[i].eAudComprType;
|
||||
|
||||
if ( ( iNewAudioBlockSize != iCurAudioBlockSizeIn ) ||
|
||||
( eNewAudComprType != AudioCompressionIn.GetType() ) )
|
||||
{
|
||||
bReinitializeIn = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Mutex.unlock();
|
||||
|
||||
// actual initialization call has to be made
|
||||
// outside the mutex region since it internally
|
||||
// usees the same mutex, too
|
||||
if ( bReinitializeIn )
|
||||
{
|
||||
// re-initialize to new value
|
||||
SetAudioBlockSizeAndComprIn (
|
||||
iNewAudioBlockSize, eNewAudComprType );
|
||||
}
|
||||
|
||||
Mutex.lock();
|
||||
{
|
||||
// only process audio if packet has correct size
|
||||
if ( bIsAudioPacket )
|
||||
if ( iNumBytes == NetwBufferInProps.iNetwInBufSize )
|
||||
{
|
||||
// decompress audio
|
||||
CVector<short> vecsDecomprAudio ( AudioCompressionIn.Decode ( vecbyData ) );
|
||||
// set audio packet flag
|
||||
bIsAudioPacket = true;
|
||||
|
||||
// convert received data from short to double
|
||||
const int iAudioSize = vecsDecomprAudio.Size();
|
||||
CVector<double> vecdDecomprAudio ( iAudioSize );
|
||||
for ( int i = 0; i < iAudioSize; i++ )
|
||||
{
|
||||
vecdDecomprAudio[i] = static_cast<double> ( vecsDecomprAudio[i] );
|
||||
}
|
||||
|
||||
if ( SockBuf.Put ( vecdDecomprAudio ) )
|
||||
// store new packet in jitter buffer
|
||||
if ( SockBuf.Put ( vecbyData ) )
|
||||
{
|
||||
eRet = PS_AUDIO_OK;
|
||||
}
|
||||
|
@ -1152,28 +1028,13 @@ EPutDataStat CChannel::PutData ( const CVector<uint8_t>& vecbyData,
|
|||
eRet = PS_AUDIO_ERR;
|
||||
}
|
||||
|
||||
// update cycle time variance measurement, take care of
|
||||
// re-initialization, too, if necessary
|
||||
if ( iAudioSize != CycleTimeVariance.GetBlockLength() )
|
||||
{
|
||||
// re-init (we have to use the buffer size which works
|
||||
// on the system sample rate, therefore we use the
|
||||
// decompressed audio buffer size instead of the network
|
||||
// buffer size)
|
||||
CycleTimeVariance.Init ( iAudioSize,
|
||||
SYSTEM_SAMPLE_RATE, TIME_MOV_AV_RESPONSE );
|
||||
|
||||
CycleTimeVariance.Reset();
|
||||
}
|
||||
else
|
||||
{
|
||||
// update cycle time variance measurement
|
||||
|
||||
// TODO only update if time difference of received packets is below
|
||||
// a limit to avoid having short network troubles incorporated in the
|
||||
// statistic
|
||||
|
||||
CycleTimeVariance.Update();
|
||||
}
|
||||
CycleTimeVariance.Update();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1219,20 +1080,24 @@ EPutDataStat CChannel::PutData ( const CVector<uint8_t>& vecbyData,
|
|||
return eRet;
|
||||
}
|
||||
|
||||
EGetDataStat CChannel::GetData ( CVector<double>& vecdData )
|
||||
EGetDataStat CChannel::GetData ( CVector<uint8_t>& vecbyData )
|
||||
{
|
||||
QMutexLocker locker ( &Mutex );
|
||||
|
||||
EGetDataStat eGetStatus;
|
||||
|
||||
const bool bSockBufState = SockBuf.Get ( vecdData );
|
||||
const bool bSockBufState = SockBuf.Get ( vecbyData );
|
||||
|
||||
// decrease time-out counter
|
||||
if ( iConTimeOut > 0 )
|
||||
{
|
||||
|
||||
// TODO
|
||||
|
||||
|
||||
// subtract the number of samples of the current block since the
|
||||
// time out counter is based on samples not on blocks
|
||||
iConTimeOut -= vecdData.Size();
|
||||
iConTimeOut -= vecbyData.Size();
|
||||
|
||||
if ( iConTimeOut <= 0 )
|
||||
{
|
||||
|
|
|
@ -62,10 +62,6 @@ enum EGetDataStat
|
|||
GS_CHAN_NOT_CONNECTED
|
||||
};
|
||||
|
||||
// low upload data rate settings
|
||||
#define LOW_UPL_SET_AUDIO_COMPRESSION CT_MSADPCM
|
||||
#define LOW_UPL_SET_BLOCK_SIZE_FACTOR_OUT MAX_NET_BLOCK_SIZE_FACTOR
|
||||
|
||||
|
||||
/* Classes ********************************************************************/
|
||||
// CChannel --------------------------------------------------------------------
|
||||
|
@ -81,7 +77,7 @@ public:
|
|||
|
||||
EPutDataStat PutData ( const CVector<uint8_t>& vecbyData,
|
||||
int iNumBytes );
|
||||
EGetDataStat GetData ( CVector<double>& vecdData );
|
||||
EGetDataStat GetData ( CVector<uint8_t>& vecbyData );
|
||||
|
||||
CVector<uint8_t> PrepSendPacket ( const CVector<short>& vecsNPacket );
|
||||
|
||||
|
@ -111,7 +107,7 @@ public:
|
|||
void SetNetwBufSizeOut ( const int iNewAudioBlockSizeOut );
|
||||
int GetNetwBufSizeOut() { return iCurAudioBlockSizeOut; }
|
||||
|
||||
int GetAudioBlockSizeIn() { return iCurAudioBlockSizeIn; }
|
||||
int GetAudioBlockSizeIn() { return NetwBufferInProps.iAudioBlockSize; }
|
||||
int GetUploadRateKbps();
|
||||
|
||||
double GetTimingStdDev() { return CycleTimeVariance.GetStdDev(); }
|
||||
|
@ -152,9 +148,6 @@ public:
|
|||
void CreateDisconnectionMes() { Protocol.CreateDisconnectionMes(); }
|
||||
|
||||
protected:
|
||||
void SetAudioBlockSizeAndComprIn ( const int iNewBlockSize,
|
||||
const EAudComprType eNewAudComprType );
|
||||
|
||||
bool ProtocolIsEnabled();
|
||||
|
||||
// audio compression
|
||||
|
@ -189,19 +182,17 @@ protected:
|
|||
bool bIsEnabled;
|
||||
bool bIsServer;
|
||||
|
||||
int iCurAudioBlockSizeIn;
|
||||
int iCurNetwOutBlSiFact;
|
||||
int iCurAudioBlockSizeOut;
|
||||
|
||||
QMutex Mutex;
|
||||
|
||||
struct sNetwBufferInProps
|
||||
struct sNetwProperties
|
||||
{
|
||||
int iNetwInBufSize;
|
||||
int iAudioBlockSize;
|
||||
EAudComprType eAudComprType;
|
||||
int iNetwInBufSize;
|
||||
int iAudioBlockSize;
|
||||
};
|
||||
CVector<sNetwBufferInProps> vecNetwBufferInProps;
|
||||
sNetwProperties NetwBufferInProps;
|
||||
|
||||
EAudComprType eAudComprTypeOut;
|
||||
|
||||
|
@ -233,7 +224,7 @@ class CChannelSet : public QObject
|
|||
Q_OBJECT
|
||||
|
||||
public:
|
||||
CChannelSet ( const int iNewUploadRateLimitKbps = DEF_MAX_UPLOAD_RATE_KBPS );
|
||||
CChannelSet();
|
||||
virtual ~CChannelSet() {}
|
||||
|
||||
bool PutData ( const CVector<uint8_t>& vecbyRecBuf,
|
||||
|
@ -267,9 +258,6 @@ public:
|
|||
void StartStatusHTMLFileWriting ( const QString& strNewFileName,
|
||||
const QString& strNewServerNameWithPort );
|
||||
|
||||
void SetUploadRateLimitKbps ( const int iNewUploadRateLimitKbps )
|
||||
{ iUploadRateLimitKbps = iNewUploadRateLimitKbps; }
|
||||
|
||||
protected:
|
||||
CVector<CChannelShortInfo> CreateChannelList();
|
||||
void CreateAndSendChanListForAllConChannels();
|
||||
|
@ -278,7 +266,7 @@ protected:
|
|||
void CreateAndSendChatTextForAllConChannels ( const int iCurChanID, const QString& strChatText );
|
||||
void WriteHTMLChannelList();
|
||||
void SetOutputParameters();
|
||||
int CalculateTotalUploadRateKbps();
|
||||
int CalculateTotalUploadRateKbps();
|
||||
|
||||
/* do not use the vector class since CChannel does not have appropriate
|
||||
copy constructor/operator */
|
||||
|
@ -287,8 +275,6 @@ protected:
|
|||
|
||||
CVector<QString> vstrChatColors;
|
||||
|
||||
int iUploadRateLimitKbps;
|
||||
|
||||
// HTML file server status
|
||||
bool bWriteStatusHTMLFile;
|
||||
QString strServerHTMLFileListName;
|
||||
|
|
130
src/client.cpp
130
src/client.cpp
|
@ -36,9 +36,7 @@ CClient::CClient ( const quint16 iPortNumber ) :
|
|||
vstrIPAddress ( MAX_NUM_SERVER_ADDR_ITEMS, "" ), strName ( "" ),
|
||||
bOpenChatOnNewMessage ( true ),
|
||||
bDoAutoSockBufSize ( true ),
|
||||
iSndCrdPreferredMonoBlSizeIndex ( CSndCrdBufferSizes::GetDefaultIndex() ),
|
||||
iClientSampleRate ( SYSTEM_SAMPLE_RATE ),
|
||||
iSndCrdMonoBlockSizeSam ( 0 )
|
||||
iSndCrdPreferredMonoBlSizeIndex ( CSndCrdBufferSizes::GetDefaultIndex() )
|
||||
{
|
||||
// connection for protocol
|
||||
QObject::connect ( &Channel,
|
||||
|
@ -164,7 +162,7 @@ void CClient::SetSndCrdPreferredMonoBlSizeIndex ( const int iNewIdx )
|
|||
}
|
||||
|
||||
// init with new block size index parameter
|
||||
Init ( iClientSampleRate, iSndCrdPreferredMonoBlSizeIndex );
|
||||
Init ( iSndCrdPreferredMonoBlSizeIndex );
|
||||
|
||||
if ( bWasRunning )
|
||||
{
|
||||
|
@ -191,7 +189,7 @@ QString CClient::SetSndCrdDev ( const int iNewDev )
|
|||
|
||||
// init again because the sound card actual buffer size might
|
||||
// be changed on new device
|
||||
Init ( iClientSampleRate, iSndCrdPreferredMonoBlSizeIndex );
|
||||
Init ( iSndCrdPreferredMonoBlSizeIndex );
|
||||
|
||||
if ( bWasRunning )
|
||||
{
|
||||
|
@ -214,7 +212,7 @@ void CClient::OnSndCrdReinitRequest()
|
|||
// reinit the driver (we use the currently selected driver) and
|
||||
// init client object, too
|
||||
Sound.SetDev ( Sound.GetDev() );
|
||||
Init ( iClientSampleRate, iSndCrdPreferredMonoBlSizeIndex );
|
||||
Init ( iSndCrdPreferredMonoBlSizeIndex );
|
||||
|
||||
if ( bWasRunning )
|
||||
{
|
||||
|
@ -225,7 +223,7 @@ void CClient::OnSndCrdReinitRequest()
|
|||
void CClient::Start()
|
||||
{
|
||||
// init object
|
||||
Init ( iClientSampleRate, iSndCrdPreferredMonoBlSizeIndex );
|
||||
Init ( iSndCrdPreferredMonoBlSizeIndex );
|
||||
|
||||
// enable channel
|
||||
Channel.SetEnable ( true );
|
||||
|
@ -254,7 +252,7 @@ void CClient::Stop()
|
|||
PostWinMessage ( MS_RESET_ALL, 0 );
|
||||
}
|
||||
|
||||
void CClient::AudioCallback ( CVector<short>& psData, void* arg )
|
||||
void CClient::AudioCallback ( CVector<int16_t>& psData, void* arg )
|
||||
{
|
||||
// get the pointer to the object
|
||||
CClient* pMyClientObj = reinterpret_cast<CClient*> ( arg );
|
||||
|
@ -263,70 +261,62 @@ void CClient::AudioCallback ( CVector<short>& psData, void* arg )
|
|||
pMyClientObj->ProcessAudioData ( psData );
|
||||
}
|
||||
|
||||
void CClient::Init ( const int iSampleRate,
|
||||
const int iPrefMonoBlockSizeSamIndexAtSndCrdSamRate )
|
||||
void CClient::Init ( const int iPrefMonoBlockSizeSamIndexAtSndCrdSamRate )
|
||||
{
|
||||
// store new sample rate
|
||||
iClientSampleRate = iSampleRate;
|
||||
|
||||
// translate block size index in actual block size
|
||||
const int iPrefMonoBlockSizeSamAtSndCrdSamRate = CSndCrdBufferSizes::
|
||||
GetBufferSizeFromIndex ( iPrefMonoBlockSizeSamIndexAtSndCrdSamRate );
|
||||
|
||||
// get actual sound card buffer size using preferred size
|
||||
iSndCrdMonoBlockSizeSam = Sound.Init ( iPrefMonoBlockSizeSamAtSndCrdSamRate );
|
||||
iSndCrdStereoBlockSizeSam = 2 * iSndCrdMonoBlockSizeSam;
|
||||
|
||||
iMonoBlockSizeSam = iSndCrdMonoBlockSizeSam * iClientSampleRate / SND_CRD_SAMPLE_RATE;
|
||||
iMonoBlockSizeSam = Sound.Init ( iPrefMonoBlockSizeSamAtSndCrdSamRate );
|
||||
iStereoBlockSizeSam = 2 * iMonoBlockSizeSam;
|
||||
|
||||
// the channel works on the same block size as the sound interface
|
||||
Channel.SetNetwBufSizeOut ( iMonoBlockSizeSam );
|
||||
|
||||
vecsAudioSndCrdStereo.Init ( iSndCrdStereoBlockSizeSam );
|
||||
vecdAudioSndCrdMono.Init ( iSndCrdMonoBlockSizeSam );
|
||||
vecdAudioSndCrdStereo.Init ( iSndCrdStereoBlockSizeSam );
|
||||
vecsAudioSndCrdStereo.Init ( iStereoBlockSizeSam );
|
||||
|
||||
vecdAudioStereo.Init ( iStereoBlockSizeSam );
|
||||
|
||||
// resample objects are always initialized with the input block size
|
||||
// record
|
||||
ResampleObjDown.Init ( iSndCrdMonoBlockSizeSam,
|
||||
SND_CRD_SAMPLE_RATE, iClientSampleRate );
|
||||
|
||||
// playback
|
||||
ResampleObjUp.Init ( iMonoBlockSizeSam,
|
||||
iClientSampleRate, SND_CRD_SAMPLE_RATE );
|
||||
|
||||
// init network buffers
|
||||
vecsNetwork.Init ( iMonoBlockSizeSam );
|
||||
vecdNetwData.Init ( iMonoBlockSizeSam );
|
||||
|
||||
// init response time evaluation
|
||||
CycleTimeVariance.Init ( iMonoBlockSizeSam,
|
||||
iClientSampleRate, TIME_MOV_AV_RESPONSE );
|
||||
SYSTEM_SAMPLE_RATE, TIME_MOV_AV_RESPONSE );
|
||||
|
||||
CycleTimeVariance.Reset();
|
||||
|
||||
// init reverberation
|
||||
AudioReverb.Init ( iClientSampleRate );
|
||||
AudioReverb.Init ( SYSTEM_SAMPLE_RATE );
|
||||
|
||||
// init audio endocder/decoder (mono)
|
||||
CeltMode = celt_mode_create (
|
||||
SYSTEM_SAMPLE_RATE, 1, iMonoBlockSizeSam, NULL );
|
||||
|
||||
CeltEncoder = celt_encoder_create ( CeltMode );
|
||||
CeltDecoder = celt_decoder_create ( CeltMode );
|
||||
|
||||
// 16: low/normal quality 132 kbsp (128) / 90 kbps (256)
|
||||
// 40: high good 204 kbps (128) / 162 kbps (256)
|
||||
iCeltNumCodedBytes = 16;
|
||||
|
||||
vecCeltData.Init ( iCeltNumCodedBytes );
|
||||
|
||||
// init network buffers
|
||||
vecsNetwork.Init ( iMonoBlockSizeSam );
|
||||
vecbyNetwData.Init ( iCeltNumCodedBytes );
|
||||
|
||||
// the channel works on the audio coded block size
|
||||
Channel.SetNetwBufSizeOut ( iCeltNumCodedBytes );
|
||||
}
|
||||
|
||||
void CClient::ProcessAudioData ( CVector<short>& vecsStereoSndCrd )
|
||||
void CClient::ProcessAudioData ( CVector<int16_t>& vecsStereoSndCrd )
|
||||
{
|
||||
int i, j;
|
||||
|
||||
// convert data from short to double
|
||||
for ( i = 0; i < iSndCrdStereoBlockSizeSam; i++ )
|
||||
{
|
||||
vecdAudioSndCrdStereo[i] = (double) vecsStereoSndCrd[i];
|
||||
}
|
||||
|
||||
// resample data for each channel seaparately
|
||||
ResampleObjDown.ResampleStereo ( vecdAudioSndCrdStereo, vecdAudioStereo );
|
||||
|
||||
// update stereo signal level meter
|
||||
SignalLevelMeter.Update ( vecdAudioStereo );
|
||||
SignalLevelMeter.Update ( vecsStereoSndCrd );
|
||||
|
||||
// convert data from short to double
|
||||
for ( i = 0; i < iStereoBlockSizeSam; i++ )
|
||||
{
|
||||
vecdAudioStereo[i] = (double) vecsStereoSndCrd[i];
|
||||
}
|
||||
|
||||
// add reverberation effect if activated
|
||||
if ( iReverbLevel != 0 )
|
||||
|
@ -395,11 +385,17 @@ void CClient::ProcessAudioData ( CVector<short>& vecsStereoSndCrd )
|
|||
}
|
||||
|
||||
// send it through the network
|
||||
Socket.SendPacket ( Channel.PrepSendPacket ( vecsNetwork ),
|
||||
Channel.GetAddress() );
|
||||
// Socket.SendPacket ( Channel.PrepSendPacket ( vecsNetwork ),
|
||||
// Channel.GetAddress() );
|
||||
|
||||
celt_encode(CeltEncoder, &vecsNetwork[0], NULL, &vecCeltData[0], iCeltNumCodedBytes);
|
||||
Socket.SendPacket ( vecCeltData, Channel.GetAddress() );
|
||||
|
||||
|
||||
|
||||
|
||||
// receive a new block
|
||||
if ( Channel.GetData ( vecdNetwData ) == GS_BUFFER_OK )
|
||||
if ( Channel.GetData ( vecbyNetwData ) == GS_BUFFER_OK )
|
||||
{
|
||||
PostWinMessage ( MS_JIT_BUF_GET, MUL_COL_LED_GREEN );
|
||||
}
|
||||
|
@ -424,16 +420,36 @@ fflush(pFileDelay);
|
|||
// check if channel is connected
|
||||
if ( Channel.IsConnected() )
|
||||
{
|
||||
// resample data
|
||||
ResampleObjUp.ResampleMono ( vecdNetwData, vecdAudioSndCrdMono );
|
||||
|
||||
/*
|
||||
// convert data from double to short type and copy mono
|
||||
// received data in both sound card channels
|
||||
for ( i = 0, j = 0; i < iSndCrdMonoBlockSizeSam; i++, j += 2 )
|
||||
{
|
||||
vecsStereoSndCrd[j] = vecsStereoSndCrd[j + 1] =
|
||||
Double2Short ( vecdAudioSndCrdMono[i] );
|
||||
Double2Short ( vecdNetwData[i] );
|
||||
}
|
||||
*/
|
||||
|
||||
CVector<short> vecsAudioSndCrdMono ( iMonoBlockSizeSam );
|
||||
/*
|
||||
for ( i = 0; i < iMonoBlockSizeSam; i++ )
|
||||
{
|
||||
vecsAudioSndCrdMono[i] = Double2Short ( vecdNetwData[i] );
|
||||
}
|
||||
*/
|
||||
// TEST CELT
|
||||
//celt_encode(CeltEncoder, &vecsAudioSndCrdMono[0], NULL, &vecCeltData[0], iCeltNumCodedBytes);
|
||||
celt_decode(CeltDecoder, &vecbyNetwData[0], iCeltNumCodedBytes, &vecsAudioSndCrdMono[0]);
|
||||
|
||||
|
||||
for ( i = 0, j = 0; i < iMonoBlockSizeSam; i++, j += 2 )
|
||||
{
|
||||
vecsStereoSndCrd[j] = vecsStereoSndCrd[j + 1] =
|
||||
vecsAudioSndCrdMono[i];
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -472,7 +488,7 @@ void CClient::UpdateSocketBufferSize()
|
|||
// a minimum buffer size of the sum of both sizes
|
||||
const double dAudioBufferDurationMs =
|
||||
( iMonoBlockSizeSam + Channel.GetAudioBlockSizeIn() ) * 1000 /
|
||||
iClientSampleRate;
|
||||
SYSTEM_SAMPLE_RATE;
|
||||
|
||||
// accumulate the standard deviations of input network stream and
|
||||
// internal timer,
|
||||
|
|
29
src/client.h
29
src/client.h
|
@ -31,9 +31,9 @@
|
|||
#include <qstring.h>
|
||||
#include <qdatetime.h>
|
||||
#include <qmessagebox.h>
|
||||
#include "celt.h"
|
||||
#include "global.h"
|
||||
#include "socket.h"
|
||||
#include "resample.h"
|
||||
#include "channel.h"
|
||||
#include "audiocompr.h"
|
||||
#include "util.h"
|
||||
|
@ -125,7 +125,7 @@ public:
|
|||
void SetSndCrdPreferredMonoBlSizeIndex ( const int iNewIdx );
|
||||
int GetSndCrdPreferredMonoBlSizeIndex()
|
||||
{ return iSndCrdPreferredMonoBlSizeIndex; }
|
||||
int GetSndCrdActualMonoBlSize() { return iSndCrdMonoBlockSizeSam; }
|
||||
int GetSndCrdActualMonoBlSize() { return iMonoBlockSizeSam; }
|
||||
|
||||
void SetAudioCompressionOut ( const EAudComprType eNewAudComprTypeOut )
|
||||
{
|
||||
|
@ -160,8 +160,7 @@ protected:
|
|||
// callback function must be static, otherwise it does not work
|
||||
static void AudioCallback ( CVector<short>& psData, void* arg );
|
||||
|
||||
void Init ( const int iSampleRate,
|
||||
const int iPrefMonoBlockSizeSamIndexAtSndCrdSamRate );
|
||||
void Init ( const int iPrefMonoBlockSizeSamIndexAtSndCrdSamRate );
|
||||
void ProcessAudioData ( CVector<short>& vecsStereoSndCrd );
|
||||
void UpdateSocketBufferSize();
|
||||
|
||||
|
@ -169,11 +168,18 @@ protected:
|
|||
CChannel Channel;
|
||||
bool bDoAutoSockBufSize;
|
||||
|
||||
// audio encoder/decoder
|
||||
CELTMode* CeltMode;
|
||||
CELTEncoder* CeltEncoder;
|
||||
CELTDecoder* CeltDecoder;
|
||||
int iCeltNumCodedBytes;
|
||||
CVector<unsigned char> vecCeltData;
|
||||
|
||||
CSocket Socket;
|
||||
CSound Sound;
|
||||
CStereoSignalLevelMeter SignalLevelMeter;
|
||||
|
||||
CVector<double> vecdNetwData;
|
||||
CVector<uint8_t> vecbyNetwData;
|
||||
|
||||
int iAudioInFader;
|
||||
bool bReverbOnLeftChan;
|
||||
|
@ -181,24 +187,15 @@ protected:
|
|||
CAudioReverb AudioReverb;
|
||||
|
||||
int iSndCrdPreferredMonoBlSizeIndex;
|
||||
int iClientSampleRate;
|
||||
|
||||
int iSndCrdMonoBlockSizeSam;
|
||||
int iSndCrdStereoBlockSizeSam;
|
||||
int iMonoBlockSizeSam;
|
||||
int iStereoBlockSizeSam;
|
||||
|
||||
bool bOpenChatOnNewMessage;
|
||||
|
||||
CVector<short> vecsAudioSndCrdStereo;
|
||||
CVector<double> vecdAudioSndCrdMono;
|
||||
CVector<double> vecdAudioSndCrdStereo;
|
||||
CVector<int16_t> vecsAudioSndCrdStereo;
|
||||
CVector<double> vecdAudioStereo;
|
||||
CVector<short> vecsNetwork;
|
||||
|
||||
// resample objects
|
||||
CStereoAudioResample ResampleObjDown;
|
||||
CStereoAudioResample ResampleObjUp;
|
||||
CVector<int16_t> vecsNetwork;
|
||||
|
||||
// for ping measurement
|
||||
CPreciseTime PreciseTime;
|
||||
|
|
|
@ -177,13 +177,13 @@ void CClientSettingsDlg::UpdateSoundCardFrame()
|
|||
// we have input and output
|
||||
TextLabelPreferredSndCrdBufDelay->setText (
|
||||
QString().setNum ( (double) iPrefBufSize * 2 *
|
||||
1000 / SND_CRD_SAMPLE_RATE, 'f', 2 ) + " ms (" +
|
||||
1000 / SYSTEM_SAMPLE_RATE, 'f', 2 ) + " ms (" +
|
||||
QString().setNum ( iPrefBufSize ) + ")" );
|
||||
|
||||
// actual size (use yellow color if different from preferred size)
|
||||
const QString strActSizeValues =
|
||||
QString().setNum ( (double) iCurActualBufSize * 2 *
|
||||
1000 / SND_CRD_SAMPLE_RATE, 'f', 2 ) + " ms (" +
|
||||
1000 / SYSTEM_SAMPLE_RATE, 'f', 2 ) + " ms (" +
|
||||
QString().setNum ( iCurActualBufSize ) + ")";
|
||||
|
||||
if ( iPrefBufSize != iCurActualBufSize )
|
||||
|
@ -299,7 +299,7 @@ void CClientSettingsDlg::OnPingTimeResult ( int iPingTime )
|
|||
// the actual sound card buffer size
|
||||
const int iTotalSoundCardDelayMS =
|
||||
3 * pClient->GetSndCrdActualMonoBlSize() *
|
||||
1000 / SND_CRD_SAMPLE_RATE;
|
||||
1000 / SYSTEM_SAMPLE_RATE;
|
||||
|
||||
const int iDelayToFillNetworkPackets =
|
||||
( pClient->GetNetwBufSizeOut() + pClient->GetAudioBlockSizeIn() ) *
|
||||
|
|
45
src/global.h
45
src/global.h
|
@ -38,12 +38,12 @@
|
|||
|
||||
/* Definitions ****************************************************************/
|
||||
// define this macro to get debug output
|
||||
#define _DEBUG_
|
||||
//#define _DEBUG_
|
||||
#undef _DEBUG_
|
||||
|
||||
// version and application name (always use this version)
|
||||
#undef VERSION
|
||||
#define VERSION "2.3.1cvs"
|
||||
#define VERSION "3.0.0cvs"
|
||||
#define APP_NAME "llcon"
|
||||
|
||||
// file name for logging file
|
||||
|
@ -53,34 +53,20 @@
|
|||
#define DEFAULT_SERVER_ADDRESS "llcon.dyndns.org"
|
||||
|
||||
// defined port number for client and server
|
||||
#define LLCON_DEFAULT_PORT_NUMBER 22123
|
||||
#define LLCON_DEFAULT_PORT_NUMBER 22124
|
||||
|
||||
// system sample rate
|
||||
#define SYSTEM_SAMPLE_RATE 33000
|
||||
// system sample rate (the sound card and audio coder works on this sample rate)
|
||||
#define SYSTEM_SAMPLE_RATE 48000
|
||||
|
||||
// sound card sample rate. Should be always 48 kHz to avoid sound card driver
|
||||
// internal sample rate conversion which might be buggy
|
||||
#define SND_CRD_SAMPLE_RATE 48000
|
||||
|
||||
// minimum server block duration - all other buffer durations must be a multiple
|
||||
// of this duration
|
||||
#define MIN_SERVER_BLOCK_DURATION_MS 2 // ms
|
||||
|
||||
#define MIN_SERVER_BLOCK_SIZE_SAMPLES ( MIN_SERVER_BLOCK_DURATION_MS * SYSTEM_SAMPLE_RATE / 1000 )
|
||||
// System block size, this is the block size on which the audio coder works.
|
||||
// All other block sizes must be a multiple of this size
|
||||
#define SYSTEM_BLOCK_SIZE_SAMPLES 128
|
||||
|
||||
// define the maximum mono audio buffer size at a sample rate
|
||||
// of 48 kHz, this is important for defining the maximum number
|
||||
// of bytes to be expected from the network interface (we assume
|
||||
// here that "MAX_NET_BLOCK_SIZE_FACTOR * MIN_SERVER_BLOCK_SIZE_SAMPLES"
|
||||
// is smaller than this value here)
|
||||
// of bytes to be expected from the network interface
|
||||
#define MAX_MONO_AUD_BUFF_SIZE_AT_48KHZ 4096
|
||||
|
||||
// maximum value of factor for network block size
|
||||
#define MAX_NET_BLOCK_SIZE_FACTOR 3
|
||||
|
||||
// default network block size factor (only used for server)
|
||||
#define DEF_NET_BLOCK_SIZE_FACTOR 2
|
||||
|
||||
// minimum/maximum network buffer size (which can be chosen by slider)
|
||||
#define MIN_NET_BUF_SIZE_NUM_BL 1 // number of blocks
|
||||
#define MAX_NET_BUF_SIZE_NUM_BL 20 // number of blocks
|
||||
|
@ -88,9 +74,6 @@
|
|||
// default network buffer size
|
||||
#define DEF_NET_BUF_SIZE_NUM_BL 10 // number of blocks
|
||||
|
||||
// default maximum upload rate at server (typical DSL upload for good DSL)
|
||||
#define DEF_MAX_UPLOAD_RATE_KBPS 800 // kbps
|
||||
|
||||
// maximum number of recognized sound cards installed in the system,
|
||||
// definition for "no device"
|
||||
#define MAX_NUMBER_SOUND_CARDS 10
|
||||
|
@ -130,10 +113,12 @@
|
|||
#elif HAVE_INTTYPES_H
|
||||
# include <inttypes.h>
|
||||
#elif defined ( _WIN32 )
|
||||
typedef __int16 int16_t;
|
||||
typedef unsigned __int32 uint32_t;
|
||||
typedef unsigned __int16 uint16_t;
|
||||
typedef unsigned __int8 uint8_t;
|
||||
#else
|
||||
typedef short int16_t;
|
||||
typedef unsigned int uint32_t;
|
||||
typedef unsigned short uint16_t;
|
||||
typedef unsigned char uint8_t;
|
||||
|
@ -196,10 +181,10 @@ public:
|
|||
|
||||
/* Prototypes for global functions ********************************************/
|
||||
// command line parsing, TODO do not declare functions globally but in a class
|
||||
std::string UsageArguments ( char **argv );
|
||||
bool GetFlagArgument ( int, char **argv, int &i, std::string strShortOpt, std::string strLongOpt );
|
||||
bool GetStringArgument ( int argc, char **argv, int &i, std::string strShortOpt, std::string strLongOpt, std::string & strArg );
|
||||
bool GetNumericArgument ( int argc, char **argv, int &i, std::string strShortOpt, std::string strLongOpt, double rRangeStart, double rRangeStop, double & rValue);
|
||||
std::string UsageArguments ( char** argv );
|
||||
bool GetFlagArgument ( int argc, char** argv, int& i, std::string strShortOpt, std::string strLongOpt );
|
||||
bool GetStringArgument ( int argc, char** argv, int& i, std::string strShortOpt, std::string strLongOpt, std::string& strArg );
|
||||
bool GetNumericArgument ( int argc, char** argv, int& i, std::string strShortOpt, std::string strLongOpt, double rRangeStart, double rRangeStop, double& rValue);
|
||||
|
||||
// posting a window message
|
||||
void PostWinMessage ( const _MESSAGE_IDENT MessID, const int iMessageParam = 0,
|
||||
|
|
51
src/main.cpp
51
src/main.cpp
|
@ -48,7 +48,6 @@ int main ( int argc, char** argv )
|
|||
bool bUseGUI = true;
|
||||
bool bConnectOnStartup = false;
|
||||
bool bDisalbeLEDs = false;
|
||||
int iUploadRateLimitKbps = DEF_MAX_UPLOAD_RATE_KBPS;
|
||||
quint16 iPortNumber = LLCON_DEFAULT_PORT_NUMBER;
|
||||
std::string strIniFileName = "";
|
||||
std::string strHTMLStatusFileName = "";
|
||||
|
@ -97,17 +96,6 @@ int main ( int argc, char** argv )
|
|||
}
|
||||
|
||||
|
||||
// force low upload data rate flag -------------------------------------
|
||||
if ( GetNumericArgument ( argc, argv, i, "-u", "--maxuploadrate",
|
||||
100, 1000000, rDbleArgument ) )
|
||||
{
|
||||
iUploadRateLimitKbps = static_cast<int> ( rDbleArgument );
|
||||
cout << "maximum upload rate: " << iUploadRateLimitKbps <<
|
||||
" kbps" << std::endl;
|
||||
continue;
|
||||
}
|
||||
|
||||
|
||||
// port number ---------------------------------------------------------
|
||||
if ( GetNumericArgument ( argc, argv, i, "-p", "--port",
|
||||
0, 65535, rDbleArgument ) )
|
||||
|
@ -246,8 +234,7 @@ int main ( int argc, char** argv )
|
|||
iPortNumber,
|
||||
strHTMLStatusFileName.c_str(),
|
||||
strHistoryFileName.c_str(),
|
||||
strServerName.c_str(),
|
||||
iUploadRateLimitKbps );
|
||||
strServerName.c_str() );
|
||||
|
||||
if ( bUseGUI )
|
||||
{
|
||||
|
@ -307,10 +294,11 @@ std::string UsageArguments ( char **argv )
|
|||
" client)\n"
|
||||
" -p, --port local port number (only avaiable for server)\n"
|
||||
" -m, --htmlstatus enable HTML status file, set file name (only\n"
|
||||
" avaiable for server)\n"
|
||||
" available for server)\n"
|
||||
" -a, --servername server name required for HTML status (only\n"
|
||||
" available for server)\n"
|
||||
" -y, --history enable connection history and set file\n"
|
||||
" name (only available for server)\n"
|
||||
" -u, --maxuploadrate maximum upload rate (only avaiable for server)\n"
|
||||
" -c, --connect connect to last server on startup (only\n"
|
||||
" available for client)\n"
|
||||
" -d, --disableleds disable LEDs in main window (only available\n"
|
||||
|
@ -319,8 +307,11 @@ std::string UsageArguments ( char **argv )
|
|||
"Example: " + std::string ( argv[0] ) + " -l -inifile myinifile.ini\n";
|
||||
}
|
||||
|
||||
bool GetFlagArgument ( int, char **argv, int &i,
|
||||
std::string strShortOpt, std::string strLongOpt )
|
||||
bool GetFlagArgument ( int argc,
|
||||
char** argv,
|
||||
int& i,
|
||||
std::string strShortOpt,
|
||||
std::string strLongOpt )
|
||||
{
|
||||
if ( ( !strShortOpt.compare ( argv[i] ) ) || ( !strLongOpt.compare ( argv[i] ) ) )
|
||||
{
|
||||
|
@ -332,9 +323,12 @@ bool GetFlagArgument ( int, char **argv, int &i,
|
|||
}
|
||||
}
|
||||
|
||||
bool GetStringArgument ( int argc, char **argv, int &i,
|
||||
std::string strShortOpt, std::string strLongOpt,
|
||||
std::string & strArg )
|
||||
bool GetStringArgument ( int argc,
|
||||
char** argv,
|
||||
int& i,
|
||||
std::string strShortOpt,
|
||||
std::string strLongOpt,
|
||||
std::string& strArg )
|
||||
{
|
||||
if ( ( !strShortOpt.compare ( argv[i] ) ) || ( !strLongOpt.compare ( argv[i] ) ) )
|
||||
{
|
||||
|
@ -355,10 +349,14 @@ bool GetStringArgument ( int argc, char **argv, int &i,
|
|||
}
|
||||
}
|
||||
|
||||
bool GetNumericArgument ( int argc, char **argv, int &i,
|
||||
std::string strShortOpt, std::string strLongOpt,
|
||||
double rRangeStart, double rRangeStop,
|
||||
double & rValue)
|
||||
bool GetNumericArgument ( int argc,
|
||||
char** argv,
|
||||
int& i,
|
||||
std::string strShortOpt,
|
||||
std::string strLongOpt,
|
||||
double rRangeStart,
|
||||
double rRangeStop,
|
||||
double& rValue)
|
||||
{
|
||||
if ( ( !strShortOpt.compare ( argv[i] ) ) || ( !strLongOpt.compare ( argv[i] ) ) )
|
||||
{
|
||||
|
@ -392,7 +390,8 @@ bool GetNumericArgument ( int argc, char **argv, int &i,
|
|||
/******************************************************************************\
|
||||
* Window Message System *
|
||||
\******************************************************************************/
|
||||
void PostWinMessage ( const _MESSAGE_IDENT MessID, const int iMessageParam,
|
||||
void PostWinMessage ( const _MESSAGE_IDENT MessID,
|
||||
const int iMessageParam,
|
||||
const int iChanNum )
|
||||
{
|
||||
// first check if application is initialized
|
||||
|
|
|
@ -124,6 +124,7 @@ MESSAGES
|
|||
- 0: none, no audio coding applied
|
||||
- 1: IMA-ADPCM
|
||||
- 2: MS-ADPCM
|
||||
- 3: CELT
|
||||
- "audiocod arg": argument for the audio coder, if not used this value shall be set to 0
|
||||
|
||||
|
||||
|
|
|
@ -40,18 +40,17 @@
|
|||
#define PROTMESSID_ACKN 1 // acknowledge
|
||||
#define PROTMESSID_JITT_BUF_SIZE 10 // jitter buffer size
|
||||
#define PROTMESSID_REQ_JITT_BUF_SIZE 11 // request jitter buffer size
|
||||
#define PROTMESSID_PING 12 // OLD, not used anymore
|
||||
#define PROTMESSID_NET_BLSI_FACTOR 13 // network buffer size factor
|
||||
#define PROTMESSID_CHANNEL_GAIN 14 // set channel gain for mix
|
||||
#define PROTMESSID_CONN_CLIENTS_LIST 15 // connected client list
|
||||
#define PROTMESSID_SERVER_FULL 16 // server full message
|
||||
#define PROTMESSID_REQ_CONN_CLIENTS_LIST 17 // request connected client list
|
||||
#define PROTMESSID_CHANNEL_NAME 18 // set channel name for fader tag
|
||||
#define PROTMESSID_CHAT_TEXT 19 // contains a chat text
|
||||
#define PROTMESSID_PING_MS 20 // for measuring ping time
|
||||
#define PROTMESSID_NETW_TRANSPORT_PROPS 21 // properties for network transport
|
||||
#define PROTMESSID_REQ_NETW_TRANSPORT_PROPS 22 // request properties for network transport
|
||||
#define PROTMESSID_DISCONNECTION 23 // disconnection
|
||||
#define PROTMESSID_NET_BLSI_FACTOR 12 // network buffer size factor
|
||||
#define PROTMESSID_CHANNEL_GAIN 13 // set channel gain for mix
|
||||
#define PROTMESSID_CONN_CLIENTS_LIST 14 // connected client list
|
||||
#define PROTMESSID_SERVER_FULL 15 // server full message
|
||||
#define PROTMESSID_REQ_CONN_CLIENTS_LIST 16 // request connected client list
|
||||
#define PROTMESSID_CHANNEL_NAME 17 // set channel name for fader tag
|
||||
#define PROTMESSID_CHAT_TEXT 18 // contains a chat text
|
||||
#define PROTMESSID_PING_MS 19 // for measuring ping time
|
||||
#define PROTMESSID_NETW_TRANSPORT_PROPS 20 // properties for network transport
|
||||
#define PROTMESSID_REQ_NETW_TRANSPORT_PROPS 21 // request properties for network transport
|
||||
#define PROTMESSID_DISCONNECTION 22 // disconnection
|
||||
|
||||
// lengths of message as defined in protocol.cpp file
|
||||
#define MESS_HEADER_LENGTH_BYTE 7 // TAG (2), ID (2), cnt (1), length (2)
|
||||
|
|
Binary file not shown.
BIN
src/res/gig.png
BIN
src/res/gig.png
Binary file not shown.
Before Width: | Height: | Size: 103 KiB After Width: | Height: | Size: 48 KiB |
|
@ -30,10 +30,8 @@ CServer::CServer ( const QString& strLoggingFileName,
|
|||
const quint16 iPortNumber,
|
||||
const QString& strHTMLStatusFileName,
|
||||
const QString& strHistoryFileName,
|
||||
const QString& strServerNameForHTMLStatusFile,
|
||||
const int iNewUploadRateLimitKbps ) :
|
||||
Socket ( &ChannelSet, this, iPortNumber ),
|
||||
ChannelSet ( iNewUploadRateLimitKbps )
|
||||
const QString& strServerNameForHTMLStatusFile ) :
|
||||
Socket ( &ChannelSet, this, iPortNumber )
|
||||
{
|
||||
vecsSendData.Init ( MIN_SERVER_BLOCK_SIZE_SAMPLES );
|
||||
|
||||
|
|
|
@ -46,8 +46,7 @@ public:
|
|||
const quint16 iPortNumber,
|
||||
const QString& strHTMLStatusFileName,
|
||||
const QString& strHistoryFileName,
|
||||
const QString& strServerNameForHTMLStatusFile,
|
||||
const int iNewUploadRateLimitKbps );
|
||||
const QString& strServerNameForHTMLStatusFile );
|
||||
virtual ~CServer() {}
|
||||
|
||||
void Start();
|
||||
|
|
|
@ -37,7 +37,7 @@ class CSoundBase : public QThread
|
|||
|
||||
public:
|
||||
CSoundBase ( const bool bNewIsCallbackAudioInterface,
|
||||
void (*fpNewProcessCallback) ( CVector<short>& psData, void* pParg ),
|
||||
void (*fpNewProcessCallback) ( CVector<int16_t>& psData, void* pParg ),
|
||||
void* pParg ) : fpProcessCallback ( fpNewProcessCallback ),
|
||||
pProcessCallbackArg ( pParg ), bRun ( false ),
|
||||
bIsCallbackAudioInterface ( bNewIsCallbackAudioInterface ) {}
|
||||
|
@ -56,25 +56,25 @@ public:
|
|||
|
||||
protected:
|
||||
// function pointer to callback function
|
||||
void (*fpProcessCallback) ( CVector<short>& psData, void* arg );
|
||||
void (*fpProcessCallback) ( CVector<int16_t>& psData, void* arg );
|
||||
void* pProcessCallbackArg;
|
||||
|
||||
// callback function call for derived classes
|
||||
void ProcessCallback ( CVector<short>& psData )
|
||||
void ProcessCallback ( CVector<int16_t>& psData )
|
||||
{
|
||||
(*fpProcessCallback) ( psData, pProcessCallbackArg );
|
||||
}
|
||||
|
||||
// these functions should be overwritten by derived class for
|
||||
// non callback based audio interfaces
|
||||
virtual bool Read ( CVector<short>& psData ) { printf ( "no sound!" ); return false; }
|
||||
virtual bool Write ( CVector<short>& psData ) { printf ( "no sound!" ); return false; }
|
||||
virtual bool Read ( CVector<int16_t>& psData ) { printf ( "no sound!" ); return false; }
|
||||
virtual bool Write ( CVector<int16_t>& psData ) { printf ( "no sound!" ); return false; }
|
||||
|
||||
void run();
|
||||
bool bRun;
|
||||
bool bIsCallbackAudioInterface;
|
||||
|
||||
CVector<short> vecsAudioSndCrdStereo;
|
||||
CVector<int16_t> vecsAudioSndCrdStereo;
|
||||
|
||||
signals:
|
||||
void ReinitRequest();
|
||||
|
|
27
src/util.cpp
27
src/util.cpp
|
@ -27,10 +27,10 @@
|
|||
|
||||
/* Implementation *************************************************************/
|
||||
// Input level meter implementation --------------------------------------------
|
||||
void CStereoSignalLevelMeter::Update ( CVector<double>& vecdAudio )
|
||||
void CStereoSignalLevelMeter::Update ( CVector<short>& vecsAudio )
|
||||
{
|
||||
// get the stereo vector size
|
||||
const int iStereoVecSize = vecdAudio.Size();
|
||||
const int iStereoVecSize = vecsAudio.Size();
|
||||
|
||||
// Get maximum of current block
|
||||
//
|
||||
|
@ -43,28 +43,28 @@ void CStereoSignalLevelMeter::Update ( CVector<double>& vecdAudio )
|
|||
// special cases but for the average music signals the following code
|
||||
// should give good results.
|
||||
//
|
||||
double dMaxL = 0.0;
|
||||
double dMaxR = 0.0;
|
||||
short sMaxL = 0;
|
||||
short sMaxR = 0;
|
||||
for ( int i = 0; i < iStereoVecSize; i += 6 ) // 2 * 3 = 6 -> stereo
|
||||
{
|
||||
// left channel
|
||||
if ( dMaxL < vecdAudio[i] )
|
||||
if ( sMaxL < vecsAudio[i] )
|
||||
{
|
||||
dMaxL = vecdAudio[i];
|
||||
sMaxL = vecsAudio[i];
|
||||
}
|
||||
|
||||
// right channel
|
||||
if ( dMaxR < vecdAudio[i + 1] )
|
||||
if ( sMaxR < vecsAudio[i + 1] )
|
||||
{
|
||||
dMaxR = vecdAudio[i + 1];
|
||||
sMaxR = vecsAudio[i + 1];
|
||||
}
|
||||
}
|
||||
|
||||
dCurLevelL = UpdateCurLevel ( dCurLevelL, dMaxL );
|
||||
dCurLevelR = UpdateCurLevel ( dCurLevelR, dMaxR );
|
||||
dCurLevelL = UpdateCurLevel ( dCurLevelL, sMaxL );
|
||||
dCurLevelR = UpdateCurLevel ( dCurLevelR, sMaxR );
|
||||
}
|
||||
|
||||
double CStereoSignalLevelMeter::UpdateCurLevel ( double dCurLevel, const double& dMax )
|
||||
double CStereoSignalLevelMeter::UpdateCurLevel ( double dCurLevel, const short& sMax )
|
||||
{
|
||||
// decrease max with time
|
||||
if ( dCurLevel >= METER_FLY_BACK )
|
||||
|
@ -78,9 +78,9 @@ double CStereoSignalLevelMeter::UpdateCurLevel ( double dCurLevel, const double&
|
|||
}
|
||||
|
||||
// update current level -> only use maximum
|
||||
if ( dMax > dCurLevel )
|
||||
if ( static_cast<double> ( sMax ) > dCurLevel )
|
||||
{
|
||||
return dMax;
|
||||
return static_cast<double> ( sMax );
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -331,6 +331,7 @@ CAboutDlg::CAboutDlg ( QWidget* parent ) : QDialog ( parent )
|
|||
"</b></p>"
|
||||
"<ul>"
|
||||
"<li>Qt cross-platform application framework: <i>http://trolltech.com</li>"
|
||||
"<li>The CELT ultra-low delay audio codec: <i>http://www.celt-codec.org</li>"
|
||||
"<li>Audio reverberation code: by Perry R. Cook and Gary P. Scavone, "
|
||||
"1995 - 2004 (taken from <i>The Synthesis ToolKit in C++ (STK)</i>)</li>"
|
||||
"<li>ADPCM coders by Erik de Castro Lopo</li>"
|
||||
|
|
19
src/util.h
19
src/util.h
|
@ -363,14 +363,14 @@ public:
|
|||
CStereoSignalLevelMeter() { Reset(); }
|
||||
virtual ~CStereoSignalLevelMeter() {}
|
||||
|
||||
void Update ( CVector<double>& vecdAudio );
|
||||
void Update ( CVector<short>& vecsAudio );
|
||||
double MicLevelLeft() { return CalcLogResult ( dCurLevelL ); }
|
||||
double MicLevelRight() { return CalcLogResult ( dCurLevelR ); }
|
||||
void Reset() { dCurLevelL = 0.0; dCurLevelR = 0.0; }
|
||||
|
||||
protected:
|
||||
double CalcLogResult ( const double& dLinearLevel );
|
||||
double UpdateCurLevel ( double dCurLevel, const double& dMax );
|
||||
double UpdateCurLevel ( double dCurLevel, const short& sMax );
|
||||
|
||||
double dCurLevelL;
|
||||
double dCurLevelR;
|
||||
|
@ -417,7 +417,8 @@ enum EAudComprType
|
|||
{
|
||||
CT_NONE = 0,
|
||||
CT_IMAADPCM = 1,
|
||||
CT_MSADPCM = 2
|
||||
CT_MSADPCM = 2,
|
||||
CT_CELT = 3
|
||||
};
|
||||
|
||||
class CNetworkTransportProps
|
||||
|
@ -448,17 +449,15 @@ public:
|
|||
// we use a conservative value as default, this value does not
|
||||
// give perfekt latency results but should work ok on most
|
||||
// sound cards and drivers
|
||||
static int GetDefaultIndex() { return 5; }
|
||||
static int GetDefaultIndex() { return 1; }
|
||||
|
||||
static int GetNumOfBufferSizes() { return 16; }
|
||||
static int GetNumOfBufferSizes() { return 4; }
|
||||
static int GetBufferSizeFromIndex ( const int iIdx )
|
||||
{
|
||||
if ( ( iIdx >= 0 ) && ( iIdx < 16 ) )
|
||||
if ( ( iIdx >= 0 ) && ( iIdx < 4 ) )
|
||||
{
|
||||
const int pSizes[16] = {
|
||||
96, 128, 160, 192, 224, 256, 288, 320, 352,
|
||||
384, 416, 448, 480, 512, 768, 1024 };
|
||||
|
||||
const int pSizes[4] = { 128, 256, 512, 1024 };
|
||||
|
||||
return pSizes[iIdx];
|
||||
}
|
||||
else
|
||||
|
|
|
@ -48,8 +48,8 @@
|
|||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="0"
|
||||
AdditionalIncludeDirectories=""$(QTDIR)\include";"$(QTDIR)\include\Qt";../src;ASIOSDK2/common;ASIOSDK2/host;ASIOSDK2/host/pc"
|
||||
PreprocessorDefinitions="WIN32;_DEBUG;_WINDOWS;QT_DLL;QT_THREAD_SUPPORT"
|
||||
AdditionalIncludeDirectories=""$(QTDIR)\include";"$(QTDIR)\include\Qt";../src;ASIOSDK2/common;ASIOSDK2/host;ASIOSDK2/host/pc;../libs/celt/libcelt"
|
||||
PreprocessorDefinitions="WIN32;_DEBUG;_WINDOWS;QT_DLL;QT_THREAD_SUPPORT;USE_ALLOCA"
|
||||
MinimalRebuild="true"
|
||||
BasicRuntimeChecks="3"
|
||||
RuntimeLibrary="3"
|
||||
|
@ -146,8 +146,8 @@
|
|||
Name="VCCLCompilerTool"
|
||||
Optimization="2"
|
||||
InlineFunctionExpansion="1"
|
||||
AdditionalIncludeDirectories=""$(QTDIR)\include";"$(QTDIR)\include\Qt";../src;ASIOSDK2/common;ASIOSDK2/host;ASIOSDK2/host/pc"
|
||||
PreprocessorDefinitions="WIN32;NDEBUG;_WINDOWS;QT_DLL;QT_THREAD_SUPPORT"
|
||||
AdditionalIncludeDirectories=""$(QTDIR)\include";"$(QTDIR)\include\Qt";../src;ASIOSDK2/common;ASIOSDK2/host;ASIOSDK2/host/pc;../libs/celt/libcelt"
|
||||
PreprocessorDefinitions="WIN32;NDEBUG;_WINDOWS;QT_DLL;QT_THREAD_SUPPORT;USE_ALLOCA"
|
||||
StringPooling="true"
|
||||
RuntimeLibrary="2"
|
||||
EnableFunctionLevelLinking="true"
|
||||
|
@ -465,28 +465,6 @@
|
|||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\resample.cpp"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Debug|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
AdditionalIncludeDirectories=""
|
||||
PreprocessorDefinitions=""
|
||||
/>
|
||||
</FileConfiguration>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
AdditionalIncludeDirectories=""
|
||||
PreprocessorDefinitions=""
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\server.cpp"
|
||||
>
|
||||
|
@ -945,6 +923,250 @@
|
|||
</FileConfiguration>
|
||||
</File>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="CELT"
|
||||
>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\bands.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\celt.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\cwrs.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\entcode.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\entdec.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\entenc.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\header.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\kfft_single.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\kiss_fft.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\kiss_fftr.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\laplace.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\mdct.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\modes.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\pitch.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\psy.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\quant_bands.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\rangedec.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\rangeenc.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\rate.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\libs\celt\libcelt\vq.c"
|
||||
>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32"
|
||||
>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
CompileAs="1"
|
||||
/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
</Filter>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="Header Files"
|
||||
|
@ -1002,14 +1224,6 @@
|
|||
RelativePath="..\src\protocol.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\resample.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\resamplefilter.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\src\server.h"
|
||||
>
|
||||
|
|
|
@ -188,7 +188,7 @@ std::string CSound::CheckDeviceCapabilities()
|
|||
// message is returned.
|
||||
|
||||
// check the sample rate
|
||||
const ASIOError CanSaRateReturn = ASIOCanSampleRate ( SND_CRD_SAMPLE_RATE );
|
||||
const ASIOError CanSaRateReturn = ASIOCanSampleRate ( SYSTEM_SAMPLE_RATE );
|
||||
if ( ( CanSaRateReturn == ASE_NoClock ) ||
|
||||
( CanSaRateReturn == ASE_NotPresent ) )
|
||||
{
|
||||
|
@ -327,7 +327,7 @@ int CSound::Init ( const int iNewPrefMonoBufferSize )
|
|||
iASIOBufferSizeStereo = 2 * iASIOBufferSizeMono;
|
||||
|
||||
// set the sample rate
|
||||
ASIOSetSampleRate ( SND_CRD_SAMPLE_RATE );
|
||||
ASIOSetSampleRate ( SYSTEM_SAMPLE_RATE );
|
||||
|
||||
// create memory for intermediate audio buffer
|
||||
vecsTmpAudioSndCrdStereo.Init ( iASIOBufferSizeStereo );
|
||||
|
|
|
@ -55,7 +55,7 @@
|
|||
class CSound : public CSoundBase
|
||||
{
|
||||
public:
|
||||
CSound ( void (*fpNewCallback) ( CVector<short>& psData, void* arg ), void* arg );
|
||||
CSound ( void (*fpNewCallback) ( CVector<int16_t>& psData, void* arg ), void* arg );
|
||||
virtual ~CSound();
|
||||
|
||||
virtual int Init ( const int iNewPrefMonoBufferSize );
|
||||
|
@ -87,7 +87,7 @@ protected:
|
|||
|
||||
// callbacks
|
||||
static void bufferSwitch ( long index, ASIOBool processNow );
|
||||
static ASIOTime* bufferSwitchTimeInfo ( ASIOTime *timeInfo, long index, ASIOBool processNow );
|
||||
static ASIOTime* bufferSwitchTimeInfo ( ASIOTime* timeInfo, long index, ASIOBool processNow );
|
||||
static void sampleRateChanged ( ASIOSampleRate sRate ) {}
|
||||
static long asioMessages ( long selector, long value, void* message, double* opt );
|
||||
|
||||
|
|
Loading…
Reference in a new issue