how to get usable data between -1 and 1 from QAudioBuffer? Qt6
-
Hi all,
I would like to know how to efficiently extract data from a QAudioBuffer object. I have a wav audio file that I am decoding with a QAudioDecoder object. I want to extract the results of the decoding contained in the QAudioBuffer object to apply filtering operations on it and finally send the filtered data to a subclass of QIODevice to listen to the result in real time.At first, I just do a test to make sure that the extraction works well. To do this, I save the data contained in the QAudioBuffer object in a txt file. But I encounter 2 problems.
- the resulting TXT file contains only characters, no numbers.
- With MATLAB, when I plot the signal represented by the data contained in the TXT file, I get the shape of the original audio signal (the one in the WAV file) but the amplitudes are too big and should be between -1 and 1.
Can you please tell me how to extract the data so that I get a result on which I can apply a filter and how to have data between -1 and 1?
Iuse Qt6.4
thanks in advance
My code
QAudioFormat *format_decoder; format_decoder = new QAudioFormat; format_decoder->setSampleRate(44100); format_decoder->setChannelCount(1); format_decoder->setSampleFormat(QAudioFormat::Int16); QAudioDecoder decoder; decoder.setSource(filenameSource); decoder.setAudioFormat(*format_decoder); decoder.start(); QObject::connect(&decoder, &QAudioDecoder::bufferReady, this, &MainWindow::test_copy_to_txt);
and the slot
void MainWindow::test_copy_to_txt() { QAudioBuffer audioBuffer = decoder.read(); const qint16* samples = audioBuffer.constData<qint16>(); // Signal shape ok, but not the amplitudes QFile outputFile(filenameTest1); if(!outputFile.open(QIODevice::WriteOnly|QIODevice::Append)){ qDebug() << "ERROR";} QTextStream out(&outputFile); for (int i = 0; i < audioBuffer.sampleCount(); ++i) { out << samples[i] << "\n"; // only characters, no numbers. } outputFile.close(); }
-
I don't know much about audio processing, but if your data format is qint16 I would expect to get data in the range of that type, so if you want it normalized to range -1..1 you'd have to divide each sample by the max value of that type, which is
std::numeric_limits<qint16>::max()
. Make sure to convert it to a floating point first, or you'll get a 0 from integer division. -
Thank you for your answers. I followed your recommendations and everything is ok now.
Here is the corrected codeout << static_cast< float >(samples[i]) / std::numeric_limits<qint16>::max() << "\r\n";