2
0
Эх сурвалжийг харах

- Making the Vbo, Vao and Fbo more caching friendly
- Transform feedback skinning WIP

Panagiotis Christopoulos Charitos 15 жил өмнө
parent
commit
7d86fa0843

Файлын зөрүү хэтэрхий том тул дарагдсан байна
+ 1 - 2
build/debug/Makefile


+ 2 - 2
docs/manual.rst

@@ -1,6 +1,6 @@
 **AnKi 3D Engine**
 
-Copyright (C) 2009, 2010 Panagiotis Christopoulos-Charitos
+Copyright (C) 2009-2011 Panayiotis Christopoulos-Charitos
 
 http://www.ancient-ritual.com
 
@@ -120,7 +120,7 @@ The engine requires:
 - Linux OS
 - Proprietary GPU drivers
 
-Development rig: Ubuntu 10.04, AMD Radeon 4870 w/ Catalyst 10.04. So it should
+Development rig: Ubuntu 10.10, AMD Radeon 4870 w/ Catalyst 10.10. So it should
 be working on similar systems.
 
 

BIN
docs/resources.odg


+ 3 - 0
src/Renderer/BufferObjects/BufferObject.cpp

@@ -8,6 +8,7 @@
 //======================================================================================================================
 void BufferObject::create(GLenum target_, uint sizeInBytes_, const void* dataPtr, GLenum usage_)
 {
+	RASSERT_THROW_EXCEPTION(isCreated());
 	// unacceptable usage_
 	RASSERT_THROW_EXCEPTION(usage_ != GL_STREAM_DRAW && usage_ != GL_STATIC_DRAW && usage_ != GL_DYNAMIC_DRAW);
 	RASSERT_THROW_EXCEPTION(sizeInBytes_ < 1); // unacceptable sizeInBytes
@@ -39,6 +40,7 @@ void BufferObject::create(GLenum target_, uint sizeInBytes_, const void* dataPtr
 //======================================================================================================================
 void BufferObject::write(void* buff)
 {
+	RASSERT_THROW_EXCEPTION(!isCreated());
 	RASSERT_THROW_EXCEPTION(usage == GL_STATIC_DRAW);
 	bind();
 	void* mapped = glMapBuffer(target, GL_WRITE_ONLY);
@@ -53,6 +55,7 @@ void BufferObject::write(void* buff)
 //======================================================================================================================
 void BufferObject::write(void* buff, size_t offset, size_t size)
 {
+	RASSERT_THROW_EXCEPTION(!isCreated());
 	RASSERT_THROW_EXCEPTION(usage == GL_STATIC_DRAW);
 	RASSERT_THROW_EXCEPTION(offset + size > sizeInBytes);
 	bind();

+ 89 - 31
src/Renderer/BufferObjects/BufferObject.h

@@ -4,35 +4,44 @@
 #include <GL/glew.h>
 #include "Exception.h"
 #include "StdTypes.h"
-#include "Object.h"
-#include "Properties.h"
 
 
 /// A wrapper for OpenGL buffer objects (vertex arrays, texture buffers etc) to prevent us from making idiotic errors
-class BufferObject: public Object
+class BufferObject
 {
-	PROPERTY_R(uint, glId, getGlId) ///< The OpenGL id of the BO
-
-	/// Used in glBindBuffer(target, glId) and its for easy access so we wont have to query the GL driver. Its the type
-	/// of the buffer eg GL_TEXTURE_BUFFER or GL_ELEMENT_ARRAY_BUFFER etc
-	PROPERTY_R(GLenum, target, getBufferTarget)
-
-	PROPERTY_R(GLenum, usage, getBufferUsage) ///< GL_STREAM_DRAW or GL_STATIC_DRAW or GL_DYNAMIC_DRAW
-
-	PROPERTY_R(size_t, sizeInBytes, getSizeInBytes)
-
 	public:
+		BufferObject(): glId(0) {}
+
 		/// Default constructor @see create
-		BufferObject(GLenum target, uint sizeInBytes, const void* dataPtr, GLenum usage, Object* parent = NULL);
+		BufferObject(GLenum target, uint sizeInBytes, const void* dataPtr, GLenum usage);
 
 		/// It deletes the BO from the GL context
-		virtual ~BufferObject() {deleteBuff();}
+		virtual ~BufferObject();
+
+		/// @name Accessors
+		/// @{
+		uint getGlId() const;
+		GLenum getBufferTarget() const;
+		GLenum getBufferUsage() const;
+		size_t getSizeInBytes() const;
+		/// @]
 
 		/// Bind BO
-		void bind() const {glBindBuffer(target, glId);}
+		void bind() const;
 
 		/// Unbind BO
-		void unbind() const {glBindBuffer(target, 0);}
+		void unbind() const;
+
+		/// Creates a new BO with the given parameters and checks if everything went OK. Throws exception if fails
+		/// @param target Depends on the BO
+		/// @param sizeInBytes The size of the buffer that we will allocate in bytes
+		/// @param dataPtr Points to the data buffer to copy to the VGA memory. Put NULL if you want just to allocate memory
+		/// @param usage It should be: GL_STREAM_DRAW or GL_STATIC_DRAW or GL_DYNAMIC_DRAW only!!!!!!!!!
+		/// @exception Exception
+		void create(GLenum target, uint sizeInBytes, const void* dataPtr, GLenum usage);
+
+		/// Delete the BO
+		void deleteBuff();
 
 		/// Write data to buffer. This means that maps the BO to local memory, writes the local memory and unmaps it.
 		/// Throws exception if the given size and the BO size are not equal. It throws an exception if the usage is
@@ -46,17 +55,18 @@ class BufferObject: public Object
 		/// @param[in] size The size in bytes we want to write
 		void write(void* buff, size_t offset, size_t size);
 
+		/// If created is run successfully it returns true
+		bool isCreated() const {return glId != 0;}
+
 	private:
-		/// Creates a new BO with the given parameters and checks if everything went OK. Throws exception if fails
-		/// @param target Depends on the BO
-		/// @param sizeInBytes The size of the buffer that we will allocate in bytes
-		/// @param dataPtr Points to the data buffer to copy to the VGA memory. Put NULL if you want just to allocate memory
-		/// @param usage It should be: GL_STREAM_DRAW or GL_STATIC_DRAW or GL_DYNAMIC_DRAW only!!!!!!!!!
-		/// @exception Exception
-		void create(GLenum target, uint sizeInBytes, const void* dataPtr, GLenum usage);
+		uint glId; ///< The OpenGL id of the BO
 
-		/// Delete the BO
-		void deleteBuff();
+		/// Used in glBindBuffer(target, glId) and its for easy access so we wont have to query the GL driver. Its the type
+		/// of the buffer eg GL_TEXTURE_BUFFER or GL_ELEMENT_ARRAY_BUFFER etc
+		GLenum target;
+
+		GLenum usage; ///< GL_STREAM_DRAW or GL_STATIC_DRAW or GL_DYNAMIC_DRAW
+		size_t sizeInBytes; ///< The size of the buffer
 };
 
 
@@ -64,20 +74,68 @@ class BufferObject: public Object
 // Inlines                                                                                                             =
 //======================================================================================================================
 
-inline BufferObject::BufferObject(GLenum target, uint sizeInBytes, const void* dataPtr, GLenum usage, Object* parent):
-	Object(parent),
+inline BufferObject::BufferObject(GLenum target, uint sizeInBytes, const void* dataPtr, GLenum usage):
 	glId(0)
 {
 	create(target, sizeInBytes, dataPtr, usage);
 }
 
 
-inline void BufferObject::deleteBuff()
+inline BufferObject::~BufferObject()
 {
-	if(glId != 0)
+	if(isCreated())
 	{
-		glDeleteBuffers(1, &glId);
+		deleteBuff();
 	}
+}
+
+
+inline uint BufferObject::getGlId() const
+{
+	RASSERT_THROW_EXCEPTION(!isCreated());
+	return glId;
+}
+
+
+inline GLenum BufferObject::getBufferTarget() const
+{
+	RASSERT_THROW_EXCEPTION(!isCreated());
+	return target;
+}
+
+
+inline GLenum BufferObject::getBufferUsage() const
+{
+	RASSERT_THROW_EXCEPTION(!isCreated());
+	return usage;
+}
+
+
+inline size_t BufferObject::getSizeInBytes() const
+{
+	RASSERT_THROW_EXCEPTION(!isCreated());
+	return sizeInBytes;
+}
+
+
+inline void BufferObject::bind() const
+{
+	RASSERT_THROW_EXCEPTION(!isCreated());
+	glBindBuffer(target, glId);
+}
+
+
+inline void BufferObject::unbind() const
+{
+	RASSERT_THROW_EXCEPTION(!isCreated());
+	glBindBuffer(target, 0);
+}
+
+
+inline void BufferObject::deleteBuff()
+{
+	RASSERT_THROW_EXCEPTION(!isCreated());
+	glDeleteBuffers(1, &glId);
 	glId = 0;
 }
 

+ 48 - 21
src/Renderer/BufferObjects/Fbo.h

@@ -3,22 +3,20 @@
 
 #include <GL/glew.h>
 #include "Exception.h"
-#include "Properties.h"
 #include "StdTypes.h"
-#include "Object.h"
 
 
 /// The class is actually a wrapper to avoid common mistakes
-class Fbo: public Object
+class Fbo
 {
-	PROPERTY_R(uint, glId, getGlId) ///< OpenGL identification
-
 	public:
 		/// Constructor
-		Fbo(Object* parent = NULL);
+		Fbo(): glId(0) {}
 
-		/// Creates a new FBO
-		void create();
+		/// Destructor
+		~Fbo();
+
+		uint getGlId() const;
 
 		/// Binds FBO
 		void bind() const;
@@ -36,6 +34,17 @@ class Fbo: public Object
 		/// Returns the GL id of the current attached FBO
 		/// @return Returns the GL id of the current attached FBO
 		static uint getCurrentFbo();
+
+		/// Creates a new FBO
+		void create();
+
+		/// Destroy it
+		void destroy();
+
+	private:
+		uint glId; ///< OpenGL identification
+
+		bool isCreated() const {return glId != 0;}
 };
 
 
@@ -43,22 +52,32 @@ class Fbo: public Object
 // Inlines                                                                                                             =
 //======================================================================================================================
 
-inline Fbo::Fbo(Object* parent):
-	Object(parent),
-	glId(0)
-{}
-
-
 inline void Fbo::create()
 {
-	RASSERT_THROW_EXCEPTION(glId != 0); // FBO already initialized
+	RASSERT_THROW_EXCEPTION(isCreated());
 	glGenFramebuffers(1, &glId);
 }
 
 
+inline uint Fbo::getGlId() const
+{
+	RASSERT_THROW_EXCEPTION(isCreated());
+	return glId;
+}
+
+
+inline Fbo::~Fbo()
+{
+	if(isCreated())
+	{
+		destroy();
+	}
+}
+
+
 inline void Fbo::bind() const
 {
-	RASSERT_THROW_EXCEPTION(glId == 0);  // FBO not initialized
+	RASSERT_THROW_EXCEPTION(!isCreated());
 	glBindFramebuffer(GL_FRAMEBUFFER, glId);
 }
 
@@ -71,7 +90,7 @@ inline void Fbo::unbind()
 
 inline void Fbo::checkIfGood() const
 {
-	RASSERT_THROW_EXCEPTION(glId == 0);  // FBO not initialized
+	RASSERT_THROW_EXCEPTION(!isCreated());
 	RASSERT_THROW_EXCEPTION(getCurrentFbo() != glId); // another FBO is binded
 
 	if(glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE)
@@ -83,7 +102,7 @@ inline void Fbo::checkIfGood() const
 
 inline void Fbo::setNumOfColorAttachements(uint num) const
 {
-	RASSERT_THROW_EXCEPTION(glId == 0);  // FBO not initialized
+	RASSERT_THROW_EXCEPTION(!isCreated());
 	RASSERT_THROW_EXCEPTION(getCurrentFbo() != glId); // another FBO is binded
 
 	if(num == 0)
@@ -93,9 +112,10 @@ inline void Fbo::setNumOfColorAttachements(uint num) const
 	}
 	else
 	{
-		static GLenum colorAttachments[] = {GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1, GL_COLOR_ATTACHMENT2,
-																				GL_COLOR_ATTACHMENT3, GL_COLOR_ATTACHMENT4, GL_COLOR_ATTACHMENT5,
-																				GL_COLOR_ATTACHMENT6, GL_COLOR_ATTACHMENT7};
+		static GLenum colorAttachments[] = {
+			GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1, GL_COLOR_ATTACHMENT2,
+			GL_COLOR_ATTACHMENT3, GL_COLOR_ATTACHMENT4, GL_COLOR_ATTACHMENT5,
+			GL_COLOR_ATTACHMENT6, GL_COLOR_ATTACHMENT7};
 
 		RASSERT_THROW_EXCEPTION(num > sizeof(colorAttachments)/sizeof(GLenum));
 		glDrawBuffers(num, colorAttachments);
@@ -111,4 +131,11 @@ inline uint Fbo::getCurrentFbo()
 }
 
 
+inline void Fbo::destroy()
+{
+	RASSERT_THROW_EXCEPTION(!isCreated());
+	glDeleteFramebuffers(1, &glId);
+}
+
+
 #endif

+ 2 - 0
src/Renderer/BufferObjects/Vao.cpp

@@ -8,6 +8,7 @@
 void Vao::attachArrayBufferVbo(const Vbo& vbo, uint attribVarLocation, GLint size, GLenum type,
 		                           GLboolean normalized, GLsizei stride, const GLvoid* pointer)
 {
+	RASSERT_THROW_EXCEPTION(!isCreated());
 	if(vbo.getBufferTarget() != GL_ARRAY_BUFFER)
 	{
 		throw EXCEPTION("Only GL_ARRAY_BUFFER is accepted");
@@ -39,6 +40,7 @@ void Vao::attachArrayBufferVbo(const Vbo& vbo, const ShaderProg::AttribVar& attr
 //======================================================================================================================
 void Vao::attachElementArrayBufferVbo(const Vbo& vbo)
 {
+	RASSERT_THROW_EXCEPTION(!isCreated());
 	if(vbo.getBufferTarget() != GL_ELEMENT_ARRAY_BUFFER)
 	{
 		throw EXCEPTION("Only GL_ELEMENT_ARRAY_BUFFER is accepted");

+ 41 - 8
src/Renderer/BufferObjects/Vao.h

@@ -5,7 +5,6 @@
 #include "StdTypes.h"
 #include "ShaderProg.h"
 #include "Object.h"
-#include "Properties.h"
 #include "GlException.h"
 
 
@@ -13,16 +12,23 @@ class Vbo;
 
 
 /// Vertex array object
-class Vao: public Object
+class Vao
 {
-	PROPERTY_R(uint, glId, getGlId) ///< The OpenGL id
-
 	public:
 		/// Default constructor
-		Vao(Object* parent = NULL);
+		Vao(): glId(0) {}
 
 		/// Destroy VAO from the OpenGL context
-		~Vao() {glDeleteVertexArrays(1, &glId);}
+		~Vao();
+
+		/// Accessor
+		uint getGlId() const;
+
+		/// Create
+		void create();
+
+		/// Destroy
+		void destroy();
 
 		/// Attach an array buffer VBO. See @link http://www.opengl.org/sdk/docs/man3/xhtml/glVertexAttribPointer.xml
 		/// @param vbo The VBO to attach
@@ -54,15 +60,42 @@ class Vao: public Object
 
 		/// Unbind all VAOs
 		static void unbind() {glBindVertexArray(0);}
+
+	private:
+		uint glId; ///< The OpenGL id
+
+		bool isCreated() const {return glId != 0;}
 };
 
 
-inline Vao::Vao(Object* parent):
-	Object(parent)
+inline void Vao::create()
 {
+	RASSERT_THROW_EXCEPTION(isCreated());
 	glGenVertexArrays(1, &glId);
 	ON_GL_FAIL_THROW_EXCEPTION();
 }
 
+inline Vao::~Vao()
+{
+	if(isCreated())
+	{
+		destroy();
+	}
+}
+
+
+inline void Vao::destroy()
+{
+	RASSERT_THROW_EXCEPTION(!isCreated());
+	glDeleteVertexArrays(1, &glId);
+}
+
+
+inline uint Vao::getGlId() const
+{
+	RASSERT_THROW_EXCEPTION(!isCreated());
+	return glId;
+}
+
 
 #endif

+ 14 - 3
src/Renderer/BufferObjects/Vbo.h

@@ -8,18 +8,29 @@
 class Vbo: public BufferObject
 {
 	public:
+		Vbo() {}
+
 		/// Adds an extra check in target_ @see BufferObject::BufferObject
-		Vbo(GLenum target_, uint sizeInBytes, const void* dataPtr, GLenum usage_, Object* parent = NULL);
+		Vbo(GLenum target_, uint sizeInBytes, const void* dataPtr, GLenum usage_);
 
 		/// Unbinds all VBOs, meaning both GL_ARRAY_BUFFER and GL_ELEMENT_ARRAY_BUFFER targets
 		static void unbindAllTargets();
+
+		/// @see BufferObject::create
+		void create(GLenum target, uint sizeInBytes, const void* dataPtr, GLenum usage);
 };
 
 
-inline Vbo::Vbo(GLenum target_, uint sizeInBytes, const void* dataPtr, GLenum usage_, Object* parent):
-	BufferObject(target_, sizeInBytes, dataPtr, usage_, parent)
+inline Vbo::Vbo(GLenum target_, uint sizeInBytes_, const void* dataPtr_, GLenum usage_)
+{
+	create(target_, sizeInBytes_, dataPtr_, usage_);
+}
+
+
+inline void Vbo::create(GLenum target_, uint sizeInBytes_, const void* dataPtr_, GLenum usage_)
 {
 	RASSERT_THROW_EXCEPTION(target_ != GL_ARRAY_BUFFER && target_ != GL_ELEMENT_ARRAY_BUFFER); // unacceptable target_
+	BufferObject::create(target_, sizeInBytes_, dataPtr_, usage_);
 }
 
 

+ 15 - 15
src/Renderer/Dbg.cpp

@@ -87,8 +87,8 @@ void Dbg::renderGrid()
 //======================================================================================================================
 void Dbg::drawSphere(float radius, int complexity)
 {
-	const float twopi  = M::PI*2;
-	const float pidiv2 = M::PI/2;
+	const float twopi  = M::PI * 2;
+	const float pidiv2 = M::PI / 2;
 
 	float theta1 = 0.0;
 	float theta2 = 0.0;
@@ -147,15 +147,15 @@ void Dbg::drawSphere(float radius, int complexity)
 		}
 	}
 
-	positionsVbo->write(&positions[0], 0, sizeof(Vec3) * pointIndex);
-	colorsVbo->write(&colors[0], 0, sizeof(Vec3) * pointIndex);
+	positionsVbo.write(&positions[0], 0, sizeof(Vec3) * pointIndex);
+	colorsVbo.write(&colors[0], 0, sizeof(Vec3) * pointIndex);
 
 	Mat4 pmv = r.getViewProjectionMat() * modelMat;
 	sProg->findUniVar("modelViewProjectionMat")->setMat4(&pmv);
 
-	vao->bind();
+	vao.bind();
 	glDrawArrays(GL_LINE_STRIP, 0, pointIndex);
-	vao->unbind();
+	vao.unbind();
 
 	// Cleanup
 	pointIndex = 0;
@@ -229,13 +229,13 @@ void Dbg::init(const RendererInitializer& initializer)
 	//
 	// VAO & VBOs
 	//
-	positionsVbo = new Vbo(GL_ARRAY_BUFFER, sizeof(positions), NULL, GL_DYNAMIC_DRAW, this);
-	colorsVbo = new Vbo(GL_ARRAY_BUFFER, sizeof(colors), NULL, GL_DYNAMIC_DRAW, this);
-	vao = new Vao(this);
+	positionsVbo.create(GL_ARRAY_BUFFER, sizeof(positions), NULL, GL_DYNAMIC_DRAW);
+	colorsVbo.create(GL_ARRAY_BUFFER, sizeof(colors), NULL, GL_DYNAMIC_DRAW);
+	vao.create();
 	const int positionAttribLoc = 0;
-	vao->attachArrayBufferVbo(*positionsVbo, positionAttribLoc, 3, GL_FLOAT, GL_FALSE, 0, NULL);
+	vao.attachArrayBufferVbo(positionsVbo, positionAttribLoc, 3, GL_FLOAT, GL_FALSE, 0, NULL);
 	const int colorAttribLoc = 1;
-	vao->attachArrayBufferVbo(*colorsVbo, colorAttribLoc, 3, GL_FLOAT, GL_FALSE, 0, NULL);
+	vao.attachArrayBufferVbo(colorsVbo, colorAttribLoc, 3, GL_FLOAT, GL_FALSE, 0, NULL);
 
 	//
 	// Rest
@@ -345,15 +345,15 @@ void Dbg::end()
 {
 	RASSERT_THROW_EXCEPTION(pointIndex == 0);
 
-	positionsVbo->write(&positions[0], 0, sizeof(Vec3) * pointIndex);
-	colorsVbo->write(&colors[0], 0, sizeof(Vec3) * pointIndex);
+	positionsVbo.write(&positions[0], 0, sizeof(Vec3) * pointIndex);
+	colorsVbo.write(&colors[0], 0, sizeof(Vec3) * pointIndex);
 
 	Mat4 pmv = r.getViewProjectionMat() * modelMat;
 	sProg->findUniVar("modelViewProjectionMat")->setMat4(&pmv);
 
-	vao->bind();
+	vao.bind();
 	glDrawArrays(GL_LINES, 0, pointIndex);
-	vao->unbind();
+	vao.unbind();
 
 	// Cleanup
 	pointIndex = 0;

+ 5 - 5
src/Renderer/Dbg.h

@@ -7,10 +7,10 @@
 #include "ShaderProg.h"
 #include "RsrcPtr.h"
 #include "Math.h"
+#include "Vbo.h"
+#include "Vao.h"
 
 
-class Vbo;
-class Vao;
 class SceneDbgDrawer;
 
 
@@ -60,9 +60,9 @@ class Dbg: public RenderingPass
 		Mat4 modelMat;
 		uint pointIndex;
 		Vec3 crntCol;
-		Vbo* positionsVbo;
-		Vbo* colorsVbo;
-		Vao* vao;
+		Vbo positionsVbo;
+		Vbo colorsVbo;
+		Vao vao;
 		SceneDbgDrawer* sceneDbgDrawer;
 };
 

+ 11 - 12
src/Renderer/Is.cpp

@@ -10,7 +10,6 @@
 #include "Scene.h"
 #include "LightData.h"
 #include "Collision.h"
-#include "Vao.h"
 #include "Sm.h"
 #include "Smo.h"
 
@@ -60,8 +59,8 @@ void Is::calcViewVectors()
 		// end of optimized code
 	}
 
-	RASSERT_THROW_EXCEPTION(sizeof(viewVectors) != viewVectorsVbo->getSizeInBytes());
-	viewVectorsVbo->write(viewVectors);
+	RASSERT_THROW_EXCEPTION(sizeof(viewVectors) != viewVectorsVbo.getSizeInBytes());
+	viewVectorsVbo.write(viewVectors);
 }
 
 
@@ -155,17 +154,17 @@ void Is::init(const RendererInitializer& initializer)
 
 	// The VBOs and VAOs
 	float quadVertCoords[][2] = {{1.0, 1.0}, {0.0, 1.0}, {0.0, 0.0}, {1.0, 0.0}};
-	quadPositionsVbo = new Vbo(GL_ARRAY_BUFFER, sizeof(quadVertCoords), quadVertCoords, GL_STATIC_DRAW, this);
+	quadPositionsVbo.create(GL_ARRAY_BUFFER, sizeof(quadVertCoords), quadVertCoords, GL_STATIC_DRAW);
 
 	ushort quadVertIndeces[2][3] = {{0, 1, 3}, {1, 2, 3}};
-	quadVertIndecesVbo = new Vbo(GL_ELEMENT_ARRAY_BUFFER, sizeof(quadVertIndeces), quadVertIndeces, GL_STATIC_DRAW, this);
+	quadVertIndecesVbo.create(GL_ELEMENT_ARRAY_BUFFER, sizeof(quadVertIndeces), quadVertIndeces, GL_STATIC_DRAW);
 
-	viewVectorsVbo = new Vbo(GL_ARRAY_BUFFER, 4 * sizeof(Vec3), NULL, GL_DYNAMIC_DRAW, this);
+	viewVectorsVbo.create(GL_ARRAY_BUFFER, 4 * sizeof(Vec3), NULL, GL_DYNAMIC_DRAW);
 
-	vao = new Vao(this);
-	vao->attachArrayBufferVbo(*quadPositionsVbo, 0, 2, GL_FLOAT, false, 0, NULL);
-	vao->attachArrayBufferVbo(*viewVectorsVbo, 1, 3, GL_FLOAT, false, 0, NULL);
-	vao->attachElementArrayBufferVbo(*quadVertIndecesVbo);
+	vao.create();
+	vao.attachArrayBufferVbo(quadPositionsVbo, 0, 2, GL_FLOAT, false, 0, NULL);
+	vao.attachArrayBufferVbo(viewVectorsVbo, 1, 3, GL_FLOAT, false, 0, NULL);
+	vao.attachElementArrayBufferVbo(quadVertIndecesVbo);
 }
 
 
@@ -174,9 +173,9 @@ void Is::init(const RendererInitializer& initializer)
 //======================================================================================================================
 void Is::drawLightPassQuad() const
 {
-	vao->bind();
+	vao.bind();
 	glDrawElements(GL_TRIANGLES, 2 * 3, GL_UNSIGNED_SHORT, 0);
-	vao->unbind();
+	vao.unbind();
 	ON_GL_FAIL_THROW_EXCEPTION();
 }
 

+ 8 - 8
src/Renderer/Is.h

@@ -8,14 +8,14 @@
 #include "ShaderProg.h"
 #include "Math.h"
 #include "Properties.h"
+#include "Vbo.h"
+#include "Vao.h"
 
 
 class PointLight;
 class SpotLight;
-class Vao;
 class Sm;
 class Smo;
-class Vbo;
 
 
 /// Illumination stage
@@ -40,10 +40,10 @@ class Is: private RenderingPass
 
 		/// @name For the quad drawing in light passes
 		/// @{
-		Vbo* quadPositionsVbo; ///< The VBO for quad positions
-		Vbo* viewVectorsVbo; ///< The VBO to pass the @ref viewVectors.
-		Vbo* quadVertIndecesVbo; ///< The VBO for quad array buffer elements
-		Vao* vao; ///< This VAO is used in light passes only
+		Vbo quadPositionsVbo; ///< The VBO for quad positions
+		Vbo viewVectorsVbo; ///< The VBO to pass the @ref viewVectors.
+		Vbo quadVertIndecesVbo; ///< The VBO for quad array buffer elements
+		Vao vao; ///< This VAO is used in light passes only
 		/// @}
 
 		Vec2 planes; ///< Used to to calculate the frag pos in view space inside the shader program
@@ -51,8 +51,8 @@ class Is: private RenderingPass
 		/// Draws the vao that has attached the viewVectorsVbo as well. Used in light passes
 		void drawLightPassQuad() const;
 
-		/// Calc the view vector that we will use inside the shader to calculate the frag pos in view space. This calculates
-		/// the view vectors and updates the @ref viewVectorsVbo
+		/// Calc the view vector that we will use inside the shader to calculate the frag pos in view space. This
+		/// calculates the view vectors and updates the @ref viewVectorsVbo
 		void calcViewVectors();
 
 		/// Calc the planes that we will use inside the shader to calculate the frag pos in view space

+ 7 - 7
src/Renderer/Renderer.cpp

@@ -51,14 +51,14 @@ void Renderer::init(const RendererInitializer& initializer)
 
 	// quad VBOs and VAO
 	float quadVertCoords[][2] = {{1.0, 1.0}, {0.0, 1.0}, {0.0, 0.0}, {1.0, 0.0}};
-	quadPositionsVbo = new Vbo(GL_ARRAY_BUFFER, sizeof(quadVertCoords), quadVertCoords, GL_STATIC_DRAW, this);
+	quadPositionsVbo.create(GL_ARRAY_BUFFER, sizeof(quadVertCoords), quadVertCoords, GL_STATIC_DRAW);
 
 	ushort quadVertIndeces[2][3] = {{0, 1, 3}, {1, 2, 3}}; // 2 triangles
-	quadVertIndecesVbo = new Vbo(GL_ELEMENT_ARRAY_BUFFER, sizeof(quadVertIndeces), quadVertIndeces, GL_STATIC_DRAW, this);
+	quadVertIndecesVbo.create(GL_ELEMENT_ARRAY_BUFFER, sizeof(quadVertIndeces), quadVertIndeces, GL_STATIC_DRAW);
 
-	globalVao = new Vao(this);
-	globalVao->attachArrayBufferVbo(*quadPositionsVbo, 0, 2, GL_FLOAT, false, 0, NULL);
-	globalVao->attachElementArrayBufferVbo(*quadVertIndecesVbo);
+	quadVao.create();
+	quadVao.attachArrayBufferVbo(quadPositionsVbo, 0, 2, GL_FLOAT, false, 0, NULL);
+	quadVao.attachElementArrayBufferVbo(quadVertIndecesVbo);
 }
 
 
@@ -86,9 +86,9 @@ void Renderer::render(Camera& cam_)
 //======================================================================================================================
 void Renderer::drawQuad()
 {
-	globalVao->bind();
+	quadVao.bind();
 	glDrawElements(GL_TRIANGLES, 2 * 3, GL_UNSIGNED_SHORT, 0);
-	globalVao->unbind();
+	quadVao.unbind();
 	ON_GL_FAIL_THROW_EXCEPTION();
 }
 

+ 3 - 3
src/Renderer/Renderer.h

@@ -135,9 +135,9 @@ class Renderer: public Object
 	private:
 		/// @name For drawing a quad into the active framebuffer
 		/// @{
-		Vbo* quadPositionsVbo; ///< The VBO for quad positions
-		Vbo* quadVertIndecesVbo; ///< The VBO for quad array buffer elements
-		Vao* globalVao; ///< This VAO is used everywhere except material stage
+		Vbo quadPositionsVbo; ///< The VBO for quad positions
+		Vbo quadVertIndecesVbo; ///< The VBO for quad array buffer elements
+		Vao quadVao; ///< This VAO is used everywhere except material stage
 		/// @}
 };
 

+ 14 - 14
src/Renderer/Smo.cpp

@@ -28,15 +28,15 @@ void Smo::init(const RendererInitializer& /*initializer*/)
 
 	// Sphere
 	//
-	spherePositionsVbo = new Vbo(GL_ARRAY_BUFFER, sizeof(sMOUvSCoords), sMOUvSCoords, GL_STATIC_DRAW, this);
-	sphereVao = new Vao(this);
-	sphereVao->attachArrayBufferVbo(*spherePositionsVbo, *sProg->findAttribVar("position"), 3, GL_FLOAT, false, 0, NULL);
+	spherePositionsVbo.create(GL_ARRAY_BUFFER, sizeof(sMOUvSCoords), sMOUvSCoords, GL_STATIC_DRAW);
+	sphereVao.create();
+	sphereVao.attachArrayBufferVbo(spherePositionsVbo, *sProg->findAttribVar("position"), 3, GL_FLOAT, false, 0, NULL);
 
 	// Camera
 	//
 
 	// 4 vertex positions: eye, top-right, top-left, bottom-left, bottom-right
-	cameraPositionsVbo = new Vbo(GL_ARRAY_BUFFER, sizeof(float) * 3 * 5, NULL, GL_DYNAMIC_DRAW, this);
+	cameraPositionsVbo.create(GL_ARRAY_BUFFER, sizeof(float) * 3 * 5, NULL, GL_DYNAMIC_DRAW);
 
 	// The vert indeces
 	enum {EYE, TR, TL, BL, BR}; // Vert positions
@@ -49,11 +49,11 @@ void Smo::init(const RendererInitializer& /*initializer*/)
 		{BR, BL, TL}, {TL, TR, BR} // Front
 	};
 
-	cameraVertIndecesVbo = new Vbo(GL_ELEMENT_ARRAY_BUFFER, sizeof(vertIndeces), vertIndeces, GL_STATIC_DRAW, this);
+	cameraVertIndecesVbo.create(GL_ELEMENT_ARRAY_BUFFER, sizeof(vertIndeces), vertIndeces, GL_STATIC_DRAW);
 
-	cameraVao = new Vao(this);
-	cameraVao->attachArrayBufferVbo(*cameraPositionsVbo, *sProg->findAttribVar("position"), 3, GL_FLOAT, false, 0, NULL);
-	cameraVao->attachElementArrayBufferVbo(*cameraVertIndecesVbo);
+	cameraVao.create();
+	cameraVao.attachArrayBufferVbo(cameraPositionsVbo, *sProg->findAttribVar("position"), 3, GL_FLOAT, false, 0, NULL);
+	cameraVao.attachElementArrayBufferVbo(cameraVertIndecesVbo);
 }
 
 
@@ -78,9 +78,9 @@ void Smo::run(const PointLight& light)
 	sProg->findUniVar("modelViewProjectionMat")->setMat4(&trf);
 
 	// render sphere to the stencil buffer
-	sphereVao->bind();
+	sphereVao.bind();
 	glDrawArrays(GL_TRIANGLES, 0, sizeof(sMOUvSCoords) / sizeof(float) / 3);
-	sphereVao->unbind();
+	sphereVao.unbind();
 
 	// restore GL
 	glEnable(GL_CULL_FACE);
@@ -130,11 +130,11 @@ void Smo::run(const SpotLight& light)
 	};
 
 	// render camera shape to stencil buffer
-	RASSERT_THROW_EXCEPTION(sizeof(vertPositions) != cameraPositionsVbo->getSizeInBytes());
-	cameraPositionsVbo->write(vertPositions);
-	cameraVao->bind();
+	RASSERT_THROW_EXCEPTION(sizeof(vertPositions) != cameraPositionsVbo.getSizeInBytes());
+	cameraPositionsVbo.write(vertPositions);
+	cameraVao.bind();
 	glDrawElements(GL_TRIANGLES, 6 * 3, GL_UNSIGNED_SHORT, 0);
-	cameraVao->unbind();
+	cameraVao.unbind();
 
 	// restore GL state
 	glEnable(GL_CULL_FACE);

+ 7 - 7
src/Renderer/Smo.h

@@ -5,12 +5,12 @@
 #include "Fbo.h"
 #include "ShaderProg.h"
 #include "RsrcPtr.h"
+#include "Vbo.h"
+#include "Vao.h"
 
 
 class PointLight;
 class SpotLight;
-class Vao;
-class Vbo;
 
 
 /// Stencil masking optimizations
@@ -26,15 +26,15 @@ class Smo: public RenderingPass
 		/// @name UV sphere stuff
 		/// @{
 		static float sMOUvSCoords[]; ///< Illumination stage stencil masking optimizations UV sphere vertex positions
-		Vbo* spherePositionsVbo; ///< Illumination stage stencil masking optimizations UV sphere VBO
-		Vao* sphereVao; ///< And a VAO
+		Vbo spherePositionsVbo; ///< Illumination stage stencil masking optimizations UV sphere VBO
+		Vao sphereVao; ///< And a VAO
 		/// @}
 
 		/// @name Camera shape stuff
 		/// @{
-		Vbo* cameraPositionsVbo; ///< A camera shape
-		Vbo* cameraVertIndecesVbo; ///< The vertex indeces
-		Vao* cameraVao; ///< And another VAO
+		Vbo cameraPositionsVbo; ///< A camera shape
+		Vbo cameraVertIndecesVbo; ///< The vertex indeces
+		Vao cameraVao; ///< And another VAO
 		/// @}
 
 		RsrcPtr<ShaderProg> sProg;

+ 13 - 27
src/Resources/Mesh.cpp

@@ -12,9 +12,7 @@
 Mesh::Mesh():
 	Resource(RT_MESH),
 	Object(NULL)
-{
-	memset(&vbos[0], NULL, sizeof(vbos));
-}
+{}
 
 
 //======================================================================================================================
@@ -51,40 +49,28 @@ void Mesh::load(const char* filename)
 //======================================================================================================================
 void Mesh::createVbos(const MeshData& meshData)
 {
-	vbos[VBO_VERT_INDECES] = new Vbo(GL_ELEMENT_ARRAY_BUFFER, meshData.getVertIndeces().getSizeInBytes(),
-	                                 &meshData.getVertIndeces()[0], GL_STATIC_DRAW, this);
-	vbos[VBO_VERT_POSITIONS] = new Vbo(GL_ARRAY_BUFFER, meshData.getVertCoords().getSizeInBytes(),
-	                                   &meshData.getVertCoords()[0], GL_STATIC_DRAW, this);
-	vbos[VBO_VERT_NORMALS] = new Vbo(GL_ARRAY_BUFFER, meshData.getVertNormals().getSizeInBytes(),
-	                                 &meshData.getVertNormals()[0], GL_STATIC_DRAW, this);
+	vbos[VBO_VERT_INDECES].create(GL_ELEMENT_ARRAY_BUFFER, meshData.getVertIndeces().getSizeInBytes(),
+	                              &meshData.getVertIndeces()[0], GL_STATIC_DRAW);
+	vbos[VBO_VERT_POSITIONS].create(GL_ARRAY_BUFFER, meshData.getVertCoords().getSizeInBytes(),
+	                                &meshData.getVertCoords()[0], GL_STATIC_DRAW);
+	vbos[VBO_VERT_NORMALS].create(GL_ARRAY_BUFFER, meshData.getVertNormals().getSizeInBytes(),
+	                              &meshData.getVertNormals()[0], GL_STATIC_DRAW);
 
 	if(meshData.getVertTangents().size() > 1)
 	{
-		vbos[VBO_VERT_TANGENTS] = new Vbo(GL_ARRAY_BUFFER, meshData.getVertTangents().getSizeInBytes(),
-		                                  &meshData.getVertTangents()[0], GL_STATIC_DRAW, this);
-	}
-	else
-	{
-		vbos[VBO_VERT_TANGENTS] = NULL;
+		vbos[VBO_VERT_TANGENTS].create(GL_ARRAY_BUFFER, meshData.getVertTangents().getSizeInBytes(),
+		                               &meshData.getVertTangents()[0], GL_STATIC_DRAW);
 	}
 
 	if(meshData.getTexCoords().size() > 1)
 	{
-		vbos[VBO_TEX_COORDS] = new Vbo(GL_ARRAY_BUFFER, meshData.getTexCoords().getSizeInBytes(),
-		                               &meshData.getTexCoords()[0], GL_STATIC_DRAW, this);
-	}
-	else
-	{
-		vbos[VBO_TEX_COORDS] = NULL;
+		vbos[VBO_TEX_COORDS].create(GL_ARRAY_BUFFER, meshData.getTexCoords().getSizeInBytes(),
+		                            &meshData.getTexCoords()[0], GL_STATIC_DRAW);
 	}
 
 	if(meshData.getVertWeights().size() > 1)
 	{
-		vbos[VBO_VERT_WEIGHTS] = new Vbo(GL_ARRAY_BUFFER, meshData.getVertWeights().getSizeInBytes(),
-		                                 &meshData.getVertWeights()[0], GL_STATIC_DRAW, this);
-	}
-	else
-	{
-		vbos[VBO_VERT_WEIGHTS] = NULL;
+		vbos[VBO_VERT_WEIGHTS].create(GL_ARRAY_BUFFER, meshData.getVertWeights().getSizeInBytes(),
+		                              &meshData.getVertWeights()[0], GL_STATIC_DRAW);
 	}
 }

+ 5 - 5
src/Resources/Mesh.h

@@ -6,11 +6,11 @@
 #include "Resource.h"
 #include "RsrcPtr.h"
 #include "Object.h"
+#include "Vbo.h"
 
 
 class Material;
 class MeshData;
-class Vbo;
 
 
 /// Mesh Resource. It contains the geometry packed in VBOs
@@ -39,17 +39,17 @@ class Mesh: public Resource, public Object
 		~Mesh() {}
 
 		/// Accessor
-		const Vbo* getVbo(Vbos id) const {return vbos[id];}
+		const Vbo& getVbo(Vbos id) const {return vbos[id];}
 
 		/// Implements @ref Resource::load
 		void load(const char* filename);
 
-		bool hasTexCoords() const {return vbos[VBO_TEX_COORDS] != NULL;}
+		bool hasTexCoords() const {return vbos[VBO_TEX_COORDS].isCreated();}
 
-		bool hasVertWeights() const {return vbos[VBO_VERT_WEIGHTS] != NULL;}
+		bool hasVertWeights() const {return vbos[VBO_VERT_WEIGHTS].isCreated();}
 
 	private:
-		boost::array<Vbo*, VBOS_NUM> vbos; ///< The vertex buffer objects
+		boost::array<Vbo, VBOS_NUM> vbos; ///< The vertex buffer objects
 
 		/// Create the VBOs
 		void createVbos(const MeshData& meshData);

+ 22 - 22
src/Resources/Model.cpp

@@ -160,62 +160,62 @@ void Model::SubModel::load(const char* meshFName, const char* mtlFName, const ch
 	//
 	// VAOs
 	//
-	createVao(*material, *mesh, *this, vao);
-	createVao(*dpMaterial, *mesh, *this, dpVao);
+	createVao(*material, *mesh, vao);
+	createVao(*dpMaterial, *mesh, dpVao);
 }
 
 
 //======================================================================================================================
 // createVao                                                                                                           =
 //======================================================================================================================
-void Model::SubModel::createVao(const Material& mtl, const Mesh& mesh, SubModel& subModel, Vao*& vao)
+void Model::SubModel::createVao(const Material& mtl, const Mesh& mesh, Vao& vao)
 {
-	vao = new Vao(&subModel);
+	vao.create();
 
 	if(mtl.getStdAttribVar(Material::SAV_POSITION) != NULL)
 	{
-		vao->attachArrayBufferVbo(*mesh.getVbo(Mesh::VBO_VERT_POSITIONS), *mtl.getStdAttribVar(Material::SAV_POSITION),
-		                          3, GL_FLOAT, GL_FALSE, 0, NULL);
+		vao.attachArrayBufferVbo(mesh.getVbo(Mesh::VBO_VERT_POSITIONS), *mtl.getStdAttribVar(Material::SAV_POSITION),
+		                         3, GL_FLOAT, GL_FALSE, 0, NULL);
 	}
 
 	if(mtl.getStdAttribVar(Material::SAV_NORMAL) != NULL)
 	{
-		vao->attachArrayBufferVbo(*mesh.getVbo(Mesh::VBO_VERT_NORMALS), *mtl.getStdAttribVar(Material::SAV_NORMAL),
-		                          3, GL_FLOAT, GL_FALSE, 0, NULL);
+		vao.attachArrayBufferVbo(mesh.getVbo(Mesh::VBO_VERT_NORMALS), *mtl.getStdAttribVar(Material::SAV_NORMAL),
+		                         3, GL_FLOAT, GL_FALSE, 0, NULL);
 	}
 
 	if(mtl.getStdAttribVar(Material::SAV_TANGENT) != NULL)
 	{
-		vao->attachArrayBufferVbo(*mesh.getVbo(Mesh::VBO_VERT_TANGENTS), *mtl.getStdAttribVar(Material::SAV_TANGENT),
-		                          4, GL_FLOAT, GL_FALSE, 0, NULL);
+		vao.attachArrayBufferVbo(mesh.getVbo(Mesh::VBO_VERT_TANGENTS), *mtl.getStdAttribVar(Material::SAV_TANGENT),
+		                         4, GL_FLOAT, GL_FALSE, 0, NULL);
 	}
 
 	if(mtl.getStdAttribVar(Material::SAV_TEX_COORDS) != NULL)
 	{
-		vao->attachArrayBufferVbo(*mesh.getVbo(Mesh::VBO_TEX_COORDS), *mtl.getStdAttribVar(Material::SAV_TEX_COORDS),
-		                          2, GL_FLOAT, GL_FALSE, 0, NULL);
+		vao.attachArrayBufferVbo(mesh.getVbo(Mesh::VBO_TEX_COORDS), *mtl.getStdAttribVar(Material::SAV_TEX_COORDS),
+		                         2, GL_FLOAT, GL_FALSE, 0, NULL);
 	}
 
 	if(mtl.getStdAttribVar(Material::SAV_VERT_WEIGHT_BONES_NUM) != NULL)
 	{
-		vao->attachArrayBufferVbo(*mesh.getVbo(Mesh::VBO_VERT_WEIGHTS),
-		                          *mtl.getStdAttribVar(Material::SAV_VERT_WEIGHT_BONES_NUM), 1,
-		                          GL_FLOAT, GL_FALSE, sizeof(MeshData::VertexWeight), BUFFER_OFFSET(0));
+		vao.attachArrayBufferVbo(mesh.getVbo(Mesh::VBO_VERT_WEIGHTS),
+		                         *mtl.getStdAttribVar(Material::SAV_VERT_WEIGHT_BONES_NUM), 1,
+		                         GL_FLOAT, GL_FALSE, sizeof(MeshData::VertexWeight), BUFFER_OFFSET(0));
 	}
 
 	if(mtl.getStdAttribVar(Material::SAV_VERT_WEIGHT_BONE_IDS) != NULL)
 	{
-		vao->attachArrayBufferVbo(*mesh.getVbo(Mesh::VBO_VERT_WEIGHTS),
-		                          *mtl.getStdAttribVar(Material::SAV_VERT_WEIGHT_BONE_IDS), 4,
-		                          GL_FLOAT, GL_FALSE, sizeof(MeshData::VertexWeight), BUFFER_OFFSET(4));
+		vao.attachArrayBufferVbo(mesh.getVbo(Mesh::VBO_VERT_WEIGHTS),
+		                         *mtl.getStdAttribVar(Material::SAV_VERT_WEIGHT_BONE_IDS), 4,
+		                         GL_FLOAT, GL_FALSE, sizeof(MeshData::VertexWeight), BUFFER_OFFSET(4));
 	}
 
 	if(mtl.getStdAttribVar(Material::SAV_VERT_WEIGHT_WEIGHTS) != NULL)
 	{
-		vao->attachArrayBufferVbo(*mesh.getVbo(Mesh::VBO_VERT_WEIGHTS),
-		                          *mtl.getStdAttribVar(Material::SAV_VERT_WEIGHT_WEIGHTS), 4,
-		                          GL_FLOAT, GL_FALSE, sizeof(MeshData::VertexWeight), BUFFER_OFFSET(20));
+		vao.attachArrayBufferVbo(mesh.getVbo(Mesh::VBO_VERT_WEIGHTS),
+		                         *mtl.getStdAttribVar(Material::SAV_VERT_WEIGHT_WEIGHTS), 4,
+		                         GL_FLOAT, GL_FALSE, sizeof(MeshData::VertexWeight), BUFFER_OFFSET(20));
 	}
 
-	vao->attachElementArrayBufferVbo(*mesh.getVbo(Mesh::VBO_VERT_INDECES));
+	vao.attachElementArrayBufferVbo(mesh.getVbo(Mesh::VBO_VERT_INDECES));
 }

+ 6 - 6
src/Resources/Model.h

@@ -5,11 +5,11 @@
 #include "Resource.h"
 #include "RsrcPtr.h"
 #include "Object.h"
+#include "Vao.h"
 
 
 class Mesh;
 class Material;
-class Vao;
 class Skeleton;
 class SkelAnim;
 class Scanner;
@@ -59,15 +59,15 @@ class Model: public Resource
 				/// @param[in] mesh For providing the VBOs
 				/// @param[in,out] subModel For setting a parent to the vao
 				/// @param[out] vao The output
-				static void createVao(const Material& material, const Mesh& mesh, SubModel& subModel, Vao*& vao);
+				static void createVao(const Material& material, const Mesh& mesh, Vao& vao);
 
 				/// @name Accessors
 				/// @{
 				const Mesh& getMesh() const {return *mesh;}
 				const Material& getMaterial() const {return *material;}
 				const Material& getDpMaterial() const {return *dpMaterial;}
-				const Vao& getVao() const {return *vao;}
-				const Vao& getDpVao() const {return *dpVao;}
+				const Vao& getVao() const {return vao;}
+				const Vao& getDpVao() const {return dpVao;}
 				/// @}
 
 				bool hasHwSkinning() const;
@@ -76,8 +76,8 @@ class Model: public Resource
 				RsrcPtr<Mesh> mesh; ///< The geometry
 				RsrcPtr<Material> material; ///< Material for MS and BS
 				RsrcPtr<Material> dpMaterial; ///< Material for depth passes
-				Vao* vao; ///< Normal VAO for MS and BS
-				Vao* dpVao; ///< Depth pass VAO for SM and EarlyZ
+				Vao vao; ///< Normal VAO for MS and BS
+				Vao dpVao; ///< Depth pass VAO for SM and EarlyZ
 		};
 
 		Model(): Resource(RT_MODEL) {}

+ 0 - 19
src/Scene/ModelNode.h

@@ -12,25 +12,6 @@ class SkelAnimModelNodeCtrl;
 class Vbo;
 
 
-/// @todo
-class Skin
-{
-	public:
-		enum Vbos
-		{
-			VBO_POSITIONS,
-			VBO_NORMALS,
-			VBO_TANGENTS,
-			VBOS_NUM
-		};
-
-		Vbo& getVbo(Vbos i) {return *vbos[i];}
-
-	private:
-		boost::array<Vbo*, VBOS_NUM> vbos;
-};
-
-
 /// The model scene node
 class ModelNode: public SceneNode
 {

+ 35 - 0
src/Scene/ModelNodePatch.h

@@ -0,0 +1,35 @@
+#ifndef MODEL_NODE_PATCH_H
+#define MODEL_NODE_PATCH_H
+
+#include <boost/array.hpp>
+#include "Vao.h"
+#include "Vbo.h"
+#include "Mesh.h" // For the Vbos enum
+
+
+/// A fragment of the ModelNode
+class ModelNodePatch
+{
+	public:
+		/// Transform feedback VBOs
+		enum TfVbos
+		{
+			TF_VBO_POSITIONS,
+			TF_VBO_NORMALS,
+			TF_VBO_TANGENTS,
+			TF_VBOS_NUM
+		};
+
+		Vbo& getTfVbo(TfVbos i) {return tfVbos[i];}
+
+	private:
+		const Model::SubModel& modelPatch;
+		boost::array<Vbo, TF_VBOS_NUM> tfVbos;
+		boost::array<Vbo*, Mesh::VBOS_NUM> vbos;
+		Vao mainVao; ///< VAO for MS and BS
+		Vao dpVao; ///< VAO for depth passes
+		Vao tfVao; ///< VAO for transform feedback
+};
+
+
+#endif

Энэ ялгаанд хэт олон файл өөрчлөгдсөн тул зарим файлыг харуулаагүй болно