summaryrefslogtreecommitdiff
path: root/src/map/status.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/map/status.c')
-rw-r--r--src/map/status.c211
1 files changed, 121 insertions, 90 deletions
diff --git a/src/map/status.c b/src/map/status.c
index 4a3a6b0d8..2f83caf52 100644
--- a/src/map/status.c
+++ b/src/map/status.c
@@ -587,7 +587,7 @@ void initChangeTables(void) {
add_sc( WL_WHITEIMPRISON , SC_WHITEIMPRISON );
set_sc_with_vfx( WL_FROSTMISTY , SC_FREEZING , SI_FROSTMISTY , SCB_ASPD|SCB_SPEED|SCB_DEF|SCB_DEF2 );
set_sc( WL_MARSHOFABYSS , SC_MARSHOFABYSS , SI_MARSHOFABYSS , SCB_SPEED|SCB_FLEE|SCB_DEF|SCB_MDEF );
- set_sc( WL_RECOGNIZEDSPELL , SC_RECOGNIZEDSPELL , SI_RECOGNIZEDSPELL , SCB_NONE );
+ set_sc(WL_RECOGNIZEDSPELL , SC_RECOGNIZEDSPELL , SI_RECOGNIZEDSPELL , SCB_MATK);
set_sc( WL_STASIS , SC_STASIS , SI_STASIS , SCB_NONE );
/**
* Ranger
@@ -1901,29 +1901,12 @@ static unsigned short status_base_atk(const struct block_list *bl, const struct
return cap_value(str, 0, USHRT_MAX);
}
-
-static inline unsigned short status_base_matk_max(const struct status_data* status)
-{
-#ifdef RENEWAL
- return status->matk_max; // in RE maximum MATK signs weapon matk, which we store in this var
-#else
- return status->int_+(status->int_/5)*(status->int_/5);
-#endif
-}
-
-#ifdef RENEWAL
-static inline unsigned short status_base_matk_min(const struct status_data* status, int lvl)
-#else
-static inline unsigned short status_base_matk_min(const struct status_data* status)
-#endif
-{
-#ifdef RENEWAL
- return status->int_+(status->int_/2)+(status->dex/5)+(status->luk/3)+(lvl/4);
+#ifndef RENEWAL
+static inline unsigned short status_base_matk_min(const struct status_data* status){ return status->int_+(status->int_/7)*(status->int_/7); }
+static inline unsigned short status_base_matk_max(const struct status_data* status){ return status->int_+(status->int_/5)*(status->int_/5); }
#else
- return status->int_+(status->int_/7)*(status->int_/7);
+unsigned short status_base_matk(const struct status_data* status, int level){ return status->int_+(status->int_/2)+(status->dex/5)+(status->luk/3)+(level/4); }
#endif
-}
-
//Fills in the misc data that can be calculated from the other status info (except for level)
void status_calc_misc(struct block_list *bl, struct status_data *status, int level)
@@ -1934,19 +1917,16 @@ void status_calc_misc(struct block_list *bl, struct status_data *status, int lev
status->hit = status->flee =
status->def2 = status->mdef2 =
status->cri = status->flee2 = 0;
-#ifdef RENEWAL
- status->matk_min = status_base_matk_min(status, level);
-#else
- status->matk_min = status_base_matk_min(status);
-#endif
- status->matk_max = status_base_matk_max(status);
#ifdef RENEWAL // renewal formulas
- status->hit += level + status->dex + status->luk/3 + 175; //base level + ( every 1 dex = +1 hit ) + (every 3 luk = +1 hit) + 175
- status->flee += level + status->agi + status->luk/5 + 100; //base level + ( every 1 agi = +1 flee ) + (every 5 luk = +1 flee) + 100
- status->def2 += (int)(((float)level + status->vit)/2 + ((float)status->agi/5)); //base level + (every 2 vit = +1 def) + (every 5 agi = +1 def)
- status->mdef2 += (int)(status->int_ + ((float)level/4) + ((float)status->dex/5) + ((float)status->vit/5)); //(every 4 base level = +1 mdef) + (every 1 int = +1 mdef) + (every 5 dex = +1 mdef) + (every 5 vit = +1 mdef)
+ status->matk_min = status->matk_max = status_base_matk(status, level);
+ status->hit += level + status->dex + status->luk/3 + 175; //base level + ( every 1 dex = +1 hit ) + (every 3 luk = +1 hit) + 175
+ status->flee += level + status->agi + status->luk/5 + 100; //base level + ( every 1 agi = +1 flee ) + (every 5 luk = +1 flee) + 100
+ status->def2 += (int)(((float)level + status->vit)/2 + ((float)status->agi/5)); //base level + (every 2 vit = +1 def) + (every 5 agi = +1 def)
+ status->mdef2 += (int)(status->int_ + ((float)level/4) + ((float)status->dex/5) + ((float)status->vit/5)); //(every 4 base level = +1 mdef) + (every 1 int = +1 mdef) + (every 5 dex = +1 mdef) + (every 5 vit = +1 mdef)
#else
+ status->matk_min = status_base_matk_min(status);
+ status->matk_max = status_base_matk_max(status);
status->hit += level + status->dex;
status->flee += level + status->agi;
status->def2 += status->vit;
@@ -2492,16 +2472,10 @@ int status_calc_pc_(struct map_session_data* sd, bool first)
wa->atk2 = refine_info[wlv].bonus[r-1] / 100;
#ifdef RENEWAL
- // in renewal max MATK is the weapon MATK
- status->matk_max += sd->inventory_data[index]->matk;
-
- if( r )
- {// renewal magic attack refine bonus
- status->matk_max += refine_info[wlv].bonus[r-1] / 100;
- }
-
- // record the weapon level for future usage
- status->wlv = wlv;
+ wa->matk += sd->inventory_data[index]->matk;
+ wa->wlv = wlv;
+ if( r ) // renewal magic attack refine bonus
+ wa->matk += refine_info[wlv].bonus[r-1] / 100;
#endif
//Overrefine bonus.
@@ -2575,11 +2549,6 @@ int status_calc_pc_(struct map_session_data* sd, bool first)
status->def += (refinedef+50)/100;
-#ifdef RENEWAL
- // increment the weapon ATK using the MATK max value
- status->matk_max += sd->bonus.sp_weapon_matk;
-#endif
-
//Parse Cards
for(i=0;i<EQI_MAX-1;i++) {
current_equip_item_index = index = sd->equip_index[i]; //We pass INDEX to current_equip_item_index - for EQUIP_SCRIPT (new cards solution) [Lupus]
@@ -3287,6 +3256,9 @@ static unsigned int status_calc_maxsp(struct block_list *,struct status_change *
static unsigned char status_calc_element(struct block_list *bl, struct status_change *sc, int element);
static unsigned char status_calc_element_lv(struct block_list *bl, struct status_change *sc, int lv);
static unsigned short status_calc_mode(struct block_list *bl, struct status_change *sc, int mode);
+#ifdef RENEWAL
+static unsigned short status_calc_ematk(struct block_list *,struct status_change *,int);
+#endif
//Calculates base regen values.
void status_calc_regen(struct block_list *bl, struct status_data *status, struct regen_data *regen)
@@ -3787,32 +3759,50 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag)
}
if(flag&SCB_MATK) {
-#ifdef RENEWAL
- status->matk_min = status_base_matk_min(status,status_get_lv(bl));
- if( sd )
- status->matk_min += sd->bonus.sp_base_matk;
+#ifndef RENEWAL
+ status->matk_min = status_base_matk_min(status) + (sd?sd->bonus.ematk:0);
+ status->matk_max = status_base_matk_max(status) + (sd?sd->bonus.ematk:0);
#else
- status->matk_min = status_base_matk_min(status);
+ /**
+ * RE MATK Formula (from irowiki:http://irowiki.org/wiki/MATK)
+ * MATK = (sMATK + wMATK + eMATK) * Multiplicative Modifiers
+ **/
+ status->matk_min = status->matk_max = status_base_matk(status, status_get_lv(bl));
+ if( bl->type&BL_PC ){
+ // Any +MATK you get from skills and cards, including cards in weapon, is added here.
+ if( sd->bonus.ematk > 0 ){
+ status->matk_max += sd->bonus.ematk;
+ status->matk_min += sd->bonus.ematk;
+ }
+ status->matk_min = status_calc_ematk(bl, sc, status->matk_min);
+ status->matk_max = status_calc_ematk(bl, sc, status->matk_max);
+ //This is the only portion in MATK that varies depending on the weapon level and refinement rate.
+ if( status->rhw.matk > 0 ){
+ int wMatk = status->rhw.matk;
+ int variance = wMatk * status->rhw.wlv / 10;
+ status->matk_min += wMatk - variance;
+ status->matk_max += wMatk + variance;
+ }
+ }
#endif
- status->matk_max = status_base_matk_max(status);
-
- if( bl->type&BL_PC && sd->matk_rate != 100 )
- {
- //Bonuses from previous matk
-#ifndef RENEWAL // only changed in non-renewal [Ind]
+ if (bl->type&BL_PC && sd->matk_rate != 100) {
status->matk_max = status->matk_max * sd->matk_rate/100;
-#endif
status->matk_min = status->matk_min * sd->matk_rate/100;
}
status->matk_min = status_calc_matk(bl, sc, status->matk_min);
-
-#ifndef RENEWAL // only changed in non-renewal [Ind]
status->matk_max = status_calc_matk(bl, sc, status->matk_max);
-#endif
- if( bl->type&BL_HOM && battle_config.hom_setting&0x20 ) //Hom Min Matk is always the same as Max Matk
- status->matk_min = status->matk_max;
+ if ((bl->type&BL_HOM && battle_config.hom_setting&0x20) //Hom Min Matk is always the same as Max Matk
+ || sc->data[SC_RECOGNIZEDSPELL])
+ status->matk_min = status->matk_max;
+
+#ifdef RENEWAL
+ if( sd && sd->right_weapon.overrefine > 0){
+ status->matk_min++;
+ status->matk_max += sd->right_weapon.overrefine - 1;
+ }
+#endif
}
@@ -4000,10 +3990,17 @@ void status_calc_bl_(struct block_list* bl, enum scb_flag flag, bool first)
clif_updatestatus(sd,SP_FLEE2);
if(b_status.cri != status->cri)
clif_updatestatus(sd,SP_CRITICAL);
+#ifndef RENEWAL
if(b_status.matk_max != status->matk_max)
clif_updatestatus(sd,SP_MATK1);
if(b_status.matk_min != status->matk_min)
+ clif_updatestatus(sd,SP_MATK2);
+#else
+ if(b_status.matk_max != status->matk_max || b_status.matk_min != status->matk_min){
clif_updatestatus(sd,SP_MATK2);
+ clif_updatestatus(sd,SP_MATK1);
+ }
+#endif
if(b_status.mdef != status->mdef){
clif_updatestatus(sd,SP_MDEF1);
#ifdef RENEWAL
@@ -4531,28 +4528,16 @@ static unsigned short status_calc_watk(struct block_list *bl, struct status_chan
return (unsigned short)cap_value(watk,0,USHRT_MAX);
}
-
-static unsigned short status_calc_matk(struct block_list *bl, struct status_change *sc, int matk)
+#ifdef RENEWAL
+static unsigned short status_calc_ematk(struct block_list *bl, struct status_change *sc, int matk)
{
- if(!sc || !sc->count)
- return cap_value(matk,0,USHRT_MAX);
-
- if(sc->data[SC_MATKPOTION])
- matk += sc->data[SC_MATKPOTION]->val1;
- if(sc->data[SC_MATKFOOD])
- matk += sc->data[SC_MATKFOOD]->val1;
- if(sc->data[SC_MAGICPOWER] && sc->data[SC_MAGICPOWER]->val4)
- matk += matk * sc->data[SC_MAGICPOWER]->val3/100;
- if(sc->data[SC_MINDBREAKER])
- matk += matk * sc->data[SC_MINDBREAKER]->val2/100;
- if(sc->data[SC_INCMATKRATE])
- matk += matk * sc->data[SC_INCMATKRATE]->val1/100;
- if(sc->data[SC_MOONLITSERENADE])
- matk += matk * sc->data[SC_MOONLITSERENADE]->val2/100;
- if(sc->data[SC_MELODYOFSINK])
- matk += matk * sc->data[SC_MELODYOFSINK]->val3/100;
- if(sc->data[SC_BEYONDOFWARCRY])
- matk -= matk * sc->data[SC_BEYONDOFWARCRY]->val3/100;
+
+ if (!sc || !sc->count)
+ return cap_value(matk,0,USHRT_MAX);
+ if (sc->data[SC_MATKPOTION])
+ matk += sc->data[SC_MATKPOTION]->val1;
+ if (sc->data[SC_MATKFOOD])
+ matk += sc->data[SC_MATKFOOD]->val1;
if(sc->data[SC_MANA_PLUS])
matk += sc->data[SC_MANA_PLUS]->val1;
if(sc->data[SC_AQUAPLAY_OPTION])
@@ -4567,6 +4552,46 @@ static unsigned short status_calc_matk(struct block_list *bl, struct status_chan
matk += 40 + 30 * sc->data[SC_ODINS_POWER]->val1; //70 lvl1, 100lvl2
if(sc->data[SC_IZAYOI])
matk += 50 * sc->data[SC_IZAYOI]->val1;
+ return (unsigned short)cap_value(matk,0,USHRT_MAX);
+}
+#endif
+static unsigned short status_calc_matk(struct block_list *bl, struct status_change *sc, int matk)
+{
+ if(!sc || !sc->count)
+ return cap_value(matk,0,USHRT_MAX);
+#ifndef RENEWAL
+ // take note fixed value first before % modifiers
+ if (sc->data[SC_MATKPOTION])
+ matk += sc->data[SC_MATKPOTION]->val1;
+ if (sc->data[SC_MATKFOOD])
+ matk += sc->data[SC_MATKFOOD]->val1;
+ if (sc->data[SC_MANA_PLUS])
+ matk += sc->data[SC_MANA_PLUS]->val1;
+ if (sc->data[SC_AQUAPLAY_OPTION])
+ matk += sc->data[SC_AQUAPLAY_OPTION]->val2;
+ if (sc->data[SC_CHILLY_AIR_OPTION])
+ matk += sc->data[SC_CHILLY_AIR_OPTION]->val2;
+ if (sc->data[SC_WATER_BARRIER])
+ matk -= sc->data[SC_WATER_BARRIER]->val3;
+ if (sc->data[SC_FIRE_INSIGNIA] && sc->data[SC_FIRE_INSIGNIA]->val1 == 3)
+ matk += 50;
+ if (sc->data[SC_ODINS_POWER])
+ matk += 40 + 30 * sc->data[SC_ODINS_POWER]->val1; //70 lvl1, 100lvl2
+ if (sc->data[SC_IZAYOI])
+ matk += 50 * sc->data[SC_IZAYOI]->val1;
+#endif
+ if (sc->data[SC_MAGICPOWER])
+ matk += matk * sc->data[SC_MAGICPOWER]->val3/100;
+ if (sc->data[SC_MINDBREAKER])
+ matk += matk * sc->data[SC_MINDBREAKER]->val2/100;
+ if (sc->data[SC_INCMATKRATE])
+ matk += matk * sc->data[SC_INCMATKRATE]->val1/100;
+ if (sc->data[SC_MOONLITSERENADE])
+ matk += matk * sc->data[SC_MOONLITSERENADE]->val2/100;
+ if (sc->data[SC_MELODYOFSINK])
+ matk += matk * sc->data[SC_MELODYOFSINK]->val3/100;
+ if (sc->data[SC_BEYONDOFWARCRY])
+ matk -= matk * sc->data[SC_BEYONDOFWARCRY]->val3/100;
if( sc->data[SC_ZANGETSU] )
matk += matk * sc->data[SC_ZANGETSU]->val2 / 100;
@@ -6160,6 +6185,14 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti
//No defense against it (buff).
rate -= (status_get_lv(bl) / 5 + status->vit / 4 + status->agi / 10)*100; // Lineal Reduction of Rate
break;
+ case SC_MARSHOFABYSS:
+ //5 second (Fixed) + 25 second - {( INT + LUK ) / 20 second }
+ tick -= (status->int_ + status->luk) / 20 * 1000;
+ break;
+ case SC_STASIS:
+ //5 second (fixed) + { Stasis Skill level * 5 - (Target�s VIT + DEX) / 20 }
+ tick -= (status->vit + status->dex) / 20 * 1000;
+ break;
case SC_WHITEIMPRISON:
if( tick == 5000 ) // 100% on caster
break;
@@ -6941,6 +6974,9 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val
case SC_INVINCIBLEOFF:
status_change_end(bl, SC_INVINCIBLE, INVALID_TIMER);
break;
+ case SC_MAGICPOWER:
+ status_change_end(bl, type, INVALID_TIMER);
+ break;
}
//Check for overlapping fails
@@ -10563,15 +10599,10 @@ int status_change_clear_buffs (struct block_list* bl, int type)
if (!sc || !sc->count)
return 0;
-
if (type&6) //Debuffs
for (i = SC_COMMON_MIN; i <= SC_COMMON_MAX; i++)
status_change_end(bl, (sc_type)i, INVALID_TIMER);
- for (i = SC_COMMON_MAX+1; i < SC_MAX; i++) {
- if (!sc->data[i])
- continue;
-
for( i = SC_COMMON_MAX+1; i < SC_MAX; i++ )
{
if(!sc->data[i])