From eeea994eea737a7715cd321024430800c4186c84 Mon Sep 17 00:00:00 2001 From: FlavioJS Date: Mon, 8 Oct 2007 21:39:57 +0000 Subject: * Delayed the check for required items when a skill is cast to when they are consumed. Now skills only fail due to lack of items after being cast. - Please make a bug report if you know of any skill that doesn't work like this in official. * Fixed hp of other party members not being sent when you join a party. * Removed unused global array names_id and renamed some structures that are used with variables of the same name. git-svn-id: https://rathena.svn.sourceforge.net/svnroot/rathena/trunk@11384 54d463be-8e91-2dee-dedb-b68131a5f0ec --- src/map/atcommand.c | 2 +- src/map/clif.c | 22 +++++++------- src/map/clif.h | 1 + src/map/itemdb.h | 7 +++++ src/map/map.h | 4 +-- src/map/mercenary.c | 6 ++-- src/map/mercenary.h | 4 +-- src/map/party.c | 8 ++++++ src/map/pet.c | 2 +- src/map/pet.h | 4 +-- src/map/skill.c | 82 ++++++++++++++++++++++++++++++----------------------- src/map/status.c | 2 +- 12 files changed, 85 insertions(+), 59 deletions(-) (limited to 'src') diff --git a/src/map/atcommand.c b/src/map/atcommand.c index d72342e0a..bfb20570a 100644 --- a/src/map/atcommand.c +++ b/src/map/atcommand.c @@ -8397,7 +8397,7 @@ int atcommand_hominfo(const int fd, struct map_session_data* sd, const char* com int atcommand_homstats(const int fd, struct map_session_data* sd, const char* command, const char* message) { struct homun_data *hd; - struct homunculus_db *db; + struct s_homunculus_db *db; struct s_homunculus *hom; int lv, min, max, evo; diff --git a/src/map/clif.c b/src/map/clif.c index 78917e5c1..3e7919159 100644 --- a/src/map/clif.c +++ b/src/map/clif.c @@ -99,7 +99,6 @@ static int max_account_id = DEFAULT_MAX_ACCOUNT_ID; static int max_char_id = DEFAULT_MAX_CHAR_ID; int clif_parse (int fd); -static void clif_hpmeter_single(int fd, struct map_session_data *sd); /*========================================== * mapŽI‚ĢipŻ’č @@ -3632,7 +3631,7 @@ void clif_getareachar_pc(struct map_session_data* sd,struct map_session_data* ds if((sd->status.party_id && dstsd->status.party_id == sd->status.party_id) || //Party-mate, or hpdisp setting. (battle_config.disp_hpmeter && (len = pc_isGM(sd)) >= battle_config.disp_hpmeter && len >= pc_isGM(dstsd)) ) - clif_hpmeter_single(sd->fd, dstsd); + clif_hpmeter_single(sd->fd, dstsd->bl.id, dstsd->battle_status.hp, dstsd->battle_status.max_hp); if(dstsd->status.manner < 0) clif_changestatus(&dstsd->bl,SP_MANNER,dstsd->status.manner); @@ -4277,8 +4276,8 @@ int clif_skillcastcancel(struct block_list* bl) /// type==4 "there is a delay after using a skill" MsgStringTable[219] /// type==5 "insufficient zeny" MsgStringTable[233] /// type==6 "wrong weapon" MsgStringTable[239] -/// type==7 "red jemstone needed" MsgStringTable[246] -/// type==8 "blue jemstone needed" MsgStringTable[247] +/// type==7 "red gemstone needed" MsgStringTable[246] +/// type==8 "blue gemstone needed" MsgStringTable[247] /// type==9 "overweight" MsgStringTable[580] /// type==10 "skill failed" MsgStringTable[285] /// type>=11 ignored @@ -5766,19 +5765,20 @@ int clif_party_hp(struct map_session_data *sd) /*========================================== * Sends HP bar to a single fd. [Skotlex] *------------------------------------------*/ -static void clif_hpmeter_single(int fd, struct map_session_data *sd) +void clif_hpmeter_single(int fd, int id, unsigned int hp, unsigned int maxhp) { WFIFOHEAD(fd,packet_len(0x106)); WFIFOW(fd,0) = 0x106; - WFIFOL(fd,2) = sd->status.account_id; - if (sd->battle_status.max_hp > SHRT_MAX) { //To correctly display the %hp bar. [Skotlex] - WFIFOW(fd,6) = sd->battle_status.hp/(sd->battle_status.max_hp/100); + WFIFOL(fd,2) = id; + if( maxhp > SHRT_MAX ) + {// To correctly display the %hp bar. [Skotlex] + WFIFOW(fd,6) = hp/(maxhp/100); WFIFOW(fd,8) = 100; } else { - WFIFOW(fd,6) = sd->battle_status.hp; - WFIFOW(fd,8) = sd->battle_status.max_hp; + WFIFOW(fd,6) = hp; + WFIFOW(fd,8) = maxhp; } - WFIFOSET (fd, packet_len(0x106)); + WFIFOSET(fd, packet_len(0x106)); } /*========================================== diff --git a/src/map/clif.h b/src/map/clif.h index 159a255ec..bda4d38ae 100644 --- a/src/map/clif.h +++ b/src/map/clif.h @@ -289,6 +289,7 @@ void clif_party_move(struct party* p, struct map_session_data* sd, int online); int clif_party_xy(struct map_session_data *sd); int clif_party_xy_single(int fd, struct map_session_data *sd); int clif_party_hp(struct map_session_data *sd); +void clif_hpmeter_single(int fd, int id, unsigned int hp, unsigned int maxhp); int clif_hpmeter(struct map_session_data *sd); // guild diff --git a/src/map/itemdb.h b/src/map/itemdb.h index ebfbf5c87..9d1a62f6d 100644 --- a/src/map/itemdb.h +++ b/src/map/itemdb.h @@ -10,6 +10,13 @@ #define MAX_SEARCH 5 //Designed for search functions, species max number of matches to display. +#define ITEMID_YELLOW_GEMSTONE 715 +#define ITEMID_RED_GEMSTONE 716 +#define ITEMID_BLUE_GEMSTONE 717 +#define itemid_isgemstone(id) ( (id) >= ITEMID_YELLOW_GEMSTONE && (id) <= ITEMID_BLUE_GEMSTONE ) + +#define ITEMID_TRAP 1065 + enum item_types { IT_HEALING = 0, diff --git a/src/map/map.h b/src/map/map.h index 34345a740..6887098d9 100644 --- a/src/map/map.h +++ b/src/map/map.h @@ -958,7 +958,7 @@ struct homun_data { struct status_data base_status, battle_status; struct status_change sc; struct regen_data regen; - struct homunculus_db *homunculusDB; //[orn] + struct s_homunculus_db *homunculusDB; //[orn] struct s_homunculus homunculus ; //[orn] struct map_session_data *master; //pointer back to its master @@ -974,7 +974,7 @@ struct pet_data { struct s_pet pet; struct status_data status; struct mob_db *db; - struct pet_db *petDB; + struct s_pet_db *petDB; int pet_hungry_timer; int target_id; struct { diff --git a/src/map/mercenary.c b/src/map/mercenary.c index b23669955..1477797c5 100644 --- a/src/map/mercenary.c +++ b/src/map/mercenary.c @@ -40,7 +40,7 @@ //Better equiprobability than rand()% [orn] #define rand(a, b) (a+(int) ((float)(b-a+1)*rand()/(RAND_MAX+1.0))) -struct homunculus_db homunculus_db[MAX_HOMUNCULUS_CLASS]; //[orn] +struct s_homunculus_db homunculus_db[MAX_HOMUNCULUS_CLASS]; //[orn] struct skill_tree_entry hskill_tree[MAX_HOMUNCULUS_CLASS][MAX_SKILL_TREE]; static int merc_hom_hungry(int tid,unsigned int tick,int id,int data); @@ -812,7 +812,7 @@ void merc_hom_revive(struct homun_data *hd, unsigned int hp, unsigned int sp) void merc_reset_stats(struct homun_data *hd) { //Resets a homunc stats back to zero (but doesn't touches hunger or intimacy) - struct homunculus_db *db; + struct s_homunculus_db *db; struct s_homunculus *hom; struct h_stats *base; hom = &hd->homunculus; @@ -892,7 +892,7 @@ int read_homunculusdb(void) int j = 0; const char *filename[]={"homunculus_db.txt","homunculus_db2.txt"}; char *str[50]; - struct homunculus_db *db; + struct s_homunculus_db *db; memset(homunculus_db,0,sizeof(homunculus_db)); for(i = 0; i<2; i++) diff --git a/src/map/mercenary.h b/src/map/mercenary.h index 143b88a06..06378d8f9 100644 --- a/src/map/mercenary.h +++ b/src/map/mercenary.h @@ -4,7 +4,7 @@ #ifndef _MERCENARY_H_ #define _MERCENARY_H_ -struct homunculus_db { +struct s_homunculus_db { int base_class, evo_class; char name[NAME_LENGTH]; struct h_stats { @@ -16,7 +16,7 @@ struct homunculus_db { long hungryDelay ; unsigned char element, race, base_size, evo_size; }; -extern struct homunculus_db homuncumlus_db[MAX_HOMUNCULUS_CLASS]; +extern struct s_homunculus_db homuncumlus_db[MAX_HOMUNCULUS_CLASS]; enum { HOMUNCULUS_CLASS, HOMUNCULUS_FOOD }; enum { SP_ACK = 0x00, diff --git a/src/map/party.c b/src/map/party.c index 3cac19240..90689a612 100644 --- a/src/map/party.c +++ b/src/map/party.c @@ -335,10 +335,12 @@ int party_reply_invite(struct map_session_data *sd,int account_id,int flag) return 1; } +/// Invoked (from char-server) when a member is added to the party. int party_member_added(int party_id,int account_id,int char_id, int flag) { struct map_session_data *sd = map_id2sd(account_id),*sd2; struct party_data *p = party_search(party_id); + int i; if(sd == NULL || sd->status.char_id != char_id){ if (flag == 0) { if(battle_config.error_log) @@ -362,6 +364,12 @@ int party_member_added(int party_id,int account_id,int char_id, int flag) sd->status.party_id=party_id; party_check_conflict(sd); clif_party_member_info(p,sd); + for( i = 0; i < ARRAYLENGTH(p->data); ++i ) + {// hp of the other party members + sd2 = p->data[i].sd; + if( sd2 && sd2->status.account_id != account_id && sd2->status.char_id != char_id ) + clif_hpmeter_single(sd->fd, sd2->bl.id, sd2->battle_status.hp, sd2->battle_status.max_hp); + } clif_party_hp(sd); clif_party_xy(sd); clif_charnameupdate(sd); //Update char name's display [Skotlex] diff --git a/src/map/pet.c b/src/map/pet.c index 0b7da5da2..302669632 100644 --- a/src/map/pet.c +++ b/src/map/pet.c @@ -32,7 +32,7 @@ #define MIN_PETTHINKTIME 100 -struct pet_db pet_db[MAX_PET_DB]; +struct s_pet_db pet_db[MAX_PET_DB]; static struct eri *item_drop_ers; //For loot drops delay structures. static struct eri *item_drop_list_ers; diff --git a/src/map/pet.h b/src/map/pet.h index 821874359..8ecf94d93 100644 --- a/src/map/pet.h +++ b/src/map/pet.h @@ -7,7 +7,7 @@ #define MAX_PET_DB 300 #define MAX_PETLOOT_SIZE 30 // [Valaris] - Changed to MAX_PETLOOT_SIZE [Skotlex] -struct pet_db { +struct s_pet_db { short class_; char name[NAME_LENGTH],jname[NAME_LENGTH]; short itemID; @@ -29,7 +29,7 @@ struct pet_db { int change_target_rate; struct script_code *script; }; -extern struct pet_db pet_db[MAX_PET_DB]; +extern struct s_pet_db pet_db[MAX_PET_DB]; enum { PET_CLASS,PET_CATCH,PET_EGG,PET_EQUIP,PET_FOOD }; diff --git a/src/map/skill.c b/src/map/skill.c index 5c8e671c3..421ceb6a8 100644 --- a/src/map/skill.c +++ b/src/map/skill.c @@ -43,7 +43,6 @@ #define HM_SKILLRANGEMIN 800 #define HM_SKILLRANGEMAX HM_SKILLRANGEMIN+MAX_HOMUNSKILL -int skill_names_id[MAX_SKILL_DB]; const struct skill_name_db skill_names[] = { { AC_CHARGEARROW, "AC_CHARGEARROW", "Arrow Repel" } , { AC_CONCENTRATION, "AC_CONCENTRATION", "Improve Concentration" } , @@ -2477,8 +2476,8 @@ static int skill_check_condition_hom (struct homun_data *hd, int skill, int lv, struct status_change *sc; TBL_PC * sd; int i,j,hp,sp,hp_rate,sp_rate,state,mhp ; - int index[10],itemid[10],amount[10]; - int checkitem_flag = 1, delitem_flag = 1; + int itemid[10],amount[10]; + int delitem_flag = 1; nullpo_retr(0, hd); sd = hd->master; @@ -2555,11 +2554,19 @@ static int skill_check_condition_hom (struct homun_data *hd, int skill, int lv, break; } - if (checkitem_flag) { - for(i=0;i<10;i++) { + if(!(type&1)) + return 1; + + if( delitem_flag ) + { + int index[ARRAYLENGTH(itemid)]; + + // Check items and reduce required amounts + for( i = 0; i < ARRAYLENGTH(itemid); ++i ) + { index[i] = -1; if(itemid[i] <= 0) - continue; + continue;// no item index[i] = pc_search_inventory(sd,itemid[i]); if(index[i] < 0 || sd->status.inventory[index[i]].amount < amount[i]) @@ -2568,13 +2575,10 @@ static int skill_check_condition_hom (struct homun_data *hd, int skill, int lv, return 0; } } - } - - if(!(type&1)) - return 1; - if(delitem_flag) { - for(i=0;i<10;i++) { + // Consume items + for( i = 0; i < ARRAYLENGTH(itemid); ++i ) + { if(index[i] >= 0) pc_delitem(sd,index[i],amount[i],0); } @@ -5206,7 +5210,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, in } }else{ memset(&item_tmp,0,sizeof(item_tmp)); - item_tmp.nameid = 1065; + item_tmp.nameid = ITEMID_TRAP; item_tmp.identify = 1; if(item_tmp.nameid && (flag=pc_additem(sd,&item_tmp,1))){ clif_additem(sd,0,0,flag); @@ -8054,13 +8058,13 @@ int skill_isammotype (struct map_session_data *sd, int skill) * &1: finished casting the skill (invoke hp/sp/item consumption) * &2: picked menu entry (Warp Portal, Teleport and other menu based skills) *------------------------------------------*/ -int skill_check_condition (struct map_session_data *sd, int skill, int lv, int type) +int skill_check_condition(struct map_session_data* sd, int skill, int lv, int type) { struct status_data *status; struct status_change *sc; int i,j,hp,sp,hp_rate,sp_rate,zeny,weapon,ammo,ammo_qty,state,spiritball,mhp; - int index[10],itemid[10],amount[10]; - int delitem_flag = 1, checkitem_flag = 1; + int itemid[10],amount[10]; + int delitem_flag = 1; nullpo_retr(0, sd); @@ -8464,7 +8468,7 @@ int skill_check_condition (struct map_session_data *sd, int skill, int lv, int t sg->skill_id == SA_VIOLENTGALE )) { if (sg->limit - DIFF_TICK(gettick(), sg->tick) > 0) - checkitem_flag = delitem_flag = 0; + delitem_flag = 0; else sg->limit = 0; //Disable it. } @@ -8597,7 +8601,7 @@ int skill_check_condition (struct map_session_data *sd, int skill, int lv, int t return 0; } if (sd->status.hom_id) //Don't delete items when hom is already out. - checkitem_flag = delitem_flag = 0; + delitem_flag = 0; break; case AM_REST: //Can't vapo homun if you don't have an active homunc or it's hp is < 80% if (!merc_is_hom_active(sd->hd) || sd->hd->battle_status.hp < (sd->hd->battle_status.max_hp*80/100)) @@ -8733,13 +8737,20 @@ int skill_check_condition (struct map_session_data *sd, int skill, int lv, int t return 0; } - if (checkitem_flag) { - for(i=0;i<10;i++) { - int x = lv%11 - 1; + if(!(type&1)) + return 1; + + if( delitem_flag ) + { + int index[ARRAYLENGTH(itemid)]; + + // Check consumed items and reduce required amounts + for( i = 0; i < ARRAYLENGTH(itemid); ++i ) + { index[i] = -1; - if(itemid[i] <= 0) - continue; - if(itemid[i] >= 715 && itemid[i] <= 717 && skill != HW_GANBANTEIN) + if( itemid[i] <= 0 ) + continue;// no item + if( itemid_isgemstone(itemid[i]) && skill != HW_GANBANTEIN ) { if (sd->special_state.no_gemstone) { //Make it substract 1 gem rather than skipping the cost. @@ -8749,33 +8760,32 @@ int skill_check_condition (struct map_session_data *sd, int skill, int lv, int t if(sc && sc->data[SC_INTOABYSS].timer != -1) continue; } else - if(itemid[i] == 1065 && sc && sc->data[SC_INTOABYSS].timer != -1) + if(itemid[i] == ITEMID_TRAP && sc && sc->data[SC_INTOABYSS].timer != -1) continue; if((skill == AM_POTIONPITCHER || skill == CR_SLIMPITCHER || - skill == CR_CULTIVATION) && i != x) + skill == CR_CULTIVATION) && i != lv%11 - 1)//TODO huh? what is this for? [FlavioJS] continue; index[i] = pc_search_inventory(sd,itemid[i]); if(index[i] < 0 || sd->status.inventory[index[i]].amount < amount[i]) { - if(itemid[i] == 716 || itemid[i] == 717) - clif_skill_fail(sd,skill,(7+(itemid[i]-716)),0); + if( itemid[i] == ITEMID_RED_GEMSTONE ) + clif_skill_fail(sd,skill,7,0);// red gemstone required + else if( itemid[i] == ITEMID_BLUE_GEMSTONE ) + clif_skill_fail(sd,skill,8,0);// blue gemstone required else clif_skill_fail(sd,skill,0,0); return 0; } - if(itemid[i] >= 715 && itemid[i] <= 717 && skill != HW_GANBANTEIN && + if( itemid_isgemstone(itemid[i]) && skill != HW_GANBANTEIN && sc && sc->data[SC_SPIRIT].timer != -1 && sc->data[SC_SPIRIT].val2 == SL_WIZARD) index[i] = -1; //Gemstones are checked, but not substracted from inventory. } - } - - if(!(type&1)) - return 1; - if(delitem_flag) { - for(i=0;i<10;i++) { + // Consume items + for( i = 0; i < ARRAYLENGTH(itemid); ++i ) + { if(index[i] >= 0) pc_delitem(sd,index[i],amount[i],0); } @@ -10255,7 +10265,7 @@ int skill_unit_timer_sub (struct block_list* bl, va_list ap) { struct item item_tmp; memset(&item_tmp,0,sizeof(item_tmp)); - item_tmp.nameid=1065; + item_tmp.nameid=ITEMID_TRAP; item_tmp.identify=1; map_addflooritem(&item_tmp,1,bl->m,bl->x,bl->y,0,0,0,0); } diff --git a/src/map/status.c b/src/map/status.c index 441ee1959..01d591d6c 100644 --- a/src/map/status.c +++ b/src/map/status.c @@ -2387,7 +2387,7 @@ int status_calc_homunculus(struct homun_data *hd, int first) status->luk = hom->luk / 10; if (first) { //[orn] - const struct homunculus_db *db = hd->homunculusDB; + const struct s_homunculus_db *db = hd->homunculusDB; status->def_ele = db->element; status->ele_lv = 1; status->race = db->race; -- cgit v1.2.3-70-g09d2