From e695e69b2b92dcfe592a3bc9fcb9bc480b88d9cf Mon Sep 17 00:00:00 2001 From: Nat Quayle Nelson Date: Wed, 11 Jun 2025 20:37:12 -0500 Subject: [PATCH] undo/redo edit placed creatures --- src/scenario/monster.cpp | 18 ++++++++++++++++++ src/scenario/monster.hpp | 4 ++++ src/scenedit/scen.actions.cpp | 8 +++++++- src/scenedit/scen.undo.cpp | 10 ++++++++++ src/scenedit/scen.undo.hpp | 13 +++++++++++++ 5 files changed, 52 insertions(+), 1 deletion(-) diff --git a/src/scenario/monster.cpp b/src/scenario/monster.cpp index bdeb0885..a2cb1041 100644 --- a/src/scenario/monster.cpp +++ b/src/scenario/monster.cpp @@ -1034,4 +1034,22 @@ bool cMonster::operator==(const cMonster& other) { CHECK_EQ(other, ambient_sound); CHECK_EQ(other, see_spec); return true; +} + +bool cTownperson::operator==(const cTownperson& other) { + CHECK_EQ(other, number); + CHECK_EQ(other, start_attitude); + CHECK_EQ(other, start_loc); + CHECK_EQ(other, mobility); + CHECK_EQ(other, time_flag); + CHECK_EQ(other, spec1); + CHECK_EQ(other, spec2); + CHECK_EQ(other, spec_enc_code); + CHECK_EQ(other, time_code); + CHECK_EQ(other, monster_time); + CHECK_EQ(other, personality); + CHECK_EQ(other, special_on_kill); + CHECK_EQ(other, special_on_talk); + CHECK_EQ(other, facial_pic); + return true; } \ No newline at end of file diff --git a/src/scenario/monster.hpp b/src/scenario/monster.hpp index 7ae88ab2..f1db1bea 100644 --- a/src/scenario/monster.hpp +++ b/src/scenario/monster.hpp @@ -98,6 +98,10 @@ public: short special_on_kill, special_on_talk; pic_num_t facial_pic; + // For detecting actual changes to town monsters in the editor + bool operator==(const cTownperson& other); + bool operator!=(const cTownperson& other) { return !(*this == other); } + void import_legacy(legacy::creature_start_type old); cTownperson(); cTownperson(location loc, mon_num_t num, const cMonster& monst); diff --git a/src/scenedit/scen.actions.cpp b/src/scenedit/scen.actions.cpp index 55d1d94a..ab3c34a8 100644 --- a/src/scenedit/scen.actions.cpp +++ b/src/scenedit/scen.actions.cpp @@ -1015,10 +1015,16 @@ static bool handle_terrain_action(location the_point, bool ctrl_hit) { break; } case MODE_EDIT_CREATURE: //edit monst - for(short x = 0; x < town->creatures.size(); x++) + for(short x = 0; x < town->creatures.size(); x++){ if(monst_on_space(spot_hit,x)) { + cTownperson old_creature = town->creatures[x]; edit_placed_monst(x); + if(town->creatures[x] != old_creature){ + undo_list.add(action_ptr(new aEditPlacedCreature(x, old_creature, town->creatures[x]))); + update_edit_menu(); + } } + } overall_mode = MODE_DRAWING; break; case MODE_EDIT_SPECIAL: //make special diff --git a/src/scenedit/scen.undo.cpp b/src/scenedit/scen.undo.cpp index 305d5cb9..dea5a3b5 100644 --- a/src/scenedit/scen.undo.cpp +++ b/src/scenedit/scen.undo.cpp @@ -319,4 +319,14 @@ bool aEditPlacedItem::undo_me() { bool aEditPlacedItem::redo_me() { town->preset_items[which] = new_item; return true; +} + +bool aEditPlacedCreature::undo_me() { + town->creatures[which] = old_creature; + return true; +} + +bool aEditPlacedCreature::redo_me() { + town->creatures[which] = new_creature; + return true; } \ No newline at end of file diff --git a/src/scenedit/scen.undo.hpp b/src/scenedit/scen.undo.hpp index 49ffddff..ce9543e0 100644 --- a/src/scenedit/scen.undo.hpp +++ b/src/scenedit/scen.undo.hpp @@ -108,6 +108,19 @@ public: which(which), old_item(old_item), new_item(new_item) {} }; +/// Action which edits a creature in a town +class aEditPlacedCreature : public cTerrainAction { + size_t which; + cTownperson old_creature; + cTownperson new_creature; + bool undo_me() override; + bool redo_me() override; +public: + aEditPlacedCreature(size_t which, cTownperson old_creature, cTownperson new_creature) : + cTerrainAction("Edit Placed Creature", new_creature.start_loc), + which(which), old_creature(old_creature), new_creature(new_creature) {} +}; + /// Action which places or erases creature(s) in a town class aPlaceEraseCreature : public cTerrainAction { bool placed;