diff --git a/common/eq_constants.h b/common/eq_constants.h index 6bd4beef5..44beffd25 100644 --- a/common/eq_constants.h +++ b/common/eq_constants.h @@ -758,10 +758,10 @@ typedef enum { FilterFocusEffects = 22, //0=show, 1=hide FilterPetSpells = 23, //0=show, 1=hide FilterHealOverTime = 24, //0=show, 1=mine only, 2=hide - FilterUnknown25 = 25, - FilterUnknown26 = 26, - FilterUnknown27 = 27, - FilterUnknown28 = 28, + FilterItemSpeech = 25, //0=show, 1=hide // RoF2 Confirmed + FilterStrikethrough = 26, //0=show, 1=hide // RoF2 Confirmed + FilterStuns = 27, //0=show, 1=hide // RoF2 Confirmed + FilterBardSongsOnPets = 28, //0=show, 1=hide // RoF2 Confirmed _FilterCount } eqFilterType; diff --git a/common/ruletypes.h b/common/ruletypes.h index 8fe67be66..9d5d94bd8 100644 --- a/common/ruletypes.h +++ b/common/ruletypes.h @@ -725,6 +725,7 @@ RULE_INT(Range, SpellParticles, 135, "The packet range in which spell particles RULE_INT(Range, DamageMessages, 50, "The packet range in which damage messages are sent (non-crit)") RULE_INT(Range, SpellMessages, 75, "The packet range in which spell damage messages are sent") RULE_INT(Range, SongMessages, 75, "The packet range in which song messages are sent") +RULE_INT(Range, StunMessages, 75, "The packet range in which stun messages are sent") RULE_INT(Range, ClientPositionUpdates, 300, "Distance in which the own changed position is communicated to other clients") RULE_INT(Range, CriticalDamage, 80, "The packet range in which critical hit messages are sent") RULE_INT(Range, MobCloseScanDistance, 600, "Close scan distance") diff --git a/zone/attack.cpp b/zone/attack.cpp index d404998cc..3c63a71a0 100644 --- a/zone/attack.cpp +++ b/zone/attack.cpp @@ -1478,8 +1478,10 @@ int64 Mob::DoDamageCaps(int64 base_damage) //SYNC WITH: tune.cpp, mob.h TuneDoAttack void Mob::DoAttack(Mob *other, DamageHitInfo &hit, ExtraAttackOptions *opts, bool FromRiposte) { - if (!other) + if (!other) { return; + } + LogCombat("[{}]::DoAttack vs [{}] base [{}] min [{}] offense [{}] tohit [{}] skill [{}]", GetName(), other->GetName(), hit.base_damage, hit.min_damage, hit.offense, hit.tohit, hit.skill); @@ -1491,14 +1493,22 @@ void Mob::DoAttack(Mob *other, DamageHitInfo &hit, ExtraAttackOptions *opts, boo if (!FromRiposte && other->AvoidDamage(this, hit)) { if (int strike_through = itembonuses.StrikeThrough + spellbonuses.StrikeThrough + aabonuses.StrikeThrough; strike_through && zone->random.Roll(strike_through)) { - MessageString(Chat::StrikeThrough, - STRIKETHROUGH_STRING); // You strike through your opponents defenses! + + FilteredMessageString( + this, /* Sender */ + Chat::StrikeThrough, /* Type: 339 */ + FilterStrikethrough, /* FilterType: 12 */ + STRIKETHROUGH_STRING /* You strike through your opponent's defenses! */ + ); + hit.damage_done = 1; // set to one, we will check this to continue } + if (hit.damage_done == DMG_RIPOSTED) { DoRiposte(other); return; } + LogCombat("Avoided/strikethrough damage with code [{}]", hit.damage_done); } @@ -1510,9 +1520,19 @@ void Mob::DoAttack(Mob *other, DamageHitInfo &hit, ExtraAttackOptions *opts, boo int stun_resist2 = other->spellbonuses.FrontalStunResist + other->itembonuses.FrontalStunResist + other->aabonuses.FrontalStunResist; int stun_resist = other->spellbonuses.StunResist + other->itembonuses.StunResist + other->aabonuses.StunResist; if (zone->random.Roll(stun_resist2)) { - other->MessageString(Chat::Stun, AVOID_STUNNING_BLOW); + other->FilteredMessageString( + this, + Chat::Stun, + FilterStuns, + AVOID_STUNNING_BLOW + ); } else if (zone->random.Roll(stun_resist)) { - other->MessageString(Chat::Stun, SHAKE_OFF_STUN); + other->FilteredMessageString( + this, + Chat::Stun, + FilterStuns, + SHAKE_OFF_STUN + ); } else { other->Stun(3000); // yuck -- 3 seconds } @@ -4506,32 +4526,59 @@ void Mob::CommonDamage(Mob* attacker, int64 &damage, const uint16 spell_id, cons Stun(RuleI(Combat, StunDuration)); if (RuleB(Combat, ClientStunMessage) && attacker->IsClient()) { if (attacker) { - entity_list.MessageClose(this, true, 500, Chat::Emote, "%s is stunned after being bashed by %s.", GetCleanName(), attacker->GetCleanName()); - } - else { - entity_list.MessageClose(this, true, 500, Chat::Emote, "%s is stunned by a bash to the head.", GetCleanName()); + entity_list.FilteredMessageClose( + this, + true, + RuleI(Range, StunMessages), + Chat::Stun, + FilterStuns, + "%s is stunned after being bashed by %s.", + GetCleanName(), + attacker->GetCleanName() + ); + } else { + entity_list.FilteredMessageClose( + this, + true, + RuleI(Range, StunMessages), + Chat::Stun, + FilterStuns, + "%s is stunned by a bash to the head.", + GetCleanName() + ); } } - } - else { + } else { // stun resist passed! - if (IsClient()) - MessageString(Chat::Stun, SHAKE_OFF_STUN); + if (IsClient()) { + FilteredMessageString( + this, + Chat::Stun, + FilterStuns, + SHAKE_OFF_STUN + ); + } + } + } else { + // stun resist 2 passed! + if (IsClient()) { + FilteredMessageString( + this, + Chat::Stun, + FilterStuns, + AVOID_STUNNING_BLOW + ); } } - else { - // stun resist 2 passed! - if (IsClient()) - MessageString(Chat::Stun, AVOID_STUNNING_BLOW); - } - } - else { + } else { // main stun failed -- extra interrupt roll - if (IsCasting() && - !EQ::ValueWithin(casting_spell_id, 859, 1023)) // these spells are excluded - // 90% chance >< -- stun immune won't reach this branch though :( - if (zone->random.Int(0, 9) > 1) + // these spells are excluded + // 90% chance >< -- stun immune won't reach this branch though :( + if (IsCasting() && !EQ::ValueWithin(casting_spell_id, 859, 1023)) { + if (zone->random.Int(0, 9) > 1) { InterruptSpell(); + } + } } } diff --git a/zone/client.cpp b/zone/client.cpp index 1aa4aca3a..4b705e24e 100644 --- a/zone/client.cpp +++ b/zone/client.cpp @@ -3403,6 +3403,11 @@ void Client::ServerFilter(SetServerFilter_Struct* filter){ } else { // these clients don't have a 'self only' filter Filter1(FilterHealOverTime); } + + Filter1(FilterItemSpeech); + Filter1(FilterStrikethrough); + Filter1(FilterStuns); + Filter1(FilterBardSongsOnPets); } // this version is for messages with no parameters @@ -12700,4 +12705,4 @@ bool Client::TakeMoneyFromPPWithOverFlow(uint64 copper, bool update_client) SaveCurrency(); RecalcWeight(); return true; -} \ No newline at end of file +} diff --git a/zone/lua_general.cpp b/zone/lua_general.cpp index 270a13a0b..eddbc3473 100644 --- a/zone/lua_general.cpp +++ b/zone/lua_general.cpp @@ -7256,10 +7256,10 @@ luabind::scope lua_register_filters() { luabind::value("FocusEffects", FilterFocusEffects), luabind::value("PetSpells", FilterPetSpells), luabind::value("HealOverTime", FilterHealOverTime), - luabind::value("Unknown25", FilterUnknown25), - luabind::value("Unknown26", FilterUnknown26), - luabind::value("Unknown27", FilterUnknown27), - luabind::value("Unknown28", FilterUnknown28) + luabind::value("ItemSpeech", FilterItemSpeech), + luabind::value("Strikethrough", FilterStrikethrough), + luabind::value("Stuns", FilterStuns), + luabind::value("BardSongsOnPets", FilterBardSongsOnPets) )]; }