From 00dd7c2b71472564fb61287fc7bbb716a426e5cf Mon Sep 17 00:00:00 2001 From: Alex Date: Sat, 12 Jun 2021 00:41:06 -0400 Subject: [PATCH] [Quest API] Add getcleannpcnamebyid(npc_id) to Perl/Lua. (#1383) * [Quest API] Add optional clean name parameter to getnpcnamebyid in Perl/Lua. - Allows Server Operators to grab the clean name without having to clean it up in their Perl/Lua. * Convert from a parameter to a method. * Add safer method. * Convert to proper type. --- common/database.cpp | 20 ++++++++++++++++++++ common/database.h | 1 + common/string_util.h | 13 +++++++++++++ zone/embparser_api.cpp | 17 ++++++++++++++++- zone/lua_general.cpp | 5 +++++ zone/questmgr.cpp | 8 ++++++++ zone/questmgr.h | 1 + 7 files changed, 64 insertions(+), 1 deletion(-) diff --git a/common/database.cpp b/common/database.cpp index 385f07c18..1290d289a 100644 --- a/common/database.cpp +++ b/common/database.cpp @@ -906,6 +906,26 @@ std::string Database::GetNPCNameByID(uint32 npc_id) { return res; } +std::string Database::GetCleanNPCNameByID(uint32 npc_id) { + std::string query = fmt::format("SELECT `name` FROM `npc_types` WHERE id = {}", npc_id); + auto results = QueryDatabase(query); + std::string res; + std::string mob_name; + + if (!results.Success()) { + return res; + } + + if (results.RowCount() == 0) { + return res; + } + + auto row = results.begin(); + mob_name = row[0]; + CleanMobName(mob_name.begin(), mob_name.end(), std::back_inserter(res)); + return res; +} + bool Database::LoadVariables() { auto results = QueryDatabase(StringFormat("SELECT varname, value, unix_timestamp() FROM variables where unix_timestamp(ts) >= %d", varcache.last_update)); diff --git a/common/database.h b/common/database.h index f6d93d5aa..1b3b736ae 100644 --- a/common/database.h +++ b/common/database.h @@ -140,6 +140,7 @@ public: void GetCharName(uint32 char_id, char* name); std::string GetCharNameByID(uint32 char_id); std::string GetNPCNameByID(uint32 npc_id); + std::string GetCleanNPCNameByID(uint32 npc_id); void LoginIP(uint32 AccountID, const char* LoginIP); /* Instancing */ diff --git a/common/string_util.h b/common/string_util.h index 5fd91281c..8c4a6878f 100644 --- a/common/string_util.h +++ b/common/string_util.h @@ -206,4 +206,17 @@ std::string convert2digit(int n, std::string suffix); std::string numberToWords(unsigned long long int n); std::string FormatName(const std::string& char_name); +template +auto CleanMobName(InputIterator first, InputIterator last, OutputIterator result) +{ + for (; first != last; ++first) { + if(*first == '_') { + *result = ' '; + } else if (isalpha(*first) || *first == '`') { + *result = *first; + } + } + return result; +} + #endif diff --git a/zone/embparser_api.cpp b/zone/embparser_api.cpp index 44c159b76..4c92c4969 100644 --- a/zone/embparser_api.cpp +++ b/zone/embparser_api.cpp @@ -3026,7 +3026,6 @@ XS(XS__getnpcnamebyid) { dXSTARG; uint32 npc_id = (int) SvIV(ST(0)); auto npc_name = quest_manager.getnpcnamebyid(npc_id); - sv_setpv(TARG, npc_name.c_str()); XSprePUSH; PUSHTARG; @@ -6760,6 +6759,21 @@ XS(XS__crosszoneaddldonwinbyexpeditionid) { XSRETURN_EMPTY; } +XS(XS__getcleannpcnamebyid); +XS(XS__getcleannpcnamebyid) { + dXSARGS; + if (items != 1) + Perl_croak(aTHX_ "Usage: quest::getcleannpcnamebyid(uint32 npc_id)"); + + dXSTARG; + uint32 npc_id = (uint32) SvUV(ST(0)); + auto npc_name = quest_manager.getcleannpcnamebyid(npc_id); + sv_setpv(TARG, npc_name.c_str()); + XSprePUSH; + PUSHTARG; + XSRETURN(1); +} + /* This is the callback perl will look for to setup the quest package's XSUBs @@ -6984,6 +6998,7 @@ EXTERN_C XS(boot_quest) { newXS(strcpy(buf, "getaaexpmodifierbycharid"), XS__getaaexpmodifierbycharid, file); newXS(strcpy(buf, "getcharidbyname"), XS__getcharidbyname, file); newXS(strcpy(buf, "getclassname"), XS__getclassname, file); + newXS(strcpy(buf, "getcleannpcnamebyid"), XS__getcleannpcnamebyid, file); newXS(strcpy(buf, "gethexcolorcode"), XS__gethexcolorcode, file); newXS(strcpy(buf, "getcurrencyid"), XS__getcurrencyid, file); newXS(strcpy(buf, "getexpmodifierbycharid"), XS__getexpmodifierbycharid, file); diff --git a/zone/lua_general.cpp b/zone/lua_general.cpp index 2e26b460f..046b8c7d6 100644 --- a/zone/lua_general.cpp +++ b/zone/lua_general.cpp @@ -2455,6 +2455,10 @@ void lua_cross_zone_add_ldon_win_by_expedition_id(uint32 expedition_id, uint32 t quest_manager.CrossZoneLDoNUpdate(update_type, update_subtype, expedition_id, theme_id); } +std::string lua_get_clean_npc_name_by_id(uint32 npc_id) { + return quest_manager.getcleannpcnamebyid(npc_id); +} + #define LuaCreateNPCParse(name, c_type, default_value) do { \ cur = table[#name]; \ if(luabind::type(cur) != LUA_TNIL) { \ @@ -2796,6 +2800,7 @@ luabind::scope lua_register_general() { luabind::def("get_char_id_by_name", (uint32(*)(const char*))&lua_get_char_id_by_name), luabind::def("get_class_name", (std::string(*)(uint8))&lua_get_class_name), luabind::def("get_class_name", (std::string(*)(uint8,uint8))&lua_get_class_name), + luabind::def("get_clean_npc_name_by_id", &lua_get_clean_npc_name_by_id), luabind::def("get_currency_id", &lua_get_currency_id), luabind::def("get_currency_item_id", &lua_get_currency_item_id), luabind::def("get_guild_name_by_id", &lua_get_guild_name_by_id), diff --git a/zone/questmgr.cpp b/zone/questmgr.cpp index 09046f775..640d5f4f6 100644 --- a/zone/questmgr.cpp +++ b/zone/questmgr.cpp @@ -2789,6 +2789,14 @@ std::string QuestManager::getnpcnamebyid(uint32 npc_id) { return res; } +std::string QuestManager::getcleannpcnamebyid(uint32 npc_id) { + std::string res; + if (npc_id > 0) { + res = database.GetCleanNPCNameByID(npc_id); + } + return res; +} + uint16 QuestManager::CreateInstance(const char *zone, int16 version, uint32 duration) { QuestManagerCurrentQuestVars(); diff --git a/zone/questmgr.h b/zone/questmgr.h index 815a10e35..999e128e6 100644 --- a/zone/questmgr.h +++ b/zone/questmgr.h @@ -274,6 +274,7 @@ public: int getguildidbycharid(uint32 char_id); int getgroupidbycharid(uint32 char_id); std::string getnpcnamebyid(uint32 npc_id); + std::string getcleannpcnamebyid(uint32 npc_id); int getraididbycharid(uint32 char_id); void SetRunning(bool val); bool IsRunning();