* Readded @disablenpc
* Fixed @reloadscript not removing old NPC's and monsters first * Some changes in mob and NPC unloading * Changed the original @disablenpc to @hidenpc git-svn-id: https://svn.code.sf.net/p/rathena/svn/branches/stable@1429 54d463be-8e91-2dee-dedb-b68131a5f0ec
This commit is contained in:
parent
ad4fcfbe12
commit
171609d4a2
@ -1,6 +1,15 @@
|
|||||||
|
|
||||||
Date Added
|
Date Added
|
||||||
|
|
||||||
|
04/07
|
||||||
|
* Readded @disablenpc (not the same as @hidenpc) [celest]
|
||||||
|
* Fixed @reloadscript not removing old NPC's and monsters first [celest]
|
||||||
|
* Some changes in mob and NPC unloading [celest]
|
||||||
|
* Changed the original @disablenpc to @hidenpc [celest]
|
||||||
|
* Fixed HP Conversion to properly not reduce HP if SP is full [celest]
|
||||||
|
* Updated Defender -- should reduce walking speed, and does not reduce attack speed
|
||||||
|
at level 5 [celest]
|
||||||
|
|
||||||
04/06
|
04/06
|
||||||
* Fixed a crash in clif_send when checking packet version, thanks to Alex14
|
* Fixed a crash in clif_send when checking packet version, thanks to Alex14
|
||||||
* Fixed a crash in Deluge, Volcano and Violent Gale, thanks to Alex14
|
* Fixed a crash in Deluge, Volcano and Violent Gale, thanks to Alex14
|
||||||
|
@ -567,6 +567,9 @@ enablenpc: 80
|
|||||||
// Disables a NPC.
|
// Disables a NPC.
|
||||||
disablenpc: 80
|
disablenpc: 80
|
||||||
|
|
||||||
|
// Hides a NPC.
|
||||||
|
hidenpc: 80
|
||||||
|
|
||||||
// Move a NPC
|
// Move a NPC
|
||||||
npcmove: 80
|
npcmove: 80
|
||||||
|
|
||||||
|
@ -61,7 +61,7 @@ Llevelcheck:
|
|||||||
Ladvclasses:
|
Ladvclasses:
|
||||||
if(SkillPoint != 0) goto Lskillpt;
|
if(SkillPoint != 0) goto Lskillpt;
|
||||||
//Lord Knight & Paladin
|
//Lord Knight & Paladin
|
||||||
if(oldclass == 7 && readparam(19) == 4001 || oldclass == 14 && readparam(19) == 4001) goto Lswordsmanhigh;
|
if(oldclass == 7 && readparam(19) == 4001 || oldclass == 13 && readparam(19) == 4001 || oldclass == 14 && readparam(19) == 4001 || oldclass == 21 && readparam(19) == 4001) goto Lswordsmanhigh;
|
||||||
if(readparam(19) == 4002 && oldclass == 7) goto Llordknight;
|
if(readparam(19) == 4002 && oldclass == 7) goto Llordknight;
|
||||||
if(readparam(19) == 4002 && oldclass == 14) goto Lpaladin;
|
if(readparam(19) == 4002 && oldclass == 14) goto Lpaladin;
|
||||||
//Assassin Cross & Stalker
|
//Assassin Cross & Stalker
|
||||||
|
@ -167,6 +167,7 @@ ACMD_FUNC(guildrecall); // by Yor
|
|||||||
ACMD_FUNC(partyrecall); // by Yor
|
ACMD_FUNC(partyrecall); // by Yor
|
||||||
ACMD_FUNC(nuke); // [Valaris]
|
ACMD_FUNC(nuke); // [Valaris]
|
||||||
ACMD_FUNC(enablenpc);
|
ACMD_FUNC(enablenpc);
|
||||||
|
ACMD_FUNC(hidenpc);
|
||||||
ACMD_FUNC(disablenpc);
|
ACMD_FUNC(disablenpc);
|
||||||
ACMD_FUNC(servertime); // by Yor
|
ACMD_FUNC(servertime); // by Yor
|
||||||
ACMD_FUNC(chardelitem); // by Yor
|
ACMD_FUNC(chardelitem); // by Yor
|
||||||
@ -433,6 +434,7 @@ static AtCommandInfo atcommand_info[] = {
|
|||||||
{ AtCommand_PartyRecall, "@partyrecall", 60, atcommand_partyrecall }, // by Yor
|
{ AtCommand_PartyRecall, "@partyrecall", 60, atcommand_partyrecall }, // by Yor
|
||||||
{ AtCommand_Nuke, "@nuke", 60, atcommand_nuke }, // [Valaris]
|
{ AtCommand_Nuke, "@nuke", 60, atcommand_nuke }, // [Valaris]
|
||||||
{ AtCommand_Enablenpc, "@enablenpc", 80, atcommand_enablenpc }, // []
|
{ AtCommand_Enablenpc, "@enablenpc", 80, atcommand_enablenpc }, // []
|
||||||
|
{ AtCommand_Hidenpc, "@hidenpc", 80, atcommand_hidenpc }, // []
|
||||||
{ AtCommand_Disablenpc, "@disablenpc", 80, atcommand_disablenpc }, // []
|
{ AtCommand_Disablenpc, "@disablenpc", 80, atcommand_disablenpc }, // []
|
||||||
{ AtCommand_ServerTime, "@time", 0, atcommand_servertime }, // by Yor
|
{ AtCommand_ServerTime, "@time", 0, atcommand_servertime }, // by Yor
|
||||||
{ AtCommand_ServerTime, "@date", 0, atcommand_servertime }, // by Yor
|
{ AtCommand_ServerTime, "@date", 0, atcommand_servertime }, // by Yor
|
||||||
@ -5735,9 +5737,9 @@ int atcommand_reloadscript(
|
|||||||
rehash();
|
rehash();
|
||||||
|
|
||||||
atcommand_broadcast( fd, sd, "@broadcast", "Reloading NPCs..." );
|
atcommand_broadcast( fd, sd, "@broadcast", "Reloading NPCs..." );
|
||||||
do_init_npc();
|
//do_init_npc();
|
||||||
do_init_script();
|
do_init_script();
|
||||||
|
npc_reload();
|
||||||
npc_event_do_oninit();
|
npc_event_do_oninit();
|
||||||
|
|
||||||
clif_displaymessage(fd, msg_table[100]); // Scripts reloaded.
|
clif_displaymessage(fd, msg_table[100]); // Scripts reloaded.
|
||||||
@ -6183,7 +6185,7 @@ int atcommand_enablenpc(const int fd, struct map_session_data* sd,
|
|||||||
*
|
*
|
||||||
*------------------------------------------
|
*------------------------------------------
|
||||||
*/
|
*/
|
||||||
int atcommand_disablenpc(const int fd, struct map_session_data* sd,
|
int atcommand_hidenpc(const int fd, struct map_session_data* sd,
|
||||||
const char* command, const char* message)
|
const char* command, const char* message)
|
||||||
{
|
{
|
||||||
char NPCname[100];
|
char NPCname[100];
|
||||||
@ -6207,6 +6209,31 @@ int atcommand_disablenpc(const int fd, struct map_session_data* sd,
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int atcommand_disablenpc(const int fd, struct map_session_data* sd,
|
||||||
|
const char* command, const char* message)
|
||||||
|
{
|
||||||
|
struct npc_data *nd;
|
||||||
|
char NPCname[100];
|
||||||
|
nullpo_retr(-1, sd);
|
||||||
|
|
||||||
|
memset(NPCname, '\0', sizeof(NPCname));
|
||||||
|
|
||||||
|
if (!message || !*message || sscanf(message, "%99[^\n]", NPCname) < 1) {
|
||||||
|
clif_displaymessage(fd, "Please, enter a NPC name (usage: @npcoff <NPC_name>).");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((nd = npc_name2id(NPCname)) != NULL) {
|
||||||
|
npc_unload(nd);
|
||||||
|
clif_displaymessage(fd, msg_table[112]); // Npc Disabled.
|
||||||
|
} else {
|
||||||
|
clif_displaymessage(fd, msg_table[111]); // This NPC doesn't exist.
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/*==========================================
|
/*==========================================
|
||||||
* time in txt for time command (by [Yor])
|
* time in txt for time command (by [Yor])
|
||||||
*------------------------------------------
|
*------------------------------------------
|
||||||
|
@ -145,6 +145,7 @@ enum AtCommandType {
|
|||||||
AtCommand_PartyRecall, // by Yor
|
AtCommand_PartyRecall, // by Yor
|
||||||
AtCommand_Nuke, // [Valaris]
|
AtCommand_Nuke, // [Valaris]
|
||||||
AtCommand_Enablenpc,
|
AtCommand_Enablenpc,
|
||||||
|
AtCommand_Hidenpc,
|
||||||
AtCommand_Disablenpc,
|
AtCommand_Disablenpc,
|
||||||
AtCommand_ServerTime, // by Yor
|
AtCommand_ServerTime, // by Yor
|
||||||
AtCommand_CharDelItem, // by Yor
|
AtCommand_CharDelItem, // by Yor
|
||||||
|
@ -242,11 +242,10 @@ int clif_foreachclient(int (*func)(struct map_session_data*, va_list),...)
|
|||||||
*/
|
*/
|
||||||
int clif_send_sub(struct block_list *bl, va_list ap)
|
int clif_send_sub(struct block_list *bl, va_list ap)
|
||||||
{
|
{
|
||||||
unsigned char *buf;
|
|
||||||
int len;
|
|
||||||
struct block_list *src_bl;
|
struct block_list *src_bl;
|
||||||
int type;
|
|
||||||
struct map_session_data *sd;
|
struct map_session_data *sd;
|
||||||
|
unsigned char *buf;
|
||||||
|
int len, type;
|
||||||
|
|
||||||
nullpo_retr(0, bl);
|
nullpo_retr(0, bl);
|
||||||
nullpo_retr(0, ap);
|
nullpo_retr(0, ap);
|
||||||
@ -259,20 +258,23 @@ int clif_send_sub(struct block_list *bl, va_list ap)
|
|||||||
|
|
||||||
switch(type) {
|
switch(type) {
|
||||||
case AREA_WOS:
|
case AREA_WOS:
|
||||||
if (bl && bl == src_bl)
|
if (bl == src_bl)
|
||||||
return 0;
|
return 0;
|
||||||
break;
|
break;
|
||||||
case AREA_WOC:
|
case AREA_WOC:
|
||||||
if ((sd && sd->chatID) || (bl && bl == src_bl))
|
if (sd->chatID || bl == src_bl)
|
||||||
return 0;
|
return 0;
|
||||||
break;
|
break;
|
||||||
case AREA_WOSC:
|
case AREA_WOSC:
|
||||||
if ((sd) && sd->chatID && sd->chatID == ((struct map_session_data*)src_bl)->chatID)
|
{
|
||||||
|
struct map_session_data *ssd = (struct map_session_data *)src_bl;
|
||||||
|
if (ssd && sd->chatID && sd->chatID == ssd->chatID)
|
||||||
return 0;
|
return 0;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((sd != NULL) && (session[sd->fd] != NULL)) {
|
if (session[sd->fd] != NULL) {
|
||||||
if (WFIFOP(sd->fd,0) == buf) {
|
if (WFIFOP(sd->fd,0) == buf) {
|
||||||
printf("WARNING: Invalid use of clif_send function\n");
|
printf("WARNING: Invalid use of clif_send function\n");
|
||||||
printf(" Packet x%4x use a WFIFO of a player instead of to use a buffer.\n", WBUFW(buf,0));
|
printf(" Packet x%4x use a WFIFO of a player instead of to use a buffer.\n", WBUFW(buf,0));
|
||||||
@ -10686,10 +10688,16 @@ static int clif_parse(int fd) {
|
|||||||
|
|
||||||
// get packet version before to parse
|
// get packet version before to parse
|
||||||
packet_ver = 0;
|
packet_ver = 0;
|
||||||
if (sd)
|
if (sd) {
|
||||||
packet_ver = sd->packet_ver;
|
packet_ver = sd->packet_ver;
|
||||||
|
if (packet_ver < 0 || packet_ver > MAX_PACKET_VER) { // unusual, but just in case
|
||||||
|
close(fd);
|
||||||
|
session[fd]->eof = 1;
|
||||||
|
printf("clif_parse: session #%d, bad packet version -> disconnected.\n", fd);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
// check authentification packet to know packet version
|
// check authentification packet to know packet version
|
||||||
else {
|
} else {
|
||||||
// packet DB
|
// packet DB
|
||||||
if (IS_PACKET_DB_VER (cmd)) {
|
if (IS_PACKET_DB_VER (cmd)) {
|
||||||
if (RFIFOREST(fd) >= packet_db[clif_config.packet_db_ver][cmd].len &&
|
if (RFIFOREST(fd) >= packet_db[clif_config.packet_db_ver][cmd].len &&
|
||||||
|
@ -3131,10 +3131,10 @@ int cleanup_sub(struct block_list *bl, va_list ap) {
|
|||||||
map_quit((struct map_session_data *) bl);
|
map_quit((struct map_session_data *) bl);
|
||||||
break;
|
break;
|
||||||
case BL_NPC:
|
case BL_NPC:
|
||||||
npc_delete((struct npc_data *)bl);
|
npc_unload((struct npc_data *)bl);
|
||||||
break;
|
break;
|
||||||
case BL_MOB:
|
case BL_MOB:
|
||||||
mob_delete((struct mob_data *)bl);
|
mob_unload((struct mob_data *)bl);
|
||||||
break;
|
break;
|
||||||
case BL_PET:
|
case BL_PET:
|
||||||
pet_remove_map((struct map_session_data *)bl);
|
pet_remove_map((struct map_session_data *)bl);
|
||||||
|
@ -914,7 +914,8 @@ int mob_spawn(int id)
|
|||||||
struct mob_data *md;
|
struct mob_data *md;
|
||||||
struct block_list *bl;
|
struct block_list *bl;
|
||||||
|
|
||||||
nullpo_retr(-1, bl=map_id2bl(id));
|
//nullpo_retr(-1, bl=map_id2bl(id));
|
||||||
|
bl=map_id2bl(id);
|
||||||
|
|
||||||
if(!bl || !bl->type || bl->type!=BL_MOB)
|
if(!bl || !bl->type || bl->type!=BL_MOB)
|
||||||
return -1;
|
return -1;
|
||||||
@ -2106,23 +2107,15 @@ static int mob_delay_item_drop2(int tid,unsigned int tick,int id,int data)
|
|||||||
* mob data is erased.
|
* mob data is erased.
|
||||||
*------------------------------------------
|
*------------------------------------------
|
||||||
*/
|
*/
|
||||||
int mob_delete(struct mob_data *md)
|
void mob_unload(struct mob_data *md)
|
||||||
{
|
{
|
||||||
nullpo_retr(1, md);
|
nullpo_retv(md);
|
||||||
|
mob_remove_map(md, 0);
|
||||||
if(md->bl.prev == NULL)
|
map_deliddb(&md->bl);
|
||||||
return 1;
|
aFree(md);
|
||||||
mob_changestate(md,MS_DEAD,0);
|
md = NULL;
|
||||||
clif_clearchar_area(&md->bl,1);
|
|
||||||
map_delblock(&md->bl);
|
|
||||||
if(mob_get_viewclass(md->class_) <= 1000)
|
|
||||||
clif_clearchar_delay(gettick()+3000,&md->bl,0);
|
|
||||||
mob_deleteslave(md);
|
|
||||||
mob_setdelayspawn(md->bl.id);
|
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
int mob_remove_map(struct mob_data *md, int type)
|
||||||
int mob_catch_delete(struct mob_data *md,int type)
|
|
||||||
{
|
{
|
||||||
nullpo_retr(1, md);
|
nullpo_retr(1, md);
|
||||||
|
|
||||||
@ -2131,17 +2124,32 @@ int mob_catch_delete(struct mob_data *md,int type)
|
|||||||
mob_changestate(md,MS_DEAD,0);
|
mob_changestate(md,MS_DEAD,0);
|
||||||
clif_clearchar_area(&md->bl,type);
|
clif_clearchar_area(&md->bl,type);
|
||||||
map_delblock(&md->bl);
|
map_delblock(&md->bl);
|
||||||
|
if (md->lootitem){
|
||||||
|
aFree(md->lootitem);
|
||||||
|
md->lootitem = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
int mob_delete(struct mob_data *md)
|
||||||
|
{
|
||||||
|
nullpo_retr(1, md);
|
||||||
|
|
||||||
|
mob_remove_map(md, 1);
|
||||||
|
if (mob_get_viewclass(md->class_) <= 1000)
|
||||||
|
clif_clearchar_delay(gettick()+3000,&md->bl,0);
|
||||||
|
mob_deleteslave(md);
|
||||||
mob_setdelayspawn(md->bl.id);
|
mob_setdelayspawn(md->bl.id);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int mob_timer_delete(int tid, unsigned int tick, int id, int data)
|
int mob_timer_delete(int tid, unsigned int tick, int id, int data)
|
||||||
{
|
{
|
||||||
struct mob_data *md=(struct mob_data *)map_id2bl(id);
|
struct mob_data *md=(struct mob_data *)map_id2bl(id);
|
||||||
nullpo_retr(0, md);
|
nullpo_retr(0, md);
|
||||||
|
|
||||||
//for Alchemist CANNIBALIZE [Lupus]
|
//for Alchemist CANNIBALIZE [Lupus]
|
||||||
mob_catch_delete(md,3);
|
mob_remove_map(md, 3);
|
||||||
|
mob_setdelayspawn(md->bl.id);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -105,6 +105,7 @@ int mob_target(struct mob_data *md,struct block_list *bl,int dist);
|
|||||||
int mob_stop_walking(struct mob_data *md,int type);
|
int mob_stop_walking(struct mob_data *md,int type);
|
||||||
int mob_stopattack(struct mob_data *);
|
int mob_stopattack(struct mob_data *);
|
||||||
int mob_spawn(int);
|
int mob_spawn(int);
|
||||||
|
int mob_setdelayspawn(int);
|
||||||
int mob_damage(struct block_list *,struct mob_data*,int,int);
|
int mob_damage(struct block_list *,struct mob_data*,int,int);
|
||||||
int mob_changestate(struct mob_data *md,int state,int type);
|
int mob_changestate(struct mob_data *md,int state,int type);
|
||||||
int mob_heal(struct mob_data*,int);
|
int mob_heal(struct mob_data*,int);
|
||||||
@ -123,8 +124,9 @@ short mob_get_clothes_color(int); //player mob dye [Valaris]
|
|||||||
int mob_get_equip(int); // mob equip [Valaris]
|
int mob_get_equip(int); // mob equip [Valaris]
|
||||||
int do_init_mob(void);
|
int do_init_mob(void);
|
||||||
|
|
||||||
|
void mob_unload(struct mob_data *md);
|
||||||
|
int mob_remove_map(struct mob_data *md, int type);
|
||||||
int mob_delete(struct mob_data *md);
|
int mob_delete(struct mob_data *md);
|
||||||
int mob_catch_delete(struct mob_data *md,int type);
|
|
||||||
int mob_timer_delete(int tid, unsigned int tick, int id, int data);
|
int mob_timer_delete(int tid, unsigned int tick, int id, int data);
|
||||||
|
|
||||||
int mob_deleteslave(struct mob_data *md);
|
int mob_deleteslave(struct mob_data *md);
|
||||||
|
463
src/map/npc.c
463
src/map/npc.c
@ -128,6 +128,15 @@ struct npc_data* npc_name2id(const char *name)
|
|||||||
{
|
{
|
||||||
return (struct npc_data *) strdb_search(npcname_db,name);
|
return (struct npc_data *) strdb_search(npcname_db,name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ev_release(struct dbn *db, int which)
|
||||||
|
{
|
||||||
|
if (which & 0x1)
|
||||||
|
aFree(db->key);
|
||||||
|
if (which & 0x2)
|
||||||
|
aFree(db->data);
|
||||||
|
}
|
||||||
|
|
||||||
/*==========================================
|
/*==========================================
|
||||||
* イベントキューのイベント処理
|
* イベントキューのイベント処理
|
||||||
*------------------------------------------
|
*------------------------------------------
|
||||||
@ -164,25 +173,6 @@ int npc_event_dequeue(struct map_session_data *sd)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int npc_delete(struct npc_data *nd)
|
|
||||||
{
|
|
||||||
nullpo_retr(1, nd);
|
|
||||||
|
|
||||||
if(nd->bl.prev == NULL)
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
#ifdef PCRE_SUPPORT
|
|
||||||
npc_chat_finalize(nd);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
clif_clearchar_area(&nd->bl,1);
|
|
||||||
map_delblock(&nd->bl);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*==========================================
|
/*==========================================
|
||||||
* イベントの遅延実行
|
* イベントの遅延実行
|
||||||
*------------------------------------------
|
*------------------------------------------
|
||||||
@ -1366,6 +1356,56 @@ int npc_stop_walking(struct npc_data *nd,int type)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int npc_remove_map (struct npc_data *nd)
|
||||||
|
{
|
||||||
|
nullpo_retr(1, nd);
|
||||||
|
|
||||||
|
if(nd->bl.prev == NULL)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
#ifdef PCRE_SUPPORT
|
||||||
|
npc_chat_finalize(nd);
|
||||||
|
#endif
|
||||||
|
clif_clearchar_area(&nd->bl,2);
|
||||||
|
strdb_erase(npcname_db, nd->name);
|
||||||
|
map_delblock(&nd->bl);
|
||||||
|
map_deliddb(&nd->bl);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int npc_unload(struct npc_data *nd)
|
||||||
|
{
|
||||||
|
nullpo_retr (0, nd);
|
||||||
|
|
||||||
|
if (nd->chat_id) {
|
||||||
|
struct chat_data *cd = (struct chat_data*)map_id2bl(nd->chat_id);
|
||||||
|
if (cd) aFree (cd);
|
||||||
|
cd = NULL;
|
||||||
|
}
|
||||||
|
if (nd->bl.subtype == SCRIPT) {
|
||||||
|
if (nd->u.scr.timerid != -1)
|
||||||
|
delete_timer(nd->u.scr.timerid, npc_timerevent);
|
||||||
|
npc_cleareventtimer (nd);
|
||||||
|
if (nd->u.scr.timer_event)
|
||||||
|
aFree(nd->u.scr.timer_event);
|
||||||
|
if (nd->u.scr.src_id == 0) {
|
||||||
|
if(nd->u.scr.script) {
|
||||||
|
aFree(nd->u.scr.script);
|
||||||
|
nd->u.scr.script = NULL;
|
||||||
|
}
|
||||||
|
if (nd->u.scr.label_list) {
|
||||||
|
aFree(nd->u.scr.label_list);
|
||||||
|
nd->u.scr.label_list = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
npc_remove_map (nd);
|
||||||
|
aFree(nd);
|
||||||
|
nd = NULL;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
// 初期化関係
|
// 初期化関係
|
||||||
@ -1798,6 +1838,11 @@ static int npc_parse_script(char *w1,char *w2,char *w3,char *w4,char *first_line
|
|||||||
nd->n=map_addnpc(m,nd);
|
nd->n=map_addnpc(m,nd);
|
||||||
map_addblock(&nd->bl);
|
map_addblock(&nd->bl);
|
||||||
|
|
||||||
|
// clear event timers upon initialise
|
||||||
|
memset(nd->eventqueue, 0, sizeof(nd->eventqueue));
|
||||||
|
for(i = 0; i < MAX_EVENTTIMER; i++)
|
||||||
|
nd->eventtimer[i] = -1;
|
||||||
|
|
||||||
if (evflag) { // イベント型
|
if (evflag) { // イベント型
|
||||||
struct event_data *ev=(struct event_data *)aCalloc(1,sizeof(struct event_data));
|
struct event_data *ev=(struct event_data *)aCalloc(1,sizeof(struct event_data));
|
||||||
ev->nd=nd;
|
ev->nd=nd;
|
||||||
@ -2240,194 +2285,18 @@ static int npc_parse_mapflag(char *w1,char *w2,char *w3,char *w4)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int npc_read_indoors(void)
|
void npc_parsesrcfile(char *name)
|
||||||
{
|
{
|
||||||
char *buf,*p;
|
int m, lines = 0;
|
||||||
int s, m;
|
|
||||||
|
|
||||||
buf=(char *) grfio_reads("data\\indoorrswtable.txt",&s);
|
|
||||||
|
|
||||||
if(buf==NULL)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
buf[s]=0;
|
|
||||||
for(p=buf;p-buf<s;){
|
|
||||||
char buf2[64];
|
|
||||||
|
|
||||||
if(sscanf(p,"%[^#]#",buf2) == 1){
|
|
||||||
char map_name[64] = "";
|
|
||||||
strncpy(map_name, buf2, strlen(buf2) - 4);
|
|
||||||
strcat(map_name, ".gat");
|
|
||||||
if ((m = map_mapname2mapid(map_name)) >= 0)
|
|
||||||
map[m].flag.indoors=1;
|
|
||||||
}
|
|
||||||
|
|
||||||
p=strchr(p,10);
|
|
||||||
if(!p) break;
|
|
||||||
p++;
|
|
||||||
}
|
|
||||||
aFree(buf);
|
|
||||||
sprintf(tmp_output,"Done reading '"CL_WHITE"%s"CL_RESET"'.\n","data\\indoorrswtable.txt");
|
|
||||||
ShowStatus(tmp_output);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
static int npc_unload(struct npc_data *nd)
|
|
||||||
{
|
|
||||||
struct chat_data *cd;
|
|
||||||
|
|
||||||
nullpo_retr (0, nd);
|
|
||||||
if (nd->chat_id && (cd=(struct chat_data*)map_id2bl(nd->chat_id))){
|
|
||||||
aFree (cd);
|
|
||||||
cd = NULL;
|
|
||||||
}
|
|
||||||
if (nd->bl.subtype == SCRIPT) {
|
|
||||||
if (nd->u.scr.timer_event)
|
|
||||||
aFree(nd->u.scr.timer_event);
|
|
||||||
if (nd->u.scr.src_id==0) {
|
|
||||||
if(nd->u.scr.script) {
|
|
||||||
aFree(nd->u.scr.script);
|
|
||||||
nd->u.scr.script=NULL;
|
|
||||||
}
|
|
||||||
if (nd->u.scr.label_list) {
|
|
||||||
aFree(nd->u.scr.label_list);
|
|
||||||
nd->u.scr.label_list = NULL;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
clif_clearchar_area(&nd->bl, 2);
|
|
||||||
map_delblock(&nd->bl);
|
|
||||||
map_deliddb(&nd->bl);
|
|
||||||
aFree(nd);
|
|
||||||
nd = NULL;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
static int ev_db_final(void *key,void *data,va_list ap)
|
|
||||||
{
|
|
||||||
aFree(data);
|
|
||||||
if(strstr((const char *) key,"::")!=NULL)
|
|
||||||
aFree(key);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
static int npcname_db_final(void *key,void *data,va_list ap)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
/*==========================================
|
|
||||||
*
|
|
||||||
*------------------------------------------
|
|
||||||
*/
|
|
||||||
int npc_reload(void)
|
|
||||||
{
|
|
||||||
struct npc_data *nd;
|
|
||||||
struct block_list *bl;
|
|
||||||
int i;
|
|
||||||
|
|
||||||
if(ev_db)
|
|
||||||
strdb_final(ev_db,ev_db_final);
|
|
||||||
if(npcname_db)
|
|
||||||
strdb_final(npcname_db,npcname_db_final);
|
|
||||||
|
|
||||||
for (i = START_NPC_NUM; i < npc_id; i++) {
|
|
||||||
if((bl = map_id2bl(i)) && bl->type == BL_NPC && (nd = (struct npc_data *)bl))
|
|
||||||
npc_unload(nd);
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
/*==========================================
|
|
||||||
* <EFBFBD>I—¹
|
|
||||||
*------------------------------------------
|
|
||||||
*/
|
|
||||||
int do_final_npc(void)
|
|
||||||
{
|
|
||||||
int i;
|
|
||||||
struct block_list *bl;
|
|
||||||
struct npc_data *nd;
|
|
||||||
struct mob_data *md;
|
|
||||||
struct pet_data *pd;
|
|
||||||
|
|
||||||
if(ev_db)
|
|
||||||
strdb_final(ev_db,ev_db_final);
|
|
||||||
if(npcname_db)
|
|
||||||
strdb_final(npcname_db,npcname_db_final);
|
|
||||||
|
|
||||||
npc_clearsrcfile();
|
|
||||||
|
|
||||||
for (i = START_NPC_NUM; i < npc_id; i++){
|
|
||||||
if((bl = map_id2bl(i))){
|
|
||||||
if(bl->type == BL_NPC && (nd = (struct npc_data *)bl)){
|
|
||||||
npc_unload(nd);
|
|
||||||
}else if (bl->type == BL_MOB && (md = (struct mob_data *)bl)){
|
|
||||||
if (md->lootitem){
|
|
||||||
aFree(md->lootitem);
|
|
||||||
md->lootitem = NULL;
|
|
||||||
}
|
|
||||||
aFree(md);
|
|
||||||
md = NULL;
|
|
||||||
}else if(bl->type == BL_PET && (pd = (struct pet_data *)bl)){
|
|
||||||
aFree(pd);
|
|
||||||
pd = NULL;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void ev_release(struct dbn *db, int which)
|
|
||||||
{
|
|
||||||
if (which & 0x1)
|
|
||||||
aFree(db->key);
|
|
||||||
if (which & 0x2)
|
|
||||||
aFree(db->data);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*==========================================
|
|
||||||
* npc<EFBFBD>‰Šú‰»
|
|
||||||
*------------------------------------------
|
|
||||||
*/
|
|
||||||
int do_init_npc(void)
|
|
||||||
{
|
|
||||||
struct npc_src_list *nsl;
|
|
||||||
FILE *fp;
|
|
||||||
char line[1024];
|
char line[1024];
|
||||||
int m,lines;
|
|
||||||
time_t last_time = time(0);
|
|
||||||
int busy = 0;
|
|
||||||
char c = '-';
|
|
||||||
|
|
||||||
// indoorrswtable.txt and etcinfo.txt [Celest]
|
FILE *fp = fopen (name,"r");
|
||||||
if (battle_config.indoors_override_grffile)
|
|
||||||
npc_read_indoors();
|
|
||||||
//npc_read_weather();
|
|
||||||
|
|
||||||
// comparing only the first 24 chars of labels that are 50 chars long isn't that nice
|
|
||||||
// will cause "duplicated" labels where actually no dup is...
|
|
||||||
//ev_db=strdb_init(24);
|
|
||||||
ev_db = strdb_init(51);
|
|
||||||
npcname_db = strdb_init(24);
|
|
||||||
|
|
||||||
ev_db->release = ev_release;
|
|
||||||
|
|
||||||
memset(&ev_tm_b,-1,sizeof(ev_tm_b));
|
|
||||||
|
|
||||||
for(nsl=npc_src_first;nsl;nsl=nsl->next) {
|
|
||||||
/*if(nsl->prev){ // [Shinomori]
|
|
||||||
aFree(nsl->prev);
|
|
||||||
nsl->prev = NULL;
|
|
||||||
}*/
|
|
||||||
fp=fopen(nsl->name,"r");
|
|
||||||
if (fp == NULL) {
|
if (fp == NULL) {
|
||||||
printf("file not found : %s\n",nsl->name);
|
ShowError ("File not found : %s\n", name);
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
current_file=nsl->name;
|
current_file = name;
|
||||||
lines=0;
|
|
||||||
while (fgets(line, 1020, fp)) {
|
while (fgets(line, 1020, fp)) {
|
||||||
char w1[1024], w2[1024], w3[1024], w4[1024], mapname[1024];
|
char w1[1024], w2[1024], w3[1024], w4[1024], mapname[1024];
|
||||||
int i, j, w4pos, count;
|
int i, j, w4pos, count;
|
||||||
@ -2480,6 +2349,195 @@ int do_init_npc(void)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
fclose(fp);
|
fclose(fp);
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int npc_read_indoors(void)
|
||||||
|
{
|
||||||
|
char *buf,*p;
|
||||||
|
int s, m;
|
||||||
|
|
||||||
|
buf=(char *) grfio_reads("data\\indoorrswtable.txt",&s);
|
||||||
|
|
||||||
|
if(buf==NULL)
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
buf[s]=0;
|
||||||
|
for(p=buf;p-buf<s;){
|
||||||
|
char buf2[64];
|
||||||
|
|
||||||
|
if(sscanf(p,"%[^#]#",buf2) == 1){
|
||||||
|
char map_name[64] = "";
|
||||||
|
strncpy(map_name, buf2, strlen(buf2) - 4);
|
||||||
|
strcat(map_name, ".gat");
|
||||||
|
if ((m = map_mapname2mapid(map_name)) >= 0)
|
||||||
|
map[m].flag.indoors=1;
|
||||||
|
}
|
||||||
|
|
||||||
|
p=strchr(p,10);
|
||||||
|
if(!p) break;
|
||||||
|
p++;
|
||||||
|
}
|
||||||
|
aFree(buf);
|
||||||
|
sprintf(tmp_output,"Done reading '"CL_WHITE"%s"CL_RESET"'.\n","data\\indoorrswtable.txt");
|
||||||
|
ShowStatus(tmp_output);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int ev_db_final(void *key,void *data,va_list ap)
|
||||||
|
{
|
||||||
|
aFree(data);
|
||||||
|
if(strstr((const char *) key,"::")!=NULL)
|
||||||
|
aFree(key);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
static int npcname_db_final(void *key,void *data,va_list ap)
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
/*==========================================
|
||||||
|
*
|
||||||
|
*------------------------------------------
|
||||||
|
*/
|
||||||
|
int npc_cleanup_sub (struct block_list *bl, va_list ap) {
|
||||||
|
nullpo_retr(0, bl);
|
||||||
|
|
||||||
|
switch(bl->type) {
|
||||||
|
case BL_NPC:
|
||||||
|
npc_unload((struct npc_data *)bl);
|
||||||
|
break;
|
||||||
|
case BL_MOB:
|
||||||
|
mob_unload((struct mob_data *)bl);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
int npc_reload(void)
|
||||||
|
{
|
||||||
|
struct npc_src_list *nsl;
|
||||||
|
int m, last_npc_id;
|
||||||
|
time_t last_time = time(0);
|
||||||
|
int busy = 0;
|
||||||
|
char c = '-';
|
||||||
|
|
||||||
|
for (m = 0; m < map_num; m++) {
|
||||||
|
map_foreachinarea(npc_cleanup_sub, m, 0, 0, map[m].xs, map[m].ys, 0);
|
||||||
|
map[m].npc_num = 0;
|
||||||
|
}
|
||||||
|
if(ev_db)
|
||||||
|
strdb_final(ev_db,ev_db_final);
|
||||||
|
if(npcname_db)
|
||||||
|
strdb_final(npcname_db,npcname_db_final);
|
||||||
|
|
||||||
|
// anything else we should cleanup?
|
||||||
|
// Reloading npc's now
|
||||||
|
ev_db = strdb_init(51);
|
||||||
|
npcname_db = strdb_init(24);
|
||||||
|
ev_db->release = ev_release;
|
||||||
|
npc_warp = npc_shop = npc_script = npc_mob = 0;
|
||||||
|
last_npc_id = npc_id;
|
||||||
|
|
||||||
|
for (nsl = npc_src_first; nsl; nsl = nsl->next) {
|
||||||
|
npc_parsesrcfile(nsl->name);
|
||||||
|
printf("\r");
|
||||||
|
ShowStatus("Loading NPCs... Working: ");
|
||||||
|
if (last_time != time(0)) {
|
||||||
|
last_time = time(0);
|
||||||
|
switch(busy) {
|
||||||
|
case 0: c='\\'; busy++; break;
|
||||||
|
case 1: c='|'; busy++; break;
|
||||||
|
case 2: c='/'; busy++; break;
|
||||||
|
case 3: c='-'; busy=0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
printf("[%c]",c);
|
||||||
|
fflush(stdout);
|
||||||
|
}
|
||||||
|
printf("\r");
|
||||||
|
ShowInfo ("Done loading '"CL_WHITE"%d"CL_RESET"' NPCs:%30s\n\t-'"
|
||||||
|
CL_WHITE"%d"CL_RESET"' Warps\n\t-'"
|
||||||
|
CL_WHITE"%d"CL_RESET"' Shops\n\t-'"
|
||||||
|
CL_WHITE"%d"CL_RESET"' Scripts\n\t-'"
|
||||||
|
CL_WHITE"%d"CL_RESET"' Mobs\n",
|
||||||
|
npc_id - last_npc_id, "", npc_warp, npc_shop, npc_script, npc_mob);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
/*==========================================
|
||||||
|
* <EFBFBD>I—¹
|
||||||
|
*------------------------------------------
|
||||||
|
*/
|
||||||
|
int do_final_npc(void)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
struct block_list *bl;
|
||||||
|
struct npc_data *nd;
|
||||||
|
struct mob_data *md;
|
||||||
|
struct pet_data *pd;
|
||||||
|
|
||||||
|
if(ev_db)
|
||||||
|
strdb_final(ev_db,ev_db_final);
|
||||||
|
if(npcname_db)
|
||||||
|
strdb_final(npcname_db,npcname_db_final);
|
||||||
|
|
||||||
|
npc_clearsrcfile();
|
||||||
|
|
||||||
|
for (i = START_NPC_NUM; i < npc_id; i++){
|
||||||
|
if((bl = map_id2bl(i))){
|
||||||
|
if(bl->type == BL_NPC && (nd = (struct npc_data *)bl)){
|
||||||
|
npc_unload(nd);
|
||||||
|
}else if (bl->type == BL_MOB && (md = (struct mob_data *)bl)){
|
||||||
|
if (md->lootitem){
|
||||||
|
aFree(md->lootitem);
|
||||||
|
md->lootitem = NULL;
|
||||||
|
}
|
||||||
|
aFree(md);
|
||||||
|
md = NULL;
|
||||||
|
}else if(bl->type == BL_PET && (pd = (struct pet_data *)bl)){
|
||||||
|
aFree(pd);
|
||||||
|
pd = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*==========================================
|
||||||
|
* npc<EFBFBD>‰Šú‰»
|
||||||
|
*------------------------------------------
|
||||||
|
*/
|
||||||
|
int do_init_npc(void)
|
||||||
|
{
|
||||||
|
struct npc_src_list *nsl;
|
||||||
|
time_t last_time = time(0);
|
||||||
|
int busy = 0;
|
||||||
|
char c = '-';
|
||||||
|
|
||||||
|
// indoorrswtable.txt and etcinfo.txt [Celest]
|
||||||
|
if (battle_config.indoors_override_grffile)
|
||||||
|
npc_read_indoors();
|
||||||
|
//npc_read_weather();
|
||||||
|
|
||||||
|
// comparing only the first 24 chars of labels that are 50 chars long isn't that nice
|
||||||
|
// will cause "duplicated" labels where actually no dup is...
|
||||||
|
//ev_db=strdb_init(24);
|
||||||
|
ev_db = strdb_init(51);
|
||||||
|
npcname_db = strdb_init(24);
|
||||||
|
ev_db->release = ev_release;
|
||||||
|
|
||||||
|
memset(&ev_tm_b, -1, sizeof(ev_tm_b));
|
||||||
|
|
||||||
|
for (nsl = npc_src_first; nsl; nsl = nsl->next) {
|
||||||
|
/*if(nsl->prev){ // [Shinomori]
|
||||||
|
aFree(nsl->prev);
|
||||||
|
nsl->prev = NULL;
|
||||||
|
}*/
|
||||||
|
//
|
||||||
|
npc_parsesrcfile(nsl->name);
|
||||||
current_file = NULL;
|
current_file = NULL;
|
||||||
printf("\r");
|
printf("\r");
|
||||||
ShowStatus("Loading NPCs... Working: ");
|
ShowStatus("Loading NPCs... Working: ");
|
||||||
@ -2498,13 +2556,12 @@ int do_init_npc(void)
|
|||||||
// fflush(stdout);
|
// fflush(stdout);
|
||||||
}
|
}
|
||||||
printf("\r");
|
printf("\r");
|
||||||
sprintf(tmp_output,"Done loading '"CL_WHITE"%d"CL_RESET"' NPCs:%30s\n\t-'"
|
ShowInfo ("Done loading '"CL_WHITE"%d"CL_RESET"' NPCs:%30s\n\t-'"
|
||||||
CL_WHITE"%d"CL_RESET"' Warps\n\t-'"
|
CL_WHITE"%d"CL_RESET"' Warps\n\t-'"
|
||||||
CL_WHITE"%d"CL_RESET"' Shops\n\t-'"
|
CL_WHITE"%d"CL_RESET"' Shops\n\t-'"
|
||||||
CL_WHITE"%d"CL_RESET"' Scripts\n\t-'"
|
CL_WHITE"%d"CL_RESET"' Scripts\n\t-'"
|
||||||
CL_WHITE"%d"CL_RESET"' Mobs\n",
|
CL_WHITE"%d"CL_RESET"' Mobs\n",
|
||||||
npc_id - START_NPC_NUM, "", npc_warp, npc_shop, npc_script, npc_mob);
|
npc_id - START_NPC_NUM, "", npc_warp, npc_shop, npc_script, npc_mob);
|
||||||
ShowInfo(tmp_output);
|
|
||||||
|
|
||||||
add_timer_func_list(npc_walktimer,"npc_walktimer"); // [Valaris]
|
add_timer_func_list(npc_walktimer,"npc_walktimer"); // [Valaris]
|
||||||
add_timer_func_list(npc_event_timer,"npc_event_timer");
|
add_timer_func_list(npc_event_timer,"npc_event_timer");
|
||||||
|
@ -52,7 +52,9 @@ int npc_timerevent_start(struct npc_data *nd, int rid);
|
|||||||
int npc_timerevent_stop(struct npc_data *nd);
|
int npc_timerevent_stop(struct npc_data *nd);
|
||||||
int npc_gettimerevent_tick(struct npc_data *nd);
|
int npc_gettimerevent_tick(struct npc_data *nd);
|
||||||
int npc_settimerevent_tick(struct npc_data *nd,int newtimer);
|
int npc_settimerevent_tick(struct npc_data *nd,int newtimer);
|
||||||
int npc_delete(struct npc_data *nd);
|
int npc_remove_map(struct npc_data *nd);
|
||||||
|
int npc_unload(struct npc_data *nd);
|
||||||
|
int npc_reload(void);
|
||||||
|
|
||||||
extern char *current_file;
|
extern char *current_file;
|
||||||
|
|
||||||
|
@ -889,7 +889,8 @@ int pet_catch_process2(struct map_session_data *sd,int target_id)
|
|||||||
pet_catch_rate = (pet_catch_rate*battle_config.pet_catch_rate)/100;
|
pet_catch_rate = (pet_catch_rate*battle_config.pet_catch_rate)/100;
|
||||||
|
|
||||||
if(rand()%10000 < pet_catch_rate) {
|
if(rand()%10000 < pet_catch_rate) {
|
||||||
mob_catch_delete(md,0);
|
mob_remove_map(md,0);
|
||||||
|
mob_setdelayspawn(md->bl.id);
|
||||||
clif_pet_rulet(sd,1);
|
clif_pet_rulet(sd,1);
|
||||||
// if(battle_config.etc_log)
|
// if(battle_config.etc_log)
|
||||||
// printf("rulet success %d\n",target_id);
|
// printf("rulet success %d\n",target_id);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user