2 // Copyright (c) Microsoft. All rights reserved.
3 // This code is licensed under the MIT License (MIT).
4 // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF
5 // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY
6 // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR
7 // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.
9 // Developed by Minigraph
11 // Author: Alex Nankervis
17 #include "TextureManager.h"
18 #include "GraphicsCore.h"
19 #include "DescriptorHeap.h"
20 #include "CommandContext.h"
23 using namespace Graphics
;
25 bool Model::LoadH3D(const char *filename
)
28 if (0 != fopen_s(&file
, filename
, "rb"))
33 if (1 != fread(&m_Header
, sizeof(Header
), 1, file
)) goto h3d_load_fail
;
35 m_pMesh
= new Mesh
[m_Header
.meshCount
];
36 m_pMaterial
= new Material
[m_Header
.materialCount
];
38 if (m_Header
.meshCount
> 0)
39 if (1 != fread(m_pMesh
, sizeof(Mesh
) * m_Header
.meshCount
, 1, file
)) goto h3d_load_fail
;
40 if (m_Header
.materialCount
> 0)
41 if (1 != fread(m_pMaterial
, sizeof(Material
) * m_Header
.materialCount
, 1, file
)) goto h3d_load_fail
;
43 m_VertexStride
= m_pMesh
[0].vertexStride
;
44 m_VertexStrideDepth
= m_pMesh
[0].vertexStrideDepth
;
46 for (uint32_t meshIndex
= 1; meshIndex
< m_Header
.meshCount
; ++meshIndex
)
48 const Mesh
& mesh
= m_pMesh
[meshIndex
];
49 ASSERT(mesh
.vertexStride
== m_VertexStride
);
50 ASSERT(mesh
.vertexStrideDepth
== m_VertexStrideDepth
);
52 for (uint32_t meshIndex
= 0; meshIndex
< m_Header
.meshCount
; ++meshIndex
)
54 const Mesh
& mesh
= m_pMesh
[meshIndex
];
56 ASSERT( mesh
.attribsEnabled
==
57 (attrib_mask_position
| attrib_mask_texcoord0
| attrib_mask_normal
| attrib_mask_tangent
| attrib_mask_bitangent
) );
58 ASSERT(mesh
.attrib
[0].components
== 3 && mesh
.attrib
[0].format
== Model::attrib_format_float
); // position
59 ASSERT(mesh
.attrib
[1].components
== 2 && mesh
.attrib
[1].format
== Model::attrib_format_float
); // texcoord0
60 ASSERT(mesh
.attrib
[2].components
== 3 && mesh
.attrib
[2].format
== Model::attrib_format_float
); // normal
61 ASSERT(mesh
.attrib
[3].components
== 3 && mesh
.attrib
[3].format
== Model::attrib_format_float
); // tangent
62 ASSERT(mesh
.attrib
[4].components
== 3 && mesh
.attrib
[4].format
== Model::attrib_format_float
); // bitangent
64 ASSERT( mesh
.attribsEnabledDepth
==
65 (attrib_mask_position
) );
66 ASSERT(mesh
.attrib
[0].components
== 3 && mesh
.attrib
[0].format
== Model::attrib_format_float
); // position
70 m_pVertexData
= new unsigned char[ m_Header
.vertexDataByteSize
];
71 m_pIndexData
= new unsigned char[ m_Header
.indexDataByteSize
];
72 m_pVertexDataDepth
= new unsigned char[ m_Header
.vertexDataByteSizeDepth
];
73 m_pIndexDataDepth
= new unsigned char[ m_Header
.indexDataByteSize
];
75 if (m_Header
.vertexDataByteSize
> 0)
76 if (1 != fread(m_pVertexData
, m_Header
.vertexDataByteSize
, 1, file
)) goto h3d_load_fail
;
77 if (m_Header
.indexDataByteSize
> 0)
78 if (1 != fread(m_pIndexData
, m_Header
.indexDataByteSize
, 1, file
)) goto h3d_load_fail
;
80 if (m_Header
.vertexDataByteSizeDepth
> 0)
81 if (1 != fread(m_pVertexDataDepth
, m_Header
.vertexDataByteSizeDepth
, 1, file
)) goto h3d_load_fail
;
82 if (m_Header
.indexDataByteSize
> 0)
83 if (1 != fread(m_pIndexDataDepth
, m_Header
.indexDataByteSize
, 1, file
)) goto h3d_load_fail
;
85 m_VertexBuffer
.Create(L
"VertexBuffer", m_Header
.vertexDataByteSize
/ m_VertexStride
, m_VertexStride
, m_pVertexData
);
86 m_IndexBuffer
.Create(L
"IndexBuffer", m_Header
.indexDataByteSize
/ sizeof(uint16_t), sizeof(uint16_t), m_pIndexData
);
87 delete [] m_pVertexData
;
88 m_pVertexData
= nullptr;
89 delete [] m_pIndexData
;
90 m_pIndexData
= nullptr;
92 m_VertexBufferDepth
.Create(L
"VertexBufferDepth", m_Header
.vertexDataByteSizeDepth
/ m_VertexStrideDepth
, m_VertexStrideDepth
, m_pVertexDataDepth
);
93 m_IndexBufferDepth
.Create(L
"IndexBufferDepth", m_Header
.indexDataByteSize
/ sizeof(uint16_t), sizeof(uint16_t), m_pIndexDataDepth
);
94 delete [] m_pVertexDataDepth
;
95 m_pVertexDataDepth
= nullptr;
96 delete [] m_pIndexDataDepth
;
97 m_pIndexDataDepth
= nullptr;
105 if (EOF
== fclose(file
))
111 bool Model::SaveH3D(const char *filename
) const
113 FILE *file
= nullptr;
114 if (0 != fopen_s(&file
, filename
, "wb"))
119 if (1 != fwrite(&m_Header
, sizeof(Header
), 1, file
)) goto h3d_save_fail
;
121 if (m_Header
.meshCount
> 0)
122 if (1 != fwrite(m_pMesh
, sizeof(Mesh
) * m_Header
.meshCount
, 1, file
)) goto h3d_save_fail
;
123 if (m_Header
.materialCount
> 0)
124 if (1 != fwrite(m_pMaterial
, sizeof(Material
) * m_Header
.materialCount
, 1, file
)) goto h3d_save_fail
;
126 if (m_Header
.vertexDataByteSize
> 0)
127 if (1 != fwrite(m_pVertexData
, m_Header
.vertexDataByteSize
, 1, file
)) goto h3d_save_fail
;
128 if (m_Header
.indexDataByteSize
> 0)
129 if (1 != fwrite(m_pIndexData
, m_Header
.indexDataByteSize
, 1, file
)) goto h3d_save_fail
;
131 if (m_Header
.vertexDataByteSizeDepth
> 0)
132 if (1 != fwrite(m_pVertexDataDepth
, m_Header
.vertexDataByteSizeDepth
, 1, file
)) goto h3d_save_fail
;
133 if (m_Header
.indexDataByteSize
> 0)
134 if (1 != fwrite(m_pIndexDataDepth
, m_Header
.indexDataByteSize
, 1, file
)) goto h3d_save_fail
;
140 if (EOF
== fclose(file
))
146 void Model::ReleaseTextures()
149 if (m_Textures != nullptr)
151 for (uint32_t materialIdx = 0; materialIdx < m_Header.materialCount; ++materialIdx)
153 for (int n = 0; n < Material::texCount; n++)
155 if (m_Textures[materialIdx * Material::texCount + n])
156 m_Textures[materialIdx * Material::texCount + n]->Release();
157 m_Textures[materialIdx * Material::texCount + n] = nullptr;
160 delete [] m_Textures;
165 void Model::LoadTextures(void)
169 m_SRVs
= new D3D12_CPU_DESCRIPTOR_HANDLE
[m_Header
.materialCount
* 6];
171 const ManagedTexture
* MatTextures
[6] = {};
173 for (uint32_t materialIdx
= 0; materialIdx
< m_Header
.materialCount
; ++materialIdx
)
175 const Material
& pMaterial
= m_pMaterial
[materialIdx
];
178 MatTextures
[0] = TextureManager::LoadFromFile(pMaterial
.texDiffusePath
, true);
179 if (!MatTextures
[0]->IsValid())
180 MatTextures
[0] = TextureManager::LoadFromFile("default", true);
183 MatTextures
[1] = TextureManager::LoadFromFile(pMaterial
.texSpecularPath
, true);
184 if (!MatTextures
[1]->IsValid())
186 MatTextures
[1] = TextureManager::LoadFromFile(std::string(pMaterial
.texDiffusePath
) + "_specular", true);
187 if (!MatTextures
[1]->IsValid())
188 MatTextures
[1] = TextureManager::LoadFromFile("default_specular", true);
192 //MatTextures[2] = TextureManager::LoadFromFile(pMaterial.texEmissivePath, true);
195 MatTextures
[3] = TextureManager::LoadFromFile(pMaterial
.texNormalPath
, false);
196 if (!MatTextures
[3]->IsValid())
198 MatTextures
[3] = TextureManager::LoadFromFile(std::string(pMaterial
.texDiffusePath
) + "_normal", false);
199 if (!MatTextures
[3]->IsValid())
200 MatTextures
[3] = TextureManager::LoadFromFile("default_normal", false);
204 //MatTextures[4] = TextureManager::LoadFromFile(pMaterial.texLightmapPath, true);
207 //MatTextures[5] = TextureManager::LoadFromFile(pMaterial.texReflectionPath, true);
209 m_SRVs
[materialIdx
* 6 + 0] = MatTextures
[0]->GetSRV();
210 m_SRVs
[materialIdx
* 6 + 1] = MatTextures
[1]->GetSRV();
211 m_SRVs
[materialIdx
* 6 + 2] = MatTextures
[0]->GetSRV();
212 m_SRVs
[materialIdx
* 6 + 3] = MatTextures
[3]->GetSRV();
213 m_SRVs
[materialIdx
* 6 + 4] = MatTextures
[0]->GetSRV();
214 m_SRVs
[materialIdx
* 6 + 5] = MatTextures
[0]->GetSRV();