博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
C语言-从声卡录音的一个demo
阅读量:6695 次
发布时间:2019-06-25

本文共 4918 字,大约阅读时间需要 16 分钟。

/*http://sdr-reu.wikispaces.com/file/view/SoundIn.cFile to read sound from sound card and record it to a file in PCM format.*/#include 
#include
#include
#include
#pragma comment(lib, "winmm.lib")#define IN_BUFFERS_NUMBER 4 //开辟三个数据缓冲区#define REC_STATUS_STARTING_RECORD 1#define REC_STATUS_RECORDING 2#define REC_STATUS_ALL_DONE -2 //录音完成#define REC_STATUS_FINISHING -1 //即将完成#define REC_STATUS_FAIL -3#define SIZE_OF_WAVEHDR 32 //wave头大小//函数void FreeBuffers(WAVEHDR * buffers);DWORD WINAPI waveInProc(LPVOID threadControls);typedef struct soundInDataAndControls{ WAVEHDR buffers[IN_BUFFERS_NUMBER]; //开辟三个数据缓冲区 int recordingStatus; //录音状态 HWAVEIN inWaveDevice; int buffers_left; //可用内存数目}SoundThreadInfo;WAVEFORMATEX sampleFormat; //全局变量char * outfilename;HMMIO m_hFile;MMCKINFO m_MMCKInfoData;MMCKINFO m_MMCKInfoParent;MMCKINFO m_MMCKInfoChild;int main(){ MMRESULT errorResult = 0 ; SoundThreadInfo soundIn; HANDLE inWaveThreadHandle; //线程 int x = 0; //计数器 soundIn.recordingStatus = 0; //设置录音状态 soundIn.buffers_left = IN_BUFFERS_NUMBER; //设置预期缓冲数量 outfilename = ".\\1.wav"; inWaveThreadHandle = CreateThread(0 ,0,(LPTHREAD_START_ROUTINE)waveInProc,/*参数*/ &soundIn, 0, &errorResult); //创建线程 if(!inWaveThreadHandle) { printf("Can't create sound in thread! -- %08X\n",GetLastError()); return 0; } CloseHandle(inWaveThreadHandle); //关闭线程 for (x = 0; x
> 3); sampleFormat.nAvgBytesPerSec = sampleFormat.nSamplesPerSec * sampleFormat.nBlockAlign; if(!CreateWaveFile()) { return getchar(); } //分配 memory sound in buffers. for(x = 0; x < IN_BUFFERS_NUMBER; x++) //this loop is not need after testing { //can be replaced with hard coded buffer allocation //clear waveheaders ZeroMemory(&soundIn.buffers[x],SIZE_OF_WAVEHDR); soundIn.buffers[x].dwBufferLength = sampleFormat.nAvgBytesPerSec << 2; //内存大小估计一块 soundIn.buffers[x].dwFlags = 0; soundIn.buffers[x].lpData = (char *) VirtualAlloc(NULL, soundIn.buffers[0].dwBufferLength, MEM_COMMIT, PAGE_READWRITE); //申请内存 if(soundIn.buffers[x].lpData == NULL) { printf("Sound In Buffer number %d failed to get allocate memory.\n",x); for(--x;x;x--) // start 1 down, and while x!=0 x-- { VirtualFree(soundIn.buffers[x].lpData, 0, MEM_RELEASE); //释放内存 } return 0; } else { printf(" %d Buffer Application sucsess\n",x); } } //open wave device errorResult = waveInOpen(&soundIn.inWaveDevice, WAVE_MAPPER, &sampleFormat, (DWORD)errorResult, 0, CALLBACK_THREAD); if(errorResult != MMSYSERR_NOERROR) { FreeBuffers(soundIn.buffers); return getchar(); } // buffers and queue them for(x=0;x
dwBytesRecorded); //collect data if(inFORMATION->recordingStatus != 0) //recording not began or stopped只有0 ,-1 -2 三个值 { if(inFORMATION->recordingStatus == REC_STATUS_ALL_DONE) { printf("Possible error recieving WIM_DATA during condition ALL_DONE\n"); break; //time for thread to end } outputlenth = mmioWrite(m_hFile, ((WAVEHDR *) msg.lParam)->lpData,((WAVEHDR *)msg.lParam)->dwBytesRecorded); if(outputlenth == ((WAVEHDR *)msg.lParam)->dwBytesRecorded) { printf("sucsess save data_dwBytesRecorded %d\n",outputlenth); printf("sucsess save data_dwBufferLength %d\n",((WAVEHDR *)msg.lParam)->dwBufferLength); } //was this that last block the user wanted. if(inFORMATION->recordingStatus == REC_STATUS_FINISHING) { //the buffers are each sent back, but not requeue if(--inFORMATION->buffers_left == 0) { inFORMATION->recordingStatus = REC_STATUS_ALL_DONE; } printf("Buffer finished.\n"); continue; } } //if stopped it only requeue s the buffer and continues. //requeue buffer if(!waveInAddBuffer(inFORMATION->inWaveDevice, (WAVEHDR *) msg.lParam, SIZE_OF_WAVEHDR)) { if(!waveInAddBuffer(inFORMATION->inWaveDevice, (WAVEHDR *) msg.lParam, SIZE_OF_WAVEHDR)) { printf("Buffer requeue error.\n"); if(--inFORMATION->buffers_left < 2) { FreeBuffers(inFORMATION->buffers); printf("in requeue error device."); errorResult = waveInClose(inFORMATION->inWaveDevice); if(errorResult) { printf("Can't Close Wave Device!\n"); getchar(); } return 0; inFORMATION->recordingStatus = REC_STATUS_FINISHING; //finishing means takes the queued blocks and no more //in thoery the next block (the last one) that was queue //previously mmioAscend(m_hFile, &m_MMCKInfoChild, 0); mmioAscend(m_hFile, &m_MMCKInfoParent, 0); return -1; } } } } } return 1;}

 

转载于:https://www.cnblogs.com/ikodota/archive/2013/02/22/2922636.html

你可能感兴趣的文章
ContiPerf接口性能测试
查看>>
linux log查看(转载)
查看>>
dedecms手机站如何ajax提交数据到自定义表单
查看>>
jquery通过新浪财经的接口获取股票走势图和股票数据
查看>>
elasticsearch安装ik中文分词插件
查看>>
JSP中request.getParameter()乱码问题
查看>>
java根据ip地址获取详细地域信息
查看>>
YUM仓库服务与PXE网络装机
查看>>
05.第一个oc的类
查看>>
java调用finalize()方法
查看>>
今天发现了个好东西——exVim~
查看>>
命令和查询责任分离(CQRS)架构模式
查看>>
我的友情链接
查看>>
flume+kafka+hdfs详解
查看>>
win2012单宿主powershell批量建立虚拟机
查看>>
PostgreSQL 帐号密码修改、新建用户,新建数据库操作方法
查看>>
php curl 跨域请求例子
查看>>
Xshell下复制粘贴的快捷键设置
查看>>
Swift 设置View的背景图片
查看>>
centos6.4 rpm mysql安装步骤
查看>>