/* ================= R_AddIQMSurfaces Add all surfaces of this model ================= */ void R_AddIQMSurfaces( trRefEntity_t *ent ) { IQModel_t *IQModel; srfIQModel_t *surface; int i, j; bool personalModel; int fogNum; shader_t *shader; skin_t *skin; IQModel = tr.currentModel->iqm; surface = IQModel->surfaces; // don't add third_person objects if not in a portal personalModel = (ent->e.renderfx & RF_THIRD_PERSON) && tr.viewParms.portalLevel == 0; // // cull the entire model if merged bounding box of both frames // is outside the view frustum. // R_CullIQM( ent ); if ( ent->cull == cullResult_t::CULL_OUT ) { return; } // // set up lighting now that we know we aren't culled // if ( !personalModel || r_shadows->integer > Util::ordinal(shadowingMode_t::SHADOWING_BLOB) ) { R_SetupEntityLighting( &tr.refdef, ent, nullptr ); } // // see if we are in a fog volume // fogNum = R_FogWorldBox( ent->worldBounds ); for ( i = 0 ; i < IQModel->num_surfaces ; i++ ) { if(ent->e.customShader) shader = R_GetShaderByHandle( ent->e.customShader ); else if(ent->e.customSkin > 0 && ent->e.customSkin < tr.numSkins) { skin = R_GetSkinByHandle(ent->e.customSkin); shader = tr.defaultShader; if (surface->name && *surface->name) { for(j = 0; j < skin->numSurfaces; j++) { if (!strcmp(skin->surfaces[j]->name, surface->name)) { shader = skin->surfaces[j]->shader; break; } } } if ( shader == tr.defaultShader && i >= 0 && i < skin->numSurfaces && skin->surfaces[ i ] ) { shader = skin->surfaces[ i ]->shader; } } else { shader = surface->shader; if ( ent->e.altShaderIndex > 0 && ent->e.altShaderIndex < MAX_ALTSHADERS && shader->altShader[ ent->e.altShaderIndex ].index ) { shader = R_GetShaderByHandle( shader->altShader[ ent->e.altShaderIndex ].index ); } } // we will add shadows even if the main object isn't visible in the view if( !personalModel ) { R_AddDrawSurf( ( surfaceType_t *)surface, shader, -1, fogNum ); } surface++; } }
/* ============== R_AddMD5Surfaces ============== */ void R_AddMD5Surfaces(trRefEntity_t * ent) { md5Model_t *model; md5Surface_t *surface; shader_t *shader; int i; qboolean personalModel; int fogNum; model = tr.currentModel->md5; // don't add third_person objects if not in a portal personalModel = (ent->e.renderfx & RF_THIRD_PERSON) && !tr.viewParms.isPortal; // cull the entire model if merged bounding box of both frames // is outside the view frustum R_CullMD5(ent); if(ent->cull == CULL_OUT) { return; } // set up world bounds for light intersection tests R_SetupEntityWorldBounds(ent); // set up lighting now that we know we aren't culled if(!personalModel || r_shadows->integer > SHADOWING_BLOB) { R_SetupEntityLighting(&tr.refdef, ent, NULL); } // see if we are in a fog volume fogNum = R_FogWorldBox(ent->worldBounds); if(!r_vboModels->integer || !model->numVBOSurfaces || (!glConfig2.vboVertexSkinningAvailable && ent->e.skeleton.type == SK_ABSOLUTE)) { // finally add surfaces for(i = 0, surface = model->surfaces; i < model->numSurfaces; i++, surface++) { if(ent->e.customShader) { shader = R_GetShaderByHandle(ent->e.customShader); } else if(ent->e.customSkin > 0 && ent->e.customSkin < tr.numSkins) { skin_t *skin; skin = R_GetSkinByHandle(ent->e.customSkin); // match the surface name to something in the skin file shader = tr.defaultShader; // FIXME: replace MD3_MAX_SURFACES for skin_t::surfaces if(i >= 0 && i < skin->numSurfaces && skin->surfaces[i]) { shader = skin->surfaces[i]->shader; } if(shader == tr.defaultShader) { ri.Printf(PRINT_DEVELOPER, "WARNING: no shader for surface %i in skin %s\n", i, skin->name); } else if(shader->defaultShader) { ri.Printf(PRINT_DEVELOPER, "WARNING: shader %s in skin %s not found\n", shader->name, skin->name); } } else { shader = R_GetShaderByHandle(surface->shaderIndex); } // we will add shadows even if the main object isn't visible in the view // don't add third_person objects if not viewing through a portal if(!personalModel) { R_AddDrawSurf((void *)surface, shader, -1, fogNum); } } } else { int i; srfVBOMD5Mesh_t *vboSurface; shader_t *shader; for(i = 0; i < model->numVBOSurfaces; i++) { vboSurface = model->vboSurfaces[i]; if(ent->e.customShader) { shader = R_GetShaderByHandle(ent->e.customShader); } else if(ent->e.customSkin > 0 && ent->e.customSkin < tr.numSkins) { skin_t *skin; skin = R_GetSkinByHandle(ent->e.customSkin); // match the surface name to something in the skin file shader = tr.defaultShader; // FIXME: replace MD3_MAX_SURFACES for skin_t::surfaces //if(i >= 0 && i < skin->numSurfaces && skin->surfaces[i]) if(vboSurface->skinIndex >= 0 && vboSurface->skinIndex < skin->numSurfaces && skin->surfaces[vboSurface->skinIndex]) { shader = skin->surfaces[vboSurface->skinIndex]->shader; } if(shader == tr.defaultShader) { ri.Printf(PRINT_DEVELOPER, "WARNING: no shader for surface %i in skin %s\n", i, skin->name); } else if(shader->defaultShader) { ri.Printf(PRINT_DEVELOPER, "WARNING: shader %s in skin %s not found\n", shader->name, skin->name); } } else { shader = vboSurface->shader; } // don't add third_person objects if not viewing through a portal if(!personalModel) { R_AddDrawSurf((void *)vboSurface, shader, -1, fogNum); } } } }
/** * @brief R_AddMDVSurfaces * @param[in,out] ent */ void R_AddMDVSurfaces(trRefEntity_t *ent) { int i; mdvModel_t *model = 0; mdvSurface_t *mdvSurface = 0; shader_t *shader = 0; int lod; qboolean personalModel; int fogNum; // don't add third_person objects if not in a portal personalModel = (ent->e.renderfx & RF_THIRD_PERSON) && !tr.viewParms.isPortal; if (ent->e.renderfx & RF_WRAP_FRAMES) { ent->e.frame %= tr.currentModel->mdv[0]->numFrames; ent->e.oldframe %= tr.currentModel->mdv[0]->numFrames; } // compute LOD if (ent->e.renderfx & RF_FORCENOLOD) { lod = 0; } else { lod = R_ComputeLOD(ent); } // Validate the frames so there is no chance of a crash. // This will write directly into the entity structure, so // when the surfaces are rendered, they don't need to be // range checked again. if ((ent->e.frame >= tr.currentModel->mdv[lod]->numFrames) || (ent->e.frame < 0) || (ent->e.oldframe >= tr.currentModel->mdv[lod]->numFrames) || (ent->e.oldframe < 0)) { //Only spam if the lod level is 0 (lods usually don't have animation frames as they are only seen from a far) if (lod == 0) { Ren_Developer("R_AddMDVSurfaces: no such frame %d to %d for '%s' (%d)\n", ent->e.oldframe, ent->e.frame, tr.currentModel->name, tr.currentModel->mdv[lod]->numFrames); } ent->e.frame = 0; ent->e.oldframe = 0; } model = tr.currentModel->mdv[lod]; // cull the entire model if merged bounding box of both frames // is outside the view frustum. R_CullMDV(model, ent); if (ent->cull == CULL_OUT) { return; } // set up lighting now that we know we aren't culled if (!personalModel || r_shadows->integer > SHADOWING_BLOB) { R_SetupEntityLighting(&tr.refdef, ent, NULL); } // see if we are in a fog volume fogNum = R_FogWorldBox(ent->worldBounds); // draw all surfaces if (r_vboModels->integer && model->numVBOSurfaces) { int i; srfVBOMDVMesh_t *vboSurface; shader_t *shader; for (i = 0; i < model->numVBOSurfaces; i++) { vboSurface = model->vboSurfaces[i]; mdvSurface = vboSurface->mdvSurface; shader = GetMDVSurfaceShader(ent, mdvSurface); // don't add third_person objects if not viewing through a portal if (!personalModel) { R_AddDrawSurf((surfaceType_t *)vboSurface, shader, LIGHTMAP_NONE, fogNum); } } } else { for (i = 0, mdvSurface = model->surfaces; i < model->numSurfaces; i++, mdvSurface++) { shader = GetMDVSurfaceShader(ent, mdvSurface); // we will add shadows even if the main object isn't visible in the view // don't add third_person objects if not viewing through a portal if (!personalModel) { R_AddDrawSurf((surfaceType_t *)mdvSurface, shader, LIGHTMAP_NONE, fogNum); } } } }