# Cinder

- Main Page
- Related Pages
- Namespaces
- Classes
- Files

- File List
- File Members

# include/cinder/qtime/QuickTime.h

Go to the documentation of this file.

    00001 /*
    00002  Copyright (c) 2010, 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 // None of this works in 64 bit on the mac or Windows. We'll need to move to QTKit on the mac.
    00026 #if ! defined( __LP64__ )
    00027
    00028 #include "cinder/Cinder.h"
    00029 #include "cinder/gl/gl.h"
    00030 #include "cinder/Surface.h"
    00031 #include "cinder/gl/Texture.h"
    00032 #include "cinder/Display.h"
    00033 #include "cinder/Url.h"
    00034 #include "cinder/DataSource.h"
    00035 #include "cinder/Thread.h"
    00036
    00037 #include <string>
    00038
    00039 #if defined( CINDER_MAC )
    00040     #include <QuickTime/QuickTime.h>
    00041     #if defined( __OBJC__ )
    00042         @class QTMovie;
    00043     #else
    00044         class QTMovie;
    00045     #endif
    00046 #endif
    00047
    00048
    00049 // these are forward-declared to avoid bringing all of QuickTime into the global namespace on Windows
    00050 #if defined( CINDER_MSW )
    00051     typedef struct MovieType**              Movie;
    00052     typedef struct OpaqueQTVisualContext*   QTVisualContextRef;
    00053     typedef long                            TimeValue;
    00054     typedef struct QTAudioFrequencyLevels   QTAudioFrequencyLevels;
    00055     typedef unsigned long                   FourCharCode;
    00056     typedef struct __CVBuffer*              CVBufferRef;
    00057     typedef CVBufferRef                     CVImageBufferRef;
    00058 #endif
    00059
    00060 namespace cinder { namespace qtime {
    00061
    00062 class MovieBase {
    00063  public:
    00064     virtual     ~MovieBase() {}
    00065
    00067     bool        checkPlayable();
    00068
    00070     int32_t     getWidth() const { return getObj()->mWidth; }
    00072     int32_t     getHeight() const { return getObj()->mHeight; }
    00074     float       getAspectRatio() const { return getObj()->mWidth / (float)getObj()->mHeight; }
    00076     float       getDuration() const { return getObj()->mDuration; }
    00078     float       getFramerate() const;
    00080     int32_t     getNumFrames() const;
    00082     bool        hasAlpha() const;
    00083
    00085     bool        hasVisuals() const;
    00087     bool        hasAudio() const;
    00088
    00089
    00091     float       getCurrentTime() const;
    00093     void        seekToTime( float seconds );
    00095     void        seekToFrame( int frame );
    00097     void        seekToStart();
    00099     void        seekToEnd();
    00101     void        setActiveSegment( float startTime, float duration );
    00103     void        resetActiveSegment();
    00104
    00106     void        setLoop( bool loop = true, bool palindrome = false );
    00108     void        stepForward();
    00110     void        stepBackward();
    00112     void        setRate( float rate );
    00113
    00115     void        setVolume( float volume );
    00117     float       getVolume() const;
    00118
    00120     void        setupMonoFft( uint32_t numBands );
    00122     void        setupStereoFft( uint32_t numBands );
    00124     void        setupMultiChannelFft( uint32_t numBands );
    00125
    00126     float*      getFftData() const;
    00127     uint32_t    getNumFftBands() const;
    00128     uint32_t    getNumFftChannels() const;
    00129
    00131     bool    isPlaying() const;
    00133     bool    isDone() const;
    00135     void    play();
    00137     void    stop();
    00138
    00140     void    setNewFrameCallback( void(*aNewFrameCallback)( long, void * ), void *aNewFrameCallbackRefcon );
    00141
    00143 	::Movie    getMovieHandle() const { return getObj()->mMovie; }
    00144
    00145  protected:
    00146     MovieBase() {}
    00147     void            init();
    00148     void            updateFrame();
    00149     void            updateLoadState();
    00150
    00151     void            setupFft( FourCharCode code, uint32_t bandNum, uint8_t channelNum );
    00152
    00153     static int32_t      countFrames( ::Movie theMovie );
    00154     TimeValue           getStartTimeOfFirstSample() const;
    00155
    00156  protected:
    00157     void    initFromPath( const std::string &path );
    00158     void    initFromLoader( const class MovieLoader &loader );
    00159     void    initFromMemory( const void *data, size_t dataSize, const std::string &fileNameHint, const std::string &mimeTypeHint );
    00160     void    initFromDataSource( DataSourceRef dataSource, const std::string &mimeTypeHint );
    00161
    00162     struct Obj {
    00163         Obj();
    00164         virtual ~Obj();
    00165
    00166         void prepareForDestruction();
    00167
    00168         void lock() { mMutex.lock(); }
    00169         void unlock() { mMutex.unlock(); }
    00170
    00171         // because the MovieBase* might change over time, but the MovieBase::Obj* will not, we need our callbacks to take an Obj* as a refcon
    00172         // which in turn means this functionality must be in the Obj, not the MovieBase
    00173         virtual void        releaseFrame() = 0;
    00174         virtual void        newFrame( CVImageBufferRef cvImage ) = 0;
    00175
    00176         int32_t                     mWidth, mHeight;
    00177         int32_t                     mFrameCount;
    00178         float                       mDuration;
    00179         bool                        mLoaded, mPlayable;
    00180         bool                        mPlayingForward, mLoop, mPalindrome;
    00181
    00182         QTAudioFrequencyLevels      *mFFTData;
    00183         FourCharCode                mFFTFourCharCode;
    00184         uint32_t                    mFFTNumBandLevels;
    00185         uint32_t                    mFFTNumChannels;
    00186         QTVisualContextRef          mVisualContext;
    00187 		::Movie                       mMovie;
    00188
    00189         void        (*mNewFrameCallback)(long timeValue, void *refcon);
    00190         void        *mNewFrameCallbackRefcon;
    00191
    00192         std::mutex                  mMutex;
    00193         DataSourceRef               mDataSource; // sometimes used to retain a reference to a data source so that it doesn't go away before we do
    00194     };
    00195
    00196     virtual Obj*        getObj() const = 0;
    00197 };
    00198
    00199 class MovieSurface : public MovieBase {
    00200  public:
    00201     MovieSurface() : MovieBase() {}
    00202     MovieSurface( const std::string &path );
    00203     MovieSurface( const class MovieLoader &loader );
    00205
    00206     MovieSurface( const void *data, size_t dataSize, const std::string &fileNameHint, const std::string &mimeTypeHint = "" );
    00207     MovieSurface( DataSourceRef dataSource, const std::string mimeTypeHint = "" );
    00208
    00210     Surface     getSurface();
    00211
    00212  protected:
    00213     void                allocateVisualContext();
    00214
    00215     struct Obj : public MovieBase::Obj {
    00216         virtual ~Obj();
    00217
    00218         virtual void        releaseFrame();
    00219         virtual void        newFrame( CVImageBufferRef cvImage );
    00220
    00221         Surface             mSurface;
    00222     };
    00223
    00224     shared_ptr<Obj>             mObj;
    00225     virtual MovieBase::Obj*     getObj() const { return mObj.get(); }
    00226
    00227   public:
    00229
    00230     typedef shared_ptr<Obj> MovieSurface::*unspecified_bool_type;
    00231     operator unspecified_bool_type() { return ( mObj.get() == 0 ) ? 0 : &MovieSurface::mObj; }
    00232     void reset() { mObj.reset(); }
    00234 };
    00235
    00240 class MovieGl : public MovieBase {
    00241   public:
    00242     MovieGl() : MovieBase() {}
    00243     MovieGl( const std::string &path );
    00244     MovieGl( const class MovieLoader &loader );
    00246
    00247     MovieGl( const void *data, size_t dataSize, const std::string &fileNameHint, const std::string &mimeTypeHint = "" );
    00248     MovieGl( DataSourceRef dataSource, const std::string mimeTypeHint = "" );
    00249
    00251     const gl::Texture   getTexture();
    00252
    00253   protected:
    00254     void                allocateVisualContext();
    00255
    00256     struct Obj : public MovieBase::Obj {
    00257         Obj();
    00258         ~Obj();
    00259
    00260         virtual void        releaseFrame();
    00261         virtual void        newFrame( CVImageBufferRef cvImage );
    00262
    00263         gl::Texture         mTexture;
    00264 #if defined( CINDER_MSW )
    00265         gl::TextureCache    mTextureCache;
    00266 #endif
    00267     };
    00268
    00269     shared_ptr<Obj>             mObj;
    00270     virtual MovieBase::Obj*     getObj() const { return mObj.get(); }
    00271
    00272   public:
    00274
    00275     typedef shared_ptr<Obj> MovieGl::*unspecified_bool_type;
    00276     operator unspecified_bool_type() { return ( mObj.get() == 0 ) ? 0 : &MovieGl::mObj; }
    00277     void reset() { mObj.reset(); }
    00279 };
    00280
    00281 class MovieLoader {
    00282   public:
    00283     MovieLoader() {}
    00284     MovieLoader( const Url &url );
    00285
    00287     bool    checkLoaded() const;
    00289     bool    checkPlayable() const;
    00291     bool    checkPlaythroughOk() const;
    00292
    00294     void    waitForLoaded() const;
    00296     void    waitForPlayable() const;
    00298     void    waitForPlaythroughOk() const;
    00299
    00301     const Url&      getUrl() const { return mObj->mUrl; }
    00302
    00304 	::Movie    getMovieHandle() const { return mObj->mMovie; }
    00305
    00307 	::Movie transferMovieHandle() const { mObj->mOwnsMovie = false; return mObj->mMovie; }
    00308
    00309   protected:
    00310     void    updateLoadState() const;
    00311
    00312     struct Obj {
    00313         Obj( const Url &url );
    00314         ~Obj();
    00315
    00316         mutable bool    mOwnsMovie;
    00317 		::Movie           mMovie;
    00318         Url             mUrl;
    00319         mutable bool    mLoaded, mPlayable, mPlaythroughOK;
    00320     };
    00321
    00322     shared_ptr<Obj>     mObj;
    00323
    00324   public:
    00326
    00327     MovieLoader( const MovieLoader &other ) { mObj = other.mObj; }
    00328     MovieLoader& operator=( const MovieLoader &other ) { mObj = other.mObj; return *this; }
    00329     bool operator==( const MovieLoader &other ) { return mObj == other.mObj; }
    00330     typedef shared_ptr<Obj> MovieLoader::*unspecified_bool_type;
    00331     operator unspecified_bool_type() { return ( mObj.get() == 0 ) ? 0 : &MovieLoader::mObj; }
    00332     void reset() { mObj.reset(); }
    00334 };
    00335
    00337 extern int32_t getQuickTimeVersion();
    00339 extern std::string getQuickTimeVersionString();
    00340
    00342 extern void quickTimeTask();
    00343
    00344 class QuickTimeExc : public std::exception {
    00345 };
    00346
    00347 class QuickTimePathInvalidExc : public QuickTimeExc {
    00348 };
    00349
    00350 class QuickTimeFileInvalidExc : public QuickTimeExc {
    00351 };
    00352
    00353 class QuickTimeExcUrlInvalid : public QuickTimeExc {
    00354 };
    00355
    00356 class QuickTimeErrorLoadingExc : public QuickTimeExc {
    00357 };
    00358
    00359 class QuickTimeExcFft : public QuickTimeExc {
    00360 };
    00361
    00362 } /* namespace qtime */ } /* namespace cinder */
    00363 #endif // ! defined( __LP64__ )