diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/server/game/Chat/ChatCommands/ChatCommandArgs.cpp | 33 | ||||
-rw-r--r-- | src/server/game/Chat/ChatCommands/ChatCommandArgs.h | 8 | ||||
-rw-r--r-- | src/server/game/Chat/ChatCommands/ChatCommandHelpers.h | 76 | ||||
-rw-r--r-- | src/server/game/Chat/ChatCommands/ChatCommandTags.h | 236 | ||||
-rw-r--r-- | src/server/game/Chat/Hyperlinks.h | 705 | ||||
-rw-r--r-- | src/server/scripts/Commands/cs_debug.cpp | 2 |
6 files changed, 530 insertions, 530 deletions
diff --git a/src/server/game/Chat/ChatCommands/ChatCommandArgs.cpp b/src/server/game/Chat/ChatCommands/ChatCommandArgs.cpp index 4c1b90ed4e9..45c3011241a 100644 --- a/src/server/game/Chat/ChatCommands/ChatCommandArgs.cpp +++ b/src/server/game/Chat/ChatCommands/ChatCommandArgs.cpp @@ -31,9 +31,9 @@ struct AchievementVisitor }; char const* Trinity::ChatCommands::ArgInfo<AchievementEntry const*>::TryConsume(AchievementEntry const*& data, char const* args) { - Variant <Hyperlink<achievement>, uint32> val; + Variant<Hyperlink<achievement>, uint32> val; if ((args = CommandArgsConsumerSingle<decltype(val)>::TryConsumeTo(val, args))) - data = boost::apply_visitor(AchievementVisitor(), val); + data = val.visit(AchievementVisitor()); return args; } @@ -45,9 +45,9 @@ struct CurrencyTypesVisitor }; char const* Trinity::ChatCommands::ArgInfo<CurrencyTypesEntry const*>::TryConsume(CurrencyTypesEntry const*& data, char const* args) { - Variant <Hyperlink<currency>, uint32> val; + Variant<Hyperlink<currency>, uint32> val; if ((args = CommandArgsConsumerSingle<decltype(val)>::TryConsumeTo(val, args))) - data = boost::apply_visitor(CurrencyTypesVisitor(), val); + data = val.visit(CurrencyTypesVisitor()); return args; } @@ -61,7 +61,7 @@ char const* Trinity::ChatCommands::ArgInfo<GameTele const*>::TryConsume(GameTele { Variant<Hyperlink<tele>, std::string> val; if ((args = CommandArgsConsumerSingle<decltype(val)>::TryConsumeTo(val, args))) - data = boost::apply_visitor(GameTeleVisitor(), val); + data = val.visit(GameTeleVisitor()); return args; } @@ -75,21 +75,22 @@ char const* Trinity::ChatCommands::ArgInfo<SpellInfo const*>::TryConsume(SpellIn { Variant<Hyperlink<spell>, uint32> val; if ((args = CommandArgsConsumerSingle<decltype(val)>::TryConsumeTo(val, args))) - data = boost::apply_visitor(SpellInfoVisitor(), val); + data = val.visit(SpellInfoVisitor()); return args; } -struct BoolVisitor -{ - using value_type = bool; - value_type operator()(uint32 i) const { return !!i; } - value_type operator()(ExactSequence<'o', 'n'>) const { return true; } - value_type operator()(ExactSequence<'o', 'f', 'f'>) const { return false; } -}; char const* Trinity::ChatCommands::ArgInfo<bool>::TryConsume(bool& data, char const* args) { - Variant<uint32, ExactSequence<'o', 'n'>, ExactSequence<'o', 'f', 'f'>> val; - if ((args = CommandArgsConsumerSingle<decltype(val)>::TryConsumeTo(val, args))) - data = boost::apply_visitor(BoolVisitor(), val); + std::string val; + if ((args = CommandArgsConsumerSingle<std::string>::TryConsumeTo(val, args))) + { + strToLower(val); + if (val == "on" || val == "yes" || val == "true" || val == "1" || val == "y") + data = true; + else if (val == "off" || val == "no" || val == "false" || val == "0" || val == "n") + data = false; + else + return nullptr; + } return args; } diff --git a/src/server/game/Chat/ChatCommands/ChatCommandArgs.h b/src/server/game/Chat/ChatCommands/ChatCommandArgs.h index fcce689c258..e32d6918a79 100644 --- a/src/server/game/Chat/ChatCommands/ChatCommandArgs.h +++ b/src/server/game/Chat/ChatCommands/ChatCommandArgs.h @@ -50,7 +50,7 @@ struct ArgInfo<T, std::enable_if_t<std::is_integral_v<T> && std::is_signed_v<T>> static char const* TryConsume(T& val, char const* args) { char const* next = args; - std::string token(args, tokenize(next)); + std::string token(args, Trinity::Impl::ChatCommands::tokenize(next)); try { size_t processedChars = 0; @@ -70,7 +70,7 @@ struct ArgInfo<T, std::enable_if_t<std::is_integral_v<T> && std::is_unsigned_v<T static char const* TryConsume(T& val, char const* args) { char const* next = args; - std::string token(args, tokenize(next)); + std::string token(args, Trinity::Impl::ChatCommands::tokenize(next)); try { size_t processedChars = 0; @@ -90,7 +90,7 @@ struct ArgInfo<T, std::enable_if_t<std::is_floating_point_v<T>>> static char const* TryConsume(T& val, char const* args) { char const* next = args; - std::string token(args, tokenize(next)); + std::string token(args, Trinity::Impl::ChatCommands::tokenize(next)); try { size_t processedChars = 0; @@ -110,7 +110,7 @@ struct ArgInfo<std::string, void> static char const* TryConsume(std::string& val, char const* args) { char const* next = args; - if (size_t len = tokenize(next)) + if (size_t len = Trinity::Impl::ChatCommands::tokenize(next)) { val.assign(args, len); return next; diff --git a/src/server/game/Chat/ChatCommands/ChatCommandHelpers.h b/src/server/game/Chat/ChatCommands/ChatCommandHelpers.h index ff9b5a3b8fc..e22823e5d35 100644 --- a/src/server/game/Chat/ChatCommands/ChatCommandHelpers.h +++ b/src/server/game/Chat/ChatCommands/ChatCommandHelpers.h @@ -20,58 +20,50 @@ #include <type_traits> -namespace Trinity -{ -namespace ChatCommands +namespace Trinity::ChatCommands { + static constexpr char COMMAND_DELIMITER = ' '; -static constexpr char COMMAND_DELIMITER = ' '; + template <typename T, typename = void> + struct tag_base + { + using type = T; + }; -/***************** HELPERS *************************\ -|* These really aren't for outside use... *| -\***************************************************/ -inline std::size_t tokenize(char const*& end) -{ - std::size_t len = 0; - for (; *end && *end != COMMAND_DELIMITER; ++end, ++len); - for (; *end && *end == COMMAND_DELIMITER; ++end); - return len; + template <typename T> + using tag_base_t = typename tag_base<T>::type; } -template <typename T, typename = void> -struct tag_base +namespace Trinity::Impl::ChatCommands { - using type = T; -}; + /***************** HELPERS *************************\ + |* These really aren't for outside use... *| + \***************************************************/ + inline std::size_t tokenize(char const*& end) + { + std::size_t len = 0; + for (; *end && *end != Trinity::ChatCommands::COMMAND_DELIMITER; ++end, ++len); + for (; *end && *end == Trinity::ChatCommands::COMMAND_DELIMITER; ++end); + return len; + } -template <typename T> -using tag_base_t = typename tag_base<T>::type; + template <typename T, typename... Ts> + struct are_all_assignable + { + static constexpr bool value = (std::is_assignable_v<T&, Ts> && ...); + }; -template <typename...> -struct are_all_assignable -{ - static constexpr bool value = true; -}; - -template <typename T1, typename T2, typename... Ts> -struct are_all_assignable<T1, T2, Ts...> -{ - static constexpr bool value = std::is_assignable_v<T1&, T2> && are_all_assignable<T1, Ts...>::value; -}; + template <std::size_t index, typename T1, typename... Ts> + struct get_nth : get_nth<index-1, Ts...> { }; -template <std::size_t index, typename T1, typename... Ts> -struct get_nth : get_nth<index-1, Ts...> { }; + template <typename T1, typename... Ts> + struct get_nth<0, T1, Ts...> + { + using type = T1; + }; -template <typename T1, typename... Ts> -struct get_nth<0, T1, Ts...> -{ - using type = T1; -}; - -template <std::size_t index, typename... Ts> -using get_nth_t = typename get_nth<index, Ts...>::type; - -} + template <std::size_t index, typename... Ts> + using get_nth_t = typename get_nth<index, Ts...>::type; } #endif diff --git a/src/server/game/Chat/ChatCommands/ChatCommandTags.h b/src/server/game/Chat/ChatCommands/ChatCommandTags.h index feffc25aa25..51171d29b2c 100644 --- a/src/server/game/Chat/ChatCommands/ChatCommandTags.h +++ b/src/server/game/Chat/ChatCommands/ChatCommandTags.h @@ -22,150 +22,160 @@ #include "ChatCommandHelpers.h" #include "Hyperlinks.h" #include "Optional.h" -#include <boost/variant.hpp> #include <cmath> #include <cstring> +#include <iostream> #include <string> #include <tuple> #include <type_traits> #include <utility> +#include <variant> -namespace Trinity +namespace Trinity::ChatCommands { -namespace ChatCommands -{ -/************************** CONTAINER TAGS **********************************************\ -|* Simple holder classes to differentiate between extraction methods *| -|* Should inherit from ContainerTag for template identification *| -|* Must implement the following: *| -|* - TryConsume: char const* -> char const* *| -|* returns nullptr if no match, otherwise pointer to first character of next token *| -|* - typedef value_type of type that is contained within the tag *| -|* - cast operator to value_type *| -|* *| -\****************************************************************************************/ -struct ContainerTag {}; -template <typename T> -struct tag_base<T, std::enable_if_t<std::is_base_of_v<ContainerTag, T>>> -{ - using type = typename T::value_type; -}; - -template <char c1, char... chars> -struct ExactSequence : public ContainerTag -{ - using value_type = void; - - static constexpr bool isSingleChar = !sizeof...(chars); - - template <bool C = isSingleChar> - static typename std::enable_if_t<!C, char const*> _TryConsume(char const* pos) + /************************** CONTAINER TAGS **********************************************\ + |* Simple holder classes to differentiate between extraction methods *| + |* Should inherit from ContainerTag for template identification *| + |* Must implement the following: *| + |* - TryConsume: char const* -> char const* *| + |* returns nullptr if no match, otherwise pointer to first character of next token *| + |* - typedef value_type of type that is contained within the tag *| + |* - cast operator to value_type *| + |* *| + \****************************************************************************************/ + struct ContainerTag {}; + template <typename T> + struct tag_base<T, std::enable_if_t<std::is_base_of_v<ContainerTag, T>>> { - if (*(pos++) == c1) - return ExactSequence<chars...>::_TryConsume(pos); - else - return nullptr; - } + using type = typename T::value_type; + }; - template <bool C = isSingleChar> - static typename std::enable_if_t<C, char const*> _TryConsume(char const* pos) + template <char c1, char... chars> + struct ExactSequence : public ContainerTag { - if (*(pos++) != c1) - return nullptr; - // if more of string is left, tokenize should return 0 (otherwise we didn't reach end of token yet) - return *pos && tokenize(pos) ? nullptr : pos; - } - - char const* TryConsume(char const* pos) const { return ExactSequence::_TryConsume(pos); } -}; - -template <typename linktag> -struct Hyperlink : public ContainerTag -{ - typedef typename linktag::value_type value_type; - typedef advstd::remove_cvref_t<value_type> storage_type; - - public: - operator value_type() const { return val; } - value_type operator*() const { return val; } - storage_type const* operator->() const { return &val; } + using value_type = void; - char const* TryConsume(char const* pos) + static char const* _TryConsume(char const* pos) { - Trinity::Hyperlinks::HyperlinkInfo info = Trinity::Hyperlinks::ParseHyperlink(pos); - // invalid hyperlinks cannot be consumed - if (!info) - return nullptr; - - // check if we got the right tag - if (info.tag.second != strlen(linktag::tag())) - return nullptr; - if (strncmp(info.tag.first, linktag::tag(), strlen(linktag::tag())) != 0) + if (*(pos++) == c1) + { + if constexpr (sizeof...(chars) > 0) + return ExactSequence<chars...>::_TryConsume(pos); + else if (Trinity::Impl::ChatCommands::tokenize(pos)) /* we did not consume the entire token */ + return nullptr; + else + return pos; + } + else return nullptr; - - // store value - if (!linktag::StoreTo(val, info.data.first, info.data.second)) - return nullptr; - - // finally, skip to end of token - pos = info.next; - tokenize(pos); - - // return final pos - return pos; } - private: - storage_type val; -}; + char const* TryConsume(char const* pos) const { return ExactSequence::_TryConsume(pos); } + }; -// pull in link tags for user convenience -using namespace ::Trinity::Hyperlinks::LinkTags; + template <typename linktag> + struct Hyperlink : public ContainerTag + { + using value_type = typename linktag::value_type; + using storage_type = advstd::remove_cvref_t<value_type>; + + public: + operator value_type() const { return val; } + value_type operator*() const { return val; } + storage_type const* operator->() const { return &val; } + + char const* TryConsume(char const* pos) + { + Trinity::Hyperlinks::HyperlinkInfo info = Trinity::Hyperlinks::ParseHyperlink(pos); + // invalid hyperlinks cannot be consumed + if (!info) + return nullptr; + + // check if we got the right tag + if (info.tag.second != strlen(linktag::tag())) + return nullptr; + if (strncmp(info.tag.first, linktag::tag(), strlen(linktag::tag())) != 0) + return nullptr; + + // store value + if (!linktag::StoreTo(val, info.data.first, info.data.second)) + return nullptr; + + // finally, skip to end of token + pos = info.next; + Trinity::Impl::ChatCommands::tokenize(pos); + + // return final pos + return pos; + } + + private: + storage_type val; + }; + + // pull in link tags for user convenience + using namespace ::Trinity::Hyperlinks::LinkTags; +} /************************** VARIANT TAG LOGIC *********************************\ |* This has some special handling over in ChatCommand.h *| \******************************************************************************/ -template <typename T> -struct CastToVisitor { - using result_type = T; - - template <typename U> - T operator()(U const& v) const { return v; } -}; - -template <typename T1, typename... Ts> -struct Variant : public boost::variant<T1, Ts...> +namespace Trinity::Impl { - using first_type = tag_base_t<T1>; - static constexpr bool have_operators = are_all_assignable<first_type, tag_base_t<Ts>...>::value; + template <typename T> + struct CastToVisitor { + template <typename U> + T operator()(U const& v) const { return v; } + }; +} - template <bool C = have_operators> - operator std::enable_if_t<C, first_type>() +namespace Trinity::ChatCommands +{ + template <typename T1, typename... Ts> + struct Variant : public std::variant<T1, Ts...> { - return operator*(); - } + using base = std::variant<T1, Ts...>; - template <bool C = have_operators> - std::enable_if_t<C, first_type> operator*() - { - return boost::apply_visitor(CastToVisitor<first_type>(), *this); - } + using first_type = tag_base_t<T1>; + static constexpr bool have_operators = Trinity::Impl::ChatCommands::are_all_assignable<first_type, tag_base_t<Ts>...>::value; - template <bool C = have_operators> - std::enable_if_t<C, first_type const&> operator*() const - { - return boost::apply_visitor(CastToVisitor<first_type const&>(), *this); - } + template <bool C = have_operators> + std::enable_if_t<C, first_type> operator*() const + { + return visit(Trinity::Impl::CastToVisitor<first_type>()); + } - template <typename T> - Variant& operator=(T&& arg) { boost::variant<T1, Ts...>::operator=(std::forward<T>(arg)); return *this; } + template <bool C = have_operators> + operator std::enable_if_t<C, first_type>() const + { + return operator*(); + } + + template <typename T> + Variant& operator=(T&& arg) { base::operator=(std::forward<T>(arg)); return *this; } - template <size_t index> - decltype(auto) get() const { return boost::get<get_nth_t<index, T1, Ts...>>(*this); } -}; + template <size_t index> + constexpr decltype(auto) get() { return std::get<index>(static_cast<base const&>(*this)); } + template <size_t index> + constexpr decltype(auto) get() const { return std::get<index>(static_cast<base const&>(*this)); } + template <typename T> + constexpr decltype(auto) visit(T&& arg) const { return std::visit(std::forward<T>(arg), static_cast<base const&>(*this)); } + + template <typename T> + constexpr bool holds_alternative() const { return std::holds_alternative<T>(static_cast<base const&>(*this)); } + }; } + +/* make the correct operator<< to use explicit, because otherwise the compiler gets confused with the implicit std::variant conversion */ +namespace std +{ + template <typename... Ts> + auto operator<<(std::ostream& os, Trinity::ChatCommands::Variant<Ts...> const& v) -> std::enable_if_t<Trinity::ChatCommands::Variant<Ts...>::have_operators, std::ostream&> + { + return (os << *v); + } } #endif diff --git a/src/server/game/Chat/Hyperlinks.h b/src/server/game/Chat/Hyperlinks.h index 435ccd02688..ababb840938 100644 --- a/src/server/game/Chat/Hyperlinks.h +++ b/src/server/game/Chat/Hyperlinks.h @@ -51,423 +51,420 @@ struct TalentEntry; struct TransmogSetEntry; struct UiMapEntry; -namespace Trinity +namespace Trinity::Hyperlinks { -namespace Hyperlinks -{ - -struct AchievementLinkData -{ - AchievementEntry const* Achievement; - ObjectGuid CharacterId; - bool IsFinished; - uint16 Year; - uint8 Month; - uint8 Day; - uint32 Criteria[4]; -}; - -struct ArtifactPowerLinkData -{ - ArtifactPowerRankEntry const* ArtifactPower; - uint8 PurchasedRank; - uint8 CurrentRankWithBonus; -}; - -struct AzeriteEssenceLinkData -{ - AzeriteEssenceEntry const* Essence; - uint8 Rank; -}; - -struct BattlePetLinkData -{ - BattlePetSpeciesEntry const* Species; - uint8 Level; - uint8 Quality; - uint32 MaxHealth; - uint32 Power; - uint32 Speed; - ObjectGuid PetGuid; - uint32 DisplayId; -}; - -struct CurrencyLinkData -{ - CurrencyTypesEntry const* Currency; - int32 Quantity; - - CurrencyContainerEntry const* Container; -}; - -struct GarrisonFollowerLinkData -{ - GarrFollowerEntry const* Follower; - uint32 Quality; - uint32 Level; - uint32 ItemLevel; - uint32 Abilities[4]; - uint32 Traits[4]; - uint32 Specialization; -}; - -struct GarrisonMissionLinkData -{ - GarrMissionEntry const* Mission; - uint64 DbID; -}; - -struct InstanceLockLinkData -{ - ObjectGuid Owner; - MapEntry const* Map; - uint32 Difficulty; - uint32 CompletedEncountersMask; -}; -struct ItemLinkData -{ - ItemTemplate const* Item; - uint32 EnchantId; - uint32 GemItemId[3]; - uint8 RenderLevel; - uint32 RenderSpecialization; - uint8 Context; - std::vector<int32> ItemBonusListIDs; - - struct Modifier + struct AchievementLinkData { - uint32 Type; - int32 Value; + AchievementEntry const* Achievement; + ObjectGuid CharacterId; + bool IsFinished; + uint16 Year; + uint8 Month; + uint8 Day; + uint32 Criteria[4]; }; - std::vector<Modifier> Modifiers; - std::vector<int32> GemItemBonusListIDs[3]; - ObjectGuid Creator; - uint32 UseEnchantId; - - uint32 Quality; - ItemNameDescriptionEntry const* Suffix; -}; - -struct JournalLinkData -{ - enum class Types : uint8 + struct ArtifactPowerLinkData { - Instance = 0, - Encounter = 1, - EncounterSection = 2, - Tier = 3 + ArtifactPowerRankEntry const* ArtifactPower; + uint8 PurchasedRank; + uint8 CurrentRankWithBonus; }; - uint8 Type; - LocalizedString const* ExpectedText; - uint32 Difficulty; -}; - -struct KeystoneLinkData -{ - uint32 ItemId; - MapChallengeModeEntry const* Map; - uint32 Level; - uint32 Affix[4]; -}; - -struct QuestLinkData -{ - ::Quest const* Quest; - uint32 ContentTuningId; -}; - -struct SpellLinkData -{ - SpellInfo const* Spell; - GlyphPropertiesEntry const* Glyph; -}; - -struct TradeskillLinkData -{ - ObjectGuid Owner; - SpellInfo const* Spell; - SkillLineEntry const* Skill; -}; - -struct WorldMapLinkData -{ - UiMapEntry const* UiMap; - uint32 X; - uint32 Y; - Optional<uint32> Z; -}; - -namespace LinkTags { - - /************************** LINK TAGS ***************************************************\ - |* Link tags must abide by the following: *| - |* - MUST expose ::value_type typedef *| - |* - storage type is remove_cvref_t<value_type> *| - |* - MUST expose static ::tag method, void -> const char* *| - |* - this method SHOULD be constexpr *| - |* - returns identifier string for the link ("creature", "creature_entry", "item") *| - |* - MUST expose static ::StoreTo method, (storage&, char const*, size_t) *| - |* - assign value_type& based on content of std::string(char const*, size_t) *| - |* - return value indicates success/failure *| - |* - for integral/string types this can be achieved by extending base_tag *| - \****************************************************************************************/ - struct base_tag + struct AzeriteEssenceLinkData { - static bool StoreTo(std::string& val, char const* pos, size_t len) - { - val.assign(pos, len); - return true; - } - - static bool StoreTo(ObjectGuid& val, char const* pos, size_t len) - { - val = ObjectGuid::FromString(std::string(pos, len)); - return true; - } - - template <typename T> - static std::enable_if_t<std::is_integral_v<T> && std::is_unsigned_v<T>, bool> StoreTo(T& val, char const* pos, size_t len) - { - try { val = std::stoull(std::string(pos, len)); } - catch (...) { return false; } - return true; - } - - template <typename T> - static std::enable_if_t<std::is_integral_v<T> && std::is_signed_v<T>, bool> StoreTo(T& val, char const* pos, size_t len) - { - try { val = std::stoll(std::string(pos, len)); } - catch (...) { return false; } - return true; - } + AzeriteEssenceEntry const* Essence; + uint8 Rank; }; -#define make_base_tag(ltag, type) struct ltag : public base_tag { using value_type = type; static constexpr char const* tag() { return #ltag; } } - // custom formats - make_base_tag(area, uint32); - make_base_tag(areatrigger, uint32); - make_base_tag(creature, ObjectGuid::LowType); - make_base_tag(creature_entry, uint32); - make_base_tag(gameevent, uint32); - make_base_tag(gameobject, ObjectGuid::LowType); - make_base_tag(gameobject_entry, uint32); - make_base_tag(itemset, uint32); - make_base_tag(player, std::string const&); - make_base_tag(skill, uint32); - make_base_tag(taxinode, uint32); - make_base_tag(tele, uint32); - make_base_tag(title, uint32); - - // client format - make_base_tag(outfit, std::string const&); // some sort of weird base91 derived encoding -#undef make_base_tag - - struct TC_GAME_API achievement + struct BattlePetLinkData { - using value_type = AchievementLinkData const&; - static constexpr char const* tag() { return "achievement"; } - static bool StoreTo(AchievementLinkData& val, char const* pos, size_t len); + BattlePetSpeciesEntry const* Species; + uint8 Level; + uint8 Quality; + uint32 MaxHealth; + uint32 Power; + uint32 Speed; + ObjectGuid PetGuid; + uint32 DisplayId; }; - struct TC_GAME_API apower + struct CurrencyLinkData { - using value_type = ArtifactPowerLinkData const&; - static constexpr char const* tag() { return "apower"; } - static bool StoreTo(ArtifactPowerLinkData& val, char const* pos, size_t len); - }; + CurrencyTypesEntry const* Currency; + int32 Quantity; - struct TC_GAME_API azessence - { - using value_type = AzeriteEssenceLinkData const&; - static constexpr char const* tag() { return "azessence"; } - static bool StoreTo(AzeriteEssenceLinkData& val, char const* pos, size_t len); + CurrencyContainerEntry const* Container; }; - struct TC_GAME_API battlepet + struct GarrisonFollowerLinkData { - using value_type = BattlePetLinkData const&; - static constexpr char const* tag() { return "battlepet"; } - static bool StoreTo(BattlePetLinkData& val, char const* pos, size_t len); + GarrFollowerEntry const* Follower; + uint32 Quality; + uint32 Level; + uint32 ItemLevel; + uint32 Abilities[4]; + uint32 Traits[4]; + uint32 Specialization; }; - struct TC_GAME_API conduit + struct GarrisonMissionLinkData { - using value_type = SoulbindConduitRankEntry const*&; - static constexpr char const* tag() { return "conduit"; } - static bool StoreTo(SoulbindConduitRankEntry const*& val, char const* pos, size_t len); + GarrMissionEntry const* Mission; + uint64 DbID; }; - struct TC_GAME_API currency + struct InstanceLockLinkData { - using value_type = CurrencyLinkData const&; - static constexpr char const* tag() { return "currency"; } - static bool StoreTo(CurrencyLinkData& val, char const* pos, size_t len); + ObjectGuid Owner; + MapEntry const* Map; + uint32 Difficulty; + uint32 CompletedEncountersMask; }; - struct TC_GAME_API enchant + struct ItemLinkData { - using value_type = SpellInfo const*; - static constexpr char const* tag() { return "enchant"; } - static bool StoreTo(SpellInfo const*& val, char const* pos, size_t len); - }; + ItemTemplate const* Item; + uint32 EnchantId; + uint32 GemItemId[3]; + uint8 RenderLevel; + uint32 RenderSpecialization; + uint8 Context; + std::vector<int32> ItemBonusListIDs; + + struct Modifier + { + uint32 Type; + int32 Value; + }; - struct TC_GAME_API garrfollower - { - using value_type = GarrisonFollowerLinkData const&; - static constexpr char const* tag() { return "garrfollower"; } - static bool StoreTo(GarrisonFollowerLinkData& val, char const* pos, size_t len); - }; + std::vector<Modifier> Modifiers; + std::vector<int32> GemItemBonusListIDs[3]; + ObjectGuid Creator; + uint32 UseEnchantId; - struct TC_GAME_API garrfollowerability - { - using value_type = GarrAbilityEntry const*&; - static constexpr char const* tag() { return "garrfollowerability"; } - static bool StoreTo(GarrAbilityEntry const*& val, char const* pos, size_t len); + uint32 Quality; + ItemNameDescriptionEntry const* Suffix; }; - struct TC_GAME_API garrmission + struct JournalLinkData { - using value_type = GarrisonMissionLinkData const&; - static constexpr char const* tag() { return "garrmission"; } - static bool StoreTo(GarrisonMissionLinkData& val, char const* pos, size_t len); + enum class Types : uint8 + { + Instance = 0, + Encounter = 1, + EncounterSection = 2, + Tier = 3 + }; + + uint8 Type; + LocalizedString const* ExpectedText; + uint32 Difficulty; }; - struct TC_GAME_API instancelock + struct KeystoneLinkData { - using value_type = InstanceLockLinkData const&; - static constexpr char const* tag() { return "instancelock"; } - static bool StoreTo(InstanceLockLinkData& val, char const* pos, size_t len); + uint32 ItemId; + MapChallengeModeEntry const* Map; + uint32 Level; + uint32 Affix[4]; }; - struct TC_GAME_API item + struct QuestLinkData { - using value_type = ItemLinkData const&; - static constexpr char const* tag() { return "item"; } - static bool StoreTo(ItemLinkData& val, char const* pos, size_t len); + ::Quest const* Quest; + uint32 ContentTuningId; }; - struct TC_GAME_API journal + struct SpellLinkData { - using value_type = JournalLinkData const&; - static constexpr char const* tag() { return "journal"; } - static bool StoreTo(JournalLinkData& val, char const* pos, size_t len); + SpellInfo const* Spell; + GlyphPropertiesEntry const* Glyph; }; - struct TC_GAME_API keystone + struct TradeskillLinkData { - using value_type = KeystoneLinkData const&; - static constexpr char const* tag() { return "keystone"; } - static bool StoreTo(KeystoneLinkData& val, char const* pos, size_t len); + ObjectGuid Owner; + SpellInfo const* Spell; + SkillLineEntry const* Skill; }; - struct TC_GAME_API mawpower + struct WorldMapLinkData { - using value_type = MawPowerEntry const*&; - static constexpr char const* tag() { return "mawpower"; } - static bool StoreTo(MawPowerEntry const*& val, char const* pos, size_t len); + UiMapEntry const* UiMap; + uint32 X; + uint32 Y; + Optional<uint32> Z; }; - struct TC_GAME_API pvptal - { - using value_type = PvpTalentEntry const*&; - static constexpr char const* tag() { return "pvptal"; } - static bool StoreTo(PvpTalentEntry const*& val, char const* pos, size_t len); - }; + namespace LinkTags { + + /************************** LINK TAGS ***************************************************\ + |* Link tags must abide by the following: *| + |* - MUST expose ::value_type typedef *| + |* - storage type is remove_cvref_t<value_type> *| + |* - MUST expose static ::tag method, void -> const char* *| + |* - this method SHOULD be constexpr *| + |* - returns identifier string for the link ("creature", "creature_entry", "item") *| + |* - MUST expose static ::StoreTo method, (storage&, char const*, size_t) *| + |* - assign value_type& based on content of std::string(char const*, size_t) *| + |* - return value indicates success/failure *| + |* - for integral/string types this can be achieved by extending base_tag *| + \****************************************************************************************/ + struct base_tag + { + static bool StoreTo(std::string& val, char const* pos, size_t len) + { + val.assign(pos, len); + return true; + } + + static bool StoreTo(ObjectGuid& val, char const* pos, size_t len) + { + val = ObjectGuid::FromString(std::string(pos, len)); + return true; + } + + template <typename T> + static std::enable_if_t<std::is_integral_v<T> && std::is_unsigned_v<T>, bool> StoreTo(T& val, char const* pos, size_t len) + { + try { val = std::stoull(std::string(pos, len)); } + catch (...) { return false; } + return true; + } + + template <typename T> + static std::enable_if_t<std::is_integral_v<T> && std::is_signed_v<T>, bool> StoreTo(T& val, char const* pos, size_t len) + { + try { val = std::stoll(std::string(pos, len)); } + catch (...) { return false; } + return true; + } + }; + + #define make_base_tag(ltag, type) struct ltag : public base_tag { using value_type = type; static constexpr char const* tag() { return #ltag; } } + // custom formats + make_base_tag(area, uint32); + make_base_tag(areatrigger, uint32); + make_base_tag(creature, ObjectGuid::LowType); + make_base_tag(creature_entry, uint32); + make_base_tag(gameevent, uint32); + make_base_tag(gameobject, ObjectGuid::LowType); + make_base_tag(gameobject_entry, uint32); + make_base_tag(itemset, uint32); + make_base_tag(player, std::string const&); + make_base_tag(skill, uint32); + make_base_tag(taxinode, uint32); + make_base_tag(tele, uint32); + make_base_tag(title, uint32); + + // client format + make_base_tag(outfit, std::string const&); // some sort of weird base91 derived encoding + #undef make_base_tag + + struct TC_GAME_API achievement + { + using value_type = AchievementLinkData const&; + static constexpr char const* tag() { return "achievement"; } + static bool StoreTo(AchievementLinkData& val, char const* pos, size_t len); + }; - struct TC_GAME_API quest - { - using value_type = QuestLinkData const&; - static constexpr char const* tag() { return "quest"; } - static bool StoreTo(QuestLinkData& val, char const* pos, size_t len); - }; + struct TC_GAME_API apower + { + using value_type = ArtifactPowerLinkData const&; + static constexpr char const* tag() { return "apower"; } + static bool StoreTo(ArtifactPowerLinkData& val, char const* pos, size_t len); + }; - struct TC_GAME_API spell - { - using value_type = SpellLinkData const&; - static constexpr char const* tag() { return "spell"; } - static bool StoreTo(SpellLinkData& val, char const* pos, size_t len); - }; + struct TC_GAME_API azessence + { + using value_type = AzeriteEssenceLinkData const&; + static constexpr char const* tag() { return "azessence"; } + static bool StoreTo(AzeriteEssenceLinkData& val, char const* pos, size_t len); + }; - struct TC_GAME_API talent - { - using value_type = TalentEntry const*&; - static constexpr char const* tag() { return "talent"; } - static bool StoreTo(TalentEntry const*& val, char const* pos, size_t len); - }; + struct TC_GAME_API battlepet + { + using value_type = BattlePetLinkData const&; + static constexpr char const* tag() { return "battlepet"; } + static bool StoreTo(BattlePetLinkData& val, char const* pos, size_t len); + }; - struct TC_GAME_API trade - { - using value_type = TradeskillLinkData const&; - static constexpr char const* tag() { return "trade"; } - static bool StoreTo(TradeskillLinkData& val, char const* pos, size_t len); - }; + struct TC_GAME_API conduit + { + using value_type = SoulbindConduitRankEntry const*&; + static constexpr char const* tag() { return "conduit"; } + static bool StoreTo(SoulbindConduitRankEntry const*& val, char const* pos, size_t len); + }; - struct TC_GAME_API transmogappearance - { - using value_type = ItemModifiedAppearanceEntry const*&; - static constexpr char const* tag() { return "transmogappearance"; } - static bool StoreTo(ItemModifiedAppearanceEntry const*& val, char const* pos, size_t len); - }; + struct TC_GAME_API currency + { + using value_type = CurrencyLinkData const&; + static constexpr char const* tag() { return "currency"; } + static bool StoreTo(CurrencyLinkData& val, char const* pos, size_t len); + }; - struct TC_GAME_API transmogillusion - { - using value_type = SpellItemEnchantmentEntry const*&; - static constexpr char const* tag() { return "transmogillusion"; } - static bool StoreTo(SpellItemEnchantmentEntry const*& val, char const* pos, size_t len); - }; + struct TC_GAME_API enchant + { + using value_type = SpellInfo const*; + static constexpr char const* tag() { return "enchant"; } + static bool StoreTo(SpellInfo const*& val, char const* pos, size_t len); + }; - struct TC_GAME_API transmogset - { - using value_type = TransmogSetEntry const*&; - static constexpr char const* tag() { return "transmogset"; } - static bool StoreTo(TransmogSetEntry const*& val, char const* pos, size_t len); - }; + struct TC_GAME_API garrfollower + { + using value_type = GarrisonFollowerLinkData const&; + static constexpr char const* tag() { return "garrfollower"; } + static bool StoreTo(GarrisonFollowerLinkData& val, char const* pos, size_t len); + }; + + struct TC_GAME_API garrfollowerability + { + using value_type = GarrAbilityEntry const*&; + static constexpr char const* tag() { return "garrfollowerability"; } + static bool StoreTo(GarrAbilityEntry const*& val, char const* pos, size_t len); + }; + + struct TC_GAME_API garrmission + { + using value_type = GarrisonMissionLinkData const&; + static constexpr char const* tag() { return "garrmission"; } + static bool StoreTo(GarrisonMissionLinkData& val, char const* pos, size_t len); + }; + + struct TC_GAME_API instancelock + { + using value_type = InstanceLockLinkData const&; + static constexpr char const* tag() { return "instancelock"; } + static bool StoreTo(InstanceLockLinkData& val, char const* pos, size_t len); + }; + + struct TC_GAME_API item + { + using value_type = ItemLinkData const&; + static constexpr char const* tag() { return "item"; } + static bool StoreTo(ItemLinkData& val, char const* pos, size_t len); + }; + + struct TC_GAME_API journal + { + using value_type = JournalLinkData const&; + static constexpr char const* tag() { return "journal"; } + static bool StoreTo(JournalLinkData& val, char const* pos, size_t len); + }; + + struct TC_GAME_API keystone + { + using value_type = KeystoneLinkData const&; + static constexpr char const* tag() { return "keystone"; } + static bool StoreTo(KeystoneLinkData& val, char const* pos, size_t len); + }; + + struct TC_GAME_API mawpower + { + using value_type = MawPowerEntry const*&; + static constexpr char const* tag() { return "mawpower"; } + static bool StoreTo(MawPowerEntry const*& val, char const* pos, size_t len); + }; + + struct TC_GAME_API pvptal + { + using value_type = PvpTalentEntry const*&; + static constexpr char const* tag() { return "pvptal"; } + static bool StoreTo(PvpTalentEntry const*& val, char const* pos, size_t len); + }; + + struct TC_GAME_API quest + { + using value_type = QuestLinkData const&; + static constexpr char const* tag() { return "quest"; } + static bool StoreTo(QuestLinkData& val, char const* pos, size_t len); + }; + + struct TC_GAME_API spell + { + using value_type = SpellLinkData const&; + static constexpr char const* tag() { return "spell"; } + static bool StoreTo(SpellLinkData& val, char const* pos, size_t len); + }; + + struct TC_GAME_API talent + { + using value_type = TalentEntry const*&; + static constexpr char const* tag() { return "talent"; } + static bool StoreTo(TalentEntry const*& val, char const* pos, size_t len); + }; + + struct TC_GAME_API trade + { + using value_type = TradeskillLinkData const&; + static constexpr char const* tag() { return "trade"; } + static bool StoreTo(TradeskillLinkData& val, char const* pos, size_t len); + }; + + struct TC_GAME_API transmogappearance + { + using value_type = ItemModifiedAppearanceEntry const*&; + static constexpr char const* tag() { return "transmogappearance"; } + static bool StoreTo(ItemModifiedAppearanceEntry const*& val, char const* pos, size_t len); + }; + + struct TC_GAME_API transmogillusion + { + using value_type = SpellItemEnchantmentEntry const*&; + static constexpr char const* tag() { return "transmogillusion"; } + static bool StoreTo(SpellItemEnchantmentEntry const*& val, char const* pos, size_t len); + }; - struct TC_GAME_API worldmap + struct TC_GAME_API transmogset + { + using value_type = TransmogSetEntry const*&; + static constexpr char const* tag() { return "transmogset"; } + static bool StoreTo(TransmogSetEntry const*& val, char const* pos, size_t len); + }; + + struct TC_GAME_API worldmap + { + using value_type = WorldMapLinkData const&; + static constexpr char const* tag() { return "worldmap"; } + static bool StoreTo(WorldMapLinkData& val, char const* pos, size_t len); + }; + } + + struct HyperlinkColor { - using value_type = WorldMapLinkData const&; - static constexpr char const* tag() { return "worldmap"; } - static bool StoreTo(WorldMapLinkData& val, char const* pos, size_t len); + HyperlinkColor(uint32 c) : r(c >> 16), g(c >> 8), b(c), a(c >> 24) {} + uint8 r, g, b, a; + bool operator==(uint32 c) const + { + if ((c & 0xff) ^ b) + return false; + if (((c >>= 8) & 0xff) ^ g) + return false; + if (((c >>= 8) & 0xff) ^ r) + return false; + if ((c >>= 8) ^ a) + return false; + return true; + } }; -} -struct HyperlinkColor -{ - HyperlinkColor(uint32 c) : r(c >> 16), g(c >> 8), b(c), a(c >> 24) {} - uint8 r, g, b, a; - bool operator==(uint32 c) const + struct HyperlinkInfo { - if ((c & 0xff) ^ b) - return false; - if (((c >>= 8) & 0xff) ^ g) - return false; - if (((c >>= 8) & 0xff) ^ r) - return false; - if ((c >>= 8) ^ a) - return false; - return true; - } -}; - -struct HyperlinkInfo -{ - HyperlinkInfo(char const* n = nullptr, uint32 c = 0, char const* tS = nullptr, size_t tL = 0, char const* dS = nullptr, size_t dL = 0, char const* cS = nullptr, size_t cL = 0) : - next(n), color(c), tag(tS, tL), data(dS, dL), text(cS, cL) {} - - explicit operator bool() { return next; } - char const* const next; - HyperlinkColor const color; - std::pair<char const*, size_t> const tag; - std::pair<char const*, size_t> const data; - std::pair<char const*, size_t> const text; -}; -HyperlinkInfo TC_GAME_API ParseHyperlink(char const* pos); -bool TC_GAME_API CheckAllLinks(std::string const&); + HyperlinkInfo(char const* n = nullptr, uint32 c = 0, char const* tS = nullptr, size_t tL = 0, char const* dS = nullptr, size_t dL = 0, char const* cS = nullptr, size_t cL = 0) : + next(n), color(c), tag(tS, tL), data(dS, dL), text(cS, cL) {} + + explicit operator bool() { return next; } + char const* const next; + HyperlinkColor const color; + std::pair<char const*, size_t> const tag; + std::pair<char const*, size_t> const data; + std::pair<char const*, size_t> const text; + }; + HyperlinkInfo TC_GAME_API ParseHyperlink(char const* pos); + bool TC_GAME_API CheckAllLinks(std::string const&); } -} #endif diff --git a/src/server/scripts/Commands/cs_debug.cpp b/src/server/scripts/Commands/cs_debug.cpp index ed6cd8c005a..8eb97be1683 100644 --- a/src/server/scripts/Commands/cs_debug.cpp +++ b/src/server/scripts/Commands/cs_debug.cpp @@ -165,7 +165,7 @@ public: // alliance Set faction balance to alliance. // horde Set faction balance to horde. // off Reset the faction balance and use the calculated value of it - switch (command.which()) + switch (command.index()) { case 0: // workaround for Variant of only ExactSequences not being supported handler->SendSysMessage(LANG_BAD_VALUE); |