diff --git a/src/gl/models/gl_models.h b/src/gl/models/gl_models.h index 4ba206983..a4effd51d 100644 --- a/src/gl/models/gl_models.h +++ b/src/gl/models/gl_models.h @@ -125,7 +125,7 @@ protected: char *vertexUsage; // Bitfield for each vertex. bool allowTexComp; // Allow texture compression with this. - static void RenderGLCommands(void *glCommands, unsigned int numVertices,FModelVertex * vertices); + static void RenderGLCommands(void *glCommands, unsigned int numVertices,FModelVertex * vertices, FModelVertex *vertices2, double inter); public: FDMDModel() diff --git a/src/gl/models/gl_models_md2.cpp b/src/gl/models/gl_models_md2.cpp index 12c8bebe7..46a7238a7 100644 --- a/src/gl/models/gl_models_md2.cpp +++ b/src/gl/models/gl_models_md2.cpp @@ -263,11 +263,13 @@ int FDMDModel::FindFrame(const char * name) // Render a set of GL commands using the given data. // //=========================================================================== -void FDMDModel::RenderGLCommands(void *glCommands, unsigned int numVertices,FModelVertex * vertices) + +void FDMDModel::RenderGLCommands(void *glCommands, unsigned int numVertices, FModelVertex * vertices, FModelVertex *vertices2, double inter) { char *pos; FGLCommandVertex * v; int count; + const bool interpolate = (vertices2 != NULL && inter != 0.); gl_RenderState.Apply(); for(pos = (char*)glCommands; *pos;) @@ -277,101 +279,55 @@ void FDMDModel::RenderGLCommands(void *glCommands, unsigned int numVertices,FMod // The type of primitive depends on the sign. glBegin(count > 0 ? GL_TRIANGLE_STRIP : GL_TRIANGLE_FAN); + count = abs(count); - while(count--) + while (count--) { - v = (FGLCommandVertex *) pos; + v = (FGLCommandVertex *)pos; pos += sizeof(FGLCommandVertex); glTexCoord2fv(&v->s); - glVertex3fv((float*)&vertices[v->index]); + if (!interpolate) + { + glVertex3fv(vertices[v->index].xyz); + } + else + { + float interp[3]; + for (int i = 0; i < 3; i++) + interp[i] = inter * vertices[v->index].xyz[i] + (1. - inter) * vertices2[v->index].xyz[i]; + glVertex3fv(interp); + } } - glEnd(); } } +void FDMDModel::RenderFrameInterpolated(FTexture * skin, int frameno, int frameno2, double inter, int translation) +{ + if (frameno >= info.numFrames || frameno2 >= info.numFrames) return; + + if (!skin) + { + if (info.numSkins == 0) return; + skin = skins[0]; + if (!skin) return; + } + + FMaterial * tex = FMaterial::ValidateTexture(skin); + + tex->Bind(0, translation); + + RenderGLCommands(lods[0].glCommands, info.numVertices, frames[frameno].vertices, frames[frameno2].vertices, inter); +} + void FDMDModel::RenderFrame(FTexture * skin, int frameno, int translation) { - int activeLod; - - if (frameno>=info.numFrames) return; - - ModelFrame * frame = &frames[frameno]; - //int mainFlags = mf->flags; - - if (!skin) - { - if (info.numSkins==0) return; - skin = skins[0]; - if (!skin) return; - } - - FMaterial * tex = FMaterial::ValidateTexture(skin); - - tex->Bind(0, translation); - - int numVerts = info.numVertices; - - // Determine the suitable LOD. - /* - if(info.numLODs > 1 && rend_model_lod != 0) - { - float lodFactor = rend_model_lod * screen->Width() / 640.0f / (GLRenderer->mCurrentFoV / 90.0f); - if(lodFactor) lodFactor = 1 / lodFactor; - - // Determine the LOD we will be using. - activeLod = (int) (lodFactor * spr->distance); - if(activeLod < 0) activeLod = 0; - if(activeLod >= mdl->info.numLODs) activeLod = mdl->info.numLODs - 1; - vertexUsage = mdl->vertexUsage; - } - else - */ - { - activeLod = 0; - } - - RenderGLCommands(lods[activeLod].glCommands, numVerts, frame->vertices/*, modelColors, NULL*/); + RenderFrameInterpolated(skin, frameno, frameno, 0., translation); } -void FDMDModel::RenderFrameInterpolated(FTexture * skin, int frameno, int frameno2, double inter, int translation) -{ - int activeLod = 0; - - if (frameno>=info.numFrames || frameno2>=info.numFrames) return; - - FModelVertex *vertices1 = frames[frameno].vertices; - FModelVertex *vertices2 = frames[frameno2].vertices; - - if (!skin) - { - if (info.numSkins==0) return; - skin = skins[0]; - if (!skin) return; - } - - FMaterial * tex = FMaterial::ValidateTexture(skin); - - tex->Bind(0, translation); - - int numVerts = info.numVertices; - - // [BB] Calculate the interpolated vertices by linear interpolation. - FModelVertex *verticesInterpolated = new FModelVertex[numVerts]; - for( int k = 0; k < numVerts; k++ ) - { - for ( int i = 0; i < 3; i++ ) - verticesInterpolated[k].xyz[i] = (1-inter)*vertices1[k].xyz[i]+ (inter)*vertices2[k].xyz[i]; - } - - RenderGLCommands(lods[activeLod].glCommands, numVerts, verticesInterpolated/*, modelColors, NULL*/); - delete[] verticesInterpolated; -} - - //=========================================================================== // // FMD2Model::Load diff --git a/src/gl/system/gl_interface.cpp b/src/gl/system/gl_interface.cpp index ac34bd2c1..d9816e120 100644 --- a/src/gl/system/gl_interface.cpp +++ b/src/gl/system/gl_interface.cpp @@ -144,6 +144,7 @@ void gl_LoadExtensions() if (CheckExtension("GL_ARB_texture_compression")) gl.flags|=RFL_TEXTURE_COMPRESSION; if (CheckExtension("GL_EXT_texture_compression_s3tc")) gl.flags|=RFL_TEXTURE_COMPRESSION_S3TC; if (gl.version >= 4.f && CheckExtension("GL_ARB_buffer_storage")) gl.flags |= RFL_BUFFER_STORAGE; + if (gl.version >= 3.2f || CheckExtension("GL_ARB_draw_elements_base_vertex")) gl.flags |= RFL_BASEINDEX; glGetIntegerv(GL_MAX_TEXTURE_SIZE,&gl.max_texturesize); glPixelStorei(GL_UNPACK_ALIGNMENT, 1); diff --git a/src/gl/system/gl_interface.h b/src/gl/system/gl_interface.h index 45e0a09ac..d280242e1 100644 --- a/src/gl/system/gl_interface.h +++ b/src/gl/system/gl_interface.h @@ -12,6 +12,7 @@ enum RenderFlags RFL_FRAMEBUFFER = 4, RFL_BUFFER_STORAGE = 8, RFL_SHADER_STORAGE_BUFFER = 16, + RFL_BASEINDEX = 32, }; enum TexMode