123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125 |
- //-----------------------------------------------------------------------------
- // Copyright (c) 2012 GarageGames, LLC
- //
- // Permission is hereby granted, free of charge, to any person obtaining a copy
- // of this software and associated documentation files (the "Software"), to
- // deal in the Software without restriction, including without limitation the
- // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
- // sell copies of the Software, and to permit persons to whom the Software is
- // furnished to do so, subject to the following conditions:
- //
- // The above copyright notice and this permission notice shall be included in
- // all copies or substantial portions of the Software.
- //
- // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
- // IN THE SOFTWARE.
- //-----------------------------------------------------------------------------
- #include "sfx/xaudio/sfxXAudioBuffer.h"
- #include "sfx/xaudio/sfxXAudioVoice.h"
- //#define DEBUG_SPEW
- SFXXAudioBuffer* SFXXAudioBuffer::create( const ThreadSafeRef< SFXStream >& stream, SFXDescription* description )
- {
- SFXXAudioBuffer *buffer = new SFXXAudioBuffer( stream, description );
- return buffer;
- }
- SFXXAudioBuffer::SFXXAudioBuffer( const ThreadSafeRef< SFXStream >& stream, SFXDescription* description )
- : Parent( stream, description )
- {
- VECTOR_SET_ASSOCIATION( mBufferQueue );
- }
- SFXXAudioBuffer::~SFXXAudioBuffer()
- {
- _flush();
- }
- void SFXXAudioBuffer::write( SFXInternal::SFXStreamPacket* const* packets, U32 num )
- {
- AssertFatal( SFXInternal::isSFXThread(), "SFXXAudioBuffer::write() - not on SFX thread" );
- using namespace SFXInternal;
- // Unqueue processed packets.
- if( isStreaming() )
- {
- EnterCriticalSection( &_getUniqueVoice()->mLock );
- XAUDIO2_VOICE_STATE state;
- _getUniqueVoice()->mXAudioVoice->GetState( &state );
- U32 numProcessed = mBufferQueue.size() - state.BuffersQueued;
- for( U32 i = 0; i < numProcessed; ++ i )
- {
- destructSingle< SFXStreamPacket* >( mBufferQueue.first().mPacket );
- mBufferQueue.pop_front();
- #ifdef DEBUG_SPEW
- Platform::outputDebugString( "[SFXXAudioBuffer] Unqueued packet" );
- #endif
- }
- LeaveCriticalSection( &_getUniqueVoice()->mLock );
- }
- // Queue new packets.
- for( U32 i = 0; i < num; ++ i )
- {
- SFXStreamPacket* packet = packets[ i ];
- Buffer buffer;
- if( packet->mIsLast )
- buffer.mData.Flags = XAUDIO2_END_OF_STREAM;
- buffer.mPacket = packet;
- buffer.mData.AudioBytes = packet->mSizeActual;
- buffer.mData.pAudioData = packet->data;
- mBufferQueue.push_back( buffer );
- #ifdef DEBUG_SPEW
- Platform::outputDebugString( "[SFXXAudioBuffer] Queued packet" );
- #endif
- // If this is a streaming buffer, submit the packet to the
- // voice queue right away.
- if( isStreaming() )
- {
- EnterCriticalSection( &_getUniqueVoice()->mLock );
- IXAudio2SourceVoice* voice = _getUniqueVoice()->mXAudioVoice;
- voice->SubmitSourceBuffer( &buffer.mData );
- LeaveCriticalSection( &_getUniqueVoice()->mLock );
- }
- }
- }
- void SFXXAudioBuffer::_flush()
- {
- #ifdef DEBUG_SPEW
- Platform::outputDebugString( "[SFXXAudioBuffer] Flushing buffer" );
- #endif
- if( _getUniqueVoice() )
- _getUniqueVoice()->_stop();
- while( !mBufferQueue.empty() )
- {
- destructSingle( mBufferQueue.last().mPacket );
- mBufferQueue.pop_back();
- }
- }
|