Browse Source

Various fixes to the OpenGL render backend

BearishSun 9 years ago
parent
commit
e2b1582a6e

+ 9 - 0
Source/BansheeGLRenderAPI/Include/BsGLBuffer.h

@@ -16,10 +16,19 @@ namespace BansheeEngine
     class BS_RSGL_EXPORT GLBuffer
     {
     public:
+		/** Creates an uninitialized buffer object. You must call initialize() before using it. */
 		GLBuffer();
+
+		/** Creates and initializes the buffer object. */
 		GLBuffer(GLenum target, UINT32 size, GpuBufferUsage usage);
 		~GLBuffer();
 
+		/** 
+		 * Initializes the internal buffer object. Done automatically if the buffer was constructed using non-zero
+		 * parameter constructor.
+		 */
+		void initialize(GLenum target, UINT32 size, GpuBufferUsage usage);
+
 		/**
 		 * Locks a portion of the buffer and returns pointer to the locked area. You must call unlock() when done.
 		 *

+ 15 - 5
Source/BansheeGLRenderAPI/Source/BsGLBuffer.cpp

@@ -15,6 +15,21 @@ namespace BansheeEngine
 	GLBuffer::GLBuffer(GLenum target, UINT32 size, GpuBufferUsage usage)
 		:mTarget(target), mBufferId(0), mZeroLocked(false)
 	{
+		initialize(target, size, usage);
+	}
+
+	GLBuffer::~GLBuffer()
+	{
+		if(mBufferId != 0)
+			glDeleteBuffers(1, &mBufferId);
+	}
+
+	void GLBuffer::initialize(GLenum target, UINT32 size, GpuBufferUsage usage)
+	{
+		assert(mBufferId == 0 && "Buffer already initialized");
+
+		mTarget = target;
+
 		glGenBuffers(1, &mBufferId);
 
 		if (!mBufferId)
@@ -26,11 +41,6 @@ namespace BansheeEngine
 		glBufferData(target, size, nullptr, GLHardwareBufferCoreManager::getGLUsage(usage));
 	}
 
-	GLBuffer::~GLBuffer()
-	{
-		glDeleteBuffers(1, &mBufferId);
-	}
-
 	void* GLBuffer::lock(UINT32 offset, UINT32 length, GpuLockOptions options)
 	{
 		GLenum access = 0;

+ 1 - 1
Source/BansheeGLRenderAPI/Source/BsGLGpuBuffer.cpp

@@ -37,7 +37,7 @@ namespace BansheeEngine
 		// Create buffer
 		const auto& props = getProperties();
 		UINT32 size = props.getElementCount() * props.getElementSize();
-		mBuffer = GLBuffer(GL_TEXTURE_BUFFER, size, props.getUsage());
+		mBuffer.initialize(GL_TEXTURE_BUFFER, size, props.getUsage());
 		
 		// Create texture
 		glGenTextures(1, &mTextureID);

+ 1 - 1
Source/BansheeGLRenderAPI/Source/BsGLIndexBuffer.cpp

@@ -18,7 +18,7 @@ namespace BansheeEngine
 
 	void GLIndexBufferCore::initialize()
 	{
-		mBuffer = GLBuffer(GL_ELEMENT_ARRAY_BUFFER, mSizeInBytes, mUsage);
+		mBuffer.initialize(GL_ELEMENT_ARRAY_BUFFER, mSizeInBytes, mUsage);
 
 		BS_INC_RENDER_STAT_CAT(ResCreated, RenderStatObject_IndexBuffer);
 		IndexBufferCore::initialize();

+ 1 - 1
Source/BansheeGLRenderAPI/Source/BsGLMultiRenderTexture.cpp

@@ -34,7 +34,7 @@ namespace BansheeEngine
 
 				if (mColorSurfaces[i]->getNumArraySlices() == 1) // Binding a single texture layer
 				{
-					surfaceDesc.allLayers = false;
+					surfaceDesc.allLayers = glColorSurface->getProperties().getNumFaces() == 1;
 
 					if (glColorSurface->getProperties().getTextureType() != TEX_TYPE_3D)
 					{

+ 47 - 41
Source/BansheeGLRenderAPI/Source/BsGLRenderTexture.cpp

@@ -39,60 +39,66 @@ namespace BansheeEngine
 
 		mFB = bs_new<GLFrameBufferObject>();
 
-		GLTextureCore* glTexture = static_cast<GLTextureCore*>(mColorSurface->getTexture().get());
-
-		GLSurfaceDesc surfaceDesc;
-		surfaceDesc.numSamples = getProperties().getMultisampleCount();
-
-		if(mColorSurface->getNumArraySlices() == 1) // Binding a single texture layer
+		if (mColorSurface != nullptr && mColorSurface->getTexture() != nullptr)
 		{
-			surfaceDesc.allLayers = false;
+			GLTextureCore* glTexture = static_cast<GLTextureCore*>(mColorSurface->getTexture().get());
 
-			if (glTexture->getProperties().getTextureType() != TEX_TYPE_3D)
+			GLSurfaceDesc surfaceDesc;
+			surfaceDesc.numSamples = getProperties().getMultisampleCount();
+
+			if (mColorSurface->getNumArraySlices() == 1) // Binding a single texture layer
 			{
-				surfaceDesc.zoffset = 0;
-				surfaceDesc.buffer = glTexture->getBuffer(mColorSurface->getFirstArraySlice(), mColorSurface->getMostDetailedMip());
+				surfaceDesc.allLayers = glTexture->getProperties().getNumFaces() == 1;
+
+				if (glTexture->getProperties().getTextureType() != TEX_TYPE_3D)
+				{
+					surfaceDesc.zoffset = 0;
+					surfaceDesc.buffer = glTexture->getBuffer(mColorSurface->getFirstArraySlice(), mColorSurface->getMostDetailedMip());
+				}
+				else
+				{
+					surfaceDesc.zoffset = mColorSurface->getFirstArraySlice();
+					surfaceDesc.buffer = glTexture->getBuffer(0, mColorSurface->getMostDetailedMip());
+				}
 			}
-			else
+			else // Binding an array of textures or a range of 3D texture slices
 			{
-				surfaceDesc.zoffset = mColorSurface->getFirstArraySlice();
-				surfaceDesc.buffer = glTexture->getBuffer(0, mColorSurface->getMostDetailedMip());
+				surfaceDesc.allLayers = true;
+
+				if (glTexture->getProperties().getTextureType() != TEX_TYPE_3D)
+				{
+					if (mColorSurface->getNumArraySlices() != glTexture->getProperties().getNumFaces())
+						LOGWRN("OpenGL doesn't support binding of arbitrary ranges for array textures. The entire range will be bound instead.");
+
+					surfaceDesc.zoffset = 0;
+					surfaceDesc.buffer = glTexture->getBuffer(0, mColorSurface->getMostDetailedMip());
+				}
+				else
+				{
+					if (mColorSurface->getNumArraySlices() != glTexture->getProperties().getDepth())
+						LOGWRN("OpenGL doesn't support binding of arbitrary ranges for array textures. The entire range will be bound instead.");
+
+					surfaceDesc.zoffset = 0;
+					surfaceDesc.buffer = glTexture->getBuffer(0, mColorSurface->getMostDetailedMip());
+				}
 			}
+
+			mFB->bindSurface(0, surfaceDesc);
 		}
-		else // Binding an array of textures or a range of 3D texture slices
-		{
-			surfaceDesc.allLayers = true;
 
-			if (glTexture->getProperties().getTextureType() != TEX_TYPE_3D)
-			{
-				if (mColorSurface->getNumArraySlices() != glTexture->getProperties().getNumFaces())
-					LOGWRN("OpenGL doesn't support binding of arbitrary ranges for array textures. The entire range will be bound instead.");
+		if (mDepthStencilSurface != nullptr && mDepthStencilSurface->getTexture() != nullptr)
+		{
+			GLTextureCore* glDepthStencilTexture = static_cast<GLTextureCore*>(mDepthStencilSurface->getTexture().get());
+			SPtr<GLPixelBuffer> depthStencilBuffer = nullptr;
 
-				surfaceDesc.zoffset = 0;
-				surfaceDesc.buffer = glTexture->getBuffer(0, mColorSurface->getMostDetailedMip());
-			}
-			else
+			if (glDepthStencilTexture->getProperties().getTextureType() != TEX_TYPE_3D)
 			{
-				if (mColorSurface->getNumArraySlices() != glTexture->getProperties().getDepth())
-					LOGWRN("OpenGL doesn't support binding of arbitrary ranges for array textures. The entire range will be bound instead.");
-
-				surfaceDesc.zoffset = 0;
-				surfaceDesc.buffer = glTexture->getBuffer(0, mColorSurface->getMostDetailedMip());
+				depthStencilBuffer = glDepthStencilTexture->getBuffer(mDepthStencilSurface->getFirstArraySlice(),
+					mDepthStencilSurface->getMostDetailedMip());
 			}
-		}
 
-		mFB->bindSurface(0, surfaceDesc);
-
-		GLTextureCore* glDepthStencilTexture = static_cast<GLTextureCore*>(mDepthStencilSurface->getTexture().get());
-		SPtr<GLPixelBuffer> depthStencilBuffer = nullptr;
-
-		if (glDepthStencilTexture->getProperties().getTextureType() != TEX_TYPE_3D)
-		{
-			depthStencilBuffer = glDepthStencilTexture->getBuffer(mDepthStencilSurface->getFirstArraySlice(),
-				mDepthStencilSurface->getMostDetailedMip());
+			mFB->bindDepthStencil(depthStencilBuffer);
 		}
-
-		mFB->bindDepthStencil(depthStencilBuffer);
 	}
 
 	void GLRenderTextureCore::getCustomAttribute(const String& name, void* data) const

+ 1 - 1
Source/BansheeGLRenderAPI/Source/BsGLVertexBuffer.cpp

@@ -24,7 +24,7 @@ namespace BansheeEngine
 
 	void GLVertexBufferCore::initialize()
 	{
-		mBuffer = GLBuffer(GL_ARRAY_BUFFER, mSizeInBytes, mUsage);
+		mBuffer.initialize(GL_ARRAY_BUFFER, mSizeInBytes, mUsage);
 		
 		BS_INC_RENDER_STAT_CAT(ResCreated, RenderStatObject_VertexBuffer);
 		VertexBufferCore::initialize();