// the method is static, because of removal all of the references on the member variables static unsafe IIndexBuffer CreateSimpleIB(MyMwmData mwmData) { string name = "IB-" + mwmData.MwmFilepath; List <MyMeshPartInfo> partInfos = mwmData.PartInfos; List <int> indicesInt = new List <int>(); int maxValue = Int32.MinValue; foreach (var partInfo in partInfos) { foreach (var index in partInfo.m_indices) { indicesInt.Add(index); maxValue = Math.Max(index, maxValue); } } if (maxValue < ushort.MaxValue) { List <ushort> indicesUShort = new List <ushort>(indicesInt.Count); for (int i = 0; i < indicesInt.Count; i++) indicesUShort.Add((ushort)(uint)indicesInt[i]); fixed(void *ptr = indicesUShort.ToArray()) { return(MyManagers.Buffers.CreateIndexBuffer(name, indicesInt.Count, new IntPtr(ptr), MyIndexBufferFormat.UShort, ResourceUsage.Immutable)); } } else fixed(void *ptr = indicesInt.ToArray()) { return(MyManagers.Buffers.CreateIndexBuffer(name, indicesInt.Count, new IntPtr(ptr), MyIndexBufferFormat.UInt, ResourceUsage.Immutable)); } }
public bool GetOrCreateModels(string filepath, out MyModels models) { filepath = MyMwmUtils.GetFullMwmFilepath(filepath); if (m_models.TryGetValue(filepath, out models)) { return(true); } // Load mwm as first lod MyMwmData firstLodMwmData = new MyMwmData(); if (!firstLodMwmData.LoadFromFile(filepath)) { MyRender11.Log.WriteLine(string.Format("Mwm '{0}' cannot be loaded from file", filepath)); return(false); } if (!IsModelSuitable(firstLodMwmData)) { return(false); } MyRenderProxy.Assert(!m_models.ContainsKey(firstLodMwmData.MwmFilepath)); models = CreateModels(firstLodMwmData); m_models.Add(firstLodMwmData.MwmFilepath, models); return(true); }
// the method is static, because of removal all of the references on the member variables static unsafe IVertexBuffer CreateSimpleVB0(MyMwmData mwmData) { string name = "VB0-" + mwmData.MwmFilepath; if (!mwmData.IsAnimated) { MyVertexFormatPositionH4[] vertices = new MyVertexFormatPositionH4[mwmData.VerticesCount]; for (int vertexIndex = 0; vertexIndex < mwmData.VerticesCount; ++vertexIndex) { vertices[vertexIndex].Position = mwmData.Positions[vertexIndex]; } fixed(void *ptr = vertices) { return(MyManagers.Buffers.CreateVertexBuffer(name, vertices.Length, MyVertexFormatPositionH4.STRIDE, new IntPtr(ptr), ResourceUsage.Immutable)); } } else { MyVertexFormatPositionSkinning[] vertices = new MyVertexFormatPositionSkinning[mwmData.VerticesCount]; for (int vertexIndex = 0; vertexIndex < mwmData.VerticesCount; ++vertexIndex) { vertices[vertexIndex].Position = mwmData.Positions[vertexIndex]; vertices[vertexIndex].BoneIndices = new Byte4(mwmData.BoneIndices[vertexIndex].X, mwmData.BoneIndices[vertexIndex].Y, mwmData.BoneIndices[vertexIndex].Z, mwmData.BoneIndices[vertexIndex].W); vertices[vertexIndex].BoneWeights = new HalfVector4(mwmData.BoneWeights[vertexIndex]); } fixed(void *ptr = vertices) { return(MyManagers.Buffers.CreateVertexBuffer(name, vertices.Length, MyVertexFormatPositionSkinning.STRIDE, new IntPtr(ptr), ResourceUsage.Immutable)); } } }
// the method is static, because of removal all of the references on the member variables static unsafe IVertexBuffer CreateSimpleVB1(MyMwmData mwmData) { MyRenderProxy.Assert(mwmData.IsValid2ndStream); string name = "VB1-" + mwmData.MwmFilepath; //Byte4 texIndices = new Byte4(0, 0, 0, 0); var vertices = new MyVertexFormatTexcoordNormalTangent[mwmData.VerticesCount]; fixed(MyVertexFormatTexcoordNormalTangent *destinationPointer = vertices) { for (int vertexIndex = 0; vertexIndex < mwmData.VerticesCount; ++vertexIndex) { destinationPointer[vertexIndex].Normal = mwmData.Normals[vertexIndex]; destinationPointer[vertexIndex].Tangent = mwmData.Tangents[vertexIndex]; destinationPointer[vertexIndex].Texcoord = mwmData.Texcoords[vertexIndex]; //destinationPointer[vertexIndex].TexIndices = texIndices; } } fixed(void *ptr = vertices) { return(MyManagers.Buffers.CreateVertexBuffer(name, vertices.Length, MyVertexFormatTexcoordNormalTangent.STRIDE, new IntPtr(ptr), ResourceUsage.Immutable)); } }
MyModels CreateModels(MyMwmData firstLodMwmData) { MyModels models = new MyModels(); models.LoadFromMwmData(firstLodMwmData); return(models); }
public bool CreateGBuffer(MyMwmData mwmData, int lodNum, ref HashSet <string> setMaterialNames) { UniqueId = MyManagers.IDGenerator.GBufferLods.Generate(); LodNum = lodNum; IB = MyManagers.ModelBuffers.GetOrCreateIB(mwmData); VB0 = MyManagers.ModelBuffers.GetOrCreateVB0(mwmData); VB1 = MyManagers.ModelBuffers.GetOrCreateVB1(mwmData); VertexInputComponents = MyManagers.ModelBuffers.CreateStandardVertexInputComponents(mwmData); m_instanceMaterialsStrategy.Init(); BoundingBox = mwmData.BoundindBox; HighlightSections = null; Parts = new List <MyPart>(); GlassParts = null; int offset = 0; foreach (var mwmPartInfo in mwmData.PartInfos) { // Making of parts is connected to the creating index buffer. It will worth to do it much more connected in future int indicesCount = mwmPartInfo.m_indices.Count; string materialName = mwmPartInfo.GetMaterialName(); if (mwmPartInfo.Technique != MyMeshDrawTechnique.GLASS) { MyMeshDrawTechnique technique = mwmPartInfo.Technique; string cmFilepath = MyMwmUtils.GetColorMetalTexture(mwmPartInfo, mwmData.MwmContentPath); string ngFilepath = MyMwmUtils.GetNormalGlossTexture(mwmPartInfo, mwmData.MwmContentPath); string extFilepath = MyMwmUtils.GetExtensionTexture(mwmPartInfo, mwmData.MwmContentPath); string alphamaskFilepath = MyMwmUtils.GetAlphamaskTexture(mwmPartInfo, mwmData.MwmContentPath); MyStandardMaterial material = MyManagers.Materials.GetOrCreateStandardMaterial(materialName, technique, cmFilepath, ngFilepath, extFilepath, alphamaskFilepath); MyPart part = new MyPart(); part.InitForGBuffer(this, materialName, mwmData.MwmContentPath, mwmPartInfo, material, offset, indicesCount, 0); Parts.Add(part); } else { MyGlassMaterial glassMaterial = MyManagers.Materials.GetGlassMaterial(materialName); MyPart part = new MyPart(); part.InitForGlass(this, mwmPartInfo.GetMaterialName(), glassMaterial, mwmPartInfo.Technique, offset, indicesCount, 0); if (GlassParts == null) { GlassParts = new List <MyPart>(); } GlassParts.Add(part); // glass parts are rendered by different pipeline than the regular "solid" geometry } offset += indicesCount; setMaterialNames.Add(materialName); } return(true); }
public IIndexBuffer GetOrCreateIB(MyMwmData mwmData) { string filepath = mwmData.MwmFilepath; if (m_ibs.ContainsKey(filepath)) { return(m_ibs[filepath]); } IIndexBuffer ib = CreateSimpleIB(mwmData); m_ibs.Add(filepath, ib); return(m_ibs[filepath]); }
public IVertexBuffer GetOrCreateVB1(MyMwmData mwmData) { string filepath = mwmData.MwmFilepath; if (m_vb1s.ContainsKey(filepath)) { return(m_vb1s[filepath]); } IVertexBuffer vb1 = CreateSimpleVB1(mwmData); m_vb1s.Add(filepath, vb1); return(m_vb1s[filepath]); }
// this method will create parts that way, that it will concatenate following parts into single part public bool CreateDepth(MyMwmData mwmData, int lodNum, ref HashSet <string> setMaterialNames) { UniqueId = MyManagers.IDGenerator.DepthLods.Generate(); LodNum = lodNum; IB = MyManagers.ModelBuffers.GetOrCreateIB(mwmData); VB0 = MyManagers.ModelBuffers.GetOrCreateVB0(mwmData); VB1 = null; VertexInputComponents = MyManagers.ModelBuffers.CreateShadowVertexInputComponents(mwmData); m_instanceMaterialsStrategy.Init(); HighlightSections = null; Parts = new List <MyPart>(); GlassParts = null; int indicesStart = 0; int indicesCount = 0; foreach (var mwmPartInfo in mwmData.PartInfos) { string materialName = mwmPartInfo.GetMaterialName(); int partIndicesCount = mwmPartInfo.m_indices.Count; if (MyMwmUtils.NoShadowCasterMaterials.Contains(materialName) && mwmPartInfo.Technique != MyMeshDrawTechnique.GLASS) // glass is not loaded and rendered for GBuffer rendering { // if the current part should be skipped, we will check, whether the previous parts will create a merged part if (indicesCount != 0) { MyPart part = new MyPart(); part.InitForDepth(this, "ShadowProxy", MyMeshDrawTechnique.MESH, indicesStart, indicesCount, 0); Parts.Add(part); } indicesStart += indicesCount; indicesCount = 0; indicesStart += partIndicesCount; } else { indicesCount += partIndicesCount; } setMaterialNames.Add(materialName); } if (indicesCount != 0) { MyPart part = new MyPart(); part.InitForDepth(this, "ShadowProxy", MyMeshDrawTechnique.MESH, indicesStart, indicesCount, 0); Parts.Add(part); } return(true); }
// The mwmData will be loaded and if there are link to another files with lods, they will be loaded bool LoadFromMwmData(MyMwmData firstLodMwmData, ICreateLodStrategy strategy) { m_tmpAllMaterialNames.Clear(); MyLod firstLods = new MyLod(); if (!strategy.CreateLod(firstLods, firstLodMwmData, 0, ref m_tmpAllMaterialNames)) { MyRender11.Log.WriteLine(string.Format("Mwm '{0}' cannot be loaded as the 1st lod", firstLodMwmData.MwmFilepath)); return(false); } // if no lods are specified inside of the mwm, models with the single lod will be created: if (firstLodMwmData.Lods.Length == 0) { CreateFromSingleLod(firstLods); } else // otherwise all lods will be loaded and initilised: { m_lodStrategyInfo.Init(firstLodMwmData.Lods); List <MyLod> multipleLods = new List <MyLod>(); multipleLods.Add(firstLods); for (int i = 0; i < firstLodMwmData.Lods.Length; i++) { string lodFilepath = firstLodMwmData.Lods[i].GetModelAbsoluteFilePath(firstLodMwmData.MwmFilepath); MyLod lod = new MyLod(); MyMwmData mwmData = new MyMwmData(); if (!mwmData.LoadFromFile(lodFilepath)) { MyRender11.Log.WriteLine(string.Format("Mwm '{0}' cannot be loaded as the other lod", lodFilepath)); continue; } strategy.CreateLod(lod, mwmData, i + 1, ref m_tmpAllMaterialNames); multipleLods.Add(lod); } CreateFromMultipleLods(multipleLods); m_lodStrategyInfo.ReduceLodsCount(m_lods.Count); } m_instanceMaterialStrategy.Init(m_tmpAllMaterialNames); return(true); }
public bool CreateHighlight(MyMwmData mwmData, int lodNum, ref HashSet <string> setMaterialNames) { UniqueId = -1; LodNum = lodNum; IB = MyManagers.ModelBuffers.GetOrCreateIB(mwmData); VB0 = MyManagers.ModelBuffers.GetOrCreateVB0(mwmData); VB1 = MyManagers.ModelBuffers.GetOrCreateVB1(mwmData); VertexInputComponents = MyManagers.ModelBuffers.CreateShadowVertexInputComponents(mwmData); m_instanceMaterialsStrategy.Init(); BoundingBox = mwmData.BoundindBox; int offset = 0; // a little bit confusion, but for highlights, there is no difference between solid geometry and glass geometry, therefore glass parts are not filled and everything is in the parts Parts = new List <MyPart>(); GlassParts = null; foreach (var mwmPartInfo in mwmData.PartInfos) { string materialName = mwmPartInfo.GetMaterialName(); int indicesCount = mwmPartInfo.m_indices.Count; MyPart part = new MyPart(); part.InitForHighlight(this, mwmPartInfo.GetMaterialName(), mwmPartInfo.Technique, offset, indicesCount, 0); Parts.Add(part); offset += indicesCount; setMaterialNames.Add(materialName); } HighlightSections = null; if (mwmData.SectionInfos != null && mwmData.SectionInfos.Count > 0) { HighlightSections = new Dictionary <string, MySection>(mwmData.SectionInfos.Count); for (int i = 0; i < mwmData.SectionInfos.Count; i++) { MyMeshSectionInfo sectionInfo = mwmData.SectionInfos[i]; MySection section = new MySection(); section.Init(this, sectionInfo, Parts); HighlightSections.Add(sectionInfo.Name, section); } } return(true); }
public bool LoadFromMwmData(MyMwmData firstLodMwmData) { StandardModel = new MyModel(); if (!StandardModel.LoadGBufferModelFromMwmData(firstLodMwmData)) { return(false); } DepthModel = new MyModel(); if (!DepthModel.LoadDepthModelFromMwmData(firstLodMwmData)) { return(false); } HighlightModel = new MyModel(); if (!HighlightModel.LoadHighlightModelFromMwmData(firstLodMwmData)) { return(false); } Filepath = firstLodMwmData.MwmFilepath; return(true); }
public bool CreateHighlight(MyMwmData mwmData, int lodNum, ref HashSet <string> setMaterialNames) { UniqueId = -1; LodNum = lodNum; IB = MyManagers.ModelBuffers.GetOrCreateIB(mwmData); VB0 = MyManagers.ModelBuffers.GetOrCreateVB0(mwmData); VB1 = MyManagers.ModelBuffers.GetOrCreateVB1(mwmData); VertexInputComponents = MyManagers.ModelBuffers.CreateShadowVertexInputComponents(mwmData); m_instanceMaterialsStrategy.Init(); BoundingBox = mwmData.BoundindBox; int offset = 0; Parts = new List <MyPart>(); foreach (var mwmPartInfo in mwmData.PartInfos) { string materialName = mwmPartInfo.GetMaterialName(); int indicesCount = mwmPartInfo.m_indices.Count; MyPart part = new MyPart(); part.InitForHighlight(this, mwmPartInfo.GetMaterialName(), mwmPartInfo.Technique, offset, indicesCount, 0); Parts.Add(part); offset += indicesCount; setMaterialNames.Add(materialName); } Sections = null; if (mwmData.SectionInfos != null && mwmData.SectionInfos.Count > 0) { Sections = new Dictionary <string, MySection>(mwmData.SectionInfos.Count); for (int i = 0; i < mwmData.SectionInfos.Count; i++) { MyMeshSectionInfo sectionInfo = mwmData.SectionInfos[i]; MySection section = new MySection(); section.Init(this, sectionInfo, Parts); Sections.Add(sectionInfo.Name, section); } } return(true); }
// This function will open the file, read it and close it again. Use it only for debug! public bool IsModelSuitable(string filepath) { filepath = MyMwmUtils.GetFullMwmFilepath(filepath); if (m_resultsForIsModelSuitable.ContainsKey(filepath)) // if the results have been resolved before, reuse them! { return(m_resultsForIsModelSuitable[filepath]); } // The file has not been analyzed before, the file will be opened and analyzed: MyMwmData mwmData = new MyMwmData(); if (!mwmData.LoadFromFile(filepath)) { m_resultsForIsModelSuitable.Add(filepath, false); return(false); } bool result = IsModelSuitable(mwmData); m_resultsForIsModelSuitable.Add(filepath, result); return(result); }
public bool GetOrCreateModels(string filepath, out MyModels models) { filepath = MyMwmUtils.GetFullMwmFilepath(filepath); if (m_models.TryGetValue(filepath, out models)) // if the model is loaded, return true { return(true); } // if the model has been loaded, but it did not been suitable, return false: if (m_resultsForIsModelSuitable.ContainsKey(filepath)) { if (m_resultsForIsModelSuitable[filepath] == false) { return(false); } } // Load mwm as first lod MyMwmData firstLodMwmData = new MyMwmData(); if (!firstLodMwmData.LoadFromFile(filepath)) { MyRender11.Log.WriteLine(string.Format("Mwm '{0}' cannot be loaded from file", filepath)); return(false); } if (!IsModelSuitable(firstLodMwmData)) { m_resultsForIsModelSuitable.Add(filepath, false); return(false); } MyRenderProxy.Assert(!m_models.ContainsKey(firstLodMwmData.MwmFilepath)); models = CreateModels(firstLodMwmData); m_models.Add(firstLodMwmData.MwmFilepath, models); return(true); }
public unsafe List <MyVertexInputComponent> CreateStandardVertexInputComponents(MyMwmData mwmData) { List <MyVertexInputComponent> vertexComponents = new List <MyVertexInputComponent>(); Debug.Assert(sizeof(HalfVector4) == sizeof(MyVertexFormatPositionH4)); vertexComponents.Add(new MyVertexInputComponent(MyVertexInputComponentType.POSITION_PACKED)); if (mwmData.IsAnimated) { vertexComponents.Add(new MyVertexInputComponent(MyVertexInputComponentType.BLEND_WEIGHTS)); vertexComponents.Add(new MyVertexInputComponent(MyVertexInputComponentType.BLEND_INDICES)); } if (mwmData.IsValid2ndStream) { vertexComponents.Add(new MyVertexInputComponent(MyVertexInputComponentType.NORMAL)); vertexComponents.Add(new MyVertexInputComponent(MyVertexInputComponentType.TANGENT_SIGN_OF_BITANGENT)); vertexComponents.Add(new MyVertexInputComponent(MyVertexInputComponentType.TEXCOORD0_H)); } return(vertexComponents); }
public bool LoadDepthModelFromMwmData(MyMwmData firstLodMwmData) { return(LoadFromMwmData(firstLodMwmData, m_createDepthLodStrategy)); }
public bool LoadHighlightModelFromMwmData(MyMwmData firstLodMwmData) { return(LoadFromMwmData(firstLodMwmData, m_createHighlightLodStrategy)); }
public bool LoadGBufferModelFromMwmData(MyMwmData firstLodMwmData) { return(LoadFromMwmData(firstLodMwmData, m_createGBufferLodStrategy)); }
bool IsModelSuitable(MyMwmData mwmData) { if (mwmData.HasBones) { return(false); } if (!mwmData.IsValid2ndStream) { return(false); } foreach (var partInfo in mwmData.PartInfos) { if (partInfo.m_MaterialDesc == null) { continue; } string materialName = partInfo.m_MaterialDesc.MaterialName; if (m_blackListMaterials.Contains(materialName)) { return(false); } switch (partInfo.m_MaterialDesc.Facing) { case MyFacingEnum.None: break; default: return(false); } switch (partInfo.Technique) { case MyMeshDrawTechnique.MESH: case MyMeshDrawTechnique.ALPHA_MASKED: case MyMeshDrawTechnique.DECAL: case MyMeshDrawTechnique.DECAL_CUTOUT: case MyMeshDrawTechnique.DECAL_NOPREMULT: break; default: return(false); } } // The current model is fine, let's check the lods foreach (var lod in mwmData.Lods) { string filepath = lod.GetModelAbsoluteFilePath(mwmData.MwmFilepath); if (filepath == null) { string errMsg = string.Format("The table for lods is specified, but it is invalid (filepath for lod is missing). File: '{0}'", mwmData.MwmFilepath); MyRenderProxy.Fail(errMsg); MyRenderProxy.Log.WriteLine(errMsg); return(false); } MyMwmData lodMwmData = new MyMwmData(); if (lodMwmData.LoadFromFile(filepath)) { bool isSuitable = IsModelSuitable(lodMwmData); if (!isSuitable) { return(false); } } } return(true); }
public bool CreateLod(MyLod lod, MyMwmData lodMwmData, int lodNum, ref HashSet <string> setMaterialNames) { // material names set should not be applied return(lod.CreateHighlight(lodMwmData, lodNum, ref setMaterialNames)); }
public bool CreateLod(MyLod lod, MyMwmData lodMwmData, int lodNum, ref HashSet <string> setMaterialNames) { return(lod.CreateGBuffer(lodMwmData, lodNum, ref setMaterialNames)); }
public unsafe List <MyVertexInputComponent> CreateShadowVertexInputComponents(MyMwmData mwmData) { List <MyVertexInputComponent> vertexComponents = new List <MyVertexInputComponent>(); Debug.Assert(sizeof(HalfVector4) == sizeof(MyVertexFormatPositionH4)); vertexComponents.Add(new MyVertexInputComponent(MyVertexInputComponentType.POSITION_PACKED)); if (mwmData.IsAnimated) { vertexComponents.Add(new MyVertexInputComponent(MyVertexInputComponentType.BLEND_WEIGHTS)); vertexComponents.Add(new MyVertexInputComponent(MyVertexInputComponentType.BLEND_INDICES)); } return(vertexComponents); }