From 20e3a961f951c3845622a176f0ef1630a5cf9eb6 Mon Sep 17 00:00:00 2001 From: MihailRis Date: Sun, 27 Apr 2025 18:21:56 +0300 Subject: [PATCH] add BlockModel struct --- src/assets/AssetsLoader.cpp | 8 ++++---- src/content/ContentBuilder.cpp | 2 +- src/content/loading/BlockLoader.cpp | 23 ++++++++++++---------- src/core_defs.cpp | 2 +- src/frontend/ContentGfxCache.cpp | 6 +++--- src/graphics/render/BlockWrapsRenderer.cpp | 2 +- src/graphics/render/BlocksPreview.cpp | 2 +- src/graphics/render/BlocksRenderer.cpp | 4 ++-- src/graphics/render/ModelsGenerator.cpp | 14 ++++++------- src/logic/scripting/lua/libs/libblock.cpp | 2 +- src/voxels/Block.cpp | 1 - src/voxels/Block.hpp | 19 +++++++++++------- 12 files changed, 46 insertions(+), 39 deletions(-) diff --git a/src/assets/AssetsLoader.cpp b/src/assets/AssetsLoader.cpp index cdbb28e2..80c1186d 100644 --- a/src/assets/AssetsLoader.cpp +++ b/src/assets/AssetsLoader.cpp @@ -257,12 +257,12 @@ void AssetsLoader::addDefaults(AssetsLoader& loader, const Content* content) { } } for (const auto& [_, def] : content->blocks.getDefs()) { - if (!def->modelName.empty() && - def->modelName.find(':') == std::string::npos) { + if (!def->model.name.empty() && + def->model.name.find(':') == std::string::npos) { loader.add( AssetType::MODEL, - MODELS_FOLDER + "/" + def->modelName, - def->modelName + MODELS_FOLDER + "/" + def->model.name, + def->model.name ); } } diff --git a/src/content/ContentBuilder.cpp b/src/content/ContentBuilder.cpp index d295e252..c8b599ea 100644 --- a/src/content/ContentBuilder.cpp +++ b/src/content/ContentBuilder.cpp @@ -28,7 +28,7 @@ std::unique_ptr ContentBuilder::build() { // Generating runtime info def.rt.id = blockDefsIndices.size(); def.rt.emissive = *reinterpret_cast(def.emission); - def.rt.solid = def.model == BlockModelType::BLOCK; + def.rt.solid = def.model.type == BlockModelType::BLOCK; def.rt.extended = def.size.x > 1 || def.size.y > 1 || def.size.z > 1; const float EPSILON = 0.01f; diff --git a/src/content/loading/BlockLoader.cpp b/src/content/loading/BlockLoader.cpp index 8f92cbe8..5e3b09be 100644 --- a/src/content/loading/BlockLoader.cpp +++ b/src/content/loading/BlockLoader.cpp @@ -86,20 +86,23 @@ template<> void ContentUnitLoader::loadUnit( } // block model - std::string modelTypeName = BlockModelTypeMeta.getNameString(def.model); + auto& model = def.model; + std::string modelTypeName = BlockModelTypeMeta.getNameString(model.type); root.at("model").get(modelTypeName); - root.at("model-name").get(def.modelName); - if (BlockModelTypeMeta.getItem(modelTypeName, def.model)) { - if (def.model == BlockModelType::CUSTOM && def.customModelRaw == nullptr) { + root.at("model-name").get(def.model.name); + if (BlockModelTypeMeta.getItem(modelTypeName, model.type)) { + if (model.type == BlockModelType::CUSTOM && def.model.customRaw == nullptr) { if (root.has("model-primitives")) { - def.customModelRaw = root["model-primitives"]; - } else if (def.modelName.empty()) { - throw std::runtime_error(name + ": no 'model-primitives' or 'model-name' found"); + def.model.customRaw = root["model-primitives"]; + } else if (def.model.name.empty()) { + throw std::runtime_error( + name + ": no 'model-primitives' or 'model-name' found" + ); } } } else if (!modelTypeName.empty()) { logger.error() << "unknown model: " << modelTypeName; - def.model = BlockModelType::NONE; + model.type = BlockModelType::NONE; } std::string cullingModeName = CullingModeMeta.getNameString(def.culling); @@ -171,9 +174,9 @@ template<> void ContentUnitLoader::loadUnit( "block " + util::quote(def.name) + ": invalid block size" ); } - if (def.model == BlockModelType::BLOCK && + if (model.type == BlockModelType::BLOCK && (def.size.x != 1 || def.size.y != 1 || def.size.z != 1)) { - def.model = BlockModelType::AABB; + model.type = BlockModelType::AABB; def.hitboxes = {AABB(def.size)}; } } diff --git a/src/core_defs.cpp b/src/core_defs.cpp index 52d95c32..fdc880da 100644 --- a/src/core_defs.cpp +++ b/src/core_defs.cpp @@ -19,7 +19,7 @@ void corecontent::setup(Input& input, ContentBuilder& builder) { block.skyLightPassing = true; block.obstacle = false; block.selectable = false; - block.model = BlockModelType::NONE; + block.model.type = BlockModelType::NONE; block.pickingItem = CORE_EMPTY; } { diff --git a/src/frontend/ContentGfxCache.cpp b/src/frontend/ContentGfxCache.cpp index 731419f0..31199a90 100644 --- a/src/frontend/ContentGfxCache.cpp +++ b/src/frontend/ContentGfxCache.cpp @@ -35,10 +35,10 @@ void ContentGfxCache::refresh(const Block& def, const Atlas& atlas) { sideregions[def.rt.id * 6 + side] = atlas.get(TEXTURE_NOTFOUND); } } - if (def.model == BlockModelType::CUSTOM) { - auto model = assets.require(def.modelName); + if (def.model.type == BlockModelType::CUSTOM) { + auto model = assets.require(def.model.name); // temporary dirty fix tbh - if (def.modelName.find(':') == std::string::npos) { + if (def.model.name.find(':') == std::string::npos) { for (auto& mesh : model.meshes) { size_t pos = mesh.texture.find(':'); if (pos == std::string::npos) { diff --git a/src/graphics/render/BlockWrapsRenderer.cpp b/src/graphics/render/BlockWrapsRenderer.cpp index 3feb6da4..3a5f118c 100644 --- a/src/graphics/render/BlockWrapsRenderer.cpp +++ b/src/graphics/render/BlockWrapsRenderer.cpp @@ -44,7 +44,7 @@ void BlockWrapsRenderer::draw(const BlockWrapper& wrapper) { } if (vox->id != BLOCK_VOID) { const auto& def = level.content.getIndices()->blocks.require(vox->id); - switch (def.model) { + switch (def.model.type) { case BlockModelType::BLOCK: batch->cube( glm::vec3(wrapper.position) + glm::vec3(0.5f), diff --git a/src/graphics/render/BlocksPreview.cpp b/src/graphics/render/BlocksPreview.cpp index 8af6a75d..34c3e7df 100644 --- a/src/graphics/render/BlocksPreview.cpp +++ b/src/graphics/render/BlocksPreview.cpp @@ -32,7 +32,7 @@ std::unique_ptr BlocksPreview::draw( cache.getRegion(id, 4), cache.getRegion(id, 5)}; glm::vec3 offset(0.1f, 0.5f, 0.1f); - switch (def.model) { + switch (def.model.type) { case BlockModelType::NONE: // something went wrong... break; diff --git a/src/graphics/render/BlocksRenderer.cpp b/src/graphics/render/BlocksRenderer.cpp index 9b0d91e1..6e838ea5 100644 --- a/src/graphics/render/BlocksRenderer.cpp +++ b/src/graphics/render/BlocksRenderer.cpp @@ -453,7 +453,7 @@ void BlocksRenderer::render( int x = i % CHUNK_W; int y = i / (CHUNK_D * CHUNK_W); int z = (i / CHUNK_D) % CHUNK_W; - switch (def.model) { + switch (def.model.type) { case BlockModelType::BLOCK: blockCube({x, y, z}, texfaces, def, vox.state, !def.shadeless, def.ambientOcclusion); @@ -516,7 +516,7 @@ SortingMeshData BlocksRenderer::renderTranslucent( int x = i % CHUNK_W; int y = i / (CHUNK_D * CHUNK_W); int z = (i / CHUNK_D) % CHUNK_W; - switch (def.model) { + switch (def.model.type) { case BlockModelType::BLOCK: blockCube({x, y, z}, texfaces, def, vox.state, !def.shadeless, def.ambientOcclusion); diff --git a/src/graphics/render/ModelsGenerator.cpp b/src/graphics/render/ModelsGenerator.cpp index d010e835..8d180182 100644 --- a/src/graphics/render/ModelsGenerator.cpp +++ b/src/graphics/render/ModelsGenerator.cpp @@ -50,16 +50,16 @@ static inline UVRegion get_region_for( void ModelsGenerator::prepare(Content& content, Assets& assets) { for (auto& [name, def] : content.blocks.getDefs()) { - if (def->model == BlockModelType::CUSTOM && def->modelName.empty()) { + if (def->model.type == BlockModelType::CUSTOM && def->model.name.empty()) { assets.store( std::make_unique( loadCustomBlockModel( - def->customModelRaw, assets, !def->shadeless + def->model.customRaw, assets, !def->shadeless ) ), name + ".model" ); - def->modelName = def->name + ".model"; + def->model.name = def->name + ".model"; } } for (auto& [name, def] : content.items.getDefs()) { @@ -131,12 +131,12 @@ model::Model ModelsGenerator::generate( if (def.iconType == ItemIconType::BLOCK) { auto model = assets.require("block"); const auto& blockDef = content.blocks.require(def.icon); - if (blockDef.model == BlockModelType::XSPRITE) { + if (blockDef.model.type == BlockModelType::XSPRITE) { return create_flat_model( "blocks:" + blockDef.textureFaces.at(0), assets ); - } else if (blockDef.model == BlockModelType::CUSTOM) { - model = assets.require(blockDef.modelName); + } else if (blockDef.model.type == BlockModelType::CUSTOM) { + model = assets.require(blockDef.model.name); for (auto& mesh : model.meshes) { mesh.scale(glm::vec3(0.2f)); } @@ -144,7 +144,7 @@ model::Model ModelsGenerator::generate( } for (auto& mesh : model.meshes) { mesh.lighting = !blockDef.shadeless; - switch (blockDef.model) { + switch (blockDef.model.type) { case BlockModelType::AABB: { glm::vec3 size = blockDef.hitboxes.at(0).size(); float m = glm::max(size.x, glm::max(size.y, size.z)); diff --git a/src/logic/scripting/lua/libs/libblock.cpp b/src/logic/scripting/lua/libs/libblock.cpp index ab872fb2..031611ee 100644 --- a/src/logic/scripting/lua/libs/libblock.cpp +++ b/src/logic/scripting/lua/libs/libblock.cpp @@ -312,7 +312,7 @@ static int l_get_textures(lua::State* L) { static int l_get_model(lua::State* L) { if (auto def = require_block(L)) { - return lua::pushlstring(L, BlockModelTypeMeta.getName(def->model)); + return lua::pushlstring(L, BlockModelTypeMeta.getName(def->model.type)); } return 0; } diff --git a/src/voxels/Block.cpp b/src/voxels/Block.cpp index e7153665..b7b0d836 100644 --- a/src/voxels/Block.cpp +++ b/src/voxels/Block.cpp @@ -143,7 +143,6 @@ void Block::cloneTo(Block& dst) { if (particles) { dst.particles = std::make_unique(*particles); } - dst.customModelRaw = customModelRaw; } static std::set> RESERVED_BLOCK_FIELDS { diff --git a/src/voxels/Block.hpp b/src/voxels/Block.hpp index dc9980c9..378cbb5d 100644 --- a/src/voxels/Block.hpp +++ b/src/voxels/Block.hpp @@ -94,6 +94,16 @@ enum class BlockModelType { CUSTOM }; +struct BlockModel { + BlockModelType type = BlockModelType::BLOCK; + + /// @brief Custom model raw data + dv::value customRaw = nullptr; + + /// @brief Custom model name (generated or an asset) + std::string name = ""; +}; + VC_ENUM_METADATA(BlockModelType) {"none", BlockModelType::NONE}, {"block", BlockModelType::BLOCK}, @@ -152,13 +162,8 @@ public: /// @brief Influences visible block sides for transparent blocks uint8_t drawGroup = 0; - /// @brief Block model type - BlockModelType model = BlockModelType::BLOCK; - - /// @brief Custom model raw data - dv::value customModelRaw = nullptr; - - std::string modelName = ""; + /// @brief Block model + BlockModel model {}; /// @brief Culling mode CullingMode culling = CullingMode::DEFAULT;