ソースを参照

Pre-renewal cast time fixes
* Mystical Amplification cast time can no longer be reduced by item bonuses except Staff of Destruction (fixes #903)
* Foresight will no longer stack additively with other cast time reductions (fixes #899)
* Suffragium and Foresight will now be consumed by skills, even if they aren't affected by them

Note: Whether skill-specific reductions stack additively with general reductions and how it works in renewal still needs to be tested, going to create separate issues for those once confirmed.

Playtester 9 年 前
コミット
4c2d5153c3
4 ファイル変更32 行追加26 行削除
  1. 1 1
      db/pre-re/skill_castnodex_db.txt
  2. 28 20
      src/map/skill.c
  3. 1 1
      src/map/skill.h
  4. 2 4
      src/map/unit.c

+ 1 - 1
db/pre-re/skill_castnodex_db.txt

@@ -19,7 +19,7 @@
 272,0,2	//MO_CHAINCOMBO
 273,0,2	//MO_COMBOFINISH
 336,1	//WE_CALLPARTNER
-366,3	//HW_MAGICPOWER
+366,7	//HW_MAGICPOWER
 370,1	//CH_PALMSTRIKE
 371,0,2	//CH_TIGERFIST
 372,0,2	//CH_CHAINCRUSH

+ 28 - 20
src/map/skill.c

@@ -15884,7 +15884,7 @@ int skill_castfix(struct block_list *bl, uint16 skill_id, uint16 skill_lv) {
 		int reduce_cast_rate = 0;
 		uint8 flag = skill_get_castnodex(skill_id);
 
-		// calculate base cast time (reduced by dex)
+		// Calculate base cast time (reduced by dex)
 		if (!(flag&1)) {
 			int scale = battle_config.castrate_dex_scale - status_get_dex(bl);
 
@@ -15894,12 +15894,13 @@ int skill_castfix(struct block_list *bl, uint16 skill_id, uint16 skill_lv) {
 				return 0; // instant cast
 		}
 
-		// calculate cast time reduced by item/card bonuses
-		if (!(flag&4) && sd) {
+		// Calculate cast time reduced by item/card bonuses
+		if (sd) {
 			int i;
 
-			if (sd->castrate != 100)
+			if (!(flag&4) && sd->castrate != 100)
 				reduce_cast_rate += 100 - sd->castrate;
+			// Skill-specific reductions work regardless of flag
 			for(i = 0; i < ARRAYLENGTH(sd->skillcastrate) && sd->skillcastrate[i].id; i++) {
 				if (sd->skillcastrate[i].id == skill_id) {
 					reduce_cast_rate -= sd->skillcastrate[i].val;
@@ -15908,16 +15909,19 @@ int skill_castfix(struct block_list *bl, uint16 skill_id, uint16 skill_lv) {
 			}
 		}
 
-		// NOTE: Magic Strings and Foresight are treated as separate factors in the calculation
-		// They are not added to the other modifiers [iRO Wiki]
-		if (sc && sc->count && !(flag&2)) {
+		// These cast time reductions are processed even if the skill fails
+		if (sc && sc->count) {
+			// Magic Strings stacks additively with item bonuses
+			if (!(flag&2) && sc->data[SC_POEMBRAGI])
+				reduce_cast_rate += sc->data[SC_POEMBRAGI]->val2;
+			// Foresight halves the cast time, it does not stack additively
 			if (sc->data[SC_MEMORIZE]) {
-				reduce_cast_rate += 50;
+				if(!(flag&2))
+					time -= time * 50 / 100;
+				// Foresight counter gets reduced even if the skill is not affected by it
 				if ((--sc->data[SC_MEMORIZE]->val2) <= 0)
 					status_change_end(bl, SC_MEMORIZE, INVALID_TIMER);
 			}
-			if (sc->data[SC_POEMBRAGI])
-				reduce_cast_rate += sc->data[SC_POEMBRAGI]->val2;
 		}
 
 		time = time * (1 - (float)reduce_cast_rate / 100);
@@ -15929,7 +15933,7 @@ int skill_castfix(struct block_list *bl, uint16 skill_id, uint16 skill_lv) {
 		time = time * battle_config.cast_rate / 100;
 	// return final cast time
 	time = max(time, 0);
-	//ShowInfo("Castime castfix = %d\n",time);
+	//ShowInfo("Castime castfix = %f\n",time);
 
 	return (int)time;
 }
@@ -15941,7 +15945,7 @@ int skill_castfix(struct block_list *bl, uint16 skill_id, uint16 skill_lv) {
  * @param time: Cast time before Status Change addition or reduction
  * @return time: Modified castime after status change addition or reduction
  */
-int skill_castfix_sc(struct block_list *bl, double time)
+int skill_castfix_sc(struct block_list *bl, double time, uint8 flag)
 {
 	struct status_change *sc = status_get_sc(bl);
 
@@ -15952,20 +15956,24 @@ int skill_castfix_sc(struct block_list *bl, double time)
 		return (int)time;
 
 	if (sc && sc->count) {
-		if (sc->data[SC_SLOWCAST])
-			time += time * sc->data[SC_SLOWCAST]->val2 / 100;
-		if (sc->data[SC_PARALYSIS])
-			time += sc->data[SC_PARALYSIS]->val3;
+		if (!(flag&2)) {
+			if (sc->data[SC_SLOWCAST])
+				time += time * sc->data[SC_SLOWCAST]->val2 / 100;
+			if (sc->data[SC_PARALYSIS])
+				time += sc->data[SC_PARALYSIS]->val3;
+			if (sc->data[SC_IZAYOI])
+				time -= time * 50 / 100;
+		}
 		if (sc->data[SC_SUFFRAGIUM]) {
-			time -= time * sc->data[SC_SUFFRAGIUM]->val2 / 100;
+			if(!(flag&2))
+				time -= time * sc->data[SC_SUFFRAGIUM]->val2 / 100;
+			//Suffragium ends even if the skill is not affected by it
 			status_change_end(bl, SC_SUFFRAGIUM, INVALID_TIMER);
 		}
-		if (sc->data[SC_IZAYOI])
-			time -= time * 50 / 100;
 	}
 
 	time = max(time, 0);
-	//ShowInfo("Castime castfix_sc = %d\n",time);
+	//ShowInfo("Castime castfix_sc = %f\n",time);
 
 	return (int)time;
 }

+ 1 - 1
src/map/skill.h

@@ -440,7 +440,7 @@ void ext_skill_unit_onplace(struct skill_unit *unit, struct block_list *bl, unsi
 int64 skill_unit_ondamaged(struct skill_unit *unit,int64 damage);
 
 int skill_castfix(struct block_list *bl, uint16 skill_id, uint16 skill_lv);
-int skill_castfix_sc(struct block_list *bl, double time);
+int skill_castfix_sc(struct block_list *bl, double time, uint8 flag);
 #ifdef RENEWAL_CAST
 int skill_vfcastfix(struct block_list *bl, double time, uint16 skill_id, uint16 skill_lv);
 #endif

+ 2 - 4
src/map/unit.c

@@ -1803,8 +1803,7 @@ int unit_skilluse_id2(struct block_list *src, int target_id, uint16 skill_id, ui
 
 	// Moved here to prevent Suffragium from ending if skill fails
 #ifndef RENEWAL_CAST
-	if (!(skill_get_castnodex(skill_id)&2))
-		casttime = skill_castfix_sc(src, casttime);
+	casttime = skill_castfix_sc(src, casttime, skill_get_castnodex(skill_id));
 #else
 	casttime = skill_vfcastfix(src, casttime, skill_id, skill_lv);
 #endif
@@ -2023,8 +2022,7 @@ int unit_skilluse_pos2( struct block_list *src, short skill_x, short skill_y, ui
 
 	// Moved here to prevent Suffragium from ending if skill fails
 #ifndef RENEWAL_CAST
-	if (!(skill_get_castnodex(skill_id)&2))
-		casttime = skill_castfix_sc(src, casttime);
+	casttime = skill_castfix_sc(src, casttime, skill_get_castnodex(skill_id));
 #else
 	casttime = skill_vfcastfix(src, casttime, skill_id, skill_lv );
 #endif