|
Public Function PlayWave(hWND As Long, StreamIdx As Integer) As Boolean
' Play's Back Audio Wave Data From String Buffers...
'------------------------------------------------------------------
Dim rc As Long ' Function Return Code
Dim hAS As Long ' ACM stream device
Dim acmHdr As ACMSTREAMHEADER ' ACM stream header
Dim acmHdr_x As ACMSTREAMHEADER ' <<Double Buffering>> ACM stream header
Dim cWavefmt As WAVEFORMATEX ' Wave compression format
Dim waveFmt As WAVEFORMATEX ' Wave format type
Dim hWaveOut As Long ' Handle To A Wave Output Device
Dim WaveOutHdr As WAVEHDR ' Handle To A Wave Output Device Header
Dim WaveOutHdr_x As WAVEHDR ' Handle To A Wave Output Device Header
'------------------------------------------------------------------
Call InitWaveFormat(waveFmt, waveCodec, TIMESLICE) ' Set current wave format
' Open Output Wave Device
rc = waveOutOpen(hWaveOut, WAVE_MAPPER, waveFmt, 0&, 0&, CALLBACK_NULL)
If Not AudioErrorHandler(rc, "waveOutOpen") Then Exit Function ' Validate Return Code
PlayDeviceFree = False ' Allocate Recording Device
' Init Extra Wave Header Format Information
Call InitWaveHDR(WaveOutHdr_x, waveFmt, (waveFmt.nAvgBytesPerSec * TIMESLICE))
' Init Wave Header Format Information
Call InitWaveHDR(WaveOutHdr, waveFmt, (waveFmt.nAvgBytesPerSec * TIMESLICE))
' Prepare Output Wave Device Header
rc = waveOutPrepareHeader(hWaveOut, WaveOutHdr_x, Len(WaveOutHdr_x)) ' Validate Return Code
If Not AudioErrorHandler(rc, "waveOutPrepareHeader") Then GoTo ErrorPlayWave
' Prepare Output Wave Device Header
rc = waveOutPrepareHeader(hWaveOut, WaveOutHdr, Len(WaveOutHdr)) ' Validate Return Code
If Not AudioErrorHandler(rc, "waveOutPrepareHeader") Then GoTo ErrorPlayWave
' <<<Double Buffer>>> Copy (extra)Wave Data To Buffer
If Not (LoadPlayBuffer(hWaveOut, WaveOutHdr_x, waveFmt, _
PlayWaveBuffer.Stream(StreamIdx).Waves(CurPlayPos(StreamIdx)).Data, _
CurPlayPos(StreamIdx))) Then GoTo ErrorPlayWave ' Cleanup And Leave
' <<Double Buffering>> Wait For Wave (xtra)Header CallBack
Call WaitForCallBack(WaveOutHdr_x.dwFlags, WHDR_PREPARED)
' Wait For Wave Header CallBack
Call WaitForCallBack(WaveOutHdr.dwFlags, WHDR_PREPARED)
'Call InitWaveFormat(cWavefmt, waveCodec, TIMESLICE) ' Set current wave format
Call InitWaveFormat(cWavefmt, WAVE_FORMAT_PCM, TIMESLICE) ' Set current wave format
' Open/Configure an acm Stream Handle For Compression
rc = acmStreamOpen(hAS, 0&, waveFmt, cWavefmt, 0&, 0&, 0&, ACM_STREAMOPENF_NONREALTIME)
Call AudioErrorHandler(rc, "acmStreamOpen")
' Initialize Audio Compression wave streaming headers...
Call InitAcmHDR(hAS, acmHdr, WaveOutHdr)
Call InitAcmHDR(hAS, acmHdr_x, WaveOutHdr_x)
' Prepare acm Stream Header
rc = acmStreamPrepareHeader(hAS, acmHdr, 0&)
Call AudioErrorHandler(rc, "acmStreamPrepareHeader")
' Prepare acm Stream Header
rc = acmStreamPrepareHeader(hAS, acmHdr_x, 0&)
Call AudioErrorHandler(rc, "acmStreamPrepareHeader_x")
' <<Double Buffering>> Wait For Wave (xtra)Header CallBack
Call WaitForACMCallBack(acmHdr_x.dwStatus, ACMSTREAMHEADER_STATUSF_PREPARED)
' Wait For Wave Header CallBack
Call WaitForACMCallBack(acmHdr.dwStatus, ACMSTREAMHEADER_STATUSF_PREPARED)
' <<<Double Buffer>>> Write (extra)Wave Buffer To Output Device...
rc = waveOutWrite(hWaveOut, WaveOutHdr_x, Len(WaveOutHdr_x))
If Not AudioErrorHandler(rc, "waveOutWrite_x") Then GoTo ErrorPlayWave ' Validate Return Code
Do
' Copy Wave Data To Buffer
If Not (LoadPlayBuffer(hWaveOut, WaveOutHdr, waveFmt, _
PlayWaveBuffer.Stream(StreamIdx).Waves(CurPlayPos(StreamIdx)).Data, _
CurPlayPos(StreamIdx))) Then GoTo CleanUpPlayWave ' Cleanup And Leave
' <<Double Buffering>> Compress acm Stream Wave Buffer
rc = acmStreamConvert(hAS, acmHdr, ACM_STREAMCONVERTF_BLOCKALIGN)
If Not AudioErrorHandler(rc, "acmStreamConvert") Then GoTo ErrorPlayWave
' Write Wave Buffer To Output Device...
rc = waveOutWrite(hWaveOut, WaveOutHdr, Len(WaveOutHdr))
If Not AudioErrorHandler(rc, "waveOutWrite") Then GoTo ErrorPlayWave ' Validate Return Code
' <<<Double Buffer>>> Wait For Wave Header CallBack
Call WaitForCallBack(WaveOutHdr_x.dwFlags, WHDR_DONE)
' <<<Double Buffer>>> Copy (extra)Wave Data To Buffer
If Not (LoadPlayBuffer(hWaveOut, WaveOutHdr_x, waveFmt, _
PlayWaveBuffer.Stream(StreamIdx).Waves(CurPlayPos(StreamIdx)).Data, _
CurPlayPos(StreamIdx))) Then GoTo CleanUpPlayWave ' Cleanup And Leave
' <<Double Buffering>> Compress acm Stream Wave Buffer
rc = acmStreamConvert(hAS, acmHdr_x, ACM_STREAMCONVERTF_BLOCKALIGN)
If Not AudioErrorHandler(rc, "acmStreamConvert_x") Then GoTo ErrorPlayWave
' <<<Double Buffer>>> Write (extra)Wave Buffer To Output Device...
rc = waveOutWrite(hWaveOut, WaveOutHdr_x, Len(WaveOutHdr_x))
If Not AudioErrorHandler(rc, "waveOutWrite_x") Then GoTo ErrorPlayWave ' Validate Return Code
' Wait For Wave Header CallBack
Call WaitForCallBack(WaveOutHdr.dwFlags, WHDR_DONE)
Loop While Playing ' Continue Playing...
'------------------------------------------------------------------
CleanUpPlayWave: ' Cleanup...
'------------------------------------------------------------------
' <<Double Buffering>> UnPrepare acm Stream Header
rc = acmStreamUnprepareHeader(hAS, acmHdr_x, 0&)
Call AudioErrorHandler(rc, "acmStreamUnprepareHeader_x")
' UnPrepare acm Stream Header
rc = acmStreamUnprepareHeader(hAS, acmHdr, 0&)
Call AudioErrorHandler(rc, "acmStreamUnprepareHeader")
Call FreeAcmHdr(acmHdr) ' Free wave header memory
Call FreeAcmHdr(acmHdr_x) ' Free extra wave header memory
' Close acm Stream Handle
rc = acmStreamClose(hAS, 0&)
Call AudioErrorHandler(rc, "acmStreamClose")
' Wait For Wave Header CallBack
Call WaitForCallBack(WaveOutHdr.dwFlags, WHDR_DONE)
' Unprepare Wave Output Buffer
rc = waveOutUnprepareHeader(hWaveOut, WaveOutHdr, Len(WaveOutHdr))
' <<Double Buffer>> Wait For Wave Header CallBack
Call WaitForCallBack(WaveOutHdr_x.dwFlags, WHDR_DONE)
' <<Double Buffer>> Unprepare Wave Output Buffer
rc = waveOutUnprepareHeader(hWaveOut, WaveOutHdr_x, Len(WaveOutHdr_x))
' Close Output Wave Device
rc = waveOutClose(hWaveOut)
If Not AudioErrorHandler(rc, "waveOutClose") Then Exit Function ' Validate Return Code
' Clean Up Memory Data...
rc = FreeWaveHDR(WaveOutHdr) ' Free Wave Header Data
rc = FreeWaveHDR(WaveOutHdr_x) ' Free Extra Wave Header Data
PlayWave = True ' Return Success
PlayDeviceFree = True ' Free Recording Device
Exit Function ' Exit
'------------------------------------------------------------------
ErrorPlayWave: ' Handle Errors And Cleanup...
'------------------------------------------------------------------
rc = acmStreamUnprepareHeader(hAS, acmHdr, 0&) ' Attempt To UnPrepare acm Stream Header
rc = acmStreamUnprepareHeader(hAS, acmHdr_x, 0&) ' Attempt To UnPrepare acm Stream (xtra)Header
Call FreeAcmHdr(acmHdr) ' Free wave header memory
Call FreeAcmHdr(acmHdr_x) ' Free extra wave header memory
rc = acmStreamClose(hAS, 0&) ' Attempt To Close acm Stream Handle
rc = waveOutUnprepareHeader(hWaveOut, WaveOutHdr, Len(WaveOutHdr)) ' Attempt To Unprepare Header
rc = waveOutUnprepareHeader(hWaveOut, WaveOutHdr_x, Len(WaveOutHdr_x)) ' Attempt To Unprepare Header
rc = waveOutClose(hWaveOut) ' Close Wave Output Device
rc = FreeWaveHDR(WaveOutHdr) ' Free Wave Header Data
rc = FreeWaveHDR(WaveOutHdr_x) ' Free Extra Wave Header Data
PlayDeviceFree = True ' Free Recording Device Flag
Exit Function ' Exit
'------------------------------------------------------------------
End Function
'------------------------------------------------------------------
|
|