2.4 获取缓冲区数据
设置了通知机制,进行数据捕获的子程序将等待缓冲区的事件通知,通过调用函数win32event.WaitForSingleObject()设置等待一个事件通知或调用win32event. WaitForMultipleObjects()设置等待多个事件通知。当缓冲区被填充到设定位置时,通知事件被触发,调用缓冲区对象PyIDirectSoundBuffer.Update()方法,将音频数据从指定位置读出,同时将该部分缓冲区锁定,以确保音频数据的准确无误。
3 二次封装
为了更简单高效地使用DirectSound编程接口,利用Python面向对象技术对DirectSound音频捕获接口进行二次封装,编写AudioRecord模块,定义类AudioRecord,主要提供以下函数接口:
Record:开始录音并实时捕获音频数据.
Stop:停止录音。
Python中的DirectSound模块封装在win32com扩展库下,可通过以下语句导入:
from win32com.directsound import directsound
另外还需导入下列模块:
import pywintypes
import win32event
3.1 AudioRecord类的初始化
在AudioRecord类的初始化中,完成音频捕获的前期准备工作,包括创建设备对象、创建缓冲区对象、设置通知位置等。主要代码如下:
def __init__(self,nchnl=2,sps=8000,bps=8,t=0.1):
dsc = directsound.DirectSoundCaptureCreate(None, None)#创建设备对象
cdesc = directsound.DSCBUFFERDESC()#创建DSCBUFFERDESC结构对象
self.bSize=int(sps*nchnl*bps/8*t)
cdesc.dwBufferBytes =self.bSize #缓存大小
cdesc.lpwfxFormat = pywintypes.WAVEFORMATEX()#DirectSound数据块格式
cdesc.lpwfxFormat.wFormatTag = pywintypes.WAVE_FORMAT_PCM
cdesc.lpwfxFormat.nChannels = nchnl
cdesc.lpwfxFormat.nSamplesPerSec = sps
cdesc.lpwfxFormat.nAvgBytesPerSec = sps*nchnl*bps/8
cdesc.lpwfxFormat.nBlockAlign = nchnl*bps/8
cdesc.lpwfxFormat.wBitsPerSample = bps
self.buffer = dsc.CreateCaptureBuffer(cdesc)#创建缓冲区对象
self.evt=[]
for i in range(2):
self.evt.append(win32event.CreateEvent(None, 0, 0, None))#创建两个事件通知
Notify=self.buffer.QueryInterface(directsound.IID_IDirectSoundNotify)#创建事件通知接口
Notify.SetNotificationPositions([(self.bSize/2-1,self.evt[0]),(self.bSize-1, self.evt[1])]) #设置两个通知位置,缓冲区每填充bSize/2个样本即发送一个通知消息
self.data=''#用于实时存储捕获的音频数据
self.STATUS=False#录音状态标志
self.wfx=cdesc.lpwfxFormat#存储声音格式
|