Mostly worked out how to do looting but now need how to take out of inventory and put into loot.

master
Zed A. Shaw 1 day ago
parent c509162be1
commit 94385b195d
  1. 4
      events.hpp
  2. 139
      gui/fsm.cpp
  3. 25
      gui/fsm.hpp
  4. 12
      gui/loot_ui.cpp
  5. 1
      gui/loot_ui.hpp
  6. 2
      gui/status_ui.cpp
  7. 2
      main.cpp

@ -6,7 +6,7 @@ namespace Events {
COMBAT_START, NO_NEIGHBORS, HP_STATUS, COMBAT_START, NO_NEIGHBORS, HP_STATUS,
ATTACK, BLOCK, EVADE, NEW_RITUAL, ATTACK, BLOCK, EVADE, NEW_RITUAL,
UPDATE_SPRITE, ENEMY_SPAWN, NOOP, UPDATE_SPRITE, ENEMY_SPAWN, NOOP,
LOOT_CLOSE, LOOT_SELECT, LOOT_PLACE LOOT_CLOSE, LOOT_SELECT, INV_SELECT
}; };
struct Combat { struct Combat {
@ -33,7 +33,7 @@ namespace gui {
STAIRS_DOWN = 13, STAIRS_DOWN = 13,
LOOT_OPEN=14, LOOT_OPEN=14,
LOOT_SELECT=15, LOOT_SELECT=15,
LOOT_PLACE=16, INV_SELECT=16,
QUIT = 17, QUIT = 17,
MOUSE_CLICK=18, MOUSE_CLICK=18,
MOUSE_MOVE=19, MOUSE_MOVE=19,

@ -39,15 +39,20 @@ namespace gui {
FSM_STATE(State, COMBAT_ROTATE, ev); FSM_STATE(State, COMBAT_ROTATE, ev);
FSM_STATE(State, NEXT_LEVEL, ev); FSM_STATE(State, NEXT_LEVEL, ev);
FSM_STATE(State, END, ev); FSM_STATE(State, END, ev);
FSM_STATE(State, LOOTING, ev, std::make_any<bool>(true)); FSM_STATE(State, LOOTING, ev, std::make_any<int>(-1));
FSM_STATE(State, LOOT_GRAB, ev, std::make_any<int>(-1));
FSM_STATE(State, INV_GRAB, ev, std::make_any<int>(-1));
} }
} }
void FSM::event(Event ev, std::any data) { void FSM::event(Event ev, std::any data) {
switch($state) { switch($state) {
FSM_STATE(State, LOOTING, ev, data); FSM_STATE(State, LOOTING, ev, data);
FSM_STATE(State, LOOT_GRAB, ev, data);
FSM_STATE(State, INV_GRAB, ev, data);
FSM_STATE(State, IDLE, ev);
default: default:
dbc::log(fmt::format("event given with data but event={} is not handled", int(ev))); dbc::log(fmt::format("event received with data but state={} is not handled", int($state)));
} }
} }
@ -118,7 +123,7 @@ namespace gui {
} }
} }
void FSM::LOOTING(Event ev, std::any data) { void FSM::LOOT_GRAB(Event ev, std::any data) {
using enum Event; using enum Event;
switch(ev) { switch(ev) {
@ -127,40 +132,118 @@ namespace gui {
state(State::IDLE); state(State::IDLE);
break; break;
case LOOT_SELECT: { case LOOT_SELECT: {
fmt::println("loot is selected");
int slot_id = std::any_cast<int>(data); int slot_id = std::any_cast<int>(data);
if(auto entity = $loot_ui.select_slot(slot_id)) { if(auto entity = $loot_ui.select_slot(slot_id)) {
fmt::println("LOOT SELECT slot={} has entity={}", slot_id, entity.value()); $status_ui.select_slot(slot_id, *entity);
$status_ui.select_slot(slot_id, entity.value()); $dumb_sprite = $loot_ui.grab_sprite(slot_id);
$window.setMouseCursorVisible(false);
$dumb_sprite->setOrigin({128, 128});
$dumb_sprite->setPosition({
float($router.position.x),
float($router.position.y)
});
} }
} break; } break;
case LOOT_PLACE: { case INV_SELECT: {
std::string slot_name = std::any_cast<std::string>(data); std::string slot_name = std::any_cast<std::string>(data);
int slot_id = $status_ui.place_slot(slot_name); int slot_id = $status_ui.place_slot(slot_name);
// BUG: fix this bullshit
if(slot_id != -1) { if(slot_id != -1) {
$loot_ui.remove_slot(slot_id); $loot_ui.remove_slot(slot_id);
} }
$window.setMouseCursorVisible(true);
$dumb_sprite = nullptr;
state(State::LOOTING);
} break; } break;
case MOUSE_CLICK: case MOUSE_CLICK:
mouse_action(false); mouse_action(false);
break; break;
case MOUSE_MOVE: case MOUSE_MOVE: {
if($dumb_sprite) {
$dumb_sprite->setPosition({
float($router.position.x),
float($router.position.y)
});
}
mouse_action(true); mouse_action(true);
break; } break;
case MOUSE_DRAG_START: case MOUSE_DRAG_START: {
mouse_action(false); mouse_action(false);
break; } break;
case MOUSE_DRAG: case MOUSE_DRAG: {
if($dumb_sprite) {
$dumb_sprite->setPosition({
float($router.position.x),
float($router.position.y)
});
}
mouse_action(true); mouse_action(true);
break; } break;
case MOUSE_DROP: case MOUSE_DROP:
mouse_action(false); mouse_action(false);
break; break;
case TICK: case TICK:
// do nothing // do nothing
break; break;
default:
state(State::LOOT_GRAB);
}
}
void FSM::INV_GRAB(Event ev, std::any data) {
using enum Event;
(void)data;
switch(ev) {
case LOOT_OPEN:
$loot_ui.active = false;
state(State::IDLE);
break;
case LOOT_SELECT: {
state(State::IDLE);
} break;
case INV_SELECT: {
state(State::IDLE);
} break;
case MOUSE_CLICK:
mouse_action(false);
break;
case MOUSE_MOVE: {
mouse_action(true);
} break;
case MOUSE_DRAG_START: {
mouse_action(false);
} break;
case MOUSE_DRAG: {
mouse_action(true);
} break;
case MOUSE_DROP:
mouse_action(false);
break;
default:
state(State::INV_GRAB);
}
}
void FSM::LOOTING(Event ev, std::any data) {
using enum Event;
switch(ev) {
case LOOT_OPEN:
$loot_ui.active = false;
state(State::IDLE);
break;
case LOOT_SELECT:
LOOT_GRAB(ev, data);
state(State::LOOT_GRAB);
break;
case INV_SELECT:
state(State::INV_GRAB);
INV_GRAB(ev, data);
break;
case MOUSE_CLICK:
mouse_action(false);
break;
default: default:
state(State::LOOTING); state(State::LOOTING);
} }
@ -213,39 +296,31 @@ namespace gui {
sound::stop("ambient"); sound::stop("ambient");
state(State::NEXT_LEVEL); state(State::NEXT_LEVEL);
break; break;
case STOP_COMBAT:
case TICK:
// do nothing
break;
case LOOT_OPEN: { case LOOT_OPEN: {
dbc::log("IDLE LOOT OPEN!");
Config items("assets/items.json"); Config items("assets/items.json");
auto& data = items["TORCH_BAD"]; auto& data = items["TORCH_BAD"];
for(int i = 0; $loot_ui.contents.size() < 10; i++) {
auto torch = $level.world->entity(); auto torch = $level.world->entity();
components::configure_entity(*$level.world, torch, data["components"]); components::configure_entity(*$level.world, torch, data["components"]);
$loot_ui.contents.push_back(torch); $loot_ui.contents.push_back(torch);
}
$loot_ui.update(); $loot_ui.update();
$loot_ui.active = true; $loot_ui.active = true;
state(State::LOOTING); state(State::LOOTING);
} break; } break;
case LOOT_PLACE: case INV_SELECT:
// ignored state(State::INV_GRAB);
break; break;
case MOUSE_CLICK: case MOUSE_CLICK:
mouse_action(false); mouse_action(false);
break; break;
case MOUSE_MOVE: case MOUSE_MOVE:
mouse_action(true); mouse_action(true);
break; break;
case MOUSE_DRAG: // ignored
case MOUSE_DRAG_START: // ignored
case MOUSE_DROP: // ignored
break;
default: default:
dbc::sentinel("unhandled event in IDLE"); break; // ignore everything else
} }
} }
@ -498,8 +573,8 @@ namespace gui {
case eGUI::LOOT_SELECT: case eGUI::LOOT_SELECT:
event(Event::LOOT_SELECT, data); event(Event::LOOT_SELECT, data);
break; break;
case eGUI::LOOT_PLACE: case eGUI::INV_SELECT:
event(Event::LOOT_PLACE, data); event(Event::INV_SELECT, data);
break; break;
case eGUI::LOOT: { case eGUI::LOOT: {
$map_ui.log(L"You picked up an item."); $map_ui.log(L"You picked up an item.");

@ -1,4 +1,5 @@
#pragma once #pragma once
#include "constants.hpp" #include "constants.hpp"
#include "levelmanager.hpp" #include "levelmanager.hpp"
#include "simplefsm.hpp" #include "simplefsm.hpp"
@ -15,16 +16,18 @@
namespace gui { namespace gui {
enum class State { enum class State {
START, START=0,
MOVING, MOVING=1,
IN_COMBAT, IN_COMBAT=2,
COMBAT_ROTATE, COMBAT_ROTATE=3,
ATTACKING, ATTACKING=4,
ROTATING, ROTATING=5,
NEXT_LEVEL, NEXT_LEVEL=6,
LOOTING, LOOTING=7,
IDLE, LOOT_GRAB=8,
END INV_GRAB=9,
IDLE=10,
END=11
}; };
class FSM : public DeadSimpleFSM<State, Event> { class FSM : public DeadSimpleFSM<State, Event> {
@ -65,6 +68,8 @@ namespace gui {
void COMBAT_ROTATE(Event ev); void COMBAT_ROTATE(Event ev);
void NEXT_LEVEL(Event ev); void NEXT_LEVEL(Event ev);
void LOOTING(Event ev, std::any data); void LOOTING(Event ev, std::any data);
void LOOT_GRAB(Event ev, std::any data);
void INV_GRAB(Event ev, std::any data);
void END(Event ev); void END(Event ev);
void try_move(int dir, bool strafe); void try_move(int dir, bool strafe);

@ -48,13 +48,19 @@ namespace gui {
} }
std::optional<DinkyECS::Entity> LootUI::select_slot(int slot_id) { std::optional<DinkyECS::Entity> LootUI::select_slot(int slot_id) {
if(size_t(slot_id) < contents.size()) { if(slot_id >= 0 && size_t(slot_id) < contents.size()) {
return contents.at(slot_id); return contents.at(slot_id);
} else { } else {
return std::nullopt; return std::nullopt;
} }
} }
shared_ptr<sf::Sprite> LootUI::grab_sprite(int slot_id) {
auto id = $gui.entity("item_", slot_id);
auto& sprite = $gui.get<guecs::Sprite>(id);
return sprite.sprite;
}
void LootUI::remove_slot(int slot_id) { void LootUI::remove_slot(int slot_id) {
dbc::check(size_t(slot_id) < contents.size(), dbc::check(size_t(slot_id) < contents.size(),
fmt::format("invalid slot id {} give, contents.size={}", fmt::format("invalid slot id {} give, contents.size={}",
@ -70,12 +76,8 @@ namespace gui {
for(size_t i = 0; i < INV_SLOTS; i++) { for(size_t i = 0; i < INV_SLOTS; i++) {
auto id = $gui.entity("item_", int(i)); auto id = $gui.entity("item_", int(i));
fmt::println("checking for sprite at {}", id);
if($gui.has<guecs::Sprite>(id)) { if($gui.has<guecs::Sprite>(id)) {
fmt::println("REMOVING SPRITE {}", id);
$gui.remove<guecs::Sprite>(id); $gui.remove<guecs::Sprite>(id);
} else {
fmt::println("nothing at {}", id);
} }
if(i < contents.size()) { if(i < contents.size()) {

@ -22,5 +22,6 @@ namespace gui {
bool mouse(float x, float y, bool hover); bool mouse(float x, float y, bool hover);
std::optional<DinkyECS::Entity> select_slot(int slot); std::optional<DinkyECS::Entity> select_slot(int slot);
void remove_slot(int slot_id); void remove_slot(int slot_id);
shared_ptr<sf::Sprite> grab_sprite(int slot_id);
}; };
} }

@ -43,7 +43,7 @@ namespace gui {
} else { } else {
$gui.set<Textual>(button, {guecs::to_wstring(name)}); $gui.set<Textual>(button, {guecs::to_wstring(name)});
$gui.set<Clickable>(button, { $gui.set<Clickable>(button, {
guecs::make_action(*$level.world, Events::GUI::LOOT_PLACE, {name}) guecs::make_action(*$level.world, Events::GUI::INV_SELECT, {name})
}); });
} }
} }

@ -35,6 +35,8 @@ int main(int argc, char* argv[]) {
if(main.in_state(gui::State::IDLE) if(main.in_state(gui::State::IDLE)
|| main.in_state(gui::State::NEXT_LEVEL) || main.in_state(gui::State::NEXT_LEVEL)
|| main.in_state(gui::State::LOOTING) || main.in_state(gui::State::LOOTING)
|| main.in_state(gui::State::LOOT_GRAB)
|| main.in_state(gui::State::INV_GRAB)
|| main.in_state(gui::State::IN_COMBAT)) || main.in_state(gui::State::IN_COMBAT))
{ {
if(main.autowalking) { if(main.autowalking) {

Loading…
Cancel
Save