Merge pull request #173 from SHADE-DP/SP3-13-Assets-Manager
Support for External Model Compiler and Model/Mesh sub assets Compiling of external files (.gltf, .fbx) done by externally built exe Models recognised as whole assets, contained meshes recognises and individual assets as well but saved into one file Structured control paths for assets with and without sub assets for loading
This commit is contained in:
commit
378e4a67ce
Binary file not shown.
|
@ -1,3 +0,0 @@
|
|||
Name: Cube.003
|
||||
ID: 71245919
|
||||
Type: 4
|
|
@ -1,3 +0,0 @@
|
|||
Name: Cube.012
|
||||
ID: 80365422
|
||||
Type: 4
|
Binary file not shown.
File diff suppressed because one or more lines are too long
Binary file not shown.
|
@ -0,0 +1,10 @@
|
|||
Name: racoon
|
||||
ID: 77816045
|
||||
Type: 4
|
||||
Sub Assets:
|
||||
Name: Bag
|
||||
ID: 144838771
|
||||
Type: 8
|
||||
Name: Raccoon
|
||||
ID: 149697411
|
||||
Type: 8
|
|
@ -7,7 +7,7 @@ echo "SHADE DEPENDENCIES (Default - All in 10 Seconds)"
|
|||
echo "A - All"
|
||||
echo "B - VMA"
|
||||
echo "C - msdf"
|
||||
echo "D - assimp"
|
||||
echo "D - ModelCompiler"
|
||||
echo "E - spdlog"
|
||||
echo "F - reactphysics3d"
|
||||
echo "G - imgui"
|
||||
|
@ -29,7 +29,7 @@ set _e=%ERRORLEVEL%
|
|||
if %_e%==1 goto VMA
|
||||
if %_e%==2 goto VMA
|
||||
if %_e%==3 goto MSDF
|
||||
if %_e%==4 goto assimp
|
||||
if %_e%==4 goto ModelCompiler
|
||||
if %_e%==5 goto spdlog
|
||||
if %_e%==6 goto reactphysics3d
|
||||
if %_e%==7 goto imgui
|
||||
|
@ -53,12 +53,13 @@ if %_e%==2 (goto :done) else (goto :MSDF)
|
|||
echo -----------------------MSDF----------------------------
|
||||
rmdir "Dependencies/msdf" /S /Q
|
||||
git clone --recurse-submodules https://github.com/SHADE-DP/msdf-atlas-gen.git "Dependencies/msdf"
|
||||
if %_e%==3 (goto :done) else (goto :assimp)
|
||||
if %_e%==3 (goto :done) else (goto :ModelCompiler)
|
||||
|
||||
:assimp
|
||||
echo -----------------------assimp----------------------------
|
||||
rmdir "Dependencies/assimp" /S /Q
|
||||
git clone https://github.com/SHADE-DP/assimp.git "Dependencies/assimp"
|
||||
:ModelCompiler
|
||||
echo -----------------------ModelCompiler----------------------------
|
||||
rmdir "Dependencies/ModelCompiler" /S /Q
|
||||
git clone https://github.com/SHADE-DP/ModelCompiler.git "Dependencies/ModelCompiler"
|
||||
Dependencies/ModelCompiler/Dependencies.bat
|
||||
if %_e%==4 (goto :done) else (goto :spdlog)
|
||||
|
||||
@REM :ktx
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
IncludeDir = {}
|
||||
IncludeDir["assimp"] = "%{wks.location}\\Dependencies\\assimp"
|
||||
IncludeDir["ModelCompiler"] = "%{wks.location}\\Dependencies\\ModelCompiler"
|
||||
IncludeDir["imgui"] = "%{wks.location}\\Dependencies\\imgui"
|
||||
IncludeDir["imguizmo"] = "%{wks.location}\\Dependencies\\imguizmo"
|
||||
IncludeDir["imnodes"] = "%{wks.location}\\Dependencies\\imnodes"
|
||||
|
|
|
@ -53,7 +53,7 @@ namespace Sandbox
|
|||
switch (asset.type)
|
||||
{
|
||||
case AssetType::MESH:
|
||||
if (asset.name == "Cube.012")
|
||||
if (asset.name == "Raccoon")
|
||||
handles.emplace_back(SHResourceManager::LoadOrGet<SHMesh>(asset.id));
|
||||
break;
|
||||
case AssetType::TEXTURE:
|
||||
|
|
|
@ -26,7 +26,6 @@ project "SHADE_Engine"
|
|||
|
||||
externalincludedirs
|
||||
{
|
||||
"%{IncludeDir.assimp}\\include",
|
||||
"%{IncludeDir.imgui}",
|
||||
"%{IncludeDir.imguizmo}",
|
||||
"%{IncludeDir.imnodes}",
|
||||
|
@ -52,8 +51,6 @@ project "SHADE_Engine"
|
|||
{
|
||||
"%{prj.location}/libs",
|
||||
"%{IncludeDir.VULKAN}/Lib",
|
||||
"%{IncludeDir.assimp}/lib/Debug",
|
||||
"%{IncludeDir.assimp}/lib/Release",
|
||||
"%{IncludeDir.RTTR}/lib",
|
||||
"%{IncludeDir.SDL}/lib",
|
||||
"%{IncludeDir.spdlog}/lib",
|
||||
|
@ -119,7 +116,8 @@ project "SHADE_Engine"
|
|||
filter "configurations:Debug"
|
||||
postbuildcommands
|
||||
{
|
||||
"xcopy /r /y /q \"%{IncludeDir.assimp}\\bin\\Debug\\assimp-vc142-mtd.dll\" \"$(OutDir)\"",
|
||||
"xcopy /r /y /q \"%{IncludeDir.ModelCompiler}\\bin\\Debug\\assimp-vc142-mtd.dll\" \"$(OutDir)\"",
|
||||
"xcopy /r /y /q \"%{IncludeDir.ModelCompiler}\\bin\\Debug\\ModelCompiler.exe\" \"$(OutDir)\"",
|
||||
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmodL.dll\" \"$(OutDir)\"",
|
||||
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmodstudioL.dll\" \"$(OutDir)\""
|
||||
}
|
||||
|
@ -127,7 +125,8 @@ project "SHADE_Engine"
|
|||
filter "configurations:Release"
|
||||
postbuildcommands
|
||||
{
|
||||
"xcopy /r /y /q \"%{IncludeDir.assimp}\\bin\\Release\\assimp-vc142-mt.dll\" \"$(OutDir)\"",
|
||||
"xcopy /r /y /q \"%{IncludeDir.ModelCompiler}\\bin\\Release\\assimp-vc142-mt.dll\" \"$(OutDir)\"",
|
||||
"xcopy /r /y /q \"%{IncludeDir.ModelCompiler}\\bin\\Release\\ModelCompiler.exe\" \"$(OutDir)\"",
|
||||
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmod.dll\" \"$(OutDir)\"",
|
||||
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmodstudio.dll\" \"$(OutDir)\""
|
||||
}
|
||||
|
@ -135,32 +134,35 @@ project "SHADE_Engine"
|
|||
filter "configurations:Publish"
|
||||
postbuildcommands
|
||||
{
|
||||
"xcopy /r /y /q \"%{IncludeDir.assimp}\\bin\\Release\\assimp-vc142-mt.dll\" \"$(OutDir)\"",
|
||||
--"xcopy /r /y /q \"%{IncludeDir.assimp}\\bin\\Release\\assimp-vc142-mt.dll\" \"$(OutDir)\"",
|
||||
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmod.dll\" \"$(OutDir)\"",
|
||||
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmodstudio.dll\" \"$(OutDir)\""
|
||||
}
|
||||
|
||||
filter "configurations:Publish"
|
||||
postbuildcommands {"xcopy /r /y /q \"%{IncludeDir.assimp}\\bin\\Release\\assimp-vc142-mt.dll\" \"$(OutDir)\""}
|
||||
postbuildcommands
|
||||
{
|
||||
--"xcopy /r /y /q \"%{IncludeDir.assimp}\\bin\\Release\\assimp-vc142-mt.dll\" \"$(OutDir)\""
|
||||
}
|
||||
|
||||
warnings 'Extra'
|
||||
|
||||
filter "configurations:Debug"
|
||||
symbols "On"
|
||||
defines {"_DEBUG", "SHEDITOR"}
|
||||
links{"assimp-vc142-mtd.lib", "librttr_core_d.lib", "spdlogd.lib"}
|
||||
links{"librttr_core_d.lib", "spdlogd.lib"}
|
||||
links{"fmodstudioL_vc.lib", "fmodL_vc.lib"}
|
||||
|
||||
filter "configurations:Release"
|
||||
optimize "On"
|
||||
defines{"_RELEASE", "SHEDITOR"}
|
||||
links{"assimp-vc142-mt.lib", "librttr_core.lib", "spdlog.lib"}
|
||||
links{"librttr_core.lib", "spdlog.lib"}
|
||||
links{"fmodstudio_vc.lib", "fmod_vc.lib"}
|
||||
|
||||
filter "configurations:Publish"
|
||||
optimize "On"
|
||||
defines{"_RELEASE", "_PUBLISH"}
|
||||
links{"assimp-vc142-mt.lib", "librttr_core.lib", "spdlog.lib"}
|
||||
links{"librttr_core.lib", "spdlog.lib"}
|
||||
excludes
|
||||
{
|
||||
-- "%{prj.location}/src/Editor/**.cpp",
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
#pragma once
|
||||
|
||||
#include "SHMeshAsset.h"
|
||||
#include "SHModelAsset.h"
|
||||
#include "SHTextureAsset.h"
|
|
@ -18,24 +18,31 @@
|
|||
|
||||
namespace SHADE
|
||||
{
|
||||
struct SH_API SHMeshAssetHeader
|
||||
{
|
||||
uint32_t vertexCount;
|
||||
uint32_t indexCount;
|
||||
std::string name;
|
||||
};
|
||||
struct SHMeshAssetHeader
|
||||
{
|
||||
uint32_t vertexCount;
|
||||
uint32_t indexCount;
|
||||
std::string name;
|
||||
};
|
||||
|
||||
struct SH_API SHMeshAsset : SHAssetData
|
||||
{
|
||||
bool compiled;
|
||||
bool changed;
|
||||
struct SHModelAssetHeader
|
||||
{
|
||||
size_t meshCount;
|
||||
};
|
||||
|
||||
SHMeshAssetHeader header;
|
||||
struct SH_API SHMeshData : SHAssetData
|
||||
{
|
||||
SHMeshAssetHeader header;
|
||||
std::vector<SHVec3> VertexPositions;
|
||||
std::vector<SHVec3> VertexTangents;
|
||||
std::vector<SHVec3> VertexNormals;
|
||||
std::vector<SHVec2> VertexTexCoords;
|
||||
std::vector<uint32_t> Indices;
|
||||
};
|
||||
|
||||
std::vector<SHVec3> vertexPosition;
|
||||
std::vector<SHVec3> vertexTangent;
|
||||
std::vector<SHVec3> vertexNormal;
|
||||
std::vector<SHVec2> texCoords;
|
||||
std::vector<uint32_t> indices;
|
||||
};
|
||||
struct SH_API SHModelAsset : SHAssetData
|
||||
{
|
||||
SHModelAssetHeader header;
|
||||
std::vector<SHMeshData*> subMeshes;
|
||||
};
|
||||
}
|
|
@ -1,201 +0,0 @@
|
|||
/*************************************************************************//**
|
||||
* \file SHMeshCompiler.cpp
|
||||
* \author Loh Xiao Qi
|
||||
* \date 30 September 2022
|
||||
* \brief Library to write data in SHMeshAsset into binary file for faster
|
||||
* loading in the future
|
||||
*
|
||||
*
|
||||
* Copyright (C) 2022 DigiPen Institute of Technology. Reproduction or
|
||||
* disclosure of this file or its contents without the prior written consent
|
||||
* of DigiPen Institute of Technology is prohibited.
|
||||
*****************************************************************************/
|
||||
#include "SHpch.h"
|
||||
#include "SHMeshCompiler.h"
|
||||
#include "Graphics/MiddleEnd/Meshes/SHMeshData.h"
|
||||
#include <assimp/postprocess.h>
|
||||
|
||||
#include <fstream>
|
||||
|
||||
namespace SHADE
|
||||
{
|
||||
|
||||
Assimp::Importer SHMeshCompiler::aiImporter;
|
||||
|
||||
void SHMeshCompiler::ProcessNode(aiNode const& node, aiScene const& scene, MeshVectorRef meshes) noexcept
|
||||
{
|
||||
for (size_t i{ 0 }; i < node.mNumMeshes; ++i)
|
||||
{
|
||||
aiMesh* mesh = scene.mMeshes[node.mMeshes[i]];
|
||||
meshes.push_back(ProcessMesh(*mesh));
|
||||
}
|
||||
|
||||
for (size_t i{ 0 }; i < node.mNumChildren; ++i)
|
||||
{
|
||||
ProcessNode(*node.mChildren[i], scene, meshes);
|
||||
}
|
||||
}
|
||||
|
||||
void SHMeshCompiler::ExtractAnimations(aiScene const& scene, AnimVectorRef anims) noexcept
|
||||
{
|
||||
if (scene.HasAnimations())
|
||||
{
|
||||
std::vector<SHAnimationAsset> anims(scene.mNumAnimations);
|
||||
for (auto i{ 0 }; i < scene.mNumAnimations; ++i)
|
||||
{
|
||||
auto const& anim{ *scene.mAnimations[i] };
|
||||
|
||||
anims[i].name = anim.mName.C_Str();
|
||||
|
||||
anims[i].duration = anim.mDuration;
|
||||
anims[i].ticksPerSecond = anim.mTicksPerSecond;
|
||||
|
||||
std::copy_n(anim.mChannels, anim.mNumChannels, anims[i].nodeChannels.data());
|
||||
std::copy_n(anim.mMeshChannels, anim.mNumMeshChannels, anims[i].meshChannels.data());
|
||||
std::copy_n(anim.mMorphMeshChannels, anim.mNumMorphMeshChannels, anims[i].morphMeshChannels.data());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
SHMeshAsset* SHMeshCompiler::ProcessMesh(aiMesh const& mesh) noexcept
|
||||
{
|
||||
SHMeshAsset* result = new SHMeshAsset();
|
||||
result->compiled = false;
|
||||
result->changed = false;
|
||||
|
||||
for (size_t i{ 0 }; i < mesh.mNumVertices; ++i)
|
||||
{
|
||||
// Vertex position
|
||||
SHVec3 vertex;
|
||||
vertex.x = mesh.mVertices[i].x;
|
||||
vertex.y = mesh.mVertices[i].y;
|
||||
vertex.z = mesh.mVertices[i].z;
|
||||
result->vertexPosition.push_back(vertex);
|
||||
|
||||
// Tex coords
|
||||
SHVec2 texCoord{ 0.f, 0.f };
|
||||
if (mesh.mTextureCoords[0])
|
||||
{
|
||||
texCoord.x = mesh.mTextureCoords[0][i].x;
|
||||
texCoord.y = mesh.mTextureCoords[0][i].y;
|
||||
}
|
||||
result->texCoords.push_back(texCoord);
|
||||
|
||||
// Normals
|
||||
SHVec3 normal{ 0.f, 0.f, 0.f };
|
||||
if (mesh.mNormals)
|
||||
{
|
||||
normal.x = mesh.mNormals[i].x;
|
||||
normal.y = mesh.mNormals[i].y;
|
||||
normal.z = mesh.mNormals[i].z;
|
||||
}
|
||||
result->vertexNormal.push_back(normal);
|
||||
|
||||
// Tangent
|
||||
SHVec3 tangent{ 0.f, 0.f, 0.f };
|
||||
if (mesh.mTangents)
|
||||
{
|
||||
tangent.x = mesh.mTangents[i].x;
|
||||
tangent.y = mesh.mTangents[i].y;
|
||||
tangent.z = mesh.mTangents[i].z;
|
||||
}
|
||||
result->vertexTangent.push_back(tangent);
|
||||
}
|
||||
|
||||
for (size_t i{ 0 }; i < mesh.mNumFaces; ++i)
|
||||
{
|
||||
aiFace face = mesh.mFaces[i];
|
||||
for (size_t j{ 0 }; j < face.mNumIndices; ++j)
|
||||
{
|
||||
result->indices.push_back(face.mIndices[j]);
|
||||
}
|
||||
}
|
||||
|
||||
result->header.vertexCount = static_cast<uint32_t>(result->vertexPosition.size());
|
||||
result->header.indexCount = static_cast<uint32_t>(result->indices.size());
|
||||
result->header.name = mesh.mName.C_Str();
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
void SHMeshCompiler::LoadFromFile(AssetPath path, MeshVectorRef meshes, AnimVectorRef anims) noexcept
|
||||
{
|
||||
const aiScene* scene = aiImporter.ReadFile(path.string().c_str(),
|
||||
aiProcess_Triangulate // Make sure we get triangles rather than nvert polygons
|
||||
| aiProcess_GenUVCoords // Convert any type of mapping to uv mapping
|
||||
| aiProcess_TransformUVCoords // preprocess UV transformations (scaling, translation ...)
|
||||
| aiProcess_FindInstances // search for instanced meshes and remove them by references to one master
|
||||
| aiProcess_CalcTangentSpace // calculate tangents and bitangents if possible
|
||||
| aiProcess_JoinIdenticalVertices // join identical vertices/ optimize indexing
|
||||
| aiProcess_RemoveRedundantMaterials // remove redundant materials
|
||||
| aiProcess_FindInvalidData // detect invalid model data, such as invalid normal vectors
|
||||
| aiProcess_FlipUVs // flip the V to match the Vulkans way of doing UVs
|
||||
);
|
||||
|
||||
if (!scene || !scene->HasMeshes())
|
||||
{
|
||||
SHLOG_ERROR("ERROR in GLTF::ASSIMP: {}\nFile: {}", aiImporter.GetErrorString(), path.string());
|
||||
return;
|
||||
}
|
||||
|
||||
//ExtractAnimations(*scene, anims);
|
||||
|
||||
ProcessNode(*scene->mRootNode, *scene, meshes);
|
||||
|
||||
aiImporter.FreeScene();
|
||||
}
|
||||
|
||||
std::optional<AssetPath> SHMeshCompiler::CompileMeshBinary(SHMeshAsset const& asset, AssetPath path) noexcept
|
||||
{
|
||||
std::string newPath{ path.parent_path().string() + '/' };
|
||||
newPath += asset.header.name + MESH_EXTENSION.data();
|
||||
|
||||
std::ofstream file{ newPath, std::ios::out | std::ios::binary | std::ios::trunc };
|
||||
if (!file.is_open())
|
||||
{
|
||||
SHLOG_ERROR("Unable to open file for writing mesh file: {}", path.string());
|
||||
}
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(&(asset.header.vertexCount)),
|
||||
sizeof(uint32_t)
|
||||
);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<const char*>(&(asset.header.indexCount)),
|
||||
sizeof(uint32_t)
|
||||
);
|
||||
|
||||
auto const vertexVec3Byte{ sizeof(SHVec3) * asset.header.vertexCount };
|
||||
auto const vertexVec2Byte{ sizeof(SHVec2) * asset.header.vertexCount };
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(asset.vertexPosition.data()),
|
||||
vertexVec3Byte
|
||||
);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(asset.vertexTangent.data()),
|
||||
vertexVec3Byte
|
||||
);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(asset.vertexNormal.data()),
|
||||
vertexVec3Byte
|
||||
);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(asset.texCoords.data()),
|
||||
vertexVec2Byte
|
||||
);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(asset.indices.data()),
|
||||
sizeof(uint32_t) * asset.header.indexCount
|
||||
);
|
||||
|
||||
file.close();
|
||||
|
||||
return newPath;
|
||||
}
|
||||
}
|
|
@ -1,40 +0,0 @@
|
|||
/*************************************************************************//**
|
||||
* \file SHMeshCompiler.h
|
||||
* \author Loh Xiao Qi
|
||||
* \date 30 September 2022
|
||||
* \brief Library to write data in SHMeshAsset into binary file for faster
|
||||
* loading in the future
|
||||
*
|
||||
*
|
||||
* Copyright (C) 2022 DigiPen Institute of Technology. Reproduction or
|
||||
* disclosure of this file or its contents without the prior written consent
|
||||
* of DigiPen Institute of Technology is prohibited.
|
||||
*****************************************************************************/
|
||||
#pragma once
|
||||
|
||||
#include <assimp/Importer.hpp>
|
||||
#include <assimp/scene.h>
|
||||
#include <vector>
|
||||
|
||||
#include "Assets/Asset Types/SHAnimationAsset.h"
|
||||
#include "Assets/Asset Types/SHMeshAsset.h"
|
||||
#include "Assets/SHAssetMacros.h"
|
||||
|
||||
namespace SHADE
|
||||
{
|
||||
class SHMeshCompiler
|
||||
{
|
||||
|
||||
using MeshVectorRef = std::vector<SHMeshAsset*>&;
|
||||
using AnimVectorRef = std::vector<SHAnimationAsset*>&;
|
||||
|
||||
static Assimp::Importer aiImporter;
|
||||
static void ProcessNode(aiNode const& node, aiScene const& scene, MeshVectorRef meshes) noexcept;
|
||||
static void ExtractAnimations(aiScene const& scene, AnimVectorRef anims) noexcept;
|
||||
static SHMeshAsset* ProcessMesh(aiMesh const& mesh) noexcept;
|
||||
|
||||
public:
|
||||
static void LoadFromFile(AssetPath path, MeshVectorRef meshes, AnimVectorRef anims) noexcept;
|
||||
static std::optional<AssetPath> CompileMeshBinary(SHMeshAsset const& asset, AssetPath path) noexcept;
|
||||
};
|
||||
}
|
|
@ -1,130 +0,0 @@
|
|||
/*************************************************************************//**
|
||||
* \file SHMeshLoader.cpp
|
||||
* \author Loh Xiao Qi
|
||||
* \date 30 September 2022
|
||||
* \brief Implementation for Mesh loader. Accounts for custom binary format
|
||||
* as well as GLTF file format.
|
||||
*
|
||||
*
|
||||
* Copyright (C) 2022 DigiPen Institute of Technology. Reproduction or
|
||||
* disclosure of this file or its contents without the prior written consent
|
||||
* of DigiPen Institute of Technology is prohibited.
|
||||
*****************************************************************************/
|
||||
#include "SHpch.h"
|
||||
#include "SHMeshLoader.h"
|
||||
#include <fstream>
|
||||
|
||||
namespace SHADE
|
||||
{
|
||||
void SHMeshLoader::LoadSHMesh(AssetPath path, SHMeshAsset& mesh) noexcept
|
||||
{
|
||||
std::ifstream file{ path.string(), std::ios::in | std::ios::binary };
|
||||
if (!file.is_open())
|
||||
{
|
||||
SHLOG_ERROR("Unable to open SHMesh File: {}", path.string());
|
||||
return;
|
||||
}
|
||||
|
||||
const std::string name{ path.stem().string() };
|
||||
|
||||
file.seekg(0);
|
||||
|
||||
uint32_t vertCount, indexCount;
|
||||
std::vector<SHVec3> vertPos, vertTan, vertNorm;
|
||||
std::vector<SHVec2> texCoord;
|
||||
std::vector<uint32_t> indices;
|
||||
|
||||
file.read(reinterpret_cast<char*>(&vertCount), sizeof(uint32_t));
|
||||
file.read(reinterpret_cast<char*>(&indexCount), sizeof(uint32_t));
|
||||
|
||||
auto const vertexVec3Byte{ sizeof(SHVec3) * vertCount };
|
||||
auto const vertexVec2Byte{ sizeof(SHVec2) * vertCount };
|
||||
|
||||
vertPos.resize(vertCount);
|
||||
vertTan.resize(vertCount);
|
||||
vertNorm.resize(vertCount);
|
||||
texCoord.resize(vertCount);
|
||||
indices.resize(indexCount);
|
||||
|
||||
file.read(reinterpret_cast<char *>(vertPos.data()), vertexVec3Byte);
|
||||
file.read(reinterpret_cast<char *>(vertTan.data()), vertexVec3Byte);
|
||||
file.read(reinterpret_cast<char *>(vertNorm.data()), vertexVec3Byte);
|
||||
file.read(reinterpret_cast<char *>(texCoord.data()), vertexVec2Byte);
|
||||
file.read(reinterpret_cast<char *>(indices.data()), sizeof(uint32_t) * indexCount);
|
||||
|
||||
mesh.compiled = true;
|
||||
mesh.changed = false;
|
||||
|
||||
mesh.header.indexCount = indexCount;
|
||||
mesh.header.vertexCount = vertCount;
|
||||
mesh.header.name = name;
|
||||
|
||||
mesh.vertexPosition = std::move(vertPos);
|
||||
mesh.vertexTangent = std::move(vertTan);
|
||||
mesh.vertexNormal = std::move(vertNorm);
|
||||
mesh.texCoords = std::move(texCoord);
|
||||
mesh.indices = std::move(indices);
|
||||
|
||||
file.close();
|
||||
}
|
||||
|
||||
SHAssetData* SHMeshLoader::Load(AssetPath path)
|
||||
{
|
||||
auto result = new SHMeshAsset();
|
||||
|
||||
LoadSHMesh(path, *result);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
void SHMeshLoader::Write(SHAssetData const* data, AssetPath path)
|
||||
{
|
||||
std::ofstream file{ path, std::ios::out | std::ios::binary | std::ios::trunc };
|
||||
if (!file.is_open())
|
||||
{
|
||||
SHLOG_ERROR("Unable to open file for writing mesh file: {}", path.string());
|
||||
}
|
||||
|
||||
auto asset = *dynamic_cast<SHMeshAsset const*>(data);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(&(asset.header.vertexCount)),
|
||||
sizeof(uint32_t)
|
||||
);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<const char*>(&(asset.header.indexCount)),
|
||||
sizeof(uint32_t)
|
||||
);
|
||||
|
||||
auto const vertexVec3Byte{ sizeof(SHVec3) * asset.header.vertexCount };
|
||||
auto const vertexVec2Byte{ sizeof(SHVec2) * asset.header.vertexCount };
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(asset.vertexPosition.data()),
|
||||
vertexVec3Byte
|
||||
);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(asset.vertexTangent.data()),
|
||||
vertexVec3Byte
|
||||
);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(asset.vertexNormal.data()),
|
||||
vertexVec3Byte
|
||||
);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(asset.texCoords.data()),
|
||||
vertexVec2Byte
|
||||
);
|
||||
|
||||
file.write(
|
||||
reinterpret_cast<char const*>(asset.indices.data()),
|
||||
sizeof(uint32_t) * asset.header.indexCount
|
||||
);
|
||||
|
||||
file.close();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,91 @@
|
|||
/*************************************************************************//**
|
||||
* \file SHModelLoader.cpp
|
||||
* \author Loh Xiao Qi
|
||||
* \date 30 September 2022
|
||||
* \brief Implementation for Mesh loader. Accounts for custom binary format
|
||||
* as well as GLTF file format.
|
||||
*
|
||||
*
|
||||
* Copyright (C) 2022 DigiPen Institute of Technology. Reproduction or
|
||||
* disclosure of this file or its contents without the prior written consent
|
||||
* of DigiPen Institute of Technology is prohibited.
|
||||
*****************************************************************************/
|
||||
#include "SHpch.h"
|
||||
#include "SHModelLoader.h"
|
||||
#include <fstream>
|
||||
|
||||
namespace SHADE
|
||||
{
|
||||
void SHModelLoader::ReadHeader(std::ifstream& file, SHMeshLoaderHeader& header) noexcept
|
||||
{
|
||||
file.read(
|
||||
reinterpret_cast<char*>(&header),
|
||||
sizeof(SHMeshLoaderHeader)
|
||||
);
|
||||
}
|
||||
|
||||
void SHModelLoader::ReadData(std::ifstream& file, SHMeshLoaderHeader const& header, SHMeshData& data) noexcept
|
||||
{
|
||||
auto const vertexVec3Byte{ sizeof(SHVec3) * header.vertexCount };
|
||||
auto const vertexVec2Byte{ sizeof(SHVec2) * header.vertexCount };
|
||||
|
||||
data.VertexPositions.resize(header.vertexCount);
|
||||
data.VertexTangents.resize(header.vertexCount);
|
||||
data.VertexNormals.resize(header.vertexCount);
|
||||
data.VertexTexCoords.resize(header.vertexCount);
|
||||
data.Indices.resize(header.indexCount);
|
||||
data.header.name.resize(header.charCount);
|
||||
|
||||
file.read(data.header.name.data(), header.charCount);
|
||||
file.read(reinterpret_cast<char*>(data.VertexPositions.data()), vertexVec3Byte);
|
||||
file.read(reinterpret_cast<char*>(data.VertexTangents.data()), vertexVec3Byte);
|
||||
file.read(reinterpret_cast<char*>(data.VertexNormals.data()), vertexVec3Byte);
|
||||
file.read(reinterpret_cast<char*>(data.VertexTexCoords.data()), vertexVec2Byte);
|
||||
file.read(reinterpret_cast<char*>(data.Indices.data()), sizeof(uint32_t) * header.indexCount);
|
||||
|
||||
data.header.vertexCount = header.vertexCount;
|
||||
data.header.indexCount = header.indexCount;
|
||||
}
|
||||
|
||||
void SHModelLoader::LoadSHMesh(AssetPath path, SHModelAsset& model) noexcept
|
||||
{
|
||||
std::ifstream file{ path.string(), std::ios::in | std::ios::binary };
|
||||
if (!file.is_open())
|
||||
{
|
||||
SHLOG_ERROR("Unable to open SHMesh File: {}", path.string());
|
||||
return;
|
||||
}
|
||||
|
||||
file.seekg(0);
|
||||
|
||||
file.read(
|
||||
reinterpret_cast<char*>(&model.header),
|
||||
sizeof(SHModelAssetHeader)
|
||||
);
|
||||
|
||||
std::vector<SHMeshLoaderHeader> headers(model.header.meshCount);
|
||||
model.subMeshes.resize(model.header.meshCount);
|
||||
|
||||
for (auto i{ 0 }; i < model.header.meshCount; ++i)
|
||||
{
|
||||
model.subMeshes[i] = new SHMeshData();
|
||||
ReadHeader(file, headers[i]);
|
||||
ReadData(file, headers[i], *model.subMeshes[i]);
|
||||
}
|
||||
file.close();
|
||||
}
|
||||
|
||||
SHAssetData* SHModelLoader::Load(AssetPath path)
|
||||
{
|
||||
auto result = new SHModelAsset();
|
||||
|
||||
LoadSHMesh(path, *result);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
void SHModelLoader::Write(SHAssetData const* data, AssetPath path)
|
||||
{
|
||||
|
||||
}
|
||||
}
|
|
@ -1,5 +1,5 @@
|
|||
/*************************************************************************//**
|
||||
* \file SHMeshLoader.h
|
||||
* \file SHModelLoader.h
|
||||
* \author Loh Xiao Qi
|
||||
* \date 30 September 2022
|
||||
* \brief Library to load gltf mesh files and custom binary format
|
||||
|
@ -10,14 +10,27 @@
|
|||
* of DigiPen Institute of Technology is prohibited.
|
||||
*****************************************************************************/
|
||||
#pragma once
|
||||
#include "Assets/Asset Types/SHMeshAsset.h"
|
||||
#include "Assets/Asset Types/SHModelAsset.h"
|
||||
#include "SHAssetLoader.h"
|
||||
#include <fstream>
|
||||
|
||||
namespace SHADE
|
||||
{
|
||||
struct SHMeshLoader : SHAssetLoader
|
||||
class SHModelLoader : public SHAssetLoader
|
||||
{
|
||||
void LoadSHMesh(AssetPath path, SHMeshAsset& meshes) noexcept;
|
||||
struct SHMeshLoaderHeader
|
||||
{
|
||||
uint32_t vertexCount;
|
||||
uint32_t indexCount;
|
||||
uint32_t charCount;
|
||||
};
|
||||
|
||||
|
||||
void ReadHeader(std::ifstream& file, SHMeshLoaderHeader& header) noexcept;
|
||||
void ReadData(std::ifstream& file, SHMeshLoaderHeader const& header, SHMeshData& data) noexcept;
|
||||
|
||||
public:
|
||||
void LoadSHMesh(AssetPath path, SHModelAsset& model) noexcept;
|
||||
SHAssetData* Load(AssetPath path) override;
|
||||
void Write(SHAssetData const* data, AssetPath path) override;
|
||||
};
|
|
@ -21,6 +21,11 @@ namespace SHADE
|
|||
AssetName name;
|
||||
AssetID id;
|
||||
AssetType type;
|
||||
AssetPath path;
|
||||
AssetPath path;
|
||||
bool isSubAsset;
|
||||
|
||||
std::vector<SHAsset*> subAssets;
|
||||
|
||||
AssetID parent;
|
||||
};
|
||||
}
|
|
@ -47,10 +47,11 @@ enum class AssetType : AssetTypeMeta
|
|||
SHADER,
|
||||
SHADER_BUILT_IN,
|
||||
TEXTURE,
|
||||
MESH,
|
||||
MODEL,
|
||||
SCENE,
|
||||
PREFAB,
|
||||
MATERIAL,
|
||||
MESH,
|
||||
MAX_COUNT
|
||||
};
|
||||
constexpr size_t TYPE_COUNT{ static_cast<size_t>(AssetType::MAX_COUNT) };
|
||||
|
@ -64,6 +65,9 @@ constexpr std::string_view ASSET_ROOT {"../../Assets"};
|
|||
constexpr std::string_view BUILT_IN_ASSET_ROOT{ "../../Built_In" };
|
||||
#endif
|
||||
|
||||
// COMPILER PATHS
|
||||
constexpr std::string_view MODEL_COMPILER_EXE{ "ModelCompiler.exe" };
|
||||
|
||||
// INTERNAL ASSET PATHS
|
||||
constexpr std::string_view SCENE_FOLDER{ "/Scenes/" };
|
||||
constexpr std::string_view PREFAB_FOLDER{ "/Prefabs/" };
|
||||
|
@ -81,7 +85,7 @@ constexpr std::string_view SCENE_EXTENSION {".shade"};
|
|||
constexpr std::string_view PREFAB_EXTENSION {".shprefab"};
|
||||
constexpr std::string_view MATERIAL_EXTENSION {".shmat"};
|
||||
constexpr std::string_view TEXTURE_EXTENSION {".shtex"};
|
||||
constexpr std::string_view MESH_EXTENSION {".shmesh"};
|
||||
constexpr std::string_view MODEL_EXTENSION {".shmodel"};
|
||||
|
||||
constexpr std::string_view EXTENSIONS[] = {
|
||||
AUDIO_EXTENSION,
|
||||
|
@ -89,7 +93,7 @@ constexpr std::string_view EXTENSIONS[] = {
|
|||
SHADER_BUILT_IN_EXTENSION,
|
||||
MATERIAL_EXTENSION,
|
||||
TEXTURE_EXTENSION,
|
||||
MESH_EXTENSION,
|
||||
MODEL_EXTENSION,
|
||||
SCRIPT_EXTENSION,
|
||||
SCENE_EXTENSION,
|
||||
PREFAB_EXTENSION,
|
||||
|
|
|
@ -11,15 +11,17 @@
|
|||
#include <random>
|
||||
#include <chrono>
|
||||
#include <ranges>
|
||||
#include <cstdlib>
|
||||
|
||||
#include "SHAssetManager.h"
|
||||
#include "SHAssetMetaHandler.h"
|
||||
|
||||
#include "Libraries/Loaders/SHMeshLoader.h"
|
||||
#include "Libraries/Loaders/SHModelLoader.h"
|
||||
#include "Libraries/Loaders/SHTextureLoader.h"
|
||||
#include "Libraries/Loaders/SHShaderSourceLoader.h"
|
||||
#include "Libraries/Loaders/SHTextBasedLoader.h"
|
||||
|
||||
#include "Libraries/Compilers/SHMeshCompiler.h"
|
||||
//#include "Libraries/Compilers/SHMeshCompiler.h"
|
||||
#include "Libraries/Compilers/SHTextureCompiler.h"
|
||||
#include "Libraries/Compilers/SHShaderSourceCompiler.h"
|
||||
|
||||
|
@ -186,7 +188,8 @@ namespace SHADE
|
|||
name,
|
||||
id,
|
||||
type,
|
||||
newPath
|
||||
newPath,
|
||||
false
|
||||
};
|
||||
|
||||
assetCollection.insert({
|
||||
|
@ -195,7 +198,8 @@ namespace SHADE
|
|||
name,
|
||||
id,
|
||||
type,
|
||||
newPath
|
||||
newPath,
|
||||
false
|
||||
)
|
||||
});
|
||||
|
||||
|
@ -334,25 +338,32 @@ namespace SHADE
|
|||
return result;
|
||||
}
|
||||
|
||||
AssetID SHAssetManager::CompileAsset(AssetPath const& path) noexcept
|
||||
void SHAssetManager::CompileAsset(AssetPath const& path) noexcept
|
||||
{
|
||||
SHAsset newAsset
|
||||
{
|
||||
.name = path.stem().string()
|
||||
};
|
||||
|
||||
if (!std::filesystem::exists(path))
|
||||
{
|
||||
SHLOG_ERROR("Path provided does not point to a file: {}", path.string());
|
||||
return;
|
||||
}
|
||||
AssetPath newPath;
|
||||
auto const ext{ path.extension().string() };
|
||||
if (ext == GLSL_EXTENSION.data())
|
||||
{
|
||||
newAsset.path = SHShaderSourceCompiler::LoadAndCompileShader(path).value();
|
||||
newAsset.id = GenerateAssetID(AssetType::SHADER_BUILT_IN);
|
||||
newAsset.type = AssetType::SHADER_BUILT_IN;
|
||||
newPath = SHShaderSourceCompiler::LoadAndCompileShader(path).value();
|
||||
}
|
||||
else if (ext == GLTF_EXTENSION.data() || ext == FBX_EXTENSION.data())
|
||||
{
|
||||
std::string command = MODEL_COMPILER_EXE.data();
|
||||
command += " " + path.string();
|
||||
std::system(command.c_str());
|
||||
|
||||
assetCollection.insert({ newAsset.id, newAsset });
|
||||
SHAssetMetaHandler::WriteMetaData(newAsset);
|
||||
std::string modelPath = path.string().substr(0, path.string().find_last_of('.'));
|
||||
modelPath += MODEL_EXTENSION;
|
||||
newPath = modelPath;
|
||||
|
||||
GenerateNewMeta(newPath);
|
||||
}
|
||||
|
||||
return newAsset.id;
|
||||
}
|
||||
|
||||
FolderPointer SHAssetManager::GetRootFolder() noexcept
|
||||
|
@ -405,46 +416,28 @@ namespace SHADE
|
|||
|
||||
for (auto const& path : paths)
|
||||
{
|
||||
SHAsset newAsset
|
||||
{
|
||||
.name = path.stem().string()
|
||||
};
|
||||
|
||||
AssetPath newPath;
|
||||
auto const ext{ path.extension().string() };
|
||||
if (ext == GLSL_EXTENSION.data())
|
||||
{
|
||||
newAsset.path = SHShaderSourceCompiler::LoadAndCompileShader(path).value();
|
||||
newAsset.id = GenerateAssetID(AssetType::SHADER_BUILT_IN);
|
||||
newAsset.type = AssetType::SHADER_BUILT_IN;
|
||||
newPath = SHShaderSourceCompiler::LoadAndCompileShader(path).value();
|
||||
}
|
||||
else if (ext == DDS_EXTENSION.data())
|
||||
{
|
||||
newAsset.path = SHTextureCompiler::CompileTextureAsset(path).value();
|
||||
newAsset.id = GenerateAssetID(AssetType::TEXTURE);
|
||||
newAsset.type = AssetType::TEXTURE;
|
||||
newPath = SHTextureCompiler::CompileTextureAsset(path).value();
|
||||
}
|
||||
else if (ext == GLTF_EXTENSION.data() || ext == FBX_EXTENSION.data())
|
||||
{
|
||||
std::vector<SHMeshAsset*> meshes;
|
||||
std::vector<SHAnimationAsset*> anims;
|
||||
SHMeshCompiler::LoadFromFile(path, meshes, anims);
|
||||
std::string command = MODEL_COMPILER_EXE.data();
|
||||
command += " " + path.string();
|
||||
std::system(command.c_str());
|
||||
|
||||
for (auto const& mesh : meshes)
|
||||
{
|
||||
SHAsset meshAsset{
|
||||
.name = mesh->header.name
|
||||
};
|
||||
meshAsset.path = SHMeshCompiler::CompileMeshBinary(*mesh, path).value();
|
||||
meshAsset.id = GenerateAssetID(AssetType::MESH);
|
||||
meshAsset.type = AssetType::MESH;
|
||||
assetCollection.insert({ meshAsset.id, meshAsset });
|
||||
SHAssetMetaHandler::WriteMetaData(meshAsset);
|
||||
}
|
||||
continue;
|
||||
std::string modelPath = path.string().substr(0, path.string().find_last_of('.'));
|
||||
modelPath += MODEL_EXTENSION;
|
||||
newPath = modelPath;
|
||||
}
|
||||
|
||||
assetCollection.insert({ newAsset.id, newAsset });
|
||||
SHAssetMetaHandler::WriteMetaData(newAsset);
|
||||
GenerateNewMeta(newPath);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -459,10 +452,11 @@ namespace SHADE
|
|||
loaders[static_cast<size_t>(AssetType::SHADER)] = dynamic_cast<SHAssetLoader*>(new SHShaderSourceLoader());
|
||||
loaders[static_cast<size_t>(AssetType::SHADER_BUILT_IN)] = loaders[static_cast<size_t>(AssetType::SHADER)];
|
||||
loaders[static_cast<size_t>(AssetType::TEXTURE)] = dynamic_cast<SHAssetLoader*>(new SHTextureLoader());
|
||||
loaders[static_cast<size_t>(AssetType::MESH)] = dynamic_cast<SHAssetLoader*>(new SHMeshLoader());
|
||||
loaders[static_cast<size_t>(AssetType::MODEL)] = dynamic_cast<SHAssetLoader*>(new SHModelLoader());
|
||||
loaders[static_cast<size_t>(AssetType::SCENE)] = dynamic_cast<SHAssetLoader*>(new SHTextBasedLoader());
|
||||
loaders[static_cast<size_t>(AssetType::PREFAB)] = loaders[static_cast<size_t>(AssetType::SCENE)];
|
||||
loaders[static_cast<size_t>(AssetType::MATERIAL)] = loaders[static_cast<size_t>(AssetType::SCENE)];
|
||||
loaders[static_cast<size_t>(AssetType::MESH)] = nullptr;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
|
@ -470,9 +464,9 @@ namespace SHADE
|
|||
****************************************************************************/
|
||||
void SHAssetManager::Load() noexcept
|
||||
{
|
||||
//CompileAll();
|
||||
BuildAssetCollection();
|
||||
InitLoaders();
|
||||
//CompileAll();
|
||||
//LoadAllData();
|
||||
}
|
||||
|
||||
|
@ -490,8 +484,12 @@ namespace SHADE
|
|||
|
||||
SHAssetData* SHAssetManager::LoadData(SHAsset const& asset) noexcept
|
||||
{
|
||||
SHAssetData* data = loaders[static_cast<size_t>(asset.type)]->Load(asset.path);
|
||||
if (asset.isSubAsset)
|
||||
{
|
||||
return LoadSubData(asset);
|
||||
}
|
||||
|
||||
SHAssetData* data = loaders[static_cast<size_t>(asset.type)]->Load(asset.path);
|
||||
if (data == nullptr)
|
||||
{
|
||||
SHLOG_ERROR("Unable to load asset into memory: {}\n", asset.path.string());
|
||||
|
@ -504,8 +502,120 @@ namespace SHADE
|
|||
return data;
|
||||
}
|
||||
|
||||
SHAssetData* SHAssetManager::LoadSubData(SHAsset const& asset) noexcept
|
||||
{
|
||||
auto const& parent = assetCollection[asset.parent];
|
||||
auto parentData = loaders[static_cast<size_t>(parent.type)]->Load(parent.path);
|
||||
|
||||
if (parentData == nullptr)
|
||||
{
|
||||
SHLOG_ERROR("Unable to load asset into memory: {}\n", parent.path.string());
|
||||
}
|
||||
else
|
||||
{
|
||||
assetData.emplace(parent.id, parentData);
|
||||
if (parent.type == AssetType::MODEL)
|
||||
{
|
||||
auto parentModel = reinterpret_cast<SHModelAsset*>(parentData);
|
||||
for (auto i {0}; i < parent.subAssets.size(); ++i)
|
||||
{
|
||||
assetData.emplace(
|
||||
parent.subAssets[i]->id,
|
||||
parentModel->subMeshes[i]
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
return assetData[asset.id];
|
||||
}
|
||||
|
||||
return parentData;
|
||||
}
|
||||
|
||||
void SHAssetManager::LoadNewData(AssetPath path) noexcept
|
||||
{
|
||||
}
|
||||
|
||||
void SHAssetManager::GenerateNewMeta(AssetPath path) noexcept
|
||||
{
|
||||
auto const ext = path.extension().string();
|
||||
if (ext == SHADER_BUILT_IN_EXTENSION.data())
|
||||
{
|
||||
SHAsset newAsset{
|
||||
path.stem().string(),
|
||||
GenerateAssetID(AssetType::SHADER_BUILT_IN),
|
||||
AssetType::SHADER_BUILT_IN,
|
||||
path,
|
||||
false
|
||||
};
|
||||
|
||||
assetCollection.emplace(newAsset.id, newAsset);
|
||||
SHAssetMetaHandler::WriteMetaData(newAsset);
|
||||
}
|
||||
else if (ext == TEXTURE_EXTENSION.data())
|
||||
{
|
||||
SHAsset newAsset{
|
||||
path.stem().string(),
|
||||
GenerateAssetID(AssetType::SHADER_BUILT_IN),
|
||||
AssetType::SHADER_BUILT_IN,
|
||||
path,
|
||||
false
|
||||
};
|
||||
|
||||
assetCollection.emplace(newAsset.id, newAsset);
|
||||
SHAssetMetaHandler::WriteMetaData(newAsset);
|
||||
}
|
||||
else if (ext == MODEL_EXTENSION)
|
||||
{
|
||||
SHAsset newAsset{
|
||||
path.stem().string(),
|
||||
GenerateAssetID(AssetType::MODEL),
|
||||
AssetType::MODEL,
|
||||
path,
|
||||
false
|
||||
};
|
||||
|
||||
assetCollection.emplace(newAsset.id, newAsset);
|
||||
|
||||
SHModelAsset* const data = reinterpret_cast<SHModelAsset*>(LoadData(newAsset));
|
||||
assetData.emplace(newAsset.id, data);
|
||||
for(auto const& subMesh : data->subMeshes)
|
||||
{
|
||||
SHAsset subAsset{
|
||||
.name = subMesh->header.name,
|
||||
.id = GenerateAssetID(AssetType::MESH),
|
||||
.type = AssetType::MESH,
|
||||
.isSubAsset = true,
|
||||
.parent = newAsset.id
|
||||
};
|
||||
|
||||
assetCollection.emplace(subAsset.id, subAsset);
|
||||
assetCollection[newAsset.id].subAssets.push_back(&assetCollection[subAsset.id]);
|
||||
|
||||
assetData.emplace(subAsset.id, subMesh);
|
||||
}
|
||||
|
||||
SHAssetMetaHandler::WriteMetaData(assetCollection[newAsset.id]);
|
||||
}
|
||||
}
|
||||
|
||||
void SHAssetManager::BuildAssetCollection() noexcept
|
||||
{
|
||||
SHFileSystem::BuildDirectory(ASSET_ROOT.data(), folderRoot, assetCollection);
|
||||
|
||||
for (auto& asset : std::ranges::views::values(assetCollection))
|
||||
{
|
||||
if (!asset.subAssets.empty())
|
||||
{
|
||||
// Add subasset data into map, replace pointer and free heap memory
|
||||
for (auto i{ 0 }; i < asset.subAssets.size(); ++i)
|
||||
{
|
||||
auto const id = asset.subAssets[i]->id;
|
||||
assetCollection[id] = *asset.subAssets[i];
|
||||
delete asset.subAssets[i];
|
||||
asset.subAssets[i] = &assetCollection[id];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -87,7 +87,7 @@ namespace SHADE
|
|||
static std::vector<SHAssetData const*> GetAllDataOfType(AssetType type) noexcept;
|
||||
static std::vector<SHAsset> GetAllRecordOfType(AssetType type) noexcept;
|
||||
|
||||
static AssetID CompileAsset(AssetPath const& path) noexcept;
|
||||
static void CompileAsset(AssetPath const& path) noexcept;
|
||||
|
||||
static FolderPointer GetRootFolder() noexcept;
|
||||
|
||||
|
@ -95,7 +95,11 @@ namespace SHADE
|
|||
|
||||
static void InitLoaders() noexcept;
|
||||
static void LoadAllData() noexcept;
|
||||
static SHAssetData* LoadData(SHAsset const& asset) noexcept;
|
||||
static SHAssetData* LoadData(SHAsset const& asset) noexcept;
|
||||
static SHAssetData* LoadSubData(SHAsset const& asset) noexcept;
|
||||
static void LoadNewData(AssetPath path) noexcept;
|
||||
static void GenerateNewMeta(AssetPath path) noexcept;
|
||||
|
||||
inline static void BuildAssetCollection() noexcept;
|
||||
|
||||
static bool IsRecognised(char const*) noexcept;
|
||||
|
|
|
@ -9,7 +9,6 @@
|
|||
******************************************************************************/
|
||||
#include "SHpch.h"
|
||||
#include "SHAssetMetaHandler.h"
|
||||
#include <fstream>
|
||||
#include <sstream>
|
||||
|
||||
namespace SHADE
|
||||
|
@ -21,11 +20,15 @@ namespace SHADE
|
|||
* \brief Helper function to retrieve field value from meta data file
|
||||
* for processing
|
||||
****************************************************************************/
|
||||
void GetFieldValue(std::ifstream& file, std::string& line) noexcept
|
||||
bool GetFieldValue(std::ifstream& file, std::string& line) noexcept
|
||||
{
|
||||
line = "";
|
||||
std::getline(file, line);
|
||||
line = line.substr(line.find_last_of(':') + 2, line.length());
|
||||
if (std::getline(file, line))
|
||||
{
|
||||
line = line.substr(line.find_last_of(':') + 2, line.length());
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
|
@ -66,7 +69,8 @@ namespace SHADE
|
|||
std::ifstream metaFile{ path.string(), std::ios_base::in };
|
||||
if (!metaFile.is_open())
|
||||
{
|
||||
// Error unable to open
|
||||
SHLOG_ERROR("Unable to open meta file: {}", path.string());
|
||||
return {};
|
||||
}
|
||||
|
||||
std::string line;
|
||||
|
@ -93,6 +97,43 @@ namespace SHADE
|
|||
typeStream >> type;
|
||||
meta.type = static_cast<AssetType>(type);
|
||||
|
||||
meta.isSubAsset = false;
|
||||
|
||||
// Burn Line
|
||||
if (std::getline(metaFile, line))
|
||||
{
|
||||
// Name Line
|
||||
while(GetFieldValue(metaFile, line))
|
||||
{
|
||||
auto subAsset = new SHAsset();
|
||||
|
||||
// Get resource name
|
||||
std::stringstream nameStream{ line };
|
||||
AssetName name;
|
||||
nameStream >> name;
|
||||
subAsset->name = name;
|
||||
|
||||
// Get resource id
|
||||
GetFieldValue(metaFile, line);
|
||||
std::stringstream idStream{ line };
|
||||
AssetID id;
|
||||
idStream >> id;
|
||||
subAsset->id = id;
|
||||
|
||||
// Get resource type
|
||||
GetFieldValue(metaFile, line);
|
||||
std::stringstream typeStream{ line };
|
||||
AssetTypeMeta type;
|
||||
typeStream >> type;
|
||||
subAsset->type = static_cast<AssetType>(type);
|
||||
|
||||
subAsset->isSubAsset = true;
|
||||
subAsset->parent = meta.id;
|
||||
|
||||
meta.subAssets.push_back(subAsset);
|
||||
}
|
||||
}
|
||||
|
||||
metaFile.close();
|
||||
|
||||
meta.path = path.parent_path().string() + "/" + path.stem().string();
|
||||
|
@ -108,6 +149,12 @@ namespace SHADE
|
|||
****************************************************************************/
|
||||
void SHAssetMetaHandler::WriteMetaData(SHAsset const& meta) noexcept
|
||||
{
|
||||
if (meta.isSubAsset)
|
||||
{
|
||||
SHLOG_WARNING("Cannot write subasset meta: {}", meta.name);
|
||||
return;
|
||||
}
|
||||
|
||||
//TODO: Write into binary eventually
|
||||
std::string path{ meta.path.string() };
|
||||
path.append(META_EXTENSION);
|
||||
|
@ -124,7 +171,23 @@ namespace SHADE
|
|||
metaFile << "ID: " << meta.id << "\n";
|
||||
metaFile << "Type: " << static_cast<AssetTypeMeta>(meta.type) << std::endl;
|
||||
|
||||
if (!meta.subAssets.empty())
|
||||
{
|
||||
metaFile << "Sub Assets:\n";
|
||||
|
||||
for (auto const& subAsset : meta.subAssets)
|
||||
{
|
||||
WriteSubAssetMeta(metaFile, *subAsset);
|
||||
}
|
||||
}
|
||||
|
||||
metaFile.close();
|
||||
}
|
||||
|
||||
void SHAssetMetaHandler::WriteSubAssetMeta(std::ofstream& metaFile, SHAsset const& subAsset) noexcept
|
||||
{
|
||||
metaFile << "Name: " << subAsset.name << "\n";
|
||||
metaFile << "ID: " << subAsset.id << "\n";
|
||||
metaFile << "Type: " << static_cast<AssetTypeMeta>(subAsset.type) << std::endl;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
|
||||
#include "SHAssetMacros.h"
|
||||
#include "SHAsset.h"
|
||||
#include <fstream>
|
||||
|
||||
namespace SHADE
|
||||
{
|
||||
|
@ -45,6 +46,8 @@ namespace SHADE
|
|||
* \brief Writes meta data into text file
|
||||
****************************************************************************/
|
||||
static void WriteMetaData(SHAsset const&) noexcept;
|
||||
|
||||
static void WriteSubAssetMeta(std::ofstream&, SHAsset const&) noexcept;
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
@ -14,7 +14,7 @@ of DigiPen Institute of Technology is prohibited.
|
|||
// STL Includes
|
||||
#include <algorithm>
|
||||
// Project Includes
|
||||
#include "../Meshes/SHMeshData.h"
|
||||
#include "Assets/Asset Types/SHModelAsset.h"
|
||||
#include "../Meshes/SHPrimitiveGenerator.h"
|
||||
#include "ECS_Base/Managers/SHSystemManager.h"
|
||||
#include "SHGraphicsSystem.h"
|
||||
|
|
|
@ -1,36 +0,0 @@
|
|||
/************************************************************************************//*!
|
||||
\file SHPrimitiveGenerator.h
|
||||
\author Tng Kah Wei, kahwei.tng, 390009620
|
||||
\par email: kahwei.tng\@digipen.edu
|
||||
\date Sep 18, 2022
|
||||
\brief Contains the static class definition of SHPrimitiveGenerator.
|
||||
|
||||
Copyright (C) 2022 DigiPen Institute of Technology.
|
||||
Reproduction or disclosure of this file or its contents without the prior written consent
|
||||
of DigiPen Institute of Technology is prohibited.
|
||||
*//*************************************************************************************/
|
||||
#pragma once
|
||||
|
||||
// STL Includes
|
||||
#include <vector>
|
||||
// Project Includes
|
||||
#include "Math/SHMath.h"
|
||||
#include "Graphics/MiddleEnd/Interface/SHMeshLibrary.h"
|
||||
|
||||
namespace SHADE
|
||||
{
|
||||
/*************************************************************************************/
|
||||
/*!
|
||||
\brief
|
||||
Static class that contains functions for generating 3D primitives.
|
||||
*/
|
||||
/*************************************************************************************/
|
||||
struct SHMeshData
|
||||
{
|
||||
std::vector<SHMesh::VertexPosition> VertexPositions;
|
||||
std::vector<SHMesh::VertexTexCoord> VertexTexCoords;
|
||||
std::vector<SHMesh::VertexTangent> VertexTangents;
|
||||
std::vector<SHMesh::VertexNormal> VertexNormals;
|
||||
std::vector<SHMesh::Index> Indices;
|
||||
};
|
||||
}
|
|
@ -288,7 +288,7 @@ namespace SHADE
|
|||
{
|
||||
return meshLibrary.AddMesh
|
||||
(
|
||||
static_cast<uint32_t>(meshData.VertexPositions.size()),
|
||||
static_cast<uint32_t>(meshData.VertexPositions.size()),
|
||||
meshData.VertexPositions.data(),
|
||||
meshData.VertexTexCoords.data(),
|
||||
meshData.VertexTangents.data(),
|
||||
|
@ -302,12 +302,12 @@ namespace SHADE
|
|||
{
|
||||
return gfxSystem.AddMesh
|
||||
(
|
||||
static_cast<uint32_t>(meshData.VertexPositions.size()),
|
||||
static_cast<uint32_t>(meshData.VertexPositions.size()),
|
||||
meshData.VertexPositions.data(),
|
||||
meshData.VertexTexCoords.data(),
|
||||
meshData.VertexTangents.data(),
|
||||
meshData.VertexNormals.data(),
|
||||
static_cast<uint32_t>(meshData.Indices.size()),
|
||||
static_cast<uint32_t>(meshData.Indices.size()),
|
||||
meshData.Indices.data()
|
||||
);
|
||||
}
|
||||
|
|
|
@ -13,7 +13,8 @@ of DigiPen Institute of Technology is prohibited.
|
|||
|
||||
// Project Includes
|
||||
#include "Math/SHMath.h"
|
||||
#include "SHMeshData.h"
|
||||
#include "Assets/Asset Types/SHModelAsset.h"
|
||||
#include "Graphics/MiddleEnd/Interface/SHMeshLibrary.h"
|
||||
#include "SH_API.h"
|
||||
|
||||
namespace SHADE
|
||||
|
|
|
@ -19,7 +19,7 @@ namespace SHADE { class SHMaterial; }
|
|||
#include "SH_API.h"
|
||||
#include "SHResourceLibrary.h"
|
||||
#include "Assets/SHAssetMacros.h"
|
||||
#include "Assets/Asset Types/SHMeshAsset.h"
|
||||
#include "Assets/Asset Types/SHModelAsset.h"
|
||||
#include "Assets/Asset Types/SHTextureAsset.h"
|
||||
#include "Assets/Asset Types/SHShaderAsset.h"
|
||||
#include "Graphics/Shaders/SHVkShaderModule.h"
|
||||
|
@ -36,7 +36,7 @@ namespace SHADE
|
|||
/// </summary>
|
||||
template<typename T = void>
|
||||
struct SHResourceLoader { using AssetType = void; };
|
||||
template<> struct SHResourceLoader<SHMesh> { using AssetType = SHMeshAsset; };
|
||||
template<> struct SHResourceLoader<SHMesh> { using AssetType = SHMeshData; };
|
||||
template<> struct SHResourceLoader<SHTexture> { using AssetType = SHTextureAsset; };
|
||||
template<> struct SHResourceLoader<SHVkShaderModule> { using AssetType = SHShaderAsset; };
|
||||
template<> struct SHResourceLoader<SHMaterialSpec> { using AssetType = SHMaterialAsset; };
|
||||
|
|
|
@ -180,13 +180,13 @@ namespace SHADE
|
|||
|
||||
return gfxSystem->AddMesh
|
||||
(
|
||||
assetData.vertexPosition.size(),
|
||||
assetData.vertexPosition.data(),
|
||||
assetData.texCoords.data(),
|
||||
assetData.vertexTangent.data(),
|
||||
assetData.vertexNormal.data(),
|
||||
assetData.indices.size(),
|
||||
assetData.indices.data()
|
||||
assetData.VertexPositions.size(),
|
||||
assetData.VertexPositions.data(),
|
||||
assetData.VertexTexCoords.data(),
|
||||
assetData.VertexTangents.data(),
|
||||
assetData.VertexNormals.data(),
|
||||
assetData.Indices.size(),
|
||||
assetData.Indices.data()
|
||||
);
|
||||
}
|
||||
// Textures
|
||||
|
|
|
@ -30,4 +30,5 @@ workspace "SHADE"
|
|||
--include "Dependencies/tracy"
|
||||
include "Dependencies/yamlcpp"
|
||||
include "Dependencies/reactphysics3d"
|
||||
include "Dependencies/ModelCompiler"
|
||||
group ""
|
||||
|
|
Loading…
Reference in New Issue