[Spells] Implemented SPA 476 SE_Weapons_Stance and Live-like AA Enable/Disable Toggle (#1477)

* Work started on SPA 476

defines

* bonus structure add

bonus structure set up

* updates spa476

updates spa476

* spell bonus now functional

spell bonus working well.

* major update with debug messages

aa, item and spell now working

* Pre clean up, effect implemented

working for AA, spells, items, all checked for stacking issues.

* removed debug messages

removed debug messages

* spdat description added

spdat description added

* minor fix

removed debug shout
removed unneeded code check.

* syntax updates, minor fixes

syntax updates, minor fixes

* syntax fixes

syntax fixes

* improvements to code

moved function to check at swap item.  Easier to manage and more live like behavior. Required minor adjustment
Still working on AA toggle.

* updates to aa buy, functionalish

* Syntax / Formatting

* Add break / default to switch

* updates

* completed v2

* Major revisions

Main function check moved to when items are swapped and out of when ever bonus are recalculated.

AA Toggle and data structure now more accurate to live.

* Update aa.cpp

* debug removed

* implemented SE_Buy_AA_Rank

Closer to live.

* Update aa.cpp

broadening AA toggle to be more general use.

* improved various checks

aa toggle is now broadly implemented to be usable with any passive effect.

Co-authored-by: Akkadius <akkadius1@gmail.com>
This commit is contained in:
KayenEQ
2021-08-10 15:46:37 -04:00
committed by GitHub
parent c69446c460
commit 51ad6d65dc
12 changed files with 548 additions and 35 deletions
+229 -12
View File
@@ -1412,7 +1412,7 @@ bool Client::UpdateLDoNPoints(uint32 theme_id, int points) {
mmc_points += (mir_points + m_pp.ldon_points_mir);
mir_points = (0 - m_pp.ldon_points_mir);
}
if(m_pp.ldon_points_mmc < (0 - mmc_points)) {
ruj_points += (mmc_points + m_pp.ldon_points_mmc);
mmc_points = (0 - m_pp.ldon_points_mmc);
@@ -2419,9 +2419,9 @@ bool Client::CheckIncreaseSkill(EQ::skills::SkillType skillid, Mob *against_who,
parse->EventPlayer(EVENT_USE_SKILL, this, buffer, 0);
if (against_who) {
if (
against_who->GetSpecialAbility(IMMUNE_AGGRO) ||
against_who->GetSpecialAbility(IMMUNE_AGGRO_CLIENT) ||
against_who->IsClient() ||
against_who->GetSpecialAbility(IMMUNE_AGGRO) ||
against_who->GetSpecialAbility(IMMUNE_AGGRO_CLIENT) ||
against_who->IsClient() ||
GetLevelCon(against_who->GetLevel()) == CON_GRAY
) {
//false by default
@@ -9966,7 +9966,7 @@ void Client::MovePCDynamicZone(const std::string& zone_name, int zone_version, b
MovePCDynamicZone(zone_id, zone_version, msg_if_invalid);
}
void Client::Fling(float value, float target_x, float target_y, float target_z, bool ignore_los, bool clipping) {
void Client::Fling(float value, float target_x, float target_y, float target_z, bool ignore_los, bool clipping) {
BuffFadeByEffect(SE_Levitate);
if (CheckLosFN(target_x, target_y, target_z, 6.0f) || ignore_los) {
auto outapp_fling = new EQApplicationPacket(OP_Fling, sizeof(fling_struct));
@@ -9975,7 +9975,7 @@ void Client::Fling(float value, float target_x, float target_y, float target_z,
flingTo->collision = 0;
else
flingTo->collision = -1;
flingTo->travel_time = -1;
flingTo->unk3 = 1;
flingTo->disable_fall_damage = 1;
@@ -10030,7 +10030,7 @@ std::vector<int> Client::GetLearnableDisciplines(uint8 min_level, uint8 max_leve
if (learnable) {
learnable_disciplines.push_back(spell_id);
}
}
}
return learnable_disciplines;
}
@@ -10040,7 +10040,7 @@ std::vector<int> Client::GetLearnedDisciplines() {
if (IsValidSpell(m_pp.disciplines.values[index])) {
learned_disciplines.push_back(m_pp.disciplines.values[index]);
}
}
}
return learned_disciplines;
}
@@ -10050,7 +10050,7 @@ std::vector<int> Client::GetMemmedSpells() {
if (IsValidSpell(m_pp.mem_spells[index])) {
memmed_spells.push_back(m_pp.mem_spells[index]);
}
}
}
return memmed_spells;
}
@@ -10096,7 +10096,7 @@ std::vector<int> Client::GetScribeableSpells(uint8 min_level, uint8 max_level) {
if (scribeable) {
scribeable_spells.push_back(spell_id);
}
}
}
return scribeable_spells;
}
@@ -10174,7 +10174,7 @@ void Client::SendToInstance(std::string instance_type, std::string zone_short_na
return;
}
DataBucket::SetData(full_bucket_name, itoa(instance_id), itoa(duration));
DataBucket::SetData(full_bucket_name, itoa(instance_id), itoa(duration));
}
AssignToInstance(instance_id);
@@ -10221,7 +10221,7 @@ void Client::RemoveItem(uint32 item_id, uint32 quantity)
};
int removed_count = 0;
const size_t size = sizeof(slots) / sizeof(slots[0]);
for (int slot_index = 0; slot_index < size; ++slot_index) {
for (int slot_index = 0; slot_index < size; ++slot_index) {
for (int slot_id = slots[slot_index][0]; slot_id <= slots[slot_index][1]; ++slot_id) {
if (removed_count == quantity) {
break;
@@ -10249,3 +10249,220 @@ void Client::SetGMStatus(int newStatus) {
if (this->Admin() != newStatus)
database.UpdateGMStatus(this->AccountID(), newStatus);
}
void Client::ApplyWeaponsStance()
{
/*
If you have a weapons stance bonus from at least one bonus type, each time you change weapons this function will ensure the correct
associated buffs are applied, and previous buff is removed. If your weapon stance bonus is completely removed it will, ensure buff is
also removed (ie, removing an item that has worn effect with weapon stance, or clicking off a buff). If client no longer has/never had
any spells/item/aa bonuses with weapon stance effect this function will only do a simple bool check.
Note: Live like behavior is once you have the triggered buff you can manually click it off to remove it. Swaping any items in inventory will
reapply it automatically.
Only buff spells should be used as triggered spell effect. IsBuffSpell function also checks spell id validity.
WeaponStance bonus arrary: 0=2H Weapon 1=Shield 2=Dualweild
Toggling ON or OFF
- From spells, just remove the Primary buff that contains the WeaponStance effect in it.
- For items with worn effect, unequip the item.
- For AA abilities, a hotkey is used to Enable and Disable the effect. See. Client::TogglePassiveAlternativeAdvancement in aa.cpp for extensive details.
Rank
- Most important for AA, but if you have more than one of WeaponStance effect for a given type, the spell trigger buff will apply whatever has the highest
'rank' value from the spells table. AA's on live for this effect naturally do this. Be awere of this if making custom spells/worn effects/AA.
When creating weapon stance effects, you do not need to use all three types. For example, can make an effect where you only get a buff from equiping shield.
*/
if (!IsWeaponStanceEnabled()) {
return;
}
bool enabled = false;
bool item_bonus_exists = false;
bool aa_bonus_exists = false;
if (weaponstance.spellbonus_enabled) {
if (spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_2H] || spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD] ||
spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD]) {
enabled = true;
// Check if no longer has correct combination of weapon type and buff, if so remove buff.
if (!HasTwoHanderEquipped() && IsBuffSpell(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_2H]) &&
FindBuff(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_2H])) {
BuffFadeBySpellID(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_2H]);
}
else if (!HasShieldEquiped() && IsBuffSpell(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD]) &&
FindBuff(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD])) {
BuffFadeBySpellID(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD]);
}
else if (!HasDualWeaponsEquiped() &&
IsBuffSpell(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD]) &&
FindBuff(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD])) {
BuffFadeBySpellID(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD]);
}
// If you have correct combination of weapon type and bonus, and do not already have buff, then apply buff.
if (HasTwoHanderEquipped() && IsBuffSpell(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_2H])) {
if (!FindBuff(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_2H])) {
SpellOnTarget(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_2H], this);
}
weaponstance.spellbonus_buff_spell_id = spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_2H];
}
else if (HasShieldEquiped() && IsBuffSpell(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD])) {
if (!FindBuff(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD])) {
SpellOnTarget(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD], this);
}
weaponstance.spellbonus_buff_spell_id = spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD];
}
else if (HasDualWeaponsEquiped() && IsBuffSpell(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD])) {
if (!FindBuff(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD])) {
SpellOnTarget(spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD], this);
}
weaponstance.spellbonus_buff_spell_id = spellbonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD];
}
}
}
// Spellbonus effect removal is checked in BuffFadeBySlot(int slot, bool iRecalcBonuses) in spell_effects.cpp when the buff is clicked off or fades.
if (weaponstance.itembonus_enabled) {
if (itembonuses.WeaponStance[WEAPON_STANCE_TYPE_2H] || itembonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD] ||
itembonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD]) {
enabled = true;
item_bonus_exists = true;
// Edge case check if have multiple items with WeaponStance worn effect. Make sure correct buffs are applied if items are removed but others left on.
if (weaponstance.itembonus_buff_spell_id) {
bool buff_desync = true;
if (weaponstance.itembonus_buff_spell_id == itembonuses.WeaponStance[WEAPON_STANCE_TYPE_2H] ||
weaponstance.itembonus_buff_spell_id == itembonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD] ||
(weaponstance.itembonus_buff_spell_id == itembonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD])) {
buff_desync = false;
}
if (buff_desync) {
int fade_spell = weaponstance.itembonus_buff_spell_id;
weaponstance.itembonus_buff_spell_id = 0; //Need to zero this before we fade to prevent any recursive loops.
BuffFadeBySpellID(fade_spell);
}
}
// Check if no longer has correct combination of weapon type and buff, if so remove buff.
if (!HasTwoHanderEquipped() && IsBuffSpell(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_2H]) &&
FindBuff(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_2H])) {
BuffFadeBySpellID(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_2H]);
}
else if (!HasShieldEquiped() && IsBuffSpell(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD]) &&
FindBuff(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD])) {
BuffFadeBySpellID(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD]);
}
else if (!HasDualWeaponsEquiped() && IsBuffSpell(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD]) &&
FindBuff(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD])) {
BuffFadeBySpellID(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD]);
}
// If you have correct combination of weapon type and bonus, and do not already have buff, then apply buff.
if (HasTwoHanderEquipped() && IsBuffSpell(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_2H])) {
if (!FindBuff(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_2H])) {
SpellOnTarget(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_2H], this);
}
weaponstance.itembonus_buff_spell_id = itembonuses.WeaponStance[WEAPON_STANCE_TYPE_2H];
}
else if (HasShieldEquiped() && IsBuffSpell(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD])) {
if (!FindBuff(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD])) {
SpellOnTarget(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD], this);
}
weaponstance.itembonus_buff_spell_id = itembonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD];
}
else if (HasDualWeaponsEquiped() && IsBuffSpell(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD])) {
if (!FindBuff(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD])) {
SpellOnTarget(itembonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD], this);
}
weaponstance.itembonus_buff_spell_id = itembonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD];
}
}
}
// Itembonus effect removal when item is removed
if (!item_bonus_exists && weaponstance.itembonus_enabled) {
weaponstance.itembonus_enabled = false;
if (weaponstance.itembonus_buff_spell_id) {
BuffFadeBySpellID(weaponstance.itembonus_buff_spell_id);
weaponstance.itembonus_buff_spell_id = 0;
}
}
if (weaponstance.aabonus_enabled) {
if (aabonuses.WeaponStance[WEAPON_STANCE_TYPE_2H] || aabonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD] ||
aabonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD]) {
enabled = true;
aa_bonus_exists = true;
//Check if no longer has correct combination of weapon type and buff, if so remove buff.
if (!HasTwoHanderEquipped() && IsBuffSpell(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_2H]) &&
FindBuff(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_2H])) {
BuffFadeBySpellID(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_2H]);
}
else if (!HasShieldEquiped() && IsBuffSpell(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD]) &&
FindBuff(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD])) {
BuffFadeBySpellID(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD]);
}
else if (!HasDualWeaponsEquiped() && IsBuffSpell(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD]) &&
FindBuff(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD])) {
BuffFadeBySpellID(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD]);
}
//If you have correct combination of weapon type and bonus, and do not already have buff, then apply buff.
if (HasTwoHanderEquipped() && IsBuffSpell(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_2H])) {
if (!FindBuff(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_2H])) {
SpellOnTarget(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_2H], this);
}
weaponstance.aabonus_buff_spell_id = aabonuses.WeaponStance[WEAPON_STANCE_TYPE_2H];
}
else if (HasShieldEquiped() && IsBuffSpell(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD])) {
if (!FindBuff(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD])) {
SpellOnTarget(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD], this);
}
weaponstance.aabonus_buff_spell_id = aabonuses.WeaponStance[WEAPON_STANCE_TYPE_SHIELD];
}
else if (HasDualWeaponsEquiped() && IsBuffSpell(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD])) {
if (!FindBuff(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD])) {
SpellOnTarget(aabonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD], this);
}
weaponstance.aabonus_buff_spell_id = aabonuses.WeaponStance[WEAPON_STANCE_TYPE_DUAL_WIELD];
}
}
}
// AA bonus removal is checked in TogglePassiveAA in aa.cpp. when the hot key is toggled.
// If no bonuses remain present, prevent additional future checks until new bonus is applied.
if (!enabled) {
SetWeaponStanceEnabled(false);
weaponstance.aabonus_enabled = false;
weaponstance.itembonus_enabled = false;
weaponstance.spellbonus_enabled = false;
}
}