00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #if !defined SOGLCONTEXT_H
00024 #define SOGLCONTEXT_H
00025
00026 #include <Inventor/devices/SoDeviceContext.h>
00027 #include <Inventor/devices/SoGLFormat.h>
00028 #include <Inventor/STL/vector>
00029 #include <Inventor/STL/list>
00030 #include <Inventor/STL/map>
00031 #include <Inventor/helpers/SbGlContextHelper.h>
00032 #include <Inventor/threads/SbThreadSpinlock.h>
00033 #include <Inventor/errors/SoError.h>
00034 #include <Inventor/image/SbRasterImage.h>
00035 #include <Inventor/threads/SbThreadLocalStorage.h>
00036
00037
00038 #include <Inventor/SbPList.h>
00039 #include <Inventor/STL/stack>
00040
00041 #include <Inventor/helpers/SbGPUCapabilities.h>
00042
00043 #if defined(_WIN32)
00044 #include <windows.h>
00045 #endif
00046
00047
00048 #ifdef _MSC_VER
00049 #pragma warning( push )
00050 #pragma warning(disable:4251)
00051 #endif
00052
00053 class SbThreadMutex;
00054 class FunctionRedirector;
00055
00191 class SoGLContext : public SoDeviceContext
00192 {
00193 public:
00194
00199 enum SharedGroupPolicy
00200 {
00202 DISABLED,
00203
00211 CONSERVATIVE,
00212
00219 AGGRESSIVE
00220 };
00221
00231 SoGLContext( bool shared );
00232
00244 SoGLContext( SbGlContextHelper::Display dpy,
00245 SbGlContextHelper::VisualInfo vis,
00246 SbGlContextHelper::Drawable drawable,
00247 SbGlContextHelper::GLContext ctx );
00248
00258 SoGLContext( const SoGLFormat& format, SbGlContextHelper::GLContext ctx, SbGlContextHelper::Drawable drawable = 0 );
00259
00267 SoGLContext( const SoGLFormat& format, SbGlContextHelper::Drawable drawable = 0 );
00268
00289 SoGLContext( SbGlContextHelper::Display dpy,
00290 SbGlContextHelper::VisualInfo vis,
00291 SbGlContextHelper::Drawable drawable,
00292 bool shared = true );
00293
00300 SoGLContext( SoGLContext* context, bool shared );
00301
00310 SoGLContext( SoGLContext* context, const SoGLFormat& format, SbGlContextHelper::Drawable drawable = 0 );
00311
00316 virtual void bind();
00317
00318
00323 virtual bool tryBind();
00324
00328 virtual void unbind();
00329
00335 bool isSharedWith( const SoGLContext* context ) const;
00336
00342 bool isValid() const;
00343
00349 void invalidate();
00350
00357 int getId() const;
00358
00368 virtual bool isCompatible( SoDeviceContext* context ) const;
00369
00374 virtual bool isCurrent() const;
00375
00395 static SoGLContext* getCurrent( bool checkGLState = false );
00396
00402 const SbGlContextHelper::GLContext& getGLContext() const;
00403
00409 static SoGLContext* findGLContext( SbGlContextHelper::GLContext );
00410
00416 #if defined(_WIN32)
00417 typedef int SharedGroupDescription;
00418 #else
00419 typedef SbGlContextHelper::Display SharedGroupDescription;
00420 #endif
00421 static SoGLContext* findSharedContext( SharedGroupDescription );
00422
00428 const SbGlContextHelper::Display& getDisplay() const;
00429
00435 const SbGlContextHelper::VisualInfo& getVisualInfo() const;
00436
00443 const SoGLFormat& getFormat() const;
00444
00451 static SoGLContext* getContextFromId( int id );
00452
00459 static SoGLContext* getContextFromSharedId( int sharedIdGroup );
00460
00465 bool isValidForCurrent() const;
00466
00470 void assertContext() const;
00471
00472 #if 1 SoDEPRECATED
00481 bool swapBuffers( int plane );
00482 #endif
00487 bool swapBuffers();
00488
00497 SbStringList getSupportedExtensions();
00498
00500 static SharedGroupPolicy getSharedGroupPolicy();
00501
00502 #if 1 SoDEPRECATED
00505 void applySharedGroupPolicy();
00506 #endif
00514 void setNoGLContextDelete() { m_noOGLContextDelete = true; }
00515
00520 const SbGPUCapabilities& getContextGraphicsCapabilities();
00521
00526 static const SbGPUCapabilities& getGraphicsCapabilities();
00527
00528 private:
00529
00530 SB_THREAD_TLS_HEADER();
00531
00532 static void initClass();
00533 static void exitClass();
00534
00536 enum GPUVendorType
00537 {
00538 GPU_TYPE_NOT_INITIALIZED = -1,
00539 GPU_NVIDIA = 0,
00540 GPU_ATI = 1,
00541 GPU_INTEL = 2,
00542 GPU_FIREPRO_MAC = 3
00543 };
00544
00545
00546 static GPUVendorType getGPUVendorType();
00547
00559 static SoGLContext* getActualCurrentContext( SoGLContext* supposedContext );
00560
00562 static void lockListsMutex();
00563
00565 static void unlockListsMutex();
00566
00570 void setUserData( void* data )
00571 { m_userData = data; }
00572
00574 void* getUserData() const
00575 { return m_userData; }
00576
00579 bool setSharedWith( SoGLContext* sharedContext );
00580
00581
00582 void forceDisplay( const SbGlContextHelper::Display& display );
00583
00584
00585 void forceDrawable( const SbGlContextHelper::Drawable& drawable );
00586
00587
00588
00589 void forceContext( const SbGlContextHelper::GLContext& context )
00590 { m_context = context; }
00591
00592
00593 inline void forceNoGLContextDelete(bool flag) { m_noOGLContextDelete = flag; }
00594
00595
00596 const SbGlContextHelper::Drawable& getDrawable() const
00597 { return m_drawable;}
00598
00599
00600 static void* glewGetCurrentContextIV(const bool printError=false)
00601 {
00602 SoGLContext* ctx = SoGLContext::getCurrent(true);
00603
00604 if ( ctx )
00605 return ctx->glewGetContextIV();
00606 else
00607 {
00608 if (printError)
00609 SoError::post("SoGLContext : Trying to access a NULL context");
00610 return glewNullContext();
00611 }
00612 };
00613
00614 # if defined(_WIN32)
00615 static void* wglewGetCurrentContextIV(const bool printError=false)
00616 {
00617 SoGLContext* ctx = SoGLContext::getCurrent(true);
00618
00619 if ( ctx )
00620 return ctx->wglewGetContextIV();
00621 else
00622 {
00623 if (printError)
00624 SoError::post("SoGLContext : Trying to access a NULL context");
00625 return NULL;
00626 }
00627 };
00628 # elif !defined(__APPLE__) || defined(GLEW_APPLE_GLX)
00629 static void* glxewGetCurrentContextIV(const bool printError=false)
00630 {
00631 SoGLContext* ctx = SoGLContext::getCurrent(true);
00632
00633 if ( ctx )
00634 return ctx->glxewGetContextIV();
00635 else
00636 {
00637 if (printError)
00638 SoError::post("SoGLContext : Trying to access a NULL context");
00639 return NULL;
00640 }
00641 };
00642 # endif // _WIN32
00643
00644
00645 struct GLEWContextStruct* glewGetContextIV() const
00646 { return m_glewContext; }
00647
00648 # if defined(_WIN32)
00649 void* wglewGetContextIV() const
00650 { return m_wglewContext; }
00651
00652 # elif !defined(__APPLE__) || defined(GLEW_APPLE_GLX)
00653 void* glxewGetContextIV() const
00654 { return m_glxewContext; }
00655
00656 # endif // _WIN32
00657
00658 bool isGLEWInitialized() { return m_glewInit; }
00659 bool initGLEW();
00660 void cleanGLEWContext();
00661
00662 virtual SbString getInfos();
00663
00664
00665 SbString getDeviceName() const;
00666
00670 void printInformation();
00671
00675 static void printCurrentContextInformation();
00676
00680 static void printContextsInformation();
00681
00687 static void invalidateDrawable(SbGlContextHelper::Drawable drawable);
00688
00694 static void invalidateDisplay(SbGlContextHelper::Display display);
00695
00714 bool setVSyncEnabled(bool on);
00715
00721 bool isVSyncEnabled();
00722
00724 bool isBinded();
00725
00726 private:
00730 virtual ~SoGLContext();
00731
00732 SoINTERNAL private:
00733
00734
00735
00736
00737 void removeSharedObjects();
00738
00739 private:
00740
00741
00742 static struct GLEWContextStruct* glewNullContext();
00743
00744 virtual bool setSharedWith( SoDeviceContext* sourceCtx );
00745
00751 void setSwapInterval(int interval);
00752
00753
00754 struct MTstruct
00755 {
00756 typedef std::vector<SoGLContext*> ContextVec;
00758 ContextVec* m_bindedContexts;
00759 };
00760
00761 bool initContext( SoGLContext* sourceContext, bool shared );
00762 void initGLEWContext();
00763 void preInitContext();
00764 bool postInitContext();
00765
00766 void checkContextParameters( const char* function );
00767
00768 typedef std::list< SoGLContext* > SoGLContextList;
00769
00771 static SoGLContextList s_contexts;
00772
00774 static int s_firstAvailableId;
00775
00777 static SbThreadSpinlock s_contextsMutex;
00778
00780 int m_id;
00781
00782 SbGlContextHelper::GLContext m_context;
00783 SbGlContextHelper::Drawable m_drawable;
00784
00785 SoGLFormat m_format;
00786
00787 void* m_userData;
00788
00789 static GPUVendorType m_GpuVendorType;
00790
00791
00792 struct GLEWContextStruct* m_glewContext;
00793
00794
00795 static struct GLEWContextStruct* s_nullGlewContext;
00796
00797 # if defined(_WIN32)
00798 struct WGLEWContextStruct* m_wglewContext;
00799 # elif !defined(__APPLE__) || defined(GLEW_APPLE_GLX)
00800 void* m_glxewContext;
00801 # endif // _WIN32
00802
00803 bool m_glewInit;
00804 bool m_noOGLContextDelete;
00805
00806 bool m_drawableIsValid;
00807 bool m_displayIsValid;
00808
00809 static int s_checkContext;
00810
00811 static int s_oivCompatibilityMode;
00812
00814 static SharedGroupPolicy s_sharedGroupPolicy;
00815
00816
00817 bool m_sharedObjectsRemoved;
00818
00819 static SoGLContext* findSoGLContext(SbGlContextHelper::GLContext ctx);
00820 void pushInBindedList();
00821 static void updateBindedList();
00822 static void updateBindedList(SbGlContextHelper::Display display, SbGlContextHelper::Drawable drawable, SbGlContextHelper::GLContext context);
00823 static SoGLContext* popBindedList();
00824
00825 bool m_thirdPartyContext;
00826 bool m_isBeingDestroyed;
00827 SbGPUCapabilities* m_graphicCapabilities;
00828 static FunctionRedirector s_deleteContextRedirector;
00829
00830 static bool callOriginalDeleteContext(SbGlContextHelper::Display display, SbGlContextHelper::GLContext context, int& returnValue);
00831 static int commonDeleteContextHook(SbGlContextHelper::Display dpy, SbGlContextHelper::GLContext ctx);
00832
00833 #if defined(WIN32)
00834 static int _stdcall deleteContextHook(SbGlContextHelper::GLContext context);
00835 #elif defined(__APPLE__)
00836 static int deleteContextHook(SbGlContextHelper::GLContext context);
00837 #else
00838 static int deleteContextHook(SbGlContextHelper::Display dpy, SbGlContextHelper::GLContext ctx);
00839 #endif
00840
00841 static MTstruct::ContextVec& getBindedContextsList();
00842 };
00843
00844 #ifdef _MSC_VER
00845 #pragma warning( pop )
00846 #endif
00847
00848
00849 #endif //SOGLCONTEXT_H
00850
00851