aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--sql/updates/hotfixes/master/2024_11_19_00_hotfixes.sql13
-rw-r--r--sql/updates/world/master/2024_11_19_00_world.sql5
-rw-r--r--src/server/database/Database/Implementation/HotfixDatabase.cpp5
-rw-r--r--src/server/database/Database/Implementation/HotfixDatabase.h3
-rw-r--r--src/server/game/DataStores/DB2LoadInfo.h14
-rw-r--r--src/server/game/DataStores/DB2Stores.cpp2
-rw-r--r--src/server/game/DataStores/DB2Stores.h1
-rw-r--r--src/server/game/DataStores/DB2Structure.h11
-rw-r--r--src/server/game/DataStores/DBCEnums.h26
-rw-r--r--src/server/game/Entities/Unit/Unit.cpp2
-rw-r--r--src/server/game/Entities/Unit/Unit.h1
-rw-r--r--src/server/game/Server/Packets/SpellPackets.cpp10
-rw-r--r--src/server/game/Server/Packets/SpellPackets.h18
-rw-r--r--src/server/game/Server/Protocol/Opcodes.cpp2
-rw-r--r--src/server/game/Spells/Auras/SpellAuraEffects.cpp18
-rw-r--r--src/server/game/Spells/Spell.h1
-rw-r--r--src/server/game/Spells/SpellEffects.cpp36
-rw-r--r--src/server/scripts/Spells/spell_generic.cpp46
18 files changed, 201 insertions, 13 deletions
diff --git a/sql/updates/hotfixes/master/2024_11_19_00_hotfixes.sql b/sql/updates/hotfixes/master/2024_11_19_00_hotfixes.sql
new file mode 100644
index 00000000000..678c526c8e2
--- /dev/null
+++ b/sql/updates/hotfixes/master/2024_11_19_00_hotfixes.sql
@@ -0,0 +1,13 @@
+--
+-- Table structure for table `mount_equipment`
+--
+DROP TABLE IF EXISTS `mount_equipment`;
+CREATE TABLE `mount_equipment` (
+ `ID` int unsigned NOT NULL DEFAULT '0',
+ `Item` int NOT NULL DEFAULT '0',
+ `BuffSpell` int NOT NULL DEFAULT '0',
+ `Unknown820` int NOT NULL DEFAULT '0',
+ `LearnedBySpell` int unsigned NOT NULL DEFAULT '0',
+ `VerifiedBuild` int NOT NULL DEFAULT '0',
+ PRIMARY KEY (`ID`,`VerifiedBuild`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
diff --git a/sql/updates/world/master/2024_11_19_00_world.sql b/sql/updates/world/master/2024_11_19_00_world.sql
new file mode 100644
index 00000000000..dc2c1212fb1
--- /dev/null
+++ b/sql/updates/world/master/2024_11_19_00_world.sql
@@ -0,0 +1,5 @@
+DELETE FROM `spell_script_names` WHERE `ScriptName`='spell_gen_comfortable_riders_barding';
+DELETE FROM `spell_script_names` WHERE `ScriptName`='spell_gen_saddlechute';
+INSERT INTO `spell_script_names` (`spell_id`, `ScriptName`) VALUES
+(296837, 'spell_gen_comfortable_riders_barding'),
+(297091, 'spell_gen_saddlechute');
diff --git a/src/server/database/Database/Implementation/HotfixDatabase.cpp b/src/server/database/Database/Implementation/HotfixDatabase.cpp
index 735d11d7574..89abafe7c36 100644
--- a/src/server/database/Database/Implementation/HotfixDatabase.cpp
+++ b/src/server/database/Database/Implementation/HotfixDatabase.cpp
@@ -1194,6 +1194,11 @@ void HotfixDatabaseConnection::DoPrepareStatements()
"ReqMapID, PlayerConditionID, FlightCapabilityID FROM mount_capability WHERE (`VerifiedBuild` > 0) = ?", CONNECTION_SYNCH);
PREPARE_MAX_ID_STMT(HOTFIX_SEL_MOUNT_CAPABILITY, "SELECT MAX(ID) + 1 FROM mount_capability", CONNECTION_SYNCH);
+ // MountEquipment.db2
+ PrepareStatement(HOTFIX_SEL_MOUNT_EQUIPMENT, "SELECT ID, Item, BuffSpell, Unknown820, LearnedBySpell FROM mount_equipment"
+ " WHERE (`VerifiedBuild` > 0) = ?", CONNECTION_SYNCH);
+ PREPARE_MAX_ID_STMT(HOTFIX_SEL_MOUNT_EQUIPMENT, "SELECT MAX(ID) + 1 FROM mount_equipment", CONNECTION_SYNCH);
+
// MountTypeXCapability.db2
PrepareStatement(HOTFIX_SEL_MOUNT_TYPE_X_CAPABILITY, "SELECT ID, MountTypeID, MountCapabilityID, OrderIndex FROM mount_type_x_capability"
" WHERE (`VerifiedBuild` > 0) = ?", CONNECTION_SYNCH);
diff --git a/src/server/database/Database/Implementation/HotfixDatabase.h b/src/server/database/Database/Implementation/HotfixDatabase.h
index 41732618ffb..a77157ff1bd 100644
--- a/src/server/database/Database/Implementation/HotfixDatabase.h
+++ b/src/server/database/Database/Implementation/HotfixDatabase.h
@@ -685,6 +685,9 @@ enum HotfixDatabaseStatements : uint32
HOTFIX_SEL_MOUNT_CAPABILITY,
HOTFIX_SEL_MOUNT_CAPABILITY_MAX_ID,
+ HOTFIX_SEL_MOUNT_EQUIPMENT,
+ HOTFIX_SEL_MOUNT_EQUIPMENT_MAX_ID,
+
HOTFIX_SEL_MOUNT_TYPE_X_CAPABILITY,
HOTFIX_SEL_MOUNT_TYPE_X_CAPABILITY_MAX_ID,
diff --git a/src/server/game/DataStores/DB2LoadInfo.h b/src/server/game/DataStores/DB2LoadInfo.h
index 4fe9d5a6f51..d7306aabb70 100644
--- a/src/server/game/DataStores/DB2LoadInfo.h
+++ b/src/server/game/DataStores/DB2LoadInfo.h
@@ -3884,6 +3884,20 @@ struct MountCapabilityLoadInfo
static constexpr DB2LoadInfo Instance{ Fields, 10, &MountCapabilityMeta::Instance, HOTFIX_SEL_MOUNT_CAPABILITY };
};
+struct MountEquipmentLoadInfo
+{
+ static constexpr DB2FieldMeta Fields[5] =
+ {
+ { false, FT_INT, "ID" },
+ { true, FT_INT, "Item" },
+ { true, FT_INT, "BuffSpell" },
+ { true, FT_INT, "Unknown820" },
+ { false, FT_INT, "LearnedBySpell" },
+ };
+
+ static constexpr DB2LoadInfo Instance{ Fields, 5, &MountEquipmentMeta::Instance, HOTFIX_SEL_MOUNT_EQUIPMENT };
+};
+
struct MountTypeXCapabilityLoadInfo
{
static constexpr DB2FieldMeta Fields[4] =
diff --git a/src/server/game/DataStores/DB2Stores.cpp b/src/server/game/DataStores/DB2Stores.cpp
index 308f53098dd..fd6952e22fd 100644
--- a/src/server/game/DataStores/DB2Stores.cpp
+++ b/src/server/game/DataStores/DB2Stores.cpp
@@ -238,6 +238,7 @@ DB2Storage<MawPowerEntry> sMawPowerStore("MawPower.db2", &
DB2Storage<ModifierTreeEntry> sModifierTreeStore("ModifierTree.db2", &ModifierTreeLoadInfo::Instance);
DB2Storage<MountCapabilityEntry> sMountCapabilityStore("MountCapability.db2", &MountCapabilityLoadInfo::Instance);
DB2Storage<MountEntry> sMountStore("Mount.db2", &MountLoadInfo::Instance);
+DB2Storage<MountEquipmentEntry> sMountEquipmentStore("MountEquipment.db2", &MountEquipmentLoadInfo::Instance);
DB2Storage<MountTypeXCapabilityEntry> sMountTypeXCapabilityStore("MountTypeXCapability.db2", &MountTypeXCapabilityLoadInfo::Instance);
DB2Storage<MountXDisplayEntry> sMountXDisplayStore("MountXDisplay.db2", &MountXDisplayLoadInfo::Instance);
DB2Storage<MovieEntry> sMovieStore("Movie.db2", &MovieLoadInfo::Instance);
@@ -851,6 +852,7 @@ uint32 DB2Manager::LoadStores(std::string const& dataPath, LocaleConstant defaul
LOAD_DB2(sModifierTreeStore);
LOAD_DB2(sMountCapabilityStore);
LOAD_DB2(sMountStore);
+ LOAD_DB2(sMountEquipmentStore);
LOAD_DB2(sMountTypeXCapabilityStore);
LOAD_DB2(sMountXDisplayStore);
LOAD_DB2(sMovieStore);
diff --git a/src/server/game/DataStores/DB2Stores.h b/src/server/game/DataStores/DB2Stores.h
index 12353f77ffc..19a45d46a69 100644
--- a/src/server/game/DataStores/DB2Stores.h
+++ b/src/server/game/DataStores/DB2Stores.h
@@ -194,6 +194,7 @@ TC_GAME_API extern DB2Storage<MawPowerEntry> sMawPowerSto
TC_GAME_API extern DB2Storage<ModifierTreeEntry> sModifierTreeStore;
TC_GAME_API extern DB2Storage<MountCapabilityEntry> sMountCapabilityStore;
TC_GAME_API extern DB2Storage<MountEntry> sMountStore;
+TC_GAME_API extern DB2Storage<MountEquipmentEntry> sMountEquipmentStore;
TC_GAME_API extern DB2Storage<MovieEntry> sMovieStore;
TC_GAME_API extern DB2Storage<MythicPlusSeasonEntry> sMythicPlusSeasonStore;
TC_GAME_API extern DB2Storage<OverrideSpellDataEntry> sOverrideSpellDataStore;
diff --git a/src/server/game/DataStores/DB2Structure.h b/src/server/game/DataStores/DB2Structure.h
index 1e3b3d6e277..7ea04668e5c 100644
--- a/src/server/game/DataStores/DB2Structure.h
+++ b/src/server/game/DataStores/DB2Structure.h
@@ -2935,7 +2935,7 @@ struct MountEntry
int32 MountSpecialRiderAnimKitID;
int32 MountSpecialSpellVisualKitID;
- bool IsSelfMount() const { return (Flags & MOUNT_FLAG_SELF_MOUNT) != 0; }
+ EnumFlag<MountFlags> GetFlags() const { return static_cast<MountFlags>(Flags); }
};
struct MountCapabilityEntry
@@ -2952,6 +2952,15 @@ struct MountCapabilityEntry
int32 FlightCapabilityID;
};
+struct MountEquipmentEntry
+{
+ uint32 ID;
+ int32 Item;
+ int32 BuffSpell;
+ int32 Unknown820;
+ uint32 LearnedBySpell;
+};
+
struct MountTypeXCapabilityEntry
{
uint32 ID;
diff --git a/src/server/game/DataStores/DBCEnums.h b/src/server/game/DataStores/DBCEnums.h
index 2417f7e3009..cbdffa8d110 100644
--- a/src/server/game/DataStores/DBCEnums.h
+++ b/src/server/game/DataStores/DBCEnums.h
@@ -1836,14 +1836,24 @@ enum MountCapabilityFlags
MOUNT_CAPABIILTY_FLAG_IGNORE_RESTRICTIONS = 0x20,
};
-enum MountFlags
-{
- MOUNT_FLAG_SELF_MOUNT = 0x02, // Player becomes the mount himself
- MOUNT_FLAG_FACTION_SPECIFIC = 0x04,
- MOUNT_FLAG_PREFERRED_SWIMMING = 0x10,
- MOUNT_FLAG_PREFERRED_WATER_WALKING = 0x20,
- MOUNT_FLAG_HIDE_IF_UNKNOWN = 0x40
-};
+enum class MountFlags : int32
+{
+ ServerOnly = 0x00000001,
+ IsSelfMount = 0x00000002,
+ ExcludeFromJournalIfFactionDoesntMatch = 0x00000004,
+ AllowMountedCombat = 0x00000008,
+ SummonRandomFavorWhileUnderwater = 0x00000010,
+ SummonRandomFavorWhileAtWaterSurface = 0x00000020,
+ ExcludeFromJournalIfNotLearned = 0x00000040,
+ SummonRandomDoNotFavorWhenGrounded = 0x00000080,
+ ShowInSpellbook = 0x00000100,
+ AddToActionBarOnLearn = 0x00000200,
+ NotForUseAsATaxi = 0x00000400,
+ MountEquipmentEffectsSuppressed = 0x00000800,
+ DisablePlayerMountPreview = 0x00001000,
+};
+
+DEFINE_ENUM_FLAG(MountFlags);
enum class PathPropertyIndex : uint8
{
diff --git a/src/server/game/Entities/Unit/Unit.cpp b/src/server/game/Entities/Unit/Unit.cpp
index f64dc9306f2..bc1b4a7e647 100644
--- a/src/server/game/Entities/Unit/Unit.cpp
+++ b/src/server/game/Entities/Unit/Unit.cpp
@@ -1570,7 +1570,7 @@ void Unit::DealMeleeDamage(CalcDamageInfo* damageInfo, bool durabilityLoss)
// -probability is between 0% and 40%
RoundToInterval(chance, 0.0f, 40.0f);
if (roll_chance_f(chance))
- CastSpell(victim, 1604 /*SPELL_DAZED*/, true);
+ CastSpell(victim, SPELL_DAZED, true);
}
if (GetTypeId() == TYPEID_PLAYER)
diff --git a/src/server/game/Entities/Unit/Unit.h b/src/server/game/Entities/Unit/Unit.h
index 91c5ffc4bf0..0fccc482f84 100644
--- a/src/server/game/Entities/Unit/Unit.h
+++ b/src/server/game/Entities/Unit/Unit.h
@@ -34,6 +34,7 @@
#define VISUAL_WAYPOINT 1 // Creature Entry ID used for waypoints show, visible only for GMs
#define WORLD_TRIGGER 12999
+#define SPELL_DAZED 1604
#define ARTIFACTS_ALL_WEAPONS_GENERAL_WEAPON_EQUIPPED_PASSIVE 197886
#define SPELL_DH_DOUBLE_JUMP 196055
#define DISPLAYID_HIDDEN_MOUNT 73200
diff --git a/src/server/game/Server/Packets/SpellPackets.cpp b/src/server/game/Server/Packets/SpellPackets.cpp
index c5271546d00..91da419d9b1 100644
--- a/src/server/game/Server/Packets/SpellPackets.cpp
+++ b/src/server/game/Server/Packets/SpellPackets.cpp
@@ -1079,6 +1079,16 @@ WorldPacket const* MountResult::Write()
return &_worldPacket;
}
+WorldPacket const* ApplyMountEquipmentResult::Write()
+{
+ _worldPacket << ItemGUID;
+ _worldPacket << int32(ItemID);
+ _worldPacket << Bits<1>(Result);
+ _worldPacket.FlushBits();
+
+ return &_worldPacket;
+}
+
WorldPacket const* MissileCancel::Write()
{
_worldPacket << OwnerGUID;
diff --git a/src/server/game/Server/Packets/SpellPackets.h b/src/server/game/Server/Packets/SpellPackets.h
index 0f38ef62e45..911afecfd4f 100644
--- a/src/server/game/Server/Packets/SpellPackets.h
+++ b/src/server/game/Server/Packets/SpellPackets.h
@@ -1105,6 +1105,24 @@ namespace WorldPackets
uint32 Result = 0;
};
+ class ApplyMountEquipmentResult final : public ServerPacket
+ {
+ public:
+ enum ApplyResult : int32
+ {
+ Success = 0,
+ Failure = 1
+ };
+
+ ApplyMountEquipmentResult() : ServerPacket(SMSG_APPLY_MOUNT_EQUIPMENT_RESULT, 16 + 4 + 1) { }
+
+ WorldPacket const* Write() override;
+
+ ObjectGuid ItemGUID;
+ int32 ItemID = 0;
+ ApplyResult Result = Success;
+ };
+
class MissileCancel final : public ServerPacket
{
public:
diff --git a/src/server/game/Server/Protocol/Opcodes.cpp b/src/server/game/Server/Protocol/Opcodes.cpp
index 177e3f0fbbb..40c52787341 100644
--- a/src/server/game/Server/Protocol/Opcodes.cpp
+++ b/src/server/game/Server/Protocol/Opcodes.cpp
@@ -1065,7 +1065,7 @@ void OpcodeTable::InitializeServerOpcodes()
DEFINE_SERVER_OPCODE_HANDLER(SMSG_ALL_ACCOUNT_CRITERIA, STATUS_NEVER, CONNECTION_TYPE_INSTANCE);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_ALL_ACHIEVEMENT_DATA, STATUS_NEVER, CONNECTION_TYPE_INSTANCE);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_ALL_GUILD_ACHIEVEMENTS, STATUS_NEVER, CONNECTION_TYPE_REALM);
- DEFINE_SERVER_OPCODE_HANDLER(SMSG_APPLY_MOUNT_EQUIPMENT_RESULT, STATUS_UNHANDLED, CONNECTION_TYPE_INSTANCE);
+ DEFINE_SERVER_OPCODE_HANDLER(SMSG_APPLY_MOUNT_EQUIPMENT_RESULT, STATUS_NEVER, CONNECTION_TYPE_INSTANCE);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_ARCHAEOLOGY_SURVERY_CAST, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_AREA_POI_UPDATE_RESPONSE, STATUS_UNHANDLED, CONNECTION_TYPE_INSTANCE);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_AREA_SPIRIT_HEALER_TIME, STATUS_NEVER, CONNECTION_TYPE_REALM);
diff --git a/src/server/game/Spells/Auras/SpellAuraEffects.cpp b/src/server/game/Spells/Auras/SpellAuraEffects.cpp
index db893f4b379..652f709496b 100644
--- a/src/server/game/Spells/Auras/SpellAuraEffects.cpp
+++ b/src/server/game/Spells/Auras/SpellAuraEffects.cpp
@@ -2729,7 +2729,7 @@ void AuraEffect::HandleAuraMounted(AuraApplication const* aurApp, uint8 mode, bo
{
if (DB2Manager::MountXDisplayContainer const* mountDisplays = sDB2Manager.GetMountDisplays(mountEntry->ID))
{
- if (mountEntry->IsSelfMount())
+ if (mountEntry->GetFlags().HasFlag(MountFlags::IsSelfMount))
{
displayId = DISPLAYID_HIDDEN_MOUNT;
}
@@ -2751,6 +2751,18 @@ void AuraEffect::HandleAuraMounted(AuraApplication const* aurApp, uint8 mode, bo
// TODO: CREATE TABLE mount_vehicle (mountId, vehicleCreatureId) for future mounts that are vehicles (new mounts no longer have proper data in MiscValue)
//if (MountVehicle const* mountVehicle = sObjectMgr->GetMountVehicle(mountEntry->Id))
// creatureEntry = mountVehicle->VehicleCreatureId;
+
+ if (mode & AURA_EFFECT_HANDLE_REAL && !mountEntry->GetFlags().HasFlag(MountFlags::MountEquipmentEffectsSuppressed))
+ {
+ if (Player* playerTarget = target->ToPlayer())
+ {
+ auto mountEquipmentItr = std::ranges::find_if(sMountEquipmentStore,
+ [&](int32 equipmentSpell) { return playerTarget->HasSpell(equipmentSpell); },
+ &MountEquipmentEntry::LearnedBySpell);
+ if (mountEquipmentItr != sMountEquipmentStore.end())
+ playerTarget->CastSpell(playerTarget, mountEquipmentItr->BuffSpell, this);
+ }
+ }
}
if (CreatureTemplate const* creatureInfo = sObjectMgr->GetCreatureTemplate(creatureEntry))
@@ -2792,7 +2804,11 @@ void AuraEffect::HandleAuraMounted(AuraApplication const* aurApp, uint8 mode, bo
// need to remove ALL arura related to mounts, this will stop client crash with broom stick
// and never endless flying after using Headless Horseman's Mount
if (mode & AURA_EFFECT_HANDLE_REAL)
+ {
target->RemoveAurasByType(SPELL_AURA_MOUNTED);
+ for (MountEquipmentEntry const* mountEquipmentStore : sMountEquipmentStore)
+ target->RemoveOwnedAura(mountEquipmentStore->BuffSpell);
+ }
if (mode & AURA_EFFECT_HANDLE_CHANGE_AMOUNT_MASK)
// remove speed aura
diff --git a/src/server/game/Spells/Spell.h b/src/server/game/Spells/Spell.h
index f1e5b6701a3..ef421373259 100644
--- a/src/server/game/Spells/Spell.h
+++ b/src/server/game/Spells/Spell.h
@@ -427,6 +427,7 @@ class TC_GAME_API Spell
void EffectRespecAzeriteEmpoweredItem();
void EffectLearnAzeriteEssencePower();
void EffectCreatePrivateConversation();
+ void EffectApplyMountEquipment();
void EffectSendChatMessage();
void EffectGrantBattlePetExperience();
void EffectLearnTransmogIllusion();
diff --git a/src/server/game/Spells/SpellEffects.cpp b/src/server/game/Spells/SpellEffects.cpp
index 45481f9ee6a..c0af44a549a 100644
--- a/src/server/game/Spells/SpellEffects.cpp
+++ b/src/server/game/Spells/SpellEffects.cpp
@@ -356,7 +356,7 @@ NonDefaultConstructible<SpellEffectHandlerFn> SpellEffectHandlers[TOTAL_SPELL_EF
&Spell::EffectLearnAzeriteEssencePower, //265 SPELL_EFFECT_LEARN_AZERITE_ESSENCE_POWER
&Spell::EffectNULL, //266 SPELL_EFFECT_SET_ITEM_BONUS_LIST_GROUP_ENTRY
&Spell::EffectCreatePrivateConversation, //267 SPELL_EFFECT_CREATE_PRIVATE_CONVERSATION
- &Spell::EffectNULL, //268 SPELL_EFFECT_APPLY_MOUNT_EQUIPMENT
+ &Spell::EffectApplyMountEquipment, //268 SPELL_EFFECT_APPLY_MOUNT_EQUIPMENT
&Spell::EffectNULL, //269 SPELL_EFFECT_INCREASE_ITEM_BONUS_LIST_GROUP_STEP
&Spell::EffectNULL, //270 SPELL_EFFECT_270
&Spell::EffectUnused, //271 SPELL_EFFECT_APPLY_AREA_AURA_PARTY_NONRANDOM
@@ -5926,6 +5926,40 @@ void Spell::EffectCreatePrivateConversation()
Conversation::CreateConversation(effectInfo->MiscValue, unitTarget, destTarget->GetPosition(), unitTarget->GetGUID(), GetSpellInfo());
}
+void Spell::EffectApplyMountEquipment()
+{
+ if (effectHandleMode != SPELL_EFFECT_HANDLE_LAUNCH_TARGET)
+ return;
+
+ Player* playerTarget = unitTarget->ToPlayer();
+ if (!playerTarget)
+ return;
+
+ for (MountEquipmentEntry const* mountEquipment : sMountEquipmentStore)
+ {
+ if (mountEquipment->LearnedBySpell == effectInfo->TriggerSpell)
+ {
+ playerTarget->LearnSpell(mountEquipment->LearnedBySpell, false, 0, true);
+ Unit::AuraEffectList const& mountAuras = playerTarget->GetAuraEffectsByType(SPELL_AURA_MOUNTED);
+ if (!mountAuras.empty())
+ if (MountEntry const* mountEntry = sDB2Manager.GetMount(mountAuras.front()->GetId()))
+ if (!mountEntry->GetFlags().HasFlag(MountFlags::MountEquipmentEffectsSuppressed))
+ playerTarget->CastSpell(playerTarget, mountEquipment->BuffSpell, true);
+ }
+ else
+ {
+ playerTarget->RemoveOwnedAura(mountEquipment->BuffSpell);
+ playerTarget->RemoveSpell(mountEquipment->LearnedBySpell, false, false, true);
+ }
+ }
+
+ WorldPackets::Spells::ApplyMountEquipmentResult applyMountEquipmentResult;
+ applyMountEquipmentResult.ItemGUID = m_castItemGUID;
+ applyMountEquipmentResult.ItemID = m_castItemEntry;
+ applyMountEquipmentResult.Result = WorldPackets::Spells::ApplyMountEquipmentResult::Success;
+ playerTarget->SendDirectMessage(applyMountEquipmentResult.Write());
+}
+
void Spell::EffectSendChatMessage()
{
if (effectHandleMode != SPELL_EFFECT_HANDLE_HIT_TARGET)
diff --git a/src/server/scripts/Spells/spell_generic.cpp b/src/server/scripts/Spells/spell_generic.cpp
index 851836d472b..61d60fdca8a 100644
--- a/src/server/scripts/Spells/spell_generic.cpp
+++ b/src/server/scripts/Spells/spell_generic.cpp
@@ -5451,6 +5451,50 @@ class spell_bg_defending_cart_aura_AuraScript final : public AuraScript
}
};
+// 296837 - Comfortable Rider's Barding
+class spell_gen_comfortable_riders_barding : public AuraScript
+{
+ bool Validate(SpellInfo const* /*spellInfo*/) override
+ {
+ return ValidateSpellInfo({ SPELL_DAZED });
+ }
+
+ template <bool apply>
+ void HandleEffect(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/) const
+ {
+ GetTarget()->ApplySpellImmune(GetId(), IMMUNITY_ID, SPELL_DAZED, apply);
+ }
+
+ void Register() override
+ {
+ OnEffectApply += AuraEffectApplyFn(spell_gen_comfortable_riders_barding::HandleEffect<true>, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
+ OnEffectRemove += AuraEffectApplyFn(spell_gen_comfortable_riders_barding::HandleEffect<false>, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
+ }
+};
+
+// 297091 - Parachute
+class spell_gen_saddlechute : public AuraScript
+{
+ static constexpr uint32 SPELL_PARACHUTE = 297092;
+
+ bool Validate(SpellInfo const* /*spellInfo*/) override
+ {
+ return ValidateSpellInfo({ SPELL_PARACHUTE });
+ }
+
+ void TriggerParachute(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/) const
+ {
+ Unit* target = GetTarget();
+ if (target->IsFlying() || target->IsFalling())
+ target->CastSpell(target, SPELL_PARACHUTE, TRIGGERED_DONT_REPORT_CAST_ERROR);
+ }
+
+ void Register() override
+ {
+ AfterEffectRemove += AuraEffectApplyFn(spell_gen_saddlechute::TriggerParachute, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
+ }
+};
+
void AddSC_generic_spell_scripts()
{
RegisterSpellScript(spell_gen_absorb0_hitlimit1);
@@ -5632,4 +5676,6 @@ void AddSC_generic_spell_scripts()
RegisterSpellScriptWithArgs(spell_gen_set_health, "spell_gen_set_health_100", 100);
RegisterSpellScriptWithArgs(spell_gen_set_health, "spell_gen_set_health_500", 500);
RegisterSpellAndAuraScriptPair(spell_bg_defending_cart_aura, spell_bg_defending_cart_aura_AuraScript);
+ RegisterSpellScript(spell_gen_comfortable_riders_barding);
+ RegisterSpellScript(spell_gen_saddlechute);
}