public void Evaluate(int SpreadMax) { //if any of the inputs has changed //recompute the outputs FColladaModel = FColladaModelIn.SliceCount > 0 ? FColladaModelIn[0] : null; if (FColladaModel == null) { return; } if (FColladaModelIn.IsChanged || FIndex.IsChanged) { int index = FIndex[0]; List <Model.SkinnedInstanceMesh> skinnedMeshes = new List <Model.SkinnedInstanceMesh>(); foreach (Model.InstanceMesh mesh in FColladaModel.InstanceMeshes) { if (mesh is Model.SkinnedInstanceMesh) { skinnedMeshes.Add((Model.SkinnedInstanceMesh)mesh); } } if (skinnedMeshes.Count > 0) { if (FSelectedMesh != skinnedMeshes[index % skinnedMeshes.Count]) { FSelectedMesh = skinnedMeshes[index % skinnedMeshes.Count]; } } else { FSelectedMesh = null; } } if (FSelectedMesh == null) { return; } if (FColladaModelIn.IsChanged || FIndex.IsChanged || FTimeInput.IsChanged) { float time = FTimeInput[0]; if (FColladaModelIn.IsChanged || FIndex.IsChanged) { FSkeleton.ClearAll(); CreateSkeleton(FSkeleton, FSelectedMesh.RootBone, FSelectedMesh.Bones); } foreach (Model.Bone bone in FSelectedMesh.Bones) { FSkeleton.JointTable[bone.Name].BaseTransform = bone.GetTransformMatrix(time).ToMatrix4x4(); } FSkeletonOutput.SetInterface(FSkeleton); FSkeletonOutput.MarkPinAsChanged(); } }
public void Evaluate(int SpreadMax) { COLLADAUtil.Logger = new LoggerWrapper(FLogger); try { //if any of the inputs has changed //recompute the outputs if (FColladaModelIn.IsChanged || FIndex.IsChanged || FBinSize.IsChanged) { FSelectedInstanceMeshes.Clear(); FMeshNameOutput.SliceCount = 0; FMeshPathOutput.SliceCount = 0; FColladaModel = FColladaModelIn.SliceCount > 0 ? FColladaModelIn[0] : null; if (FColladaModel == null) { FMyMeshOutput.SliceCount = 0; FMaterialNameOutput.SliceCount = 0; // FFxIdOutput.SliceCount = 0; FTextureFileNameOutput.SliceCount = 0; FEmissiveColorOut.SliceCount = 0; FDiffuseColorOut.SliceCount = 0; FSpecularColorOut.SliceCount = 0; FShininessOut.SliceCount = 0; FOpaqueOut.SliceCount = 0; } else { //make negative bin sizes ok int binSize = FBinSize[0]; if (binSize < 0) { binSize = FColladaModel.InstanceMeshes.Count / Math.Abs(binSize); } List <Model.BasicMaterial> materialList = new List <Model.BasicMaterial>(); // FFxIdOutput.SliceCount = 0; for (int i = 0; i < FIndex.SliceCount; i++) { int index = FIndex[i] * binSize; index = ((index % FColladaModel.InstanceMeshes.Count) + FColladaModel.InstanceMeshes.Count) % FColladaModel.InstanceMeshes.Count; for (int j = index; j < index + binSize; j++) { Model.InstanceMesh instanceMesh = FColladaModel.InstanceMeshes[j % FColladaModel.InstanceMeshes.Count]; FSelectedInstanceMeshes.Add(instanceMesh); FLogger.Log(LogType.Debug, "Instance of mesh '" + instanceMesh + "' loaded."); string name = instanceMesh.ParentBone.NodeName; string path = name; var bone = instanceMesh.ParentBone; while (bone.Parent.NodeType == "NODE") { path = bone.Parent.NodeName + "/" + path; bone = bone.Parent; } foreach (Document.Primitive primitive in instanceMesh.Mesh.Primitives) { Model.BasicMaterial material; string bindedMaterialId; if (!instanceMesh.MaterialBinding.TryGetValue(primitive.material, out bindedMaterialId)) { bindedMaterialId = primitive.material; } if (FColladaModel.BasicMaterialsBinding.TryGetValue(bindedMaterialId, out material)) { materialList.Add(material); // FFxIdOutput.Add(bindedMaterialId); } else { materialList.Add(FNoMaterial); // FFxIdOutput.Add(bindedMaterialId); } FMeshNameOutput.Add(name); //add name of the mesh FMeshPathOutput.Add(path); //and prepend the group names it's in } } } FMaterialNameOutput.SliceCount = materialList.Count; FTextureFileNameOutput.SliceCount = materialList.Count; FEmissiveColorOut.SliceCount = materialList.Count; FDiffuseColorOut.SliceCount = materialList.Count; FSpecularColorOut.SliceCount = materialList.Count; FShininessOut.SliceCount = materialList.Count; FOpaqueOut.SliceCount = materialList.Count; for (int j = 0; j < materialList.Count; j++) { Model.BasicMaterial material = materialList[j]; FMaterialNameOutput[j] = material.Name; FTextureFileNameOutput[j] = material.Texture; if (material.EmissiveColor.HasValue) { FEmissiveColorOut[j] = new RGBAColor(material.EmissiveColor.Value.X, material.EmissiveColor.Value.Y, material.EmissiveColor.Value.Z, 1.0); } else { FEmissiveColorOut[j] = VColor.Black; } if (material.DiffuseColor.HasValue) { FDiffuseColorOut[j] = new RGBAColor(material.DiffuseColor.Value.X, material.DiffuseColor.Value.Y, material.DiffuseColor.Value.Z, 1.0); } else { FDiffuseColorOut[j] = VColor.White; } if (material.SpecularColor.HasValue) { FSpecularColorOut[j] = new RGBAColor(material.SpecularColor.Value.X, material.SpecularColor.Value.Y, material.SpecularColor.Value.Z, 1.0); } else { FSpecularColorOut[j] = VColor.Black; } if (material.SpecularPower.HasValue) { FShininessOut[j] = material.SpecularPower.Value; } else { FShininessOut[j] = 25.0; } // as of FCollada 3.03 opaque = 1.0, before opaque = 0.0 double alpha = 1.0; if (material.Alpha.HasValue) { alpha = material.Alpha.Value; } if (!FOpaqueIsOne) { FOpaqueOut[j] = 1 - alpha; } else { FOpaqueOut[j] = alpha; } } FMyMeshOutput.SliceCount = materialList.Count; FMyMeshOutput.MarkPinAsChanged(); foreach (Mesh m in FDeviceMeshes.Values) { FLogger.Log(LogType.Debug, "Destroying Resource..."); m.Dispose(); } FDeviceMeshes.Clear(); } } if (FColladaModelIn.IsChanged || FIndex.IsChanged || FBinSize.IsChanged || FTimeInput.IsChanged) { int maxCount = Math.Max(FTimeInput.SliceCount, FSelectedInstanceMeshes.Count); List <Matrix> transforms = new List <Matrix>(); List <Matrix> skinningTransforms = new List <Matrix>(); List <Matrix> bindShapeTransforms = new List <Matrix>(); List <Matrix> invBindPoseTransforms = new List <Matrix>(); for (int i = 0; i < maxCount && FSelectedInstanceMeshes.Count > 0; i++) { int meshIndex = i % FSelectedInstanceMeshes.Count; Model.InstanceMesh instanceMesh = FSelectedInstanceMeshes[meshIndex]; float time = FTimeInput[i]; Matrix m = instanceMesh.ParentBone.GetAbsoluteTransformMatrix(time) * FColladaModel.ConversionMatrix; for (int j = 0; j < instanceMesh.Mesh.Primitives.Count; j++) { transforms.Add(m); } // Skinning if (instanceMesh is Model.SkinnedInstanceMesh) { Model.SkinnedInstanceMesh skinnedInstanceMesh = (Model.SkinnedInstanceMesh)instanceMesh; skinningTransforms.AddRange(skinnedInstanceMesh.GetSkinningMatrices(time)); // am i right, that this whole thing will only work with 1 selected mesh? bindShapeTransforms.Add(skinnedInstanceMesh.BindShapeMatrix); for (int j = 0; j < skinnedInstanceMesh.InvBindMatrixList.Count; j++) { invBindPoseTransforms.Add(skinnedInstanceMesh.InvBindMatrixList[j]); } } } FTransformOutput.SliceCount = transforms.Count; for (int j = 0; j < transforms.Count; j++) { FTransformOutput.SetMatrix(j, transforms[j].ToMatrix4x4()); } FSkinningTransformOutput.SliceCount = skinningTransforms.Count; for (int j = 0; j < skinningTransforms.Count; j++) { FSkinningTransformOutput.SetMatrix(j, skinningTransforms[j].ToMatrix4x4()); } FBindShapeTransformOutput.SliceCount = bindShapeTransforms.Count; for (int j = 0; j < bindShapeTransforms.Count; j++) { FBindShapeTransformOutput.SetMatrix(j, bindShapeTransforms[j].ToMatrix4x4()); } FInvBindPoseTransformOutput.SliceCount = invBindPoseTransforms.Count; for (int j = 0; j < invBindPoseTransforms.Count; j++) { FInvBindPoseTransformOutput.SetMatrix(j, invBindPoseTransforms[j].ToMatrix4x4()); } } } catch (Exception e) { FLogger.Log(e); } }