Implement & link m_npc_schedule.c

This commit is contained in:
Cuyler36
2023-07-27 20:42:38 -04:00
parent 132ae88c8f
commit e803ad257e
11 changed files with 312 additions and 5 deletions
+3
View File
@@ -104,6 +104,9 @@ m_needlework.c:
.text: [0x803C98EC, 0x803C9F7C]
.data: [0x8065ABC0, 0x8065AE30]
.bss: [0x81298F60, 0x81299180]
m_npc_schedule.c:
.text: [0x803D7570, 0x803D7890]
.data: [0x8065B638, 0x8065B7F0]
m_olib.c:
.text: [0x803D88E8, 0x803D8A34]
.rodata: [0x80642A00, 0x80642A10]
+1 -1
View File
@@ -33,7 +33,7 @@ extern void sAdo_PlayerStatusLevel(f32 speed, int p);
/* Not sure about the last param name */
extern void sAdo_VoiceSe(u8 num, u8 num2, u8 num3, s16 character_idx, u8 scale, u8 mode);
extern void sAdo_Inst(s8 num, void* p);
extern void sAdo_Inst(u16 num, u8* p);
extern void sAdo_MessageStatus(u8 status);
extern void sAdo_MessageSpeed(u8 speed);
extern u8 sAdo_MessageSpeedGet();
+1 -1
View File
@@ -7,7 +7,7 @@
extern "C"{
#endif
extern void Na_Inst(s8, void*);
extern void Na_Inst(u16, u8*);
extern void Na_FurnitureInst(int,s8,s32,u16,f32);
extern int Na_InstCountGet();
+4 -1
View File
@@ -28,11 +28,14 @@
#include "m_scene.h"
#include "m_npc_walk.h"
#include "m_mask_cat.h"
#include "m_npc_schedule_h.h"
#ifdef __cplusplus
extern "C" {
#endif
#define SCHEDULE_NUM ANIMAL_NUM_MAX + mISL_ISLANDER_NUM
typedef struct time_s {
u32 season;
u32 term_idx;
@@ -183,7 +186,7 @@ typedef struct common_data_s {
/* 0x026678 */ u8 _26678[0x2669C - 0x26678];
/* 0x02669C */ mQst_not_saved_c quest;
/* 0x0266A4 */ int scene_from_title_demo; /* next scene to be loaded when title demo finishes */
/* 0x0266A8 */ u8 _266A8[0x267A8 - 0x266A8];
/* 0x0266A8 */ mNPS_schedule_c npc_schedule[SCHEDULE_NUM];
/* 0x0267A8 */ mNpc_walk_c npc_walk;
/* 0x026838 */ u8 _26838[0x2852C - 0x26838];
/* 0x02852C */ s16 money_power;
+1
View File
@@ -115,6 +115,7 @@ enum event_table {
mEv_EVENT_FATHERS_DAY = 26,
mEv_EVENT_FISHING_TOURNEY_1 = 29,
mEv_EVENT_MUSHROOM_SEASON = 47,
mEv_EVENT_HALLOWEEN = 49,
mEv_EVENT_FISHING_TOURNEY_2 = 54,
mEv_EVENT_GHOST = 64,
mEv_EVENT_BROKER_SALE = 75,
+2
View File
@@ -13,6 +13,8 @@
extern "C" {
#endif
#define mISL_ISLANDER_NUM 1
#define mISL_ISLAND_NAME_LEN 8
#define mISL_FG_BLOCK_X_NUM 2
+11
View File
@@ -9,6 +9,17 @@
extern "C" {
#endif
enum {
mNpc_LOOKS_GIRL,
mNpc_LOOKS_KO_GIRL,
mNpc_LOOKS_BOY,
mNpc_LOOKS_SPORT_MAN,
mNpc_LOOKS_GRIM_MAN,
mNpc_LOOKS_NANIWA_LADY,
mNpc_LOOKS_NUM
};
/* sizeof(AnmPersonalID_c) == 0xE */
typedef struct animal_personal_id_s {
/* 0x00 */ mActor_name_t npc_id; /* id */
+17
View File
@@ -0,0 +1,17 @@
#ifndef M_NPC_SCHEDULE_H
#define M_NPC_SCHEDULE_H
#include "types.h"
#include "m_npc_schedule_h.h"
#ifdef __cplusplus
extern "C" {
#endif
#ifdef __cplusplus
}
#endif
#endif
+45
View File
@@ -0,0 +1,45 @@
#ifndef M_NPC_SCHEDULE_H_H
#define M_NPC_SCHEDULE_H_H
#include "types.h"
#include "m_npc_personal_id.h"
#ifdef __cplusplus
extern "C" {
#endif
enum {
mNPS_SCHED_FIELD, /* in same acre as their home */
mNPS_SCHED_IN_HOUSE, /* inside their house */
mNPS_SCHED_SLEEP, /* asleep in their house */
mNPS_SCHED_STAND, /* standing around town?? */
mNPS_SCHED_WANDER, /* wander around town */
mNPS_SCHED_SPECIAL, /* unique schedule method for each NPC actor type */
mNPS_SCHED_TYPE_NUM
};
typedef struct schedule_data_s {
u32 type;
int end_time;
} mNPS_schedule_data_c;
typedef struct schedule_data_table_s {
int count;
mNPS_schedule_data_c* sched_data;
} mNPS_schedule_data_table_c;
typedef struct schedule_s {
AnmPersonalID_c* id;
mNPS_schedule_data_table_c* data_table;
u8 current_type;
u8 forced_type;
u8 saved_type;
int forced_timer;
} mNPS_schedule_c;
#ifdef __cplusplus
}
#endif
#endif
+1 -2
View File
@@ -106,8 +106,7 @@ extern void sAdo_VoiceSe(u8 num, u8 num2, u8 num3, s16 character_idx, u8 scale,
Na_VoiceSe(num,num2,num3,character_idx, scale, mode);
}
extern void sAdo_Inst(s8 num, void* p){
extern void sAdo_Inst(u16 num, u8* p){
Na_Inst(num,p);
}
+226
View File
@@ -0,0 +1,226 @@
#include "m_npc_schedule.h"
#include "m_common_data.h"
#define mNPS_TIME_2_SEC(hour, min, sec) ((hour) * 3600 + (min) * 60 + (sec))
#define mNPS_MAKE_SCHEDULE_TABLE(sched_data) { ARRAY_SIZE(sched_data, mNPS_schedule_data_c), sched_data }
static mNPS_schedule_data_c girl_schedule_dt[] = {
{ mNPS_SCHED_SLEEP, mNPS_TIME_2_SEC(5, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(6, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(12, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(13, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(18, 30, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(21, 0, 0) },
{ mNPS_SCHED_SLEEP, mNPS_TIME_2_SEC(24, 0, 0) }
};
static mNPS_schedule_data_table_c girl_schedule = mNPS_MAKE_SCHEDULE_TABLE(girl_schedule_dt);
static mNPS_schedule_data_c ko_girl_schedule_dt[] = {
{ mNPS_SCHED_SLEEP, mNPS_TIME_2_SEC(7, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(8, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(13, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(14, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(22, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(23, 30, 0) },
{ mNPS_SCHED_SLEEP, mNPS_TIME_2_SEC(24, 0, 0) }
};
static mNPS_schedule_data_table_c ko_girl_schedule = mNPS_MAKE_SCHEDULE_TABLE(ko_girl_schedule_dt);
static mNPS_schedule_data_c boy_schedule_dt[] = {
{ mNPS_SCHED_SLEEP, mNPS_TIME_2_SEC(8, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(9, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(12, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(14, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(19, 30, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(22, 0, 0) },
{ mNPS_SCHED_SLEEP, mNPS_TIME_2_SEC(24, 0, 0) }
};
static mNPS_schedule_data_table_c boy_schedule = mNPS_MAKE_SCHEDULE_TABLE(boy_schedule_dt);
static mNPS_schedule_data_c sport_man_schedule_dt[] = {
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(1, 0, 0) },
{ mNPS_SCHED_SLEEP, mNPS_TIME_2_SEC(5, 30, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(6, 30, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(12, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(12, 30, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(23, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(24, 0, 0) }
};
static mNPS_schedule_data_table_c sport_man_schedule = mNPS_MAKE_SCHEDULE_TABLE(sport_man_schedule_dt);
static mNPS_schedule_data_c grim_man_schedule_dt[] = {
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(4, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(5, 0, 0) },
{ mNPS_SCHED_SLEEP, mNPS_TIME_2_SEC(10, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(11, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(15, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(16, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(22, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(23, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(24, 0, 0) }
};
static mNPS_schedule_data_table_c grim_man_schedule = mNPS_MAKE_SCHEDULE_TABLE(grim_man_schedule_dt);
static mNPS_schedule_data_c naniwa_lady_schedule_dt[] = {
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(1, 30, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(2, 30, 0) },
{ mNPS_SCHED_SLEEP, mNPS_TIME_2_SEC(9, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(10, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(13, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(14, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(21, 0, 0) },
{ mNPS_SCHED_IN_HOUSE, mNPS_TIME_2_SEC(22, 0, 0) },
{ mNPS_SCHED_FIELD, mNPS_TIME_2_SEC(24, 0, 0) }
};
static mNPS_schedule_data_table_c naniwa_lady_schedule = mNPS_MAKE_SCHEDULE_TABLE(naniwa_lady_schedule_dt);
static mNPS_schedule_data_table_c* mNPS_schedule[mNpc_LOOKS_NUM] = {
&girl_schedule,
&ko_girl_schedule,
&boy_schedule,
&sport_man_schedule,
&grim_man_schedule,
&naniwa_lady_schedule
};
extern mNPS_schedule_c* mNPS_get_schedule_area(AnmPersonalID_c* anm_id) {
mNPS_schedule_c* schedule = Common_Get(npc_schedule);
int i;
for (i = 0; i < SCHEDULE_NUM; i++) {
if (schedule->id == anm_id) {
return schedule;
}
schedule++;
}
return NULL;
}
static void mNPS_set_schedule_area(AnmPersonalID_c* anm_id) {
mNPS_schedule_c* schedule = mNPS_get_schedule_area(NULL); /* try to get an unused schedule */
if (schedule != NULL) {
schedule->id = anm_id;
schedule->data_table = mNPS_schedule[anm_id->looks];
schedule->forced_timer = 0;
}
}
extern void mNPS_set_island_schedule_area(AnmPersonalID_c* anm_id) {
if (Common_Get(npc_schedule[ANIMAL_NUM_MAX]).id != NULL) {
return;
}
Common_Set(npc_schedule[ANIMAL_NUM_MAX].id, anm_id);
Common_Set(npc_schedule[ANIMAL_NUM_MAX].data_table, mNPS_schedule[anm_id->looks]);
Common_Set(npc_schedule[ANIMAL_NUM_MAX].forced_timer, 0);
}
extern void mNPS_reset_schedule_area(AnmPersonalID_c* anm_id) {
mNPS_schedule_c* schedule = mNPS_get_schedule_area(anm_id);
if (schedule != NULL) {
schedule->id = NULL;
}
}
static void mNPS_schedule_manager_sub(mNPS_schedule_c* schedule) {
int now_sec = Common_Get(time.now_sec);
int count = schedule->data_table->count;
mNPS_schedule_data_c* schedule_entry = schedule->data_table->sched_data;
/* Locate our current scehdule entry */
for (count; count != 0; count--) {
if (schedule_entry->end_time > now_sec) {
break;
}
schedule_entry++;
}
schedule->saved_type = schedule_entry->type;
if (schedule->forced_timer > 0) {
schedule->current_type = schedule->forced_type;
schedule->forced_timer--;
}
else {
schedule->current_type = schedule->saved_type;
}
}
static void mNPS_schedule_manager_sub0() {
mNPS_schedule_c* schedule = Common_Get(npc_schedule);
int i;
/* Set all town animals to go outside in their home block */
for (i = 0; i < ANIMAL_NUM_MAX; i++) {
if (schedule->id != NULL) {
schedule->current_type = mNPS_SCHED_FIELD;
}
schedule++;
}
}
static void mNPS_schedule_manager_sub1() {
mNPS_schedule_c* schedule = Common_Get(npc_schedule);
int i;
/* Set all town animals to go about their intended schedule */
for (i = 0; i < ANIMAL_NUM_MAX; i++) {
if (schedule->id != NULL) {
mNPS_schedule_manager_sub(schedule);
}
schedule++;
}
}
static void mNPS_island_schedule_manager() {
mNPS_schedule_c* schedule = Common_GetPointer(npc_schedule[ANIMAL_NUM_MAX]);
if (schedule->id != NULL) {
mNPS_schedule_manager_sub(schedule);
}
}
extern void mNPS_schedule_manager() {
int force_outside = FALSE;
if (mEv_CheckFirstJob() == TRUE || mEv_check_status(mEv_EVENT_HALLOWEEN, mEv_STATUS_ACTIVE)) {
force_outside = TRUE;
}
if (force_outside == TRUE) {
mNPS_schedule_manager_sub0();
}
else {
mNPS_schedule_manager_sub1();
}
mNPS_island_schedule_manager();
}
extern void mNPS_set_all_schedule_area() {
Animal_c* animal = Save_Get(animals);
int i;
for (i = 0; i < ANIMAL_NUM_MAX; i++) {
if (mNpc_CheckFreeAnimalInfo(animal) == FALSE) {
mNPS_set_schedule_area(&animal->id);
}
animal++;
}
mNPS_schedule_manager();
}