47 m_initialized( false ),
51 m_curFbo( DIRECT_RENDERING ),
66 catch(
const std::runtime_error& exc )
68 wxLogError( wxT(
"Run time exception `%s` occurred in OPENGL_COMPOSITOR destructor." ),
101 m_antialiasing = std::make_unique<ANTIALIASING_SUPERSAMPLING>(
this );
109 assert( dims.
x != 0 && dims.
y != 0 );
112 glGetIntegerv( GL_MAX_RENDERBUFFER_SIZE_EXT, &maxBufSize );
114 if( dims.
x < 0 || dims.
y < 0 || dims.
x > maxBufSize || dims.
y >= maxBufSize )
115 throw std::runtime_error(
"Requested render buffer size is not supported" );
120 checkGlError(
"generating framebuffer", __FILE__, __LINE__ );
126 checkGlError(
"generating renderbuffer", __FILE__, __LINE__ );
128 checkGlError(
"binding renderbuffer", __FILE__, __LINE__ );
130 glRenderbufferStorageEXT( GL_RENDERBUFFER_EXT, GL_DEPTH24_STENCIL8, dims.
x, dims.
y );
131 checkGlError(
"creating renderbuffer storage", __FILE__, __LINE__ );
132 glFramebufferRenderbufferEXT( GL_FRAMEBUFFER_EXT, GL_DEPTH_STENCIL_ATTACHMENT,
134 checkGlError(
"attaching renderbuffer", __FILE__, __LINE__ );
167 int maxBuffers, maxTextureSize;
170 glGetIntegerv( GL_MAX_COLOR_ATTACHMENTS, (GLint*) &maxBuffers );
174 throw std::runtime_error(
"Cannot create more framebuffers. OpenGL rendering backend requires at "
175 "least 3 framebuffers. You may try to update/change your graphic drivers." );
178 glGetIntegerv( GL_MAX_TEXTURE_SIZE, (GLint*) &maxTextureSize );
180 if( maxTextureSize < (
int) aDimensions.
x || maxTextureSize < (
int) aDimensions.
y )
182 throw std::runtime_error(
"Requested texture size is not supported. Could not create a buffer." );
186 GLuint attachmentPoint = GL_COLOR_ATTACHMENT0 +
usedBuffers();
187 GLuint textureTarget;
190 glActiveTexture( GL_TEXTURE0 );
191 glGenTextures( 1, &textureTarget );
192 checkGlError(
"generating framebuffer texture target", __FILE__, __LINE__ );
193 glBindTexture( GL_TEXTURE_2D, textureTarget );
194 checkGlError(
"binding framebuffer texture target", __FILE__, __LINE__ );
197 glTexEnvf( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE );
198 glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA8, aDimensions.
x, aDimensions.
y, 0, GL_RGBA, GL_UNSIGNED_BYTE,
nullptr );
199 checkGlError(
"creating framebuffer texture", __FILE__, __LINE__ );
200 glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
201 glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST );
205 glFramebufferTexture2DEXT( GL_FRAMEBUFFER_EXT, attachmentPoint, GL_TEXTURE_2D, textureTarget, 0 );
208 GLenum status = glCheckFramebufferStatusEXT( GL_FRAMEBUFFER_EXT );
210 if( status != GL_FRAMEBUFFER_COMPLETE_EXT )
214 case GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT_EXT:
215 throw std::runtime_error(
"The framebuffer attachment points are incomplete." );
217 case GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT_EXT:
218 throw std::runtime_error(
"No images attached to the framebuffer." );
220 case GL_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER_EXT:
221 throw std::runtime_error(
"The framebuffer does not have at least one image attached to it." );
223 case GL_FRAMEBUFFER_INCOMPLETE_READ_BUFFER_EXT:
224 throw std::runtime_error(
"The framebuffer read buffer is incomplete." );
226 case GL_FRAMEBUFFER_UNSUPPORTED_EXT:
227 throw std::runtime_error(
"The combination of internal formats of the attached images violates "
228 "an implementation-dependent set of restrictions." );
230 case GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE_EXT:
231 throw std::runtime_error(
"GL_RENDERBUFFER_SAMPLES is not the same for all attached renderbuffers" );
233 case GL_FRAMEBUFFER_INCOMPLETE_LAYER_TARGETS_EXT:
234 throw std::runtime_error(
"Framebuffer incomplete layer targets errors." );
236 case GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS_EXT:
237 throw std::runtime_error(
"Framebuffer attachments have different dimensions" );
240 throw std::runtime_error(
"Unknown error occurred when creating the framebuffer." );
250 OPENGL_BUFFER buffer = { aDimensions, textureTarget, attachmentPoint };
259 wxCHECK( aBufferHandle > 0 && aBufferHandle <=
usedBuffers(), 0 );
260 return m_buffers[aBufferHandle - 1].textureTarget;
276 checkGlError(
"setting draw buffer", __FILE__, __LINE__ );
292 glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT );
299 wxASSERT(
m_width <=
static_cast<unsigned int>( std::numeric_limits<coord_t>::max() ) );
300 wxASSERT(
m_height <=
static_cast<unsigned int>( std::numeric_limits<coord_t>::max() ) );
302 return {
static_cast<coord_t
>(
m_width ),
static_cast<coord_t
>(
m_height ) };
327 glDisable( GL_DEPTH_TEST );
328 glBlendFunc( GL_ONE, GL_ONE_MINUS_SRC_ALPHA );
331 glEnable( GL_TEXTURE_2D );
332 glBindTexture( GL_TEXTURE_2D,
m_buffers[aSourceHandle - 1].textureTarget );
335 glMatrixMode( GL_MODELVIEW );
338 glMatrixMode( GL_PROJECTION );
342 glBegin( GL_TRIANGLES );
343 glTexCoord2f( 0.0f, 1.0f );
344 glVertex2f( -1.0f, 1.0f );
345 glTexCoord2f( 0.0f, 0.0f );
346 glVertex2f( -1.0f, -1.0f );
347 glTexCoord2f( 1.0f, 1.0f );
348 glVertex2f( 1.0f, 1.0f );
350 glTexCoord2f( 1.0f, 1.0f );
351 glVertex2f( 1.0f, 1.0f );
352 glTexCoord2f( 0.0f, 0.0f );
353 glVertex2f( -1.0f, -1.0f );
354 glTexCoord2f( 1.0f, 0.0f );
355 glVertex2f( 1.0f, -1.0f );
359 glMatrixMode( GL_MODELVIEW );
377 glBindFramebufferEXT( GL_FRAMEBUFFER, aFb );
378 checkGlError(
"switching framebuffer", __FILE__, __LINE__ );
391 glDeleteTextures( 1, &buffer.textureTarget );
395 if( glDeleteFramebuffersEXT )
396 glDeleteFramebuffersEXT( 1, &
m_mainFbo );
398 if( glDeleteRenderbuffersEXT )
A color representation with 4 components: red, green, blue, alpha.
static const COLOR4D BLACK
unsigned int m_height
Height of the buffer (in pixels)
unsigned int m_width
Width of the buffer (in pixels)
GAL_ANTIALIASING_MODE m_currentAntialiasingMode
virtual ~OPENGL_COMPOSITOR()
VECTOR2D GetAntialiasRenderingOffset() const
virtual void Begin() override
Call this at the beginning of each frame.
unsigned int usedBuffers()
Returns number of used buffers.
void SetAntialiasingMode(GAL_ANTIALIASING_MODE aMode)
static const unsigned int DIRECT_RENDERING
VECTOR2I GetScreenSize() const
void clean()
Perform freeing of resources.
virtual void Present() override
Call this to present the output buffer to the screen.
bool m_initialized
Initialization status flag.
void bindFb(unsigned int aFb)
Binds a specific Framebuffer Object.
GAL_ANTIALIASING_MODE GetAntialiasingMode() const
GLuint m_curFbo
Store the used FBO name in case there was more than one compositor used.
virtual void Initialize() override
Perform primary initialization, necessary to use the object.
GLuint m_depthBuffer
Depth buffer handle.
virtual void ClearBuffer(const COLOR4D &aColor) override
Clear the selected buffer (set by the SetBuffer() function).
std::unique_ptr< OPENGL_PRESENTOR > m_antialiasing
virtual void Resize(unsigned int aWidth, unsigned int aHeight) override
Clear the state of COMPOSITOR, so it has to be reinitialized again with the new dimensions.
OPENGL_BUFFERS m_buffers
Stores information about initialized buffers.
virtual void DrawBuffer(unsigned int aBufferHandle) override
Draw the selected buffer to the output buffer.
GLuint m_mainFbo
Main FBO handle (storing all target textures)
int GetAntialiasSupersamplingFactor() const
unsigned int m_curBuffer
Currently used buffer handle.
GLenum GetBufferTexture(unsigned int aBufferHandle)
virtual void SetBuffer(unsigned int aBufferHandle) override
Set the selected buffer as the rendering target.
virtual unsigned int CreateBuffer() override
Prepare a new buffer that may be used as a rendering target.
The Cairo implementation of the graphics abstraction layer.
Handle multitarget rendering (ie.
int checkGlError(const std::string &aInfo, const char *aFile, int aLine, bool aThrow)
Check if a recent OpenGL operation has failed.
VECTOR2< double > VECTOR2D