diff options
Diffstat (limited to 'loader/ground-atlas.cpp')
-rw-r--r-- | loader/ground-atlas.cpp | 146 |
1 files changed, 23 insertions, 123 deletions
diff --git a/loader/ground-atlas.cpp b/loader/ground-atlas.cpp index ba4eaeb0..02186cec 100644 --- a/loader/ground-atlas.cpp +++ b/loader/ground-atlas.cpp @@ -1,30 +1,36 @@ #include "impl.hpp" +#include "atlas-loader-storage.hpp" +#include "atlas-loader.inl" +#include "ground-traits.hpp" +#include "ground-cell.hpp" #include "src/tile-constants.hpp" #include "src/ground-atlas.hpp" #include "compat/exception.hpp" #include "serialize/json-helper.hpp" -#include "serialize/corrade-string.hpp" #include "serialize/ground-atlas.hpp" -#include "src/tile-defs.hpp" #include <Corrade/Containers/ArrayViewStl.h> #include <Corrade/Utility/Path.h> #include <Magnum/Trade/ImageData.h> #include <Magnum/ImageView.h> +namespace floormat::loader_detail { + +template class atlas_loader<ground_atlas>; + +} // namespace floormat::loader_detail + namespace floormat { -using loader_detail::loader_impl; + +using loader_detail::atlas_loader_traits; +using ALT = atlas_loader_traits<ground_atlas>; std::shared_ptr<ground_atlas> loader_::get_ground_atlas(StringView name, Vector2ub size, pass_mode pass) noexcept(false) { fm_assert(name != loader.INVALID); - - char buf[FILENAME_MAX]; - auto filename = make_atlas_path(buf, loader.GROUND_TILESET_PATH, name); - auto tex = texture(""_s, filename); - + auto tex = texture(loader.GROUND_TILESET_PATH, name); auto info = ground_def{name, size, pass}; - auto atlas = std::make_shared<class ground_atlas>(info, filename, tex); + auto atlas = std::make_shared<class ground_atlas>(info, tex); return atlas; } @@ -32,128 +38,22 @@ loader_::get_ground_atlas(StringView name, Vector2ub size, pass_mode pass) noexc namespace floormat::loader_detail { -// todo copypasta from wall-atlas.cpp -std::shared_ptr<class ground_atlas> loader_impl::ground_atlas(StringView name, loader_policy policy) noexcept(false) +atlas_loader<class ground_atlas>* loader_impl::make_ground_atlas_loader() { - (void)ground_atlas_list(); - - switch (policy) - { - case loader_policy::error: - fm_assert(name != INVALID); - break; - case loader_policy::ignore: - case loader_policy::warn: - break; - default: - fm_abort("invalid loader_policy"); - } - - fm_soft_assert(check_atlas_name(name)); - auto it = ground_atlas_map.find(name); - - if (it != ground_atlas_map.end()) [[likely]] - { - if (it->second == (ground_info*)-1) [[unlikely]] - { - switch (policy) - { - case loader_policy::error: - goto error; - case loader_policy::warn: - case loader_policy::ignore: - goto missing_ok; - } - fm_assert(false); - std::unreachable(); - } - else if (!it->second->atlas) - return it->second->atlas = get_ground_atlas(name, it->second->size, it->second->pass); - else - return it->second->atlas; - } - else - { - switch (policy) - { - case loader_policy::error: - goto error; - case loader_policy::warn: - goto missing_warn; - case loader_policy::ignore: - goto missing_ok; - } - fm_assert(false); - std::unreachable(); - } - -missing_warn: - { - missing_ground_atlases.push_back(String { AllocatedInit, name }); - auto string_view = StringView{missing_ground_atlases.back()}; - ground_atlas_map[string_view] = (ground_info*)-1; - } - - if (name != loader.INVALID) - DBG_nospace << "ground_atlas '" << name << "' doesn't exist"; - -missing_ok: - return make_invalid_ground_atlas().atlas; - -error: - fm_throw("no such ground atlas '{}'"_cf, name); + return new atlas_loader<class ground_atlas>; } -ArrayView<const ground_info> loader_impl::ground_atlas_list() noexcept(false) -{ - if (ground_atlas_map.empty()) [[unlikely]] - { - get_ground_atlas_list(); - fm_assert(!ground_atlas_map.empty()); - } - return ground_atlas_array; -} +auto loader_impl::ground_atlas_list() noexcept(false) -> ArrayView<const ground_cell> { return _ground_loader->ensure_atlas_list(); } -void loader_impl::get_ground_atlas_list() +const ground_cell& loader_impl::make_invalid_ground_atlas() { - fm_assert(ground_atlas_map.empty()); - - auto defs = json_helper::from_json<std::vector<ground_def>>(Path::join(loader_::GROUND_TILESET_PATH, "ground.json"_s)); - std::vector<ground_info> infos; - infos.reserve(defs.size()); - - for (auto& x : defs) - infos.push_back(ground_info{std::move(x.name), {}, x.size, x.pass}); - - ground_atlas_array = infos; - ground_atlas_array.shrink_to_fit(); - ground_atlas_map.clear(); - ground_atlas_map.reserve(ground_atlas_array.size()*2); - - for (auto& x : ground_atlas_array) - { - fm_soft_assert(x.name != loader.INVALID); - fm_soft_assert(check_atlas_name(x.name)); - StringView name = x.name; - ground_atlas_map[name] = &x; - fm_debug_assert(name.data() == ground_atlas_map[name]->name.data()); - } - - fm_assert(!ground_atlas_map.empty()); + return _ground_loader->get_invalid_atlas(); } -const ground_info& loader_impl::make_invalid_ground_atlas() +const std::shared_ptr<class ground_atlas>& +loader_impl::ground_atlas(StringView filename, loader_policy policy) noexcept(false) { - if (invalid_ground_atlas) [[likely]] - return *invalid_ground_atlas; - - auto atlas = std::make_shared<class ground_atlas>( - ground_def{loader.INVALID, Vector2ub{1,1}, pass_mode::pass}, - ""_s, make_error_texture(Vector2ui(iTILE_SIZE2))); - invalid_ground_atlas = Pointer<ground_info>{ - InPlaceInit, atlas->name(), - atlas, atlas->num_tiles2(), atlas->pass_mode()}; - return *invalid_ground_atlas; + return _ground_loader->get_atlas(filename, policy); } } // namespace floormat::loader_detail |