📄 map.c
字号:
last_object_id--;
return 0;
}
/*==========================================
* 堦帪object偺夝曻
* block_list偐傜偺嶍彍丄id_db偐傜偺嶍彍
* object data偺free丄object[]傊偺NULL戙擖
*
* add偲偺懳徧惈偑柍偄偺偑婥偵側傞
*------------------------------------------
*/
int map_delobject(int id)
{
struct block_list *obj=object[id];
if(obj==NULL)
return 0;
map_delobjectnofree(id);
map_freeblock(obj);
return 0;
}
/*==========================================
* 慡堦帪obj憡庤偵func傪屇傇
*
*------------------------------------------
*/
void map_foreachobject(int (*func)(struct block_list*,va_list),int type,...)
{
int i;
int blockcount=bl_list_count;
va_list ap;
va_start(ap,type);
for(i=2;i<=last_object_id;i++){
if(object[i]){
if(type && object[i]->type!=type)
continue;
if(bl_list_count>=BL_LIST_MAX) {
if(battle_config.error_log)
printf("map_foreachobject: too many block !\n");
}
else
bl_list[bl_list_count++]=object[i];
}
}
map_freeblock_lock();
for(i=blockcount;i<bl_list_count;i++)
if( bl_list[i]->prev || bl_list[i]->next )
func(bl_list[i],ap);
map_freeblock_unlock();
va_end(ap);
bl_list_count = blockcount;
}
/*==========================================
* 彴傾僀僥儉傪徚偡
*
* data==0偺帪偼timer偱徚偊偨帪
* data!=0偺帪偼廍偆摍偱徚偊偨帪偲偟偰摦嶌
*
* 屻幰偼丄map_clearflooritem(id)傊
* map.h撪偱#define偟偰偁傞
*------------------------------------------
*/
int map_clearflooritem_timer(int tid,unsigned int tick,int id,int data)
{
struct flooritem_data *fitem;
fitem = (struct flooritem_data *)object[id];
if(fitem==NULL || fitem->bl.type!=BL_ITEM || (!data && fitem->cleartimer != tid)){
if(battle_config.error_log)
printf("map_clearflooritem_timer : error\n");
return 1;
}
if(data)
delete_timer(fitem->cleartimer,map_clearflooritem_timer);
else if(fitem->item_data.card[0] == (short)0xff00)
intif_delete_petdata(*((long *)(&fitem->item_data.card[1])));
clif_clearflooritem(fitem,0);
map_delobject(fitem->bl.id);
return 0;
}
/*==========================================
* (m,x,y)偺廃埻range儅僗撪偺嬻偒(=怤擖壜擻)cell偺
* 撪偐傜揔摉側儅僗栚偺嵗昗傪x+(y<<16)偱曉偡
*
* 尰忬range=1偱傾僀僥儉僪儘僢僾梡搑偺傒
*------------------------------------------
*/
int map_searchrandfreecell(int m,int x,int y,int range)
{
int free_cell,i,j,c;
for(free_cell=0,i=-range;i<=range;i++){
if(i+y<0 || i+y>=map[m].ys)
continue;
for(j=-range;j<=range;j++){
if(j+x<0 || j+x>=map[m].xs)
continue;
if((c=read_gat(m,j+x,i+y))==1 || c==5)
continue;
free_cell++;
}
}
if(free_cell==0)
return -1;
free_cell=rand()%free_cell;
for(i=-range;i<=range;i++){
if(i+y<0 || i+y>=map[m].ys)
continue;
for(j=-range;j<=range;j++){
if(j+x<0 || j+x>=map[m].xs)
continue;
if((c=read_gat(m,j+x,i+y))==1 || c==5)
continue;
if(free_cell==0){
x+=j;
y+=i;
i=range+1;
break;
}
free_cell--;
}
}
return x+(y<<16);
}
/*==========================================
* (m,x,y)傪拞怱偵3x3埲撪偵彴傾僀僥儉愝抲
*
* item_data偼amount埲奜傪copy偡傞
*------------------------------------------
*/
int map_addflooritem(struct item *item_data,int amount,int m,int x,int y,struct map_session_data *first_sd,
struct map_session_data *second_sd,struct map_session_data *third_sd,int type)
{
int xy,r;
unsigned int tick;
struct flooritem_data *fitem;
if((xy=map_searchrandfreecell(m,x,y,1))<0)
return 0;
r=rand();
fitem = calloc(sizeof(*fitem), 1);
if(fitem==NULL){
printf("out of memory : map_addflooritem\n");
exit(1);
}
fitem->bl.type=BL_ITEM;
fitem->bl.prev = fitem->bl.next = NULL;
fitem->bl.m=m;
fitem->bl.x=xy&0xffff;
fitem->bl.y=(xy>>16)&0xffff;
fitem->first_get_id = 0;
fitem->first_get_tick = 0;
fitem->second_get_id = 0;
fitem->second_get_tick = 0;
fitem->third_get_id = 0;
fitem->third_get_tick = 0;
fitem->bl.id = map_addobject(&fitem->bl);
if(fitem->bl.id==0){
free(fitem);
return 0;
}
tick = gettick();
if(first_sd) {
fitem->first_get_id = first_sd->bl.id;
if(type)
fitem->first_get_tick = tick + battle_config.mvp_item_first_get_time;
else
fitem->first_get_tick = tick + battle_config.item_first_get_time;
}
if(second_sd) {
fitem->second_get_id = second_sd->bl.id;
if(type)
fitem->second_get_tick = tick + battle_config.mvp_item_first_get_time + battle_config.mvp_item_second_get_time;
else
fitem->second_get_tick = tick + battle_config.item_first_get_time + battle_config.item_second_get_time;
}
if(third_sd) {
fitem->third_get_id = third_sd->bl.id;
if(type)
fitem->third_get_tick = tick + battle_config.mvp_item_first_get_time + battle_config.mvp_item_second_get_time + battle_config.mvp_item_third_get_time;
else
fitem->third_get_tick = tick + battle_config.item_first_get_time + battle_config.item_second_get_time + battle_config.item_third_get_time;
}
memcpy(&fitem->item_data,item_data,sizeof(*item_data));
fitem->item_data.amount=amount;
fitem->subx=(r&3)*3+3;
fitem->suby=((r>>2)&3)*3+3;
fitem->cleartimer=add_timer(gettick()+battle_config.flooritem_lifetime,map_clearflooritem_timer,fitem->bl.id,0);
map_addblock(&fitem->bl);
clif_dropflooritem(fitem);
return fitem->bl.id;
}
/*==========================================
* charid_db傊捛壛(曉怣懸偪偑偁傟偽曉怣)
*------------------------------------------
*/
void map_addchariddb(int charid,char *name)
{
struct charid2nick *p;
int req=0;
p=numdb_search(charid_db,charid);
if(p==NULL){ // 僨乕僞儀乕僗偵側偄
p = calloc(sizeof(struct charid2nick), 1);
if(p==NULL){
printf("out of memory : map_addchariddb\n");
exit(1);
}
p->req_id=0;
}else
numdb_erase(charid_db,charid);
req=p->req_id;
memcpy(p->nick,name,24);
p->req_id=0;
numdb_insert(charid_db,charid,p);
if(req){ // 曉怣懸偪偑偁傟偽曉怣
struct map_session_data *sd = map_id2sd(req);
if(sd!=NULL)
clif_solved_charname(sd,charid);
}
}
/*==========================================
* charid_db傊捛壛乮曉怣梫媮偺傒乯
*------------------------------------------
*/
int map_reqchariddb(struct map_session_data * sd,int charid)
{
struct charid2nick *p;
p=numdb_search(charid_db,charid);
if(p!=NULL) // 僨乕僞儀乕僗偵偡偱偵偁傞
return 0;
p = calloc(sizeof(struct charid2nick), 1);
if(p==NULL){
printf("out of memory : map_reqchariddb\n");
exit(1);
}
p->req_id=sd->bl.id;
numdb_insert(charid_db,charid,p);
return 0;
}
/*==========================================
* id_db傊bl傪捛壛
*------------------------------------------
*/
void map_addiddb(struct block_list *bl)
{
numdb_insert(id_db,bl->id,bl);
}
/*==========================================
* id_db偐傜bl傪嶍彍
*------------------------------------------
*/
void map_deliddb(struct block_list *bl)
{
numdb_erase(id_db,bl->id);
}
/*==========================================
* nick_db傊sd傪捛壛
*------------------------------------------
*/
void map_addnickdb(struct map_session_data *sd)
{
strdb_insert(nick_db,sd->status.name,sd);
}
/*==========================================
* PC偺quit張棟 map.c撪暘
*
* quit張棟偺庡懱偑堘偆傛偆側婥傕偟偰偒偨
*------------------------------------------
*/
int map_quit(struct map_session_data *sd)
{
if(sd->chatID) // 僠儍僢僩偐傜弌傞
chat_leavechat(sd);
if(sd->trade_partner) // 庢堷傪拞抐偡傞
trade_tradecancel(sd);
if(sd->party_invite>0) // 僷乕僥傿姪桿傪嫅斲偡傞
party_reply_invite(sd,sd->party_invite_account,0);
if(sd->guild_invite>0) // 僊儖僪姪桿傪嫅斲偡傞
guild_reply_invite(sd,sd->guild_invite,0);
if(sd->guild_alliance>0) // 僊儖僪摨柨姪桿傪嫅斲偡傞
guild_reply_reqalliance(sd,sd->guild_alliance_account,0);
party_send_logout(sd); // 僷乕僥傿偺儘僌傾僂僩儊僢僙乕僕憲怣
guild_send_memberinfoshort(sd,0); // 僊儖僪偺儘僌傾僂僩儊僢僙乕僕憲怣
pc_cleareventtimer(sd); // 僀儀儞僩僞僀儅傪攋婞偡傞
if(sd->state.storage_flag)
storage_guild_storage_quit(sd,0);
else
storage_storage_quit(sd); // 憅屔傪奐偄偰傞側傜曐懚偡傞
skill_castcancel(&sd->bl,0); // 塺彞傪拞抐偡傞
skill_status_change_clear(&sd->bl,1); // 僗僥乕僞僗堎忢傪夝彍偡傞
skill_clear_unitgroup(&sd->bl); // 僗僉儖儐僯僢僩僌儖乕僾偺嶍彍
skill_cleartimerskill(&sd->bl);
pc_stop_walking(sd,0);
pc_stopattack(sd);
pc_delinvincibletimer(sd);
pc_delspiritball(sd,sd->spiritball,1);
skill_gangsterparadise(sd,0);
pc_calcstatus(sd,4);
clif_clearchar_area(&sd->bl,2);
if(sd->status.pet_id && sd->pd) {
pet_remove_map(sd);
if(sd->pet.intimate <= 0) {
intif_delete_petdata(sd->status.pet_id);
sd->status.pet_id = 0;
sd->pd = NULL;
sd->petDB = NULL;
}
else
intif_save_petdata(sd->status.account_id,&sd->pet);
}
if(pc_isdead(sd))
pc_setrestartvalue(sd,2);
pc_makesavestatus(sd);
chrif_save(sd);
storage_storage_save(sd);
map_delblock(&sd->bl);
numdb_erase(id_db,sd->bl.id);
strdb_erase(nick_db,sd->status.name);
return 0;
}
/*==========================================
* id斣崋偺PC傪扵偡丅嫃側偗傟偽NULL
*------------------------------------------
*/
struct map_session_data * map_id2sd(int id)
{
struct block_list *bl;
bl=numdb_search(id_db,id);
if(bl && bl->type==BL_PC)
return (struct map_session_data*)bl;
return NULL;
}
/*==========================================
* char_id斣崋偺柤慜傪扵偡
*------------------------------------------
*/
char * map_charid2nick(int id)
{
struct charid2nick *p=numdb_search(charid_db,id);
if(p==NULL)
return NULL;
if(p->req_id!=0)
return NULL;
return p->nick;
}
/*==========================================
* 柤慜偑nick偺PC傪扵偡丅嫃側偗傟偽NULL
*------------------------------------------
*/
struct map_session_data * map_nick2sd(char *nick)
{
return strdb_search(nick_db,nick);
}
/*==========================================
* id斣崋偺暔傪扵偡
* 堦帪object偺応崌偼攝楍傪堷偔偺傒
*------------------------------------------
*/
struct block_list * map_id2bl(int id)
{
if(id<sizeof(object)/sizeof(object[0]))
return object[id];
return numdb_search(id_db,id);
}
/*==========================================
* id_db撪偺慡偰偵func傪幚峴
*------------------------------------------
*/
int map_foreachiddb(int (*func)(void*,void*,va_list),...)
{
va_list ap;
va_start(ap,func);
numdb_foreach(id_db,func,ap);
va_end(ap);
return 0;
}
/*==========================================
* map.npc傊捛壛 (warp摍偺椞堟帩偪偺傒)
*------------------------------------------
*/
int map_addnpc(int m,struct npc_data *nd)
{
int i;
if(m<0 || m>=map_num)
return -1;
for(i=0;i<map[m].npc_num && i<MAX_NPC_PER_MAP;i++)
if(map[m].npc[i]==NULL)
break;
if(i==MAX_NPC_PER_MAP){
if(battle_config.error_log)
printf("too many NPCs in one map %s\n",map[m].name);
return -1;
}
if(i==map[m].npc_num){
map[m].npc_num++;
}
map[m].npc[i]=nd;
nd->n = i;
numdb_insert(id_db,nd->bl.id,nd);
return i;
}
/*==========================================
* map柤偐傜map斣崋傊曄姺
*------------------------------------------
*/
int map_mapname2mapid(char *name)
{
struct map_data *md;
md=strdb_search(map_db,name);
if(md==NULL || md->gat==NULL)
return -1;
return md->m;
}
/*==========================================
* 懠嶪map柤偐傜ip,port曄姺
*------------------------------------------
*/
int map_mapname2ipport(char *name,int *ip,int *port)
{
struct map_data_other_server *mdos;
mdos=strdb_search(map_db,name);
if(mdos==NULL || mdos->gat)
return -1;
*ip=mdos->ip;
*port=mdos->port;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -