From 386421a953a51e90fa56da5e294ecdac58647549 Mon Sep 17 00:00:00 2001 From: skotlex Date: Mon, 20 Nov 2006 17:25:05 +0000 Subject: - Fixed itemskill variable being cleared before parsing the skill, this causes auto-casted teleport to fail to skip the skill menu. It is now cleared on castend_pos/id directly. - The item skill/lv variables now use 0 as default to signal they aren't being used (instead of -1) - Skills with state 'move_enable' will now do a "walk path" check between target cell/object and caster instead of a "shoot path" check, this would fix skills like snap or charge from letting you "teleport" across pits. - Fixed a possible double map_addblock when hatching a pet egg right before going through a warp. git-svn-id: https://rathena.svn.sourceforge.net/svnroot/rathena/trunk@9275 54d463be-8e91-2dee-dedb-b68131a5f0ec --- src/map/clif.c | 8 ++++---- src/map/pc.c | 2 -- src/map/pet.c | 15 ++++++++------- src/map/skill.c | 21 ++++++++++++--------- src/map/unit.c | 28 ++++++++++++++++++++-------- 5 files changed, 44 insertions(+), 30 deletions(-) (limited to 'src') diff --git a/src/map/clif.c b/src/map/clif.c index b268818ce..0d04d0bc3 100644 --- a/src/map/clif.c +++ b/src/map/clif.c @@ -9822,14 +9822,14 @@ void clif_parse_UseSkillToId(int fd, struct map_session_data *sd) { if(target_id<0 && -target_id == sd->bl.id) // for disguises [Valaris] target_id = sd->bl.id; - if (sd->skillitem >= 0 && sd->skillitem == skillnum) { + if (sd->skillitem == skillnum) { if (skilllv != sd->skillitemlv) skilllv = sd->skillitemlv; unit_skilluse_id(&sd->bl, target_id, skillnum, skilllv); return; } - sd->skillitem = sd->skillitemlv = -1; + sd->skillitem = sd->skillitemlv = 0; if (skillnum == MO_EXTREMITYFIST) { if ((sd->sc.data[SC_COMBO].timer == -1 || (sd->sc.data[SC_COMBO].val1 != MO_COMBOFINISH && @@ -9918,12 +9918,12 @@ void clif_parse_UseSkillToPosSub(int fd, struct map_session_data *sd, int skilll if (sd->invincible_timer != -1) pc_delinvincibletimer(sd); - if (sd->skillitem >= 0 && sd->skillitem == skillnum) { + if (sd->skillitem == skillnum) { if (skilllv != sd->skillitemlv) skilllv = sd->skillitemlv; unit_skilluse_pos(&sd->bl, x, y, skillnum, skilllv); } else { - sd->skillitem = sd->skillitemlv = -1; + sd->skillitem = sd->skillitemlv = 0; if ((lv = pc_checkskill(sd, skillnum)) > 0) { if (skilllv > lv) skilllv = lv; diff --git a/src/map/pc.c b/src/map/pc.c index e28c1859d..0ae9eaae9 100644 --- a/src/map/pc.c +++ b/src/map/pc.c @@ -596,8 +596,6 @@ int pc_authok(struct map_session_data *sd, int login_id2, time_t connect_until_t sd->state.connect_new = 1; sd->followtimer = -1; // [MouseJstr] - sd->skillitem = -1; - sd->skillitemlv = -1; sd->invincible_timer = -1; sd->canuseitem_tick = tick; diff --git a/src/map/pet.c b/src/map/pet.c index d4069513f..12731cb34 100644 --- a/src/map/pet.c +++ b/src/map/pet.c @@ -459,13 +459,14 @@ int pet_birth_process(struct map_session_data *sd, struct s_pet *pet) if (save_settings&8) chrif_save(sd,0); //is it REALLY Needed to save the char for hatching a pet? [Skotlex] - map_addblock(&sd->pd->bl); - clif_spawn(&sd->pd->bl); - clif_send_petdata(sd,0,0); - clif_send_petdata(sd,5,battle_config.pet_hair_style); - clif_pet_equip(sd->pd); - clif_send_petstatus(sd); - + if(sd->bl.prev != NULL) { + map_addblock(&sd->pd->bl); + clif_spawn(&sd->pd->bl); + clif_send_petdata(sd,0,0); + clif_send_petdata(sd,5,battle_config.pet_hair_style); + clif_pet_equip(sd->pd); + clif_send_petstatus(sd); + } Assert((sd->status.pet_id == 0 || sd->pd == 0) || sd->pd->msd == sd); return 0; diff --git a/src/map/skill.c b/src/map/skill.c index 957f4f34a..acef1a96d 100644 --- a/src/map/skill.c +++ b/src/map/skill.c @@ -5701,6 +5701,9 @@ int skill_castend_id (int tid, unsigned int tick, int id, int data) else skill_castend_damage_id(src,target,ud->skillid,ud->skilllv,tick,0); + if (sd && sd->skillitem == ud->skillid) //Clear item skill data. + sd->skillitem = sd->skillitemlv = 0; + sc = status_get_sc(src); if(sc && sc->count && sc->data[SC_MAGICPOWER].timer != -1 && ud->skillid != HW_MAGICPOWER && ud->skillid != WZ_WATERBALL) status_change_end(src,SC_MAGICPOWER,-1); @@ -5750,7 +5753,7 @@ int skill_castend_id (int tid, unsigned int tick, int id, int data) //You can't place a skill failed packet here because it would be //sent in ALL cases, even cases where skill_check_condition fails //which would lead to double 'skill failed' messages u.u [Skotlex] - if(sd) sd->skillitem = sd->skillitemlv = -1; + if(sd) sd->skillitem = sd->skillitemlv = 0; else if(md) md->skillidx = -1; return 0; @@ -5853,6 +5856,9 @@ int skill_castend_pos (int tid, unsigned int tick, int id, int data) unit_set_walkdelay(src, tick, battle_config.default_skill_delay+skill_get_walkdelay(ud->skillid, ud->skilllv), 1); skill_castend_pos2(src,ud->skillx,ud->skilly,ud->skillid,ud->skilllv,tick,0); + if (sd && sd->skillitem == ud->skillid) //Clear item skill data. + sd->skillitem = sd->skillitemlv = 0; + if (ud->skilltimer == -1) { if (md) md->skillidx = -1; else ud->skillid = 0; //Non mobs can't clear this one as it is used for skill condition 'afterskill' @@ -5865,7 +5871,7 @@ int skill_castend_pos (int tid, unsigned int tick, int id, int data) ud->skillid = ud->skilllv = 0; if(sd) { clif_skill_fail(sd,ud->skillid,0,0); - sd->skillitem = sd->skillitemlv = -1; + sd->skillitem = sd->skillitemlv = 0; } else if (hd && hd->master) clif_skill_fail(hd->master, ud->skillid, 0, 0); @@ -6244,7 +6250,6 @@ int skill_castend_pos2 (struct block_list *src, int x, int y, int skillid, int s if (sd && !(flag&1) && sd->state.arrow_atk) //Consume arrow if a ground skill was not invoked. [Skotlex] battle_consume_ammo(sd, skillid, skilllv); - return 0; } @@ -7843,7 +7848,7 @@ int skill_check_condition (struct map_session_data *sd, int skill, int lv, int t pc_isGM(sd)>= battle_config.gm_skilluncond && sd->skillitem != skill) { //GMs don't override the skillItem check, otherwise they can use items without them being consumed! [Skotlex] - sd->skillitem = sd->skillitemlv = -1; + sd->skillitem = sd->skillitemlv = 0; return 1; } @@ -7854,13 +7859,13 @@ int skill_check_condition (struct map_session_data *sd, int skill, int lv, int t if(pc_is90overweight(sd)) { clif_skill_fail(sd,skill,9,0); - sd->skillitem = sd->skillitemlv = -1; + sd->skillitem = sd->skillitemlv = 0; return 0; } if (sd->state.abra_flag) { - sd->skillitem = sd->skillitemlv = -1; + sd->skillitem = sd->skillitemlv = 0; if(type&1) sd->state.abra_flag = 0; return 1; } @@ -7869,7 +7874,7 @@ int skill_check_condition (struct map_session_data *sd, int skill, int lv, int t (skill == AM_PHARMACY || skill == AC_MAKINGARROW || skill == BS_REPAIRWEAPON || skill == AM_TWILIGHT1 || skill == AM_TWILIGHT2 || skill == AM_TWILIGHT3 )) { - sd->skillitem = sd->skillitemlv = -1; + sd->skillitem = sd->skillitemlv = 0; return 0; } @@ -7894,8 +7899,6 @@ int skill_check_condition (struct map_session_data *sd, int skill, int lv, int t else pc_delitem(sd,i,1,0); } - if (type&1) //Casting finished - sd->skillitem = sd->skillitemlv = -1; return 1; } // for the guild skills [celest] diff --git a/src/map/unit.c b/src/map/unit.c index f3b0562e8..15571bc99 100644 --- a/src/map/unit.c +++ b/src/map/unit.c @@ -880,10 +880,18 @@ int unit_skilluse_id2(struct block_list *src, int target_id, int skill_num, int //Check range when not using skill on yourself or is a combo-skill during attack //(these are supposed to always have the same range as your attack) - if(src->id != target_id && (!temp || ud->attacktimer == -1) && - !battle_check_range(src,target,skill_get_range2(src, skill_num,skill_lv) - +(skill_num==RG_CLOSECONFINE?0:1))) //Close confine is exploitable thanks to this extra range "feature" of the client. [Skotlex] - return 0; + if(src->id != target_id && (!temp || ud->attacktimer == -1)) + { + if (skill_get_state(ud->skillid) == ST_MOVE_ENABLE) + { + if (!unit_can_reach_bl(src, target, skill_get_range2(src, skill_num,skill_lv)+1, 1, NULL, NULL)) + return 0; //Walk-path check failed. + } else + if (!battle_check_range(src, target, skill_get_range2(src, skill_num,skill_lv) + +(skill_num==RG_CLOSECONFINE?0:1))) + //Close confine is exploitable thanks to this extra range "feature" of the client. [Skotlex] + return 0; //Arrow-path check failed. + } if (!temp) //Stop attack on non-combo skills [Skotlex] unit_stop_attack(src); @@ -1041,9 +1049,14 @@ int unit_skilluse_pos2( struct block_list *src, int skill_x, int skill_y, int sk bl.m = src->m; bl.x = skill_x; bl.y = skill_y; - if(skill_num != TK_HIGHJUMP && - !battle_check_range(src,&bl,skill_get_range2(src, skill_num,skill_lv)+1)) - return 0; + + if (skill_get_state(ud->skillid) == ST_MOVE_ENABLE) + { + if (!unit_can_reach_bl(src, &bl, skill_get_range2(src, skill_num,skill_lv)+1, 1, NULL, NULL)) + return 0; //Walk-path check failed. + } else + if (!battle_check_range(src,&bl,skill_get_range2(src, skill_num,skill_lv)+1)) + return 0; //Arrow-path check failed. unit_stop_attack(src); ud->state.skillcastcancel = castcancel; @@ -1837,7 +1850,6 @@ int unit_free(struct block_list *bl, int clrtype) { intif_homunculus_requestdelete(hd->homunculus.hom_id); if (sd) sd->status.hom_id = 0; } - aFree(hd); // Remember to free it! [Lance] if(sd) sd->hd = NULL; } -- cgit v1.2.3-60-g2f50