収集したオーディオをaac符号化して保存する

5604 ワード

ダイレクトコード
#include "RtAudio.h"
#include "../libaac/faac.h"
#include "../libaac/faaccfg.h"

#include 
#include 
#include 
#include 
#include 

using namespace std;


const unsigned long uiSampleteRate = 44100;
const unsigned int uiChannels = 2;
const int uiBitRate = 96000;
unsigned long ulSamplesInputSize = 0;
vector vHeader;
vector vBytesCache;
mutex g_i_mutex;
BOOL bStop = false;
shared_ptr frame = nullptr;
faacEncHandle pFaacHandle;
unsigned long ulMaxOutputSize = 0;
shared_ptr pOutputBuffer = nullptr;
shared_ptr pGrabEngine = make_shared();// 
FILE* fp_out = nullptr;
FILE* fp_out1 = nullptr;

float getFrameDuration()
{
	float frameDuration = (float)ulSamplesInputSize * 1000.00 / (float)uiSampleteRate / uiChannels;
	cout < lock(g_i_mutex);
	for (int i = 0; i < size; ++i)
	{
		vBytesCache.push_back(data[i]);
	}
}

void stopCapture()
{
	if (pGrabEngine.get()->isStreamOpen())
		pGrabEngine.get()->closeStream();


	if (pFaacHandle) faacEncClose(pFaacHandle);
}

int handleAudioData(void *outputBuffer, void *inputBuffer, unsigned int nBufferFrames, double streamTime, RtAudioStreamStatus status, void *data)
{
	int bytesReady = nBufferFrames * 16 / 8 * uiChannels;
	//cout << "zzq " << nBufferFrames << endl;
	onDataCaptured((char*)inputBuffer, bytesReady);
	//fwrite((char*)inputBuffer, 1, bytesReady, fp_out1);
	return 0;// 
}

void EncodeAudio()
{
	int frameSize = ulSamplesInputSize * 16 / 8;;
	frame = shared_ptr(new unsigned char[frameSize], [](unsigned char* p){delete[] p; });// 
	while (!bStop) {
		

		lock_guard lock(g_i_mutex);

		if (vBytesCache.size() < frameSize) {
			this_thread::sleep_for(chrono::milliseconds(20));
			continue;
		}

		while (vBytesCache.size() >= frameSize) {
			memcpy(frame.get(), &(vBytesCache[0]), frameSize);
			vBytesCache.erase(vBytesCache.begin(), vBytesCache.begin() + frameSize);

			// 
			int encodedBytes = faacEncEncode(pFaacHandle, (int32_t*)frame.get(), ulSamplesInputSize, pOutputBuffer.get(), ulMaxOutputSize);
			//log_info("aac ori data %d , encode data %d", data.size(), encodedBytes);
			//test
			//cout << "zzq" << frame.use_count() << " " << encodedBytes << endl;
			if (encodedBytes < 0) {
				cout<version != FAAC_CFG_VERSION)
	{
		faacEncClose(pFaacHandle);
		cout<(new unsigned char[ulMaxOutputSize], [](unsigned char* p){delete[] p; });

	// put the options in the configuration struct.
	pAACConfig->aacObjectType = LOW; // MAIN
	pAACConfig->mpegVersion = MPEG4;
	pAACConfig->useTns = 1;
	pAACConfig->useLfe = 1;
	pAACConfig->allowMidside = 1;
	pAACConfig->bitRate = uiBitRate / uiChannels;
	pAACConfig->bandWidth = 0;
	pAACConfig->quantqual = 100;
	pAACConfig->outputFormat = 1;
	pAACConfig->inputFormat = FAAC_INPUT_16BIT;
	pAACConfig->shortctl = SHORTCTL_NORMAL;

	// 
	if (!faacEncSetConfiguration(pFaacHandle, pAACConfig))
	{
		cout << ("faacEncSetConfiguration failed") << endl;
		return -1;
	}
	unsigned int uiFrameSize = ulSamplesInputSize / uiChannels;
	//m_pInBuf = new int32_t[m_samplesInputSize];
	//shared_ptr pInBuf = shared_ptr(new unsigned char[ulSamplesInputSize], [](unsigned char* p){delete[] p; });


	// set decoder specific info
	unsigned long extradata_size = 0;
	unsigned char *buffer;
	unsigned long decoder_specific_info_size;

	if (!faacEncGetDecoderSpecificInfo(pFaacHandle, &buffer, &decoder_specific_info_size)) {
		extradata_size = decoder_specific_info_size;
	}
	cout << "aac encoder extradata_size=" << extradata_size << endl;

	vHeader.clear();
	vHeader.push_back('0xaf');
	vHeader.push_back('0x00');
	for (int i = 0; i < extradata_size; ++i)
	{
		vHeader.push_back(buffer[i]);
	}
	delete[] buffer;


	
	//RtAudio* pGrabEngine = new RtAudio;

	unsigned int bufferFrames = ulSamplesInputSize / uiChannels;;

	RtAudio::StreamParameters params;
	int deviceCount = pGrabEngine.get()->getDeviceCount();
	for (int i = 0; i < deviceCount; ++i)
	{
		RtAudio::DeviceInfo info = pGrabEngine.get()->getDeviceInfo(i);
	}

	errno_t err = fopen_s(&fp_out, "test.aac", "wb");
	if (!fp_out)
	{
		cout << "Could not open output aac file." << endl;
		return -1;
	}
	err = fopen_s(&fp_out1, "test.raw", "wb");
	if (!fp_out1)
	{
		cout << "Could not open output raw file." << endl;
		return -1;
	}

	int deviceID = pGrabEngine.get()->getDefaultInputDevice();// id    getDeviceCount getDeviceInfo  
	params.deviceId = deviceID;
	params.nChannels = uiChannels;
	params.firstChannel = 0;

	
	pGrabEngine.get()->openStream(NULL, &params, RTAUDIO_SINT16, uiSampleteRate, &bufferFrames, &handleAudioData, NULL);
	
	// 
	thread t2(EncodeAudio);
	t2.detach();
	
	pGrabEngine.get()->startStream();
	
	int c;
	while (true)
	{
		if (getch() == 'q')
		{
			break;
		}
	}
	bStop = true;
	this_thread::sleep_for(chrono::milliseconds(100));// 
	stopCapture();
	fclose(fp_out);
	fclose(fp_out1);
	return 0;
}


生成したaacファイルをvlcで開いて再生し、イヤホンをつけないと音が少し小さくなります.
最後にダウンロードリソースアドレスを添付しますhttps://download.csdn.net/download/zzqgtt/10618585