Implement initial Unity-style asset library cache

This commit is contained in:
2026-04-02 03:03:36 +08:00
parent 619856ab22
commit 4c167bec0e
29 changed files with 4818 additions and 73 deletions

View File

@@ -1,10 +1,12 @@
#include <XCEngine/Resources/Material/MaterialLoader.h>
#include <XCEngine/Resources/BuiltinResources.h>
#include <XCEngine/Core/Asset/ResourceManager.h>
#include <XCEngine/Core/Asset/ResourceTypes.h>
#include <XCEngine/Resources/Shader/ShaderLoader.h>
#include <cctype>
#include <cstdlib>
#include <filesystem>
#include <string>
namespace XCEngine {
@@ -531,6 +533,24 @@ ResourceHandle<Shader> LoadShaderHandle(const Containers::String& shaderPath) {
return ResourceHandle<Shader>(static_cast<Shader*>(shaderResult.resource));
}
bool MaterialFileExists(const Containers::String& path) {
const std::filesystem::path inputPath(path.CStr());
if (std::filesystem::exists(inputPath)) {
return true;
}
if (inputPath.is_absolute()) {
return false;
}
const Containers::String& resourceRoot = ResourceManager::Get().GetResourceRoot();
if (resourceRoot.Empty()) {
return false;
}
return std::filesystem::exists(std::filesystem::path(resourceRoot.CStr()) / inputPath);
}
} // namespace
MaterialLoader::MaterialLoader() = default;
@@ -546,6 +566,10 @@ Containers::Array<Containers::String> MaterialLoader::GetSupportedExtensions() c
}
bool MaterialLoader::CanLoad(const Containers::String& path) const {
if (IsBuiltinMaterialPath(path)) {
return true;
}
Containers::String ext = GetExtension(path);
return ext == "mat" || ext == "material" || ext == "json";
}
@@ -553,17 +577,22 @@ bool MaterialLoader::CanLoad(const Containers::String& path) const {
LoadResult MaterialLoader::Load(const Containers::String& path, const ImportSettings* settings) {
(void)settings;
Containers::Array<Core::uint8> data = ReadFileData(path);
if (data.Empty()) {
return LoadResult("Failed to read material file: " + path);
if (IsBuiltinMaterialPath(path)) {
return CreateBuiltinMaterialResource(path);
}
Containers::Array<Core::uint8> data = ReadFileData(path);
Material* material = new Material();
material->m_path = path;
material->m_name = path;
material->m_guid = ResourceGUID::Generate(path);
if (!ParseMaterialData(data, material)) {
if (data.Empty() && !MaterialFileExists(path)) {
delete material;
return LoadResult("Failed to read material file: " + path);
}
if (!data.Empty() && !ParseMaterialData(data, material)) {
delete material;
return LoadResult("Failed to parse material file: " + path);
}