//-----------------------------------------------------------------------------
void GLESFrameBufferObject::detachDepthBuffer()
{
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, mMultisampleFB ? mMultisampleFB : mFB );
    glFramebufferRenderbufferOES( GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, 0 );
    glFramebufferRenderbufferOES( GL_FRAMEBUFFER_OES, GL_STENCIL_ATTACHMENT_OES,
                                  GL_RENDERBUFFER_OES, 0 );
}
		void OpenGLES1RenderManager::_generateOpenglBuffers()
		{
			#ifdef AURORA_IOS

			// Create & bind the color buffer so that the caller can allocate its space.
			glGenRenderbuffersOES(1, &m_colorRenderbuffer);
			glBindRenderbufferOES(GL_RENDERBUFFER_OES, m_colorRenderbuffer);

			// Create the depth buffer.
			glGenRenderbuffersOES(1, &m_depthRenderbuffer);
			glBindRenderbufferOES(GL_RENDERBUFFER_OES, m_depthRenderbuffer);
			glRenderbufferStorageOES(GL_RENDERBUFFER_OES,GL_DEPTH_COMPONENT16_OES,_width,_height);

			// Create the framebuffer object; attach the depth and color buffers.
			glGenFramebuffersOES(1, &m_framebuffer);
			glBindFramebufferOES(GL_FRAMEBUFFER_OES, m_framebuffer);
			glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES,
				GL_COLOR_ATTACHMENT0_OES,
				GL_RENDERBUFFER_OES,
				m_colorRenderbuffer);

			glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES,
				GL_DEPTH_ATTACHMENT_OES,
				GL_RENDERBUFFER_OES,
				m_depthRenderbuffer);

			// Bind the color buffer for rendering.
			glBindRenderbufferOES(GL_RENDERBUFFER_OES, m_colorRenderbuffer);

			#endif
		}
Ejemplo n.º 3
0
void Screen::CreateHardwareSurfaces()
{
	glGenFramebuffersOES(1, &frameBuffer);
	glGenRenderbuffersOES(1, &renderBuffer);

	glBindFramebufferOES(GL_FRAMEBUFFER_OES, frameBuffer);
	glBindRenderbufferOES(GL_RENDERBUFFER_OES, renderBuffer);
	iphPrepareGLContext();
	glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, renderBuffer);

	glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES, GL_RENDERBUFFER_WIDTH_OES, &iWidth);
	glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES, GL_RENDERBUFFER_HEIGHT_OES, &iHeight);

#if SEED_ENABLE_DEPTH_TEST
	glGenRenderbuffersOES(1, &depthRenderbuffer);
	glBindRenderbufferOES(GL_RENDERBUFFER_OES, depthRenderbuffer);
	glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_DEPTH_COMPONENT16_OES, iWidth, iHeight);
	glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, depthRenderbuffer);
#endif // SEED_ENABLE_DEPTH_TEST

	if (iMode == LANDSCAPE || iMode == LANDSCAPE_GOOFY)
	{
		this->iModeWidth = this->iHeight;
		this->iModeHeight = this->iWidth;
	}
	else
	{
		this->iModeWidth = this->iHeight;
		this->iModeHeight = this->iWidth;
	}
}
Ejemplo n.º 4
0
    /** Try a certain packed depth/stencil format, and return the status.
        @returns true    if this combo is supported
                 false   if this combo is not supported
    */
    bool GLESFBOManager::_tryPackedFormat(GLenum packedFormat)
    {
        GLuint packedRB;

        /// Generate renderbuffer
        glGenRenderbuffersOES(1, &packedRB);

        /// Bind it to FBO
        glBindRenderbufferOES(GL_RENDERBUFFER_OES, packedRB);

        /// Allocate storage for buffer
        glRenderbufferStorageOES(GL_RENDERBUFFER_OES, packedFormat, PROBE_SIZE, PROBE_SIZE);

        /// Attach depth
        glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES,
            GL_RENDERBUFFER_OES, packedRB);

        /// Attach stencil
        glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_STENCIL_ATTACHMENT_OES,
            GL_RENDERBUFFER_OES, packedRB);

        GLuint status = glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES);

        /// Detach and destroy
        glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, 0);
        glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_STENCIL_ATTACHMENT_OES, GL_RENDERBUFFER_OES, 0);
        glDeleteRenderbuffersOES(1, &packedRB);

        return status == GL_FRAMEBUFFER_COMPLETE_OES;
    }
void GLESFrameBufferObject::attachDepthBuffer( DepthBuffer *depthBuffer )
{
    GLESDepthBuffer *glDepthBuffer = static_cast<GLESDepthBuffer*>(depthBuffer);

    glBindFramebufferOES(GL_FRAMEBUFFER_OES, mMultisampleFB ? mMultisampleFB : mFB );

    if( glDepthBuffer )
    {
        GLESRenderBuffer *depthBuf   = glDepthBuffer->getDepthBuffer();
        GLESRenderBuffer *stencilBuf = glDepthBuffer->getStencilBuffer();

        //Attach depth buffer, if it has one.
        if( depthBuf )
            depthBuf->bindToFramebuffer( GL_DEPTH_ATTACHMENT_OES, 0 );

        //Attach stencil buffer, if it has one.
        if( stencilBuf )
            stencilBuf->bindToFramebuffer( GL_STENCIL_ATTACHMENT_OES, 0 );
    }
    else
    {
        glFramebufferRenderbufferOES( GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES,
                                      GL_RENDERBUFFER_OES, 0);
        glFramebufferRenderbufferOES( GL_FRAMEBUFFER_OES, GL_STENCIL_ATTACHMENT_OES,
                                      GL_RENDERBUFFER_OES, 0);
    }
}
Ejemplo n.º 6
0
    /** Try a certain FBO format, and return the status. Also sets mDepthRB and mStencilRB.
        @returns true    if this combo is supported
                 false   if this combo is not supported
    */
    GLuint GLESFBOManager::_tryFormat(GLenum depthFormat, GLenum stencilFormat)
    {
        GLuint status, depthRB = 0, stencilRB = 0;

        if(depthFormat != GL_NONE)
        {
            /// Generate depth renderbuffer
            glGenRenderbuffersOES(1, &depthRB);

            /// Bind it to FBO
            glBindRenderbufferOES(GL_RENDERBUFFER_OES, depthRB);
            
            /// Allocate storage for depth buffer
            glRenderbufferStorageOES(GL_RENDERBUFFER_OES, depthFormat,
                                PROBE_SIZE, PROBE_SIZE);
            
            /// Attach depth
            glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES,
                                    GL_RENDERBUFFER_OES, depthRB);
        }

        // Stencil buffers aren't available on iPhone
        if(stencilFormat != GL_NONE)
        {
            /// Generate stencil renderbuffer
            glGenRenderbuffersOES(1, &stencilRB);
            
            /// Bind it to FBO
            glBindRenderbufferOES(GL_RENDERBUFFER_OES, stencilRB);

            /// Allocate storage for stencil buffer
            glRenderbufferStorageOES(GL_RENDERBUFFER_OES, stencilFormat,
                                PROBE_SIZE, PROBE_SIZE); 

            /// Attach stencil
            glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_STENCIL_ATTACHMENT_OES,
                            GL_RENDERBUFFER_OES, stencilRB);
        }

        status = glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES);

        /// If status is negative, clean up
        // Detach and destroy
        glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, 0);

        glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_STENCIL_ATTACHMENT_OES, GL_RENDERBUFFER_OES, 0);

        if (depthRB)
            glDeleteRenderbuffersOES(1, &depthRB);

        if (stencilRB)
            glDeleteRenderbuffersOES(1, &stencilRB);
        
        return status == GL_FRAMEBUFFER_COMPLETE_OES;
    }
void CreateSurfaceMultisampleBuffersGLES(EAGLSurfaceDesc* surface)
{
	UNITY_DBG_LOG ("CreateSurfaceMultisampleBuffers: samples=%i\n", surface->msaaSamples);
	GLES_CHK( glBindRenderbufferOES(GL_RENDERBUFFER_OES, surface->renderbuffer) );

	UNITY_DBG_LOG ("glBindFramebufferOES(GL_FRAMEBUFFER_OES, %d) :: AppCtrl\n", surface->framebuffer);
	GLES_CHK( glBindFramebufferOES(GL_FRAMEBUFFER_OES, surface->framebuffer) );

	gDefaultFBO = surface->framebuffer;

	DestroySurfaceMultisampleBuffersGLES(surface);

	GLES_CHK( glBindRenderbufferOES(GL_RENDERBUFFER_OES, surface->renderbuffer) );

	UNITY_DBG_LOG ("glBindFramebufferOES(GL_FRAMEBUFFER_OES, %d) :: AppCtrl\n", surface->framebuffer);
	GLES_CHK( glBindFramebufferOES(GL_FRAMEBUFFER_OES, surface->framebuffer) );

#if GL_APPLE_framebuffer_multisample
	if(surface->msaaSamples > 1)
	{
		GLES_CHK( glGenRenderbuffersOES(1, &surface->msaaRenderbuffer) );
		GLES_CHK( glBindRenderbufferOES(GL_RENDERBUFFER_OES, surface->msaaRenderbuffer) );

		GLES_CHK( glGenFramebuffersOES(1, &surface->msaaFramebuffer) );

		UNITY_DBG_LOG ("glBindFramebufferOES(GL_FRAMEBUFFER_OES, %d) :: AppCtrl\n", surface->msaaFramebuffer);
		GLES_CHK( glBindFramebufferOES(GL_FRAMEBUFFER_OES, surface->msaaFramebuffer) );

		gDefaultFBO = surface->msaaFramebuffer;

		GLES_CHK( glRenderbufferStorageMultisampleAPPLE(GL_RENDERBUFFER_OES, surface->msaaSamples, surface->format, surface->w, surface->h) );
		GLES_CHK( glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, surface->msaaRenderbuffer) );

		if(surface->depthFormat)
		{
			GLES_CHK( glGenRenderbuffersOES(1, &surface->msaaDepthbuffer) );
			GLES_CHK( glBindRenderbufferOES(GL_RENDERBUFFER_OES, surface->msaaDepthbuffer) );
			GLES_CHK( glRenderbufferStorageMultisampleAPPLE(GL_RENDERBUFFER_OES, surface->msaaSamples, GL_DEPTH_COMPONENT16_OES, surface->w, surface->h) );
			GLES_CHK( glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, surface->msaaDepthbuffer) );
		}
	}
	else
#endif
	{
		if(surface->depthFormat)
		{
			GLES_CHK( glGenRenderbuffersOES(1, &surface->depthbuffer) );
			GLES_CHK( glBindRenderbufferOES(GL_RENDERBUFFER_OES, surface->depthbuffer) );
			GLES_CHK( glRenderbufferStorageOES(GL_RENDERBUFFER_OES, surface->depthFormat, surface->w, surface->h) );

			UNITY_DBG_LOG ("glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, %d) :: AppCtrl\n", surface->depthbuffer);
			GLES_CHK( glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, surface->depthbuffer) );
		}
	}
}
 inline void VL_glFramebufferRenderbuffer(GLenum target, GLenum attachment, GLenum renderbuffertarget, GLuint renderbuffer)
 {
   if (glFramebufferRenderbufferOES)
     glFramebufferRenderbufferOES(target, attachment, renderbuffertarget, renderbuffer);
   else
     VL_TRAP();
 }
 //-----------------------------------------------------------------------------  
 void GLESRenderBuffer::bindToFramebuffer(GLenum attachment, size_t zoffset)
 {
     assert(zoffset < mDepth);
     glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, attachment,
                                  GL_RENDERBUFFER_OES, mRenderbufferID);
     GL_CHECK_ERROR;
 }
void CreateSurfaceGLES(EAGLSurfaceDesc* surface)
{
	GLuint oldRenderbuffer;
	GLES_CHK( glGetIntegerv(GL_RENDERBUFFER_BINDING_OES, (GLint *) &oldRenderbuffer) );

	DestroySurfaceGLES(surface);

	InitEAGLLayer(surface->eaglLayer, surface->use32bitColor);

	GLES_CHK( glGenRenderbuffersOES(1, &surface->renderbuffer) );
	GLES_CHK( glBindRenderbufferOES(GL_RENDERBUFFER_OES, surface->renderbuffer) );

	if( !AllocateRenderBufferStorageFromEAGLLayer(surface->eaglLayer) )
	{
		GLES_CHK( glDeleteRenderbuffersOES(1, &surface->renderbuffer) );
		GLES_CHK( glBindRenderbufferOES(GL_RENDERBUFFER_BINDING_OES, oldRenderbuffer) );

		printf_console("FAILED allocating render buffer storage from gles context\n");
		return;
	}

	GLES_CHK( glGenFramebuffersOES(1, &surface->framebuffer) );

	UNITY_DBG_LOG ("glBindFramebufferOES(GL_FRAMEBUFFER_OES, %d) :: AppCtrl\n", surface->framebuffer);
	GLES_CHK( glBindFramebufferOES(GL_FRAMEBUFFER_OES, surface->framebuffer) );

	gDefaultFBO = surface->framebuffer;

	UNITY_DBG_LOG ("glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, %d) :: AppCtrl\n", surface->renderbuffer);
	GLES_CHK( glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, surface->renderbuffer) );

	CreateSurfaceMultisampleBuffersGLES(surface);
}
void GLES11RenderEngine::bindImageAsFramebuffer(EGLImageKHR image,
        uint32_t* texName, uint32_t* fbName, uint32_t* status,
        bool useReadPixels, int reqWidth, int reqHeight) {
    GLuint tname, name;
    if (!useReadPixels) {
        // turn our EGLImage into a texture
        glGenTextures(1, &tname);
        glBindTexture(GL_TEXTURE_2D, tname);
        glEGLImageTargetTexture2DOES(GL_TEXTURE_2D, (GLeglImageOES)image);

        // create a Framebuffer Object to render into
        glGenFramebuffersOES(1, &name);
        glBindFramebufferOES(GL_FRAMEBUFFER_OES, name);
        glFramebufferTexture2DOES(GL_FRAMEBUFFER_OES,
                GL_COLOR_ATTACHMENT0_OES, GL_TEXTURE_2D, tname, 0);
    } else {
        // since we're going to use glReadPixels() anyways,
        // use an intermediate renderbuffer instead
        glGenRenderbuffersOES(1, &tname);
        glBindRenderbufferOES(GL_RENDERBUFFER_OES, tname);
        glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_RGBA8_OES, reqWidth, reqHeight);
        // create a FBO to render into
        glGenFramebuffersOES(1, &name);
        glBindFramebufferOES(GL_FRAMEBUFFER_OES, name);
        glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, tname);
    }

    *status = glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES);
    *texName = tname;
    *fbName = name;
}
Ejemplo n.º 12
0
void RenderingEngine1::Initialize(int width, int height)
{
    // Create the framebuffer object and attach the color buffer.
    glGenFramebuffersOES(1, &m_framebuffer);
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, m_framebuffer);
    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES,
                                 GL_COLOR_ATTACHMENT0_OES,
                                 GL_RENDERBUFFER_OES,
                                 m_renderbuffer);

    glViewport(0, 0, width, height);

    glMatrixMode(GL_PROJECTION);

    // Initialize the projection matrix.
    const float maxX = 2;
    const float maxY = 3;
    glOrthof(-maxX, +maxX, -maxY, +maxY, -1, 1);

    glMatrixMode(GL_MODELVIEW);

    // Initialize the rotation animation state.
    OnRotate(DeviceOrientationPortrait);
    m_currentAngle = m_desiredAngle;
}
Ejemplo n.º 13
0
void RenderES1::setViewPort(int width, int height)
{
    
    glGenRenderbuffersOES(1, &_render_buffer);
    glBindRenderbufferOES(GL_RENDERBUFFER_OES, _render_buffer);
    //
    glGenFramebuffersOES(1, &_frame_buffer);
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, _frame_buffer);
    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, _render_buffer);
    glViewport(0, 0, width, height);
}
extern "C" bool UnityResolveMSAA(GLuint destFBO, GLuint colorTex, GLuint colorBuf, GLuint depthTex, GLuint depthBuf)
{
#if GL_APPLE_framebuffer_multisample
	if (_surface.msaaSamples > 0 && _supportsMSAA && destFBO!=_surface.msaaFramebuffer && destFBO!=_surface.framebuffer)
	{
		Profiler_StartMSAAResolve();

		GLint oldFBO;
		GLES_CHK( glGetIntegerv (GL_FRAMEBUFFER_BINDING_OES, &oldFBO) );

		UNITY_DBG_LOG ("UnityResolveMSAA: samples=%i msaaFBO=%i destFBO=%i colorTex=%i colorRB=%i depthTex=%i depthRB=%i\n", _surface.msaaSamples, _surface.msaaFramebuffer, destFBO, colorTex, colorBuf, depthTex, depthBuf);
		UNITY_DBG_LOG ("  bind dest as DRAW FBO and textures/buffers into it\n");

		GLES_CHK( glBindFramebufferOES (GL_DRAW_FRAMEBUFFER_APPLE, destFBO) );
		if (colorTex)
			GLES_CHK( glFramebufferTexture2DOES( GL_DRAW_FRAMEBUFFER_APPLE, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, colorTex, 0 ) );
		else if (colorBuf)
			GLES_CHK( glFramebufferRenderbufferOES (GL_DRAW_FRAMEBUFFER_APPLE, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, colorBuf) );

		if (depthTex)
			GLES_CHK( glFramebufferTexture2DOES( GL_DRAW_FRAMEBUFFER_APPLE, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, depthTex, 0 ) );
		else if (depthBuf)
			GLES_CHK( glFramebufferRenderbufferOES (GL_DRAW_FRAMEBUFFER_APPLE, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, depthBuf) );

		UNITY_DBG_LOG ("  bind msaa as READ FBO\n");
		GLES_CHK( glBindFramebufferOES(GL_READ_FRAMEBUFFER_APPLE, _surface.msaaFramebuffer) );

		UNITY_DBG_LOG ("  glResolveMultisampleFramebufferAPPLE ();\n");
		GLES_CHK( glResolveMultisampleFramebufferAPPLE() );

		GLES_CHK( glBindFramebufferOES (GL_FRAMEBUFFER_OES, oldFBO) );

		Profiler_EndMSAAResolve();
		return true;
	}
	#endif
	return false;
}
Ejemplo n.º 15
0
void RenderingEngine1::initialize(int width, int height){
    glGenFramebuffersOES(1, &frameBuffer);
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, frameBuffer);
    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES,
                                 GL_COLOR_ATTACHMENT0_OES,
                                 GL_RENDERBUFFER_OES,
                                 renderBuffer);
    glViewport(0, 0, width, height);
    glMatrixMode(GL_PROJECTION);
    const float maxX = 2;
    const float maxY = 3;
    glOrthof(-maxX, +maxX, -maxY, +maxY, -1, 1);
    glMatrixMode(GL_MODELVIEW);
}
Ejemplo n.º 16
0
void EJCanvasContext::createStencilBufferOnce()
{
	if( stencilBuffer ) { return; }
#ifdef _WINDOWS

	glGenRenderbuffersEXT(1, &stencilBuffer);
	glBindRenderbufferEXT(GL_RENDERBUFFER_EXT, stencilBuffer);
	if( msaaEnabled ) {
		glRenderbufferStorageMultisample(GL_RENDERBUFFER_EXT, msaaSamples, GL_DEPTH24_STENCIL8, bufferWidth, bufferHeight);
	}
	else {
		glRenderbufferStorage(GL_RENDERBUFFER_EXT, GL_DEPTH24_STENCIL8, bufferWidth, bufferHeight);
	}
	glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER_EXT, stencilBuffer);
	glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER_EXT, stencilBuffer);

	glBindRenderbufferEXT(GL_RENDERBUFFER_EXT, msaaEnabled ? msaaRenderBuffer : viewRenderBuffer );

#else

	glGenRenderbuffersOES(1, &stencilBuffer);
	glBindRenderbufferOES(GL_RENDERBUFFER_OES, stencilBuffer);
	if( msaaEnabled ) {
		//glRenderbufferStorageMultisampleAPPLE(GL_RENDERBUFFER, msaaSamples, GL_DEPTH24_STENCIL8_OES, bufferWidth, bufferHeight);
	}
	else {
		glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_DEPTH24_STENCIL8_OES, bufferWidth, bufferHeight);
	}
	glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, stencilBuffer);
	glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_STENCIL_ATTACHMENT_OES, GL_RENDERBUFFER_OES, stencilBuffer);

	glBindRenderbufferOES(GL_RENDERBUFFER_OES, msaaEnabled ? msaaRenderBuffer : viewRenderBuffer );

#endif
	glClear(GL_STENCIL_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

}
Ejemplo n.º 17
0
void sgTexture::makeRendertarget()
{
	if(textype != GL_TEXTURE_2D || fbo != -1)
		return;

	if(sgRenderer::oglversion > 1)
	{
#if defined __IOS__
		glGenFramebuffers(1, &fbo);
		glBindFramebuffer(GL_FRAMEBUFFER, fbo);
		glBindTexture(textype, 0);
		glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texid, 0);
		glClear(GL_COLOR_BUFFER_BIT);

		glGenRenderbuffers(1, &fbo_depth);
		glBindRenderbuffer(GL_RENDERBUFFER, fbo_depth);
//		glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH24_STENCIL8_OES, width, height);
		glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT16, width, height);
		glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, fbo_depth);
#else
		glGenFramebuffersEXT(1, &fbo);
		glBindFramebufferEXT(GL_FRAMEBUFFER, fbo);
		glBindTexture(textype, 0);
		glFramebufferTexture2DEXT(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texid, 0);
		glClear(GL_COLOR_BUFFER_BIT);

		glGenRenderbuffersEXT(1, &fbo_depth);
		glBindRenderbufferEXT(GL_RENDERBUFFER, fbo_depth);
//		glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH24_STENCIL8_OES, width, height);
		glRenderbufferStorageEXT(GL_RENDERBUFFER, GL_DEPTH_COMPONENT16, width, height);
		glFramebufferRenderbufferEXT(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, fbo_depth);
#endif
	}else
	{
#if defined __IOS__
		glGenFramebuffersOES(1, &fbo);
		glBindFramebufferOES(GL_FRAMEBUFFER_OES, fbo);
		glBindTexture(GL_TEXTURE_2D, 0);
		glFramebufferTexture2DOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_TEXTURE_2D, texid, 0);

		glGenRenderbuffersOES(1, &fbo_depth);
		glBindRenderbufferOES(GL_RENDERBUFFER_OES, fbo_depth);
		glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_DEPTH_COMPONENT16_OES, width, height);
		glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, fbo_depth);
#endif
	}
}
Ejemplo n.º 18
0
void RenderingEngine1::Initialize(int width, int height)
{
    glGenFramebuffersOES(1, &_frameBuffer);
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, _frameBuffer);
    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, _renderBuffer);
    glViewport(0, 0, width, height);
    glMatrixMode(GL_PROJECTION);
    
    const float maxX = 2;
    const float maxY = 3;
    
    glOrthof(-maxX, +maxX, -maxY, +maxY, -1, 1);
    glMatrixMode(GL_MODELVIEW);
    
    OnRotate(DeviceOrientationPortrait);
    _currentAngle = _desiredAngle;
}
Ejemplo n.º 19
0
	OpenGLRTTexture::OpenGLRTTexture(unsigned int _texture, int width, int height) :
		mTextureID(_texture),
		mWidth(width),
		mHeight(height),
		mFBOID(0),
		mRBOID(0)
	{
		int miplevel = 0;
		glBindTexture(GL_TEXTURE_2D, mTextureID);
		//glGetTexLevelParameteriv(GL_TEXTURE_2D, miplevel, GL_TEXTURE_WIDTH, &mWidth);    // Unsupported by OpenGL ES, using param
		//glGetTexLevelParameteriv(GL_TEXTURE_2D, miplevel, GL_TEXTURE_HEIGHT, &mHeight);  // Unsupported by OpenGL ES, using param
		glBindTexture(GL_TEXTURE_2D, 0);

		mRenderTargetInfo.maximumDepth = 1.0f;
		mRenderTargetInfo.hOffset = 0;
		mRenderTargetInfo.vOffset = 0;
		mRenderTargetInfo.aspectCoef = float(mHeight) / float(mWidth);
		mRenderTargetInfo.pixScaleX = 1.0f / float(mWidth);
		mRenderTargetInfo.pixScaleY = 1.0f / float(mHeight);

		// create a framebuffer object, you need to delete them when program exits.
		glGenFramebuffersOES(1, &mFBOID);
		glBindFramebufferOES(GL_FRAMEBUFFER_OES, mFBOID);

		// create a renderbuffer object to store depth info
		// NOTE: A depth renderable image should be attached the FBO for depth test.
		// If we don't attach a depth renderable image to the FBO, then
		// the rendering output will be corrupted because of missing depth test.
		// If you also need stencil test for your rendering, then you must
		// attach additional image to the stencil attachement point, too.
		glGenRenderbuffersOES(1, &mRBOID);
		glBindRenderbufferOES(GL_RENDERBUFFER_OES, mRBOID);
		glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_DEPTH_COMPONENT16_OES, mWidth, mHeight);
		glBindRenderbufferOES(GL_RENDERBUFFER_OES, 0);

		// attach a texture to FBO color attachement point
		glFramebufferTexture2DOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_TEXTURE_2D, mTextureID, 0);

		// attach a renderbuffer to depth attachment point
		glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, mRBOID);

		glBindFramebufferOES(GL_FRAMEBUFFER_OES, 0);
	}
Ejemplo n.º 20
0
FBO *createFBO(s32 width, s32 height, bool hd) {
    // save current FBO
    FBO *oldFBO = getFBOUsed();
    
    GLuint framebuffer;
    GLuint depthRenderbuffer;
    
    width = width;
    height = height;

    s32 texturePtrId = createTexture(0, 0);
    setTexture(texturePtrId, width, height, 3, NULL);
    Texture *tex = getTexture(texturePtrId);
    
    // create depth renderbuffer
    glGenRenderbuffersOES(1, &depthRenderbuffer);
    glBindRenderbufferOES(GL_RENDERBUFFER_OES, depthRenderbuffer);
    glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_DEPTH_COMPONENT16_OES, width, height);
    
    // bind framebuffer & attach texture
    glGenFramebuffersOES(1, &framebuffer);
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, framebuffer);
    glFramebufferTexture2DOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_TEXTURE_2D, tex->mTextureId, 0);
    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES, GL_RENDERBUFFER_OES, depthRenderbuffer);
    
    // check binding
    if (glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES) != GL_FRAMEBUFFER_COMPLETE_OES) {
        logError(TAG, "CRITICAL ERROR: FBO no complete");
        return 0;
    }

    // save info into structure
    FBO *fbo = (FBO *)malloc(sizeof(FBO));
    fbo->mFBO = framebuffer;
    fbo->mWidth = width;
    fbo->mHeight = height;
    fbo->mTexturePtrId = texturePtrId;
    fbo->mDepthRenderBuffer = depthRenderbuffer;
    
    // restore FBO
    useFBO(oldFBO);
    return fbo;
}
Ejemplo n.º 21
0
void EJCanvasContext::create()
{
#ifdef _WINDOWS
	if( msaaEnabled ) {
		glGenFramebuffersEXT(1, &msaaFrameBuffer);
		glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, msaaFrameBuffer);

		glGenRenderbuffersEXT(1, &msaaRenderBuffer);
		glBindRenderbufferEXT(GL_RENDERBUFFER_EXT, msaaRenderBuffer);

		//glRenderbufferStorageMultisampleIMG(GL_RENDERBUFFER, msaaSamples, GL_RGBA8, bufferWidth, bufferHeight);
		glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER_EXT, msaaRenderBuffer);
	}

	glGenFramebuffersEXT(1, &viewFrameBuffer);
	glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, viewFrameBuffer);

	glGenRenderbuffersEXT(1, &viewRenderBuffer);
	glBindRenderbufferEXT(GL_RENDERBUFFER_EXT, viewRenderBuffer);

#else
	if( msaaEnabled ) {
		glGenFramebuffersOES(1, &msaaFrameBuffer);
		glBindFramebufferOES(GL_FRAMEBUFFER_OES, msaaFrameBuffer);

		glGenRenderbuffersOES(1, &msaaRenderBuffer);
		glBindRenderbufferOES(GL_RENDERBUFFER_OES, msaaRenderBuffer);

		//glRenderbufferStorageMultisampleIMG(GL_RENDERBUFFER_OES, msaaSamples, GL_RGBA8_OES, bufferWidth, bufferHeight);
		glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, msaaRenderBuffer);
	}

	 glGenFramebuffersOES(1, &viewFrameBuffer);
	 glBindFramebufferOES(GL_FRAMEBUFFER_OES, viewFrameBuffer);

	 glGenRenderbuffersOES(1, &viewRenderBuffer);
	 glBindRenderbufferOES(GL_RENDERBUFFER_OES, viewRenderBuffer);
#endif

}
Ejemplo n.º 22
0
		virtual GLenum createFBO(GLuint& framebuffer, GLuint& depthbuffer, GLuint& img, int width, int height)
		{
			// get currently bound fbo to reset to it later
			GLint current_fbo;
			glGetIntegerv(GL_FRAMEBUFFER_BINDING_OES, &current_fbo);

			// generate depth buffer
			glGenRenderbuffersOES(1, &depthbuffer);
			glBindRenderbufferOES(GL_RENDERBUFFER_OES, depthbuffer);
			glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_DEPTH_COMPONENT16_OES, width, height);
			glBindRenderbufferOES(GL_RENDERBUFFER_OES, 0);

			// generate texture save target
			glGenTextures(1, &img);
			glBindTexture(GL_TEXTURE_2D, img);
			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
			
			glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8_OES, width, height,
					0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
			glBindTexture(GL_TEXTURE_2D, 0);

			// create framebuffer
			glGenFramebuffersOES(1, &framebuffer);
			glBindFramebufferOES(GL_FRAMEBUFFER_OES, framebuffer);
			glFramebufferTexture2DOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES,
					GL_TEXTURE_2D, img, 0);
			glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES,
					GL_RENDERBUFFER_OES, depthbuffer);
			GLenum status = glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES);

			// unbind framebuffer
			glBindFramebufferOES(GL_FRAMEBUFFER_OES, (GLuint)current_fbo);
			return status;
		}
Ejemplo n.º 23
0
void RenderingEngine::Initialize(const vector<ISurface*>& surfaces)
{
    vector<ISurface*>::const_iterator surface;
    for (surface = surfaces.begin(); surface != surfaces.end(); ++surface) {
        
        // Create the VBO for the vertices.
        vector<float> vertices;
        unsigned char vertexFlags = VertexFlagsNormals | VertexFlagsTexCoords;
        (*surface)->GenerateVertices(vertices, vertexFlags);
        GLuint vertexBuffer;
        glGenBuffers(1, &vertexBuffer);
        glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
        glBufferData(GL_ARRAY_BUFFER,
                     vertices.size() * sizeof(vertices[0]),
                     &vertices[0],
                     GL_STATIC_DRAW);
        
        // Create a new VBO for the indices if needed.
        int indexCount = (*surface)->GetTriangleIndexCount();
        GLuint indexBuffer;
        if (!m_drawables.empty() && indexCount == m_drawables[0].IndexCount) {
            indexBuffer = m_drawables[0].IndexBuffer;
        } else {
            vector<GLushort> indices(indexCount);
            (*surface)->GenerateTriangleIndices(indices);
            glGenBuffers(1, &indexBuffer);
            glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
            glBufferData(GL_ELEMENT_ARRAY_BUFFER,
                         indexCount * sizeof(GLushort),
                         &indices[0],
                         GL_STATIC_DRAW);
        }
        
        Drawable drawable = { vertexBuffer, indexBuffer, indexCount};
        m_drawables.push_back(drawable);
    }

    // Extract width and height from the color buffer.
    int width, height;
    glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES,
                                    GL_RENDERBUFFER_WIDTH_OES, &width);
    glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES,
                                    GL_RENDERBUFFER_HEIGHT_OES, &height);

    // Create a depth buffer that has the same size as the color buffer.
    glGenRenderbuffersOES(1, &m_depthRenderbuffer);
    glBindRenderbufferOES(GL_RENDERBUFFER_OES, m_depthRenderbuffer);
    glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_DEPTH_COMPONENT16_OES,
                             width, height);

    // Create the framebuffer object.
    GLuint framebuffer;
    glGenFramebuffersOES(1, &framebuffer);
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, framebuffer);
    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES,
                                 GL_RENDERBUFFER_OES, m_colorRenderbuffer);
    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES,
                                 GL_RENDERBUFFER_OES, m_depthRenderbuffer);
    glBindRenderbufferOES(GL_RENDERBUFFER_OES, m_colorRenderbuffer);

    void* pixels;
    ivec2 size;

    // Load the background texture.
    glGenTextures(1, &m_backgroundTexture);
    glBindTexture(GL_TEXTURE_2D, m_backgroundTexture);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); 
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
    m_resourceManager->LoadPngImage("Background");
    pixels = m_resourceManager->GetImageData();
    size = m_resourceManager->GetImageSize();
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, size.x, size.y, 0, GL_RGB, GL_UNSIGNED_BYTE, pixels);
    m_resourceManager->UnloadImage();
    
    // Load the checkboard texture.
    glGenTextures(1, &m_gridTexture);
    glBindTexture(GL_TEXTURE_2D, m_gridTexture);
    glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); 
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
    m_resourceManager->LoadPngImage("Checkerboard");
    pixels = m_resourceManager->GetImageData();
    size = m_resourceManager->GetImageSize();
    glTexImage2D(GL_TEXTURE_2D, 0, GL_LUMINANCE, size.x, size.y, 0, GL_LUMINANCE, GL_UNSIGNED_BYTE, pixels);
    m_resourceManager->UnloadImage();

    // Set up various GL state.
    glEnableClientState(GL_VERTEX_ARRAY);
    glEnableClientState(GL_NORMAL_ARRAY);
    glEnableClientState(GL_TEXTURE_COORD_ARRAY);
    glEnable(GL_LIGHTING);
    glEnable(GL_LIGHT0);
    glEnable(GL_DEPTH_TEST);
    glEnable(GL_TEXTURE_2D);
    
    // Set up the material properties.
    vec4 specular(0.5f, 0.5f, 0.5f, 1);
    glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, specular.Pointer());
    glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, 50.0f);

    m_translation = mat4::Translate(0, 0, -7);
}
Ejemplo n.º 24
0
 void RenderingEngine::Initialize(const vector<ISurface*>& surfaces)
 {
     vector<ISurface*>::const_iterator surface;
     for (surface = surfaces.begin(); surface != surfaces.end(); ++surface) {
         
         // Create the VBO for the vertices.
         vector<float> vertices;
         (*surface)->GenerateVertices(vertices, VertexFlagsNormals);
         GLuint vertexBuffer;
         glGenBuffers(1, &vertexBuffer);
         glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
         glBufferData(GL_ARRAY_BUFFER,
                      vertices.size() * sizeof(vertices[0]),
                      &vertices[0],
                      GL_STATIC_DRAW);
         
         // Create a new VBO for the indices if needed.
         int indexCount = (*surface)->GetTriangleIndexCount();
         GLuint indexBuffer;
         if (!m_drawables.empty() && indexCount == m_drawables[0].IndexCount) {
             indexBuffer = m_drawables[0].IndexBuffer;
         } else {
             vector<GLushort> indices(indexCount);
             (*surface)->GenerateTriangleIndices(indices);
             glGenBuffers(1, &indexBuffer);
             glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
             glBufferData(GL_ELEMENT_ARRAY_BUFFER,
                          indexCount * sizeof(GLushort),
                          &indices[0],
                          GL_STATIC_DRAW);
         }
         
         Drawable drawable = { vertexBuffer, indexBuffer, indexCount};
         m_drawables.push_back(drawable);
     }
     
     // Extract width and height from the color buffer.
     int width, height;
     glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES,
                                     GL_RENDERBUFFER_WIDTH_OES, &width);
     glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES,
                                     GL_RENDERBUFFER_HEIGHT_OES, &height);
     
     // Create a depth buffer that has the same size as the color buffer.
     glGenRenderbuffersOES(1, &m_depthRenderbuffer);
     glBindRenderbufferOES(GL_RENDERBUFFER_OES, m_depthRenderbuffer);
     glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_DEPTH_COMPONENT16_OES,
                              width, height);
     
     // Create the framebuffer object.
     GLuint framebuffer;
     glGenFramebuffersOES(1, &framebuffer);
     glBindFramebufferOES(GL_FRAMEBUFFER_OES, framebuffer);
     glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES,
                                  GL_RENDERBUFFER_OES, m_colorRenderbuffer);
     glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_DEPTH_ATTACHMENT_OES,
                                  GL_RENDERBUFFER_OES, m_depthRenderbuffer);
     glBindRenderbufferOES(GL_RENDERBUFFER_OES, m_colorRenderbuffer);
     
     // Set up various GL state.
     glEnableClientState(GL_VERTEX_ARRAY);
     glEnableClientState(GL_NORMAL_ARRAY);
     glEnable(GL_LIGHTING);
     glEnable(GL_LIGHT0);
     glEnable(GL_DEPTH_TEST);
     
     // Set up the material properties.
     vec4 specular(0.5f, 0.5f, 0.5f, 1);
     glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, specular.Pointer());
     glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, 50.0f);
     
     m_translation = mat4::Translate(0, 0, -7);
 }
void GLESFrameBufferObject::initialise()
{
    // Release depth and stencil, if they were bound
    mManager->releaseRenderBuffer(mDepth);
    mManager->releaseRenderBuffer(mStencil);
    mManager->releaseRenderBuffer(mMultisampleColourBuffer);
    /// First buffer must be bound
    if(!mColour[0].buffer)
    {
        OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                    "Attachment 0 must have surface attached",
                    "GLESFrameBufferObject::initialise");
    }

    // If we're doing multisampling, then we need another FBO which contains a
    // renderbuffer which is set up to multisample, and we'll blit it to the final
    // FBO afterwards to perform the multisample resolve. In that case, the
    // mMultisampleFB is bound during rendering and is the one with a depth/stencil

    /// Store basic stats
    size_t width = mColour[0].buffer->getWidth();
    size_t height = mColour[0].buffer->getHeight();
    GLuint format = mColour[0].buffer->getGLFormat();

    // Bind simple buffer to add colour attachments
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, mFB);
    GL_CHECK_ERROR;

    /// Bind all attachment points to frame buffer
    for(size_t x=0; x<OGRE_MAX_MULTIPLE_RENDER_TARGETS; ++x)
    {
        if(mColour[x].buffer)
        {
            if(mColour[x].buffer->getWidth() != width || mColour[x].buffer->getHeight() != height)
            {
                StringStream ss;
                ss << "Attachment " << x << " has incompatible size ";
                ss << mColour[x].buffer->getWidth() << "x" << mColour[x].buffer->getHeight();
                ss << ". It must be of the same as the size of surface 0, ";
                ss << width << "x" << height;
                ss << ".";
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS, ss.str(), "GLESFrameBufferObject::initialise");
            }
            if(mColour[x].buffer->getGLFormat() != format)
            {
                StringStream ss;
                ss << "Attachment " << x << " has incompatible format.";
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS, ss.str(), "GLESFrameBufferObject::initialise");
            }
            mColour[x].buffer->bindToFramebuffer(GL_COLOR_ATTACHMENT0_OES+x, mColour[x].zoffset);
        }
        else
        {
            // Detach
            glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES+x,
                                         GL_RENDERBUFFER_OES, 0);
            GL_CHECK_ERROR;
        }
    }

    // Now deal with depth / stencil
    if (mMultisampleFB)
    {
        // Bind multisample buffer
        glBindFramebufferOES(GL_FRAMEBUFFER_OES, mMultisampleFB);
        GL_CHECK_ERROR;

        // Create AA render buffer (colour)
        // note, this can be shared too because we blit it to the final FBO
        // right after the render is finished
        mMultisampleColourBuffer = mManager->requestRenderBuffer(format, width, height, mNumSamples);

        // Attach it, because we won't be attaching below and non-multisample has
        // actually been attached to other FBO
        mMultisampleColourBuffer.buffer->bindToFramebuffer(GL_COLOR_ATTACHMENT0_OES,
                mMultisampleColourBuffer.zoffset);

        // depth & stencil will be dealt with below
    }

    /// Depth buffer is not handled here anymore.
    /// See GLESFrameBufferObject::attachDepthBuffer() & RenderSystem::setDepthBufferFor()

    /// Do glDrawBuffer calls
    GLenum bufs[OGRE_MAX_MULTIPLE_RENDER_TARGETS];
    for(size_t x=0; x<OGRE_MAX_MULTIPLE_RENDER_TARGETS; ++x)
    {
        // Fill attached colour buffers
        if(mColour[x].buffer)
        {
            bufs[x] = GL_COLOR_ATTACHMENT0_OES + x;
        }
        else
        {
            bufs[x] = GL_NONE;
        }
    }

    /// Check status
    GLuint status;
    status = glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES);
    GL_CHECK_ERROR;

    /// Bind main buffer
#if OGRE_PLATFORM == OGRE_PLATFORM_APPLE_IOS
    // The screen buffer is 1 on iOS
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, 1);
#else
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, 0);
#endif
    GL_CHECK_ERROR;

    switch(status)
    {
    case GL_FRAMEBUFFER_COMPLETE_OES:
        // All is good
        break;
    case GL_FRAMEBUFFER_UNSUPPORTED_OES:
        OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                    "All framebuffer formats with this texture internal format unsupported",
                    "GLESFrameBufferObject::initialise");
    default:
        OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                    "Framebuffer incomplete or other FBO status error",
                    "GLESFrameBufferObject::initialise");
    }

}
Ejemplo n.º 26
0
void GL11Renderer::Initialize( int width, int height )
{
    //
    // Buffer Setup...
    //
    
    // Create the depth buffer.
    glGenRenderbuffersOES( 1, &m_depthRenderbuffer );
    glBindRenderbufferOES( GL_RENDERBUFFER_OES, m_depthRenderbuffer );
    glRenderbufferStorageOES( GL_RENDERBUFFER_OES,
                              GL_DEPTH_COMPONENT16_OES,
                              width,
                              height );
    
    // Create the framebuffer object; attach the depth and color buffers.
    glGenFramebuffersOES( 1, &m_framebuffer );
    glBindFramebufferOES( GL_FRAMEBUFFER_OES, m_framebuffer );
    glFramebufferRenderbufferOES( GL_FRAMEBUFFER_OES,
                                  GL_COLOR_ATTACHMENT0_OES,
                                  GL_RENDERBUFFER_OES,
                                  m_colorRenderbuffer );
    glFramebufferRenderbufferOES( GL_FRAMEBUFFER_OES,
                                  GL_DEPTH_ATTACHMENT_OES,
                                  GL_RENDERBUFFER_OES,
                                  m_depthRenderbuffer );
    
    // Bind the color buffer for rendering.
    glBindRenderbufferOES( GL_RENDERBUFFER_OES, m_colorRenderbuffer );

    //
    // General Setup...
    //
    
    glEnable( GL_TEXTURE_2D );
    glDisable( GL_LIGHTING );
    
    //
    // Point Sprites...
    //
    
    glEnable( GL_POINT_SPRITE_OES );
    glTexEnvi( GL_POINT_SPRITE_OES, GL_COORD_REPLACE_OES, GL_TRUE );
    glTexEnvi( GL_POINT_SPRITE_OES, GL_COORD_REPLACE_OES, GL_FALSE );
    //glPointSize( 10.0f );
    
    // This helps as a work around for order-dependency artifacts that can occur when sprites overlap.
    glBlendFunc( GL_SRC_ALPHA, GL_ONE );
    
    //
    // Texture Setup...
    //

    glGenTextures( 1, &m_snowTextureId );
    glBindTexture( GL_TEXTURE_2D, m_snowTextureId );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
    TextureDescription desc = m_resourceLoader->LoadPngImage( "snow.png" );
    GLvoid* pixels = m_resourceLoader->GetImageData();
    glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA, desc.Width, desc.Height, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixels );
    m_resourceLoader->UnloadImage();

    //
    // VBO Setup for Snow Flakes...
    //
    
    for( int i = 0; i < MaxSnowFlakes; ++i )
    {
		m_pos[i][0] = RandomFloat( -ViewMaxX, ViewMaxX );
        m_pos[i][1] = RandomFloat( -ViewMaxY, ViewMaxY );
        
		m_vel[i][0] = RandomFloat( -0.004f, 0.004f ); // Flakes move side to side
		m_vel[i][1] = RandomFloat( -0.01f, -0.008f ); // Flakes fall down
        
		m_col[i][0] = 1.0f;
		m_col[i][1] = 1.0f;
		m_col[i][2] = 1.0f;
		m_col[i][3] = 1.0f; //RandomFloat( 0.6f, 1.0f ); // It seems that Doodle Jump snow does not use alpha.
        
        m_size[i] = RandomFloat( 3.0, 6.0f );
        
        // It looks strange if the flakes all turn at the same time, so
        // lets vary their turn times with a random negative value.
        m_timeSinceLastTurn[i] = RandomFloat( -5.0, 0.0f );
	}

    // VBO for vertex positions.
    glGenBuffers( 1, &m_vertexBufferId );
    glBindBuffer( GL_ARRAY_BUFFER, m_vertexBufferId );
    glBufferData( GL_ARRAY_BUFFER, sizeof(m_pos), m_pos, GL_DYNAMIC_DRAW );
    glBindBuffer( GL_ARRAY_BUFFER, 0 );
    
// TODO: Due to the possibility of cache misses, it might be a little faster to
//       combine the colors and point sizes into an interleaved array, but it
//       seems that this optimization makes less sense on newer CPUs.

    // VBO for vertex colors.
    glGenBuffers( 1, &m_colorBufferId );
    glBindBuffer( GL_ARRAY_BUFFER, m_colorBufferId );
    glBufferData( GL_ARRAY_BUFFER, sizeof(m_col), m_col, GL_STATIC_DRAW );
    glBindBuffer( GL_ARRAY_BUFFER, 0 );
    
    // VBO for point sizes of point sprites.
    glGenBuffers( 1, &m_pointSizeBufferId );
    glBindBuffer( GL_ARRAY_BUFFER, m_pointSizeBufferId );
    glBufferData( GL_ARRAY_BUFFER, sizeof(m_size), m_size, GL_STATIC_DRAW );
    glBindBuffer( GL_ARRAY_BUFFER, 0 );
 
    //
    // View Settings...
    //

    glViewport( 0, 0, width, height );

    // Initialize the projection matrix to orthogrpahic and create 
    // a flat 2D game space that is 2 units wide and 3 units high.
    glMatrixMode( GL_PROJECTION );
    glOrthof( -ViewMaxX, +ViewMaxX, -ViewMaxY, +ViewMaxY, -1, 1 );
}
Ejemplo n.º 27
0
void RenderingEngine::Initialize()
{
    // Create vertices for full-screen quad.
    m_backgroundVertices.resize(4);
    m_backgroundVertices[0].Position = vec3(-1, -1.5, 0);
    m_backgroundVertices[0].TexCoord = vec2(0, 0);
    m_backgroundVertices[1].Position = vec3(-1, 1.5, 0);
    m_backgroundVertices[1].TexCoord = vec2(0, 1);
    m_backgroundVertices[2].Position = vec3(1, -1.5, 0);
    m_backgroundVertices[2].TexCoord = vec2(1, 0);
    m_backgroundVertices[3].Position = vec3(1, 1.5, 0);
    m_backgroundVertices[3].TexCoord = vec2(1, 1);

    if (false) {
        m_backgroundVertices[0].TexCoord *= 0.3;
        m_backgroundVertices[1].TexCoord *= 0.3;
        m_backgroundVertices[2].TexCoord *= 0.3;
        m_backgroundVertices[3].TexCoord *= 0.3;
    }
    
    // Create the line-based stick figure.
    size_t indexCount = sizeof(StickFigureIndices) / sizeof(GLushort);
    size_t lineCount = indexCount / 2;
    m_stickFigure.Indices = IndexList(StickFigureIndices, StickFigureIndices + indexCount);
    glGenBuffers(1, &m_stickFigure.IndexBuffer);
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_stickFigure.IndexBuffer);
    glBufferData(GL_ELEMENT_ARRAY_BUFFER,
                 m_stickFigure.Indices.size() * sizeof(GLushort),
                 &m_stickFigure.Indices[0],
                 GL_STATIC_DRAW);
    m_stickFigure.Vertices.resize(JointCount);
    
    // Create the triangle-based stick figure.
    GenerateTriangleIndices(lineCount, m_aaStickFigure.Indices);
    glGenBuffers(1, &m_aaStickFigure.IndexBuffer);
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_aaStickFigure.IndexBuffer);
    glBufferData(GL_ELEMENT_ARRAY_BUFFER,
                 m_aaStickFigure.Indices.size() * sizeof(GLushort),
                 &m_aaStickFigure.Indices[0],
                 GL_STATIC_DRAW);
    m_aaStickFigure.Vertices.resize(lineCount * 8);
    GenerateTriangleTexCoords(m_aaStickFigure);

    // Initialize the demo state.
    m_demoState = DemoStateAaLines;
    
    // Load up some textures.
    m_textures.Tile = CreateTexture(Tile);
    m_textures.Circle = CreateTexture(Circle);
    m_textures.BlurryCircle = CreateTexture(BlurryCircle);

    // Extract width and height from the color buffer.
    ivec2 screenSize;
    glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES,
                                    GL_RENDERBUFFER_WIDTH_OES, &screenSize.x);
    glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES,
                                    GL_RENDERBUFFER_HEIGHT_OES, &screenSize.y);
    
    // Create the on-screen FBO.
    glGenFramebuffersOES(1, &m_framebuffers.Screen);
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, m_framebuffers.Screen);
    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES,
                                 GL_RENDERBUFFER_OES, m_renderbuffers.Screen);
    
    // Set up various GL state.
    glEnableClientState(GL_VERTEX_ARRAY);
    glEnableClientState(GL_TEXTURE_COORD_ARRAY);
    glEnable(GL_TEXTURE_2D);
    glViewport(0, 0, screenSize.x, screenSize.y);
    glAlphaFunc(GL_LESS, 0.5);
    
    // Set up the transforms.
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    
    const float NearPlane = 5, FarPlane = 100;
    const float Scale = 0.0005;
    glFrustumf(-Scale * screenSize.x / 2, Scale * screenSize.x / 2,
               -Scale * screenSize.y / 2, Scale * screenSize.y / 2,
               NearPlane, FarPlane);
    
    glMatrixMode(GL_MODELVIEW);
}
Ejemplo n.º 28
0
status_t SurfaceFlinger::captureScreenImplLocked(DisplayID dpy,
        sp<IMemoryHeap>* heap,
        uint32_t* w, uint32_t* h, PixelFormat* f,
        uint32_t sw, uint32_t sh)
{
   LOGI("captureScreenImplLocked");
    status_t result = PERMISSION_DENIED;

    // only one display supported for now
    if (UNLIKELY(uint32_t(dpy) >= DISPLAY_COUNT))
        return BAD_VALUE;

    if (!GLExtensions::getInstance().haveFramebufferObject())
        return INVALID_OPERATION;

    // get screen geometry
    const DisplayHardware& hw(graphicPlane(dpy).displayHardware());
    const uint32_t hw_w = hw.getWidth();
    const uint32_t hw_h = hw.getHeight();

    if ((sw > hw_w) || (sh > hw_h))
        return BAD_VALUE;

    sw = (!sw) ? hw_w : sw;
    sh = (!sh) ? hw_h : sh;
    const size_t size = sw * sh * 4;

    // make sure to clear all GL error flags
    while ( glGetError() != GL_NO_ERROR ) ;

    // create a FBO
    GLuint name, tname;
    glGenRenderbuffersOES(1, &tname);
    glBindRenderbufferOES(GL_RENDERBUFFER_OES, tname);
    glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_RGBA8_OES, sw, sh);
    glGenFramebuffersOES(1, &name);
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, name);
    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES,
            GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, tname);

    GLenum status = glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES);
    if (status == GL_FRAMEBUFFER_COMPLETE_OES) {

        // invert everything, b/c glReadPixel() below will invert the FB
        glViewport(0, 0, sw, sh);
        glScissor(0, 0, sw, sh);
        glMatrixMode(GL_PROJECTION);
        glPushMatrix();
        glLoadIdentity();
        glOrthof(0, hw_w, 0, hw_h, 0, 1);
        glMatrixMode(GL_MODELVIEW);

        // redraw the screen entirely...
        glClearColor(0,0,0,1);
        glClear(GL_COLOR_BUFFER_BIT);

        const Vector< sp<LayerBase> >& layers(mVisibleLayersSortedByZ);
        const size_t count = layers.size();
        for (size_t i=0 ; i<count ; ++i) {
            const sp<LayerBase>& layer(layers[i]);
            layer->drawForSreenShot();
        }

        // XXX: this is needed on tegra
        glScissor(0, 0, sw, sh);

        // check for errors and return screen capture
        if (glGetError() != GL_NO_ERROR) {
            // error while rendering
            result = INVALID_OPERATION;
        } else {
            // allocate shared memory large enough to hold the
            // screen capture
            sp<MemoryHeapBase> base(
                    new MemoryHeapBase(size, 0, "screen-capture") );
            void* const ptr = base->getBase();
            if (ptr) {
                // capture the screen with glReadPixels()
                glReadPixels(0, 0, sw, sh, GL_RGBA, GL_UNSIGNED_BYTE, ptr);
                if (glGetError() == GL_NO_ERROR) {
                    *heap = base;
                    *w = sw;
                    *h = sh;
                    *f = PIXEL_FORMAT_RGBA_8888;
                    result = NO_ERROR;
                }
            } else {
                result = NO_MEMORY;
            }
        }
        glEnable(GL_SCISSOR_TEST);
        glViewport(0, 0, hw_w, hw_h);
        glMatrixMode(GL_PROJECTION);
        glPopMatrix();
        glMatrixMode(GL_MODELVIEW);


    } else {
        result = BAD_VALUE;
    }

    // release FBO resources
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, 0);
    glDeleteRenderbuffersOES(1, &tname);
    glDeleteFramebuffersOES(1, &name);

    hw.compositionComplete();

    return result;
}
    //-----------------------------------------------------------------------------  
    // Very fast texture-to-texture blitter and hardware bi/trilinear scaling implementation using FBO
    // Destination texture must be 2D
    // Source texture must be 2D
    // Supports compressed formats as both source and destination format, it will use the hardware DXT compressor
    // if available.
    // @author W.J. van der Laan
    void GLESTextureBuffer::blitFromTexture(GLESTextureBuffer *src, const Image::Box &srcBox, const Image::Box &dstBox)
    {
        if(Root::getSingleton().getRenderSystem()->getCapabilities()->hasCapability(RSC_FBO) == false)
        {
            // the following code depends on FBO support, it crashes if FBO is not supported.
            // TODO - write PBUFFER version of this function or a version that doesn't require FBO
            return; // for now - do nothing.
        }

//        std::cerr << "GLESTextureBuffer::blitFromTexture " <<
//        src->mTextureID << ":" << srcBox.left << "," << srcBox.top << "," << srcBox.right << "," << srcBox.bottom << " " << 
//        mTextureID << ":" << dstBox.left << "," << dstBox.top << "," << dstBox.right << "," << dstBox.bottom << std::endl;

        // Store reference to FBO manager
        GLESFBOManager *fboMan = static_cast<GLESFBOManager *>(GLESRTTManager::getSingletonPtr());
        
        // Save and clear GL state for rendering
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT |  GL_STENCIL_BUFFER_BIT);
        
        RenderSystem* rsys = Root::getSingleton().getRenderSystem();
        rsys->_disableTextureUnitsFrom(0);

        // Disable alpha, depth and scissor testing, disable blending, 
        // disable culling, disble lighting, disable fog and reset foreground
        // colour.
        glDisable(GL_ALPHA_TEST);
        glDisable(GL_DEPTH_TEST);
        glDisable(GL_SCISSOR_TEST);
        glDisable(GL_BLEND);
        glDisable(GL_CULL_FACE);
        glDisable(GL_LIGHTING);
        glDisable(GL_FOG);
        glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
        GL_CHECK_ERROR;

        // Save and reset matrices
        glMatrixMode(GL_MODELVIEW);
        glPushMatrix();
        glLoadIdentity();
        glMatrixMode(GL_PROJECTION);
        glPushMatrix();
        glLoadIdentity();
        glMatrixMode(GL_TEXTURE);
        glPushMatrix();
        glLoadIdentity();
        GL_CHECK_ERROR;
        
        // Set up source texture
        glBindTexture(src->mTarget, src->mTextureID);
        GL_CHECK_ERROR;
        
        // Set filtering modes depending on the dimensions and source
        if(srcBox.getWidth()==dstBox.getWidth() &&
           srcBox.getHeight()==dstBox.getHeight() &&
           srcBox.getDepth()==dstBox.getDepth())
        {
            // Dimensions match -- use nearest filtering (fastest and pixel correct)
            glTexParameteri(src->mTarget, GL_TEXTURE_MIN_FILTER, GL_NEAREST_MIPMAP_NEAREST);
            GL_CHECK_ERROR;
            glTexParameteri(src->mTarget, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
            GL_CHECK_ERROR;
        }
        else
        {
            // Dimensions don't match -- use bi or trilinear filtering depending on the
            // source texture.
            if(src->mUsage & TU_AUTOMIPMAP)
            {
                // Automatic mipmaps, we can safely use trilinear filter which
                // brings greatly imporoved quality for minimisation.
                glTexParameteri(src->mTarget, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
                GL_CHECK_ERROR;
                glTexParameteri(src->mTarget, GL_TEXTURE_MAG_FILTER, GL_LINEAR);    
                GL_CHECK_ERROR;
            }
            else
            {
                // Manual mipmaps, stay safe with bilinear filtering so that no
                // intermipmap leakage occurs.
                glTexParameteri(src->mTarget, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
                GL_CHECK_ERROR;
                glTexParameteri(src->mTarget, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
                GL_CHECK_ERROR;
            }
        }
        // Clamp to edge (fastest)
        glTexParameteri(src->mTarget, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
        GL_CHECK_ERROR;
        glTexParameteri(src->mTarget, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
        GL_CHECK_ERROR;
        
        // Store old binding so it can be restored later
        GLint oldfb;
        glGetIntegerv(GL_FRAMEBUFFER_BINDING_OES, &oldfb);
        GL_CHECK_ERROR;

        // Set up temporary FBO
        glBindFramebufferOES(GL_FRAMEBUFFER_OES, fboMan->getTemporaryFBO());
        GL_CHECK_ERROR;

        GLuint tempTex = 0;
        if(!fboMan->checkFormat(mFormat))
        {
            // If target format not directly supported, create intermediate texture
            GLenum tempFormat = GLESPixelUtil::getClosestGLInternalFormat(fboMan->getSupportedAlternative(mFormat));
            glGenTextures(1, &tempTex);
            GL_CHECK_ERROR;
            glBindTexture(GL_TEXTURE_2D, tempTex);
            GL_CHECK_ERROR;
            // Allocate temporary texture of the size of the destination area
            glTexImage2D(GL_TEXTURE_2D, 0, tempFormat, 
                         GLESPixelUtil::optionalPO2(dstBox.getWidth()), GLESPixelUtil::optionalPO2(dstBox.getHeight()), 
                         0, GL_RGBA, GL_UNSIGNED_BYTE, 0);
            GL_CHECK_ERROR;
            glFramebufferTexture2DOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES,
                                      GL_TEXTURE_2D, tempTex, 0);
            GL_CHECK_ERROR;
            // Set viewport to size of destination slice
            glViewport(0, 0, dstBox.getWidth(), dstBox.getHeight());
            GL_CHECK_ERROR;
        }
        else
        {
            // We are going to bind directly, so set viewport to size and position of destination slice
            glViewport(dstBox.left, dstBox.top, dstBox.getWidth(), dstBox.getHeight());
            GL_CHECK_ERROR;
        }
        
        // Process each destination slice
        for(size_t slice=dstBox.front; slice<dstBox.back; ++slice)
        {
            if(!tempTex)
            {
                /// Bind directly
                bindToFramebuffer(GL_COLOR_ATTACHMENT0_OES, slice);
            }

            if(tempTex)
            {
                // Copy temporary texture
                glBindTexture(mTarget, mTextureID);
                GL_CHECK_ERROR;
                switch(mTarget)
                {
                    case GL_TEXTURE_2D:
#if OGRE_PLATFORM == OGRE_PLATFORM_ANDROID
                    case GL_TEXTURE_CUBE_MAP_OES:
#endif
                        glCopyTexSubImage2D(mFaceTarget, mLevel, 
                                            dstBox.left, dstBox.top, 
                                            0, 0, dstBox.getWidth(), dstBox.getHeight());
                        GL_CHECK_ERROR;
                        break;
                }
            }
        }
        // Finish up 
        if(!tempTex)
        {
            // Generate mipmaps
            if(mUsage & TU_AUTOMIPMAP)
            {
                glBindTexture(mTarget, mTextureID);
                GL_CHECK_ERROR;
                glGenerateMipmapOES(mTarget);
                GL_CHECK_ERROR;
            }
        }
        
        // Reset source texture to sane state
        glBindTexture(src->mTarget, src->mTextureID);
        GL_CHECK_ERROR;
        
        // Detach texture from temporary framebuffer
        glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES,
                                     GL_RENDERBUFFER_OES, 0);
        GL_CHECK_ERROR;
        // Restore old framebuffer
        glBindFramebufferOES(GL_FRAMEBUFFER_OES, oldfb);
        GL_CHECK_ERROR;
        // Restore matrix stacks and render state
        glMatrixMode(GL_TEXTURE);
        glPopMatrix();
        glMatrixMode(GL_PROJECTION);
        glPopMatrix();
        glMatrixMode(GL_MODELVIEW);
        glPopMatrix();
        GL_CHECK_ERROR;
        glDeleteTextures(1, &tempTex);
        GL_CHECK_ERROR;
    }
void glFramebufferRenderbufferOESLogged(GLenum target, GLenum attachment, GLenum renderbuffertarget, GLuint renderbuffer) {
	printf("glFramebufferRenderbufferOES(%s, %s, %s, %u)\n", GLEnumName(target), GLEnumName(attachment), GLEnumName(renderbuffertarget), renderbuffer);
	glFramebufferRenderbufferOES(target, attachment, renderbuffertarget, renderbuffer);
}