First implementation of EGL/Angle support. Tested with GLES3 on DirectX11 platform.
Pixelbuffer currently not supported.
This commit is contained in:
parent
bd50af117b
commit
fbc31d9987
4
.gitignore
vendored
4
.gitignore
vendored
@ -99,3 +99,7 @@ _CPack_Packages/
|
||||
#packages
|
||||
*.tar.gz
|
||||
*.zip
|
||||
|
||||
#individual build files
|
||||
config.yaml
|
||||
_build
|
||||
|
@ -276,8 +276,25 @@ IF(APPLE)
|
||||
SET(OSG_COMPILE_FRAMEWORKS_INSTALL_NAME_DIR "@executable_path/../Frameworks" CACHE STRING "install name dir for compiled frameworks")
|
||||
ELSE()
|
||||
# Non-Apple: Find OpenGL
|
||||
FIND_PACKAGE(OpenGL)
|
||||
|
||||
# Support EGL on Windows
|
||||
IF(OSG_WINDOWING_SYSTEM STREQUAL "Win32" AND (OSG_GLES2_AVAILABLE OR OSG_GLES3_AVAILABLE ) )
|
||||
FIND_PACKAGE(EGL)
|
||||
|
||||
set(OSG_USE_EGL ON)
|
||||
|
||||
IF(OSG_GLES3_AVAILABLE)
|
||||
FIND_PATH(OPENGL_INCLUDE_DIR GLES3/gl3.h)
|
||||
ENDIF()
|
||||
IF(OSG_GLES2_AVAILABLE)
|
||||
FIND_PATH(OPENGL_INCLUDE_DIR GLES2/gl2.h)
|
||||
ENDIF()
|
||||
FIND_LIBRARY(OPENGL_gl_LIBRARY "libGLESv2.dll")
|
||||
ELSE()
|
||||
# Non-Apple: Find OpenGL
|
||||
FIND_PACKAGE(OpenGL)
|
||||
ENDIF()
|
||||
|
||||
ENDIF()
|
||||
ENDIF()
|
||||
|
||||
|
@ -10,24 +10,26 @@
|
||||
|
||||
|
||||
FIND_PATH( EGL_INCLUDE_DIR
|
||||
NAMES EGL/egl.h
|
||||
HINTS ENV EGL_DIR
|
||||
NAMES egl.h
|
||||
PATH_SUFFIXES EGL
|
||||
PATHS ENV EGL_DIR
|
||||
)
|
||||
|
||||
FIND_LIBRARY(EGL_LIBRARY
|
||||
NAMES EGL
|
||||
HINTS ENV EGL_DIR
|
||||
PATH_SUFFIXES lib
|
||||
NAMES EGL libEGL.dll.lib
|
||||
PATHS ENV EGL_DIR
|
||||
)
|
||||
|
||||
# handle the QUIETLY and REQUIRED arguments and set
|
||||
# EGL_FOUND to TRUE as appropriate
|
||||
INCLUDE( FindPackageHandleStandardArgs )
|
||||
|
||||
FIND_PACKAGE_HANDLE_STANDARD_ARGS(EGL
|
||||
REQUIRED_VARS EGL_LIBRARY EGL_INCLUDE_DIR)
|
||||
|
||||
MARK_AS_ADVANCED(
|
||||
EGL_INCLUDE_DIR
|
||||
find_package_handle_standard_args(EGL
|
||||
FOUND_VAR
|
||||
EGL_FOUND
|
||||
REQUIRED_VARS
|
||||
EGL_LIBRARY
|
||||
EGL_INCLUDE_DIR
|
||||
FAIL_MESSAGE
|
||||
"Could NOT find EGL, try to set the path to EGL root folder in the system variable EGL_DIR"
|
||||
)
|
||||
|
@ -180,12 +180,17 @@ IF(DYNAMIC_OPENSCENEGRAPH)
|
||||
ADD_SUBDIRECTORY(osgfpdepth)
|
||||
ENDIF()
|
||||
|
||||
IF(NOT OSG_GLES1_AVAILABLE AND NOT OSG_GLES2_AVAILABLE AND NOT OSG_GL3_AVAILABLE)
|
||||
IF(NOT OSG_GLES1_AVAILABLE AND NOT OSG_GLES2_AVAILABLE AND NOT OSG_GLES3_AVAILABLE AND NOT OSG_GL3_AVAILABLE)
|
||||
ADD_SUBDIRECTORY(osgscreencapture)
|
||||
ADD_SUBDIRECTORY(osgmotionblur)
|
||||
ADD_SUBDIRECTORY(osgteapot)
|
||||
ENDIF()
|
||||
|
||||
# GLES3 example
|
||||
IF(EGL_FOUND AND OSG_GLES3_AVAILABLE)
|
||||
ADD_SUBDIRECTORY(osgsimpleGLES3)
|
||||
ENDIF()
|
||||
|
||||
ADD_SUBDIRECTORY(osgphotoalbum)
|
||||
ADD_SUBDIRECTORY(osgtessellate)
|
||||
ADD_SUBDIRECTORY(osgtessellationshaders)
|
||||
|
4
examples/osgsimpleGLES3/CMakeLists.txt
Normal file
4
examples/osgsimpleGLES3/CMakeLists.txt
Normal file
@ -0,0 +1,4 @@
|
||||
SET(TARGET_SRC osgsimplegles3.cpp )
|
||||
|
||||
#### end var setup ###
|
||||
SETUP_EXAMPLE(osgsimpleGLES3)
|
103
examples/osgsimpleGLES3/osgsimplegles3.cpp
Normal file
103
examples/osgsimpleGLES3/osgsimplegles3.cpp
Normal file
@ -0,0 +1,103 @@
|
||||
// This is public domain software and comes with
|
||||
// absolutely no warranty. Use of public domain software
|
||||
// may vary between counties, but in general you are free
|
||||
// to use and distribute this software for any purpose.
|
||||
|
||||
|
||||
// Example: OSG using EGL.
|
||||
// The comment block at the end of the source describes building OSG
|
||||
// for use with OpenGL 3.x.
|
||||
|
||||
#include <osgViewer/Viewer>
|
||||
#include <osg/GraphicsContext>
|
||||
#include <osg/Camera>
|
||||
#include <osg/Viewport>
|
||||
#include <osg/StateSet>
|
||||
#include <osg/Program>
|
||||
#include <osg/Shader>
|
||||
|
||||
osg::Geode* makeGeometry(float v)
|
||||
{
|
||||
osg::Geode* geode = new osg::Geode();
|
||||
osg::Geometry* geom = new osg::Geometry();
|
||||
osg::Vec3Array* verts = new osg::Vec3Array();
|
||||
verts->push_back(osg::Vec3(v - 1, 0, 0));
|
||||
verts->push_back(osg::Vec3(v + 1, 0, 0));
|
||||
verts->push_back(osg::Vec3(v, 0, 2));
|
||||
geom->setVertexArray(verts);
|
||||
geom->setUseVertexBufferObjects(true);
|
||||
osg::Vec4Array* colors = new osg::Vec4Array(osg::Array::BIND_OVERALL);
|
||||
colors->push_back(osg::Vec4(0, 0, 1, 1));
|
||||
geom->setColorArray(colors);
|
||||
geom->addPrimitiveSet(new osg::DrawArrays(GL_TRIANGLES, 0, 3));
|
||||
geode->addDrawable(geom);
|
||||
return geode;
|
||||
}
|
||||
|
||||
int main( int argc, char** argv )
|
||||
{
|
||||
osg::ArgumentParser arguments( &argc, argv );
|
||||
osgViewer::Viewer viewer(arguments);
|
||||
viewer.setThreadingModel(osgViewer::Viewer::SingleThreaded);
|
||||
|
||||
osg::Geode* geode = makeGeometry(1.0);
|
||||
|
||||
const std::string vertexSource =
|
||||
"#version 300 es\n"
|
||||
"void main() { \n"
|
||||
" gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; \n"
|
||||
"} \n";
|
||||
|
||||
osg::Shader* vShader = new osg::Shader(osg::Shader::VERTEX, vertexSource);
|
||||
|
||||
const std::string fragmentSource =
|
||||
"#version 300 es\n"
|
||||
"precision mediump float;\n"
|
||||
"out vec4 color;\n"
|
||||
"void main() { \n"
|
||||
" color = vec4(0.5, 0.3, 0.3, 1.0);\n"
|
||||
"} \n";
|
||||
|
||||
osg::Shader* fShader = new osg::Shader(osg::Shader::FRAGMENT, fragmentSource);
|
||||
|
||||
osg::Program* program = new osg::Program;
|
||||
program->addShader(vShader);
|
||||
program->addShader(fShader);
|
||||
geode->getOrCreateStateSet()->setAttributeAndModes(program, osg::StateAttribute::ON | osg::StateAttribute::PROTECTED);
|
||||
|
||||
osg::Group* root = new osg::Group();
|
||||
root->addChild(geode);
|
||||
|
||||
#if 0
|
||||
// Create a Camera that uses the above OpenGL context.
|
||||
osg::Camera* cam = viewer.getCamera();
|
||||
// Must set perspective projection for fovy and aspect.
|
||||
cam->setProjectionMatrix( osg::Matrix::perspective( 30., (double)width/(double)height, 1., 100. ) );
|
||||
// Unlike OpenGL, OSG viewport does *not* default to window dimensions.
|
||||
cam->setViewport( new osg::Viewport( 0, 0, width, height ) );
|
||||
#endif
|
||||
viewer.setSceneData( root );
|
||||
|
||||
return( viewer.run() );
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
Building OSG for OpenGLES3
|
||||
|
||||
OSG currently support GLES3 on Windows. This comment block describes the
|
||||
necessary configuration steps.
|
||||
|
||||
* Add Google Angle libraries and include folder to CMake
|
||||
CMake use FindEGL.cmake to find this. The library name of Google-Angle for Windows is "libEGL.dll.lib"
|
||||
|
||||
* Enable the following CMake variable:
|
||||
OSG_GLES3_AVAILABLE
|
||||
|
||||
* Disable the following CMake variables:
|
||||
OSG_GL1_AVAILABLE
|
||||
OSG_GL2_AVAILABLE
|
||||
OSG_GLES1_AVAILABLE
|
||||
OSG_GLES2_AVAILABLE
|
||||
|
||||
*/
|
@ -29,19 +29,67 @@
|
||||
#define _WIN32_WINNT 0x0500 // Windows NT
|
||||
#endif
|
||||
#include <windows.h>
|
||||
#if defined(OSG_USE_EGL)
|
||||
#include "EGL/egl.h"
|
||||
#endif
|
||||
|
||||
namespace osgViewer
|
||||
{
|
||||
|
||||
/** Class to encapsulate platform-specific OpenGL context handle variables.
|
||||
/** Class to encapsulate platform-specific OpenGL context handle variables.
|
||||
* Derived osg::GraphicsContext classes can inherit from this class to
|
||||
* share OpenGL resources.*/
|
||||
|
||||
class OSGVIEWER_EXPORT GraphicsHandleWin32
|
||||
{
|
||||
#if defined(OSG_USE_EGL)
|
||||
class OSGVIEWER_EXPORT GraphicsHandleWin32
|
||||
{
|
||||
public:
|
||||
struct EGLContextInfo {
|
||||
EGLContextInfo() { clear(); }
|
||||
EGLContextInfo(EGLContext _eglContext, EGLDisplay _eglDisplay, EGLSurface _eglSurface) : eglContext(_eglContext), eglDisplay(_eglDisplay), eglSurface(_eglSurface) {}
|
||||
EGLContextInfo(const EGLContextInfo& o) : eglContext(o.eglContext), eglDisplay(o.eglDisplay), eglSurface(o.eglSurface) {}
|
||||
EGLContextInfo& operator=(const EGLContextInfo& o) { eglContext = o.eglContext; eglDisplay = o.eglDisplay; eglSurface = o.eglSurface; return *this; }
|
||||
void clear() { eglContext = EGL_NO_CONTEXT; eglDisplay = EGL_NO_DISPLAY; eglSurface = EGL_NO_SURFACE; }
|
||||
bool isEmpty() { return eglContext == 0 && eglDisplay == 0; }
|
||||
EGLContext eglContext;
|
||||
EGLDisplay eglDisplay;
|
||||
EGLSurface eglSurface;
|
||||
};
|
||||
|
||||
GraphicsHandleWin32()
|
||||
: _hwnd(0), _hdc(0) {}
|
||||
|
||||
/** Set native window.*/
|
||||
inline void setHWND(HWND hwnd) { _hwnd = hwnd; }
|
||||
|
||||
/** Get native window.*/
|
||||
inline HWND getHWND() const { return _hwnd; }
|
||||
|
||||
/** Set device context.*/
|
||||
inline void setHDC(HDC hdc) { _hdc = hdc; }
|
||||
|
||||
/** Get device context.*/
|
||||
inline HDC getHDC() const { return _hdc; }
|
||||
|
||||
/** Set native EGL graphics context.*/
|
||||
inline void setEGLContext(const EGLContextInfo& eglContextInfo) { _eglContextInfo = eglContextInfo; }
|
||||
|
||||
/** Get native EGL graphics context.*/
|
||||
inline const EGLContextInfo& getEGLContext() const { return _eglContextInfo; }
|
||||
|
||||
protected:
|
||||
|
||||
HWND _hwnd;
|
||||
HDC _hdc;
|
||||
EGLContextInfo _eglContextInfo;
|
||||
};
|
||||
|
||||
#else
|
||||
class OSGVIEWER_EXPORT GraphicsHandleWin32
|
||||
{
|
||||
public:
|
||||
|
||||
GraphicsHandleWin32():
|
||||
GraphicsHandleWin32() :
|
||||
_hwnd(0),
|
||||
_hdc(0),
|
||||
_hglrc(0) {}
|
||||
@ -70,11 +118,10 @@ class OSGVIEWER_EXPORT GraphicsHandleWin32
|
||||
HDC _hdc;
|
||||
HGLRC _hglrc;
|
||||
|
||||
};
|
||||
|
||||
};
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
// Definitions required to create an OpenGL pixel format, from the WGL_ARB_pixel_format specification document.
|
||||
// See http://www.opengl.org/registry/specs/ARB/wgl_pixel_format.txt
|
||||
|
||||
|
@ -116,7 +116,11 @@ class OSGVIEWER_EXPORT GraphicsWindowWin32 : public osgViewer::GraphicsWindow, p
|
||||
virtual bool registerWindowProcedure();
|
||||
virtual bool unregisterWindowProcedure();
|
||||
|
||||
#ifdef OSG_USE_EGL
|
||||
virtual const GraphicsHandleWin32::EGLContextInfo createContextImplementation();
|
||||
#else
|
||||
virtual HGLRC createContextImplementation();
|
||||
#endif
|
||||
virtual bool createWindow();
|
||||
virtual bool setWindow( HWND handle );
|
||||
|
||||
|
@ -24,7 +24,8 @@
|
||||
|
||||
namespace osgViewer
|
||||
{
|
||||
|
||||
#if defined(OSG_USE_EGL)
|
||||
#else
|
||||
class OSGVIEWER_EXPORT PixelBufferWin32 : public osg::GraphicsContext, public osgViewer::GraphicsHandleWin32
|
||||
{
|
||||
public:
|
||||
@ -69,7 +70,7 @@ class OSGVIEWER_EXPORT PixelBufferWin32 : public osg::GraphicsContext, public os
|
||||
bool _realized;
|
||||
int _boundBuffer;
|
||||
};
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -344,7 +344,7 @@ OSG_INIT_SINGLETON_PROXY(GLExtensionDisableStringInitializationProxy, osg::getGL
|
||||
|
||||
#elif defined(WIN32)
|
||||
|
||||
#if defined(OSG_GLES2_AVAILABLE)
|
||||
#if defined(OSG_GLES2_AVAILABLE) || defined(OSG_GLES3_AVAILABLE)
|
||||
static HMODULE hmodule = GetModuleHandle(TEXT("libGLESv2.dll"));
|
||||
return convertPointerType<void*, PROC>(GetProcAddress(hmodule, funcName));
|
||||
#elif defined(OSG_GLES1_AVAILABLE)
|
||||
|
@ -5,6 +5,11 @@ ELSE()
|
||||
ADD_DEFINITIONS(-DOSG_LIBRARY_STATIC)
|
||||
ENDIF()
|
||||
|
||||
IF(OSG_USE_EGL)
|
||||
ADD_DEFINITIONS(-DOSG_USE_EGL)
|
||||
ENDIF()
|
||||
|
||||
|
||||
SET(LIB_NAME osgViewer)
|
||||
|
||||
|
||||
|
@ -30,6 +30,11 @@
|
||||
#include <sstream>
|
||||
#include <windowsx.h>
|
||||
|
||||
#if defined(OSG_USE_EGL)
|
||||
#define EGL_EGLEXT_PROTOTYPES
|
||||
#include <EGL/eglext.h>
|
||||
#endif
|
||||
|
||||
#define MOUSEEVENTF_FROMTOUCH 0xFF515700
|
||||
|
||||
// _MSC_VER 1500: VS 2008
|
||||
@ -177,11 +182,50 @@ namespace osgViewer
|
||||
|
||||
static osg::ApplicationUsageProxy GraphicsWindowWin32_e0(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_WIN32_NV_MULTIMON_MULTITHREAD_WORKAROUND on/off","Enable/disable duplicate makeCurrentContext call used as workaround for WinXP/NVidia/MultiView/MulitThread isues (pre 178.13 drivers).");
|
||||
|
||||
//
|
||||
// Utility class to specify the visual attributes for wglChoosePixelFormatARB() function
|
||||
//
|
||||
|
||||
template <typename T> class XGLAttributes
|
||||
{
|
||||
public:
|
||||
|
||||
XGLAttributes() {}
|
||||
~XGLAttributes() {}
|
||||
|
||||
void begin() { m_parameters.clear(); }
|
||||
void set(const T& id, const T& value) { add(id); add(value); }
|
||||
void enable(const T& id) { add(id); add(true); }
|
||||
void disable(const T& id) { add(id); add(false); }
|
||||
#if defined(OSG_USE_EGL)
|
||||
void end() { add(EGL_NONE); }
|
||||
#else
|
||||
void end() { add(0); }
|
||||
#endif
|
||||
|
||||
const T* get() const { return &m_parameters.front(); }
|
||||
|
||||
protected:
|
||||
|
||||
void add(const T& t) { m_parameters.push_back(t); }
|
||||
|
||||
std::vector<T> m_parameters; // parameters added
|
||||
|
||||
private:
|
||||
|
||||
// No implementation for these
|
||||
XGLAttributes(const XGLAttributes&);
|
||||
XGLAttributes& operator=(const XGLAttributes&);
|
||||
};
|
||||
|
||||
typedef XGLAttributes<int> XGLIntegerAttributes;
|
||||
typedef XGLAttributes<float> XGLFloatAttributes;
|
||||
|
||||
#if !defined(OSG_USE_EGL)
|
||||
//
|
||||
// Defines from the WGL_ARB_pixel_format specification document
|
||||
// See http://www.opengl.org/registry/specs/ARB/wgl_pixel_format.txt
|
||||
//
|
||||
|
||||
#define WGL_NUMBER_PIXEL_FORMATS_ARB 0x2000
|
||||
#define WGL_DRAW_TO_WINDOW_ARB 0x2001
|
||||
#define WGL_DRAW_TO_BITMAP_ARB 0x2002
|
||||
@ -265,41 +309,15 @@ typedef HGLRC (WINAPI * PFNWGLCREATECONTEXTATTRIBSARBPROC) (HDC hDC, HGLRC hShar
|
||||
//
|
||||
|
||||
typedef bool (WINAPI * WGLChoosePixelFormatARB) ( HDC, const int *, const float *, unsigned int, int *, unsigned int * );
|
||||
|
||||
//
|
||||
// Utility class to specify the visual attributes for wglChoosePixelFormatARB() function
|
||||
//
|
||||
|
||||
template <typename T> class WGLAttributes
|
||||
{
|
||||
public:
|
||||
|
||||
WGLAttributes() {}
|
||||
~WGLAttributes() {}
|
||||
|
||||
void begin() { m_parameters.clear(); }
|
||||
void set( const T& id, const T& value ) { add(id); add(value); }
|
||||
void enable( const T& id ) { add(id); add(true); }
|
||||
void disable( const T& id ) { add(id); add(false); }
|
||||
void end() { add(0); }
|
||||
|
||||
const T* get() const { return &m_parameters.front(); }
|
||||
|
||||
protected:
|
||||
|
||||
void add( const T& t ) { m_parameters.push_back(t); }
|
||||
|
||||
std::vector<T> m_parameters; // parameters added
|
||||
|
||||
private:
|
||||
|
||||
// No implementation for these
|
||||
WGLAttributes( const WGLAttributes& );
|
||||
WGLAttributes& operator=( const WGLAttributes& );
|
||||
};
|
||||
|
||||
typedef WGLAttributes<int> WGLIntegerAttributes;
|
||||
typedef WGLAttributes<float> WGLFloatAttributes;
|
||||
#else
|
||||
#if defined(OSG_GLES3_AVAILABLE)
|
||||
EGLint eglOpenglBit = EGL_OPENGL_ES3_BIT, eglContextClientVersion = 3;
|
||||
#endif
|
||||
#if defined(OSG_GLES2_AVAILABLE)
|
||||
EGLint eglOpenglBit = 0, eglContextClientVersion = 2;
|
||||
#endif
|
||||
EGLenum eglApi = EGL_OPENGL_ES_API;
|
||||
#endif
|
||||
|
||||
//
|
||||
// Class responsible for interfacing with the Win32 Window Manager
|
||||
@ -325,7 +343,73 @@ class Win32WindowingSystem : public osg::GraphicsContext::WindowingSystemInterfa
|
||||
{
|
||||
public:
|
||||
|
||||
// A class representing an OpenGL rendering context
|
||||
// A class representing an OpenGL rendering context for WGL
|
||||
#if defined(OSG_USE_EGL)
|
||||
class OpenGLContext
|
||||
{
|
||||
public:
|
||||
|
||||
OpenGLContext() :
|
||||
_hwnd(0),
|
||||
_hdc(0),
|
||||
_eglConfig(0)
|
||||
{}
|
||||
|
||||
OpenGLContext(HWND hwnd, HDC hdc, EGLContext eglContext, EGLDisplay eglDisplay, EGLSurface eglSurface) :
|
||||
_hwnd(hwnd),
|
||||
_hdc(hdc),
|
||||
_eglCtx(eglContext, eglDisplay,eglSurface)
|
||||
{}
|
||||
|
||||
~OpenGLContext();
|
||||
|
||||
void set(HWND hwnd, HDC hdc, EGLContext eglContext, EGLDisplay eglDisplay, EGLSurface eglSurface, EGLConfig eglConfig)
|
||||
{
|
||||
_hwnd = hwnd;
|
||||
_hdc = hdc;
|
||||
_eglCtx.eglContext = eglContext;
|
||||
_eglCtx.eglDisplay = eglDisplay;
|
||||
_eglCtx.eglSurface = eglSurface;
|
||||
_eglConfig = eglConfig;
|
||||
}
|
||||
|
||||
void clear() {
|
||||
_hwnd = 0;
|
||||
_hdc = 0;
|
||||
_eglCtx.clear();
|
||||
}
|
||||
|
||||
HDC deviceContext() { return _hdc; }
|
||||
EGLConfig getConfig() { return _eglConfig; }
|
||||
|
||||
bool makeCurrent(HDC restoreOnHdc, bool restorePreviousOnExit);
|
||||
|
||||
const GraphicsHandleWin32::EGLContextInfo& contextInfo() {
|
||||
return _eglCtx;
|
||||
}
|
||||
|
||||
protected:
|
||||
|
||||
//
|
||||
// Data members
|
||||
//
|
||||
|
||||
GraphicsHandleWin32::EGLContextInfo _eglCtx;
|
||||
EGLConfig _eglConfig;
|
||||
|
||||
HDC _previousHdc; // previously HDC to restore rendering context on
|
||||
EGLContext _previousContext; // previously current rendering context
|
||||
|
||||
HWND _hwnd; // handle to OpenGL window
|
||||
HDC _hdc; // handle to device context
|
||||
|
||||
private:
|
||||
|
||||
// no implementation for these
|
||||
OpenGLContext(const OpenGLContext&);
|
||||
OpenGLContext& operator=(const OpenGLContext&);
|
||||
};
|
||||
#else
|
||||
class OpenGLContext
|
||||
{
|
||||
public:
|
||||
@ -357,6 +441,12 @@ class Win32WindowingSystem : public osg::GraphicsContext::WindowingSystemInterfa
|
||||
_hglrc = hglrc;
|
||||
}
|
||||
|
||||
void clear() {
|
||||
_hwnd = 0;
|
||||
_hdc = 0;
|
||||
_hglrc = 0;
|
||||
}
|
||||
|
||||
HDC deviceContext() { return _hdc; }
|
||||
|
||||
bool makeCurrent( HDC restoreOnHdc, bool restorePreviousOnExit );
|
||||
@ -380,6 +470,7 @@ class Win32WindowingSystem : public osg::GraphicsContext::WindowingSystemInterfa
|
||||
OpenGLContext( const OpenGLContext& );
|
||||
OpenGLContext& operator=( const OpenGLContext& );
|
||||
};
|
||||
#endif
|
||||
|
||||
static std::string osgGraphicsWindowWithCursorClass; //!< Name of Win32 window class (with cursor) used by OSG graphics window instances
|
||||
static std::string osgGraphicsWindowWithoutCursorClass; //!< Name of Win32 window class (without cursor) used by OSG graphics window instances
|
||||
@ -701,6 +792,22 @@ static int remapWin32Key(int key)
|
||||
return s_win32KeyboardMap.remapKey(key);
|
||||
}
|
||||
|
||||
#if defined(OSG_USE_EGL)
|
||||
static void destroyEGLContext(GraphicsHandleWin32::EGLContextInfo& c)
|
||||
{
|
||||
if (!::eglMakeCurrent(c.eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT)) {
|
||||
reportError("Win32WindowingSystem.destroyEGLContext() - Unable to set current EGL rendering context", ::eglGetError());
|
||||
}
|
||||
if (!::eglDestroySurface(c.eglDisplay, c.eglSurface)) {
|
||||
reportError("Win32WindowingSystem.destroyEGLContext() - Unable to destroy current EGL Surface context", ::eglGetError());
|
||||
}
|
||||
if (!::eglDestroyContext(c.eglDisplay, c.eglContext)) {
|
||||
reportError("Win32WindowingSystem.destroyEGLContext() - Unable to destroy current EGL rendering context", ::eglGetError());
|
||||
}
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
// Window procedure for all GraphicsWindowWin32 instances
|
||||
// Dispatches the call to the actual instance
|
||||
@ -719,20 +826,28 @@ static LRESULT CALLBACK WindowProc( HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM
|
||||
|
||||
Win32WindowingSystem::OpenGLContext::~OpenGLContext()
|
||||
{
|
||||
if (_restorePreviousOnExit && _previousHglrc!=_hglrc && !::wglMakeCurrent(_previousHdc, _previousHglrc))
|
||||
#if defined(OSG_USE_EGL)
|
||||
if(_eglCtx.eglContext)
|
||||
{
|
||||
destroyEGLContext(_eglCtx);
|
||||
_eglCtx.clear();
|
||||
OSG_NOTIFY(osg::INFO) << "eglMakeCurrent: " << _eglCtx.eglDisplay << " " << EGL_NO_SURFACE << std::endl;
|
||||
}
|
||||
#else
|
||||
if(_restorePreviousOnExit && _previousHglrc != _hglrc && !::wglMakeCurrent(_previousHdc, _previousHglrc))
|
||||
{
|
||||
reportError("Win32WindowingSystem::OpenGLContext() - Unable to restore current OpenGL rendering context", ::GetLastError());
|
||||
}
|
||||
|
||||
_previousHdc = 0;
|
||||
_previousHglrc = 0;
|
||||
|
||||
if (_hglrc)
|
||||
if(_hglrc)
|
||||
{
|
||||
::wglMakeCurrent(_hdc, NULL);
|
||||
::wglDeleteContext(_hglrc);
|
||||
_hglrc = 0;
|
||||
}
|
||||
_previousHdc = 0;
|
||||
_previousHglrc = 0;
|
||||
#endif
|
||||
|
||||
|
||||
if (_hdc)
|
||||
{
|
||||
@ -747,8 +862,22 @@ Win32WindowingSystem::OpenGLContext::~OpenGLContext()
|
||||
}
|
||||
}
|
||||
|
||||
bool Win32WindowingSystem::OpenGLContext::makeCurrent( HDC restoreOnHdc, bool restorePreviousOnExit )
|
||||
bool Win32WindowingSystem::OpenGLContext::makeCurrent(HDC restoreOnHdc, bool restorePreviousOnExit)
|
||||
{
|
||||
#if defined(OSG_USE_EGL)
|
||||
if(_hdc == 0 || _eglCtx.isEmpty()) return false;
|
||||
_previousContext = restorePreviousOnExit ? ::eglGetCurrentContext() : 0;
|
||||
_previousHdc = restoreOnHdc;
|
||||
|
||||
if(_eglCtx.eglContext == _previousContext) return true;
|
||||
|
||||
if(!::eglMakeCurrent(_eglCtx.eglDisplay, _eglCtx.eglSurface, _eglCtx.eglSurface, _eglCtx.eglContext))
|
||||
{
|
||||
reportError("Win32WindowingSystem::OpenGLContext() - Unable to set current OpenGL rendering context", ::GetLastError());
|
||||
return false;
|
||||
}
|
||||
OSG_NOTIFY(osg::INFO) << "eglMakeCurrent: " << _eglCtx.eglDisplay << " " << _eglCtx.eglSurface << " " << _eglCtx.eglContext << std::endl;
|
||||
#else
|
||||
if (_hdc==0 || _hglrc==0) return false;
|
||||
|
||||
_previousHglrc = restorePreviousOnExit ? ::wglGetCurrentContext() : 0;
|
||||
@ -763,6 +892,7 @@ bool Win32WindowingSystem::OpenGLContext::makeCurrent( HDC restoreOnHdc, bool re
|
||||
}
|
||||
|
||||
_restorePreviousOnExit = restorePreviousOnExit;
|
||||
#endif
|
||||
|
||||
return true;
|
||||
}
|
||||
@ -809,7 +939,7 @@ Win32WindowingSystem::Win32WindowingSystem()
|
||||
if (hModuleShore) {
|
||||
setProcessDpiAwareness = (SetProcessDpiAwarenessFunc *) GetProcAddress(hModuleShore, "SetProcessDpiAwareness");
|
||||
if (setProcessDpiAwareness) {
|
||||
(*setProcessDpiAwareness)(PROCESS_PER_MONITOR_DPI_AWARE);
|
||||
(*setProcessDpiAwareness)(PROCESS_DPI_AWARENESS::PROCESS_PER_MONITOR_DPI_AWARE);
|
||||
}
|
||||
}
|
||||
// #endif
|
||||
@ -922,7 +1052,7 @@ void Win32WindowingSystem::unregisterWindowClasses()
|
||||
|
||||
bool Win32WindowingSystem::getSampleOpenGLContext( OpenGLContext& context, HDC windowHDC, int windowOriginX, int windowOriginY )
|
||||
{
|
||||
context.set(0, 0, 0);
|
||||
context.clear();
|
||||
|
||||
registerWindowClasses();
|
||||
|
||||
@ -990,6 +1120,73 @@ bool Win32WindowingSystem::getSampleOpenGLContext( OpenGLContext& context, HDC w
|
||||
return false;
|
||||
}
|
||||
|
||||
#if defined(OSG_USE_EGL)
|
||||
|
||||
/* possible types:
|
||||
EGL_PLATFORM_ANGLE_TYPE_DEFAULT_ANGLE
|
||||
EGL_PLATFORM_ANGLE_TYPE_D3D9_ANGLE
|
||||
EGL_PLATFORM_ANGLE_TYPE_D3D11_ANGLE
|
||||
EGL_PLATFORM_ANGLE_TYPE_OPENGL_ANGLE
|
||||
EGL_PLATFORM_ANGLE_TYPE_OPENGLES_ANGLE
|
||||
EGL_PLATFORM_ANGLE_TYPE_VULKAN_ANGLE
|
||||
EGL_PLATFORM_ANGLE_TYPE_NULL_ANGLE
|
||||
*/
|
||||
GLenum platformType = EGL_PLATFORM_ANGLE_TYPE_D3D11_ANGLE;
|
||||
|
||||
std::vector<EGLint> displayAttributes;
|
||||
displayAttributes.push_back(EGL_PLATFORM_ANGLE_TYPE_ANGLE);
|
||||
displayAttributes.push_back(platformType);
|
||||
displayAttributes.push_back(EGL_PLATFORM_ANGLE_MAX_VERSION_MAJOR_ANGLE);
|
||||
displayAttributes.push_back(EGL_DONT_CARE);
|
||||
displayAttributes.push_back(EGL_PLATFORM_ANGLE_MAX_VERSION_MINOR_ANGLE);
|
||||
displayAttributes.push_back(EGL_DONT_CARE);
|
||||
displayAttributes.push_back(EGL_PLATFORM_ANGLE_DEVICE_TYPE_ANGLE);
|
||||
displayAttributes.push_back(EGL_PLATFORM_ANGLE_DEVICE_TYPE_HARDWARE_ANGLE);
|
||||
displayAttributes.push_back(EGL_NONE);
|
||||
|
||||
const EGLint configAttribs[] = {
|
||||
EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
|
||||
EGL_BLUE_SIZE, 8,
|
||||
EGL_GREEN_SIZE, 8,
|
||||
EGL_RED_SIZE, 8,
|
||||
EGL_ALPHA_SIZE, 8,
|
||||
EGL_DEPTH_SIZE, 16,
|
||||
EGL_RENDERABLE_TYPE, eglOpenglBit,
|
||||
EGL_NONE
|
||||
};
|
||||
|
||||
EGLint major, minor;
|
||||
EGLConfig windowConfig;
|
||||
EGLint numConfigs;
|
||||
|
||||
EGLDisplay eglDisplay = eglGetPlatformDisplayEXT(EGL_PLATFORM_ANGLE_ANGLE,
|
||||
reinterpret_cast<void *>(hdc),
|
||||
displayAttributes.data());
|
||||
|
||||
eglInitialize(eglDisplay, &major, &minor);
|
||||
|
||||
printf("EGL Version: \"%s\"\n", eglQueryString(eglDisplay, EGL_VERSION));
|
||||
printf("EGL Vendor: \"%s\"\n", eglQueryString(eglDisplay, EGL_VENDOR));
|
||||
printf("EGL Extensions: \"%s\"\n", eglQueryString(eglDisplay, EGL_EXTENSIONS));
|
||||
|
||||
EGLBoolean err = eglChooseConfig(eglDisplay, configAttribs, &windowConfig, 1, &numConfigs);
|
||||
if(!err) {
|
||||
std::ostringstream str;
|
||||
str << "Win32WindowingSystem::getSampleOpenGLContext() - eglChooseConfig";
|
||||
reportError(str.str(), err);
|
||||
return false;
|
||||
}
|
||||
|
||||
//EGLint surfaceAttributes[] = { EGL_RENDER_BUFFER, EGL_POST_SUB_BUFFER_SUPPORTED_NV, EGL_NONE };
|
||||
EGLint surfaceAttributes[] = { EGL_NONE, EGL_NONE };
|
||||
EGLSurface eglSurface = eglCreateWindowSurface(eglDisplay, windowConfig, hwnd, surfaceAttributes);
|
||||
eglBindAPI(eglApi);
|
||||
|
||||
EGLint contextAttributes[] = { EGL_CONTEXT_CLIENT_VERSION, eglContextClientVersion, EGL_NONE };
|
||||
EGLContext eglContext = eglCreateContext(eglDisplay, windowConfig, EGL_NO_CONTEXT, contextAttributes);
|
||||
context.set(hwnd, hdc, eglContext, eglDisplay, eglSurface, windowConfig);
|
||||
if(!context.makeCurrent(windowHDC, true)) return false;
|
||||
#else
|
||||
HGLRC hglrc = ::wglCreateContext(hdc);
|
||||
if (hglrc==0)
|
||||
{
|
||||
@ -1002,7 +1199,7 @@ bool Win32WindowingSystem::getSampleOpenGLContext( OpenGLContext& context, HDC w
|
||||
context.set(hwnd, hdc, hglrc);
|
||||
|
||||
if (!context.makeCurrent(windowHDC, true)) return false;
|
||||
|
||||
#endif
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -1208,9 +1405,13 @@ osg::GraphicsContext* Win32WindowingSystem::createGraphicsContext( osg::Graphics
|
||||
{
|
||||
if (traits->pbuffer)
|
||||
{
|
||||
#if defined(OSG_USE_EGL)
|
||||
return 0;
|
||||
#else
|
||||
osg::ref_ptr<osgViewer::PixelBufferWin32> pbuffer = new PixelBufferWin32(traits);
|
||||
if (pbuffer->valid()) return pbuffer.release();
|
||||
else return 0;
|
||||
#endif
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -1435,7 +1636,17 @@ bool GraphicsWindowWin32::createWindow()
|
||||
//
|
||||
// Create the OpenGL rendering context associated with this window
|
||||
//
|
||||
|
||||
#ifdef OSG_USE_EGL
|
||||
_eglContextInfo = createContextImplementation();
|
||||
if (_eglContextInfo.eglContext == EGL_NO_CONTEXT) {
|
||||
destroyEGLContext(_eglContextInfo);
|
||||
_eglContextInfo.clear();
|
||||
::ReleaseDC(_hwnd, _hdc);
|
||||
_hdc = 0;
|
||||
destroyWindow();
|
||||
return false;
|
||||
}
|
||||
#else
|
||||
_hglrc = createContextImplementation();
|
||||
if (_hglrc==0)
|
||||
{
|
||||
@ -1445,6 +1656,7 @@ bool GraphicsWindowWin32::createWindow()
|
||||
destroyWindow();
|
||||
return false;
|
||||
}
|
||||
#endif
|
||||
|
||||
Win32WindowingSystem::getInterface()->registerWindow(_hwnd, this);
|
||||
|
||||
@ -1495,6 +1707,23 @@ bool GraphicsWindowWin32::setWindow( HWND handle )
|
||||
return false;
|
||||
}
|
||||
|
||||
#ifdef OSG_USE_EGL
|
||||
_eglContextInfo = createContextImplementation();
|
||||
WindowData *windowData = _traits.get() ? dynamic_cast<WindowData*>(_traits->inheritedWindowData.get()) : 0;
|
||||
|
||||
if (!windowData || windowData->_installEventHandler)
|
||||
{
|
||||
if (!registerWindowProcedure())
|
||||
{
|
||||
destroyEGLContext(_eglContextInfo);
|
||||
::ReleaseDC(_hwnd, _hdc);
|
||||
_eglContextInfo.clear();
|
||||
_hdc = 0;
|
||||
_hwnd = 0;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
#else
|
||||
_hglrc = createContextImplementation();
|
||||
if (_hglrc==0)
|
||||
{
|
||||
@ -1519,7 +1748,7 @@ bool GraphicsWindowWin32::setWindow( HWND handle )
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
Win32WindowingSystem::getInterface()->registerWindow(_hwnd, this);
|
||||
|
||||
_initialized = true;
|
||||
@ -1552,11 +1781,14 @@ void GraphicsWindowWin32::destroyWindow( bool deleteNativeWindow )
|
||||
{
|
||||
releaseContext();
|
||||
|
||||
#ifdef OSG_USE_EGL
|
||||
#else
|
||||
if (_hglrc)
|
||||
{
|
||||
::wglDeleteContext(_hglrc);
|
||||
_hglrc = 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
::ReleaseDC(_hwnd, _hdc);
|
||||
_hdc = 0;
|
||||
@ -1696,8 +1928,172 @@ bool GraphicsWindowWin32::determineWindowPositionAndStyle( unsigned int screenN
|
||||
return true;
|
||||
}
|
||||
|
||||
#ifdef OSG_USE_EGL
|
||||
const GraphicsHandleWin32::EGLContextInfo GraphicsWindowWin32::createContextImplementation()
|
||||
{
|
||||
GraphicsHandleWin32::EGLContextInfo context;
|
||||
|
||||
if(OSG_GLES3_FEATURES) {
|
||||
OSG_NOTIFY(osg::INFO) << "GLES3: Attempting to create GLES3 context." << std::endl;
|
||||
OSG_NOTIFY(osg::INFO) << "GLES3: version: " << _traits->glContextVersion << std::endl;
|
||||
OSG_NOTIFY(osg::INFO) << "GLES3: context flags: " << _traits->glContextFlags << std::endl;
|
||||
Win32WindowingSystem::OpenGLContext openGLContext;
|
||||
if(!Win32WindowingSystem::getInterface()->getSampleOpenGLContext(openGLContext, _hdc, _screenOriginX, _screenOriginY))
|
||||
{
|
||||
reportErrorForScreen("GLES3: Can't create context.",
|
||||
_traits->screenNum, ::GetLastError());
|
||||
}
|
||||
else
|
||||
{
|
||||
EGLint contextAttributes[] = { EGL_CONTEXT_CLIENT_VERSION, eglContextClientVersion, EGL_NONE };
|
||||
context.eglContext = eglCreateContext(openGLContext.contextInfo().eglDisplay, openGLContext.getConfig(), EGL_NO_CONTEXT, contextAttributes);
|
||||
context.eglDisplay = openGLContext.contextInfo().eglDisplay;
|
||||
|
||||
EGLint surfaceAttributes[] = { EGL_NONE, EGL_NONE };
|
||||
context.eglSurface = eglCreateWindowSurface(openGLContext.contextInfo().eglDisplay, openGLContext.getConfig(), _hwnd, surfaceAttributes);
|
||||
|
||||
OSG_NOTIFY(osg::INFO) << "GLES3: context created successfully." << std::endl;
|
||||
}
|
||||
}
|
||||
else {
|
||||
reportErrorForScreen("Can't create context.",
|
||||
_traits->screenNum, ::GetLastError());
|
||||
}
|
||||
return context;
|
||||
}
|
||||
|
||||
static void PreparePixelFormatSpecifications(const osg::GraphicsContext::Traits& traits,
|
||||
XGLIntegerAttributes& attributes,
|
||||
bool allowSwapExchangeARB)
|
||||
{
|
||||
attributes.begin();
|
||||
|
||||
attributes.set(EGL_SURFACE_TYPE, EGL_WINDOW_BIT);
|
||||
attributes.set(EGL_RENDERABLE_TYPE, eglOpenglBit);
|
||||
|
||||
//attributes.set(EGL_COLOWGL_COLOR_BITS_ARB, traits.red + traits.green + traits.blue);
|
||||
attributes.set(EGL_RED_SIZE, traits.red);
|
||||
attributes.set(EGL_GREEN_SIZE, traits.green);
|
||||
attributes.set(EGL_BLUE_SIZE, traits.blue);
|
||||
attributes.set(EGL_DEPTH_SIZE, traits.depth);
|
||||
#if 0
|
||||
if(traits.doubleBuffer)
|
||||
{
|
||||
attributes.enable(WGL_DOUBLE_BUFFER_ARB);
|
||||
|
||||
switch(traits.swapMethod)
|
||||
{
|
||||
case osg::DisplaySettings::SWAP_COPY:
|
||||
attributes.set(WGL_SWAP_METHOD_ARB, WGL_SWAP_COPY_ARB);
|
||||
break;
|
||||
case osg::DisplaySettings::SWAP_EXCHANGE:
|
||||
attributes.set(WGL_SWAP_METHOD_ARB, WGL_SWAP_EXCHANGE_ARB);
|
||||
break;
|
||||
case osg::DisplaySettings::SWAP_UNDEFINED:
|
||||
attributes.set(WGL_SWAP_METHOD_ARB, WGL_SWAP_UNDEFINED_ARB);
|
||||
break;
|
||||
case osg::DisplaySettings::SWAP_DEFAULT:
|
||||
// Wojtek Lewandowski 2010-09-28:
|
||||
// Keep backward compatibility if no method is selected via traits
|
||||
// and let wglSwapExchangeARB flag select swap method.
|
||||
// However, I would rather remove this flag because its
|
||||
// now redundant to Traits::swapMethod and it looks like
|
||||
// WGL_SWAP_EXCHANGE_ARB is the GL default when no WGL_SWAP attrib is given.
|
||||
// To be precise: At least on Windows 7 and Nvidia it seems to be a default.
|
||||
if(allowSwapExchangeARB)
|
||||
attributes.set(WGL_SWAP_METHOD_ARB, WGL_SWAP_EXCHANGE_ARB);
|
||||
break;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
if(traits.alpha) attributes.set(EGL_ALPHA_SIZE, traits.alpha);
|
||||
if(traits.stencil) attributes.set(EGL_STENCIL_SIZE, traits.stencil);
|
||||
if(traits.sampleBuffers) attributes.set(EGL_SAMPLE_BUFFERS, traits.sampleBuffers);
|
||||
if(traits.samples) attributes.set(EGL_SAMPLES, traits.samples);
|
||||
|
||||
attributes.end();
|
||||
}
|
||||
|
||||
bool GraphicsWindowWin32::setPixelFormat()
|
||||
{
|
||||
Win32WindowingSystem::OpenGLContext openGLContext;
|
||||
if(!Win32WindowingSystem::getInterface()->getSampleOpenGLContext(openGLContext, _hdc, _screenOriginX, _screenOriginY)) return false;
|
||||
|
||||
//
|
||||
// Build the specifications of the requested pixel format
|
||||
//
|
||||
|
||||
XGLIntegerAttributes formatSpecs;
|
||||
::PreparePixelFormatSpecifications(*_traits, formatSpecs, true);
|
||||
|
||||
//
|
||||
// Choose the closest matching pixel format from the specified traits
|
||||
//
|
||||
|
||||
EGLConfig windowConfig;
|
||||
EGLint numConfigs;
|
||||
|
||||
if(!eglChooseConfig(openGLContext.contextInfo().eglDisplay, formatSpecs.get(), NULL, 0, &numConfigs))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
// 2. Select an appropriate configuration
|
||||
EGLBoolean err = eglChooseConfig(openGLContext.contextInfo().eglDisplay, formatSpecs.get(), &windowConfig, 1, &numConfigs);
|
||||
|
||||
if(err == EGL_FALSE)
|
||||
{
|
||||
unsigned int bpp;
|
||||
Win32WindowingSystem::getInterface()->getScreenColorDepth(*_traits.get(), bpp);
|
||||
if(bpp < 32) {
|
||||
OSG_INFO << "GraphicsWindowWin32::setPixelFormat() - Display setting is not 32 bit colors, "
|
||||
<< bpp
|
||||
<< " bits per pixel on screen #"
|
||||
<< _traits->screenNum
|
||||
<< std::endl;
|
||||
|
||||
_traits->red = bpp / 4; //integer divide, determine minimum number of bits we will accept
|
||||
_traits->green = bpp / 4;
|
||||
_traits->blue = bpp / 4;
|
||||
::PreparePixelFormatSpecifications(*_traits, formatSpecs, true);// try again with WGL_SWAP_METHOD_ARB
|
||||
err = eglChooseConfig(openGLContext.contextInfo().eglDisplay, formatSpecs.get(), &windowConfig, 1, &numConfigs);
|
||||
}
|
||||
}
|
||||
if(err == EGL_FALSE)
|
||||
{
|
||||
::PreparePixelFormatSpecifications(*_traits, formatSpecs, false);
|
||||
err = eglChooseConfig(openGLContext.contextInfo().eglDisplay, formatSpecs.get(), &windowConfig, 1, &numConfigs);
|
||||
if(err == EGL_FALSE)
|
||||
{
|
||||
reportErrorForScreen("GraphicsWindowWin32::setPixelFormat() - No matching pixel format found based on traits specified", _traits->screenNum, 0);
|
||||
return false;
|
||||
}
|
||||
|
||||
OSG_INFO << "GraphicsWindowWin32::setPixelFormat() - Found a matching pixel format but without the WGL_SWAP_METHOD_ARB specification for screen #"
|
||||
<< _traits->screenNum
|
||||
<< std::endl;
|
||||
}
|
||||
#if 0
|
||||
//
|
||||
// Set the pixel format found
|
||||
//
|
||||
|
||||
PIXELFORMATDESCRIPTOR pfd;
|
||||
::memset(&pfd, 0, sizeof(pfd));
|
||||
pfd.nSize = sizeof(PIXELFORMATDESCRIPTOR);
|
||||
pfd.nVersion = 1;
|
||||
|
||||
if(!::SetPixelFormat(_hdc, pixelFormatIndex, &pfd))
|
||||
{
|
||||
reportErrorForScreen("GraphicsWindowWin32::setPixelFormat() - Unable to set pixel format", _traits->screenNum, ::GetLastError());
|
||||
return false;
|
||||
}
|
||||
#endif
|
||||
return true;
|
||||
}
|
||||
|
||||
#else
|
||||
static void PreparePixelFormatSpecifications( const osg::GraphicsContext::Traits& traits,
|
||||
WGLIntegerAttributes& attributes,
|
||||
XGLIntegerAttributes& attributes,
|
||||
bool allowSwapExchangeARB )
|
||||
{
|
||||
attributes.begin();
|
||||
@ -1753,7 +2149,7 @@ static void PreparePixelFormatSpecifications( const osg::GraphicsContext::Traits
|
||||
attributes.end();
|
||||
}
|
||||
|
||||
static int ChooseMatchingPixelFormat( HDC hdc, int screenNum, const WGLIntegerAttributes& formatSpecifications ,osg::GraphicsContext::Traits* _traits)
|
||||
static int ChooseMatchingPixelFormat( HDC hdc, int screenNum, const XGLIntegerAttributes& formatSpecifications ,osg::GraphicsContext::Traits* _traits)
|
||||
{
|
||||
//
|
||||
// Access the entry point for the wglChoosePixelFormatARB function
|
||||
@ -1827,7 +2223,7 @@ bool GraphicsWindowWin32::setPixelFormat()
|
||||
// Build the specifications of the requested pixel format
|
||||
//
|
||||
|
||||
WGLIntegerAttributes formatSpecs;
|
||||
XGLIntegerAttributes formatSpecs;
|
||||
::PreparePixelFormatSpecifications(*_traits, formatSpecs, true);
|
||||
|
||||
//
|
||||
@ -1970,6 +2366,7 @@ HGLRC GraphicsWindowWin32::createContextImplementation()
|
||||
|
||||
return( context );
|
||||
}
|
||||
#endif !OSG_USE_EGL
|
||||
|
||||
bool GraphicsWindowWin32::setWindowDecorationImplementation( bool decorated )
|
||||
{
|
||||
@ -2057,6 +2454,8 @@ bool GraphicsWindowWin32::realizeImplementation()
|
||||
|
||||
if (_traits.valid() && (_traits->sharedContext.valid() || _traits->vsync || _traits->swapGroupEnabled))
|
||||
{
|
||||
#ifdef OSG_USE_EGL
|
||||
#else
|
||||
// make context current so we can test capabilities and set up context sharing
|
||||
struct RestoreContext
|
||||
{
|
||||
@ -2073,6 +2472,7 @@ bool GraphicsWindowWin32::realizeImplementation()
|
||||
HDC _hdc;
|
||||
HGLRC _hglrc;
|
||||
} restoreContext;
|
||||
#endif
|
||||
|
||||
_realized = true;
|
||||
bool result = makeCurrent();
|
||||
@ -2083,6 +2483,8 @@ bool GraphicsWindowWin32::realizeImplementation()
|
||||
return false;
|
||||
}
|
||||
|
||||
#ifdef OSG_USE_EGL
|
||||
#else
|
||||
// set up sharing of contexts if required
|
||||
GraphicsHandleWin32* graphicsHandleWin32 = dynamic_cast<GraphicsHandleWin32*>(_traits->sharedContext.get());
|
||||
if (graphicsHandleWin32)
|
||||
@ -2093,18 +2495,18 @@ bool GraphicsWindowWin32::realizeImplementation()
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// if vysnc should be on then enable it.
|
||||
if (_traits->vsync)
|
||||
if(_traits->vsync)
|
||||
{
|
||||
setSyncToVBlank(_traits->vsync);
|
||||
}
|
||||
|
||||
// If the swap group is active then enable it.
|
||||
if (_traits->swapGroupEnabled)
|
||||
if(_traits->swapGroupEnabled)
|
||||
{
|
||||
setSwapGroup(_traits->swapGroupEnabled, _traits->swapGroup, _traits->swapBarrier);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (_ownsWindow)
|
||||
@ -2151,7 +2553,20 @@ bool GraphicsWindowWin32::makeCurrentImplementation()
|
||||
reportErrorForScreen("GraphicsWindowWin32::makeCurrentImplementation() - Window not realized; cannot do makeCurrent.", _traits->screenNum, 0);
|
||||
return false;
|
||||
}
|
||||
#ifdef OSG_USE_EGL
|
||||
const EGLContextInfo& c = getEGLContext();
|
||||
|
||||
if (eglGetCurrentContext() == c.eglContext) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if(!::eglMakeCurrent(c.eglDisplay, c.eglSurface, c.eglSurface, c.eglContext))
|
||||
{
|
||||
reportErrorForScreen("GraphicsWindowWin32::makeCurrentImplementation() - Unable to set current OpenGL rendering context", _traits->screenNum, ::GetLastError());
|
||||
return false;
|
||||
}
|
||||
OSG_NOTIFY(osg::INFO) << "eglMakeCurrent: " << c.eglDisplay << " " << c.eglSurface << " " << c.eglContext << std::endl;
|
||||
#else
|
||||
if( _applyWorkaroundForMultimonitorMultithreadNVidiaWin32Issues )
|
||||
{
|
||||
if( ::wglGetCurrentDC() != _hdc ||
|
||||
@ -2170,18 +2585,21 @@ bool GraphicsWindowWin32::makeCurrentImplementation()
|
||||
reportErrorForScreen("GraphicsWindowWin32::makeCurrentImplementation() - Unable to set current OpenGL rendering context", _traits->screenNum, ::GetLastError());
|
||||
return false;
|
||||
}
|
||||
|
||||
#endif
|
||||
return true;
|
||||
}
|
||||
|
||||
bool GraphicsWindowWin32::releaseContextImplementation()
|
||||
{
|
||||
#ifdef OSG_USE_EGL
|
||||
if(!::eglMakeCurrent(_eglContextInfo.eglDisplay, _eglContextInfo.eglSurface, EGL_NO_SURFACE, EGL_NO_CONTEXT))
|
||||
#else
|
||||
if (!::wglMakeCurrent(_hdc, NULL))
|
||||
#endif
|
||||
{
|
||||
reportErrorForScreen("GraphicsWindowWin32::releaseContextImplementation() - Unable to release current OpenGL rendering context", _traits->screenNum, ::GetLastError());
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -2197,10 +2615,18 @@ void GraphicsWindowWin32::closeImplementation()
|
||||
void GraphicsWindowWin32::swapBuffersImplementation()
|
||||
{
|
||||
if (!_realized) return;
|
||||
if (!::SwapBuffers(_hdc) && ::GetLastError() != 0)
|
||||
#ifdef OSG_USE_EGL
|
||||
EGLBoolean res = eglSwapBuffers(_eglContextInfo.eglDisplay, _eglContextInfo.eglSurface);
|
||||
if(!res) {
|
||||
reportErrorForScreen("GraphicsWindowWin32::swapBuffersImplementation() - Unable to swap display buffers", _traits->screenNum, res);
|
||||
}
|
||||
#else
|
||||
if(!::SwapBuffers(_hdc) && ::GetLastError() != 0)
|
||||
{
|
||||
reportErrorForScreen("GraphicsWindowWin32::swapBuffersImplementation() - Unable to swap display buffers", _traits->screenNum, ::GetLastError());
|
||||
}
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
bool GraphicsWindowWin32::checkEvents()
|
||||
@ -2457,6 +2883,8 @@ HCURSOR GraphicsWindowWin32::getOrCreateCursor(MouseCursor mouseCursor)
|
||||
|
||||
void GraphicsWindowWin32::setSwapGroup(bool on, GLuint group, GLuint barrier)
|
||||
{
|
||||
#if defined(OSG_USE_EGL)
|
||||
#else
|
||||
if (_traits.valid())
|
||||
{
|
||||
_traits->swapGroupEnabled = on;
|
||||
@ -2483,10 +2911,13 @@ void GraphicsWindowWin32::setSwapGroup(bool on, GLuint group, GLuint barrier)
|
||||
int swapBarrier = (on ? barrier : 0);
|
||||
BOOL resultBind = wglBindSwapBarrierNV(swapGroup, swapBarrier);
|
||||
OSG_INFO << "GraphicsWindowWin32::wglBindSwapBarrierNV (" << swapGroup << ", " << swapBarrier << ") returned " << resultBind << std::endl;
|
||||
#endif
|
||||
}
|
||||
|
||||
void GraphicsWindowWin32::setSyncToVBlank( bool on )
|
||||
{
|
||||
#if defined(OSG_USE_EGL)
|
||||
#else
|
||||
if (_traits.valid())
|
||||
{
|
||||
_traits->vsync = on;
|
||||
@ -2513,6 +2944,7 @@ void GraphicsWindowWin32::setSyncToVBlank( bool on )
|
||||
//#else
|
||||
// OSG_INFO << "GraphicsWindowWin32::setSyncToVBlank(bool) not yet implemented."<< std::endl;
|
||||
//#endif
|
||||
#endif // OSG_USE_EGL
|
||||
}
|
||||
|
||||
void GraphicsWindowWin32::adaptKey( WPARAM wParam, LPARAM lParam, int& keySymbol, unsigned int& modifierMask, int& unmodifiedKeySymbol)
|
||||
@ -3158,7 +3590,8 @@ static RegisterWindowingSystemInterfaceProxy createWindowingSystemInterfaceProxy
|
||||
} // namespace OsgViewer
|
||||
|
||||
|
||||
REGISTER_WINDOWINGSYSTEMINTERFACE2(Win32,Win32WindowingSystem,OSGVIEWER_EXPORT)
|
||||
extern "C" OSGVIEWER_EXPORT void graphicswindow_Win32(void) {}
|
||||
static osg::WindowingSystemInterfaceProxy<Win32WindowingSystem> s_proxy_Win32WindowingSystem("Win32");
|
||||
|
||||
void GraphicsWindowWin32::raiseWindow()
|
||||
{
|
||||
|
@ -14,6 +14,8 @@
|
||||
* These elements are licensed under OSGPL as above, with Copyright (C) 2001-2004 Don Burns.
|
||||
*/
|
||||
|
||||
#if defined(OSG_USE_EGL)
|
||||
#else
|
||||
#include <osgViewer/api/Win32/PixelBufferWin32>
|
||||
#include <osgViewer/api/Win32/GraphicsWindowWin32>
|
||||
#include <osg/TextureRectangle>
|
||||
@ -809,3 +811,4 @@ void PixelBufferWin32::swapBuffersImplementation()
|
||||
SwapBuffers( _hdc );
|
||||
}
|
||||
|
||||
#endif // OSG_USE_EGL
|
||||
|
Loading…
Reference in New Issue
Block a user