示例#1
0
        public void ExportAssImp(string fileName, string modelType, ExportSettings settings)
        {
            fileName = Path.GetFullPath(fileName); // Get absolute path instead of relative
            string outDir        = Path.GetDirectoryName(fileName);
            string fileNameNoExt = Path.GetFileNameWithoutExtension(fileName);

            fileName = Path.Combine(outDir, fileNameNoExt + ".dae");

            Scene outScene = new Scene();

            outScene.RootNode = new Node("RootNode");

            Materials.FillScene(outScene, Textures, outDir);
            Shapes.FillScene(outScene, VertexData.Attributes, Joints.FlatSkeleton, SkinningEnvelopes.InverseBindMatrices);
            Scenegraph.FillScene(outScene, Joints.FlatSkeleton, settings.UseSkeletonRoot);
            Scenegraph.CorrectMaterialIndices(outScene, Materials);
            Textures.DumpTextures(outDir);


            foreach (Mesh mesh in outScene.Meshes)
            {
                // Assimp has a JoinIdenticalVertices post process step, but we can't use that or the skinning info we manually add won't take it into account.
                RemoveDuplicateVertices(mesh);
            }


            AssimpContext cont = new AssimpContext();

            cont.ExportFile(outScene, fileName, "collada", PostProcessSteps.ValidateDataStructure);


            //if (SkinningEnvelopes.Weights.Count == 0)
            //    return; // There's no skinning information, so we can stop here

            // Now we need to add some skinning info, since AssImp doesn't do it for some bizarre reason

            StreamWriter test = new StreamWriter(fileName + ".tmp");
            StreamReader dae  = File.OpenText(fileName);

            while (!dae.EndOfStream)
            {
                string line = dae.ReadLine();

                if (line == "  <library_visual_scenes>")
                {
                    AddControllerLibrary(outScene, test);
                    test.WriteLine(line);
                    test.Flush();
                }
                else if (line.Contains("<node"))
                {
                    Regex reg   = new Regex("^( +)<node id=\"([^\"]+)\" +name=\"[^\"]+\" +type=\"NODE\">$");
                    Match match = reg.Match(line);

                    if (match.Success)
                    {
                        string indentation = match.Groups[1].Value;
                        string joint_name  = match.Groups[2].Value;
                        if (Joints.FlatSkeleton.Exists(x => x.Name == joint_name))
                        {
                            string jointLine = indentation + $"<node id=\"{joint_name}\" name=\"{joint_name}\" sid=\"{joint_name}\" type=\"JOINT\">";
                            test.WriteLine(jointLine);
                        }
                        else
                        {
                            test.WriteLine(line);
                        }
                    }
                    else
                    {
                        test.WriteLine(line);
                    }
                    test.Flush();
                }
                else if (line.Contains("<material id=\""))
                {
                    Regex reg   = new Regex("^    <material id=\"([^\"]+)\" name=\"[^\"]+\">$");
                    Match match = reg.Match(line);
                    if (match.Success)
                    {
                        string mat_name_sanitized = match.Groups[1].Value;
                        int    mat_index          = Materials.GetMaterialIndexFromSanitizedMaterialName(mat_name_sanitized);
                        string mat_name           = Materials.m_Materials[mat_index].Name;
                        string matLine            = $"    <material id=\"{mat_name_sanitized}\" name=\"{mat_name}\">";
                        test.WriteLine(matLine);
                    }
                    else
                    {
                        test.WriteLine(line);
                    }
                    test.Flush();
                }
                else if (line.Contains("</visual_scene>"))
                {
                    foreach (Mesh mesh in outScene.Meshes)
                    {
                        test.WriteLine($"      <node id=\"{ mesh.Name }\" name=\"{ mesh.Name }\" type=\"NODE\">");

                        test.WriteLine($"       <instance_controller url=\"#{ mesh.Name }-skin\">");
                        test.WriteLine("        <skeleton>#skeleton_root</skeleton>");
                        test.WriteLine("        <bind_material>");
                        test.WriteLine("         <technique_common>");
                        test.WriteLine($"          <instance_material symbol=\"{ Materials.m_Materials[mesh.MaterialIndex].Name }\" target=\"#{ Materials.m_Materials[mesh.MaterialIndex].Name.Replace("(", "_").Replace(")", "_") }\" />");
                        test.WriteLine("         </technique_common>");
                        test.WriteLine("        </bind_material>");
                        test.WriteLine("       </instance_controller>");

                        test.WriteLine("      </node>");
                        test.Flush();
                    }

                    test.WriteLine(line);
                    test.Flush();
                }
                else
                {
                    test.WriteLine(line);
                    test.Flush();
                }
            }

            test.Close();
            dae.Close();

            File.Copy(fileName + ".tmp", fileName, true);
            File.Delete(fileName + ".tmp");
        }
示例#2
0
文件: Model.cs 项目: kai13xd/SuperBMD
        public void ExportAssImp(string fileName, string outFilepath, string modelType, ExportSettings settings, bool keepmatnames = true)
        {
            string outDir = Path.GetDirectoryName(outFilepath);

            //string fileNameNoExt = Path.GetFileNameWithoutExtension(fileName);
            fileName = outFilepath;//Path.Combine(outDir, fileNameNoExt + ".dae");

            Scene outScene = new Scene();

            outScene.RootNode = new Node("RootNode");

            Scenegraph.FillScene(outScene, Joints.FlatSkeleton, settings.UseSkeletonRoot);
            Dictionary <string, int> slots_to_uvindex = Materials.FillScene(outScene, Textures, outDir, keepmatnames);

            Shapes.FillScene(outScene, VertexData.Attributes, Joints.FlatSkeleton, SkinningEnvelopes.InverseBindMatrices);
            Scenegraph.CorrectMaterialIndices(outScene, Materials);
            Textures.DumpTextures(outDir);

            foreach (Mesh mesh in outScene.Meshes)
            {
                Console.WriteLine(String.Format("Texcoord count: {0}", mesh.TextureCoordinateChannelCount));
            }

            if (true)  //(SkinningEnvelopes.Weights.Count == 0)
            {
                Assimp.Node geomNode = new Node(Path.GetFileNameWithoutExtension(fileName), outScene.RootNode);

                for (int i = 0; i < Shapes.Shapes.Count; i++)
                {
                    geomNode.MeshIndices.Add(i);
                }

                outScene.RootNode.Children.Add(geomNode);
            }

            AssimpContext cont = new AssimpContext();

            cont.ExportFile(outScene, fileName, "collada", PostProcessSteps.ValidateDataStructure | PostProcessSteps.JoinIdenticalVertices);
            //cont.ExportFile(outScene, fileName, "collada");


            List <string> a;

            //if (SkinningEnvelopes.Weights.Count == 0)
            //    return; // There's no skinning information, so we can stop here

            //return; // adding skinning info is buggy so we won't do it
            // Now we need to add some skinning info, since AssImp doesn't do it for some bizarre reason

            bool hasWeights = SkinningEnvelopes.Weights.Count != 0;

            hasWeights = false;
            StreamWriter test      = new StreamWriter(fileName + ".tmp");
            StreamReader dae       = File.OpenText(fileName);
            bool         dontWrite = false;

            while (!dae.EndOfStream)
            {
                string line = dae.ReadLine();

                //if (SkinningEnvelopes.Weights.Count != 0) {
                if (hasWeights && line == "  <library_visual_scenes>")
                {
                    AddControllerLibrary(outScene, test);
                    test.WriteLine(line);
                    test.Flush();
                }
                else if (hasWeights && line.Contains("<node"))
                {
                    string[] testLn = line.Split('\"');
                    string   name   = testLn[3];

                    if (Joints.FlatSkeleton.Exists(x => x.Name == name))
                    {
                        string jointLine = line.Replace(">", $" sid=\"{ name }\" type=\"JOINT\">");
                        test.WriteLine(jointLine);
                        test.Flush();
                    }
                    else
                    {
                        test.WriteLine(line);
                        test.Flush();
                    }
                }
                else if (hasWeights && line.Contains("</visual_scene>"))
                {
                    foreach (Mesh mesh in outScene.Meshes)
                    {
                        string matname = "mat";
                        if (keepmatnames == true)
                        {
                            matname = AssimpMatnameSanitize(mesh.MaterialIndex, outScene.Materials[mesh.MaterialIndex].Name);
                        }
                        else
                        {
                            matname = AssimpMatnameSanitize(mesh.MaterialIndex, matname);
                        }

                        test.WriteLine($"      <node id=\"{ mesh.Name }\" name=\"{ mesh.Name }\" type=\"NODE\">");

                        test.WriteLine($"       <instance_controller url=\"#{ mesh.Name }-skin\">");
                        test.WriteLine("        <skeleton>#skeleton_root</skeleton>");
                        test.WriteLine("        <bind_material>");
                        test.WriteLine("         <technique_common>");
                        test.WriteLine($"          <instance_material symbol=\"theresonlyone\" target=\"#{matname}\" />");
                        test.WriteLine("         </technique_common>");
                        test.WriteLine("        </bind_material>");
                        test.WriteLine("       </instance_controller>");

                        test.WriteLine("      </node>");
                        test.Flush();
                    }

                    test.WriteLine(line);
                    test.Flush();
                }
                else if (hasWeights && line.Contains("<matrix"))
                {
                    string matLine = line.Replace("<matrix>", "<matrix sid=\"matrix\">");
                    test.WriteLine(matLine);
                    test.Flush();
                }
                else if (line.Contains("<library_images>"))
                {
                    dontWrite = true;
                    Console.WriteLine("Hello Hallo");
                }
                else if (line.Contains("</library_images>"))
                {
                    dontWrite = false;
                    Console.WriteLine("Hello Hallo2");
                    // Add our own images here
                    test.WriteLine("  <library_images>");
                    WriteTexturesToStream(outScene, test);
                    test.WriteLine(line);
                    test.Flush();
                }
                else if (line.Contains("<library_effects>"))
                {
                    dontWrite = true;
                    Console.WriteLine("Hello Hallo3");
                    // We get rid of the existing library effects
                }
                else if (line.Contains("</library_effects>"))
                {
                    dontWrite = false;
                    Console.WriteLine("Hello Hallo4");
                    // Add our own library_effects here
                    test.WriteLine("    <library_effects>");
                    WriteMaterialsToStream(outScene, test, slots_to_uvindex);
                    test.WriteLine(line);
                    test.Flush();
                }
                else if (!dontWrite)
                {
                    test.WriteLine(line);
                    test.Flush();
                }
            }
            test.Close();
            dae.Close();

            File.Copy(fileName + ".tmp", fileName, true);
            File.Delete(fileName + ".tmp");
        }
示例#3
0
        public void ExportAssImp(string fileName, string modelType, ExportSettings settings)
        {
            string outDir        = Path.GetDirectoryName(fileName);
            string fileNameNoExt = Path.GetFileNameWithoutExtension(fileName);

            fileName = Path.Combine(outDir, fileNameNoExt + ".dae");

            Scene outScene = new Scene();

            outScene.RootNode = new Node("RootNode");

            Scenegraph.FillScene(outScene, Joints.FlatSkeleton, settings.UseSkeletonRoot);
            Materials.FillScene(outScene, Textures, outDir);
            Shapes.FillScene(outScene, VertexData.Attributes, Joints.FlatSkeleton, SkinningEnvelopes.InverseBindMatrices);
            Scenegraph.CorrectMaterialIndices(outScene, Materials);

            if (SkinningEnvelopes.Weights.Count == 0)
            {
                Assimp.Node geomNode = new Node(Path.GetFileNameWithoutExtension(fileName), outScene.RootNode);

                for (int i = 0; i < Shapes.Shapes.Count; i++)
                {
                    geomNode.MeshIndices.Add(i);
                }

                outScene.RootNode.Children.Add(geomNode);
            }

            AssimpContext cont = new AssimpContext();

            cont.ExportFile(outScene, fileName, "collada", PostProcessSteps.ValidateDataStructure);

            if (SkinningEnvelopes.Weights.Count == 0)
            {
                return; // There's no skinning information, so we can stop here
            }
            // Now we need to add some skinning info, since AssImp doesn't do it for some bizarre reason

            StreamWriter test = new StreamWriter(fileName + ".tmp");
            StreamReader dae  = File.OpenText(fileName);

            while (!dae.EndOfStream)
            {
                string line = dae.ReadLine();

                if (line == "  <library_visual_scenes>")
                {
                    AddControllerLibrary(outScene, test);
                    test.WriteLine(line);
                    test.Flush();
                }
                else if (line.Contains("<node"))
                {
                    string[] testLn = line.Split('\"');
                    string   name   = testLn[3];

                    if (Joints.FlatSkeleton.Exists(x => x.Name == name))
                    {
                        string jointLine = line.Replace(">", $" sid=\"{ name }\" type=\"JOINT\">");
                        test.WriteLine(jointLine);
                        test.Flush();
                    }
                    else
                    {
                        test.WriteLine(line);
                        test.Flush();
                    }
                }
                else if (line.Contains("</visual_scene>"))
                {
                    foreach (Mesh mesh in outScene.Meshes)
                    {
                        test.WriteLine($"      <node id=\"{ mesh.Name }\" name=\"{ mesh.Name }\" type=\"NODE\">");

                        test.WriteLine($"       <instance_controller url=\"#{ mesh.Name }-skin\">");
                        test.WriteLine("        <skeleton>#skeleton_root</skeleton>");
                        test.WriteLine("        <bind_material>");
                        test.WriteLine("         <technique_common>");
                        test.WriteLine($"          <instance_material symbol=\"theresonlyone\" target=\"#m{ mesh.MaterialIndex }mat\" />");
                        test.WriteLine("         </technique_common>");
                        test.WriteLine("        </bind_material>");
                        test.WriteLine("       </instance_controller>");

                        test.WriteLine("      </node>");
                        test.Flush();
                    }

                    test.WriteLine(line);
                    test.Flush();
                }
                else if (line.Contains("<matrix"))
                {
                    string matLine = line.Replace("<matrix>", "<matrix sid=\"matrix\">");
                    test.WriteLine(matLine);
                    test.Flush();
                }
                else
                {
                    test.WriteLine(line);
                    test.Flush();
                }
            }

            test.Close();
            dae.Close();

            File.Copy(fileName + ".tmp", fileName, true);
            File.Delete(fileName + ".tmp");
        }
示例#4
0
        public void ExportAssImp(string fileName, string modelType, ExportSettings settings, Arguments cmdargs)
        {
            fileName = Path.GetFullPath(fileName); // Get absolute path instead of relative
            string outDir        = Path.GetDirectoryName(fileName);
            string fileNameNoExt = Path.GetFileNameWithoutExtension(fileName);

            if (modelType == "obj")
            {
                fileName = Path.Combine(outDir, fileNameNoExt + ".obj");
            }
            else
            {
                fileName = Path.Combine(outDir, fileNameNoExt + ".dae");
            }
            Scene outScene = new Scene {
                RootNode = new Node("RootNode")
            };

            Console.WriteLine();
            Console.WriteLine("Processing Materials ->");
            Materials.FillScene(outScene, Textures, outDir);
            Console.WriteLine();
            Console.WriteLine("Processing Meshes ->");
            Shapes.FillScene(outScene, VertexData.Attributes, Joints.FlatSkeleton, SkinningEnvelopes.InverseBindMatrices);
            Console.WriteLine();
            Console.Write("Processing Skeleton");
            Scenegraph.FillScene(outScene, Joints.FlatSkeleton, settings.UseSkeletonRoot);
            Scenegraph.CorrectMaterialIndices(outScene, Materials);
            Console.WriteLine();
            Console.WriteLine();
            Console.WriteLine("Processing Textures ->");
            Textures.DumpTextures(outDir, fileNameNoExt + "_tex_headers.json", true, cmdargs.readMipmaps);

            string infPath = Path.Combine(outDir, fileNameNoExt + "_hierarchy.json");

            this.Scenegraph.DumpJson(infPath);

            Console.WriteLine();
            Console.WriteLine("Removing Duplicate Verticies ->");
            foreach (Mesh mesh in outScene.Meshes)
            {
                Console.Write(mesh.Name.Replace('_', ' ') + ": ");
                // Assimp has a JoinIdenticalVertices post process step, but we can't use that or the skinning info we manually add won't take it into account.
                RemoveDuplicateVertices(mesh);
                Console.Write("✓");
                Console.WriteLine();
            }


            AssimpContext cont = new AssimpContext();

            if (modelType == "obj")
            {
                Console.WriteLine("Writing the OBJ file...");
                cont.ExportFile(outScene, fileName, "obj");//, PostProcessSteps.ValidateDataStructure);
                using (System.IO.StreamWriter file = new System.IO.StreamWriter(fileName)) {
                    string mtllibname = fileName.Split(new char[] { '\\', '/' }, StringSplitOptions.RemoveEmptyEntries).Last() + ".mtl";
                    file.WriteLine(String.Format("mtllib {0}", mtllibname));
                    foreach (Assimp.Mesh mesh in outScene.Meshes)
                    {
                        foreach (Assimp.Vector3D vertex in mesh.Vertices)
                        {
                            file.WriteLine(String.Format("v {0} {1} {2}", vertex.X, vertex.Y, vertex.Z));
                        }
                    }

                    foreach (Assimp.Mesh mesh in outScene.Meshes)
                    {
                        foreach (Assimp.Vector3D normal in mesh.Normals)
                        {
                            file.WriteLine(String.Format("vn {0} {1} {2}", normal.X, normal.Y, normal.Z));
                        }
                    }

                    foreach (Assimp.Mesh mesh in outScene.Meshes)
                    {
                        if (mesh.HasTextureCoords(0))
                        {
                            foreach (Assimp.Vector3D uv in mesh.TextureCoordinateChannels[0])
                            {
                                file.WriteLine(String.Format("vt {0} {1}", uv.X, uv.Y));
                            }
                        }
                    }

                    int vertex_offset = 1;

                    foreach (Assimp.Mesh mesh in outScene.Meshes)
                    {
                        string material_name = outScene.Materials[mesh.MaterialIndex].Name;
                        file.WriteLine(String.Format("usemtl {0}", material_name));



                        foreach (Assimp.Face face in mesh.Faces)
                        {
                            file.Write("f ");
                            foreach (int index in face.Indices)
                            {
                                file.Write(index + vertex_offset);
                                if (mesh.HasTextureCoords(0))
                                {
                                    file.Write("/");
                                    file.Write(index + vertex_offset);
                                }
                                if (!mesh.HasTextureCoords(0) && mesh.HasNormals)
                                {
                                    file.Write("//");
                                    file.Write(index + vertex_offset);
                                }
                                else if (mesh.HasNormals)
                                {
                                    file.Write("/");
                                    file.Write(index + vertex_offset);
                                }
                                file.Write(" ");
                            }
                            file.Write("\n");
                        }

                        vertex_offset += mesh.VertexCount;
                    }
                }
                return;
            }
            else
            {
                cont.ExportFile(outScene, fileName, "collada", PostProcessSteps.ValidateDataStructure);
            }

            //if (SkinningEnvelopes.Weights.Count == 0)
            //    return; // There's no skinning information, so we can stop here

            // Now we need to add some skinning info, since AssImp doesn't do it for some bizarre reason

            StreamWriter test = new StreamWriter(fileName + ".tmp");
            StreamReader dae  = File.OpenText(fileName);

            Console.WriteLine();
            Console.Write("Finalizing the Mesh");
            while (!dae.EndOfStream)
            {
                string line = dae.ReadLine();

                if (line == "  <library_visual_scenes>")
                {
                    AddControllerLibrary(outScene, test);
                    test.WriteLine(line);
                    test.Flush();
                }
                else if (line.Contains("<node"))
                {
                    string[] testLn = line.Split('\"');
                    string   name   = testLn[3];

                    if (Joints.FlatSkeleton.Exists(x => x.Name == name))
                    {
                        string jointLine = line.Replace(">", $" sid=\"{ name }\" type=\"JOINT\">");
                        test.WriteLine(jointLine);
                        test.Flush();
                    }
                    else
                    {
                        test.WriteLine(line);
                        test.Flush();
                    }
                }
                else if (line.Contains("</visual_scene>"))
                {
                    foreach (Mesh mesh in outScene.Meshes)
                    {
                        string matname      = "mat";
                        bool   keepmatnames = false;
                        if (keepmatnames == true)
                        {
                            matname = AssimpMatnameSanitize(mesh.MaterialIndex, outScene.Materials[mesh.MaterialIndex].Name);
                        }
                        else
                        {
                            matname = AssimpMatnameSanitize(mesh.MaterialIndex, Materials.m_Materials[mesh.MaterialIndex].Name);
                        }

                        test.WriteLine($"      <node id=\"{ mesh.Name }\" name=\"{ mesh.Name }\" type=\"NODE\">");

                        test.WriteLine($"       <instance_controller url=\"#{ mesh.Name }-skin\">");
                        test.WriteLine("        <skeleton>#skeleton_root</skeleton>");
                        test.WriteLine("        <bind_material>");
                        test.WriteLine("         <technique_common>");
                        test.WriteLine($"          <instance_material symbol=\"m{matname}\" target=\"#{matname}\" />");
                        test.WriteLine("         </technique_common>");
                        test.WriteLine("        </bind_material>");
                        test.WriteLine("       </instance_controller>");

                        test.WriteLine("      </node>");
                        test.Flush();
                    }

                    test.WriteLine(line);
                    test.Flush();
                }
                else if (line.Contains("<matrix"))
                {
                    string matLine = line.Replace("<matrix>", "<matrix sid=\"matrix\">");
                    test.WriteLine(matLine);
                    test.Flush();
                }
                else
                {
                    test.WriteLine(line);
                    test.Flush();
                }
                Console.Write(".");
            }

            Console.Write("✓");
            Console.WriteLine();

            test.Close();
            dae.Close();

            File.Copy(fileName + ".tmp", fileName, true);
            File.Delete(fileName + ".tmp");
        }