void Cal3dModel::renderMesh(bool useTextures, bool useLighting, bool select_mode) { // get the renderer of the model CalRenderer *pCalRenderer = m_calModel->getRenderer(); assert(pCalRenderer != NULL); // We let open gl do this, so no need to do it twice pCalRenderer->setNormalization(false); // begin the rendering loop if (!pCalRenderer->beginRendering()) { // Some kind of error here! return; } // get the number of meshes int meshCount = pCalRenderer->getMeshCount(); int numSubMeshes = 0; for (int i = 0; i < meshCount; ++i) { numSubMeshes += pCalRenderer->getSubmeshCount(i); } m_dos.resize(numSubMeshes); int counter = -1; // render all meshes of the model for(int meshId = 0; meshId < meshCount; ++meshId) { // get the number of submeshes int submeshCount = pCalRenderer->getSubmeshCount(meshId); // render all submeshes of the mesh for(int submeshId = 0; submeshId < submeshCount; ++submeshId) { // select mesh and submesh for further data access if(pCalRenderer->selectMeshSubmesh(meshId, submeshId)) { DynamicObject* dyno = m_dos[++counter]; if (!dyno) { dyno = new DynamicObject(); dyno->init(); dyno->contextCreated(); m_dos[counter] = dyno; // Lets assume this doesn't change static unsigned char meshColor[4]; static float ambient[4]; static float diffuse[4]; static float specular[4]; static float shininess; pCalRenderer->getAmbientColor(&meshColor[0]); ambient[0] = meshColor[0] / 255.0f; ambient[1] = meshColor[1] / 255.0f; ambient[2] = meshColor[2] / 255.0f; ambient[3] = meshColor[3] / 255.0f; dyno->setAmbient(ambient); // set the material diffuse color pCalRenderer->getDiffuseColor(&meshColor[0]); diffuse[0] = meshColor[0] / 255.0f; diffuse[1] = meshColor[1] / 255.0f; diffuse[2] = meshColor[2] / 255.0f; diffuse[3] = 1.0f;//meshColor[3] / 255.0f; dyno->setDiffuse(diffuse); // set the material specular color pCalRenderer->getSpecularColor(&meshColor[0]); specular[0] = meshColor[0] / 255.0f; specular[1] = meshColor[1] / 255.0f; specular[2] = meshColor[2] / 255.0f; specular[3] = meshColor[3] / 255.0f; dyno->setSpecular(specular); dyno->setEmission(0.0f, 0.0f, 0.0f,0.0f); shininess = pCalRenderer->getShininess(); dyno->setShininess(shininess); dyno->getMatrix().rotateZ(-m_rotate / 180.0 * WFMath::Pi); dyno->setState(m_state); dyno->setSelectState(m_select_state); dyno->setUseStencil(m_use_stencil); } // get the transformed vertices of the submesh int vertexCount = pCalRenderer->getVertexCount(); bool realloc = false; float *vertex_ptr, *normal_ptr, *texture_ptr; int textureCoordinateCount = 0; if (vertexCount > dyno->getNumPoints()) { realloc = true; vertex_ptr = dyno->createVertexData(vertexCount * 3); pCalRenderer->getVertices(vertex_ptr); dyno->releaseVertexDataPtr(); normal_ptr = dyno->createNormalData(vertexCount * 3); pCalRenderer->getNormals(normal_ptr); dyno->releaseNormalDataPtr(); } else { vertex_ptr = dyno->getVertexDataPtr(); pCalRenderer->getVertices(vertex_ptr); dyno->releaseVertexDataPtr(); normal_ptr = dyno->getNormalDataPtr(); pCalRenderer->getNormals(normal_ptr); dyno->releaseNormalDataPtr(); } int faceCount = pCalRenderer->getFaceCount(); if (faceCount > 0) { int *face_ptr; if (faceCount > dyno->getNumFaces()) { face_ptr = dyno->createIndices(faceCount * 3); } else { face_ptr = dyno->getIndicesPtr(); } pCalRenderer->getFaces(face_ptr); dyno->releaseIndicesPtr(); dyno->setNumFaces(faceCount); } dyno->setNumPoints(vertexCount); // There are several situations that can happen here. // Model with/without texture coordinates // Model with/without texture maps // Model with/without texture mas name defined // Each model can be a mixture of the above. We want objects with // textures and texture coords. bool mapDataFound = false; std::vector<std::vector<CalCoreSubmesh::TextureCoordinate> > & vectorvectorTextureCoordinate = m_calModel->getVectorMesh()[meshId]->getSubmesh(submeshId)->getCoreSubmesh()->getVectorVectorTextureCoordinate(); // check if the map id is valid if ( vectorvectorTextureCoordinate.size() > 0) { textureCoordinateCount = vectorvectorTextureCoordinate[0].size(); } if((pCalRenderer->getMapCount() > 0) && (textureCoordinateCount > 0)) { for (int i = 0; i < pCalRenderer->getMapCount(); ++i) { MapData *md = reinterpret_cast<MapData*> (pCalRenderer->getMapUserData(i)); if (md) { dyno->setTexture(i, md->textureID, md->textureMaskID); mapDataFound = true; } else { // Can't have a missing texture map between units. break; } } } if (mapDataFound){ if (realloc) { texture_ptr = dyno->createTextureData(vertexCount * 2); textureCoordinateCount = pCalRenderer->getTextureCoordinates(0, texture_ptr); dyno->releaseTextureDataPtr(); } else { texture_ptr = dyno->getTextureDataPtr(); textureCoordinateCount = pCalRenderer->getTextureCoordinates(0, texture_ptr); dyno->releaseTextureDataPtr(); } if (textureCoordinateCount == -1) { // Need to ignore the texture buffer } // assert(textureCoordinateCount == vertexCount); } } } } pCalRenderer->endRendering(); }
void CCal3DSceneNode::render() { if ( bInitialized ) { irr::video::IVideoDriver* driver = SceneManager->getVideoDriver(); driver->setTransform( irr::video::ETS_WORLD, AbsoluteTransformation ); irr::video::S3DVertex tmp; irr::scene::SMeshBuffer mb; unsigned char meshColor[4]; // r g b a // get the renderer of the model CalRenderer* pCalRenderer; pCalRenderer = m_calModel->getRenderer(); pCalRenderer->setNormalization( true ); if ( this->DebugDataVisible ) { irr::video::SMaterial mat; mat.Wireframe = false; mat.Lighting = false; driver->setMaterial( mat ); driver->draw3DBox( Box ); CalSkeleton* pCalSkeleton = m_calModel->getSkeleton(); pCalSkeleton->calculateBoundingBoxes(); std::vector<CalBone*>& vectorCoreBone = pCalSkeleton->getVectorBone(); irr::core::aabbox3df b; CalVector p[8]; Vector3 v[8]; for ( size_t boneId = 0; boneId < vectorCoreBone.size(); ++boneId ) { CalBone* bone = vectorCoreBone[boneId]; CalBoundingBox& calBoundingBox = bone->getBoundingBox(); calBoundingBox.computePoints( p ); for ( int i = 0; i < 8; ++i ) { v[i].set( p[i].x, p[i].y, p[i].z ); } driver->setMaterial( mat ); // draw the box driver->draw3DLine( v[0], v[1], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[0], v[2], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[1], v[3], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[2], v[3], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[4], v[5], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[4], v[6], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[5], v[7], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[6], v[7], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[0], v[4], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[1], v[5], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[2], v[6], irr::video::SColor( 255, 0, 0, 255 ) ); driver->draw3DLine( v[3], v[7], irr::video::SColor( 255, 0, 0, 255 ) ); //printf("F: %f\n", v[0].X); } } // begin the rendering loop if ( pCalRenderer->beginRendering() ) { // get the number of meshes int meshCount; meshCount = pCalRenderer->getMeshCount(); // render all meshes of the model int meshId; for ( meshId = 0; meshId < meshCount; meshId++ ) { // get the number of submeshes int submeshCount; submeshCount = pCalRenderer->getSubmeshCount( meshId ); // render all submeshes of the mesh int submeshId; for ( submeshId = 0; submeshId < submeshCount; submeshId++ ) { // select mesh and submesh for further data access if ( pCalRenderer->selectMeshSubmesh( meshId, submeshId ) ) { // set the material ambient color pCalRenderer->getAmbientColor( &meshColor[0] ); material.AmbientColor.set( meshColor[3], meshColor[0], meshColor[1], meshColor[2] ); // set the material diffuse color pCalRenderer->getDiffuseColor( &meshColor[0] ); material.DiffuseColor.set( meshColor[3], meshColor[0], meshColor[1], meshColor[2] ); // set the material specular color pCalRenderer->getSpecularColor( &meshColor[0] ); material.SpecularColor.set( meshColor[3], meshColor[0], meshColor[1], meshColor[2] ); // set the material shininess factor material.Shininess = pCalRenderer->getShininess(); // get the transformed vertices of the submesh static float meshVertices[3000][3]; int vertexCount = 0; // TODO: //if (KERNEL.GetTicks() % 3 == 0) //- make lod dependent? vertexCount = pCalRenderer->getVertices( &meshVertices[0][0] ); // get the transformed normals of the submesh static float meshNormals[3000][3]; int normalsCount = 0; // if (KERNEL.GetTicks() % 3 == 0) normalsCount = pCalRenderer->getNormals( &meshNormals[0][0] ); // get the texture coordinates of the submesh static float meshTextureCoordinates[3000][2]; int textureCoordinateCount = 0; textureCoordinateCount = pCalRenderer->getTextureCoordinates( 0, &meshTextureCoordinates[0][0] ); // get the faces of the submesh static CalIndex meshFaces[5000][3]; int faceCount = 0; //if (KERNEL.GetTicks() % 12 == 0) faceCount = pCalRenderer->getFaces( &meshFaces[0][0] ); if ( ( pCalRenderer->getMapCount() > 0 ) && ( textureCoordinateCount > 0 ) ) { irr::video::ITexture* t = static_cast<irr::video::ITexture*>( pCalRenderer->getMapUserData( 0 ) ); material.Texture1 = t; } static S3DVertex vs[5000]; for ( int i = 0; i < vertexCount; i++ ) { vs[i].Pos.set( meshVertices[i][0], meshVertices[i][1], meshVertices[i][2] ); vs[i].Normal.set( meshNormals[i][0], meshNormals[i][1], meshNormals[i][2] ); vs[i].TCoords.set( meshTextureCoordinates[i][0], meshTextureCoordinates[i][1] ); vs[i].Color = irr::video::SColor( 255, 255, 255, 255 ); } static u16 is[5000]; for ( int i = 0; i < faceCount; i += 1 ) { is[i * 3 + 0] = meshFaces[i][0]; is[i * 3 + 1] = meshFaces[i][1]; is[i * 3 + 2] = meshFaces[i][2]; } //mb.Vertices.clear(); //mb.Vertices.reallocate(vertexCount); //for(int i=0;i<vertexCount;i++) //{ // tmp.Pos.set(meshVertices[i][0],meshVertices[i][1],meshVertices[i][2]); // tmp.Normal.set(meshNormals[i][0],meshNormals[i][1],meshNormals[i][2]); // tmp.TCoords.set(meshTextureCoordinates[i][0],meshTextureCoordinates[i][1]); // tmp.Color=irr::video::SColor(255,255,255,255); // mb.Vertices.push_back(tmp); //} //mb.Indices.clear(); //mb.Indices.reallocate(faceCount); //for(int i=0; i<faceCount; ++i) //{ // mb.Indices.push_back(meshFaces[i][0]); // mb.Indices.push_back(meshFaces[i][1]); // mb.Indices.push_back(meshFaces[i][2]); //} // draw driver->setMaterial( material ); //driver->drawIndexedTriangleList(mb.Vertices.const_pointer(),mb.Vertices.size(),mb.Indices.const_pointer(),faceCount); driver->drawIndexedTriangleList( vs, vertexCount, is, faceCount ); //driver->drawMeshBuffer(&mb); //CONSOLE.addx("#Verts %d #Norm %d #Tex %d #Faces %d #Map %d", // vertexCount,normalsCount,textureCoordinateCount,faceCount, pCalRenderer->getMapCount()); } } } // end the rendering pCalRenderer->endRendering(); } } }