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 #include "cinder/Cinder.h" 00026 #include "cinder/app/Renderer.h" 00027 #include "cinder/Vector.h" 00028 #include "cinder/app/MouseEvent.h" 00029 #include "cinder/app/KeyEvent.h" 00030 #include "cinder/app/FileDropEvent.h" 00031 #include "cinder/Stream.h" 00032 #include "cinder/Display.h" 00033 #include "cinder/DataSource.h" 00034 #include "cinder/Timer.h" 00035 #if defined( CINDER_COCOA ) 00036 #if defined( CINDER_COCOA_TOUCH ) 00037 #if defined( __OBJC__ ) 00038 #import <UIKit/UIKit.h> 00039 #import <CoreFoundation/CoreFoundation.h> 00040 #endif 00041 #else 00042 #include <ApplicationServices/ApplicationServices.h> 00043 #endif 00044 #if defined __OBJC__ 00045 @class CinderView; 00046 @class AppImplCocoaRendererQuartz; 00047 @class AppImplCocoaRendererGl; 00048 #else 00049 class AppImplCocoaRendererQuartz; 00050 class AppImplCocoaRendererGl; 00051 #endif 00052 // class CinderView; 00053 #elif defined( CINDER_MSW ) 00054 #include "cinder/msw/OutputDebugStringStream.h" 00055 #endif 00056 00057 #include <vector> 00058 00059 namespace cinder { namespace app { 00060 00061 class App { 00062 public: 00063 class Settings { 00064 public: 00065 // whether or not the app should terminate prior to launching 00066 bool isPrepared() const { return !mShouldQuit; }; 00067 00069 void setWindowSize( int aWindowSizeX, int aWindowSizeY ); 00070 00072 void setFrameRate( float aFrameRate ); 00073 00075 void enablePowerManagement( bool aPowerManagement = true ); 00076 00078 bool isFullScreen() const { return mFullScreen; } 00080 int getWindowWidth() const { return mWindowSizeX; } 00082 int getWindowHeight() const { return mWindowSizeY; } 00084 Vec2i getWindowSize() const { return Vec2i( mWindowSizeX, mWindowSizeY ); } 00086 Area getWindowBounds() const { return Area( 0, 0, mWindowSizeX, mWindowSizeY ); } 00088 void setTitle( const std::string &title ) { mTitle = title; } 00089 00091 float getFrameRate() const { return mFrameRate; } 00093 bool isResizable() const { return mResizable; } 00095 bool getPowerManagement() const { return mPowerManagement; } 00096 00097 protected: 00098 Settings(); 00099 virtual ~Settings() {} 00100 00101 bool mShouldQuit; // defaults to false, facilitates early termination 00102 int mWindowSizeX, mWindowSizeY; // default: 640x480 00103 bool mFullScreen; // window covers screen. default: false 00104 float mFrameRate; 00105 bool mResizable; // window is Resizable. default: true 00106 bool mPowerManagement; // allow screensavers or power management to hide app. default: false 00107 std::string mTitle; 00108 }; 00109 00110 00111 public: 00112 // interface 00113 App(); 00114 virtual ~App(); 00115 00117 virtual void setup() {} 00119 virtual void shutdown() {} 00120 00122 virtual void update() {} 00124 virtual void draw() {} 00125 00127 virtual void mouseDown( MouseEvent event ) {} 00129 virtual void mouseUp( MouseEvent event ) {} 00131 virtual void mouseWheel( MouseEvent event ) {} 00133 virtual void mouseMove( MouseEvent event ) {} 00135 virtual void mouseDrag( MouseEvent event ) {} 00137 virtual void keyDown( KeyEvent event ) {} 00139 virtual void keyUp( KeyEvent event ) {} 00141 virtual void resize( int width, int height ) {} 00143 virtual void fileDrop( FileDropEvent event ) {} 00144 00146 virtual void quit() = 0; 00147 00148 class Listener { 00149 public: 00150 virtual bool mouseDown( MouseEvent event ) { return false; } 00151 virtual bool mouseUp( MouseEvent event ) { return false; } 00152 virtual bool mouseWheel( MouseEvent event ) { return false; } 00153 virtual bool mouseMove( MouseEvent event ) { return false; } 00154 virtual bool mouseDrag( MouseEvent event ) { return false; } 00155 virtual bool keyDown( KeyEvent event ) { return false; } 00156 virtual bool keyUp( KeyEvent event ) { return false; } 00157 virtual bool resize( int width, int height ) { return false; } 00158 virtual bool fileDrop( FileDropEvent event ) { return false; } 00159 }; 00160 00162 void addListener( Listener *listener ); 00164 void removeListener( Listener *listener ); 00165 00166 // Accessors 00167 virtual const Settings& getSettings() const { return getSettings(); } 00168 Renderer* getRenderer() const { return mRenderer.get(); } 00169 00171 virtual int getWindowWidth() const = 0; 00173 virtual void setWindowWidth( int windowWidth ) = 0; 00175 virtual int getWindowHeight() const = 0; 00177 virtual void setWindowHeight( int windowHeight ) = 0; 00179 virtual void setWindowSize( int windowWidth, int windowHeight ) = 0; 00181 void setWindowSize( const Vec2i &size ) { setWindowSize( size.x, size.y ); } 00183 00184 Vec2f getWindowCenter() const { return Vec2f( (float)getWindowWidth(), (float)getWindowHeight() ) * 0.5f; } 00186 Vec2i getWindowSize() const { return Vec2i( getWindowWidth(), getWindowHeight() ); } 00188 float getWindowAspectRatio() const { return getWindowWidth() / (float)getWindowHeight(); } 00190 00191 Area getWindowBounds() const { return Area( 0, 0, getWindowWidth(), getWindowHeight() ); } 00193 virtual float getFrameRate() const = 0; 00195 virtual void setFrameRate( float aFrameRate ) = 0; 00197 virtual bool isFullScreen() const = 0; 00199 virtual void setFullScreen( bool aFullScreen ) = 0; 00200 00202 double getElapsedSeconds() const { return mTimer.getSeconds(); } 00204 uint32_t getElapsedFrames() const { return mFrameCount; } 00205 00206 // utilities 00207 static DataSourceRef loadResource( const std::string &macPath, int mswID, const std::string &mswType ); 00208 #if defined( CINDER_COCOA ) 00209 static DataSourcePathRef loadResource( const std::string &macPath ); 00210 std::string getResourcePath( const std::string &rsrcRelativePath ); 00211 #else 00212 static DataSourceBufferRef loadResource( int mswID, const std::string &mswType ); 00213 #endif 00214 00216 virtual std::string getAppPath() = 0; 00218 00221 std::string getOpenFilePath( const std::string &initialPath = "", std::vector<std::string> extensions = std::vector<std::string>() ); 00223 00226 std::string getSaveFilePath( const std::string &initialPath = "", std::vector<std::string> extensions = std::vector<std::string>() ); 00227 00229 std::ostream& console(); 00230 00232 Surface copyWindowSurface(); 00234 Surface copyWindowSurface( const Area &area ); 00236 void restoreWindowContext(); 00237 00238 00239 // DO NOT CALL - should be private but aren't for esoteric reasons 00241 // Internal handlers - these are called into by AppImpl's. If you are calling one of these, you have likely strayed far off the path. 00242 void privateMouseDown__( const MouseEvent &event ); 00243 void privateMouseUp__( const MouseEvent &event ); 00244 void privateMouseWheel__( const MouseEvent &event ); 00245 void privateMouseMove__( const MouseEvent &event ); 00246 void privateMouseDrag__( const MouseEvent &event ); 00247 void privateKeyDown__( const KeyEvent &event ); 00248 void privateKeyUp__( const KeyEvent &event ); 00249 void privateFileDrop__( const FileDropEvent &event ); 00250 00251 virtual void privateSetup__(); 00252 virtual void privateResize__( int width, int height ); 00253 virtual void privateUpdate__(); 00254 virtual void privateDraw__(); 00255 virtual void privateShutdown__(); 00257 00258 #if defined( CINDER_MSW ) 00259 // Not all Windows target types receive paint events, and the AppImplMswRenderer* needs to know that. 00260 virtual bool getsWindowsPaintEvents() = 0; 00261 #endif 00262 00263 virtual bool receivesEvents() const { return true; } 00264 00266 static App* get() { return sInstance; } 00267 00268 protected: 00270 // These are called by application instantation macros and are only used in the launch process 00271 static void prepareLaunch(); 00272 static void executeLaunch( App *app, class Renderer *renderer, const char *title, int argc, char * const argv[] ); 00273 static void cleanupLaunch(); 00274 00275 virtual void launch( const char *title, int argc, char * const argv[] ) = 0; 00277 00278 private: 00279 00280 #if defined( CINDER_MSW ) 00281 friend class AppImplMsw; 00282 shared_ptr<cinder::msw::dostream> mOutputStream; 00283 #else 00284 static void *sAutoReleasePool; 00285 #endif 00286 00287 Timer mTimer; 00288 uint32_t mFrameCount; 00289 00290 shared_ptr<Renderer> mRenderer; 00291 std::vector<Listener*> mListeners; 00292 00293 static App* sInstance; 00294 }; 00295 00300 00301 inline int getWindowWidth() { return App::get()->getWindowWidth(); } 00303 inline void setWindowWidth( int windowWidth ) { App::get()->setWindowWidth( windowWidth ); } 00305 inline int getWindowHeight() { return App::get()->getWindowHeight(); } 00307 inline void setWindowHeight( int windowHeight ) { App::get()->setWindowHeight( windowHeight ); } 00309 inline void setWindowSize( int windowWidth, int windowHeight ) { App::get()->setWindowSize( windowWidth, windowHeight ); } 00311 00312 inline Vec2f getWindowCenter() { return App::get()->getWindowCenter(); } 00314 inline Vec2i getWindowSize() { return App::get()->getWindowSize(); } 00316 inline float getWindowAspectRatio() { return App::get()->getWindowAspectRatio(); } 00318 00319 inline Area getWindowBounds() { return App::get()->getWindowBounds(); } 00321 inline float getFrameRate() { return App::get()->getFrameRate(); } 00323 inline void setFrameRate( float frameRate ) { App::get()->setFrameRate( frameRate ); } 00325 inline bool isFullScreen() { return App::get()->isFullScreen(); } 00327 inline void setFullScreen( bool fullScreen = true ) { App::get()->setFullScreen( fullScreen ); } 00328 00330 inline double getElapsedSeconds() { return App::get()->getElapsedSeconds(); } 00332 inline uint32_t getElapsedFrames() { return App::get()->getElapsedFrames(); } 00333 00334 inline DataSourceRef loadResource( const std::string &macPath, int mswID, const std::string &mswType ) { return App::get()->loadResource( macPath, mswID, mswType ); } 00335 #if defined( CINDER_COCOA ) 00336 inline DataSourcePathRef loadResource( const std::string &macPath ) { return App::get()->loadResource( macPath ); } 00337 inline std::string getResourcePath( const std::string &rsrcRelativePath ) { return App::get()->getResourcePath( rsrcRelativePath ); } 00338 #else 00339 inline DataSourceBufferRef loadResource( int mswID, const std::string &mswType ) { return App::get()->loadResource( mswID, mswType ); } 00340 #endif 00341 00343 inline std::string getAppPath() { return App::get()->getAppPath(); } 00345 00348 inline std::string getOpenFilePath( const std::string &initialPath = "", std::vector<std::string> extensions = std::vector<std::string>() ) { return App::get()->getOpenFilePath( initialPath, extensions ); } 00350 00353 inline std::string getSaveFilePath( const std::string &initialPath = "", std::vector<std::string> extensions = std::vector<std::string>() ) { return App::get()->getSaveFilePath( initialPath, extensions ); } 00354 00356 00359 inline std::ostream& console() { return App::get()->console(); } 00360 00362 inline Surface copyWindowSurface() { return App::get()->copyWindowSurface(); } 00364 inline Surface copyWindowSurface( const Area &area ) { return App::get()->copyWindowSurface( area ); } 00366 inline void restoreWindowContext() { return App::get()->restoreWindowContext(); } 00367 00368 #if defined( CINDER_COCOA ) 00370 inline ::CGContextRef createWindowCgContext() { return ((Renderer2d*)(App::get()->getRenderer()))->getCgContext(); } 00371 #endif 00372 00374 00375 } } // namespace cinder::app