00001 00002 // 00003 // Copyright (c) 2006 Audiokinetic Inc. / All Rights Reserved 00004 // 00006 00007 #ifndef _AKFXDURATIONHANDLER_H_ 00008 #define _AKFXDURATIONHANDLER_H_ 00009 00010 #include <AK/SoundEngine/Common/AkTypes.h> 00011 00014 class AkFXDurationHandler 00015 { 00016 public: 00017 00019 inline void Setup( 00020 AkReal32 in_fDuration, 00021 AkInt16 in_iLoopingCount, 00022 AkUInt32 in_uSampleRate 00023 ) 00024 { 00025 m_uSampleRate = in_uSampleRate; 00026 SetDuration( in_fDuration ); 00027 SetLooping( in_iLoopingCount ); 00028 Reset(); 00029 } 00030 00032 inline void Reset() 00033 { 00034 m_uFrameCount = 0; 00035 } 00036 00038 inline void SetLooping( AkInt16 in_iNumLoops ) 00039 { 00040 m_iNumLoops = in_iNumLoops; 00041 } 00042 00044 inline void SetDuration( AkReal32 in_fDuration ) 00045 { 00046 m_uIterationFrame = (AkUInt32) (in_fDuration*m_uSampleRate); 00047 m_uIterationFrame = (m_uIterationFrame + 3) & ~3; // Align to next 4 frame boundary for SIMD alignment 00048 } 00049 00051 inline AkReal32 GetDuration() const 00052 { 00053 // Note: Infinite looping will return a duration of 0 secs. 00054 return (AkReal32)(m_uIterationFrame*m_iNumLoops)/m_uSampleRate; 00055 } 00056 00059 inline void ProduceBuffer( AkAudioBuffer * io_pBuffer ) 00060 { 00061 io_pBuffer->eState = ProduceBuffer( io_pBuffer->MaxFrames(), io_pBuffer->uValidFrames ); 00062 } 00063 00066 inline AKRESULT ProduceBuffer( AkUInt16 in_uMaxFrames, AkUInt16 & out_uValidFrames ) 00067 { 00068 // Infinite looping or not reached the end, always producing full capacity 00069 out_uValidFrames = in_uMaxFrames; 00070 AKRESULT eState = AK_DataReady; 00071 00072 if ( m_iNumLoops != 0 ) 00073 { 00074 // Finite looping, produce full buffer untill the end. 00075 const AkUInt32 uTotalFrames = m_iNumLoops*m_uIterationFrame; 00076 if ( m_uFrameCount < uTotalFrames ) 00077 { 00078 const AkUInt32 uFramesRemaining = uTotalFrames-m_uFrameCount; 00079 if ( uFramesRemaining <= in_uMaxFrames ) 00080 { 00081 out_uValidFrames = (AkUInt16)uFramesRemaining; 00082 eState = AK_NoMoreData; 00083 } 00084 } 00085 else 00086 { 00087 out_uValidFrames = 0; 00088 eState = AK_NoMoreData; 00089 } 00090 } 00091 m_uFrameCount += out_uValidFrames; 00092 00093 return eState; 00094 } 00095 00096 protected: 00097 00098 AkUInt32 m_uIterationFrame; // Number of frames in a single loop iteration 00099 AkUInt32 m_uFrameCount; // Number of frames output in the current iteration 00100 AkUInt32 m_uSampleRate; // Sample rate used to convert time to samples 00101 AkInt16 m_iNumLoops; // Number of loop iterations (0 == infinite looping) 00102 00103 }; 00104 00105 #endif // _AKFXDURATIONHANDLER_H_