diff --git a/Makefile b/Makefile index c03917b..27ba792 100644 --- a/Makefile +++ b/Makefile @@ -37,7 +37,7 @@ tracy_build: meson compile -j 10 -C builddir test: build - ./builddir/runtests -d yes "[systems-engine]" + ./builddir/runtests -d yes run: build test ifeq '$(OS)' 'Windows_NT' @@ -48,7 +48,7 @@ else endif debug: build - gdb --nx -x .gdbinit --ex run --args builddir/runtests "[systems-engine]" + gdb --nx -x .gdbinit --ex run --args builddir/runtests debug_run: build gdb --nx -x .gdbinit --batch --ex run --ex bt --ex q --args builddir/zedcaster @@ -60,7 +60,7 @@ clean: meson compile --clean -C builddir debug_test: build - gdb --nx -x .gdbinit --ex run --ex bt --ex q --args builddir/runtests "[systems-engine]" + gdb --nx -x .gdbinit --ex run --ex bt --ex q --args builddir/runtests win_installer: powershell 'start "C:\Program Files (x86)\solicus\InstallForge\bin\ifbuilderenvx86.exe" scripts\win_installer.ifp' diff --git a/assets/animation.json b/assets/animation.json index 9098a9f..3ce25a6 100644 --- a/assets/animation.json +++ b/assets/animation.json @@ -65,7 +65,7 @@ "close": [] } }, - "rat_with_sword": { + "spider_bot": { "sheet": { "frames": 1, "frame_width": 256, @@ -98,14 +98,14 @@ "close": [] } }, - "female_hand": { + "hands_sword_attack": { "sheet": { "frames": 3, - "frame_width": 900, - "frame_height": 600 + "frame_width": 512, + "frame_height": 341 }, "sequences": { - "idle": {"frames": [0, 1, 2], "durations": [10, 10, 20] } + "idle": {"frames": [0, 1, 2], "durations": [25, 5, 20] } }, "transforms": { "basic": { @@ -115,7 +115,7 @@ "max_y": 1.0, "flipped": false, "scaled": false, - "toggled": true, + "toggled": false, "looped": false, "relative": false, "easing": "none", diff --git a/assets/config.json b/assets/config.json index 00ecef8..f521e8b 100644 --- a/assets/config.json +++ b/assets/config.json @@ -1,62 +1,29 @@ { "sounds": { - "Sword_Hit_1": "assets/sounds/Creature_Sounds-Sword_Hit_1.ogg", - "Evil_Eye_Sound_1": "assets/sounds/Creature_Sounds-Evil_Eye_Sound_1.ogg", - "Evil_Eye_Sound_2": "assets/sounds/Creature_Sounds-Evil_Eye_Sound_2.ogg", - "Giant_Voice_1": "assets/sounds/Creature_Sounds-Giant_Voice_1.ogg", - "Medium_Rat": "assets/sounds/Creature_Sounds-Medium_Rat.ogg", - "Ranger_1": "assets/sounds/Creature_Sounds-Ranger_1.ogg", - "Small_Rat": "assets/sounds/Creature_Sounds-Small_Rat.ogg", - "Spider_1": "assets/sounds/Creature_Sounds-Spider_1.ogg", - "Spider_2": "assets/sounds/Creature_Sounds-Spider_2.ogg", - "Sword_Hit_1": "assets/sounds/Creature_Sounds-Sword_Hit_1.ogg", - "Sword_Hit_2": "assets/sounds/Creature_Sounds-Sword_Hit_2.ogg", - "walk": "assets/sounds/Creature_Sounds-Walk.ogg", - "Creature_Death_1": "assets/sounds/Creature_Sounds-Creature_Death_1.ogg", - "Humanoid_Death_1": "assets/sounds/Creature_Sounds-Humanoid_Death_1.ogg", - "Marmot_Scream_1": "assets/sounds/Creature_Sounds-Marmot_Scream_1.ogg", "blank": "assets/sounds/blank.ogg", "pickup": "assets/sounds/pickup.ogg", - "ambient_1": "assets/sounds/ambient_1.ogg", "ui_click": "assets/sounds/ui_click.ogg", "ui_hover": "assets/sounds/ui_hover.ogg", - "punch_cartoony": "assets/sounds/punch_cartoony.ogg", - "electric_shock_01": "assets/sounds/electric_shock_01.ogg", - "fireball_01": "assets/sounds/fireball_01.ogg", - "hp_status_80": "assets/sounds/hp_status_80.ogg", - "hp_status_60": "assets/sounds/hp_status_60.ogg", - "hp_status_30": "assets/sounds/hp_status_30.ogg", - "hp_status_10": "assets/sounds/hp_status_10.ogg", - "hp_status_00": "assets/sounds/hp_status_00.ogg" + "walk": "assets/sounds/walk.ogg" }, "sprites": { - "rat_with_sword": - {"path": "assets/sprites/rat_with_sword.png", + "spider_bot": + {"path": "assets/sprites/spider_bot.png", "frame_width": 256, "frame_height": 256 }, - "torch_crappy": - {"path": "assets/items/torch_crappy.png", + "repair_kit": + {"path": "assets/items/repair_kit.png", "frame_width": 256, "frame_height": 256 }, - "torch_horizontal_floor": - {"path": "assets/items/torch_horizontal_floor.png", + "sword_1": + {"path": "assets/items/sword_1_sprite.png", "frame_width": 256, "frame_height": 256 }, - "peasant_girl": - {"path": "assets/sprites/peasant_girl_2.png", - "frame_width": 256, - "frame_height": 256 - }, - "healing_potion_small": - {"path": "assets/items/healing_potion_small.png", - "frame_width": 256, - "frame_height": 256 - }, - "well_down": - {"path": "assets/sprites/well_down.png", + "ladder_down": + {"path": "assets/sprites/ladder_down.png", "frame_width": 256, "frame_height": 256 }, @@ -75,13 +42,8 @@ "frame_width": 256, "frame_height": 256 }, - "peasant_girl": - {"path": "assets/sprites/peasant_girl_2.png", - "frame_width": 256, - "frame_height": 256 - }, - "female_hand": - {"path": "assets/hands/female_hand.png", + "hands_sword_attack": + {"path": "assets/hands/hands_sword_attack.png", "frame_width": 900, "frame_height": 600 } @@ -109,9 +71,9 @@ "border_px": 1, "text_size": 20, "label_size": 20, - "font_file_name": "assets/text.otf" + "font_file_name": "assets/text.ttf" }, "player": { - "hands": "female_hand" + "hands": "hands_sword_attack" } } diff --git a/assets/devices.json b/assets/devices.json index 0f52e02..70abeb3 100644 --- a/assets/devices.json +++ b/assets/devices.json @@ -14,7 +14,7 @@ {"_type": "Device", "config": {}, "events": ["STAIRS_DOWN"]}, - {"_type": "Sprite", "name": "well_down", "width": 256, "height": 256, "scale": 1.0} + {"_type": "Sprite", "name": "ladder_down", "width": 256, "height": 256, "scale": 1.0} ] }, "DEAD_BODY_LOOTABLE": { diff --git a/assets/doors/door_plain.png b/assets/doors/door_plain.png new file mode 100644 index 0000000..bfca6c6 Binary files /dev/null and b/assets/doors/door_plain.png differ diff --git a/assets/enemies.json b/assets/enemies.json index 4018979..57f5a2e 100644 --- a/assets/enemies.json +++ b/assets/enemies.json @@ -6,7 +6,7 @@ "foreground": "enemies/fg:player", "background": "color:transparent" }, - {"_type": "Combat", "hp": 200, "max_hp": 200, "ap": 0, "max_ap": 12, "ap_delta": 6, "damage": 50, "dead": false}, + {"_type": "Combat", "ap": 0, "max_ap": 12, "ap_delta": 6, "damage": 50, "dead": false}, {"_type": "Motion", "dx": 0, "dy": 0, "random": false}, {"_type": "Collision", "has": true}, {"_type": "EnemyConfig", "ai_script": "Host::actions", "ai_start_name": "Host::initial_state", "ai_goal_name": "Host::final_state"}, @@ -14,19 +14,18 @@ {"_type": "LightSource", "strength": 35, "radius": 2.0} ] }, - "RAT_GIANT": { + "SPIDER_BOT": { "components": [ {"_type": "Tile", "display": 2220, "foreground": "enemies/fg:rat_giant", "background": "color:transparent" }, - {"_type": "Combat", "hp": 50, "max_hp": 50, "ap": 0, "max_ap": 12, "ap_delta": 6,"damage": 2, "dead": false}, + {"_type": "Combat", "ap": 0, "max_ap": 12, "ap_delta": 6,"damage": 2, "dead": false}, {"_type": "Collision", "has": true}, {"_type": "Motion", "dx": 0, "dy": 0, "random": false}, {"_type": "EnemyConfig", "ai_script": "Enemy::actions", "ai_start_name": "Enemy::initial_state", "ai_goal_name": "Enemy::final_state"}, {"_type": "Personality", "hearing_distance": 5, "tough": false}, - {"_type": "Sprite", "name": "rat_with_sword", "scale": 1.0}, - {"_type": "Sound", "attack": "Small_Rat", "death": "Creature_Death_1"} + {"_type": "Sprite", "name": "spider_bot", "scale": 1.0} ] } } diff --git a/assets/hands/hands_sword_attack.png b/assets/hands/hands_sword_attack.png new file mode 100644 index 0000000..81dbbb3 Binary files /dev/null and b/assets/hands/hands_sword_attack.png differ diff --git a/assets/icons.json b/assets/icons.json index 904cd97..418cc89 100644 --- a/assets/icons.json +++ b/assets/icons.json @@ -1,12 +1,12 @@ { - "healing_potion_small": - {"path": "assets/icons/healing_potion_small.png", + "repair_kit": + {"path": "assets/icons/repair_kit.png", "frame_width": 96, "frame_height": 96 }, - "torch_horizontal_floor": - {"path": "assets/icons/torch_horizontal_floor.png", - "frame_width": 96, - "frame_height": 96 + "sword_1": + {"path": "assets/icons/sword_1_icon.png", + "frame_width": 300, + "frame_height": 100 } } diff --git a/assets/icons/repair_kit.png b/assets/icons/repair_kit.png new file mode 100644 index 0000000..634e48b Binary files /dev/null and b/assets/icons/repair_kit.png differ diff --git a/assets/icons/sword_1_icon.png b/assets/icons/sword_1_icon.png new file mode 100644 index 0000000..6d38330 Binary files /dev/null and b/assets/icons/sword_1_icon.png differ diff --git a/assets/items.json b/assets/items.json index 5c25db3..61d824d 100644 --- a/assets/items.json +++ b/assets/items.json @@ -1,23 +1,8 @@ { - "TORCH_BAD": { - "id": "TORCH_BAD", - "name": "Crappy Torch", - "description": "A torch that barely lights the way. You wonder if it'd be better to not see the person who murders you.", - "inventory_count": 1, - "components": [ - {"_type": "LightSource", "strength": 50, "radius": 2.5}, - {"_type": "Tile", "display": 3848, - "foreground": "items/fg:flame", - "background": "color:transparent" - }, - {"_type": "Sprite", "name": "torch_horizontal_floor", "width": 256, "height": 256, "scale": 1.0}, - {"_type": "Sound", "attack": "pickup", "death": "blank"} - ] - }, - "POTION_HEALING_SMALL": { - "id": "POTION_HEALING_SMALL", - "name": "Small Healing Potion", - "description": "A small healing potion.", + "REPAIR_KIT": { + "id": "REPAIR_KIT", + "name": "Robot Repair Kit", + "description": "A healing item for robots.", "inventory_count": 1, "components": [ {"_type": "Tile", "display": 1003, @@ -25,7 +10,21 @@ "background": "color:transparent" }, {"_type": "Curative", "hp": 20}, - {"_type": "Sprite", "name": "healing_potion_small", "width": 256, "height": 256, "scale": 1.0}, + {"_type": "Sprite", "name": "repair_kit", "width": 256, "height": 256, "scale": 1.0}, + {"_type": "Sound", "attack": "pickup", "death": "blank"} + ] + }, + "SWORD_1": { + "id": "SWORD_1", + "name": "Robot Repair Kit", + "description": "A healing item for robots.", + "inventory_count": 1, + "components": [ + {"_type": "Tile", "display": 1004, + "foreground": "items/fg:potion", + "background": "color:transparent" + }, + {"_type": "Sprite", "name": "sword_1", "width": 300, "height": 100, "scale": 1.0}, {"_type": "Sound", "attack": "pickup", "death": "blank"} ] } diff --git a/assets/items/repair_kit.png b/assets/items/repair_kit.png new file mode 100644 index 0000000..a540c09 Binary files /dev/null and b/assets/items/repair_kit.png differ diff --git a/assets/items/sword_1_sprite.png b/assets/items/sword_1_sprite.png new file mode 100644 index 0000000..2b84057 Binary files /dev/null and b/assets/items/sword_1_sprite.png differ diff --git a/assets/items/torch_horizontal_floor.png b/assets/items/torch_horizontal_floor.png new file mode 100644 index 0000000..2d8c7d7 Binary files /dev/null and b/assets/items/torch_horizontal_floor.png differ diff --git a/assets/map_tiles.png b/assets/map_tiles.png new file mode 100644 index 0000000..67c5ae3 Binary files /dev/null and b/assets/map_tiles.png differ diff --git a/assets/palette.json b/assets/palette.json index e3c68e1..856bf04 100644 --- a/assets/palette.json +++ b/assets/palette.json @@ -5,17 +5,17 @@ }, "gui/theme": { "black": [0, 0, 0, 255], - "dark_dark": [10, 10, 10, 255], - "dark_mid": [30, 30, 30, 255], - "dark_light": [60, 60, 60, 255], - "mid": [100, 100, 100, 255], - "light_dark": [150, 150, 150, 255], - "light_mid": [200, 200, 200, 255], - "light_light": [230, 230, 230, 255], + "dark_dark": [22, 10, 7, 255], + "dark_mid": [53, 25, 18, 255], + "dark_light": [91, 42, 31, 255], + "mid": [142, 65, 48, 255], + "light_dark": [193, 89, 65, 255], + "light_mid": [255, 117, 86, 255], + "light_light": [255, 194, 181, 255], "white": [255, 255, 255, 255], - "fill_color": "gui/theme:dark_mid", - "text_color": "gui/theme:light_light", - "bg_color": "gui/theme:mid", + "fill_color": [28, 29, 33, 255], + "text_color": [209, 209, 209, 255], + "bg_color": "gui/theme:dark_light", "border_color": "gui/theme:dark_dark", "bg_color_dark": "gui/theme:black" }, diff --git a/assets/sounds/blank.ogg b/assets/sounds/blank.ogg new file mode 100644 index 0000000..3322d4b Binary files /dev/null and b/assets/sounds/blank.ogg differ diff --git a/assets/sounds/pickup.ogg b/assets/sounds/pickup.ogg new file mode 100644 index 0000000..de7e095 Binary files /dev/null and b/assets/sounds/pickup.ogg differ diff --git a/assets/sounds/ui_click.ogg b/assets/sounds/ui_click.ogg new file mode 100644 index 0000000..7ff2e8c Binary files /dev/null and b/assets/sounds/ui_click.ogg differ diff --git a/assets/sounds/ui_hover.ogg b/assets/sounds/ui_hover.ogg new file mode 100644 index 0000000..be6e679 Binary files /dev/null and b/assets/sounds/ui_hover.ogg differ diff --git a/assets/sounds/walk.ogg b/assets/sounds/walk.ogg new file mode 100644 index 0000000..3d288ad Binary files /dev/null and b/assets/sounds/walk.ogg differ diff --git a/assets/sprites/dead_body.png b/assets/sprites/dead_body.png new file mode 100644 index 0000000..cb6a592 Binary files /dev/null and b/assets/sprites/dead_body.png differ diff --git a/assets/sprites/dead_body_lootable.png b/assets/sprites/dead_body_lootable.png new file mode 100644 index 0000000..cb6a592 Binary files /dev/null and b/assets/sprites/dead_body_lootable.png differ diff --git a/assets/sprites/ladder_down.png b/assets/sprites/ladder_down.png new file mode 100644 index 0000000..d80862b Binary files /dev/null and b/assets/sprites/ladder_down.png differ diff --git a/assets/sprites/rat_with_sword.png b/assets/sprites/rat_with_sword.png new file mode 100644 index 0000000..0d5763b Binary files /dev/null and b/assets/sprites/rat_with_sword.png differ diff --git a/assets/sprites/spider_bot.png b/assets/sprites/spider_bot.png new file mode 100644 index 0000000..4b912a4 Binary files /dev/null and b/assets/sprites/spider_bot.png differ diff --git a/assets/text.ttf b/assets/text.ttf new file mode 100644 index 0000000..350d33b Binary files /dev/null and b/assets/text.ttf differ diff --git a/assets/textures/ceiling_black.png b/assets/textures/ceiling_black.png new file mode 100644 index 0000000..b17688f Binary files /dev/null and b/assets/textures/ceiling_black.png differ diff --git a/assets/textures/floor_gray_stone.png b/assets/textures/floor_gray_stone.png new file mode 100644 index 0000000..d03a1a8 Binary files /dev/null and b/assets/textures/floor_gray_stone.png differ diff --git a/assets/textures/wall_plain.png b/assets/textures/wall_plain.png new file mode 100644 index 0000000..a7ad29d Binary files /dev/null and b/assets/textures/wall_plain.png differ diff --git a/src/combat/combat.cpp b/src/combat/combat.cpp index 042895b..23f3d7a 100644 --- a/src/combat/combat.cpp +++ b/src/combat/combat.cpp @@ -8,9 +8,30 @@ namespace components { if(attack) { my_dmg = Random::uniform(1, damage); - target.hp -= my_dmg; + target.hit_limb(my_dmg); } return my_dmg; } + + void Combat::hit_limb(int my_dmg) { + body_parts["head"] -= my_dmg; + } + + bool Combat::is_dead() { + return body_parts["head"] < 0; + } + + bool Combat::almost_dead() { + return body_parts["head"] < 20; + } + + bool Combat::can_heal() { + return body_parts["head"] < 50; + } + + void Combat::apply_healing(Curative& cure) { + int new_hp = body_parts["head"] + cure.hp; + body_parts["head"] = std::min(new_hp, 50); + } } diff --git a/src/game/components.hpp b/src/game/components.hpp index de49c35..9f31969 100644 --- a/src/game/components.hpp +++ b/src/game/components.hpp @@ -83,10 +83,6 @@ namespace components { std::string ai_goal_name; }; - struct Curative { - int hp = 10; - }; - struct Sprite { string name; float scale; @@ -106,12 +102,17 @@ namespace components { std::vector> beats; }; + struct Curative { + int hp = 10; + }; + struct Combat { - int hp; - int max_hp; int ap_delta; int max_ap; int damage; + std::unordered_map body_parts{ + {"head", 50}, + }; // everyone starts at 0 but ap_delta is added each round int ap = 0; @@ -120,6 +121,11 @@ namespace components { bool dead = false; int attack(Combat &target); + void hit_limb(int my_dmg); + bool is_dead(); + bool almost_dead(); + bool can_heal(); + void apply_healing(Curative& cure); }; struct LightSource { @@ -156,7 +162,7 @@ namespace components { ENROLL_COMPONENT(EnemyConfig, ai_script, ai_start_name, ai_goal_name); ENROLL_COMPONENT(Personality, hearing_distance, tough); ENROLL_COMPONENT(Motion, dx, dy, random); - ENROLL_COMPONENT(Combat, hp, max_hp, ap_delta, max_ap, damage, dead); + ENROLL_COMPONENT(Combat, ap_delta, max_ap, damage, dead); ENROLL_COMPONENT(Device, config, events); ENROLL_COMPONENT(Storyboard, image, audio, layout, beats); ENROLL_COMPONENT(Sound, attack, death); diff --git a/src/game/registry.hpp b/src/game/registry.hpp new file mode 100644 index 0000000..cf5b8ee --- /dev/null +++ b/src/game/registry.hpp @@ -0,0 +1,82 @@ +#pragma once + +#include +#include "game/components.hpp" + +namespace System { + using MovingFunc = std::function; + using CombatFunc = std::function; + using RenderFunc = std::function; + using UpdateFunc = std::function; + using UseItemFunc = std::function; + using PickupFunc = std::function; + + struct Registry { + std::vector $moving; + std::vector $combat; + std::vector $render; + std::vector $update; + std::vector $use_item; + std::vector $pickup; + + void addMoving(MovingFunc action) { + $moving.emplace_back(action); + } + + void addCombat(CombatFunc action) { + $combat.emplace_back(action); + } + + void addRender(RenderFunc action) { + $render.emplace_back(action); + } + + void addUpdate(UpdateFunc action) { + $update.emplace_back(action); + } + + void addUseItem(UseItemFunc action) { + $use_item.emplace_back(action); + } + + void addPickup(PickupFunc action) { + $pickup.emplace_back(action); + } + + void runMoving(components::Position move_to) { + for(auto func : $moving) { + func(move_to); + } + } + + void runCombat(int attack_id) { + for(auto func : $combat) { + func(attack_id); + } + } + + void runRender() { + for(auto func : $render) { + func(); + } + } + + void runUpdate() { + for(auto func : $update) { + func(); + } + } + + void runUseItem(const std::string& slot_name) { + for(auto func : $use_item) { + func(slot_name); + } + } + + void runPickup() { + for(auto func : $pickup) { + func(); + } + } + }; +} diff --git a/src/game/systems.cpp b/src/game/systems.cpp index d01fb93..75b9e12 100644 --- a/src/game/systems.cpp +++ b/src/game/systems.cpp @@ -167,16 +167,15 @@ void System::distribute_loot(Position target_pos) { auto loot_entity = world.entity(); if(inventory_count > 0) { - auto& entity_data = config.devices["DEAD_BODY_LOOTABLE"]; - components::configure_entity(world, loot_entity, entity_data["components"]); - // BUG: inventory_count here isn't really used to remove it - world.set(loot_entity, {inventory_count, entity_data}); - } else { - // this creates a dead body on the ground - auto& entity_data = config.devices["DEAD_BODY"]; - components::configure_entity(world, loot_entity, entity_data["components"]); + dbc::log("!!!!!!!!!!!!!!!! ============= LOOTING BODIES NOT READY"); } + // NOTE: refer to the code in raycaster for this + + // this creates a dead body on the ground + auto& entity_data = config.devices["DEAD_BODY"]; + components::configure_entity(world, loot_entity, entity_data["components"]); + set_position(world, *level.collision, loot_entity, target_pos); level.world->send(game::Event::ENTITY_SPAWN, loot_entity, {}); } @@ -189,7 +188,7 @@ void System::death() { world.query([&](auto ent, auto &combat) { // bring out yer dead - if(combat.hp <= 0 && !combat.dead) { + if(combat.is_dead() && !combat.dead) { combat.dead = true; if(ent != player.entity) { // we won't change out the player's components later @@ -197,7 +196,7 @@ void System::death() { } // we need to send this event for everything that dies world.send(game::Event::DEATH, ent, {}); - } else if(float(combat.hp) / float(combat.max_hp) < 0.5f) { + } else if(combat.almost_dead()) { // if enemies are below 50% health they are marked with bad health if(world.has(ent)) { auto& enemy_ai = world.get(ent); @@ -474,34 +473,23 @@ bool System::inventory_occupied(Entity container_id, const std::string& name) { return inventory.has(name); } -bool System::use_item(const string& slot_name) { +void System::use_item(const string& slot_name) { auto& level = GameDB::current_level(); auto& world = *level.world; auto& inventory = world.get(level.player); auto& player_combat = world.get(level.player); - if(player_combat.hp >= player_combat.max_hp) return false; - if(!inventory.has(slot_name)) return false; + if(!player_combat.can_heal()) return; + if(!inventory.has(slot_name)) return; auto what = inventory.get(slot_name); if(auto curative = world.get_if(what)) { inventory.remove(what); - - player_combat.hp += curative->hp; - - if(player_combat.hp > player_combat.max_hp) { - player_combat.hp = player_combat.max_hp; - } - - dbc::log($F("player health now {}", - player_combat.hp)); - + player_combat.apply_healing(*curative); world.remove(what); - return true; } else { dbc::log($F("no usable item at {}", what)); - return false; } } @@ -541,3 +529,19 @@ void System::clear_attack() { void System::spawn_attack(World& world, int attack_id, DinkyECS::Entity enemy) { } + + +void System::init(Registry& reg) { + reg.addRender(System::clear_attack); + reg.addUseItem(System::use_item); + reg.addMoving(System::move_player); + reg.addCombat(System::combat); + reg.addPickup(System::pickup); + reg.addUpdate(System::generate_paths); + reg.addUpdate(System::enemy_ai_initialize); + reg.addUpdate(System::enemy_pathing); + reg.addUpdate(System::motion); + reg.addUpdate(System::collision); + reg.addUpdate(System::lighting); + reg.addUpdate(System::death); +} diff --git a/src/game/systems.hpp b/src/game/systems.hpp index b1edd4e..38f29e0 100644 --- a/src/game/systems.hpp +++ b/src/game/systems.hpp @@ -5,8 +5,10 @@ #include "algos/spatialmap.hpp" #include "game/level.hpp" #include "events.hpp" +#include "game/registry.hpp" namespace System { + using namespace components; using namespace DinkyECS; using std::string, matrix::Matrix; @@ -32,15 +34,15 @@ namespace System { void pickup(); + // BUG: these might need to go somewhere else.... bool place_in_container(Entity cont_id, const string& name, Entity world_entity); - void remove_from_container(Entity cont_id, const std::string& name); void remove_from_world(Entity entity); void inventory_swap(Entity container_id, const std::string& a_name, const std::string &b_name); bool inventory_occupied(Entity container_id, const std::string& name); void set_position(DinkyECS::World& world, SpatialMap& collision, Entity entity, Position pos); - bool use_item(const std::string& slot_name); + void use_item(const std::string& slot_name); game::Event shortest_rotate(Point player_at, Point aiming_at, Point turning_to); @@ -67,4 +69,6 @@ namespace System { void clear_attack(); void spawn_attack(World& world, int attack_id, DinkyECS::Entity enemy); + + void init(Registry& reg); } diff --git a/src/game/worldbuilder.cpp b/src/game/worldbuilder.cpp index cac4c5c..b596ff2 100644 --- a/src/game/worldbuilder.cpp +++ b/src/game/worldbuilder.cpp @@ -199,15 +199,14 @@ void WorldBuilder::place_stairs(DinkyECS::World& world, GameConfig& config) { void WorldBuilder::configure_starting_items(DinkyECS::World &world) { auto& player = world.get_the(); - - auto torch_id = System::spawn_item(world, "TORCH_BAD"); - auto &inventory = world.get(player.entity); - inventory.add("hand_r", torch_id); - world.make_constant(torch_id); - auto healing = System::spawn_item(world, "POTION_HEALING_SMALL"); - inventory.add("pocket_l", healing); + auto healing = System::spawn_item(world, "REPAIR_KIT"); + inventory.add("inv0", healing); + + auto sword = System::spawn_item(world, "SWORD_1"); + inventory.add("hand_main", sword); + world.make_constant(healing); } diff --git a/src/graphics/raycaster.cpp b/src/graphics/raycaster.cpp index 0956a09..ca800f6 100644 --- a/src/graphics/raycaster.cpp +++ b/src/graphics/raycaster.cpp @@ -121,7 +121,7 @@ inline void set_scale_position(sf::Sprite& sprite, sf::Vector2f& position, sf::V } -void Raycaster::sprite_casting() { +void Raycaster::sprite_casting(sf::RenderTarget& target) { auto& lights = $level.lights->lighting(); auto world = $level.world; $level.collision->distance_sorted($sprite_order, {(size_t)$pos_x, (size_t)$pos_y}, RENDER_DISTANCE); @@ -212,7 +212,6 @@ void Raycaster::sprite_casting() { sf::Vector2f scale{sprite_scale_w, sprite_scale_h}; sf::Vector2f position{x + origin.x * scale.x, y + origin.y * scale.y}; sf::IntRect in_texture{ {tex_x, tex_y}, {tex_render_width, texture_height}}; - shared_ptr effect = System::sprite_effect(rec.entity); if(effect) { @@ -231,7 +230,7 @@ void Raycaster::sprite_casting() { set_scale_position(*sf_sprite, position, scale, in_texture, origin); } - $sprites_to_render.emplace_back(sf_sprite, effect); + target.draw(*sf_sprite, effect.get()); } } } @@ -438,16 +437,12 @@ void Raycaster::update() { draw_ceiling_floor(); cast_rays(); draw_pixel_buffer(); - sprite_casting(); } // BUG: if target is a rendertarget then I can say it has to be the viewport only, then I can get rid of $screen_pos_x/y void Raycaster::render(sf::RenderTarget& target) { target.draw($view_sprite); - - for(auto [sprite, effect] : $sprites_to_render) { - target.draw(*sprite, effect.get()); - } + sprite_casting(target); } void Raycaster::update_sprite(DinkyECS::Entity ent, components::Sprite& sprite) { diff --git a/src/graphics/raycaster.hpp b/src/graphics/raycaster.hpp index 922eda9..d1038cf 100644 --- a/src/graphics/raycaster.hpp +++ b/src/graphics/raycaster.hpp @@ -21,7 +21,7 @@ struct CameraLOL { double target_plane_y = 0.0; }; -using SpriteRender = std::pair, std::shared_ptr>; +using SpriteRender = std::pair>; struct Raycaster { sf::Texture $view_texture; @@ -64,7 +64,7 @@ struct Raycaster { void cast_rays(); void draw_ceiling_floor(); void draw_pixel_buffer(); - void sprite_casting(); + void sprite_casting(sf::RenderTarget& target); void update(); void render(sf::RenderTarget& target); diff --git a/src/gui/body_ui.cpp b/src/gui/body_ui.cpp new file mode 100644 index 0000000..2fa4f5b --- /dev/null +++ b/src/gui/body_ui.cpp @@ -0,0 +1,61 @@ +#include "gui/body_ui.hpp" +#include "game/components.hpp" +#include +#include "algos/rand.hpp" +#include +#include "gui/guecstra.hpp" +#include "game/systems.hpp" +#include "game/inventory.hpp" +#include "game/level.hpp" + +namespace gui { + using namespace guecs; + using std::any, std::any_cast, std::string, std::make_any; + + void BodyUI::init(size_t x, size_t y, size_t width, size_t height) { + $gui.position(x, y, width, height); + $gui.layout( + "[head]" + "[chest]" + "[right_arm]" + "[left_arm]" + "[stomach]" + "[left_leg]" + "[right_leg]"); + + $gui.set($gui.MAIN, {$gui.$parser, }); + + for(auto& [name, cell] : $gui.cells()) { + auto gui_id = $gui.entity(name); + + $gui.set(gui_id, {guecs::to_wstring(name)}); + $gui.set(gui_id, {1.0f, THEME.DARK_MID, {}}); + } + + $gui.init(); + update(); + } + + bool BodyUI::mouse(float x, float y, guecs::Modifiers mods) { + return $gui.mouse(x, y, mods); + } + + void BodyUI::update() { + auto world = GameDB::current_world(); + auto& player = world->get_the(); + auto& player_combat = world->get(player.entity); + + for(auto& [key, value] : player_combat.body_parts) { + auto gui_id = $gui.entity(key); + + if(auto meter = $gui.get_if(gui_id)) { + meter->percent = float(value) / 50.0; + } + } + } + + void BodyUI::render(sf::RenderWindow &window) { + $gui.render(window); + // $gui.debug_layout(window); + } +} diff --git a/src/gui/body_ui.hpp b/src/gui/body_ui.hpp new file mode 100644 index 0000000..99b048e --- /dev/null +++ b/src/gui/body_ui.hpp @@ -0,0 +1,18 @@ +#pragma once +#include "constants.hpp" +#include +#include "graphics/textures.hpp" +#include +#include "gui/guecstra.hpp" + +namespace gui { + class BodyUI { + public: + guecs::UI $gui{}; + + void init(size_t x, size_t y, size_t width, size_t height); + void render(sf::RenderWindow &window); + void update(); + bool mouse(float x, float y, guecs::Modifiers mods); + }; +} diff --git a/src/gui/debug_ui.cpp b/src/gui/debug_ui.cpp index f703a5c..c4f9fcc 100644 --- a/src/gui/debug_ui.cpp +++ b/src/gui/debug_ui.cpp @@ -19,7 +19,7 @@ namespace gui { "[spawn1|spawn2|spawn3]" "[spawn4|spawn5|spawn6]"); - add_spawn_button("RAT_GIANT", "rat_with_sword", "spawn4"); + // add_spawn_button("RAT_GIANT", "rat_with_sword", "spawn4"); $gui.init(); } @@ -48,7 +48,6 @@ namespace gui { auto map = level.map; std::wstring stats = $F(L"STATS\n" - L"HP: {}\n" L"mean:{:>8.5}\n" L"sdev: {:>8.5}\n" L"min: {:>8.5}\n" @@ -58,7 +57,7 @@ namespace gui { L"VSync? {}\n" L"FR Limit: {}\n" L"Debug? {}\n\n", - player_combat.hp, $stats.mean(), $stats.stddev(), $stats.min, + $stats.mean(), $stats.stddev(), $stats.min, $stats.max, $stats.n, level.index, map->width(), map->height(), VSYNC, FRAME_LIMIT, DEBUG_BUILD); @@ -74,9 +73,6 @@ namespace gui { if(active) { auto& level = GameDB::current_level(); // it's on now, enable things - auto player = level.world->get_the(); - auto& player_combat = level.world->get(player.entity); - player_combat.hp = player_combat.max_hp; $gui.show_text("debug_text", L"STATS"); } else { // it's off now, close it diff --git a/src/gui/fsm.cpp b/src/gui/fsm.cpp index 8a7686a..9062526 100644 --- a/src/gui/fsm.cpp +++ b/src/gui/fsm.cpp @@ -58,7 +58,7 @@ namespace gui { void FSM::MOVING(Event ) { // this should be an optional that returns a point if(auto move_to = $main_ui.play_move()) { - System::move_player(*move_to); + $systems.runMoving(*move_to); run_systems(); $main_ui.dirty(); state(State::IDLE); @@ -70,7 +70,7 @@ namespace gui { switch(ev) { case TICK: { dbc::log("!!!!!! FIX System::combat(0) doesn't use any weapons, only first"); - System::combat(0); + $systems.runCombat(0); run_systems(); state(State::IN_COMBAT); } break; @@ -79,7 +79,7 @@ namespace gui { break; case ATTACK: { int attack_id = std::any_cast(data); - System::combat(attack_id); + $systems.runCombat(attack_id); run_systems(); } break; default: @@ -174,10 +174,8 @@ namespace gui { case USE_ITEM: { auto gui_id = std::any_cast(data); auto& slot_name = $status_ui.$gui.name_for(gui_id); - - if(System::use_item(slot_name)) { - $status_ui.update(); - } + $systems.runUseItem(slot_name); + $status_ui.update(); } break; case MOUSE_CLICK: mouse_action(guecs::NO_MODS); @@ -186,7 +184,7 @@ namespace gui { mouse_action({1 << guecs::ModBit::hover}); } break; case AIM_CLICK: - System::pickup(); + $systems.runPickup(); break; default: break; // ignore everything else @@ -312,9 +310,6 @@ namespace gui { $debug_ui.debug(); shaders::reload(); break; - case KEY::O: - autowalking = true; - break; case KEY::L: // This will go away as soon as containers work $loot_ui.set_target($loot_ui.$temp_loot); @@ -360,10 +355,8 @@ namespace gui { } void FSM::render() { - $window.clear(); - // this clears any attack animations, like fire - System::clear_attack(); + $systems.runRender(); // BUG: this is the render for this class, and where I add an update draw_gui(); @@ -371,13 +364,7 @@ namespace gui { } void FSM::run_systems() { - System::generate_paths(); - System::enemy_ai_initialize(); - System::enemy_pathing(); - System::motion(); - System::collision(); - System::lighting(); - System::death(); + $systems.runUpdate(); } bool FSM::active() { diff --git a/src/gui/fsm.hpp b/src/gui/fsm.hpp index 0610626..36aed03 100644 --- a/src/gui/fsm.hpp +++ b/src/gui/fsm.hpp @@ -1,6 +1,7 @@ #pragma once #include "constants.hpp" +#include "game/registry.hpp" #include "algos/simplefsm.hpp" #include "gui/debug_ui.hpp" #include "gui/main_ui.hpp" @@ -35,12 +36,11 @@ namespace gui { LootUI $loot_ui; gui::routing::Router $router; DNDLoot $dnd_loot; + System::Registry $systems; FSM(); void event(game::Event ev, std::any data={}); - void autowalk(); - void start_autowalk(double rot_speed); void START(game::Event ev); void MOVING(game::Event ev); diff --git a/src/gui/loot_ui.cpp b/src/gui/loot_ui.cpp index c76049a..07c55b4 100644 --- a/src/gui/loot_ui.cpp +++ b/src/gui/loot_ui.cpp @@ -78,6 +78,7 @@ namespace gui { dbc::check(world->has(item), "item in inventory UI doesn't exist in world. New level?"); auto& sprite = world->get(item); + fmt::println("!!!!!!!!!!! trying to load {}", sprite.name); $gui.set_init(id, {sprite.name}); guecs::GrabSource grabber{ diff --git a/src/gui/main_ui.cpp b/src/gui/main_ui.cpp index 1d5cd2b..559df5e 100644 --- a/src/gui/main_ui.cpp +++ b/src/gui/main_ui.cpp @@ -17,9 +17,11 @@ namespace gui { $window.setFramerateLimit(FRAME_LIMIT); auto config = settings::get("config"); - $hand = textures::get_sprite(config["player"]["hands"]); $hand_anim = animation::load("assets/animation.json", config["player"]["hands"]); + int width = $hand_anim.sheet.frame_width; + int height = $hand_anim.sheet.frame_height; + $hand.sprite->setPosition({float(RAY_VIEW_X + (RAY_VIEW_WIDTH - width) / 2), float(RAY_VIEW_HEIGHT - height)}); } void MainUI::dirty() { @@ -148,7 +150,6 @@ namespace gui { if($hand_anim.playing) { $hand_anim.update(); $hand_anim.apply(*$hand.sprite); - $hand.sprite->setPosition({RAY_VIEW_X, RAY_VIEW_Y}); $window.draw(*$hand.sprite); } } diff --git a/src/gui/overlay_ui.cpp b/src/gui/overlay_ui.cpp index 8d797b0..6f16f71 100644 --- a/src/gui/overlay_ui.cpp +++ b/src/gui/overlay_ui.cpp @@ -18,12 +18,13 @@ namespace gui { $gui.init(); } - inline void make_clickable_area(guecs::UI &gui, const std::string &name) { + inline void make_clickable_area(guecs::UI &gui, const std::string name) { auto area = gui.entity(name); gui.set(area, { - [&](auto) { + [=](auto) { auto world = GameDB::current_world(); + fmt::println("CLICK {}", name); world->send(game::Event::AIM_CLICK, area, {}); } }); diff --git a/src/gui/status_ui.cpp b/src/gui/status_ui.cpp index 3dbdeb5..87b6b39 100644 --- a/src/gui/status_ui.cpp +++ b/src/gui/status_ui.cpp @@ -16,10 +16,14 @@ namespace gui { { $gui.position(x, y, width, height); $gui.layout( - "[=slot1]" - "[=slot2]" - "[=hand_r]" - "[=pocket_l]"); + "[*%(100, 300)body_ui]" + "[_]" + "[_]" + "[=inv0|=inv1|=inv2]" + "[=inv3|=inv4|=inv5]" + "[=inv6|=inv7|=inv8]" + "[=hand_main]" + "[=hand_off]"); } void StatusUI::init() { @@ -28,17 +32,22 @@ namespace gui { for(auto& [name, cell] : $gui.cells()) { auto gui_id = $gui.entity(name); - $gui.set(gui_id, {}); - $gui.set(gui_id, {guecs::to_wstring(name)}); - $gui.set(gui_id, { - guecs::make_action(gui_id, game::Event::INV_SELECT, {gui_id}) - }); - $gui.set(gui_id, { - .commit=[&, gui_id](DinkyECS::Entity world_target) -> bool { - return place_slot(gui_id, world_target); - } - }); + + if(name.starts_with("body_")) { + auto& cell = $gui.cell_for(name); + $body_ui.init(cell.x, cell.y, cell.w, cell.h); + } else { + $gui.set(gui_id, {}); + $gui.set(gui_id, { + guecs::make_action(gui_id, game::Event::INV_SELECT, {gui_id}) + }); + $gui.set(gui_id, { + .commit=[&, gui_id](DinkyECS::Entity world_target) -> bool { + return place_slot(gui_id, world_target); + } + }); + } } $gui.init(); @@ -54,6 +63,8 @@ namespace gui { auto player = world->get_the(); auto& inventory = world->get(player.entity); + $body_ui.update(); + for(const auto& [slot, cell] : $gui.cells()) { if(inventory.has(slot)) { @@ -79,6 +90,7 @@ namespace gui { void StatusUI::render(sf::RenderWindow &window) { $gui.render(window); + $body_ui.render(window); // $gui.debug_layout(window); } diff --git a/src/gui/status_ui.hpp b/src/gui/status_ui.hpp index b64ebcf..233191b 100644 --- a/src/gui/status_ui.hpp +++ b/src/gui/status_ui.hpp @@ -4,11 +4,13 @@ #include "graphics/textures.hpp" #include #include "gui/guecstra.hpp" +#include "gui/body_ui.hpp" namespace gui { class StatusUI { public: - guecs::UI $gui; + guecs::UI $gui{}; + BodyUI $body_ui{}; explicit StatusUI(size_t x, size_t y, size_t width, size_t height); diff --git a/src/main.cpp b/src/main.cpp index a889731..28a5f35 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -7,6 +7,7 @@ #include "gui/backend.hpp" #include "game/level.hpp" #include "graphics/camera.hpp" +#include "game/systems.hpp" int main(int argc, char* argv[]) { try { @@ -21,6 +22,7 @@ int main(int argc, char* argv[]) { sound::mute(true); gui::FSM main; + System::init(main.$systems); main.event(game::Event::START); sound::play("ambient_1", true); diff --git a/src/meson.build b/src/meson.build index 35ec50d..8017508 100644 --- a/src/meson.build +++ b/src/meson.build @@ -19,6 +19,7 @@ sources = files( 'gui/status_ui.cpp', 'gui/main_ui.cpp', 'gui/overlay_ui.cpp', + 'gui/body_ui.cpp', # graphics 'graphics/animation.cpp', diff --git a/tests/battle.cpp b/tests/battle.cpp index eb46d09..d33ee05 100644 --- a/tests/battle.cpp +++ b/tests/battle.cpp @@ -25,20 +25,17 @@ TEST_CASE("battle operations fantasy", "[combat-battle]") { DinkyECS::Entity host = 0; ai::EntityAI host_ai("Host::actions", host_start, host_goal); - components::Combat host_combat{ - .hp=100, .max_hp=100, .ap_delta=6, .max_ap=12, .damage=20}; + components::Combat host_combat{.ap_delta=6, .max_ap=12, .damage=20}; battle.add_enemy({host, &host_ai, &host_combat, true}); DinkyECS::Entity axe_ranger = 1; ai::EntityAI axe_ai("Enemy::actions", ai_start, ai_goal); - components::Combat axe_combat{ - .hp=20, .max_hp=20, .ap_delta=8, .max_ap=12, .damage=20}; + components::Combat axe_combat{.ap_delta=8, .max_ap=12, .damage=20}; battle.add_enemy({axe_ranger, &axe_ai, &axe_combat}); DinkyECS::Entity rat = 2; ai::EntityAI rat_ai("Enemy::actions", ai_start, ai_goal); - components::Combat rat_combat{ - .hp=10, .max_hp=10, .ap_delta=2, .max_ap=10, .damage=10}; + components::Combat rat_combat{.ap_delta=2, .max_ap=10, .damage=10}; battle.add_enemy({rat, &rat_ai, &rat_combat}); battle.set_all("enemy_found", true); @@ -50,8 +47,8 @@ TEST_CASE("battle operations fantasy", "[combat-battle]") { battle.set(host, "have_healing", false); battle.set(host, "tough_personality", false); - while(host_combat.hp > 0) { - battle.set(host, "health_good", host_combat.hp > 20); + while(!host_combat.is_dead()) { + battle.set(host, "health_good", host_combat.almost_dead()); battle.player_request("use_healing"); battle.player_request("kill_enemy"); @@ -62,11 +59,6 @@ TEST_CASE("battle operations fantasy", "[combat-battle]") { while(auto act = battle.next()) { auto& [enemy, wants_to, cost, enemy_state] = *act; - // fmt::println(">>>>> entity: {} wants to {} cost={}; has {} HP; {} ap", - // enemy.entity, wants_to, - // cost, enemy.combat->hp, - // enemy.combat->ap); - switch(enemy_state) { case BattleHostState::agree: // fmt::println("HOST and PLAYER requests match {}, doing it.", wants_to); diff --git a/tests/loot.cpp b/tests/loot.cpp index 6f72bd2..eac74fe 100644 --- a/tests/loot.cpp +++ b/tests/loot.cpp @@ -10,12 +10,12 @@ using namespace components; TEST_CASE("test the loot ui", "[loot]") { auto items = settings::get("assets/items.json"); DinkyECS::World world; - auto torch = world.entity(); - auto& data = items["TORCH_BAD"]; + auto repair_kit = world.entity(); + auto& data = items["REPAIR_KIT"]; components::init(); - components::configure_entity(world, torch, data["components"]); + components::configure_entity(world, repair_kit, data["components"]); - auto& torch_sprite = world.get(torch); - REQUIRE(torch_sprite.name == "torch_horizontal_floor"); + auto& repair_kit_sprite = world.get(repair_kit); + REQUIRE(repair_kit_sprite.name == "repair_kit"); } diff --git a/tests/palette.cpp b/tests/palette.cpp index a96ad81..a38ad8e 100644 --- a/tests/palette.cpp +++ b/tests/palette.cpp @@ -11,14 +11,8 @@ TEST_CASE("color palette test", "[color-palette]") { // confirm it's idempotent palette::init(); - sf::Color expect{10, 10, 10, 255}; - auto gui_text = palette::get("gui/theme:dark_dark"); - REQUIRE(gui_text == expect); - - gui_text = palette::get("gui/theme", "mid"); - REQUIRE(gui_text != expect); - - expect = {100, 100, 100, 255}; - REQUIRE(gui_text == expect); + REQUIRE(gui_text.r > 0); + REQUIRE(gui_text.g > 0); + REQUIRE(gui_text.b > 0); } diff --git a/tests/systems.cpp b/tests/systems.cpp index 55c7308..4272a9d 100644 --- a/tests/systems.cpp +++ b/tests/systems.cpp @@ -3,7 +3,9 @@ #include "game/systems.hpp" #include #include +#include "game/registry.hpp" +using components::Position; TEST_CASE("figure out best rotation direction", "[systems-rotate]") { Matrix map = matrix::make(3, 3); @@ -35,104 +37,45 @@ TEST_CASE("figure out best rotation direction", "[systems-rotate]") { } } -using MovingFunc = std::function; -using CombatFunc = std::function; -using RenderFunc = std::function; -using UpdateFunc = std::function; -using UseFunc = std::function; -using PickupFunc = std::function; -struct Engine { - std::vector $moving; - std::vector $combat; - std::vector $render; - std::vector $update; - std::vector $use; - std::vector $pickup; - - void addMoving(MovingFunc action) { - $moving.emplace_back(action); - } - - void addCombat(CombatFunc action) { - $combat.emplace_back(action); - } - - void addRender(RenderFunc action) { - $render.emplace_back(action); - } - - void addUpdate(UpdateFunc action) { - $update.emplace_back(action); - } - - void addUse(UseFunc action) { - $use.emplace_back(action); - } - - void addPickup(PickupFunc action) { - $pickup.emplace_back(action); - } - - void runMoving() { - for(auto func : $moving) { - func(); - } - } - - void runCombat(bool attr) { - for(auto func : $combat) { - func(attr); - } - } - - void runRender() { - for(auto func : $render) { - func(); - } - } - - void runUpdate() { - for(auto func : $update) { - func(); - } - } - - void runUse() { - for(auto func : $use) { - func(); - } - } - - void runPickup() { - for(auto func : $pickup) { - func(); - } - } -}; - -void test_system_1() { - fmt::println("TEST 1"); +void test_moving(Position& move_to) { + fmt::println("MOVING: {},{}", move_to.location.x, move_to.location.y); } -void test_combat(bool what) { - fmt::println("TEST 2: {}", what); +void test_combat(int attack_id) { + fmt::println("ATTACK: {}", attack_id); +} + +void test_render() { + fmt::println("RENDER"); +} + +void test_update() { + fmt::println("UPDATE"); +} + +void test_use_item(const std::string& slot_name) { + fmt::println("USE ITEM {}", slot_name); +} + +void test_pickup() { + fmt::println("PICKUP"); } TEST_CASE("new system running engine thing", "[systems-engine]") { - Engine systems; + System::Registry systems; - systems.addMoving(test_system_1); + systems.addMoving(test_moving); systems.addCombat(test_combat); - systems.addRender(test_system_1); - systems.addUpdate(test_system_1); - systems.addUse(test_system_1); - systems.addPickup(test_system_1); + systems.addRender(test_render); + systems.addUpdate(test_update); + systems.addUseItem(test_use_item); + systems.addPickup(test_pickup); - systems.runCombat(false); - systems.runMoving(); + systems.runCombat(1); + systems.runMoving({1,1}); systems.runRender(); systems.runUpdate(); - systems.runUse(); + systems.runUseItem("hand_l"); systems.runPickup(); } diff --git a/tests/textures.cpp b/tests/textures.cpp index eb5d490..50d3c8e 100644 --- a/tests/textures.cpp +++ b/tests/textures.cpp @@ -11,13 +11,13 @@ TEST_CASE("test texture management", "[textures]") { components::init(); textures::init(); - auto spider = textures::get_sprite("rat_with_sword"); + auto spider = textures::get_sprite("spider_bot"); REQUIRE(spider.sprite != nullptr); REQUIRE(spider.texture != nullptr); REQUIRE(spider.frame_size.x == TEXTURE_WIDTH); REQUIRE(spider.frame_size.y == TEXTURE_HEIGHT); - auto image = textures::load_image("assets/sprites/rat_with_sword.png"); + auto image = textures::load_image("assets/sprites/spider_bot.png"); size_t floor_tile = textures::get_id("floor_tile"); size_t gray_stone = textures::get_id("door_plain");