Dawn/src/dawn/asset/loader/SceneLoader.cpp
2024-12-02 20:00:54 -06:00

121 lines
3.2 KiB
C++

// Copyright (c) 2024 Dominic Masters
//
// This software is released under the MIT License.
// https://opensource.org/licenses/MIT
#include "SceneLoader.hpp"
#include "game/Game.hpp"
#include "assert/assert.hpp"
#include "scene/Scene.hpp"
#include "component/SceneComponentRegistry.hpp"
using namespace Dawn;
const std::string SceneLoader::ASSET_TYPE = "scene";
SceneLoader::SceneLoader(
const std::shared_ptr<AssetManager> assetManager,
const std::string name
) :
LoaderForSceneItems(assetManager, name),
state(SceneLoaderState::INITIAL)
{
this->typetest = this->getAssetType();
}
void SceneLoader::updateAsync() {
switch(this->state) {
case SceneLoaderState::INITIAL:
this->jsonLoader = getAssetManager()->get<JSONLoader>(this->name);
this->state = SceneLoaderState::LOADING_JSON;
break;
case SceneLoaderState::LOADING_JSON:
assertNotNull(this->jsonLoader, "JSON Loader is NULL?");
if(!this->jsonLoader->loaded) return;
this->setupDependencies();
this->state = SceneLoaderState::LOADING_DEPENDENCIES;
break;
case SceneLoaderState::LOADING_DEPENDENCIES:
assertTrue(this->jsonLoader->loaded, "JSON loader not loaded?");
// Check if all dependencies are loaded.
for(auto &asset : ctx.assets) {
if(!asset.second->loaded) return;
}
ctx.scene = std::make_shared<Scene>(this->getAssetManager()->getGame());
this->state = SceneLoaderState::PENDING_STAGE;
break;
default:
break;
}
}
void SceneLoader::updateSync() {
if(this->state != SceneLoaderState::PENDING_STAGE) return;
assertTrue(this->jsonLoader->loaded, "JSON loader not loaded?");
auto &data = this->jsonLoader->data;
if(data.contains("items")) {
// Create the scene items
for(auto &item : data["items"].items()) {
auto &itemName = item.key();
auto &itemData = item.value();
auto sceneItem = ctx.scene->createSceneItem();
ctx.items[itemName] = sceneItem;
}
// Add components to each scene item
for(auto &item : data["items"].items()) {
auto &itemName = item.key();
auto &itemData = item.value();
auto sceneItem = ctx.items[itemName];
ctx.data = itemData;
sceneItem->load(ctx);
if(itemData.contains("components")) {
for(auto &cmpItem : itemData["components"].items()) {
auto &cmpName = cmpItem.key();
auto &cmpData = cmpItem.value();
assertTrue(
cmpData.contains("type"),
"Component missing type in %s",
cmpName.c_str()
);
auto cmpType = cmpData["type"].get<std::string>();
auto cmp = SceneComponentRegistry::createComponent(
cmpType, sceneItem
);
ctx.data = cmpData;
ctx.components[cmpName] = cmp;
cmp->load(ctx);
}
}
}
}
this->jsonLoader = nullptr;
this->state = SceneLoaderState::DONE;
this->loaded = true;
ctx.assets.clear();
ctx.components.clear();
ctx.items.clear();
ctx.data = {};
}
std::string SceneLoader::getAssetType() const {
return SceneLoader::ASSET_TYPE;
}
std::shared_ptr<Scene> SceneLoader::getScene() {
return ctx.scene;
}
SceneLoader::~SceneLoader() {
ctx = {};
jsonLoader = nullptr;
}