From f8de9f0a51086dae63b9b5e033aed00f227195fa Mon Sep 17 00:00:00 2001 From: failcake <4944278+edunad@users.noreply.github.com> Date: Wed, 9 Oct 2024 11:10:26 +0200 Subject: [PATCH 1/4] - Add CRITICAL_RAWRBOX to trace files - Add ERROR_RAWRBOX to trace files --- CMakeLists.txt | 3 - README.md | 3 +- .../include/rawrbox/bass/utils/bass.hpp | 5 +- rawrbox.bass/src/manager.cpp | 8 +- rawrbox.bass/src/resources/sound.cpp | 4 - rawrbox.bass/src/sound/base.cpp | 4 +- rawrbox.bass/src/sound/instance.cpp | 4 +- rawrbox.bass/src/utils/bass.cpp | 6 +- .../include/rawrbox/engine/engine.hpp | 1 - rawrbox.engine/src/engine.cpp | 111 +++++++----------- .../include/rawrbox/gltf/importer.hpp | 4 +- rawrbox.gltf/src/importer.cpp | 28 ++--- .../include/rawrbox/render/decals/decal.hpp | 3 + .../include/rawrbox/render/materials/base.hpp | 20 ++-- .../rawrbox/render/materials/skinned.hpp | 2 +- .../rawrbox/render/materials/skinnedLit.hpp | 2 +- .../include/rawrbox/render/models/base.hpp | 31 ++--- .../rawrbox/render/models/instanced.hpp | 12 +- .../include/rawrbox/render/models/model.hpp | 30 +++-- .../include/rawrbox/render/models/spline.hpp | 2 +- .../rawrbox/render/models/utils/mesh.hpp | 8 +- .../rawrbox/render/particles/emitter.hpp | 6 +- .../include/rawrbox/render/renderer.hpp | 4 +- .../rawrbox/render/textures/utils/utils.hpp | 4 + .../include/rawrbox/render/utils/barrier.hpp | 3 + rawrbox.render/src/bindless.cpp | 20 ++-- rawrbox.render/src/cameras/base.cpp | 10 +- rawrbox.render/src/decals/decal.cpp | 10 +- rawrbox.render/src/decals/manager.cpp | 6 +- rawrbox.render/src/lights/manager.cpp | 4 +- rawrbox.render/src/materials/lit.cpp | 2 +- rawrbox.render/src/materials/particle.cpp | 2 +- rawrbox.render/src/plugins/clustered.cpp | 16 +-- .../src/plugins/particle_engine.cpp | 16 +-- rawrbox.render/src/plugins/post_process.cpp | 4 +- rawrbox.render/src/post_process/base.cpp | 6 +- rawrbox.render/src/renderer.cpp | 40 +++---- rawrbox.render/src/stencil.cpp | 26 ++-- rawrbox.render/src/svg/engine.cpp | 4 +- rawrbox.render/src/text/engine.cpp | 4 +- rawrbox.render/src/text/font.cpp | 10 +- rawrbox.render/src/textures/animated.cpp | 2 +- rawrbox.render/src/textures/atlas.cpp | 12 +- rawrbox.render/src/textures/base.cpp | 8 +- rawrbox.render/src/textures/gif.cpp | 4 - rawrbox.render/src/textures/image.cpp | 18 +-- rawrbox.render/src/textures/pack.cpp | 4 +- rawrbox.render/src/textures/render.cpp | 10 +- rawrbox.render/src/textures/streaming.cpp | 6 +- rawrbox.render/src/textures/utils/blit.cpp | 8 +- rawrbox.render/src/textures/utils/gif.cpp | 8 +- rawrbox.render/src/textures/utils/stbi.cpp | 10 +- rawrbox.render/src/textures/utils/utils.cpp | 12 +- rawrbox.render/src/textures/utils/webp.cpp | 28 ++--- rawrbox.render/src/textures/webp.cpp | 4 - rawrbox.render/src/utils/barrier.cpp | 3 +- rawrbox.render/src/utils/pipeline.cpp | 28 ++--- rawrbox.render/src/utils/render.cpp | 6 +- rawrbox.render/src/window.cpp | 50 ++++---- .../include/rawrbox/resources/loader.hpp | 2 +- .../rawrbox/resources/loaders/json.hpp | 5 + .../include/rawrbox/resources/manager.hpp | 18 +-- rawrbox.resources/src/loaders/json.cpp | 6 +- rawrbox.scripting/src/manager.cpp | 21 ++-- rawrbox.scripting/src/mod.cpp | 10 +- .../include/rawrbox/steamworks/utils.hpp | 4 + rawrbox.steamworks/src/callbacks/manager.cpp | 22 ++-- rawrbox.steamworks/src/input.cpp | 4 +- rawrbox.steamworks/src/sdk.cpp | 12 +- rawrbox.steamworks/src/utils.cpp | 8 +- rawrbox.steamworks/src/workshop/manager.cpp | 86 +++++++------- rawrbox.steamworks/src/workshop/storage.cpp | 2 +- rawrbox.ui/include/rawrbox/ui/container.hpp | 6 +- .../include/rawrbox/ui/elements/anim.hpp | 4 +- rawrbox.ui/src/container.cpp | 2 +- rawrbox.ui/src/elements/console.cpp | 2 +- rawrbox.ui/src/elements/tabs.cpp | 14 +-- rawrbox.ui/src/popup/manager.cpp | 4 +- rawrbox.utils/CMakeLists.txt | 36 +++--- .../include/rawrbox/utils/logger.hpp | 78 +++++------- .../include/rawrbox/utils/settings.hpp | 8 +- rawrbox.utils/src/i18n.cpp | 2 +- rawrbox.utils/src/logger.cpp | 30 ++++- rawrbox.utils/src/threading.cpp | 12 +- rawrbox.webm/src/decoder.cpp | 14 +-- rawrbox.webm/src/loader.cpp | 32 ++--- rawrbox.webm/src/textures/webm.cpp | 13 +- 87 files changed, 568 insertions(+), 598 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 1c1d1d97..8f20a132 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -58,7 +58,6 @@ option(RAWRBOX_DISABLE_SUPPORT_VULKAN "Disable vulkan support" OFF) # Other ----- option(RAWRBOX_DEV_MODE "Builds all modules, used for developing rawrbox" OFF) -option(RAWRBOX_TRACE_EXCEPTIONS "Enables exception tracing" ON) option(RAWRBOX_INTERPROCEDURAL_OPTIMIZATION "Enables IPO" ON) # --------------- # ----- @@ -103,8 +102,6 @@ if(RAWRBOX_DEV_MODE) set(RAWRBOX_BUILD_RAWRBOX_IMGUI ON) set(RAWRBOX_BUILD_QHULL ON) - set(RAWRBOX_TRACE_EXCEPTIONS OFF) - if(NOT DEFINED STEAMWORKS_APPID) message(STATUS "Set STEAMWORKS_APPID to 480 (SpaceWars example game)") set(STEAMWORKS_APPID 480) # SpaceWars example game diff --git a/README.md b/README.md index 68b05c4b..065dba77 100644 --- a/README.md +++ b/README.md @@ -155,7 +155,6 @@ This engine started as a C++ training project, with hopes of being applied in my | -- | -- | -- | | `RAWRBOX_DEV_MODE` | Enables all the modules, used for rawrbox development | OFF | | -- | -- | -- | -| `RAWRBOX_TRACE_EXCEPTIONS` | Enables exception tracing | ON | | `RAWRBOX_INTERPROCEDURAL_OPTIMIZATION` | Enables IPO compilation on release | ON |

@@ -199,6 +198,6 @@ This engine started as a C++ training project, with hopes of being applied in my | curl | Used for HTTP / HTTPS requests | [MIT](https://github.com/libcpr/cpr/blob/master/LICENSE) | | libcpr | Used for HTTP / HTTPS requests | [MIT](https://github.com/libcpr/cpr/blob/master/LICENSE) | | lunasvg | Used for SVG loading | [MIT](https://github.com/sammycage/lunasvg/blob/master/LICENSE) | -| cpptrace | Used for easy error tracing | [MIT](https://github.com/jeremy-rifkin/cpptrace/blob/main/LICENSE) | | meshoptimizer | Used to optimize meshes | [MIT](https://github.com/zeux/meshoptimizer/blob/master/LICENSE.md) | | ozz-animation | Used to animate skinned meshes | [MIT](https://github.com/guillaumeblanc/ozz-animation/blob/master/LICENSE.md) | +| spdlog | Used for logging | [MIT](https://github.com/gabime/spdlog/blob/v1.x/LICENSE) | diff --git a/rawrbox.bass/include/rawrbox/bass/utils/bass.hpp b/rawrbox.bass/include/rawrbox/bass/utils/bass.hpp index 6fbafb44..3f038362 100644 --- a/rawrbox.bass/include/rawrbox/bass/utils/bass.hpp +++ b/rawrbox.bass/include/rawrbox/bass/utils/bass.hpp @@ -1,7 +1,10 @@ #pragma once - +#include namespace rawrbox { class BASSUtils { + protected: + static std::unique_ptr _logger; + public: static void checkBASSError(); }; diff --git a/rawrbox.bass/src/manager.cpp b/rawrbox.bass/src/manager.cpp index c823702c..6ee72572 100644 --- a/rawrbox.bass/src/manager.cpp +++ b/rawrbox.bass/src/manager.cpp @@ -72,7 +72,7 @@ namespace rawrbox { void BASS::initialize() { auto fxVersion = HIWORD(BASS_FX_GetVersion()); - if (fxVersion != BASSVERSION) throw _logger->error("BASS Version missmatch! FX [{}] | BASS [{}]", fxVersion, BASSVERSION); + if (fxVersion != BASSVERSION) CRITICAL_RAWRBOX("BASS Version missmatch! FX [{}] | BASS [{}]", fxVersion, BASSVERSION); _initialized = (BASS_Init(-1, 44100, BASS_DEVICE_3D, nullptr, nullptr) != 0); if (_initialized) { @@ -82,7 +82,7 @@ namespace rawrbox { BASS_Set3DFactors(1.0F, 10.0F, 1.0F); BASS_Apply3D(); } else { - throw _logger->error("BASS initialize error: {}", BASS_ErrorGetCode()); + CRITICAL_RAWRBOX("BASS initialize error: {}", BASS_ErrorGetCode()); } } @@ -104,7 +104,7 @@ namespace rawrbox { std::string pth = path.generic_string(); if (sounds.find(pth) != sounds.end()) return sounds[pth].get(); - if (!std::filesystem::exists(path)) throw _logger->error("File '{}' not found!", pth); + if (!std::filesystem::exists(path)) CRITICAL_RAWRBOX("File '{}' not found!", pth); auto size = std::filesystem::file_size(path); if (path.generic_string().rfind(".3D") != std::string::npos) flags |= SoundFlags::SOUND_3D; @@ -141,7 +141,7 @@ namespace rawrbox { } rawrbox::SoundBase* BASS::loadHTTPSound(const std::string& url, uint32_t flags) { - if (!url.starts_with("http://") && !url.starts_with("https://")) throw _logger->error("Invalid sound url '{}'", url); + if (!url.starts_with("http://") && !url.starts_with("https://")) CRITICAL_RAWRBOX("Invalid sound url '{}'", url); if (sounds.find(url) != sounds.end()) return sounds[url].get(); if (url.rfind(".3D") != std::string::npos) flags |= SoundFlags::SOUND_3D; diff --git a/rawrbox.bass/src/resources/sound.cpp b/rawrbox.bass/src/resources/sound.cpp index 299e2d1c..cc216513 100644 --- a/rawrbox.bass/src/resources/sound.cpp +++ b/rawrbox.bass/src/resources/sound.cpp @@ -15,11 +15,7 @@ namespace rawrbox { } else { loaded = rawrbox::BASS::loadSound(this->filePath, this->flags); } -#ifdef RAWRBOX_TRACE_EXCEPTIONS - } catch (const cpptrace::exception_with_message& e) { -#else } catch (const std::exception& e) { -#endif fmt::print("\n\t{}\n\t\t └── Loading fallback sound!\n", e.what()); loaded = rawrbox::BASS::loadSound("./assets/sound/error.ogg", this->flags); } diff --git a/rawrbox.bass/src/sound/base.cpp b/rawrbox.bass/src/sound/base.cpp index b2a0d70d..446d2621 100644 --- a/rawrbox.bass/src/sound/base.cpp +++ b/rawrbox.bass/src/sound/base.cpp @@ -23,7 +23,7 @@ namespace rawrbox { } std::shared_ptr SoundBase::createInstance() { - if (!this->isValid()) throw this->_logger->error("Sound sample not valid!"); + if (!this->isValid()) CRITICAL_RAWRBOX("Sound sample not valid!"); auto ptr = std::make_shared(this->_sample, this->_isStream, this->_flags); this->_instances.push_back(std::move(ptr)); @@ -31,7 +31,7 @@ namespace rawrbox { } std::shared_ptr SoundBase::getInstance(size_t i) { - if (i >= this->_instances.size()) throw this->_logger->error("Sound instance '{}' not found!", i); + if (i >= this->_instances.size()) CRITICAL_RAWRBOX("Sound instance '{}' not found!", i); return this->_instances[i]; } diff --git a/rawrbox.bass/src/sound/instance.cpp b/rawrbox.bass/src/sound/instance.cpp index 47ceec0b..ccab7d47 100644 --- a/rawrbox.bass/src/sound/instance.cpp +++ b/rawrbox.bass/src/sound/instance.cpp @@ -164,7 +164,7 @@ namespace rawrbox { flag = BASS_DATA_FFT4096; break; default: - throw this->_logger->error("Unknown FFT length {}, should be power of 2! Check: http://bass.radio42.com/help/html/a13cfef0-1056-bb94-81c4-a4fdf21bd463.htm", bass_length); + CRITICAL_RAWRBOX("Unknown FFT length {}, should be power of 2! Check: http://bass.radio42.com/help/html/a13cfef0-1056-bb94-81c4-a4fdf21bd463.htm", bass_length); } buffer.resize(bass_length); @@ -180,7 +180,7 @@ namespace rawrbox { // -------------- void SoundInstance::setBeatSettings(float bandwidth, float center_freq, float release_time) { - if ((this->_flags & SoundFlags::BEAT_DETECTION) == 0) throw this->_logger->error("Load flag BEAT_DETECTION not set!"); + if ((this->_flags & SoundFlags::BEAT_DETECTION) == 0) CRITICAL_RAWRBOX("Load flag BEAT_DETECTION not set!"); if (!this->isCreated()) return; BASS_FX_BPM_BeatSetParameters(this->_channel, bandwidth, center_freq, release_time); diff --git a/rawrbox.bass/src/utils/bass.cpp b/rawrbox.bass/src/utils/bass.cpp index a07e25f8..508e63c0 100644 --- a/rawrbox.bass/src/utils/bass.cpp +++ b/rawrbox.bass/src/utils/bass.cpp @@ -6,6 +6,10 @@ #include namespace rawrbox { + // PRIVATE --- + std::unique_ptr BASSUtils::_logger = std::make_unique("RawrBox-BASS"); + // ---------- + void BASSUtils::checkBASSError() { int err = BASS_ErrorGetCode(); std::string readErr; @@ -41,7 +45,7 @@ namespace rawrbox { break; } - throw rawrbox::Logger::err("RawrBox-BASS", "Bass audio error:\n\t{}", readErr); + CRITICAL_RAWRBOX("Bass audio error:\n\t{}", readErr); } } // namespace rawrbox diff --git a/rawrbox.engine/include/rawrbox/engine/engine.hpp b/rawrbox.engine/include/rawrbox/engine/engine.hpp index a0fb22ab..1a693d10 100644 --- a/rawrbox.engine/include/rawrbox/engine/engine.hpp +++ b/rawrbox.engine/include/rawrbox/engine/engine.hpp @@ -39,7 +39,6 @@ namespace rawrbox { virtual void draw(); virtual void onThreadShutdown(rawrbox::ENGINE_THREADS thread); - static void prettyPrintErr(const std::string& err); public: virtual ~Engine() = default; diff --git a/rawrbox.engine/src/engine.cpp b/rawrbox.engine/src/engine.cpp index 21cc9caa..cd08e16a 100644 --- a/rawrbox.engine/src/engine.cpp +++ b/rawrbox.engine/src/engine.cpp @@ -26,7 +26,7 @@ namespace rawrbox { } // Create the GLFW window - void Engine::setupGLFW() { throw this->_logger->error("Method 'setupGLFW' not implemented"); } + void Engine::setupGLFW() { CRITICAL_RAWRBOX("Method 'setupGLFW' not implemented"); } void Engine::init() {} void Engine::pollEvents() {} void Engine::fixedUpdate() {} @@ -41,12 +41,6 @@ namespace rawrbox { rawrbox::ASYNC::shutdown(); } - void Engine::prettyPrintErr(const std::string& err) { - fmt::print("\n ---- FATAL ENGINE ERROR ----\n"); - fmt::print(" {}\n", err); - fmt::print("-------------------------------\n\n"); - } - void Engine::run() { rawrbox::ASYNC::init(); rawrbox::ThreadUtils::setName("rawrbox:input"); @@ -57,82 +51,59 @@ namespace rawrbox { // Setup render threading auto renderThread = std::jthread([this]() { -#ifdef RAWRBOX_TRACE_EXCEPTIONS - try { -#endif - rawrbox::RENDER_THREAD_ID = std::this_thread::get_id(); - rawrbox::ThreadUtils::setName("rawrbox:render"); + rawrbox::RENDER_THREAD_ID = std::this_thread::get_id(); + rawrbox::ThreadUtils::setName("rawrbox:render"); - // INITIALIZE ENGINE --- - this->init(); - // --------- + // INITIALIZE ENGINE --- + this->init(); + // --------- - while (this->_shutdown != ENGINE_THREADS::THREAD_RENDER) { - rawrbox::DELTA_TIME = static_cast(std::max(0.0, this->_timer.record_elapsed_seconds())); + while (this->_shutdown != ENGINE_THREADS::THREAD_RENDER) { + rawrbox::DELTA_TIME = static_cast(std::max(0.0, this->_timer.record_elapsed_seconds())); - const float target_deltaTime = 1.0F / this->_fps; - if (rawrbox::DELTA_TIME < target_deltaTime) { - sleep((target_deltaTime - rawrbox::DELTA_TIME) * 1000); - rawrbox::DELTA_TIME += static_cast(std::max(0.0, this->_timer.record_elapsed_seconds())); - } - - // THREADING ---- - rawrbox::___runThreadInvokes(); - // ------- + const float target_deltaTime = 1.0F / this->_fps; + if (rawrbox::DELTA_TIME < target_deltaTime) { + sleep((target_deltaTime - rawrbox::DELTA_TIME) * 1000); + rawrbox::DELTA_TIME += static_cast(std::max(0.0, this->_timer.record_elapsed_seconds())); + } - // Fixed time update -------- - this->_deltaTimeAccumulator += rawrbox::DELTA_TIME; - if (this->_deltaTimeAccumulator > 10.F) this->_deltaTimeAccumulator = 0; // Prevent dead loop + // THREADING ---- + rawrbox::___runThreadInvokes(); + // ------- - const float targetFrameRateInv = 1.0F / this->_tps; - rawrbox::FIXED_DELTA_TIME = targetFrameRateInv; + // Fixed time update -------- + this->_deltaTimeAccumulator += rawrbox::DELTA_TIME; + if (this->_deltaTimeAccumulator > 10.F) this->_deltaTimeAccumulator = 0; // Prevent dead loop - while (this->_deltaTimeAccumulator >= targetFrameRateInv) { - this->fixedUpdate(); + const float targetFrameRateInv = 1.0F / this->_tps; + rawrbox::FIXED_DELTA_TIME = targetFrameRateInv; - this->_deltaTimeAccumulator -= targetFrameRateInv; - if (this->_shutdown != ENGINE_THREADS::NONE) break; - } + while (this->_deltaTimeAccumulator >= targetFrameRateInv) { + this->fixedUpdate(); + this->_deltaTimeAccumulator -= targetFrameRateInv; if (this->_shutdown != ENGINE_THREADS::NONE) break; - // --------------------------- + } - // VARIABLE-TIME - rawrbox::TIMER::update(); - this->update(); - // ---- + if (this->_shutdown != ENGINE_THREADS::NONE) break; + // --------------------------- - // ACTUAL DRAWING - rawrbox::FRAME_ALPHA = this->_deltaTimeAccumulator / rawrbox::DELTA_TIME; - this->draw(); - // ---------- - } + // VARIABLE-TIME + rawrbox::TIMER::update(); + this->update(); + // ---- - this->_logger->warn("Thread 'rawrbox:render' shutdown"); - rawrbox::TIMER::clear(); - - this->onThreadShutdown(rawrbox::ENGINE_THREADS::THREAD_RENDER); - this->_shutdown = rawrbox::ENGINE_THREADS::THREAD_INPUT; // Done killing rendering, now destroy glfw -#ifdef RAWRBOX_TRACE_EXCEPTIONS - } catch (const cpptrace::exception_with_message& err) { - this->prettyPrintErr(err.message()); - - err.trace().print(); - throw err; - } catch (const std::exception& err) { - this->prettyPrintErr(err.what()); - - fmt::print("▒▒{}▒▒\n", fmt::styled(" If you are a developer, please use logger error in RAWRBOX.UTILS for a better stack trace ", fmt::bg(fmt::color::dark_red) | fmt::fg(fmt::color::white))); - cpptrace::generate_trace().print(); - throw err; - } catch (...) { - this->prettyPrintErr("Unknown error"); - - fmt::print("▒▒{}▒▒\n", fmt::styled(" If you are a developer, please use logger error in RAWRBOX.UTILS for a better stack trace ", fmt::bg(fmt::color::dark_red) | fmt::fg(fmt::color::white))); - cpptrace::generate_trace().print(); - throw std::runtime_error("Unknown error"); + // ACTUAL DRAWING + rawrbox::FRAME_ALPHA = this->_deltaTimeAccumulator / rawrbox::DELTA_TIME; + this->draw(); + // ---------- } -#endif + + this->_logger->warn("Thread 'rawrbox:render' shutdown"); + rawrbox::TIMER::clear(); + + this->onThreadShutdown(rawrbox::ENGINE_THREADS::THREAD_RENDER); + this->_shutdown = rawrbox::ENGINE_THREADS::THREAD_INPUT; // Done killing rendering, now destroy glfw }); // ---- diff --git a/rawrbox.gltf/include/rawrbox/gltf/importer.hpp b/rawrbox.gltf/include/rawrbox/gltf/importer.hpp index 76f18a16..202f0606 100644 --- a/rawrbox.gltf/include/rawrbox/gltf/importer.hpp +++ b/rawrbox.gltf/include/rawrbox/gltf/importer.hpp @@ -225,11 +225,11 @@ namespace rawrbox { template fastgltf::span subspan(fastgltf::span span, size_t offset, size_t count = fastgltf::dynamic_extent) { if (offset >= span.size()) { - throw _logger->error("Offset is out of range"); + CRITICAL_RAWRBOX("Offset is out of range"); } if (count != fastgltf::dynamic_extent && count > span.size() - offset) { - throw _logger->error("Count is out of range"); + CRITICAL_RAWRBOX("Count is out of range"); } if (count == fastgltf::dynamic_extent) { diff --git a/rawrbox.gltf/src/importer.cpp b/rawrbox.gltf/src/importer.cpp index 245677ac..528a91e1 100644 --- a/rawrbox.gltf/src/importer.cpp +++ b/rawrbox.gltf/src/importer.cpp @@ -360,7 +360,7 @@ namespace rawrbox { printBone = [this, &printBone](const ozz::animation::offline::RawSkeleton::Joint& bn, int depth, bool isLast) -> void { std::string indent(depth * 4, ' '); std::string branch = isLast ? "└── " : "├── "; - this->_logger->info("{}{}{}", indent, branch, bn.name); + this->_logger->debug("{}{}{}", indent, branch, bn.name); for (size_t i = 0; i < bn.children.size(); i++) { bool lastChild = (i == bn.children.size() - 1); @@ -420,7 +420,7 @@ namespace rawrbox { // DEBUG ---- if (printBone != nullptr) { - this->_logger->info("Found skeleton '{}' ->", fmt::styled(skin.name, fmt::fg(fmt::color::green_yellow))); + this->_logger->debug("Found skeleton '{}' ->", fmt::styled(skin.name, fmt::fg(fmt::color::green_yellow))); for (const ozz::animation::offline::RawSkeleton::Joint& root : rawSkeleton.roots) { printBone(root, 0, true); } @@ -444,7 +444,7 @@ namespace rawrbox { const std::string jointName = std::string(node.name); auto fnd = this->joints.find(jointName); - if (fnd == this->joints.end()) throw this->_logger->error("Invalid joint '{}', could not find in skeleton", jointName); + if (fnd == this->joints.end()) CRITICAL_RAWRBOX("Invalid joint '{}', could not find in skeleton", jointName); fnd->second->skeleton = this->skeletons[i].get(); } @@ -482,7 +482,7 @@ namespace rawrbox { gltfAnim.duration = 0.001F; if ((this->loadFlags & rawrbox::ModelLoadFlags::Debug::PRINT_ANIMATIONS) > 0) { - this->_logger->info("Found animation '{}'", fmt::styled(gltfAnim.name, fmt::fg(fmt::color::green_yellow))); + this->_logger->debug("Found animation '{}'", fmt::styled(gltfAnim.name, fmt::fg(fmt::color::green_yellow))); } for (size_t c = 0; c < anim.channels.size(); c++) { @@ -581,7 +581,7 @@ namespace rawrbox { if (this->_parsedAnimations.empty()) return; ozz::animation::offline::AnimationBuilder builder; - this->_logger->info("Building {} animations...", this->_parsedAnimations.size()); + this->_logger->debug("Building {} animations...", this->_parsedAnimations.size()); this->animations.resize(this->_parsedAnimations.size()); for (size_t i = 0; i < this->_parsedAnimations.size(); i++) { @@ -682,7 +682,7 @@ namespace rawrbox { for (size_t o = 0; o < primitive.targets.size(); o++) { const auto& blendNames = this->targetNames[meshIndex]; - if (blendNames.empty()) throw this->_logger->error("Invalid blend shape names for mesh '{}'", gltfMesh->name); + if (blendNames.empty()) CRITICAL_RAWRBOX("Invalid blend shape names for mesh '{}'", gltfMesh->name); rawrbox::GLTFBlendShape& shape = rawrPrimitive.blendShapes[o]; shape.name = fmt::format("{}-{}", gltfMesh->name, blendNames[o]); @@ -732,7 +732,7 @@ namespace rawrbox { if ((this->loadFlags & rawrbox::ModelLoadFlags::Debug::PRINT_OPTIMIZATION_STATS) > 0) { if (startVert != rawrPrimitive.vertices.size() || startInd != rawrPrimitive.indices.size()) { - this->_logger->info("Optimized mesh '{}'\n\tVertices -> {} to {}\n\tIndices -> {} to {}", fmt::styled(gltfMesh->name, fmt::fg(fmt::color::cyan)), startVert, rawrPrimitive.vertices.size(), startInd, rawrPrimitive.indices.size()); + this->_logger->debug("Optimized mesh '{}'\n\tVertices -> {} to {}\n\tIndices -> {} to {}", fmt::styled(gltfMesh->name, fmt::fg(fmt::color::cyan)), startVert, rawrPrimitive.vertices.size(), startInd, rawrPrimitive.indices.size()); } } } else { @@ -751,7 +751,7 @@ namespace rawrbox { // POSITION ---- const auto* positionAttribute = primitive.findAttribute("POSITION"); - if (positionAttribute == nullptr) throw this->_logger->error("Invalid gltf model, missing 'POSITION' attribute!"); // All models have POSITION + if (positionAttribute == nullptr) CRITICAL_RAWRBOX("Invalid gltf model, missing 'POSITION' attribute!"); // All models have POSITION const auto& positionAccessor = scene.accessors[positionAttribute->accessorIndex]; verts.resize(positionAccessor.count); @@ -843,13 +843,13 @@ namespace rawrbox { fastgltf::sources::ByteView GLTFImporter::getSourceData(const fastgltf::Asset& scene, const fastgltf::DataSource& source) { return std::visit(fastgltf::visitor{ [&](auto& /*arg*/) -> fastgltf::sources::ByteView { - throw this->_logger->error("Invalid data"); + CRITICAL_RAWRBOX("Invalid data"); }, [&](std::monostate) -> fastgltf::sources::ByteView { - throw this->_logger->error("Invalid data"); + CRITICAL_RAWRBOX("Invalid data"); }, [&](fastgltf::sources::Fallback) -> fastgltf::sources::ByteView { - throw this->_logger->error("Invalid data"); + CRITICAL_RAWRBOX("Invalid data"); }, [&](const fastgltf::sources::BufferView& buffer_view) -> fastgltf::sources::ByteView { const fastgltf::BufferView& view = scene.bufferViews.at(buffer_view.bufferViewIndex); @@ -859,7 +859,7 @@ namespace rawrbox { return {subspan(data.bytes, view.byteOffset, view.byteLength), buffer_view.mimeType}; }, [&](const fastgltf::sources::URI& /*filePath*/) -> fastgltf::sources::ByteView { - throw this->_logger->error("Use fastgltf::Options::LoadExternalImages instead!"); + CRITICAL_RAWRBOX("Use fastgltf::Options::LoadExternalImages instead!"); }, [&](const fastgltf::sources::Vector& vector) -> fastgltf::sources::ByteView { fastgltf::span data{std::bit_cast(vector.bytes.data()), vector.bytes.size()}; @@ -870,7 +870,7 @@ namespace rawrbox { return {data, array.mimeType}; }, [&](const fastgltf::sources::CustomBuffer& /*custom_buffer*/) -> fastgltf::sources::ByteView { - throw this->_logger->error("Invalid data"); + CRITICAL_RAWRBOX("Invalid data"); }, [&](fastgltf::sources::ByteView& byte_view) -> fastgltf::sources::ByteView { return {byte_view.bytes, byte_view.mimeType}; @@ -923,7 +923,7 @@ namespace rawrbox { } void GLTFImporter::load(const std::filesystem::path& path) { - if (!std::filesystem::exists(path)) throw this->_logger->error("File '{}' does not exist!", path.generic_string()); + if (!std::filesystem::exists(path)) CRITICAL_RAWRBOX("File '{}' does not exist!", path.generic_string()); this->filePath = path; diff --git a/rawrbox.render/include/rawrbox/render/decals/decal.hpp b/rawrbox.render/include/rawrbox/render/decals/decal.hpp index bab2bfe4..ded6e7c7 100644 --- a/rawrbox.render/include/rawrbox/render/decals/decal.hpp +++ b/rawrbox.render/include/rawrbox/render/decals/decal.hpp @@ -6,6 +6,9 @@ namespace rawrbox { struct Decal { + private: + static std::unique_ptr _logger; + public: rawrbox::Matrix4x4 worldToLocal = {}; rawrbox::Vector4u data = {}; diff --git a/rawrbox.render/include/rawrbox/render/materials/base.hpp b/rawrbox.render/include/rawrbox/render/materials/base.hpp index 1a750109..2c626933 100644 --- a/rawrbox.render/include/rawrbox/render/materials/base.hpp +++ b/rawrbox.render/include/rawrbox/render/materials/base.hpp @@ -80,7 +80,7 @@ namespace rawrbox { // SETUP UNIFORMS ---------------------------- { Diligent::MapHelper PixelConstants(rawrbox::RENDERER->context(), rawrbox::BindlessManager::signatureBufferPixel, Diligent::MAP_WRITE, Diligent::MAP_FLAG_DISCARD); - if (PixelConstants == nullptr) throw _logger->error("Failed to map the pixel constants buffer!"); + if (PixelConstants == nullptr) CRITICAL_RAWRBOX("Failed to map the pixel constants buffer!"); std::memcpy(PixelConstants, &this->_lastPixelBuffer.value(), sizeof(rawrbox::BindlessPixelBuffer)); } @@ -99,7 +99,7 @@ namespace rawrbox { // SETUP UNIFORMS ---------------------------- { Diligent::MapHelper VertexConstants(rawrbox::RENDERER->context(), rawrbox::BindlessManager::signatureBufferVertex, Diligent::MAP_WRITE, Diligent::MAP_FLAG_DISCARD); - if (VertexConstants == nullptr) throw _logger->error("Failed to map the vertex constants buffer!"); + if (VertexConstants == nullptr) CRITICAL_RAWRBOX("Failed to map the vertex constants buffer!"); std::memcpy(VertexConstants, &this->_lastVertexBuffer.value(), sizeof(rawrbox::BindlessVertexBuffer)); } @@ -115,26 +115,26 @@ namespace rawrbox { template requires(std::derived_from) void bindPipeline(const rawrbox::Mesh& mesh) { - if (this->base == nullptr) throw this->_logger->error("Material not initialized!"); + if (this->base == nullptr) CRITICAL_RAWRBOX("Material not initialized!"); auto* context = rawrbox::RENDERER->context(); if (mesh.getWireframe()) { - if (this->wireframe == nullptr) throw this->_logger->error("Wireframe not supported on material"); + if (this->wireframe == nullptr) CRITICAL_RAWRBOX("Wireframe not supported on material"); context->SetPipelineState(this->wireframe); } else if (mesh.getLineMode()) { - if (this->line == nullptr) throw this->_logger->error("Line not supported on material"); + if (this->line == nullptr) CRITICAL_RAWRBOX("Line not supported on material"); context->SetPipelineState(this->line); } else { if (mesh.culling == Diligent::CULL_MODE_NONE) { - if (this->cullnone == nullptr) throw this->_logger->error("Disabled cull not supported on material"); - if (mesh.isTransparent() && this->cullnone_alpha == nullptr) throw this->_logger->error("Disabled alpha cull not supported on material"); + if (this->cullnone == nullptr) CRITICAL_RAWRBOX("Disabled cull not supported on material"); + if (mesh.isTransparent() && this->cullnone_alpha == nullptr) CRITICAL_RAWRBOX("Disabled alpha cull not supported on material"); context->SetPipelineState(mesh.isTransparent() ? this->cullnone_alpha : this->cullnone); } else if (mesh.culling == Diligent::CULL_MODE_BACK) { - if (this->cullback == nullptr) throw this->_logger->error("Cull back not supported on material"); - if (mesh.isTransparent() && this->cullback_alpha == nullptr) throw this->_logger->error("Cull back alpha not supported on material"); + if (this->cullback == nullptr) CRITICAL_RAWRBOX("Cull back not supported on material"); + if (mesh.isTransparent() && this->cullback_alpha == nullptr) CRITICAL_RAWRBOX("Cull back alpha not supported on material"); context->SetPipelineState(mesh.isTransparent() ? this->cullback_alpha : this->cullback); } else { - if (mesh.isTransparent() && this->base_alpha == nullptr) throw this->_logger->error("Alpha not supported on material"); + if (mesh.isTransparent() && this->base_alpha == nullptr) CRITICAL_RAWRBOX("Alpha not supported on material"); context->SetPipelineState(mesh.isTransparent() ? this->base_alpha : this->base); } } diff --git a/rawrbox.render/include/rawrbox/render/materials/skinned.hpp b/rawrbox.render/include/rawrbox/render/materials/skinned.hpp index dc562156..6fc6f36b 100644 --- a/rawrbox.render/include/rawrbox/render/materials/skinned.hpp +++ b/rawrbox.render/include/rawrbox/render/materials/skinned.hpp @@ -32,7 +32,7 @@ namespace rawrbox { // SETUP UNIFORMS ---------------------------- { Diligent::MapHelper VertexSkinnedConstants(rawrbox::RENDERER->context(), rawrbox::BindlessManager::signatureBufferVertexSkinned, Diligent::MAP_WRITE, Diligent::MAP_FLAG_DISCARD); - if (VertexSkinnedConstants == nullptr) throw _logger->error("Failed to map the vertex skinned constants buffer!"); + if (VertexSkinnedConstants == nullptr) CRITICAL_RAWRBOX("Failed to map the vertex skinned constants buffer!"); std::memcpy(VertexSkinnedConstants, &this->_lastSkinnedVertexBuffer.value(), sizeof(rawrbox::BindlessVertexSkinnedBuffer)); } diff --git a/rawrbox.render/include/rawrbox/render/materials/skinnedLit.hpp b/rawrbox.render/include/rawrbox/render/materials/skinnedLit.hpp index de1a445f..d569dc61 100644 --- a/rawrbox.render/include/rawrbox/render/materials/skinnedLit.hpp +++ b/rawrbox.render/include/rawrbox/render/materials/skinnedLit.hpp @@ -29,7 +29,7 @@ namespace rawrbox { // SETUP UNIFORMS ---------------------------- { Diligent::MapHelper VertexSkinnedConstants(rawrbox::RENDERER->context(), rawrbox::BindlessManager::signatureBufferVertexSkinned, Diligent::MAP_WRITE, Diligent::MAP_FLAG_DISCARD); - if (VertexSkinnedConstants == nullptr) throw _logger->error("Failed to map the vertex skinned constants buffer!"); + if (VertexSkinnedConstants == nullptr) CRITICAL_RAWRBOX("Failed to map the vertex skinned constants buffer!"); std::memcpy(VertexSkinnedConstants, &this->_lastSkinnedVertexBuffer.value(), sizeof(rawrbox::BindlessVertexSkinnedBuffer)); } diff --git a/rawrbox.render/include/rawrbox/render/models/base.hpp b/rawrbox.render/include/rawrbox/render/models/base.hpp index 6feaaba7..bf4aa7c2 100644 --- a/rawrbox.render/include/rawrbox/render/models/base.hpp +++ b/rawrbox.render/include/rawrbox/render/models/base.hpp @@ -62,7 +62,7 @@ namespace rawrbox { auto indcSize = static_cast(this->_mesh->indices.size()); auto empty = vertSize == 0 || indcSize == 0; - if (empty) throw this->_logger->error("Invalid mesh! Missing vertices / indices!"); + if (empty) CRITICAL_RAWRBOX("Invalid mesh! Missing vertices / indices!"); // Store original positions for blendstates this->_original_data.clear(); @@ -79,8 +79,8 @@ namespace rawrbox { } virtual void applyBlendShapes() { - if (!this->isUploaded()) throw this->_logger->error("Blendshapes require the model to be uploaded!"); - if (!this->isDynamic()) throw this->_logger->error("Blendshapes require the model to be dynamic!"); + if (!this->isUploaded()) CRITICAL_RAWRBOX("Blendshapes require the model to be uploaded!"); + if (!this->isDynamic()) CRITICAL_RAWRBOX("Blendshapes require the model to be dynamic!"); if (this->_original_data.empty()) this->calculateOriginalShape(); // Initial setup @@ -92,11 +92,11 @@ namespace rawrbox { auto& blendNormals = shape.second->normals; if (!blendPos.empty() && blendPos.size() != verts.size()) { - throw this->_logger->error("Blendshape verts do not match with the mesh '{}' verts! Total verts: {}, blend shape verts: {}", shape.first, verts.size(), blendPos.size()); + CRITICAL_RAWRBOX("Blendshape verts do not match with the mesh '{}' verts! Total verts: {}, blend shape verts: {}", shape.first, verts.size(), blendPos.size()); } if (!blendNormals.empty() && blendNormals.size() != verts.size()) { - throw this->_logger->error("Blendshape normals do not match with the mesh '{}' verts! Total verts: {}, blend shape verts: {}", shape.first, verts.size(), blendNormals.size()); + CRITICAL_RAWRBOX("Blendshape normals do not match with the mesh '{}' verts! Total verts: {}, blend shape verts: {}", shape.first, verts.size(), blendNormals.size()); } float step = std::clamp(shape.second->weight, 0.F, 1.F); @@ -142,7 +142,7 @@ namespace rawrbox { this->_mesh->vertices.reserve(vertSize + RB_RENDER_BUFFER_INCREASE_OFFSET); this->createVertexBuffer(); - this->_logger->info("Resizing vertex buffer ({} -> {})", vertSize, this->_mesh->vertices.capacity()); + this->_logger->debug("Resizing vertex buffer ({} -> {})", fmt::styled(vertSize, fmt::fg(fmt::color::cyan)), fmt::styled(this->_mesh->vertices.capacity(), fmt::fg(fmt::color::cyan))); } if (resizeIndex) { @@ -151,7 +151,8 @@ namespace rawrbox { this->_mesh->indices.reserve(indcSize + RB_RENDER_BUFFER_INCREASE_OFFSET); this->createIndexBuffer(); - this->_logger->info("Resizing index buffer ({} -> {})", indcSize, this->_mesh->indices.capacity()); + this->_logger->debug("Resizing index buffer ({} -> {})", fmt::styled(indcSize, fmt::fg(fmt::color::cyan)), fmt::styled(this->_mesh->indices.capacity(), fmt::fg(fmt::color::cyan))); + CRITICAL_RAWRBOX("Resizing vertex buffer ({} -> {})", vertSize, this->_mesh->vertices.capacity()); } if (resizeVertex && resizeIndex) { @@ -183,7 +184,7 @@ namespace rawrbox { auto* device = rawrbox::RENDERER->device(); auto indcSize = static_cast(std::max(this->_mesh->indices.capacity(), this->isDynamic() ? 1U : 0U)); // RESIZABLE requires at least one vertice - if (indcSize == 0) throw this->_logger->error("Indices data cannot be empty!"); + if (indcSize == 0) CRITICAL_RAWRBOX("Indices data cannot be empty!"); Diligent::BufferDesc IndcBuffDesc; IndcBuffDesc.Name = "RawrBox::Buffer::Indices"; @@ -197,7 +198,7 @@ namespace rawrbox { IBData.DataSize = IndcBuffDesc.Size; device->CreateBuffer(IndcBuffDesc, &IBData, &this->_ibh); - if (this->_ibh == nullptr) throw this->_logger->error("Failed to create index buffer"); + if (this->_ibh == nullptr) CRITICAL_RAWRBOX("Failed to create index buffer"); rawrbox::BarrierUtils::barrier({{this->_ibh, Diligent::RESOURCE_STATE_UNKNOWN, Diligent::RESOURCE_STATE_INDEX_BUFFER, Diligent::STATE_TRANSITION_FLAG_UPDATE_STATE}}); } @@ -206,7 +207,7 @@ namespace rawrbox { auto* device = rawrbox::RENDERER->device(); auto vertSize = static_cast(std::max(this->_mesh->vertices.capacity(), this->isDynamic() ? 1U : 0U)); // RESIZABLE requires at least one vertice - if (vertSize == 0) throw this->_logger->error("Vertices data cannot be empty!"); + if (vertSize == 0) CRITICAL_RAWRBOX("Vertices data cannot be empty!"); Diligent::BufferDesc VertBuffDesc; VertBuffDesc.Name = "RawrBox::Buffer::Vertex"; @@ -219,7 +220,7 @@ namespace rawrbox { VBData.DataSize = VertBuffDesc.Size; device->CreateBuffer(VertBuffDesc, &VBData, &this->_vbh); - if (this->_vbh == nullptr) throw this->_logger->error("Failed to create vertex buffer"); + if (this->_vbh == nullptr) CRITICAL_RAWRBOX("Failed to create vertex buffer"); rawrbox::BarrierUtils::barrier({{this->_vbh, Diligent::RESOURCE_STATE_UNKNOWN, Diligent::RESOURCE_STATE_VERTEX_BUFFER, Diligent::STATE_TRANSITION_FLAG_UPDATE_STATE}}); } @@ -243,7 +244,7 @@ namespace rawrbox { // BLEND SHAPES --- bool createBlendShape(const std::string& id, const std::vector& newVertexPos, const std::vector& newNormPos, float weight = 0.F) { - if (this->_mesh == nullptr) throw this->_logger->error("Mesh not initialized!"); + if (this->_mesh == nullptr) CRITICAL_RAWRBOX("Mesh not initialized!"); auto blend = std::make_unique>(); blend->pos = newVertexPos; @@ -340,7 +341,7 @@ namespace rawrbox { // ---- virtual void upload(rawrbox::UploadType type = rawrbox::UploadType::STATIC) { - if (this->isUploaded()) throw this->_logger->error("Already uploaded!"); + if (this->isUploaded()) CRITICAL_RAWRBOX("Already uploaded!"); this->_uploadType = type; // BUFFERS ---- @@ -354,8 +355,8 @@ namespace rawrbox { } virtual void draw() { - if (!this->isUploaded()) throw this->_logger->error("Failed to render model, vertex / index buffer is not uploaded"); - if (this->_material == nullptr) throw this->_logger->error("Material not set"); + if (!this->isUploaded()) CRITICAL_RAWRBOX("Failed to render model, vertex / index buffer is not uploaded"); + if (this->_material == nullptr) CRITICAL_RAWRBOX("Material not set"); auto* context = rawrbox::RENDERER->context(); diff --git a/rawrbox.render/include/rawrbox/render/models/instanced.hpp b/rawrbox.render/include/rawrbox/render/models/instanced.hpp index c88ffa24..b592535c 100644 --- a/rawrbox.render/include/rawrbox/render/models/instanced.hpp +++ b/rawrbox.render/include/rawrbox/render/models/instanced.hpp @@ -35,7 +35,7 @@ namespace rawrbox { } virtual void setTemplate(rawrbox::Mesh mesh) { - if (mesh.empty()) throw this->_logger->error("Invalid mesh! Missing vertices / indices!"); + if (mesh.empty()) CRITICAL_RAWRBOX("Invalid mesh! Missing vertices / indices!"); this->_mesh = std::make_unique>(mesh); if (this->isUploaded() && this->isDynamic()) { @@ -44,7 +44,7 @@ namespace rawrbox { } [[nodiscard]] virtual rawrbox::Mesh& getTemplate() const { - if (this->_mesh == nullptr) throw this->_logger->error("Invalid mesh! Missing vertices / indices!"); + if (this->_mesh == nullptr) CRITICAL_RAWRBOX("Invalid mesh! Missing vertices / indices!"); return *this->_mesh; } @@ -53,12 +53,12 @@ namespace rawrbox { } virtual void removeInstance(size_t i = 0) { - if (i >= this->_instances.size()) throw this->_logger->error("Failed to find instance"); + if (i >= this->_instances.size()) CRITICAL_RAWRBOX("Failed to find instance"); this->_instances.erase(this->_instances.begin() + i); } [[nodiscard]] rawrbox::Instance& getInstance(size_t i = 0) { - if (i >= this->_instances.size()) throw this->_logger->error("Failed to find instance"); + if (i >= this->_instances.size()) CRITICAL_RAWRBOX("Failed to find instance"); return this->_instances[i]; } @@ -92,7 +92,7 @@ namespace rawrbox { } virtual void updateInstances() { - if (this->_dataBuffer == nullptr) throw this->_logger->error("Data buffer not valid! Did you call upload()?"); + if (this->_dataBuffer == nullptr) CRITICAL_RAWRBOX("Data buffer not valid! Did you call upload()?"); auto* context = rawrbox::RENDERER->context(); auto* device = rawrbox::RENDERER->device(); @@ -114,7 +114,7 @@ namespace rawrbox { } void draw() override { - if (!this->isUploaded()) throw this->_logger->error("Failed to render model, vertex / index buffer is not uploaded"); + if (!this->isUploaded()) CRITICAL_RAWRBOX("Failed to render model, vertex / index buffer is not uploaded"); if (this->_instances.empty()) return; auto* context = rawrbox::RENDERER->context(); diff --git a/rawrbox.render/include/rawrbox/render/models/model.hpp b/rawrbox.render/include/rawrbox/render/models/model.hpp index d04d949d..dfc33bf7 100644 --- a/rawrbox.render/include/rawrbox/render/models/model.hpp +++ b/rawrbox.render/include/rawrbox/render/models/model.hpp @@ -67,13 +67,13 @@ namespace rawrbox { if constexpr (supportsBones) { this->processSkeletonAnimations(dynamic_cast(sample)); } else { - throw this->_logger->error("Failed to play animation {}, model does not support bones", sample->getAnimation()->name()); + CRITICAL_RAWRBOX("Failed to play animation {}, model does not support bones", sample->getAnimation()->name()); } break; default: case ozz::animation::UNKNOWN: - throw this->_logger->error("Unknown animation type"); + CRITICAL_RAWRBOX("Unknown animation type"); } } @@ -213,22 +213,22 @@ namespace rawrbox { virtual void optimize(float complexity_threshold = 0.9F) { for (auto& mesh : this->_meshes) { if (mesh == nullptr || mesh->empty()) continue; -#ifdef _DEBUG + size_t oldVerts = mesh->vertices.size(); size_t oldInds = mesh->indices.size(); -#endif + rawrbox::MeshOptimization::optimize(mesh->vertices, mesh->indices); rawrbox::MeshOptimization::simplify(mesh->vertices, mesh->indices, complexity_threshold); -#ifdef _DEBUG - if (oldVerts != mesh->vertices.size() || oldInds != mesh->indices.size()) this->_logger->info("Optimized mesh for rendering (Before {} | After {})", oldVerts, mesh->vertices.size()); -#endif + + if (oldVerts != mesh->vertices.size() || oldInds != mesh->indices.size()) { + this->_logger->debug("Optimized mesh for rendering ({} -> {}), ideally you should optimize the model on a external tool.", fmt::styled(oldVerts, fmt::fg(fmt::color::cyan)), fmt::styled(mesh->vertices.size(), fmt::fg(fmt::color::cyan))); + } } } virtual void merge() { -#ifdef _DEBUG size_t old = this->_meshes.size(); -#endif + for (size_t i1 = 0; i1 < this->_meshes.size(); i1++) { auto& mesh1 = this->_meshes[i1]; @@ -259,14 +259,12 @@ namespace rawrbox { } } -#ifdef _DEBUG - if (old != this->_meshes.size() && !this->isUploaded()) this->_logger->info("Merged mesh for rendering (Before {} | After {}), this will only display once to prevent spam.", old, this->_meshes.size()); // Only do it once -#endif + if (old != this->_meshes.size() && !this->isUploaded()) this->_logger->debug("Merged mesh for rendering ({} -> {})", fmt::styled(old, fmt::fg(fmt::color::cyan)), fmt::styled(this->_meshes.size(), fmt::fg(fmt::color::cyan))); // Only do it once } void updateBuffers() override { - if (!this->isUploaded()) throw this->_logger->error("Model is not uploaded!"); - if (!this->isDynamic()) throw this->_logger->error("Model is not dynamic!"); + if (!this->isUploaded()) CRITICAL_RAWRBOX("Model is not uploaded!"); + if (!this->isDynamic()) CRITICAL_RAWRBOX("Model is not dynamic!"); this->flattenMeshes(); rawrbox::ModelBase::updateBuffers(); @@ -274,7 +272,7 @@ namespace rawrbox { // ANIMATIONS ---- virtual bool blendAnimation(const std::string& /*otherAnim*/, float /*blend*/) { - throw this->_logger->error("TODO"); + CRITICAL_RAWRBOX("TODO"); } virtual std::vector playAnimation(std::function onComplete = nullptr) { @@ -402,7 +400,7 @@ namespace rawrbox { } virtual rawrbox::Mesh* addMesh(size_t index, rawrbox::Mesh mesh) { - if (index >= this->_meshes.size()) throw this->_logger->error("Index out of bounds"); + if (index >= this->_meshes.size()) CRITICAL_RAWRBOX("Index out of bounds"); this->_bbox.combine(mesh.getBBOX()); mesh.owner = this; diff --git a/rawrbox.render/include/rawrbox/render/models/spline.hpp b/rawrbox.render/include/rawrbox/render/models/spline.hpp index 91f75018..bcef65ba 100644 --- a/rawrbox.render/include/rawrbox/render/models/spline.hpp +++ b/rawrbox.render/include/rawrbox/render/models/spline.hpp @@ -78,7 +78,7 @@ namespace rawrbox { } virtual void generateMesh() { - if (this->_shape == nullptr) throw this->_logger->error("Missing mesh shape!"); + if (this->_shape == nullptr) CRITICAL_RAWRBOX("Missing mesh shape!"); this->_mesh->clear(); std::vector shapeSegments = this->_shape->getLineSegments(); diff --git a/rawrbox.render/include/rawrbox/render/models/utils/mesh.hpp b/rawrbox.render/include/rawrbox/render/models/utils/mesh.hpp index aad6e07e..551546af 100644 --- a/rawrbox.render/include/rawrbox/render/models/utils/mesh.hpp +++ b/rawrbox.render/include/rawrbox/render/models/utils/mesh.hpp @@ -376,7 +376,7 @@ namespace rawrbox { template requires(std::derived_from) static rawrbox::Mesh generateCone(const rawrbox::Vector3f& pos, const rawrbox::Vector3f& size, const uint16_t ratio = 11, const rawrbox::Colorf& cl = rawrbox::Colors::White()) { - if (ratio < 3) throw rawrbox::Logger::err("RawrBox-MeshUtils", "'generateCone' ratio '{}' needs to be at least 3", ratio); + if (ratio < 3) throw std::runtime_error(fmt::format("[RawrBox-MeshUtils] 'generateCone' ratio '{}' needs to be at least 3", ratio)); rawrbox::Mesh mesh = {}; @@ -452,7 +452,7 @@ namespace rawrbox { template requires(std::derived_from) static rawrbox::Mesh generateCylinder(const rawrbox::Vector3f& pos, const rawrbox::Vector3f& size, const uint16_t ratio = 11, const rawrbox::Colorf& cl = rawrbox::Colors::White()) { - if (ratio < 3) throw rawrbox::Logger::err("RawrBox-MeshUtils", "'generateCylinder' ratio '{}' needs to be at least 3", ratio); + if (ratio < 3) throw std::runtime_error(fmt::format("[RawrBox-MeshUtils] 'generateCylinder' ratio '{}' needs to be at least 3", ratio)); rawrbox::Mesh mesh = {}; @@ -544,7 +544,7 @@ namespace rawrbox { template requires(std::derived_from) static rawrbox::Mesh generateSphere(const rawrbox::Vector3f& pos, const rawrbox::Vector3f& size, float ratio = 1, const rawrbox::Colorf& cl = rawrbox::Colors::White()) { - if (ratio <= 0.F) throw rawrbox::Logger::err("RawrBox-MeshUtils", "'generateSphere' ratio '{}' cannot be less than 0", ratio); + if (ratio <= 0.F) throw std::runtime_error(fmt::format("[RawrBox-MeshUtils] 'generateSphere' ratio '{}' cannot be less than 0", ratio)); rawrbox::Mesh mesh = {}; auto sphereSize = size / 2; @@ -683,7 +683,7 @@ namespace rawrbox { requires(std::derived_from) static rawrbox::Mesh generateGrid(uint16_t size, const rawrbox::Vector3f& pos, const rawrbox::Colorf& cl = rawrbox::Colors::Gray().strength(0.4F), const rawrbox::Colorf& borderCl = rawrbox::Colors::Transparent()) { if constexpr (supportsNormals) { - throw rawrbox::Logger::err("RawrBox-MeshUtils", "'generateGrid' does not support normals"); + throw std::runtime_error("[RawrBox-MeshUtils] 'generateGrid' does not support normals"); } rawrbox::Mesh mesh = {}; diff --git a/rawrbox.render/include/rawrbox/render/particles/emitter.hpp b/rawrbox.render/include/rawrbox/render/particles/emitter.hpp index b8a9e4b3..b92daa2e 100644 --- a/rawrbox.render/include/rawrbox/render/particles/emitter.hpp +++ b/rawrbox.render/include/rawrbox/render/particles/emitter.hpp @@ -143,10 +143,10 @@ namespace rawrbox { // -------- virtual void upload() { - if (this->_buffer != nullptr) throw this->_logger->error("Emitter already uploaded"); + if (this->_buffer != nullptr) CRITICAL_RAWRBOX("Emitter already uploaded"); auto* engine = rawrbox::RENDERER->getPlugin("ParticleEngine"); - if (engine == nullptr) throw this->_logger->error("Emitter requires the `ParticleEngine` renderer plugin"); + if (engine == nullptr) CRITICAL_RAWRBOX("Emitter requires the `ParticleEngine` renderer plugin"); // Create data -- Diligent::BufferDesc BuffDesc; @@ -181,7 +181,7 @@ namespace rawrbox { auto* context = rawrbox::RENDERER->context(); auto* engine = rawrbox::RENDERER->getPlugin("ParticleEngine"); - if (engine == nullptr) throw this->_logger->error("Emitter requires the `ParticleEngine` renderer plugin"); + if (engine == nullptr) CRITICAL_RAWRBOX("Emitter requires the `ParticleEngine` renderer plugin"); auto* bind = engine->getBind(); this->_uniforms.time += rawrbox::DELTA_TIME; diff --git a/rawrbox.render/include/rawrbox/render/renderer.hpp b/rawrbox.render/include/rawrbox/render/renderer.hpp index 55856d4e..39fe6e02 100644 --- a/rawrbox.render/include/rawrbox/render/renderer.hpp +++ b/rawrbox.render/include/rawrbox/render/renderer.hpp @@ -125,11 +125,11 @@ namespace rawrbox { template requires(std::derived_from) T* addPlugin(CallbackArgs&&... args) { - if (this->_initialized) throw this->_logger->error("'addPlugin' must be called before 'init'!"); + if (this->_initialized) CRITICAL_RAWRBOX("'addPlugin' must be called before 'init'!"); auto renderPass = std::make_unique(std::forward(args)...); auto id = renderPass->getID(); - if (this->_renderPlugins.contains(id)) throw this->_logger->error("Plugin '{}' already registered!", id); + if (this->_renderPlugins.contains(id)) CRITICAL_RAWRBOX("Plugin '{}' already registered!", id); auto* pass = renderPass.get(); this->_renderPlugins[id] = std::move(renderPass); diff --git a/rawrbox.render/include/rawrbox/render/textures/utils/utils.hpp b/rawrbox.render/include/rawrbox/render/textures/utils/utils.hpp index c322d11e..a5630a57 100644 --- a/rawrbox.render/include/rawrbox/render/textures/utils/utils.hpp +++ b/rawrbox.render/include/rawrbox/render/textures/utils/utils.hpp @@ -2,6 +2,7 @@ #include #include +#include #include @@ -19,6 +20,9 @@ namespace rawrbox { struct ImageData; class TextureUtils { + protected: + static std::unique_ptr _logger; + public: static rawrbox::Vector4f atlasToUV(const rawrbox::Vector2i& atlasSize, uint32_t spriteSize, uint32_t id); static std::vector generateCheckboard(const rawrbox::Vector2u& size, const rawrbox::Color& color1, const rawrbox::Color& color2, uint32_t amount); diff --git a/rawrbox.render/include/rawrbox/render/utils/barrier.hpp b/rawrbox.render/include/rawrbox/render/utils/barrier.hpp index e5b4ba9f..7153f288 100644 --- a/rawrbox.render/include/rawrbox/render/utils/barrier.hpp +++ b/rawrbox.render/include/rawrbox/render/utils/barrier.hpp @@ -1,6 +1,7 @@ #pragma once #include +#include #include #include @@ -14,6 +15,8 @@ namespace rawrbox { static std::unordered_map _barrierCache; // ------------------------- + static std::unique_ptr _logger; + public: static void barrier(const std::vector& resources); static void clearBarrierCache(); diff --git a/rawrbox.render/src/bindless.cpp b/rawrbox.render/src/bindless.cpp index 6db7295c..cc9c7b00 100644 --- a/rawrbox.render/src/bindless.cpp +++ b/rawrbox.render/src/bindless.cpp @@ -28,7 +28,7 @@ namespace rawrbox { // -------------- void BindlessManager::init() { - if (signature != nullptr) throw _logger->error("Signature already bound!"); + if (signature != nullptr) CRITICAL_RAWRBOX("Signature already bound!"); _logger->info("Initializing bindless manager"); auto* renderer = rawrbox::RENDERER; @@ -238,13 +238,13 @@ namespace rawrbox { // REGISTER TEXTURES ------- void BindlessManager::registerTexture(rawrbox::TextureRender& texture) { - if (signature == nullptr) throw _logger->error("Signature not bound! Did you call init?"); + if (signature == nullptr) CRITICAL_RAWRBOX("Signature not bound! Did you call init?"); if (texture.isRegistered()) return; // Check if it's already registered -- auto* pDepthSRV = texture.getDepth(); // Get depth if (pDepthSRV != nullptr) { auto id = internalRegister(pDepthSRV, rawrbox::TEXTURE_TYPE::PIXEL); - _logger->info("Registering {} bindless texture '{}' on slot '{}'", fmt::styled("DEPTH", fmt::fg(fmt::color::red)), fmt::styled(texture.getName(), fmt::fg(fmt::color::violet)), fmt::styled(std::to_string(id), fmt::fg(fmt::color::violet))); + _logger->debug("Registering {} bindless texture '{}' on slot '{}'", fmt::styled("DEPTH", fmt::fg(fmt::color::red)), fmt::styled(texture.getName(), fmt::fg(fmt::color::violet)), fmt::styled(std::to_string(id), fmt::fg(fmt::color::violet))); // Register depth texture.setDepthTextureID(id); @@ -256,15 +256,15 @@ namespace rawrbox { } void BindlessManager::registerTexture(rawrbox::TextureBase& texture) { - if (signature == nullptr) throw _logger->error("Signature not bound! Did you call init?"); + if (signature == nullptr) CRITICAL_RAWRBOX("Signature not bound! Did you call init?"); if (texture.isRegistered()) return; // Check if it's already registered -- auto* pTextureSRV = texture.getHandle(); // Get shader resource view from the texture - if (pTextureSRV == nullptr) throw _logger->error("Failed to register texture '{}'! Texture view is null, not uploaded?", texture.getName()); + if (pTextureSRV == nullptr) CRITICAL_RAWRBOX("Failed to register texture '{}'! Texture view is null, not uploaded?", texture.getName()); const bool isVertex = texture.getType() == rawrbox::TEXTURE_TYPE::VERTEX; const auto id = internalRegister(pTextureSRV, texture.getType()); - _logger->info("Registering bindless {} texture '{}' on slot '{}'", isVertex ? "vertex" : "pixel", fmt::styled(texture.getName(), fmt::fg(fmt::color::violet)), fmt::styled(std::to_string(id), fmt::fg(fmt::color::violet))); + _logger->debug("Registering bindless {} texture '{}' on slot '{}'", isVertex ? "vertex" : "pixel", fmt::styled(texture.getName(), fmt::fg(fmt::color::violet)), fmt::styled(std::to_string(id), fmt::fg(fmt::color::violet))); // Register for updates registerUpdateTexture(texture); @@ -281,8 +281,8 @@ namespace rawrbox { const auto id = texture.getTextureID(); const auto depthId = texture.getDepthTextureID(); - if (id >= handler.size()) throw _logger->error("Index '{}' not found!", id); - if (depthId >= handler.size()) throw _logger->error("Depth index '{}' not found!", id); + if (id >= handler.size()) CRITICAL_RAWRBOX("Index '{}' not found!", id); + if (depthId >= handler.size()) CRITICAL_RAWRBOX("Depth index '{}' not found!", id); // Cleanup ---- unregisterUpdateTexture(texture); @@ -292,7 +292,7 @@ namespace rawrbox { // -------------------- // No need to update signature, it will be overriden by another texture - _logger->info("Un-registering bindless {} texture slot '{}'", isVertex ? "vertex" : "pixel", fmt::styled(std::to_string(id), fmt::fg(fmt::color::violet))); + _logger->debug("Un-registering bindless {} texture slot '{}'", isVertex ? "vertex" : "pixel", fmt::styled(std::to_string(id), fmt::fg(fmt::color::violet))); } void BindlessManager::registerUpdateTexture(rawrbox::TextureBase& texture) { @@ -314,7 +314,7 @@ namespace rawrbox { int size = static_cast(handler.size()); if (size == static_cast(max / 1.2F)) _logger->warn("Aproaching max texture limit of {}", fmt::styled(std::to_string(max), fmt::fg(fmt::color::red))); - if (size >= static_cast(max)) throw _logger->error("Max texture limit reached! Cannot allocate texture, remove some unecessary textures or increase max textures on renderer"); + if (size >= static_cast(max)) CRITICAL_RAWRBOX("Max texture limit reached! Cannot allocate texture, remove some unecessary textures or increase max textures on renderer"); int id = -1; diff --git a/rawrbox.render/src/cameras/base.cpp b/rawrbox.render/src/cameras/base.cpp index dd9abd0f..3846f0b8 100644 --- a/rawrbox.render/src/cameras/base.cpp +++ b/rawrbox.render/src/cameras/base.cpp @@ -11,7 +11,7 @@ namespace rawrbox { } void CameraBase::initialize() { - if (this->_staticUniforms != nullptr) throw this->_logger->error("Camera already initialized!"); + if (this->_staticUniforms != nullptr) CRITICAL_RAWRBOX("Camera already initialized!"); { auto staticData = this->getStaticData(); @@ -46,7 +46,7 @@ namespace rawrbox { this->_logger->info("Initializing camera"); } - void CameraBase::updateMtx() { throw this->_logger->error("Not implemented"); }; + void CameraBase::updateMtx() { CRITICAL_RAWRBOX("Not implemented"); }; rawrbox::CameraStaticUniforms CameraBase::getStaticData() { auto screenSize = rawrbox::RENDERER->getSize().cast(); @@ -135,7 +135,7 @@ namespace rawrbox { } void CameraBase::updateBuffer() { - if (this->_uniforms == nullptr) throw this->_logger->error("Buffer not initialized! Did you call initialize?"); + if (this->_uniforms == nullptr) CRITICAL_RAWRBOX("Buffer not initialized! Did you call initialize?"); auto view = rawrbox::Matrix4x4::mtxTranspose(this->getViewMtx()); auto viewInv = rawrbox::Matrix4x4::mtxInverse(this->getViewMtx()); @@ -158,11 +158,11 @@ namespace rawrbox { void CameraBase::update() {} rawrbox::Vector3f CameraBase::worldToScreen(const rawrbox::Vector3f& /*pos*/) const { - throw this->_logger->error("Not implemented"); + CRITICAL_RAWRBOX("Not implemented"); } rawrbox::Vector3f CameraBase::screenToWorld(const rawrbox::Vector2f& /*screen_pos*/, const rawrbox::Vector3f& /*origin*/) const { - throw this->_logger->error("Not implemented"); + CRITICAL_RAWRBOX("Not implemented"); } Diligent::IBuffer* CameraBase::uniforms() const { return this->_uniforms; } diff --git a/rawrbox.render/src/decals/decal.cpp b/rawrbox.render/src/decals/decal.cpp index d267ee8f..60ab8ace 100644 --- a/rawrbox.render/src/decals/decal.cpp +++ b/rawrbox.render/src/decals/decal.cpp @@ -2,12 +2,20 @@ #include namespace rawrbox { + // PRIVATE --- + std::unique_ptr Decal::_logger = std::make_unique("RawrBox-DECAL"); + // ------ + Decal::Decal(const rawrbox::Matrix4x4& _mtx, const rawrbox::TextureBase& _texture, const rawrbox::Colorf& _color, uint32_t _atlas) : worldToLocal(_mtx), color(_color) { this->setTexture(_texture, _atlas); } void Decal::setTexture(const rawrbox::TextureBase& texture, uint32_t id) { - if (!texture.isValid()) throw rawrbox::Logger::err("RawrBox-DECAL", "Invalid texture, not uploaded?"); + if (!texture.isValid()) { + ERROR_RAWRBOX("Invalid texture, not uploaded?"); + return; + } + this->data.x = texture.getTextureID(); this->data.y = id; diff --git a/rawrbox.render/src/decals/manager.cpp b/rawrbox.render/src/decals/manager.cpp index 9ead4a6a..c7c2d95d 100644 --- a/rawrbox.render/src/decals/manager.cpp +++ b/rawrbox.render/src/decals/manager.cpp @@ -84,7 +84,7 @@ namespace rawrbox { } void DECALS::updateBuffer() { - if (_buffer == nullptr) throw _logger->error("Buffer not initialized! Did you call 'init' ?"); + if (_buffer == nullptr) CRITICAL_RAWRBOX("Buffer not initialized! Did you call 'init' ?"); if (!rawrbox::__DECALS_DIRTY__ || _decals.empty()) return; auto* device = rawrbox::RENDERER->device(); @@ -110,7 +110,7 @@ namespace rawrbox { } void DECALS::update() { - if (uniforms == nullptr) throw _logger->error("Buffer not initialized! Did you call 'init' ?"); + if (uniforms == nullptr) CRITICAL_RAWRBOX("Buffer not initialized! Did you call 'init' ?"); updateBuffer(); // Update all decals if dirty updateConstants(); // Update buffer if dirty @@ -119,7 +119,7 @@ namespace rawrbox { // UTILS ---- Diligent::IBufferView* DECALS::getBuffer() { return _bufferRead; } const rawrbox::Decal& DECALS::get(size_t indx) { - if (indx >= _decals.size()) throw _logger->error("Invalid decal index {}", indx); + if (indx >= _decals.size()) CRITICAL_RAWRBOX("Invalid decal index {}", indx); return _decals[indx]; } diff --git a/rawrbox.render/src/lights/manager.cpp b/rawrbox.render/src/lights/manager.cpp index 51b4f4ec..2157513e 100644 --- a/rawrbox.render/src/lights/manager.cpp +++ b/rawrbox.render/src/lights/manager.cpp @@ -92,7 +92,7 @@ namespace rawrbox { } void LIGHTS::updateBuffer() { - if (_buffer == nullptr) throw _logger->error("Buffer not initialized! Did you call 'init' ?"); + if (_buffer == nullptr) CRITICAL_RAWRBOX("Buffer not initialized! Did you call 'init' ?"); if (!rawrbox::__LIGHT_DIRTY__ || _lights.empty()) return; // Update lights --- @@ -150,7 +150,7 @@ namespace rawrbox { } void LIGHTS::update() { - if (uniforms == nullptr) throw _logger->error("Buffer not initialized! Did you call 'init' ?"); + if (uniforms == nullptr) CRITICAL_RAWRBOX("Buffer not initialized! Did you call 'init' ?"); updateBuffer(); // Update all lights if dirty updateConstants(); // Update buffer if dirty diff --git a/rawrbox.render/src/materials/lit.cpp b/rawrbox.render/src/materials/lit.cpp index 25afec0b..2a85d345 100644 --- a/rawrbox.render/src/materials/lit.cpp +++ b/rawrbox.render/src/materials/lit.cpp @@ -22,7 +22,7 @@ namespace rawrbox { void MaterialLit::createPipelines(const std::string& id, const std::vector& layout, const Diligent::ShaderMacroHelper& helper) { auto* cluster = rawrbox::RENDERER->getPlugin("Clustered"); - if (cluster == nullptr) throw this->_logger->error("This material requires the `Clustered` renderer plugin"); + if (cluster == nullptr) CRITICAL_RAWRBOX("This material requires the `Clustered` renderer plugin"); // PIPELINE ---- rawrbox::PipeSettings settings; diff --git a/rawrbox.render/src/materials/particle.cpp b/rawrbox.render/src/materials/particle.cpp index f55c81e9..a4736e27 100644 --- a/rawrbox.render/src/materials/particle.cpp +++ b/rawrbox.render/src/materials/particle.cpp @@ -23,7 +23,7 @@ namespace rawrbox { void MaterialParticle::createPipelines(const std::string& id, const std::vector& /*layout*/, const Diligent::ShaderMacroHelper& /*helper*/) { auto* engine = rawrbox::RENDERER->getPlugin("ParticleEngine"); - if (engine == nullptr) throw this->_logger->error("This material requires the `ParticleEngine` renderer plugin"); + if (engine == nullptr) CRITICAL_RAWRBOX("This material requires the `ParticleEngine` renderer plugin"); // PIPELINE ---- rawrbox::PipeSettings settings; settings.pVS = "particle.vsh"; diff --git a/rawrbox.render/src/plugins/clustered.cpp b/rawrbox.render/src/plugins/clustered.cpp index 6f2ef8a3..a17c83b1 100644 --- a/rawrbox.render/src/plugins/clustered.cpp +++ b/rawrbox.render/src/plugins/clustered.cpp @@ -29,8 +29,8 @@ namespace rawrbox { CLUSTERS_GROUP_SIZE = CLUSTERS_X * CLUSTERS_Y * RB_RENDER_CLUSTERS_Z; - if constexpr (RB_RENDER_CLUSTERS_Z % RB_RENDER_CLUSTERS_Z_THREADS != 0) throw this->_logger->error("Number of cluster depth slices must be divisible by thread count z-dimension"); - if constexpr (RB_RENDER_MAX_DATA_PER_CLUSTER % 32 != 0) throw this->_logger->error("MAX_DATA_PER_CLUSTER must be divisible by 32"); + if constexpr (RB_RENDER_CLUSTERS_Z % RB_RENDER_CLUSTERS_Z_THREADS != 0) CRITICAL_RAWRBOX("Number of cluster depth slices must be divisible by thread count z-dimension"); + if constexpr (RB_RENDER_MAX_DATA_PER_CLUSTER % 32 != 0) CRITICAL_RAWRBOX("MAX_DATA_PER_CLUSTER must be divisible by 32"); // Setup dispatch --- this->_dispatch.ThreadGroupCountX = rawrbox::MathUtils::divideRound(CLUSTERS_X, RB_RENDER_CLUSTERS_X_THREADS); @@ -96,10 +96,10 @@ namespace rawrbox { auto* camera = renderer->camera(); auto* context = renderer->context(); - if (renderer == nullptr) throw this->_logger->error("Renderer not initialized!"); - if (camera == nullptr) throw this->_logger->error("Camera not initialized!"); + if (renderer == nullptr) CRITICAL_RAWRBOX("Renderer not initialized!"); + if (camera == nullptr) CRITICAL_RAWRBOX("Camera not initialized!"); - if (this->_clusterBuildingComputeProgram == nullptr || this->_cullingComputeProgram == nullptr || this->_cullingResetProgram == nullptr) throw this->_logger->error("Compute pipelines not initialized, did you call 'initialize'"); + if (this->_clusterBuildingComputeProgram == nullptr || this->_cullingComputeProgram == nullptr || this->_cullingResetProgram == nullptr) CRITICAL_RAWRBOX("Compute pipelines not initialized, did you call 'initialize'"); // Update light & decals rawrbox::LIGHTS::update(); @@ -193,8 +193,8 @@ namespace rawrbox { } void ClusteredPlugin::buildSignatures() { - if (this->_signature != nullptr || this->_signatureBind != nullptr) throw this->_logger->error("Signatures already bound!"); - if (rawrbox::MAIN_CAMERA == nullptr) throw this->_logger->error("Clustered plugin requires at least one camera!"); + if (this->_signature != nullptr || this->_signatureBind != nullptr) CRITICAL_RAWRBOX("Signatures already bound!"); + if (rawrbox::MAIN_CAMERA == nullptr) CRITICAL_RAWRBOX("Clustered plugin requires at least one camera!"); std::vector resources = { // CAMERA ------ @@ -250,7 +250,7 @@ namespace rawrbox { } void ClusteredPlugin::buildPipelines() { - if (rawrbox::MAIN_CAMERA == nullptr) throw this->_logger->error("Clustered plugin requires at least one camera!"); + if (rawrbox::MAIN_CAMERA == nullptr) CRITICAL_RAWRBOX("Clustered plugin requires at least one camera!"); rawrbox::PipeComputeSettings settings; settings.macros = this->getClusterMacros(); diff --git a/rawrbox.render/src/plugins/particle_engine.cpp b/rawrbox.render/src/plugins/particle_engine.cpp index ab6c3016..b0173462 100644 --- a/rawrbox.render/src/plugins/particle_engine.cpp +++ b/rawrbox.render/src/plugins/particle_engine.cpp @@ -16,8 +16,8 @@ namespace rawrbox { } void ParticleEnginePlugin::createSignatures() { - if (this->_signature != nullptr || this->_signatureBind != nullptr) throw this->_logger->error("Signatures already bound!"); - if (rawrbox::MAIN_CAMERA == nullptr) throw this->_logger->error("Clustered plugin requires at least one camera!"); + if (this->_signature != nullptr || this->_signatureBind != nullptr) CRITICAL_RAWRBOX("Signatures already bound!"); + if (rawrbox::MAIN_CAMERA == nullptr) CRITICAL_RAWRBOX("Clustered plugin requires at least one camera!"); std::vector resources = { // CAMERA ------ @@ -86,7 +86,7 @@ namespace rawrbox { } void ParticleEnginePlugin::createPipelines() { - if (rawrbox::MAIN_CAMERA == nullptr) throw this->_logger->error("Particle engine plugin requires at least one camera!"); + if (rawrbox::MAIN_CAMERA == nullptr) CRITICAL_RAWRBOX("Particle engine plugin requires at least one camera!"); rawrbox::PipeComputeSettings settings; settings.signatures = {this->_signature}; @@ -140,13 +140,13 @@ namespace rawrbox { // RENDERING --- void ParticleEnginePlugin::setupEmitter(rawrbox::Emitter<>* emitter) { - if (emitter == nullptr) throw _logger->error("Invalid emitter"); - if (this->_signature == nullptr || this->_signatureBind == nullptr || this->_uniforms == nullptr) throw _logger->error("Plugin not uploaded!"); + if (emitter == nullptr) CRITICAL_RAWRBOX("Invalid emitter"); + if (this->_signature == nullptr || this->_signatureBind == nullptr || this->_uniforms == nullptr) CRITICAL_RAWRBOX("Plugin not uploaded!"); // Update uniforms ---- { Diligent::MapHelper Constants(rawrbox::RENDERER->context(), this->_uniforms, Diligent::MAP_WRITE, Diligent::MAP_FLAG_DISCARD); - if (Constants == nullptr) throw _logger->error("Failed to map emitter constants buffer!"); + if (Constants == nullptr) CRITICAL_RAWRBOX("Failed to map emitter constants buffer!"); std::memcpy(Constants, &emitter->getUniform(), sizeof(rawrbox::EmitterUniforms)); } @@ -158,8 +158,8 @@ namespace rawrbox { } void ParticleEnginePlugin::computeEmitter(rawrbox::Emitter<>* emitter) { - if (emitter == nullptr) throw _logger->error("Invalid emitter"); - if (this->_signature == nullptr || this->_signatureBind == nullptr || this->_uniforms == nullptr) throw _logger->error("Plugin not uploaded!"); + if (emitter == nullptr) CRITICAL_RAWRBOX("Invalid emitter"); + if (this->_signature == nullptr || this->_signatureBind == nullptr || this->_uniforms == nullptr) CRITICAL_RAWRBOX("Plugin not uploaded!"); auto* renderer = rawrbox::RENDERER; auto* context = renderer->context(); diff --git a/rawrbox.render/src/plugins/post_process.cpp b/rawrbox.render/src/plugins/post_process.cpp index 3dc5e502..7b7e349a 100644 --- a/rawrbox.render/src/plugins/post_process.cpp +++ b/rawrbox.render/src/plugins/post_process.cpp @@ -48,12 +48,12 @@ namespace rawrbox { // Post utils ---- void PostProcessPlugin::remove(size_t indx) { - if (this->_postProcesses.empty() || indx >= this->_postProcesses.size()) throw this->_logger->error("Failed to remove {}!", indx); + if (this->_postProcesses.empty() || indx >= this->_postProcesses.size()) CRITICAL_RAWRBOX("Failed to remove {}!", indx); this->_postProcesses.erase(this->_postProcesses.begin() + indx); } rawrbox::PostProcessBase* PostProcessPlugin::get(size_t indx) const { - if (indx >= this->_postProcesses.size()) throw this->_logger->error("Failed to get {}!", indx); + if (indx >= this->_postProcesses.size()) CRITICAL_RAWRBOX("Failed to get {}!", indx); return this->_postProcesses[indx].get(); } diff --git a/rawrbox.render/src/post_process/base.cpp b/rawrbox.render/src/post_process/base.cpp index 0c76ad5e..ed6be61e 100644 --- a/rawrbox.render/src/post_process/base.cpp +++ b/rawrbox.render/src/post_process/base.cpp @@ -6,13 +6,13 @@ namespace rawrbox { void PostProcessBase::init() { auto* plugin = rawrbox::RENDERER->getPlugin("PostProcess"); - if (plugin == nullptr) throw this->_logger->error("Post process plugin requires the 'PostProcess' renderer plugin!"); + if (plugin == nullptr) CRITICAL_RAWRBOX("Post process plugin requires the 'PostProcess' renderer plugin!"); this->_buffer = plugin->getBuffer(); } void PostProcessBase::applyEffect(const rawrbox::TextureBase& texture) { - if (!texture.isValid()) throw this->_logger->error("Effect texture not uploaded!"); + if (!texture.isValid()) CRITICAL_RAWRBOX("Effect texture not uploaded!"); auto* context = rawrbox::RENDERER->context(); context->SetPipelineState(this->_pipeline); @@ -20,7 +20,7 @@ namespace rawrbox { // SETUP UNIFORMS ---------------------------- { Diligent::MapHelper CBConstants(context, this->_buffer, Diligent::MAP_WRITE, Diligent::MAP_FLAG_DISCARD); - if (CBConstants == nullptr) throw _logger->error("Failed to map the postprocess constants buffer!"); + if (CBConstants == nullptr) CRITICAL_RAWRBOX("Failed to map the postprocess constants buffer!"); CBConstants->data = this->_data; CBConstants->textureIDs = {texture.getTextureID(), texture.getDepthTextureID(), 0, 0}; diff --git a/rawrbox.render/src/renderer.cpp b/rawrbox.render/src/renderer.cpp index d3893d2d..c9bf3c9a 100644 --- a/rawrbox.render/src/renderer.cpp +++ b/rawrbox.render/src/renderer.cpp @@ -192,33 +192,33 @@ namespace rawrbox { break; #endif // GL_SUPPORTED - default: throw this->_logger->error("Invalid diligent api"); + default: CRITICAL_RAWRBOX("Invalid diligent api"); } // Check device limitations --- if (!(this->_device->GetAdapterInfo().DrawCommand.CapFlags & Diligent::DRAW_COMMAND_CAP_FLAG_BASE_VERTEX)) { - throw this->_logger->error("Base vertex not supported"); + CRITICAL_RAWRBOX("Base vertex not supported"); } // ---------------------------- // Setup shader pipeline if not exists if (rawrbox::SHADER_FACTORY == nullptr) { auto rootDir = this->getShadersDirectory(); - if (!std::filesystem::exists(rootDir)) throw this->_logger->error("Shaders directory '{}' not found!", rootDir.generic_string()); + if (!std::filesystem::exists(rootDir)) CRITICAL_RAWRBOX("Shaders directory '{}' not found!", rootDir.generic_string()); auto dirs = rawrbox::PathUtils::glob(rootDir, true); auto paths = fmt::format("{}", fmt::join(dirs, ";")); - this->_logger->info("Initializing shader factory (using {}):", fmt::styled(rootDir.generic_string(), fmt::fg(fmt::color::coral))); + this->_logger->debug("Initializing shader factory (using {}):", fmt::styled(rootDir.generic_string(), fmt::fg(fmt::color::coral))); for (const auto& dir : dirs) { - this->_logger->info("\t{}", dir); + this->_logger->debug("\t{}", dir); } this->_engineFactory->CreateDefaultShaderSourceStreamFactory(paths.c_str(), &rawrbox::SHADER_FACTORY); } // ----------- - if (this->_engineFactory == nullptr) throw this->_logger->error("Failed to initialize"); + if (this->_engineFactory == nullptr) CRITICAL_RAWRBOX("Failed to initialize"); // Single draw call to setup window background this->clear(); @@ -242,7 +242,7 @@ namespace rawrbox { // ---------------------- // Setup camera ----- - if (this->_camera == nullptr) throw this->_logger->error("No camera found!"); + if (this->_camera == nullptr) CRITICAL_RAWRBOX("No camera found!"); this->_camera->initialize(); // ------------------ @@ -401,8 +401,8 @@ namespace rawrbox { } void RendererBase::render() { - if (this->_swapChain == nullptr || this->_context == nullptr || this->_device == nullptr) throw this->_logger->error("Failed to bind swapChain / context / device! Did you call 'init' ?"); - if (this->_drawCall == nullptr) throw this->_logger->error("Missing draw call! Did you call 'setDrawCall' ?"); + if (this->_swapChain == nullptr || this->_context == nullptr || this->_device == nullptr) CRITICAL_RAWRBOX("Failed to bind swapChain / context / device! Did you call 'init' ?"); + if (this->_drawCall == nullptr) CRITICAL_RAWRBOX("Missing draw call! Did you call 'setDrawCall' ?"); // Clear backbuffer ---- this->clear(); @@ -420,7 +420,7 @@ namespace rawrbox { for (auto& plugin : this->_renderPlugins) { if (plugin.second == nullptr || !plugin.second->isEnabled()) continue; #ifdef _DEBUG - // this->_context->BeginDebugGroup(plugin.first.c_str()); + // this->_context->BeginDebugGroup(plugin.first.c_str()); #endif plugin.second->preRender(); #ifdef _DEBUG @@ -451,7 +451,7 @@ namespace rawrbox { for (auto& plugin : this->_renderPlugins) { if (plugin.second == nullptr || !plugin.second->isEnabled()) continue; #ifdef _DEBUG - // this->_context->BeginDebugGroup(plugin.first.c_str()); + // this->_context->BeginDebugGroup(plugin.first.c_str()); #endif plugin.second->postRender(*this->_render); #ifdef _DEBUG @@ -472,8 +472,8 @@ namespace rawrbox { this->_drawCall(rawrbox::DrawPass::PASS_OVERLAY); if (this->_stencil != nullptr) this->_stencil->render(); #ifdef _DEBUG - // this->endQuery("OVERLAY"); - // this->_context->EndDebugGroup(); + // this->endQuery("OVERLAY"); + // this->_context->EndDebugGroup(); #endif // ------------------ @@ -572,12 +572,12 @@ namespace rawrbox { } void RendererBase::skipIntros(bool skip) { - if (skip) this->_logger->info("Skipping intros :("); + if (skip) this->_logger->debug("Skipping intros :("); this->_skipIntros = skip; } void RendererBase::addIntro(const std::filesystem::path& webpPath, float speed, bool cover, const rawrbox::Colorf& color) { - if (webpPath.extension() != ".webp") throw this->_logger->error("Invalid intro '{}', only '.webp' format is supported!", webpPath.generic_string()); + if (webpPath.extension() != ".webp") CRITICAL_RAWRBOX("Invalid intro '{}', only '.webp' format is supported!", webpPath.generic_string()); this->_introList[webpPath.generic_string()] = {speed, cover, color}; } //------------------------- @@ -633,7 +633,7 @@ namespace rawrbox { // -------------- if (pipelineHelper == nullptr || durationHelper == nullptr) { - throw this->_logger->error("Failed to create & begin query '{}'", query); + CRITICAL_RAWRBOX("Failed to create & begin query '{}'", query); } // Start queries --- @@ -653,7 +653,7 @@ namespace rawrbox { auto fndDuration = this->_query.find(durationName); if (fndPipeline->second == nullptr || fndDuration->second == nullptr) { - throw this->_logger->error("Failed to end query '{}', not found!", query); + CRITICAL_RAWRBOX("Failed to end query '{}', not found!", query); } // End queries --- @@ -711,11 +711,11 @@ namespace rawrbox { void RendererBase::setVSync(bool vsync) { this->_vsync = vsync; } void RendererBase::gpuPick(const rawrbox::Vector2i& pos, const std::function& callback) { - if (this->_render == nullptr) throw _logger->error("Render target texture not initialized"); - if (callback == nullptr) throw _logger->error("Render target texture not initialized"); + if (this->_render == nullptr) CRITICAL_RAWRBOX("Render target texture not initialized"); + if (callback == nullptr) CRITICAL_RAWRBOX("Render target texture not initialized"); auto size = this->_size.cast(); - if (pos.x < 0 || pos.y < 0 || pos.x >= size.x || pos.y >= size.y) throw _logger->error("Outside of window range"); + if (pos.x < 0 || pos.y < 0 || pos.x >= size.x || pos.y >= size.y) CRITICAL_RAWRBOX("Outside of window range"); Diligent::Box MapRegion; MapRegion.MinX = pos.x; diff --git a/rawrbox.render/src/stencil.cpp b/rawrbox.render/src/stencil.cpp index 893ff196..ddf10c6a 100644 --- a/rawrbox.render/src/stencil.cpp +++ b/rawrbox.render/src/stencil.cpp @@ -33,7 +33,7 @@ namespace rawrbox { } void Stencil::upload() { - if (this->_2dPipeline != nullptr || this->_linePipeline != nullptr) throw this->_logger->error("Upload already called"); + if (this->_2dPipeline != nullptr || this->_linePipeline != nullptr) CRITICAL_RAWRBOX("Upload already called"); // PIPELINE ---- rawrbox::PipeSettings settings; @@ -533,12 +533,12 @@ namespace rawrbox { } void Stencil::render() { - if (!this->_offsets.empty()) throw this->_logger->error("Missing 'popOffset', cannot draw"); - if (!this->_rotations.empty()) throw this->_logger->error("Missing 'popRotation', cannot draw"); - if (!this->_outlines.empty()) throw this->_logger->error("Missing 'popOutline', cannot draw"); - if (!this->_clips.empty()) throw this->_logger->error("Missing 'popClipping', cannot draw"); - if (!this->_scales.empty()) throw this->_logger->error("Missing 'popScale', cannot draw"); - if (!this->_optimizations.empty()) throw this->_logger->error("Missing 'popOptimize', cannot draw"); + if (!this->_offsets.empty()) CRITICAL_RAWRBOX("Missing 'popOffset', cannot draw"); + if (!this->_rotations.empty()) CRITICAL_RAWRBOX("Missing 'popRotation', cannot draw"); + if (!this->_outlines.empty()) CRITICAL_RAWRBOX("Missing 'popOutline', cannot draw"); + if (!this->_clips.empty()) CRITICAL_RAWRBOX("Missing 'popClipping', cannot draw"); + if (!this->_scales.empty()) CRITICAL_RAWRBOX("Missing 'popScale', cannot draw"); + if (!this->_optimizations.empty()) CRITICAL_RAWRBOX("Missing 'popOptimize', cannot draw"); this->internalDraw(); } @@ -552,7 +552,7 @@ namespace rawrbox { } void Stencil::popOffset() { - if (this->_offsets.empty()) throw this->_logger->error("Offset is empty, failed to pop"); + if (this->_offsets.empty()) CRITICAL_RAWRBOX("Offset is empty, failed to pop"); this->_offset -= this->_offsets.back(); this->_offsets.pop_back(); @@ -575,7 +575,7 @@ namespace rawrbox { } void Stencil::popRotation() { - if (this->_rotations.empty()) throw this->_logger->error("Rotations is empty, failed to pop"); + if (this->_rotations.empty()) CRITICAL_RAWRBOX("Rotations is empty, failed to pop"); this->_rotation -= this->_rotations.back(); this->_rotations.pop_back(); @@ -589,7 +589,7 @@ namespace rawrbox { } void Stencil::popOutline() { - if (this->_outlines.empty()) throw this->_logger->error("Outline is empty, failed to pop"); + if (this->_outlines.empty()) CRITICAL_RAWRBOX("Outline is empty, failed to pop"); this->_outline -= this->_outlines.back(); this->_outlines.pop_back(); @@ -605,7 +605,7 @@ namespace rawrbox { } void Stencil::popClipping() { - if (this->_clips.empty()) throw this->_logger->error("Clips is empty, failed to pop"); + if (this->_clips.empty()) CRITICAL_RAWRBOX("Clips is empty, failed to pop"); this->_clips.pop_back(); } // -------------------- @@ -617,7 +617,7 @@ namespace rawrbox { } void Stencil::popScale() { - if (this->_scales.empty()) throw this->_logger->error("Scale is empty, failed to pop"); + if (this->_scales.empty()) CRITICAL_RAWRBOX("Scale is empty, failed to pop"); this->_scale -= this->_scales.back(); this->_scales.pop_back(); @@ -630,7 +630,7 @@ namespace rawrbox { } void Stencil::popOptimize() { - if (this->_optimizations.empty()) throw this->_logger->error("Optimize is empty, failed to pop"); + if (this->_optimizations.empty()) CRITICAL_RAWRBOX("Optimize is empty, failed to pop"); this->_optimizations.pop_back(); } // ------------------- diff --git a/rawrbox.render/src/svg/engine.cpp b/rawrbox.render/src/svg/engine.cpp index fdf422f2..7f9e4ba6 100644 --- a/rawrbox.render/src/svg/engine.cpp +++ b/rawrbox.render/src/svg/engine.cpp @@ -21,7 +21,7 @@ namespace rawrbox { } auto svg = lunasvg::Document::loadFromFile(name); - if (svg == nullptr) throw _logger->error("Failed to load '{}'", name); + if (svg == nullptr) CRITICAL_RAWRBOX("Failed to load '{}'", name); auto* ptr = svg.get(); _svgs[name] = std::move(svg); @@ -54,7 +54,7 @@ namespace rawrbox { if (fnd != _renderedSVGS.end()) return fnd->second.get(); auto* doc = SVGEngine::internalLoad(filename); - if (doc == nullptr) throw _logger->error("Failed to load '{}'", filename.generic_string()); + if (doc == nullptr) CRITICAL_RAWRBOX("Failed to load '{}'", filename.generic_string()); auto img = doc->renderToBitmap(size.x, size.y); auto texture = std::make_unique(size, img.data()); diff --git a/rawrbox.render/src/text/engine.cpp b/rawrbox.render/src/text/engine.cpp index d81da887..ebb82c33 100644 --- a/rawrbox.render/src/text/engine.cpp +++ b/rawrbox.render/src/text/engine.cpp @@ -60,7 +60,7 @@ namespace rawrbox { rawrbox::TexturePack* TextEngine::getPack(uint16_t id) { auto fnd = _packs.find(id); - if (fnd == _packs.end()) throw _logger->error("Failed to find pack id '{}'", id); + if (fnd == _packs.end()) CRITICAL_RAWRBOX("Failed to find pack id '{}'", id); return fnd->second.get(); } @@ -85,7 +85,7 @@ namespace rawrbox { } auto bytes = rawrbox::FileUtils::getRawData(pth); - if (bytes.empty()) throw _logger->error("Failed to load font '{}'", filename.generic_string()); + if (bytes.empty()) CRITICAL_RAWRBOX("Failed to load font '{}'", filename.generic_string()); _fonts[key] = std::make_unique(filename); _fonts[key]->load(bytes, size, index); diff --git a/rawrbox.render/src/text/font.cpp b/rawrbox.render/src/text/font.cpp index d2a19e8e..5e5b1c12 100644 --- a/rawrbox.render/src/text/font.cpp +++ b/rawrbox.render/src/text/font.cpp @@ -31,7 +31,7 @@ namespace rawrbox { // INTERNAL --- void Font::loadFontInfo() { - if (this->_font == nullptr) throw this->_logger->error("Font not loaded"); + if (this->_font == nullptr) CRITICAL_RAWRBOX("Font not loaded"); int ascent = 0; int descent = 0; @@ -56,7 +56,7 @@ namespace rawrbox { } std::unique_ptr Font::bakeGlyphAlpha(uint32_t codePoint) { - if (this->_font == nullptr) throw this->_logger->error("Font not loaded"); + if (this->_font == nullptr) CRITICAL_RAWRBOX("Font not loaded"); int32_t ascent = 0; int32_t descent = 0; @@ -92,7 +92,7 @@ namespace rawrbox { stbtt_MakeCodepointBitmap(this->_font.get(), buffer.data(), ww, hh, dstPitch, scale, scale, codePoint); auto pack = rawrbox::TextEngine::requestPack(ww, hh, Diligent::TEXTURE_FORMAT::TEX_FORMAT_RGBA8_UNORM); // FONT_TYPE_ALPHA - if (pack.second == nullptr) throw this->_logger->error("Failed to generate / get atlas texture"); + if (pack.second == nullptr) CRITICAL_RAWRBOX("Failed to generate / get atlas texture"); auto& packNode = pack.second->addSprite(ww, hh, rawrbox::ColorUtils::setChannels(1, 4, ww, hh, buffer)); auto size = pack.second->getSize(); @@ -122,7 +122,7 @@ namespace rawrbox { // Load this->_font = std::make_shared(); - if (stbtt_InitFont(this->_font.get(), buffer.data(), offset) == 0) throw this->_logger->error("Failed to load font"); + if (stbtt_InitFont(this->_font.get(), buffer.data(), offset) == 0) CRITICAL_RAWRBOX("Failed to load font"); this->_scale = stbtt_ScaleForMappingEmToPixels(this->_font.get(), static_cast(pixelHeight)); this->_pixelSize = static_cast(pixelHeight); @@ -214,7 +214,7 @@ namespace rawrbox { } void Font::render(const std::string& text, const rawrbox::Vector2f& pos, bool yIsUp, const std::function& renderGlyph) const { - if (renderGlyph == nullptr) throw this->_logger->error("Failed to render glyph! Missing 'renderGlyph' param"); + if (renderGlyph == nullptr) CRITICAL_RAWRBOX("Failed to render glyph! Missing 'renderGlyph' param"); auto info = this->getFontInfo(); const float lineHeight = this->getLineHeight(); diff --git a/rawrbox.render/src/textures/animated.cpp b/rawrbox.render/src/textures/animated.cpp index f0d71538..ee43a7db 100644 --- a/rawrbox.render/src/textures/animated.cpp +++ b/rawrbox.render/src/textures/animated.cpp @@ -10,7 +10,7 @@ namespace rawrbox { TextureAnimatedBase::TextureAnimatedBase(const std::filesystem::path& filePath, const std::vector& /*buffer*/, bool /*useFallback*/) : _filePath(filePath) {} // NOLINTEND(modernize-pass-by-value) - void TextureAnimatedBase::internalLoad(const std::vector& /*_buffer*/, bool /*_useFallback*/) { throw this->_logger->error("Not implemented"); } + void TextureAnimatedBase::internalLoad(const std::vector& /*_buffer*/, bool /*_useFallback*/) { CRITICAL_RAWRBOX("Not implemented"); } // ANIMATION ------ void TextureAnimatedBase::update() { diff --git a/rawrbox.render/src/textures/atlas.cpp b/rawrbox.render/src/textures/atlas.cpp index 53892cc5..7eb36ec8 100644 --- a/rawrbox.render/src/textures/atlas.cpp +++ b/rawrbox.render/src/textures/atlas.cpp @@ -8,11 +8,7 @@ namespace rawrbox { TextureAtlas::TextureAtlas(const std::filesystem::path& filePath, const std::vector& buffer, uint32_t spriteSize, bool useFallback) : _spriteSize(spriteSize) { try { this->processAtlas(rawrbox::STBI::decode(buffer)); -#ifdef RAWRBOX_TRACE_EXCEPTIONS - } catch (const cpptrace::exception_with_message& e) { -#else } catch (const std::exception& e) { -#endif if (useFallback) { this->loadFallback(); this->_logger->warn("Failed to load '{}' ──> \n\t{}\n\t\t └── Loading fallback texture!", filePath.generic_string(), e.what()); @@ -26,11 +22,7 @@ namespace rawrbox { TextureAtlas::TextureAtlas(const std::filesystem::path& filePath, uint32_t spriteSize, bool useFallback) : _spriteSize(spriteSize) { try { this->processAtlas(rawrbox::STBI::decode(filePath)); -#ifdef RAWRBOX_TRACE_EXCEPTIONS - } catch (const cpptrace::exception_with_message& e) { -#else } catch (const std::exception& e) { -#endif if (useFallback) { this->loadFallback(); this->_logger->warn("Failed to load '{}' ──> \n\t{}\n\t\t └── Loading fallback texture!", filePath.generic_string(), e.what()); @@ -53,13 +45,13 @@ namespace rawrbox { } std::vector TextureAtlas::getSprite(size_t id) const { - if (id >= this->_data.frames.size()) throw this->_logger->error("Invalid ID {}", id); + if (id >= this->_data.frames.size()) CRITICAL_RAWRBOX("Invalid ID {}", id); return this->_data.frames[id].pixels; } // -------------------- void TextureAtlas::processAtlas(const rawrbox::ImageData& data) { - if (!data.valid() || data.total() == 0) throw this->_logger->error("Invalid image data!"); + if (!data.valid() || data.total() == 0) CRITICAL_RAWRBOX("Invalid image data!"); const auto& pixels = data.frames[0].pixels; diff --git a/rawrbox.render/src/textures/base.cpp b/rawrbox.render/src/textures/base.cpp index 1a74b660..b1062377 100644 --- a/rawrbox.render/src/textures/base.cpp +++ b/rawrbox.render/src/textures/base.cpp @@ -86,7 +86,7 @@ namespace rawrbox { const rawrbox::ImageData& TextureBase::getData() const { return this->_data; } const std::vector& TextureBase::getPixels(size_t index) const { - if (index > this->_data.frames.size()) throw this->_logger->error("Pixel data from frame index {} not found", index); + if (index > this->_data.frames.size()) CRITICAL_RAWRBOX("Pixel data from frame index {} not found", index); return this->_data.frames[index].pixels; } @@ -136,8 +136,8 @@ namespace rawrbox { void TextureBase::upload(Diligent::TEXTURE_FORMAT format, bool dynamic) { if (this->_failedToLoad || this->_handle != nullptr) return; // Failed texture is already bound, so skip it - if (!this->_data.valid()) throw this->_logger->error("Cannot upload invalid image data"); - if (this->_data.total() > 2048U) throw this->_logger->error("Cannot upload more than 2048 image frames"); + if (!this->_data.valid()) CRITICAL_RAWRBOX("Cannot upload invalid image data"); + if (this->_data.total() > 2048U) CRITICAL_RAWRBOX("Cannot upload more than 2048 image frames"); // Try to determine texture format this->tryGetFormatChannels(format, this->_data.channels); @@ -178,7 +178,7 @@ namespace rawrbox { data.NumSubresources = static_cast(subresData.size()); rawrbox::RENDERER->device()->CreateTexture(desc, &data, &this->_tex); - if (this->_tex == nullptr) throw this->_logger->error("Failed to create texture '{}'", this->_name); + if (this->_tex == nullptr) CRITICAL_RAWRBOX("Failed to create texture '{}'", this->_name); // Get handles -- this->_handle = this->_tex->GetDefaultView(Diligent::TEXTURE_VIEW_SHADER_RESOURCE); diff --git a/rawrbox.render/src/textures/gif.cpp b/rawrbox.render/src/textures/gif.cpp index 78840ae7..6db99847 100644 --- a/rawrbox.render/src/textures/gif.cpp +++ b/rawrbox.render/src/textures/gif.cpp @@ -17,11 +17,7 @@ namespace rawrbox { } else { this->_data = rawrbox::GIF::decode(buffer); } -#ifdef RAWRBOX_TRACE_EXCEPTIONS - } catch (const cpptrace::exception_with_message& e) { -#else } catch (const std::exception& e) { -#endif if (useFallback) { this->_logger->warn("Failed to load '{}' ──> {}\n └── Loading fallback texture!", this->_filePath.generic_string(), e.what()); this->loadFallback(); diff --git a/rawrbox.render/src/textures/image.cpp b/rawrbox.render/src/textures/image.cpp index 2598c1a9..8269f08e 100644 --- a/rawrbox.render/src/textures/image.cpp +++ b/rawrbox.render/src/textures/image.cpp @@ -8,12 +8,8 @@ namespace rawrbox { TextureImage::TextureImage(const std::filesystem::path& filePath, const std::vector& buffer, bool useFallback) : _filePath(filePath) { try { this->_data = rawrbox::STBI::decode(buffer); - if (!this->_data.valid() || this->_data.total() == 0) throw this->_logger->error("Invalid image data!"); -#ifdef RAWRBOX_TRACE_EXCEPTIONS - } catch (const cpptrace::exception_with_message& e) { -#else + if (!this->_data.valid() || this->_data.total() == 0) CRITICAL_RAWRBOX("Invalid image data!"); } catch (const std::exception& e) { -#endif if (useFallback) { this->loadFallback(); this->_logger->warn("Failed to load '{}' ──> {}\n └── Loading fallback texture!", this->_filePath.generic_string(), e.what()); @@ -27,12 +23,8 @@ namespace rawrbox { TextureImage::TextureImage(const std::filesystem::path& filePath, bool useFallback) : _filePath(filePath) { try { this->_data = rawrbox::STBI::decode(filePath); - if (!this->_data.valid() || this->_data.total() == 0) throw this->_logger->error("Invalid image data!"); -#ifdef RAWRBOX_TRACE_EXCEPTIONS - } catch (const cpptrace::exception_with_message& e) { -#else + if (!this->_data.valid() || this->_data.total() == 0) CRITICAL_RAWRBOX("Invalid image data!"); } catch (const std::exception& e) { -#endif if (useFallback) { this->loadFallback(); this->_logger->warn("Failed to load '{}' ──> {}\n └── Loading fallback texture!", this->_filePath.generic_string(), e.what()); @@ -46,12 +38,8 @@ namespace rawrbox { TextureImage::TextureImage(const uint8_t* buffer, int bufferSize, bool useFallback) { try { this->_data = rawrbox::STBI::decode(buffer, bufferSize); - if (!this->_data.valid() || this->_data.total() == 0) throw this->_logger->error("Invalid image data!"); -#ifdef RAWRBOX_TRACE_EXCEPTIONS - } catch (const cpptrace::exception_with_message& e) { -#else + if (!this->_data.valid() || this->_data.total() == 0) CRITICAL_RAWRBOX("Invalid image data!"); } catch (const std::exception& e) { -#endif if (useFallback) { this->loadFallback(); this->_logger->warn("Failed to load '{}' ──> {}\n └── Loading fallback texture!", this->_filePath.generic_string(), e.what()); diff --git a/rawrbox.render/src/textures/pack.cpp b/rawrbox.render/src/textures/pack.cpp index 0e07ca9b..6353303f 100644 --- a/rawrbox.render/src/textures/pack.cpp +++ b/rawrbox.render/src/textures/pack.cpp @@ -24,10 +24,10 @@ namespace rawrbox { } rawrbox::PackNode& TexturePack::addSprite(uint32_t width, uint32_t height, const std::vector& data) { - if (this->_tex == nullptr) throw this->_logger->error("Texture not bound"); + if (this->_tex == nullptr) CRITICAL_RAWRBOX("Texture not bound"); auto nodeOpt = this->_root->InsertNode(width, height); - if (!nodeOpt.has_value()) throw this->_logger->error("Failed to add sprite with size {}, {}", width, height); + if (!nodeOpt.has_value()) CRITICAL_RAWRBOX("Failed to add sprite with size {}, {}", width, height); auto& node = (*nodeOpt).get(); node.data = data; // Set the data of that node diff --git a/rawrbox.render/src/textures/render.cpp b/rawrbox.render/src/textures/render.cpp index 3f906df5..cca187fc 100644 --- a/rawrbox.render/src/textures/render.cpp +++ b/rawrbox.render/src/textures/render.cpp @@ -51,7 +51,7 @@ namespace rawrbox { // ------ RENDER void TextureRender::startRecord(bool clear, size_t renderTargets) { - if (this->_recording) throw this->_logger->error("Already recording"); + if (this->_recording) CRITICAL_RAWRBOX("Already recording"); auto* context = rawrbox::RENDERER->context(); // BARRIER ---- @@ -76,7 +76,7 @@ namespace rawrbox { } void TextureRender::stopRecord() { - if (!this->_recording) throw this->_logger->error("Not recording"); + if (!this->_recording) CRITICAL_RAWRBOX("Not recording"); auto* pRTV = rawrbox::RENDERER->swapChain()->GetCurrentBackBufferRTV(); auto* depth = rawrbox::RENDERER->swapChain()->GetDepthBufferDSV(); @@ -91,7 +91,7 @@ namespace rawrbox { size_t TextureRender::addTexture(Diligent::TEXTURE_FORMAT format, Diligent::BIND_FLAGS flags) { bool isDepth = (flags & Diligent::BIND_DEPTH_STENCIL) != 0; - if (isDepth && this->_depthHandle != nullptr) throw _logger->error("Only one depth texture is allowed"); + if (isDepth && this->_depthHandle != nullptr) CRITICAL_RAWRBOX("Only one depth texture is allowed"); std::string name = isDepth ? fmt::format("{}::DEPTH", this->_name) : this->_name; @@ -143,7 +143,7 @@ namespace rawrbox { void TextureRender::addView(size_t index, Diligent::TEXTURE_VIEW_TYPE format) { auto* tex = this->getTexture(index); - if (tex == nullptr) throw _logger->error("Invalid texture index '{}'! Did you call 'addTexture`?", index); + if (tex == nullptr) CRITICAL_RAWRBOX("Invalid texture index '{}'! Did you call 'addTexture`?", index); if (format == Diligent::TEXTURE_VIEW_RENDER_TARGET) { this->_viewsRT.push_back(tex->GetDefaultView(format)); @@ -153,7 +153,7 @@ namespace rawrbox { } void TextureRender::upload(Diligent::TEXTURE_FORMAT format, bool /*dynamic*/) { - if (format == Diligent::TEXTURE_FORMAT::TEX_FORMAT_UNKNOWN) throw this->_logger->error("Invalid format"); + if (format == Diligent::TEXTURE_FORMAT::TEX_FORMAT_UNKNOWN) CRITICAL_RAWRBOX("Invalid format"); auto view = this->addTexture(format); this->addView(view, Diligent::TEXTURE_VIEW_RENDER_TARGET); diff --git a/rawrbox.render/src/textures/streaming.cpp b/rawrbox.render/src/textures/streaming.cpp index e7a80380..60c54295 100644 --- a/rawrbox.render/src/textures/streaming.cpp +++ b/rawrbox.render/src/textures/streaming.cpp @@ -24,10 +24,10 @@ namespace rawrbox { } void TextureStreaming::setImage(const rawrbox::ImageData& data) { - if (data.frames.empty()) throw _logger->error("Cannot set empty data"); + if (data.frames.empty()) CRITICAL_RAWRBOX("Cannot set empty data"); auto frame = data.pixels(); - if (frame.empty()) throw _logger->error("Cannot set empty pixels"); + if (frame.empty()) CRITICAL_RAWRBOX("Cannot set empty pixels"); if (data.channels != this->_data.channels) frame = rawrbox::ColorUtils::setChannels(data.channels, this->_data.channels, data.size.x, data.size.y, frame); frame = rawrbox::TextureUtils::resize(data.size, frame, this->_data.size, this->_data.channels); @@ -48,7 +48,7 @@ namespace rawrbox { void TextureStreaming::update() { if (!this->_pendingUpdate || this->_tex == nullptr) return; - if (this->_data.empty()) throw this->_logger->error("Cannot update empty data"); + if (this->_data.empty()) CRITICAL_RAWRBOX("Cannot update empty data"); auto* context = rawrbox::RENDERER->context(); diff --git a/rawrbox.render/src/textures/utils/blit.cpp b/rawrbox.render/src/textures/utils/blit.cpp index c1ab0ae6..38c2a444 100644 --- a/rawrbox.render/src/textures/utils/blit.cpp +++ b/rawrbox.render/src/textures/utils/blit.cpp @@ -16,7 +16,7 @@ namespace rawrbox { } void TextureBLIT::upload(Diligent::TEXTURE_FORMAT /*format*/, bool /*dynamic*/) { - if (this->_tex != nullptr) throw _logger->error("Already uploaded"); + if (this->_tex != nullptr) CRITICAL_RAWRBOX("Already uploaded"); Diligent::TextureDesc desc; desc.Type = Diligent::RESOURCE_DIM_TEX_2D; @@ -33,8 +33,8 @@ namespace rawrbox { } void TextureBLIT::copy(Diligent::ITexture* base, Diligent::Box* box, const std::function& callback) { - if (base == nullptr) throw _logger->error("Invalid texture"); - if (callback == nullptr) throw _logger->error("Invalid callback"); + if (base == nullptr) CRITICAL_RAWRBOX("Invalid texture"); + if (callback == nullptr) CRITICAL_RAWRBOX("Invalid callback"); auto* device = rawrbox::RENDERER->device(); auto* context = rawrbox::RENDERER->context(); @@ -68,7 +68,7 @@ namespace rawrbox { } void TextureBLIT::blit(Diligent::Box* box, const std::function& callback) { - if (callback == nullptr) throw _logger->error("Invalid callback"); + if (callback == nullptr) CRITICAL_RAWRBOX("Invalid callback"); auto* context = rawrbox::RENDERER->context(); Diligent::MappedTextureSubresource MappedSubres; diff --git a/rawrbox.render/src/textures/utils/gif.cpp b/rawrbox.render/src/textures/utils/gif.cpp index b68e6f30..95bc48ee 100644 --- a/rawrbox.render/src/textures/utils/gif.cpp +++ b/rawrbox.render/src/textures/utils/gif.cpp @@ -7,10 +7,10 @@ namespace rawrbox { std::unique_ptr GIF::_logger = std::make_unique("RawrBox-GIF"); rawrbox::ImageData GIF::internalLoad(int width, int height, int frames_n, uint8_t* gifPixels, int* delays) { - if (width == 0 || height == 0) throw _logger->error("Invalid image size: {}x{}", width, height); + if (width == 0 || height == 0) CRITICAL_RAWRBOX("Invalid image size: {}x{}", width, height); if (gifPixels == nullptr || delays == nullptr) { const auto* failure = stbi_failure_reason(); - throw _logger->error("Error loading image: {}", failure); + CRITICAL_RAWRBOX("Error loading image: {}", failure); } rawrbox::ImageData imgData = {}; @@ -38,7 +38,7 @@ namespace rawrbox { } rawrbox::ImageData GIF::decode(const std::filesystem::path& path) { - if (!std::filesystem::exists(path)) throw _logger->error("Could not find file {}", path.generic_string()); + if (!std::filesystem::exists(path)) CRITICAL_RAWRBOX("Could not find file {}", path.generic_string()); int frames_n = 0; int* delays = nullptr; @@ -52,7 +52,7 @@ namespace rawrbox { } rawrbox::ImageData GIF::decode(const std::vector& data) { - if (data.empty()) throw _logger->error("Invalid data, cannot be empty!"); + if (data.empty()) CRITICAL_RAWRBOX("Invalid data, cannot be empty!"); int frames_n = 0; int* delays = nullptr; diff --git a/rawrbox.render/src/textures/utils/stbi.cpp b/rawrbox.render/src/textures/utils/stbi.cpp index 3ad0bc48..49144b7d 100644 --- a/rawrbox.render/src/textures/utils/stbi.cpp +++ b/rawrbox.render/src/textures/utils/stbi.cpp @@ -19,11 +19,11 @@ namespace rawrbox { std::unique_ptr STBI::_logger = std::make_unique("RawrBox-STBI"); rawrbox::ImageData STBI::internalLoad(int width, int height, int channels, uint8_t* pixels) { - if (width == 0 || height == 0) throw _logger->error("Invalid image size: {}x{}", width, height); - if (channels == 0) throw _logger->error("Invalid image channels: {}", channels); + if (width == 0 || height == 0) CRITICAL_RAWRBOX("Invalid image size: {}x{}", width, height); + if (channels == 0) CRITICAL_RAWRBOX("Invalid image channels: {}", channels); if (pixels == nullptr) { const auto* failure = stbi_failure_reason(); - throw _logger->error("Error loading image: {}", failure); + CRITICAL_RAWRBOX("Error loading image: {}", failure); } rawrbox::ImageData imgData = {}; @@ -41,7 +41,7 @@ namespace rawrbox { } rawrbox::ImageData STBI::decode(const std::filesystem::path& path) { - if (!std::filesystem::exists(path)) throw _logger->error("Could not find file {}", path.generic_string()); + if (!std::filesystem::exists(path)) CRITICAL_RAWRBOX("Could not find file {}", path.generic_string()); int width = 0; int height = 0; @@ -54,7 +54,7 @@ namespace rawrbox { } rawrbox::ImageData STBI::decode(const std::vector& data) { - if (data.empty()) throw _logger->error("Invalid data, cannot be empty!"); + if (data.empty()) CRITICAL_RAWRBOX("Invalid data, cannot be empty!"); int width = 0; int height = 0; diff --git a/rawrbox.render/src/textures/utils/utils.cpp b/rawrbox.render/src/textures/utils/utils.cpp index ad98a29e..4f316a96 100644 --- a/rawrbox.render/src/textures/utils/utils.cpp +++ b/rawrbox.render/src/textures/utils/utils.cpp @@ -9,6 +9,10 @@ #include namespace rawrbox { + // PRIVATE --- + std::unique_ptr TextureUtils::_logger = std::make_unique("RawrBox-TextureUtils"); + // ---------- + rawrbox::Vector4f TextureUtils::atlasToUV(const rawrbox::Vector2i& atlasSize, uint32_t spriteSize, uint32_t id) { // UV ------- rawrbox::Vector2i totalSprites = atlasSize / spriteSize; @@ -27,8 +31,8 @@ namespace rawrbox { }; std::vector TextureUtils::generateCheckboard(const rawrbox::Vector2u& size, const rawrbox::Color& color1, const rawrbox::Color& color2, uint32_t amount) { - if (amount % 2 != 0) throw rawrbox::Logger::err("TextureUtils", "Amount must be a power of 2."); - if (std::bitset<32>(amount).count() != 1) throw rawrbox::Logger::err("TextureUtils", "Size must be power of 2."); + if (amount % 2 != 0) CRITICAL_RAWRBOX("Amount must be a power of 2."); + if (std::bitset<32>(amount).count() != 1) CRITICAL_RAWRBOX("Size must be power of 2."); std::vector pixels = {}; @@ -67,7 +71,7 @@ namespace rawrbox { } std::vector TextureUtils::resize(const rawrbox::Vector2u& originalSize, const std::vector& data, const rawrbox::Vector2u& newSize, uint8_t channels) { - if (data.empty()) throw rawrbox::Logger::err("TextureUtils", "Data cannot be empty"); + if (data.empty()) CRITICAL_RAWRBOX("Data cannot be empty"); std::vector resizedData(newSize.x * newSize.y * channels); // Assuming RGBA format @@ -152,7 +156,7 @@ namespace rawrbox { return rawrbox::WEBP::decode(data); default: case IMAGE_INVALID: - throw rawrbox::Logger::err("TextureUtils", "Invalid image type!"); + CRITICAL_RAWRBOX("Invalid image type!"); } } } // namespace rawrbox diff --git a/rawrbox.render/src/textures/utils/webp.cpp b/rawrbox.render/src/textures/utils/webp.cpp index 7ae2df70..023eee87 100644 --- a/rawrbox.render/src/textures/utils/webp.cpp +++ b/rawrbox.render/src/textures/utils/webp.cpp @@ -11,21 +11,21 @@ namespace rawrbox { std::unique_ptr WEBP::_logger = std::make_unique("RawrBox-WEBP"); rawrbox::ImageData WEBP::decode(const uint8_t* buffer, size_t bufferSize) { - if (buffer == nullptr || bufferSize <= 0) throw _logger->error("Invalid data, cannot be empty!"); + if (buffer == nullptr || bufferSize <= 0) CRITICAL_RAWRBOX("Invalid data, cannot be empty!"); WebPAnimDecoderOptions options; options.use_threads = 1; - if (WebPAnimDecoderOptionsInit(&options) == 0) throw _logger->error("Error initializing image!"); + if (WebPAnimDecoderOptionsInit(&options) == 0) CRITICAL_RAWRBOX("Error initializing image!"); WebPData webp_data = {buffer, bufferSize}; auto* decoder = WebPAnimDecoderNew(&webp_data, &options); - if (decoder == nullptr) throw _logger->error("Error initializing decoder!"); + if (decoder == nullptr) CRITICAL_RAWRBOX("Error initializing decoder!"); WebPAnimInfo info; if (WebPAnimDecoderGetInfo(decoder, &info) == 0) { WebPAnimDecoderDelete(decoder); - throw _logger->error("Error decoding image info!"); + CRITICAL_RAWRBOX("Error decoding image info!"); } rawrbox::ImageData webpData = {}; @@ -40,7 +40,7 @@ namespace rawrbox { if (WebPAnimDecoderGetNext(decoder, &buf, &delay) == 0) { WebPAnimDecoderDelete(decoder); - throw _logger->error("Error decoding image!"); + CRITICAL_RAWRBOX("Error decoding image!"); } rawrbox::ImageFrame frame = {}; @@ -61,27 +61,27 @@ namespace rawrbox { } std::vector WEBP::encode(const rawrbox::ImageData& /*data*/) { - throw _logger->error("Encoding WebP is not supported yet!"); - /*if (data.frames.empty() || data.size.length() <= 0.F) throw _logger->error("Invalid webpData, frames cannot be empty!"); + CRITICAL_RAWRBOX("Encoding WebP is not supported yet!"); + /*if (data.frames.empty() || data.size.length() <= 0.F) CRITICAL_RAWRBOX("Invalid webpData, frames cannot be empty!"); int loop_count = 0; // infinite int timems_per_frame = 33; WebPConfig config; - if (WebPConfigInit(&config) == 0) throw _logger->error("Error initializing WebP config!"); + if (WebPConfigInit(&config) == 0) CRITICAL_RAWRBOX("Error initializing WebP config!"); config.quality = 100; // Set quality to 100 config.lossless = 1; // Set lossless encoding WebPPicture picture; - if (WebPPictureInit(&picture) == 0) throw _logger->error("Error initializing WebP picture!"); + if (WebPPictureInit(&picture) == 0) CRITICAL_RAWRBOX("Error initializing WebP picture!"); picture.width = data.size.x; picture.height = data.size.y; if (WebPPictureAlloc(&picture) == 0) { WebPPictureFree(&picture); - throw _logger->error("Error allocating WebP picture!"); + CRITICAL_RAWRBOX("Error allocating WebP picture!"); } WebPAnimEncoder* encoder = nullptr; @@ -89,7 +89,7 @@ namespace rawrbox { if (WebPAnimEncoderOptionsInit(&enc_options) == 0) { WebPPictureFree(&picture); - throw _logger->error("Error initializing WebP animation encoder options!"); + CRITICAL_RAWRBOX("Error initializing WebP animation encoder options!"); } for (size_t i = 0; i < data.frames.size(); i++) { @@ -97,7 +97,7 @@ namespace rawrbox { if (WebPPictureImportRGBA(&picture, frame.pixels.data(), static_cast(frame.pixels.size() / 4)) == 0) { WebPPictureFree(&picture); - throw _logger->error("Error importing RGBA data to WebP picture!"); + CRITICAL_RAWRBOX("Error importing RGBA data to WebP picture!"); } // if (colorspace == 0) WebPPictureARGBToYUVA(&pic, WebPEncCSP::WEBP_YUV420); @@ -107,7 +107,7 @@ namespace rawrbox { if (WebPAnimEncoderAdd(encoder, &picture, timems_per_frame * static_cast(i), &config) == 0) { WebPPictureFree(&picture); - throw _logger->error("Error adding frame to WebP animation encoder!"); + CRITICAL_RAWRBOX("Error adding frame to WebP animation encoder!"); } } @@ -116,7 +116,7 @@ namespace rawrbox { if (WebPAnimEncoderAssemble(encoder, &webpData) == 0) { WebPPictureFree(&picture); - throw _logger->error("Error assembling WebP animation!"); + CRITICAL_RAWRBOX("Error assembling WebP animation!"); } // Mux assemble diff --git a/rawrbox.render/src/textures/webp.cpp b/rawrbox.render/src/textures/webp.cpp index 4b682c8f..8777715a 100644 --- a/rawrbox.render/src/textures/webp.cpp +++ b/rawrbox.render/src/textures/webp.cpp @@ -14,11 +14,7 @@ namespace rawrbox { try { this->_data = rawrbox::WEBP::decode(buffer, bufferSize); -#ifdef RAWRBOX_TRACE_EXCEPTIONS - } catch (const cpptrace::exception_with_message& e) { -#else } catch (const std::exception& e) { -#endif if (useFallback) { this->_logger->warn("Failed to load '{}' ──> \n\t{}\n\t\t └── Loading fallback texture!", this->_filePath.generic_string(), e.what()); this->loadFallback(); diff --git a/rawrbox.render/src/utils/barrier.cpp b/rawrbox.render/src/utils/barrier.cpp index 33442002..504f19b1 100644 --- a/rawrbox.render/src/utils/barrier.cpp +++ b/rawrbox.render/src/utils/barrier.cpp @@ -4,10 +4,11 @@ namespace rawrbox { // BARRIER ---- std::unordered_map BarrierUtils::_barrierCache = {}; + std::unique_ptr BarrierUtils::_logger = std::make_unique("RawrBox-BarrierUtils"); // ------------- void BarrierUtils::barrier(const std::vector& resources) { - if (std::this_thread::get_id() != rawrbox::RENDER_THREAD_ID) throw rawrbox::Logger::err("BarrierUtils", "Barriers can only be processed on the main render thread"); + if (std::this_thread::get_id() != rawrbox::RENDER_THREAD_ID) CRITICAL_RAWRBOX("Barriers can only be processed on the main render thread"); std::vector states = {}; for (auto barrier : resources) { diff --git a/rawrbox.render/src/utils/pipeline.cpp b/rawrbox.render/src/utils/pipeline.cpp index 800e1ff6..76587a35 100644 --- a/rawrbox.render/src/utils/pipeline.cpp +++ b/rawrbox.render/src/utils/pipeline.cpp @@ -41,7 +41,7 @@ namespace rawrbox { // Initialize pipeline cache ----- Diligent::RenderStateCacheCreateInfo CacheCI; CacheCI.pDevice = &device; - // CacheCI.LogLevel = Diligent::RENDER_STATE_CACHE_LOG_LEVEL_VERBOSE; + CacheCI.LogLevel = Diligent::RENDER_STATE_CACHE_LOG_LEVEL_DISABLED; Diligent::CreateRenderStateCache(CacheCI, &_stateCache); // ------------------------- @@ -64,7 +64,7 @@ namespace rawrbox { auto pCacheData = Diligent::DataBlobImpl::Create(); if (CacheDataFile->Read(pCacheData)) { - _logger->info("Loaded pipeline cache from '{}'", pString); + _logger->debug("Loaded pipeline cache from '{}'", pString); _stateCache->Load(pCacheData); } } @@ -82,9 +82,9 @@ namespace rawrbox { const auto pString = _stateCachePath.generic_string(); Diligent::FileWrapper CacheDataFile{pString.c_str(), Diligent::EFileAccessMode::Overwrite}; if (CacheDataFile->Write(pCacheData->GetConstDataPtr(), pCacheData->GetSize())) { - _logger->info("Saved pipeline cache to '{}'", pString); + _logger->debug("Saved pipeline cache to '{}'", pString); } else { - _logger->error("Failed to save pipeline cache to '{}'", pString); + ERROR_RAWRBOX("Failed to save pipeline cache to '{}'", pString); } } } @@ -146,17 +146,13 @@ namespace rawrbox { Diligent::RefCntAutoPtr shader; _stateCache->CreateShader(ShaderCI, &shader); - _logger->setAutoNewLine(false); - _logger->info("Shader '{}'", fmt::styled(name, fmt::fg(fmt::color::coral))); - _logger->setAutoNewLine(true); - if (shader != nullptr) { - fmt::print("{}\n", fmt::styled(" [✓ OK]", fmt::fg(fmt::color::green_yellow))); + _logger->info("Shader '{}' {}", fmt::styled(name, fmt::fg(fmt::color::coral)), fmt::styled(" [✓ OK]", fmt::fg(fmt::color::green_yellow))); } else { - fmt::print("{}\n", fmt::styled(" [✖ FAILED]", fmt::fg(fmt::color::red))); + CRITICAL_RAWRBOX("Shader '{}' {}", fmt::styled(name, fmt::fg(fmt::color::coral)), fmt::styled(" [✖ FAILED]", fmt::fg(fmt::color::red))); } - if (shader == nullptr) throw _logger->error("Failed to compile shader '{}'", name); + if (shader == nullptr) CRITICAL_RAWRBOX("Failed to compile shader '{}'", name); _shaders[id] = std::move(shader); return _shaders[id]; } @@ -177,7 +173,7 @@ namespace rawrbox { } Diligent::IPipelineState* PipelineUtils::createComputePipeline(const std::string& name, rawrbox::PipeComputeSettings settings) { - if (settings.pCS.empty()) throw _logger->error("Failed to create shader {}, pCS shader cannot be empty!", name); + if (settings.pCS.empty()) CRITICAL_RAWRBOX("Failed to create shader {}, pCS shader cannot be empty!", name); auto fnd = _pipelines.find(name); if (fnd != _pipelines.end()) return fnd->second; @@ -205,14 +201,14 @@ namespace rawrbox { PSOCreateInfo.pCS = rawrbox::PipelineUtils::compileShader(settings.pCS, Diligent::SHADER_TYPE_COMPUTE, settings.macros); _stateCache->CreateComputePipelineState(PSOCreateInfo, &pipe); - if (pipe == nullptr) throw _logger->error("Failed to create pipeline '{}'", name); + if (pipe == nullptr) CRITICAL_RAWRBOX("Failed to create pipeline '{}'", name); if (settings.signatures.empty()) { for (auto& uni : settings.uniforms) { if (uni.uniform == nullptr) continue; auto* var = pipe->GetStaticVariableByName(uni.type, uni.name.c_str()); - if (var == nullptr) throw _logger->error("Failed to create pipeline '{}', could not find variable '{}' on '{}'", name, uni.name, magic_enum::enum_name(uni.type)); + if (var == nullptr) CRITICAL_RAWRBOX("Failed to create pipeline '{}', could not find variable '{}' on '{}'", name, uni.name, magic_enum::enum_name(uni.type)); var->Set(uni.uniform); } } @@ -308,14 +304,14 @@ namespace rawrbox { // --------------------- _stateCache->CreateGraphicsPipelineState(info, &pipe); - if (pipe == nullptr) throw _logger->error("Failed to create pipeline '{}'", name); + if (pipe == nullptr) CRITICAL_RAWRBOX("Failed to create pipeline '{}'", name); if (settings.signatures.empty()) { for (auto& uni : settings.uniforms) { if (uni.uniform == nullptr) continue; auto* var = pipe->GetStaticVariableByName(uni.type, uni.name.c_str()); - if (var == nullptr) throw _logger->error("Failed to create pipeline '{}', could not find variable '{}' on '{}'", name, uni.name, magic_enum::enum_name(uni.type)); + if (var == nullptr) CRITICAL_RAWRBOX("Failed to create pipeline '{}', could not find variable '{}' on '{}'", name, uni.name, magic_enum::enum_name(uni.type)); var->Set(uni.uniform); } diff --git a/rawrbox.render/src/utils/render.cpp b/rawrbox.render/src/utils/render.cpp index a817a11f..ee6f91e9 100644 --- a/rawrbox.render/src/utils/render.cpp +++ b/rawrbox.render/src/utils/render.cpp @@ -12,7 +12,7 @@ namespace rawrbox { // ------------- void RenderUtils::init() { - if (_pipe != nullptr) throw _logger->error("Pipeline already initialized!"); + if (_pipe != nullptr) CRITICAL_RAWRBOX("Pipeline already initialized!"); rawrbox::PipeSettings settings; settings.cull = Diligent::CULL_MODE_BACK; @@ -34,14 +34,14 @@ namespace rawrbox { // SETUP VERTEX UNIFORMS ---------------------------- { Diligent::MapHelper CBConstants(context, rawrbox::BindlessManager::signatureBufferVertex, Diligent::MAP_WRITE, Diligent::MAP_FLAG_DISCARD); - if (CBConstants == nullptr) throw _logger->error("Failed to map the vertex constants buffer!"); + if (CBConstants == nullptr) CRITICAL_RAWRBOX("Failed to map the vertex constants buffer!"); } // ----------- // SETUP PIXEL UNIFORMS ---------------------------- { Diligent::MapHelper CBConstants(context, rawrbox::BindlessManager::signatureBufferPixel, Diligent::MAP_WRITE, Diligent::MAP_FLAG_DISCARD); - if (CBConstants == nullptr) throw _logger->error("Failed to map the pixel constants buffer!"); + if (CBConstants == nullptr) CRITICAL_RAWRBOX("Failed to map the pixel constants buffer!"); CBConstants->textureIDs = {texture.getTextureID(), 0, 0, 0}; } diff --git a/rawrbox.render/src/window.cpp b/rawrbox.render/src/window.cpp index 1522639e..742bb10a 100644 --- a/rawrbox.render/src/window.cpp +++ b/rawrbox.render/src/window.cpp @@ -75,7 +75,7 @@ namespace rawrbox { #endif #endif if (Window::__RENDER_TYPE == Diligent::RENDER_DEVICE_TYPE_COUNT) { - throw _logger->error("Failed to automatically determine best renderer type"); + CRITICAL_RAWRBOX("Failed to automatically determine best renderer type"); } } else { Window::__RENDER_TYPE = render; @@ -90,7 +90,7 @@ namespace rawrbox { } rawrbox::Window* Window::getWindow(size_t indx) { - if (indx > Window::__WINDOWS.size()) throw _logger->error("Invalid window index '{}'", indx); + if (indx > Window::__WINDOWS.size()) CRITICAL_RAWRBOX("Invalid window index '{}'", indx); return Window::__WINDOWS[indx].get(); } @@ -139,7 +139,7 @@ namespace rawrbox { } // --------------------- - _logger->success("Thread 'rawrbox:render' shutdown complete"); + _logger->debug("Thread 'rawrbox:render' shutdown complete"); return; } @@ -148,7 +148,7 @@ namespace rawrbox { glfwPostEmptyEvent(); glfwTerminate(); - _logger->success("Thread 'rawrbox:input' shutdown complete"); + _logger->debug("Thread 'rawrbox:input' shutdown complete"); _logger.reset(); } @@ -197,7 +197,7 @@ namespace rawrbox { } void Window::init(uint32_t width, uint32_t height, uint32_t flags) { - if (rawrbox::RENDER_THREAD_ID == std::this_thread::get_id()) throw _logger->error("'init' should be called inside engine's 'setupGLFW'!"); + if (rawrbox::RENDER_THREAD_ID == std::this_thread::get_id()) CRITICAL_RAWRBOX("'init' should be called inside engine's 'setupGLFW'!"); int APIHint = GLFW_NO_API; #ifndef _WIN32 @@ -209,7 +209,7 @@ namespace rawrbox { #endif glfwSetErrorCallback(glfw_errorCallback); - if (glfwInit() == 0) throw _logger->error("Failed to initialize glfw"); + if (glfwInit() == 0) CRITICAL_RAWRBOX("Failed to initialize glfw"); glfwWindowHint(GLFW_CLIENT_API, APIHint); // Disable opengl if (APIHint == GLFW_OPENGL_API) { @@ -232,7 +232,7 @@ namespace rawrbox { } } - if (mon == nullptr) throw _logger->error("Failed to get primary window"); + if (mon == nullptr) CRITICAL_RAWRBOX("Failed to get primary window"); // ---------------------------- // Fullscreen / borderless @@ -245,8 +245,8 @@ namespace rawrbox { bool borderless = (flags & WindowFlags::Window::BORDERLESS) > 0; bool fullscreen = (flags & WindowFlags::Window::FULLSCREEN) > 0; - if (!fullscreen && !windowed && !borderless) throw _logger->error("Window flag attribute missing"); - if ((windowed && (borderless || fullscreen)) || (borderless && (windowed || fullscreen)) || (fullscreen && (windowed || borderless))) throw _logger->error("Only one window flag attribute can be selected"); + if (!fullscreen && !windowed && !borderless) CRITICAL_RAWRBOX("Window flag attribute missing"); + if ((windowed && (borderless || fullscreen)) || (borderless && (windowed || fullscreen)) || (fullscreen && (windowed || borderless))) CRITICAL_RAWRBOX("Only one window flag attribute can be selected"); if (borderless || fullscreen || (width >= vidW || height >= vidH)) { width = vidW; height = vidH; @@ -274,7 +274,7 @@ namespace rawrbox { #endif auto* glfwHandle = glfwCreateWindow(width, height, this->_settings.title.c_str(), windowed || borderless ? nullptr : mon, nullptr); - if (glfwHandle == nullptr) throw _logger->error("Failed to initialize window [{} - {}x{}]", this->_settings.title, width, height); + if (glfwHandle == nullptr) CRITICAL_RAWRBOX("Failed to initialize window [{} - {}x{}]", this->_settings.title, width, height); this->_handle = glfwHandle; glfwSetWindowUserPointer(glfwHandle, this); @@ -359,13 +359,13 @@ namespace rawrbox { } void Window::setOpacity(float opacity) { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); glfwSetWindowOpacity(this->_handle, opacity); } #ifdef _WIN32 void Window::alert() { // Blink application - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); HWND hwnd = glfwGetWin32Window(this->_handle); // Set up the FLASHWINFO structure @@ -383,12 +383,12 @@ namespace rawrbox { // CURSOR ------ void Window::hideCursor(bool hidden) { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); glfwSetInputMode(this->_handle, GLFW_CURSOR, hidden ? GLFW_CURSOR_HIDDEN : GLFW_CURSOR_NORMAL); } void Window::setCursor(uint32_t cursor) { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); if (this->_cursor != nullptr) glfwDestroyCursor(this->_cursor); // Delete old one auto* icon = glfwCreateStandardCursor(cursor); this->_cursor = icon; @@ -397,8 +397,8 @@ namespace rawrbox { } void Window::setCursor(const std::array& cursor) { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); - if (cursor.empty()) throw _logger->error("Cursor pixels cannot be empty"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); + if (cursor.empty()) CRITICAL_RAWRBOX("Cursor pixels cannot be empty"); std::memcpy(this->_cursorPixels.data(), cursor.data(), cursor.size() * sizeof(uint8_t)); if (this->_cursor != nullptr) glfwDestroyCursor(this->_cursor); // Delete old one @@ -433,7 +433,7 @@ namespace rawrbox { } void Window::setPos(const rawrbox::Vector2i& pos) { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); glfwSetWindowPos(this->_handle, pos.x, pos.y); this->_settings.pos = pos; @@ -444,17 +444,17 @@ namespace rawrbox { } rawrbox::Vector2u Window::getMonitorSize() const { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); GLFWmonitor* w = getWindowMonitor(); - if (w == nullptr) throw _logger->error("Failed to find screen dimensions"); + if (w == nullptr) CRITICAL_RAWRBOX("Failed to find screen dimensions"); const auto* vidmode = glfwGetVideoMode(w); return {static_cast(vidmode->width), static_cast(vidmode->height)}; } float Window::getAspectRatio() const { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); rawrbox::Vector2f ret = this->getSize().cast(); return ret.x / ret.y; @@ -471,8 +471,8 @@ namespace rawrbox { GLFWwindow* Window::getGLFWHandle() const { return this->_handle; } Diligent::NativeWindow Window::getHandle() const { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); - // Get native window ---- + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); + // Get native window ---- #if PLATFORM_WIN32 Diligent::Win32NativeWindow window{glfwGetWin32Window(this->_handle)}; #endif @@ -499,12 +499,12 @@ namespace rawrbox { rawrbox::RendererBase& Window::getRenderer() const { return *this->_renderer; } bool Window::isKeyDown(int key) const { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); return glfwGetKey(this->_handle, key) == GLFW_PRESS; } bool Window::isMouseDown(int key) const { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); return glfwGetMouseButton(this->_handle, key) == GLFW_PRESS; } @@ -607,7 +607,7 @@ namespace rawrbox { // Adapted from : https://github.com/glfw/glfw/pull/2220/files GLFWmonitor* Window::getWindowMonitor() const { - if (this->_handle == nullptr) throw _logger->error("Invalid window handle"); + if (this->_handle == nullptr) CRITICAL_RAWRBOX("Invalid window handle"); int monitorCount = 0; GLFWmonitor** monitors = glfwGetMonitors(&monitorCount); diff --git a/rawrbox.resources/include/rawrbox/resources/loader.hpp b/rawrbox.resources/include/rawrbox/resources/loader.hpp index 59d034b8..70426ded 100644 --- a/rawrbox.resources/include/rawrbox/resources/loader.hpp +++ b/rawrbox.resources/include/rawrbox/resources/loader.hpp @@ -31,7 +31,7 @@ namespace rawrbox { // UTILS ----- [[nodiscard]] virtual const std::vector>& getPreload() const { return this->_preLoadFiles; } virtual void addToPreLoad(const std::filesystem::path& path, uint32_t loadFlags = 0) { - this->_logger->info("Content `{}` marked for pre-loading", fmt::styled(path.generic_string(), fmt::fg(fmt::color::coral))); + this->_logger->debug("Content `{}` marked for pre-loading", fmt::styled(path.generic_string(), fmt::fg(fmt::color::coral))); this->_preLoadFiles.emplace_back(path, loadFlags); } diff --git a/rawrbox.resources/include/rawrbox/resources/loaders/json.hpp b/rawrbox.resources/include/rawrbox/resources/loaders/json.hpp index f0627d1b..9a762710 100644 --- a/rawrbox.resources/include/rawrbox/resources/loaders/json.hpp +++ b/rawrbox.resources/include/rawrbox/resources/loaders/json.hpp @@ -6,6 +6,11 @@ namespace rawrbox { class ResourceJSON : public rawrbox::Resource { + protected: + // PRIVATE --- + static std::unique_ptr _logger; + // ------ + glz::json_t _json = {}; public: diff --git a/rawrbox.resources/include/rawrbox/resources/manager.hpp b/rawrbox.resources/include/rawrbox/resources/manager.hpp index fb688fd8..22114df3 100644 --- a/rawrbox.resources/include/rawrbox/resources/manager.hpp +++ b/rawrbox.resources/include/rawrbox/resources/manager.hpp @@ -69,14 +69,14 @@ namespace rawrbox { if (loader->supportsBuffer(ext)) { buffer = rawrbox::FileUtils::getRawData(filePath); if (buffer.empty()) { - throw _logger->error("Failed to load file '{}'", path); + CRITICAL_RAWRBOX("Failed to load file '{}'", path); } ret->crc32 = CRC::Calculate(buffer.data(), buffer.size(), CRC::CRC_32()); } ret->status = rawrbox::LoadStatus::LOADING; - if (!ret->load(buffer)) throw _logger->error("Failed to load file '{}'", path); + if (!ret->load(buffer)) CRITICAL_RAWRBOX("Failed to load file '{}'", path); ret->upload(); ret->status = rawrbox::LoadStatus::LOADED; @@ -91,7 +91,7 @@ namespace rawrbox { return ret; } - throw _logger->error("Attempted to load unknown file extension '{}'. Missing loader!", filePath.generic_string()); + CRITICAL_RAWRBOX("Attempted to load unknown file extension '{}'. Missing loader!", filePath.generic_string()); } // --------- @@ -132,7 +132,7 @@ namespace rawrbox { template requires(std::derived_from) static T* loadFile(const std::filesystem::path& filePath, uint32_t loadFlags = 0) { - if (filePath.empty()) throw _logger->error("Attempted to load empty path"); + if (filePath.empty()) CRITICAL_RAWRBOX("Attempted to load empty path"); return loadFileImpl(filePath, loadFlags); } @@ -144,7 +144,7 @@ namespace rawrbox { for (const auto& file : files) { rawrbox::ASYNC::run([file, onComplete]() { loadFileImpl(file.first, file.second); - _logger->info("Loaded '{}'", fmt::styled(file.first, fmt::fg(fmt::color::coral))); + _logger->debug("Loaded '{}'", fmt::styled(file.first, fmt::fg(fmt::color::coral))); _loadingFiles = std::max(_loadingFiles - 1, 0); if (_loadingFiles <= 0 && onComplete != nullptr) onComplete(); @@ -155,11 +155,11 @@ namespace rawrbox { template requires(std::derived_from) static void loadFileAsync(const std::filesystem::path& filePath, uint32_t loadFlags = 0, const std::function& onComplete = nullptr) { - if (filePath.empty()) throw _logger->error("Attempted to load empty path"); + if (filePath.empty()) CRITICAL_RAWRBOX("Attempted to load empty path"); rawrbox::ASYNC::run([filePath, loadFlags, onComplete]() { loadFileImpl(filePath, loadFlags); - _logger->info("Loaded '{}'", fmt::format(fmt::fg(fmt::color::coral), filePath.generic_string())); + _logger->debug("Loaded '{}'", fmt::format(fmt::fg(fmt::color::coral), filePath.generic_string())); if (onComplete != nullptr) onComplete(); }); @@ -170,7 +170,7 @@ namespace rawrbox { [[nodiscard]] static T* getFile(const std::filesystem::path& filePath) { auto fl = getFileImpl(filePath); if (fl == nullptr) { - throw _logger->error("File '{}' not loaded / found!", filePath.generic_string()); + CRITICAL_RAWRBOX("File '{}' not loaded / found!", filePath.generic_string()); } return fl; @@ -201,7 +201,7 @@ namespace rawrbox { loadFile(file.first, file.second); if (endLoad != nullptr) endLoad(file.first.generic_string(), file.second); - _logger->info("Loaded '{}'", fmt::styled(file.first.generic_string(), fmt::fg(fmt::color::coral))); + _logger->debug("Loaded '{}'", fmt::styled(file.first.generic_string(), fmt::fg(fmt::color::coral))); _loadingPreloadFiles = std::max(_loadingPreloadFiles - 1, 0); if (_loadingPreloadFiles <= 0 && onComplete != nullptr) onComplete(); diff --git a/rawrbox.resources/src/loaders/json.cpp b/rawrbox.resources/src/loaders/json.cpp index 24a0f91a..ad85e114 100644 --- a/rawrbox.resources/src/loaders/json.cpp +++ b/rawrbox.resources/src/loaders/json.cpp @@ -5,10 +5,14 @@ namespace rawrbox { // Resource ---- + // PRIVATE --- + std::unique_ptr ResourceJSON::_logger = std::make_unique("RawrBox-ResourceJSON"); + // ------ + bool ResourceJSON::load(const std::vector& buffer) { auto err = glz::read_json(this->_json, buffer); if (err != glz::error_code::none) { - throw rawrbox::Logger::err("ResourceJSON", "Failed to load '{}' ──> {}\n", this->filePath.generic_string(), magic_enum::enum_name(err.ec)); + CRITICAL_RAWRBOX("Failed to load '{}' ──> {}\n", this->filePath.generic_string(), magic_enum::enum_name(err.ec)); } return true; diff --git a/rawrbox.scripting/src/manager.cpp b/rawrbox.scripting/src/manager.cpp index 04e576f8..b4b80ab3 100644 --- a/rawrbox.scripting/src/manager.cpp +++ b/rawrbox.scripting/src/manager.cpp @@ -87,7 +87,7 @@ namespace rawrbox { // LOAD ----- void SCRIPTING::loadLibraries(rawrbox::Mod& mod) { auto* L = mod.getEnvironment(); - if (L == nullptr) throw _logger->error("LUA is not set! Reference got destroyed?"); + if (L == nullptr) CRITICAL_RAWRBOX("LUA is not set! Reference got destroyed?"); // COMMON ----- luaL_openlibs(L); // Should be safe, since LUAU takes care of non-secure libs (https://luau-lang.org/sandbox#library) @@ -121,7 +121,7 @@ namespace rawrbox { void SCRIPTING::loadTypes(rawrbox::Mod& mod) { auto* L = mod.getEnvironment(); - if (L == nullptr) throw _logger->error("LUA is not set! Reference got destroyed?"); + if (L == nullptr) CRITICAL_RAWRBOX("LUA is not set! Reference got destroyed?"); // Register types, these will be read-only & sandboxed! // Rawrbox --- @@ -164,7 +164,7 @@ namespace rawrbox { void SCRIPTING::loadGlobals(rawrbox::Mod& mod) { auto* L = mod.getEnvironment(); - if (L == nullptr) throw _logger->error("LUA is not set! Reference got destroyed?"); + if (L == nullptr) CRITICAL_RAWRBOX("LUA is not set! Reference got destroyed?"); // Register globals, these will be read-only & sandboxed! // OVERRIDES ---- @@ -293,7 +293,7 @@ namespace rawrbox { } if (hotReloadEnabled()) { - _logger->info("Registered {} -> {} for hot reload", fmt::styled(modId, fmt::fg(fmt::color::coral)), filePath.generic_string()); + _logger->debug("Registered {} -> {} for hot reload", fmt::styled(modId, fmt::fg(fmt::color::coral)), filePath.generic_string()); _watcher->watchFile(filePath); } } @@ -315,7 +315,7 @@ namespace rawrbox { try { rawrbox::LuaUtils::compileAndLoadFile(env, md->first, filePath); } catch (const std::exception& err) { - _logger->printError("{}", err.what()); + ERROR_RAWRBOX("{}", err.what()); } // --------------- @@ -347,7 +347,7 @@ namespace rawrbox { // LOADING ---- std::unordered_map SCRIPTING::loadMods(const std::filesystem::path& rootFolder) { // Load mods - if (!std::filesystem::exists(rootFolder)) throw _logger->error("Failed to locate root folder '{}'", rootFolder.generic_string()); + if (!std::filesystem::exists(rootFolder)) CRITICAL_RAWRBOX("Failed to locate root folder '{}'", rootFolder.generic_string()); std::unordered_map success = {}; for (const auto& p : std::filesystem::directory_iterator(rootFolder)) { @@ -361,8 +361,9 @@ namespace rawrbox { } rawrbox::Mod* SCRIPTING::loadMod(const std::string& id, const std::filesystem::path& modFolder) { - if (id.empty()) throw _logger->error("Mod ID cannot be empty"); - if (!std::filesystem::exists(modFolder)) throw _logger->error("Failed to locate mod folder '{}'", modFolder.generic_string()); + if (id.empty()) CRITICAL_RAWRBOX("Mod ID cannot be empty"); + if (!std::filesystem::exists(modFolder)) CRITICAL_RAWRBOX("Failed to locate mod folder '{}'", modFolder.generic_string()); + if (_mods.find(id) != _mods.end()) { _logger->warn("Mod {} already loaded! Mod name conflict?", id); return nullptr; @@ -374,7 +375,7 @@ namespace rawrbox { if (std::filesystem::exists(configPath)) { auto ec = glz::read_file_json(metadataJSON, configPath.generic_string(), std::string{}); - if (ec) throw _logger->error("Failed to load mod.json"); + if (ec) CRITICAL_RAWRBOX("Failed to load mod.json"); } // ----------------- @@ -397,7 +398,7 @@ namespace rawrbox { _logger->info("Mod '{}' loaded", fmt::styled(id, fmt::fg(fmt::color::coral))); registerLoadedFile(mod->getID(), mod->getEntryFilePath()); // Register file for hot-reloading } catch (const std::runtime_error& err) { - _logger->printError("{}", err.what()); + ERROR_RAWRBOX("{}", err.what()); return nullptr; } diff --git a/rawrbox.scripting/src/mod.cpp b/rawrbox.scripting/src/mod.cpp index 66a2f1f4..0c0514b1 100644 --- a/rawrbox.scripting/src/mod.cpp +++ b/rawrbox.scripting/src/mod.cpp @@ -10,12 +10,12 @@ namespace rawrbox { } void Mod::shutdown() { - if (this->_L == nullptr) throw _logger->error("Invalid lua handle"); + if (this->_L == nullptr) CRITICAL_RAWRBOX("Invalid lua handle"); this->call("onShutdown"); } void Mod::init() { - if (this->_L == nullptr) throw _logger->error("Invalid lua handle"); + if (this->_L == nullptr) CRITICAL_RAWRBOX("Invalid lua handle"); #ifdef RAWRBOX_SCRIPTING_EXCEPTION luabridge::enableExceptions(_L); @@ -46,17 +46,17 @@ namespace rawrbox { } void Mod::gc() { - if (this->_L == nullptr) throw _logger->error("Invalid lua handle"); + if (this->_L == nullptr) CRITICAL_RAWRBOX("Invalid lua handle"); rawrbox::LuaUtils::collect_garbage(this->_L); } void Mod::load() { - if (this->_L == nullptr) throw _logger->error("Invalid lua sandbox environment"); + if (this->_L == nullptr) CRITICAL_RAWRBOX("Invalid lua sandbox environment"); rawrbox::LuaUtils::compileAndLoadFile(this->_L, this->getID(), this->getEntryFilePath()); } void Mod::script(const std::string& script) { - if (this->_L == nullptr) throw _logger->error("Invalid lua sandbox environment"); + if (this->_L == nullptr) CRITICAL_RAWRBOX("Invalid lua sandbox environment"); rawrbox::LuaUtils::compileAndLoadScript(this->_L, "unknown", script); } diff --git a/rawrbox.steamworks/include/rawrbox/steamworks/utils.hpp b/rawrbox.steamworks/include/rawrbox/steamworks/utils.hpp index ef526f74..7ce2c920 100644 --- a/rawrbox.steamworks/include/rawrbox/steamworks/utils.hpp +++ b/rawrbox.steamworks/include/rawrbox/steamworks/utils.hpp @@ -1,5 +1,7 @@ #pragma once +#include + #include #include @@ -14,6 +16,8 @@ namespace rawrbox { class SteamUTILS { protected: + static std::unique_ptr _logger; + public: static rawrbox::SteamImage getImage(int handle); }; diff --git a/rawrbox.steamworks/src/callbacks/manager.cpp b/rawrbox.steamworks/src/callbacks/manager.cpp index 2f6b37c4..61b46f20 100644 --- a/rawrbox.steamworks/src/callbacks/manager.cpp +++ b/rawrbox.steamworks/src/callbacks/manager.cpp @@ -32,40 +32,40 @@ namespace rawrbox { void SteamCALLBACKS::OnWorkshopItemSubscribed(RemoteStoragePublishedFileSubscribed_t* pParam) { if (pParam->m_nAppID != STEAMWORKS_APPID) return; - this->_logger->info("Steam workshop subscribed: {}", pParam->m_nPublishedFileId); + this->_logger->debug("Steam workshop subscribed: {}", pParam->m_nPublishedFileId); this->onModSubscribed(pParam->m_nPublishedFileId); } void SteamCALLBACKS::OnWorkshopItemInstalled(ItemInstalled_t* pParam) { if (pParam->m_unAppID != STEAMWORKS_APPID) return; - this->_logger->info("Steam workshop installed: {}", pParam->m_nPublishedFileId); + this->_logger->debug("Steam workshop installed: {}", pParam->m_nPublishedFileId); this->onModInstalled(pParam->m_nPublishedFileId); } void SteamCALLBACKS::OnWorkshopItemUnSubscribed(RemoteStoragePublishedFileUnsubscribed_t* pParam) { if (pParam->m_nAppID != STEAMWORKS_APPID) return; - this->_logger->info("Steam workshop unsubscribed: {}", pParam->m_nPublishedFileId); // Seems to only be triggered after game shutsdown.. wow + this->_logger->debug("Steam workshop unsubscribed: {}", pParam->m_nPublishedFileId); // Seems to only be triggered after game shutsdown.. wow this->onModUnSubscribed(pParam->m_nPublishedFileId); } void SteamCALLBACKS::OnWorkshopItemDownloaded(DownloadItemResult_t* pParam) { if (pParam->m_unAppID != STEAMWORKS_APPID) return; - this->_logger->info("Steam workshop updated: {}", pParam->m_nPublishedFileId); + this->_logger->debug("Steam workshop updated: {}", pParam->m_nPublishedFileId); this->onModUpdated(pParam->m_nPublishedFileId); } // -------- // WORKSHOP --- void SteamCALLBACKS::OnWorkshopCreateItem(CreateItemResult_t* result, bool bIOFailure) { - if (bIOFailure) throw _logger->error("Failed to create workshop item"); + if (bIOFailure) CRITICAL_RAWRBOX("Failed to create workshop item"); if (this->_CreateItemResultCallback != nullptr) this->_CreateItemResultCallback(result); } void SteamCALLBACKS::OnWorkshopUpdateItem(SubmitItemUpdateResult_t* result, bool bIOFailure) { - if (bIOFailure) throw _logger->error("Failed to update workshop item"); + if (bIOFailure) CRITICAL_RAWRBOX("Failed to update workshop item"); if (this->_UpdateItemResultCallback != nullptr) this->_UpdateItemResultCallback(result); } // ------------- @@ -79,7 +79,7 @@ namespace rawrbox { _CallbackWorkshopItemDownloaded(this, &SteamCALLBACKS::OnWorkshopItemDownloaded) {} void SteamCALLBACKS::init() { - if (this->_initialized) throw this->_logger->error("Already initialized"); + if (this->_initialized) CRITICAL_RAWRBOX("Already initialized"); this->_initialized = true; } @@ -96,7 +96,7 @@ namespace rawrbox { // QUERY --- void SteamCALLBACKS::addUGCQueryCallback(SteamAPICall_t apicall, const std::function)>& callback) { auto fnd = this->_ugcQueries.find(apicall); - if (fnd != this->_ugcQueries.end()) throw _logger->error("AddUGCQueryCallback with api call {} already called! Wait for previous call to complete", apicall); + if (fnd != this->_ugcQueries.end()) CRITICAL_RAWRBOX("AddUGCQueryCallback with api call {} already called! Wait for previous call to complete", apicall); std::unique_ptr query = std::make_unique(apicall, [this, apicall, callback](std::vector details) { callback(std::move(details)); @@ -109,14 +109,14 @@ namespace rawrbox { // WORKSHOP --- void SteamCALLBACKS::addCreateItemCallback(SteamAPICall_t apicall, const std::function& callback) { - if (this->_CreateItemResultCallback != nullptr) throw _logger->error("AddUGCQueryCallback already called! Wait for previous call to complete"); + if (this->_CreateItemResultCallback != nullptr) CRITICAL_RAWRBOX("AddUGCQueryCallback already called! Wait for previous call to complete"); this->_CreateItemResultCallback = callback; this->_CreateItemResult.Set(apicall, this, &SteamCALLBACKS::OnWorkshopCreateItem); } void SteamCALLBACKS::addUpdateItemCallback(SteamAPICall_t apicall, const std::function& callback) { - if (this->_UpdateItemResultCallback != nullptr) throw _logger->error("AddUGCQueryCallback already called! Wait for previous call to complete"); + if (this->_UpdateItemResultCallback != nullptr) CRITICAL_RAWRBOX("AddUGCQueryCallback already called! Wait for previous call to complete"); this->_UpdateItemResultCallback = callback; this->_UpdateItemResult.Set(apicall, this, &SteamCALLBACKS::OnWorkshopUpdateItem); @@ -136,7 +136,7 @@ namespace rawrbox { void SteamCALLBACKS::addUGCRequest(UGCHandle_t handle, SteamAPICall_t apicall, const std::function)>& callback) { auto fnd = this->_ugcStorageQueries.find(apicall); - if (fnd != this->_ugcStorageQueries.end()) throw _logger->error("addUGCRequest with api call {} already called! Wait for previous call to complete", apicall); + if (fnd != this->_ugcStorageQueries.end()) CRITICAL_RAWRBOX("addUGCRequest with api call {} already called! Wait for previous call to complete", apicall); std::unique_ptr query = std::make_unique(handle, apicall, [this, apicall, callback](std::vector data) { callback(std::move(data)); diff --git a/rawrbox.steamworks/src/input.cpp b/rawrbox.steamworks/src/input.cpp index e63efbdc..73291db4 100644 --- a/rawrbox.steamworks/src/input.cpp +++ b/rawrbox.steamworks/src/input.cpp @@ -21,7 +21,7 @@ namespace rawrbox { // ------------ void SteamINPUT::init() { - if (SteamInput() == nullptr) throw _logger->error("SteamInput is null"); + if (SteamInput() == nullptr) CRITICAL_RAWRBOX("SteamInput is null"); SteamInput()->Init(false); } @@ -93,7 +93,7 @@ namespace rawrbox { _inputID = inputHandle; _actionID = actionHandle; - _logger->info("Set controller action to {}", actionSTR); + _logger->debug("Set controller action to {}", actionSTR); } ControllerJoystickData SteamINPUT::getAnalogData(ControllerActionAnalogHandle handle) { diff --git a/rawrbox.steamworks/src/sdk.cpp b/rawrbox.steamworks/src/sdk.cpp index 20215bb4..71d19ca0 100644 --- a/rawrbox.steamworks/src/sdk.cpp +++ b/rawrbox.steamworks/src/sdk.cpp @@ -33,7 +33,7 @@ namespace rawrbox { rawrbox::Event<> SteamSDK::onInitialized = {}; bool SteamSDK::init() { - if (_initialized) throw _logger->error("SteamSDK already initialized"); + if (_initialized) CRITICAL_RAWRBOX("SteamSDK already initialized"); #ifdef NDEBUG if (SteamAPI_RestartAppIfNecessary(STEAMWORKS_APPID)) return false; @@ -82,7 +82,7 @@ namespace rawrbox { } std::string SteamSDK::getBuildVersion() { - if (SteamApps() == nullptr) throw _logger->error("SteamApps not initialized"); + if (SteamApps() == nullptr) CRITICAL_RAWRBOX("SteamApps not initialized"); int id = SteamApps()->GetAppBuildId(); std::string str = fmt::format("BUILD {}", id); @@ -100,12 +100,12 @@ namespace rawrbox { // USER --- CSteamID SteamSDK::getSteamID() { - if (SteamUser() == nullptr) throw _logger->error("SteamUser not initialized"); + if (SteamUser() == nullptr) CRITICAL_RAWRBOX("SteamUser not initialized"); return SteamUser()->GetSteamID(); } std::string SteamSDK::getPersonaName(const CSteamID& id) { - if (SteamFriends() == nullptr) throw _logger->error("SteamFriends not initialized"); + if (SteamFriends() == nullptr) CRITICAL_RAWRBOX("SteamFriends not initialized"); if (!SteamFriends()->RequestUserInformation(id, true)) { const auto* name = SteamFriends()->GetFriendPersonaName(id); @@ -116,7 +116,7 @@ namespace rawrbox { } rawrbox::SteamImage SteamSDK::getAvatar(const CSteamID& id, const rawrbox::AvatarSize& size) { - if (SteamUser() == nullptr) throw _logger->error("SteamUser not initialized"); + if (SteamUser() == nullptr) CRITICAL_RAWRBOX("SteamUser not initialized"); rawrbox::SteamImage avatar = {}; int ptrId = 0; @@ -131,7 +131,7 @@ namespace rawrbox { } std::vector SteamSDK::getFriends() { - if (SteamFriends() == nullptr) throw _logger->error("SteamUser not initialized"); + if (SteamFriends() == nullptr) CRITICAL_RAWRBOX("SteamUser not initialized"); int friendCount = SteamFriends()->GetFriendCount(k_EFriendFlagImmediate); std::vector friends = {}; diff --git a/rawrbox.steamworks/src/utils.cpp b/rawrbox.steamworks/src/utils.cpp index 86cbb8c3..09afdaed 100644 --- a/rawrbox.steamworks/src/utils.cpp +++ b/rawrbox.steamworks/src/utils.cpp @@ -4,9 +4,13 @@ #include namespace rawrbox { + // PRIVATE ------------- + std::unique_ptr SteamUTILS::_logger = std::make_unique("RawrBox-SteamUTILS"); + // ------------- + rawrbox::SteamImage SteamUTILS::getImage(int handle) { - if (SteamUtils() == nullptr) throw rawrbox::Logger::err("SteamUTILS", "SteamUtils not initialized"); - if (handle == 0) throw rawrbox::Logger::err("SteamUTILS", "Invalid handle"); + if (SteamUtils() == nullptr) CRITICAL_RAWRBOX("SteamUtils not initialized"); + if (handle == 0) CRITICAL_RAWRBOX("Invalid handle"); rawrbox::SteamImage image = {}; diff --git a/rawrbox.steamworks/src/workshop/manager.cpp b/rawrbox.steamworks/src/workshop/manager.cpp index c85b66e9..35664e02 100644 --- a/rawrbox.steamworks/src/workshop/manager.cpp +++ b/rawrbox.steamworks/src/workshop/manager.cpp @@ -34,15 +34,15 @@ namespace rawrbox { auto status = getWorkshopModState(detail.m_nPublishedFileId); switch (status) { case WorkshopStatus::INSTALLED: - _logger->info("Found workshop item '{}'", detail.m_nPublishedFileId); + _logger->debug("Found workshop item '{}'", detail.m_nPublishedFileId); loadedMods.emplace_back(detail); break; case WorkshopStatus::NEEDS_UPDATE: { - _logger->info("Updating workshop item '{}'", detail.m_nPublishedFileId); + _logger->debug("Updating workshop item '{}'", detail.m_nPublishedFileId); if (!downloadMod(detail.m_nPublishedFileId, true)) { - throw _logger->error("Failed to update workshop item '{}'", detail.m_nPublishedFileId); + CRITICAL_RAWRBOX("Failed to update workshop item '{}'", detail.m_nPublishedFileId); } } break; @@ -59,12 +59,12 @@ namespace rawrbox { // UTILS --- void SteamWORKSHOP::patchConfig(const std::filesystem::path& rootPath, const rawrbox::WorkshopModConfig& config) { auto configPath = fmt::format("{}/mod.json", rootPath.generic_string()); - if (!std::filesystem::exists(configPath)) throw _logger->error("Missing 'mod.json' file"); + if (!std::filesystem::exists(configPath)) CRITICAL_RAWRBOX("Missing 'mod.json' file"); auto ec = glz::write_file_json(config, configPath, std::string{}); - if (ec != glz::error_code::none) throw _logger->error("Failed to patch settings '{}'", configPath); + if (ec != glz::error_code::none) CRITICAL_RAWRBOX("Failed to patch settings '{}'", configPath); - _logger->success("Patched mod config"); + _logger->debug("Patched mod config"); } // ------- @@ -91,49 +91,49 @@ namespace rawrbox { } void SteamWORKSHOP::updateItem(PublishedFileId_t id, const rawrbox::WorkshopModConfig& config, const std::filesystem::path& uploadPath, const std::function& callback, bool isNewMod) { - if (SteamUGC() == nullptr) throw _logger->error("SteamUGC not initialized"); - if (!config.id.has_value()) throw _logger->error("Invalid mod id"); + if (SteamUGC() == nullptr) CRITICAL_RAWRBOX("SteamUGC not initialized"); + if (!config.id.has_value()) CRITICAL_RAWRBOX("Invalid mod id"); UGCUpdateHandle_t updateHandle = SteamUGC()->StartItemUpdate(STEAMWORKS_APPID, id); - if (updateHandle == k_UGCUpdateHandleInvalid) throw _logger->error("Failed to start item update"); + if (updateHandle == k_UGCUpdateHandleInvalid) CRITICAL_RAWRBOX("Failed to start item update"); // SETUP TITLE AND DESCRIPTION ---- if (isNewMod) { auto description = config.description.value_or("Mod's description"); - if (!SteamUGC()->SetItemTitle(updateHandle, config.title.c_str())) throw _logger->error("Failed to set workshop item title"); - if (!SteamUGC()->SetItemDescription(updateHandle, description.c_str())) throw _logger->error("Failed to set workshop item description"); + if (!SteamUGC()->SetItemTitle(updateHandle, config.title.c_str())) CRITICAL_RAWRBOX("Failed to set workshop item title"); + if (!SteamUGC()->SetItemDescription(updateHandle, description.c_str())) CRITICAL_RAWRBOX("Failed to set workshop item description"); } // ------ // SETUP KEY VALUES ---- std::string type = config.type.value_or("MOD"); if (!type.empty()) { - if (!SteamUGC()->AddItemKeyValueTag(updateHandle, "MOD_TYPE", type.c_str())) throw _logger->error("Failed to set workshop type"); + if (!SteamUGC()->AddItemKeyValueTag(updateHandle, "MOD_TYPE", type.c_str())) CRITICAL_RAWRBOX("Failed to set workshop type"); } - if (!SteamUGC()->AddItemKeyValueTag(updateHandle, "MOD_ID", config.id.value().c_str())) throw _logger->error("Failed to set workshop mod id"); + if (!SteamUGC()->AddItemKeyValueTag(updateHandle, "MOD_ID", config.id.value().c_str())) CRITICAL_RAWRBOX("Failed to set workshop mod id"); // ---------------------- // SETUP DEPENDENCIES ---- if (config.dependencies.has_value()) { for (const auto& dep : config.dependencies.value()) { PublishedFileId_t depId = std::strtoull(dep.c_str(), nullptr, 10); - if (depId == id) throw _logger->error("Cannot add self as a dependency"); + if (depId == id) CRITICAL_RAWRBOX("Cannot add self as a dependency"); - if (SteamUGC()->AddDependency(id, depId) == 0) throw _logger->error("Failed to set workshop dependency {}", dep); + if (SteamUGC()->AddDependency(id, depId) == 0) CRITICAL_RAWRBOX("Failed to set workshop dependency {}", dep); } } // ---------------- // SETUP CONTENT ---- - if (!SteamUGC()->SetItemContent(updateHandle, uploadPath.generic_string().c_str())) throw _logger->error("Failed to set workshop item content"); + if (!SteamUGC()->SetItemContent(updateHandle, uploadPath.generic_string().c_str())) CRITICAL_RAWRBOX("Failed to set workshop item content"); // ------ // SETUP PREVIEW ---- if (config.preview.has_value()) { std::string previewPath = std::filesystem::absolute(fmt::format("{}/{}", uploadPath.generic_string(), config.preview.value())).generic_string(); - if (!SteamUGC()->SetItemPreview(updateHandle, previewPath.c_str())) throw _logger->error("Failed to set workshop item preview image"); + if (!SteamUGC()->SetItemPreview(updateHandle, previewPath.c_str())) CRITICAL_RAWRBOX("Failed to set workshop item preview image"); } // ------------- @@ -144,7 +144,7 @@ namespace rawrbox { std::string changelog = fmt::format("Auto-update by engine v{}", rawrbox::SteamSDK::getBuildVersion()); SteamAPICall_t apicall = SteamUGC()->SubmitItemUpdate(updateHandle, changelog.c_str()); - if (apicall == 0) throw _logger->error("Failed to update workshop item"); + if (apicall == 0) CRITICAL_RAWRBOX("Failed to update workshop item"); SteamCALLBACKS::getInstance().addUpdateItemCallback(apicall, callback); } @@ -163,7 +163,7 @@ namespace rawrbox { rawrbox::Event SteamWORKSHOP::onModValidate = {}; void SteamWORKSHOP::init() { - if (SteamUGC() == nullptr) throw _logger->error("SteamUGC not initialized"); + if (SteamUGC() == nullptr) CRITICAL_RAWRBOX("SteamUGC not initialized"); // Register callback events --- SteamCALLBACKS::getInstance().onModInstalled += [](PublishedFileId_t id) { @@ -201,13 +201,13 @@ namespace rawrbox { } bool SteamWORKSHOP::downloadMod(PublishedFileId_t id, bool highPriority) { - if (SteamUGC() == nullptr) throw _logger->error("SteamUGC not initialized"); + if (SteamUGC() == nullptr) CRITICAL_RAWRBOX("SteamUGC not initialized"); return SteamUGC()->DownloadItem(id, highPriority); } // UTILS ----- std::vector SteamWORKSHOP::getSubbedWorkshopMods() { - if (SteamUGC() == nullptr) throw _logger->error("SteamUGC not initialized"); + if (SteamUGC() == nullptr) CRITICAL_RAWRBOX("SteamUGC not initialized"); uint32_t totalItems = SteamUGC()->GetNumSubscribedItems(); std::vector mods(totalItems); @@ -217,7 +217,7 @@ namespace rawrbox { } std::filesystem::path SteamWORKSHOP::getWorkshopModFolder(PublishedFileId_t id) { - if (SteamUGC() == nullptr) throw _logger->error("SteamUGC not initialized"); + if (SteamUGC() == nullptr) CRITICAL_RAWRBOX("SteamUGC not initialized"); uint64 size = 0; uint32 updateTimestamp = 0; @@ -230,7 +230,7 @@ namespace rawrbox { rawrbox::WorkshopStatus SteamWORKSHOP::getWorkshopModState(PublishedFileId_t id) { if (id == 0) return rawrbox::WorkshopStatus::INSTALLED; // Assume local mod & unpublished - if (SteamUGC() == nullptr) throw _logger->error("SteamUGC not initialized"); + if (SteamUGC() == nullptr) CRITICAL_RAWRBOX("SteamUGC not initialized"); uint32 state = SteamUGC()->GetItemState(id); if ((state & EItemState::k_EItemStateSubscribed) == 0U) { @@ -260,11 +260,11 @@ namespace rawrbox { // QUERIES ---- void SteamWORKSHOP::queryUserMods(const std::function)>& callback, EUserUGCList type, const std::vector& tags, uint32_t page) { - if (SteamUGC() == nullptr) throw _logger->error("SteamUGC not initialized"); + if (SteamUGC() == nullptr) CRITICAL_RAWRBOX("SteamUGC not initialized"); auto id = SteamUser()->GetSteamID().GetAccountID(); UGCQueryHandle_t handle = SteamUGC()->CreateQueryUserUGCRequest(id, type, k_EUGCMatchingUGCType_Items, k_EUserUGCListSortOrder_CreationOrderDesc, STEAMWORKS_APPID, STEAMWORKS_APPID, page); - if (handle == k_UGCQueryHandleInvalid) throw _logger->error("Failed to request workshop items"); + if (handle == k_UGCQueryHandleInvalid) CRITICAL_RAWRBOX("Failed to request workshop items"); // TAGS ----- for (const auto& tag : tags) { @@ -275,7 +275,7 @@ namespace rawrbox { } // ----------- - if (!SteamUGC()->SetReturnKeyValueTags(handle, true)) throw _logger->error("Failed to request key values"); + if (!SteamUGC()->SetReturnKeyValueTags(handle, true)) CRITICAL_RAWRBOX("Failed to request key values"); SteamAPICall_t hSteamAPICall = SteamUGC()->SendQueryUGCRequest(handle); SteamCALLBACKS::getInstance().addUGCQueryCallback(hSteamAPICall, [callback](const std::vector& details) { @@ -284,10 +284,10 @@ namespace rawrbox { } void SteamWORKSHOP::queryMods(const std::function)>& callback, EUGCQuery type, const std::vector& tags, uint32_t page) { - if (SteamUGC() == nullptr) throw _logger->error("SteamUGC not initialized"); + if (SteamUGC() == nullptr) CRITICAL_RAWRBOX("SteamUGC not initialized"); UGCQueryHandle_t handle = SteamUGC()->CreateQueryAllUGCRequest(type, k_EUGCMatchingUGCType_Items, STEAMWORKS_APPID, STEAMWORKS_APPID, page); - if (handle == k_UGCQueryHandleInvalid) throw _logger->error("Failed to request workshop items"); + if (handle == k_UGCQueryHandleInvalid) CRITICAL_RAWRBOX("Failed to request workshop items"); // TAGS ----- for (const auto& tag : tags) { @@ -298,7 +298,7 @@ namespace rawrbox { } // ----------- - if (!SteamUGC()->SetReturnKeyValueTags(handle, true)) throw _logger->error("Failed to request key values"); + if (!SteamUGC()->SetReturnKeyValueTags(handle, true)) CRITICAL_RAWRBOX("Failed to request key values"); SteamAPICall_t hSteamAPICall = SteamUGC()->SendQueryUGCRequest(handle); SteamCALLBACKS::getInstance().addUGCQueryCallback(hSteamAPICall, [callback](const std::vector& details) { @@ -308,8 +308,8 @@ namespace rawrbox { void SteamWORKSHOP::queryMods(std::vector ids, const std::function)>& callback) { UGCQueryHandle_t handle = SteamUGC()->CreateQueryUGCDetailsRequest(ids.data(), static_cast(ids.size())); - if (handle == k_UGCQueryHandleInvalid) throw _logger->error("Failed to request workshop items"); - if (!SteamUGC()->SetReturnKeyValueTags(handle, true)) throw _logger->error("Failed to request workshop items"); + if (handle == k_UGCQueryHandleInvalid) CRITICAL_RAWRBOX("Failed to request workshop items"); + if (!SteamUGC()->SetReturnKeyValueTags(handle, true)) CRITICAL_RAWRBOX("Failed to request workshop items"); SteamAPICall_t hSteamAPICall = SteamUGC()->SendQueryUGCRequest(handle); SteamCALLBACKS::getInstance().addUGCQueryCallback(hSteamAPICall, [callback](const std::vector& details) { @@ -324,13 +324,13 @@ namespace rawrbox { auto result = glz::read_file_json(config, fmt::format("{}/mod.json", rootPath.generic_string()), std::string{}); if (result.ec != glz::error_code::none) { - throw _logger->error("Failed to read 'mod.json' file {{}}", magic_enum::enum_name(result.ec)); + CRITICAL_RAWRBOX("Failed to read 'mod.json' file {{}}", magic_enum::enum_name(result.ec)); } // Always override and fill id if (!config.id.has_value()) { config.id = rootPath.filename().generic_string(); - _logger->info("Missing mod id, using {}", config.id.value()); + _logger->warn("Missing mod id, using {}", config.id.value()); } // --------------- @@ -339,7 +339,7 @@ namespace rawrbox { auto previewPath = std::filesystem::absolute(rootPath / config.preview.value()); if (!std::filesystem::exists(previewPath)) { - throw _logger->error("Failed to find 'preview' image '{}'", previewPath.generic_string()); + CRITICAL_RAWRBOX("Failed to find 'preview' image '{}'", previewPath.generic_string()); } } // ---------------- @@ -378,7 +378,7 @@ namespace rawrbox { }; validateAndCollectFiles(std::filesystem::recursive_directory_iterator(rootPath)); - if (uploadFiles.empty()) throw _logger->error("\nCannot upload empty mod!"); + if (uploadFiles.empty()) CRITICAL_RAWRBOX("\nCannot upload empty mod!"); return uploadFiles; } @@ -402,10 +402,10 @@ namespace rawrbox { } void SteamWORKSHOP::updateWorkshop(PublishedFileId_t id, const rawrbox::WorkshopModConfig& config, const std::filesystem::path& rootPath, const std::vector& files, const std::function& onComplete) { - if (files.empty()) throw _logger->error("Cannot upload empty mod!"); + if (files.empty()) CRITICAL_RAWRBOX("Cannot upload empty mod!"); auto tempFolder = moveToTempModFolder(rootPath.generic_string(), files); - _logger->info("Created temp folder '{}'", tempFolder.generic_string()); + _logger->debug("Created temp folder '{}'", tempFolder.generic_string()); updateItem( id, @@ -416,19 +416,19 @@ namespace rawrbox { } void SteamWORKSHOP::createWorkshop(rawrbox::WorkshopModConfig& config, const std::filesystem::path& rootPath, const std::vector& files, const std::function& onComplete) { - if (files.empty()) throw _logger->error("Cannot upload empty mod!"); - if (config.__workshop_id__.has_value()) throw _logger->error("Mod already has a workshop id"); + if (files.empty()) CRITICAL_RAWRBOX("Cannot upload empty mod!"); + if (config.__workshop_id__.has_value()) CRITICAL_RAWRBOX("Mod already has a workshop id"); SteamAPICall_t apicall = SteamUGC()->CreateItem(STEAMWORKS_APPID, k_EWorkshopFileTypeCommunity); - if (apicall == 0) throw _logger->error("Failed to create workshop item"); + if (apicall == 0) CRITICAL_RAWRBOX("Failed to create workshop item"); SteamCALLBACKS::getInstance().addCreateItemCallback(apicall, [&config, &rootPath, &files, onComplete](CreateItemResult_t* result) { if (result->m_bUserNeedsToAcceptWorkshopLegalAgreement) { - throw _logger->error("User needs to accept steam's workshop agreement (https://steamcommunity.com/sharedfiles/workshoplegalagreement)"); + CRITICAL_RAWRBOX("User needs to accept steam's workshop agreement (https://steamcommunity.com/sharedfiles/workshoplegalagreement)"); } auto err = checkErrors(result->m_eResult); - if (!err.empty()) throw _logger->error("{}", err); + if (!err.empty()) CRITICAL_RAWRBOX("{}", err); // PATCH CONFIG ---- config.__workshop_id__ = std::to_string(result->m_nPublishedFileId); @@ -436,7 +436,7 @@ namespace rawrbox { // ------ auto tempFolder = moveToTempModFolder(rootPath.generic_string(), files); - _logger->info("Created temp folder '{}'", tempFolder.generic_string()); + _logger->debug("Created temp folder '{}'", tempFolder.generic_string()); updateItem( result->m_nPublishedFileId, config, tempFolder, [onComplete](SubmitItemUpdateResult_t* result) { diff --git a/rawrbox.steamworks/src/workshop/storage.cpp b/rawrbox.steamworks/src/workshop/storage.cpp index 9678fa2f..0d130647 100644 --- a/rawrbox.steamworks/src/workshop/storage.cpp +++ b/rawrbox.steamworks/src/workshop/storage.cpp @@ -21,7 +21,7 @@ namespace rawrbox { } void SteamSTORAGE::download(UGCHandle_t handle, const std::function)>& callback, uint32_t priority) { - if (SteamRemoteStorage() == nullptr) throw _logger->error("SteamRemoteStorage not initialized"); + if (SteamRemoteStorage() == nullptr) CRITICAL_RAWRBOX("SteamRemoteStorage not initialized"); // DOWNLOAD --- SteamAPICall_t hAPICall = SteamRemoteStorage()->UGCDownload(handle, priority); diff --git a/rawrbox.ui/include/rawrbox/ui/container.hpp b/rawrbox.ui/include/rawrbox/ui/container.hpp index 65ae6cd9..6b15b64a 100644 --- a/rawrbox.ui/include/rawrbox/ui/container.hpp +++ b/rawrbox.ui/include/rawrbox/ui/container.hpp @@ -2,6 +2,7 @@ #include #include +#include #include #include @@ -20,6 +21,7 @@ namespace rawrbox { rawrbox::UIRoot* _root = nullptr; std::vector> _children = {}; + std::unique_ptr _logger = std::make_unique("RawrBox-UIContainer"); bool _alwaysOnTop = false; rawrbox::AABBf _aabb = {}; @@ -31,9 +33,9 @@ namespace rawrbox { virtual ~UIContainer() = default; UIContainer(rawrbox::UIRoot* root); - UIContainer(const UIContainer&) = default; + UIContainer(const UIContainer&) = delete; UIContainer(UIContainer&&) noexcept; - UIContainer& operator=(const UIContainer&) = default; + UIContainer& operator=(const UIContainer&) = delete; UIContainer& operator=(UIContainer&&) = delete; // UTILS --- diff --git a/rawrbox.ui/include/rawrbox/ui/elements/anim.hpp b/rawrbox.ui/include/rawrbox/ui/elements/anim.hpp index ec89b976..362dbfd3 100644 --- a/rawrbox.ui/include/rawrbox/ui/elements/anim.hpp +++ b/rawrbox.ui/include/rawrbox/ui/elements/anim.hpp @@ -65,8 +65,8 @@ namespace rawrbox { virtual void setPos(const rawrbox::Vector2f& pos) { this->_posOffset = pos; }; virtual void setElement(T* element) { this->_element = element; }; virtual void setAnimation(const glz::json_t& json) { - if (!json.contains("anim")) throw rawrbox::Logger::err("RawrBox-UI", "Missing anim data"); - if (!json["anim"].holds()) throw rawrbox::Logger::err("RawrBox-UI", "Invalid anim data"); + if (!json.contains("anim")) throw std::runtime_error("[RawrBox-UI] Missing 'anim' data"); + if (!json["anim"].holds()) throw std::runtime_error("[RawrBox-UI] Invalid 'anim' data"); auto jsonData = json["anim"].get(); for (auto& data : jsonData) { diff --git a/rawrbox.ui/src/container.cpp b/rawrbox.ui/src/container.cpp index f084f375..d8666fd3 100644 --- a/rawrbox.ui/src/container.cpp +++ b/rawrbox.ui/src/container.cpp @@ -4,7 +4,7 @@ namespace rawrbox { UIContainer::UIContainer(rawrbox::UIRoot* root) : _root(root) { - if (_root == nullptr) throw rawrbox::Logger::err("UIContainer", "UI root cannot be null!"); + if (_root == nullptr) CRITICAL_RAWRBOX("UI root cannot be null!"); } UIContainer::UIContainer(rawrbox::UIContainer&& other) noexcept : _parent(other._parent), _children(std::move(other._children)), _alwaysOnTop(other._alwaysOnTop), _aabb(other._aabb) {} diff --git a/rawrbox.ui/src/elements/console.cpp b/rawrbox.ui/src/elements/console.cpp index e7489f89..3469ddca 100644 --- a/rawrbox.ui/src/elements/console.cpp +++ b/rawrbox.ui/src/elements/console.cpp @@ -10,7 +10,7 @@ namespace rawrbox { UIConsole::UIConsole(rawrbox::UIRoot* root, rawrbox::Console& console) : rawrbox::UIContainer(root), _console(&console) { - if (this->_console == nullptr) throw rawrbox::Logger::err("UIConsole", "Invalid console reference"); + if (this->_console == nullptr) CRITICAL_RAWRBOX("Invalid console reference"); this->_overlay = rawrbox::RESOURCES::getFile("./assets/textures/ui/overlay/overlay.png")->get(); diff --git a/rawrbox.ui/src/elements/tabs.cpp b/rawrbox.ui/src/elements/tabs.cpp index 489c2cbf..c67480c0 100644 --- a/rawrbox.ui/src/elements/tabs.cpp +++ b/rawrbox.ui/src/elements/tabs.cpp @@ -7,7 +7,7 @@ namespace rawrbox { // PRIVATE ---- void UITabs::generate() { - if (this->_buttonGroup == nullptr) throw rawrbox::Logger::err("UITabs", "Button group is null"); + if (this->_buttonGroup == nullptr) CRITICAL_RAWRBOX("Button group is null"); const auto& size = this->getSize(); // Create the main group --- @@ -62,11 +62,11 @@ namespace rawrbox { // TABS --- void UITabs::setActive(size_t index) { - if (index > this->_tabs.size()) throw rawrbox::Logger::err("UITabs", "Invalid index {}", index); + if (index > this->_tabs.size()) CRITICAL_RAWRBOX("Invalid index {}", index); auto& tab = this->_tabs[index]; - if (tab.button == nullptr) throw rawrbox::Logger::err("UITabs", "Invalid tab button from index {}", index); - if (tab.group == nullptr) throw rawrbox::Logger::err("UITabs", "Invalid tab group from index {}", index); + if (tab.button == nullptr) CRITICAL_RAWRBOX("Invalid tab button from index {}", index); + if (tab.group == nullptr) CRITICAL_RAWRBOX("Invalid tab group from index {}", index); if (this->_activeTab == &tab) return; @@ -85,11 +85,11 @@ namespace rawrbox { } void UITabs::setEnabled(size_t index, bool enabled) { - if (index > this->_tabs.size()) throw rawrbox::Logger::err("UITabs", "Invalid index {}", index); + if (index > this->_tabs.size()) CRITICAL_RAWRBOX("Invalid index {}", index); auto& tab = this->_tabs[index]; - if (tab.button == nullptr) throw rawrbox::Logger::err("UITabs", "Invalid tab button from index {}", index); - if (tab.group == nullptr) throw rawrbox::Logger::err("UITabs", "Invalid tab group from index {}", index); + if (tab.button == nullptr) CRITICAL_RAWRBOX("Invalid tab button from index {}", index); + if (tab.group == nullptr) CRITICAL_RAWRBOX("Invalid tab group from index {}", index); tab.button->setEnabled(enabled); } diff --git a/rawrbox.ui/src/popup/manager.cpp b/rawrbox.ui/src/popup/manager.cpp index 670ac174..cbb26891 100644 --- a/rawrbox.ui/src/popup/manager.cpp +++ b/rawrbox.ui/src/popup/manager.cpp @@ -15,7 +15,7 @@ namespace rawrbox { // ---------- void POPUP::init(rawrbox::UIRoot* root) { - if (root == nullptr) throw _logger->error("Invalid UIRoot!"); + if (root == nullptr) CRITICAL_RAWRBOX("Invalid UIRoot!"); _root = root; } @@ -25,7 +25,7 @@ namespace rawrbox { } rawrbox::UIFrame* POPUP::spawn(const std::string& id, const std::string& title, const std::string& message, rawrbox::PopupType type, const std::function& callback) { - if (_root == nullptr) throw _logger->error("UIRoot is not initialized!"); + if (_root == nullptr) CRITICAL_RAWRBOX("UIRoot is not initialized!"); auto titleColor = rawrbox::Color::RGBHex(0xFFFFFF); auto btnColor = rawrbox::Color::RGBHex(0x282a2e); diff --git a/rawrbox.utils/CMakeLists.txt b/rawrbox.utils/CMakeLists.txt index dcedaec9..a9bf5cc0 100644 --- a/rawrbox.utils/CMakeLists.txt +++ b/rawrbox.utils/CMakeLists.txt @@ -76,16 +76,20 @@ if(thread-pool_ADDED) target_include_directories(thread-pool INTERFACE ${thread-pool_SOURCE_DIR}/include) endif() -# DEPS ---- -if(RAWRBOX_TRACE_EXCEPTIONS) - CPMAddPackage("gh:jeremy-rifkin/cpptrace@0.7.2") - if(cpptrace_ADDED) - set_lib_runtime_mt(cpptrace-lib) - endif() - - list(APPEND EXTRA_UTIL_LIBS cpptrace::cpptrace) +CPMAddPackage( + NAME + spdlog + GITHUB_REPOSITORY + gabime/spdlog + VERSION + 1.14.1 + OPTIONS + "SPDLOG_FMT_EXTERNAL ON" + ) + +if(spdlog_ADDED) + set_lib_runtime_mt(spdlog) endif() -# -------------- # ---- # LIB ---- @@ -95,14 +99,11 @@ target_include_directories(${output_target} PUBLIC "include" ${EXTRA_UTIL_INCLUD target_compile_features(${output_target} PUBLIC cxx_std_${CMAKE_CXX_STANDARD}) target_compile_definitions(${output_target} PRIVATE _CRT_SECURE_NO_WARNINGS NOMINMAX) target_compile_definitions(${output_target} PUBLIC RAWRBOX_UTILS) -if(RAWRBOX_TRACE_EXCEPTIONS) - target_compile_definitions(${output_target} PUBLIC RAWRBOX_TRACE_EXCEPTIONS) -endif() - target_link_libraries(${output_target} PUBLIC ${EXTRA_UTIL_LIBS} thread-pool + spdlog fmt::fmt glaze::glaze magic_enum::magic_enum @@ -114,12 +115,3 @@ set_lib_runtime_mt(${output_target}) # TEST ---- include(../cmake/catch2.cmake) # -------------- - -if(WIN32 AND RAWRBOX_TRACE_EXCEPTIONS) - add_custom_command( - TARGET ${output_target} POST_BUILD - COMMAND ${CMAKE_COMMAND} -E copy_if_different - $ - $ - ) -endif() diff --git a/rawrbox.utils/include/rawrbox/utils/logger.hpp b/rawrbox.utils/include/rawrbox/utils/logger.hpp index 9773b110..0bc3fa00 100644 --- a/rawrbox.utils/include/rawrbox/utils/logger.hpp +++ b/rawrbox.utils/include/rawrbox/utils/logger.hpp @@ -1,80 +1,66 @@ #pragma once -#ifdef RAWRBOX_TRACE_EXCEPTIONS - #include -#endif - #include #include +#include +#include +#include #include +#define CRITICAL_RAWRBOX(...) \ + { \ + spdlog::critical("] {}\n └── {}:{}\n\t└── {}", fmt::format(__VA_ARGS__), __FILE__, __LINE__, fmt::styled(__FUNCTION__, fmt::fg(fmt::color::red))); \ + throw std::runtime_error(fmt::format(__VA_ARGS__)); \ + } + +#define ERROR_RAWRBOX(...) \ + spdlog::error("] {}\n └── {}:{}\n\t└── {}", fmt::format(__VA_ARGS__), __FILE__, __LINE__, fmt::styled(__FUNCTION__, fmt::fg(fmt::color::red))); + namespace rawrbox { class Logger { protected: - std::string _title = "UNKNOWN"; - bool _autoNewLine = true; + std::string _title; public: + static std::shared_ptr LOGGER; + static spdlog::level::level_enum LEVEL; + static bool ENABLE_FILE_LOGGING; + Logger(const std::string& title); - void setAutoNewLine(bool set); + // LOGGING ---- template - void warn(fmt::format_string fmt, T&&... args) { - auto str = fmt::format(fmt, std::forward(args)...); - - fmt::print("[{} ▓ {}]: {}", fmt::styled("WARN", fmt::fg(fmt::color::yellow)), fmt::styled(this->_title, fmt::fg(fmt::color::gold)), fmt::styled(str, fmt::fg(fmt::color::yellow))); - if (this->_autoNewLine) fmt::print("\n"); - } + void info(fmt::format_string fmt, T&&... args) { + if (LOGGER == nullptr) return; -#ifdef RAWRBOX_TRACE_EXCEPTIONS - template - cpptrace::runtime_error error(fmt::format_string fmt, T&&... args) { auto str = fmt::format(fmt, std::forward(args)...); - return cpptrace::runtime_error(fmt::format("[{} ▓ {}]: {}", fmt::styled("ERROR", fmt::fg(fmt::color::red)), fmt::styled(this->_title, fmt::fg(fmt::color::gold)), str)); + LOGGER->info(" ▓ {}] {}", this->_title, str); } template - static cpptrace::runtime_error err(const std::string& title, fmt::format_string fmt, T&&... args) { - auto str = fmt::format(fmt, std::forward(args)...); - return cpptrace::runtime_error(fmt::format("[{} ▓ {}]: {}", fmt::styled("ERROR", fmt::fg(fmt::color::red)), fmt::styled(title, fmt::fg(fmt::color::gold)), str)); - } -#else - template - std::exception error(fmt::format_string fmt, T&&... args) { - auto str = fmt::format(fmt, std::forward(args)...); - return std::runtime_error(fmt::format("[{} ▓ {}]: {}", fmt::styled("ERROR", fmt::fg(fmt::color::red)), fmt::styled(this->_title, fmt::fg(fmt::color::gold)), str)); - } + void warn(fmt::format_string fmt, T&&... args) { + if (LOGGER == nullptr) return; - template - static std::exception err(const std::string& title, fmt::format_string fmt, T&&... args) { auto str = fmt::format(fmt, std::forward(args)...); - return std::runtime_error(fmt::format("[{} ▓ {}]: {}", fmt::styled("ERROR", fmt::fg(fmt::color::red)), fmt::styled(title, fmt::fg(fmt::color::gold)), str)); + LOGGER->warn(" ▓ {}] {}", this->_title, fmt::styled(str, fmt::fg(fmt::color::gold))); } -#endif template - void printError(fmt::format_string fmt, T&&... args) { - auto str = fmt::format(fmt, std::forward(args)...); - - fmt::print("[{} ▓ {}]: {}", fmt::styled("ERROR", fmt::fg(fmt::color::red)), fmt::styled(this->_title, fmt::fg(fmt::color::gold)), str); - if (this->_autoNewLine) fmt::print("\n"); - } + void trace(fmt::format_string fmt, T&&... args) { + if (LOGGER == nullptr) return; - template - void info(fmt::format_string fmt, T&&... args) { auto str = fmt::format(fmt, std::forward(args)...); - - fmt::print("[{} ▓ {}]: {}", fmt::styled("INFO", fmt::fg(fmt::color::alice_blue)), fmt::styled(this->_title, fmt::fg(fmt::color::gold)), str); - if (this->_autoNewLine) fmt::print("\n"); + LOGGER->trace(" ▓ {}] {}", this->_title, str); } template - void success(fmt::format_string fmt, T&&... args) { - auto str = fmt::format(fmt, std::forward(args)...); + void debug(fmt::format_string fmt, T&&... args) { + if (LOGGER == nullptr) return; - fmt::print("[{} ▓ {}]: {}", fmt::styled("SUCCESS", fmt::fg(fmt::color::lime_green)), fmt::styled(this->_title, fmt::fg(fmt::color::gold)), str); - if (this->_autoNewLine) fmt::print("\n"); + auto str = fmt::format(fmt, std::forward(args)...); + LOGGER->debug(" ▓ {}] {}", this->_title, str); } + // ---------- }; } // namespace rawrbox diff --git a/rawrbox.utils/include/rawrbox/utils/settings.hpp b/rawrbox.utils/include/rawrbox/utils/settings.hpp index 57ca20a2..8c121861 100644 --- a/rawrbox.utils/include/rawrbox/utils/settings.hpp +++ b/rawrbox.utils/include/rawrbox/utils/settings.hpp @@ -38,7 +38,7 @@ namespace rawrbox { virtual void load(const std::string& rawData) { if (!rawData.empty()) { auto err = glz::read(this->_settings, rawData); - if (err != glz::error_code::none) throw this->_logger->error("Failed to load settings ──> {}", magic_enum::enum_name(err.ec)); + if (err != glz::error_code::none) CRITICAL_RAWRBOX("Failed to load settings ──> {}", magic_enum::enum_name(err.ec)); } else { this->_settings = {}; } @@ -51,7 +51,7 @@ namespace rawrbox { if (std::filesystem::exists(this->getFileName())) { auto err = glz::read_file_json(this->_settings, filePath.generic_string(), std::string{}); - if (err != glz::error_code::none) throw _logger->error("Failed to load '{}' ──> {}", filePath.generic_string(), magic_enum::enum_name(err.ec)); + if (err != glz::error_code::none) CRITICAL_RAWRBOX("Failed to load '{}' ──> {}", filePath.generic_string(), magic_enum::enum_name(err.ec)); } else { this->_settings = {}; } @@ -62,11 +62,11 @@ namespace rawrbox { virtual void save() { auto fileName = this->getFileName().generic_string(); auto ec = glz::write_file_json(this->_settings, fileName, std::string{}); - if (ec != glz::error_code::none) throw this->_logger->error("Failed to save settings '{}'", fileName); + if (ec != glz::error_code::none) CRITICAL_RAWRBOX("Failed to save settings '{}'", fileName); } [[nodiscard]] virtual std::filesystem::path getFileName() const { - throw this->_logger->error("Implement getFileName"); + throw std::runtime_error("Implement getFileName"); } [[nodiscard]] virtual T& getSettings() { diff --git a/rawrbox.utils/src/i18n.cpp b/rawrbox.utils/src/i18n.cpp index 868d18ac..10c5da1e 100644 --- a/rawrbox.utils/src/i18n.cpp +++ b/rawrbox.utils/src/i18n.cpp @@ -50,7 +50,7 @@ namespace rawrbox { try { rawrbox::Translation tr = {}; - if (glz::read_json(tr, langRawStr) != glz::error_code::none) throw _logger->error("Invalid JSON file"); + if (glz::read_json(tr, langRawStr) != glz::error_code::none) CRITICAL_RAWRBOX("Invalid JSON file"); addToLanguagePack(id, fileCleanName, tr); fmt::print("- '{}' language\n", fileCleanName); diff --git a/rawrbox.utils/src/logger.cpp b/rawrbox.utils/src/logger.cpp index 7da4731e..a682949f 100644 --- a/rawrbox.utils/src/logger.cpp +++ b/rawrbox.utils/src/logger.cpp @@ -1,9 +1,31 @@ #include namespace rawrbox { - // NOLINTBEGIN(*) - Logger::Logger(const std::string& title) : _title(title) {} - // NOLINTEND(*) +#ifdef _DEBUG + spdlog::level::level_enum Logger::LEVEL = spdlog::level::trace; // Default +#else + spdlog::level::level_enum Logger::LEVEL = spdlog::level::warn; // Default +#endif - void Logger::setAutoNewLine(bool set) { this->_autoNewLine = set; } + bool Logger::ENABLE_FILE_LOGGING = false; + std::shared_ptr Logger::LOGGER = nullptr; + + Logger::Logger(const std::string& title) : _title(title) { + if (LOGGER != nullptr) return; + + auto _spdConsole = std::make_shared(); + + if (ENABLE_FILE_LOGGING) { + auto _spdLogFile = std::make_shared("logs.log", true); + LOGGER = std::make_shared("CONSOLE", spdlog::sinks_init_list{_spdConsole, _spdLogFile}); + } else { + LOGGER = std::make_shared("CONSOLE", spdlog::sinks_init_list{_spdConsole}); + } + + LOGGER->set_pattern("[%^%l%$%v"); + LOGGER->set_level(Logger::LEVEL); + + spdlog::set_default_logger(LOGGER); + spdlog::set_error_handler([](const std::string& msg) { fmt::print("*** LOG ERROR: {} ***\n", msg); }); + } } // namespace rawrbox diff --git a/rawrbox.utils/src/threading.cpp b/rawrbox.utils/src/threading.cpp index a6ee2250..076ee670 100644 --- a/rawrbox.utils/src/threading.cpp +++ b/rawrbox.utils/src/threading.cpp @@ -12,7 +12,7 @@ namespace rawrbox { // ------------- void ASYNC::init(uint32_t threads) { - if (_pool != nullptr) throw _logger->error("ASYNC init already called!"); + if (_pool != nullptr) CRITICAL_RAWRBOX("ASYNC init already called!"); _pool = std::make_unique(threads); } @@ -24,16 +24,12 @@ namespace rawrbox { } void ASYNC::run(const std::function& job) { - if (_pool == nullptr) throw _logger->error("ASYNC not initialized!"); + if (_pool == nullptr) CRITICAL_RAWRBOX("ASYNC not initialized!"); -#ifdef RAWRBOX_TRACE_EXCEPTIONS try { _pool->detach_task(job); - } catch (const cpptrace::exception_with_message& e) { - throw _logger->error("Fatal error\n └── {}", e.message()); + } catch (const std::exception& e) { + CRITICAL_RAWRBOX("Fatal error\n └── {}", e.what()); } -#else - _pool->detach_task(job); -#endif } } // namespace rawrbox diff --git a/rawrbox.webm/src/decoder.cpp b/rawrbox.webm/src/decoder.cpp index 5c985f6c..1076ef5e 100644 --- a/rawrbox.webm/src/decoder.cpp +++ b/rawrbox.webm/src/decoder.cpp @@ -35,7 +35,7 @@ namespace rawrbox { codecIface = vpx_codec_vp9_dx(); break; default: - throw _logger->error("Invalid vpx codec"); + CRITICAL_RAWRBOX("Invalid vpx codec"); } _codec = codec; @@ -43,7 +43,7 @@ namespace rawrbox { if (vpx_codec_dec_init(_ctx.get(), codecIface, &codecCfg, VPX_CODEC_USE_FRAME_THREADING)) { _ctx.reset(); - throw _logger->error("Failed to initialize vpx codec"); + CRITICAL_RAWRBOX("Failed to initialize vpx codec"); } } @@ -54,20 +54,20 @@ namespace rawrbox { bool WEBMDecoder::decode(const rawrbox::WEBMFrame& frame, rawrbox::WEBMImage& image) { if (_ctx == nullptr) - throw _logger->error("Codec not initialized, did you call 'init' ?"); + CRITICAL_RAWRBOX("Codec not initialized, did you call 'init' ?"); if (frame.codec != _codec) { const auto* badname = magic_enum::enum_name(static_cast(frame.codec)).data(); const auto* name = magic_enum::enum_name(static_cast(_codec)).data(); - throw _logger->error("Codec '{}' not set as config! '{}' was loaded instead", badname, name); + CRITICAL_RAWRBOX("Codec '{}' not set as config! '{}' was loaded instead", badname, name); } _iter = nullptr; if (vpx_codec_decode(_ctx.get(), frame.buffer.data(), static_cast(frame.buffer.size()), nullptr, 0) != 0) return false; if (vpx_image_t* img = vpx_codec_get_frame(_ctx.get(), &_iter)) { - if ((img->fmt & VPX_IMG_FMT_PLANAR) == 0) throw _logger->error("Failed to get image! Image not in FMT_PLANAR!"); + if ((img->fmt & VPX_IMG_FMT_PLANAR) == 0) CRITICAL_RAWRBOX("Failed to get image! Image not in FMT_PLANAR!"); rawrbox::YUVLuminanceScale scale = rawrbox::YUVLuminanceScale::UNKNOWN; int channels = 4; @@ -83,7 +83,7 @@ namespace rawrbox { scale = rawrbox::YUVLuminanceScale::FULL; break; default: - throw _logger->error("Unknown luminance format"); + CRITICAL_RAWRBOX("Unknown luminance format"); } switch (img->fmt) { @@ -95,7 +95,7 @@ namespace rawrbox { } break; default: - throw _logger->error("Format not supported, video not in I420 format"); + CRITICAL_RAWRBOX("Format not supported, video not in I420 format"); } } diff --git a/rawrbox.webm/src/loader.cpp b/rawrbox.webm/src/loader.cpp index 3bb578bd..e3d32dff 100644 --- a/rawrbox.webm/src/loader.cpp +++ b/rawrbox.webm/src/loader.cpp @@ -10,41 +10,41 @@ namespace rawrbox { void WEBM::preloadVideo() { std::lock_guard lock(RENDER_THREAD_LOCK); - this->_logger->info("Pre-loading video '{}'", fmt::styled(this->_filePath.generic_string(), fmt::fg(fmt::color::light_coral))); + this->_logger->debug("Pre-loading video '{}'", fmt::styled(this->_filePath.generic_string(), fmt::fg(fmt::color::light_coral))); while (this->advance()) { auto frame = this->getFrame(); - if (!frame.valid()) throw this->_logger->error("Failed to find frame"); + if (!frame.valid()) CRITICAL_RAWRBOX("Failed to find frame"); rawrbox::WEBMImage img; - if (!rawrbox::WEBMDecoder::decode(frame, img) || !img.valid()) throw this->_logger->error("Failed to decode frame"); + if (!rawrbox::WEBMDecoder::decode(frame, img) || !img.valid()) CRITICAL_RAWRBOX("Failed to decode frame"); this->_preloadedFrames[frame.pos] = img; } - this->_logger->info("Done pre-loading '{}'", fmt::styled(this->_filePath.generic_string(), fmt::fg(fmt::color::light_coral))); + this->_logger->debug("Done pre-loading '{}'", fmt::styled(this->_filePath.generic_string(), fmt::fg(fmt::color::light_coral))); this->reset(); } void WEBM::internalLoad() { - if (this->_reader == nullptr) throw this->_logger->error("Reader not initialized!"); + if (this->_reader == nullptr) CRITICAL_RAWRBOX("Reader not initialized!"); // Get the file info long long pos = 0; if (mkvparser::EBMLHeader().Parse(this->_reader.get(), pos) != 0) { - throw this->_logger->error("File parsing failed"); + CRITICAL_RAWRBOX("File parsing failed"); } // Create a segment instance mkvparser::Segment* pSegment = nullptr; if (mkvparser::Segment::CreateInstance(this->_reader.get(), pos, pSegment) != 0) { - throw this->_logger->error("Failed to create file segment"); + CRITICAL_RAWRBOX("Failed to create file segment"); } this->_segment = std::unique_ptr(pSegment); if (this->_segment == nullptr || this->_segment->Load() < 0) { - throw this->_logger->error("Failed to load segment"); + CRITICAL_RAWRBOX("Failed to load segment"); } const mkvparser::Tracks* tracks = this->_segment->GetTracks(); @@ -52,10 +52,10 @@ namespace rawrbox { const mkvparser::SegmentInfo* const segmentInfo = this->_segment->GetInfo(); if (segmentInfo == nullptr) { - throw this->_logger->error("Failed to load segment info"); + CRITICAL_RAWRBOX("Failed to load segment info"); } - if (this->_segment->GetCount() <= 0) throw this->_logger->error("Track {} does not contain any cluster data!", this->_trackId); + if (this->_segment->GetCount() <= 0) CRITICAL_RAWRBOX("Track {} does not contain any cluster data!", this->_trackId); this->_info.duration = segmentInfo->GetDuration(); this->_info.timeScale = segmentInfo->GetTimeCodeScale(); @@ -79,7 +79,7 @@ namespace rawrbox { if (this->_info.vCodec != rawrbox::VIDEO_CODEC::UNKNOWN) { this->_video = dynamic_cast(track); } else { - throw this->_logger->error("Unknown video codec '{}'", codecId); + CRITICAL_RAWRBOX("Unknown video codec '{}'", codecId); } break; @@ -88,7 +88,7 @@ namespace rawrbox { } // ---- - if (this->_video == nullptr) throw this->_logger->error("Failed to find track {}", this->_trackId); + if (this->_video == nullptr) CRITICAL_RAWRBOX("Failed to find track {}", this->_trackId); this->_videoTrack = this->_video->GetNumber(); // Append extra info ---- @@ -123,13 +123,13 @@ namespace rawrbox { this->_reader = std::make_unique(); if (this->_reader->Open(filePath.string().c_str()) != 0) - throw this->_logger->error("Filename is invalid or error while opening"); + CRITICAL_RAWRBOX("Filename is invalid or error while opening"); this->internalLoad(); } bool WEBM::advance() { - if (this->_video == nullptr) throw this->_logger->error("Video not loaded! Did you call load()?"); + if (this->_video == nullptr) CRITICAL_RAWRBOX("Video not loaded! Did you call load()?"); if (this->_paused) return false; if (this->eos()) { @@ -211,7 +211,7 @@ namespace rawrbox { } void WEBM::reset() { - if (this->_video == nullptr || this->_segment == nullptr) throw this->_logger->error("Video not loaded! Did you call 'load' ?"); + if (this->_video == nullptr || this->_segment == nullptr) CRITICAL_RAWRBOX("Video not loaded! Did you call 'load' ?"); this->_cluster = this->_segment->GetFirst(); @@ -224,7 +224,7 @@ namespace rawrbox { } void WEBM::seek(uint64_t timeMS) { - if (this->_video == nullptr || this->_segment == nullptr) throw this->_logger->error("Video not loaded! Did you call 'load' ?"); + if (this->_video == nullptr || this->_segment == nullptr) CRITICAL_RAWRBOX("Video not loaded! Did you call 'load' ?"); this->_cluster = this->_segment->FindCluster(timeMS * 1000000); diff --git a/rawrbox.webm/src/textures/webm.cpp b/rawrbox.webm/src/textures/webm.cpp index 41b3e2d8..6c2f0f7b 100644 --- a/rawrbox.webm/src/textures/webm.cpp +++ b/rawrbox.webm/src/textures/webm.cpp @@ -16,7 +16,7 @@ namespace rawrbox { this->_name = "RawrBox::Texture::WEBM"; try { - if (!std::filesystem::exists(this->_filePath)) throw this->_logger->error("Video not found!"); + if (!std::filesystem::exists(this->_filePath)) CRITICAL_RAWRBOX("Video not found!"); this->_webm = std::make_unique(); this->_webm->load(this->_filePath, this->_flags); @@ -27,12 +27,7 @@ namespace rawrbox { this->_data.channels = 4; // Force 4 channels this->_data.size = this->_webm->getSize(); this->_data.createFrame(); - -#ifdef RAWRBOX_TRACE_EXCEPTIONS - } catch (const cpptrace::exception_with_message& e) { -#else } catch (const std::exception& e) { -#endif if (useFallback) { _logger->warn("Failed to load '{}' ──> \n\t{}\n\t\t └── Loading fallback texture!", this->_filePath.generic_string(), e.what()); this->loadFallback(); @@ -66,7 +61,7 @@ namespace rawrbox { void TextureWEBM::update() { if (this->_failedToLoad || this->_handle == nullptr) return; // Not bound if (this->_pause || this->_cooldown >= rawrbox::TimeUtils::curtime()) return; - if (this->_webm == nullptr) throw this->_logger->error("WEBM loader not initialized!"); + if (this->_webm == nullptr) CRITICAL_RAWRBOX("WEBM loader not initialized!"); rawrbox::WEBMImage img; if (!this->_webm->getNextFrame(img)) return; // Reached end @@ -111,11 +106,11 @@ namespace rawrbox { } float TextureWEBM::getSpeed() const { - throw this->_logger->error("Not supported"); + CRITICAL_RAWRBOX("Not supported"); } void TextureWEBM::setSpeed(float /*speed*/) { - throw this->_logger->error("Not supported"); + CRITICAL_RAWRBOX("Not supported"); } // ---- From 537ea1a004b42b33b45791994f4e1a25536d3e88 Mon Sep 17 00:00:00 2001 From: failcake <4944278+edunad@users.noreply.github.com> Date: Wed, 9 Oct 2024 11:20:28 +0200 Subject: [PATCH 2/4] Remove log test line, woops --- rawrbox.render/include/rawrbox/render/models/base.hpp | 1 - 1 file changed, 1 deletion(-) diff --git a/rawrbox.render/include/rawrbox/render/models/base.hpp b/rawrbox.render/include/rawrbox/render/models/base.hpp index bf4aa7c2..d77dd1d6 100644 --- a/rawrbox.render/include/rawrbox/render/models/base.hpp +++ b/rawrbox.render/include/rawrbox/render/models/base.hpp @@ -152,7 +152,6 @@ namespace rawrbox { this->createIndexBuffer(); this->_logger->debug("Resizing index buffer ({} -> {})", fmt::styled(indcSize, fmt::fg(fmt::color::cyan)), fmt::styled(this->_mesh->indices.capacity(), fmt::fg(fmt::color::cyan))); - CRITICAL_RAWRBOX("Resizing vertex buffer ({} -> {})", vertSize, this->_mesh->vertices.capacity()); } if (resizeVertex && resizeIndex) { From 8d2e0df74854239551baf8c476897db5850a391a Mon Sep 17 00:00:00 2001 From: failcake <4944278+edunad@users.noreply.github.com> Date: Wed, 9 Oct 2024 11:25:39 +0200 Subject: [PATCH 3/4] Replace RAWRBOX_ERROR with _logger->error --- rawrbox.render/src/decals/decal.cpp | 2 +- rawrbox.render/src/utils/pipeline.cpp | 2 +- rawrbox.scripting/src/manager.cpp | 4 ++-- rawrbox.utils/include/rawrbox/utils/logger.hpp | 11 ++++++++--- 4 files changed, 12 insertions(+), 7 deletions(-) diff --git a/rawrbox.render/src/decals/decal.cpp b/rawrbox.render/src/decals/decal.cpp index 60ab8ace..7c0a36a1 100644 --- a/rawrbox.render/src/decals/decal.cpp +++ b/rawrbox.render/src/decals/decal.cpp @@ -12,7 +12,7 @@ namespace rawrbox { void Decal::setTexture(const rawrbox::TextureBase& texture, uint32_t id) { if (!texture.isValid()) { - ERROR_RAWRBOX("Invalid texture, not uploaded?"); + this->_logger->error("Invalid texture, not uploaded?"); return; } diff --git a/rawrbox.render/src/utils/pipeline.cpp b/rawrbox.render/src/utils/pipeline.cpp index 76587a35..b934c7b4 100644 --- a/rawrbox.render/src/utils/pipeline.cpp +++ b/rawrbox.render/src/utils/pipeline.cpp @@ -84,7 +84,7 @@ namespace rawrbox { if (CacheDataFile->Write(pCacheData->GetConstDataPtr(), pCacheData->GetSize())) { _logger->debug("Saved pipeline cache to '{}'", pString); } else { - ERROR_RAWRBOX("Failed to save pipeline cache to '{}'", pString); + _logger->error("Failed to save pipeline cache to '{}'", pString); } } } diff --git a/rawrbox.scripting/src/manager.cpp b/rawrbox.scripting/src/manager.cpp index b4b80ab3..c8ed38f9 100644 --- a/rawrbox.scripting/src/manager.cpp +++ b/rawrbox.scripting/src/manager.cpp @@ -315,7 +315,7 @@ namespace rawrbox { try { rawrbox::LuaUtils::compileAndLoadFile(env, md->first, filePath); } catch (const std::exception& err) { - ERROR_RAWRBOX("{}", err.what()); + _logger->error("{}", err.what()); } // --------------- @@ -398,7 +398,7 @@ namespace rawrbox { _logger->info("Mod '{}' loaded", fmt::styled(id, fmt::fg(fmt::color::coral))); registerLoadedFile(mod->getID(), mod->getEntryFilePath()); // Register file for hot-reloading } catch (const std::runtime_error& err) { - ERROR_RAWRBOX("{}", err.what()); + _logger->error("{}", err.what()); return nullptr; } diff --git a/rawrbox.utils/include/rawrbox/utils/logger.hpp b/rawrbox.utils/include/rawrbox/utils/logger.hpp index 0bc3fa00..09b112dc 100644 --- a/rawrbox.utils/include/rawrbox/utils/logger.hpp +++ b/rawrbox.utils/include/rawrbox/utils/logger.hpp @@ -14,9 +14,6 @@ throw std::runtime_error(fmt::format(__VA_ARGS__)); \ } -#define ERROR_RAWRBOX(...) \ - spdlog::error("] {}\n └── {}:{}\n\t└── {}", fmt::format(__VA_ARGS__), __FILE__, __LINE__, fmt::styled(__FUNCTION__, fmt::fg(fmt::color::red))); - namespace rawrbox { class Logger { protected: @@ -61,6 +58,14 @@ namespace rawrbox { auto str = fmt::format(fmt, std::forward(args)...); LOGGER->debug(" ▓ {}] {}", this->_title, str); } + + template + void error(fmt::format_string fmt, T&&... args) { + if (LOGGER == nullptr) return; + + auto str = fmt::format(fmt, std::forward(args)...); + LOGGER->error(" ▓ {}] {}", this->_title, str); + } // ---------- }; } // namespace rawrbox From cbf7d01e0d724295965e9429443abe957fbe58e2 Mon Sep 17 00:00:00 2001 From: failcake <4944278+edunad@users.noreply.github.com> Date: Wed, 9 Oct 2024 11:30:22 +0200 Subject: [PATCH 4/4] Enable file logging by default --- rawrbox.utils/src/logger.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rawrbox.utils/src/logger.cpp b/rawrbox.utils/src/logger.cpp index a682949f..70d00000 100644 --- a/rawrbox.utils/src/logger.cpp +++ b/rawrbox.utils/src/logger.cpp @@ -7,7 +7,7 @@ namespace rawrbox { spdlog::level::level_enum Logger::LEVEL = spdlog::level::warn; // Default #endif - bool Logger::ENABLE_FILE_LOGGING = false; + bool Logger::ENABLE_FILE_LOGGING = true; std::shared_ptr Logger::LOGGER = nullptr; Logger::Logger(const std::string& title) : _title(title) {