2

我的程序正在循环读取配置文件行,并为 time = lines*100ms 进行录音。但是对于 5 个相同的配置文件,我得到 5 个不同的长度。(对于 5sek 录音 +-100ms)

我试图改变 QThread::msleep(1500); 或在循环外声明 QEventLoop 和 QTimer,但没有任何变化。

我怎样才能得到正确时间的录音?

音频.cpp

// ************************************************************************************************
// Audio-Class
// ************************************************************************************************

#include "Audio.h"
#include "Measure.h"
#include <QAudioInput>
#include <QTimer>

// ************************************************************************************************

Audio::Audio()
{
    QTimer *m_timer = new QTimer(this);
    m_timer->setSingleShot(true);
    AudioRecord();
}

// ************************************************************************************************
//Initialization and signal-slot connection

void Audio::AudioRecord()
{
    //Set audio configuration
    QAudioFormat format;
    format.setSampleRate(44100);
    format.setChannelCount(1);
    format.setSampleSize(16);
    format.setCodec("audio/PCM");
    format.setByteOrder(QAudioFormat::LittleEndian);
    format.setSampleType(QAudioFormat::SignedInt);


    //Wrong configuration detection
    QAudioDeviceInfo info = QAudioDeviceInfo::defaultInputDevice();
    if (!info.isFormatSupported(format))
    {
        qWarning() << "Default format not supported";
        format = info.nearestFormat(format);
    }

    //Signal-slot connection to show actual Audio state or errors output
    m_audio = new QAudioInput(format, this);
    connect(m_audio, SIGNAL(stateChanged(QAudio::State)), this, SLOT(handleStateChanged(QAudio::State)));
}

// ************************************************************************************************
//Start recording

//void Audio::StartRecording(QString rec_file_path)
void Audio::StartRecording(QString rec_file_path, quint32 record_time_msec)
{
    m_file.setFileName(rec_file_path); //audio recording path format
    m_file.open(QIODevice::WriteOnly); //audio access mode initialisation

    writeHeader(); //writing header to convert PCM to *.wav (Step 1)

    m_audio->start(&m_file); //start recording

    //QTimer::singleShot((15000), this, SLOT(StopRecording()));
    QTimer::singleShot((record_time_msec), this, SLOT(StopRecording()));
    QCoreApplication::processEvents();


    qDebug()<< m_audio->format();
    //qDebug()<< m_file.open();
    QAudioDeviceInfo::defaultInputDevice();
    QAudioDeviceInfo::availableDevices(QAudio::AudioInput);
    //qDebug()<< m_audio->error();
    //qDebug()<< m_audio->notifyInterval();
}


// ************************************************************************************************
//Write Header
// ************************************************************************************************

void Audio::writeHeader(){

    quint64 data64 = 0;
    quint32 data_Filesize_fill = 0;
    quint32 data_lenght = 16;
    quint16 data_PCM = 1;
    quint16 data_Chanel = 1;
    quint32 data_SamplRate = 44100;
    quint32 data_Value = (44100 * 16 * 1)/8;
    quint16 data_mono = (16 * 1)/8;
    quint16 data_BPS = 16;
    quint32 data_FileSize = 44;



    m_file.write("RIFF",4);
    m_file.write((char*)&data_Filesize_fill, 4);
    m_file.write("WAVE",4);
    m_file.write("fmt ",4);                     // "fmt " chunk size (always 16 for PCM)
    m_file.write((char*)&data_lenght, 4);
    m_file.write((char*)&data_PCM, 2);
    m_file.write((char*)&data_Chanel, 2);
    m_file.write((char*)&data_SamplRate, 4);
    m_file.write((char*)&data_Value, 4);        // bytes per second
    m_file.write((char*)&data_mono, 2);         // Block align
    m_file.write((char*)&data_BPS, 2);          // Bits per sample
    m_file.write("data",4);
    m_file.write((char*)&data_FileSize, 4);

    m_file.flush();
}

// ************************************************************************************************
//Stop recording

void Audio::StopRecording()
{
    m_audio->stop();
    qDebug() << "stop";
    writeHeaderFinal();
    m_file.close();
    qDebug() << "close";
}

// ************************************************************************************************
//Write Header
void Audio::writeHeaderFinal(){

    quint32 data_Filesize_fill_after = m_file.size() - 8;
    quint32 data_FileSize_after = m_file.size() - 44;
    m_file.seek(4);
    m_file.write((char*)&data_Filesize_fill_after, 4);
    m_file.seek(40);
    m_file.write((char*)&data_FileSize_after, 4);
}
// ************************************************************************************************
//Recording DEBUG output

void Audio::handleStateChanged(QAudio::State newState)
{
    switch (newState)
    {
        case QAudio::StoppedState:
            if (m_audio->error() != QAudio::NoError)
            {
                qDebug() << "Error audio recording!!";
            } else
            {
                qDebug() << "Finished audio recording";
            }
            break;

        case QAudio::ActiveState:
            qDebug() << "Started audio recording";
            break;

        default:

            break;
    }
}

// ************************************************************************************************

测量.cpp

// ************************************************************************************************
// Measure-Class
// ************************************************************************************************

//class initialisation

#include "Measure.h"
#include "Conf.h"
#include "Audio.h"

// ************************************************************************************************
Measure::Measure(Audio *audio)
{
    //member variables init
    m_audio = audio;

    //UART-status debug
    if (0 == connectSerial())
    {
        qDebug() << "Serial connection OK!\n";
    }
    else
    {
        qDebug() << "Serial connection Error!\n";
        return;
    }

    auto info = QAudioDeviceInfo::availableDevices(QAudio::AudioInput);
    foreach (auto i, info) qDebug() << i.deviceName();

    //m_timer = new QTimer(this); double

    //set serial connection
    //connect(m_timer, SIGNAL(timeout()), this, SLOT(processMeas()),Qt::QueuedConnection);

    measure_cnt = 0;

    qDebug()<<"Starting programm";

}

// ************************************************************************************************
// Start measure

void Measure::start()
{
    //QTimer *m_timer = new QTimer(this);
    //m_timer->setSingleShot(true);
    //m_timer->start(1000); 555
    processMeas();
}

// ************************************************************************************************
// Serial connection initialization and signal-slot connection

uint32_t Measure::connectSerial(void)
{

    //serial connection configuration
    m_serial.setPortName("/dev/ttyACM0");
    m_serial.setBaudRate(QSerialPort::Baud115200);
    m_serial.setDataBits(QSerialPort::Data8);
    m_serial.setParity(QSerialPort::NoParity);
    m_serial.setStopBits(QSerialPort::OneStop);
    m_serial.setFlowControl(QSerialPort::NoFlowControl);

    if (!m_serial.open(QIODevice::ReadWrite))
        return 1;

    //einable serial connection
    connect(&m_serial, SIGNAL(readyRead()), this, SLOT(readRequest()));

    return 0;
}

// ************************************************************************************************
// State maschine
// ************************************************************************************************

void Measure::processMeas()
{

    // Declaration ************************************************************
    static uint32_t i = 0;
    static uint32_t j = 0;

    static uint8_t stm = 0;

    static uint16_t m1 = 0;
    static uint16_t m2 = 0;
    static uint16_t m3 = 0;
    static uint16_t m4 = 0;
    static uint16_t var;

    static QByteArray hextest;

    // Read config files ***********************************************************************************
    QDir directory("/home/nikitajarocky/workspace/QT/Software_2.0_QT/Config_files/");
    QStringList config_files = directory.entryList(QStringList() << "*.config", QDir::Files);
    config_files_cnt = config_files.count();

    foreach(QString filename, config_files)
    {
        Conf *conf = new Conf(directory.absoluteFilePath(filename));
        qDebug() << "Config file: " << filename << " is processed";

        // Error message *************************
        if(conf->getConf_lines().size() == 0)
        {
            qDebug()<<"Error conf file!!";
            return;
        }

    // Prepare measure ****************************************************************
        qDebug()<<"Debug: Prepare measure";

        QStringList lines = conf->getConf_lines(); //read all rows of config files

        record_time_100ms = lines.count()-9; // lines Audio config data + end lines
        record_time_msec = record_time_100ms * 100; //msec conversion

        for(i=0; i < (uint32_t)lines.length(); i++) //prepare single rows of config files
        {

            //uint32_t j = 0;
            QString uart;
            QString uart_hex;

            if(i > 5 && i < lines.length())
            {
            QStringList speed_chunks = lines.at(i).split(","); //split rows by decimal point

            m1 = speed_chunks.at(2).toInt();
            m2 = speed_chunks.at(3).toInt();
            m3 = speed_chunks.at(4).toInt();
            m4 = speed_chunks.at(5).toInt();

            hextest.resize(10);
            hextest[0]=255;
            hextest[1]=m1>>8;
            hextest[2]=m1;
            hextest[3]=m2>>8;
            hextest[4]=m2;
            hextest[5]=m3>>8;
            hextest[6]=m3;
            hextest[7]=m4>>8;
            hextest[8]=m4;
            hextest[9]=238;

            qDebug()<< "Transfer data: " << i-8 << " from " << lines.count()-9 << " rows transmitted";
            qDebug() << "Config file: " << filename << " is processed";

            m_serial.write(hextest);
            m_serial.waitForBytesWritten(1000);
            QThread::usleep(50000);

            }//if(lines.at(i).contains(",")) end }//for end
        }//for end

            //Beep


            // Measurement ******************************************************************
            qDebug()<<"Debug: Measurement in progress";
            QEventLoop event_loop(this);                      //create method class QEventLoop
            QTimer exit_timer(this);                                //create method class QTimer

            exit_timer.setSingleShot(true);                     //set timer in mode singleShot
            connect(&exit_timer, SIGNAL(timeout()), &event_loop, SLOT(quit())); //connect exit timer to event loop slot
            QThread::msleep(1500);
            QString path = SAVE_AUDIO_PATH+filename.left( filename.lastIndexOf( '.' ) )+"_"+QDateTime::currentDateTime().toString("yyyyMMdd_hhmmss");
            //QThread::msleep(1500);
            m_file.setFileName(path+".log");
            //m_audio->StartRecording(path+".wav");
            m_audio->StartRecording(path+".wav", record_time_msec);//+0.6
            //exit_timer.start(15000);
            exit_timer.start(record_time_msec);//event loop timer durring measure time
            event_loop.exec();

            qDebug()<<"Measurement takes " << record_time_msec << " seconds";

            // Stop measure ************************************
            QThread::msleep(2000);
            stm=0;
            record_time_msec = 0;
            measure_cnt++;

            // All configs files done *********************************

            if(measure_cnt>=config_files_cnt)
            {
                qDebug()<<"All measure done";
                qApp->quit();
            }

    }//foreach



}//processMeas()

// ************************************************************************************************
// Data from STM32 receive

void Measure::readRequest()
{
    m_file.open(QIODevice::WriteOnly | QIODevice::Append);
    m_file.write(m_serial.readAll());
    m_file.close();
}

// ************************************************************************************************
// save received data to log File

void Measure::saveFile(QByteArray buffer)
{
     m_file.write(buffer);
}

录音总是有点长,所以它不是随机错误: 在此处输入图像描述

图片上有 4 个相同的配置文件,两次


编辑:我将代码更改为:

m_audio->StartRecording(path+".wav", record_time_msec+5000);
exit_timer.start(record_time_msec+5000);//event loop timer  
event_loop.exec();

得到: 修改后的代码结果

但是我怎样才能延迟开始测量呢?(我想跳过开始声音(蜂鸣器))?

4

0 回答 0