From 812407c3dfdea1dd81ef67ad93428e1c7306eeba Mon Sep 17 00:00:00 2001 From: "Zed A. Shaw" Date: Sat, 21 Jun 2025 10:51:45 -0400 Subject: [PATCH] Now the loot UI can work with any container and only uses an ECS id to work, not have its own contents. --- gui/fsm.cpp | 9 ++++++--- gui/fsm.hpp | 1 + gui/loot_ui.cpp | 18 +++++++++--------- gui/loot_ui.hpp | 8 ++++++-- systems.cpp | 45 +++++++++++++++++++++++++++++++++------------ systems.hpp | 23 +++++++++++++++-------- 6 files changed, 70 insertions(+), 34 deletions(-) diff --git a/gui/fsm.cpp b/gui/fsm.cpp index 2ea7494..aa77969 100644 --- a/gui/fsm.cpp +++ b/gui/fsm.cpp @@ -27,7 +27,8 @@ namespace gui { $mini_map($level), $loot_ui($level), $font{FONT_FILE_NAME}, - $dnd_loot($status_ui, $loot_ui, $window, $router) + $dnd_loot($status_ui, $loot_ui, $window, $router), + $temp_loot($level.world->entity()) { $window.setPosition({0,0}); } @@ -66,6 +67,8 @@ namespace gui { $map_ui.log(L"Welcome to the game!"); $mini_map.init($main_ui.$overlay_ui.$gui); + $level.world->set($temp_loot, {}); + run_systems(); state(State::IDLE); @@ -458,8 +461,8 @@ namespace gui { case eGUI::LOOT_ITEM: { dbc::check(world.has(entity), "INVALID LOOT_ITEM, that entity has no InventoryItem"); - dbc::log("@@@@ SENDING LOOT_ITEM"); - $loot_ui.contents.add("item_0", entity); + System::place_in_container(*$level.world, $temp_loot, "item_0", entity); + $loot_ui.set_target($temp_loot); $loot_ui.update(); event(Event::LOOT_ITEM); } break; diff --git a/gui/fsm.hpp b/gui/fsm.hpp index 6000820..d43c1a7 100644 --- a/gui/fsm.hpp +++ b/gui/fsm.hpp @@ -49,6 +49,7 @@ namespace gui { sf::Font $font; gui::routing::Router $router; DNDLoot $dnd_loot; + DinkyECS::Entity $temp_loot; FSM(); diff --git a/gui/loot_ui.cpp b/gui/loot_ui.cpp index e691516..46830df 100644 --- a/gui/loot_ui.cpp +++ b/gui/loot_ui.cpp @@ -1,6 +1,7 @@ #include "gui/loot_ui.hpp" #include "constants.hpp" #include +#include "systems.hpp" namespace gui { using namespace guecs; @@ -57,6 +58,10 @@ namespace gui { } void LootUI::update() { + if(!$level.world->has($target)) return; + + auto& contents = $level.world->get($target); + for(size_t i = 0; i < INV_SLOTS; i++) { auto id = $gui.entity("item_", int(i)); auto& slot_name = $slot_to_name.at(id); @@ -88,20 +93,15 @@ namespace gui { void LootUI::remove_slot(DinkyECS::Entity slot_id) { auto& name = $slot_to_name.at(slot_id); - contents.remove(name); + System::remove_from_container(*$level.world, $target, name); update(); } bool LootUI::place_slot(guecs::Entity id, DinkyECS::Entity world_entity) { auto& name = $slot_to_name.at(id); - - if(!contents.has(name)) { - contents.add(name, world_entity); - update(); - return true; - } else { - return false; - } + bool worked = System::place_in_container(*$level.world, $target, name, world_entity); + if(worked) update(); + return worked; } void LootUI::render(sf::RenderWindow& window) { diff --git a/gui/loot_ui.hpp b/gui/loot_ui.hpp index 87652e5..64ab48b 100644 --- a/gui/loot_ui.hpp +++ b/gui/loot_ui.hpp @@ -14,10 +14,14 @@ namespace gui { guecs::UI $gui; GameLevel $level; std::unordered_map $slot_to_name; - // NOTE: this should then become just an ECS id for a container - inventory::Model contents; + DinkyECS::Entity $target; LootUI(GameLevel level); + + void set_target(DinkyECS::Entity entity) { + $target = entity; + } + void init(); void update(); void render(sf::RenderWindow& window); diff --git a/systems.cpp b/systems.cpp index 6d862a4..09067cb 100644 --- a/systems.cpp +++ b/systems.cpp @@ -20,6 +20,7 @@ using std::string; using namespace fmt; using namespace components; +using namespace DinkyECS; using lighting::LightSource; void System::lighting(GameLevel &level) { @@ -100,7 +101,7 @@ void System::enemy_pathing(GameLevel &level) { map.clear_target(player_position.location); } -void System::init_positions(DinkyECS::World &world, SpatialMap &collider) { +void System::init_positions(World &world, SpatialMap &collider) { world.query([&](auto ent, auto &pos) { if(world.has(ent)) { const auto& combat = world.get(ent); @@ -113,7 +114,7 @@ void System::init_positions(DinkyECS::World &world, SpatialMap &collider) { }); } -inline void move_entity(SpatialMap &collider, Map &game_map, Position &position, Motion &motion, DinkyECS::Entity ent) { +inline void move_entity(SpatialMap &collider, Map &game_map, Position &position, Motion &motion, Entity ent) { Point move_to = { position.location.x + motion.dx, position.location.y + motion.dy @@ -140,7 +141,7 @@ void System::motion(GameLevel &level) { }); } -void System::distribute_loot(DinkyECS::World &world, DinkyECS::Entity& ent, nlohmann::json& entity_data) { +void System::distribute_loot(World &world, Entity& ent, nlohmann::json& entity_data) { dbc::log("!!!!!!!!!!!!! THIS is where you update the dead body contents"); int inventory_count = entity_data["inventory_count"]; world.set(ent, {inventory_count, entity_data}); @@ -168,7 +169,7 @@ void System::death(GameLevel &level) { auto &world = *level.world; auto player = world.get_the(); auto& config = world.get_the(); - std::vector dead_things; + std::vector dead_things; world.query([&](auto ent, auto &combat) { // bring out yer dead @@ -217,7 +218,7 @@ void System::death(GameLevel &level) { } } -inline void animate_entity(DinkyECS::World &world, DinkyECS::Entity entity) { +inline void animate_entity(World &world, Entity entity) { if(world.has(entity)) { auto& animation = world.get(entity); animation.play(); @@ -315,7 +316,7 @@ void System::collision(GameLevel &level) { } } -void System::pickup(GameLevel &level, DinkyECS::Entity entity) { +void System::pickup(GameLevel &level, Entity entity) { auto &world = *level.world; auto player = world.get_the(); @@ -346,7 +347,7 @@ void System::pickup(GameLevel &level, DinkyECS::Entity entity) { } -void System::device(DinkyECS::World &world, DinkyECS::Entity actor, DinkyECS::Entity item) { +void System::device(World &world, Entity actor, Entity item) { auto& device = world.get(item); dbc::log(fmt::format("entity {} INTERACTED WITH DEVICE {}", actor, item)); @@ -367,7 +368,7 @@ void System::device(DinkyECS::World &world, DinkyECS::Entity actor, DinkyECS::En } } -void System::plan_motion(DinkyECS::World& world, Point move_to) { +void System::plan_motion(World& world, Point move_to) { auto& player = world.get_the(); auto& player_position = world.get(player.entity); auto& motion = world.get(player.entity); @@ -380,7 +381,7 @@ void System::plan_motion(DinkyECS::World& world, Point move_to) { * just avoid GameMap unlike the others. */ std::wstring System::draw_map(GameLevel level, size_t view_x, size_t view_y, int compass_dir) { - DinkyECS::World &world = *level.world; + World &world = *level.world; Map &map = *level.map; auto player_pos = world.get(level.player).location; @@ -446,7 +447,7 @@ void System::player_status(GameLevel &level) { } } -std::shared_ptr System::sprite_effect(GameLevel &level, DinkyECS::Entity entity) { +std::shared_ptr System::sprite_effect(GameLevel &level, Entity entity) { if(level.world->has(entity)) { auto& se = level.world->get(entity); @@ -462,7 +463,7 @@ std::shared_ptr System::sprite_effect(GameLevel &level, DinkyECS::En } } -DinkyECS::Entity System::spawn_item(DinkyECS::World& world, const std::string& name) { +Entity System::spawn_item(World& world, const std::string& name) { Config config("assets/items.json"); auto& item_config = config[name]; auto item_id = world.entity(); @@ -472,7 +473,7 @@ DinkyECS::Entity System::spawn_item(DinkyECS::World& world, const std::string& n return item_id; } -bool System::drop_item(GameLevel& level, DinkyECS::Entity item) { +bool System::drop_item(GameLevel& level, Entity item) { auto& world = *level.world; auto& map = *level.map; auto& collision = *level.collision; @@ -497,3 +498,23 @@ bool System::drop_item(GameLevel& level, DinkyECS::Entity item) { return false; } + +bool System::place_in_container(World& world, Entity cont_id, const std::string& name, Entity world_entity) { + auto& container = world.get(cont_id); + + if(container.has(world_entity)) { + // NOTE: I think this would be a move?! + return false; + } else if(container.has(name)) { + // this is an already occupied slot + return false; + } else { + container.add(name, world_entity); + return true; + } +} + +void System::remove_from_container(World& world, Entity cont_id, const std::string& name) { + auto& container = world.get(cont_id); + container.remove(name); +} diff --git a/systems.hpp b/systems.hpp index 6f85ff4..0642dbf 100644 --- a/systems.hpp +++ b/systems.hpp @@ -5,6 +5,8 @@ namespace System { using namespace components; + using namespace DinkyECS; + using std::string; void lighting(GameLevel &level); void motion(GameLevel &level); @@ -14,19 +16,24 @@ namespace System { void enemy_pathing(GameLevel &level); void enemy_ai_initialize(GameLevel &level); - void init_positions(DinkyECS::World &world, SpatialMap &collider); - void device(DinkyECS::World &world, DinkyECS::Entity actor, DinkyECS::Entity item); - void plan_motion(DinkyECS::World& world, Point move_to); + void init_positions(World &world, SpatialMap &collider); + void device(World &world, Entity actor, Entity item); + void plan_motion(World& world, Point move_to); std::wstring draw_map(GameLevel level, size_t view_x, size_t view_y, int compass_dir); - DinkyECS::Entity spawn_item(DinkyECS::World& world, const std::string& name); - bool drop_item(GameLevel& level, DinkyECS::Entity item); + Entity spawn_item(World& world, const string& name); + bool drop_item(GameLevel& level, Entity item); void enemy_ai(GameLevel &level); void combat(GameLevel &level, int attack_id); - std::shared_ptr sprite_effect(GameLevel &level, DinkyECS::Entity entity); + std::shared_ptr sprite_effect(GameLevel &level, Entity entity); void player_status(GameLevel &level); - void distribute_loot(DinkyECS::World &world, DinkyECS::Entity& ent, nlohmann::json& entity_data); + void distribute_loot(World &world, Entity& ent, nlohmann::json& entity_data); + + void pickup(GameLevel &level, Entity entity); + + bool place_in_container(World& world, Entity cont_id, const string& name, Entity world_entity); + + void remove_from_container(World& world, Entity cont_id, const string& name); - void pickup(GameLevel &level, DinkyECS::Entity entity); }