From e778f4f5f1b6a08adee5e7e908a44c38cd29bd12 Mon Sep 17 00:00:00 2001 From: Haru Date: Sat, 27 Dec 2014 06:35:34 +0100 Subject: Cleaned up spirit charms implementation (optimized memory and CPU usage) Signed-off-by: Haru --- src/map/battle.c | 67 ++++++++++++-------------- src/map/clif.c | 41 +++++++--------- src/map/clif.h | 4 +- src/map/map.h | 21 +++++---- src/map/pc.c | 141 ++++++++++++++++++++++++++++++++----------------------- src/map/pc.h | 9 ++-- src/map/skill.c | 46 ++++++------------ src/map/status.c | 10 ++-- src/map/unit.c | 10 ++-- 9 files changed, 170 insertions(+), 179 deletions(-) diff --git a/src/map/battle.c b/src/map/battle.c index 0201e0e3a..d32a799ab 100644 --- a/src/map/battle.c +++ b/src/map/battle.c @@ -1251,8 +1251,8 @@ int64 battle_calc_defense(int attack_type, struct block_list *src, struct block_ def1 -= def1 * i / 100; def2 -= def2 * i / 100; } - if ( sd->spiritcharm[SPIRITS_TYPE_CHARM_LAND] > 0 ) // hidden from status window - def1 += 10 * def1 * sd->spiritcharm[SPIRITS_TYPE_CHARM_LAND] / 100; + if (sd->charm_type == CHARM_TYPE_LAND && sd->charm_count > 0 ) // hidden from status window + def1 += 10 * def1 * sd->charm_count / 100; } if( sc && sc->data[SC_EXPIATIO] ){ @@ -1491,39 +1491,39 @@ int battle_calc_skillratio(int attack_type, struct block_list *src, struct block break; case NJ_KOUENKA: skillratio -= 10; - if ( sd && sd->spiritcharm[SPIRITS_TYPE_CHARM_FIRE] > 0 ) - skillratio += 20 * sd->spiritcharm[SPIRITS_TYPE_CHARM_FIRE]; + if (sd && sd->charm_type == CHARM_TYPE_FIRE && sd->charm_count > 0) + skillratio += 20 * sd->charm_count; break; case NJ_KAENSIN: skillratio -= 50; - if ( sd && sd->spiritcharm[SPIRITS_TYPE_CHARM_FIRE] > 0 ) - skillratio += 10 * sd->spiritcharm[SPIRITS_TYPE_CHARM_FIRE]; + if (sd && sd->charm_type == CHARM_TYPE_FIRE && sd->charm_count > 0) + skillratio += 10 * sd->charm_count; break; case NJ_BAKUENRYU: skillratio += 50 * (skill_lv - 1); - if ( sd && sd->spiritcharm[SPIRITS_TYPE_CHARM_FIRE] > 0 ) - skillratio += 15 * sd->spiritcharm[SPIRITS_TYPE_CHARM_FIRE]; + if (sd && sd->charm_type == CHARM_TYPE_FIRE && sd->charm_count > 0) + skillratio += 15 * sd->charm_count; break; #ifdef RENEWAL case NJ_HYOUSENSOU: skillratio -= 30; - if ( sd && sd->spiritcharm[SPIRITS_TYPE_CHARM_WATER] > 0 ) - skillratio += 5 * sd->spiritcharm[SPIRITS_TYPE_CHARM_WATER]; + if (sd && sd->charm_type == CHARM_TYPE_WATER && sd->charm_count > 0) + skillratio += 5 * sd->charm_count; #endif /* Fall through */ case NJ_HYOUSYOURAKU: skillratio += 50 * skill_lv; - if ( sd && sd->spiritcharm[SPIRITS_TYPE_CHARM_WATER] > 0 ) - skillratio += 25 * sd->spiritcharm[SPIRITS_TYPE_CHARM_WATER]; + if (sd && sd->charm_type == CHARM_TYPE_WATER && sd->charm_count > 0) + skillratio += 25 * sd->charm_count; break; case NJ_RAIGEKISAI: skillratio += 60 + 40 * skill_lv; - if ( sd && sd->spiritcharm[SPIRITS_TYPE_CHARM_WIND] > 0 ) - skillratio += 15 * sd->spiritcharm[SPIRITS_TYPE_CHARM_WIND]; + if (sd && sd->charm_type == CHARM_TYPE_WIND && sd->charm_count > 0) + skillratio += 15 * sd->charm_count; break; case NJ_KAMAITACHI: - if ( sd && sd->spiritcharm[SPIRITS_TYPE_CHARM_WIND] > 0 ) - skillratio += 10 * sd->spiritcharm[SPIRITS_TYPE_CHARM_WIND]; + if (sd && sd->charm_type == CHARM_TYPE_WIND && sd->charm_count > 0) + skillratio += 10 * sd->charm_count; /* Fall through */ case NPC_ENERGYDRAIN: skillratio += 100 * skill_lv; @@ -1550,8 +1550,8 @@ int battle_calc_skillratio(int attack_type, struct block_list *src, struct block break; case NJ_HUUJIN: skillratio += 50; - if ( sd && sd->spiritcharm[SPIRITS_TYPE_CHARM_WIND] > 0 ) - skillratio += 20 * sd->spiritcharm[SPIRITS_TYPE_CHARM_WIND]; + if (sd && sd->charm_type == CHARM_TYPE_WIND && sd->charm_count > 0) + skillratio += 20 * sd->charm_count; break; #else case WZ_VERMILION: @@ -1773,13 +1773,10 @@ int battle_calc_skillratio(int attack_type, struct block_list *src, struct block skillratio += 100 * skill_lv; break; case KO_KAIHOU: - if ( sd ) { - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, i, sd->spiritcharm[i] > 0); - if ( i < SPIRITS_TYPE_SPHERE ) { - skillratio += -100 + 200 * sd->spiritcharm[i]; - RE_LVL_DMOD(100); - pc->del_charm(sd, sd->spiritcharm[i], i); - } + if (sd && sd->charm_type != CHARM_TYPE_NONE && sd->charm_count > 0) { + skillratio += -100 + 200 * sd->charm_count; + RE_LVL_DMOD(100); + pc->del_charm(sd, sd->charm_count, sd->charm_type); } break; default: @@ -3389,10 +3386,9 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list if (s_ele == -1){ // pl=-1 : the skill takes the weapon's element s_ele = sstatus->rhw.ele; - if( sd ){ //Summoning 10 spiritcharm will endow your weapon - int i; - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, i, sd->spiritcharm[i] >= MAX_SPIRITCHARM); - if( i < SPIRITS_TYPE_SPHERE ) s_ele = i; + if (sd && sd->charm_type != CHARM_TYPE_NONE && sd->charm_count >= MAX_SPIRITCHARM) { + //Summoning 10 spiritcharm will endow your weapon + s_ele = sd->charm_type; } }else if (s_ele == -2) //Use status element s_ele = status_get_attack_sc_element(src,status->get_sc(src)); @@ -3434,11 +3430,8 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list s_ele = ELE_DARK; break; case KO_KAIHOU: - if (sd) { - int i; - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, i, sd->spiritcharm[i] > 0); - if( i < SPIRITS_TYPE_SPHERE ) - s_ele = i; + if (sd && sd->charm_type != CHARM_TYPE_NONE && sd->charm_count > 0) { + s_ele = sd->charm_type; } break; #ifdef RENEWAL @@ -4296,9 +4289,9 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list { //Take weapon's element s_ele = sstatus->rhw.ele; s_ele_ = sstatus->lhw.ele; - if( sd ){ //Summoning 10 spiritcharm will endow your weapon. - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, i, sd->spiritcharm[i] >= MAX_SPIRITCHARM); - if( i < SPIRITS_TYPE_SPHERE ) s_ele = s_ele_ = i; + if (sd && sd->charm_type != CHARM_TYPE_NONE && sd->charm_count >= MAX_SPIRITCHARM) { + //Summoning 10 spiritcharm will endow your weapon. + s_ele = s_ele_ = sd->charm_type; } if( flag.arrow && sd && sd->bonus.arrow_ele ) s_ele = sd->bonus.arrow_ele; diff --git a/src/map/clif.c b/src/map/clif.c index d39d87a8f..268066d1a 100644 --- a/src/map/clif.c +++ b/src/map/clif.c @@ -1280,16 +1280,13 @@ void clif_spiritball_single(int fd, struct map_session_data *sd) { /*========================================== * Kagerou/Oboro amulet spirit *------------------------------------------*/ -void clif_charm_single(int fd, struct map_session_data *sd, short type) { - - if ( type <= SPIRITS_TYPE_NONE || type >= SPIRITS_TYPE_SPHERE ) - return; - +void clif_charm_single(int fd, struct map_session_data *sd) +{ WFIFOHEAD(fd, packet_len(0x08cf)); - WFIFOW(fd,0)=0x08cf; - WFIFOL(fd,2)=sd->bl.id; - WFIFOW(fd,6)=type; - WFIFOW(fd,8)=sd->spiritcharm[type]; + WFIFOW(fd,0) = 0x08cf; + WFIFOL(fd,2) = sd->bl.id; + WFIFOW(fd,6) = sd->charm_type; + WFIFOW(fd,8) = sd->charm_count; WFIFOSET(fd, packet_len(0x08cf)); } @@ -1375,8 +1372,8 @@ bool clif_spawn(struct block_list *bl) for( i = 0; i < sd->sc_display_count; i++ ) { clif->sc_load(&sd->bl, sd->bl.id,AREA,status->IconChangeTable[sd->sc_display[i]->type],sd->sc_display[i]->val1,sd->sc_display[i]->val2,sd->sc_display[i]->val3); } - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, i, sd->spiritcharm[i] > 0); - clif->spiritcharm(sd, i); + if (sd->charm_type != CHARM_TYPE_NONE && sd->charm_count > 0) + clif->spiritcharm(sd); if (sd->status.robe) clif->refreshlook(bl,bl->id,LOOK_ROBE,sd->status.robe,AREA); } @@ -4275,8 +4272,8 @@ void clif_getareachar_pc(struct map_session_data* sd,struct map_session_data* ds if(dstsd->spiritball > 0) clif->spiritball_single(sd->fd, dstsd); - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, i, sd->spiritcharm[i] > 0); - clif->charm_single(sd->fd, dstsd, i); + if (sd->charm_type != CHARM_TYPE_NONE && sd->charm_count > 0) + clif->charm_single(sd->fd, dstsd); for( i = 0; i < dstsd->sc_display_count; i++ ) { clif->sc_load(&sd->bl,dstsd->bl.id,SELF,status->IconChangeTable[dstsd->sc_display[i]->type],dstsd->sc_display[i]->val1,dstsd->sc_display[i]->val2,dstsd->sc_display[i]->val3); @@ -8473,7 +8470,6 @@ void clif_refresh_storagewindow( struct map_session_data *sd ) { // refresh the client's screen, getting rid of any effects void clif_refresh(struct map_session_data *sd) { - int i; nullpo_retv(sd); clif->changemap(sd,sd->bl.m,sd->bl.x,sd->bl.y); @@ -8492,8 +8488,8 @@ void clif_refresh(struct map_session_data *sd) clif->updatestatus(sd,SP_LUK); if (sd->spiritball) clif->spiritball_single(sd->fd, sd); - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, i, sd->spiritcharm[i] > 0); - clif->charm_single(sd->fd, sd, i); + if (sd->charm_type != CHARM_TYPE_NONE && sd->charm_count > 0) + clif->charm_single(sd->fd, sd); if (sd->vd.cloth_color) clif->refreshlook(&sd->bl,sd->bl.id,LOOK_CLOTHES_COLOR,sd->vd.cloth_color,SELF); @@ -17471,19 +17467,16 @@ void clif_parse_SkillSelectMenu(int fd, struct map_session_data *sd) { /*========================================== * Kagerou/Oboro amulet spirit *------------------------------------------*/ -void clif_charm(struct map_session_data *sd,short type) +void clif_charm(struct map_session_data *sd) { unsigned char buf[10]; nullpo_retv(sd); - if ( type <= SPIRITS_TYPE_NONE || type >= SPIRITS_TYPE_SPHERE ) - return; - - WBUFW(buf,0)=0x08cf; - WBUFL(buf,2)=sd->bl.id; - WBUFW(buf,6)=type; - WBUFW(buf,8)=sd->spiritcharm[type]; + WBUFW(buf,0) = 0x08cf; + WBUFL(buf,2) = sd->bl.id; + WBUFW(buf,6) = sd->charm_type; + WBUFW(buf,8) = sd->charm_count; clif->send(buf,packet_len(0x08cf),&sd->bl,AREA); } /// Move Item from or to Personal Tab (CZ_WHATSOEVER) [FE] diff --git a/src/map/clif.h b/src/map/clif.h index 3144f1586..6a99ba79a 100644 --- a/src/map/clif.h +++ b/src/map/clif.h @@ -820,8 +820,8 @@ struct clif_interface { void (*specialeffect_single) (struct block_list* bl, int type, int fd); void (*specialeffect_value) (struct block_list* bl, int effect_id, int num, send_target target); void (*millenniumshield) (struct block_list *bl, short shields ); - void (*spiritcharm) (struct map_session_data *sd, short type); - void (*charm_single) (int fd, struct map_session_data *sd, short type); + void (*spiritcharm) (struct map_session_data *sd); + void (*charm_single) (int fd, struct map_session_data *sd); void (*snap) ( struct block_list *bl, short x, short y ); void (*weather_check) (struct map_session_data *sd); /* sound effects client-side */ diff --git a/src/map/map.h b/src/map/map.h index 3b24872fe..c28a65f52 100644 --- a/src/map/map.h +++ b/src/map/map.h @@ -283,7 +283,7 @@ enum { RC2_MAX }; -enum { +enum elements { ELE_NEUTRAL=0, ELE_WATER, ELE_EARTH, @@ -297,14 +297,17 @@ enum { ELE_MAX }; -enum { - SPIRITS_TYPE_NONE = 0, - SPIRITS_TYPE_CHARM_WATER, - SPIRITS_TYPE_CHARM_LAND, - SPIRITS_TYPE_CHARM_FIRE, - SPIRITS_TYPE_CHARM_WIND, - SPIRITS_TYPE_SPHERE, - SPIRITS_TYPE_END +/** + * Types of spirit charms. + * + * Note: Code assumes that this matches the first entries in enum elements. + */ +enum spirit_charm_types { + CHARM_TYPE_NONE = 0, + CHARM_TYPE_WATER, + CHARM_TYPE_LAND, + CHARM_TYPE_FIRE, + CHARM_TYPE_WIND }; enum auto_trigger_flag { diff --git a/src/map/pc.c b/src/map/pc.c index af630a5c6..806bfb42c 100644 --- a/src/map/pc.c +++ b/src/map/pc.c @@ -7017,8 +7017,8 @@ int pc_dead(struct map_session_data *sd,struct block_list *src) { if ( sd->spiritball ) pc->delspiritball(sd, sd->spiritball, 0); - for ( i = SPIRITS_TYPE_CHARM_WATER; i < SPIRITS_TYPE_SPHERE; i++ ) - pc->del_charm(sd, sd->spiritcharm[i], i); + if (sd->charm_type != CHARM_TYPE_NONE && sd->charm_count > 0) + pc->del_charm(sd, sd->charm_count, sd->charm_type); if (src) { switch (src->type) { @@ -9794,103 +9794,124 @@ bool pc_can_use_command(struct map_session_data *sd, const char *command) { return atcommand->can_use(sd,command); } -int pc_charm_timer(int tid, int64 tick, int id, intptr_t data) { +/** + * Spirit Charm expiration timer. + * + * @see TimerFunc + */ +int pc_charm_timer(int tid, int64 tick, int id, intptr_t data) +{ struct map_session_data *sd; - int i, type; + int i; if( (sd=(struct map_session_data *)map->id2sd(id)) == NULL || sd->bl.type!=BL_PC ) return 1; - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, type, sd->spiritcharm[type] > 0); - - if( sd->spiritcharm[type] <= 0 ) - { - ShowError("pc_charm_timer: %d spiritcharm's available. (aid=%d cid=%d tid=%d)\n", sd->spiritcharm[type], sd->status.account_id, sd->status.char_id, tid); - sd->spiritcharm[type] = 0; + if (sd->charm_count <= 0) { + ShowError("pc_charm_timer: %d spiritcharm's available. (aid=%d cid=%d tid=%d)\n", sd->charm_count, sd->status.account_id, sd->status.char_id, tid); + sd->charm_count = 0; return 0; } - ARR_FIND(0, sd->spiritcharm[type], i, sd->charm_timer[type][i] == tid); - if( i == sd->spiritcharm[type] ) - { + ARR_FIND(0, sd->charm_count, i, sd->charm_timer[i] == tid); + if (i == sd->charm_count) { ShowError("pc_charm_timer: timer not found (aid=%d cid=%d tid=%d)\n", sd->status.account_id, sd->status.char_id, tid); return 0; } - sd->spiritcharm[type]--; - if( i != sd->spiritcharm[type] ) - memmove(sd->charm_timer[type]+i, sd->charm_timer[type]+i+1, (sd->spiritcharm[type]-i)*sizeof(int)); - sd->charm_timer[type][sd->spiritcharm[type]] = INVALID_TIMER; + sd->charm_count--; + if(i != sd->charm_count) + memmove(sd->charm_timer+i, sd->charm_timer+i+1, (sd->charm_count-i)*sizeof(int)); + sd->charm_timer[sd->charm_count] = INVALID_TIMER; - clif->spiritcharm(sd, type); + clif->spiritcharm(sd); return 0; } -int pc_add_charm(struct map_session_data *sd,int interval,int max,int type) +/** + * Adds a spirit charm. + * + * @param sd Target character. + * @param interval Duration. + * @param max Maximum amount of charms to add. + * @param type Charm type (@see spirit_charm_types) + */ +void pc_add_charm(struct map_session_data *sd, int interval, int max, int type) { int tid, i; - nullpo_ret(sd); + nullpo_retv(sd); - if(max > 10) - max = 10; - if(sd->spiritcharm[type] < 0) - sd->spiritcharm[type] = 0; + if (sd->charm_type != CHARM_TYPE_NONE && type != sd->charm_type) { + pc->del_charm(sd, sd->charm_count, sd->charm_type); + } - if( sd->spiritcharm[type] && sd->spiritcharm[type] >= max ) - { - if(sd->charm_timer[type][0] != INVALID_TIMER) - timer->delete(sd->charm_timer[type][0],pc->charm_timer); - sd->spiritcharm[type]--; - if( sd->spiritcharm[type] != 0 ) - memmove(sd->charm_timer[type]+0, sd->charm_timer[type]+1, (sd->spiritcharm[type])*sizeof(int)); - sd->charm_timer[type][sd->spiritcharm[type]] = INVALID_TIMER; + if (max > MAX_SPIRITCHARM) + max = MAX_SPIRITCHARM; + if (sd->charm_count < 0) + sd->charm_count = 0; + + if (sd->charm_count && sd->charm_count >= max) { + if (sd->charm_timer[0] != INVALID_TIMER) + timer->delete(sd->charm_timer[0],pc->charm_timer); + sd->charm_count--; + if (sd->charm_count != 0) + memmove(sd->charm_timer+0, sd->charm_timer+1, sd->charm_count*sizeof(int)); + sd->charm_timer[sd->charm_count] = INVALID_TIMER; } tid = timer->add(timer->gettick()+interval, pc->charm_timer, sd->bl.id, 0); - ARR_FIND(0, sd->spiritcharm[type], i, sd->charm_timer[type][i] == INVALID_TIMER || DIFF_TICK(timer->get(tid)->tick, timer->get(sd->charm_timer[type][i])->tick) < 0); - if( i != sd->spiritcharm[type] ) - memmove(sd->charm_timer[type]+i+1, sd->charm_timer[type]+i, (sd->spiritcharm[type]-i)*sizeof(int)); - sd->charm_timer[type][i] = tid; - sd->spiritcharm[type]++; + ARR_FIND(0, sd->charm_count, i, sd->charm_timer[i] == INVALID_TIMER || DIFF_TICK(timer->get(tid)->tick, timer->get(sd->charm_timer[i])->tick) < 0); + if (i != sd->charm_count) + memmove(sd->charm_timer+i+1, sd->charm_timer+i, (sd->charm_count-i)*sizeof(int)); + sd->charm_timer[i] = tid; + sd->charm_count++; - clif->spiritcharm(sd, type); - return 0; + clif->spiritcharm(sd); } -int pc_del_charm(struct map_session_data *sd,int count,int type) +/** + * Removes one or more spirit charms. + * + * @param sd The target character. + * @param count Amount of charms to remove. + * @param type Type of charm to remove. + */ +void pc_del_charm(struct map_session_data *sd, int count, int type) { int i; - nullpo_ret(sd); + nullpo_retv(sd); - if( sd->spiritcharm[type] <= 0 ) { - sd->spiritcharm[type] = 0; - return 0; + if (sd->charm_type != type) + return; + + if (sd->charm_count <= 0) { + sd->charm_count = 0; + return; } - if( count <= 0 ) - return 0; - if( count > sd->spiritcharm[type] ) - count = sd->spiritcharm[type]; - sd->spiritcharm[type] -= count; - if( count > 10 ) - count = 10; + if (count <= 0) + return; + if (count > sd->charm_count) + count = sd->charm_count; + sd->charm_count -= count; + if (count > MAX_SPIRITCHARM) + count = MAX_SPIRITCHARM; - for(i = 0; i < count; i++) { - if(sd->charm_timer[type][i] != INVALID_TIMER) { - timer->delete(sd->charm_timer[type][i],pc->charm_timer); - sd->charm_timer[type][i] = INVALID_TIMER; + for (i = 0; i < count; i++) { + if(sd->charm_timer[i] != INVALID_TIMER) { + timer->delete(sd->charm_timer[i],pc->charm_timer); + sd->charm_timer[i] = INVALID_TIMER; } } - for(i = count; i < 10; i++) { - sd->charm_timer[type][i-count] = sd->charm_timer[type][i]; - sd->charm_timer[type][i] = INVALID_TIMER; + for (i = count; i < MAX_SPIRITCHARM; i++) { + sd->charm_timer[i-count] = sd->charm_timer[i]; + sd->charm_timer[i] = INVALID_TIMER; } - clif->spiritcharm(sd, type); - return 0; + clif->spiritcharm(sd); } /*========================================== * Renewal EXP/Itemdrop rate modifier base on level penalty diff --git a/src/map/pc.h b/src/map/pc.h index b7839147d..1785bd4c4 100644 --- a/src/map/pc.h +++ b/src/map/pc.h @@ -366,8 +366,9 @@ struct map_session_data { short catch_target_class; // pet catching, stores a pet class to catch (short now) [zzo] short spiritball, spiritball_old; int spirit_timer[MAX_SPIRITBALL]; - short spiritcharm[SPIRITS_TYPE_END]; - int charm_timer[SPIRITS_TYPE_END][MAX_SPIRITCHARM]; + short charm_count; + int charm_type; + int charm_timer[MAX_SPIRITCHARM]; unsigned char potion_success_counter; //Potion successes in row counter unsigned char mission_count; //Stores the bounty kill count for TK_MISSION short mission_mobid; //Stores the target mob_id for TK_MISSION @@ -970,8 +971,8 @@ struct pc_interface { int (*load_combo) (struct map_session_data *sd); - int (*add_charm) (struct map_session_data *sd,int interval,int max,int type); - int (*del_charm) (struct map_session_data *sd,int count,int type); + void (*add_charm) (struct map_session_data *sd, int interval, int max, int type); + void (*del_charm) (struct map_session_data *sd, int count, int type); void (*baselevelchanged) (struct map_session_data *sd); int (*level_penalty_mod) (int diff, unsigned char race, unsigned short mode, int type); diff --git a/src/map/skill.c b/src/map/skill.c index 81095b4ac..55b86310e 100644 --- a/src/map/skill.c +++ b/src/map/skill.c @@ -6168,10 +6168,8 @@ int skill_castend_nodamage_id(struct block_list *src, struct block_list *bl, uin sp = 2 * dstmd->level; mob->target(dstmd,src,0); } - if ( dstsd ) { - int i; - for ( i = SPIRITS_TYPE_CHARM_WATER; i < SPIRITS_TYPE_SPHERE; i++ ) - pc->del_charm(dstsd, dstsd->spiritcharm[i], i); + if (dstsd && dstsd->charm_type != CHARM_TYPE_NONE && dstsd->charm_count > 0) { + pc->del_charm(dstsd, dstsd->charm_count, dstsd->charm_type); } if (sp) status->heal(src, 0, sp, 3); clif->skill_nodamage(src,bl,skill_id,skill_lv,sp?1:0); @@ -9039,10 +9037,8 @@ int skill_castend_nodamage_id(struct block_list *src, struct block_list *bl, uin pc->delspiritball(dstsd, dstsd->spiritball, 0); status_percent_heal(src, 0, sp); } - if ( dstsd ) { - int i; - for (i = SPIRITS_TYPE_CHARM_WATER; i < SPIRITS_TYPE_SPHERE; i++) - pc->del_charm(dstsd, dstsd->spiritcharm[i], i); + if (dstsd && dstsd->charm_type != CHARM_TYPE_NONE && dstsd->charm_count > 0) { + pc->del_charm(dstsd, dstsd->charm_count, dstsd->charm_type); } clif->skill_nodamage(src, bl, skill_id, skill_lv, sp ? 1:0); } else { @@ -9620,13 +9616,9 @@ int skill_castend_nodamage_id(struct block_list *src, struct block_list *bl, uin case KO_KAZEHU_SEIRAN: case KO_DOHU_KOUKAI: if(sd) { - int i; int ttype = skill->get_ele(skill_id, skill_lv); clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, i, sd->spiritcharm[i] > 0 && ttype != i); - if( i < SPIRITS_TYPE_SPHERE ) - pc->del_charm(sd, sd->spiritcharm[i], i); // replace with a new one. - pc->add_charm(sd, skill->get_time(skill_id, skill_lv), MAX_SPIRITCHARM, ttype); + pc->add_charm(sd, skill->get_time(skill_id, skill_lv), MAX_SPIRITCHARM, ttype); // replace existing charms of other type } break; @@ -11397,14 +11389,13 @@ struct skill_unit_group* skill_unitsetting(struct block_list *src, uint16 skill_ val3 = (x<<16)|y; break; case KO_ZENKAI: - if( sd ){ - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, i, sd->spiritcharm[i] > 0); - if( i < SPIRITS_TYPE_SPHERE ){ - val1 = sd->spiritcharm[i]; // no. of aura - val2 = i; // aura type + if (sd) { + if (sd->charm_type != CHARM_TYPE_NONE && sd->charm_count > 0) { + val1 = sd->charm_count; // no. of aura + val2 = sd->charm_type; // aura type limit += val1 * 1000; - subunt = i - 1; - pc->del_charm(sd, sd->spiritcharm[i], i); + subunt = sd->charm_type - 1; + pc->del_charm(sd, sd->charm_count, sd->charm_type); } } break; @@ -13732,24 +13723,17 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id case KO_HYOUHU_HUBUKI: case KO_KAZEHU_SEIRAN: case KO_DOHU_KOUKAI: - { - int ttype = skill->get_ele(skill_id, skill_lv); - if( sd->spiritcharm[ttype] >= MAX_SPIRITCHARM ){ - clif->skill_fail(sd, skill_id, USESKILL_FAIL_SUMMON, 0); - return 0; - } + if (sd->charm_type == skill->get_ele(skill_id, skill_lv) && sd->charm_count >= MAX_SPIRITCHARM) { + clif->skill_fail(sd, skill_id, USESKILL_FAIL_SUMMON, 0); + return 0; } break; case KO_KAIHOU: case KO_ZENKAI: - { - int i; - ARR_FIND(SPIRITS_TYPE_CHARM_WATER, SPIRITS_TYPE_SPHERE, i, sd->spiritcharm[i] > 0); - if( i >= SPIRITS_TYPE_SPHERE ) { + if (sd->charm_type != CHARM_TYPE_NONE && sd->charm_count > 0) { clif->skill_fail(sd,skill_id,USESKILL_FAIL_SUMMON,0); return 0; } - } break; default: { diff --git a/src/map/status.c b/src/map/status.c index 9ad8d849f..3da0238c5 100644 --- a/src/map/status.c +++ b/src/map/status.c @@ -8648,11 +8648,9 @@ int status_change_start(struct block_list *src, struct block_list *bl, enum sc_t break; case SC__ENERVATION: val2 = 20 + 10 * val1; // ATK Reduction - if ( sd ) { - int i; + if (sd) { pc->delspiritball(sd, sd->spiritball, 0); - for (i = SPIRITS_TYPE_CHARM_WATER; i < SPIRITS_TYPE_SPHERE; i++) - pc->del_charm(sd, sd->spiritcharm[i], i); + pc->del_charm(sd, sd->charm_count, sd->charm_type); } break; case SC__GROOMY: @@ -11495,8 +11493,8 @@ int status_get_weapon_atk(struct block_list *bl, struct weapon_atk *watk, int fl max += (rnd() % 100) % r + 1; } - if ( sd->spiritcharm[SPIRITS_TYPE_CHARM_LAND] > 0 ) - max += 10 * max * sd->spiritcharm[SPIRITS_TYPE_CHARM_LAND] / 100; + if (sd->charm_type == CHARM_TYPE_LAND && sd->charm_count > 0) + max += 10 * max * sd->charm_count / 100; } max = status->calc_watk(bl, sc, max, false); diff --git a/src/map/unit.c b/src/map/unit.c index 27b96c55b..6e4efd533 100644 --- a/src/map/unit.c +++ b/src/map/unit.c @@ -2593,8 +2593,6 @@ int unit_free(struct block_list *bl, clr_type clrtype) { case BL_PC: { struct map_session_data *sd = (struct map_session_data*)bl; - int i; - unsigned int k; sd->state.loggingout = 1; @@ -2619,8 +2617,7 @@ int unit_free(struct block_list *bl, clr_type clrtype) { pc->cleareventtimer(sd); pc->inventory_rental_clear(sd); pc->delspiritball(sd,sd->spiritball,1); - for(i = SPIRITS_TYPE_CHARM_WATER; i < SPIRITS_TYPE_SPHERE; i++) - pc->del_charm(sd, sd->spiritcharm[i], i); + pc->del_charm(sd, sd->charm_count, sd->charm_type); if( sd->st && sd->st->state != RUN ) {// free attached scripts that are waiting script->free_state(sd->st); @@ -2634,6 +2631,7 @@ int unit_free(struct block_list *bl, clr_type clrtype) { sd->combo_count = 0; /* [Ind/Hercules] */ if( sd->sc_display_count ) { + int i; for(i = 0; i < sd->sc_display_count; i++) { ers_free(pc->sc_display_ers, sd->sc_display[i]); } @@ -2657,8 +2655,8 @@ int unit_free(struct block_list *bl, clr_type clrtype) { sd->num_quests = sd->avail_quests = 0; } - if( sd->hdata ) - { + if (sd->hdata) { + unsigned int k; for( k = 0; k < sd->hdatac; k++ ) { if( sd->hdata[k]->flag.free ) { aFree(sd->hdata[k]->data); -- cgit v1.2.3-60-g2f50