FCDMaterialInstance* FCDGeometryInstance::AddMaterialInstance(FCDMaterial* material, const fchar* semantic) { FCDMaterialInstance* instance = AddMaterialInstance(); instance->SetMaterial(material); instance->SetSemantic(semantic); return instance; }
void CModelConverter::ReadDAESceneTree(FCDSceneNode* pNode, CConversionSceneNode* pScene) { size_t iTransforms = pNode->GetTransformCount(); Matrix4x4 mTransformations; for (size_t t = 0; t < iTransforms; t++) { FCDTransform* pTransform = pNode->GetTransform(t); FMMatrix44 m = pTransform->ToMatrix(); mTransformations *= Matrix4x4(m); } pScene->SetTransformations(mTransformations); size_t iInstances = pNode->GetInstanceCount(); for (size_t i = 0; i < iInstances; i++) { FCDEntityInstance* pInstance = pNode->GetInstance(i); switch (pInstance->GetType()) { case FCDEntityInstance::GEOMETRY: { FCDGeometryInstance* pGeometryInstance = dynamic_cast<FCDGeometryInstance*>(pInstance); FCDEntity* pEntity = pGeometryInstance->GetEntity(); size_t iMesh = pScene->m_pScene->FindMesh(convert_from_fstring(pEntity->GetName())); size_t iMeshInstance = pScene->AddMeshInstance(iMesh); size_t iMaterialInstances = pGeometryInstance->GetMaterialInstanceCount(); for (size_t m = 0; m < iMaterialInstances; m++) { FCDMaterialInstance* pMaterialInstance = pGeometryInstance->GetMaterialInstance(m); FCDMaterial* pMaterial = pMaterialInstance->GetMaterial(); tstring sMaterial = pMaterial?convert_from_fstring(pMaterialInstance->GetMaterial()->GetName()):""; tstring sMaterialStub = convert_from_fstring(pMaterialInstance->GetSemantic()); size_t iMaterial = pScene->m_pScene->FindMaterial(sMaterial); size_t iMaterialStub = pScene->m_pScene->GetMesh(iMesh)->FindMaterialStub(sMaterialStub); pScene->GetMeshInstance(iMeshInstance)->AddMappedMaterial(iMaterialStub, iMaterial); } } } } size_t iChildren = pNode->GetChildrenCount(); for (size_t j = 0; j < iChildren; j++) { FCDSceneNode* pChildNode = pNode->GetChild(j); size_t iNode = pScene->AddChild(convert_from_fstring(pChildNode->GetName())); ReadDAESceneTree(pChildNode, pScene->GetChild(iNode)); } }
ColladaMeshInstance * ColladaScene::CreateMeshInstance( ColladaMesh * mesh, FCDGeometryInstance * geometryInstance, bool animated) { ColladaMeshInstance * meshInstance = new ColladaMeshInstance(animated); meshInstance->geometryInstance = geometryInstance; // now the most difficult, material binding for (int i = 0; i < mesh->GetPolygonGroupCount(); i++) { fstring polygonMaterialSemantic = mesh->GetPolygonGroup(i)->GetMaterialSemantic(); ColladaMaterial * material = 0; // look for this material_semantic in geometry_instance for (int k = 0; k < (int) geometryInstance->GetMaterialInstanceCount(); k++) { // look for this material in my material lib, so I store a pointer FCDMaterialInstance * materialInstance = geometryInstance->GetMaterialInstance(k); fstring materialSemantic = materialInstance->GetSemantic(); if (materialSemantic == polygonMaterialSemantic) { fm::string materialId = materialInstance->GetMaterial()->GetDaeId(); material = FindMaterialWithName(materialId); } } printf(" - mesh instance: %s ", mesh->mesh->GetDaeId().c_str()); if (material) { printf(" material: %s ", material->material->GetDaeId().c_str()); if (material->hasDiffuseTexture) wprintf(L" diftex: %s\n", (wchar_t*)(material->diffuseTexture->image->GetFilename().c_str())); } printf("\n"); ColladaPolygonGroup * polyGroup = mesh->GetPolygonGroup(i); printf("- mesh instance added polygroup: 0x%08x %d\n", polyGroup, i); ColladaPolygonGroupInstance * polygonGroupInstance = new ColladaPolygonGroupInstance(polyGroup, material); meshInstance->AddPolygonGroupInstance(polygonGroupInstance); } return meshInstance; }
FCDMaterialInstance* FCDGeometryInstance::AddMaterialInstance(FCDMaterial* material, FCDGeometryPolygons* polygons) { FCDMaterialInstance* instance = AddMaterialInstance(); instance->SetMaterial(material); if (polygons != NULL) { const fstring& semantic = polygons->GetMaterialSemantic(); if (!semantic.empty()) { instance->SetSemantic(polygons->GetMaterialSemantic()); } else { // Generate a semantic. fstring semantic = TO_FSTRING(material->GetDaeId()) + TO_FSTRING(polygons->GetFaceOffset()); polygons->SetMaterialSemantic(semantic); instance->SetSemantic(semantic); } } return instance; }
bool FArchiveXML::LoadMaterialInstance(FCDObject* object, xmlNode* instanceNode) { FCDMaterialInstance* materialInstance = (FCDMaterialInstance*)object; // This is not loaded the same as the FCDEntityInstance ones. // Load it first, otherwise FCDEntityInstance will ASSERT (with no Uri) fm::string uri = ReadNodeProperty(instanceNode, DAE_TARGET_ATTRIBUTE); AddAttribute(instanceNode, DAE_URL_ATTRIBUTE, uri); if (!FArchiveXML::LoadEntityInstance(object, instanceNode)) return false; materialInstance->SetSemantic(TO_FSTRING(ReadNodeProperty(instanceNode, DAE_SYMBOL_ATTRIBUTE))); // Read in the ColladaFX bindings while (materialInstance->GetBindingCount() != 0) materialInstance->GetBinding(materialInstance->GetBindingCount() - 1)->Release(); xmlNodeList bindNodes; FindChildrenByType(instanceNode, DAE_BIND_ELEMENT, bindNodes); for (xmlNodeList::iterator itB = bindNodes.begin(); itB != bindNodes.end(); ++itB) { fm::string semantic = ReadNodeSemantic(*itB); fm::string target = ReadNodeProperty(*itB, DAE_TARGET_ATTRIBUTE); materialInstance->AddBinding(semantic, target); } // Read in the ColladaFX vertex inputs xmlNodeList bindVertexNodes; while (materialInstance->GetVertexInputBindingCount() != 0) materialInstance->GetVertexInputBinding(materialInstance->GetVertexInputBindingCount() - 1)->Release(); FindChildrenByType(instanceNode, DAE_BIND_VERTEX_INPUT_ELEMENT, bindVertexNodes); for (xmlNodeList::iterator itB = bindVertexNodes.begin(); itB != bindVertexNodes.end(); ++itB) { fm::string inputSet = ReadNodeProperty(*itB, DAE_INPUT_SET_ATTRIBUTE); fm::string inputSemantic = ReadNodeProperty(*itB, DAE_INPUT_SEMANTIC_ATTRIBUTE); materialInstance->AddVertexInputBinding(ReadNodeSemantic(*itB).c_str(), FUDaeGeometryInput::FromString(inputSemantic.c_str()), FUStringConversion::ToInt32(inputSet)); } materialInstance->SetDirtyFlag(); return true; }
void ColladaMeshFactory::GenerateMeshDatafromPolygonsFull( RevModel** aModel, RevIndexData& aIndexData, RevVertexDataNormal& aVertexData, RevInputData& aInputData, FCDGeometryInstance* aInstance, FCDGeometryMesh* aMesh, FCDocument* aColladaDocument, bool aHasBoneWeightsFlag, FCDController* aController, FCDControllerInstance* aControllerInstance) { int polygonalMeshes= static_cast<int>(aMesh->GetPolygonsCount()); // assert(polygonalMeshes==1); // how to handle multiple meshes ? handle later // To do add support for multiple meshes ? FCDSkinController* skinControl=NULL; if(aHasBoneWeightsFlag==true) { skinControl=aController->GetSkinController(); skinControl->ReduceInfluences(4); } int myVertexCount=0; int duplicatesCount=0; int currentIndex=0; std::map<RevVertexIndexmapKey,int> vertexList; std::map<RevVertexIndexmapKey,int>::iterator vertexIterator; std::vector<RevVertexIndexmapKey> vertexes; aIndexData.myNrOfIndexes =0; aIndexData.myFormat =DXGI_FORMAT_R32_UINT; for(int polygonMeshIndex=0;polygonMeshIndex<static_cast<int>(polygonalMeshes);polygonMeshIndex++) { FCDGeometryPolygons* somePolygons=aMesh->GetPolygons(polygonMeshIndex); FCDGeometryPolygonsInput* positionInput=somePolygons->FindInput(FUDaeGeometryInput::POSITION); aIndexData.myNrOfIndexes+=positionInput->GetIndexCount(); } aIndexData.mySize=aIndexData.myNrOfIndexes*sizeof(unsigned int); aIndexData.myIndexData = new char [aIndexData.mySize] (); UINT* indexArray=reinterpret_cast<unsigned int*>(aIndexData.myIndexData); FCDGeometrySource* positionSource=aMesh->FindSourceByType(FUDaeGeometryInput::POSITION); FCDGeometrySource* normalSource=aMesh->FindSourceByType(FUDaeGeometryInput::NORMAL); FCDGeometrySource* colorSource=aMesh->FindSourceByType(FUDaeGeometryInput::COLOR); FCDGeometrySource* textureCordinatesSource=aMesh->FindSourceByType(FUDaeGeometryInput::TEXCOORD); FCDGeometrySource* geoTangentSource=aMesh->FindSourceByType(FUDaeGeometryInput::GEOTANGENT); FCDGeometrySource* texTangentSource=aMesh->FindSourceByType(FUDaeGeometryInput::TEXTANGENT); FCDGeometrySource* geoBiNormalSource=aMesh->FindSourceByType(FUDaeGeometryInput::GEOBINORMAL); FCDGeometrySource* texBiNormalSource=aMesh->FindSourceByType(FUDaeGeometryInput::TEXBINORMAL); RevModelRenderEssentials renderEssentials( D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST ); SelectEffectOnModel(aModel, aInputData); RevTextures tex; for(int polygonMeshIndex=0;polygonMeshIndex<polygonalMeshes;polygonMeshIndex++) { (*aModel)->SetIsNullObjectFlag( false ); FCDGeometryPolygons* somePolygons=aMesh->GetPolygons(polygonMeshIndex); FCDGeometryPolygonsInput* positionInput=somePolygons->FindInput(FUDaeGeometryInput::POSITION); FCDGeometryPolygonsInput* normalInput=somePolygons->FindInput(FUDaeGeometryInput::NORMAL); FCDGeometryPolygonsInput* colorInput=somePolygons->FindInput(FUDaeGeometryInput::COLOR); FCDGeometryPolygonsInput* texCoordInput=somePolygons->FindInput(FUDaeGeometryInput::TEXCOORD); FCDGeometryPolygonsInput* geoTangentInput=somePolygons->FindInput(FUDaeGeometryInput::GEOTANGENT); FCDGeometryPolygonsInput* texTangentInput=somePolygons->FindInput(FUDaeGeometryInput::TEXTANGENT); FCDGeometryPolygonsInput* geoBiNormalInput=somePolygons->FindInput(FUDaeGeometryInput::GEOBINORMAL); FCDGeometryPolygonsInput* texBiNormalInput=somePolygons->FindInput(FUDaeGeometryInput::TEXBINORMAL); somePolygons->GetFaceVertexCount(); renderEssentials.myVertexStart = 0; renderEssentials.myIndexStart = currentIndex; renderEssentials.myIndexCount = positionInput->GetIndexCount(); for(int i=0;i<static_cast<int>(positionInput->GetIndexCount());i++) { RevVertexIndexmapKey key; if(positionInput!=NULL) { key.myKeys[0]=positionInput->GetIndices()[i]; } if(normalInput!=NULL) { key.myKeys[1]=normalInput->GetIndices()[i]; } if(colorInput!=NULL) { key.myKeys[2]=colorInput->GetIndices()[i]; } if(texCoordInput!=NULL) { key.myKeys[3]=texCoordInput->GetIndices()[i]; } if(geoTangentInput!=NULL) { key.myKeys[4]=geoTangentInput->GetIndices()[i]; } if(texTangentInput!=NULL) { key.myKeys[5]=texTangentInput->GetIndices()[i]; } if(geoBiNormalInput!=NULL) { key.myKeys[6]=geoBiNormalInput->GetIndices()[i]; } if(texBiNormalInput!=NULL) { key.myKeys[7]=texBiNormalInput->GetIndices()[i]; } vertexIterator=vertexList.find(key); if(vertexIterator==vertexList.end()) { indexArray[currentIndex]=myVertexCount; std::pair<RevVertexIndexmapKey,int> tempPair(key,myVertexCount); vertexList.insert(tempPair); vertexes.push_back(key); myVertexCount++; // create indexes } else { indexArray[currentIndex]=(*vertexIterator).second; duplicatesCount++; // Read Created Vertex } currentIndex++; } for (unsigned int k=0; k<aInstance->GetMaterialInstanceCount(); k++) { FCDMaterialInstance* materialInstance; materialInstance=aInstance->GetMaterialInstance(k); if(aMesh->GetPolygons(polygonMeshIndex)->GetMaterialSemantic()==materialInstance->GetSemantic()) { LoadMaterialNew(polygonMeshIndex,materialInstance->GetMaterial(),aColladaDocument, tex); } } } (*aModel)->SetModelTextures( tex ); aVertexData.myNrOfVertexes=myVertexCount; aVertexData.mySize=aVertexData.myStride*aVertexData.myNrOfVertexes; aVertexData.myVertexData =new char [aVertexData.mySize] (); for(int i=0;i<aIndexData.myNrOfIndexes;i+=3) { unsigned int temp; temp=indexArray[i+0]; indexArray[i+0]=indexArray[i+2]; indexArray[i+2]=temp; } myVertexCount=0; for(int i=0;i<static_cast<int>(vertexes.size());i++) { RevVertexIndexmapKey key=vertexes[i]; int offset=0; std::pair<RevVertexIndexmapKey,int> tempPair(key,myVertexCount); vertexList.insert(tempPair); // Create Vertex if(key.myKeys[0]!=-1) { CU::Vector3f pos; memcpy(&pos, &positionSource->GetData()[key.myKeys[0]*positionSource->GetStride()],12); // pos.y=-pos.y; // pos.z=-pos.z; memcpy(&aVertexData.myVertexData[myVertexCount*aVertexData.myStride+offset], &pos,12); offset+=12; } if(aHasBoneWeightsFlag==true) { assert(key.myKeys[0]!=-1); FCDSkinControllerVertex* vertexsInfluence; vertexsInfluence=skinControl->GetVertexInfluence(key.myKeys[0]); int boneData=0; int weightData=0; assert(vertexsInfluence->GetPairCount()<=4); for(int j=0;j<static_cast<int>(vertexsInfluence->GetPairCount());j++) { assert(j<4); FCDJointWeightPair* pair=vertexsInfluence->GetPair(j); assert(pair->jointIndex<256); boneData |= pair->jointIndex << (j*8); int weight=static_cast<int>((pair->weight*255.0f+0.5)); assert(weight>=0); assert(weight<=255); weightData |= weight << (j*8); } memcpy(&aVertexData.myVertexData[myVertexCount*aVertexData.myStride+offset],&weightData,4); offset+=4; memcpy(&aVertexData.myVertexData[myVertexCount*aVertexData.myStride+offset],&boneData,4); offset+=4; } if(key.myKeys[1]!=-1) { CU::Vector3f normal; memcpy(&normal, &normalSource->GetData()[key.myKeys[1]*normalSource->GetStride()],12); // normal.y=-normal.y; memcpy(&aVertexData.myVertexData[myVertexCount*aVertexData.myStride+offset], &normal,12); offset+=12; } if(key.myKeys[2]!=-1) { memcpy(&aVertexData.myVertexData[myVertexCount*aVertexData.myStride+offset], &colorSource->GetData()[key.myKeys[2]*colorSource->GetStride()],16); offset+=16; } if(key.myKeys[3]!=-1) { CU::Vector2f UV; memcpy(&UV, &textureCordinatesSource->GetData()[key.myKeys[3]*textureCordinatesSource->GetStride()],8); UV.v=1.0f-UV.v; memcpy(&aVertexData.myVertexData[myVertexCount*aVertexData.myStride+offset], &UV,8); offset+=8; } if(key.myKeys[4]!=-1) { CU::Vector3f tangent; memcpy(&tangent, &geoTangentSource->GetData()[key.myKeys[4]*geoTangentSource->GetStride()],12); // tangent.y=-tangent.y; memcpy(&aVertexData.myVertexData[myVertexCount*aVertexData.myStride+offset], &tangent,12); offset+=12; } if(key.myKeys[5]!=-1) { CU::Vector3f tangent; memcpy(&tangent, &texTangentSource->GetData()[key.myKeys[5]*texTangentSource->GetStride()],12); // tangent.y=-tangent.y; memcpy(&aVertexData.myVertexData[myVertexCount*aVertexData.myStride+offset], &tangent,12); offset+=12; } if(key.myKeys[6]!=-1) { memcpy(&aVertexData.myVertexData[myVertexCount*aVertexData.myStride+offset], &geoBiNormalSource->GetData()[key.myKeys[6]*geoBiNormalSource->GetStride()],12); offset+=12; } if(key.myKeys[7]!=-1) { memcpy(&aVertexData.myVertexData[myVertexCount*aVertexData.myStride+offset], &texBiNormalSource->GetData()[key.myKeys[7]*texBiNormalSource->GetStride()],12); offset+=12; } myVertexCount++; } if( (*aModel)->Init( aVertexData, aIndexData, aInputData, renderEssentials ) ==false) { assert(0 && "Something went wrong in trying to init the current model"); } }