From 5d0d26164c95eed2cd04ab46136b66d416bde4f8 Mon Sep 17 00:00:00 2001 From: Glenn Maynard Date: Thu, 22 Mar 2007 19:03:31 +0000 Subject: [PATCH] implement RageTextureLock with PBOs --- stepmania/src/RageDisplay_OGL.cpp | 77 +++++++++++++++++++++++++++++++ stepmania/src/RageDisplay_OGL.h | 1 + 2 files changed, 78 insertions(+) diff --git a/stepmania/src/RageDisplay_OGL.cpp b/stepmania/src/RageDisplay_OGL.cpp index d04cedda62..9d035943f4 100644 --- a/stepmania/src/RageDisplay_OGL.cpp +++ b/stepmania/src/RageDisplay_OGL.cpp @@ -2138,6 +2138,83 @@ unsigned RageDisplay_OGL::CreateTexture( return iTexHandle; } +struct RageTextureLock_OGL: public RageTextureLock, public InvalidateObject +{ +public: + RageTextureLock_OGL() + { + m_iTexHandle = 0; + m_iBuffer = 0; + + CreateObject(); + } + + ~RageTextureLock_OGL() + { + ASSERT( m_iTexHandle == 0 ); // locked! + GLExt.glDeleteBuffersARB( 1, &m_iBuffer ); + } + + /* This is called when our OpenGL context is invalidated. */ + void Invalidate() + { + m_iTexHandle = 0; + } + + void Lock( unsigned iTexHandle, RageSurface *pSurface ) + { + ASSERT( m_iTexHandle == 0 ); + ASSERT( pSurface->pixels == NULL ); + + CreateObject(); + + m_iTexHandle = iTexHandle; + GLExt.glBindBufferARB( GL_PIXEL_UNPACK_BUFFER_ARB, m_iBuffer ); + + int iSize = pSurface->h * pSurface->pitch; + GLExt.glBufferDataARB( GL_PIXEL_UNPACK_BUFFER_ARB, iSize, NULL, GL_STREAM_DRAW ); + + void *pSurfaceMemory = GLExt.glMapBufferARB( GL_PIXEL_UNPACK_BUFFER_ARB, GL_WRITE_ONLY ); + pSurface->pixels = (uint8_t *) pSurfaceMemory; + pSurface->pixels_owned = false; + } + + void Unlock( RageSurface *pSurface, bool bChanged ) + { + GLExt.glUnmapBufferARB( GL_PIXEL_UNPACK_BUFFER_ARB ); + + pSurface->pixels = (uint8_t *) BUFFER_OFFSET(0); + + if( bChanged ) + DISPLAY->UpdateTexture( m_iTexHandle, pSurface, 0, 0, pSurface->w, pSurface->h ); + + pSurface->pixels = NULL; + + m_iTexHandle = 0; + GLExt.glBindBufferARB( GL_PIXEL_UNPACK_BUFFER_ARB, 0 ); + } + +private: + void CreateObject() + { + if( m_iBuffer != 0 ) + return; + + FlushGLErrors(); + GLExt.glGenBuffersARB( 1, &m_iBuffer ); + AssertNoGLError(); + } + + GLuint m_iBuffer; + + unsigned m_iTexHandle; +}; + +RageTextureLock *RageDisplay_OGL::CreateTextureLock() +{ + return new RageTextureLock_OGL; +} + void RageDisplay_OGL::UpdateTexture( unsigned iTexHandle, RageSurface* pImg, diff --git a/stepmania/src/RageDisplay_OGL.h b/stepmania/src/RageDisplay_OGL.h index 1decbe37d4..4df1cb7a6b 100644 --- a/stepmania/src/RageDisplay_OGL.h +++ b/stepmania/src/RageDisplay_OGL.h @@ -41,6 +41,7 @@ public: ); void DeleteTexture( unsigned iTexHandle ); RageSurface *GetTexture( unsigned iTexture ); + RageTextureLock *CreateTextureLock(); void ClearAllTextures(); int GetNumTextureUnits();