Qt--使用RtAudio进行录音以及播放

其实,本篇博客主要是介绍一下RtAudio,只是在qt中使用罢了!

什么是RtAudio?
RtAudio provides a common API for realtime audio input/output across Linux (native ALSA, Jack, and OSS), Macintosh OS X (CoreAudio and Jack), and Windows(DirectSound, ASIO and WASAPI) operating systems.

官方地址:
http://www.music.mcgill.ca/~gary/rtaudio/

github地址:
https://github.com/thestk/rtaudio

下载rtaudio:
最新版本 (22 February 2016): Version 4.1.2

官方文档应用例子:

#include "RtAudio.h"
#include 
#include 
#include 
int record( void *outputBuffer, void *inputBuffer, unsigned int nBufferFrames,
         double streamTime, RtAudioStreamStatus status, void *userData )
{
  if ( status )
    std::cout << "Stream overflow detected!" << std::endl;
  // Do something with the data in the "inputBuffer" buffer.
  return 0;
}
int main()
{
  RtAudio adc;
  if ( adc.getDeviceCount() < 1 ) {
    std::cout << "\nNo audio devices found!\n";
    exit( 0 );
  }
  RtAudio::StreamParameters parameters;
  parameters.deviceId = adc.getDefaultInputDevice();
  parameters.nChannels = 2;
  parameters.firstChannel = 0;
  unsigned int sampleRate = 44100;
  unsigned int bufferFrames = 256; // 256 sample frames
  try {
    adc.openStream( NULL, ¶meters, RTAUDIO_SINT16,
                    sampleRate, &bufferFrames, &record );
    adc.startStream();
  }
  catch ( RtAudioError& e ) {
    e.printMessage();
    exit( 0 );
  }

  char input;
  std::cout << "\nRecording ... press  to quit.\n";
  std::cin.get( input );
  try {
    // Stop the stream
    adc.stopStream();
  }
  catch (RtAudioError& e) {
    e.printMessage();
  }
  if ( adc.isStreamOpen() ) adc.closeStream();
  return 0;
}

Qt中的应用

功能:
1左声道
2右声道
3双声道

封装一个类,叫ThreadRecord,在多线程中使用RrAudio,当然是继承QThread:

class ThreadRecord :public QThread
{
public:
    ThreadRecord();
    static int record(void *outputBuffer, void *inputBuffer, unsigned int nBufferFrames, double streamTime, RtAudioStreamStatus status, void *userData);
    bool flag;
    int type;//通过type进行判断是使用左声道、右声道、双声道

protected:
    void run();
private:
    RtAudio adc;
    RtAudio::StreamParameters input;
    RtAudio::StreamParameters output;
};

实现threadrecord.cc:

int ThreadRecord::record(void *outputBuffer, void *inputBuffer, unsigned int nBufferFrames, double streamTime, RtAudioStreamStatus status, void *userData)
{
    if (status)
        cout << "Stream overflow detected!" << std::endl;

    short* output = static_cast<short*>(outputBuffer);
    short* input = static_cast<short*>(inputBuffer);
    short n = nBufferFrames;

    int i = *(static_cast<int*>(userData));

    if(i == 2) {
        for (i = 0; i < nBufferFrames; i += 1) {
            output[i] = input[i];
        }
    } else {
        for (; i < nBufferFrames; i += 2) {
            output[i] = input[i];
        }
    }

    return 0;
}

void ThreadRecord::run()
{
    //adc为成员变量:RtAudio adc_;
    // adc_.getDeviceCount()获得音频设备数量
    for(int i = 0 ; i < adc_.getDeviceCount() ; i++)
    {
        qDebug()<< i << adc_.getDeviceInfo(i).name.c_str();
    }

    if (adc_.getDeviceCount() < 1) {
        cout << "\nNo audio devices found!\n";
        exit( 0 );
    }

    //adc_.getDefaultInputDevice();获得默认输入设备
    input.deviceId = adc_.getDefaultInputDevice();
    input.nChannels = 2;
    input.firstChannel = 0;

    output.deviceId = adc_.getDefaultOutputDevice();
    output.nChannels = 2;
    output.firstChannel = 0;

    unsigned int sampleRate = 44100;
    unsigned int bufferFrames = 256; 
    try {
        adc_.openStream(&output, &input, RTAUDIO_SINT16, sampleRate,
                       &bufferFrames, &record, static_cast<void*>(&type),
                       NULL, &ErrorCallback);
        adc_.startStream();
    }
    catch (RtAudioError& e) {
        e.printMessage();
        exit(0);
    }

    while (flag);

    try {
        adc_.stopStream();
    }
    catch (RtAudioError& e) {
        e.printMessage();
    }
    if (adc_.isStreamOpen())
        adc_.closeStream();

}

使用,为了节省篇幅,只写一个函数:
type=0 左声道
type=1 右声道
type=2 双声道

void Recording::onLeftSoundButtonClicked()
{
    if (thread_record.isRunning())
        thread_record.exit(0);
    thread_record.flag = true;
    thread_record.type = 0;
    thread_record.start();
}

你可能感兴趣的:(Qt)