/// Invoked (from char-server) when a new member is added to the party. /// flag: 0-success, 1-failure int party_member_added(int party_id,uint32 account_id,uint32 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 || !sd->party_joining ) { if (!flag) //Char logged off before being accepted into party. intif_party_leave(party_id,account_id,char_id,"",PARTY_MEMBER_WITHDRAW_LEAVE); return 0; } sd2 = map_id2sd(sd->party_invite_account); sd->party_joining = false; sd->party_invite = 0; sd->party_invite_account = 0; if (!p) { ShowError("party_member_added: party %d not found.\n",party_id); intif_party_leave(party_id,account_id,char_id,"",PARTY_MEMBER_WITHDRAW_LEAVE); return 0; } if( flag ) { // failed if( sd2 != NULL ) clif_party_invite_reply(sd2,sd->status.name,PARTY_REPLY_FULL); return 0; } sd->status.party_id = party_id; clif_party_member_info(p,sd); clif_party_option(p,sd,0x100); clif_party_info(p,sd); if( sd2 != NULL ) clif_party_invite_reply(sd2,sd->status.name,PARTY_REPLY_ACCEPTED); 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_name_area(&sd->bl); //Update char name's display [Skotlex] if( p->instance_id ) instance_reqinfo(sd,p->instance_id); return 0; }
/// Invoked (from char-server) when a party member leaves the party. int party_member_withdraw(int party_id, uint32 account_id, uint32 char_id, char *name, enum e_party_member_withdraw type) { struct map_session_data* sd = map_charid2sd(char_id); struct party_data* p = party_search(party_id); if( p ) { int i; clif_party_withdraw(party_getavailablesd(p), account_id, name, type, PARTY); ARR_FIND( 0, MAX_PARTY, i, p->party.member[i].account_id == account_id && p->party.member[i].char_id == char_id ); if( i < MAX_PARTY ) { memset(&p->party.member[i], 0, sizeof(p->party.member[0])); memset(&p->data[i], 0, sizeof(p->data[0])); p->party.count--; party_check_state(p); } } if( sd && sd->status.party_id == party_id ) { #ifdef BOUND_ITEMS int idxlist[MAX_INVENTORY]; //or malloc to reduce consumtion int j,i; party_trade_bound_cancel(sd); j = pc_bound_chk(sd,BOUND_PARTY,idxlist); for(i = 0; i < j; i++) pc_delitem(sd,idxlist[i],sd->inventory.u.items_inventory[idxlist[i]].amount,0,1,LOG_TYPE_BOUND_REMOVAL); #endif sd->status.party_id = 0; clif_name_area(&sd->bl); //Update name display [Skotlex] //TODO: hp bars should be cleared too if( p->instance_id ) { struct map_data *mapdata = map_getmapdata(sd->bl.m); if( mapdata->instance_id ) { // User was on the instance map if( mapdata->save.map ) pc_setpos(sd, mapdata->save.map, mapdata->save.x, mapdata->save.y, CLR_TELEPORT); else pc_setpos(sd, sd->status.save_point.map, sd->status.save_point.x, sd->status.save_point.y, CLR_TELEPORT); } } } return 0; }
/** * Acknowledge change name request from inter-server * @param sd * @param name * @param flag */ void hom_change_name_ack(struct map_session_data *sd, char* name, int flag) { struct homun_data *hd = sd->hd; if (!hom_is_active(hd)) return; normalize_name(name," ");//bugreport:3032 if (!flag || name[0] == '\0') { clif_displaymessage(sd->fd, msg_txt(sd,280)); // You cannot use this name return; } safestrncpy(hd->homunculus.name,name,NAME_LENGTH); clif_name_area(&hd->bl); hd->homunculus.rename_flag = 1; clif_hominfo(sd,hd,0); }
int party_recv_info(struct party* sp, uint32 char_id) { struct party_data* p; struct party_member* member; struct map_session_data* sd; int removed[MAX_PARTY];// member_id in old data int removed_count = 0; int added[MAX_PARTY];// member_id in new data int added_count = 0; int member_id; bool rename = false; nullpo_ret(sp); p = (struct party_data*)idb_get(party_db, sp->party_id); if( p != NULL ) { // diff members int i; for( member_id = 0; member_id < MAX_PARTY; ++member_id ) { member = &p->party.member[member_id]; if( member->char_id == 0 ) continue; // empty ARR_FIND(0, MAX_PARTY, i, sp->member[i].account_id == member->account_id && sp->member[i].char_id == member->char_id); if( i == MAX_PARTY ) removed[removed_count++] = member_id; // If the member already existed, compare the old to the (possible) new name else if( !rename && strcmp(member->name,sp->member[i].name) ) rename = true; } for( member_id = 0; member_id < MAX_PARTY; ++member_id ) { member = &sp->member[member_id]; if( member->char_id == 0 ) continue; // empty ARR_FIND(0, MAX_PARTY, i, p->party.member[i].account_id == member->account_id && p->party.member[i].char_id == member->char_id); if( i == MAX_PARTY ) added[added_count++] = member_id; } } else { for( member_id = 0; member_id < MAX_PARTY; ++member_id ) if( sp->member[member_id].char_id != 0 ) added[added_count++] = member_id; CREATE(p, struct party_data, 1); idb_put(party_db, sp->party_id, p); } while( removed_count > 0 ) { // no longer in party member_id = removed[--removed_count]; sd = p->data[member_id].sd; if( sd == NULL ) continue; // not online party_member_withdraw(sp->party_id, sd->status.account_id, sd->status.char_id, sd->status.name, PARTY_MEMBER_WITHDRAW_LEAVE); } memcpy(&p->party, sp, sizeof(struct party)); memset(&p->state, 0, sizeof(p->state)); memset(&p->data, 0, sizeof(p->data)); for( member_id = 0; member_id < MAX_PARTY; member_id++ ) { member = &p->party.member[member_id]; if ( member->char_id == 0 ) continue;// empty p->data[member_id].sd = party_sd_check(sp->party_id, member->account_id, member->char_id); } party_check_state(p); while( added_count > 0 ) { // new in party member_id = added[--added_count]; sd = p->data[member_id].sd; if( sd == NULL ) continue;// not online clif_name_area(&sd->bl); //Update other people's display. [Skotlex] clif_party_member_info(p,sd); // Only send this on party creation, otherwise it will be sent by party_send_movemap [Lemongrass] if( sd->party_creating ){ clif_party_option(p,sd,0x100); } clif_party_info(p,NULL); if( p->instance_id != 0 ) instance_reqinfo(sd,p->instance_id); } // If a player was renamed, make sure to resend the party information if( rename ){ clif_party_info(p,NULL); } if( char_id != 0 ) { // requester sd = map_charid2sd(char_id); if( sd && sd->status.party_id == sp->party_id && party_getmemberid(p,sd) == -1 ) sd->status.party_id = 0;// was not in the party } return 0; }