From c54e6dbf5d4aa71ed035211ade0607dda3f7304c Mon Sep 17 00:00:00 2001 From: Mark Vejvoda Date: Tue, 18 Jan 2011 07:52:06 +0000 Subject: [PATCH] - a little bit of plumbing for VBO's for static models (currently disabled via # define) - small small speed improvement when calculating interpolations --- source/glest_game/graphics/renderer.cpp | 10 +- source/glest_game/menu/menu_background.h | 1 + source/glest_game/type_instances/object.cpp | 4 + source/glest_game/type_instances/object.h | 1 + source/glest_game/type_instances/unit.cpp | 10 ++ source/glest_game/type_instances/unit.h | 1 + source/glest_game/types/object_type.cpp | 1 + source/glest_game/types/resource_type.h | 2 +- source/glest_game/types/skill_type.h | 2 +- .../include/graphics/gl/model_renderer_gl.h | 4 +- source/shared_lib/include/graphics/model.h | 37 +++++-- .../sources/graphics/gl/model_renderer_gl.cpp | 99 +++++++++++++------ .../sources/graphics/interpolation.cpp | 6 -- source/shared_lib/sources/graphics/model.cpp | 99 ++++++++++++++++--- 14 files changed, 214 insertions(+), 63 deletions(-) diff --git a/source/glest_game/graphics/renderer.cpp b/source/glest_game/graphics/renderer.cpp index 416936d3..75013285 100644 --- a/source/glest_game/graphics/renderer.cpp +++ b/source/glest_game/graphics/renderer.cpp @@ -736,7 +736,7 @@ void Renderer::renderMouse3d() { modelRenderer->begin(true, true, false); glColor4fv(color.ptr()); glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, color.ptr()); - const Model *buildingModel= building->getFirstStOfClass(scStop)->getAnimation(); + Model *buildingModel= building->getFirstStOfClass(scStop)->getAnimation(); if(gui->getSelectedFacing() != CardinalDir::NORTH) { float rotateAmount = gui->getSelectedFacing() * 90.f; @@ -1815,7 +1815,7 @@ void Renderer::renderObjects(const int renderFps) { visibleIndex < qCache.visibleObjectList.size(); ++visibleIndex) { Object *o = qCache.visibleObjectList[visibleIndex]; - const Model *objModel= o->getModel(); + Model *objModel= o->getModelPtr(); const Vec3f &v= o->getConstPos(); if(modelRenderStarted == false) { @@ -2078,7 +2078,7 @@ void Renderer::renderUnits(const int renderFps) { } //render - const Model *model= unit->getCurrentModel(); + Model *model= unit->getCurrentModelPtr(); model->updateInterpolationData(unit->getAnimProgress(), unit->isAlive()); modelRenderer->render(model); @@ -2617,7 +2617,7 @@ void Renderer::renderMenuBackground(const MenuBackground *menuBackground){ glPushMatrix(); glLoadIdentity(); glTranslatef(i*2.f-4.f, -1.4f, -7.5f); - menuBackground->getCharacterModel(i)->updateInterpolationData(menuBackground->getAnim(), true); + menuBackground->getCharacterModelPtr(i)->updateInterpolationData(menuBackground->getAnim(), true); modelRenderer->render(menuBackground->getCharacterModel(i)); glPopMatrix(); } @@ -3287,7 +3287,7 @@ void Renderer::renderUnitsFast(bool renderingShadows) { glRotatef(unit->getRotation(), 0.f, 1.f, 0.f); //render - const Model *model= unit->getCurrentModel(); + Model *model= unit->getCurrentModelPtr(); model->updateInterpolationVertices(unit->getAnimProgress(), unit->isAlive()); modelRenderer->render(model); diff --git a/source/glest_game/menu/menu_background.h b/source/glest_game/menu/menu_background.h index 555f3efe..a9fca143 100644 --- a/source/glest_game/menu/menu_background.h +++ b/source/glest_game/menu/menu_background.h @@ -85,6 +85,7 @@ public: Texture2D *getWaterTexture() const {return waterTexture;} const Camera *getCamera() const {return &camera;} const Model *getCharacterModel(int i) const {return characterModels[i];} + Model *getCharacterModelPtr(int i) const {return characterModels[i];} const Model *getMainModel() const {return mainModel;} float getFade() const {return fade;} Vec2f getRaindropPos(int i) const {return raindropPos[i];} diff --git a/source/glest_game/type_instances/object.cpp b/source/glest_game/type_instances/object.cpp index a4980404..97e73b47 100644 --- a/source/glest_game/type_instances/object.cpp +++ b/source/glest_game/type_instances/object.cpp @@ -53,6 +53,10 @@ Object::~Object(){ renderer.removeObjectFromQuadCache(this); } +Model *Object::getModelPtr() const { + return objectType==NULL ? (resource != NULL && resource->getType() != NULL ? resource->getType()->getModel() : NULL ) : objectType->getModel(variation); +} + const Model *Object::getModel() const{ return objectType==NULL ? (resource != NULL && resource->getType() != NULL ? resource->getType()->getModel() : NULL ) : objectType->getModel(variation); } diff --git a/source/glest_game/type_instances/object.h b/source/glest_game/type_instances/object.h index 7d3b8530..6949e9d2 100644 --- a/source/glest_game/type_instances/object.h +++ b/source/glest_game/type_instances/object.h @@ -53,6 +53,7 @@ public: const Vec3f & getConstPos() const {return pos;} float getRotation() {return rotation;} const Model *getModel() const; + Model *getModelPtr() const; bool getWalkable() const; void setResource(const ResourceType *resourceType, const Vec2i &pos); diff --git a/source/glest_game/type_instances/unit.cpp b/source/glest_game/type_instances/unit.cpp index 5b234097..dab30b21 100644 --- a/source/glest_game/type_instances/unit.cpp +++ b/source/glest_game/type_instances/unit.cpp @@ -636,6 +636,16 @@ void Unit::setVisible(const bool visible) { // =============================== Render related ================================== +Model *Unit::getCurrentModelPtr() const { + if(currSkill == NULL) { + char szBuf[4096]=""; + sprintf(szBuf,"In [%s::%s Line: %d] ERROR: currSkill == NULL, Unit = [%s]\n",__FILE__,__FUNCTION__,__LINE__,this->toString().c_str()); + throw runtime_error(szBuf); + } + + return currSkill->getAnimation(); +} + const Model *Unit::getCurrentModel() const{ if(currSkill == NULL) { char szBuf[4096]=""; diff --git a/source/glest_game/type_instances/unit.h b/source/glest_game/type_instances/unit.h index 89282b6b..aec7e3e9 100644 --- a/source/glest_game/type_instances/unit.h +++ b/source/glest_game/type_instances/unit.h @@ -392,6 +392,7 @@ public: //render related const Model *getCurrentModel() const; + Model *getCurrentModelPtr() const; Vec3f getCurrVector() const; Vec3f getCurrVectorFlat() const; diff --git a/source/glest_game/types/object_type.cpp b/source/glest_game/types/object_type.cpp index f2f96386..ec214883 100644 --- a/source/glest_game/types/object_type.cpp +++ b/source/glest_game/types/object_type.cpp @@ -29,6 +29,7 @@ void ObjectType::init(int modelCount, int objectClass, bool walkable, int height void ObjectType::loadModel(const string &path){ Model *model= Renderer::getInstance().newModel(rsGame); + model->setIsStaticModel(true); model->load(path); color= Vec3f(0.f); if(model->getMeshCount()>0 && model->getMesh(0)->getTexture(0) != NULL) { diff --git a/source/glest_game/types/resource_type.h b/source/glest_game/types/resource_type.h index 71603f4f..670ecd44 100644 --- a/source/glest_game/types/resource_type.h +++ b/source/glest_game/types/resource_type.h @@ -56,7 +56,7 @@ public: int getResourceNumber() const {return resourceNumber;} int getInterval() const {return interval;} int getDefResPerPatch() const {return defResPerPatch;} - const Model *getModel() const {return model;} + Model *getModel() const {return model;} bool getRecoup_cost() const { return recoup_cost;} static ResourceClass strToRc(const string &s); diff --git a/source/glest_game/types/skill_type.h b/source/glest_game/types/skill_type.h index fdf14b14..ebcaeafe 100755 --- a/source/glest_game/types/skill_type.h +++ b/source/glest_game/types/skill_type.h @@ -98,7 +98,7 @@ public: int getEpCost() const {return mpCost;} int getSpeed() const {return speed;} int getAnimSpeed() const {return animSpeed;} - const Model *getAnimation() const {return animation;} + Model *getAnimation() const {return animation;} StaticSound *getSound() const {return sounds.getRandSound();} float getSoundStartTime() const {return soundStartTime;} diff --git a/source/shared_lib/include/graphics/gl/model_renderer_gl.h b/source/shared_lib/include/graphics/gl/model_renderer_gl.h index bdb75de6..e74f98b4 100644 --- a/source/shared_lib/include/graphics/gl/model_renderer_gl.h +++ b/source/shared_lib/include/graphics/gl/model_renderer_gl.h @@ -42,8 +42,8 @@ public: private: - void renderMesh(const Mesh *mesh); - void renderMeshNormals(const Mesh *mesh); + void renderMesh(const Mesh *mesh, bool isStaticModel); + void renderMeshNormals(const Mesh *mesh, bool isStaticModel); }; }}}//end namespace diff --git a/source/shared_lib/include/graphics/model.h b/source/shared_lib/include/graphics/model.h index 8c341f7b..49495f90 100644 --- a/source/shared_lib/include/graphics/model.h +++ b/source/shared_lib/include/graphics/model.h @@ -25,6 +25,8 @@ using std::string; using std::map; using std::pair; +//#define ENABLE_VBO_CODE + namespace Shared{ namespace Graphics{ class Model; @@ -39,7 +41,7 @@ class TextureManager; // Part of a 3D model // ===================================================== -class Mesh{ +class Mesh { private: //mesh data Texture2D *textures[meshTextureCount]; @@ -50,6 +52,7 @@ private: uint32 frameCount; uint32 vertexCount; uint32 indexCount; + uint32 texCoordFrameCount; //vertex data Vec3f *vertices; @@ -71,6 +74,12 @@ private: InterpolationData *interpolationData; TextureManager *textureManager; +#if defined(ENABLE_VBO_CODE) + // Vertex Buffer Object Names + uint32 m_nVBOVertices; // Vertex VBO Name + uint32 m_nVBOTexCoords; // Texture Coordinate VBO Name +#endif + public: //init & end Mesh(); @@ -87,6 +96,12 @@ public: uint32 getIndexCount() const {return indexCount;} uint32 getTriangleCount() const; +#if defined(ENABLE_VBO_CODE) + uint32 getVBOVertices() const { return m_nVBOVertices;} + uint32 getVBOTexCoords() const { return m_nVBOTexCoords;} + void BuildVBOs(); +#endif + //data const Vec3f *getVertices() const {return vertices;} const Vec3f *getNormals() const {return normals;} @@ -109,8 +124,8 @@ public: //interpolation void buildInterpolationData(); - void updateInterpolationData(float t, bool cycle) const; - void updateInterpolationVertices(float t, bool cycle) const; + void updateInterpolationData(float t, bool cycle); + void updateInterpolationVertices(float t, bool cycle); //load void loadV2(const string &dir, FILE *f, TextureManager *textureManager,bool deletePixMapAfterLoad); @@ -130,7 +145,7 @@ private: // 3D Model, than can be loaded from a g3d file // ===================================================== -class Model{ +class Model { private: TextureManager *textureManager; @@ -139,6 +154,13 @@ private: uint32 meshCount; Mesh *meshes; + float lastTData; + bool lastCycleData; + float lastTVertex; + bool lastCycleVertex; + + bool isStaticModel; + public: //constructor & destructor Model(); @@ -147,8 +169,8 @@ public: virtual void end()= 0; //data - void updateInterpolationData(float t, bool cycle) const; - void updateInterpolationVertices(float t, bool cycle) const; + void updateInterpolationData(float t, bool cycle); + void updateInterpolationVertices(float t, bool cycle); void buildShadowVolumeData() const; //get @@ -168,6 +190,9 @@ public: void setTextureManager(TextureManager *textureManager) {this->textureManager= textureManager;} void deletePixels(); + bool getIsStaticModel() const { return isStaticModel; } + void setIsStaticModel(bool value) { isStaticModel = value; } + private: void buildInterpolationData() const; }; diff --git a/source/shared_lib/sources/graphics/gl/model_renderer_gl.cpp b/source/shared_lib/sources/graphics/gl/model_renderer_gl.cpp index dd3184bd..a2a70257 100644 --- a/source/shared_lib/sources/graphics/gl/model_renderer_gl.cpp +++ b/source/shared_lib/sources/graphics/gl/model_renderer_gl.cpp @@ -104,7 +104,7 @@ void ModelRendererGl::render(const Model *model) { //render every mesh for(uint32 i=0; igetMeshCount(); ++i) { - renderMesh(model->getMesh(i)); + renderMesh(model->getMesh(i),model->getIsStaticModel()); } //assertions @@ -118,7 +118,7 @@ void ModelRendererGl::renderNormalsOnly(const Model *model) { //render every mesh for(uint32 i=0; igetMeshCount(); ++i) { - renderMeshNormals(model->getMesh(i)); + renderMeshNormals(model->getMesh(i),model->getIsStaticModel()); } //assertions @@ -127,7 +127,7 @@ void ModelRendererGl::renderNormalsOnly(const Model *model) { // ===================== PRIVATE ======================= -void ModelRendererGl::renderMesh(const Mesh *mesh) { +void ModelRendererGl::renderMesh(const Mesh *mesh, bool isStaticModel) { //assertions assertGl(); @@ -178,37 +178,80 @@ void ModelRendererGl::renderMesh(const Mesh *mesh) { //assertions assertGl(); - //vertices - glVertexPointer(3, GL_FLOAT, 0, mesh->getInterpolationData()->getVertices()); +#if defined(ENABLE_VBO_CODE) + if(isStaticModel == true) { + //vertices + glBindBufferARB( GL_ARRAY_BUFFER_ARB, mesh->getVBOVertices() ); + glVertexPointer( 3, GL_FLOAT, 0, (char *) NULL ); // Set The Vertex Pointer To The Vertex Buffer - //normals - if(renderNormals) { - glEnableClientState(GL_NORMAL_ARRAY); - glNormalPointer(GL_FLOAT, 0, mesh->getInterpolationData()->getNormals()); - } - else{ - glDisableClientState(GL_NORMAL_ARRAY); - } + //normals + if(renderNormals) { + glEnableClientState(GL_NORMAL_ARRAY); + glNormalPointer(GL_FLOAT, 0, mesh->getInterpolationData()->getNormals()); + } + else{ + glDisableClientState(GL_NORMAL_ARRAY); + } - //tex coords - if(renderTextures && mesh->getTexture(mtDiffuse)!=NULL ) { - if(duplicateTexCoords) { - glActiveTexture(GL_TEXTURE0 + secondaryTexCoordUnit); + //tex coords + if(renderTextures && mesh->getTexture(mtDiffuse) != NULL ) { + glBindBufferARB( GL_ARRAY_BUFFER_ARB, mesh->getVBOTexCoords() ); + if(duplicateTexCoords) { + glActiveTexture(GL_TEXTURE0 + secondaryTexCoordUnit); + //glEnableClientState(GL_TEXTURE_COORD_ARRAY); + //glTexCoordPointer(2, GL_FLOAT, 0, mesh->getTexCoords()); + glTexCoordPointer( 2, GL_FLOAT, 0, (char *) NULL ); // Set The TexCoord Pointer To The TexCoord Buffer + } + + glActiveTexture(GL_TEXTURE0); + //glEnableClientState(GL_TEXTURE_COORD_ARRAY); + //glTexCoordPointer(2, GL_FLOAT, 0, mesh->getTexCoords()); + glTexCoordPointer( 2, GL_FLOAT, 0, (char *) NULL ); // Set The TexCoord Pointer To The TexCoord Buffer + } + else { + if(duplicateTexCoords) { + glActiveTexture(GL_TEXTURE0 + secondaryTexCoordUnit); + glDisableClientState(GL_TEXTURE_COORD_ARRAY); + } + glActiveTexture(GL_TEXTURE0); + glDisableClientState(GL_TEXTURE_COORD_ARRAY); + } + } + else +#endif + { + //vertices + glVertexPointer(3, GL_FLOAT, 0, mesh->getInterpolationData()->getVertices()); + + //normals + if(renderNormals) { + glEnableClientState(GL_NORMAL_ARRAY); + glNormalPointer(GL_FLOAT, 0, mesh->getInterpolationData()->getNormals()); + } + else{ + glDisableClientState(GL_NORMAL_ARRAY); + } + + //tex coords + if(renderTextures && mesh->getTexture(mtDiffuse)!=NULL ) { + if(duplicateTexCoords) { + glActiveTexture(GL_TEXTURE0 + secondaryTexCoordUnit); + glEnableClientState(GL_TEXTURE_COORD_ARRAY); + glTexCoordPointer(2, GL_FLOAT, 0, mesh->getTexCoords()); + } + + glActiveTexture(GL_TEXTURE0); glEnableClientState(GL_TEXTURE_COORD_ARRAY); glTexCoordPointer(2, GL_FLOAT, 0, mesh->getTexCoords()); } - - glActiveTexture(GL_TEXTURE0); - glEnableClientState(GL_TEXTURE_COORD_ARRAY); - glTexCoordPointer(2, GL_FLOAT, 0, mesh->getTexCoords()); - } - else { - if(duplicateTexCoords) { - glActiveTexture(GL_TEXTURE0 + secondaryTexCoordUnit); + else { + if(duplicateTexCoords) { + glActiveTexture(GL_TEXTURE0 + secondaryTexCoordUnit); + glDisableClientState(GL_TEXTURE_COORD_ARRAY); + } + glActiveTexture(GL_TEXTURE0); glDisableClientState(GL_TEXTURE_COORD_ARRAY); } - glActiveTexture(GL_TEXTURE0); - glDisableClientState(GL_TEXTURE_COORD_ARRAY); } //draw model @@ -218,7 +261,7 @@ void ModelRendererGl::renderMesh(const Mesh *mesh) { assertGl(); } -void ModelRendererGl::renderMeshNormals(const Mesh *mesh) { +void ModelRendererGl::renderMeshNormals(const Mesh *mesh,bool isStaticModel) { glBegin(GL_LINES); for(unsigned int i= 0; igetIndexCount(); ++i){ diff --git a/source/shared_lib/sources/graphics/interpolation.cpp b/source/shared_lib/sources/graphics/interpolation.cpp index c98aa3ce..603ee58b 100644 --- a/source/shared_lib/sources/graphics/interpolation.cpp +++ b/source/shared_lib/sources/graphics/interpolation.cpp @@ -84,9 +84,6 @@ void InterpolationData::updateVertices(float t, bool cycle) { if(iterFind != cacheVertices.end()) { std::map::iterator iterFind2 = iterFind->second.find(cycle); if(iterFind2 != iterFind->second.end()) { - //for(uint32 j=0; j< vertexCount; ++j){ - // vertices[j] = iterFind2->second[j]; - //} memcpy(vertices,iterFind2->second,sizeof(Vec3f) * vertexCount); return; } @@ -130,9 +127,6 @@ void InterpolationData::updateNormals(float t, bool cycle){ if(iterFind != cacheNormals.end()) { std::map::iterator iterFind2 = iterFind->second.find(cycle); if(iterFind2 != iterFind->second.end()) { - //for(uint32 j=0; j< vertexCount; ++j){ - // normals[j] = iterFind2->second[j]; - //} memcpy(normals,iterFind2->second,sizeof(Vec3f) * vertexCount); return; } diff --git a/source/shared_lib/sources/graphics/model.cpp b/source/shared_lib/sources/graphics/model.cpp index b27f9f49..e93402ec 100644 --- a/source/shared_lib/sources/graphics/model.cpp +++ b/source/shared_lib/sources/graphics/model.cpp @@ -18,6 +18,13 @@ #include "interpolation.h" #include "conversion.h" #include "util.h" + +#if defined(ENABLE_VBO_CODE) + +#include "opengl.h" + +#endif + #include "leak_dumper.h" using namespace Shared::Platform; @@ -39,6 +46,7 @@ Mesh::Mesh() { frameCount= 0; vertexCount= 0; indexCount= 0; + texCoordFrameCount = 0; vertices= NULL; normals= NULL; @@ -94,14 +102,36 @@ void Mesh::buildInterpolationData(){ interpolationData= new InterpolationData(this); } -void Mesh::updateInterpolationData(float t, bool cycle) const{ +void Mesh::updateInterpolationData(float t, bool cycle) { interpolationData->update(t, cycle); } -void Mesh::updateInterpolationVertices(float t, bool cycle) const{ +void Mesh::updateInterpolationVertices(float t, bool cycle) { interpolationData->updateVertices(t, cycle); } +#if defined(ENABLE_VBO_CODE) + +void Mesh::BuildVBOs() { + // Generate And Bind The Vertex Buffer + glGenBuffersARB( 1, &m_nVBOVertices ); // Get A Valid Name + glBindBufferARB( GL_ARRAY_BUFFER_ARB, m_nVBOVertices ); // Bind The Buffer + // Load The Data + glBufferDataARB( GL_ARRAY_BUFFER_ARB, getVertexCount() * 3 * sizeof(float), vertices, GL_STATIC_DRAW_ARB ); + + // Generate And Bind The Texture Coordinate Buffer + glGenBuffersARB( 1, &m_nVBOTexCoords ); // Get A Valid Name + glBindBufferARB( GL_ARRAY_BUFFER_ARB, m_nVBOTexCoords ); // Bind The Buffer + // Load The Data + glBufferDataARB( GL_ARRAY_BUFFER_ARB, getVertexCount() * 2 * sizeof(float), texCoords, GL_STATIC_DRAW_ARB ); + + // Our Copy Of The Data Is No Longer Necessary, It Is Safe In The Graphics Card + delete [] vertices; vertices = NULL; + delete [] texCoords; texCoords = NULL; +} + +#endif + // ==================== load ==================== void Mesh::loadV2(const string &dir, FILE *f, TextureManager *textureManager,bool deletePixMapAfterLoad) { @@ -123,6 +153,7 @@ void Mesh::loadV2(const string &dir, FILE *f, TextureManager *textureManager,boo frameCount= meshHeader.vertexFrameCount; vertexCount= meshHeader.pointCount; indexCount= meshHeader.indexCount; + texCoordFrameCount = meshHeader.texCoordFrameCount; init(); @@ -176,6 +207,7 @@ void Mesh::loadV3(const string &dir, FILE *f, TextureManager *textureManager,boo frameCount= meshHeader.vertexFrameCount; vertexCount= meshHeader.pointCount; indexCount= meshHeader.indexCount; + texCoordFrameCount = meshHeader.texCoordFrameCount; init(); @@ -366,10 +398,16 @@ Model::Model(){ meshCount= 0; meshes= NULL; textureManager= NULL; + lastTData = -1; + lastCycleData = -1; + lastTVertex = -1; + lastCycleVertex = -1; + isStaticModel = false; } Model::~Model(){ delete [] meshes; + meshes = NULL; } // ==================== data ==================== @@ -380,15 +418,23 @@ void Model::buildInterpolationData() const{ } } -void Model::updateInterpolationData(float t, bool cycle) const{ - for(unsigned int i=0; iupdateInterpolationData(0.f, true); + for(uint32 i=0; iupdateInterpolationData(0.f, true); + for(uint32 i=0; iupdateInterpolationData(0.f, true); + for(uint32 i=0; i