From 1c6a76246f14c9738d22fac2e62642fed5d9fd52 Mon Sep 17 00:00:00 2001 From: Akkadius Date: Sun, 11 Aug 2019 02:40:23 -0500 Subject: [PATCH] Added bulk edit command #npceditmass --- changelog.txt | 3 +++ common/string_util.cpp | 22 +++++++++++----- common/string_util.h | 2 +- zone/command.cpp | 59 +++++++++++++++++++++++++++++++++++++++--- 4 files changed, 76 insertions(+), 10 deletions(-) diff --git a/changelog.txt b/changelog.txt index 3f69bf570..43451a7ea 100644 --- a/changelog.txt +++ b/changelog.txt @@ -1,5 +1,8 @@ EQEMu Changelog (Started on Sept 24, 2003 15:50) ------------------------------------------------------- +== 8/11/2019 == +Akkadius: Added bulk edit command #npceditmass + == 8/6/2019 == Akkadius: Optimizations to movement updates to eliminate ghosting possibilities in larger zones diff --git a/common/string_util.cpp b/common/string_util.cpp index b12811159..ec53663cc 100644 --- a/common/string_util.cpp +++ b/common/string_util.cpp @@ -27,6 +27,8 @@ #else #include #include +#include + #endif #ifndef va_copy @@ -119,19 +121,27 @@ std::vector SplitString(const std::string &str, char delim) { while(std::getline(ss, item, delim)) { ret.push_back(item); } - + return ret; } -static std::string implode(char *sep, std::vector src) +std::string implode(std::string glue, std::vector src) { - std::ostringstream output; + if (src.empty()) { + return {}; + } + + std::ostringstream output; std::vector::iterator src_iter; - for (src_iter = src.begin(); src_iter != src.end(); src_iter++) - output << *src_iter << sep; + for (src_iter = src.begin(); src_iter != src.end(); src_iter++) { + output << *src_iter << glue; + } - return output.str(); + std::string final_output = output.str(); + final_output.resize (output.str().size () - glue.size()); + + return final_output; } std::string EscapeString(const std::string &s) { diff --git a/common/string_util.h b/common/string_util.h index cf1dbc761..23a8af05b 100644 --- a/common/string_util.h +++ b/common/string_util.h @@ -30,7 +30,7 @@ const std::string ucfirst(std::string s); std::vector split(std::string str_to_split, char delimiter); const std::string StringFormat(const char* format, ...); const std::string vStringFormat(const char* format, va_list args); -static std::string implode(char *sep, std::vector src); +std::string implode(std::string glue, std::vector src); std::vector SplitString(const std::string &s, char delim); std::string EscapeString(const char *src, size_t sz); std::string EscapeString(const std::string &s); diff --git a/zone/command.cpp b/zone/command.cpp index 5ee0f1b1c..725f40ea5 100755 --- a/zone/command.cpp +++ b/zone/command.cpp @@ -7337,6 +7337,15 @@ void command_npceditmass(Client *c, const Seperator *sep) zone->GetInstanceVersion() ); + std::string status = "(Searching)"; + + if (strcasecmp(sep->arg[5], "apply") == 0) { + status = "(Applying)"; + } + + std::vector npc_ids; + + int found_count = 0; results = database.QueryDatabase(query); for (auto row = results.begin(); row != results.end(); ++row) { @@ -7352,16 +7361,60 @@ void command_npceditmass(Client *c, const Seperator *sep) c->Message( 15, fmt::format( - "NPC ({0}) [{1}] ({2}) [{3}] Current ({4}) [{5}] New [{6}]", + "NPC ({0}) [{1}] ({2}) [{3}] Current ({4}) [{5}] New [{6}] {7}", npc_id, npc_name, search_column, search_column_value, change_column, change_column_current_value, - change_value + change_value, + status ).c_str() ); + + npc_ids.push_back(npc_id); + + found_count++; + } + + std::string saylink = fmt::format( + "#npceditmass {} {} {} {} apply", + search_column, + search_value, + change_column, + change_value + ); + + if (strcasecmp(sep->arg[5], "apply") == 0) { + std::string npc_ids_string = implode(",", npc_ids); + if (npc_ids_string.empty()) { + c->Message(Chat::Red, "Error: Ran into an unknown error compiling NPC IDs"); + return; + } + + database.QueryDatabase( + fmt::format( + "UPDATE `npc_types` SET {} = {} WHERE id IN ({})", + change_column, + change_value, + npc_ids_string + ) + ); + + c->Message(Chat::Yellow, "Changes applied to (%i) NPC's", found_count); + zone->Repop(); + } + else { + c->Message(Chat::Yellow, "Found (%i) NPC's that match this search...", found_count); + + if (found_count > 0) { + c->Message( + Chat::Yellow, "To apply these changes, click <%s> or type [%s]", + EQEmu::SayLinkEngine::GenerateQuestSaylink(saylink, false, "Apply").c_str(), + saylink.c_str() + ); + } } } @@ -12232,7 +12285,7 @@ void command_scale(Client *c, const Seperator *sep) c->Message(Chat::Yellow, "Found (%i) NPC's that match this search...", found_count); c->Message( - 15, "To apply these changes, click <%s> or type %s", + Chat::Yellow, "To apply these changes, click <%s> or type %s", EQEmu::SayLinkEngine::GenerateQuestSaylink(saylink, false, "Apply").c_str(), saylink.c_str() );