Cinder

  • Main Page
  • Related Pages
  • Namespaces
  • Classes
  • Files
  • Examples
  • File List
  • File Members

include/cinder/audio/OutputImplAudioUnit.h

Go to the documentation of this file.
00001 /*
00002  Copyright (c) 2009, The Barbarian Group
00003  All rights reserved.
00004 
00005  Redistribution and use in source and binary forms, with or without modification, are permitted provided that
00006  the following conditions are met:
00007 
00008     * Redistributions of source code must retain the above copyright notice, this list of conditions and
00009     the following disclaimer.
00010     * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and
00011     the following disclaimer in the documentation and/or other materials provided with the distribution.
00012 
00013  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED
00014  WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
00015  PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
00016  ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
00017  TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
00018  HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
00019  NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
00020  POSSIBILITY OF SUCH DAMAGE.
00021 */
00022 
00023 #pragma once
00024 
00025 #include "cinder/audio/Output.h"
00026 #include <CoreAudio/CoreAudioTypes.h>
00027 #include <AudioUnit/AudioUnit.h>
00028 #include <AudioToolbox/AUGraph.h>
00029 #include <boost/thread/mutex.hpp>
00030 #if defined( CINDER_MAC) && (MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_7)
00031     #include <CoreAudio/AudioHardware.h>
00032 #endif
00033 #include <stack>
00034 
00035 namespace cinder { namespace audio {
00036 
00037 class OutputImplAudioUnit;
00038 
00039 class TargetOutputImplAudioUnit : public Target {
00040   public: 
00041     static std::shared_ptr<TargetOutputImplAudioUnit> createRef( const OutputImplAudioUnit *aOutput ){ return std::shared_ptr<TargetOutputImplAudioUnit>( new TargetOutputImplAudioUnit( aOutput ) );  };
00042     ~TargetOutputImplAudioUnit() {}
00043   private:
00044     TargetOutputImplAudioUnit( const OutputImplAudioUnit *aOutput );
00045     
00046     //uint64_t                      mPacketOffset;
00047     //AudioStreamPacketDescription  * mCurrentPacketDescriptions;
00048 };
00049 
00050 class OutputImplAudioUnit : public OutputImpl {
00051   public:
00052     OutputImplAudioUnit();
00053     ~OutputImplAudioUnit();
00054     
00055     TrackRef    addTrack( SourceRef source, bool autoplay );
00056     void        removeTrack( TrackId trackId );
00057     
00058     void setVolume( float aVolume );
00059     float getVolume() const;
00060     
00061     //TargetRef getTarget();
00062   protected:
00063     TrackId                         availableTrackId() { 
00064                                         if( mAvailableBuses.size() < 1 ) return -1;
00065                                         TrackId bus = mAvailableBuses.top(); 
00066                                         mAvailableBuses.pop(); return bus; 
00067                                     }
00068   private:
00069   
00070     static const uint32_t           sDefaultNumberBuses;
00071     std::stack<TrackId>             mAvailableBuses;
00072     uint32_t                        mNumberBuses;
00073 #if defined(CINDER_MAC)
00074     AudioDeviceID                   mOutputDeviceId;
00075 #endif
00076     AUGraph                         mGraph;
00077     AUNode                          mMixerNode;
00078     AUNode                          mOutputNode;
00079     AudioUnit                       mOutputUnit;
00080     AudioUnit                       mMixerUnit;
00081     AudioStreamBasicDescription     * mPlayerDescription;
00082     
00083     class Track : public cinder::audio::Track
00084     {
00085       public:
00086         Track( SourceRef source, OutputImplAudioUnit * output );
00087         ~Track();
00088         void play();
00089         void stop();
00090         bool isPlaying() const { return mIsPlaying; } 
00091         
00092         TrackId getTrackId() const { return mInputBus; }
00093         
00094         void setVolume( float aVolume );
00095         float getVolume() const;
00096         
00097         double getTime() const { return ( mLoader->getSampleOffset() / (double)mSource->getSampleRate() ); }
00098         void setTime( double aTime );
00099         
00100         bool isLooping() const { return mIsLooping; }
00101         void setLooping( bool isLooping ) { mIsLooping = isLooping; }
00102         
00103         void enablePcmBuffering( bool isBuffering ) { mIsPcmBuffering = isBuffering; }
00104         bool isPcmBuffering() { return mIsPcmBuffering; }
00105         
00106         PcmBuffer32fRef getPcmBuffer();
00107       private:
00108         static OSStatus renderCallback( void * audioLoader, AudioUnitRenderActionFlags *ioActionFlags, const AudioTimeStamp *inTimeStamp, UInt32 inBusNumber, UInt32 inNumberFrames, AudioBufferList *ioData );
00109         static OSStatus renderNotifyCallback( void * audioTrack, AudioUnitRenderActionFlags *ioActionFlags, const AudioTimeStamp *inTimeStamp, UInt32 inBusNumber, UInt32 inNumberFrames, AudioBufferList *ioData );
00110         
00111         void createPcmBuffer();
00112         
00113         SourceRef       mSource;
00114         std::shared_ptr<TargetOutputImplAudioUnit> mTarget;
00115         OutputImplAudioUnit * mOutput;
00116         TrackId         mInputBus;
00117         LoaderRef       mLoader;
00118         bool            mIsPlaying;
00119         bool            mIsLooping;
00120         bool            mIsPcmBuffering;
00121         
00122         PcmBuffer32fRef mLoadingPcmBuffer;
00123         PcmBuffer32fRef mLoadedPcmBuffer;
00124         boost::mutex    mPcmBufferMutex;
00125     };
00126     
00127     std::map<TrackId,std::shared_ptr<OutputImplAudioUnit::Track> >  mTracks;
00128     
00129     friend class TargetOutputImplAudioUnit;
00130 };
00131 
00132 }} //namespace