從圖書館借來的書上摘抄下來的,打字手好酸啊,:-)
用底層設備接口函數回放聲音
采樣點:就是聲音的一個采樣數據,按采樣位數的不同,可能占1,2,4個字節。采樣數據為16位時,一個采樣點是一個短整型數,占兩字節,取值范圍-32768~32767.采樣數據為8位或更少時,一個采樣點是一個無符號字符型數據,取值范圍0至255。
立體聲聲音有左聲道和右聲道兩個 通道 。
單聲道聲音只有一個 通道 。
采樣幀:立體聲左聲道的第一個采樣點和右聲道的第一個采樣點構成一個采樣幀;同理他們的第二個采樣點又構成一個采樣幀。如果是單聲道,一個采樣點就是一個采樣幀。
所用函數需要包含頭文件mmsystem.h,並且在編譯連接時加入庫文件winmm.lib。
1.打開音頻設備
用waveOutOpen,調用時要指定:
設備ID,通常用WAVE_MAPPER,即標准音頻設備;
采樣數據格式,如采樣率,采樣位數等;
回調方式。
如果調用成功,我們將得到一個設備句柄,以后的函數調用需要這個句柄。
在打開音頻設備時,用戶可以向系統傳遞一個 函數地址 或 一個事件 或 窗口句柄。
2.傳送采樣數據
首先用waveOutPrepareHeader准備采樣數據,然后用waveOutWrite把准備好的數據發給設備開始回放,回放完畢后用waveOutUnprepareHeader取消采樣數據的准備。
3.關閉設備
用函數waveOutClose實現。
下面是一段用底層函數回放的代碼,假設采樣數據已經從WAV文件中取出,放在指針lpwavedata指向的內存,大小為wavesize,聲音格式為PCM,立體聲,采樣頻率44.1kHz,采樣位16:
//打開音頻設備
HWAVEOUT hWave;
PCMWAVEFORMAT fmt = {{1, //PCM
2, //通道數
44100, //采樣頻率
4*44100 //每秒數據量(字節)
4}, //采樣幀大小
16}; //采樣位
HANDLE hEvent = CreateEvent(NULL,FALSE,FALSE,NULL);
waveOutOpen(&hWave,WAVE_MAPPER,(LPWAVEFORMATEX)&fmt,(DWORD)hEvent,0,CALLBACK_EVENT);
//准備數據
WAVEHDR whdr;
memset(&whdr,0,sizeof(WAVEHDR));
whdr.lpData=lpwavedata;
whdr.dwBufferLength=wavesize;
waveOutPrepareHeader(hWave,&whdr,sizeof(WAVEHDR));
//輸出
waveOutWrite(hWave,&whdr,sizeof(WAVEHDR));
//等待回放完畢
WaitForSingleObject(hEvent,INFINITE);
//取消准備
waveOutUnprepareHeader(hWave,&whdr,sizeof(WAVEHDR));
//關閉設備
waveOutClose(hWave);
WaitForSingleObject(hEvent,INFINITE);
CloseHandle(hEvent);
本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系我们删除。