summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/battle_setup.c2
-rw-r--r--src/berry_tag_screen.c877
-rw-r--r--src/blend_palette.c1
-rw-r--r--src/calculate_base_damage.c1484
-rw-r--r--src/coins.c1
-rw-r--r--src/decompress.c2
-rw-r--r--src/field_camera.c2
-rw-r--r--src/field_door.c3
-rw-r--r--src/field_ground_effect.c256
-rw-r--r--src/field_player_avatar.c5
-rw-r--r--src/fieldmap.c22
-rw-r--r--src/intro.c2
-rw-r--r--src/item.c2
-rw-r--r--src/link.c30
-rw-r--r--src/load_save.c164
-rw-r--r--src/mail.c683
-rw-r--r--src/main.c15
-rw-r--r--src/main_menu.c1
-rw-r--r--src/matsuda_debug_menu.c179
-rw-r--r--src/menu.c33
-rw-r--r--src/metatile_behavior.c1064
-rw-r--r--src/money.c240
-rw-r--r--src/mori_debug_menu.c17
-rw-r--r--src/mystery_event_menu.c346
-rw-r--r--src/mystery_event_script.c97
-rw-r--r--src/new_game.c12
-rw-r--r--src/player_pc.c818
-rw-r--r--src/pokedex.c4
-rw-r--r--src/pokemon_1.c7
-rw-r--r--src/pokemon_2.c6
-rw-r--r--src/pokemon_3.c477
-rw-r--r--src/pokemon_size_record.c1
-rw-r--r--src/rom4.c38
-rw-r--r--src/rtc.c10
-rw-r--r--src/save.c28
-rw-r--r--src/save_failed_screen.c301
-rw-r--r--src/scrcmd.c5
-rw-r--r--src/script_menu.c431
-rw-r--r--src/sound.c3
-rw-r--r--src/sprite.c18
-rw-r--r--src/start_menu.c37
-rw-r--r--src/starter_choose.c8
-rw-r--r--src/text.c57
-rw-r--r--src/trainer_card.c23
-rw-r--r--src/trainer_see.c37
-rw-r--r--src/truck_scene.c4
-rw-r--r--src/weather.c2
-rw-r--r--src/wild_encounter.c1
48 files changed, 7547 insertions, 309 deletions
diff --git a/src/battle_setup.c b/src/battle_setup.c
index 4822cd585..68690bf1d 100644
--- a/src/battle_setup.c
+++ b/src/battle_setup.c
@@ -20,6 +20,7 @@
#include "field_message_box.h"
#include "trainer.h"
#include "starter_choose.h"
+#include "metatile_behavior.h"
#define NUM_TRAINER_EYE_TRAINERS 56
#define TRAINER_REMATCH_STEPS 255
@@ -448,7 +449,6 @@ u8 GetWildBattleTransition(void)
u8 GetTrainerBattleTransition(void)
{
struct Trainer *trainer;
- u8 trainerClass;
u8 partyCount;
u8 flashVar;
u8 level;
diff --git a/src/berry_tag_screen.c b/src/berry_tag_screen.c
new file mode 100644
index 000000000..e7ef9ca76
--- /dev/null
+++ b/src/berry_tag_screen.c
@@ -0,0 +1,877 @@
+#include "global.h"
+#include "berry_tag_screen.h"
+#include "asm.h"
+#include "berry.h"
+#include "decompress.h"
+#include "main.h"
+#include "menu.h"
+#include "palette.h"
+#include "rom4.h"
+#include "songs.h"
+#include "sound.h"
+#include "sprite.h"
+#include "string_util.h"
+#include "task.h"
+#include "text.h"
+
+#define OFFSET_7B (123)
+#define FIRST_BERRY (0x85) // ITEM_CHERI_BERRY
+
+struct Struct2000000 {
+ /*0x00*/ u8 filler_0[0x1FFFF];
+ /*0x1FFFF*/ bool8 var_1FFFF;
+};
+
+struct BerryTagStatus {
+ s16 circles[5];
+};
+
+extern struct Struct2000000 unk_2000000;
+extern u16 gBGTilemapBuffers[4][0x400];
+extern u8 gUnknown_0203932C;
+extern struct BerryTagStatus gUnknown_0203932E;
+extern u16 gScriptItemId;
+extern u16 gUnknown_030041B4;
+
+extern const struct SpriteSheet gUnknown_083C1F74;
+extern const struct SpritePalette gUnknown_083C1F7C;
+
+extern u8 gOtherText_ThreeQuestions2[];
+extern u8 gOtherText_Size[];
+extern u8 gOtherText_Firm[];
+extern u8 gContestStatsText_Unknown1[];
+extern u8 *gUnknown_0841192C[];
+
+extern u8 gBerryCheck_Gfx[];
+extern u8 gBerryCheck_Pal[];
+extern u8 gUnknown_08E788E4[];
+extern u8 gUnknown_08E78A84[];
+
+static void sub_8146014(void);
+static void sub_814602C(void);
+static bool8 sub_8146058(void);
+static void sub_8146288(void);
+static bool8 sub_81462B8(void);
+static void sub_814640C(u8 taskId);
+static void sub_8146440(u8 taskId);
+static void sub_8146480(u8 taskid);
+static void sub_81464E4(void);
+static void sub_8146600(u8 berry);
+// static void sub_81466A0(void);
+static void sub_81466E8(u8 taskId, s32 direction);
+// static void sub_8146798(u8 berry);
+// static void sub_8146810(u8 berry);
+// static void sub_81468BC(void);
+
+static void sub_8146014(void) {
+ AnimateSprites();
+ BuildOamBuffer();
+ RunTasks();
+ UpdatePaletteFade();
+}
+
+static void sub_814602C(void) {
+ REG_BG0VOFS = gUnknown_030041B4;
+ REG_BG1VOFS = gUnknown_030041B4;
+
+ LoadOam();
+ ProcessSpriteCopyRequests();
+ TransferPlttBuffer();
+}
+
+static bool8 sub_8146058(void) {
+ u8 berry;
+ u16 backup;
+
+ switch (gMain.state) {
+ case 0:
+ sub_80F9438();
+ sub_80F9368();
+ sub_8146288();
+ REG_BLDCNT = 0;
+ gMain.state += 1;
+ break;
+
+ case 1:
+ ResetPaletteFade();
+ gPaletteFade.bufferTransferDisabled = 1;
+ gMain.state += 1;
+ break;
+
+ case 2:
+ ResetSpriteData();
+ gMain.state += 1;
+ break;
+
+ case 3:
+ SetUpWindowConfig(&gWindowConfig_81E6E18);
+ gMain.state += 1;
+ break;
+
+ case 4:
+ MultistepInitMenuWindowBegin(&gWindowConfig_81E6E18);
+ gMain.state += 1;
+ break;
+
+ case 5:
+ if (!MultistepInitMenuWindowContinue()) {
+ return FALSE;
+ }
+ unk_2000000.var_1FFFF = 0;
+ gMain.state += 1;
+ break;
+
+ case 6:
+ if (!sub_81462B8()) {
+ break;
+ }
+
+ unk_2000000.var_1FFFF = 0;
+ gMain.state += 1;
+ break;
+
+ case 7:
+ sub_81464E4();
+ gMain.state += 1;
+ break;
+
+ case 8:
+ berry = gScriptItemId + OFFSET_7B;
+ gUnknown_0203932C = sub_80A7D8C(berry, 56, 64);
+ gMain.state += 1;
+ break;
+
+ case 9:
+ sub_8146600(gScriptItemId + OFFSET_7B);
+ gMain.state += 1;
+ break;
+
+ case 10:
+ backup = REG_IME;
+ REG_IME = 0;
+ REG_IE |= INTR_FLAG_VBLANK;
+ REG_IME = backup;
+
+ REG_DISPSTAT |= DISPSTAT_VBLANK_INTR;
+ SetVBlankCallback(sub_814602C);
+ REG_DISPCNT = DISPCNT_OBJ_ON | DISPCNT_BG_ALL_ON | DISPCNT_OBJ_1D_MAP;
+ gMain.state += 1;
+ break;
+
+ case 11:
+ if (sub_8055870() == TRUE) {
+ break;
+ }
+ gMain.state += 1;
+ break;
+
+ case 12:
+ BeginNormalPaletteFade(-1, 0, 0x10, 0, 0);
+ gPaletteFade.bufferTransferDisabled = 0;
+ SetMainCallback2(sub_8146014);
+ return TRUE;
+
+ }
+
+ return FALSE;
+}
+
+void BerryTagScreen_814625C(u8 taskId) {
+ do {
+ if (sub_8146058() == TRUE) {
+ CreateTask(sub_8146480, 0);
+ return;
+ }
+
+ } while (sub_80F9344() != TRUE);
+}
+
+static void sub_8146288(void) {
+ REG_BG1CNT = 0x502;
+ REG_BG2CNT = 0x600;
+ REG_BG3CNT = 0x703;
+ gUnknown_030041B4 = 0;
+}
+
+#ifdef NONMATCHING
+bool8 sub_81462B8(void) {
+ u16 i;
+
+ switch (unk_2000000.var_1FFFF) {
+ case 0:
+ LZDecompressVram(gBerryCheck_Gfx, (void *) VRAM);
+ unk_2000000.var_1FFFF += 1;
+ break;
+
+ case 1:
+ LZDecompressVram(gUnknown_08E788E4, (void *) VRAM + 0x2800);
+ unk_2000000.var_1FFFF += 1;
+ break;
+
+ case 2:
+ LZDecompressVram(gUnknown_08E78A84, (void *) VRAM + 0x3000);
+ unk_2000000.var_1FFFF += 1;
+ break;
+
+ case 3:
+ for (i = 0; i < 0x400; i++) {
+ u16 (*buffer)[0x400] = &gBGTilemapBuffers[3];
+ if (gSaveBlock2.playerGender == MALE) {
+ (*buffer)[i] = 0x4042;
+ } else {
+ (*buffer)[i] = 0x5042;
+ }
+ }
+ unk_2000000.var_1FFFF += 1;
+ break;
+
+ case 4:
+ LoadCompressedPalette(gBerryCheck_Pal, 0, 96 * 2);
+ unk_2000000.var_1FFFF += 1;
+ break;
+
+ case 5:
+ LoadCompressedObjectPic(&gUnknown_083C1F74);
+ unk_2000000.var_1FFFF += 1;
+ break;
+
+ case 6:
+ LoadCompressedObjectPalette(&gUnknown_083C1F7C);
+ unk_2000000.var_1FFFF = 0;
+ return TRUE;
+ }
+
+ return FALSE;
+}
+#else
+__attribute__((naked))
+static bool8 sub_81462B8(void) {
+ asm(".syntax unified\n\
+ push {r4-r7,lr}\n\
+ ldr r1, _081462D4 @ =0x02000000\n\
+ ldr r2, _081462D8 @ =0x0001ffff\n\
+ adds r0, r1, r2\n\
+ ldrb r0, [r0]\n\
+ mov r12, r1\n\
+ cmp r0, 0x6\n\
+ bls _081462CA\n\
+ b _08146404\n\
+_081462CA:\n\
+ lsls r0, 2\n\
+ ldr r1, _081462DC @ =_081462E0\n\
+ adds r0, r1\n\
+ ldr r0, [r0]\n\
+ mov pc, r0\n\
+ .align 2, 0\n\
+_081462D4: .4byte 0x02000000\n\
+_081462D8: .4byte 0x0001ffff\n\
+_081462DC: .4byte _081462E0\n\
+ .align 2, 0\n\
+_081462E0:\n\
+ .4byte _081462FC\n\
+ .4byte _0814630C\n\
+ .4byte _0814632C\n\
+ .4byte _08146340\n\
+ .4byte _081463A4\n\
+ .4byte _081463C4\n\
+ .4byte _081463E4\n\
+_081462FC:\n\
+ ldr r0, _08146308 @ =gBerryCheck_Gfx\n\
+ movs r1, 0xC0\n\
+ lsls r1, 19\n\
+ bl LZDecompressVram\n\
+ b _081463CA\n\
+ .align 2, 0\n\
+_08146308: .4byte gBerryCheck_Gfx\n\
+_0814630C:\n\
+ ldr r0, _0814631C @ =gUnknown_08E788E4\n\
+ ldr r1, _08146320 @ =0x06002800\n\
+ bl LZDecompressVram\n\
+ ldr r1, _08146324 @ =0x02000000\n\
+ ldr r2, _08146328 @ =0x0001ffff\n\
+ adds r1, r2\n\
+ b _081463D0\n\
+ .align 2, 0\n\
+_0814631C: .4byte gUnknown_08E788E4\n\
+_08146320: .4byte 0x06002800\n\
+_08146324: .4byte 0x02000000\n\
+_08146328: .4byte 0x0001ffff\n\
+_0814632C:\n\
+ ldr r0, _08146338 @ =gUnknown_08E78A84\n\
+ ldr r1, _0814633C @ =0x06003000\n\
+ bl LZDecompressVram\n\
+ b _081463CA\n\
+ .align 2, 0\n\
+_08146338: .4byte gUnknown_08E78A84\n\
+_0814633C: .4byte 0x06003000\n\
+_08146340:\n\
+ movs r1, 0\n\
+ ldr r7, _0814635C @ =gBGTilemapBuffers + 0x1000\n\
+ adds r2, r7, 0\n\
+ ldr r6, _08146360 @ =0x00004042\n\
+ ldr r5, _08146364 @ =gSaveBlock2\n\
+ ldr r4, _08146368 @ =0x00005042\n\
+ ldr r3, _0814636C @ =0x000003ff\n\
+_0814634E:\n\
+ ldrb r0, [r5, 0x8]\n\
+ cmp r0, 0\n\
+ bne _08146370\n\
+ lsls r0, r1, 1\n\
+ adds r0, r2\n\
+ strh r6, [r0]\n\
+ b _08146376\n\
+ .align 2, 0\n\
+_0814635C: .4byte gBGTilemapBuffers + 0x1000\n\
+_08146360: .4byte 0x00004042\n\
+_08146364: .4byte gSaveBlock2\n\
+_08146368: .4byte 0x00005042\n\
+_0814636C: .4byte 0x000003ff\n\
+_08146370:\n\
+ lsls r0, r1, 1\n\
+ adds r0, r2\n\
+ strh r4, [r0]\n\
+_08146376:\n\
+ adds r0, r1, 0x1\n\
+ lsls r0, 16\n\
+ lsrs r1, r0, 16\n\
+ cmp r1, r3\n\
+ bls _0814634E\n\
+ ldr r1, _08146394 @ =0x06003800\n\
+ ldr r0, _08146398 @ =0x040000d4\n\
+ str r7, [r0]\n\
+ str r1, [r0, 0x4]\n\
+ ldr r1, _0814639C @ =0x80000400\n\
+ str r1, [r0, 0x8]\n\
+ ldr r0, [r0, 0x8]\n\
+ ldr r1, _081463A0 @ =0x0001ffff\n\
+ add r1, r12\n\
+ b _081463D0\n\
+ .align 2, 0\n\
+_08146394: .4byte 0x06003800\n\
+_08146398: .4byte 0x040000d4\n\
+_0814639C: .4byte 0x80000400\n\
+_081463A0: .4byte 0x0001ffff\n\
+_081463A4:\n\
+ ldr r0, _081463B8 @ =gBerryCheck_Pal\n\
+ movs r1, 0\n\
+ movs r2, 0xC0\n\
+ bl LoadCompressedPalette\n\
+ ldr r1, _081463BC @ =0x02000000\n\
+ ldr r2, _081463C0 @ =0x0001ffff\n\
+ adds r1, r2\n\
+ b _081463D0\n\
+ .align 2, 0\n\
+_081463B8: .4byte gBerryCheck_Pal\n\
+_081463BC: .4byte 0x02000000\n\
+_081463C0: .4byte 0x0001ffff\n\
+_081463C4:\n\
+ ldr r0, _081463D8 @ =gUnknown_083C1F74\n\
+ bl LoadCompressedObjectPic\n\
+_081463CA:\n\
+ ldr r1, _081463DC @ =0x02000000\n\
+ ldr r0, _081463E0 @ =0x0001ffff\n\
+ adds r1, r0\n\
+_081463D0:\n\
+ ldrb r0, [r1]\n\
+ adds r0, 0x1\n\
+ strb r0, [r1]\n\
+ b _08146404\n\
+ .align 2, 0\n\
+_081463D8: .4byte gUnknown_083C1F74\n\
+_081463DC: .4byte 0x02000000\n\
+_081463E0: .4byte 0x0001ffff\n\
+_081463E4:\n\
+ ldr r0, _081463F8 @ =gUnknown_083C1F7C\n\
+ bl LoadCompressedObjectPalette\n\
+ ldr r0, _081463FC @ =0x02000000\n\
+ ldr r1, _08146400 @ =0x0001ffff\n\
+ adds r0, r1\n\
+ movs r1, 0\n\
+ strb r1, [r0]\n\
+ movs r0, 0x1\n\
+ b _08146406\n\
+ .align 2, 0\n\
+_081463F8: .4byte gUnknown_083C1F7C\n\
+_081463FC: .4byte 0x02000000\n\
+_08146400: .4byte 0x0001ffff\n\
+_08146404:\n\
+ movs r0, 0\n\
+_08146406:\n\
+ pop {r4-r7}\n\
+ pop {r1}\n\
+ bx r1\n\
+ .syntax divided\n");
+}
+#endif
+
+static void sub_814640C(u8 taskId) {
+ if (gPaletteFade.active) {
+ return;
+ }
+
+ SetMainCallback2(sub_80A5B40);
+ sub_80A7DD4();
+ gpu_pal_allocator_reset__manage_upper_four();
+ DestroyTask(taskId);
+}
+
+static void sub_8146440(u8 taskId) {
+ PlaySE(SE_SELECT);
+ BeginNormalPaletteFade(-1, 0, 0, 0x10, 0);
+
+ gTasks[taskId].func = sub_814640C;
+}
+
+static void sub_8146480(u8 taskid) {
+ register u16 keys asm("r1");
+
+ if (gPaletteFade.active) {
+ return;
+ }
+
+ keys = gMain.newAndRepeatedKeys & (DPAD_RIGHT | DPAD_LEFT | DPAD_UP | DPAD_DOWN);
+ if (keys == DPAD_UP) {
+ sub_81466E8(taskid, -1);
+ }
+
+ keys = gMain.newAndRepeatedKeys & (DPAD_RIGHT | DPAD_LEFT | DPAD_UP | DPAD_DOWN);
+ if (keys == DPAD_DOWN) {
+ sub_81466E8(taskid, 1);
+ }
+
+ if (gMain.newKeys & A_BUTTON || gMain.newKeys & B_BUTTON) {
+ sub_8146440(taskid);
+ }
+}
+
+static void sub_81464E4(void) {
+ struct Berry *berryInfo;
+ u32 size;
+ s32 sizeMajor;
+ s32 sizeMinor;
+
+ berryInfo = GetBerryInfo(gScriptItemId + OFFSET_7B + 1);
+
+ ConvertIntToDecimalStringN(gStringVar1, gScriptItemId - FIRST_BERRY + 1, STR_CONV_MODE_LEADING_ZEROS, 2);
+ MenuPrint(gStringVar1, 12, 4);
+
+ MenuPrint(berryInfo->name, 14, 4);
+ MenuPrint(berryInfo->description1, 4, 14);
+ MenuPrint(berryInfo->description2, 4, 16);
+
+ size = (berryInfo->size * 1000) / 254;
+ if (size % 10 >= 5) {
+ size += 10;
+ }
+ sizeMinor = (size % 100) / 10;
+ sizeMajor = size / 100;
+
+ MenuPrint(gOtherText_Size, 11, 7);
+ if (berryInfo->size != 0) {
+ ConvertIntToDecimalStringN(gStringVar1, sizeMajor, STR_CONV_MODE_LEFT_ALIGN, 2);
+ ConvertIntToDecimalStringN(gStringVar2, sizeMinor, STR_CONV_MODE_LEFT_ALIGN, 2);
+ MenuPrint(gContestStatsText_Unknown1, 16, 7);
+ } else {
+ MenuPrint(gOtherText_ThreeQuestions2, 16, 7);
+ }
+
+ MenuPrint(gOtherText_Firm, 11, 9);
+ if (berryInfo->firmness != 0) {
+ MenuPrint(gUnknown_0841192C[berryInfo->firmness - 1], 16, 9);
+ } else {
+ MenuPrint(gOtherText_ThreeQuestions2, 16, 9);
+ }
+}
+
+#ifdef NONMATCHING
+static void sub_8146600(u8 berry) {
+ struct Berry *berryInfo;
+ u16 i;
+
+ berryInfo = GetBerryInfo(berry +1);
+
+ for (i = 0; i < 5; i++) {
+ gUnknown_0203932E.circles[i] |= 0xFFFF;
+ }
+
+ if (berryInfo->spicy) {
+ // argument is the center of the circle
+ gUnknown_0203932E.circles[0] = sub_80A7E5C(48);
+ }
+
+ if (berryInfo->dry) {
+ gUnknown_0203932E.circles[1] = sub_80A7E5C(88);
+ }
+
+ if (berryInfo->sweet) {
+ gUnknown_0203932E.circles[2] = sub_80A7E5C(128);
+ }
+
+ if (berryInfo->bitter) {
+ gUnknown_0203932E.circles[3] = sub_80A7E5C(168);
+ }
+
+ if (berryInfo->sour) {
+ gUnknown_0203932E.circles[4] = sub_80A7E5C(208);
+ }
+}
+#else
+__attribute__((naked))
+static void sub_8146600(u8 berry) {
+ asm(".syntax unified\n\
+ push {r4,r5,lr}\n\
+ lsls r0, 24\n\
+ movs r1, 0x80\n\
+ lsls r1, 17\n\
+ adds r0, r1\n\
+ lsrs r0, 24\n\
+ bl GetBerryInfo\n\
+ adds r4, r0, 0\n\
+ movs r2, 0\n\
+ ldr r5, _08146698 @ =gUnknown_0203932E\n\
+ ldr r0, _0814669C @ =0x0000ffff\n\
+ adds r3, r0, 0\n\
+_0814661A:\n\
+ lsls r0, r2, 1\n\
+ adds r0, r5\n\
+ ldrh r1, [r0]\n\
+ orrs r1, r3\n\
+ strh r1, [r0]\n\
+ adds r0, r2, 0x1\n\
+ lsls r0, 16\n\
+ lsrs r2, r0, 16\n\
+ cmp r2, 0x4\n\
+ bls _0814661A\n\
+ ldrb r0, [r4, 0x15]\n\
+ cmp r0, 0\n\
+ beq _08146642\n\
+ movs r0, 0x30\n\
+ bl sub_80A7E5C\n\
+ ldr r1, _08146698 @ =gUnknown_0203932E\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ strh r0, [r1]\n\
+_08146642:\n\
+ ldrb r0, [r4, 0x16]\n\
+ cmp r0, 0\n\
+ beq _08146656\n\
+ movs r0, 0x58\n\
+ bl sub_80A7E5C\n\
+ ldr r1, _08146698 @ =gUnknown_0203932E\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ strh r0, [r1, 0x2]\n\
+_08146656:\n\
+ ldrb r0, [r4, 0x17]\n\
+ cmp r0, 0\n\
+ beq _0814666A\n\
+ movs r0, 0x80\n\
+ bl sub_80A7E5C\n\
+ ldr r1, _08146698 @ =gUnknown_0203932E\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ strh r0, [r1, 0x4]\n\
+_0814666A:\n\
+ ldrb r0, [r4, 0x18]\n\
+ cmp r0, 0\n\
+ beq _0814667E\n\
+ movs r0, 0xA8\n\
+ bl sub_80A7E5C\n\
+ ldr r1, _08146698 @ =gUnknown_0203932E\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ strh r0, [r1, 0x6]\n\
+_0814667E:\n\
+ ldrb r0, [r4, 0x19]\n\
+ cmp r0, 0\n\
+ beq _08146692\n\
+ movs r0, 0xD0\n\
+ bl sub_80A7E5C\n\
+ ldr r1, _08146698 @ =gUnknown_0203932E\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ strh r0, [r1, 0x8]\n\
+_08146692:\n\
+ pop {r4,r5}\n\
+ pop {r0}\n\
+ bx r0\n\
+ .align 2, 0\n\
+_08146698: .4byte gUnknown_0203932E\n\
+_0814669C: .4byte 0x0000ffff\n\
+ .syntax divided\n");
+}
+#endif
+
+
+void sub_81466A0(void) {
+ u16 i;
+
+ for (i = 0; i < 5; i++) {
+ if (gUnknown_0203932E.circles[i] != -1) {
+ DestroySprite(&gSprites[gUnknown_0203932E.circles[i]]);
+ gUnknown_0203932E.circles[i] = -1;
+ }
+ }
+}
+
+
+__attribute__((naked))
+static void sub_81466E8(u8 taskId, s32 direction) {
+ asm(".syntax unified\n\
+ push {r4-r7,lr}\n\
+ mov r7, r8\n\
+ push {r7}\n\
+ lsls r0, 24\n\
+ lsrs r7, r0, 24\n\
+ lsls r1, 24\n\
+ lsrs r2, r1, 24\n\
+ lsls r0, r7, 2\n\
+ adds r0, r7\n\
+ lsls r0, 3\n\
+ ldr r1, _08146748 @ =gTasks + 0x8\n\
+ adds r6, r0, r1\n\
+ ldr r4, _0814674C @ =gUnknown_03005D10\n\
+ movs r0, 0xC\n\
+ adds r0, r4\n\
+ mov r8, r0\n\
+ ldrb r1, [r0, 0x1]\n\
+ ldrb r0, [r4, 0xC]\n\
+ adds r1, r0\n\
+ cmp r1, 0\n\
+ bne _08146718\n\
+ lsls r0, r2, 24\n\
+ cmp r0, 0\n\
+ blt _0814678C\n\
+_08146718:\n\
+ adds r0, r1, 0x1\n\
+ lsls r5, r2, 24\n\
+ mov r1, r8\n\
+ ldrb r1, [r1, 0x2]\n\
+ cmp r0, r1\n\
+ bne _08146728\n\
+ cmp r5, 0\n\
+ bgt _0814678C\n\
+_08146728:\n\
+ movs r0, 0x5\n\
+ bl PlaySE\n\
+ mov r2, r8\n\
+ ldrb r3, [r2, 0x1]\n\
+ ldrb r4, [r4, 0xC]\n\
+ mov r12, r4\n\
+ adds r0, r3, r4\n\
+ asrs r2, r5, 24\n\
+ adds r1, r0, r2\n\
+ cmp r1, 0\n\
+ bge _08146750\n\
+ negs r0, r0\n\
+ strh r0, [r6, 0x2]\n\
+ b _08146766\n\
+ .align 2, 0\n\
+_08146748: .4byte gTasks + 0x8\n\
+_0814674C: .4byte gUnknown_03005D10\n\
+_08146750:\n\
+ mov r4, r8\n\
+ ldrb r0, [r4, 0x2]\n\
+ cmp r1, r0\n\
+ blt _08146764\n\
+ subs r0, r3\n\
+ mov r1, r12\n\
+ subs r0, r1\n\
+ subs r0, 0x1\n\
+ strh r0, [r6, 0x2]\n\
+ b _08146766\n\
+_08146764:\n\
+ strh r2, [r6, 0x2]\n\
+_08146766:\n\
+ ldr r0, _08146780 @ =gTasks\n\
+ lsls r1, r7, 2\n\
+ adds r1, r7\n\
+ lsls r1, 3\n\
+ adds r1, r0\n\
+ ldr r0, _08146784 @ =sub_8146798\n\
+ str r0, [r1]\n\
+ cmp r5, 0\n\
+ bge _08146788\n\
+ movs r2, 0x10\n\
+ negs r2, r2\n\
+ adds r0, r2, 0\n\
+ b _0814678A\n\
+ .align 2, 0\n\
+_08146780: .4byte gTasks\n\
+_08146784: .4byte sub_8146798\n\
+_08146788:\n\
+ movs r0, 0x10\n\
+_0814678A:\n\
+ strh r0, [r6]\n\
+_0814678C:\n\
+ pop {r3}\n\
+ mov r8, r3\n\
+ pop {r4-r7}\n\
+ pop {r0}\n\
+ bx r0\n\
+ .syntax divided\n");
+}
+
+__attribute__((naked))
+void sub_8146798(u8 berry) {
+ asm(".syntax unified\n\
+ push {r4,r5,lr}\n\
+ lsls r0, 24\n\
+ lsrs r4, r0, 24\n\
+ lsls r0, r4, 2\n\
+ adds r0, r4\n\
+ lsls r0, 3\n\
+ ldr r1, _08146800 @ =gTasks + 0x8\n\
+ adds r0, r1\n\
+ ldr r2, _08146804 @ =gUnknown_030041B4\n\
+ ldrh r1, [r0]\n\
+ ldrh r5, [r2]\n\
+ adds r3, r1, r5\n\
+ movs r1, 0xFF\n\
+ ands r3, r1\n\
+ strh r3, [r2]\n\
+ movs r1, 0\n\
+ ldrsh r0, [r0, r1]\n\
+ cmp r0, 0\n\
+ ble _081467C2\n\
+ cmp r3, 0x90\n\
+ beq _081467CA\n\
+_081467C2:\n\
+ cmp r0, 0\n\
+ bge _081467E0\n\
+ cmp r3, 0x70\n\
+ bne _081467E0\n\
+_081467CA:\n\
+ ldr r0, _08146808 @ =gTasks\n\
+ lsls r1, r4, 2\n\
+ adds r1, r4\n\
+ lsls r1, 3\n\
+ adds r1, r0\n\
+ movs r0, 0xA\n\
+ ldrsb r0, [r1, r0]\n\
+ bl sub_8146810\n\
+ bl sub_81468BC\n\
+_081467E0:\n\
+ ldr r0, _08146804 @ =gUnknown_030041B4\n\
+ ldrh r2, [r0]\n\
+ cmp r2, 0\n\
+ bne _081467FA\n\
+ ldr r0, _08146808 @ =gTasks\n\
+ lsls r1, r4, 2\n\
+ adds r1, r4\n\
+ lsls r1, 3\n\
+ adds r1, r0\n\
+ strh r2, [r1, 0x8]\n\
+ strh r2, [r1, 0xA]\n\
+ ldr r0, _0814680C @ =sub_8146480\n\
+ str r0, [r1]\n\
+_081467FA:\n\
+ pop {r4,r5}\n\
+ pop {r0}\n\
+ bx r0\n\
+ .align 2, 0\n\
+_08146800: .4byte gTasks + 0x8\n\
+_08146804: .4byte gUnknown_030041B4\n\
+_08146808: .4byte gTasks\n\
+_0814680C: .4byte sub_8146480\n\
+ .syntax divided\n");
+}
+
+__attribute__((naked))
+void sub_8146810(u8 berry) {
+ asm(".syntax unified\n\
+ push {r4-r6,lr}\n\
+ lsls r0, 24\n\
+ lsrs r3, r0, 24\n\
+ adds r4, r3, 0\n\
+ lsls r0, r3, 24\n\
+ asrs r1, r0, 24\n\
+ cmp r1, 0\n\
+ ble _08146848\n\
+ ldr r0, _08146840 @ =gUnknown_03005D10\n\
+ adds r4, r0, 0\n\
+ adds r4, 0xC\n\
+ ldrb r2, [r0, 0xC]\n\
+ adds r1, r2, r1\n\
+ adds r6, r0, 0\n\
+ cmp r1, 0x7\n\
+ ble _08146844\n\
+ adds r0, r3, 0\n\
+ adds r0, 0xF9\n\
+ adds r0, r2, r0\n\
+ ldrb r1, [r4, 0x1]\n\
+ adds r0, r1\n\
+ strb r0, [r4, 0x1]\n\
+ movs r0, 0x7\n\
+ b _0814686E\n\
+ .align 2, 0\n\
+_08146840: .4byte gUnknown_03005D10\n\
+_08146844:\n\
+ adds r0, r2, r3\n\
+ b _0814686E\n\
+_08146848:\n\
+ ldr r0, _08146868 @ =gUnknown_03005D10\n\
+ adds r5, r0, 0\n\
+ adds r5, 0xC\n\
+ ldrb r2, [r0, 0xC]\n\
+ adds r1, r2, r1\n\
+ adds r6, r0, 0\n\
+ cmp r1, 0\n\
+ bge _0814686C\n\
+ adds r0, r2, r3\n\
+ ldrb r1, [r5, 0x1]\n\
+ adds r0, r1\n\
+ movs r1, 0\n\
+ strb r0, [r5, 0x1]\n\
+ strb r1, [r6, 0xC]\n\
+ b _08146870\n\
+ .align 2, 0\n\
+_08146868: .4byte gUnknown_03005D10\n\
+_0814686C:\n\
+ adds r0, r2, r4\n\
+_0814686E:\n\
+ strb r0, [r6, 0xC]\n\
+_08146870:\n\
+ ldr r2, _081468AC @ =gScriptItemId\n\
+ movs r0, 0x3\n\
+ lsls r0, 2\n\
+ adds r0, r6\n\
+ ldrb r1, [r0, 0x1]\n\
+ ldrb r0, [r0]\n\
+ adds r1, r0\n\
+ ldr r0, _081468B0 @ =gUnknown_03005D24\n\
+ ldr r0, [r0]\n\
+ lsls r1, 2\n\
+ adds r1, r0\n\
+ ldrh r0, [r1]\n\
+ strh r0, [r2]\n\
+ ldr r0, _081468B4 @ =gUnknown_0203932C\n\
+ ldrb r1, [r0]\n\
+ lsls r0, r1, 4\n\
+ adds r0, r1\n\
+ lsls r0, 2\n\
+ ldr r1, _081468B8 @ =gSprites\n\
+ adds r0, r1\n\
+ bl DestroySprite\n\
+ bl sub_81466A0\n\
+ bl sub_80A7DD4\n\
+ pop {r4-r6}\n\
+ pop {r0}\n\
+ bx r0\n\
+ .align 2, 0\n\
+_081468AC: .4byte gScriptItemId\n\
+_081468B0: .4byte gUnknown_03005D24\n\
+_081468B4: .4byte gUnknown_0203932C\n\
+_081468B8: .4byte gSprites\n\
+ .syntax divided\n");
+}
+
+void sub_81468BC(void) {
+ MenuZeroFillWindowRect(0, 4, 29, 19);
+ sub_81464E4();
+
+ // center of berry sprite
+ gUnknown_0203932C = sub_80A7D8C(gScriptItemId + OFFSET_7B, 56, 64);
+
+ sub_8146600(gScriptItemId + OFFSET_7B);
+}
diff --git a/src/blend_palette.c b/src/blend_palette.c
index c9503388f..843c50ac1 100644
--- a/src/blend_palette.c
+++ b/src/blend_palette.c
@@ -1,4 +1,5 @@
#include "global.h"
+#include "blend_palette.h"
#include "palette.h"
void BlendPalette(u16 palOffset, u16 numEntries, u8 coeff, u16 blendColor)
diff --git a/src/calculate_base_damage.c b/src/calculate_base_damage.c
new file mode 100644
index 000000000..186fa062c
--- /dev/null
+++ b/src/calculate_base_damage.c
@@ -0,0 +1,1484 @@
+#include "global.h"
+#include "text.h"
+#include "string_util.h"
+#include "pokemon.h"
+#include "species.h"
+#include "main.h"
+#include "sprite.h"
+#include "berry.h"
+#include "item.h"
+#include "abilities.h"
+#include "hold_effects.h"
+#include "flag.h"
+
+extern u8 gPlayerPartyCount;
+extern struct Pokemon gPlayerParty[6];
+extern u8 gEnemyPartyCount;
+extern struct Pokemon gEnemyParty[6];
+
+extern u16 unk_20160BC[];
+extern struct SecretBaseRecord gSecretBaseRecord;
+extern u32 dword_2017100[];
+extern u16 gUnknown_020239F8;
+extern struct BattlePokemon gBattleMons[4];
+extern u16 gUnknown_02024BE6;
+extern u8 byte_2024C06;
+extern u8 gCritMultiplier;
+extern u16 gBattleWeather;
+extern struct BattleEnigmaBerry gEnigmaBerries[];
+extern u16 gBattleMovePower;
+extern struct SpriteTemplate gUnknown_02024E8C;
+extern u16 gTrainerBattleOpponent;
+extern struct PokemonStorage gPokemonStorage;
+
+extern u8 gBadEggNickname[];
+extern u8 gEggNickname[];
+extern u32 gBitTable[];
+extern struct BaseStats gBaseStats[];
+extern u8 gSpeciesNames[][11];
+extern struct BattleMove gBattleMoves[];
+extern struct SpriteTemplate gSpriteTemplate_8208288[];
+extern union AmimCmd *gSpriteAnimTable_81E7C64[];
+extern union AnimCmd **gUnknown_081EC2A4[];
+extern union AnimCmd **gUnknown_081ECACC[];
+extern u8 gTrainerClassToPicIndex[];
+extern u8 gTrainerClassToNameIndex[];
+extern u8 gSecretBaseTrainerClasses[];
+extern u8 gUnknown_08208238[];
+extern u8 gUnknown_0820823C[];
+extern u8 gStatStageRatios[];
+extern u8 gHoldEffectToType[][2];
+
+extern u8 battle_side_get_owner(u8);
+extern u8 sub_8018324(u8, u8, u8, u8, u16);
+extern u8 sub_803C348(u8);
+
+#define APPLY_STAT_MOD(var, mon, stat, statIndex) \
+{ \
+ (var) = (stat) * (gStatStageRatios)[(mon)->statStages[(statIndex)] * 2]; \
+ (var) /= (gStatStageRatios + 1)[(mon)->statStages[(statIndex)] * 2]; \
+}
+
+#ifdef NONMATCHING
+s32 CalculateBaseDamage(struct BattlePokemon *attacker, struct BattlePokemon *defender, u32 move, u8 a4, u16 powerOverride, u8 typeOverride, u8 a7, u8 a8)
+{
+ s32 i;
+ s32 damage = 0;
+ u8 type;
+ u16 attack, defense;
+ u16 spAttack, spDefense;
+ u8 defenderHoldEffect;
+ u8 defenderHoldEffectParam;
+ u8 attackerHoldEffect;
+ u8 attackerHoldEffectParam;
+ s32 a, b;
+
+ if (!powerOverride)
+ gBattleMovePower = gBattleMoves[move].power;
+ else
+ gBattleMovePower = powerOverride;
+
+ if (!typeOverride)
+ type = gBattleMoves[move].type;
+ else
+ type = typeOverride & 0x3F;
+
+ attack = attacker->attack;
+ defense = defender->defense;
+ spAttack = attacker->spAttack;
+ spDefense = defender->spDefense;
+
+ if (attacker->item == 175)
+ {
+ attackerHoldEffect = gEnigmaBerries[a7].holdEffect;
+ attackerHoldEffectParam = gEnigmaBerries[a7].holdEffectParam;
+ }
+ else
+ {
+ attackerHoldEffect = ItemId_GetHoldEffect(attacker->item);
+ attackerHoldEffectParam = ItemId_GetHoldEffectParam(attacker->item);
+ }
+
+ if (defender->item == 175)
+ {
+ defenderHoldEffect = gEnigmaBerries[a8].holdEffect;
+ defenderHoldEffectParam = gEnigmaBerries[a8].holdEffectParam;
+ }
+ else
+ {
+ defenderHoldEffect = ItemId_GetHoldEffect(defender->item);
+ defenderHoldEffectParam = ItemId_GetHoldEffectParam(defender->item);
+ }
+
+ if (attacker->ability == ABILITY_HUGE_POWER || attacker->ability == ABILITY_PURE_POWER)
+ attack *= 2;
+
+ if (!(gUnknown_020239F8 & 0x902))
+ {
+ if ((gUnknown_020239F8 & 8)
+ && gTrainerBattleOpponent != 1024
+ && FlagGet(BADGE01_GET)
+ && !battle_side_get_owner(a7))
+ attack = (110 * attack) / 100;
+
+ if (!(gUnknown_020239F8 & 0x902))
+ {
+ if ((gUnknown_020239F8 & 8)
+ && gTrainerBattleOpponent != 1024
+ && FlagGet(BADGE05_GET)
+ && !battle_side_get_owner(a8))
+ defense = (110 * defense) / 100;
+
+ if (!(gUnknown_020239F8 & 0x902))
+ {
+ if ((gUnknown_020239F8 & 8)
+ && gTrainerBattleOpponent != 1024
+ && FlagGet(BADGE07_GET)
+ && !battle_side_get_owner(a7))
+ spAttack = (110 * spAttack) / 100;
+
+ if (!(gUnknown_020239F8 & 0x902))
+ {
+ if ((gUnknown_020239F8 & 8)
+ && gTrainerBattleOpponent != 1024
+ && FlagGet(BADGE07_GET)
+ && !battle_side_get_owner(a8))
+ spDefense = (110 * spDefense) / 100;
+ }
+ }
+ }
+ }
+
+ for (i = 0; i < 17; i++)
+ {
+ if (attackerHoldEffect == gHoldEffectToType[i][0]
+ && type == gHoldEffectToType[i][1])
+ {
+ if (type <= 8)
+ attack = (attack * (attackerHoldEffectParam + 100)) / 100;
+ else
+ spAttack = (spAttack * (attackerHoldEffectParam + 100)) / 100;
+ break;
+ }
+ }
+
+ if (attackerHoldEffect == HOLD_EFFECT_CHOICE_BAND)
+ attack = (150 * attack) / 100;
+ if (attackerHoldEffect == HOLD_EFFECT_SOUL_DEW && !(gUnknown_020239F8 & 0x100) && (attacker->species == SPECIES_LATIAS || attacker->species == SPECIES_LATIOS))
+ spAttack = (150 * spAttack) / 100;
+ if (defenderHoldEffect == HOLD_EFFECT_SOUL_DEW && !(gUnknown_020239F8 & 0x100) && (defender->species == SPECIES_LATIAS || defender->species == SPECIES_LATIOS))
+ spDefense = (150 * spDefense) / 100;
+ if (attackerHoldEffect == HOLD_EFFECT_DEEP_SEA_TOOTH && attacker->species == SPECIES_CLAMPERL)
+ spAttack *= 2;
+ if (defenderHoldEffect == HOLD_EFFECT_DEEP_SEA_SCALE && defender->species == SPECIES_CLAMPERL)
+ spDefense *= 2;
+ if (attackerHoldEffect == HOLD_EFFECT_LIGHT_BALL && attacker->species == SPECIES_PIKACHU)
+ spAttack *= 2;
+ if (defenderHoldEffect == HOLD_EFFECT_METAL_POWDER && defender->species == SPECIES_DITTO)
+ defense *= 2;
+ if (attackerHoldEffect == HOLD_EFFECT_THICK_CLUB && (attacker->species == SPECIES_CUBONE || attacker->species == SPECIES_MAROWAK))
+ attack *= 2;
+ if (defender->ability == ABILITY_THICK_FAT && (type == TYPE_FIRE || type == TYPE_ICE))
+ spAttack /= 2;
+ if (attacker->ability == ABILITY_HUSTLE)
+ attack = (150 * attack) / 100;
+ if (attacker->ability == ABILITY_PLUS && sub_8018324(0xE, 0, ABILITY_MINUS, 0, 0))
+ spAttack = (150 * spAttack) / 100;
+ if (attacker->ability == ABILITY_MINUS && sub_8018324(0xE, 0, ABILITY_PLUS, 0, 0))
+ spAttack = (150 * spAttack) / 100;
+ if (attacker->ability == ABILITY_GUTS && attacker->status1)
+ attack = (150 * attack) / 100;
+ if (defender->ability == ABILITY_MARVEL_SCALE && defender->status1)
+ defense = (150 * defense) / 100;
+ if (type == TYPE_ELECTRIC && sub_8018324(0xE, 0, 0, 0xFD, 0))
+ gBattleMovePower /= 2;
+ if (type == TYPE_FIRE && sub_8018324(0xE, 0, 0, 0xFE, 0))
+ gBattleMovePower /= 2;
+ if (type == TYPE_GRASS && attacker->ability == ABILITY_OVERGROW && attacker->hp <= (attacker->maxHP / 3))
+ gBattleMovePower = (150 * gBattleMovePower) / 100;
+ if (type == TYPE_FIRE && attacker->ability == ABILITY_BLAZE && attacker->hp <= (attacker->maxHP / 3))
+ gBattleMovePower = (150 * gBattleMovePower) / 100;
+ if (type == TYPE_WATER && attacker->ability == ABILITY_TORRENT && attacker->hp <= (attacker->maxHP / 3))
+ gBattleMovePower = (150 * gBattleMovePower) / 100;
+ if (type == TYPE_BUG && attacker->ability == ABILITY_SWARM && attacker->hp <= (attacker->maxHP / 3))
+ gBattleMovePower = (150 * gBattleMovePower) / 100;
+ if (gBattleMoves[gUnknown_02024BE6].effect == 7)
+ defense /= 2;
+
+ if (type <= 8)
+ {
+ if (gCritMultiplier == 2)
+ {
+ if (attacker->statStages[1] > 6)
+ APPLY_STAT_MOD(a, attacker, attack, 1)
+ else
+ a = attack;
+ }
+ else
+ APPLY_STAT_MOD(a, attacker, attack, 1)
+
+ a = a * gBattleMovePower * (2 * attacker->level / 5 + 2);
+
+ if (gCritMultiplier == 2)
+ {
+ if (defender->statStages[2] < 6)
+ APPLY_STAT_MOD(b, defender, defense, 2)
+ else
+ b = defense;
+ }
+ else
+ APPLY_STAT_MOD(b, defender, defense, 2)
+
+ damage = (a / b) / 50;
+
+ if ((attacker->status1 & 0x10) && attacker->ability != ABILITY_GUTS)
+ damage /= 2;
+
+ if ((a4 & 1) && gCritMultiplier == 1)
+ {
+ if ((gUnknown_020239F8 & 1) && sub_803C348(2) == 2)
+ damage = 2 * (damage / 3);
+ else
+ damage /= 2;
+ }
+
+ if ((gUnknown_020239F8 & 1) && gBattleMoves[move].target == 8 && sub_803C348(2) == 2)
+ damage /= 2;
+
+ if (damage == 0)
+ damage = 1;
+ }
+
+ if (type == 9)
+ damage = 0;
+
+ if (type > 9)
+ {
+ if (gCritMultiplier == 2)
+ {
+ if (attacker->statStages[4] > 6)
+ APPLY_STAT_MOD(a, attacker, spAttack, 4)
+ else
+ a = spAttack;
+ }
+ else
+ APPLY_STAT_MOD(a, attacker, spAttack, 4)
+
+ a = a * gBattleMovePower * (2 * attacker->level / 5 + 2);
+
+ if (gCritMultiplier == 2)
+ {
+ if (defender->statStages[5] < 6)
+ APPLY_STAT_MOD(b, defender, spDefense, 5)
+ else
+ b = spDefense;
+ }
+ else
+ APPLY_STAT_MOD(b, defender, spDefense, 5)
+
+ damage = (a / b) / 50;
+
+ if ((a4 & 2) && gCritMultiplier == 1)
+ {
+ if ((gUnknown_020239F8 & 1) && sub_803C348(2) == 2)
+ damage = 2 * (damage / 3);
+ else
+ damage /= 2;
+ }
+
+ if ((gUnknown_020239F8 & 1) && gBattleMoves[move].target == 8 && sub_803C348(2) == 2)
+ damage /= 2;
+
+ if (!sub_8018324(0xE, 0, ABILITY_CLOUD_NINE, 0, 0) && !sub_8018324(0xE, 0, ABILITY_AIR_LOCK, 0, 0))
+ {
+ if (gBattleWeather & 1)
+ {
+ if (type == TYPE_FIRE)
+ {
+ damage /= 2;
+ }
+ else if (type == TYPE_WATER)
+ {
+ damage = (15 * damage) / 10;
+ }
+ }
+ if ((gBattleWeather & 0x9F) && gUnknown_02024BE6 == 76)
+ damage /= 2;
+ if (gBattleWeather & 0x60)
+ {
+ if (type == TYPE_FIRE)
+ {
+ damage = (15 * damage) / 10;
+ }
+ else if (type == TYPE_WATER)
+ {
+ damage /= 2;
+ }
+ }
+ }
+ if ((dword_2017100[a7] & 1) && type == TYPE_FIRE)
+ damage = (15 * damage) / 10;
+ }
+
+ return damage + 2;
+}
+#else
+__attribute__((naked))
+s32 CalculateBaseDamage(struct BattlePokemon *attacker, struct BattlePokemon *defender, u32 move, u8 a4, u16 powerOverride, u8 typeOverride, u8 a7, u8 a8)
+{
+ asm(".syntax unified\n\
+ push {r4-r7,lr}\n\
+ mov r7, r10\n\
+ mov r6, r9\n\
+ mov r5, r8\n\
+ push {r5-r7}\n\
+ sub sp, 0x2C\n\
+ adds r7, r0, 0\n\
+ str r1, [sp, 0x4]\n\
+ str r2, [sp, 0x8]\n\
+ ldr r0, [sp, 0x4C]\n\
+ ldr r1, [sp, 0x50]\n\
+ ldr r2, [sp, 0x54]\n\
+ ldr r4, [sp, 0x58]\n\
+ lsls r3, 16\n\
+ lsrs r3, 16\n\
+ str r3, [sp, 0xC]\n\
+ lsls r0, 16\n\
+ lsrs r3, r0, 16\n\
+ lsls r1, 24\n\
+ lsrs r6, r1, 24\n\
+ lsls r2, 24\n\
+ lsrs r2, 24\n\
+ str r2, [sp, 0x10]\n\
+ lsls r4, 24\n\
+ lsrs r4, 24\n\
+ movs r5, 0\n\
+ cmp r3, 0\n\
+ bne _0803BA80\n\
+ ldr r2, _0803BA78 @ =gBattleMovePower\n\
+ ldr r1, _0803BA7C @ =gBattleMoves\n\
+ ldr r3, [sp, 0x8]\n\
+ lsls r0, r3, 1\n\
+ adds r0, r3\n\
+ lsls r0, 2\n\
+ adds r0, r1\n\
+ ldrb r0, [r0, 0x1]\n\
+ strh r0, [r2]\n\
+ b _0803BA84\n\
+ .align 2, 0\n\
+_0803BA78: .4byte gBattleMovePower\n\
+_0803BA7C: .4byte gBattleMoves\n\
+_0803BA80:\n\
+ ldr r0, _0803BA9C @ =gBattleMovePower\n\
+ strh r3, [r0]\n\
+_0803BA84:\n\
+ cmp r6, 0\n\
+ bne _0803BAA4\n\
+ ldr r1, _0803BAA0 @ =gBattleMoves\n\
+ ldr r6, [sp, 0x8]\n\
+ lsls r0, r6, 1\n\
+ adds r0, r6\n\
+ lsls r0, 2\n\
+ adds r0, r1\n\
+ ldrb r0, [r0, 0x2]\n\
+ mov r9, r0\n\
+ b _0803BAAE\n\
+ .align 2, 0\n\
+_0803BA9C: .4byte gBattleMovePower\n\
+_0803BAA0: .4byte gBattleMoves\n\
+_0803BAA4:\n\
+ movs r0, 0x3F\n\
+ mov r9, r0\n\
+ mov r1, r9\n\
+ ands r1, r6\n\
+ mov r9, r1\n\
+_0803BAAE:\n\
+ ldrh r6, [r7, 0x2]\n\
+ ldr r2, [sp, 0x4]\n\
+ ldrh r2, [r2, 0x4]\n\
+ str r2, [sp, 0x14]\n\
+ ldrh r3, [r7, 0x8]\n\
+ mov r8, r3\n\
+ ldr r0, [sp, 0x4]\n\
+ ldrh r0, [r0, 0xA]\n\
+ str r0, [sp, 0x18]\n\
+ ldrh r0, [r7, 0x2E]\n\
+ cmp r0, 0xAF\n\
+ bne _0803BAE0\n\
+ ldr r1, _0803BADC @ =gEnigmaBerries\n\
+ ldr r2, [sp, 0x10]\n\
+ lsls r0, r2, 3\n\
+ subs r0, r2\n\
+ lsls r0, 2\n\
+ adds r0, r1\n\
+ ldrb r3, [r0, 0x7]\n\
+ mov r10, r3\n\
+ ldrb r0, [r0, 0x1A]\n\
+ b _0803BAF6\n\
+ .align 2, 0\n\
+_0803BADC: .4byte gEnigmaBerries\n\
+_0803BAE0:\n\
+ ldrh r0, [r7, 0x2E]\n\
+ bl ItemId_GetHoldEffect\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ mov r10, r0\n\
+ ldrh r0, [r7, 0x2E]\n\
+ bl ItemId_GetHoldEffectParam\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+_0803BAF6:\n\
+ str r0, [sp, 0x20]\n\
+ ldr r1, [sp, 0x4]\n\
+ ldrh r0, [r1, 0x2E]\n\
+ cmp r0, 0xAF\n\
+ bne _0803BB26\n\
+ ldr r1, _0803BB10 @ =gEnigmaBerries\n\
+ lsls r0, r4, 3\n\
+ subs r0, r4\n\
+ lsls r0, 2\n\
+ adds r0, r1\n\
+ ldrb r0, [r0, 0x7]\n\
+ str r0, [sp, 0x1C]\n\
+ b _0803BB3C\n\
+ .align 2, 0\n\
+_0803BB10: .4byte gEnigmaBerries\n\
+_0803BB14:\n\
+ ldr r0, [sp, 0x20]\n\
+ adds r0, 0x64\n\
+ muls r0, r6\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r6, r0, 16\n\
+ b _0803BCDC\n\
+_0803BB26:\n\
+ ldr r2, [sp, 0x4]\n\
+ ldrh r0, [r2, 0x2E]\n\
+ bl ItemId_GetHoldEffect\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ str r0, [sp, 0x1C]\n\
+ ldr r3, [sp, 0x4]\n\
+ ldrh r0, [r3, 0x2E]\n\
+ bl ItemId_GetHoldEffectParam\n\
+_0803BB3C:\n\
+ adds r0, r7, 0\n\
+ adds r0, 0x20\n\
+ ldrb r1, [r0]\n\
+ str r0, [sp, 0x24]\n\
+ cmp r1, 0x25\n\
+ beq _0803BB4C\n\
+ cmp r1, 0x4A\n\
+ bne _0803BB50\n\
+_0803BB4C:\n\
+ lsls r0, r6, 17\n\
+ lsrs r6, r0, 16\n\
+_0803BB50:\n\
+ ldr r0, _0803BCB8 @ =gUnknown_020239F8\n\
+ ldrh r1, [r0]\n\
+ ldr r0, _0803BCBC @ =0x00000902\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803BB5E\n\
+ b _0803BC78\n\
+_0803BB5E:\n\
+ movs r0, 0x8\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803BB98\n\
+ ldr r0, _0803BCC0 @ =gTrainerBattleOpponent\n\
+ ldrh r1, [r0]\n\
+ movs r0, 0x80\n\
+ lsls r0, 3\n\
+ cmp r1, r0\n\
+ beq _0803BB98\n\
+ ldr r0, _0803BCC4 @ =0x00000807\n\
+ bl FlagGet\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ beq _0803BB98\n\
+ ldr r0, [sp, 0x10]\n\
+ bl battle_side_get_owner\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ bne _0803BB98\n\
+ movs r0, 0x6E\n\
+ muls r0, r6\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r6, r0, 16\n\
+_0803BB98:\n\
+ ldr r0, _0803BCB8 @ =gUnknown_020239F8\n\
+ ldrh r1, [r0]\n\
+ ldr r0, _0803BCBC @ =0x00000902\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ bne _0803BC78\n\
+ movs r0, 0x8\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803BBE2\n\
+ ldr r0, _0803BCC0 @ =gTrainerBattleOpponent\n\
+ ldrh r1, [r0]\n\
+ movs r0, 0x80\n\
+ lsls r0, 3\n\
+ cmp r1, r0\n\
+ beq _0803BBE2\n\
+ ldr r0, _0803BCC8 @ =0x0000080b\n\
+ bl FlagGet\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ beq _0803BBE2\n\
+ adds r0, r4, 0\n\
+ bl battle_side_get_owner\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ bne _0803BBE2\n\
+ movs r0, 0x6E\n\
+ ldr r1, [sp, 0x14]\n\
+ muls r0, r1\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ str r0, [sp, 0x14]\n\
+_0803BBE2:\n\
+ ldr r0, _0803BCB8 @ =gUnknown_020239F8\n\
+ ldrh r1, [r0]\n\
+ ldr r0, _0803BCBC @ =0x00000902\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ bne _0803BC78\n\
+ movs r0, 0x8\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803BC2E\n\
+ ldr r0, _0803BCC0 @ =gTrainerBattleOpponent\n\
+ ldrh r1, [r0]\n\
+ movs r0, 0x80\n\
+ lsls r0, 3\n\
+ cmp r1, r0\n\
+ beq _0803BC2E\n\
+ ldr r0, _0803BCCC @ =0x0000080d\n\
+ bl FlagGet\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ beq _0803BC2E\n\
+ ldr r0, [sp, 0x10]\n\
+ bl battle_side_get_owner\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ bne _0803BC2E\n\
+ movs r0, 0x6E\n\
+ mov r2, r8\n\
+ muls r2, r0\n\
+ adds r0, r2, 0\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ mov r8, r0\n\
+_0803BC2E:\n\
+ ldr r0, _0803BCB8 @ =gUnknown_020239F8\n\
+ ldrh r1, [r0]\n\
+ ldr r0, _0803BCBC @ =0x00000902\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ bne _0803BC78\n\
+ movs r0, 0x8\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803BC78\n\
+ ldr r0, _0803BCC0 @ =gTrainerBattleOpponent\n\
+ ldrh r1, [r0]\n\
+ movs r0, 0x80\n\
+ lsls r0, 3\n\
+ cmp r1, r0\n\
+ beq _0803BC78\n\
+ ldr r0, _0803BCCC @ =0x0000080d\n\
+ bl FlagGet\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ beq _0803BC78\n\
+ adds r0, r4, 0\n\
+ bl battle_side_get_owner\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ bne _0803BC78\n\
+ movs r0, 0x6E\n\
+ ldr r3, [sp, 0x18]\n\
+ muls r0, r3\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ str r0, [sp, 0x18]\n\
+_0803BC78:\n\
+ movs r2, 0\n\
+ ldr r4, _0803BCD0 @ =gHoldEffectToType\n\
+ ldr r0, [sp, 0x4]\n\
+ adds r0, 0x20\n\
+ str r0, [sp, 0x28]\n\
+ adds r3, r4, 0\n\
+_0803BC84:\n\
+ lsls r1, r2, 1\n\
+ ldrb r0, [r3]\n\
+ cmp r10, r0\n\
+ bne _0803BCD4\n\
+ adds r0, r4, 0x1\n\
+ adds r0, r1, r0\n\
+ ldrb r0, [r0]\n\
+ cmp r9, r0\n\
+ bne _0803BCD4\n\
+ mov r1, r9\n\
+ cmp r1, 0x8\n\
+ bhi _0803BC9E\n\
+ b _0803BB14\n\
+_0803BC9E:\n\
+ ldr r0, [sp, 0x20]\n\
+ adds r0, 0x64\n\
+ mov r2, r8\n\
+ muls r2, r0\n\
+ adds r0, r2, 0\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ mov r8, r0\n\
+ b _0803BCDC\n\
+ .align 2, 0\n\
+_0803BCB8: .4byte gUnknown_020239F8\n\
+_0803BCBC: .4byte 0x00000902\n\
+_0803BCC0: .4byte gTrainerBattleOpponent\n\
+_0803BCC4: .4byte 0x00000807\n\
+_0803BCC8: .4byte 0x0000080b\n\
+_0803BCCC: .4byte 0x0000080d\n\
+_0803BCD0: .4byte gHoldEffectToType\n\
+_0803BCD4:\n\
+ adds r3, 0x2\n\
+ adds r2, 0x1\n\
+ cmp r2, 0x10\n\
+ bls _0803BC84\n\
+_0803BCDC:\n\
+ mov r3, r10\n\
+ cmp r3, 0x1D\n\
+ bne _0803BCF0\n\
+ movs r0, 0x96\n\
+ muls r0, r6\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r6, r0, 16\n\
+_0803BCF0:\n\
+ mov r0, r10\n\
+ cmp r0, 0x22\n\
+ bne _0803BD28\n\
+ ldr r0, _0803BFDC @ =gUnknown_020239F8\n\
+ ldrh r1, [r0]\n\
+ movs r0, 0x80\n\
+ lsls r0, 1\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ bne _0803BD28\n\
+ ldr r1, _0803BFE0 @ =0xfffffe69\n\
+ adds r0, r1, 0\n\
+ ldrh r2, [r7]\n\
+ adds r0, r2\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ cmp r0, 0x1\n\
+ bhi _0803BD28\n\
+ movs r0, 0x96\n\
+ mov r3, r8\n\
+ muls r3, r0\n\
+ adds r0, r3, 0\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ mov r8, r0\n\
+_0803BD28:\n\
+ ldr r0, [sp, 0x1C]\n\
+ cmp r0, 0x22\n\
+ bne _0803BD60\n\
+ ldr r0, _0803BFDC @ =gUnknown_020239F8\n\
+ ldrh r1, [r0]\n\
+ movs r0, 0x80\n\
+ lsls r0, 1\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ bne _0803BD60\n\
+ ldr r1, _0803BFE0 @ =0xfffffe69\n\
+ adds r0, r1, 0\n\
+ ldr r2, [sp, 0x4]\n\
+ ldrh r2, [r2]\n\
+ adds r0, r2\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ cmp r0, 0x1\n\
+ bhi _0803BD60\n\
+ movs r0, 0x96\n\
+ ldr r3, [sp, 0x18]\n\
+ muls r0, r3\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ str r0, [sp, 0x18]\n\
+_0803BD60:\n\
+ mov r0, r10\n\
+ cmp r0, 0x23\n\
+ bne _0803BD76\n\
+ ldrh r1, [r7]\n\
+ ldr r0, _0803BFE4 @ =0x00000175\n\
+ cmp r1, r0\n\
+ bne _0803BD76\n\
+ mov r1, r8\n\
+ lsls r0, r1, 17\n\
+ lsrs r0, 16\n\
+ mov r8, r0\n\
+_0803BD76:\n\
+ ldr r2, [sp, 0x1C]\n\
+ cmp r2, 0x24\n\
+ bne _0803BD8E\n\
+ ldr r3, [sp, 0x4]\n\
+ ldrh r1, [r3]\n\
+ ldr r0, _0803BFE4 @ =0x00000175\n\
+ cmp r1, r0\n\
+ bne _0803BD8E\n\
+ ldr r1, [sp, 0x18]\n\
+ lsls r0, r1, 17\n\
+ lsrs r0, 16\n\
+ str r0, [sp, 0x18]\n\
+_0803BD8E:\n\
+ mov r2, r10\n\
+ cmp r2, 0x2D\n\
+ bne _0803BDA2\n\
+ ldrh r0, [r7]\n\
+ cmp r0, 0x19\n\
+ bne _0803BDA2\n\
+ mov r3, r8\n\
+ lsls r0, r3, 17\n\
+ lsrs r0, 16\n\
+ mov r8, r0\n\
+_0803BDA2:\n\
+ ldr r0, [sp, 0x1C]\n\
+ cmp r0, 0x40\n\
+ bne _0803BDB8\n\
+ ldr r1, [sp, 0x4]\n\
+ ldrh r0, [r1]\n\
+ cmp r0, 0x84\n\
+ bne _0803BDB8\n\
+ ldr r2, [sp, 0x14]\n\
+ lsls r0, r2, 17\n\
+ lsrs r0, 16\n\
+ str r0, [sp, 0x14]\n\
+_0803BDB8:\n\
+ mov r3, r10\n\
+ cmp r3, 0x41\n\
+ bne _0803BDCE\n\
+ ldrh r0, [r7]\n\
+ subs r0, 0x68\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ cmp r0, 0x1\n\
+ bhi _0803BDCE\n\
+ lsls r0, r6, 17\n\
+ lsrs r6, r0, 16\n\
+_0803BDCE:\n\
+ ldr r1, [sp, 0x28]\n\
+ ldrb r0, [r1]\n\
+ cmp r0, 0x2F\n\
+ bne _0803BDE6\n\
+ mov r2, r9\n\
+ cmp r2, 0xA\n\
+ beq _0803BDE0\n\
+ cmp r2, 0xF\n\
+ bne _0803BDE6\n\
+_0803BDE0:\n\
+ mov r3, r8\n\
+ lsrs r3, 1\n\
+ mov r8, r3\n\
+_0803BDE6:\n\
+ ldr r0, [sp, 0x24]\n\
+ ldrb r4, [r0]\n\
+ cmp r4, 0x37\n\
+ bne _0803BDFC\n\
+ movs r0, 0x96\n\
+ muls r0, r6\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r6, r0, 16\n\
+_0803BDFC:\n\
+ cmp r4, 0x39\n\
+ bne _0803BE2A\n\
+ movs r0, 0\n\
+ str r0, [sp]\n\
+ movs r0, 0xE\n\
+ movs r1, 0\n\
+ movs r2, 0x3A\n\
+ movs r3, 0\n\
+ bl sub_8018324\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ beq _0803BE2A\n\
+ movs r0, 0x96\n\
+ mov r1, r8\n\
+ muls r1, r0\n\
+ adds r0, r1, 0\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ mov r8, r0\n\
+_0803BE2A:\n\
+ ldr r2, [sp, 0x24]\n\
+ ldrb r0, [r2]\n\
+ cmp r0, 0x3A\n\
+ bne _0803BE5C\n\
+ movs r0, 0\n\
+ str r0, [sp]\n\
+ movs r0, 0xE\n\
+ movs r1, 0\n\
+ movs r2, 0x39\n\
+ movs r3, 0\n\
+ bl sub_8018324\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ beq _0803BE5C\n\
+ movs r0, 0x96\n\
+ mov r3, r8\n\
+ muls r3, r0\n\
+ adds r0, r3, 0\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ mov r8, r0\n\
+_0803BE5C:\n\
+ ldr r1, [sp, 0x24]\n\
+ ldrb r0, [r1]\n\
+ cmp r0, 0x3E\n\
+ bne _0803BE78\n\
+ ldr r0, [r7, 0x4C]\n\
+ cmp r0, 0\n\
+ beq _0803BE78\n\
+ movs r0, 0x96\n\
+ muls r0, r6\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r6, r0, 16\n\
+_0803BE78:\n\
+ ldr r2, [sp, 0x28]\n\
+ ldrb r0, [r2]\n\
+ cmp r0, 0x3F\n\
+ bne _0803BE9A\n\
+ ldr r3, [sp, 0x4]\n\
+ ldr r0, [r3, 0x4C]\n\
+ cmp r0, 0\n\
+ beq _0803BE9A\n\
+ movs r0, 0x96\n\
+ ldr r1, [sp, 0x14]\n\
+ muls r0, r1\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ str r0, [sp, 0x14]\n\
+_0803BE9A:\n\
+ mov r2, r9\n\
+ cmp r2, 0xD\n\
+ bne _0803BEBE\n\
+ movs r0, 0\n\
+ str r0, [sp]\n\
+ movs r0, 0xE\n\
+ movs r1, 0\n\
+ movs r2, 0\n\
+ movs r3, 0xFD\n\
+ bl sub_8018324\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ beq _0803BEBE\n\
+ ldr r1, _0803BFE8 @ =gBattleMovePower\n\
+ ldrh r0, [r1]\n\
+ lsrs r0, 1\n\
+ strh r0, [r1]\n\
+_0803BEBE:\n\
+ mov r3, r9\n\
+ cmp r3, 0xA\n\
+ bne _0803BEE2\n\
+ movs r0, 0\n\
+ str r0, [sp]\n\
+ movs r0, 0xE\n\
+ movs r1, 0\n\
+ movs r2, 0\n\
+ movs r3, 0xFE\n\
+ bl sub_8018324\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ beq _0803BEE2\n\
+ ldr r1, _0803BFE8 @ =gBattleMovePower\n\
+ ldrh r0, [r1]\n\
+ lsrs r0, 1\n\
+ strh r0, [r1]\n\
+_0803BEE2:\n\
+ mov r0, r9\n\
+ cmp r0, 0xC\n\
+ bne _0803BF12\n\
+ ldr r1, [sp, 0x24]\n\
+ ldrb r0, [r1]\n\
+ cmp r0, 0x41\n\
+ bne _0803BF12\n\
+ ldrh r0, [r7, 0x2C]\n\
+ movs r1, 0x3\n\
+ bl __udivsi3\n\
+ ldrh r1, [r7, 0x28]\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ cmp r1, r0\n\
+ bhi _0803BF12\n\
+ ldr r4, _0803BFE8 @ =gBattleMovePower\n\
+ ldrh r1, [r4]\n\
+ movs r0, 0x96\n\
+ muls r0, r1\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ strh r0, [r4]\n\
+_0803BF12:\n\
+ mov r2, r9\n\
+ cmp r2, 0xA\n\
+ bne _0803BF42\n\
+ ldr r3, [sp, 0x24]\n\
+ ldrb r0, [r3]\n\
+ cmp r0, 0x42\n\
+ bne _0803BF42\n\
+ ldrh r0, [r7, 0x2C]\n\
+ movs r1, 0x3\n\
+ bl __udivsi3\n\
+ ldrh r1, [r7, 0x28]\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ cmp r1, r0\n\
+ bhi _0803BF42\n\
+ ldr r4, _0803BFE8 @ =gBattleMovePower\n\
+ ldrh r1, [r4]\n\
+ movs r0, 0x96\n\
+ muls r0, r1\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ strh r0, [r4]\n\
+_0803BF42:\n\
+ mov r0, r9\n\
+ cmp r0, 0xB\n\
+ bne _0803BF72\n\
+ ldr r1, [sp, 0x24]\n\
+ ldrb r0, [r1]\n\
+ cmp r0, 0x43\n\
+ bne _0803BF72\n\
+ ldrh r0, [r7, 0x2C]\n\
+ movs r1, 0x3\n\
+ bl __udivsi3\n\
+ ldrh r1, [r7, 0x28]\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ cmp r1, r0\n\
+ bhi _0803BF72\n\
+ ldr r4, _0803BFE8 @ =gBattleMovePower\n\
+ ldrh r1, [r4]\n\
+ movs r0, 0x96\n\
+ muls r0, r1\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ strh r0, [r4]\n\
+_0803BF72:\n\
+ mov r2, r9\n\
+ cmp r2, 0x6\n\
+ bne _0803BFA2\n\
+ ldr r3, [sp, 0x24]\n\
+ ldrb r0, [r3]\n\
+ cmp r0, 0x44\n\
+ bne _0803BFA2\n\
+ ldrh r0, [r7, 0x2C]\n\
+ movs r1, 0x3\n\
+ bl __udivsi3\n\
+ ldrh r1, [r7, 0x28]\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ cmp r1, r0\n\
+ bhi _0803BFA2\n\
+ ldr r4, _0803BFE8 @ =gBattleMovePower\n\
+ ldrh r1, [r4]\n\
+ movs r0, 0x96\n\
+ muls r0, r1\n\
+ movs r1, 0x64\n\
+ bl __divsi3\n\
+ strh r0, [r4]\n\
+_0803BFA2:\n\
+ ldr r2, _0803BFEC @ =gBattleMoves\n\
+ ldr r0, _0803BFF0 @ =gUnknown_02024BE6\n\
+ ldrh r1, [r0]\n\
+ lsls r0, r1, 1\n\
+ adds r0, r1\n\
+ lsls r0, 2\n\
+ adds r0, r2\n\
+ ldrb r0, [r0]\n\
+ cmp r0, 0x7\n\
+ bne _0803BFBC\n\
+ ldr r0, [sp, 0x14]\n\
+ lsrs r0, 1\n\
+ str r0, [sp, 0x14]\n\
+_0803BFBC:\n\
+ mov r1, r9\n\
+ cmp r1, 0x8\n\
+ bls _0803BFC4\n\
+ b _0803C122\n\
+_0803BFC4:\n\
+ ldr r0, _0803BFF4 @ =gCritMultiplier\n\
+ ldrb r1, [r0]\n\
+ adds r4, r0, 0\n\
+ cmp r1, 0x2\n\
+ bne _0803C000\n\
+ movs r0, 0x19\n\
+ ldrsb r0, [r7, r0]\n\
+ cmp r0, 0x6\n\
+ ble _0803BFFC\n\
+ ldr r2, _0803BFF8 @ =gStatStageRatios\n\
+ b _0803C006\n\
+ .align 2, 0\n\
+_0803BFDC: .4byte gUnknown_020239F8\n\
+_0803BFE0: .4byte 0xfffffe69\n\
+_0803BFE4: .4byte 0x00000175\n\
+_0803BFE8: .4byte gBattleMovePower\n\
+_0803BFEC: .4byte gBattleMoves\n\
+_0803BFF0: .4byte gUnknown_02024BE6\n\
+_0803BFF4: .4byte gCritMultiplier\n\
+_0803BFF8: .4byte gStatStageRatios\n\
+_0803BFFC:\n\
+ adds r5, r6, 0\n\
+ b _0803C01E\n\
+_0803C000:\n\
+ ldr r2, _0803C050 @ =gStatStageRatios\n\
+ movs r0, 0x19\n\
+ ldrsb r0, [r7, r0]\n\
+_0803C006:\n\
+ lsls r0, 1\n\
+ adds r1, r0, r2\n\
+ ldrb r1, [r1]\n\
+ adds r5, r6, 0\n\
+ muls r5, r1\n\
+ adds r2, 0x1\n\
+ adds r0, r2\n\
+ ldrb r1, [r0]\n\
+ adds r0, r5, 0\n\
+ bl __divsi3\n\
+ adds r5, r0, 0\n\
+_0803C01E:\n\
+ ldr r0, _0803C054 @ =gBattleMovePower\n\
+ ldrh r0, [r0]\n\
+ muls r5, r0\n\
+ adds r0, r7, 0\n\
+ adds r0, 0x2A\n\
+ ldrb r0, [r0]\n\
+ lsls r0, 1\n\
+ movs r1, 0x5\n\
+ bl __divsi3\n\
+ adds r0, 0x2\n\
+ muls r5, r0\n\
+ ldrb r0, [r4]\n\
+ cmp r0, 0x2\n\
+ bne _0803C05C\n\
+ ldr r2, [sp, 0x4]\n\
+ movs r0, 0x1A\n\
+ ldrsb r0, [r2, r0]\n\
+ cmp r0, 0x5\n\
+ bgt _0803C058\n\
+ ldr r2, _0803C050 @ =gStatStageRatios\n\
+ ldr r3, [sp, 0x4]\n\
+ movs r0, 0x1A\n\
+ ldrsb r0, [r3, r0]\n\
+ b _0803C064\n\
+ .align 2, 0\n\
+_0803C050: .4byte gStatStageRatios\n\
+_0803C054: .4byte gBattleMovePower\n\
+_0803C058:\n\
+ ldr r3, [sp, 0x14]\n\
+ b _0803C07E\n\
+_0803C05C:\n\
+ ldr r2, _0803C0DC @ =gStatStageRatios\n\
+ ldr r1, [sp, 0x4]\n\
+ movs r0, 0x1A\n\
+ ldrsb r0, [r1, r0]\n\
+_0803C064:\n\
+ lsls r0, 1\n\
+ adds r1, r0, r2\n\
+ ldrb r1, [r1]\n\
+ ldr r6, [sp, 0x14]\n\
+ adds r3, r6, 0\n\
+ muls r3, r1\n\
+ adds r2, 0x1\n\
+ adds r0, r2\n\
+ ldrb r1, [r0]\n\
+ adds r0, r3, 0\n\
+ bl __divsi3\n\
+ adds r3, r0, 0\n\
+_0803C07E:\n\
+ adds r0, r5, 0\n\
+ adds r1, r3, 0\n\
+ bl __divsi3\n\
+ adds r5, r0, 0\n\
+ movs r1, 0x32\n\
+ bl __divsi3\n\
+ adds r5, r0, 0\n\
+ ldr r0, [r7, 0x4C]\n\
+ movs r1, 0x10\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803C0A8\n\
+ ldr r1, [sp, 0x24]\n\
+ ldrb r0, [r1]\n\
+ cmp r0, 0x3E\n\
+ beq _0803C0A8\n\
+ lsrs r0, r5, 31\n\
+ adds r0, r5, r0\n\
+ asrs r5, r0, 1\n\
+_0803C0A8:\n\
+ movs r0, 0x1\n\
+ ldr r2, [sp, 0xC]\n\
+ ands r0, r2\n\
+ cmp r0, 0\n\
+ beq _0803C0EA\n\
+ ldrb r1, [r4]\n\
+ cmp r1, 0x1\n\
+ bne _0803C0EA\n\
+ ldr r0, _0803C0E0 @ =gUnknown_020239F8\n\
+ ldrh r0, [r0]\n\
+ ands r1, r0\n\
+ cmp r1, 0\n\
+ beq _0803C0E4\n\
+ movs r0, 0x2\n\
+ bl sub_803C348\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ cmp r0, 0x2\n\
+ bne _0803C0E4\n\
+ adds r0, r5, 0\n\
+ movs r1, 0x3\n\
+ bl __divsi3\n\
+ lsls r5, r0, 1\n\
+ b _0803C0EA\n\
+ .align 2, 0\n\
+_0803C0DC: .4byte gStatStageRatios\n\
+_0803C0E0: .4byte gUnknown_020239F8\n\
+_0803C0E4:\n\
+ lsrs r0, r5, 31\n\
+ adds r0, r5, r0\n\
+ asrs r5, r0, 1\n\
+_0803C0EA:\n\
+ ldr r0, _0803C148 @ =gUnknown_020239F8\n\
+ ldrh r1, [r0]\n\
+ movs r0, 0x1\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803C11C\n\
+ ldr r0, _0803C14C @ =gBattleMoves\n\
+ ldr r3, [sp, 0x8]\n\
+ lsls r1, r3, 1\n\
+ adds r1, r3\n\
+ lsls r1, 2\n\
+ adds r1, r0\n\
+ ldrb r0, [r1, 0x6]\n\
+ cmp r0, 0x8\n\
+ bne _0803C11C\n\
+ movs r0, 0x2\n\
+ bl sub_803C348\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ cmp r0, 0x2\n\
+ bne _0803C11C\n\
+ lsrs r0, r5, 31\n\
+ adds r0, r5, r0\n\
+ asrs r5, r0, 1\n\
+_0803C11C:\n\
+ cmp r5, 0\n\
+ bne _0803C122\n\
+ movs r5, 0x1\n\
+_0803C122:\n\
+ mov r6, r9\n\
+ cmp r6, 0x9\n\
+ bne _0803C12A\n\
+ movs r5, 0\n\
+_0803C12A:\n\
+ mov r0, r9\n\
+ cmp r0, 0x9\n\
+ bhi _0803C132\n\
+ b _0803C330\n\
+_0803C132:\n\
+ ldr r0, _0803C150 @ =gCritMultiplier\n\
+ ldrb r1, [r0]\n\
+ adds r4, r0, 0\n\
+ cmp r1, 0x2\n\
+ bne _0803C15C\n\
+ movs r0, 0x1C\n\
+ ldrsb r0, [r7, r0]\n\
+ cmp r0, 0x6\n\
+ ble _0803C158\n\
+ ldr r2, _0803C154 @ =gStatStageRatios\n\
+ b _0803C162\n\
+ .align 2, 0\n\
+_0803C148: .4byte gUnknown_020239F8\n\
+_0803C14C: .4byte gBattleMoves\n\
+_0803C150: .4byte gCritMultiplier\n\
+_0803C154: .4byte gStatStageRatios\n\
+_0803C158:\n\
+ mov r5, r8\n\
+ b _0803C17A\n\
+_0803C15C:\n\
+ ldr r2, _0803C1A8 @ =gStatStageRatios\n\
+ movs r0, 0x1C\n\
+ ldrsb r0, [r7, r0]\n\
+_0803C162:\n\
+ lsls r0, 1\n\
+ adds r1, r0, r2\n\
+ ldrb r1, [r1]\n\
+ mov r5, r8\n\
+ muls r5, r1\n\
+ adds r2, 0x1\n\
+ adds r0, r2\n\
+ ldrb r1, [r0]\n\
+ adds r0, r5, 0\n\
+ bl __divsi3\n\
+ adds r5, r0, 0\n\
+_0803C17A:\n\
+ ldr r0, _0803C1AC @ =gBattleMovePower\n\
+ ldrh r0, [r0]\n\
+ muls r5, r0\n\
+ adds r0, r7, 0\n\
+ adds r0, 0x2A\n\
+ ldrb r0, [r0]\n\
+ lsls r0, 1\n\
+ movs r1, 0x5\n\
+ bl __divsi3\n\
+ adds r0, 0x2\n\
+ muls r5, r0\n\
+ ldrb r0, [r4]\n\
+ cmp r0, 0x2\n\
+ bne _0803C1B4\n\
+ ldr r1, [sp, 0x4]\n\
+ movs r0, 0x1D\n\
+ ldrsb r0, [r1, r0]\n\
+ cmp r0, 0x5\n\
+ bgt _0803C1B0\n\
+ ldr r2, _0803C1A8 @ =gStatStageRatios\n\
+ b _0803C1BC\n\
+ .align 2, 0\n\
+_0803C1A8: .4byte gStatStageRatios\n\
+_0803C1AC: .4byte gBattleMovePower\n\
+_0803C1B0:\n\
+ ldr r3, [sp, 0x18]\n\
+ b _0803C1D6\n\
+_0803C1B4:\n\
+ ldr r2, _0803C21C @ =gStatStageRatios\n\
+ ldr r1, [sp, 0x4]\n\
+ movs r0, 0x1D\n\
+ ldrsb r0, [r1, r0]\n\
+_0803C1BC:\n\
+ lsls r0, 1\n\
+ adds r1, r0, r2\n\
+ ldrb r1, [r1]\n\
+ ldr r6, [sp, 0x18]\n\
+ adds r3, r6, 0\n\
+ muls r3, r1\n\
+ adds r2, 0x1\n\
+ adds r0, r2\n\
+ ldrb r1, [r0]\n\
+ adds r0, r3, 0\n\
+ bl __divsi3\n\
+ adds r3, r0, 0\n\
+_0803C1D6:\n\
+ adds r0, r5, 0\n\
+ adds r1, r3, 0\n\
+ bl __divsi3\n\
+ adds r5, r0, 0\n\
+ movs r1, 0x32\n\
+ bl __divsi3\n\
+ adds r5, r0, 0\n\
+ movs r0, 0x2\n\
+ ldr r1, [sp, 0xC]\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803C22A\n\
+ ldrb r1, [r4]\n\
+ cmp r1, 0x1\n\
+ bne _0803C22A\n\
+ ldr r0, _0803C220 @ =gUnknown_020239F8\n\
+ ldrh r0, [r0]\n\
+ ands r1, r0\n\
+ cmp r1, 0\n\
+ beq _0803C224\n\
+ movs r0, 0x2\n\
+ bl sub_803C348\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ cmp r0, 0x2\n\
+ bne _0803C224\n\
+ adds r0, r5, 0\n\
+ movs r1, 0x3\n\
+ bl __divsi3\n\
+ lsls r5, r0, 1\n\
+ b _0803C22A\n\
+ .align 2, 0\n\
+_0803C21C: .4byte gStatStageRatios\n\
+_0803C220: .4byte gUnknown_020239F8\n\
+_0803C224:\n\
+ lsrs r0, r5, 31\n\
+ adds r0, r5, r0\n\
+ asrs r5, r0, 1\n\
+_0803C22A:\n\
+ ldr r0, _0803C2A4 @ =gUnknown_020239F8\n\
+ ldrh r1, [r0]\n\
+ movs r0, 0x1\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803C25C\n\
+ ldr r0, _0803C2A8 @ =gBattleMoves\n\
+ ldr r2, [sp, 0x8]\n\
+ lsls r1, r2, 1\n\
+ adds r1, r2\n\
+ lsls r1, 2\n\
+ adds r1, r0\n\
+ ldrb r0, [r1, 0x6]\n\
+ cmp r0, 0x8\n\
+ bne _0803C25C\n\
+ movs r0, 0x2\n\
+ bl sub_803C348\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ cmp r0, 0x2\n\
+ bne _0803C25C\n\
+ lsrs r0, r5, 31\n\
+ adds r0, r5, r0\n\
+ asrs r5, r0, 1\n\
+_0803C25C:\n\
+ movs r0, 0\n\
+ str r0, [sp]\n\
+ movs r0, 0xE\n\
+ movs r1, 0\n\
+ movs r2, 0xD\n\
+ movs r3, 0\n\
+ bl sub_8018324\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ cmp r0, 0\n\
+ bne _0803C30C\n\
+ str r0, [sp]\n\
+ movs r0, 0xE\n\
+ movs r1, 0\n\
+ movs r2, 0x4D\n\
+ movs r3, 0\n\
+ bl sub_8018324\n\
+ lsls r0, 24\n\
+ cmp r0, 0\n\
+ bne _0803C30C\n\
+ ldr r2, _0803C2AC @ =gBattleWeather\n\
+ ldrh r1, [r2]\n\
+ movs r0, 0x1\n\
+ ands r0, r1\n\
+ adds r4, r2, 0\n\
+ cmp r0, 0\n\
+ beq _0803C2C4\n\
+ mov r3, r9\n\
+ cmp r3, 0xA\n\
+ beq _0803C2B0\n\
+ cmp r3, 0xB\n\
+ beq _0803C2B8\n\
+ b _0803C2C4\n\
+ .align 2, 0\n\
+_0803C2A4: .4byte gUnknown_020239F8\n\
+_0803C2A8: .4byte gBattleMoves\n\
+_0803C2AC: .4byte gBattleWeather\n\
+_0803C2B0:\n\
+ lsrs r0, r5, 31\n\
+ adds r0, r5, r0\n\
+ asrs r5, r0, 1\n\
+ b _0803C2C4\n\
+_0803C2B8:\n\
+ lsls r0, r5, 4\n\
+ subs r0, r5\n\
+ movs r1, 0xA\n\
+ bl __divsi3\n\
+ adds r5, r0, 0\n\
+_0803C2C4:\n\
+ ldrh r1, [r4]\n\
+ movs r0, 0x9F\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803C2DC\n\
+ ldr r0, _0803C2F4 @ =gUnknown_02024BE6\n\
+ ldrh r0, [r0]\n\
+ cmp r0, 0x4C\n\
+ bne _0803C2DC\n\
+ lsrs r0, r5, 31\n\
+ adds r0, r5, r0\n\
+ asrs r5, r0, 1\n\
+_0803C2DC:\n\
+ ldrh r1, [r4]\n\
+ movs r0, 0x60\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803C30C\n\
+ mov r6, r9\n\
+ cmp r6, 0xA\n\
+ beq _0803C2F8\n\
+ cmp r6, 0xB\n\
+ beq _0803C306\n\
+ b _0803C30C\n\
+ .align 2, 0\n\
+_0803C2F4: .4byte gUnknown_02024BE6\n\
+_0803C2F8:\n\
+ lsls r0, r5, 4\n\
+ subs r0, r5\n\
+ movs r1, 0xA\n\
+ bl __divsi3\n\
+ adds r5, r0, 0\n\
+ b _0803C30C\n\
+_0803C306:\n\
+ lsrs r0, r5, 31\n\
+ adds r0, r5, r0\n\
+ asrs r5, r0, 1\n\
+_0803C30C:\n\
+ ldr r1, _0803C344 @ =0x02017100\n\
+ ldr r2, [sp, 0x10]\n\
+ lsls r0, r2, 2\n\
+ adds r0, r1\n\
+ ldr r0, [r0]\n\
+ movs r1, 0x1\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0803C330\n\
+ mov r3, r9\n\
+ cmp r3, 0xA\n\
+ bne _0803C330\n\
+ lsls r0, r5, 4\n\
+ subs r0, r5\n\
+ movs r1, 0xA\n\
+ bl __divsi3\n\
+ adds r5, r0, 0\n\
+_0803C330:\n\
+ adds r0, r5, 0x2\n\
+ add sp, 0x2C\n\
+ pop {r3-r5}\n\
+ mov r8, r3\n\
+ mov r9, r4\n\
+ mov r10, r5\n\
+ pop {r4-r7}\n\
+ pop {r1}\n\
+ bx r1\n\
+ .align 2, 0\n\
+_0803C344: .4byte 0x02017100\n\
+ .syntax divided");
+}
+#endif
diff --git a/src/coins.c b/src/coins.c
index c07a0c7c7..87d96f2bb 100644
--- a/src/coins.c
+++ b/src/coins.c
@@ -29,7 +29,6 @@ void PrintCoins(s32 a, u8 b, u8 c, u8 d)
u8 string[16];
u8 *ptr;
u8 r1;
- u8 r6;
u8 foo;
ConvertIntToDecimalString(string, a);
diff --git a/src/decompress.c b/src/decompress.c
index 7f8ed9271..ebfd78ffb 100644
--- a/src/decompress.c
+++ b/src/decompress.c
@@ -107,7 +107,7 @@ void sub_800D378(const struct SpriteSheet *a, u32 b, u32 c, u32 d, void *dest, s
DrawSpindaSpots(f, g, dest, r7);
}
-static void Unused_LZDecompressWramIndirect(const void **src, void *dest)
+void Unused_LZDecompressWramIndirect(const void **src, void *dest)
{
LZ77UnCompWram(*src, dest);
}
diff --git a/src/field_camera.c b/src/field_camera.c
index b9a813bdf..c55d8e2a3 100644
--- a/src/field_camera.c
+++ b/src/field_camera.c
@@ -427,7 +427,7 @@ void CameraUpdate(void)
gUnknown_03004898 -= r8;
}
-static void camera_move_and_redraw(int a, int b)
+void camera_move_and_redraw(int a, int b)
{
CameraMove(a, b);
UpdateFieldObjectsForCameraUpdate(a, b);
diff --git a/src/field_door.c b/src/field_door.c
index da57988ca..85a5965a0 100644
--- a/src/field_door.c
+++ b/src/field_door.c
@@ -2,6 +2,7 @@
#include "asm.h"
#include "task.h"
#include "field_camera.h"
+#include "metatile_behavior.h"
struct DoorGraphics
{
@@ -186,7 +187,7 @@ static s8 cur_mapdata_get_door_x2_at(struct DoorGraphics *gfx, u32 x, u32 y)
return gfx->unk2;
}
-static void unref_sub_805869C(u32 x, u32 y)
+void unref_sub_805869C(u32 x, u32 y)
{
StartDoorOpenAnimation(gDoorAnimGraphicsTable, x, y);
}
diff --git a/src/field_ground_effect.c b/src/field_ground_effect.c
new file mode 100644
index 000000000..42cf5d676
--- /dev/null
+++ b/src/field_ground_effect.c
@@ -0,0 +1,256 @@
+#include "global.h"
+#include "asm_fieldmap.h"
+#include "metatile_behavior.h"
+
+extern u32 gUnknown_08376008[];
+
+void FieldObjectUpdateMetatileBehaviors(struct MapObject *);
+void GetGroundEffectFlags_Reflection(struct MapObject *, u32 *);
+void GetGroundEffectFlags_TallGrassOnSpawn(struct MapObject *, u32 *);
+void GetGroundEffectFlags_TallGrassOnBeginStep(struct MapObject *, u32 *);
+void GetGroundEffectFlags_LongGrassOnSpawn(struct MapObject *, u32 *);
+void GetGroundEffectFlags_LongGrassOnBeginStep(struct MapObject *, u32 *);
+void GetGroundEffectFlags_Tracks(struct MapObject *, u32 *);
+void GetGroundEffectFlags_SandPile(struct MapObject *, u32 *);
+void GetGroundEffectFlags_ShallowFlowingWater(struct MapObject *, u32 *);
+void GetGroundEffectFlags_Puddle(struct MapObject *, u32 *);
+void GetGroundEffectFlags_Ripple(struct MapObject *, u32 *);
+void GetGroundEffectFlags_ShortGrass(struct MapObject *, u32 *);
+void GetGroundEffectFlags_HotSprings(struct MapObject *, u32 *);
+void GetGroundEffectFlags_Seaweed(struct MapObject *, u32 *);
+void GetGroundEffectFlags_JumpLanding(struct MapObject *, u32 *);
+u8 FieldObjectCheckForReflectiveSurface(struct MapObject *);
+
+void GetAllGroundEffectFlags_OnSpawn(struct MapObject *mapObj, u32 *flags)
+{
+ FieldObjectUpdateMetatileBehaviors(mapObj);
+ GetGroundEffectFlags_Reflection(mapObj, flags);
+ GetGroundEffectFlags_TallGrassOnSpawn(mapObj, flags);
+ GetGroundEffectFlags_LongGrassOnSpawn(mapObj, flags);
+ GetGroundEffectFlags_SandPile(mapObj, flags);
+ GetGroundEffectFlags_ShallowFlowingWater(mapObj, flags);
+ GetGroundEffectFlags_ShortGrass(mapObj, flags);
+ GetGroundEffectFlags_HotSprings(mapObj, flags);
+}
+
+void GetAllGroundEffectFlags_OnBeginStep(struct MapObject *mapObj, u32 *flags)
+{
+ FieldObjectUpdateMetatileBehaviors(mapObj);
+ GetGroundEffectFlags_Reflection(mapObj, flags);
+ GetGroundEffectFlags_TallGrassOnBeginStep(mapObj, flags);
+ GetGroundEffectFlags_LongGrassOnBeginStep(mapObj, flags);
+ GetGroundEffectFlags_Tracks(mapObj, flags);
+ GetGroundEffectFlags_SandPile(mapObj, flags);
+ GetGroundEffectFlags_ShallowFlowingWater(mapObj, flags);
+ GetGroundEffectFlags_Puddle(mapObj, flags);
+ GetGroundEffectFlags_ShortGrass(mapObj, flags);
+ GetGroundEffectFlags_HotSprings(mapObj, flags);
+}
+
+void GetAllGroundEffectFlags_OnFinishStep(struct MapObject *mapObj, u32 *flags)
+{
+ FieldObjectUpdateMetatileBehaviors(mapObj);
+ GetGroundEffectFlags_ShallowFlowingWater(mapObj, flags);
+ GetGroundEffectFlags_SandPile(mapObj, flags);
+ GetGroundEffectFlags_Puddle(mapObj, flags);
+ GetGroundEffectFlags_Ripple(mapObj, flags);
+ GetGroundEffectFlags_ShortGrass(mapObj, flags);
+ GetGroundEffectFlags_HotSprings(mapObj, flags);
+ GetGroundEffectFlags_Seaweed(mapObj, flags);
+ GetGroundEffectFlags_JumpLanding(mapObj, flags);
+}
+
+void FieldObjectUpdateMetatileBehaviors(struct MapObject *mapObj)
+{
+ mapObj->mapobj_unk_1F = MapGridGetMetatileBehaviorAt(mapObj->coords3.x, mapObj->coords3.y);
+ mapObj->mapobj_unk_1E = MapGridGetMetatileBehaviorAt(mapObj->coords2.x, mapObj->coords2.y);
+}
+
+void GetGroundEffectFlags_Reflection(struct MapObject *mapObj, u32 *flags)
+{
+ u32 reflectionFlags[2] = { 0x00000020, 0x00000010 };
+ u8 type = FieldObjectCheckForReflectiveSurface(mapObj);
+
+ if (type)
+ {
+ if (!mapObj->mapobj_bit_17)
+ {
+ mapObj->mapobj_bit_17 = 0;
+ mapObj->mapobj_bit_17 = 1;
+ *flags |= reflectionFlags[type - 1];
+ }
+ }
+ else
+ {
+ mapObj->mapobj_bit_17 = 0;
+ }
+}
+
+void GetGroundEffectFlags_TallGrassOnSpawn(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_IsTallGrass(mapObj->mapobj_unk_1E))
+ *flags |= 0x1;
+}
+
+void GetGroundEffectFlags_TallGrassOnBeginStep(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_IsTallGrass(mapObj->mapobj_unk_1E))
+ *flags |= 0x2;
+}
+
+void GetGroundEffectFlags_LongGrassOnSpawn(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_IsLongGrass(mapObj->mapobj_unk_1E))
+ *flags |= 0x4;
+}
+
+void GetGroundEffectFlags_LongGrassOnBeginStep(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_IsLongGrass(mapObj->mapobj_unk_1E))
+ *flags |= 0x8;
+}
+
+void GetGroundEffectFlags_Tracks(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_IsDeepSand(mapObj->mapobj_unk_1F))
+ {
+ *flags |= 0x100;
+ }
+ else if (MetatileBehavior_IsSandOrDeepSand(mapObj->mapobj_unk_1F)
+ || MetatileBehavior_IsUnusedFootprintMetatile(mapObj->mapobj_unk_1F))
+ {
+ *flags |= 0x80;
+ }
+}
+
+void GetGroundEffectFlags_SandPile(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_IsDeepSand(mapObj->mapobj_unk_1E)
+ && MetatileBehavior_IsDeepSand(mapObj->mapobj_unk_1F))
+ {
+ if (!mapObj->mapobj_bit_20)
+ {
+ mapObj->mapobj_bit_20 = 0;
+ mapObj->mapobj_bit_20 = 1;
+ *flags |= 0x800;
+ }
+ }
+ else
+ {
+ mapObj->mapobj_bit_20 = 0;
+ }
+}
+
+void GetGroundEffectFlags_ShallowFlowingWater(struct MapObject *mapObj, u32 *flags)
+{
+ if ((MetatileBehavior_IsShallowFlowingWater(mapObj->mapobj_unk_1E) && MetatileBehavior_IsShallowFlowingWater(mapObj->mapobj_unk_1F))
+ || (MetatileBehavior_IsPacifidlogLog(mapObj->mapobj_unk_1E) && MetatileBehavior_IsPacifidlogLog(mapObj->mapobj_unk_1F)))
+ {
+ if (!mapObj->mapobj_bit_19)
+ {
+ mapObj->mapobj_bit_19 = 0;
+ mapObj->mapobj_bit_19 = 1;
+ *flags |= 0x40;
+ }
+ }
+ else
+ {
+ mapObj->mapobj_bit_19 = 0;
+ }
+}
+
+void GetGroundEffectFlags_Puddle(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_IsPuddle(mapObj->mapobj_unk_1E)
+ && MetatileBehavior_IsPuddle(mapObj->mapobj_unk_1F))
+ {
+ *flags |= 0x400;
+ }
+}
+
+void GetGroundEffectFlags_Ripple(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_HasRipples(mapObj->mapobj_unk_1E))
+ *flags |= 0x200;
+}
+
+void GetGroundEffectFlags_ShortGrass(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_IsShortGrass(mapObj->mapobj_unk_1E)
+ && MetatileBehavior_IsShortGrass(mapObj->mapobj_unk_1F))
+ {
+ if (!mapObj->mapobj_bit_18)
+ {
+ mapObj->mapobj_bit_18 = 0;
+ mapObj->mapobj_bit_18 = 1;
+ *flags |= 0x20000;
+ }
+ }
+ else
+ {
+ mapObj->mapobj_bit_18 = 0;
+ }
+}
+
+void GetGroundEffectFlags_HotSprings(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_IsHotSprings(mapObj->mapobj_unk_1E)
+ && MetatileBehavior_IsHotSprings(mapObj->mapobj_unk_1F))
+ {
+ if (!mapObj->mapobj_bit_21)
+ {
+ mapObj->mapobj_bit_21 = 0;
+ mapObj->mapobj_bit_21 = 1;
+ *flags |= 0x40000;
+ }
+ }
+ else
+ {
+ mapObj->mapobj_bit_21 = 0;
+ }
+}
+
+void GetGroundEffectFlags_Seaweed(struct MapObject *mapObj, u32 *flags)
+{
+ if (MetatileBehavior_IsSeaweed(mapObj->mapobj_unk_1E))
+ *flags |= 0x80000;
+}
+
+void GetGroundEffectFlags_JumpLanding(struct MapObject *mapObj, u32 *flags)
+{
+ typedef bool8 (*MetatileFunc)(u8);
+
+ static const MetatileFunc metatileFuncs[] =
+ {
+ MetatileBehavior_IsTallGrass,
+ MetatileBehavior_IsLongGrass,
+ MetatileBehavior_IsPuddle,
+ MetatileBehavior_IsSurfableWaterOrUnderwater,
+ MetatileBehavior_IsShallowFlowingWater,
+ sub_8056D9C,
+ };
+
+ static const u32 jumpLandingFlags[] =
+ {
+ 0x00001000, // Landing in tall grass
+ 0x00002000, // Landing in long grass
+ 0x00004000, // Landing on puddle
+ 0x00008000, // Landing on surfable water or underwater
+ 0x00004000, // Landing on shallow flowing water
+ 0x00010000, // Landing on any other type of ground
+ };
+
+ if (mapObj->mapobj_bit_5 && !mapObj->mapobj_bit_25)
+ {
+ u8 i;
+
+ for (i = 0; i < 6; i++)
+ {
+ if (metatileFuncs[i](mapObj->mapobj_unk_1E))
+ {
+ *flags |= jumpLandingFlags[i];
+ return;
+ }
+ }
+ }
+}
diff --git a/src/field_player_avatar.c b/src/field_player_avatar.c
index 708544b87..5fffa785f 100644
--- a/src/field_player_avatar.c
+++ b/src/field_player_avatar.c
@@ -14,6 +14,7 @@
#include "field_effect.h"
#include "wild_encounter.h"
#include "asm_fieldmap.h"
+#include "metatile_behavior.h"
extern u8 gOtherText_OhABite[];
extern u8 gOtherText_PokeOnHook[];
@@ -821,7 +822,7 @@ u8 PlayerGetZCoord(void)
return gMapObjects[gPlayerAvatar.mapObjectId].elevation;
}
-static void unref_sub_8059790(s16 a, s16 b)
+void unref_sub_8059790(s16 a, s16 b)
{
sub_805C058(&gMapObjects[gPlayerAvatar.mapObjectId], a, b);
}
@@ -874,7 +875,7 @@ u8 GetPlayerAvatarGraphicsIdByStateId(u8 a)
return GetPlayerAvatarGraphicsIdByStateIdAndGender(a, gPlayerAvatar.gender);
}
-static u8 unref_sub_8059888(u8 a)
+u8 unref_sub_8059888(u8 a)
{
switch (a)
{
diff --git a/src/fieldmap.c b/src/fieldmap.c
index cd9baa217..4dcfbe30b 100644
--- a/src/fieldmap.c
+++ b/src/fieldmap.c
@@ -42,7 +42,7 @@ EWRAM_DATA struct MapHeader gMapHeader = {0};
EWRAM_DATA struct Camera gUnknown_0202E844 = {0};
EWRAM_DATA static struct ConnectionFlags gUnknown_0202E850 = {0};
-extern const struct ConnectionFlags gUnknown_08308E28;
+static const struct ConnectionFlags sDummyConnectionFlags = {0};
void mapheader_copy_mapdata_with_padding(struct MapHeader *mapHeader);
void sub_80560AC(struct MapHeader *);
@@ -112,7 +112,7 @@ void sub_80560AC(struct MapHeader *mapHeader) {
int count;
count = mapHeader->connections->count;
connection = mapHeader->connections->connections;
- gUnknown_0202E850 = gUnknown_08308E28;
+ gUnknown_0202E850 = sDummyConnectionFlags;
for (i = 0; i < count; i++, connection++) {
cMap = mapconnection_get_mapheader(connection);
offset = connection->offset;
@@ -156,8 +156,8 @@ void sub_8056134(int x, int y, struct MapHeader *mapHeader, int x2, int y2, int
void fillSouthConnection(struct MapHeader *mapHeader, struct MapHeader *connectedMapHeader, s32 offset) {
int x, y;
- int x2, y2;
- int width, height;
+ int x2;
+ int width;
int cWidth;
if (connectedMapHeader) {
@@ -190,9 +190,9 @@ void fillSouthConnection(struct MapHeader *mapHeader, struct MapHeader *connecte
}
void fillNorthConnection(struct MapHeader *mapHeader, struct MapHeader *connectedMapHeader, s32 offset) {
- int x, y;
+ int x;
int x2, y2;
- int width, height;
+ int width;
int cWidth, cHeight;
if (connectedMapHeader) {
@@ -229,9 +229,9 @@ void fillNorthConnection(struct MapHeader *mapHeader, struct MapHeader *connecte
void fillWestConnection(struct MapHeader *mapHeader, struct MapHeader *connectedMapHeader, s32 offset) {
- int x, y;
+ int y;
int x2, y2;
- int width, height;
+ int height;
int cWidth, cHeight;
if (connectedMapHeader) {
cWidth = connectedMapHeader->mapData->width;
@@ -265,9 +265,9 @@ void fillWestConnection(struct MapHeader *mapHeader, struct MapHeader *connected
void fillEastConnection(struct MapHeader *mapHeader, struct MapHeader *connectedMapHeader, s32 offset) {
int x, y;
- int x2, y2;
- int width, height;
- int cWidth, cHeight;
+ int y2;
+ int height;
+ int cHeight;
if (connectedMapHeader) {
cHeight = connectedMapHeader->mapData->height;
x = mapHeader->mapData->width + 7;
diff --git a/src/intro.c b/src/intro.c
index 13e35976e..dfc1d6a4c 100644
--- a/src/intro.c
+++ b/src/intro.c
@@ -520,8 +520,6 @@ static void task_intro_13(u8 taskId)
static void task_intro_14(u8 taskId)
{
- u8 newTaskId;
-
REG_WIN0H = 0xF0;
REG_WIN0V = 0xA0;
REG_WININ = 0x1C;
diff --git a/src/item.c b/src/item.c
index 84ab4c1c8..3f74b5925 100644
--- a/src/item.c
+++ b/src/item.c
@@ -58,7 +58,7 @@ void CopyItemName(u16 itemId, u8 *string)
}
//Unreferenced
-static s8 CountUsedBagPocketSlots(u8 pocket)
+s8 CountUsedBagPocketSlots(u8 pocket)
{
u8 i;
diff --git a/src/link.c b/src/link.c
index 56635def2..d2b5770e9 100644
--- a/src/link.c
+++ b/src/link.c
@@ -41,8 +41,8 @@ extern u16 word_3004858;
extern u8 gMultiText_LinkError[];
static void InitLinkTestBG(u8, u8, u8, u8);
-static void InitLinkTestBG_Unused(u8, u8, u8, u8);
-static void LinkTestScreen();
+void InitLinkTestBG_Unused(u8, u8, u8, u8);
+void LinkTestScreen();
static void InitLocalLinkPlayer(void);
static void VBlankCB_LinkTest(void);
static void InitLink(void);
@@ -60,15 +60,15 @@ static void LinkCB_BlockSendBegin(void);
static void LinkCB_BlockSend(void);
static void LinkCB_BlockSendEnd(void);
static void sub_8007E04(void);
-static u32 sub_8007E40(void);
+u32 sub_8007E40(void);
static void SetBlockReceivedFlag(u8);
static u16 LinkTestCalcBlockChecksum(void *, u16);
static void PrintHexDigit(u8, u8, u8);
static void PrintHex(u32, u8, u8, u8);
static void LinkCB_RequestPlayerDataExchange(void);
static void Task_PrintTestData(u8);
-static bool8 sub_8008224(void);
-static u8 GetDummy2(void);
+bool8 sub_8008224(void);
+u8 GetDummy2(void);
static void sub_8008350(void);
static void sub_800837C(void);
static void sub_80083E0(void);
@@ -90,8 +90,8 @@ static void DoRecv(void);
static void DoSend(void);
static void StopTimer(void);
static void SendRecvDone(void);
-static void ResetSendBuffer(void);
-static void ResetRecvBuffer(void);
+void ResetSendBuffer(void);
+void ResetRecvBuffer(void);
static struct BlockTransfer sBlockSend;
static struct BlockTransfer sBlockRecv[MAX_LINK_PLAYERS];
@@ -212,7 +212,7 @@ static void InitLinkTestBG(u8 paletteNum, u8 bgNum, u8 screenBaseBlock, u8 charB
}
}
-static void InitLinkTestBG_Unused(u8 paletteNum, u8 bgNum, u8 screenBaseBlock, u8 charBaseBlock)
+void InitLinkTestBG_Unused(u8 paletteNum, u8 bgNum, u8 screenBaseBlock, u8 charBaseBlock)
{
LoadPalette(sLinkTestDigitPalette, 16 * paletteNum, 32);
DmaCopy16(3, sLinkTestDigitTiles, BG_CHAR_ADDR(charBaseBlock), 0x220);
@@ -223,7 +223,7 @@ static void InitLinkTestBG_Unused(u8 paletteNum, u8 bgNum, u8 screenBaseBlock, u
*gBGControlRegs[bgNum] = (screenBaseBlock << 8) | (charBaseBlock << 2);
}
-static void LinkTestScreen(void)
+void LinkTestScreen(void)
{
s32 i;
ResetSpriteData();
@@ -840,7 +840,7 @@ void sub_8007E24(void)
gLinkCallback = sub_8007E04;
}
-static u32 sub_8007E40(void)
+u32 sub_8007E40(void)
{
return dword_20238BC;
}
@@ -1025,7 +1025,7 @@ u8 sub_8008218(void)
return gSavedMultiplayerId;
}
-static bool8 sub_8008224(void)
+bool8 sub_8008224(void)
{
s32 count = 0;
s32 i;
@@ -1072,7 +1072,7 @@ bool8 IsLinkMaster(void)
return EXTRACT_MASTER(gLinkStatus);
}
-static u8 GetDummy2(void)
+u8 GetDummy2(void)
{
return sDummy2;
}
@@ -1236,7 +1236,7 @@ void CB2_LinkError(void)
static void CB2_PrintErrorMessage(void)
{
- u8 array[64]; // unused
+ u8 array[64] __attribute__((unused)); // unused
switch (gMain.state)
{
@@ -1772,7 +1772,7 @@ static void SendRecvDone(void)
}
}
-static void ResetSendBuffer(void)
+void ResetSendBuffer(void)
{
u8 i;
u8 j;
@@ -1785,7 +1785,7 @@ static void ResetSendBuffer(void)
gLink.sendQueue.data[i][j] = 0xEFFF;
}
-static void ResetRecvBuffer(void)
+void ResetRecvBuffer(void)
{
u8 i;
u8 j;
diff --git a/src/load_save.c b/src/load_save.c
new file mode 100644
index 000000000..0d4f1238d
--- /dev/null
+++ b/src/load_save.c
@@ -0,0 +1,164 @@
+#include "global.h"
+#include "load_save.h"
+#include "asm.h"
+#include "main.h"
+#include "pokemon.h"
+#include "rom4.h"
+
+extern u8 gPlayerPartyCount;
+extern u32 gUnknown_3004820;
+
+struct LoadedSaveData
+{
+ struct ItemSlot items[20];
+ struct ItemSlot keyItems[20];
+ struct ItemSlot pokeBalls[16];
+ struct ItemSlot TMsHMs[64];
+ struct ItemSlot berries[46];
+ struct SaveBlock1_2B4C_Struct unknownSaveData[16];
+};
+
+extern struct LoadedSaveData gLoadedSaveData[];
+
+void CheckForFlashMemory(void)
+{
+ if(!IdentifyFlash())
+ {
+ gUnknown_3004820 = 1;
+ InitFlashTimer();
+ }
+ else
+ gUnknown_3004820 = 0;
+}
+
+bool32 GetSecretBase2Field_9(void)
+{
+ return gSaveBlock2.specialSaveWarp;
+}
+
+void ClearSecretBase2Field_9(void)
+{
+ gSaveBlock2.specialSaveWarp = 0;
+}
+
+void SetSecretBase2Field_9(void)
+{
+ gSaveBlock2.specialSaveWarp = 1;
+}
+
+void SetSecretBase2Field_9_AndHideBG(void) // note: no other function sets specialSaveWarp to values other than 0 or 1, hence clear and set distinctions.
+{
+ gpu_sync_bg_hide(0); // the function doesn't use the parameter passed to it, but this is necessary to match.
+ gSaveBlock2.specialSaveWarp = 1;
+}
+
+void ClearSecretBase2Field_9_2(void) // duplicate function
+{
+ gSaveBlock2.specialSaveWarp = 0;
+}
+
+void SavePlayerParty(void)
+{
+ int i;
+
+ gSaveBlock1.playerPartyCount = gPlayerPartyCount;
+
+ for (i = 0; i < 6; i++)
+ gSaveBlock1.playerParty[i] = gPlayerParty[i];
+}
+
+void LoadPlayerParty(void)
+{
+ int i;
+
+ gPlayerPartyCount = gSaveBlock1.playerPartyCount;
+
+ for (i = 0; i < 6; i++)
+ gPlayerParty[i] = gSaveBlock1.playerParty[i];
+}
+
+static void SaveMapObjects(void)
+{
+ int i;
+
+ for(i = 0; i < 16; i++)
+ gSaveBlock1.mapObjects[i] = gMapObjects[i];
+}
+
+static void LoadMapObjects(void)
+{
+ int i;
+
+ for(i = 0; i < 16; i++)
+ gMapObjects[i] = gSaveBlock1.mapObjects[i];
+}
+
+void SaveSerializedGame(void)
+{
+ SavePlayerParty();
+ SaveMapObjects();
+}
+
+void LoadSerializedGame(void)
+{
+ LoadPlayerParty();
+ LoadMapObjects();
+}
+
+void LoadPlayerData(void)
+{
+ int i;
+
+ // load player items.
+ for(i = 0; i < 20; i++)
+ gLoadedSaveData->items[i] = gSaveBlock1.bagPocket_Items[i];
+
+ // load player key items.
+ for(i = 0; i < 20; i++)
+ gLoadedSaveData->keyItems[i] = gSaveBlock1.bagPocket_KeyItems[i];
+
+ // load player pokeballs.
+ for(i = 0; i < 16; i++)
+ gLoadedSaveData->pokeBalls[i] = gSaveBlock1.bagPocket_PokeBalls[i];
+
+ // load player TMs and HMs.
+ for(i = 0; i < 64; i++)
+ gLoadedSaveData->TMsHMs[i] = gSaveBlock1.bagPocket_TMHM[i];
+
+ // load player berries.
+ for(i = 0; i < 46; i++)
+ gLoadedSaveData->berries[i] = gSaveBlock1.bagPocket_Berries[i];
+
+ // load misc data.
+ for(i = 0; i < 16; i++)
+ gLoadedSaveData->unknownSaveData[i] = gSaveBlock1.unkSave[i];
+}
+
+void SavePlayerData(void)
+{
+ int i;
+
+ // save player items.
+ for(i = 0; i < 20; i++)
+ gSaveBlock1.bagPocket_Items[i] = gLoadedSaveData->items[i];
+
+ // save player key items.
+ for(i = 0; i < 20; i++)
+ gSaveBlock1.bagPocket_KeyItems[i] = gLoadedSaveData->keyItems[i];
+
+ // save player pokeballs.
+ for(i = 0; i < 16; i++)
+ gSaveBlock1.bagPocket_PokeBalls[i] = gLoadedSaveData->pokeBalls[i];
+
+ // save player TMs and HMs.
+ for(i = 0; i < 64; i++)
+ gSaveBlock1.bagPocket_TMHM[i] = gLoadedSaveData->TMsHMs[i];
+
+ // save player berries.
+ for(i = 0; i < 46; i++)
+ gSaveBlock1.bagPocket_Berries[i] = gLoadedSaveData->berries[i];
+
+ // save misc data.
+ for(i = 0; i < 16; i++)
+ gSaveBlock1.unkSave[i] = gLoadedSaveData->unknownSaveData[i];
+}
diff --git a/src/mail.c b/src/mail.c
new file mode 100644
index 000000000..c1ec02e4e
--- /dev/null
+++ b/src/mail.c
@@ -0,0 +1,683 @@
+#include "global.h"
+#include "mail.h"
+#include "asm.h"
+#include "menu.h"
+#include "palette.h"
+#include "rom4.h"
+#include "sprite.h"
+#include "string_util.h"
+#include "task.h"
+#include "text.h"
+
+struct UnkMailStruct
+{
+ u8 unk_0_0:2;
+ u8 unk_0_2:2;
+ u8 unk_0_4:4;
+};
+
+struct MailLayout {
+ u8 var0;
+ u8 var1;
+ u8 var2;
+ u8 var3_0:4;
+ u8 var3_4:4;
+ struct UnkMailStruct *var4;
+};
+
+struct Unk2000000 {
+ /* 0x00 */ u8 words[8][27];
+ /* 0xEC */ u8 varD8[20];
+ /* 0xEC */ MainCallback varEC;
+ /* 0xF0 */ MainCallback varF0;
+ /* 0xFF */ struct MailStruct *varF4;
+ /* 0xF8 */ u8 varF8;
+ /* 0xF9 */ u8 varF9;
+ /* 0xFA */ u8 varFA;
+ /* 0xFB */ u8 varFB;
+ /* 0xFC */ u8 varFC;
+ u8 padFD[1];
+ /* 0xFE */ u8 varFE;
+ /* 0xFF */ u8 varFF;
+ /* 0x100 */ u8 var100;
+ u8 pad101[3];
+ /* 0x104 */ MainCallback var104;
+ /* 0x108 */ MainCallback var108;
+ /* 0x10C */ struct MailLayout *var10C;
+};
+
+struct MailGraphics {
+ u16 (*palette)[];
+ u8 (*tiles)[];
+ u8 (*tileMap)[];
+ u16 var0C;
+ u16 var0E;
+ u16 color10;
+ u16 color12;
+};
+
+enum {
+ ITEM_ORANGE_MAIL = 0x79,
+ ITEM_HARBOR_MAIL,
+ ITEM_GLITTER_MAIL,
+ ITEM_MECH_MAIL,
+ ITEM_WOOD_MAIL,
+ ITEM_WAVE_MAIL,
+ ITEM_BEAD_MAIL,
+ ITEM_SHADOW_MAIL,
+ ITEM_TROPIC_MAIL,
+ ITEM_DREAM_MAIL,
+ ITEM_FAB_MAIL,
+ ITEM_RETRO_MAIL,
+};
+
+extern struct Unk2000000 unk_2000000;
+extern struct MailGraphics gMailGraphicsTable[];
+extern u16 gUnknown_083E562C[][2];
+
+extern struct MailLayout gUnknown_083E5730[];
+extern struct MailLayout gUnknown_083E57A4[];
+
+extern u8 gOtherText_From[];
+
+static u8 sub_80F8A28(void);
+// static void sub_80F8D50(void);
+// static u8 *sub_80F8D7C(u8 *dest, u8 *src);
+static void sub_80F8DA0(void);
+static void sub_80F8E80(void);
+static void sub_80F8F18(void);
+static void sub_80F8F2C(void);
+static void sub_80F8F58(void);
+static void sub_80F8F78(void);
+static void sub_80F8FB4(void);
+
+#ifdef NONMATCHING
+void sub_80F890C(struct MailStruct *arg0, MainCallback arg1, bool8 arg2) {
+ u16 mailDesign;
+ u8 buffer[4];
+ u8 local1;
+
+ unk_2000000.varFF = GAME_LANGUAGE;
+
+ // Compiler uses [sub 1], while asm uses [ptr + FE]
+ unk_2000000.varFE = 1;
+ unk_2000000.var104 = (MainCallback) sub_80EB3FC;
+ unk_2000000.var108 = (MainCallback) ConvertEasyChatWordsToString;
+
+ mailDesign = arg0->var20 - ITEM_ORANGE_MAIL;
+
+ if (mailDesign <= 11) {
+ unk_2000000.varFA = arg0->var20 - ITEM_ORANGE_MAIL;
+ } else {
+ unk_2000000.varFA = 0;
+ arg2 = FALSE;
+ }
+
+ switch (unk_2000000.var100) {
+ case 0:
+ default:
+ unk_2000000.var10C = &gUnknown_083E5730[unk_2000000.varFA];
+ break;
+
+ case 1:
+ unk_2000000.var10C = &gUnknown_083E57A4[unk_2000000.varFA];
+ break;
+ }
+
+ if (((sub_80A2D64(arg0->var1E, buffer) << 16) +0xFFFF0000) <= (410 << 16)) {
+ switch (unk_2000000.varFA) {
+ case 6:
+ unk_2000000.varFB = 1;
+ break;
+
+ case 9:
+ unk_2000000.varFB = 2;
+ break;
+
+ default:
+ unk_2000000.varFB = 0;
+ break;
+ }
+ } else {
+ unk_2000000.varFB = 0;
+ }
+
+
+ unk_2000000.varF4 = arg0;
+ unk_2000000.varEC = arg1;
+ unk_2000000.varF8 = arg2;
+
+ SetMainCallback2(sub_80F8D50);
+}
+#else
+__attribute__((naked))
+void sub_80F890C(struct MailStruct *arg0, MainCallback arg1, bool8 arg2) {
+ asm(".syntax unified\n\
+ push {r4-r6,lr}\n\
+ sub sp, 0x4\n\
+ adds r4, r0, 0\n\
+ adds r6, r1, 0\n\
+ lsls r2, 24\n\
+ lsrs r5, r2, 24\n\
+ ldr r2, _080F8958 @ =0x02000000\n\
+ adds r1, r2, 0\n\
+ adds r1, 0xFF\n\
+ movs r0, 0x2\n\
+ strb r0, [r1]\n\
+ adds r0, 0xFE\n\
+ adds r1, r2, r0\n\
+ movs r0, 0x1\n\
+ strb r0, [r1]\n\
+ movs r0, 0x82\n\
+ lsls r0, 1\n\
+ adds r1, r2, r0\n\
+ ldr r0, _080F895C @ =sub_80EB3FC\n\
+ str r0, [r1]\n\
+ movs r0, 0x84\n\
+ lsls r0, 1\n\
+ adds r1, r2, r0\n\
+ ldr r0, _080F8960 @ =ConvertEasyChatWordsToString\n\
+ str r0, [r1]\n\
+ ldrh r1, [r4, 0x20]\n\
+ adds r0, r1, 0\n\
+ subs r0, 0x79\n\
+ lsls r0, 16\n\
+ lsrs r0, 16\n\
+ cmp r0, 0xB\n\
+ bhi _080F8964\n\
+ subs r1, 0x79\n\
+ adds r0, r2, 0\n\
+ adds r0, 0xFA\n\
+ strb r1, [r0]\n\
+ b _080F896E\n\
+ .align 2, 0\n\
+_080F8958: .4byte 0x02000000\n\
+_080F895C: .4byte sub_80EB3FC\n\
+_080F8960: .4byte ConvertEasyChatWordsToString\n\
+_080F8964:\n\
+ adds r1, r2, 0\n\
+ adds r1, 0xFA\n\
+ movs r0, 0\n\
+ strb r0, [r1]\n\
+ movs r5, 0\n\
+_080F896E:\n\
+ ldr r1, _080F8994 @ =0x02000000\n\
+ movs r2, 0x80\n\
+ lsls r2, 1\n\
+ adds r0, r1, r2\n\
+ ldrb r0, [r0]\n\
+ cmp r0, 0\n\
+ beq _080F8980\n\
+ cmp r0, 0x1\n\
+ beq _080F899C\n\
+_080F8980:\n\
+ movs r0, 0x86\n\
+ lsls r0, 1\n\
+ adds r2, r1, r0\n\
+ adds r0, r1, 0\n\
+ adds r0, 0xFA\n\
+ ldrb r0, [r0]\n\
+ lsls r0, 3\n\
+ ldr r1, _080F8998 @ =gUnknown_083E5730\n\
+ b _080F89AC\n\
+ .align 2, 0\n\
+_080F8994: .4byte 0x02000000\n\
+_080F8998: .4byte gUnknown_083E5730\n\
+_080F899C:\n\
+ movs r0, 0x86\n\
+ lsls r0, 1\n\
+ adds r2, r1, r0\n\
+ adds r0, r1, 0\n\
+ adds r0, 0xFA\n\
+ ldrb r0, [r0]\n\
+ lsls r0, 3\n\
+ ldr r1, _080F89DC @ =gUnknown_083E57A4\n\
+_080F89AC:\n\
+ adds r0, r1\n\
+ str r0, [r2]\n\
+ ldrh r0, [r4, 0x1E]\n\
+ mov r1, sp\n\
+ bl sub_80A2D64\n\
+ lsls r0, 16\n\
+ ldr r1, _080F89E0 @ =0xffff0000\n\
+ adds r0, r1\n\
+ movs r1, 0xCD\n\
+ lsls r1, 17\n\
+ cmp r0, r1\n\
+ bhi _080F89F8\n\
+ ldr r0, _080F89E4 @ =0x02000000\n\
+ adds r1, r0, 0\n\
+ adds r1, 0xFA\n\
+ ldrb r2, [r1]\n\
+ adds r1, r0, 0\n\
+ cmp r2, 0x6\n\
+ beq _080F89E8\n\
+ cmp r2, 0x9\n\
+ beq _080F89F0\n\
+ b _080F89FA\n\
+ .align 2, 0\n\
+_080F89DC: .4byte gUnknown_083E57A4\n\
+_080F89E0: .4byte 0xffff0000\n\
+_080F89E4: .4byte 0x02000000\n\
+_080F89E8:\n\
+ adds r2, r1, 0\n\
+ adds r2, 0xFB\n\
+ movs r0, 0x1\n\
+ b _080F8A00\n\
+_080F89F0:\n\
+ adds r2, r1, 0\n\
+ adds r2, 0xFB\n\
+ movs r0, 0x2\n\
+ b _080F8A00\n\
+_080F89F8:\n\
+ ldr r1, _080F8A20 @ =0x02000000\n\
+_080F89FA:\n\
+ adds r2, r1, 0\n\
+ adds r2, 0xFB\n\
+ movs r0, 0\n\
+_080F8A00:\n\
+ strb r0, [r2]\n\
+ adds r0, r1, 0\n\
+ adds r0, 0xF4\n\
+ str r4, [r0]\n\
+ subs r0, 0x8\n\
+ str r6, [r0]\n\
+ adds r0, 0xC\n\
+ strb r5, [r0]\n\
+ ldr r0, _080F8A24 @ =sub_80F8D50\n\
+ bl SetMainCallback2\n\
+ add sp, 0x4\n\
+ pop {r4-r6}\n\
+ pop {r0}\n\
+ bx r0\n\
+ .align 2, 0\n\
+_080F8A20: .4byte 0x02000000\n\
+_080F8A24: .4byte sub_80F8D50\n\
+ .syntax divided\n");
+}
+
+#endif
+
+#define RETURN_UP_STATE break
+#define RETURN_SKIP_STATE return FALSE
+
+static u8 sub_80F8A28(void) {
+ switch (gMain.state) {
+ case 0:
+ SetVBlankCallback(NULL);
+ remove_some_task();
+ REG_DISPCNT = 0;
+ RETURN_UP_STATE;
+
+ case 1: CpuFill16(0, (void *) OAM, OAM_SIZE);
+ RETURN_UP_STATE;
+
+ case 2:
+ ResetPaletteFade();
+ RETURN_UP_STATE;
+
+ case 3:
+ ResetTasks();
+ RETURN_UP_STATE;
+
+ case 4:
+ ResetSpriteData();
+ RETURN_UP_STATE;
+
+ case 5:
+ FreeAllSpritePalettes();
+ REG_BG0HOFS = 0;
+ REG_BG0VOFS = 0;
+ REG_BG1HOFS = 0;
+ REG_BG1VOFS = 0;
+ REG_BG2VOFS = 0;
+ REG_BG2HOFS = 0;
+ REG_BG3HOFS = 0;
+ REG_BG3VOFS = 0;
+ REG_BLDCNT = 0;
+ REG_BLDALPHA = 0;
+ RETURN_UP_STATE;
+
+ case 6:
+ SetUpWindowConfig(&gWindowConfig_81E6DFC);
+ RETURN_UP_STATE;
+
+ case 7:
+ MultistepInitMenuWindowBegin(&gWindowConfig_81E6DFC);
+ RETURN_UP_STATE;
+
+ case 8:
+ if (MultistepInitMenuWindowContinue() == 0) {
+ return FALSE;
+ }
+ RETURN_UP_STATE;
+
+ case 9:
+ MenuZeroFillScreen();
+ RETURN_UP_STATE;
+
+ case 10: CpuFill16(1, (void *) (VRAM + 0x4800), 0x800);
+ RETURN_UP_STATE;
+
+ case 11:
+ LoadPalette(gMailGraphicsTable[unk_2000000.varFA].palette, 0, 16 * 2);
+ RETURN_UP_STATE;
+
+ case 12:
+ LZ77UnCompVram(gMailGraphicsTable[unk_2000000.varFA].tileMap, (void *) (VRAM + 0x4000));
+ RETURN_UP_STATE;
+
+ case 13:
+ LZ77UnCompVram(gMailGraphicsTable[unk_2000000.varFA].tiles, (void *) (VRAM));
+
+ gPlttBufferUnfaded[241] = gMailGraphicsTable[unk_2000000.varFA].color10;
+ gPlttBufferUnfaded[248] = gMailGraphicsTable[unk_2000000.varFA].color12;
+ gPlttBufferUnfaded[10] = gUnknown_083E562C[gSaveBlock2.playerGender][0];
+ gPlttBufferUnfaded[11] = gUnknown_083E562C[gSaveBlock2.playerGender][1];
+ RETURN_UP_STATE;
+
+ case 14:
+ if (unk_2000000.varF8 != 0) {
+ sub_80F8DA0();
+ }
+ RETURN_UP_STATE;
+
+ case 15:
+ if (unk_2000000.varF8 != 0) {
+ sub_80F8E80();
+ }
+
+ SetVBlankCallback(sub_80F8F18);
+ gPaletteFade.bufferTransferDisabled = 1;
+ RETURN_UP_STATE;
+
+ case 16: {
+ u16 local1;
+
+ local1 = sub_809D4A8(unk_2000000.varF4->var1E);
+
+ switch (unk_2000000.varFB) {
+ case 1:
+ sub_809D580(local1);
+ unk_2000000.varFC = sub_809D3A4(local1, SpriteCallbackDummy, 96, 128, 0);
+ break;
+
+ case 2:
+ sub_809D580(local1);
+ unk_2000000.varFC = sub_809D3A4(local1, SpriteCallbackDummy, 40, 128, 0);
+ break;
+ }
+ RETURN_UP_STATE;
+ }
+
+ case 17:
+ if (sub_8055870() != TRUE) {
+ RETURN_UP_STATE;
+ }
+ RETURN_SKIP_STATE;
+
+ case 18:
+ REG_BG0CNT = 0x9F08;
+ REG_BG1CNT = 0x0801;
+ REG_BG2CNT = 0x0902;
+ REG_BLDCNT = 0;
+ REG_DISPCNT = DISPCNT_OBJ_1D_MAP | DISPCNT_BG0_ON | DISPCNT_BG1_ON | DISPCNT_BG2_ON | DISPCNT_OBJ_ON;
+ BeginNormalPaletteFade(-1, 0, 16, 0, 0);
+ gPaletteFade.bufferTransferDisabled = 0;
+ unk_2000000.varF0 = sub_80F8F58;
+ return TRUE;
+
+ default:
+ return FALSE;
+ }
+
+ gMain.state += 1;
+ return FALSE;
+}
+
+void sub_80F8D50(void) {
+ do {
+ if (sub_80F8A28() == 1) {
+ SetMainCallback2(sub_80F8F2C);
+ return;
+ }
+ } while (sub_80F9344() != 1);
+}
+
+u8 *sub_80F8D7C(u8 *dest, u8 *src) {
+ u16 length;
+
+ StringCopy(dest, src);
+ sub_814A568(dest);
+
+ length = StringLength(dest);
+
+ return dest + length;
+}
+
+#ifdef NONMATCHING
+static void sub_80F8DA0(void) {
+ u8 local0;
+
+ local0 = unk_2000000.var10C->var0;
+
+ // No idea what's happening in this loop.
+ if (local0 <= 0) {
+ u8 i;
+ u8 i2 = 0;
+
+ for (i = 0; i < unk_2000000.var10C->var0; i++) {
+ ConvertEasyChatWordsToString(unk_2000000.words[i], &unk_2000000.varF4->words[i2],
+ ((*unk_2000000.var10C->var4)[i] << 28) >> 30, 1);
+ i2 += ((*unk_2000000.var10C->var4)[i] << 28) >> 30;
+ }
+ }
+
+ if (unk_2000000.var100 == 0) {
+ u8 *ptr;
+ u16 length;
+
+ ptr = sub_80F8D7C(unk_2000000.varD8, unk_2000000.varF4->var12);
+ StringCopy(ptr, gOtherText_From);
+
+ length = StringLength(unk_2000000.varD8);
+
+ unk_2000000.varF9 = unk_2000000.var10C->var2 - length;
+ } else {
+ u8 *ptr;
+
+ ptr = StringCopy(unk_2000000.varD8, gOtherText_From);
+ sub_80F8D7C(ptr, unk_2000000.varF4->var12);
+
+ unk_2000000.varF9 = unk_2000000.var10C->var2;
+ }
+}
+#else
+__attribute__((naked))
+static void sub_80F8DA0(void) {
+ asm(".syntax unified\n\
+ push {r4-r7,lr}\n\
+ mov r7, r8\n\
+ push {r7}\n\
+ movs r6, 0\n\
+ movs r5, 0\n\
+ ldr r2, _080F8E3C @ =0x02000000\n\
+ movs r0, 0x86\n\
+ lsls r0, 1\n\
+ adds r1, r2, r0\n\
+ ldr r0, [r1]\n\
+ ldrb r0, [r0]\n\
+ cmp r5, r0\n\
+ bcs _080F8E04\n\
+ mov r8, r2\n\
+ adds r7, r1, 0\n\
+_080F8DBE:\n\
+ lsls r0, r5, 3\n\
+ subs r0, r5\n\
+ lsls r0, 2\n\
+ subs r0, r5\n\
+ add r0, r8\n\
+ mov r1, r8\n\
+ adds r1, 0xF4\n\
+ lsls r2, r6, 1\n\
+ ldr r1, [r1]\n\
+ adds r1, r2\n\
+ ldr r2, [r7]\n\
+ ldr r2, [r2, 0x4]\n\
+ lsls r4, r5, 2\n\
+ adds r2, r4, r2\n\
+ ldr r2, [r2]\n\
+ lsls r2, 28\n\
+ lsrs r2, 30\n\
+ movs r3, 0x1\n\
+ bl ConvertEasyChatWordsToString\n\
+ ldr r1, [r7]\n\
+ ldr r0, [r1, 0x4]\n\
+ adds r4, r0\n\
+ ldr r0, [r4]\n\
+ lsls r0, 28\n\
+ lsrs r0, 30\n\
+ adds r0, r6, r0\n\
+ lsls r0, 24\n\
+ lsrs r6, r0, 24\n\
+ adds r0, r5, 0x1\n\
+ lsls r0, 16\n\
+ lsrs r5, r0, 16\n\
+ ldrb r1, [r1]\n\
+ cmp r5, r1\n\
+ bcc _080F8DBE\n\
+_080F8E04:\n\
+ ldr r2, _080F8E40 @ =0x020000d8\n\
+ adds r4, r2, 0\n\
+ subs r4, 0xD8\n\
+ adds r0, r2, 0\n\
+ adds r0, 0x28\n\
+ ldrb r0, [r0]\n\
+ cmp r0, 0\n\
+ bne _080F8E48\n\
+ ldr r1, [r2, 0x1C]\n\
+ adds r1, 0x12\n\
+ adds r0, r2, 0\n\
+ bl sub_80F8D7C\n\
+ adds r2, r0, 0\n\
+ ldr r1, _080F8E44 @ =gOtherText_From\n\
+ bl StringCopy\n\
+ ldr r0, _080F8E40 @ =0x020000d8\n\
+ bl StringLength\n\
+ movs r2, 0x86\n\
+ lsls r2, 1\n\
+ adds r1, r4, r2\n\
+ ldr r1, [r1]\n\
+ ldrb r1, [r1, 0x2]\n\
+ subs r1, r0\n\
+ b _080F8E6A\n\
+ .align 2, 0\n\
+_080F8E3C: .4byte 0x02000000\n\
+_080F8E40: .4byte 0x020000d8\n\
+_080F8E44: .4byte gOtherText_From\n\
+_080F8E48:\n\
+ ldr r1, _080F8E7C @ =gOtherText_From\n\
+ adds r0, r2, 0\n\
+ bl StringCopy\n\
+ adds r2, r0, 0\n\
+ adds r0, r4, 0\n\
+ adds r0, 0xF4\n\
+ ldr r1, [r0]\n\
+ adds r1, 0x12\n\
+ adds r0, r2, 0\n\
+ bl sub_80F8D7C\n\
+ movs r1, 0x86\n\
+ lsls r1, 1\n\
+ adds r0, r4, r1\n\
+ ldr r0, [r0]\n\
+ ldrb r1, [r0, 0x2]\n\
+_080F8E6A:\n\
+ adds r0, r4, 0\n\
+ adds r0, 0xF9\n\
+ strb r1, [r0]\n\
+ pop {r3}\n\
+ mov r8, r3\n\
+ pop {r4-r7}\n\
+ pop {r0}\n\
+ bx r0\n\
+ .align 2, 0\n\
+_080F8E7C: .4byte gOtherText_From\n\
+ .syntax divided\n");
+}
+#endif
+
+static void sub_80F8E80(void) {
+ u16 pos;
+ u8 x;
+ u8 y = 0;
+
+ for (pos = 0; pos < unk_2000000.var10C->var0; pos++) {
+ if (unk_2000000.words[pos][0] == 0xFF) {
+ continue;
+ }
+
+ if (unk_2000000.words[pos][0] == 0x00) {
+ continue;
+ }
+
+ x = unk_2000000.var10C->var4[pos].unk_0_4;
+ y += unk_2000000.var10C->var4[pos].unk_0_0;
+ MenuPrint(unk_2000000.words[pos], unk_2000000.var10C->var3_4 + x, unk_2000000.var10C->var3_0 + y);
+ y += 2;
+ }
+
+ MenuPrint(unk_2000000.varD8, unk_2000000.varF9, unk_2000000.var10C->var1);
+}
+
+static void sub_80F8F18(void) {
+ LoadOam();
+ ProcessSpriteCopyRequests();
+ TransferPlttBuffer();
+}
+
+static void sub_80F8F2C(void) {
+ if(unk_2000000.varFB != 0) {
+ AnimateSprites();
+ BuildOamBuffer();
+ }
+
+ unk_2000000.varF0();
+}
+
+static void sub_80F8F58(void) {
+ u8 local0;
+
+ local0 = UpdatePaletteFade();
+ if(local0 == 0) {
+ unk_2000000.varF0 = sub_80F8F78;
+ }
+}
+
+static void sub_80F8F78(void) {
+ if (gMain.newKeys & (A_BUTTON | B_BUTTON)) {
+ BeginNormalPaletteFade(-1, 0, 0, 16, 0);
+ unk_2000000.varF0 = sub_80F8FB4;
+ }
+}
+
+static void sub_80F8FB4(void) {
+ u16 local1;
+
+ if (UpdatePaletteFade()) {
+ return;
+ }
+
+ SetMainCallback2(unk_2000000.varEC);
+ switch (unk_2000000.varFB) {
+ case 2:
+ case 1:
+ local1 = sub_809D4A8(unk_2000000.varF4->var1E);
+ sub_809D608(local1);
+
+ sub_809D510(&gSprites[unk_2000000.varFC]);
+ break;
+ }
+
+ memset(&unk_2000000, 0, 0x110);
+ ResetPaletteFade();
+}
diff --git a/src/main.c b/src/main.c
index ad131547b..a3d5c4f30 100644
--- a/src/main.c
+++ b/src/main.c
@@ -1,17 +1,18 @@
#include "global.h"
#include "main.h"
#include "asm.h"
-#include "play_time.h"
-#include "m4a.h"
-#include "gba/m4a_internal.h"
#include "gba/flash_internal.h"
-#include "siirtc.h"
-#include "rtc.h"
+#include "gba/m4a_internal.h"
+#include "intro.h"
#include "link.h"
+#include "load_save.h"
+#include "m4a.h"
+#include "play_time.h"
#include "rng.h"
#include "rom4.h"
+#include "rtc.h"
+#include "siirtc.h"
#include "sound.h"
-#include "intro.h"
extern struct SoundInfo gSoundInfo;
extern u32 gUnknown_3004820;
@@ -31,7 +32,7 @@ static void IntrDummy(void);
const u8 gGameVersion = GAME_VERSION;
-const u8 gGameLanguage = 2; // English
+const u8 gGameLanguage = GAME_LANGUAGE; // English
const char BuildDateTime[] = "2002 10 15 20:34";
diff --git a/src/main_menu.c b/src/main_menu.c
index 274386b03..9842d6f39 100644
--- a/src/main_menu.c
+++ b/src/main_menu.c
@@ -3,6 +3,7 @@
#include "asm.h"
#include "decompress.h"
#include "menu.h"
+#include "mystery_event_menu.h"
#include "option_menu.h"
#include "palette.h"
#include "rom4.h"
diff --git a/src/matsuda_debug_menu.c b/src/matsuda_debug_menu.c
index 18f644cbb..df2ca3206 100644
--- a/src/matsuda_debug_menu.c
+++ b/src/matsuda_debug_menu.c
@@ -1,12 +1,15 @@
#include "global.h"
+#include "asm.h"
+#include "link.h"
#include "main.h"
#include "menu.h"
#include "palette.h"
-#include "task.h"
-#include "link.h"
-#include "text.h"
+#include "rom4.h"
#include "sprite.h"
+#include "start_menu.h"
#include "string_util.h"
+#include "task.h"
+#include "text.h"
#define BIT(n) (1 << (n))
@@ -16,30 +19,6 @@ extern u8 gContestPlayerMonIndex;
extern u16 gScriptContestCategory;
extern u16 gScriptContestRank;
extern u8 (*gCallback_03004AE8)(void);
-extern void sub_80034D4(u8 *, u8 *);
-extern void sub_80AF668(void);
-extern void sub_80C2358(void);
-extern void sub_8071C20(void);
-extern void sub_80AA10C(void);
-extern void sub_80A9C98(u8);
-extern void sub_80C8734(void);
-extern void sub_80A9CC0(u8);
-extern void sub_80C88AC(u8);
-extern void sub_80A9CDC(u8);
-extern void sub_80C8E1C(u8);
-extern void sub_80A9D58(u8);
-extern void sub_80C8EBC(u8);
-extern void sub_80A9DBC(u8);
-extern u8 sub_80C4B34(u8 *);
-extern void sub_80B0F28(u8);
-extern void sub_80C8F34(u8);
-extern void sub_80A9DD8(u8);
-extern void sub_80A9F10(u8);
-extern void sub_805469C(void);
-extern void sub_80AE398(u8, u8);
-extern void sub_80AE098(u8);
-extern void sub_80AA5BC(u8);
-extern u32 sub_80AE770(u8, u8);
extern struct Window gMenuWindow;
@@ -64,16 +43,16 @@ extern u8 gMatsudaDebugMenu_GoBackText[];
extern u8 gMatsudaDebugMenu_BattlePointsText[];
extern u8 gMatsudaDebugMenu_StartText[];
-extern u8 gUnknown_083C92BC[];
-extern u8 gUnknown_083C92B4[];
+extern struct SpritePalette gUnknown_083C92BC;
+extern struct SpriteSheet gUnknown_083C92B4;
extern struct SpriteTemplate gSpriteTemplate_83C92CC;
extern u8 gMoveNames[][13];
extern u8 gMatsudaDebugMenu_UnknownByteArray[];
-extern u32 gMatsudaDebugMenuTextList1[];
-extern u32 gMatsudaDebugMenuTextList2[];
-extern u32 gMatsudaDebugMenuTextList3[];
+extern u8* gMatsudaDebugMenuTextList1[];
+extern u8* gMatsudaDebugMenuTextList2[];
+extern u8* gMatsudaDebugMenuTextList3[];
extern u8 gMatsudaDebugMenuContestTopLeft[][2];
struct ContestPokemon
@@ -97,24 +76,24 @@ extern struct ContestPokemon gContestMons[];
extern bool8 gReceivedRemoteLinkPlayers;
extern u16 gBlockRecvBuffer[MAX_LINK_PLAYERS][BLOCK_BUFFER_SIZE / 2];
-struct DebugMenuAction
-{
- u8 *text;
- u8 (*func)(void);
-};
-
-extern struct DebugMenuAction gMatsudaDebugMenuActions[];
-
-s8 sub_80A9B78(void);
-void sub_80A9BE4(u8 taskId);
-void sub_80A9E04(u8 taskId);
-void sub_80A9E3C(u8 taskId);
-void sub_80A9ED8(u8);
-void sub_80A9E80(u8);
-void sub_80AA280(u8);
-void sub_80AA5E8(u8);
-void sub_80AA614(u8, u8);
-void sub_80AA658(u8);
+extern struct MenuAction gMatsudaDebugMenuActions[];
+
+static bool8 sub_80A9B78(void);
+static void sub_80A9BE4(u8 taskId);
+static void sub_80A9C98(u8);
+static void sub_80A9CC0(u8);
+static void sub_80A9CDC(u8);
+static void sub_80A9D58(u8);
+static void sub_80A9DBC(u8);
+static void sub_80A9DD8(u8);
+static void sub_80A9E04(u8 taskId);
+static void sub_80A9E3C(u8 taskId);
+static void sub_80A9E80(u8);
+static void sub_80A9ED8(u8);
+static void sub_80A9F10(u8);
+static void sub_80AA10C(void);
+static void sub_80AA5BC(u8);
+static void sub_80AA614(u8, u8);
u8 unref_sub_80A9B28(void)
{
@@ -126,20 +105,20 @@ u8 unref_sub_80A9B28(void)
return 0;
}
-s8 sub_80A9B78(void)
+static bool8 sub_80A9B78(void)
{
s8 choice = ProcessMenuInput();
switch(choice)
{
case -2:
- return 0;
+ return FALSE;
default:
gCallback_03004AE8 = gMatsudaDebugMenuActions[choice].func;
- return 0;
+ return FALSE;
case -1:
sub_8071C20();
- return 1;
+ return TRUE;
}
}
@@ -150,7 +129,7 @@ s8 MatsudaDebugMenu_ContestResults(void)
return 1;
}
-void sub_80A9BE4(u8 taskId)
+static void sub_80A9BE4(u8 taskId)
{
if(!gPaletteFade.active)
{
@@ -189,23 +168,23 @@ s8 MatsudaDebugMenu_CommTest(void)
return 1;
}
-void sub_80A9C98(u8 taskId)
+static void sub_80A9C98(u8 taskId)
{
sub_80AE098(0);
SetTaskFuncWithFollowupFunc(taskId, sub_80C8734, sub_80A9CC0);
}
-void sub_80A9CC0(u8 taskId)
+static void sub_80A9CC0(u8 taskId)
{
SetTaskFuncWithFollowupFunc(taskId, sub_80C88AC, sub_80A9CDC);
}
-void sub_80A9CDC(u8 taskId)
+static void sub_80A9CDC(u8 taskId)
{
SetTaskFuncWithFollowupFunc(taskId, sub_80C8E1C, sub_80A9D58);
}
-void sub_80A9CF8(u8 taskId)
+static void sub_80A9CF8(u8 taskId)
{
if(gReceivedRemoteLinkPlayers == FALSE)
{
@@ -215,13 +194,13 @@ void sub_80A9CF8(u8 taskId)
}
}
-void sub_80A9D30(u8 taskId)
+static void sub_80A9D30(u8 taskId)
{
sub_800832C();
gTasks[taskId].func = sub_80A9CF8;
}
-void sub_80A9D58(u8 taskId)
+static void sub_80A9D58(u8 taskId)
{
int i;
u8 dest[4];
@@ -229,31 +208,31 @@ void sub_80A9D58(u8 taskId)
for(i = 0; i < 4; i++)
dest[i] = gTasks[taskId].data[5 + i];
- gUnknown_0203869B = sub_80C4B34(&dest);
+ gUnknown_0203869B = sub_80C4B34(dest);
sub_80AE82C((u8)gScriptContestCategory);
sub_80B0F28(0);
SetTaskFuncWithFollowupFunc(taskId, sub_80C8EBC, sub_80A9DBC);
}
-void sub_80A9DBC(u8 taskId)
+static void sub_80A9DBC(u8 taskId)
{
SetTaskFuncWithFollowupFunc(taskId, sub_80C8F34, sub_80A9DD8);
}
-void sub_80A9DD8(u8 taskId)
+static void sub_80A9DD8(u8 taskId)
{
DestroyTask(gTasks[taskId].data[10]);
DestroyTask(taskId);
sub_8071C20();
}
-void sub_80A9E04(u8 taskId)
+static void sub_80A9E04(u8 taskId)
{
if(gMain.newKeys == 2)
gTasks[(u8)gTasks[taskId].data[10]].func = sub_80A9D30;
}
-void sub_80A9E3C(u8 taskId)
+static void sub_80A9E3C(u8 taskId)
{
u8 i;
@@ -266,7 +245,7 @@ void sub_80A9E3C(u8 taskId)
gTasks[taskId].func = sub_80A9E80;
}
-void sub_80A9E80(u8 taskId)
+static void sub_80A9E80(u8 taskId)
{
TaskFunc func;
@@ -292,7 +271,7 @@ void sub_80A9E80(u8 taskId)
}
}
-void sub_80A9ED8(u8 taskId)
+static void sub_80A9ED8(u8 taskId)
{
gTasks[taskId].data[0] = gTasks[taskId].data[0] + 1;
if((gTasks[taskId].data[0]) == 101)
@@ -303,7 +282,7 @@ void sub_80A9ED8(u8 taskId)
}
}
-void sub_80A9F10(u8 taskId)
+static void sub_80A9F10(u8 taskId)
{
if(gReceivedRemoteLinkPlayers)
{
@@ -316,7 +295,7 @@ void sub_80A9F10(u8 taskId)
}
}
-void sub_80A9F50(void)
+static void sub_80A9F50(void)
{
REG_DISPCNT = DISPCNT_OBJ_1D_MAP;
REG_DISPCNT |= DISPCNT_OBJ_ON | DISPCNT_BG0_ON;
@@ -338,7 +317,7 @@ void sub_80A9F50(void)
gUnknown_030041B8 = 0;
}
-void sub_80A9FE4(void)
+static void sub_80A9FE4(void)
{
u8 *addr;
u32 i;
@@ -360,11 +339,11 @@ void sub_80A9FE4(void)
break;
}
}
- sub_80034D4(VRAM, &ptr);
+ sub_80034D4((void *)VRAM, ptr);
LoadFontDefaultPalette(&gWindowConfig_81E6C3C);
}
-void sub_80AA064(void)
+static void sub_80AA064(void)
{
AnimateSprites();
BuildOamBuffer();
@@ -374,7 +353,7 @@ void sub_80AA064(void)
SetMainCallback2(sub_805469C);
}
-void sub_80AA090(void)
+static void sub_80AA090(void)
{
REG_BG0HOFS = gUnknown_030042A4;
REG_BG0VOFS = gUnknown_030042A0;
@@ -390,7 +369,7 @@ void sub_80AA090(void)
sub_8089668();
}
-void sub_80AA10C(void)
+static void sub_80AA10C(void)
{
u8 i;
u8 zero;
@@ -428,8 +407,8 @@ void sub_80AA10C(void)
sub_80AA5E8(gScriptContestRank);
sub_8003460(&gMenuWindow, gMatsudaDebugMenu_GoBackText, 0xD6, 0x12, 0x12);
sub_8003460(&gMenuWindow, gMatsudaDebugMenu_BattlePointsText, 0xDC, zero, 0xC);
- LoadSpriteSheet(gUnknown_083C92B4);
- LoadSpritePalette(gUnknown_083C92BC);
+ LoadSpriteSheet(&gUnknown_083C92B4);
+ LoadSpritePalette(&gUnknown_083C92BC);
sub_80AA280(3);
sub_80AA658(3);
sub_80AA614(3, zero);
@@ -445,7 +424,7 @@ void sub_80AA280(u8 var)
u8 i;
FillWindowRect_DefaultPalette(&gMenuWindow, 0, 0, 0, 0x1E, 3);
- StringCopy(unk_2000000, &gMatsudaDebugMenu_StartText);
+ StringCopy(unk_2000000, gMatsudaDebugMenu_StartText);
StringAppend(unk_2000000, &gUnknown_0203857D[var][0]);
for(i = 0; i < 4; i++)
@@ -462,43 +441,43 @@ void sub_80AA280(u8 var)
}
}
-void sub_80AA340(u8 var)
+static void sub_80AA340(u8 var)
{
ConvertIntToDecimalStringN(unk_2000000, gContestMons[var].cool, STR_CONV_MODE_RIGHT_ALIGN, 3);
sub_8003460(&gMenuWindow, unk_2000000, 0x66, gUnknown_083C9282[0], gUnknown_083C9282[1]);
}
-void sub_80AA388(u8 var)
+static void sub_80AA388(u8 var)
{
ConvertIntToDecimalStringN(unk_2000000, gContestMons[var].cute, STR_CONV_MODE_RIGHT_ALIGN, 3);
sub_8003460(&gMenuWindow, unk_2000000, 0x6C, gUnknown_083C9282[2], gUnknown_083C9282[3]);
}
-void sub_80AA3D0(u8 var)
+static void sub_80AA3D0(u8 var)
{
ConvertIntToDecimalStringN(unk_2000000, gContestMons[var].beauty, STR_CONV_MODE_RIGHT_ALIGN, 3);
sub_8003460(&gMenuWindow, unk_2000000, 0x72, gUnknown_083C9282[4], gUnknown_083C9282[5]);
}
-void sub_80AA418(u8 var)
+static void sub_80AA418(u8 var)
{
ConvertIntToDecimalStringN(unk_2000000, gContestMons[var].smart, STR_CONV_MODE_RIGHT_ALIGN, 3);
sub_8003460(&gMenuWindow, unk_2000000, 0x78, gUnknown_083C9282[6], gUnknown_083C9282[7]);
}
-void sub_80AA460(u8 var)
+static void sub_80AA460(u8 var)
{
ConvertIntToDecimalStringN(unk_2000000, gContestMons[var].tough, STR_CONV_MODE_RIGHT_ALIGN, 3);
sub_8003460(&gMenuWindow, unk_2000000, 0x7E, gUnknown_083C9282[8], gUnknown_083C9282[9]);
}
-void sub_80AA4A8(u8 var)
+static void sub_80AA4A8(u8 var)
{
ConvertIntToDecimalStringN(unk_2000000, gContestMons[var].sheen, STR_CONV_MODE_RIGHT_ALIGN, 3);
sub_8003460(&gMenuWindow, unk_2000000, 0x84, gUnknown_083C9282[10], gUnknown_083C9282[11]);
}
-void sub_80AA4F0(u8 var1, u8 var2)
+static void sub_80AA4F0(u8 var1, u8 var2)
{
FillWindowRect_DefaultPalette(&gMenuWindow, 0, gUnknown_083C928E[var2][0], gUnknown_083C928E[var2][1], gUnknown_083C928E[var2][0] + 7, gUnknown_083C928E[var2][1] + 1);
sub_8003460(&gMenuWindow, gMoveNames[gContestMons[var1].moves[var2]], 0x8A + var2 * 14, gUnknown_083C928E[var2][0], gUnknown_083C928E[var2][1]);
@@ -506,7 +485,7 @@ void sub_80AA4F0(u8 var1, u8 var2)
sub_8003460(&gMenuWindow, gStringVar1, 0xFA + var2 * 6, gUnknown_083C928E[var2][0] + 7, gUnknown_083C928E[var2][1]);
}
-void sub_80AA5BC(u8 var)
+static void sub_80AA5BC(u8 var)
{
sub_8003460(&gMenuWindow, gMatsudaDebugMenuTextList2[var], 0xC2, 3, 0x12);
}
@@ -516,7 +495,7 @@ void sub_80AA5E8(u8 var)
sub_8003460(&gMenuWindow, gMatsudaDebugMenuTextList3[var], 0xE8, 3, 4);
}
-void sub_80AA614(u8 var1, u8 var2)
+static void sub_80AA614(u8 var1, u8 var2)
{
u16 var = sub_80AE770(var1, var2);
@@ -541,16 +520,16 @@ void sub_80AA658(u8 var)
void SetDebugMonForContest(void)
{
- SetMonData(&gPlayerParty, MON_DATA_COOL, &gContestMons[gContestPlayerMonIndex].cool);
- SetMonData(&gPlayerParty, MON_DATA_CUTE, &gContestMons[gContestPlayerMonIndex].cute);
- SetMonData(&gPlayerParty, MON_DATA_BEAUTY, &gContestMons[gContestPlayerMonIndex].beauty);
- SetMonData(&gPlayerParty, MON_DATA_SMART, &gContestMons[gContestPlayerMonIndex].smart);
- SetMonData(&gPlayerParty, MON_DATA_TOUGH, &gContestMons[gContestPlayerMonIndex].tough);
- SetMonData(&gPlayerParty, MON_DATA_SHEEN, &gContestMons[gContestPlayerMonIndex].sheen);
- SetMonData(&gPlayerParty, MON_DATA_MOVE1, &gContestMons[gContestPlayerMonIndex].moves[0]);
- SetMonData(&gPlayerParty, MON_DATA_MOVE2, &gContestMons[gContestPlayerMonIndex].moves[1]);
- SetMonData(&gPlayerParty, MON_DATA_MOVE3, &gContestMons[gContestPlayerMonIndex].moves[2]);
- SetMonData(&gPlayerParty, MON_DATA_MOVE4, &gContestMons[gContestPlayerMonIndex].moves[3]);
+ SetMonData(&gPlayerParty[0], MON_DATA_COOL, &gContestMons[gContestPlayerMonIndex].cool);
+ SetMonData(&gPlayerParty[0], MON_DATA_CUTE, &gContestMons[gContestPlayerMonIndex].cute);
+ SetMonData(&gPlayerParty[0], MON_DATA_BEAUTY, &gContestMons[gContestPlayerMonIndex].beauty);
+ SetMonData(&gPlayerParty[0], MON_DATA_SMART, &gContestMons[gContestPlayerMonIndex].smart);
+ SetMonData(&gPlayerParty[0], MON_DATA_TOUGH, &gContestMons[gContestPlayerMonIndex].tough);
+ SetMonData(&gPlayerParty[0], MON_DATA_SHEEN, &gContestMons[gContestPlayerMonIndex].sheen);
+ SetMonData(&gPlayerParty[0], MON_DATA_MOVE1, (const u8 *) &gContestMons[gContestPlayerMonIndex].moves[0]);
+ SetMonData(&gPlayerParty[0], MON_DATA_MOVE2, (const u8 *) &gContestMons[gContestPlayerMonIndex].moves[1]);
+ SetMonData(&gPlayerParty[0], MON_DATA_MOVE3, (const u8 *) &gContestMons[gContestPlayerMonIndex].moves[2]);
+ SetMonData(&gPlayerParty[0], MON_DATA_MOVE4, (const u8 *) &gContestMons[gContestPlayerMonIndex].moves[3]);
}
// too complicated
@@ -735,7 +714,7 @@ _080AA89C: .4byte gUnknown_083C92A8\n\
.syntax divided");
}
-void sub_80AA8A0(struct Sprite *sprite, s8 var1, u8 var2)
+static void sub_80AA8A0(struct Sprite *sprite, s8 var1, u8 var2)
{
if(var1 == 1)
{
@@ -765,7 +744,7 @@ void sub_80AA8F8(struct Sprite *sprite, s8 var1)
sub_80AA8A0(sprite, var1, 3);
}
-u8 sub_80AA908(u32 a1, u8 a2, s8 a3) // first param is unused.
+static u8 sub_80AA908(u32 a1, u8 a2, s8 a3) // first param is unused.
{
s16 val = a2 + a3;
@@ -826,7 +805,7 @@ void sub_80AAA84(struct Sprite *sprite, u8 var2)
}
// a similar function is at 0x80AA908, however, it apparently returns the wrong type (u8 vs u16).
-u16 sub_80AAAC8(u32 a1, u16 a2, s8 a3) // first param is unused.
+static u16 sub_80AAAC8(u32 a1, u16 a2, s8 a3) // first param is unused.
{
s16 val = a2 + a3;
diff --git a/src/menu.c b/src/menu.c
index 0b5eab831..a06463ba3 100644
--- a/src/menu.c
+++ b/src/menu.c
@@ -6,6 +6,8 @@
#include "text_window.h"
#include "sound.h"
#include "menu_cursor.h"
+#include "map_obj_lock.h"
+#include "script.h"
struct Menu
{
@@ -24,8 +26,8 @@ static void MultistepInitMenuWindowInternal(const struct WindowConfig *, u16);
static void InitMenuWindowInternal(const struct WindowConfig *, u16);
static bool8 sub_80723D4(void);
static u8 sub_8072484(u8, u8, u8, u8, u8, u8, u32);
-static u8 sub_80724F4(u8, u8, u8, u8 * const [][2], u8);
-static void sub_8072620(u8, u8, u8, u8 * const [][2], u8);
+static u8 sub_80724F4(u8, u8, u8, const struct MenuAction[], u8);
+static void sub_8072620(u8, u8, u8, const struct MenuAction[], u8);
static void sub_8072D18(u8, u8);
static struct Menu gMenu;
@@ -41,6 +43,21 @@ EWRAM_DATA u16 gMenuMessageBoxContentTileOffset = 0;
extern const struct MenuAction gUnknown_08376D74[];
+void sub_8071C20(void)
+{
+ PlaySE(SE_SELECT);
+ MenuZeroFillScreen();
+ sub_8064E2C();
+ ScriptContext2_Disable();
+ sub_8072DEC();
+}
+
+void AppendToList(u8 *list, u8 *pindex, u32 value)
+{
+ list[*pindex] = value;
+ (*pindex)++;
+}
+
void InitMenuWindow(const struct WindowConfig *winConfig)
{
InitMenuWindowInternal(winConfig, 1);
@@ -390,7 +407,7 @@ static u8 sub_8072484(u8 a1, u8 a2, u8 menuItemCount, u8 a4, u8 width, u8 a6, u3
return a4;
}
-static u8 sub_80724F4(u8 left, u8 top, u8 menuItemCount, u8 * const menuItems[][2], u8 columnCount)
+static u8 sub_80724F4(u8 left, u8 top, u8 menuItemCount, const struct MenuAction menuItems[], u8 columnCount)
{
u8 i;
u8 maxWidth;
@@ -402,7 +419,7 @@ static u8 sub_80724F4(u8 left, u8 top, u8 menuItemCount, u8 * const menuItems[][
maxWidth = 0;
for (i = 0; i < menuItemCount; i++)
{
- u8 width = (sub_8072CA4(menuItems[i][0]) + 7) / 8;
+ u8 width = (sub_8072CA4(menuItems[i].text) + 7) / 8;
if (width > maxWidth)
maxWidth = width;
@@ -448,7 +465,7 @@ static u8 sub_80724F4(u8 left, u8 top, u8 menuItemCount, u8 * const menuItems[][
return maxWidth;
}
-static void sub_8072620(u8 left, u8 top, u8 menuItemCount, u8 * const menuItems[][2], u8 columnCount)
+static void sub_8072620(u8 left, u8 top, u8 menuItemCount, const struct MenuAction menuItems[], u8 columnCount)
{
u8 i;
u8 maxWidth;
@@ -459,7 +476,7 @@ static void sub_8072620(u8 left, u8 top, u8 menuItemCount, u8 * const menuItems[
maxWidth = 0;
for (i = 0; i < menuItemCount; i++)
{
- u8 width = (sub_8072CA4(menuItems[i][0]) + 7) / 8;
+ u8 width = (sub_8072CA4(menuItems[i].text) + 7) / 8;
if (width > maxWidth)
maxWidth = width;
@@ -478,11 +495,11 @@ static void sub_8072620(u8 left, u8 top, u8 menuItemCount, u8 * const menuItems[
u8 row = 0;
u8 j;
for (j = 0; i + j < menuItemCount; j += columnCount, row++)
- MenuPrint(menuItems[i + j][0], left + gMenu.columnXCoords[i % columnCount], top + 2 * row);
+ MenuPrint(menuItems[i + j].text, left + gMenu.columnXCoords[i % columnCount], top + 2 * row);
}
}
-void sub_807274C(u8 left, u8 top, u8 menuItemCount, u8 a4, u8 * const menuItems[][2], u8 columnCount, u32 a7)
+void sub_807274C(u8 left, u8 top, u8 menuItemCount, u8 a4, const struct MenuAction menuItems[], u8 columnCount, u32 a7)
{
u8 maxWidth = sub_80724F4(left, top, menuItemCount, menuItems, columnCount);
diff --git a/src/metatile_behavior.c b/src/metatile_behavior.c
new file mode 100644
index 000000000..dd1ac75e3
--- /dev/null
+++ b/src/metatile_behavior.c
@@ -0,0 +1,1064 @@
+#include "global.h"
+#include "metatile_behaviors.h"
+
+extern u8 gUnknown_08308E2C[];
+
+bool8 MetatileBehavior_IsWaterfall(u8);
+
+bool8 sub_8056D9C(u8 var)
+{
+ return TRUE;
+}
+
+bool8 sub_8056DA0(u8 var)
+{
+ if((gUnknown_08308E2C[var] & 1) != 0)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsJumpEast(u8 var)
+{
+ if(var == MB_JUMP_EAST)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsJumpWest(u8 var)
+{
+ if(var == MB_JUMP_WEST)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsJumpNorth(u8 var)
+{
+ if(var == MB_JUMP_NORTH)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsJumpSouth(u8 var)
+{
+ if(var == MB_JUMP_SOUTH)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8056E14(u8 var)
+{
+ if(var == MB_TALL_GRASS || var == MB_LONG_GRASS)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSandOrDeepSand(u8 var)
+{
+ if(var == MB_SAND || var == MB_DEEP_SAND)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsDeepSand(u8 var)
+{
+ if(var == MB_DEEP_SAND)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsReflective(u8 var)
+{
+ if(var == MB_POND_WATER || var == MB_PUDDLE || var == MB_1A || var == MB_ICE || var == MB_SOOTOPOLIS_DEEP_WATER || var == MB_REFLECTION_UNDER_BRIDGE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsIce(u8 var)
+{
+ if(var == MB_ICE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 is_tile_x69_2_warp_door(u8 var)
+{
+ if(var == MB_ANIMATED_DOOR)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsDoor(u8 var)
+{
+ if(var == MB_8D || var == MB_ANIMATED_DOOR)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsEscalator(u8 var)
+{
+ if(var == MB_UP_ESCALATOR || var == MB_DOWN_ESCALATOR)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 unref_sub_8056EE0(u8 var)
+{
+ if(var == MB_04)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsLadder(u8 var)
+{
+ if(var == MB_LADDER)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8056F08(u8 var)
+{
+ if(var == MB_NON_ANIMATED_DOOR || var == MB_WATER_DOOR || var == MB_DEEP_SOUTH_WARP)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8056F24(u8 var)
+{
+ if(var == MB_DEEP_SOUTH_WARP)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSurfableWaterOrUnderwater(u8 var)
+{
+ if((gUnknown_08308E2C[var] & 2) != 0)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsEastArrowWarp(u8 var)
+{
+ if(var == MB_EAST_ARROW_WARP)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsWestArrowWarp(u8 var)
+{
+ if(var == MB_WEST_ARROW_WARP)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsNorthArrowWarp(u8 var)
+{
+ if(var == MB_NORTH_ARROW_WARP || var == MB_STAIRS_OUTSIDE_ABANDONED_SHIP)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSouthArrowWarp(u8 var)
+{
+ if(var == MB_SOUTH_ARROW_WARP || var == MB_WATER_SOUTH_ARROW_WARP || var == MB_SHOAL_CAVE_ENTRANCE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+// unused
+bool8 MetatileBehavior_IsArrowWarp(u8 var)
+{
+ u8 var2 = 0;
+
+ if(MetatileBehavior_IsEastArrowWarp(var)
+ || MetatileBehavior_IsWestArrowWarp(var)
+ || MetatileBehavior_IsNorthArrowWarp(var)
+ || MetatileBehavior_IsSouthArrowWarp(var))
+ {
+ var2 = 1;
+ }
+ return var2;
+}
+
+bool8 sub_8056FFC(u8 var)
+{
+ if((var >= MB_WALK_EAST && var <= MB_TRICK_HOUSE_PUZZLE_8_FLOOR) || (var >= MB_EASTWARD_CURRENT && var <= MB_SOUTHWARD_CURRENT)
+ || var == MB_MUDDY_SLOPE || var == MB_CRACKED_FLOOR || var == MB_WATERFALL || var == MB_ICE || var == MB_BB || var == MB_BC)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsIce_2(u8 var)
+{
+ if(var == MB_ICE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsTrickHouseSlipperyFloor(u8 var)
+{
+ if(var == MB_TRICK_HOUSE_PUZZLE_8_FLOOR)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_0x05(u8 var)
+{
+ if(var == MB_05)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsWalkNorth(u8 var)
+{
+ if(var == MB_WALK_NORTH)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsWalkSouth(u8 var)
+{
+ if(var == MB_WALK_SOUTH)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsWalkWest(u8 var)
+{
+ if(var == MB_WALK_WEST)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsWalkEast(u8 var)
+{
+ if(var == MB_WALK_EAST)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsNorthwardCurrent(u8 var)
+{
+ if(var == MB_NORTHWARD_CURRENT)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSouthwardCurrent(u8 var)
+{
+ if(var == MB_SOUTHWARD_CURRENT)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsWestwardCurrent(u8 var)
+{
+ if(var == MB_WESTWARD_CURRENT)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsEastwardCurrent(u8 var)
+{
+ if(var == MB_EASTWARD_CURRENT)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSlideNorth(u8 var)
+{
+ if(var == MB_SLIDE_NORTH)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSlideSouth(u8 var)
+{
+ if(var == MB_SLIDE_SOUTH)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSlideWest(u8 var)
+{
+ if(var == MB_SLIDE_WEST)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSlideEast(u8 var)
+{
+ if(var == MB_SLIDE_EAST)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsCounter(u8 var)
+{
+ if(var == MB_COUNTER)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsPlayerFacingTVScreen(u8 tile, u8 playerDir)
+{
+ if(playerDir != 2) // if the player isn't facing north, forget about it.
+ return FALSE;
+ else if(tile == MB_TELEVISION) // is the player's north tile a TV?
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsPC(u8 var)
+{
+ if(var == MB_PC)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 is_tile_x84(u8 var)
+{
+ if(var == MB_84)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80571C0(u8 var)
+{
+ if(var == MB_91 || var == MB_93 || var == MB_95 || var == MB_97
+ || var == MB_99 || var == MB_9B || var == MB_9D)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80571EC(u8 var)
+{
+ if(var == MB_SECRET_BASE_SPOT_RED_CAVE || var == MB_SECRET_BASE_SPOT_BROWN_CAVE || var == MB_SECRET_BASE_SPOT_YELLOW_CAVE || var == MB_SECRET_BASE_SPOT_BLUE_CAVE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_805720C(u8 var)
+{
+ if(var == MB_SECRET_BASE_SPOT_TREE_1 || var == MB_SECRET_BASE_SPOT_TREE_2)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 is_tile_x98(u8 var)
+{
+ if(var == MB_SECRET_BASE_SPOT_SHRUB)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057238(u8 var)
+{
+ if(var == MB_SECRET_BASE_PC)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_805724C(u8 var)
+{
+ if(var == MB_B1)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 unref_sub_8057260(u8 var)
+{
+ if(var == MB_B2)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057274(u8 var)
+{
+ if(var == MB_B3)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057288(u8 var)
+{
+ if(var == MB_B9)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_805729C(u8 var)
+{
+ if(var == MB_NORMAL)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80572B0(u8 var)
+{
+ if(var == MB_B7)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 unref_sub_80572C4(u8 var)
+{
+ if(var == MB_B2)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80572D8(u8 var)
+{
+ if(var == MB_B5)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80572EC(u8 var)
+{
+ if(var == MB_C3)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057300(u8 var)
+{
+ if(var == MB_C2)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057314(u8 var)
+{
+ if(var == MB_B8)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057328(u8 var)
+{
+ if(var == MB_BE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_805733C(u8 var)
+{
+ if(var == MB_BD)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057350(u8 var)
+{
+ if(var == MB_BA)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057364(u8 var)
+{
+ if(var == MB_BF)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057378(u8 var)
+{
+ if(var == MB_C4)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_805738C(u8 var)
+{
+ if(var == MB_C5)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_HasRipples(u8 var)
+{
+ if(var == MB_POND_WATER || var == MB_PUDDLE || var == MB_SOOTOPOLIS_DEEP_WATER)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsPuddle(u8 var)
+{
+ if(var == MB_PUDDLE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsTallGrass(u8 var)
+{
+ if(var == MB_TALL_GRASS)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsLongGrass(u8 var)
+{
+ if(var == MB_LONG_GRASS)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsBerryTreeSoil(u8 var)
+{
+ if(var == MB_BERRY_TREE_SOIL)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsAsh(u8 var)
+{
+ if(var == MB_ASH)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsUnusedFootprintMetatile(u8 var)
+{
+ if(var == MB_25)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsBridge(u8 var)
+{
+ if(var >= MB_WARP_OR_BRIDGE && var <= MB_ROUTE120_NORTH_BRIDGE_2)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+u8 sub_8057450(u8 var)
+{
+ u8 result = var - MB_WARP_OR_BRIDGE;
+
+ if(result > 3)
+ result = 0;
+
+ return result;
+}
+
+bool8 MetatileBehavior_IsLandWildEncounter(u8 var)
+{
+ if(MetatileBehavior_IsSurfableWaterOrUnderwater(var) == FALSE && sub_8056DA0(var) == TRUE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsWaterWildEncounter(u8 var)
+{
+ if(MetatileBehavior_IsSurfableWaterOrUnderwater(var) == TRUE && sub_8056DA0(var) == TRUE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80574C4(u8 var)
+{
+ if(var == MB_0B)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80574D8(u8 var)
+{
+ if(var == MB_MOUNTAIN_TOP)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80574EC(u8 var)
+{
+ if(var == MB_SEMI_DEEP_WATER || var == MB_DEEP_WATER || var == MB_SOOTOPOLIS_DEEP_WATER)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_805750C(u8 var)
+{
+ if(var == MB_NO_SURFACING || var == MB_SEAWEED_NO_SURFACING)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsShallowFlowingWater(u8 var)
+{
+ if(var == MB_SHALLOW_WATER || var == MB_STAIRS_OUTSIDE_ABANDONED_SHIP || var == MB_SHOAL_CAVE_ENTRANCE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057540(u8 var)
+{
+ if(var == MB_THIN_ICE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057554(u8 var)
+{
+ if(var == MB_CRACKED_ICE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057568(u8 var)
+{
+ if(var == MB_OCEAN_WATER || var == MB_SEMI_DEEP_WATER || var == MB_DEEP_WATER)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 unref_sub_8057584(u8 var)
+{
+ if(var == MB_18 || var == MB_1A)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_805759C(u8 var)
+{
+ if(MetatileBehavior_IsSurfableWaterOrUnderwater(var) && MetatileBehavior_IsWaterfall(var) == FALSE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsEastBlocked(u8 var)
+{
+ if(var == MB_IMPASSABLE_EAST || var == MB_IMPASSABLE_NORTHEAST || var == MB_IMPASSABLE_SOUTHEAST || var == MB_C1 || var == MB_BE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsWestBlocked(u8 var)
+{
+ if(var == MB_IMPASSABLE_WEST || var == MB_IMPASSABLE_NORTHWEST || var == MB_IMPASSABLE_SOUTHWEST || var == MB_C1 || var == MB_BE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsNorthBlocked(u8 var)
+{
+ if(var == MB_IMPASSABLE_NORTH || var == MB_IMPASSABLE_NORTHEAST || var == MB_IMPASSABLE_NORTHWEST || var == MB_BED)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSouthBlocked(u8 var)
+{
+ if(var == MB_IMPASSABLE_SOUTH || var == MB_IMPASSABLE_SOUTHEAST || var == MB_IMPASSABLE_SOUTHWEST || var == MB_BED)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsShortGrass(u8 var)
+{
+ if(var == MB_SHORT_GRASS)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsHotSprings(u8 var)
+{
+ if(var == MB_HOT_SPRINGS)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsWaterfall(u8 var)
+{
+ if(var == MB_WATERFALL)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsFortreeBridge(u8 var)
+{
+ if(var == MB_FORTREE_BRIDGE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80576A0(u8 var)
+{
+ if(var == MB_PACIFIDLOG_VERTICAL_LOG_1)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80576B4(u8 var)
+{
+ if(var == MB_PACIFIDLOG_VERTICAL_LOG_2)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80576C8(u8 var)
+{
+ if(var == MB_PACIFIDLOG_HORIZONTAL_LOG_1)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80576DC(u8 var)
+{
+ if(var == MB_PACIFIDLOG_HORIZONTAL_LOG_2)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsPacifidlogLog(u8 var)
+{
+ if(var >= MB_PACIFIDLOG_VERTICAL_LOG_1 && var <= MB_PACIFIDLOG_HORIZONTAL_LOG_2)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 is_tile_x8C(u8 var)
+{
+ if(var == MB_TRICK_HOUSE_PUZZLE_DOOR)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 is_tile_x85(u8 var)
+{
+ if(var == MB_REGION_MAP)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 is_tile_x8B(u8 var)
+{
+ if(var == MB_CLOSED_SOOTOPOLIS_GYM_DOOR)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 is_tile_x8A(u8 var)
+{
+ if(var == MB_ROULETTE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 is_tile_x87(u8 var)
+{
+ if(var == MB_POKEBLOCK_FEEDER)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_0xBB(u8 var)
+{
+ if(var == MB_BB)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_0xBC(u8 var)
+{
+ if(var == MB_BC)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057798(u8 var)
+{
+ if(var == MB_LAVARIDGE_GYM_B1F_WARP)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 is_role_x68(u8 var)
+{
+ if(var == MB_LAVARIDGE_GYM_1F_WARP)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsAquaHideoutWarp(u8 var)
+{
+ if(var == MB_AQUA_HIDEOUT_WARP)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSurfableFishableWater(u8 var)
+{
+ if(var == MB_POND_WATER || var == MB_OCEAN_WATER || var == MB_SEMI_DEEP_WATER || var == MB_DEEP_WATER || var == MB_SOOTOPOLIS_DEEP_WATER || (var >= MB_EASTWARD_CURRENT && var <= MB_SOUTHWARD_CURRENT))
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057804(u8 var)
+{
+ if(var == MB_MT_PYRE_HOLE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057818(u8 var)
+{
+ if(var == MB_CRACKED_FLOOR_HOLE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_805782C(u8 var)
+{
+ if(var == MB_CRACKED_FLOOR)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsMuddySlope(u8 var)
+{
+ if(var == MB_MUDDY_SLOPE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsBumpySlope(u8 var)
+{
+ if(var == MB_BUMPY_SLOPE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsIsolatedVerticalRail(u8 var)
+{
+ if(var == MB_ISOLATED_VERTICAL_RAIL)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsIsolatedHorizontalRail(u8 var)
+{
+ if(var == MB_ISOLATED_HORIZONTAL_RAIL)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsVerticalRail(u8 var)
+{
+ if(var == MB_VERTICAL_RAIL)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsHorizontalRail(u8 var)
+{
+ if(var == MB_HORIZONTAL_RAIL)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsSeaweed(u8 var)
+{
+ if(var == MB_SEAWEED || var == MB_SEAWEED_NO_SURFACING)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 MetatileBehavior_IsRunningDisallowed(u8 var)
+{
+ if(var == MB_NO_RUNNING || var == MB_LONG_GRASS || var == MB_HOT_SPRINGS || MetatileBehavior_IsPacifidlogLog(var) != FALSE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80578F8(u8 var)
+{
+ if(var == MB_TALL_GRASS || var == MB_LONG_GRASS || var == MB_ASH || var == MB_LONG_GRASS_SOUTH_EDGE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_805791C(u8 var)
+{
+ if(var == MB_8E)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057930(u8 var)
+{
+ if(var == MB_PICTURE_BOOK_SHELF)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057944(u8 var)
+{
+ if(var == MB_BOOKSHELF)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057958(u8 var)
+{
+ if(var == MB_POKEMON_CENTER_BOOKSHELF)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_805796C(u8 var)
+{
+ if(var == MB_VASE)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057980(u8 var)
+{
+ if(var == MB_TRASH_CAN)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_8057994(u8 var)
+{
+ if(var == MB_SHOP_SHELF)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+bool8 sub_80579A8(u8 var)
+{
+ if(var == MB_BLUEPRINT)
+ return TRUE;
+ else
+ return FALSE;
+}
diff --git a/src/money.c b/src/money.c
new file mode 100644
index 000000000..2a59cab50
--- /dev/null
+++ b/src/money.c
@@ -0,0 +1,240 @@
+#include "global.h"
+#include "money.h"
+#include "decompress.h"
+#include "menu.h"
+#include "sprite.h"
+#include "string_util.h"
+
+#define SPRITE_TAG_MONEY (0x2722)
+
+extern u16 gSpecialVar_0x8005;
+extern u8 gUnknown_02038734;
+
+extern const struct SpriteSheet gUnknown_083CF584;
+extern const struct SpritePalette gUnknown_083CF58C;
+extern const struct SpriteTemplate gSpriteTemplate_83CF56C;
+
+bool8 IsEnoughMoney(u32 budget, u32 cost) {
+ if (budget >= cost) {
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+void sub_80B79B8(u32 *arg0, u32 arg1) {
+ if (*arg0 > *arg0 + arg1) {
+ *arg0 = 999999;
+ return;
+ }
+
+ *arg0 = *arg0 + arg1;
+ if (*arg0 > 999999) {
+ *arg0 = 999999;
+ }
+}
+
+void sub_80B79E0(u32 *arg0, u32 arg1) {
+ if (*arg0 < arg1) {
+ *arg0 = 0;
+ } else {
+ *arg0 = *arg0 - arg1;
+ }
+}
+
+void sub_80B79F8(u8 *buffer, u32 arg1, u8 arg2) {
+ u8 width;
+ u8 i;
+
+ if (arg1 > 999999) {
+ width = 7;
+ } else if (arg1 > 99999) {
+ width = 6;
+ } else if (arg1 > 10000) {
+ width = 5;
+ } else if (arg1 > 999) {
+ width = 4;
+ } else if (arg1 > 99) {
+ width = 3;
+ } else if (arg1 > 9) {
+ width = 2;
+ } else {
+ width = 1;
+ }
+
+ buffer[0] = EXT_CTRL_CODE_BEGIN;
+ buffer[1] = 0x14;
+ buffer[2] = 0x06;
+ buffer += 3;
+
+ for (i = 0; i < arg2 - width; i++) {
+ buffer[0] = CHAR_SPACE;
+ buffer += 1;
+ }
+
+ buffer[0] = CHAR_CURRENCY;
+ buffer += 1;
+
+ buffer = ConvertIntToDecimalString(buffer, arg1);
+
+ buffer[0] = EXT_CTRL_CODE_BEGIN;
+ buffer[1] = 0x14;
+ buffer[2] = 0x00;
+ buffer[3] = EOS;
+}
+
+void sub_80B7A94(u32 arg0, u8 size, u8 x, u8 y) {
+ u8 buffer[16];
+ u8 stringWidth;
+
+ sub_80B79F8(buffer, arg0, size);
+ stringWidth = sub_8072CA4(buffer);
+
+ if (stringWidth >= (size + 1) * 8)
+ MenuPrint(buffer, x, y);
+ else
+ {
+ int xPlusOne = x + 1;
+ MenuPrint_PixelCoords(buffer, (xPlusOne + size) * 8 - stringWidth, y * 8, 1);
+ }
+}
+
+void sub_80B7AEC(u32 arg0, u8 left, u8 top) {
+ u8 buffer[32];
+ u8 *ptr;
+
+ ptr = &buffer[0];
+
+ ptr[0] = CHAR_CURRENCY;
+ ptr++;
+
+ ptr = ConvertIntToDecimalString(ptr, arg0);
+
+ MenuPrint_RightAligned(buffer, left, top);
+
+ ptr[0] = 0xFC;
+ ptr[1] = 0x14;
+ ptr[2] = 0x00;
+ ptr[3] = 0xFF;
+}
+
+__attribute__((naked))
+void sub_80B7B34(void) {
+ asm(".syntax unified\n\
+ push {r4-r7,lr}\n\
+ mov r7, r9\n\
+ mov r6, r8\n\
+ push {r6,r7}\n\
+ sub sp, 0x4\n\
+ mov r8, r0\n\
+ adds r5, r1, 0\n\
+ mov r9, r2\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ mov r8, r0\n\
+ lsls r5, 24\n\
+ lsrs r5, 24\n\
+ mov r1, r9\n\
+ lsls r1, 8\n\
+ mov r9, r1\n\
+ ldr r4, _080B7BD8 @ =gDecoration10000_Gfx\n\
+ adds r0, r1, r4\n\
+ lsls r6, r5, 4\n\
+ subs r6, r5\n\
+ lsls r1, r6, 6\n\
+ mov r3, r8\n\
+ adds r3, 0x1\n\
+ lsls r3, 5\n\
+ ldr r2, _080B7BDC @ =0x06008000\n\
+ adds r3, r2\n\
+ adds r1, r3\n\
+ movs r2, 0x20\n\
+ str r3, [sp]\n\
+ bl CpuFastSet\n\
+ adds r4, 0x80\n\
+ add r9, r4\n\
+ adds r0, r5, 0x1\n\
+ lsls r4, r0, 4\n\
+ subs r4, r0\n\
+ lsls r1, r4, 6\n\
+ ldr r3, [sp]\n\
+ adds r1, r3\n\
+ mov r0, r9\n\
+ movs r2, 0x20\n\
+ bl CpuFastSet\n\
+ movs r3, 0\n\
+ lsls r5, 5\n\
+ mov r0, r8\n\
+ adds r7, r5, r0\n\
+ lsls r6, 1\n\
+ adds r6, 0x1\n\
+ add r6, r8\n\
+ ldr r1, _080B7BE0 @ =0xfffff000\n\
+ adds r5, r1, 0\n\
+ ldr r0, _080B7BE4 @ =0x0600f800\n\
+ mov r12, r0\n\
+ ldr r1, _080B7BE8 @ =0x0600f840\n\
+ mov r9, r1\n\
+ lsls r4, 1\n\
+ adds r4, 0x1\n\
+ add r4, r8\n\
+_080B7BAA:\n\
+ adds r1, r7, r3\n\
+ lsls r1, 1\n\
+ mov r0, r12\n\
+ adds r2, r1, r0\n\
+ adds r0, r3, r6\n\
+ adds r0, r5\n\
+ strh r0, [r2]\n\
+ add r1, r9\n\
+ adds r0, r3, r4\n\
+ adds r0, r5\n\
+ strh r0, [r1]\n\
+ adds r0, r3, 0x1\n\
+ lsls r0, 16\n\
+ lsrs r3, r0, 16\n\
+ cmp r3, 0x3\n\
+ bls _080B7BAA\n\
+ add sp, 0x4\n\
+ pop {r3,r4}\n\
+ mov r8, r3\n\
+ mov r9, r4\n\
+ pop {r4-r7}\n\
+ pop {r0}\n\
+ bx r0\n\
+ .align 2, 0\n\
+_080B7BD8: .4byte gDecoration10000_Gfx\n\
+_080B7BDC: .4byte 0x06008000\n\
+_080B7BE0: .4byte 0xfffff000\n\
+_080B7BE4: .4byte 0x0600f800\n\
+_080B7BE8: .4byte 0x0600f840\n\
+ .syntax divided\n");
+}
+
+void sub_80B7BEC(u32 arg0, u8 x, u8 y) {
+ sub_80B7A94(arg0, 6, x + 6, y + 1);
+}
+
+void sub_80B7C14(u32 arg0, u8 x, u8 y) {
+ MenuDrawTextWindow(x, y, x + 13, y + 3);
+ sub_80B7BEC(arg0, x, y);
+
+ LoadCompressedObjectPic(&gUnknown_083CF584);
+ LoadCompressedObjectPalette(&gUnknown_083CF58C);
+
+ gUnknown_02038734 = CreateSprite(&gSpriteTemplate_83CF56C, x * 8 + 19, y * 8 + 11, 0);
+}
+
+void RemoveMoneyLabelObject(u8 x, u8 y) {
+ DestroySpriteAndFreeResources(&gSprites[gUnknown_02038734]);
+ FreeSpritePaletteByTag(SPRITE_TAG_MONEY);
+ MenuZeroFillWindowRect(x, y, x + 13, y + 3);
+}
+
+bool8 sub_80B7CE8(void) {
+ return IsEnoughMoney(gSaveBlock1.money, gSpecialVar_0x8005);
+}
+
+void sub_80B7D0C(void) {
+ sub_80B79E0(&gSaveBlock1.money, gSpecialVar_0x8005);
+}
diff --git a/src/mori_debug_menu.c b/src/mori_debug_menu.c
index fbb796ca4..44f8542a5 100644
--- a/src/mori_debug_menu.c
+++ b/src/mori_debug_menu.c
@@ -5,9 +5,15 @@
#include "menu.h"
#include "main.h"
#include "string_util.h"
+#include "link.h"
+#define SIO_MULTI_CNT ((struct SioMultiCnt *)REG_ADDR_SIOCNT)
+
+extern u8 gUnknown_03004DA0[];
extern u8 (*gCallback_03004AE8)(void);
+extern u8 gUnknown_0839B22C[][3];
+extern u8 gUnknown_0839B24A[];
extern u8 gUnknown_0839B24D[];
extern u8 gUnknown_0839B255[];
extern u8 gUnknown_0839B257[];
@@ -16,6 +22,17 @@ extern const struct MenuAction gMoriDebugMenuActions[];
extern u8 gSpeciesNames[][11];
+void unref_sub_8083CF0(void)
+{
+ int i;
+ int id = SIO_MULTI_CNT->id;
+ gUnknown_03004DA0[0] = EOS;
+ StringAppend(gUnknown_03004DA0, gUnknown_0839B24A);
+ for (i = 0; i < 10; i++)
+ if ((word_3002910[id ^ 1] >> i) & 1)
+ StringAppend(gUnknown_03004DA0, gUnknown_0839B22C[i]);
+}
+
bool8 sub_8083D4C(void)
{
if ( gMain.newKeys & A_BUTTON )
diff --git a/src/mystery_event_menu.c b/src/mystery_event_menu.c
new file mode 100644
index 000000000..09523ff40
--- /dev/null
+++ b/src/mystery_event_menu.c
@@ -0,0 +1,346 @@
+#include "global.h"
+#include "sprite.h"
+#include "menu.h"
+#include "link.h"
+#include "text.h"
+#include "main.h"
+#include "palette.h"
+#include "task.h"
+#include "string_util.h"
+#include "songs.h"
+#include "sound.h"
+#include "save.h"
+#include "asm.h"
+#include "mystery_event_menu.h"
+
+extern u8 unk_2000000[];
+extern u8 gUnknown_02039338;
+
+extern u8 gSystemText_LinkStandby[];
+extern u8 gSystemText_LoadEventPressA[];
+extern u8 gSystemText_LoadingEvent[];
+extern u8 gSystemText_DontCutLink[];
+extern u8 gSystemText_EventLoadSuccess[];
+extern u8 gSystemText_LoadingError[];
+
+static void VBlankCB(void);
+static bool8 CheckLanguageMatch(void);
+static bool8 GetEventLoadMessage(u8 *dest, u32 status);
+static void CB2_MysteryEventMenu(void);
+
+static void VBlankCB(void)
+{
+ LoadOam();
+ ProcessSpriteCopyRequests();
+ TransferPlttBuffer();
+}
+
+static bool8 CheckLanguageMatch(void)
+{
+ bool8 val = FALSE;
+
+ if (gLinkPlayers[0].language == gLinkPlayers[1].language)
+ val = TRUE;
+
+ return val;
+}
+
+void CB2_InitMysteryEventMenu(void)
+{
+ ResetSpriteData();
+ FreeAllSpritePalettes();
+ ResetTasks();
+ SetVBlankCallback(VBlankCB);
+ SetUpWindowConfig(&gWindowConfig_81E6CE4);
+ InitMenuWindow(&gWindowConfig_81E6CE4);
+ MenuZeroFillScreen();
+ REG_DISPCNT = 320;
+ REG_BLDCNT = 0;
+ CreateTask(Task_DestroySelf, 0);
+ StopMapMusic();
+ RunTasks();
+ AnimateSprites();
+ BuildOamBuffer();
+ UpdatePaletteFade();
+ FillPalette(0, 0, 2);
+ SetMainCallback2(CB2_MysteryEventMenu);
+}
+
+static bool8 GetEventLoadMessage(u8 *dest, u32 status)
+{
+ bool8 retVal = 1;
+
+ if (status == 0)
+ {
+ StringCopy(dest, gSystemText_EventLoadSuccess);
+ retVal = 0;
+ }
+
+ if (status == 2)
+ retVal = 0;
+
+ if (status == 1)
+ StringCopy(dest, gSystemText_LoadingError);
+
+ return retVal;
+}
+
+static void CB2_MysteryEventMenu(void)
+{
+ u16 unkVal;
+
+ switch (gMain.state)
+ {
+ case 0:
+ MenuDrawTextWindow(0, 14, 29, 19);
+ BeginNormalPaletteFade(0xFFFFFFFF, 0, 0x10, 0, 0);
+ gMain.state++;
+ break;
+ case 1:
+ if (gPaletteFade.active)
+ break;
+ sub_8072044(gSystemText_LinkStandby);
+ gMain.state++;
+ break;
+ case 2:
+ if (MenuUpdateWindowText())
+ {
+ gMain.state++;
+ gLinkType = 21761;
+ OpenLink();
+ }
+ break;
+ case 3:
+ if ((gLinkStatus & 0x20) && (gLinkStatus & 0x1C) > 4)
+ {
+ PlaySE(SE_PIN);
+ sub_8072044(gSystemText_LoadEventPressA);
+ gMain.state++;
+ }
+ if (gMain.newKeys & B_BUTTON)
+ {
+ PlaySE(SE_SELECT);
+ CloseLink();
+ gMain.state = 15;
+ }
+ break;
+ case 4:
+ if (MenuUpdateWindowText())
+ gMain.state++;
+ break;
+#ifdef NONMATCHING
+ case 5:
+ if (GetLinkPlayerCount_2() != 2)
+ {
+ GetEventLoadMessage(gStringVar4, 1);
+ sub_8072044(gStringVar4);
+ gMain.state = 13;
+ break;
+ }
+ if (gMain.newKeys & A_BUTTON)
+ {
+ PlaySE(SE_SELECT);
+ sub_8007F4C();
+ MenuDrawTextWindow(6, 5, 23, 8);
+ MenuPrint(gSystemText_LoadingEvent, 7, 6);
+ gMain.state++;
+ }
+ else if (gMain.newKeys & B_BUTTON)
+ {
+ PlaySE(SE_SELECT);
+ CloseLink();
+ gMain.state = 15;
+ }
+ break;
+ case 6:
+ if (IsLinkConnectionEstablished())
+ {
+ if (!gReceivedRemoteLinkPlayers)
+ break;
+
+ if (GetLinkPlayerDataExchangeStatusTimed() == 3)
+ {
+ sub_800832C();
+ MenuZeroFillWindowRect(6, 5, 23, 8);
+ GetEventLoadMessage(gStringVar4, 1);
+ sub_8072044(gStringVar4);
+ gMain.state = 13;
+ break;
+ }
+ else if (CheckLanguageMatch())
+ {
+ sub_8072044(gSystemText_DontCutLink);
+ gMain.state++;
+ break;
+ }
+ else
+ {
+ CloseLink();
+ MenuZeroFillWindowRect(6, 5, 23, 8);
+ GetEventLoadMessage(gStringVar4, 1);
+ sub_8072044(gStringVar4);
+ gMain.state = 13;
+ break;
+ }
+ }
+ if (gMain.newKeys & B_BUTTON)
+ {
+ PlaySE(SE_SELECT);
+ CloseLink();
+ gMain.state = 15;
+ break;
+ }
+ break;
+#else
+ case 5:
+ if (GetLinkPlayerCount_2() != 2)
+ {
+ goto label;
+ }
+ if (gMain.newKeys & A_BUTTON)
+ {
+ PlaySE(SE_SELECT);
+ sub_8007F4C();
+ MenuDrawTextWindow(6, 5, 23, 8);
+ MenuPrint(gSystemText_LoadingEvent, 7, 6);
+ gMain.state++;
+ }
+ else if (gMain.newKeys & B_BUTTON)
+ {
+ PlaySE(SE_SELECT);
+ CloseLink();
+ gMain.state = 15;
+ }
+ break;
+ case 6:
+ if (IsLinkConnectionEstablished())
+ {
+ register u8 *ptr asm("r0");
+ register u32 offset1 asm("r2");
+ register u32 offset2 asm("r1");
+
+ if (!gReceivedRemoteLinkPlayers)
+ break;
+
+ if (GetLinkPlayerDataExchangeStatusTimed() == 3)
+ {
+ sub_800832C();
+ MenuZeroFillWindowRect(6, 5, 23, 8);
+ GetEventLoadMessage(gStringVar4, 1);
+ sub_8072044(gStringVar4);
+ ptr = (u8 *)&gMain;
+ offset1 = offsetof(struct Main, state);
+ asm("" ::: "r1");
+ ptr += offset1;
+ *ptr = 13;
+ }
+ else if (CheckLanguageMatch())
+ {
+ register u8 *ptr2 asm("r1");
+ register int offset3 asm("r0");
+ register int dummy asm("r2");
+ sub_8072044(gSystemText_DontCutLink);
+ ptr2 = (u8 *)&gMain;
+ offset3 = offsetof(struct Main, state);
+ if (dummy)
+ dummy++;
+ ptr2 += offset3;
+ (*ptr2)++;
+ break;
+ }
+ else
+ {
+ CloseLink();
+ MenuZeroFillWindowRect(6, 5, 23, 8);
+ label:
+ GetEventLoadMessage(gStringVar4, 1);
+ sub_8072044(gStringVar4);
+ ptr = (u8 *)&gMain;
+ offset2 = offsetof(struct Main, state);
+ ptr += offset2;
+ *ptr = 13;
+ }
+ break;
+ }
+ if (gMain.newKeys & B_BUTTON)
+ {
+ PlaySE(SE_SELECT);
+ CloseLink();
+ gMain.state = 15;
+ break;
+ }
+ break;
+#endif
+ case 7:
+ if (MenuUpdateWindowText())
+ gMain.state++;
+ break;
+ case 8:
+ if (GetBlockReceivedStatus())
+ {
+ ResetBlockReceivedFlags();
+ gMain.state++;
+ }
+ break;
+ case 9:
+ gMain.state++;
+ break;
+ case 10:
+ sub_800832C();
+ gMain.state++;
+ break;
+ case 11:
+ if (gReceivedRemoteLinkPlayers)
+ break;
+ unkVal = sub_812613C(unk_2000000);
+ CpuFill32(0, unk_2000000, 0x7D4);
+ if (!GetEventLoadMessage(gStringVar4, unkVal))
+ sub_8125D44(0);
+ gMain.state++;
+ break;
+ case 12:
+ sub_8072044(gStringVar4);
+ gMain.state++;
+ break;
+ case 13:
+ MenuZeroFillWindowRect(6, 5, 23, 8);
+ if (MenuUpdateWindowText())
+ {
+ gMain.state++;
+ gUnknown_02039338 = 0;
+ }
+ break;
+ case 14:
+ if (gMain.newKeys & A_BUTTON)
+ {
+ PlaySE(SE_SELECT);
+ gMain.state++;
+ }
+ break;
+ case 15:
+ BeginNormalPaletteFade(0xFFFFFFFF, 0, 0, 0x10, 0);
+ gMain.state++;
+ break;
+ case 16:
+ if (!gPaletteFade.active)
+ DoSoftReset();
+ break;
+ }
+
+ if (gLinkStatus & 0x40)
+ {
+ if (!IsLinkMaster())
+ {
+ CloseLink();
+ MenuZeroFillWindowRect(6, 5, 23, 8);
+ GetEventLoadMessage(gStringVar4, 1);
+ sub_8072044(gStringVar4);
+ gMain.state = 13;
+ }
+ }
+
+ RunTasks();
+ AnimateSprites();
+ BuildOamBuffer();
+ UpdatePaletteFade();
+}
diff --git a/src/mystery_event_script.c b/src/mystery_event_script.c
new file mode 100644
index 000000000..4aa3784d7
--- /dev/null
+++ b/src/mystery_event_script.c
@@ -0,0 +1,97 @@
+#include "global.h"
+#include "script.h"
+#include "string_util.h"
+
+#ifdef SAPPHIRE
+#define UNK_MASK 0x100
+#else
+#define UNK_MASK 0x80
+#endif
+
+extern struct ScriptContext gUnknown_02039288;
+
+extern ScrCmdFunc gScriptFuncs[];
+extern ScrCmdFunc gScriptFuncs_End[];
+
+extern u8 gOtherText_DataCannotUseVersion[];
+
+void sub_8126160(u32 val);
+
+bool32 sub_8126098(u16 a1, u32 a2, u16 a3, u32 a4)
+{
+ if (!(a1 & 0x2))
+ return FALSE;
+
+ if (!(a2 & 0x2))
+ return FALSE;
+
+ if (!(a3 & 0x4))
+ return FALSE;
+
+ if (!(a4 & UNK_MASK))
+ return FALSE;
+
+ return TRUE;
+}
+
+void sub_81260D0(void)
+{
+ StringExpandPlaceholders(gStringVar4, gOtherText_DataCannotUseVersion);
+ sub_8126160(3);
+}
+
+void sub_81260EC(struct ScriptContext *ctx, u8 *ptr)
+{
+ InitScriptContext(ctx, gScriptFuncs, gScriptFuncs_End);
+ SetupBytecodeScript(ctx, ptr);
+ ctx->data[0] = (u32)ptr;
+ ctx->data[1] = 0;
+ ctx->data[2] = 0;
+ ctx->data[3] = 0;
+}
+
+bool32 sub_812611C(struct ScriptContext *ctx)
+{
+ if (RunScript(ctx) && ctx->data[3])
+ return TRUE;
+ else
+ return FALSE;
+}
+
+u32 sub_812613C(u8 *ptr)
+{
+ struct ScriptContext *ctx = &gUnknown_02039288;
+ sub_81260EC(ctx, ptr);
+ while (sub_812611C(ctx))
+ ;
+ return ctx->data[2];
+}
+
+void sub_8126160(u32 val)
+{
+ gUnknown_02039288.data[2] = val;
+}
+
+int sub_812616C(u8 *a1, int a2)
+{
+ unsigned int i;
+ int sum = 0;
+
+ for (i = 0; i < a2; i++)
+ sum += a1[i];
+
+ return sum;
+}
+
+u32 sub_812618C(u8 *ptr)
+{
+ return ptr[0] | (ptr[1] << 8) | (ptr[2] << 16) | (ptr[3] << 24);
+}
+
+void sub_81261A4(u8 *ptr, u32 val)
+{
+ ptr[0] = val;
+ ptr[1] = val >> 8;
+ ptr[2] = val >> 16;
+ ptr[3] = val >> 24;
+}
diff --git a/src/new_game.c b/src/new_game.c
index c36337409..fa1894086 100644
--- a/src/new_game.c
+++ b/src/new_game.c
@@ -18,7 +18,15 @@ extern u8 gUnknown_03005CE8;
extern u16 gSaveFileStatus;
extern u8 gUnknown_0819FA81[];
-extern const struct SB1_2EFC_Struct gUnknown_08216604;
+
+const struct SB1_2EFC_Struct gUnknown_08216604 =
+{
+ {
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ }
+};
void write_word_to_mem(u32 a1, u8 *a2)
{
@@ -102,7 +110,7 @@ void NewGameInitData(void)
sub_8052DE4();
memset(&gSaveBlock1, 0, sizeof(gSaveBlock1));
sub_80A2B18();
- gSaveBlock2.sb2_field_9 = 0;
+ gSaveBlock2.specialSaveWarp = 0;
set_player_trainer_id();
PlayTimeCounter_Reset();
sub_8052D78();
diff --git a/src/player_pc.c b/src/player_pc.c
new file mode 100644
index 000000000..822e2108e
--- /dev/null
+++ b/src/player_pc.c
@@ -0,0 +1,818 @@
+#include "global.h"
+#include "item.h"
+#include "task.h"
+#include "menu.h"
+#include "sound.h"
+#include "main.h"
+#include "script.h"
+#include "palette.h"
+#include "weather.h"
+#include "asm.h"
+#include "string_util.h"
+
+extern void DisplayItemMessageOnField(u8, u8*, TaskFunc, u16);
+extern void ItemStorageMenuProcessInput(u8);
+extern void DoPlayerPCDecoration(u8);
+extern void BuyMenuFreeMemory(void);
+extern void DestroyVerticalScrollIndicator(u8);
+extern u8 sub_813AF3C(void);
+extern void sub_813AF78(void);
+extern void sub_813A240(u8);
+extern void sub_813B108(u8);
+extern void sub_813B174(u8);
+extern void sub_80A6A30(void);
+extern u8 sub_807D770(void);
+extern void sub_813A280(u8);
+extern void sub_813AE6C(u8, u8);
+extern void sub_813A240(u8);
+extern void sub_813AD58(u16);
+extern void sub_813AE0C(u8);
+extern void sub_813ABE8(u8);
+extern void sub_813AA30(u8, u8);
+extern void sub_813A4B4(u8);
+extern void sub_813A468(u8);
+
+extern u8 gOtherText_NoItems[];
+
+extern u16 gNewGamePCItems[];
+
+extern u8 gOtherText_WhatWillYouDo[];
+extern u8 gOtherText_NoMailHere[];
+
+extern u8 *gUnknown_02039314;
+extern struct MenuAction gUnknown_08406298[];
+extern u8 gUnknown_084062B8[];
+extern u8 gUnknown_084062BC[];
+extern u8 gUnknown_030007B4;
+extern u8 unk_201FE00[];
+
+extern u8 gUnknown_08152850;
+extern u8 gUnknown_08152C75;
+
+extern u32 gUnknown_08406288[];
+extern const struct MenuAction gUnknown_084062C0[];
+
+void InitPlayerPCMenu(u8 taskId);
+void PlayerPCProcessMenuInput(u8 taskId);
+void InitItemStorageMenu(u8);
+void ItemStorageMenuPrint(u8 *);
+
+void NewGameInitPCItems(void)
+{
+ u8 i = 0;
+
+ ClearItemSlots(gSaveBlock1.pcItems, 0x32);
+
+ while (gNewGamePCItems[i * 2] && (gNewGamePCItems + 1)[i * 2])
+ {
+ if(AddPCItem(gNewGamePCItems[i * 2], (gNewGamePCItems + 1)[i * 2]) != 1)
+ break;
+ i++;
+ }
+}
+
+void BedroomPC(void)
+{
+ u8 taskId;
+
+ gUnknown_02039314 = gUnknown_084062B8;
+ gUnknown_030007B4 = 4;
+ taskId = CreateTask(TaskDummy, 0);
+ DisplayItemMessageOnField(taskId, gOtherText_WhatWillYouDo, InitPlayerPCMenu, 0);
+}
+
+void PlayerPC(void)
+{
+ u8 taskId;
+
+ gUnknown_02039314 = gUnknown_084062BC;
+ gUnknown_030007B4 = 3;
+ taskId = CreateTask(TaskDummy, 0);
+ DisplayItemMessageOnField(taskId, gOtherText_WhatWillYouDo, InitPlayerPCMenu, 0);
+}
+
+void InitPlayerPCMenu(u8 taskId)
+{
+ MenuDrawTextWindow(0, 0, 10, gUnknown_030007B4 * 2 + 1);
+ PrintMenuItemsReordered(1, 1, gUnknown_030007B4, gUnknown_08406298, gUnknown_02039314);
+ InitMenu(0, 1, 1, gUnknown_030007B4, 0, 9);
+ gTasks[taskId].func = PlayerPCProcessMenuInput;
+}
+
+void PlayerPCProcessMenuInput(u8 taskId)
+{
+ if(gMain.newAndRepeatedKeys & 0x40)
+ {
+ PlaySE(5);
+ MoveMenuCursor(-1);
+ }
+ else if(gMain.newAndRepeatedKeys & 0x80)
+ {
+ PlaySE(5);
+ MoveMenuCursor(1);
+ }
+ else if(gMain.newKeys & 0x1)
+ {
+ sub_8072DEC();
+ PlaySE(5);
+ gUnknown_08406298[gUnknown_02039314[GetMenuCursorPos()]].func(taskId);
+ }
+ else if(gMain.newKeys & 0x2)
+ {
+ sub_8072DEC();
+ PlaySE(5);
+ gUnknown_08406298[gUnknown_030007B4[gUnknown_02039314 - 1]].func(taskId);
+ }
+}
+
+void ReshowPlayerPC(u8 var)
+{
+ DisplayItemMessageOnField(var, gOtherText_WhatWillYouDo, InitPlayerPCMenu, 0);
+}
+
+void PlayerPC_ItemStorage(u8 taskId)
+{
+ InitItemStorageMenu(0);
+ gTasks[taskId].func = ItemStorageMenuProcessInput;
+}
+
+void PlayerPC_Mailbox(u8 taskId)
+{
+ MenuZeroFillWindowRect(0, 0, 10, 9);
+ unk_201FE00[3] = sub_813AF3C();
+ if(!unk_201FE00[3])
+ DisplayItemMessageOnField(taskId, gOtherText_NoMailHere, ReshowPlayerPC, 0);
+ else
+ {
+ unk_201FE00[0] = 0;
+ unk_201FE00[2] = 0;
+ sub_813AF78();
+ sub_813A240(taskId);
+ sub_813B108(taskId);
+ gTasks[taskId].func = sub_813B174;
+ }
+}
+
+void PlayerPC_Decoration(u8 var)
+{
+ MenuZeroFillWindowRect(0, 0, 10, 9);
+ DoPlayerPCDecoration(var);
+}
+
+void PlayerPC_TurnOff(u8 taskId)
+{
+ if(gUnknown_030007B4 == 4)
+ {
+ MenuZeroFillWindowRect(0, 0, 0x1D, 0x13);
+ if(!gSaveBlock2.playerGender)
+ ScriptContext1_SetupScript(&gUnknown_08152850); // male
+ else
+ ScriptContext1_SetupScript(&gUnknown_08152C75); // female
+ }
+ else
+ {
+ MenuZeroFillWindowRect(0, 0, 10, 9);
+ EnableBothScriptContexts();
+ }
+ DestroyTask(taskId);
+}
+
+void InitItemStorageMenu(u8 var)
+{
+ MenuZeroFillWindowRect(0, 0, 10, 9);
+ MenuDrawTextWindow(0, 0, 11, 9);
+ PrintMenuItems(1, 1, 4, gUnknown_084062C0);
+ InitMenu(0, 1, 1, 4, var, 10);
+ ItemStorageMenuPrint((u8 *)gUnknown_08406288[var]);
+}
+
+void ItemStorageMenuPrint(u8 *textPtr)
+{
+ MenuFillWindowRectWithBlankTile(2, 15, 27, 18);
+ MenuPrint(textPtr, 2, 15);
+}
+
+void ItemStorageMenuProcessInput(u8 var)
+{
+ if(gMain.newAndRepeatedKeys & 0x40)
+ {
+ PlaySE(5);
+ MoveMenuCursor(-1);
+ ItemStorageMenuPrint((u8 *)gUnknown_08406288[GetMenuCursorPos()]);
+ }
+ else if(gMain.newAndRepeatedKeys & 0x80)
+ {
+ PlaySE(5);
+ MoveMenuCursor(1);
+ ItemStorageMenuPrint((u8 *)gUnknown_08406288[GetMenuCursorPos()]);
+ }
+ else if(gMain.newKeys & 0x1)
+ {
+ PlaySE(5);
+ gUnknown_084062C0[GetMenuCursorPos()].func(var);
+ }
+ else if(gMain.newKeys & 0x2)
+ {
+ sub_8072DEC();
+ PlaySE(5);
+ gUnknown_084062C0[3].func(var);
+ }
+}
+
+void Task_ItemStorage_Deposit(u8 taskId)
+{
+ if(!gPaletteFade.active)
+ {
+ sub_80A6A30();
+ DestroyTask(taskId);
+ }
+}
+
+void ItemStorage_Deposit(u8 taskId)
+{
+ gTasks[taskId].func = Task_ItemStorage_Deposit;
+ fade_screen(1, 0);
+}
+
+void sub_813A0C8(u8 taskId)
+{
+ if(sub_807D770() == 1)
+ gTasks[taskId].func = ItemStorageMenuProcessInput;
+}
+
+void sub_813A0F8(void)
+{
+ MenuDisplayMessageBox();
+ InitItemStorageMenu(1);
+ CreateTask(sub_813A0C8, 0);
+ pal_fill_black();
+}
+
+void ItemStorage_Withdraw(u8 taskId)
+{
+ u8 var;
+ u16 * data = gTasks[taskId].data;
+
+ sub_8072DEC();
+ MenuZeroFillWindowRect(0, 0, 11, 9);
+ var = CountUsedPCItemSlots();
+ data[2] = var;
+
+ if(var)
+ {
+ MenuZeroFillWindowRect(0, 14, 29, 19);
+ data[6] = 0;
+ data[0] = 0;
+ data[1] = 0;
+ sub_813A240(taskId);
+ sub_813AE6C(taskId, 0);
+ gTasks[taskId].func = sub_813A280;
+ }
+ else
+ DisplayItemMessageOnField(taskId, gOtherText_NoItems, PlayerPC_ItemStorage, 0);
+}
+
+void ItemStorage_Toss(u8 taskId)
+{
+ u8 var;
+ u16 * data = gTasks[taskId].data;
+
+ sub_8072DEC();
+ MenuZeroFillWindowRect(0, 0, 11, 9);
+ var = CountUsedPCItemSlots();
+ data[2] = var;
+
+ if(var)
+ {
+ MenuZeroFillWindowRect(0, 14, 29, 19);
+ data[6] = 2;
+ data[0] = 0;
+ data[1] = 0;
+ sub_813A240(taskId);
+ sub_813AE6C(taskId, 2);
+ gTasks[taskId].func = sub_813A280;
+ }
+ else
+ DisplayItemMessageOnField(taskId, gOtherText_NoItems, PlayerPC_ItemStorage, 0);
+}
+
+void ItemStorage_Exit(u8 var)
+{
+ sub_8072DEC();
+ MenuZeroFillWindowRect(0, 0, 11, 9);
+ ReshowPlayerPC(var);
+}
+
+void sub_813A240(u8 taskId)
+{
+ s16 *data = gTasks[taskId].data;
+
+ if (data[2] > 7)
+ data[4] = 8;
+ else
+ data[4] = data[2] + 1;
+
+ if(unk_201FE00[3] > 7)
+ unk_201FE00[1] = 8;
+ else
+ unk_201FE00[1] = unk_201FE00[3] + 1;
+}
+
+#ifdef NONMATCHING
+void sub_813A280(u8 taskId)
+{
+ s16 *data = gTasks[taskId].data;
+
+ if(gMain.newAndRepeatedKeys & 0x40)
+ {
+ if(data[0])
+ {
+ PlaySE(5);
+ data[0] = MoveMenuCursor(-1);
+ if(!data[9])
+ {
+ if(data[1] + data[0] == data[2])
+ {
+ sub_813AD58(0xFFFF);
+ return;
+ }
+ sub_813AD58(gSaveBlock1.pcItems[data[1] + data[0]].itemId);
+ }
+ return;
+ }
+ if(!data[1])
+ return;
+ PlaySE(5);
+ sub_813AE0C(taskId);
+ if(data[9])
+ MoveMenuCursor(0);
+ return;
+ }
+ if(!(gMain.newAndRepeatedKeys & 0x80))
+ {
+ if(gMain.newKeys & 0x4)
+ {
+ if(!data[9])
+ {
+ if(data[0] + data[1] != data[2])
+ {
+ PlaySE(5);
+ data[9] = 1;
+ data[8] = data[0] + data[1];
+ sub_813AD58(0xFFF7);
+ }
+ sub_813ABE8(taskId);
+ return;
+ }
+ PlaySE(5);
+ sub_813AA30(taskId, 0);
+ sub_813AE0C(taskId);
+ return;
+ }
+ if(gMain.newKeys & 0x1)
+ {
+ PlaySE(5);
+ if(data[9])
+ {
+ sub_813AA30(taskId, 0);
+ sub_813AE0C(taskId);
+ return;
+ }
+ if(data[1] + data[0] != data[2])
+ {
+ sub_813A4B4(taskId);
+ return;
+ }
+ }
+ else
+ {
+ if(!(gMain.newKeys & 0x2))
+ return;
+ PlaySE(5);
+ if(data[9])
+ {
+ sub_813AA30(taskId, 1);
+ sub_813AE0C(taskId);
+ return;
+ }
+ sub_8072DEC();
+ }
+ sub_813A468(taskId);
+ return;
+ }
+ if(data[0] == data[4] - 1)
+ {
+ if(data[1] + data[0] == data[2])
+ return;
+ PlaySE(5);
+ data[1]++;
+ sub_813AE0C(taskId);
+ if(data[9])
+ MoveMenuCursor(0);
+ return;
+ }
+ PlaySE(5);
+ data[0] = MoveMenuCursor(1);
+ if(!data[9])
+ {
+ if(data[1] + data[0] != data[2])
+ {
+ sub_813AD58(gSaveBlock1.pcItems[data[1] + data[0]].itemId);
+ return;
+ }
+ sub_813AD58(0xFFFF);
+ }
+}
+#else
+__attribute__((naked))
+void sub_813A280(u8 taskId)
+{
+ asm(".syntax unified\n\
+ push {r4-r6,lr}\n\
+ lsls r0, 24\n\
+ lsrs r5, r0, 24\n\
+ adds r6, r5, 0\n\
+ lsls r0, r5, 2\n\
+ adds r0, r5\n\
+ lsls r0, 3\n\
+ ldr r1, _0813A2DC @ =gTasks + 0x8\n\
+ adds r4, r0, r1\n\
+ ldr r2, _0813A2E0 @ =gMain\n\
+ ldrh r1, [r2, 0x30]\n\
+ movs r0, 0x40\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0813A306\n\
+ movs r1, 0\n\
+ ldrsh r0, [r4, r1]\n\
+ cmp r0, 0\n\
+ beq _0813A2E4\n\
+ movs r0, 0x5\n\
+ bl PlaySE\n\
+ movs r0, 0x1\n\
+ negs r0, r0\n\
+ bl MoveMenuCursor\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ strh r0, [r4]\n\
+ ldrh r1, [r4, 0x2]\n\
+ adds r1, r0\n\
+ lsls r1, 16\n\
+ lsrs r1, 16\n\
+ movs r2, 0x12\n\
+ ldrsh r0, [r4, r2]\n\
+ cmp r0, 0\n\
+ beq _0813A2CC\n\
+ b _0813A460\n\
+_0813A2CC:\n\
+ lsls r0, r1, 16\n\
+ asrs r1, r0, 16\n\
+ movs r2, 0x4\n\
+ ldrsh r0, [r4, r2]\n\
+ cmp r1, r0\n\
+ beq _0813A34C\n\
+ b _0813A358\n\
+ .align 2, 0\n\
+_0813A2DC: .4byte gTasks + 0x8\n\
+_0813A2E0: .4byte gMain\n\
+_0813A2E4:\n\
+ movs r1, 0x2\n\
+ ldrsh r0, [r4, r1]\n\
+ cmp r0, 0\n\
+ bne _0813A2EE\n\
+ b _0813A460\n\
+_0813A2EE:\n\
+ movs r0, 0x5\n\
+ bl PlaySE\n\
+ ldrh r0, [r4, 0x2]\n\
+ subs r0, 0x1\n\
+ strh r0, [r4, 0x2]\n\
+ adds r0, r5, 0\n\
+ bl sub_813AE0C\n\
+ movs r2, 0x12\n\
+ ldrsh r0, [r4, r2]\n\
+ b _0813A394\n\
+_0813A306:\n\
+ movs r0, 0x80\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0813A3A0\n\
+ movs r0, 0\n\
+ ldrsh r1, [r4, r0]\n\
+ movs r2, 0x8\n\
+ ldrsh r0, [r4, r2]\n\
+ subs r0, 0x1\n\
+ cmp r1, r0\n\
+ beq _0813A370\n\
+ movs r0, 0x5\n\
+ bl PlaySE\n\
+ movs r0, 0x1\n\
+ bl MoveMenuCursor\n\
+ lsls r0, 24\n\
+ lsrs r0, 24\n\
+ strh r0, [r4]\n\
+ ldrh r1, [r4, 0x2]\n\
+ adds r1, r0\n\
+ lsls r1, 16\n\
+ lsrs r1, 16\n\
+ movs r2, 0x12\n\
+ ldrsh r0, [r4, r2]\n\
+ cmp r0, 0\n\
+ beq _0813A340\n\
+ b _0813A460\n\
+_0813A340:\n\
+ lsls r0, r1, 16\n\
+ asrs r1, r0, 16\n\
+ movs r2, 0x4\n\
+ ldrsh r0, [r4, r2]\n\
+ cmp r1, r0\n\
+ bne _0813A358\n\
+_0813A34C:\n\
+ ldr r0, _0813A354 @ =0x0000ffff\n\
+ bl sub_813AD58\n\
+ b _0813A460\n\
+ .align 2, 0\n\
+_0813A354: .4byte 0x0000ffff\n\
+_0813A358:\n\
+ ldr r0, _0813A36C @ =gSaveBlock1\n\
+ lsls r1, 2\n\
+ adds r1, r0\n\
+ movs r0, 0x93\n\
+ lsls r0, 3\n\
+ adds r1, r0\n\
+ ldrh r0, [r1]\n\
+ bl sub_813AD58\n\
+ b _0813A460\n\
+ .align 2, 0\n\
+_0813A36C: .4byte gSaveBlock1\n\
+_0813A370:\n\
+ movs r2, 0x2\n\
+ ldrsh r0, [r4, r2]\n\
+ adds r0, r1\n\
+ movs r2, 0x4\n\
+ ldrsh r1, [r4, r2]\n\
+ cmp r0, r1\n\
+ beq _0813A460\n\
+ movs r0, 0x5\n\
+ bl PlaySE\n\
+ ldrh r0, [r4, 0x2]\n\
+ adds r0, 0x1\n\
+ strh r0, [r4, 0x2]\n\
+ adds r0, r5, 0\n\
+ bl sub_813AE0C\n\
+ movs r1, 0x12\n\
+ ldrsh r0, [r4, r1]\n\
+_0813A394:\n\
+ cmp r0, 0\n\
+ beq _0813A460\n\
+ movs r0, 0\n\
+ bl MoveMenuCursor\n\
+ b _0813A460\n\
+_0813A3A0:\n\
+ ldrh r1, [r2, 0x2E]\n\
+ movs r0, 0x4\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0813A3F0\n\
+ movs r2, 0x12\n\
+ ldrsh r0, [r4, r2]\n\
+ cmp r0, 0\n\
+ bne _0813A3E8\n\
+ movs r1, 0\n\
+ ldrsh r0, [r4, r1]\n\
+ movs r2, 0x2\n\
+ ldrsh r1, [r4, r2]\n\
+ adds r0, r1\n\
+ movs r2, 0x4\n\
+ ldrsh r1, [r4, r2]\n\
+ cmp r0, r1\n\
+ beq _0813A3DC\n\
+ movs r0, 0x5\n\
+ bl PlaySE\n\
+ movs r0, 0x1\n\
+ strh r0, [r4, 0x12]\n\
+ ldrh r0, [r4]\n\
+ ldrh r1, [r4, 0x2]\n\
+ adds r0, r1\n\
+ strh r0, [r4, 0x10]\n\
+ ldr r0, _0813A3E4 @ =0x0000fff7\n\
+ bl sub_813AD58\n\
+_0813A3DC:\n\
+ adds r0, r5, 0\n\
+ bl sub_813ABE8\n\
+ b _0813A460\n\
+ .align 2, 0\n\
+_0813A3E4: .4byte 0x0000fff7\n\
+_0813A3E8:\n\
+ movs r0, 0x5\n\
+ bl PlaySE\n\
+ b _0813A420\n\
+_0813A3F0:\n\
+ movs r0, 0x1\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0813A430\n\
+ movs r0, 0x5\n\
+ bl PlaySE\n\
+ movs r2, 0x12\n\
+ ldrsh r0, [r4, r2]\n\
+ cmp r0, 0\n\
+ bne _0813A420\n\
+ movs r1, 0x2\n\
+ ldrsh r0, [r4, r1]\n\
+ movs r2, 0\n\
+ ldrsh r1, [r4, r2]\n\
+ adds r0, r1\n\
+ movs r2, 0x4\n\
+ ldrsh r1, [r4, r2]\n\
+ cmp r0, r1\n\
+ beq _0813A44A\n\
+ adds r0, r5, 0\n\
+ bl sub_813A4B4\n\
+ b _0813A460\n\
+_0813A420:\n\
+ adds r0, r5, 0\n\
+ movs r1, 0\n\
+ bl sub_813AA30\n\
+ adds r0, r5, 0\n\
+ bl sub_813AE0C\n\
+ b _0813A460\n\
+_0813A430:\n\
+ movs r0, 0x2\n\
+ ands r0, r1\n\
+ cmp r0, 0\n\
+ beq _0813A460\n\
+ movs r0, 0x5\n\
+ bl PlaySE\n\
+ movs r1, 0x12\n\
+ ldrsh r0, [r4, r1]\n\
+ cmp r0, 0\n\
+ bne _0813A452\n\
+ bl sub_8072DEC\n\
+_0813A44A:\n\
+ adds r0, r5, 0\n\
+ bl sub_813A468\n\
+ b _0813A460\n\
+_0813A452:\n\
+ adds r0, r6, 0\n\
+ movs r1, 0x1\n\
+ bl sub_813AA30\n\
+ adds r0, r6, 0\n\
+ bl sub_813AE0C\n\
+_0813A460:\n\
+ pop {r4-r6}\n\
+ pop {r0}\n\
+ bx r0\n\
+ .syntax divided");
+}
+#endif
+
+void sub_813A468(u8 taskId)
+{
+ BuyMenuFreeMemory();
+ DestroyVerticalScrollIndicator(0);
+ DestroyVerticalScrollIndicator(1);
+ MenuZeroFillWindowRect(0, 0, 29, 19);
+ MenuDisplayMessageBox();
+ InitItemStorageMenu(gTasks[taskId].data[6]);
+ gTasks[taskId].func = ItemStorageMenuProcessInput;
+}
+
+#ifdef NONMATCHING
+void sub_813A4B4(u8 taskId)
+{
+ u16 *data = gTasks[taskId].data;
+ u16 var = data[2] + data[0];
+
+ sub_80F996C(0);
+ sub_80F996C(1);
+
+ if(data[6])
+ {
+ if(gSaveBlock1.pcItems[var].itemId == 1)
+ {
+ data[3] = 1;
+ sub_813A794(taskId);
+ return;
+ }
+ sub_813AD58(0xFFF7);
+ data[3] = 1;
+ MenuDrawTextWindow(6, 8, 13, 11);
+ sub_80A418C(data[3], STR_CONV_MODE_RIGHT_ALIGN, 8, 9, 3);
+ gTasks[taskId].func = sub_813A584;
+ return;
+ }
+ if(gSaveBlock1.pcItems[var].itemId != 1)
+ {
+ sub_813AD58(0xFFF7);
+ data[3] = 1;
+ MenuDrawTextWindow(6, 8, 13, 11);
+ sub_80A418C(data[3], STR_CONV_MODE_RIGHT_ALIGN, 8, 9, 3);
+ gTasks[taskId].func = sub_813A584;
+ return;
+ }
+ data[3] = 1;
+ sub_813A6FC(taskId);
+}
+#else
+__attribute__((naked))
+void sub_813A4B4(u8 taskId)
+{
+ asm(".syntax unified\n\
+ push {r4-r6,lr}\n\
+ sub sp, 0x4\n\
+ lsls r0, 24\n\
+ lsrs r6, r0, 24\n\
+ lsls r0, r6, 2\n\
+ adds r0, r6\n\
+ lsls r0, 3\n\
+ ldr r1, _0813A500 @ =gTasks + 0x8\n\
+ adds r4, r0, r1\n\
+ ldrb r0, [r4, 0x2]\n\
+ ldrb r1, [r4]\n\
+ adds r0, r1\n\
+ lsls r0, 24\n\
+ lsrs r5, r0, 24\n\
+ movs r0, 0\n\
+ bl sub_80F996C\n\
+ movs r0, 0x1\n\
+ bl sub_80F996C\n\
+ movs r1, 0xC\n\
+ ldrsh r0, [r4, r1]\n\
+ cmp r0, 0\n\
+ bne _0813A518\n\
+ ldr r1, _0813A504 @ =gSaveBlock1\n\
+ lsls r0, r5, 2\n\
+ adds r0, r1\n\
+ ldr r1, _0813A508 @ =0x0000049a\n\
+ adds r0, r1\n\
+ ldrh r0, [r0]\n\
+ cmp r0, 0x1\n\
+ bne _0813A50C\n\
+ strh r0, [r4, 0x6]\n\
+ adds r0, r6, 0\n\
+ bl sub_813A6FC\n\
+ b _0813A570\n\
+ .align 2, 0\n\
+_0813A500: .4byte gTasks + 0x8\n\
+_0813A504: .4byte gSaveBlock1\n\
+_0813A508: .4byte 0x0000049a\n\
+_0813A50C:\n\
+ ldr r0, _0813A514 @ =0x0000fffe\n\
+ bl sub_813AD58\n\
+ b _0813A542\n\
+ .align 2, 0\n\
+_0813A514: .4byte 0x0000fffe\n\
+_0813A518:\n\
+ ldr r1, _0813A534 @ =gSaveBlock1\n\
+ lsls r0, r5, 2\n\
+ adds r0, r1\n\
+ ldr r1, _0813A538 @ =0x0000049a\n\
+ adds r0, r1\n\
+ ldrh r0, [r0]\n\
+ cmp r0, 0x1\n\
+ bne _0813A53C\n\
+ strh r0, [r4, 0x6]\n\
+ adds r0, r6, 0\n\
+ bl sub_813A794\n\
+ b _0813A570\n\
+ .align 2, 0\n\
+_0813A534: .4byte gSaveBlock1\n\
+_0813A538: .4byte 0x0000049a\n\
+_0813A53C:\n\
+ ldr r0, _0813A578 @ =0x0000fffc\n\
+ bl sub_813AD58\n\
+_0813A542:\n\
+ movs r0, 0x1\n\
+ strh r0, [r4, 0x6]\n\
+ movs r0, 0x6\n\
+ movs r1, 0x8\n\
+ movs r2, 0xD\n\
+ movs r3, 0xB\n\
+ bl MenuDrawTextWindow\n\
+ ldrh r0, [r4, 0x6]\n\
+ movs r1, 0x3\n\
+ str r1, [sp]\n\
+ movs r1, 0x1\n\
+ movs r2, 0x8\n\
+ movs r3, 0x9\n\
+ bl sub_80A418C\n\
+ ldr r1, _0813A57C @ =gTasks\n\
+ lsls r0, r6, 2\n\
+ adds r0, r6\n\
+ lsls r0, 3\n\
+ adds r0, r1\n\
+ ldr r1, _0813A580 @ =sub_813A584\n\
+ str r1, [r0]\n\
+_0813A570:\n\
+ add sp, 0x4\n\
+ pop {r4-r6}\n\
+ pop {r0}\n\
+ bx r0\n\
+ .align 2, 0\n\
+_0813A578: .4byte 0x0000fffc\n\
+_0813A57C: .4byte gTasks\n\
+_0813A580: .4byte sub_813A584\n\
+ .syntax divided");
+}
+#endif
diff --git a/src/pokedex.c b/src/pokedex.c
index aa832a681..54fa5912c 100644
--- a/src/pokedex.c
+++ b/src/pokedex.c
@@ -170,7 +170,6 @@ void sub_808C0B8(void)
void ClearPokedexView(struct PokedexView *pokedexView)
{
u16 i;
- struct UnknownStruct3 *p;
for(i = 0; i <= 385; i++)
{
@@ -1732,7 +1731,6 @@ void sub_808E6BC(void)
u8 sub_808E71C(void)
{
u16 r2;
- u16 r3;
u16 r4 = gPokedexView->selectedPokemon;
if((gMain.newKeys & DPAD_UP) && r4)
@@ -2177,8 +2175,6 @@ void sub_808F168(struct Sprite *sprite)
if(gPokedexView->menuIsOpen != 0 && gPokedexView->menuY == r1)
{
- u8 data2;
-
sprite->invisible = 0;
sprite->pos2.y = gPokedexView->menuCursorPos * 16;
sprite->pos2.x = gSineTable[(u8)sprite->data2] / 64;
diff --git a/src/pokemon_1.c b/src/pokemon_1.c
index 3971e08dd..d6f475171 100644
--- a/src/pokemon_1.c
+++ b/src/pokemon_1.c
@@ -200,7 +200,7 @@ void CreateMonWithGenderNatureLetter(struct Pokemon *mon, u16 species, u8 level,
do
{
personality = Random32();
- actualLetter = ((((personality & 0x3000000) >> 18) | ((personality & 0x30000) >> 12) | ((personality & 0x300) >> 6) | personality & 0x3) % 28);
+ actualLetter = ((((personality & 0x3000000) >> 18) | ((personality & 0x30000) >> 12) | ((personality & 0x300) >> 6) | (personality & 0x3)) % 28);
}
while (nature != GetNatureFromPersonality(personality)
|| gender != GetGenderFromSpeciesAndPersonality(species, personality)
@@ -302,9 +302,9 @@ void sub_803ADE8(struct Pokemon *mon, struct UnknownPokemonStruct *src)
StringCopy(nickname, src->nickname);
if (nickname[0] == 0xFC && nickname[1] == 0x15)
- language = 1;
+ language = LANGUAGE_JAPANESE;
else
- language = 2;
+ language = GAME_LANGUAGE;
SetMonData(mon, MON_DATA_LANGUAGE, &language);
StripExtCtrlCodes(nickname);
@@ -422,7 +422,6 @@ void CalculateMonStats(struct Pokemon *mon)
u16 species = GetMonData(mon, MON_DATA_SPECIES, NULL);
s32 level = GetLevelFromMonExp(mon);
s32 newMaxHP;
- u8 nature;
SetMonData(mon, MON_DATA_LEVEL, (u8 *)&level);
diff --git a/src/pokemon_2.c b/src/pokemon_2.c
index aeffb29a0..2baf1155e 100644
--- a/src/pokemon_2.c
+++ b/src/pokemon_2.c
@@ -26,7 +26,7 @@ extern u8 gUnknown_02024C07;
extern u8 gUnknown_02024C08;
extern u8 gUnknown_02024C0C;
extern u8 gXXX_CritRelated;
-extern u16 word_2024DB8;
+extern u16 gBattleWeather;
extern struct BattleEnigmaBerry gEnigmaBerries[];
extern u16 gBattleMovePower;
extern struct SpriteTemplate gUnknown_02024E8C;
@@ -1016,7 +1016,11 @@ void SetBoxMonData(struct BoxPokemon *boxMon, s32 field, const u8 *data)
break;
case MON_DATA_IVS:
{
+#ifdef BUGFIX_SETMONIVS
+ u32 ivs = data[0] | (data[1] << 8) | (data[2] << 16) | (data[3] << 24);
+#else
u32 ivs = *data; // Bug: Only the HP IV and the lower 3 bits of the Attack IV are read. The rest become 0.
+#endif
substruct3->hpIV = ivs & 0x1F;
substruct3->attackIV = (ivs >> 5) & 0x1F;
substruct3->defenseIV = (ivs >> 10) & 0x1F;
diff --git a/src/pokemon_3.c b/src/pokemon_3.c
new file mode 100644
index 000000000..f69ffcfef
--- /dev/null
+++ b/src/pokemon_3.c
@@ -0,0 +1,477 @@
+#include "global.h"
+#include "asm.h"
+#include "text.h"
+#include "string_util.h"
+#include "pokemon.h"
+#include "rng.h"
+#include "species.h"
+#include "main.h"
+#include "sprite.h"
+#include "flag.h"
+#include "rtc.h"
+#include "item.h"
+
+#define EVO_FRIENDSHIP 0x0001 // Pokémon levels up with friendship ≥ 220
+#define EVO_FRIENDSHIP_DAY 0x0002 // Pokémon levels up during the day with friendship ≥ 220
+#define EVO_FRIENDSHIP_NIGHT 0x0003 // Pokémon levels up at night with friendship ≥ 220
+#define EVO_LEVEL 0x0004 // Pokémon reaches the specified level
+#define EVO_TRADE 0x0005 // Pokémon is traded
+#define EVO_TRADE_ITEM 0x0006 // Pokémon is traded while it's holding the specified item
+#define EVO_ITEM 0x0007 // specified item is used on Pokémon
+#define EVO_LEVEL_ATK_GT_DEF 0x0008 // Pokémon reaches the specified level with attack > defense
+#define EVO_LEVEL_ATK_EQ_DEF 0x0009 // Pokémon reaches the specified level with attack = defense
+#define EVO_LEVEL_ATK_LT_DEF 0x000a // Pokémon reaches the specified level with attack < defense
+#define EVO_LEVEL_SILCOON 0x000b // Pokémon reaches the specified level with a Silcoon personality value
+#define EVO_LEVEL_CASCOON 0x000c // Pokémon reaches the specified level with a Cascoon personality value
+#define EVO_LEVEL_NINJASK 0x000d // Pokémon reaches the specified level (special value for Ninjask)
+#define EVO_LEVEL_SHEDINJA 0x000e // Pokémon reaches the specified level (special value for Shedinja)
+#define EVO_BEAUTY 0x000f // Pokémon levels up with beauty ≥ specified value
+
+struct Evolution
+{
+ u16 method;
+ u16 param;
+ u16 targetSpecies;
+};
+
+struct EvolutionData
+{
+ struct Evolution evolutions[5];
+};
+
+extern void get_battle_strings_(u8 *);
+
+extern u8 gPlayerPartyCount;
+extern struct Pokemon gPlayerParty[6];
+extern u8 gEnemyPartyCount;
+extern struct Pokemon gEnemyParty[6];
+extern struct BattlePokemon gBattleMons[4];
+extern u8 * const gItemEffectTable[];
+extern u8 gUnknown_02024A60;
+extern struct BattleEnigmaBerry gEnigmaBerries[];
+extern struct EvolutionData gEvolutionTable[];
+extern u16 gSpeciesToHoennPokedexNum[];
+extern u16 gSpeciesToNationalPokedexNum[];
+extern u16 gHoennToNationalOrder[];
+extern u16 gSpeciesIdToCryId[];
+extern u8 gUnknown_030041C0[];
+extern u8 gUnknown_03004290[];
+extern u8 gUnknown_020238CC[];
+extern u8 gUnknown_02024C07;
+extern u8 gUnknown_02024C08;
+extern u8 gUnknown_02024C0B;
+extern u8 gUnknown_02024E6C;
+
+extern u8 gUnknown_082082F8[];
+extern u8 gUnknown_083FFDB3[];
+extern u8 gUnknown_083FFDD3[];
+extern u8 gUnknown_083FEE5D[];
+extern u8 gUnknown_083FEE92[];
+extern u8 *gUnknown_08400F58[];
+
+bool8 HealStatusConditions(struct Pokemon *mon, u32 unused, u32 healMask, u8 battleId)
+{
+ u32 status = GetMonData(mon, MON_DATA_STATUS, 0);
+
+ if (status & healMask)
+ {
+ status &= ~healMask;
+ SetMonData(mon, MON_DATA_STATUS, (u8 *)&status);
+ if (gMain.inBattle && battleId != 4)
+ gBattleMons[battleId].status1 &= ~healMask;
+ return FALSE;
+ }
+ else
+ {
+ return TRUE;
+ }
+}
+
+u8 GetItemEffectParamOffset(u16 itemId, u8 effectByte, u8 effectBit)
+{
+ u8 *temp;
+ u8 *itemEffect;
+ u8 offset;
+ int i;
+ u8 j;
+ u8 val;
+
+ offset = 6;
+
+ temp = gItemEffectTable[itemId - 13];
+
+ if (!temp && itemId != 175)
+ return 0;
+
+ if (itemId == 175)
+ {
+ temp = gEnigmaBerries[gUnknown_02024A60].itemEffect;
+ }
+
+ itemEffect = temp;
+
+ for (i = 0; i < 6; i++)
+ {
+ switch (i)
+ {
+ case 0:
+ case 1:
+ case 2:
+ case 3:
+ if (i == effectByte)
+ return 0;
+ break;
+ case 4:
+ val = itemEffect[4];
+ if (val & 0x20)
+ val &= 0xDF;
+ j = 0;
+ while (val)
+ {
+ if (val & 1)
+ {
+ switch (j)
+ {
+ case 2:
+ if (val & 0x10)
+ val &= 0xEF;
+ case 0:
+ if (i == effectByte && (val & effectBit))
+ return offset;
+ offset++;
+ break;
+ case 1:
+ if (i == effectByte && (val & effectBit))
+ return offset;
+ offset++;
+ break;
+ case 3:
+ if (i == effectByte && (val & effectBit))
+ return offset;
+ offset++;
+ break;
+ case 7:
+ if (i == effectByte)
+ return 0;
+ break;
+ }
+ }
+ j++;
+ val >>= 1;
+ if (i == effectByte)
+ effectBit >>= 1;
+ }
+ break;
+ case 5:
+ val = itemEffect[5];
+ j = 0;
+ while (val)
+ {
+ if (val & 1)
+ {
+ switch (j)
+ {
+ case 0:
+ case 1:
+ case 2:
+ case 3:
+ case 4:
+ case 5:
+ case 6:
+ if (i == effectByte && (val & effectBit))
+ return offset;
+ offset++;
+ break;
+ case 7:
+ if (i == effectByte)
+ return 0;
+ break;
+ }
+ }
+ j++;
+ val >>= 1;
+ if (i == effectByte)
+ effectBit >>= 1;
+ }
+ break;
+ }
+ }
+
+ return offset;
+}
+
+void sub_803F324(int stat)
+{
+ gUnknown_02024C08 = gUnknown_02024E6C;
+ StringCopy(gUnknown_030041C0, gUnknown_08400F58[gUnknown_082082F8[stat]]);
+ StringCopy(gUnknown_03004290, gUnknown_083FFDB3);
+ get_battle_strings_(gUnknown_083FFDD3);
+}
+
+u8 *sub_803F378(u16 itemId)
+{
+ int i;
+ u8 *itemEffect;
+
+ if (itemId == 175)
+ {
+ if (gMain.inBattle)
+ {
+ itemEffect = gEnigmaBerries[gUnknown_02024E6C].itemEffect;
+ }
+ else
+ {
+ itemEffect = gSaveBlock1.enigmaBerry.itemEffect;
+ }
+ }
+ else
+ {
+ itemEffect = gItemEffectTable[itemId - 13];
+ }
+
+ gUnknown_02024C0B = gUnknown_02024E6C;
+
+ for (i = 0; i < 3; i++)
+ {
+ if (itemEffect[i] & 0xF)
+ sub_803F324(i * 2);
+ if (itemEffect[i] & 0xF0)
+ {
+ if (i)
+ {
+ sub_803F324(i * 2 + 1);
+ }
+ else
+ {
+ gUnknown_02024C07 = gUnknown_02024E6C;
+ get_battle_strings_(gUnknown_083FEE92);
+ }
+ }
+ }
+
+ if (itemEffect[3] & 0x80)
+ {
+ gUnknown_02024C07 = gUnknown_02024E6C;
+ get_battle_strings_(gUnknown_083FEE5D);
+ }
+
+ return gUnknown_020238CC;
+}
+
+u8 GetNature(struct Pokemon *mon)
+{
+ return GetMonData(mon, MON_DATA_PERSONALITY, 0) % 25;
+}
+
+u8 GetNatureFromPersonality(u32 personality)
+{
+ return personality % 25;
+}
+
+u16 GetEvolutionTargetSpecies(struct Pokemon *mon, u8 type, u16 evolutionItem)
+{
+ int i;
+ u16 targetSpecies = 0;
+ u16 species = GetMonData(mon, MON_DATA_SPECIES, 0);
+ u16 heldItem = GetMonData(mon, MON_DATA_HELD_ITEM, 0);
+ u32 personality = GetMonData(mon, MON_DATA_PERSONALITY, 0);
+ u8 level;
+ u16 friendship;
+ u8 beauty = GetMonData(mon, MON_DATA_BEAUTY, 0);
+ u16 upperPersonality = personality >> 16;
+ u8 holdEffect;
+
+ if (heldItem == 175)
+ holdEffect = gSaveBlock1.enigmaBerry.holdEffect;
+ else
+ holdEffect = ItemId_GetHoldEffect(heldItem);
+
+ if (holdEffect == 38 && type != 3)
+ return 0;
+
+ switch (type)
+ {
+ case 0:
+ level = GetMonData(mon, MON_DATA_LEVEL, 0);
+ friendship = GetMonData(mon, MON_DATA_FRIENDSHIP, 0);
+
+ for (i = 0; i < 5; i++)
+ {
+ switch (gEvolutionTable[species].evolutions[i].method)
+ {
+ case EVO_FRIENDSHIP:
+ if (friendship >= 220)
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_FRIENDSHIP_DAY:
+ RtcCalcLocalTime();
+ if (gLocalTime.hours >= 12 && gLocalTime.hours < 24 && friendship >= 220)
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_FRIENDSHIP_NIGHT:
+ RtcCalcLocalTime();
+ if (gLocalTime.hours >= 0 && gLocalTime.hours < 12 && friendship >= 220)
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_LEVEL:
+ if (gEvolutionTable[species].evolutions[i].param <= level)
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_LEVEL_ATK_GT_DEF:
+ if (gEvolutionTable[species].evolutions[i].param <= level)
+ if (GetMonData(mon, MON_DATA_ATK, 0) > GetMonData(mon, MON_DATA_DEF, 0))
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_LEVEL_ATK_EQ_DEF:
+ if (gEvolutionTable[species].evolutions[i].param <= level)
+ if (GetMonData(mon, MON_DATA_ATK, 0) == GetMonData(mon, MON_DATA_DEF, 0))
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_LEVEL_ATK_LT_DEF:
+ if (gEvolutionTable[species].evolutions[i].param <= level)
+ if (GetMonData(mon, MON_DATA_ATK, 0) < GetMonData(mon, MON_DATA_DEF, 0))
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_LEVEL_SILCOON:
+ if (gEvolutionTable[species].evolutions[i].param <= level && (upperPersonality % 10) <= 4)
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_LEVEL_CASCOON:
+ if (gEvolutionTable[species].evolutions[i].param <= level && (upperPersonality % 10) > 4)
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_LEVEL_NINJASK:
+ if (gEvolutionTable[species].evolutions[i].param <= level)
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_BEAUTY:
+ if (gEvolutionTable[species].evolutions[i].param <= beauty)
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ }
+ }
+ break;
+ case 1:
+ for (i = 0; i < 5; i++)
+ {
+ switch (gEvolutionTable[species].evolutions[i].method)
+ {
+ case EVO_TRADE:
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ case EVO_TRADE_ITEM:
+ if (gEvolutionTable[species].evolutions[i].param == heldItem)
+ {
+ heldItem = 0;
+ SetMonData(mon, MON_DATA_HELD_ITEM, (u8 *)&heldItem);
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ }
+ break;
+ }
+ }
+ break;
+ case 2:
+ case 3:
+ for (i = 0; i < 5; i++)
+ {
+ if (gEvolutionTable[species].evolutions[i].method == EVO_ITEM
+ && gEvolutionTable[species].evolutions[i].param == evolutionItem)
+ {
+ targetSpecies = gEvolutionTable[species].evolutions[i].targetSpecies;
+ break;
+ }
+ }
+ break;
+ }
+
+ return targetSpecies;
+}
+
+u16 HoennPokedexNumToSpecies(u16 hoennNum)
+{
+ u16 species;
+
+ if (!hoennNum)
+ return 0;
+
+ species = 0;
+
+ while (species < 411 && gSpeciesToHoennPokedexNum[species] != hoennNum)
+ species++;
+
+ if (species == 411)
+ return 0;
+
+ return species + 1;
+}
+
+u16 NationalPokedexNumToSpecies(u16 nationalNum)
+{
+ u16 species;
+
+ if (!nationalNum)
+ return 0;
+
+ species = 0;
+
+ while (species < 411 && gSpeciesToNationalPokedexNum[species] != nationalNum)
+ species++;
+
+ if (species == 411)
+ return 0;
+
+ return species + 1;
+}
+
+u16 NationalToHoennOrder(u16 nationalNum)
+{
+ u16 hoennNum;
+
+ if (!nationalNum)
+ return 0;
+
+ hoennNum = 0;
+
+ while (hoennNum < 411 && gHoennToNationalOrder[hoennNum] != nationalNum)
+ hoennNum++;
+
+ if (hoennNum == 411)
+ return 0;
+
+ return hoennNum + 1;
+}
+
+u16 SpeciesToNationalPokedexNum(u16 species)
+{
+ if (!species)
+ return 0;
+
+ return gSpeciesToNationalPokedexNum[species - 1];
+}
+
+u16 SpeciesToHoennPokedexNum(u16 species)
+{
+ if (!species)
+ return 0;
+
+ return gSpeciesToHoennPokedexNum[species - 1];
+}
+
+u16 HoennToNationalOrder(u16 hoennNum)
+{
+ if (!hoennNum)
+ return 0;
+
+ return gHoennToNationalOrder[hoennNum - 1];
+}
+
+u32 SpeciesToCryId(u16 species)
+{
+ if (species <= 250)
+ return species;
+
+ if (species < 276)
+ return 200;
+
+ return gSpeciesIdToCryId[species - 276];
+}
diff --git a/src/pokemon_size_record.c b/src/pokemon_size_record.c
index 11c00dbe2..21f386f2d 100644
--- a/src/pokemon_size_record.c
+++ b/src/pokemon_size_record.c
@@ -61,7 +61,6 @@ static u32 GetMonSize(u16 species, u16 b)
u64 unk0;
u32 r7;
u32 var;
- struct UnknownStruct *s;
r7 = sub_8090D54(SpeciesToNationalPokedexNum(species), 0);
var = TranslateBigMonSizeTableIndex(b);
diff --git a/src/rom4.c b/src/rom4.c
index a3b0b221d..bd5a9d285 100644
--- a/src/rom4.c
+++ b/src/rom4.c
@@ -4,31 +4,33 @@
#include "asm_fieldmap.h"
#include "battle_setup.h"
#include "berry.h"
+#include "field_camera.h"
+#include "field_effect.h"
#include "field_map_obj.h"
+#include "field_message_box.h"
#include "field_player_avatar.h"
+#include "flag.h"
+#include "heal_location.h"
+#include "link.h"
+#include "load_save.h"
+#include "main.h"
#include "menu.h"
-#include "weather.h"
-#include "task.h"
-#include "tileset_anim.h"
-#include "start_menu.h"
-#include "play_time.h"
-#include "truck_scene.h"
#include "new_game.h"
-#include "heal_location.h"
-#include "field_message_box.h"
+#include "palette.h"
+#include "play_time.h"
+#include "rng.h"
#include "safari_zone.h"
#include "script.h"
#include "songs.h"
#include "sound.h"
-#include "rng.h"
-#include "main.h"
-#include "palette.h"
-#include "link.h"
-#include "flag.h"
+#include "start_menu.h"
+#include "task.h"
+#include "tileset_anim.h"
+#include "truck_scene.h"
#include "var.h"
-#include "field_camera.h"
-#include "field_effect.h"
+#include "weather.h"
#include "wild_encounter.h"
+#include "metatile_behavior.h"
#ifdef SAPPHIRE
#define LEGENDARY_MUSIC BGM_OOAME // Heavy Rain
@@ -454,7 +456,7 @@ void sub_80537CC(u8 a1)
warp_set(&gSaveBlock1.warp1, warp->group, warp->map, -1, warp->x, warp->y);
}
-void gpu_sync_bg_hide(void)
+void gpu_sync_bg_hide()
{
gSaveBlock1.warp1 = gSaveBlock1.warp2;
}
@@ -1262,9 +1264,9 @@ void CB2_ContinueSavedGame(void)
PlayTimeCounter_Start();
ScriptContext1_Init();
ScriptContext2_Disable();
- if (sub_80479F8() == 1)
+ if (GetSecretBase2Field_9() == 1)
{
- sub_8047A04();
+ ClearSecretBase2Field_9();
sub_8053778();
warp_in();
SetMainCallback2(CB2_LoadMap);
diff --git a/src/rtc.c b/src/rtc.c
index 3d24253b9..d73f943d2 100644
--- a/src/rtc.c
+++ b/src/rtc.c
@@ -63,9 +63,8 @@ u16 ConvertDateToDayCount(u8 year, u8 month, u8 day)
s32 i;
u16 dayCount = 0;
-#if (REVISION < 2)
- // Revisions 0 and 1 don't add days for the year 2000,
- // causing the berry glitch.
+#ifndef BUGFIX_BERRY
+ // The berry glitch was caused by not adding days for the year 2000.
for (i = year - 1; i > 0; i--)
{
dayCount += 365;
@@ -74,8 +73,7 @@ u16 ConvertDateToDayCount(u8 year, u8 month, u8 day)
dayCount++;
}
#else
- // Revision 2 has "i >= 0" as the condition instead of "i > 0",
- // which fixes the issue.
+ // The fix was to use "i >= 0" as the condition instead of "i > 0".
for (i = year - 1; i >= 0; i--)
{
dayCount += 365;
@@ -83,7 +81,7 @@ u16 ConvertDateToDayCount(u8 year, u8 month, u8 day)
if (IsLeapYear(i) == TRUE)
dayCount++;
}
-#endif
+#endif // BUGFIX_BERRY
for (i = 0; i < month - 1; i++)
dayCount += sNumDaysInMonths[i];
diff --git a/src/save.c b/src/save.c
index a26e0da98..2771b4ea5 100644
--- a/src/save.c
+++ b/src/save.c
@@ -2,8 +2,10 @@
#include "save.h"
#include "asm.h"
#include "gba/gba.h"
+#include "load_save.h"
#include "rom4.h"
#include "gba/flash_internal.h"
+#include "save_failed_screen.h"
extern struct SaveSection unk_2000000;
@@ -550,27 +552,27 @@ u8 sub_8125C3C(u8 a1)
sav12_xor_increment(10);
for (i = 0; i < 2; i++)
sub_81253C8(28 + i, gHallOfFameSaveSectionLocations[i].data, gHallOfFameSaveSectionLocations[i].size);
- save_serialize_game();
+ SaveSerializedGame();
save_write_to_flash(0xFFFF, gSaveSectionLocations);
break;
case 0:
default:
- save_serialize_game();
+ SaveSerializedGame();
save_write_to_flash(0xFFFF, gSaveSectionLocations);
break;
case 1:
- save_serialize_game();
+ SaveSerializedGame();
for (i = 0; i < 5; i++)
save_write_to_flash(i, gSaveSectionLocations);
break;
case 2:
- save_serialize_game();
+ SaveSerializedGame();
save_write_to_flash(0, gSaveSectionLocations);
break;
case 4:
for (i = 28; i < 32; i++)
EraseFlashSector(i);
- save_serialize_game();
+ SaveSerializedGame();
save_write_to_flash(0xFFFF, gSaveSectionLocations);
break;
}
@@ -584,7 +586,7 @@ u8 sub_8125D44(u8 a1)
sub_8125C3C(a1);
if (!gUnknown_03005EA8)
return 1;
- fullscreen_save_activate(a1);
+ DoSaveFailedScreen(a1);
return 0xFF;
}
@@ -592,7 +594,7 @@ u8 sub_8125D80(void)
{
if (gUnknown_3004820 != 1)
return 1;
- save_serialize_game();
+ SaveSerializedGame();
sub_812546C(gSaveSectionLocations);
return 0;
}
@@ -601,7 +603,7 @@ bool8 sub_8125DA8(void)
{
u8 v0 = sub_812550C(14, gSaveSectionLocations);
if (gUnknown_03005EA8)
- fullscreen_save_activate(0);
+ DoSaveFailedScreen(0);
if (v0 == 0xFF)
return 1;
else
@@ -612,7 +614,7 @@ u8 sub_8125DDC(void)
{
sub_812556C(14, gSaveSectionLocations);
if (gUnknown_03005EA8)
- fullscreen_save_activate(0);
+ DoSaveFailedScreen(0);
return 0;
}
@@ -620,7 +622,7 @@ u8 sub_8125E04(void)
{
sub_8125758(14, gSaveSectionLocations);
if (gUnknown_03005EA8)
- fullscreen_save_activate(0);
+ DoSaveFailedScreen(0);
return 0;
}
@@ -629,7 +631,7 @@ u8 sub_8125E2C(void)
if (gUnknown_3004820 != 1)
return 1;
- save_serialize_game();
+ SaveSerializedGame();
sub_81254C8(gSaveSectionLocations);
sub_812556C(gUnknown_03005EB4 + 1, gSaveSectionLocations);
return 0;
@@ -650,7 +652,7 @@ u8 sub_8125E6C(void)
retVal = 1;
}
if (gUnknown_03005EA8)
- fullscreen_save_activate(1);
+ DoSaveFailedScreen(1);
return retVal;
}
@@ -669,7 +671,7 @@ u8 sub_8125EC8(u8 a1)
case 0:
default:
result = sub_812587C(0xFFFF, gSaveSectionLocations);
- save_deserialize_game();
+ LoadSerializedGame();
gSaveFileStatus = result;
gUnknown_03005EBC = 0;
break;
diff --git a/src/save_failed_screen.c b/src/save_failed_screen.c
new file mode 100644
index 000000000..41e61eadb
--- /dev/null
+++ b/src/save_failed_screen.c
@@ -0,0 +1,301 @@
+#include "global.h"
+#include "main.h"
+#include "sprite.h"
+#include "palette.h"
+#include "task.h"
+#include "text.h"
+#include "menu.h"
+#include "save.h"
+#include "m4a.h"
+#include "gba/flash_internal.h"
+#include "asm.h"
+
+// In English 1.0, the text window is too small, causing text to overflow.
+
+#ifdef BUGFIX_SAVEFAILEDSCREEN1
+#define MSG_WIN_TOP 10
+#else
+#define MSG_WIN_TOP 12
+#endif
+
+#define CLOCK_WIN_TOP (MSG_WIN_TOP - 4)
+
+struct SaveFailedStruct
+{
+ u16 unk0;
+ u16 unk2;
+};
+
+extern u8 unk_2000000[];
+
+extern u16 gUnknown_0203933C;
+extern struct SaveFailedStruct gUnknown_0203933E;
+extern u32 gUnknown_03005EA8;
+extern u32 gUnknown_03005EBC;
+
+extern struct OamData gUnknown_08411940;
+extern u8 gUnknown_08411948[][3];
+
+extern u8 gBirchHelpGfx[];
+
+extern u8 gSystemText_SaveFailedBackupCheck[];
+extern u8 gSystemText_CheckCompleteSaveAttempt[];
+extern u8 gSystemText_BackupDamagedGameContinue[];
+extern u8 gSystemText_SaveCompletedPressA[];
+extern u8 gSystemText_SaveCompletedGameEnd[];
+extern u8 gSystemText_GameplayEnded[];
+
+extern u8 gBirchGrassTilemap[];
+extern u8 gBirchBagTilemap[];
+
+extern const u8 gSaveFailedClockGfx[];
+extern const u8 gSaveFailedClockPal[];
+extern u8 gBirchBagGrassPal[];
+
+static void VBlankCB(void);
+static void CB2_SaveFailedScreen(void);
+static void CB2_WipeSave(void);
+static void CB2_GameplayCannotBeContinued(void);
+static void CB2_FadeAndReturnToTitleScreen(void);
+static void CB2_ReturnToTitleScreen(void);
+static void VBlankCB_UpdateClockGraphics(void);
+static bool8 VerifySectorWipe(u16 sector);
+static bool8 WipeSector(u16 sector);
+static bool8 WipeSectors(u32 sectorBits);
+
+void DoSaveFailedScreen(u8 var)
+{
+ SetMainCallback2(CB2_SaveFailedScreen);
+ gUnknown_0203933C = var;
+ gUnknown_0203933E.unk0 = 0;
+}
+
+static void VBlankCB(void)
+{
+ LoadOam();
+ ProcessSpriteCopyRequests();
+ TransferPlttBuffer();
+}
+
+static void CB2_SaveFailedScreen(void)
+{
+ u16 ime;
+
+ switch(gMain.state)
+ {
+ case 0:
+ default:
+ SetVBlankCallback(0);
+ REG_DISPCNT = 0;
+ REG_BG3CNT = 0;
+ REG_BG2CNT = 0;
+ REG_BG1CNT = 0;
+ REG_BG0CNT = 0;
+ REG_BG3HOFS = 0;
+ REG_BG3VOFS = 0;
+ REG_BG2HOFS = 0;
+ REG_BG2VOFS = 0;
+ REG_BG1HOFS = 0;
+ REG_BG1VOFS = 0;
+ REG_BG0HOFS = 0;
+ REG_BG0VOFS = 0;
+ DmaFill16(3, 0, VRAM, VRAM_SIZE);
+ DmaFill32(3, 0, OAM, OAM_SIZE);
+ DmaFill16(3, 0, PLTT, PLTT_SIZE);
+ LZ77UnCompVram(&gBirchHelpGfx, (void *)VRAM);
+ LZ77UnCompVram(&gBirchBagTilemap, (void *)(VRAM + 0x3000));
+ LZ77UnCompVram(&gBirchGrassTilemap, (void *)(VRAM + 0x3800));
+ LZ77UnCompVram(&gSaveFailedClockGfx, (void *)(VRAM + 0x10020));
+ ResetSpriteData();
+ ResetTasks();
+ ResetPaletteFade();
+ LoadPalette(&gBirchBagGrassPal, 0, 0x40);
+ LoadPalette(&gSaveFailedClockPal, 0x100, 0x20);
+ SetUpWindowConfig(&gWindowConfig_81E6C3C);
+ InitMenuWindow(&gWindowConfig_81E6CE4);
+ MenuDrawTextWindow(13, CLOCK_WIN_TOP, 16, CLOCK_WIN_TOP + 3); // clock window
+ MenuDrawTextWindow(1, MSG_WIN_TOP, 28, 19); // message window
+ MenuPrint(gSystemText_SaveFailedBackupCheck, 2, MSG_WIN_TOP + 1);
+ BeginNormalPaletteFade(0xFFFFFFFF, 0, 16, 0, 0);
+ ime = REG_IME;
+ REG_IME = 0;
+ REG_IE |= INTR_FLAG_VBLANK;
+ REG_IME = ime;
+ REG_DISPSTAT |= DISPSTAT_VBLANK_INTR;
+ SetVBlankCallback(VBlankCB);
+ REG_BG3CNT = 0x703;
+ REG_BG2CNT = 0x602;
+ REG_BG0CNT = 0x1f08;
+ REG_DISPCNT = DISPCNT_OBJ_ON | DISPCNT_BG3_ON | DISPCNT_BG2_ON | DISPCNT_BG0_ON | DISPCNT_OBJ_1D_MAP | DISPCNT_MODE_0;
+ gMain.state++;
+ break;
+ case 1:
+ if (!UpdatePaletteFade())
+ {
+ SetMainCallback2(CB2_WipeSave);
+ SetVBlankCallback(VBlankCB_UpdateClockGraphics);
+ }
+ break;
+ }
+}
+
+static void CB2_WipeSave(void)
+{
+ u8 wipeTries = 0;
+
+ gUnknown_0203933E.unk0 = 1;
+
+ while (gUnknown_03005EA8 && wipeTries < 3)
+ {
+ if (WipeSectors(gUnknown_03005EA8))
+ {
+ MenuDrawTextWindow(1, MSG_WIN_TOP, 28, 19);
+ MenuPrint(gSystemText_BackupDamagedGameContinue, 2, MSG_WIN_TOP + 1);
+ SetMainCallback2(CB2_GameplayCannotBeContinued);
+ return;
+ }
+
+ MenuDrawTextWindow(1, MSG_WIN_TOP, 28, 19);
+ MenuPrint(gSystemText_CheckCompleteSaveAttempt, 2, MSG_WIN_TOP + 1);
+ sub_8125C3C(gUnknown_0203933C);
+
+ if (gUnknown_03005EA8)
+ {
+#ifdef BUGFIX_SAVEFAILEDSCREEN2
+ MenuDrawTextWindow(1, MSG_WIN_TOP, 28, 19);
+#endif
+ MenuPrint(gSystemText_SaveFailedBackupCheck, 2, MSG_WIN_TOP + 1);
+ }
+
+ wipeTries++;
+ }
+
+ if (wipeTries == 3)
+ {
+ MenuDrawTextWindow(1, MSG_WIN_TOP, 28, 19);
+ MenuPrint(gSystemText_BackupDamagedGameContinue, 2, MSG_WIN_TOP + 1);
+ SetMainCallback2(CB2_FadeAndReturnToTitleScreen); // called again below
+ }
+ else
+ {
+ MenuDrawTextWindow(1, MSG_WIN_TOP, 28, 19);
+
+ if (!gUnknown_03005EBC) // cant continue game.
+ MenuPrint(gSystemText_SaveCompletedGameEnd, 2, MSG_WIN_TOP + 1);
+ else // can continue game.
+ MenuPrint(gSystemText_SaveCompletedPressA, 2, MSG_WIN_TOP + 1);
+ }
+
+ SetMainCallback2(CB2_FadeAndReturnToTitleScreen);
+}
+
+static void CB2_GameplayCannotBeContinued(void)
+{
+ gUnknown_0203933E.unk0 = 0;
+
+ if (gMain.newKeys & A_BUTTON)
+ {
+ MenuDrawTextWindow(1, MSG_WIN_TOP, 28, 19);
+ MenuPrint(gSystemText_GameplayEnded, 2, MSG_WIN_TOP + 1);
+ SetVBlankCallback(VBlankCB);
+ SetMainCallback2(CB2_FadeAndReturnToTitleScreen);
+ }
+}
+
+static void CB2_FadeAndReturnToTitleScreen(void)
+{
+ u8 zero;
+
+ gUnknown_0203933E.unk0 = zero = 0;
+
+ if (gMain.newKeys & A_BUTTON)
+ {
+ BeginNormalPaletteFade(0xFFFFFFFF, 0, zero, 16, 0);
+ SetVBlankCallback(VBlankCB);
+ SetMainCallback2(CB2_ReturnToTitleScreen);
+ }
+}
+
+static void CB2_ReturnToTitleScreen(void)
+{
+ if (!UpdatePaletteFade())
+ {
+ if (!gUnknown_03005EBC)
+ {
+ DoSoftReset();
+ }
+ else
+ {
+ SetMainCallback2((MainCallback)gUnknown_03005EBC);
+ gUnknown_03005EBC = 0;
+ }
+ }
+}
+
+static void VBlankCB_UpdateClockGraphics(void)
+{
+ unsigned int n = (gMain.vblankCounter2 >> 3) & 7;
+
+ gMain.oamBuffer[0] = gUnknown_08411940;
+ gMain.oamBuffer[0].x = 112;
+ gMain.oamBuffer[0].y = (CLOCK_WIN_TOP + 1) * 8;
+
+ if (gUnknown_0203933E.unk0)
+ {
+ gMain.oamBuffer[0].tileNum = gUnknown_08411948[n][0];
+ gMain.oamBuffer[0].matrixNum = (gUnknown_08411948[n][2] << 4) | (gUnknown_08411948[n][1] << 3);
+ }
+ else
+ {
+ gMain.oamBuffer[0].tileNum = 1;
+ }
+
+ CpuFastCopy(gMain.oamBuffer, (void *)OAM, 4);
+
+ if (gUnknown_0203933E.unk2)
+ gUnknown_0203933E.unk2--;
+}
+
+static bool8 VerifySectorWipe(u16 sector)
+{
+ u32 *ptr = (u32 *)unk_2000000;
+ u16 i;
+
+ ReadFlash(sector, 0, (u8 *)ptr, 4096);
+
+ for (i = 0; i < 0x400; i++, ptr++)
+ if (*ptr)
+ return TRUE;
+
+ return FALSE;
+}
+
+static bool8 WipeSector(u16 sector)
+{
+ u16 i, j;
+ bool8 failed = TRUE;
+
+ for (i = 0; failed && i < 130; i++)
+ {
+ for (j = 0; j < 0x1000; j++)
+ ProgramFlashByte(sector, j, 0);
+
+ failed = VerifySectorWipe(sector);
+ }
+
+ return failed;
+}
+
+static bool8 WipeSectors(u32 sectorBits)
+{
+ u16 i;
+
+ for (i = 0; i < 0x20; i++)
+ if ((sectorBits & (1 << i)) && !WipeSector(i))
+ sectorBits &= ~(1 << i);
+
+ if (sectorBits == 0)
+ return FALSE;
+ else
+ return TRUE;
+}
diff --git a/src/scrcmd.c b/src/scrcmd.c
index 8051b0cb0..a8567a2bb 100644
--- a/src/scrcmd.c
+++ b/src/scrcmd.c
@@ -12,6 +12,7 @@
#include "asm_fieldmap.h"
#include "main.h"
#include "menu.h"
+#include "money.h"
#include "decoration.h"
#include "field_message_box.h"
#include "sound.h"
@@ -1697,7 +1698,7 @@ bool8 ScrCmd_setanimation(struct ScriptContext *ctx)
return FALSE;
}
-bool8 sub_8067B48()
+static bool8 sub_8067B48()
{
if (!FieldEffectActiveListContains(gUnknown_0202E8BC))
return TRUE;
@@ -1775,7 +1776,7 @@ bool8 ScrCmd_setdoorclosed(struct ScriptContext *ctx)
return FALSE;
}
-bool8 IsDoorAnimationStopped()
+static bool8 IsDoorAnimationStopped()
{
if (!FieldIsDoorAnimationRunning())
return TRUE;
diff --git a/src/script_menu.c b/src/script_menu.c
new file mode 100644
index 000000000..1010435cc
--- /dev/null
+++ b/src/script_menu.c
@@ -0,0 +1,431 @@
+#include "global.h"
+#include "task.h"
+#include "menu.h"
+#include "palette.h"
+#include "script.h"
+#include "sound.h"
+#include "flag.h"
+#include "sprite.h"
+
+struct MultichoiceListStruct
+{
+ struct MenuAction *list;
+ u8 count;
+};
+
+extern const struct MultichoiceListStruct gMultichoiceLists[];
+
+extern u16 gScriptResult;
+
+extern void FreeResourcesAndDestroySprite(struct Sprite *sprite);
+extern u8 CreateMonSprite_PicBox(u16, s16, s16, u8);
+extern u8 sub_80B59AC(void);
+
+extern u8 gPCText_PlayersPC[];
+extern u8 gPCText_SomeonesPC[];
+extern u8 gPCText_HallOfFame[];
+extern u8 gPCText_LogOff[];
+extern u8 gPCText_LanettesPC[];
+extern u8 gPCText_WhichPCShouldBeAccessed[];
+
+void DrawMultichoiceMenu(u8, u8, u8, struct MenuAction *list, u8, u8);
+void sub_80B53B4(u8, u8, u8, struct MenuAction *list, u8);
+void sub_80B52B4(u8);
+void sub_80B5230(u8, u8, u8, u8, u8, u8);
+void task_yes_no_maybe(u8);
+void sub_80B5684(u8);
+void CreatePCMenu(void);
+
+bool8 sub_80B5054(u8 left, u8 top, u8 var3, u8 var4)
+{
+ if(FuncIsActiveTask(sub_80B52B4) == 1)
+ return FALSE;
+ else
+ {
+ gScriptResult = 0xFF;
+ DrawMultichoiceMenu(left, top, gMultichoiceLists[var3].count, gMultichoiceLists[var3].list, var4, 0);
+ return TRUE;
+ }
+}
+
+bool8 sub_80B50B0(u8 left, u8 top, u8 var3, u8 var4, u8 var5)
+{
+ if(FuncIsActiveTask(sub_80B52B4) == 1)
+ return FALSE;
+ else
+ {
+ gScriptResult = 0xFF;
+ DrawMultichoiceMenu(left, top, gMultichoiceLists[var3].count, gMultichoiceLists[var3].list, var4, var5);
+ return TRUE;
+ }
+}
+
+u16 GetStringWidthInTilesForScriptMenu(u8 *str)
+{
+ // each tile on screen is 8x8, so it needs the number of tiles and not pixels, hence the division by 8.
+ return (GetStringWidthGivenWindowConfig((struct WindowConfig *)&gWindowConfig_81E6CE4, str) + 7) / 8;
+}
+
+void DrawMultichoiceMenu(u8 left, u8 top, u8 count, struct MenuAction *list, u8 var4, u8 cursorPos)
+{
+ u16 width = GetStringWidthInTilesForScriptMenu(list[0].text);
+ u16 newWidth;
+ u8 i;
+ u8 right;
+ u8 bottom;
+
+ for(i = 1; i < count; i++)
+ {
+ newWidth = GetStringWidthInTilesForScriptMenu(list[i].text);
+ if(width < newWidth)
+ width = newWidth;
+ }
+
+ right = width;
+ right = (right + left) + 1;
+
+ if(right > 29)
+ {
+ left = left + (29 - right);
+ right = 29;
+ }
+
+ bottom = top + (2 * count + 1);
+
+ MenuDrawTextWindow(left, top, right, bottom);
+ PrintMenuItems(left + 1, top + 1, count, list);
+ InitMenu(0, left + 1, top + 1, count, cursorPos, right - left - 1);
+ sub_80B5230(left, top, right, bottom, var4, count);
+}
+
+void sub_80B5230(u8 left, u8 top, u8 right, u8 bottom, u8 unkVar, u8 count)
+{
+ u8 taskId = CreateTask(sub_80B52B4, 80);
+
+ gTasks[taskId].data[0] = left;
+ gTasks[taskId].data[1] = top;
+ gTasks[taskId].data[2] = right;
+ gTasks[taskId].data[3] = bottom;
+ gTasks[taskId].data[4] = unkVar;
+
+ if(count > 3)
+ gTasks[taskId].data[5] = TRUE;
+ else
+ gTasks[taskId].data[5] = FALSE;
+}
+
+void sub_80B52B4(u8 taskId)
+{
+ s8 var;
+
+ if(!gPaletteFade.active)
+ {
+ if(!gTasks[taskId].data[5])
+ var = ProcessMenuInputNoWrap();
+ else
+ var = ProcessMenuInput();
+
+ if(var != -2)
+ {
+ if(var == -1)
+ {
+ if(!gTasks[taskId].data[4])
+ {
+ PlaySE(5);
+ gScriptResult = 127;
+ }
+ else
+ {
+ return;
+ }
+ }
+ else
+ {
+ gScriptResult = var;
+ }
+ sub_8072DEC();
+ MenuZeroFillWindowRect(gTasks[taskId].data[0], gTasks[taskId].data[1], gTasks[taskId].data[2], gTasks[taskId].data[3]);
+ DestroyTask(taskId);
+ EnableBothScriptContexts();
+ }
+ }
+}
+
+bool8 Multichoice(u8 var1, u8 var2, u8 var3, u8 var4)
+{
+ if(FuncIsActiveTask(sub_80B52B4) == 1)
+ return FALSE;
+ else
+ {
+ gScriptResult = 0xFF;
+ sub_80B53B4(var1, var2, gMultichoiceLists[var3].count, gMultichoiceLists[var3].list, var4);
+ return TRUE;
+ }
+}
+
+void sub_80B53B4(u8 left, u8 top, u8 count, struct MenuAction *list, u8 var4)
+{
+ u16 width = GetStringWidthInTilesForScriptMenu(list[0].text);
+ u16 newWidth;
+ u8 i;
+ u8 right;
+ u8 bottom;
+
+ for(i = 1; i < count; i++)
+ {
+ newWidth = GetStringWidthInTilesForScriptMenu(list[i].text);
+ if(width < newWidth)
+ width = newWidth;
+ }
+
+ right = width;
+ right = (right + left) + 2;
+ bottom = top + (2 * count + 1);
+
+ PrintMenuItems(left, top, count, list);
+ InitMenu(0, left, top, count, 0, right - left - 1);
+ sub_80B5230(left, top, right, bottom, var4, count);
+}
+
+bool8 yes_no_box(u8 var1, u8 var2)
+{
+ u8 taskId;
+
+ if(FuncIsActiveTask(task_yes_no_maybe) == 1)
+ return FALSE;
+ else
+ {
+ gScriptResult = 0xFF;
+ DisplayYesNoMenu(var1, var2, 1);
+ taskId = CreateTask(task_yes_no_maybe, 0x50);
+ gTasks[taskId].data[0] = var1;
+ gTasks[taskId].data[1] = var2;
+ return TRUE;
+ }
+}
+
+// unused
+bool8 IsScriptActive(void)
+{
+ if(gScriptResult == 0xFF)
+ return FALSE;
+ else
+ return TRUE;
+}
+
+void task_yes_no_maybe(u8 taskId)
+{
+ u8 left, top;
+
+ if (gTasks[taskId].data[2] < 5)
+ {
+ gTasks[taskId].data[2]++;
+ return;
+ }
+
+ switch (ProcessMenuInputNoWrap())
+ {
+ case -2:
+ return;
+ case -1:
+ case 1:
+ PlaySE(5);
+ gScriptResult = 0;
+ break;
+ case 0:
+ gScriptResult = 1;
+ break;
+ }
+
+ left = gTasks[taskId].data[0];
+ top = gTasks[taskId].data[1];
+
+ MenuZeroFillWindowRect(left, top, left + 6, top + 5);
+ DestroyTask(taskId);
+ EnableBothScriptContexts();
+}
+
+bool8 sub_80B5578(u8 left, u8 top, u8 multichoiceId, u8 a4, u8 columnCount)
+{
+ u8 bottom = 0;
+
+ if (FuncIsActiveTask(sub_80B5684) == TRUE)
+ {
+ return FALSE;
+ }
+ else
+ {
+ u8 taskId;
+ u8 width;
+
+ gScriptResult = 0xFF;
+
+ sub_807274C(left, top, gMultichoiceLists[multichoiceId].count, 0, gMultichoiceLists[multichoiceId].list, columnCount, 0);
+
+ taskId = CreateTask(sub_80B5684, 80);
+
+ if (!((gMultichoiceLists[multichoiceId].count >> 1) < columnCount || (gMultichoiceLists[multichoiceId].count & 1))
+ || columnCount == 1 || gMultichoiceLists[multichoiceId].count == columnCount)
+ {
+ bottom = (2 * (gMultichoiceLists[multichoiceId].count / columnCount)) + 1 + top;
+ }
+ else
+ {
+ bottom = (2 * (gMultichoiceLists[multichoiceId].count / columnCount)) + 3 + top;
+ }
+
+ width = sub_807288C(columnCount);
+ gTasks[taskId].data[0] = left;
+ gTasks[taskId].data[1] = top;
+ gTasks[taskId].data[2] = width + left + 2;
+ gTasks[taskId].data[3] = bottom;
+ gTasks[taskId].data[4] = a4;
+ return TRUE;
+ }
+}
+
+void sub_80B5684(u8 taskId)
+{
+ s8 var = sub_80727CC();
+
+ if (var != -2)
+ {
+ if (var == -1)
+ {
+ if (!gTasks[taskId].data[4])
+ {
+ PlaySE(5);
+ gScriptResult = 127;
+ }
+ else
+ {
+ return;
+ }
+ }
+ else
+ {
+ gScriptResult = var;
+ }
+ sub_8072DEC();
+ MenuZeroFillWindowRect(gTasks[taskId].data[0], gTasks[taskId].data[1], gTasks[taskId].data[2], gTasks[taskId].data[3]);
+ DestroyTask(taskId);
+ EnableBothScriptContexts();
+ }
+}
+
+bool8 TryCreatePCMenu(void)
+{
+ if(FuncIsActiveTask(sub_80B52B4) == 1)
+ return FALSE;
+ else
+ {
+ gScriptResult = 0xFF;
+ CreatePCMenu();
+ return TRUE;
+ }
+}
+
+void CreatePCMenu(void)
+{
+ u16 playersPCWidth = GetStringWidthInTilesForScriptMenu(gPCText_PlayersPC);
+ u8 width;
+ u8 numChoices;
+
+ if(playersPCWidth > GetStringWidthInTilesForScriptMenu(gPCText_SomeonesPC))
+ width = playersPCWidth;
+ else
+ width = 8;
+
+ if(FlagGet(0x804)) // player has cleared game?
+ {
+ numChoices = 4;
+ MenuDrawTextWindow(0, 0, width + 2, 9);
+ MenuPrint(gPCText_HallOfFame, 1, 5);
+ MenuPrint(gPCText_LogOff, 1, 7);
+ }
+ else
+ {
+ numChoices = 3;
+ MenuDrawTextWindow(0, 0, width + 2, 7);
+ MenuPrint(gPCText_LogOff, 1, 5);
+ }
+
+ if(FlagGet(0x84B)) // player met lanette?
+ MenuPrint(gPCText_LanettesPC, 1, 1);
+ else
+ MenuPrint(gPCText_SomeonesPC, 1, 1);
+
+ MenuPrint(gPCText_PlayersPC, 1, 3);
+ InitMenu(0, 1, 1, numChoices, 0, width + 1);
+ sub_80B5230(0, 0, width + 2, 2 * numChoices + 1, 0, numChoices);
+}
+
+void sub_80B5838(void)
+{
+ MenuDisplayMessageBox();
+ MenuPrint(gPCText_WhichPCShouldBeAccessed, 2, 15);
+}
+
+void task_picbox(u8 taskId)
+{
+ struct Task *task = &gTasks[taskId];
+
+ switch(task->data[0])
+ {
+ case 0:
+ task->data[0]++;
+ break;
+ case 1:
+ break;
+ case 2:
+ FreeResourcesAndDestroySprite(&gSprites[task->data[2]]);
+ task->data[0]++;
+ break;
+ case 3:
+ MenuZeroFillWindowRect(task->data[3], task->data[4], task->data[3] + 9, task->data[4] + 10);
+ DestroyTask(taskId);
+ break;
+ }
+}
+
+bool8 sub_80B58C4(u16 var1, u8 var2, u8 var3)
+{
+ u8 taskId;
+ u8 var;
+
+ if(FindTaskIdByFunc(task_picbox) != 0xFF)
+ return FALSE;
+ else
+ {
+ MenuDrawTextWindow(var2, var3, var2 + 9, var3 + 10);
+ taskId = CreateTask(task_picbox, 0x50);
+ gTasks[taskId].data[0] = 0;
+ gTasks[taskId].data[1] = var1;
+ var = CreateMonSprite_PicBox(var1, var2 * 8 + 40, var3 * 8 + 40, 0);
+ gTasks[taskId].data[2] = var;
+ gTasks[taskId].data[3] = var2;
+ gTasks[taskId].data[4] = var3;
+ gSprites[var].callback = SpriteCallbackDummy;
+ gSprites[var].oam.priority = 0;
+ return TRUE;
+ }
+}
+
+void *picbox_close(void)
+{
+ u8 taskId = FindTaskIdByFunc(task_picbox);
+
+ if(taskId == 0xFF)
+ return NULL;
+
+ gTasks[taskId].data[0]++;
+ return (void *)sub_80B59AC;
+}
+
+bool8 sub_80B59AC(void)
+{
+ if(FindTaskIdByFunc(task_picbox) == 0xFF)
+ return TRUE;
+ else
+ return FALSE;
+}
diff --git a/src/sound.c b/src/sound.c
index 56719aa08..69accd1c2 100644
--- a/src/sound.c
+++ b/src/sound.c
@@ -12,6 +12,9 @@ struct Fanfare
u16 duration;
};
+// Hack: different prototype than definition
+u32 SpeciesToCryId(u32);
+
extern u16 gUnknown_020239F8;
extern struct MusicPlayerInfo *gMPlay_PokemonCry;
extern u8 gPokemonCryBGMDuckingCounter;
diff --git a/src/sprite.c b/src/sprite.c
index 78a8608ad..df101b61f 100644
--- a/src/sprite.c
+++ b/src/sprite.c
@@ -10,12 +10,8 @@
#define SET_SPRITE_TILE_RANGE(index, start, count) \
{ \
- u16 *rangeStarts; \
- u16 *rangeCounts; \
- rangeStarts = sSpriteTileRanges; \
- rangeStarts[index * 2] = start; \
- rangeCounts = sSpriteTileRanges + 1; \
- rangeCounts[index * 2] = count; \
+ sSpriteTileRanges[index * 2] = start; \
+ (sSpriteTileRanges + 1)[index * 2] = count; \
}
#define ALLOC_SPRITE_TILE(n) \
@@ -61,10 +57,8 @@ static void ClearSpriteCopyRequests(void);
static void ResetOamMatrices(void);
static void ResetSprite(struct Sprite *sprite);
static s16 AllocSpriteTiles(u16 tileCount);
-static u8 SpriteTileAllocBitmapOp(u16 bit, u8 op);
+u8 SpriteTileAllocBitmapOp(u16 bit, u8 op);
static void RequestSpriteFrameImageCopy(u16 index, u16 tileNum, struct SpriteFrameImage *images);
-static void CopyFromSprites(u8 *dest);
-static void CopyToSprites(u8 *src);
static void ResetAllSprites(void);
static void BeginAnim(struct Sprite *sprite);
static void ContinueAnim(struct Sprite *sprite);
@@ -786,7 +780,7 @@ static s16 AllocSpriteTiles(u16 tileCount)
return start;
}
-static u8 SpriteTileAllocBitmapOp(u16 bit, u8 op)
+u8 SpriteTileAllocBitmapOp(u16 bit, u8 op)
{
u8 index = bit / 8;
u8 shift = bit % 8;
@@ -855,7 +849,7 @@ void RequestSpriteCopy(u8 *src, u8 *dest, u16 size)
}
}
-static void CopyFromSprites(u8 *dest)
+void CopyFromSprites(u8 *dest)
{
u32 i;
u8 *src = (u8 *)gSprites;
@@ -867,7 +861,7 @@ static void CopyFromSprites(u8 *dest)
}
}
-static void CopyToSprites(u8 *src)
+void CopyToSprites(u8 *src)
{
u32 i;
u8 *dest = (u8 *)gSprites;
diff --git a/src/start_menu.c b/src/start_menu.c
index 06eb28909..850f610e3 100644
--- a/src/start_menu.c
+++ b/src/start_menu.c
@@ -1,10 +1,19 @@
#include "global.h"
#include "start_menu.h"
#include "asm.h"
+#include "field_player_avatar.h"
+#include "flag.h"
+#include "load_save.h"
#include "main.h"
+#include "map_obj_lock.h"
#include "menu.h"
+#include "option_menu.h"
#include "palette.h"
#include "pokedex.h"
+#include "rom4.h"
+#include "safari_zone.h"
+#include "save.h"
+#include "save_menu_util.h"
#include "script.h"
#include "songs.h"
#include "sound.h"
@@ -12,15 +21,7 @@
#include "string_util.h"
#include "task.h"
#include "trainer_card.h"
-#include "flag.h"
-#include "rom4.h"
-#include "safari_zone.h"
-#include "field_player_avatar.h"
#include "weather.h"
-#include "save.h"
-#include "option_menu.h"
-#include "map_obj_lock.h"
-#include "save_menu_util.h"
//Menu actions
enum {
@@ -76,7 +77,6 @@ static void BuildStartMenuActions_Link(void);
static void DisplaySafariBallsWindow(void);
static bool32 PrintStartMenuItemsMultistep(s16 *a, u32 b);
static bool32 InitStartMenuMultistep(s16 *a, s16 *b);
-static void sub_8071230(void);
static void Task_StartMenu(u8 taskId);
static u8 StartMenu_InputProcessCallback(void);
static u8 SaveCallback1(void);
@@ -811,14 +811,14 @@ static void Task_8071B64(u8 taskId)
(*step)++;
break;
case 1:
- sub_8047A1C();
+ SetSecretBase2Field_9_AndHideBG();
sub_8125E2C();
(*step)++;
break;
case 2:
if(!sub_8125E6C())
break;
- sub_8047A34();
+ ClearSecretBase2Field_9_2();
(*step)++;
break;
case 3:
@@ -832,18 +832,3 @@ static void Task_8071B64(u8 taskId)
}
}
}
-
-void sub_8071C20(void)
-{
- PlaySE(SE_SELECT);
- MenuZeroFillScreen();
- sub_8064E2C();
- ScriptContext2_Disable();
- sub_8072DEC();
-}
-
-void AppendToList(u8 *list, u8 *pindex, u32 value)
-{
- list[*pindex] = value;
- (*pindex)++;
-}
diff --git a/src/starter_choose.c b/src/starter_choose.c
index 341f73e4c..2750705b8 100644
--- a/src/starter_choose.c
+++ b/src/starter_choose.c
@@ -20,12 +20,12 @@ struct MonCoords
extern void * const gUnknown_081FAF4C[];
extern const u8 gStarterChoose_PokeballCoords[][2];
-extern u8 gUnknown_083F66F0[];
+extern u8 gBirchHelpGfx[];
extern u8 gBirchBagTilemap[];
extern u8 gBirchGrassTilemap[];
extern struct SpriteSheet gUnknown_083F7794;
extern struct SpriteSheet gUnknown_083F77A4;
-extern u8 gUnknown_083F62EC[];
+extern u8 gBirchBagGrassPal[];
extern const u8 gStarterChoose_LabelCoords[][2];
extern u16 gStarterMons[];
extern union AffineAnimCmd *gUnknown_083F778C[];
@@ -108,7 +108,7 @@ void CB2_ChooseStarter(void)
DmaFill32(3, 0, OAM, OAM_SIZE);
DmaFill16(3, 0, PLTT, PLTT_SIZE);
- LZ77UnCompVram(&gUnknown_083F66F0, (void *)VRAM);
+ LZ77UnCompVram(&gBirchHelpGfx, (void *)VRAM);
LZ77UnCompVram(&gBirchBagTilemap, (void *)(VRAM + 0x3000));
LZ77UnCompVram(&gBirchGrassTilemap, (void *)(VRAM + 0x3800));
remove_some_task();
@@ -116,7 +116,7 @@ void CB2_ChooseStarter(void)
ResetSpriteData();
ResetPaletteFade();
FreeAllSpritePalettes();
- LoadPalette(gUnknown_083F62EC, 0, 0x40);
+ LoadPalette(gBirchBagGrassPal, 0, 0x40);
LoadCompressedObjectPic(&gUnknown_083F7794);
LoadCompressedObjectPic(&gUnknown_083F77A4);
LoadSpritePalettes(gUnknown_083F77B4);
diff --git a/src/text.c b/src/text.c
index c632a4fa6..265ef5493 100644
--- a/src/text.c
+++ b/src/text.c
@@ -8,12 +8,6 @@
enum
{
- CHARSET_JAPANESE = 1,
- CHARSET_LATIN
-};
-
-enum
-{
WIN_STATE_END,
WIN_STATE_BEGIN,
WIN_STATE_NORMAL,
@@ -361,7 +355,7 @@ static const WriteGlyphTilemapFunc sWriteGlyphTilemapFuncs[] =
WriteGlyphTilemap_Font6,
};
-static const struct Window sDefaultWindow = { .charset = CHARSET_LATIN };
+static const struct Window sDefaultWindow = { .language = GAME_LANGUAGE };
typedef u8 (*ExtCtrlCodeFunc)(struct Window *);
@@ -1918,7 +1912,7 @@ static void MultistepLoadFont_LoadGlyph(struct Window *win, u16 startOffset, u8
}
}
-static void EmptyFunc(void)
+void EmptyFunc(void)
{
}
@@ -1947,7 +1941,7 @@ void InitWindow(struct Window *win, const u8 *text, u16 tileDataStartOffset, u8
struct WindowConfig *winConfig = win->config;
win->textMode = winConfig->textMode;
win->fontNum = winConfig->fontNum;
- win->charset = CHARSET_LATIN;
+ win->language = GAME_LANGUAGE;
win->paletteNum = winConfig->paletteNum;
win->win_field_B = 0;
win->win_field_C = 0;
@@ -2045,7 +2039,7 @@ u8 sub_8002F44(struct Window *win)
static u8 sub_8002FA0(struct Window *win, const u8 *text)
{
u8 retVal;
- u8 savedCharset = win->charset;
+ u8 savedLanguage = win->language;
const u8 *savedText = win->text;
u16 savedTextIndex = win->textIndex;
win->text = text;
@@ -2055,7 +2049,7 @@ static u8 sub_8002FA0(struct Window *win, const u8 *text)
win->text = savedText;
win->textIndex = savedTextIndex;
win->state = WIN_STATE_NORMAL;
- win->charset = savedCharset;
+ win->language = savedLanguage;
return retVal;
}
@@ -2291,13 +2285,13 @@ static u8 ExtCtrlCode_Spacing(struct Window *win)
static u8 ExtCtrlCode_Japanese(struct Window *win)
{
- win->charset = CHARSET_JAPANESE;
+ win->language = LANGUAGE_JAPANESE;
return 2;
}
static u8 ExtCtrlCode_Latin(struct Window *win)
{
- win->charset = CHARSET_LATIN;
+ win->language = GAME_LANGUAGE;
return 2;
}
@@ -2596,7 +2590,7 @@ static void LoadFixedWidthGlyph(struct Window *win, u32 glyph, u8 *dest)
u8 *upperTile;
u8 *lowerTile;
- GetGlyphTilePointers(win->fontNum, win->charset, glyph, &upperTile, &lowerTile);
+ GetGlyphTilePointers(win->fontNum, win->language, glyph, &upperTile, &lowerTile);
switch (win->fontNum)
{
@@ -2627,17 +2621,17 @@ static void WriteGlyphTilemap(struct Window *win, u16 upperTileNum, u16 lowerTil
}
}
-static void GetGlyphTilePointers(u8 fontNum, u8 charset, u16 glyph, u8 **upperTilePtr, u8 **lowerTilePtr)
+static void GetGlyphTilePointers(u8 fontNum, u8 language, u16 glyph, u8 **upperTilePtr, u8 **lowerTilePtr)
{
u16 index;
const struct Font *font;
- if (charset == CHARSET_JAPANESE)
- charset = 0;
+ if (language == LANGUAGE_JAPANESE)
+ language = 0;
else
- charset = 7;
+ language = 7;
- font = &sFonts[charset + fontNum];
+ font = &sFonts[language + fontNum];
switch (font->type)
{
@@ -3137,7 +3131,7 @@ static void DrawDownArrow(struct Window *win)
{
u8 *upperTile;
u8 *lowerTile;
- GetGlyphTilePointers(win->fontNum, win->charset, 0, &upperTile, &lowerTile);
+ GetGlyphTilePointers(win->fontNum, win->language, 0, &upperTile, &lowerTile);
glyphTileInfo.width = 8 - glyphTileInfo.startPixel;
glyphTileInfo.src = upperTile;
glyphTileInfo.dest = (u32 *)(win->tileData + 32 * GetCursorTileNum(win, 1, 0));
@@ -3340,10 +3334,10 @@ static u8 GetGlyphWidth(struct Window *win, u32 glyph)
{
u8 width = 8;
-#if REVISION >= 1
- if (win->charset != CHARSET_JAPANESE)
+#ifdef BUGFIX_GLYPHWIDTH
+ if (win->language != LANGUAGE_JAPANESE)
#else
- if (win->charset == CHARSET_LATIN)
+ if (win->language == LANGUAGE_ENGLISH)
#endif
{
width = win->spacing;
@@ -3539,7 +3533,7 @@ u8 GetStringWidth(struct Window *win, const u8 *s)
{
u8 width = 0;
u8 savedFontNum = win->fontNum;
- u8 savedCharset = win->charset;
+ u8 savedCharset = win->language;
u8 savedSpacing = win->spacing;
s32 i = 0;
@@ -3552,9 +3546,9 @@ u8 GetStringWidth(struct Window *win, const u8 *s)
{
u8 temp;
i++;
- temp = win->charset;
+ temp = win->language;
width += GetStringWidth(win, GetExpandedPlaceholder(s[i]));
- win->charset = temp;
+ win->language = temp;
i++;
break;
}
@@ -3580,10 +3574,10 @@ u8 GetStringWidth(struct Window *win, const u8 *s)
win->spacing = s[i + 1];
break;
case 0x15:
- win->charset = 1;
+ win->language = LANGUAGE_JAPANESE;
break;
case 0x16:
- win->charset = 2;
+ win->language = GAME_LANGUAGE;
break;
}
@@ -3596,7 +3590,7 @@ u8 GetStringWidth(struct Window *win, const u8 *s)
}
win->spacing = savedSpacing;
- win->charset = savedCharset;
+ win->language = savedCharset;
win->fontNum = savedFontNum;
return width;
@@ -3659,10 +3653,9 @@ u8 GetStringWidthGivenWindowConfig(struct WindowConfig *winConfig, const u8 *s)
void ConvertInternationalString(u8 *s, u8 language)
{
- if (language == CHARSET_JAPANESE)
+ if (language == LANGUAGE_JAPANESE)
{
u8 i;
- u8 length;
StripExtCtrlCodes(s);
i = StringLength(s);
@@ -4254,7 +4247,7 @@ static s32 DrawGlyphTiles(struct Window *win, u32 glyph, u32 glyphWidth)
u8 *lowerTile;
s32 retVal = 0;
- GetGlyphTilePointers(win->fontNum, win->charset, glyph, &upperTile, &lowerTile);
+ GetGlyphTilePointers(win->fontNum, win->language, glyph, &upperTile, &lowerTile);
glyphTileInfo.textMode = win->textMode;
glyphTileInfo.startPixel = (win->left + win->cursorX) & 7;
glyphTileInfo.width = glyphWidth;
diff --git a/src/trainer_card.c b/src/trainer_card.c
index a04ad4359..453cec76d 100644
--- a/src/trainer_card.c
+++ b/src/trainer_card.c
@@ -6,6 +6,7 @@
#include "link.h"
#include "main.h"
#include "menu.h"
+#include "money.h"
#include "palette.h"
#include "pokedex.h"
#include "rom4.h"
@@ -81,7 +82,7 @@ static void sub_809323C(void);
static void sub_8093254(void);
static void sub_80932AC(Callback callBack);
static void sub_80932E4(u8 arg1, Callback callBack);
-static void sub_8093324(void);
+void sub_8093324(void);
static void nullsub_60(u8);
static u32 sav12_xor_get_clamped_above(u8 index, u32 maxVal);
static u8 sub_80934F4(struct TrainerCard *);
@@ -91,7 +92,7 @@ static void sub_8093598(void);
static void sub_80935EC(void);
static void sub_8093610(void);
static void sub_8093688(void);
-static void sub_80936D4(void);
+void sub_80936D4(void);
static void sub_80937A4(void);
static void sub_80937BC(void);
static void sub_80937D8(void);
@@ -106,13 +107,13 @@ static void sub_80939DC(u8 taskId);
static void sub_8093A28(void);
static u8 sub_8093A48(void);
static void sub_8093A68(u8 taskId);
-static void sub_8093D7C(void);
+void sub_8093D7C(void);
static void sub_8093DAC(void);
static void sub_8093DC8(void);
static void sub_8093DEC(void);
static void sub_8093E04(void);
static void sub_8093E28(void);
-static void sub_8093EA0(void);
+void sub_8093EA0(void);
static void sub_8093EF8(void);
static void sub_8093F14(void);
static void sub_8093F48(void);
@@ -142,12 +143,12 @@ static void TrainerCard_Back_PrintLinkPokeblocks_Label(void);
static void TrainerCard_Back_PrintLinkPokeblocks(void);
static void TrainerCard_Back_PrintPokemonTrades_Label(void);
static void TrainerCard_Back_PrintPokemonTrades(void);
-static void unref_sub_8094588(u16 left, u16 top);
+void unref_sub_8094588(u16 left, u16 top);
void sub_8093110(Callback arg1) {
sub_80932AC(arg1);
SetMainCallback2(sub_8093174);
- unk_2000000.language = 2;
+ unk_2000000.language = GAME_LANGUAGE;
}
void sub_8093130(u8 playerIndex, Callback arg2) {
@@ -253,7 +254,7 @@ static void sub_80932E4(u8 arg1, Callback callBack) {
StoreWordInTwoHalfwords(&task->data[TD_CALLBACK], (u32) callBack);
}
-static void sub_8093324(void) {
+void sub_8093324(void) {
u8 taskId = FindTaskIdByFunc(nullsub_60);
struct Task *task = &gTasks[taskId];
unk_2000000.var_1 = task->data[TD_0];
@@ -592,7 +593,7 @@ _080936D0: .4byte 0x02000000\n\
#endif
-static void sub_80936D4(void) {
+void sub_80936D4(void) {
unk_2000000.var_7 = FALSE;
unk_2000000.var_8 = FALSE;
unk_2000000.var_9 = FALSE;
@@ -1338,7 +1339,7 @@ bool8 sub_8093D50(void) {
}
__attribute__((naked))
-static void sub_8093D7C(void) {
+void sub_8093D7C(void) {
asm(".syntax unified\n\
ldr r1, _08093DA0 @ =gUnknown_03004DE0\n\
ldr r0, _08093DA4 @ =REG_VCOUNT\n\
@@ -1471,7 +1472,7 @@ _08093E9C: .4byte 0x80000200\n\
.syntax divided\n");
}
-static void sub_8093EA0(void) {
+void sub_8093EA0(void) {
LoadPalette(gUnknown_083B5EF8[unk_2000000.var_2], 0, 48 * 2);
LoadPalette(gBadgesPalette, 48, 16 * 2);
LoadPalette(gUnknown_083B5F4C, 64, 16 * 2);
@@ -2016,7 +2017,7 @@ static void TrainerCard_Back_PrintPokemonTrades(void) {
MenuPrint_RightAligned(buffer, 28, 9);
}
-static void unref_sub_8094588(u16 left, u16 top) {
+void unref_sub_8094588(u16 left, u16 top) {
u8 *text = gOtherText_Boy;
if (gSaveBlock2.playerGender == FEMALE) {
diff --git a/src/trainer_see.c b/src/trainer_see.c
index 969bc94c1..2b4ecbcc1 100644
--- a/src/trainer_see.c
+++ b/src/trainer_see.c
@@ -20,7 +20,7 @@ extern u32 gUnknown_0202FF84[];
bool8 CheckTrainers(void)
{
u8 i;
-
+
for(i = 0; i < 16; i++)
{
if ( gMapObjects[i].active )
@@ -60,7 +60,7 @@ bool8 TrainerCanApproachPlayer(struct MapObject *trainerObj)
s16 x, y;
u8 i;
u8 playerCoord;
-
+
PlayerGetDestCoords(&x, &y);
if ( trainerObj->trainerType == 1 ) // trainers that don't spin
{
@@ -119,6 +119,12 @@ bool8 IsTrainerInRangeEast(struct MapObject *trainerObj, s16 vision, s16 x, s16
return FALSE;
}
+#ifdef BUGFIX_TRAINERAPPROACH
+#define COLLISION_MASK ~1
+#else
+#define COLLISION_MASK 1
+#endif
+
bool8 CheckPathBetweenTrainerAndPlayer(struct MapObject2 *trainerObj, u8 playerCoord, u8 direction)
{
s16 x, y;
@@ -127,21 +133,18 @@ bool8 CheckPathBetweenTrainerAndPlayer(struct MapObject2 *trainerObj, u8 playerC
u8 i;
u8 var;
- if ( !playerCoord )
+ if (!playerCoord)
return FALSE;
x = trainerObj->coords2.x;
y = trainerObj->coords2.y;
- for(i = 0; i <= playerCoord - 1;)
+ for (i = 0; i <= playerCoord - 1; i++, MoveCoords(direction, &x, &y))
{
var = sub_8060024((struct MapObject *)trainerObj, x, y, direction);
- if (var != 0 && (var & 1) != 0 )
+ if (var && (var & COLLISION_MASK))
return FALSE;
-
- i++;
- MoveCoords(direction, &x, &y);
}
// preserve mapobj_unk_19 before clearing.
@@ -154,7 +157,7 @@ bool8 CheckPathBetweenTrainerAndPlayer(struct MapObject2 *trainerObj, u8 playerC
trainerObj->mapobj_unk_19 = unk19_temp;
trainerObj->mapobj_unk_19b = unk19b_temp;
- if ( var == 4 )
+ if (var == 4)
return playerCoord;
return FALSE;
@@ -173,7 +176,7 @@ void sub_80842FC(TaskFunc func)
{
TaskFunc func2 = RunTrainerSeeFuncList;
u8 taskId = FindTaskIdByFunc(func2);
-
+
SetTaskFuncWithFollowupFunc(taskId, RunTrainerSeeFuncList, func);
gTasks[taskId].data[0] = 1;
func2(taskId);
@@ -201,7 +204,7 @@ s8 sub_8084398(u8 taskId, struct Task *task, struct MapObject *trainerObj)
FieldObjectGetLocalIdAndMap(trainerObj, (u8 *)&gUnknown_0202FF84[0], (u8 *)&gUnknown_0202FF84[1], (u8 *)&gUnknown_0202FF84[2]);
FieldEffectStart(0);
-
+
direction = GetFaceDirectionAnimId(trainerObj->mapobj_unk_18);
FieldObjectSetSpecialAnim(trainerObj, direction);
@@ -267,17 +270,17 @@ s8 sub_8084478(u8 taskId, struct Task *task, struct MapObject *trainerObj)
s8 sub_8084534(u8 taskId, struct Task *task, struct MapObject *trainerObj) // technically only 1 parameter, but needs all 3 for TrainerSeeFuncList call.
{
struct MapObject *playerObj = &gMapObjects[gPlayerAvatar.mapObjectId];
-
+
if ( !FieldObjectIsSpecialAnimOrDirectionSequenceAnimActive(playerObj)
|| FieldObjectClearAnimIfSpecialAnimFinished(playerObj) )
SwitchTaskToFollowupFunc(taskId);
-
+
return 0;
}
s8 sub_8084578(u8 taskId, struct Task *task, struct MapObject *trainerObj)
{
- if(!FieldObjectIsSpecialAnimOrDirectionSequenceAnimActive(trainerObj)
+ if(!FieldObjectIsSpecialAnimOrDirectionSequenceAnimActive(trainerObj)
|| FieldObjectClearAnimIfSpecialAnimFinished(trainerObj))
{
FieldObjectSetSpecialAnim(trainerObj, 0x59);
@@ -290,13 +293,13 @@ s8 sub_80845AC(u8 taskId, struct Task *task, struct MapObject *trainerObj)
{
if ( FieldObjectClearAnimIfSpecialAnimFinished(trainerObj) )
task->data[0] = 3;
-
+
return 0;
}
s8 sub_80845C8(u8 taskId, struct Task *task, struct MapObject *trainerObj)
{
- if(!FieldObjectIsSpecialAnimOrDirectionSequenceAnimActive(trainerObj)
+ if(!FieldObjectIsSpecialAnimOrDirectionSequenceAnimActive(trainerObj)
|| FieldObjectClearAnimIfSpecialAnimFinished(trainerObj))
{
FieldObjectSetSpecialAnim(trainerObj, 0x3E);
@@ -327,7 +330,7 @@ s8 sub_8084654(u8 taskId, struct Task *task, struct MapObject *trainerObj)
{
trainerObj->mapobj_bit_26 = 0;
trainerObj->mapobj_bit_2 = 1;
-
+
sprite = &gSprites[trainerObj->spriteId];
sprite->oam.priority = 2;
FieldObjectClearAnimIfSpecialAnimFinished(trainerObj);
diff --git a/src/truck_scene.c b/src/truck_scene.c
index 4e45bd165..64eca498c 100644
--- a/src/truck_scene.c
+++ b/src/truck_scene.c
@@ -12,8 +12,6 @@ extern s8 gTruckCamera_HorizontalTable[];
s32 GetTruckCameraBobbingY(int a1)
{
- s32 result;
-
if (!(a1 % 120))
return -1;
else if ((a1 % 10) <= 4)
@@ -24,8 +22,6 @@ s32 GetTruckCameraBobbingY(int a1)
s32 GetTruckBoxMovement(int a1) // for the box movement?
{
- s32 result;
-
if (!((a1 + 120) % 180))
return -1;
diff --git a/src/weather.c b/src/weather.c
index c16faaed8..520185441 100644
--- a/src/weather.c
+++ b/src/weather.c
@@ -192,7 +192,7 @@ void sub_807CB10(void) {
v4 += v11;
dunno = v4 - v9;
if (dunno > 0) {
- v4 -= dunno + ((u16)dunno >> 15) >> 1;
+ v4 -= (dunno + ((u16)dunno >> 15)) >> 1;
}
v1[v6][v2] = v4 >> 8;
if (v1[v6][v2] > 0x1f) {
diff --git a/src/wild_encounter.c b/src/wild_encounter.c
index 48fe3c116..1291242a7 100644
--- a/src/wild_encounter.c
+++ b/src/wild_encounter.c
@@ -11,6 +11,7 @@
#include "var.h"
#include "rom4.h"
#include "vars.h"
+#include "metatile_behavior.h"
struct WildPokemon
{