summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Changelog-Trunk.txt10
-rw-r--r--db/skill_unit_db.txt5
-rw-r--r--src/map/map.c2
-rw-r--r--src/map/pc.c6
-rw-r--r--src/map/skill.c53
-rw-r--r--src/map/status.c54
6 files changed, 78 insertions, 52 deletions
diff --git a/Changelog-Trunk.txt b/Changelog-Trunk.txt
index 4f17ffee3..93ebda1f0 100644
--- a/Changelog-Trunk.txt
+++ b/Changelog-Trunk.txt
@@ -4,6 +4,16 @@ AS OF SVN REV. 5091, WE ARE NOW USING TRUNK. ALL UNTESTED BUGFIXES/FEATURES GO
IF YOU HAVE A WORKING AND TESTED BUGFIX PUT IT INTO STABLE AS WELL AS TRUNK.
2006/05/01
+ * Modified how Rogue's treasure works so that you get +1% to your steal
+ rate rather than +0.01% to the final rate. [Skotlex]
+ * Rewrote Warmth to use ground-skill-units, it should behave now like in
+ officials (implementation is not quite the same, but it should yield the
+ same effects while consuming less bandwidth). "Stacking", as it's called,
+ is possible now, but limited to eA's minimum timer skill interval (100ms).
+ [Skotlex]
+ * Modified NPC_POWERUP so that it gives +10 dex * skill level rather than
+ +5+lv to all stats (as explained by Playtester and Tharis on how the skill
+ behaves). [Skotlex]
* Allowed SG_FEEL memorizing the same map for all three. [Skotlex]
* SC_FUSION won't end when you die now. [Skotlex]
* Added knockback when you run into a wall during running. However
diff --git a/db/skill_unit_db.txt b/db/skill_unit_db.txt
index 7ac5f8ed9..9614505cb 100644
--- a/db/skill_unit_db.txt
+++ b/db/skill_unit_db.txt
@@ -81,10 +81,13 @@
405,0xb7, , 0, 1,1000,enemy, 0x000 //PF_SPIDERWEB#スパイダーウェッブ
409,0xb2, , 0,-1, -1,noone, 0x000 //WE_CALLBABY
410,0xb2, , 0,-1, -1,noone, 0x000 //WE_CALLPARENT
+428,0x86, , 0, 1, 500,enemy, 0x000 //SG_SUN_WARM
+429,0x86, , 0, 1, 500,enemy, 0x000 //SG_MOON_WARM
+430,0x86, , 0, 1, 500,enemy, 0x000 //SG_STAR_WARM
484,0xb8, , 2, 0,1000,enemy, 0x808 //HW_GRAVITATION
488,0xb9, , 3, 0, -1,all, 0x100 //CG_HERMODE
516,0xbc, , 0, 3,1000,enemy,0x000,GS_DESPERADO#デスペラード
521,0xbd, , 0, 1,1000,enemy,0x006,GS_GROUNDDRIFT#グラウンドドリフト
535,0x86, , 0, 2,2000,enemy,0x008,NJ_KAENSIN#火炎陣#
536,0x86, , 0, 2, 300,enemy,0x008,NJ_BAKUENRYU#爆炎龍#
-538,0xbb,,1:1:1:2:2:2:3:3:3:4,0, -1,all,0x010,NJ_SUITON#水遁# \ No newline at end of file
+538,0xbb,,1:1:1:2:2:2:3:3:3:4,0, -1,all,0x010,NJ_SUITON#水遁#
diff --git a/src/map/map.c b/src/map/map.c
index 87fd292ba..6357d09d1 100644
--- a/src/map/map.c
+++ b/src/map/map.c
@@ -524,6 +524,8 @@ int map_moveblock(struct block_list *bl, int x1, int y1, unsigned int tick) {
else
skill_unit_move_unit_group((struct skill_unit_group *)sc->data[SC_DANCING].val2, bl->m, x1-x0, y1-y0);
}
+ if (sc->data[SC_WARM].timer != -1)
+ skill_unit_move_unit_group((struct skill_unit_group *)sc->data[SC_WARM].val4, bl->m, x1-x0, y1-y0);
}
}
}
diff --git a/src/map/pc.c b/src/map/pc.c
index b58c7d624..770b857a1 100644
--- a/src/map/pc.c
+++ b/src/map/pc.c
@@ -2939,6 +2939,8 @@ int pc_steal_item(struct map_session_data *sd,struct block_list *bl)
? (sd->paramc[4] - md->db->dex)/2 + pc_checkskill(sd,TF_STEAL)*6 + 10
: sd->paramc[4] - md->db->dex + pc_checkskill(sd,TF_STEAL)*3 + 10;
+ skill+= sd->add_steal_rate; //Better make the steal_Rate addition affect % rather than an absolute on top of the total drop rate. [Skotlex]
+
if (skill < 1)
return 0;
@@ -2950,7 +2952,7 @@ int pc_steal_item(struct map_session_data *sd,struct block_list *bl)
itemid = md->db->dropitem[i].nameid;
if(itemid <= 0 || (itemid>4000 && itemid<5000 && pc_checkskill(sd,TF_STEAL) <= 5))
continue;
- if(rand() % 10000 <= ((md->db->dropitem[i].p * skill) / 100 + sd->add_steal_rate))
+ if(rand() % 10000 <= md->db->dropitem[i].p*skill/100)
break;
}
if (i == MAX_MOB_DROP)
@@ -2977,7 +2979,7 @@ int pc_steal_item(struct map_session_data *sd,struct block_list *bl)
}
if(log_config.steal) { //this drop log contains ALL stolen items [Lupus]
- int log_item[10]; //for stolen items logging Lupus
+ int log_item[MAX_MOB_DROP]; //for stolen items logging Lupus
memset(&log_item,0,sizeof(log_item));
log_item[i] = itemid; //i == monster's drop slot
log_drop(sd, md->class_, log_item);
diff --git a/src/map/skill.c b/src/map/skill.c
index 2ba07fecb..acbcdeb18 100644
--- a/src/map/skill.c
+++ b/src/map/skill.c
@@ -1934,9 +1934,6 @@ int skill_attack( int attack_type, struct block_list* src, struct block_list *ds
case ASC_METEORASSAULT:
case GS_DESPERADO:
case GS_SPREADATTACK:
- case SG_SUN_WARM:
- case SG_MOON_WARM:
- case SG_STAR_WARM:
dmg.dmotion = clif_skill_damage(dsrc,bl,tick,dmg.amotion,dmg.dmotion, damage, dmg.div_, skillid, -1, 5);
break;
case KN_BRANDISHSPEAR:
@@ -2016,7 +2013,7 @@ int skill_attack( int attack_type, struct block_list* src, struct block_list *ds
if (su->group && skill_get_inf2(su->group->skill_id)&INF2_TRAP)
damage = 0; //Only Heaven's drive may damage traps. [Skotlex]
}
- if (!dmg.amotion) { // do not really deal damage for ASC_BREAKER's 1st attack
+ if (!dmg.amotion) {
battle_damage(src,bl,damage,dmg.dmotion,0); //Deal damage before knockback to allow stuff like firewall+storm gust combo.
if (dmg.dmg_lv == ATK_DEF || damage > 0) {
if (!status_isdead(bl))
@@ -3716,10 +3713,14 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, in
case SG_SUN_WARM:
case SG_MOON_WARM:
case SG_STAR_WARM:
+ {
+ struct skill_unit_group *sg;
+ if (!tsc) break;
+ sg = skill_unitsetting(bl,skillid,skilllv,src->x,src->y,0);
clif_skill_nodamage(src,bl,skillid,skilllv,
- sc_start4(bl,type,100,skilllv,0,skillid,
- skill_get_splash(skillid,skilllv),skill_get_time(skillid,skilllv)));
+ sc_start4(bl,type,100,skilllv,0,0,(int)sg,skill_get_time(skillid,skilllv)));
break;
+ }
case CG_MOONLIT: /* 月明りの泉に落ちる花びら */
clif_skill_nodamage(src,bl,skillid,skilllv,1);
@@ -5025,14 +5026,15 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, in
case NPC_POWERUP:
sc_start(bl,SC_INCATKRATE,100,40*skilllv,skill_get_time(skillid, skilllv));
- // another random guess xP
- clif_skill_nodamage(src,bl,skillid,skilllv,
- sc_start(bl,SC_INCALLSTATUS,100,skilllv*5,skill_get_time(skillid, skilllv)));
+//From experience it appears powerup is more hit, not +all stats.
+ sc_start(bl,SC_INCDEX,100,10*skilllv,skill_get_time(skillid, skilllv));
+// sc_start(bl,SC_INCALLSTATUS,100,skilllv*5,skill_get_time(skillid, skilllv));
+ clif_skill_nodamage(src,bl,skillid,skilllv,1);
break;
case NPC_AGIUP:
clif_skill_nodamage(src,bl,skillid,skilllv,
- sc_start(bl,SC_INCAGI,100,skilllv*10,skill_get_time(skillid, skilllv)));
+ sc_start(bl,SC_INCAGI,100,10*skilllv,skill_get_time(skillid, skilllv)));
break;
case NPC_INVISIBLE:
@@ -6862,11 +6864,24 @@ int skill_unit_onplace_timer(struct skill_unit *src,struct block_list *bl,unsign
}
case UNT_ATTACK_SKILLS:
- skill_attack(skill_get_type(sg->skill_id),ss,&src->bl,bl,sg->skill_id,sg->skill_lv,tick,0);
- if (sg->skill_id == AC_SHOWER)
- sg->val2++; //Store count of hitted enemies to know when to delete an arrow.
+ switch (sg->skill_id)
+ {
+ case SG_SUN_WARM: //SG skills [Komurka]
+ case SG_MOON_WARM:
+ case SG_STAR_WARM:
+ if(bl->type==BL_PC)
+ //Only damage SP [Skotlex]
+ pc_damage_sp((TBL_PC*)bl, 60, 0);
+ else if(!sd || pc_damage_sp(sd, 2, 0) >= 0)
+ //Otherwise, Knockback attack.
+ skill_attack(BF_WEAPON,ss,&src->bl,bl,sg->skill_id,sg->skill_lv,tick,0);
+ break;
+ case AC_SHOWER:
+ sg->val2++; //Store count of hitted enemies to know when to delete an arrow.
+ default:
+ skill_attack(skill_get_type(sg->skill_id),ss,&src->bl,bl,sg->skill_id,sg->skill_lv,tick,0);
+ }
break;
-
case UNT_FIREPILLAR_WAITING:
skill_unitsetting(ss,sg->skill_id,sg->skill_lv,src->bl.x,src->bl.y,1);
skill_delunit(src);
@@ -9488,6 +9503,16 @@ int skill_delunitgroup(struct block_list *src, struct skill_unit_group *group)
status_change_end(src,SC_GOSPEL,-1);
}
}
+ if (group->skill_id == SG_SUN_WARM ||
+ group->skill_id == SG_MOON_WARM ||
+ group->skill_id == SG_STAR_WARM) {
+ struct status_change *sc = status_get_sc(src);
+ if(sc && sc->data[SC_WARM].timer != -1) {
+ sc->data[SC_WARM].val4 = 0;
+ status_change_end(src,SC_WARM,-1);
+ }
+ }
+
if (group->skill_id == AC_SHOWER && group->val2 && src->type==BL_PC)
battle_consume_ammo((TBL_PC*)src, group->skill_id, -group->skill_lv); //Delete arrow if at least one target was hit.
diff --git a/src/map/status.c b/src/map/status.c
index 35c37bb25..e5b16aec3 100644
--- a/src/map/status.c
+++ b/src/map/status.c
@@ -3883,10 +3883,13 @@ int status_change_start(struct block_list *bl,int type,int rate,int val1,int val
if (sc->data[type].val2 && !val2)
return 0;
break;
- case SC_GOSPEL:
- //Must not override a casting gospel char.
- if (sc->data[type].val4 == BCT_SELF)
- return 0;
+ case SC_WARM:
+ { //Fetch the Group, half the attack interval. [Skotlex]
+ struct skill_unit_group *group = (struct skill_unit_group *)sc->data[type].val4;
+ if (group)
+ group->interval/=2;
+ return 1;
+ }
case SC_STUN:
case SC_SLEEP:
case SC_POISON:
@@ -3908,6 +3911,10 @@ int status_change_start(struct block_list *bl,int type,int rate,int val1,int val
case SC_ATKPOTION:
case SC_MATKPOTION:
break;
+ case SC_GOSPEL:
+ //Must not override a casting gospel char.
+ if (sc->data[type].val4 == BCT_SELF)
+ return 0;
default:
if(sc->data[type].val1 > val1)
return 1; //Return true to not mess up skill animations. [Skotlex
@@ -4279,13 +4286,6 @@ int status_change_start(struct block_list *bl,int type,int rate,int val1,int val
calc_flag = 1;
break;
- case SC_WARM: //SG skills [Komurka]
- if (!(flag&4)) {
- val2 = tick/100;
- tick = 100;
- }
- break;
-
case SC_GOSPEL:
if (val4 == BCT_SELF) { // self effect
if (flag&4)
@@ -4578,6 +4578,7 @@ int status_change_start(struct block_list *bl,int type,int rate,int val1,int val
case SC_ASSUMPTIO: /* アスムプティオ */
case SC_SLEEP:
case SC_SMA:
+ case SC_WARM:
break;
// gs_something1 [Vicious]
case SC_MADNESSCANCEL:
@@ -5175,6 +5176,13 @@ int status_change_end( struct block_list* bl , int type,int tid )
if (vd) vd->dead_sit = 0;
break;
}
+ case SC_WARM:
+ if (sc->data[type].val4) { //Clear the group.
+ struct skill_unit_group *group = (struct skill_unit_group *)sc->data[type].val4;
+ sc->data[type].val4 = 0;
+ skill_delunitgroup(bl, group);
+ }
+ break;
//gs_something2 [Vicious]
case SC_MADNESSCANCEL:
@@ -5415,16 +5423,6 @@ int status_change_timer(int tid, unsigned int tick, int id, int data)
}
break;
- case SC_WARM: //SG skills [Komurka]
- if( (--sc->data[type].val2)>0){
- map_foreachinrange( status_change_timer_sub, bl,
- sc->data[type].val4,BL_CHAR,
- bl,sc,type,tick);
- sc->data[type].timer=add_timer(tick+100, status_change_timer,bl->id, data);
- return 0;
- }
- break;
-
case SC_PROVOKE: /* プロボック/オ?トバ?サ?ク */
if(sc->data[type].val2!=0){ /* オ?トバ?サ?ク(1秒ごとにHPチェック) */
if(sd && sd->status.hp>sd->status.max_hp>>2) /* 停止 */
@@ -5757,20 +5755,6 @@ int status_change_timer_sub(struct block_list *bl, va_list ap )
}
}
break;
- case SC_WARM: //SG skills [Komurka]
- if(sc && sc->data[type].val2 &&
- battle_check_target( src,bl, BCT_ENEMY ) > 0)
- {
- if(tsd)
- //Only damage SP [Skotlex]
- pc_damage_sp(tsd, 60, 0);
- else { //Otherwise, Knockback attack.
- if(sd && pc_damage_sp(sd, 2, 0) <= 0)
- sd->sc.data[type].val2 = 0; //Makes it end on the next tick.
- skill_attack(BF_WEAPON,src,src,bl,sc->data[type].val3,sc->data[type].val1,tick,0);
- }
- }
- break;
case SC_CLOSECONFINE:
//Lock char has released the hold on everyone...
if (tsc && tsc->count && tsc->data[SC_CLOSECONFINE2].timer != -1 && tsc->data[SC_CLOSECONFINE2].val2 == src->id) {