Fix OPENGL_GAL initialization sequence
- New public static function OPENGL_GAL::CheckFeatures() gets called in EDA_DRAW_PANEL_GAL::SwitchBackend() before switching to OPENGL_GAL - Moved all OpenGL feature checks from OPENGL_GAL constructor to OPENGL_GAL::init() Fixes https://gitlab.com/kicad/code/kicad/-/issues/4714
This commit is contained in:
parent
3bf7cf2b54
commit
f3f17401dc
|
@ -372,21 +372,22 @@ bool EDA_DRAW_PANEL_GAL::SwitchBackend( GAL_TYPE aGalType )
|
||||||
switch( aGalType )
|
switch( aGalType )
|
||||||
{
|
{
|
||||||
case GAL_TYPE_OPENGL:
|
case GAL_TYPE_OPENGL:
|
||||||
try
|
{
|
||||||
|
wxString errormsg = KIGFX::OPENGL_GAL::CheckFeatures( m_options );
|
||||||
|
|
||||||
|
if( errormsg.empty() )
|
||||||
{
|
{
|
||||||
new_gal = new KIGFX::OPENGL_GAL( m_options, this, this, this );
|
new_gal = new KIGFX::OPENGL_GAL( m_options, this, this, this );
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
catch( std::runtime_error& err )
|
else
|
||||||
{
|
{
|
||||||
aGalType = GAL_TYPE_CAIRO;
|
aGalType = GAL_TYPE_CAIRO;
|
||||||
DisplayInfoMessage( m_parent,
|
DisplayInfoMessage( m_parent,
|
||||||
_( "Could not use OpenGL, falling back to software rendering" ),
|
_( "Could not use OpenGL, falling back to software rendering" ), errormsg );
|
||||||
wxString( err.what() ) );
|
new_gal = new KIGFX::CAIRO_GAL( m_options, this, this, this );
|
||||||
}
|
}
|
||||||
|
|
||||||
new_gal = new KIGFX::CAIRO_GAL( m_options, this, this, this );
|
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
case GAL_TYPE_CAIRO:
|
case GAL_TYPE_CAIRO:
|
||||||
new_gal = new KIGFX::CAIRO_GAL( m_options, this, this, this );
|
new_gal = new KIGFX::CAIRO_GAL( m_options, this, this, this );
|
||||||
|
|
|
@ -207,30 +207,15 @@ OPENGL_GAL::OPENGL_GAL( GAL_DISPLAY_OPTIONS& aDisplayOptions, wxWindow* aParent,
|
||||||
isContextLocked( false ),
|
isContextLocked( false ),
|
||||||
lockClientCookie( 0 )
|
lockClientCookie( 0 )
|
||||||
{
|
{
|
||||||
// IsDisplayAttr() handles WX_GL_{MAJOR,MINOR}_VERSION correctly only in 3.0.4
|
|
||||||
// starting with 3.1.0 one should use wxGLContext::IsOk() (done by GL_CONTEXT_MANAGER)
|
|
||||||
#if wxCHECK_VERSION( 3, 0, 3 ) and !wxCHECK_VERSION( 3, 1, 0 )
|
|
||||||
const int attr[] = { WX_GL_MAJOR_VERSION, 2, WX_GL_MINOR_VERSION, 1, 0 };
|
|
||||||
|
|
||||||
if( !IsDisplaySupported( attr ) )
|
|
||||||
throw std::runtime_error( "OpenGL 2.1 or higher is required!" );
|
|
||||||
#endif /* wxCHECK_VERSION( 3, 0, 3 ) */
|
|
||||||
|
|
||||||
if( glMainContext == NULL )
|
if( glMainContext == NULL )
|
||||||
{
|
{
|
||||||
glMainContext = GL_CONTEXT_MANAGER::Get().CreateCtx( this );
|
glMainContext = GL_CONTEXT_MANAGER::Get().CreateCtx( this );
|
||||||
|
|
||||||
if( !glMainContext )
|
|
||||||
throw std::runtime_error( "Could not create the main OpenGL context" );
|
|
||||||
|
|
||||||
glPrivContext = glMainContext;
|
glPrivContext = glMainContext;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
glPrivContext = GL_CONTEXT_MANAGER::Get().CreateCtx( this, glMainContext );
|
glPrivContext = GL_CONTEXT_MANAGER::Get().CreateCtx( this, glMainContext );
|
||||||
|
|
||||||
if( !glPrivContext )
|
|
||||||
throw std::runtime_error( "Could not create a private OpenGL context" );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
shader = new SHADER();
|
shader = new SHADER();
|
||||||
|
@ -281,9 +266,6 @@ OPENGL_GAL::OPENGL_GAL( GAL_DISPLAY_OPTIONS& aDisplayOptions, wxWindow* aParent,
|
||||||
tesselator = gluNewTess();
|
tesselator = gluNewTess();
|
||||||
InitTesselatorCallbacks( tesselator );
|
InitTesselatorCallbacks( tesselator );
|
||||||
|
|
||||||
if( tesselator == NULL )
|
|
||||||
throw std::runtime_error( "Could not create the tesselator" );
|
|
||||||
|
|
||||||
gluTessProperty( tesselator, GLU_TESS_WINDING_RULE, GLU_TESS_WINDING_POSITIVE );
|
gluTessProperty( tesselator, GLU_TESS_WINDING_RULE, GLU_TESS_WINDING_POSITIVE );
|
||||||
|
|
||||||
SetTarget( TARGET_NONCACHED );
|
SetTarget( TARGET_NONCACHED );
|
||||||
|
@ -340,6 +322,36 @@ OPENGL_GAL::~OPENGL_GAL()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
wxString OPENGL_GAL::CheckFeatures( GAL_DISPLAY_OPTIONS& aOptions )
|
||||||
|
{
|
||||||
|
|
||||||
|
wxFrame* testFrame =
|
||||||
|
new wxFrame( NULL, wxID_ANY, wxT( "" ), wxDefaultPosition, wxSize( 1, 1 ) );
|
||||||
|
KIGFX::OPENGL_GAL* opengl_gal = new KIGFX::OPENGL_GAL( aOptions, testFrame );
|
||||||
|
|
||||||
|
testFrame->Raise();
|
||||||
|
testFrame->Show();
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
GAL_CONTEXT_LOCKER lock( opengl_gal );
|
||||||
|
opengl_gal->init();
|
||||||
|
}
|
||||||
|
catch( std::runtime_error& err )
|
||||||
|
{
|
||||||
|
//Test failed
|
||||||
|
delete opengl_gal;
|
||||||
|
delete testFrame;
|
||||||
|
return wxString( err.what() );
|
||||||
|
}
|
||||||
|
|
||||||
|
//Test passed
|
||||||
|
delete opengl_gal;
|
||||||
|
delete testFrame;
|
||||||
|
return wxEmptyString;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
bool OPENGL_GAL::updatedGalDisplayOptions( const GAL_DISPLAY_OPTIONS& aOptions )
|
bool OPENGL_GAL::updatedGalDisplayOptions( const GAL_DISPLAY_OPTIONS& aOptions )
|
||||||
{
|
{
|
||||||
bool refresh = false;
|
bool refresh = false;
|
||||||
|
@ -1993,10 +2005,31 @@ unsigned int OPENGL_GAL::getNewGroupNumber()
|
||||||
|
|
||||||
void OPENGL_GAL::init()
|
void OPENGL_GAL::init()
|
||||||
{
|
{
|
||||||
|
|
||||||
wxASSERT( IsShownOnScreen() );
|
wxASSERT( IsShownOnScreen() );
|
||||||
|
|
||||||
wxASSERT_MSG( isContextLocked, "This should only be called from within a locked context." );
|
wxASSERT_MSG( isContextLocked, "This should only be called from within a locked context." );
|
||||||
|
|
||||||
|
// IsDisplayAttr() handles WX_GL_{MAJOR,MINOR}_VERSION correctly only in 3.0.4
|
||||||
|
// starting with 3.1.0 one should use wxGLContext::IsOk() (done by GL_CONTEXT_MANAGER)
|
||||||
|
#if wxCHECK_VERSION( 3, 0, 3 ) and !wxCHECK_VERSION( 3, 1, 0 )
|
||||||
|
const int attr[] = { WX_GL_MAJOR_VERSION, 2, WX_GL_MINOR_VERSION, 1, 0 };
|
||||||
|
|
||||||
|
if( !IsDisplaySupported( attr ) )
|
||||||
|
throw std::runtime_error( "OpenGL 2.1 or higher is required!" );
|
||||||
|
#endif /* wxCHECK_VERSION( 3, 0, 3 ) */
|
||||||
|
|
||||||
|
// Check correct initialization from the constructor
|
||||||
|
if( !glMainContext )
|
||||||
|
throw std::runtime_error( "Could not create the main OpenGL context" );
|
||||||
|
|
||||||
|
if( !glPrivContext )
|
||||||
|
throw std::runtime_error( "Could not create a private OpenGL context" );
|
||||||
|
|
||||||
|
if( tesselator == NULL )
|
||||||
|
throw std::runtime_error( "Could not create the tesselator" );
|
||||||
|
// End initialzation checks
|
||||||
|
|
||||||
GLenum err = glewInit();
|
GLenum err = glewInit();
|
||||||
|
|
||||||
if( GLEW_OK != err )
|
if( GLEW_OK != err )
|
||||||
|
@ -2035,7 +2068,7 @@ void OPENGL_GAL::init()
|
||||||
int maxTextureSize;
|
int maxTextureSize;
|
||||||
glGetIntegerv( GL_MAX_TEXTURE_SIZE, &maxTextureSize );
|
glGetIntegerv( GL_MAX_TEXTURE_SIZE, &maxTextureSize );
|
||||||
|
|
||||||
if( maxTextureSize < (int) font_image.width || maxTextureSize < (int)font_image.height )
|
if( maxTextureSize < (int) font_image.width || maxTextureSize < (int) font_image.height )
|
||||||
{
|
{
|
||||||
// TODO implement software texture scaling
|
// TODO implement software texture scaling
|
||||||
// for bitmap fonts and use a higher resolution texture?
|
// for bitmap fonts and use a higher resolution texture?
|
||||||
|
|
|
@ -86,6 +86,13 @@ public:
|
||||||
|
|
||||||
virtual ~OPENGL_GAL();
|
virtual ~OPENGL_GAL();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Checks OpenGL features
|
||||||
|
* @param aOptions
|
||||||
|
* @return wxEmptyString if OpenGL 2.1 or greater is available, otherwise returns error message
|
||||||
|
*/
|
||||||
|
static wxString CheckFeatures( GAL_DISPLAY_OPTIONS& aOptions );
|
||||||
|
|
||||||
virtual bool IsOpenGlEngine() override { return true; }
|
virtual bool IsOpenGlEngine() override { return true; }
|
||||||
|
|
||||||
/// @copydoc GAL::IsInitialized()
|
/// @copydoc GAL::IsInitialized()
|
||||||
|
@ -479,7 +486,8 @@ private:
|
||||||
VECTOR2D getScreenPixelSize() const;
|
VECTOR2D getScreenPixelSize() const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Basic OpenGL initialization.
|
* @brief Basic OpenGL initialization and feature checks
|
||||||
|
* @throw std::runtime_error if any of the OpenGL feature checks failed
|
||||||
*/
|
*/
|
||||||
void init();
|
void init();
|
||||||
};
|
};
|
||||||
|
|
Loading…
Reference in New Issue