|
@@ -199,7 +199,7 @@ int npc_enable(const char* name, int flag)
|
|
} else
|
|
} else
|
|
clif_changeoption(&nd->bl);
|
|
clif_changeoption(&nd->bl);
|
|
|
|
|
|
- if( flag&3 && (nd->u.scr.xs >= 0 || nd->u.scr.ys >= 0) ) //check if player standing on a OnTouchArea
|
|
|
|
|
|
+ if( flag&3 && (nd->u.scr.xs >= 0 || nd->u.scr.ys >= 0) ) //check if player standing on a OnTouchArea
|
|
map_foreachinarea( npc_enable_sub, nd->bl.m, nd->bl.x-nd->u.scr.xs, nd->bl.y-nd->u.scr.ys, nd->bl.x+nd->u.scr.xs, nd->bl.y+nd->u.scr.ys, BL_PC, nd );
|
|
map_foreachinarea( npc_enable_sub, nd->bl.m, nd->bl.x-nd->u.scr.xs, nd->bl.y-nd->u.scr.ys, nd->bl.x+nd->u.scr.xs, nd->bl.y+nd->u.scr.ys, BL_PC, nd );
|
|
|
|
|
|
return 0;
|
|
return 0;
|
|
@@ -302,7 +302,7 @@ int npc_event_sub(struct map_session_data* sd, struct event_data* ev, const char
|
|
|
|
|
|
/**
|
|
/**
|
|
* Exec name (NPC events) on player or global
|
|
* Exec name (NPC events) on player or global
|
|
- * Do on all NPC when called with foreach
|
|
|
|
|
|
+ * Do on all NPC when called with foreach
|
|
* @see DBApply
|
|
* @see DBApply
|
|
*/
|
|
*/
|
|
int npc_event_doall_sub(DBKey key, DBData *data, va_list ap)
|
|
int npc_event_doall_sub(DBKey key, DBData *data, va_list ap)
|
|
@@ -411,22 +411,22 @@ int npc_event_do_clock(int tid, unsigned int tick, int id, intptr_t data)
|
|
case 6: day = "Sat"; break;
|
|
case 6: day = "Sat"; break;
|
|
default:day = ""; break;
|
|
default:day = ""; break;
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
sprintf(buf,"OnMinute%02d",t->tm_min);
|
|
sprintf(buf,"OnMinute%02d",t->tm_min);
|
|
c += npc_event_doall(buf);
|
|
c += npc_event_doall(buf);
|
|
-
|
|
|
|
|
|
+
|
|
sprintf(buf,"OnClock%02d%02d",t->tm_hour,t->tm_min);
|
|
sprintf(buf,"OnClock%02d%02d",t->tm_hour,t->tm_min);
|
|
c += npc_event_doall(buf);
|
|
c += npc_event_doall(buf);
|
|
-
|
|
|
|
|
|
+
|
|
sprintf(buf,"On%s%02d%02d",day,t->tm_hour,t->tm_min);
|
|
sprintf(buf,"On%s%02d%02d",day,t->tm_hour,t->tm_min);
|
|
c += npc_event_doall(buf);
|
|
c += npc_event_doall(buf);
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
if (t->tm_hour != ev_tm_b.tm_hour) {
|
|
if (t->tm_hour != ev_tm_b.tm_hour) {
|
|
sprintf(buf,"OnHour%02d",t->tm_hour);
|
|
sprintf(buf,"OnHour%02d",t->tm_hour);
|
|
c += npc_event_doall(buf);
|
|
c += npc_event_doall(buf);
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
if (t->tm_mday != ev_tm_b.tm_mday) {
|
|
if (t->tm_mday != ev_tm_b.tm_mday) {
|
|
sprintf(buf,"OnDay%02d%02d",t->tm_mon+1,t->tm_mday);
|
|
sprintf(buf,"OnDay%02d%02d",t->tm_mon+1,t->tm_mday);
|
|
c += npc_event_doall(buf);
|
|
c += npc_event_doall(buf);
|
|
@@ -539,13 +539,13 @@ int npc_timerevent(int tid, unsigned int tick, int id, intptr_t data)
|
|
sd->npc_timer_id = INVALID_TIMER;
|
|
sd->npc_timer_id = INVALID_TIMER;
|
|
else
|
|
else
|
|
nd->u.scr.timerid = INVALID_TIMER;
|
|
nd->u.scr.timerid = INVALID_TIMER;
|
|
-
|
|
|
|
|
|
+
|
|
ers_free(timer_event_ers, ted);
|
|
ers_free(timer_event_ers, ted);
|
|
}
|
|
}
|
|
|
|
|
|
// Run the script
|
|
// Run the script
|
|
run_script(nd->u.scr.script,te->pos,nd->u.scr.rid,nd->bl.id);
|
|
run_script(nd->u.scr.script,te->pos,nd->u.scr.rid,nd->bl.id);
|
|
-
|
|
|
|
|
|
+
|
|
nd->u.scr.rid = old_rid; // Attached-rid should be restored anyway.
|
|
nd->u.scr.rid = old_rid; // Attached-rid should be restored anyway.
|
|
if( sd )
|
|
if( sd )
|
|
{ // Restore previous data, only if this timer is a player-attached one.
|
|
{ // Restore previous data, only if this timer is a player-attached one.
|
|
@@ -564,7 +564,7 @@ int npc_timerevent_start(struct npc_data* nd, int rid)
|
|
unsigned int tick = gettick();
|
|
unsigned int tick = gettick();
|
|
struct map_session_data *sd = NULL; //Player to whom script is attached.
|
|
struct map_session_data *sd = NULL; //Player to whom script is attached.
|
|
struct timer_event_data *ted;
|
|
struct timer_event_data *ted;
|
|
-
|
|
|
|
|
|
+
|
|
nullpo_ret(nd);
|
|
nullpo_ret(nd);
|
|
|
|
|
|
// Check if there is an OnTimer Event
|
|
// Check if there is an OnTimer Event
|
|
@@ -584,7 +584,7 @@ int npc_timerevent_start(struct npc_data* nd, int rid)
|
|
}
|
|
}
|
|
else if( nd->u.scr.timerid != INVALID_TIMER || nd->u.scr.timertick )
|
|
else if( nd->u.scr.timerid != INVALID_TIMER || nd->u.scr.timertick )
|
|
return 0;
|
|
return 0;
|
|
-
|
|
|
|
|
|
+
|
|
if (j < nd->u.scr.timeramount)
|
|
if (j < nd->u.scr.timeramount)
|
|
{
|
|
{
|
|
// Arrange for the next event
|
|
// Arrange for the next event
|
|
@@ -606,7 +606,7 @@ int npc_timerevent_start(struct npc_data* nd, int rid)
|
|
}
|
|
}
|
|
else if (!sd)
|
|
else if (!sd)
|
|
{
|
|
{
|
|
- nd->u.scr.timertick = tick;
|
|
|
|
|
|
+ nd->u.scr.timertick = tick;
|
|
}
|
|
}
|
|
|
|
|
|
return 0;
|
|
return 0;
|
|
@@ -627,7 +627,7 @@ int npc_timerevent_stop(struct npc_data* nd)
|
|
ShowError("npc_timerevent_stop: Attached player not found!\n");
|
|
ShowError("npc_timerevent_stop: Attached player not found!\n");
|
|
return 1;
|
|
return 1;
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
tid = sd?&sd->npc_timer_id:&nd->u.scr.timerid;
|
|
tid = sd?&sd->npc_timer_id:&nd->u.scr.timerid;
|
|
if( *tid == INVALID_TIMER && (sd || !nd->u.scr.timertick) ) // Nothing to stop
|
|
if( *tid == INVALID_TIMER && (sd || !nd->u.scr.timertick) ) // Nothing to stop
|
|
return 0;
|
|
return 0;
|
|
@@ -700,7 +700,7 @@ void npc_timerevent_quit(struct map_session_data* sd)
|
|
nd->u.scr.rid = sd->bl.id;
|
|
nd->u.scr.rid = sd->bl.id;
|
|
nd->u.scr.timertick = gettick();
|
|
nd->u.scr.timertick = gettick();
|
|
nd->u.scr.timer = ted->time;
|
|
nd->u.scr.timer = ted->time;
|
|
-
|
|
|
|
|
|
+
|
|
//Execute label
|
|
//Execute label
|
|
run_script(nd->u.scr.script,ev->pos,sd->bl.id,nd->bl.id);
|
|
run_script(nd->u.scr.script,ev->pos,sd->bl.id,nd->bl.id);
|
|
|
|
|
|
@@ -855,7 +855,7 @@ int npc_touchnext_areanpc(struct map_session_data* sd, bool leavemap)
|
|
xs = nd->u.scr.xs;
|
|
xs = nd->u.scr.xs;
|
|
ys = nd->u.scr.ys;
|
|
ys = nd->u.scr.ys;
|
|
|
|
|
|
- if( sd->bl.m != nd->bl.m ||
|
|
|
|
|
|
+ if( sd->bl.m != nd->bl.m ||
|
|
sd->bl.x < nd->bl.x - xs || sd->bl.x > nd->bl.x + xs ||
|
|
sd->bl.x < nd->bl.x - xs || sd->bl.x > nd->bl.x + xs ||
|
|
sd->bl.y < nd->bl.y - ys || sd->bl.y > nd->bl.y + ys ||
|
|
sd->bl.y < nd->bl.y - ys || sd->bl.y > nd->bl.y + ys ||
|
|
pc_ishiding(sd) || leavemap )
|
|
pc_ishiding(sd) || leavemap )
|
|
@@ -1012,7 +1012,7 @@ int npc_check_areanpc(int flag, int m, int x, int y, int range)
|
|
y0 = max(y-range, 0);
|
|
y0 = max(y-range, 0);
|
|
x1 = min(x+range, map[m].xs-1);
|
|
x1 = min(x+range, map[m].xs-1);
|
|
y1 = min(y+range, map[m].ys-1);
|
|
y1 = min(y+range, map[m].ys-1);
|
|
-
|
|
|
|
|
|
+
|
|
//First check for npc_cells on the range given
|
|
//First check for npc_cells on the range given
|
|
i = 0;
|
|
i = 0;
|
|
for (ys = y0; ys <= y1 && !i; ys++) {
|
|
for (ys = y0; ys <= y1 && !i; ys++) {
|
|
@@ -1106,7 +1106,7 @@ void run_tomb(struct map_session_data* sd, struct npc_data* nd)
|
|
{
|
|
{
|
|
char buffer[200];
|
|
char buffer[200];
|
|
char time[10];
|
|
char time[10];
|
|
-
|
|
|
|
|
|
+
|
|
strftime(time, sizeof(time), "%H:%M", localtime(&nd->u.tomb.kill_time));
|
|
strftime(time, sizeof(time), "%H:%M", localtime(&nd->u.tomb.kill_time));
|
|
|
|
|
|
// TODO: Find exact color?
|
|
// TODO: Find exact color?
|
|
@@ -1117,7 +1117,7 @@ void run_tomb(struct map_session_data* sd, struct npc_data* nd)
|
|
|
|
|
|
snprintf(buffer, sizeof(buffer), msg_txt(659), time);
|
|
snprintf(buffer, sizeof(buffer), msg_txt(659), time);
|
|
clif_scriptmes(sd, nd->bl.id, buffer);
|
|
clif_scriptmes(sd, nd->bl.id, buffer);
|
|
-
|
|
|
|
|
|
+
|
|
clif_scriptmes(sd, nd->bl.id, msg_txt(660));
|
|
clif_scriptmes(sd, nd->bl.id, msg_txt(660));
|
|
|
|
|
|
snprintf(buffer, sizeof(buffer), msg_txt(661), nd->u.tomb.killer_name[0] ? nd->u.tomb.killer_name : "Unknown");
|
|
snprintf(buffer, sizeof(buffer), msg_txt(661), nd->u.tomb.killer_name[0] ? nd->u.tomb.killer_name : "Unknown");
|
|
@@ -1128,7 +1128,7 @@ void run_tomb(struct map_session_data* sd, struct npc_data* nd)
|
|
|
|
|
|
/*==========================================
|
|
/*==========================================
|
|
* NPC 1st call when clicking on npc
|
|
* NPC 1st call when clicking on npc
|
|
- * Do specific action for NPC type (openshop, run scripts...)
|
|
|
|
|
|
+ * Do specific action for NPC type (openshop, run scripts...)
|
|
*------------------------------------------*/
|
|
*------------------------------------------*/
|
|
int npc_click(struct map_session_data* sd, struct npc_data* nd)
|
|
int npc_click(struct map_session_data* sd, struct npc_data* nd)
|
|
{
|
|
{
|
|
@@ -1179,7 +1179,7 @@ int npc_scriptcont(struct map_session_data* sd, int id)
|
|
nd?(char*)nd->name:"'Unknown NPC'", (int)id);
|
|
nd?(char*)nd->name:"'Unknown NPC'", (int)id);
|
|
return 1;
|
|
return 1;
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
if(id != fake_nd->bl.id) { // Not item script
|
|
if(id != fake_nd->bl.id) { // Not item script
|
|
if ((npc_checknear(sd,map_id2bl(id))) == NULL){
|
|
if ((npc_checknear(sd,map_id2bl(id))) == NULL){
|
|
ShowWarning("npc_scriptcont: failed npc_checknear test.\n");
|
|
ShowWarning("npc_scriptcont: failed npc_checknear test.\n");
|
|
@@ -1218,7 +1218,7 @@ int npc_buysellsel(struct map_session_data* sd, int id, int type)
|
|
|
|
|
|
if ((nd = npc_checknear(sd,map_id2bl(id))) == NULL)
|
|
if ((nd = npc_checknear(sd,map_id2bl(id))) == NULL)
|
|
return 1;
|
|
return 1;
|
|
-
|
|
|
|
|
|
+
|
|
if (nd->subtype!=SHOP) {
|
|
if (nd->subtype!=SHOP) {
|
|
ShowError("no such shop npc : %d\n",id);
|
|
ShowError("no such shop npc : %d\n",id);
|
|
if (sd->npc_id == id)
|
|
if (sd->npc_id == id)
|
|
@@ -1459,7 +1459,7 @@ int npc_buylist(struct map_session_data* sd, int n, unsigned short* item_list)
|
|
int nameid, amount, value;
|
|
int nameid, amount, value;
|
|
|
|
|
|
// find this entry in the shop's sell list
|
|
// find this entry in the shop's sell list
|
|
- ARR_FIND( 0, nd->u.shop.count, j,
|
|
|
|
|
|
+ ARR_FIND( 0, nd->u.shop.count, j,
|
|
item_list[i*2+1] == nd->u.shop.shop_item[j].nameid || //Normal items
|
|
item_list[i*2+1] == nd->u.shop.shop_item[j].nameid || //Normal items
|
|
item_list[i*2+1] == itemdb_viewid(nd->u.shop.shop_item[j].nameid) //item_avail replacement
|
|
item_list[i*2+1] == itemdb_viewid(nd->u.shop.shop_item[j].nameid) //item_avail replacement
|
|
);
|
|
);
|
|
@@ -1515,11 +1515,7 @@ int npc_buylist(struct map_session_data* sd, int n, unsigned short* item_list)
|
|
if( pc_inventoryblank(sd) < new_ )
|
|
if( pc_inventoryblank(sd) < new_ )
|
|
return 3; // Not enough space to store items
|
|
return 3; // Not enough space to store items
|
|
|
|
|
|
- //Logs (S)hopping Zeny [Lupus]
|
|
|
|
- log_zeny(sd, LOG_TYPE_NPC, sd, -(int)z);
|
|
|
|
- //Logs
|
|
|
|
-
|
|
|
|
- pc_payzeny(sd,(int)z);
|
|
|
|
|
|
+ pc_payzeny(sd,(int)z,LOG_TYPE_NPC, NULL);
|
|
|
|
|
|
for( i = 0; i < n; ++i )
|
|
for( i = 0; i < n; ++i )
|
|
{
|
|
{
|
|
@@ -1584,7 +1580,7 @@ static int npc_selllist_sub(struct map_session_data* sd, int n, unsigned short*
|
|
snprintf(card_slot, sizeof(card_slot), "@sold_card%d", j + 1);
|
|
snprintf(card_slot, sizeof(card_slot), "@sold_card%d", j + 1);
|
|
script_cleararray_pc(sd, card_slot, (void*)0);
|
|
script_cleararray_pc(sd, card_slot, (void*)0);
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
// save list of to be sold items
|
|
// save list of to be sold items
|
|
for( i = 0; i < n; i++ )
|
|
for( i = 0; i < n; i++ )
|
|
{
|
|
{
|
|
@@ -1598,7 +1594,7 @@ static int npc_selllist_sub(struct map_session_data* sd, int n, unsigned short*
|
|
script_setarray_pc(sd, "@sold_refine", i, (void*)(intptr_t)sd->status.inventory[idx].refine, &key_refine);
|
|
script_setarray_pc(sd, "@sold_refine", i, (void*)(intptr_t)sd->status.inventory[idx].refine, &key_refine);
|
|
script_setarray_pc(sd, "@sold_attribute", i, (void*)(intptr_t)sd->status.inventory[idx].attribute, &key_attribute);
|
|
script_setarray_pc(sd, "@sold_attribute", i, (void*)(intptr_t)sd->status.inventory[idx].attribute, &key_attribute);
|
|
script_setarray_pc(sd, "@sold_identify", i, (void*)(intptr_t)sd->status.inventory[idx].identify, &key_identify);
|
|
script_setarray_pc(sd, "@sold_identify", i, (void*)(intptr_t)sd->status.inventory[idx].identify, &key_identify);
|
|
-
|
|
|
|
|
|
+
|
|
for( j = 0; j < MAX_SLOTS; j++ )
|
|
for( j = 0; j < MAX_SLOTS; j++ )
|
|
{// store each of the cards from the equipment in the array
|
|
{// store each of the cards from the equipment in the array
|
|
snprintf(card_slot, sizeof(card_slot), "@sold_card%d", j + 1);
|
|
snprintf(card_slot, sizeof(card_slot), "@sold_card%d", j + 1);
|
|
@@ -1691,11 +1687,7 @@ int npc_selllist(struct map_session_data* sd, int n, unsigned short* item_list)
|
|
if( z > MAX_ZENY )
|
|
if( z > MAX_ZENY )
|
|
z = MAX_ZENY;
|
|
z = MAX_ZENY;
|
|
|
|
|
|
- //Logs (S)hopping Zeny [Lupus]
|
|
|
|
- log_zeny(sd, LOG_TYPE_NPC, sd, (int)z);
|
|
|
|
- //Logs
|
|
|
|
-
|
|
|
|
- pc_getzeny(sd, (int)z);
|
|
|
|
|
|
+ pc_getzeny(sd, (int)z, LOG_TYPE_NPC, NULL);
|
|
|
|
|
|
// custom merchant shop exp bonus
|
|
// custom merchant shop exp bonus
|
|
if( battle_config.shop_exp > 0 && z > 0 && ( skill = pc_checkskill(sd,MC_OVERCHARGE) ) > 0)
|
|
if( battle_config.shop_exp > 0 && z > 0 && ( skill = pc_checkskill(sd,MC_OVERCHARGE) ) > 0)
|
|
@@ -1793,13 +1785,13 @@ int npc_unload(struct npc_data* nd, bool single) {
|
|
if( nd->path && nd->path != npc_last_ref ) {
|
|
if( nd->path && nd->path != npc_last_ref ) {
|
|
npd = strdb_get(npc_path_db, nd->path);
|
|
npd = strdb_get(npc_path_db, nd->path);
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
if( npd && --npd->references == 0 ) {
|
|
if( npd && --npd->references == 0 ) {
|
|
strdb_remove(npc_path_db, nd->path);/* remove from db */
|
|
strdb_remove(npc_path_db, nd->path);/* remove from db */
|
|
aFree(nd->path);/* remove now that no other instances exist */
|
|
aFree(nd->path);/* remove now that no other instances exist */
|
|
}
|
|
}
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
if( (nd->subtype == SHOP || nd->subtype == CASHSHOP) && nd->src_id == 0) //src check for duplicate shops [Orcao]
|
|
if( (nd->subtype == SHOP || nd->subtype == CASHSHOP) && nd->src_id == 0) //src check for duplicate shops [Orcao]
|
|
aFree(nd->u.shop.shop_item);
|
|
aFree(nd->u.shop.shop_item);
|
|
else if( nd->subtype == SCRIPT ) {
|
|
else if( nd->subtype == SCRIPT ) {
|
|
@@ -1809,7 +1801,7 @@ int npc_unload(struct npc_data* nd, bool single) {
|
|
if( single )
|
|
if( single )
|
|
ev_db->foreach(ev_db,npc_unload_ev,nd->exname); //Clean up all events related
|
|
ev_db->foreach(ev_db,npc_unload_ev,nd->exname); //Clean up all events related
|
|
|
|
|
|
- iter = mapit_geteachpc();
|
|
|
|
|
|
+ iter = mapit_geteachpc();
|
|
for( bl = (struct block_list*)mapit_first(iter); mapit_exists(iter); bl = (struct block_list*)mapit_next(iter) ) {
|
|
for( bl = (struct block_list*)mapit_first(iter); mapit_exists(iter); bl = (struct block_list*)mapit_next(iter) ) {
|
|
struct map_session_data *sd = ((TBL_PC*)bl);
|
|
struct map_session_data *sd = ((TBL_PC*)bl);
|
|
if( sd && sd->npc_timer_id != INVALID_TIMER ) {
|
|
if( sd && sd->npc_timer_id != INVALID_TIMER ) {
|
|
@@ -1823,13 +1815,13 @@ int npc_unload(struct npc_data* nd, bool single) {
|
|
delete_timer(sd->npc_timer_id, npc_timerevent);
|
|
delete_timer(sd->npc_timer_id, npc_timerevent);
|
|
sd->npc_timer_id = INVALID_TIMER;
|
|
sd->npc_timer_id = INVALID_TIMER;
|
|
}
|
|
}
|
|
- }
|
|
|
|
|
|
+ }
|
|
mapit_free(iter);
|
|
mapit_free(iter);
|
|
|
|
|
|
if (nd->u.scr.timerid != INVALID_TIMER) {
|
|
if (nd->u.scr.timerid != INVALID_TIMER) {
|
|
const struct TimerData *td = NULL;
|
|
const struct TimerData *td = NULL;
|
|
td = get_timer(nd->u.scr.timerid);
|
|
td = get_timer(nd->u.scr.timerid);
|
|
- if (td && td->data)
|
|
|
|
|
|
+ if (td && td->data)
|
|
ers_free(timer_event_ers, (void*)td->data);
|
|
ers_free(timer_event_ers, (void*)td->data);
|
|
delete_timer(nd->u.scr.timerid, npc_timerevent);
|
|
delete_timer(nd->u.scr.timerid, npc_timerevent);
|
|
}
|
|
}
|
|
@@ -1988,20 +1980,20 @@ static void npc_parsename(struct npc_data* nd, const char* name, const char* sta
|
|
ShowDebug("other npc in '%s' :\n display name '%s'\n unique name '%s'\n map=%s, x=%d, y=%d\n",dnd->path, dnd->name, dnd->exname, other_mapname, dnd->bl.x, dnd->bl.y);
|
|
ShowDebug("other npc in '%s' :\n display name '%s'\n unique name '%s'\n map=%s, x=%d, y=%d\n",dnd->path, dnd->name, dnd->exname, other_mapname, dnd->bl.x, dnd->bl.y);
|
|
safestrncpy(nd->exname, newname, sizeof(nd->exname));
|
|
safestrncpy(nd->exname, newname, sizeof(nd->exname));
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
if( npc_last_path != filepath ) {
|
|
if( npc_last_path != filepath ) {
|
|
struct npc_path_data * npd = NULL;
|
|
struct npc_path_data * npd = NULL;
|
|
-
|
|
|
|
|
|
+
|
|
if( !(npd = strdb_get(npc_path_db,filepath) ) ) {
|
|
if( !(npd = strdb_get(npc_path_db,filepath) ) ) {
|
|
CREATE(npd, struct npc_path_data, 1);
|
|
CREATE(npd, struct npc_path_data, 1);
|
|
strdb_put(npc_path_db, filepath, npd);
|
|
strdb_put(npc_path_db, filepath, npd);
|
|
-
|
|
|
|
|
|
+
|
|
CREATE(npd->path, char, strlen(filepath)+1);
|
|
CREATE(npd->path, char, strlen(filepath)+1);
|
|
safestrncpy(npd->path, filepath, strlen(filepath)+1);
|
|
safestrncpy(npd->path, filepath, strlen(filepath)+1);
|
|
-
|
|
|
|
|
|
+
|
|
npd->references = 0;
|
|
npd->references = 0;
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
nd->path = npd->path;
|
|
nd->path = npd->path;
|
|
npd->references++;
|
|
npd->references++;
|
|
|
|
|
|
@@ -2122,7 +2114,7 @@ static const char* npc_parse_warp(char* w1, char* w2, char* w3, char* w4, const
|
|
/// Parses a shop/cashshop npc.
|
|
/// Parses a shop/cashshop npc.
|
|
static const char* npc_parse_shop(char* w1, char* w2, char* w3, char* w4, const char* start, const char* buffer, const char* filepath)
|
|
static const char* npc_parse_shop(char* w1, char* w2, char* w3, char* w4, const char* start, const char* buffer, const char* filepath)
|
|
{
|
|
{
|
|
- //TODO: could be rewritten to NOT need this temp array [ultramage]
|
|
|
|
|
|
+ //TODO: could be rewritten to NOT need this temp array [ultramage]
|
|
#define MAX_SHOPITEM 100
|
|
#define MAX_SHOPITEM 100
|
|
struct npc_item_list items[MAX_SHOPITEM];
|
|
struct npc_item_list items[MAX_SHOPITEM];
|
|
char *p;
|
|
char *p;
|
|
@@ -2144,7 +2136,7 @@ static const char* npc_parse_shop(char* w1, char* w2, char* w3, char* w4, const
|
|
ShowError("npc_parse_shop: Invalid shop definition in file '%s', line '%d'.\n * w1=%s\n * w2=%s\n * w3=%s\n * w4=%s\n", filepath, strline(buffer,start-buffer), w1, w2, w3, w4);
|
|
ShowError("npc_parse_shop: Invalid shop definition in file '%s', line '%d'.\n * w1=%s\n * w2=%s\n * w3=%s\n * w4=%s\n", filepath, strline(buffer,start-buffer), w1, w2, w3, w4);
|
|
return strchr(start,'\n');// skip and continue
|
|
return strchr(start,'\n');// skip and continue
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
m = map_mapname2mapid(mapname);
|
|
m = map_mapname2mapid(mapname);
|
|
}
|
|
}
|
|
|
|
|
|
@@ -2464,17 +2456,17 @@ static const char* npc_parse_script(char* w1, char* w2, char* w3, char* w4, cons
|
|
if( runOnInit ) {
|
|
if( runOnInit ) {
|
|
char evname[EVENT_NAME_LENGTH];
|
|
char evname[EVENT_NAME_LENGTH];
|
|
struct event_data *ev;
|
|
struct event_data *ev;
|
|
-
|
|
|
|
|
|
+
|
|
snprintf(evname, ARRAYLENGTH(evname), "%s::OnInit", nd->exname);
|
|
snprintf(evname, ARRAYLENGTH(evname), "%s::OnInit", nd->exname);
|
|
-
|
|
|
|
|
|
+
|
|
if( ( ev = (struct event_data*)strdb_get(ev_db, evname) ) ) {
|
|
if( ( ev = (struct event_data*)strdb_get(ev_db, evname) ) ) {
|
|
-
|
|
|
|
|
|
+
|
|
//Execute OnInit
|
|
//Execute OnInit
|
|
run_script(nd->u.scr.script,ev->pos,0,nd->bl.id);
|
|
run_script(nd->u.scr.script,ev->pos,0,nd->bl.id);
|
|
-
|
|
|
|
|
|
+
|
|
}
|
|
}
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
return end;
|
|
return end;
|
|
}
|
|
}
|
|
|
|
|
|
@@ -2630,7 +2622,7 @@ const char* npc_parse_duplicate(char* w1, char* w2, char* w3, char* w4, const ch
|
|
|
|
|
|
int npc_duplicate4instance(struct npc_data *snd, int m) {
|
|
int npc_duplicate4instance(struct npc_data *snd, int m) {
|
|
char newname[NAME_LENGTH];
|
|
char newname[NAME_LENGTH];
|
|
-
|
|
|
|
|
|
+
|
|
if( map[m].instance_id == 0 )
|
|
if( map[m].instance_id == 0 )
|
|
return 1;
|
|
return 1;
|
|
|
|
|
|
@@ -2858,9 +2850,9 @@ int npc_do_atcmd_event(struct map_session_data* sd, const char* command, const c
|
|
// split atcmd parameters based on spaces
|
|
// split atcmd parameters based on spaces
|
|
i = 0;
|
|
i = 0;
|
|
j = 0;
|
|
j = 0;
|
|
-
|
|
|
|
|
|
+
|
|
temp = (char*)aMalloc(strlen(message) + 1);
|
|
temp = (char*)aMalloc(strlen(message) + 1);
|
|
-
|
|
|
|
|
|
+
|
|
while( message[i] != '\0' ) {
|
|
while( message[i] != '\0' ) {
|
|
if( message[i] == ' ' && k < 127 ) {
|
|
if( message[i] == ' ' && k < 127 ) {
|
|
temp[j] = '\0';
|
|
temp[j] = '\0';
|
|
@@ -3108,7 +3100,7 @@ static const char* npc_parse_mapflag(char* w1, char* w2, char* w3, char* w4, con
|
|
|
|
|
|
if (w4 && !strcmpi(w4, "off"))
|
|
if (w4 && !strcmpi(w4, "off"))
|
|
state = 0; //Disable mapflag rather than enable it. [Skotlex]
|
|
state = 0; //Disable mapflag rather than enable it. [Skotlex]
|
|
-
|
|
|
|
|
|
+
|
|
if (!strcmpi(w3, "nosave")) {
|
|
if (!strcmpi(w3, "nosave")) {
|
|
char savemap[32];
|
|
char savemap[32];
|
|
int savex, savey;
|
|
int savex, savey;
|
|
@@ -3556,7 +3548,7 @@ void npc_read_event_script(void)
|
|
ShowWarning("npc_read_event_script: too many occurences of event '%s'!\n", config[i].event_name);
|
|
ShowWarning("npc_read_event_script: too many occurences of event '%s'!\n", config[i].event_name);
|
|
break;
|
|
break;
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
if( (p=strchr(p,':')) && p && strcmpi(name,p)==0 )
|
|
if( (p=strchr(p,':')) && p && strcmpi(name,p)==0 )
|
|
{
|
|
{
|
|
script_event[i].event[count] = ed;
|
|
script_event[i].event[count] = ed;
|
|
@@ -3576,14 +3568,14 @@ void npc_read_event_script(void)
|
|
|
|
|
|
void npc_clear_pathlist(void) {
|
|
void npc_clear_pathlist(void) {
|
|
struct npc_path_data *npd = NULL;
|
|
struct npc_path_data *npd = NULL;
|
|
- DBIterator *path_list = db_iterator(npc_path_db);
|
|
|
|
-
|
|
|
|
|
|
+ DBIterator *path_list = db_iterator(npc_path_db);
|
|
|
|
+
|
|
/* free all npc_path_data filepaths */
|
|
/* free all npc_path_data filepaths */
|
|
for( npd = dbi_first(path_list); dbi_exists(path_list); npd = dbi_next(path_list) ) {
|
|
for( npd = dbi_first(path_list); dbi_exists(path_list); npd = dbi_next(path_list) ) {
|
|
if( npd->path )
|
|
if( npd->path )
|
|
aFree(npd->path);
|
|
aFree(npd->path);
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
dbi_destroy(path_list);
|
|
dbi_destroy(path_list);
|
|
}
|
|
}
|
|
|
|
|
|
@@ -3596,12 +3588,12 @@ int npc_reload(void) {
|
|
struct block_list* bl;
|
|
struct block_list* bl;
|
|
|
|
|
|
npc_clear_pathlist();
|
|
npc_clear_pathlist();
|
|
-
|
|
|
|
|
|
+
|
|
db_clear(npc_path_db);
|
|
db_clear(npc_path_db);
|
|
|
|
|
|
db_clear(npcname_db);
|
|
db_clear(npcname_db);
|
|
db_clear(ev_db);
|
|
db_clear(ev_db);
|
|
-
|
|
|
|
|
|
+
|
|
//Remove all npcs/mobs. [Skotlex]
|
|
//Remove all npcs/mobs. [Skotlex]
|
|
|
|
|
|
iter = mapit_geteachiddb();
|
|
iter = mapit_geteachiddb();
|
|
@@ -3662,20 +3654,20 @@ int npc_reload(void) {
|
|
npc_id - npc_new_min, npc_warp, npc_shop, npc_script, npc_mob, npc_cache_mob, npc_delay_mob);
|
|
npc_id - npc_new_min, npc_warp, npc_shop, npc_script, npc_mob, npc_cache_mob, npc_delay_mob);
|
|
|
|
|
|
do_final_instance();
|
|
do_final_instance();
|
|
-
|
|
|
|
|
|
+
|
|
for( i = 0; i < ARRAYLENGTH(instance); ++i )
|
|
for( i = 0; i < ARRAYLENGTH(instance); ++i )
|
|
instance_init(instance[i].instance_id);
|
|
instance_init(instance[i].instance_id);
|
|
|
|
|
|
//Re-read the NPC Script Events cache.
|
|
//Re-read the NPC Script Events cache.
|
|
npc_read_event_script();
|
|
npc_read_event_script();
|
|
-
|
|
|
|
|
|
+
|
|
/* refresh guild castle flags on both woe setups */
|
|
/* refresh guild castle flags on both woe setups */
|
|
npc_event_doall("OnAgitInit");
|
|
npc_event_doall("OnAgitInit");
|
|
npc_event_doall("OnAgitInit2");
|
|
npc_event_doall("OnAgitInit2");
|
|
-
|
|
|
|
|
|
+
|
|
//Execute the OnInit event for freshly loaded npcs. [Skotlex]
|
|
//Execute the OnInit event for freshly loaded npcs. [Skotlex]
|
|
ShowStatus("Event '"CL_WHITE"OnInit"CL_RESET"' executed with '"CL_WHITE"%d"CL_RESET"' NPCs.\n",npc_event_doall("OnInit"));
|
|
ShowStatus("Event '"CL_WHITE"OnInit"CL_RESET"' executed with '"CL_WHITE"%d"CL_RESET"' NPCs.\n",npc_event_doall("OnInit"));
|
|
-
|
|
|
|
|
|
+
|
|
// Execute rest of the startup events if connected to char-server. [Lance]
|
|
// Execute rest of the startup events if connected to char-server. [Lance]
|
|
if(!CheckForCharServer()){
|
|
if(!CheckForCharServer()){
|
|
ShowStatus("Event '"CL_WHITE"OnInterIfInit"CL_RESET"' executed with '"CL_WHITE"%d"CL_RESET"' NPCs.\n", npc_event_doall("OnInterIfInit"));
|
|
ShowStatus("Event '"CL_WHITE"OnInterIfInit"CL_RESET"' executed with '"CL_WHITE"%d"CL_RESET"' NPCs.\n", npc_event_doall("OnInterIfInit"));
|
|
@@ -3689,7 +3681,7 @@ bool npc_unloadfile( const char* path ) {
|
|
DBIterator * iter = db_iterator(npcname_db);
|
|
DBIterator * iter = db_iterator(npcname_db);
|
|
struct npc_data* nd = NULL;
|
|
struct npc_data* nd = NULL;
|
|
bool found = false;
|
|
bool found = false;
|
|
-
|
|
|
|
|
|
+
|
|
for( nd = dbi_first(iter); dbi_exists(iter); nd = dbi_next(iter) ) {
|
|
for( nd = dbi_first(iter); dbi_exists(iter); nd = dbi_next(iter) ) {
|
|
if( nd->path && strcasecmp(nd->path,path) == 0 ) {
|
|
if( nd->path && strcasecmp(nd->path,path) == 0 ) {
|
|
found = true;
|
|
found = true;
|
|
@@ -3697,12 +3689,12 @@ bool npc_unloadfile( const char* path ) {
|
|
npc_unload(nd, true);
|
|
npc_unload(nd, true);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
-
|
|
|
|
|
|
+
|
|
dbi_destroy(iter);
|
|
dbi_destroy(iter);
|
|
-
|
|
|
|
|
|
+
|
|
if( found ) /* refresh event cache */
|
|
if( found ) /* refresh event cache */
|
|
npc_read_event_script();
|
|
npc_read_event_script();
|
|
-
|
|
|
|
|
|
+
|
|
return found;
|
|
return found;
|
|
}
|
|
}
|
|
|
|
|
|
@@ -3712,7 +3704,7 @@ void do_clear_npc(void) {
|
|
}
|
|
}
|
|
|
|
|
|
/*==========================================
|
|
/*==========================================
|
|
- * Destructor
|
|
|
|
|
|
+ * Destructor
|
|
*------------------------------------------*/
|
|
*------------------------------------------*/
|
|
int do_final_npc(void) {
|
|
int do_final_npc(void) {
|
|
npc_clear_pathlist();
|
|
npc_clear_pathlist();
|
|
@@ -3770,15 +3762,15 @@ int do_init_npc(void)
|
|
//Stock view data for normal npcs.
|
|
//Stock view data for normal npcs.
|
|
memset(&npc_viewdb, 0, sizeof(npc_viewdb));
|
|
memset(&npc_viewdb, 0, sizeof(npc_viewdb));
|
|
npc_viewdb[0].class_ = INVISIBLE_CLASS; //Invisible class is stored here.
|
|
npc_viewdb[0].class_ = INVISIBLE_CLASS; //Invisible class is stored here.
|
|
- for( i = 1; i < MAX_NPC_CLASS; i++ )
|
|
|
|
|
|
+ for( i = 1; i < MAX_NPC_CLASS; i++ )
|
|
npc_viewdb[i].class_ = i;
|
|
npc_viewdb[i].class_ = i;
|
|
|
|
|
|
ev_db = strdb_alloc((DBOptions)(DB_OPT_DUP_KEY|DB_OPT_RELEASE_DATA),2*NAME_LENGTH+2+1);
|
|
ev_db = strdb_alloc((DBOptions)(DB_OPT_DUP_KEY|DB_OPT_RELEASE_DATA),2*NAME_LENGTH+2+1);
|
|
npcname_db = strdb_alloc(DB_OPT_BASE,NAME_LENGTH);
|
|
npcname_db = strdb_alloc(DB_OPT_BASE,NAME_LENGTH);
|
|
npc_path_db = strdb_alloc(DB_OPT_BASE|DB_OPT_DUP_KEY|DB_OPT_RELEASE_DATA,80);
|
|
npc_path_db = strdb_alloc(DB_OPT_BASE|DB_OPT_DUP_KEY|DB_OPT_RELEASE_DATA,80);
|
|
-
|
|
|
|
|
|
+
|
|
timer_event_ers = ers_new(sizeof(struct timer_event_data),"clif.c::timer_event_ers",ERS_OPT_NONE);
|
|
timer_event_ers = ers_new(sizeof(struct timer_event_data),"clif.c::timer_event_ers",ERS_OPT_NONE);
|
|
-
|
|
|
|
|
|
+
|
|
// process all npc files
|
|
// process all npc files
|
|
ShowStatus("Loading NPCs...\r");
|
|
ShowStatus("Loading NPCs...\r");
|
|
for( file = npc_src_files; file != NULL; file = file->next ) {
|
|
for( file = npc_src_files; file != NULL; file = file->next ) {
|
|
@@ -3822,6 +3814,6 @@ int do_init_npc(void)
|
|
fake_nd->u.scr.timerid = INVALID_TIMER;
|
|
fake_nd->u.scr.timerid = INVALID_TIMER;
|
|
map_addiddb(&fake_nd->bl);
|
|
map_addiddb(&fake_nd->bl);
|
|
// End of initialization
|
|
// End of initialization
|
|
-
|
|
|
|
|
|
+
|
|
return 0;
|
|
return 0;
|
|
}
|
|
}
|