kopia lustrzana https://gitlab.com/eliggett/wfview
Added signal/slot communication for audio format. The rx audio handler
will now send to the tx audio handler information about the speaker output hardware on the host. The tx handler is now smart enough to check if the format needs conversion or not.monitor
rodzic
4fdcc4bf26
commit
7dfac11315
|
@ -182,6 +182,13 @@ bool audioHandler::init(audioSetup setup)
|
|||
return true;
|
||||
}
|
||||
|
||||
void audioHandler::acceptMonitorAudioFormat(QAudioFormat mformat)
|
||||
{
|
||||
// TODO
|
||||
qDebug(logAudio()) << "Error, this should not have been called: " << __PRETTY_FUNCTION__;
|
||||
(void)mformat;
|
||||
}
|
||||
|
||||
void audioHandler::start()
|
||||
{
|
||||
qInfo(logAudio()) << (setup.isinput ? "Input" : "Output") << "start() running";
|
||||
|
|
|
@ -64,6 +64,7 @@ public slots:
|
|||
virtual void incomingAudio(const audioPacket data);
|
||||
virtual void convertedInput(audioPacket audio);
|
||||
virtual void convertedOutput(audioPacket audio);
|
||||
virtual void acceptMonitorAudioFormat(QAudioFormat mformat);
|
||||
|
||||
private slots:
|
||||
virtual void stateChanged(QAudio::State state);
|
||||
|
@ -77,6 +78,7 @@ signals:
|
|||
void haveLevels(quint16 amplitudePeak, quint16 amplitudeRMS, quint16 latency,quint16 current,bool under,bool over);
|
||||
void setupConverter(QAudioFormat in, QAudioFormat out, quint8 opus, quint8 resamp);
|
||||
void sendToConverter(audioPacket audio);
|
||||
void haveAudioFormat(QAudioFormat format);
|
||||
|
||||
|
||||
private:
|
||||
|
|
|
@ -41,6 +41,27 @@ void paHandler::setSharedAudioData(sharedAudioType *m)
|
|||
this->monitorFormat = m->monitorFormat;
|
||||
}
|
||||
|
||||
void paHandler::acceptMonitorAudioFormat(QAudioFormat mformat)
|
||||
{
|
||||
qDebug(logAudio()) << "Monitor audio format received into tx audio handler.";
|
||||
this->monitorFormat = mformat;
|
||||
this->sharedAudioInfo->monitorFormat = mformat;
|
||||
emit setupMonitorStreamConverter(outFormat, monitorFormat, 7, setup.resampleQuality);
|
||||
connect(converterToMonitor, SIGNAL(converted(audioPacket)), this, SLOT(convertedMonitorAudio(audioPacket)));
|
||||
if(checkFormatsSame(&outFormat, &monitorFormat))
|
||||
{
|
||||
convertMonitorFormat = false;
|
||||
} else {
|
||||
convertMonitorFormat = true;
|
||||
qDebug(logAudio()) << "outFormat: " << outFormat;
|
||||
qDebug(logAudio()) << "monitorFormat: " << monitorFormat;
|
||||
}
|
||||
qInfo(logAudio()) << "Conversion for monitor audio: " << convertMonitorFormat;
|
||||
|
||||
haveMonitorInformation = true;
|
||||
|
||||
}
|
||||
|
||||
bool paHandler::init(audioSetup setup)
|
||||
{
|
||||
if (isInitialized) {
|
||||
|
@ -210,17 +231,16 @@ bool paHandler::init(audioSetup setup)
|
|||
}
|
||||
}
|
||||
|
||||
if (setup.isinput) {
|
||||
|
||||
err = Pa_OpenStream(&audio, &aParams, 0, outFormat.sampleRate(), this->chunkSize, paNoFlag, &paHandler::staticWrite, (void*)this);
|
||||
emit setupConverter(outFormat, inFormat, 7, setup.resampleQuality);
|
||||
emit setupMonitorStreamConverter(outFormat, outFormat, 7, setup.resampleQuality);
|
||||
connect(converterToMonitor, SIGNAL(converted(audioPacket)), this, SLOT(convertedMonitorAudio(audioPacket)));
|
||||
connect(converter, SIGNAL(converted(audioPacket)), this, SLOT(convertedInput(audioPacket)));
|
||||
}
|
||||
else {
|
||||
if (setup.isinput) {
|
||||
err = Pa_OpenStream(&audio, &aParams, 0, outFormat.sampleRate(), this->chunkSize, paNoFlag, &paHandler::staticWrite, (void*)this);
|
||||
emit setupConverter(outFormat, inFormat, 7, setup.resampleQuality);
|
||||
//emit setupMonitorStreamConverter(outFormat, monitorFormat, 7, setup.resampleQuality);
|
||||
connect(converter, SIGNAL(converted(audioPacket)), this, SLOT(convertedInput(audioPacket)));
|
||||
}
|
||||
else {
|
||||
err = Pa_OpenStream(&audio, 0, &aParams, outFormat.sampleRate(), this->chunkSize, paNoFlag, NULL, NULL);
|
||||
emit setupConverter(inFormat, outFormat, 7, setup.resampleQuality);
|
||||
emit haveAudioFormat(outFormat);
|
||||
connect(converter, SIGNAL(converted(audioPacket)), this, SLOT(convertedOutput(audioPacket)));
|
||||
}
|
||||
|
||||
|
@ -263,17 +283,21 @@ void paHandler::incomingAudio(audioPacket packet)
|
|||
// (not currently working)
|
||||
//convertedOutput(packet);
|
||||
|
||||
// Convert: (if needed)
|
||||
//emit sendToMonitorConverter(packet);
|
||||
|
||||
// if the formats are actually the same, no need to convert:
|
||||
convertedMonitorAudio(packet);
|
||||
if(haveMonitorInformation)
|
||||
{
|
||||
if(convertMonitorFormat)
|
||||
{
|
||||
// Convert format: (if needed)
|
||||
emit sendToMonitorConverter(packet);
|
||||
} else {
|
||||
// if the formats are actually the same, no need to convert:
|
||||
convertedMonitorAudio(packet);
|
||||
}
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
|
||||
int paHandler::writeData(const void* inputBuffer, void* outputBuffer,
|
||||
unsigned long nFrames, const PaStreamCallbackTimeInfo * streamTime,
|
||||
PaStreamCallbackFlags status)
|
||||
|
@ -313,12 +337,12 @@ void paHandler::mixAudio(QByteArray *dest, unsigned char *monitorSource)
|
|||
int size = dest->size();
|
||||
float* mon = reinterpret_cast<float*>(monitorSource);
|
||||
float* dst = reinterpret_cast<float*>(dest->data());
|
||||
//32 bits per float sample means the size is divide by four.
|
||||
// 32 bits per float sample means the size is divide by four.
|
||||
int floatSize = size / 4;
|
||||
|
||||
for(int s=0; s < floatSize; s++)
|
||||
{
|
||||
dst[s] = dst[s] + mon[s];
|
||||
dst[s] = dst[s] + sharedAudioInfo->monitorVolume*mon[s];
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -416,7 +440,6 @@ void paHandler::convertedMonitorAudio(audioPacket audio)
|
|||
|
||||
}
|
||||
|
||||
|
||||
void paHandler::convertedInput(audioPacket packet)
|
||||
{
|
||||
if (packet.data.size() > 0) {
|
||||
|
@ -428,7 +451,17 @@ void paHandler::convertedInput(audioPacket packet)
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
bool paHandler::checkFormatsSame(QAudioFormat *a, QAudioFormat *b)
|
||||
{
|
||||
bool same = true;
|
||||
same = same && (a->codec() == b->codec());
|
||||
same = same && (a->sampleRate() == b->sampleRate());
|
||||
same = same && (a->byteOrder() == b->byteOrder());
|
||||
same = same && (a->channelCount() == b->channelCount());
|
||||
same = same && (a->sampleSize() == b->sampleSize());
|
||||
same = same && (a->sampleType() == b->sampleType());
|
||||
return same;
|
||||
}
|
||||
|
||||
void paHandler::changeLatency(const quint16 newSize)
|
||||
{
|
||||
|
|
|
@ -50,6 +50,7 @@ public slots:
|
|||
void convertedOutput(audioPacket audio);
|
||||
void convertedMonitorAudio(audioPacket audio);
|
||||
void incomingAudio(const audioPacket data);
|
||||
void acceptMonitorAudioFormat(QAudioFormat mformat);
|
||||
|
||||
|
||||
private slots:
|
||||
|
@ -63,6 +64,7 @@ signals:
|
|||
void setupMonitorStreamConverter(QAudioFormat in, QAudioFormat out, quint8 opus, quint8 resamp);
|
||||
void sendToConverter(audioPacket audio);
|
||||
void sendToMonitorConverter(audioPacket audio);
|
||||
void haveAudioFormat(QAudioFormat format);
|
||||
|
||||
|
||||
private:
|
||||
|
@ -76,8 +78,10 @@ private:
|
|||
}
|
||||
|
||||
void mixAudio(QByteArray *dest, unsigned char *monitorSource);
|
||||
|
||||
bool isInitialized = false;
|
||||
bool checkFormatsSame(QAudioFormat *a, QAudioFormat *b);
|
||||
bool convertMonitorFormat = true;
|
||||
bool haveMonitorInformation = false;
|
||||
bool isInitialized = false;
|
||||
PaStream* audio = Q_NULLPTR;
|
||||
PaStreamParameters aParams;
|
||||
const PaDeviceInfo* info;
|
||||
|
|
|
@ -250,6 +250,11 @@ errorHandler:
|
|||
|
||||
}
|
||||
|
||||
void rtHandler::acceptMonitorAudioFormat(QAudioFormat mformat)
|
||||
{
|
||||
// TODO
|
||||
(void)mformat;
|
||||
}
|
||||
|
||||
void rtHandler::setVolume(unsigned char volume)
|
||||
{
|
||||
|
|
|
@ -54,7 +54,7 @@ public slots:
|
|||
void convertedInput(audioPacket audio);
|
||||
void convertedOutput(audioPacket audio);
|
||||
void incomingAudio(const audioPacket data);
|
||||
|
||||
void acceptMonitorAudioFormat(QAudioFormat mformat);
|
||||
|
||||
private slots:
|
||||
|
||||
|
|
|
@ -23,8 +23,11 @@ udpAudio::udpAudio(QHostAddress local, QHostAddress ip, quint16 audioPort, quint
|
|||
monitorAudio.testNumber = 17; // TODO remove
|
||||
monitorAudio.monitorVolume = 0.5;
|
||||
monitorAudio.monitorFeatureOn = true;
|
||||
monitorAudio.hostSetup = rxSetup;
|
||||
monitorAudio.monitorFormat = toQAudioFormat(rxSetup.codec, rxSetup.sampleRate);
|
||||
|
||||
// TODO: This is not the right format to copy, this is the radio's format, not
|
||||
// the host audio format (speaker).
|
||||
//monitorAudio.hostSetup = rxSetup;
|
||||
//monitorAudio.monitorFormat = toQAudioFormat(rxSetup.codec, rxSetup.sampleRate);
|
||||
startAudio();
|
||||
|
||||
watchdogTimer = new QTimer();
|
||||
|
@ -303,6 +306,7 @@ void udpAudio::startAudio() {
|
|||
connect(txaudio, SIGNAL(haveLevels(quint16, quint16, quint16, quint16, bool, bool)), this, SLOT(getTxLevels(quint16, quint16, quint16, quint16, bool, bool)));
|
||||
|
||||
connect(txAudioThread, SIGNAL(finished()), txaudio, SLOT(deleteLater()));
|
||||
connect(rxaudio, SIGNAL(haveAudioFormat(QAudioFormat)), txaudio, SLOT(acceptMonitorAudioFormat(QAudioFormat)));
|
||||
emit setupTxAudio(txSetup);
|
||||
}
|
||||
|
||||
|
|
Ładowanie…
Reference in New Issue