ATKpercent, Base Damage, Occult Impaction, Freezing Trap, Acid Terror, Paladin skills (#8210)
- A handful of skills grant status changes that actually are calculated together into a value "ATKpercent" rather than increasing BATK/WATK, this value is then applied to most weapon skills * Pre-re - Damage after skill ratio but before DEF reduction is multiplied with ATKpercent * Renewal - Is a linear addition to skill ratio instead (ATKpercent of 200 means +100% to any skill ratio, so 100% becomes 200%, but 500% only becomes 600%) * For further information which status changes go into ATKpercent and which skills are not influenced by it, please see the battle_get_atkpercent function - Fixed base damage not being calculated correctly for certain skills - MO_INVESTIGATE is no longer influenced by Spirit Spheres except when you have the WATK_ELEMENT effect (Magnum Break) - Freezing trap now deals 100% damage on all levels and can miss - Acid Terror now ignores DEF, but its base attack is reduced by VIT - Acid Terror skill ratio is now 50%+50%*level - Acid Terror and Martyr's Reckoning (PA_SACRIFICE) are no longer affected by refine and mastery bonus - Magnum Break/EDP bonus no longer affects Acid Terror and unit skills - Fixed damage formula of Shield Boomerang and Rapid Smiting - Code improvements - Fixes #8193
This commit is contained in:
parent
23787bdfa4
commit
4247bc50c5
@ -4408,7 +4408,6 @@ Body:
|
||||
TargetType: Ground
|
||||
DamageFlags:
|
||||
Splash: true
|
||||
IgnoreFlee: true
|
||||
Flags:
|
||||
IsTrap: true
|
||||
AlterRangeResearchTrap: true
|
||||
@ -6461,6 +6460,7 @@ Body:
|
||||
TargetType: Attack
|
||||
DamageFlags:
|
||||
IgnoreAtkCard: true
|
||||
IgnoreDefense: true
|
||||
IgnoreFlee: true
|
||||
Flags:
|
||||
IgnoreAutoGuard: true
|
||||
@ -32636,7 +32636,6 @@ Body:
|
||||
TargetType: Ground
|
||||
DamageFlags:
|
||||
Splash: true
|
||||
IgnoreFlee: true
|
||||
Flags:
|
||||
IsTrap: true
|
||||
AlterRangeResearchTrap: true
|
||||
|
@ -41,6 +41,7 @@ static struct eri *delay_damage_ers; //For battle delay damage structures.
|
||||
int battle_get_weapon_element(struct Damage *wd, struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv, short weapon_position, bool calc_for_damage_only);
|
||||
int battle_get_magic_element(struct block_list* src, struct block_list* target, uint16 skill_id, uint16 skill_lv, int mflag);
|
||||
int battle_get_misc_element(struct block_list* src, struct block_list* target, uint16 skill_id, uint16 skill_lv, int mflag);
|
||||
static void battle_calc_defense_reduction(struct Damage* wd, struct block_list* src, struct block_list* target, uint16 skill_id, uint16 skill_lv);
|
||||
|
||||
/**
|
||||
* Returns the current/list skill used by the bl
|
||||
@ -3365,7 +3366,9 @@ static bool battle_skill_stacks_masteries_vvs(uint16 skill_id)
|
||||
if (
|
||||
#ifndef RENEWAL
|
||||
skill_id == PA_SHIELDCHAIN || skill_id == CR_SHIELDBOOMERANG ||
|
||||
skill_id == PA_SACRIFICE || skill_id == AM_ACIDTERROR ||
|
||||
#endif
|
||||
skill_id == MO_INVESTIGATE || skill_id == MO_EXTREMITYFIST ||
|
||||
skill_id == RK_DRAGONBREATH || skill_id == RK_DRAGONBREATH_WATER || skill_id == NC_SELFDESTRUCTION ||
|
||||
skill_id == LG_SHIELDPRESS || skill_id == LG_EARTHDRIVE)
|
||||
return false;
|
||||
@ -3657,11 +3660,13 @@ static void battle_calc_element_damage(struct Damage* wd, struct block_list *src
|
||||
|
||||
#ifndef RENEWAL
|
||||
if (sd && (wd->damage > 0 || wd->damage2 > 0)) { // Applies only to player damage, monsters and mercenaries don't get this damage boost
|
||||
if (sc && sc->getSCE(SC_WATK_ELEMENT)) { // Descriptions indicate this means adding a percent of a normal attack in another element [Skotlex]
|
||||
// This adds a percentual damage bonus based on the damage you would deal with a normal attack
|
||||
// Does not apply to unit skills or skills that have their own base damage formula such as AM_ACIDTERROR
|
||||
if (sc && sc->getSCE(SC_WATK_ELEMENT) && !skill_get_unit_id(skill_id) && skill_id != AM_ACIDTERROR) {
|
||||
int64 damage = wd->basedamage * sc->getSCE(SC_WATK_ELEMENT)->val2;
|
||||
damage = battle_attr_fix(src, target, damage, sc->getSCE(SC_WATK_ELEMENT)->val1, tstatus->def_ele, tstatus->ele_lv, 1);
|
||||
//Spirit Sphere bonus damage is not affected by element
|
||||
if (skill_id == MO_FINGEROFFENSIVE) { //Need to calculate number of Spirit Balls you had before cast
|
||||
if (skill_id == MO_FINGEROFFENSIVE || skill_id == MO_INVESTIGATE) { //Need to calculate number of Spirit Balls you had before cast
|
||||
damage += ((wd->div_ + sd->spiritball) * 3 * sc->getSCE(SC_WATK_ELEMENT)->val2);
|
||||
}
|
||||
else
|
||||
@ -3720,21 +3725,24 @@ static void battle_calc_attack_masteries(struct Damage* wd, struct block_list *s
|
||||
struct status_data *sstatus = status_get_status_data(src);
|
||||
int t_class = status_get_class(target);
|
||||
|
||||
if (sd && battle_skill_stacks_masteries_vvs(skill_id) &&
|
||||
skill_id != MO_INVESTIGATE &&
|
||||
skill_id != MO_EXTREMITYFIST &&
|
||||
skill_id != CR_GRANDCROSS)
|
||||
if (sd) {
|
||||
wd->basedamage = battle_addmastery(sd, target, wd->basedamage, 0);
|
||||
if (is_attack_left_handed(src, skill_id)) {
|
||||
wd->basedamage2 = battle_addmastery(sd, target, wd->basedamage2, 1);
|
||||
}
|
||||
}
|
||||
|
||||
// Grand Cross is confirmed to be affected by refine bonus but not masteries
|
||||
if (sd && battle_skill_stacks_masteries_vvs(skill_id) && skill_id != CR_GRANDCROSS)
|
||||
{ //Add mastery damage
|
||||
uint16 skill;
|
||||
|
||||
wd->damage = battle_addmastery(sd,target,wd->damage,0);
|
||||
wd->basedamage = battle_addmastery(sd, target, wd->basedamage, 0);
|
||||
#ifdef RENEWAL
|
||||
wd->masteryAtk = battle_addmastery(sd,target,wd->weaponAtk,0);
|
||||
#endif
|
||||
if (is_attack_left_handed(src, skill_id)) {
|
||||
wd->damage2 = battle_addmastery(sd,target,wd->damage2,1);
|
||||
wd->basedamage2 = battle_addmastery(sd, target, wd->basedamage2, 1);
|
||||
#ifdef RENEWAL
|
||||
wd->masteryAtk2 = battle_addmastery(sd,target,wd->weaponAtk2,1);
|
||||
#endif
|
||||
@ -3972,12 +3980,19 @@ static void battle_calc_skill_base_damage(struct Damage* wd, struct block_list *
|
||||
if (sd) {
|
||||
short index = sd->equip_index[EQI_HAND_L];
|
||||
|
||||
//Base damage of shield skills is [batk + 4*refine + weight]
|
||||
if (index >= 0 && sd->inventory_data[index] && sd->inventory_data[index]->type == IT_ARMOR) {
|
||||
ATK_ADD(wd->damage, wd->damage2, 4 * sd->inventory.u.items_inventory[index].refine);
|
||||
ATK_ADD(wd->damage, wd->damage2, sd->inventory_data[index]->weight / 10);
|
||||
#ifdef RENEWAL
|
||||
ATK_ADD(wd->weaponAtk, wd->weaponAtk2, 4 * sd->inventory.u.items_inventory[index].refine);
|
||||
ATK_ADD(wd->weaponAtk, wd->weaponAtk2, sd->inventory_data[index]->weight / 10);
|
||||
#endif
|
||||
}
|
||||
#ifndef RENEWAL
|
||||
// Shield Boomerang and Rapid Smiting calculate DEF before the skill ratio
|
||||
battle_calc_defense_reduction(wd, src, target, skill_id, skill_lv);
|
||||
#endif
|
||||
} else
|
||||
ATK_ADD(wd->damage, wd->damage2, sstatus->rhw.atk2); //Else use Atk2
|
||||
break;
|
||||
@ -4119,6 +4134,9 @@ static void battle_calc_skill_base_damage(struct Damage* wd, struct block_list *
|
||||
if (tsd != nullptr && tsd->bonus.crit_def_rate != 0 && !skill_id && (bflag & BDMG_CRIT)) {
|
||||
ATK_ADDRATE(wd->damage, wd->damage2, -tsd->bonus.crit_def_rate);
|
||||
}
|
||||
//Acid Terror ignores DEF but will substract VIT from base attack value instead
|
||||
if (skill_id == AM_ACIDTERROR)
|
||||
ATK_ADD(wd->damage, wd->damage2, -tstatus->def2);
|
||||
#endif
|
||||
break;
|
||||
} //End switch(skill_id)
|
||||
@ -4287,6 +4305,74 @@ static void battle_calc_multi_attack(struct Damage* wd, struct block_list *src,s
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Calculates the percentual attack modificator (ATKpercent) based on status changes
|
||||
* These bonuses are added together and the percent is applied to the damage before the defense reduction in pre-renewal
|
||||
* In renewal this simply sets the base skillratio before the actual skill ratio of the skill used is added
|
||||
* This bonus works as a separate unit to the rest (e.g., if one of these is not applied to a skill, then we know none are)
|
||||
* Do not add additional status changes here unless they are confirmed to use ATKpercent
|
||||
* @param bl: Object to calc atkpercent for
|
||||
* @param skill_id: Skill used by object
|
||||
* @param sc: Object's status change information
|
||||
* @return atkpercent with cap_value(watk,0,USHRT_MAX)
|
||||
*/
|
||||
static unsigned short battle_get_atkpercent(struct block_list* bl, uint16 skill_id, status_change* sc)
|
||||
{
|
||||
//These skills are not affected by ATKpercent
|
||||
switch (skill_id) {
|
||||
#ifndef RENEWAL
|
||||
// Need to be confirmed for renewal as masteries have been coded to apply to those two in renewal
|
||||
case PA_SHIELDCHAIN:
|
||||
case CR_SHIELDBOOMERANG:
|
||||
#endif
|
||||
case AM_ACIDTERROR:
|
||||
case CR_GRANDCROSS:
|
||||
case NPC_GRANDDARKNESS:
|
||||
case MO_INVESTIGATE:
|
||||
case MO_EXTREMITYFIST:
|
||||
case PA_SACRIFICE:
|
||||
case NPC_DRAGONBREATH:
|
||||
case RK_DRAGONBREATH:
|
||||
case RK_DRAGONBREATH_WATER:
|
||||
return 100;
|
||||
}
|
||||
|
||||
int atkpercent = 100;
|
||||
|
||||
if (sc->getSCE(SC_CURSE))
|
||||
atkpercent -= 25;
|
||||
if (sc->getSCE(SC_PROVOKE))
|
||||
atkpercent += sc->getSCE(SC_PROVOKE)->val2;
|
||||
if (sc->getSCE(SC_STRIPWEAPON) && bl->type != BL_PC)
|
||||
atkpercent -= sc->getSCE(SC_STRIPWEAPON)->val2;
|
||||
if (sc->getSCE(SC_CONCENTRATION))
|
||||
atkpercent += sc->getSCE(SC_CONCENTRATION)->val2;
|
||||
if (sc->getSCE(SC_TRUESIGHT))
|
||||
atkpercent += 2 * sc->getSCE(SC_TRUESIGHT)->val1;
|
||||
if (sc->getSCE(SC_JOINTBEAT) && sc->getSCE(SC_JOINTBEAT)->val2 & BREAK_WAIST)
|
||||
atkpercent -= 25;
|
||||
if (sc->getSCE(SC_INCATKRATE))
|
||||
atkpercent += sc->getSCE(SC_INCATKRATE)->val1;
|
||||
if (sc->getSCE(SC_SKE))
|
||||
atkpercent += 300;
|
||||
if (sc->getSCE(SC_BLOODLUST))
|
||||
atkpercent += sc->getSCE(SC_BLOODLUST)->val2;
|
||||
if (sc->getSCE(SC_FLEET))
|
||||
atkpercent += sc->getSCE(SC_FLEET)->val3;
|
||||
|
||||
/* Only few selected skills should use this function, DO NOT ADD any that are not caused by the skills listed below
|
||||
* TODO:
|
||||
* NPC_INVINCIBLE (+100)
|
||||
* GD_GUARDUP (2*skLevel+8)
|
||||
* EL_WATERBARRIER (-3)
|
||||
* SC_ENERVATION (-30/-40/-50)
|
||||
* MH_EQC (skLevel*5)
|
||||
* MH_VOLCANIC_ASH (-50)
|
||||
*/
|
||||
|
||||
return (unsigned short)cap_value(atkpercent, 0, USHRT_MAX);
|
||||
}
|
||||
|
||||
/*======================================================
|
||||
* Calculate skill level ratios for weapon-based skills
|
||||
*------------------------------------------------------
|
||||
@ -4308,6 +4394,10 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
||||
|
||||
//Skill damage modifiers that stack linearly
|
||||
if(sc && skill_id != PA_SACRIFICE) {
|
||||
#ifdef RENEWAL
|
||||
//ATK percent modifier (in renewal, it's applied before the skillratio)
|
||||
skillratio = battle_get_atkpercent(src, skill_id, sc);
|
||||
#endif
|
||||
if(sc->getSCE(SC_OVERTHRUST))
|
||||
skillratio += sc->getSCE(SC_OVERTHRUST)->val3;
|
||||
if(sc->getSCE(SC_MAXOVERTHRUST))
|
||||
@ -4317,10 +4407,6 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
||||
skillratio += 100;
|
||||
#else
|
||||
skillratio += 200;
|
||||
if (sc && sc->getSCE(SC_TRUESIGHT))
|
||||
skillratio += 2 * sc->getSCE(SC_TRUESIGHT)->val1;
|
||||
if (sc->getSCE(SC_CONCENTRATION) && (skill_id != RK_DRAGONBREATH && skill_id != RK_DRAGONBREATH_WATER && skill_id != NPC_DRAGONBREATH))
|
||||
skillratio += sc->getSCE(SC_CONCENTRATION)->val2;
|
||||
#endif
|
||||
if (!skill_id || skill_id == KN_AUTOCOUNTER) {
|
||||
if (sc->getSCE(SC_CRUSHSTRIKE)) {
|
||||
@ -4378,12 +4464,6 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
||||
case MA_CHARGEARROW:
|
||||
skillratio += 50;
|
||||
break;
|
||||
#ifndef RENEWAL
|
||||
case HT_FREEZINGTRAP:
|
||||
case MA_FREEZINGTRAP:
|
||||
skillratio += -50 + 10 * skill_lv;
|
||||
break;
|
||||
#endif
|
||||
case KN_PIERCE:
|
||||
skillratio += 10 * skill_lv;
|
||||
if (sc && sc->getSCE(SC_CHARGINGPIERCE_COUNT) && sc->getSCE(SC_CHARGINGPIERCE_COUNT)->val1 >= 10)
|
||||
@ -4533,7 +4613,7 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
||||
if (sd && pc_checkskill(sd, AM_LEARNINGPOTION))
|
||||
skillratio += 100; // !TODO: What's this bonus increase?
|
||||
#else
|
||||
skillratio += 40 * skill_lv;
|
||||
skillratio += -50 + 50 * skill_lv;
|
||||
#endif
|
||||
break;
|
||||
case MO_FINGEROFFENSIVE:
|
||||
@ -6151,10 +6231,9 @@ static void battle_attack_sc_bonus(struct Damage* wd, struct block_list *src, st
|
||||
if (sc->getSCE(SC_GATLINGFEVER))
|
||||
ATK_ADD(wd->equipAtk, wd->equipAtk2, sc->getSCE(SC_GATLINGFEVER)->val3);
|
||||
#else
|
||||
if (sc->getSCE(SC_TRUESIGHT)) {
|
||||
ATK_ADDRATE(wd->damage, wd->damage2, 2 * sc->getSCE(SC_TRUESIGHT)->val1);
|
||||
ATK_ADDRATE(wd->basedamage, wd->basedamage2, 2 * sc->getSCE(SC_TRUESIGHT)->val1);
|
||||
}
|
||||
//ATK percent modifier (in pre-renewal, it's applied multiplicatively after the skill ratio)
|
||||
ATK_RATE(wd->damage, wd->damage2, battle_get_atkpercent(src, skill_id, sc));
|
||||
ATK_RATE(wd->basedamage, wd->basedamage2, battle_get_atkpercent(src, 0, sc));
|
||||
#endif
|
||||
if (sc->getSCE(SC_SPIRIT)) {
|
||||
if (skill_id == AS_SONICBLOW && sc->getSCE(SC_SPIRIT)->val2 == SL_ASSASIN) {
|
||||
@ -6377,16 +6456,15 @@ static void battle_calc_defense_reduction(struct Damage* wd, struct block_list *
|
||||
def2 -= (target_count - (battle_config.vit_penalty_count - 1))*battle_config.vit_penalty_num;
|
||||
}
|
||||
}
|
||||
if (skill_id == AM_ACIDTERROR)
|
||||
#ifdef RENEWAL
|
||||
def2 = 0; //Ignore only status defense. [FatalEror]
|
||||
#else
|
||||
def1 = 0; //Ignores only armor defense. [Skotlex]
|
||||
#endif
|
||||
if(def2 < 1)
|
||||
def2 = 1;
|
||||
}
|
||||
|
||||
#ifdef RENEWAL
|
||||
if (skill_id == AM_ACIDTERROR)
|
||||
def2 = 0; // Ignore only status defense.
|
||||
#endif
|
||||
|
||||
//Damage reduction based on vitality
|
||||
if (tsd) { //Sd vit-eq
|
||||
int skill;
|
||||
@ -6466,18 +6544,12 @@ static void battle_calc_defense_reduction(struct Damage* wd, struct block_list *
|
||||
attack_ignores_def(wd, src, target, skill_id, skill_lv, EQI_HAND_R) ?100:(is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_R) ? (int64)is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_R)*(def1+vit_def) : (100-def1)),
|
||||
attack_ignores_def(wd, src, target, skill_id, skill_lv, EQI_HAND_L) ?100:(is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_L) ? (int64)is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_L)*(def1+vit_def) : (100-def1))
|
||||
);
|
||||
ATK_RATE2(wd->basedamage, wd->basedamage2,
|
||||
attack_ignores_def(wd, src, target, skill_id, skill_lv, EQI_HAND_R) ? 100 : (is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_R) ? (int64)is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_R) * (def1 + vit_def) : (100 - def1)),
|
||||
attack_ignores_def(wd, src, target, skill_id, skill_lv, EQI_HAND_L) ? 100 : (is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_L) ? (int64)is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_L) * (def1 + vit_def) : (100 - def1))
|
||||
);
|
||||
ATK_RATE(wd->basedamage, wd->basedamage2, 100 - def1);
|
||||
ATK_ADD2(wd->damage, wd->damage2,
|
||||
attack_ignores_def(wd, src, target, skill_id, skill_lv, EQI_HAND_R) || is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_R) ?0:-vit_def,
|
||||
attack_ignores_def(wd, src, target, skill_id, skill_lv, EQI_HAND_L) || is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_L) ?0:-vit_def
|
||||
);
|
||||
ATK_ADD2(wd->basedamage, wd->basedamage2,
|
||||
attack_ignores_def(wd, src, target, skill_id, skill_lv, EQI_HAND_R) || is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_R) ? 0 : -vit_def,
|
||||
attack_ignores_def(wd, src, target, skill_id, skill_lv, EQI_HAND_L) || is_attack_piercing(wd, src, target, skill_id, skill_lv, EQI_HAND_L) ? 0 : -vit_def
|
||||
);
|
||||
ATK_ADD(wd->basedamage, wd->basedamage2, -vit_def);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -6517,8 +6589,10 @@ static void battle_calc_attack_post_defense(struct Damage* wd, struct block_list
|
||||
// Post skill/vit reduction damage increases
|
||||
#ifndef RENEWAL
|
||||
//Refine bonus
|
||||
if (sd && battle_skill_stacks_masteries_vvs(skill_id) && skill_id != MO_INVESTIGATE && skill_id != MO_EXTREMITYFIST) { // Counts refine bonus multiple times
|
||||
ATK_ADD2(wd->damage, wd->damage2, sstatus->rhw.atk2, sstatus->lhw.atk2);
|
||||
if (sd) {
|
||||
if (battle_skill_stacks_masteries_vvs(skill_id)) {
|
||||
ATK_ADD2(wd->damage, wd->damage2, sstatus->rhw.atk2, sstatus->lhw.atk2);
|
||||
}
|
||||
ATK_ADD2(wd->basedamage, wd->basedamage2, sstatus->rhw.atk2, sstatus->lhw.atk2);
|
||||
}
|
||||
|
||||
@ -7184,9 +7258,13 @@ static struct Damage battle_calc_weapon_attack(struct block_list *src, struct bl
|
||||
wd.dmg_lv = ATK_FLEE;
|
||||
else if(!(infdef = is_infinite_defense(target, wd.flag))) { //no need for math against plants
|
||||
|
||||
battle_calc_skill_base_damage(&wd, src, target, skill_id, skill_lv); // base skill damage
|
||||
// First call function with skill_id 0 to get base damage of a normal attack
|
||||
battle_calc_skill_base_damage(&wd, src, target, 0, 0); // base damage
|
||||
wd.basedamage = wd.damage;
|
||||
wd.basedamage2 = wd.damage2;
|
||||
// Now get actual skill damage
|
||||
if (skill_id != 0)
|
||||
battle_calc_skill_base_damage(&wd, src, target, skill_id, skill_lv); // base skill damage
|
||||
|
||||
int64 ratio = 0;
|
||||
|
||||
@ -7347,8 +7425,14 @@ static struct Damage battle_calc_weapon_attack(struct block_list *src, struct bl
|
||||
battle_attack_sc_bonus(&wd, src, target, skill_id, skill_lv);
|
||||
#endif
|
||||
|
||||
if (wd.damage + wd.damage2) { //Check if attack ignores DEF
|
||||
if (wd.damage + wd.damage2) {
|
||||
#ifdef RENEWAL
|
||||
// Check if attack ignores DEF (in pre-renewal we need to update base damage even when the skill ignores DEF)
|
||||
if(!attack_ignores_def(&wd, src, target, skill_id, skill_lv, EQI_HAND_L) || !attack_ignores_def(&wd, src, target, skill_id, skill_lv, EQI_HAND_R))
|
||||
#else
|
||||
// Shield Boomerang and Rapid Smiting already calculated the defense before the skill ratio was applied
|
||||
if(skill_id != PA_SHIELDCHAIN && skill_id != CR_SHIELDBOOMERANG)
|
||||
#endif
|
||||
battle_calc_defense_reduction(&wd, src, target, skill_id, skill_lv);
|
||||
|
||||
battle_calc_attack_post_defense(&wd, src, target, skill_id, skill_lv);
|
||||
@ -7455,14 +7539,20 @@ static struct Damage battle_calc_weapon_attack(struct block_list *src, struct bl
|
||||
ATK_ADD(wd.damage, wd.damage2, 4);
|
||||
if (skill_id == MO_FINGEROFFENSIVE) { //Need to calculate number of Spirit Balls you had before cast
|
||||
ATK_ADD(wd.damage, wd.damage2, (wd.div_ + sd->spiritball) * 3);
|
||||
} else
|
||||
} else if (skill_id != MO_INVESTIGATE)
|
||||
ATK_ADD(wd.damage, wd.damage2, ((wd.div_ < 1) ? 1 : wd.div_) * sd->spiritball * 3);
|
||||
#endif
|
||||
if( skill_id == CR_SHIELDBOOMERANG || skill_id == PA_SHIELDCHAIN ) { //Refine bonus applies after cards and elements.
|
||||
if (sd && skill_id == PA_SHIELDCHAIN) { //Rapid Smiting has a unique mastery bonus
|
||||
short index = sd->equip_index[EQI_HAND_L];
|
||||
|
||||
if( index >= 0 && sd->inventory_data[index] && sd->inventory_data[index]->type == IT_ARMOR )
|
||||
ATK_ADD(wd.damage, wd.damage2, 10*sd->inventory.u.items_inventory[index].refine);
|
||||
//The bonus is [max(100, Random(100, 0.7*weight + pow(skill level + refine)))]
|
||||
if (index >= 0 && sd->inventory_data[index] && sd->inventory_data[index]->type == IT_ARMOR) {
|
||||
//First calculate the random part of the bonus
|
||||
int bonus = (7 * sd->inventory_data[index]->weight) / 100;
|
||||
bonus += pow(skill_lv + sd->inventory.u.items_inventory[index].refine, 2);
|
||||
//Now get a random value between 100 and the random part
|
||||
bonus = max(100, rnd_value(100, bonus));
|
||||
ATK_ADD(wd.damage, wd.damage2, bonus);
|
||||
}
|
||||
}
|
||||
#ifndef RENEWAL
|
||||
//Card Fix for attacker (sd), 2 is added to the "left" flag meaning "attacker cards only"
|
||||
|
@ -7027,27 +7027,6 @@ static unsigned short status_calc_batk(struct block_list *bl, status_change *sc,
|
||||
batk += sc->getSCE(SC_ANGRIFFS_MODUS)->val2;
|
||||
if(sc->getSCE(SC_2011RWC_SCROLL))
|
||||
batk += 30;
|
||||
if(sc->getSCE(SC_INCATKRATE))
|
||||
batk += batk * sc->getSCE(SC_INCATKRATE)->val1/100;
|
||||
if(sc->getSCE(SC_PROVOKE))
|
||||
batk += batk * sc->getSCE(SC_PROVOKE)->val2/100;
|
||||
#ifndef RENEWAL
|
||||
if(sc->getSCE(SC_CONCENTRATION))
|
||||
batk += batk * sc->getSCE(SC_CONCENTRATION)->val2/100;
|
||||
#endif
|
||||
if(sc->getSCE(SC_SKE))
|
||||
batk += batk * 3;
|
||||
if(sc->getSCE(SC_BLOODLUST))
|
||||
batk += batk * sc->getSCE(SC_BLOODLUST)->val2/100;
|
||||
if(sc->getSCE(SC_JOINTBEAT) && sc->getSCE(SC_JOINTBEAT)->val2&BREAK_WAIST)
|
||||
batk -= batk * 25/100;
|
||||
if(sc->getSCE(SC_CURSE))
|
||||
batk -= batk * 25/100;
|
||||
/* Curse shouldn't effect on this? <- Curse OR Bleeding??
|
||||
if(sc->getSCE(SC_BLEEDING))
|
||||
batk -= batk * 25 / 100; */
|
||||
if(sc->getSCE(SC_FLEET))
|
||||
batk += batk * sc->getSCE(SC_FLEET)->val3/100;
|
||||
if(sc->getSCE(SC__ENERVATION))
|
||||
batk -= batk * sc->getSCE(SC__ENERVATION)->val2 / 100;
|
||||
if( sc->getSCE(SC_ZANGETSU) )
|
||||
@ -7122,21 +7101,7 @@ static unsigned short status_calc_watk(struct block_list *bl, status_change *sc,
|
||||
watk += sc->getSCE(SC_NIBELUNGEN)->val2;
|
||||
}
|
||||
}
|
||||
if(sc->getSCE(SC_CONCENTRATION))
|
||||
watk += watk * sc->getSCE(SC_CONCENTRATION)->val2 / 100;
|
||||
#endif
|
||||
if(sc->getSCE(SC_INCATKRATE))
|
||||
watk += watk * sc->getSCE(SC_INCATKRATE)->val1/100;
|
||||
if(sc->getSCE(SC_PROVOKE))
|
||||
watk += watk * sc->getSCE(SC_PROVOKE)->val2/100;
|
||||
if(sc->getSCE(SC_SKE))
|
||||
watk += watk * 3;
|
||||
if(sc->getSCE(SC_FLEET))
|
||||
watk += watk * sc->getSCE(SC_FLEET)->val3/100;
|
||||
if(sc->getSCE(SC_CURSE))
|
||||
watk -= watk * 25/100;
|
||||
if(sc->getSCE(SC_STRIPWEAPON) && bl->type != BL_PC)
|
||||
watk -= watk * sc->getSCE(SC_STRIPWEAPON)->val2/100;
|
||||
if(sc->getSCE(SC_FIGHTINGSPIRIT))
|
||||
watk += sc->getSCE(SC_FIGHTINGSPIRIT)->val1;
|
||||
if (sc->getSCE(SC_SHIELDSPELL_ATK))
|
||||
@ -12228,7 +12193,7 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
||||
case SC_ASH:
|
||||
val2 = 0; // hit % reduc
|
||||
val3 = 0; // def % reduc
|
||||
val4 = 0; // atk flee & reduc
|
||||
val4 = 0; // atk flee % reduc
|
||||
if (!status_bl_has_mode(bl,MD_STATUSIMMUNE)) {
|
||||
val2 = 50;
|
||||
if (status_get_race(bl) == RC_PLANT) // plant type
|
||||
|
Loading…
x
Reference in New Issue
Block a user