diff --git a/rsrc/dialogs/edit-monster-abils.xml b/rsrc/dialogs/edit-monster-abils.xml
index fc43356b..a1e0d517 100644
--- a/rsrc/dialogs/edit-monster-abils.xml
+++ b/rsrc/dialogs/edit-monster-abils.xml
@@ -37,6 +37,7 @@
Special treasure:
Item to drop when killed:
+
Chance of dropping: (0-100)
diff --git a/src/dialogxml/dialogs/strchoice.cpp b/src/dialogxml/dialogs/strchoice.cpp
index f84bbe1f..be546087 100644
--- a/src/dialogxml/dialogs/strchoice.cpp
+++ b/src/dialogxml/dialogs/strchoice.cpp
@@ -15,9 +15,11 @@
#include
#include "dialogxml/widgets/field.hpp"
+#include "dialogxml/dialogs/strdlog.hpp"
#include "fileio/resmgr/res_dialog.hpp"
#include "sounds.hpp"
#include "gfx/render_shapes.hpp"
+#include "tools/cursors.hpp"
const sf::Color HILITE_COLOUR = Colours::LIGHT_GREEN;
@@ -310,3 +312,71 @@ void cStringChoice::savePage() {
strings[string_idx] = dlg[text_id].getText();
}
}
+
+static bool get_num_response_event_filter(cDialog& me, std::string, eKeyMod) {
+ if(me.toast(true)){
+ me.setResult(me["number"].getTextAsNum());
+ }
+ return true;
+}
+
+short get_num_response(short min, short max, std::string prompt, std::vector choice_names, boost::optional cancel_value, short initial_value, std::string extra_led, bool* led_output) {
+ std::ostringstream sout;
+ sout << prompt;
+
+ set_cursor(sword_curs);
+
+ cDialog numPanel(*ResMgr::dialogs.get("get-num"));
+ numPanel.attachClickHandlers(get_num_response_event_filter, {"okay"});
+
+ if(extra_led.empty()){
+ numPanel["extra-led"].hide();
+ }else{
+ numPanel["extra-led"].setText(extra_led);
+ numPanel["extra-led"].recalcRect();
+ if(led_output != nullptr)
+ dynamic_cast(numPanel["extra-led"]).setState(*led_output ? led_red : led_off);
+ }
+
+ sout << " (" << min << '-' << max << ')';
+ numPanel["prompt"].setText(sout.str());
+ numPanel["number"].setTextToNum(initial_value);
+ if(!choice_names.empty()){
+ numPanel["choose"].attachClickHandler([&choice_names, &prompt](cDialog& me,std::string,eKeyMod) -> bool {
+ cStringChoice choose_dlg(choice_names, prompt, &me);
+ me["number"].setTextToNum(choose_dlg.show(me["number"].getTextAsNum()));
+ return true;
+ });
+ }else{
+ numPanel["choose"].hide();
+ }
+ if(min < max)
+ numPanel["number"].attachFocusHandler([min,max](cDialog& me,std::string,bool losing) -> bool {
+ if(!losing) return true;
+ int val = me["number"].getTextAsNum();
+ if(val < min || val > max) {
+ showError("Number out of range!");
+ return false;
+ }
+ return true;
+ });
+
+ bool cancel_clicked = false;
+ if(cancel_value){
+ numPanel["cancel"].attachClickHandler([cancel_value, &cancel_clicked](cDialog& me,std::string,eKeyMod) -> bool {
+ cancel_clicked = true;
+ me.setResult(*cancel_value);
+ me.toast(false);
+ return true;
+ });
+ }else{
+ numPanel["cancel"].hide();
+ }
+
+ numPanel.run();
+ if(!cancel_clicked && led_output != nullptr){
+ *led_output = dynamic_cast(numPanel["extra-led"]).getState() == led_red;
+ }
+
+ return numPanel.getResult();
+}
\ No newline at end of file
diff --git a/src/dialogxml/dialogs/strchoice.hpp b/src/dialogxml/dialogs/strchoice.hpp
index 3d48f0f0..f76d7769 100644
--- a/src/dialogxml/dialogs/strchoice.hpp
+++ b/src/dialogxml/dialogs/strchoice.hpp
@@ -12,6 +12,7 @@
#include
#include
#include
+#include
#include "dialog.hpp"
#include "dialogxml/widgets/ledgroup.hpp"
@@ -78,4 +79,9 @@ public:
std::vector getStrings() const { return strings; }
};
+// Prompt the player/designer for a number, which might be an index in a given list of strings.
+// Specify cancel_value to show a cancel button, which will return the given value (for example, -1)
+// Specify extra_led and led_output to show a labeled LED which will assign led_output with its status unless the dialog is canceled
+short get_num_response(short min, short max, std::string prompt, std::vector choice_names = {}, boost::optional cancel_value = boost::none, short initial_value = 0, std::string extra_led = "", bool* led_output = nullptr);
+
#endif
diff --git a/src/game/boe.items.cpp b/src/game/boe.items.cpp
index 64e621ce..4e9cc41c 100644
--- a/src/game/boe.items.cpp
+++ b/src/game/boe.items.cpp
@@ -854,67 +854,6 @@ std::string get_text_response(std::string prompt, pic_num_t pic) {
return result;
}
-short get_num_response(short min, short max, std::string prompt, std::vector choice_names, boost::optional cancel_value, short initial_value, std::string extra_led, bool* led_output) {
- std::ostringstream sout;
- sout << prompt;
-
- set_cursor(sword_curs);
-
- cDialog numPanel(*ResMgr::dialogs.get("get-num"));
- numPanel.attachClickHandlers(get_num_of_items_event_filter, {"okay"});
-
- if(extra_led.empty()){
- numPanel["extra-led"].hide();
- }else{
- numPanel["extra-led"].setText(extra_led);
- numPanel["extra-led"].recalcRect();
- if(led_output != nullptr)
- dynamic_cast(numPanel["extra-led"]).setState(*led_output ? led_red : led_off);
- }
-
- sout << " (" << min << '-' << max << ')';
- numPanel["prompt"].setText(sout.str());
- numPanel["number"].setTextToNum(initial_value);
- if(!choice_names.empty()){
- numPanel["choose"].attachClickHandler([&choice_names, &prompt](cDialog& me,std::string,eKeyMod) -> bool {
- cStringChoice choose_dlg(choice_names, prompt, &me);
- me["number"].setTextToNum(choose_dlg.show(me["number"].getTextAsNum()));
- return true;
- });
- }else{
- numPanel["choose"].hide();
- }
- if(min < max)
- numPanel["number"].attachFocusHandler([min,max](cDialog& me,std::string,bool losing) -> bool {
- if(!losing) return true;
- int val = me["number"].getTextAsNum();
- if(val < min || val > max) {
- showError("Number out of range!");
- return false;
- }
- return true;
- });
-
- bool cancel_clicked = false;
- if(cancel_value){
- numPanel["cancel"].attachClickHandler([cancel_value, &cancel_clicked](cDialog& me,std::string,eKeyMod) -> bool {
- cancel_clicked = true;
- me.setResult(*cancel_value);
- me.toast(false);
- return true;
- });
- }else{
- numPanel["cancel"].hide();
- }
-
- numPanel.run();
- if(!cancel_clicked && led_output != nullptr){
- *led_output = dynamic_cast(numPanel["extra-led"]).getState() == led_red;
- }
-
- return numPanel.getResult();
-}
-
static bool select_pc_event_filter (cDialog& me, std::string item_hit, eKeyMod) {
me.toast(true);
if(item_hit == "pick-all"){
diff --git a/src/game/boe.items.hpp b/src/game/boe.items.hpp
index f7870fe0..6a727512 100644
--- a/src/game/boe.items.hpp
+++ b/src/game/boe.items.hpp
@@ -35,10 +35,6 @@ void reset_item_max();
short item_val(cItem item);
void place_treasure(location where,short level,short loot,short mode);
std::string get_text_response(std::string prompt = "", pic_num_t pic = 16);
-// Prompt the player for a number, which might be an index in a given list of strings.
-// Specify cancel_value to show a cancel button, which will return the given value (for example, -1)
-// Specify extra_led and led_output to show a labeled LED which will assign led_output with its status unless the dialog is canceled
-short get_num_response(short min, short max, std::string prompt, std::vector choice_names = {}, boost::optional cancel_value = boost::none, short initial_value = 0, std::string extra_led = "", bool* led_output = nullptr);
enum class eSelectPC {
ANY,
diff --git a/src/game/boe.specials.cpp b/src/game/boe.specials.cpp
index 70857a80..f40b905d 100644
--- a/src/game/boe.specials.cpp
+++ b/src/game/boe.specials.cpp
@@ -28,6 +28,7 @@
#include "dialogxml/dialogs/strdlog.hpp"
#include "dialogxml/dialogs/choicedlog.hpp"
#include "dialogxml/dialogs/3choice.hpp"
+#include "dialogxml/dialogs/strchoice.hpp"
#include "fileio/fileio.hpp"
#include
#include "spell.hpp"
diff --git a/src/scenedit/scen.core.cpp b/src/scenedit/scen.core.cpp
index 69b51c6f..5a714051 100644
--- a/src/scenedit/scen.core.cpp
+++ b/src/scenedit/scen.core.cpp
@@ -1414,6 +1414,17 @@ cMonster edit_monst_abil(cMonster initial,short which,cDialog& parent) {
cDialog monst_dlg(*ResMgr::dialogs.get("edit-monster-abils"),&parent);
monst_dlg["loot-item"].attachFocusHandler(std::bind(check_range_msg, _1, _2, _3, -1, 399, "Item To Drop", "-1 for no item"));
+
+ monst_dlg["pick-item"].attachClickHandler([](cDialog& me, std::string, eKeyMod) -> bool {
+ std::vector item_names;
+ for(cItem& item : scenario.scen_items){
+ item_names.push_back(item.full_name);
+ }
+ short current = me["loot-item"].getTextAsNum();
+ short i = get_num_response(0, scenario.scen_items.size()-1, "Which item?", item_names, current, current);
+ me["loot-item"].setTextToNum(i);
+ return true;
+ });
monst_dlg["loot-chance"].attachFocusHandler(std::bind(check_range_msg, _1, _2, _3, -1, 100, "Dropping Chance", "-1 for no item"));
monst_dlg.attachClickHandlers(std::bind(edit_monst_abil_detail, _1, _2, std::ref(initial)), {"abil-edit1", "abil-edit2", "abil-edit3", "abil-edit4"});
monst_dlg.attachClickHandlers(std::bind(edit_monst_abil_event_filter, _1, _2, std::ref(initial)), {"okay", "cancel", "abil-up", "abil-down", "edit-see", "pick-snd"});