예제 #1
0
        public void ExportData(string tagName, MyModelFractures modelFractures)
        {
            WriteTag(tagName);

            m_writer.Write(modelFractures.Version);

            m_writer.Write(modelFractures.Fractures != null ? modelFractures.Fractures.Length : 0);

            foreach (var modelFracture in modelFractures.Fractures)
            {
                if (modelFracture is RandomSplitFractureSettings)
                {
                    var settings = (RandomSplitFractureSettings)modelFracture;
                    m_writer.Write("RandomSplit");
                    m_writer.Write(settings.NumObjectsOnLevel1);
                    m_writer.Write(settings.NumObjectsOnLevel2);
                    m_writer.Write(settings.RandomRange);
                    m_writer.Write(settings.RandomSeed1);
                    m_writer.Write(settings.RandomSeed2);
                    m_writer.Write(settings.SplitPlane);
                }
                else
                    if (modelFracture is VoronoiFractureSettings)
                    {
                        var settings = (VoronoiFractureSettings)modelFracture;
                        m_writer.Write("Voronoi");
                        m_writer.Write(settings.Seed);
                        m_writer.Write(settings.NumSitesToGenerate);
                        m_writer.Write(settings.NumIterations);
                        m_writer.Write(settings.SplitPlane);
                    }
            }
        }
예제 #2
0
        static MyModelFractures ReadModelFractures(BinaryReader reader)
        {
            MyModelFractures modelFractures = new MyModelFractures();

            modelFractures.Version = reader.ReadInt32();

            var fracturesCount = reader.ReadInt32();

            for (int i = 0; i < fracturesCount; i++)
            {
                string fractureName = reader.ReadString();

                if (fractureName == "RandomSplit")
                {
                    var settings = new RandomSplitFractureSettings();

                    settings.NumObjectsOnLevel1 = reader.ReadInt32();
                    settings.NumObjectsOnLevel2 = reader.ReadInt32();
                    settings.RandomRange        = reader.ReadInt32();
                    settings.RandomSeed1        = reader.ReadInt32();
                    settings.RandomSeed2        = reader.ReadInt32();
                    settings.SplitPlane         = reader.ReadString();

                    modelFractures.Fractures = new MyFractureSettings[] { settings };
                }
                else if (fractureName == "Voronoi")
                {
                    var settings = new VoronoiFractureSettings();
                    settings.Seed = reader.ReadInt32();
                    settings.NumSitesToGenerate = reader.ReadInt32();
                    settings.NumIterations      = reader.ReadInt32();
                    settings.SplitPlane         = reader.ReadString();

                    modelFractures.Fractures = new MyFractureSettings[] { settings };
                }
            }

            return(modelFractures);
        }
예제 #3
0
        //  Sort of lazy-load, where constructor just saves information about what this model should be, but real load is done here - and only one time.
        //  This loads only vertex data, doesn't touch GPU
        //  Can be called from main and background thread
        public void LoadData()
        {
            if (m_loadedData)
            {
                return;
            }

            VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("MyModel::LoadData");


            MyLog.Default.WriteLine("MyModel.LoadData -> START", LoggingOptions.LOADING_MODELS);
            MyLog.Default.IncreaseIndent(LoggingOptions.LOADING_MODELS);

            MyLog.Default.WriteLine("m_assetName: " + m_assetName, LoggingOptions.LOADING_MODELS);

            //  Read data from model TAG parameter. There are stored vertex positions, triangle indices, vectors, ... everything we need.
            VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - import data");

            MyLog.Default.WriteLine(String.Format("Importing asset {0}, path: {1}", m_assetName, AssetName), LoggingOptions.LOADING_MODELS);


            string assetForImport = AssetName;
            var    fsPath         = Path.IsPathRooted(AssetName) ? AssetName : Path.Combine(MyFileSystem.ContentPath, AssetName);

            if (!MyFileSystem.FileExists(fsPath))
            {
                assetForImport = @"Models\Debug\Error.mwm";
            }

            try
            {
                m_importer.ImportData(assetForImport);
            }
            catch
            {
                MyLog.Default.WriteLine(String.Format("Importing asset failed {0}", m_assetName));
                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                throw;
            }
            VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

            DataVersion = m_importer.DataVersion;

            VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - load tag data");
            Dictionary <string, object> tagData = m_importer.GetTagData();

            if (tagData.Count == 0)
            {
                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                throw new Exception(String.Format("Uncompleted tagData for asset: {0}, path: {1}", m_assetName, AssetName));
            }
            VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

            VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - vertex, normals, texture coords");


            HalfVector4[] vertices = (HalfVector4[])tagData[MyImporterConstants.TAG_VERTICES];

            System.Diagnostics.Debug.Assert(vertices.Length > 0);

            Byte4[] normals = (Byte4[])tagData[MyImporterConstants.TAG_NORMALS];
            m_vertices = new MyCompressedVertexNormal[vertices.Length];
            if (normals.Length > 0)
            {
                for (int v = 0; v < vertices.Length; v++)
                {
                    m_vertices[v] = new MyCompressedVertexNormal()
                    {
                        Position = vertices[v], // VF_Packer.PackPosition(ref vertices[v]),
                        Normal   = normals[v]   //VF_Packer.PackNormalB4(ref normals[v])
                    };
                }
            }
            else
            {
                for (int v = 0; v < vertices.Length; v++)
                {
                    m_vertices[v] = new MyCompressedVertexNormal()
                    {
                        Position = vertices[v],// VF_Packer.PackPosition(ref vertices[v]),
                    };
                }
            }


            m_verticesCount = vertices.Length;

            VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

            VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - mesh");
            m_meshContainer.Clear();

            if (tagData.ContainsKey(MyImporterConstants.TAG_MESH_PARTS))
            {
                List <int> indices  = new List <int>(GetVerticesCount()); // Default capacity estimation
                int        maxIndex = 0;

                List <MyMeshPartInfo> meshParts = tagData[MyImporterConstants.TAG_MESH_PARTS] as List <MyMeshPartInfo>;
                foreach (MyMeshPartInfo meshPart in meshParts)
                {
                    MyMesh mesh = new MyMesh(meshPart, m_assetName);
                    mesh.IndexStart = indices.Count;
                    mesh.TriCount   = meshPart.m_indices.Count / 3;

                    if (m_loadUV && false == m_hasUV)
                    {
                        m_texCoords = (HalfVector2[])tagData[MyImporterConstants.TAG_TEXCOORDS0];
                        m_hasUV     = true;
                        m_loadUV    = false;
                    }

                    if (meshPart.m_MaterialDesc != null && meshPart.Technique == MyMeshDrawTechnique.GLASS)
                    {
                        GlassData = mesh;

                        HalfVector2[]      forLoadingTexCoords0 = (HalfVector2[])tagData[MyImporterConstants.TAG_TEXCOORDS0];
                        List <HalfVector2> neededTexCoords      = new List <HalfVector2>();

                        for (int t = 0; t < meshPart.m_indices.Count; t++)
                        {
                            int index = meshPart.m_indices[t];
                            neededTexCoords.Add(forLoadingTexCoords0[index]);
                        }

                        GlassTexCoords = neededTexCoords.ToArray();
                    }

                    System.Diagnostics.Debug.Assert(mesh.TriCount > 0);

                    if (mesh.TriCount == 0)
                    {
                        VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                        VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                        return;
                    }

                    foreach (var i in meshPart.m_indices)
                    {
                        indices.Add(i);
                        if (i > maxIndex)
                        {
                            maxIndex = i;
                        }
                    }



                    m_meshContainer.Add(mesh);
                }

                if (maxIndex <= ushort.MaxValue)
                {
                    // create 16 bit indices
                    m_Indices_16bit = new ushort[indices.Count];
                    for (int i = 0; i < indices.Count; i++)
                    {
                        m_Indices_16bit[i] = (ushort)indices[i];
                    }
                }
                else
                {
                    // use 32bit indices
                    m_Indices = indices.ToArray();
                }
            }

            if (tagData.ContainsKey(MyImporterConstants.TAG_MODEL_BVH))
            {
                m_bvh = new MyQuantizedBvhAdapter(tagData[MyImporterConstants.TAG_MODEL_BVH] as GImpactQuantizedBvh, this);
            }

            VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

            VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - other data");

            Animations = (ModelAnimations)tagData[MyImporterConstants.TAG_ANIMATIONS];
            Bones      = (MyModelBone[])tagData[MyImporterConstants.TAG_BONES];

            BoundingBox         = (BoundingBox)tagData[MyImporterConstants.TAG_BOUNDING_BOX];
            BoundingSphere      = (BoundingSphere)tagData[MyImporterConstants.TAG_BOUNDING_SPHERE];
            BoundingBoxSize     = BoundingBox.Max - BoundingBox.Min;
            BoundingBoxSizeHalf = BoundingBoxSize / 2.0f;
            Dummies             = tagData[MyImporterConstants.TAG_DUMMIES] as Dictionary <string, MyModelDummy>;
            BoneMapping         = tagData[MyImporterConstants.TAG_BONE_MAPPING] as VRageMath.Vector3I[];

            if (tagData.ContainsKey(MyImporterConstants.TAG_MODEL_FRACTURES))
            {
                ModelFractures = (MyModelFractures)tagData[MyImporterConstants.TAG_MODEL_FRACTURES];
            }

            object patternScale;

            if (tagData.TryGetValue(MyImporterConstants.TAG_PATTERN_SCALE, out patternScale))
            {
                PatternScale = (float)patternScale;
            }

            if (BoneMapping.Length == 0)
            {
                BoneMapping = null;
            }

            if (tagData.ContainsKey(MyImporterConstants.TAG_HAVOK_COLLISION_GEOMETRY))
            {
                HavokData = (byte[])tagData[MyImporterConstants.TAG_HAVOK_COLLISION_GEOMETRY];
                byte[] tagCollisionData = (byte[])tagData[MyImporterConstants.TAG_HAVOK_COLLISION_GEOMETRY];
                if (tagCollisionData.Length > 0 && HkBaseSystem.IsThreadInitialized)
                {
                    bool           containsSceneData;
                    bool           containsDestructionData;
                    List <HkShape> shapesList = new List <HkShape>();
                    if (!HkShapeLoader.LoadShapesListFromBuffer(tagCollisionData, shapesList, out containsSceneData, out containsDestructionData))
                    {
                        MyLog.Default.WriteLine(string.Format("Model {0} - Unable to load collision geometry", AssetName), LoggingOptions.LOADING_MODELS);
                        Debug.Fail("Collision model was exported in wrong way: " + m_assetName);
                    }

                    if (shapesList.Count > 10)
                    {
                        MyLog.Default.WriteLine(string.Format("Model {0} - Found too many collision shapes, only the first 10 will be used", AssetName), LoggingOptions.LOADING_MODELS);
                    }

                    if (HavokCollisionShapes != null)
                    {
                        Debug.Fail("Shapes already loaded");
                    }
                    if (shapesList.Count > 0)
                    {
                        HavokCollisionShapes = shapesList.ToArray();
                    }
                    else
                    {
                        MyLog.Default.WriteLine(string.Format("Model {0} - Unable to load collision geometry from file, default collision will be used !", AssetName));
                    }

                    if (containsDestructionData)
                    {
                        HavokDestructionData = tagCollisionData;
                    }

                    ExportedWrong = !containsSceneData;
                }
            }


            if (tagData.ContainsKey(MyImporterConstants.TAG_HAVOK_DESTRUCTION))
            {
                if (((byte[])tagData[MyImporterConstants.TAG_HAVOK_DESTRUCTION]).Length > 0)
                {
                    HavokDestructionData = (byte[])tagData[MyImporterConstants.TAG_HAVOK_DESTRUCTION];
                }
            }

            VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

            VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - copy triangle indices");
            //  Prepare data
            CopyTriangleIndices();
            m_trianglesCount = Triangles.Count();

            //  Remember this numbers as list may be cleared at the end of this method
            VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

            MyLog.Default.WriteLine("Triangles.Length: " + Triangles.Length, LoggingOptions.LOADING_MODELS);
            MyLog.Default.WriteLine("Vertexes.Length: " + GetVerticesCount(), LoggingOptions.LOADING_MODELS);
            MyLog.Default.WriteLine("Centered: " + (bool)tagData[MyImporterConstants.TAG_CENTERED], LoggingOptions.LOADING_MODELS);
            MyLog.Default.WriteLine("UseChannelTextures: " + (bool)tagData[MyImporterConstants.TAG_USE_CHANNEL_TEXTURES], LoggingOptions.LOADING_MODELS);
            MyLog.Default.WriteLine("Length in meters: " + (float)tagData[MyImporterConstants.TAG_LENGTH_IN_METERS], LoggingOptions.LOADING_MODELS);
            MyLog.Default.WriteLine("Rescale to length in meters?: " + (bool)tagData[MyImporterConstants.TAG_RESCALE_TO_LENGTH_IN_METERS], LoggingOptions.LOADING_MODELS);
            MyLog.Default.WriteLine("BoundingBox: " + BoundingBox, LoggingOptions.LOADING_MODELS);
            MyLog.Default.WriteLine("BoundingSphere: " + BoundingSphere, LoggingOptions.LOADING_MODELS);

            Stats.PerAppLifetime.MyModelsCount++;
            Stats.PerAppLifetime.MyModelsMeshesCount    += m_meshContainer.Count;
            Stats.PerAppLifetime.MyModelsVertexesCount  += GetVerticesCount();
            Stats.PerAppLifetime.MyModelsTrianglesCount += Triangles.Length;

            ModelInfo = new MyModelInfo(GetTrianglesCount(), GetVerticesCount(), BoundingBoxSize);

            m_loadedData            = true;
            m_loadingErrorProcessed = false;
            MyLog.Default.DecreaseIndent(LoggingOptions.LOADING_MODELS);
            MyLog.Default.WriteLine("MyModel.LoadData -> END", LoggingOptions.LOADING_MODELS);

            VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
        }
        void FractureBreakableShape(HkdBreakableShape bShape, MyModelFractures modelFractures, string modPath)
        {
            HkdFracture       fracture = null;
            HkReferenceObject geometry = null;

            if (modelFractures.Fractures[0] is RandomSplitFractureSettings)
            {
                var settings = (RandomSplitFractureSettings)modelFractures.Fractures[0];
                fracture = new HkdRandomSplitFracture()
                {
                    NumObjectsOnLevel1 = settings.NumObjectsOnLevel1,
                    NumObjectsOnLevel2 = settings.NumObjectsOnLevel2,
                    RandomRange        = settings.RandomRange,
                    RandomSeed1        = settings.RandomSeed1,
                    RandomSeed2        = settings.RandomSeed2,
                    SplitGeometryScale = Vector4.One
                };

                if (!string.IsNullOrEmpty(settings.SplitPlane))
                {
                    var splitPlane = settings.SplitPlane;
                    if (!string.IsNullOrEmpty(modPath))
                    {
                        splitPlane = Path.Combine(modPath, settings.SplitPlane);
                    }

                    geometry = CreateGeometryFromSplitPlane(splitPlane);
                    if (geometry != null)
                    {
                        ((HkdRandomSplitFracture)fracture).SetGeometry(geometry);
                        VRageRender.MyRenderProxy.PreloadMaterials(splitPlane);
                    }
                }
            }
            if (modelFractures.Fractures[0] is VoronoiFractureSettings)
            {
                var settings = (VoronoiFractureSettings)modelFractures.Fractures[0];
                fracture = new HkdVoronoiFracture()
                {
                    Seed = settings.Seed,
                    NumSitesToGenerate = settings.NumSitesToGenerate,
                    NumIterations      = settings.NumIterations
                };

                if (!string.IsNullOrEmpty(settings.SplitPlane))
                {
                    var splitPlane = settings.SplitPlane;
                    if (!string.IsNullOrEmpty(modPath))
                    {
                        splitPlane = Path.Combine(modPath, settings.SplitPlane);
                    }

                    geometry = CreateGeometryFromSplitPlane(splitPlane);

                    var pspm = MyModels.GetModel(splitPlane);

                    if (geometry != null)
                    {
                        ((HkdVoronoiFracture)fracture).SetGeometry(geometry);
                        VRageRender.MyRenderProxy.PreloadMaterials(splitPlane);
                    }
                }
            }
            //if (woodButton.IsChecked)
            //{
            //    fracture = new HkdWoodFracture()
            //    {
            //        RandomSeed = 123456,
            //        BoardSplittingData = new HkdWoodFracture.SplittingData()
            //        {
            //        },
            //        SplinterSplittingData = new HkdWoodFracture.SplittingData()
            //        {
            //        }
            //    };
            //}

            if (fracture != null)
            {
                Storage.FractureShape(bShape, fracture);
                fracture.Dispose();
            }

            if (geometry != null)
            {
                geometry.Dispose();
            }
        }
예제 #5
0
        public void ExportData(string tagName, MyModelFractures modelFractures)
        {
            WriteTag(tagName);

            m_writer.Write(modelFractures.Version);

            m_writer.Write(modelFractures.Fractures != null ? modelFractures.Fractures.Length : 0);

            foreach (var modelFracture in modelFractures.Fractures)
            {
                if (modelFracture is RandomSplitFractureSettings)
                {
                    var settings = (RandomSplitFractureSettings)modelFracture;
                    m_writer.Write("RandomSplit");
                    m_writer.Write(settings.NumObjectsOnLevel1);
                    m_writer.Write(settings.NumObjectsOnLevel2);
                    m_writer.Write(settings.RandomRange);
                    m_writer.Write(settings.RandomSeed1);
                    m_writer.Write(settings.RandomSeed2);
                    m_writer.Write(settings.SplitPlane);
                }
                else
                    if (modelFracture is VoronoiFractureSettings)
                    {
                        var settings = (VoronoiFractureSettings)modelFracture;
                        m_writer.Write("Voronoi");
                        m_writer.Write(settings.Seed);
                        m_writer.Write(settings.NumSitesToGenerate);
                        m_writer.Write(settings.NumIterations);
                        m_writer.Write(settings.SplitPlane);
                    }
                    else
                        if (modelFracture is WoodFractureSettings)
                        {                            
                            var settings = (WoodFractureSettings)modelFracture;
                            m_writer.Write("WoodFracture");                            
                            m_writer.Write(settings.BoardCustomSplittingPlaneAxis);
                            m_writer.Write(settings.BoardFractureLineShearingRange);
                            m_writer.Write(settings.BoardFractureNormalShearingRange);
                            m_writer.Write(settings.BoardNumSubparts);
                            m_writer.Write((int)settings.BoardRotateSplitGeom);
                            WriteVector(settings.BoardScale);
                            WriteVector(settings.BoardScaleRange);
                            m_writer.Write(settings.BoardSplitGeomShiftRangeY);
                            m_writer.Write(settings.BoardSplitGeomShiftRangeZ);
                            WriteVector(settings.BoardSplittingAxis);
                            m_writer.Write(settings.BoardSplittingPlane);
                            m_writer.Write(settings.BoardSurfaceNormalShearingRange);
                            m_writer.Write(settings.BoardWidthRange);
                            m_writer.Write(settings.SplinterCustomSplittingPlaneAxis);
                            m_writer.Write(settings.SplinterFractureLineShearingRange);
                            m_writer.Write(settings.SplinterFractureNormalShearingRange);
                            m_writer.Write(settings.SplinterNumSubparts);
                            m_writer.Write((int)settings.SplinterRotateSplitGeom);
                            WriteVector(settings.SplinterScale);
                            WriteVector(settings.SplinterScaleRange);
                            m_writer.Write(settings.SplinterSplitGeomShiftRangeY);
                            m_writer.Write(settings.SplinterSplitGeomShiftRangeZ);
                            WriteVector(settings.SplinterSplittingAxis);
                            m_writer.Write(settings.SplinterSplittingPlane);
                            m_writer.Write(settings.SplinterSurfaceNormalShearingRange);
                            m_writer.Write(settings.SplinterWidthRange);
                        }
            }
        }
예제 #6
0
        static MyModelFractures ReadModelFractures(BinaryReader reader)
        {
            MyModelFractures modelFractures = new MyModelFractures();

            modelFractures.Version = reader.ReadInt32();

            var fracturesCount = reader.ReadInt32();

            for (int i = 0; i < fracturesCount; i++)
            {
                string fractureName = reader.ReadString();

                if (fractureName == "RandomSplit")
                {
                    var settings = new RandomSplitFractureSettings();

                    settings.NumObjectsOnLevel1 = reader.ReadInt32();
                    settings.NumObjectsOnLevel2 = reader.ReadInt32();
                    settings.RandomRange        = reader.ReadInt32();
                    settings.RandomSeed1        = reader.ReadInt32();
                    settings.RandomSeed2        = reader.ReadInt32();
                    settings.SplitPlane         = reader.ReadString();

                    modelFractures.Fractures = new MyFractureSettings[] { settings };
                }
                else if (fractureName == "Voronoi")
                {
                    var settings = new VoronoiFractureSettings();
                    settings.Seed = reader.ReadInt32();
                    settings.NumSitesToGenerate = reader.ReadInt32();
                    settings.NumIterations      = reader.ReadInt32();
                    settings.SplitPlane         = reader.ReadString();

                    modelFractures.Fractures = new MyFractureSettings[] { settings };
                }
                else if (fractureName == "WoodFracture")
                {
                    var settings = new WoodFractureSettings();
                    settings.BoardCustomSplittingPlaneAxis    = reader.ReadBoolean();
                    settings.BoardFractureLineShearingRange   = reader.ReadSingle();
                    settings.BoardFractureNormalShearingRange = reader.ReadSingle();
                    settings.BoardNumSubparts                    = reader.ReadInt32();
                    settings.BoardRotateSplitGeom                = (WoodFractureSettings.Rotation)reader.ReadInt32();
                    settings.BoardScale                          = ReadVector3(reader);
                    settings.BoardScaleRange                     = ReadVector3(reader);
                    settings.BoardSplitGeomShiftRangeY           = reader.ReadSingle();
                    settings.BoardSplitGeomShiftRangeZ           = reader.ReadSingle();
                    settings.BoardSplittingAxis                  = ReadVector3(reader);
                    settings.BoardSplittingPlane                 = reader.ReadString();
                    settings.BoardSurfaceNormalShearingRange     = reader.ReadSingle();
                    settings.BoardWidthRange                     = reader.ReadSingle();
                    settings.SplinterCustomSplittingPlaneAxis    = reader.ReadBoolean();
                    settings.SplinterFractureLineShearingRange   = reader.ReadSingle();
                    settings.SplinterFractureNormalShearingRange = reader.ReadSingle();
                    settings.SplinterNumSubparts                 = reader.ReadInt32();
                    settings.SplinterRotateSplitGeom             = (WoodFractureSettings.Rotation)reader.ReadInt32();
                    settings.SplinterScale                       = ReadVector3(reader);
                    settings.SplinterScaleRange                  = ReadVector3(reader);
                    settings.SplinterSplitGeomShiftRangeY        = reader.ReadSingle();
                    settings.SplinterSplitGeomShiftRangeZ        = reader.ReadSingle();
                    settings.SplinterSplittingAxis               = ReadVector3(reader);
                    settings.SplinterSplittingPlane              = reader.ReadString();
                    settings.SplinterSurfaceNormalShearingRange  = reader.ReadSingle();
                    settings.SplinterWidthRange                  = reader.ReadSingle();

                    modelFractures.Fractures = new MyFractureSettings[] { settings };
                }
            }

            return(modelFractures);
        }
예제 #7
0
        //  Sort of lazy-load, where constructor just saves information about what this model should be, but real load is done here - and only one time.
        //  This loads only vertex data, doesn't touch GPU
        //  Can be called from main and background thread
        public void LoadData()
        {
            if (m_loadedData) return;

            lock (this)
            {
                VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("MyModel::LoadData");


                MyLog.Default.WriteLine("MyModel.LoadData -> START", LoggingOptions.LOADING_MODELS);
                MyLog.Default.IncreaseIndent(LoggingOptions.LOADING_MODELS);

                MyLog.Default.WriteLine("m_assetName: " + m_assetName, LoggingOptions.LOADING_MODELS);

                //  Read data from model TAG parameter. There are stored vertex positions, triangle indices, vectors, ... everything we need.
                VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - import data");

                MyLog.Default.WriteLine(String.Format("Importing asset {0}, path: {1}", m_assetName, AssetName), LoggingOptions.LOADING_MODELS);


                string assetForImport = AssetName;
                var fsPath = Path.IsPathRooted(AssetName) ? AssetName : Path.Combine(MyFileSystem.ContentPath, AssetName);
                if (!MyFileSystem.FileExists(fsPath))
                {
                    assetForImport = @"Models\Debug\Error.mwm";
                }

                try
                {
                    m_importer.ImportData(assetForImport);
                }
                catch
                {
                    MyLog.Default.WriteLine(String.Format("Importing asset failed {0}", m_assetName));
                    VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                    VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                    throw;
                }
                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

                DataVersion = m_importer.DataVersion;

                VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - load tag data");
                Dictionary<string, object> tagData = m_importer.GetTagData();
                if (tagData.Count == 0)
                {
                    VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                    VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                    throw new Exception(String.Format("Uncompleted tagData for asset: {0}, path: {1}", m_assetName, AssetName));
                }
                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

                VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - vertex, normals, texture coords");


                HalfVector4[] vertices = (HalfVector4[])tagData[MyImporterConstants.TAG_VERTICES];

                System.Diagnostics.Debug.Assert(vertices.Length > 0);

                Byte4[] normals = (Byte4[])tagData[MyImporterConstants.TAG_NORMALS];
                m_vertices = new MyCompressedVertexNormal[vertices.Length];
                if (normals.Length > 0)
                {
                    for (int v = 0; v < vertices.Length; v++)
                    {
                        m_vertices[v] = new MyCompressedVertexNormal()
                        {
                            Position = vertices[v],// VF_Packer.PackPosition(ref vertices[v]),
                            Normal = normals[v]//VF_Packer.PackNormalB4(ref normals[v])
                        };
                    }
                }
                else
                {
                    for (int v = 0; v < vertices.Length; v++)
                    {
                        m_vertices[v] = new MyCompressedVertexNormal()
                        {
                            Position = vertices[v],// VF_Packer.PackPosition(ref vertices[v]),
                        };
                    }
                }


                m_verticesCount = vertices.Length;

                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

                VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - mesh");

                var materials = new Dictionary<string, MyMeshMaterial>();
                m_meshContainer.Clear();
                if (tagData.ContainsKey(MyImporterConstants.TAG_MESH_PARTS))
                {
                    List<int> indices = new List<int>(GetVerticesCount()); // Default capacity estimation
                    int maxIndex = 0;

                    List<MyMeshPartInfo> meshParts = tagData[MyImporterConstants.TAG_MESH_PARTS] as List<MyMeshPartInfo>;
                    foreach (MyMeshPartInfo meshPart in meshParts)
                    {
                        MyMesh mesh = new MyMesh(meshPart, m_assetName);
                        mesh.IndexStart = indices.Count;
                        mesh.TriCount = meshPart.m_indices.Count / 3;

                        if (mesh.Material.Name != null)
                            materials.Add(mesh.Material.Name, mesh.Material);

                        if (m_loadUV && false == m_hasUV)
                        {
                            m_texCoords = (HalfVector2[])tagData[MyImporterConstants.TAG_TEXCOORDS0];
                            m_hasUV = true;
                            m_loadUV = false;
                        }

                        if (meshPart.m_MaterialDesc != null && meshPart.Technique == MyMeshDrawTechnique.GLASS)
                        {
                            GlassData = mesh;

                            HalfVector2[] forLoadingTexCoords0 = (HalfVector2[])tagData[MyImporterConstants.TAG_TEXCOORDS0];
                            List<HalfVector2> neededTexCoords = new List<HalfVector2>();

                            for (int t = 0; t < meshPart.m_indices.Count; t++)
                            {
                                int index = meshPart.m_indices[t];
                                neededTexCoords.Add(forLoadingTexCoords0[index]);
                            }

                            GlassTexCoords = neededTexCoords.ToArray();
                        }

                        System.Diagnostics.Debug.Assert(mesh.TriCount > 0);

                        if (mesh.TriCount == 0)
                        {
                            VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                            VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
                            return;
                        }

                        foreach (var i in meshPart.m_indices)
                        {
                            indices.Add(i);
                            if (i > maxIndex)
                            {
                                maxIndex = i;
                            }
                        }



                        m_meshContainer.Add(mesh);
                    }

                    if (maxIndex <= ushort.MaxValue)
                    {
                        // create 16 bit indices
                        m_Indices_16bit = new ushort[indices.Count];
                        for (int i = 0; i < indices.Count; i++)
                        {
                            m_Indices_16bit[i] = (ushort)indices[i];
                        }
                    }
                    else
                    {
                        // use 32bit indices
                        m_Indices = indices.ToArray();
                    }
                }

                m_meshSections.Clear();
                if (tagData.ContainsKey(MyImporterConstants.TAG_MESH_SECTIONS))
                {
                    List<MyMeshSectionInfo> sections = tagData[MyImporterConstants.TAG_MESH_SECTIONS] as List<MyMeshSectionInfo>;
                    int sectionindex = 0;
                    foreach (MyMeshSectionInfo sectinfo in sections)
                    {
                        MyMeshSection section = new MyMeshSection() { Name = sectinfo.Name, Index = sectionindex };
                        m_meshSections.Add(section.Name, section);
                        sectionindex++;
                    }
                }

                if (tagData.ContainsKey(MyImporterConstants.TAG_MODEL_BVH))
                {
                    m_bvh = new MyQuantizedBvhAdapter(tagData[MyImporterConstants.TAG_MODEL_BVH] as GImpactQuantizedBvh, this);
                }

                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

                VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - other data");

                Animations = (ModelAnimations)tagData[MyImporterConstants.TAG_ANIMATIONS];
                Bones = (MyModelBone[])tagData[MyImporterConstants.TAG_BONES];

                BoundingBox = (BoundingBox)tagData[MyImporterConstants.TAG_BOUNDING_BOX];
                BoundingSphere = (BoundingSphere)tagData[MyImporterConstants.TAG_BOUNDING_SPHERE];
                BoundingBoxSize = BoundingBox.Max - BoundingBox.Min;
                BoundingBoxSizeHalf = BoundingBoxSize / 2.0f;
                Dummies = tagData[MyImporterConstants.TAG_DUMMIES] as Dictionary<string, MyModelDummy>;
                BoneMapping = tagData[MyImporterConstants.TAG_BONE_MAPPING] as VRageMath.Vector3I[];

                if (tagData.ContainsKey(MyImporterConstants.TAG_MODEL_FRACTURES))
                    ModelFractures = (MyModelFractures)tagData[MyImporterConstants.TAG_MODEL_FRACTURES];

                object patternScale;
                if (tagData.TryGetValue(MyImporterConstants.TAG_PATTERN_SCALE, out patternScale))
                {
                    PatternScale = (float)patternScale;
                }

                if (BoneMapping.Length == 0)
                    BoneMapping = null;

                if (tagData.ContainsKey(MyImporterConstants.TAG_HAVOK_COLLISION_GEOMETRY))
                {
                    HavokData = (byte[])tagData[MyImporterConstants.TAG_HAVOK_COLLISION_GEOMETRY];
                    byte[] tagCollisionData = (byte[])tagData[MyImporterConstants.TAG_HAVOK_COLLISION_GEOMETRY];
                    if (tagCollisionData.Length > 0 && HkBaseSystem.IsThreadInitialized)
                    {
                        bool containsSceneData;
                        bool containsDestructionData;
                        List<HkShape> shapesList = new List<HkShape>();
                        if (!HkShapeLoader.LoadShapesListFromBuffer(tagCollisionData, shapesList, out containsSceneData, out containsDestructionData))
                        {
                            MyLog.Default.WriteLine(string.Format("Model {0} - Unable to load collision geometry", AssetName), LoggingOptions.LOADING_MODELS);
                        //Debug.Fail("Collision model was exported in wrong way: " + m_assetName);
                        }

                        if (shapesList.Count > 10)
                            MyLog.Default.WriteLine(string.Format("Model {0} - Found too many collision shapes, only the first 10 will be used", AssetName), LoggingOptions.LOADING_MODELS);

                        if (HavokCollisionShapes != null)
                        {
                            Debug.Fail("Shapes already loaded");
                        }
                        if (shapesList.Count > 0)
                        {
                            HavokCollisionShapes = shapesList.ToArray();
                        }
                        else
                        {
                            MyLog.Default.WriteLine(string.Format("Model {0} - Unable to load collision geometry from file, default collision will be used !", AssetName));
                        }

                        if (containsDestructionData)
                            HavokDestructionData = tagCollisionData;

                        ExportedWrong = !containsSceneData;
                    }
                }


                if (tagData.ContainsKey(MyImporterConstants.TAG_HAVOK_DESTRUCTION))
                {
                    if (((byte[])tagData[MyImporterConstants.TAG_HAVOK_DESTRUCTION]).Length > 0)
                        HavokDestructionData = (byte[])tagData[MyImporterConstants.TAG_HAVOK_DESTRUCTION];
                }

                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

                VRageRender.MyRenderProxy.GetRenderProfiler().StartProfilingBlock("Model - load data - copy triangle indices");
                //  Prepare data
                CopyTriangleIndices();
                m_trianglesCount = Triangles.Length;

                //  Remember this numbers as list may be cleared at the end of this method
                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();

                MyLog.Default.WriteLine("Triangles.Length: " + Triangles.Length, LoggingOptions.LOADING_MODELS);
                MyLog.Default.WriteLine("Vertexes.Length: " + GetVerticesCount(), LoggingOptions.LOADING_MODELS);
                MyLog.Default.WriteLine("Centered: " + (bool)tagData[MyImporterConstants.TAG_CENTERED], LoggingOptions.LOADING_MODELS);
                MyLog.Default.WriteLine("UseChannelTextures: " + (bool)tagData[MyImporterConstants.TAG_USE_CHANNEL_TEXTURES], LoggingOptions.LOADING_MODELS);
                MyLog.Default.WriteLine("Length in meters: " + (float)tagData[MyImporterConstants.TAG_LENGTH_IN_METERS], LoggingOptions.LOADING_MODELS);
                MyLog.Default.WriteLine("Rescale to length in meters?: " + (bool)tagData[MyImporterConstants.TAG_RESCALE_TO_LENGTH_IN_METERS], LoggingOptions.LOADING_MODELS);
                MyLog.Default.WriteLine("BoundingBox: " + BoundingBox, LoggingOptions.LOADING_MODELS);
                MyLog.Default.WriteLine("BoundingSphere: " + BoundingSphere, LoggingOptions.LOADING_MODELS);

                VRage.Utils.Stats.PerAppLifetime.MyModelsCount++;
                VRage.Utils.Stats.PerAppLifetime.MyModelsMeshesCount += m_meshContainer.Count;
                VRage.Utils.Stats.PerAppLifetime.MyModelsVertexesCount += GetVerticesCount();
                VRage.Utils.Stats.PerAppLifetime.MyModelsTrianglesCount += Triangles.Length;

                ModelInfo = new MyModelInfo(GetTrianglesCount(), GetVerticesCount(), BoundingBoxSize);

                m_loadedData = true;
                m_loadingErrorProcessed = false;
                MyLog.Default.DecreaseIndent(LoggingOptions.LOADING_MODELS);
                MyLog.Default.WriteLine("MyModel.LoadData -> END", LoggingOptions.LOADING_MODELS);

                VRageRender.MyRenderProxy.GetRenderProfiler().EndProfilingBlock();
            }
        }
예제 #8
0
        public void ExportData(string tagName, MyModelFractures modelFractures)
        {
            WriteTag(tagName);

            m_writer.Write(modelFractures.Version);

            m_writer.Write(modelFractures.Fractures != null ? modelFractures.Fractures.Length : 0);

            foreach (var modelFracture in modelFractures.Fractures)
            {
                if (modelFracture is RandomSplitFractureSettings)
                {
                    var settings = (RandomSplitFractureSettings)modelFracture;
                    m_writer.Write("RandomSplit");
                    m_writer.Write(settings.NumObjectsOnLevel1);
                    m_writer.Write(settings.NumObjectsOnLevel2);
                    m_writer.Write(settings.RandomRange);
                    m_writer.Write(settings.RandomSeed1);
                    m_writer.Write(settings.RandomSeed2);
                    m_writer.Write(settings.SplitPlane);
                }
                else
                if (modelFracture is VoronoiFractureSettings)
                {
                    var settings = (VoronoiFractureSettings)modelFracture;
                    m_writer.Write("Voronoi");
                    m_writer.Write(settings.Seed);
                    m_writer.Write(settings.NumSitesToGenerate);
                    m_writer.Write(settings.NumIterations);
                    m_writer.Write(settings.SplitPlane);
                }
                else
                if (modelFracture is WoodFractureSettings)
                {
                    var settings = (WoodFractureSettings)modelFracture;
                    m_writer.Write("WoodFracture");
                    m_writer.Write(settings.BoardCustomSplittingPlaneAxis);
                    m_writer.Write(settings.BoardFractureLineShearingRange);
                    m_writer.Write(settings.BoardFractureNormalShearingRange);
                    m_writer.Write(settings.BoardNumSubparts);
                    m_writer.Write((int)settings.BoardRotateSplitGeom);
                    WriteVector(settings.BoardScale);
                    WriteVector(settings.BoardScaleRange);
                    m_writer.Write(settings.BoardSplitGeomShiftRangeY);
                    m_writer.Write(settings.BoardSplitGeomShiftRangeZ);
                    WriteVector(settings.BoardSplittingAxis);
                    m_writer.Write(settings.BoardSplittingPlane);
                    m_writer.Write(settings.BoardSurfaceNormalShearingRange);
                    m_writer.Write(settings.BoardWidthRange);
                    m_writer.Write(settings.SplinterCustomSplittingPlaneAxis);
                    m_writer.Write(settings.SplinterFractureLineShearingRange);
                    m_writer.Write(settings.SplinterFractureNormalShearingRange);
                    m_writer.Write(settings.SplinterNumSubparts);
                    m_writer.Write((int)settings.SplinterRotateSplitGeom);
                    WriteVector(settings.SplinterScale);
                    WriteVector(settings.SplinterScaleRange);
                    m_writer.Write(settings.SplinterSplitGeomShiftRangeY);
                    m_writer.Write(settings.SplinterSplitGeomShiftRangeZ);
                    WriteVector(settings.SplinterSplittingAxis);
                    m_writer.Write(settings.SplinterSplittingPlane);
                    m_writer.Write(settings.SplinterSurfaceNormalShearingRange);
                    m_writer.Write(settings.SplinterWidthRange);
                }
            }
        }
예제 #9
0
        void FractureBreakableShape(HkdBreakableShape bShape, MyModelFractures modelFractures, string modPath)
        {
            HkdFracture fracture = null;
            HkReferenceObject geometry = null;

            if (modelFractures.Fractures[0] is RandomSplitFractureSettings)
            {
                var settings = (RandomSplitFractureSettings)modelFractures.Fractures[0];
                fracture = new HkdRandomSplitFracture()
                {
                    NumObjectsOnLevel1 = settings.NumObjectsOnLevel1,
                    NumObjectsOnLevel2 = settings.NumObjectsOnLevel2,
                    RandomRange = settings.RandomRange,
                    RandomSeed1 = settings.RandomSeed1,
                    RandomSeed2 = settings.RandomSeed2,
                    SplitGeometryScale = Vector4.One
                };

                if (!string.IsNullOrEmpty(settings.SplitPlane))
                {
                    var splitPlane = settings.SplitPlane;
                    if (!string.IsNullOrEmpty(modPath))
                        splitPlane = Path.Combine(modPath, settings.SplitPlane);

                    geometry = CreateGeometryFromSplitPlane(splitPlane);
                    if (geometry != null)
                    {
                        ((HkdRandomSplitFracture)fracture).SetGeometry(geometry);
                        VRageRender.MyRenderProxy.PreloadMaterials(splitPlane);
                    }
                }
            }
            if (modelFractures.Fractures[0] is VoronoiFractureSettings)
            {
                var settings = (VoronoiFractureSettings)modelFractures.Fractures[0];
                fracture = new HkdVoronoiFracture()
                {
                    Seed = settings.Seed,
                    NumSitesToGenerate = settings.NumSitesToGenerate,
                    NumIterations = settings.NumIterations
                };

                if (!string.IsNullOrEmpty(settings.SplitPlane))
                {
                    var splitPlane = settings.SplitPlane;
                    if (!string.IsNullOrEmpty(modPath))
                        splitPlane = Path.Combine(modPath, settings.SplitPlane);

                    geometry = CreateGeometryFromSplitPlane(splitPlane);

                    var pspm = VRage.Game.Models.MyModels.GetModel(splitPlane);

                    if (geometry != null)
                    {
                        ((HkdVoronoiFracture)fracture).SetGeometry(geometry);
                        VRageRender.MyRenderProxy.PreloadMaterials(splitPlane);
                    }
                }

            }
            if (modelFractures.Fractures[0] is WoodFractureSettings)
            {
                //TODO: Apply wood fracture algorithm
                var settings = (WoodFractureSettings)modelFractures.Fractures[0];
                fracture = new HkdWoodFracture()
                {
                    //Seed = settings.Seed,
                    //NumSitesToGenerate = settings.NumSitesToGenerate,
                    //NumIterations = settings.NumIterations
                };

                //if (!string.IsNullOrEmpty(settings.SplitPlane))
                //{
                //    var splitPlane = settings.SplitPlane;
                //    if (!string.IsNullOrEmpty(modPath))
                //        splitPlane = Path.Combine(modPath, settings.SplitPlane);

                //    geometry = CreateGeometryFromSplitPlane(splitPlane);

                //    var pspm = VRage.Game.Models.MyModels.GetModel(splitPlane);

                //    if (geometry != null)
                //    {
                //        ((HkdWoodFracture)fracture).SetGeometry(geometry);
                //        VRageRender.MyRenderProxy.PreloadMaterials(splitPlane);
                //    }
                //}
            }
           
            //if (woodButton.IsChecked)
            //{
            //    fracture = new HkdWoodFracture()
            //    {
            //        RandomSeed = 123456,
            //        BoardSplittingData = new HkdWoodFracture.SplittingData()
            //        {
            //        },
            //        SplinterSplittingData = new HkdWoodFracture.SplittingData()
            //        {
            //        }
            //    };
            //}

            if (fracture != null)
            {
                Storage.FractureShape(bShape, fracture);
                fracture.Dispose();
            }

            if (geometry != null)
                geometry.Dispose();
        }