diff options
author | yenatch <yenatch@gmail.com> | 2018-04-04 21:04:14 -0400 |
---|---|---|
committer | GitHub <noreply@github.com> | 2018-04-04 21:04:14 -0400 |
commit | fe4377ce532d1fea1b28d2c52e4f62f0ca702a30 (patch) | |
tree | 6ce2635ce57ff2735839235e3061e7f3009cfe5d /engine/menus | |
parent | 0c446367ce79dfe2a26f4bd7668036477811a279 (diff) | |
parent | 38107209a6ad431b399cc36405c0af8b5babf5ef (diff) |
Merge pull request #501 from mid-kid/reorg
Organize the engine/ directory
Diffstat (limited to 'engine/menus')
-rw-r--r-- | engine/menus/debug.asm | 1447 | ||||
-rw-r--r-- | engine/menus/delete_save.asm | 36 | ||||
-rw-r--r-- | engine/menus/empty_sram.asm | 19 | ||||
-rw-r--r-- | engine/menus/init_gender.asm | 111 | ||||
-rw-r--r-- | engine/menus/intro_menu.asm | 1418 | ||||
-rw-r--r-- | engine/menus/main_menu.asm | 361 | ||||
-rw-r--r-- | engine/menus/menu.asm | 841 | ||||
-rw-r--r-- | engine/menus/menu_2.asm | 253 | ||||
-rw-r--r-- | engine/menus/naming_screen.asm | 1467 | ||||
-rw-r--r-- | engine/menus/options_menu.asm | 583 | ||||
-rw-r--r-- | engine/menus/save.asm | 1210 | ||||
-rw-r--r-- | engine/menus/savemenu_copytilemapatonce.asm | 77 | ||||
-rw-r--r-- | engine/menus/scrolling_menu.asm | 543 | ||||
-rw-r--r-- | engine/menus/start_menu.asm | 1993 | ||||
-rw-r--r-- | engine/menus/trainer_card.asm | 623 |
15 files changed, 10982 insertions, 0 deletions
diff --git a/engine/menus/debug.asm b/engine/menus/debug.asm new file mode 100644 index 000000000..4c3110fe1 --- /dev/null +++ b/engine/menus/debug.asm @@ -0,0 +1,1447 @@ + const_def $6a + const DEBUGTEST_UP_ARROW ; $6a + const DEBUGTEST_TICKS ; $6b + const DEBUGTEST_WHITE ; $6c + const DEBUGTEST_LIGHT ; $6d + const DEBUGTEST_DARK ; $6e + const DEBUGTEST_BLACK ; $6f + const DEBUGTEST_0 ; $70 + const DEBUGTEST_1 ; $71 + const DEBUGTEST_2 ; $72 + const DEBUGTEST_3 ; $73 + const DEBUGTEST_4 ; $74 + const DEBUGTEST_5 ; $75 + const DEBUGTEST_6 ; $76 + const DEBUGTEST_7 ; $77 + const DEBUGTEST_8 ; $78 + const DEBUGTEST_9 ; $79 + const DEBUGTEST_A ; $7a + const DEBUGTEST_B ; $7b + const DEBUGTEST_C ; $7c + const DEBUGTEST_D ; $7d + const DEBUGTEST_E ; $7e + const DEBUGTEST_F ; $7f + +ColorTest: ; 818ac +; A debug menu to test monster and trainer palettes at runtime. + + ld a, [hCGB] + and a + jr nz, .asm_818b5 + ld a, [hSGB] + and a + ret z + +.asm_818b5 + ld a, [hInMenu] + push af + ld a, $1 + ld [hInMenu], a + call DisableLCD + call Function81948 + call Function8197c + call Function819a7 + call Function818f4 + call EnableLCD + ld de, MUSIC_NONE + call PlayMusic + xor a + ld [wJumptableIndex], a + ld [wcf66], a + ld [wd003], a +.asm_818de + ld a, [wJumptableIndex] + bit 7, a + jr nz, .asm_818f0 + call Function81a74 + call Function81f5e + call DelayFrame + jr .asm_818de + +.asm_818f0 + pop af + ld [hInMenu], a + ret +; 818f4 + +Function818f4: ; 818f4 + ld a, [wd002] + and a + jr nz, Function81911 + ld hl, PokemonPalettes + +Function818fd: ; 818fd + ld de, wOverworldMap + ld c, NUM_POKEMON + 1 +.asm_81902 + push bc + push hl + call Function81928 + pop hl + ld bc, 8 + add hl, bc + pop bc + dec c + jr nz, .asm_81902 + ret + +Function81911: ; 81911 + ld hl, TrainerPalettes + ld de, wOverworldMap + ld c, NUM_TRAINER_CLASSES +.asm_81919 + push bc + push hl + call Function81928 + pop hl + ld bc, 4 + add hl, bc + pop bc + dec c + jr nz, .asm_81919 + ret +; 81928 + +Function81928: ; 81928 + ld a, BANK(PokemonPalettes) ; BANK(TrainerPalettes) + call GetFarByte + ld [de], a + inc de + inc hl + ld a, BANK(PokemonPalettes) ; BANK(TrainerPalettes) + call GetFarByte + ld [de], a + inc de + inc hl + ld a, BANK(PokemonPalettes) ; BANK(TrainerPalettes) + call GetFarByte + ld [de], a + inc de + inc hl + ld a, BANK(PokemonPalettes) ; BANK(TrainerPalettes) + call GetFarByte + ld [de], a + inc de + ret +; 81948 + +Function81948: ; 81948 + ld a, $1 + ld [rVBK], a + ld hl, vTiles0 + ld bc, sScratch - vTiles0 + xor a + call ByteFill + ld a, $0 + ld [rVBK], a + ld hl, vTiles0 + ld bc, sScratch - vTiles0 + xor a + call ByteFill + hlcoord 0, 0, wAttrMap + ld bc, SCREEN_WIDTH * SCREEN_HEIGHT + xor a + call ByteFill + hlcoord 0, 0 + ld bc, SCREEN_WIDTH * SCREEN_HEIGHT + xor a + call ByteFill + call ClearSprites + ret +; 8197c + +Function8197c: ; 8197c + ld hl, DebugColorTestGFX + 1 tiles + ld de, vTiles2 tile DEBUGTEST_UP_ARROW + ld bc, 22 tiles + call CopyBytes + ld hl, DebugColorTestGFX + ld de, vTiles0 + ld bc, 1 tiles + call CopyBytes + call LoadStandardFont + ld hl, vTiles1 + lb bc, 8, 0 +.asm_8199d + ld a, [hl] + xor $ff + ld [hli], a + dec bc + ld a, c + or b + jr nz, .asm_8199d + ret +; 819a7 + +Function819a7: ; 819a7 + ld a, [hCGB] + and a + ret z + ld a, [rSVBK] + push af + ld a, BANK(wBGPals2) + ld [rSVBK], a + ld hl, Palette_DebugBG + ld de, wBGPals2 + ld bc, 16 palettes + call CopyBytes + ld a, 1 << rBGPI_AUTO_INCREMENT + ld [rBGPI], a + ld hl, Palette_DebugBG + ld c, 8 palettes + xor a +.asm_819c8 + ld [rBGPD], a + dec c + jr nz, .asm_819c8 + ld a, 1 << rOBPI_AUTO_INCREMENT + ld [rOBPI], a + ld hl, Palette_DebugOB + ld c, 8 palettes +.asm_819d6 + ld a, [hli] + ld [rOBPD], a + dec c + jr nz, .asm_819d6 + ld a, $94 + ld [wc608], a + ld a, $52 + ld [wc608 + 1], a + ld a, $4a + ld [wc608 + 2], a + ld a, $29 + ld [wc608 + 3], a + pop af + ld [rSVBK], a + ret +; 819f4 + +Palette_DebugBG: ; 819f4 +INCLUDE "gfx/debug/bg.pal" + +Palette_DebugOB: ; 81a34 +INCLUDE "gfx/debug/ob.pal" +; 81a74 + +Function81a74: ; 81a74 + call JoyTextDelay + ld a, [wJumptableIndex] + cp $4 + jr nc, .asm_81a8b + ld hl, hJoyLast + ld a, [hl] + and SELECT + jr nz, .asm_81a9a + ld a, [hl] + and START + jr nz, .asm_81aab + +.asm_81a8b + ld a, [wJumptableIndex] + ld e, a + ld d, 0 + ld hl, Jumptable_81acf + add hl, de + add hl, de + ld a, [hli] + ld h, [hl] + ld l, a + jp hl + +.asm_81a9a + call Function81eca + call Function81ac3 + ld e, a + ld a, [wcf66] + inc a + cp e + jr c, .asm_81aba + xor a + jr .asm_81aba + +.asm_81aab + call Function81eca + ld a, [wcf66] + dec a + cp $ff + jr nz, .asm_81aba + call Function81ac3 + dec a + +.asm_81aba + ld [wcf66], a + ld a, $0 + ld [wJumptableIndex], a + ret +; 81ac3 + +Function81ac3: ; 81ac3 +; Looping back around the pic set. + ld a, [wd002] + and a + jr nz, .asm_81acc + ld a, NUM_POKEMON ; CELEBI + ret + +.asm_81acc + ld a, NUM_TRAINER_CLASSES - 1 ; MYSTICALMAN + ret +; 81acf + +Jumptable_81acf: ; 81acf + dw Function81adb + dw Function81c18 + dw Function81c33 + dw Function81cc2 + dw Function81d8e + dw Function81daf +; 81adb + +Function81adb: ; 81adb + xor a + ld [hBGMapMode], a + hlcoord 0, 0 + ld bc, SCREEN_WIDTH * SCREEN_HEIGHT + ld a, DEBUGTEST_BLACK + call ByteFill + hlcoord 1, 3 + lb bc, 7, 18 + ld a, DEBUGTEST_WHITE + call Bank20_FillBoxWithByte + hlcoord 11, 0 + lb bc, 2, 3 + ld a, DEBUGTEST_LIGHT + call Bank20_FillBoxWithByte + hlcoord 16, 0 + lb bc, 2, 3 + ld a, DEBUGTEST_DARK + call Bank20_FillBoxWithByte + call Function81bc0 + call Function81bf4 + ld a, [wcf66] + inc a + ld [wCurPartySpecies], a + ld [wd265], a + hlcoord 0, 1 + ld de, wd265 + lb bc, PRINTNUM_LEADINGZEROS | 1, 3 + call PrintNum + ld a, [wd002] + and a + jr nz, .asm_81b7a + ld a, $1 + ld [wUnownLetter], a + call GetPokemonName + hlcoord 4, 1 + call PlaceString + xor a + ld [wBoxAlignment], a + hlcoord 12, 3 + call _PrepMonFrontpic + ld de, vTiles2 tile $31 + predef GetMonBackpic + ld a, $31 + ld [hGraphicStartTile], a + hlcoord 2, 4 + lb bc, 6, 6 + predef PlaceGraphic + ld a, [wd003] + and a + jr z, .asm_81b66 + ld de, String_81baf + jr .asm_81b69 + +.asm_81b66 + ld de, String_81bb4 + +.asm_81b69 + hlcoord 7, 17 + call PlaceString + hlcoord 0, 17 + ld de, String_81bb9 + call PlaceString + jr .asm_81ba9 + +.asm_81b7a + ld a, [wd265] + ld [wTrainerClass], a + callfar GetTrainerAttributes + ld de, wStringBuffer1 + hlcoord 4, 1 + call PlaceString + ld de, vTiles2 + callfar GetTrainerPic + xor a + ld [wTempEnemyMonSpecies], a + ld [hGraphicStartTile], a + hlcoord 2, 3 + lb bc, 7, 7 + predef PlaceGraphic + +.asm_81ba9 + ld a, $1 + ld [wJumptableIndex], a + ret +; 81baf + +String_81baf: db "レア", DEBUGTEST_BLACK, DEBUGTEST_BLACK, "@" ; rare (shiny) +String_81bb4: db "ノーマル@" ; normal +String_81bb9: db DEBUGTEST_A, "きりかえ▶@" ; (A) switches +; 81bc0 + +Function81bc0: ; 81bc0 + decoord 0, 11, wAttrMap + hlcoord 2, 11 + ld a, $1 + call Function81bde + decoord 0, 13, wAttrMap + hlcoord 2, 13 + ld a, $2 + call Function81bde + decoord 0, 15, wAttrMap + hlcoord 2, 15 + ld a, $3 + +Function81bde: ; 81bde + push af + ld a, DEBUGTEST_UP_ARROW + ld [hli], a + ld bc, $f + ld a, DEBUGTEST_TICKS + call ByteFill + ld l, e + ld h, d + pop af + ld bc, $28 + call ByteFill + ret +; 81bf4 + +Function81bf4: ; 81bf4 + ld a, [wcf66] + inc a + ld l, a + ld h, $0 + add hl, hl + add hl, hl + ld de, wOverworldMap + add hl, de + ld de, wc608 + ld bc, 4 + call CopyBytes + xor a + ld [wcf64], a + ld [wcf65], a + ld de, wc608 + call Function81ea5 + ret +; 81c18 + +Function81c18: ; 81c18 + ld a, [hCGB] + and a + jr z, .asm_81c2a + ld a, $2 + ld [hBGMapMode], a + call DelayFrame + call DelayFrame + call DelayFrame + +.asm_81c2a + call WaitBGMap + ld a, $2 + ld [wJumptableIndex], a + ret +; 81c33 + +Function81c33: ; 81c33 + ld a, [hCGB] + and a + jr z, .asm_81c69 + ld a, [rSVBK] + push af + ld a, BANK(wBGPals2) + ld [rSVBK], a + ld hl, wBGPals2 + ld de, wc608 + ld c, $1 + call Function81ee3 + hlcoord 10, 2 + ld de, wc608 + call Function81ca7 + hlcoord 15, 2 + ld de, wc608 + 2 + call Function81ca7 + ld a, $1 + ld [hCGBPalUpdate], a + ld a, $3 + ld [wJumptableIndex], a + pop af + ld [rSVBK], a + ret + +.asm_81c69 + ld hl, wSGBPals + ld a, 1 + ld [hli], a + ld a, LOW(PALRGB_WHITE) + ld [hli], a + ld a, HIGH(PALRGB_WHITE) + ld [hli], a + ld a, [wc608] + ld [hli], a + ld a, [wc608 + 1] + ld [hli], a + ld a, [wc608 + 2] + ld [hli], a + ld a, [wc608 + 3] + ld [hli], a + xor a + ld [hli], a + ld [hli], a + ld [hl], a + ld hl, wSGBPals + call Function81f0c + hlcoord 10, 2 + ld de, wc608 + call Function81ca7 + hlcoord 15, 2 + ld de, wc608 + 2 + call Function81ca7 + ld a, $3 + ld [wJumptableIndex], a + ret +; 81ca7 + +Function81ca7: ; 81ca7 + inc hl + inc hl + inc hl + ld a, [de] + call Function81cbc + ld a, [de] + swap a + call Function81cbc + inc de + ld a, [de] + call Function81cbc + ld a, [de] + swap a + +Function81cbc: ; 81cbc + and $f + add DEBUGTEST_0 + ld [hld], a + ret +; 81cc2 + +Function81cc2: ; 81cc2 + ld a, [hJoyLast] + and B_BUTTON + jr nz, .asm_81cdf + ld a, [hJoyLast] + and A_BUTTON + jr nz, .asm_81ce5 + ld a, [wcf64] + and $3 + ld e, a + ld d, 0 + ld hl, Jumptable_81d02 + add hl, de + add hl, de + ld a, [hli] + ld h, [hl] + ld l, a + jp hl + +.asm_81cdf + ld a, $4 + ld [wJumptableIndex], a + ret + +.asm_81ce5 + ld a, [wd002] + and a + ret nz + ld a, [wd003] + xor $4 + ld [wd003], a + ld c, a + ld b, 0 + ld hl, PokemonPalettes + add hl, bc + call Function818fd + ld a, $0 + ld [wJumptableIndex], a + ret +; 81d02 + +Jumptable_81d02: ; 81d02 + dw Function81d0a + dw Function81d34 + dw Function81d46 + dw Function81d58 +; 81d0a + +Function81d0a: ; 81d0a + ld hl, hJoyLast + ld a, [hl] + and D_DOWN + jr nz, Function81d89 + ld a, [hl] + and D_LEFT + jr nz, .asm_81d1d + ld a, [hl] + and D_RIGHT + jr nz, .asm_81d28 + ret + +.asm_81d1d + xor a + ld [wcf65], a + ld de, wc608 + call Function81ea5 + ret + +.asm_81d28 + ld a, $1 + ld [wcf65], a + ld de, wc608 + 2 + call Function81ea5 + ret + +Function81d34: ; 81d34 + ld hl, hJoyLast + ld a, [hl] + and D_DOWN + jr nz, Function81d89 + ld a, [hl] + and D_UP + jr nz, Function81d84 + ld hl, wc608 + 10 + jr Function81d63 + +Function81d46: ; 81d46 + ld hl, hJoyLast + ld a, [hl] + and D_DOWN + jr nz, Function81d89 + ld a, [hl] + and D_UP + jr nz, Function81d84 + ld hl, wc608 + 11 + jr Function81d63 + +Function81d58: ; 81d58 + ld hl, hJoyLast + ld a, [hl] + and D_UP + jr nz, Function81d84 + ld hl, wc608 + 12 + +Function81d63: ; 81d63 + ld a, [hJoyLast] + and D_RIGHT + jr nz, Function81d70 + ld a, [hJoyLast] + and D_LEFT + jr nz, Function81d77 + ret + +Function81d70: ; 81d70 + ld a, [hl] + cp $1f + ret nc + inc [hl] + jr Function81d7b + +Function81d77: ; 81d77 + ld a, [hl] + and a + ret z + dec [hl] + +Function81d7b: ; 81d7b + call Function81e67 + ld a, $2 + ld [wJumptableIndex], a + ret + +Function81d84: ; 81d84 + ld hl, wcf64 + dec [hl] + ret + +Function81d89: ; 81d89 + ld hl, wcf64 + inc [hl] + ret +; 81d8e + +Function81d8e: ; 81d8e + hlcoord 0, 10 + ld bc, $a0 + ld a, DEBUGTEST_BLACK + call ByteFill + hlcoord 2, 12 + ld de, String_81fcd + call PlaceString + xor a + ld [wd004], a + call Function81df4 + ld a, $5 + ld [wJumptableIndex], a + ret +; 81daf + +Function81daf: ; 81daf + ld hl, hJoyPressed + ld a, [hl] + and B_BUTTON + jr nz, .asm_81dbb + call Function81dc7 + ret + +.asm_81dbb + ld a, $0 + ld [wJumptableIndex], a + ret +; 81dc1 + +Function81dc1: ; 81dc1 + ld hl, wJumptableIndex + set 7, [hl] + ret +; 81dc7 + +Function81dc7: ; 81dc7 + ld hl, hJoyLast + ld a, [hl] + and D_UP + jr nz, .asm_81dd5 + ld a, [hl] + and D_DOWN + jr nz, .asm_81de2 + ret + +.asm_81dd5 + ld a, [wd004] + cp $3b + jr z, .asm_81ddf + inc a + jr .asm_81ded + +.asm_81ddf + xor a + jr .asm_81ded + +.asm_81de2 + ld a, [wd004] + and a + jr z, .asm_81deb + dec a + jr .asm_81ded + +.asm_81deb + ld a, $3b + +.asm_81ded + ld [wd004], a + call Function81df4 + ret +; 81df4 + +Function81df4: ; 81df4 + hlcoord 10, 11 + call Function81e5e + hlcoord 10, 12 + call Function81e5e + hlcoord 10, 13 + call Function81e5e + hlcoord 10, 14 + call Function81e5e + ld a, [wd004] + inc a + ld [wd265], a + predef GetTMHMMove + ld a, [wd265] + ld [wPutativeTMHMMove], a + call GetMoveName + hlcoord 10, 12 + call PlaceString + ld a, [wd004] + call Function81e55 + ld [wCurItem], a + predef CanLearnTMHMMove + ld a, c + and a + ld de, String_81e46 + jr nz, .asm_81e3f + ld de, String_81e4d + +.asm_81e3f + hlcoord 10, 14 + call PlaceString + ret +; 81e46 + +String_81e46: db "おぼえられる@" ; can be taught +String_81e4d: db "おぼえられない@" ; cannot be taught +; 81e55 + +Function81e55: ; 81e55 + cp $32 + jr c, .asm_81e5b + inc a + inc a + +.asm_81e5b + add $bf + ret +; 81e5e + +Function81e5e: ; 81e5e + ld bc, 10 + ld a, DEBUGTEST_BLACK + call ByteFill + ret +; 81e67 + +Function81e67: ; 81e67 + ld a, [wc608 + 10] + and $1f + ld e, a + ld a, [wc608 + 11] + and $7 + sla a + swap a + or e + ld e, a + ld a, [wc608 + 11] + and $18 + sla a + swap a + ld d, a + ld a, [wc608 + 12] + and $1f + sla a + sla a + or d + ld d, a + ld a, [wcf65] + and a + jr z, .asm_81e9c + ld a, e + ld [wc608 + 2], a + ld a, d + ld [wc608 + 3], a + ret + +.asm_81e9c + ld a, e + ld [wc608], a + ld a, d + ld [wc608 + 1], a + ret +; 81ea5 + +Function81ea5: ; 81ea5 + ld a, [de] + and $1f + ld [wc608 + 10], a + ld a, [de] + and $e0 + swap a + srl a + ld b, a + inc de + ld a, [de] + and $3 + swap a + srl a + or b + ld [wc608 + 11], a + ld a, [de] + and $7c + srl a + srl a + ld [wc608 + 12], a + ret +; 81eca + +Function81eca: ; 81eca + ld a, [wcf66] + inc a + ld l, a + ld h, $0 + add hl, hl + add hl, hl + ld de, wOverworldMap + add hl, de + ld e, l + ld d, h + ld hl, wc608 + ld bc, 4 + call CopyBytes + ret +; 81ee3 + +Function81ee3: ; 81ee3 +.asm_81ee3 + ld a, LOW(PALRGB_WHITE) + ld [hli], a + ld a, HIGH(PALRGB_WHITE) + ld [hli], a + ld a, [de] + inc de + ld [hli], a + ld a, [de] + inc de + ld [hli], a + ld a, [de] + inc de + ld [hli], a + ld a, [de] + inc de + ld [hli], a + xor a + ld [hli], a + ld [hli], a + dec c + jr nz, .asm_81ee3 + ret +; 81efc + +Bank20_FillBoxWithByte: ; 81efc +; For some reason, we have another copy of FillBoxWithByte here +.row + push bc + push hl +.col + ld [hli], a + dec c + jr nz, .col + pop hl + ld bc, SCREEN_WIDTH + add hl, bc + pop bc + dec b + jr nz, .row + ret +; 81f0c + +Function81f0c: ; 81f0c + ld a, [wcfbe] + push af + set 7, a + ld [wcfbe], a + call Function81f1d + pop af + ld [wcfbe], a + ret +; 81f1d + +Function81f1d: ; 81f1d + ld a, [hl] + and $7 + ret z + ld b, a +.asm_81f22 + push bc + xor a + ld [rJOYP], a + ld a, $30 + ld [rJOYP], a + ld b, $10 +.asm_81f2c + ld e, $8 + ld a, [hli] + ld d, a +.asm_81f30 + bit 0, d + ld a, $10 + jr nz, .asm_81f38 + ld a, $20 + +.asm_81f38 + ld [rJOYP], a + ld a, $30 + ld [rJOYP], a + rr d + dec e + jr nz, .asm_81f30 + dec b + jr nz, .asm_81f2c + ld a, $20 + ld [rJOYP], a + ld a, $30 + ld [rJOYP], a + ld de, 7000 +.asm_81f51 + nop + nop + nop + dec de + ld a, d + or e + jr nz, .asm_81f51 + pop bc + dec b + jr nz, .asm_81f22 + ret +; 81f5e + +Function81f5e: ; 81f5e + ld a, DEBUGTEST_BLACK + hlcoord 10, 0 + ld [hl], a + hlcoord 15, 0 + ld [hl], a + hlcoord 1, 11 + ld [hl], a + hlcoord 1, 13 + ld [hl], a + hlcoord 1, 15 + ld [hl], a + ld a, [wJumptableIndex] + cp $3 + jr nz, .asm_81fc9 + ld a, [wcf64] + and a + jr z, .asm_81f8d + dec a + hlcoord 1, 11 + ld bc, 2 * SCREEN_WIDTH + call AddNTimes + ld [hl], $ed + +.asm_81f8d + ld a, [wcf65] + and a + jr z, .asm_81f98 + hlcoord 15, 0 + jr .asm_81f9b + +.asm_81f98 + hlcoord 10, 0 + +.asm_81f9b + ld [hl], $ed + ld b, $70 + ld c, $5 + ld hl, wVirtualOAM + ld de, wc608 + 10 + call .asm_81fb7 + ld de, wc608 + 11 + call .asm_81fb7 + ld de, wc608 + 12 + call .asm_81fb7 + ret + +.asm_81fb7 + ld a, b + ld [hli], a ; y + ld a, [de] + add a + add a + add 3 * TILE_WIDTH + ld [hli], a ; x + xor a + ld [hli], a ; tile id + ld a, c + ld [hli], a ; attributes + ld a, 2 * TILE_WIDTH + add b + ld b, a + inc c + ret + +.asm_81fc9 + call ClearSprites + ret +; 81fcd + +String_81fcd: ; 81fcd + db "おわりますか?" ; Are you finished? + next "はい<DOT><DOT><DOT>", DEBUGTEST_A ; YES...(A) + next "いいえ<DOT><DOT>", DEBUGTEST_B ; NO..(B) + db "@" +; 81fe3 + +DebugColorTestGFX: +INCBIN "gfx/debug/color_test.2bpp" + + +TilesetColorTest: + ret + xor a + ld [wJumptableIndex], a + ld [wcf64], a + ld [wcf65], a + ld [wcf66], a + ld [hMapAnims], a + call ClearSprites + call OverworldTextModeSwitch + call WaitBGMap2 + xor a + ld [hBGMapMode], a + ld de, DebugColorTestGFX + 1 tiles + ld hl, vTiles2 tile DEBUGTEST_UP_ARROW + lb bc, BANK(DebugColorTestGFX), 22 + call Request2bpp + ld de, DebugColorTestGFX + ld hl, vTiles1 + lb bc, BANK(DebugColorTestGFX), 1 + call Request2bpp + ld a, HIGH(vBGMap1) + ld [hBGMapAddress + 1], a + hlcoord 0, 0 + ld bc, SCREEN_WIDTH * SCREEN_HEIGHT + ld a, DEBUGTEST_BLACK + call ByteFill + hlcoord 0, 0, wAttrMap + ld bc, SCREEN_WIDTH * SCREEN_HEIGHT + ld a, $7 + call ByteFill + ld de, $15 + ld a, DEBUGTEST_WHITE + call Function821d2 + ld de, $1a + ld a, DEBUGTEST_LIGHT + call Function821d2 + ld de, $1f + ld a, DEBUGTEST_DARK + call Function821d2 + ld de, $24 + ld a, DEBUGTEST_BLACK + call Function821d2 + call Function821f4 + call Function8220f + call WaitBGMap2 + ld [wJumptableIndex], a + ld a, $40 + ld [hWY], a + ret +; 821d2 + +Function821d2: ; 821d2 + hlcoord 0, 0 + call Function821de + +Function821d8: ; 821d8 + ld a, [wcf64] + hlcoord 0, 0, wAttrMap + +Function821de: ; 821de + add hl, de +rept 4 + ld [hli], a +endr + ld bc, $10 + add hl, bc +rept 4 + ld [hli], a +endr + ld bc, $10 + add hl, bc +rept 4 + ld [hli], a +endr + ret +; 821f4 + +Function821f4: ; 821f4 + hlcoord 2, 4 + call Function82203 + hlcoord 2, 6 + call Function82203 + hlcoord 2, 8 + +Function82203: ; 82203 + ld a, DEBUGTEST_UP_ARROW + ld [hli], a + ld bc, $10 - 1 + ld a, DEBUGTEST_TICKS + call ByteFill + ret +; 8220f + +Function8220f: ; 8220f + ld a, [rSVBK] + push af + ld a, BANK(wBGPals1) + ld [rSVBK], a + ld a, [wcf64] + ld l, a + ld h, $0 + add hl, hl + add hl, hl + add hl, hl + ld de, wBGPals1 + add hl, de + ld de, wc608 + ld bc, 8 + call CopyBytes + ld de, wc608 + call Function81ea5 + pop af + ld [rSVBK], a + ret +; 82236 + + +Function82236: ; 82236 + ld hl, hJoyLast + ld a, [hl] + and SELECT + jr nz, .loop7 + ld a, [hl] + and B_BUTTON + jr nz, .asm_82299 + call Function822f0 + ret + +.loop7 + ld hl, wcf64 + ld a, [hl] + inc a + and $7 + cp $7 + jr nz, .asm_82253 + xor a + +.asm_82253 + ld [hl], a + ld de, $15 + call Function821d8 + ld de, $1a + call Function821d8 + ld de, $1f + call Function821d8 + ld de, $24 + call Function821d8 + ld a, [rSVBK] + push af + ld a, BANK(wBGPals2) + ld [rSVBK], a + ld hl, wBGPals2 + ld a, [wcf64] + ld bc, 1 palettes + call AddNTimes + ld de, wc608 + ld bc, 1 palettes + call CopyBytes + pop af + ld [rSVBK], a + ld a, $2 + ld [hBGMapMode], a + ld c, 3 + call DelayFrames + ld a, $1 + ld [hBGMapMode], a + ret + +.asm_82299 + call ClearSprites + ld a, [hWY] + xor $d0 + ld [hWY], a + ret +; 822a3 + +Function822a3: ; 822a3 + ld a, [rSVBK] + push af + ld a, BANK(wBGPals2) + ld [rSVBK], a + ld hl, wBGPals2 + ld a, [wcf64] + ld bc, 1 palettes + call AddNTimes + ld e, l + ld d, h + ld hl, wc608 + ld bc, 1 palettes + call CopyBytes + hlcoord 1, 0 + ld de, wc608 + call Function81ca7 + hlcoord 6, 0 + ld de, wc608 + 2 + call Function81ca7 + hlcoord 11, 0 + ld de, wc608 + 4 + call Function81ca7 + hlcoord 16, 0 + ld de, wc608 + 6 + call Function81ca7 + pop af + ld [rSVBK], a + ld a, $1 + ld [hCGBPalUpdate], a + call DelayFrame + ret +; 822f0 + +Function822f0: ; 822f0 + ld a, [wcf65] + and 3 + ld e, a + ld d, 0 + ld hl, .dw + add hl, de + add hl, de + ld a, [hli] + ld h, [hl] + ld l, a + jp hl +; 82301 + +.dw ; 82301 + dw Function82309 + dw Function82339 + dw Function8234b + dw Function8235d +; 82309 + +Function82309: ; 82309 + ld hl, hJoyLast + ld a, [hl] + and D_DOWN + jr nz, Function8238c + ld a, [hl] + and D_LEFT + jr nz, .asm_8231c + ld a, [hl] + and D_RIGHT + jr nz, .asm_82322 + ret + +.asm_8231c + ld a, [wcf66] + dec a + jr .asm_82326 + +.asm_82322 + ld a, [wcf66] + inc a + +.asm_82326 + and $3 + ld [wcf66], a + ld e, a + ld d, $0 + ld hl, wc608 + add hl, de + add hl, de + ld e, l + ld d, h + call Function81ea5 + ret + +Function82339: ; 82338 + ld hl, hJoyLast + ld a, [hl] + and D_DOWN + jr nz, Function8238c + ld a, [hl] + and D_UP + jr nz, Function82387 + ld hl, wc608 + 10 + jr Function82368 + +Function8234b: ; 8234b + ld hl, hJoyLast + ld a, [hl] + and D_DOWN + jr nz, Function8238c + ld a, [hl] + and D_UP + jr nz, Function82387 + ld hl, wc608 + 11 + jr Function82368 + +Function8235d: ; 8235d + ld hl, hJoyLast + ld a, [hl] + and D_UP + jr nz, Function82387 + ld hl, wc608 + 12 + +Function82368: ; 82368 + ld a, [hJoyLast] + and D_RIGHT + jr nz, .asm_82375 + ld a, [hJoyLast] + and D_LEFT + jr nz, .asm_8237c + ret + +.asm_82375 + ld a, [hl] + cp $1f + ret nc + inc [hl] + jr .asm_82380 + +.asm_8237c + ld a, [hl] + and a + ret z + dec [hl] + +.asm_82380 + call Function82391 + call Function822a3 + ret + +Function82387: ; 82387 + ld hl, wcf65 + dec [hl] + ret + +Function8238c: ; 8238c + ld hl, wcf65 + inc [hl] + ret +; 82391 + +Function82391: ; 82391 + ld a, [wc608 + 10] + and $1f + ld e, a + ld a, [wc608 + 11] + and $7 + sla a + swap a + or e + ld e, a + ld a, [wc608 + 11] + and $18 + sla a + swap a + ld d, a + ld a, [wc608 + 12] + and $1f + sla a + sla a + or d + ld d, a + ld a, [wcf66] + ld c, a + ld b, $0 + ld hl, wc608 + add hl, bc + add hl, bc + ld a, e + ld [hli], a + ld [hl], d + ret +; 823c6 + +Function823c6: ; 823c6 + ret + +Function823c7: ; 823c7 + ret +; 823c8 diff --git a/engine/menus/delete_save.asm b/engine/menus/delete_save.asm new file mode 100644 index 000000000..a86faf06a --- /dev/null +++ b/engine/menus/delete_save.asm @@ -0,0 +1,36 @@ +_DeleteSaveData: ; 4d54c + farcall BlankScreen + ld b, SCGB_DIPLOMA + call GetSGBLayout + call LoadStandardFont + call LoadFontsExtra + ld de, MUSIC_MAIN_MENU + call PlayMusic + ld hl, .Text_ClearAllSaveData + call PrintText + ld hl, .NoYesMenuHeader + call CopyMenuHeader + call VerticalMenu + ret c + ld a, [wMenuCursorY] + cp $1 + ret z + farcall EmptyAllSRAMBanks + ret + +.Text_ClearAllSaveData: ; 0x4d580 + ; Clear all save data? + text_jump UnknownText_0x1c564a + db "@" + +.NoYesMenuHeader: ; 0x4d585 + db 0 ; flags + menu_coords 14, 7, SCREEN_WIDTH - 1, TEXTBOX_Y - 1 + dw .MenuData + db 1 ; default option + +.MenuData: ; 0x4d58d + db STATICMENU_CURSOR | STATICMENU_NO_TOP_SPACING ; flags + db 2 ; items + db "NO@" + db "YES@" diff --git a/engine/menus/empty_sram.asm b/engine/menus/empty_sram.asm new file mode 100644 index 000000000..8b060f3ef --- /dev/null +++ b/engine/menus/empty_sram.asm @@ -0,0 +1,19 @@ +EmptyAllSRAMBanks: ; 4cf1f + ld a, 0 + call .EmptyBank + ld a, 1 + call .EmptyBank + ld a, 2 + call .EmptyBank + ld a, 3 + call .EmptyBank + ret + +.EmptyBank: ; 4cf34 + call GetSRAMBank + ld hl, SRAM_Begin + ld bc, SRAM_End - SRAM_Begin + xor a + call ByteFill + call CloseSRAM + ret diff --git a/engine/menus/init_gender.asm b/engine/menus/init_gender.asm new file mode 100644 index 000000000..8fd95bc85 --- /dev/null +++ b/engine/menus/init_gender.asm @@ -0,0 +1,111 @@ +InitCrystalData: ; 48000 + ld a, $1 + ld [wd474], a + xor a + ld [wd473], a + ld [wPlayerGender], a + ld [wd475], a + ld [wd476], a + ld [wd477], a + ld [wd478], a + ld [wd002], a + ld [wd003], a + ; could have done "ld a, [wd479] \ and %11111100", saved four operations + ld a, [wd479] + res 0, a + ld [wd479], a + ld a, [wd479] + res 1, a + ld [wd479], a + ret +; 4802f + +INCLUDE "mobile/mobile_12.asm" + +InitGender: ; 48dcb (12:4dcb) + call InitGenderScreen + call LoadGenderScreenPal + call LoadGenderScreenLightBlueTile + call WaitBGMap2 + call SetPalettes + ld hl, TextJump_AreYouABoyOrAreYouAGirl + call PrintText + ld hl, .MenuHeader + call LoadMenuHeader + call WaitBGMap2 + call VerticalMenu + call CloseWindow + ld a, [wMenuCursorY] + dec a + ld [wPlayerGender], a + ld c, 10 + call DelayFrames + ret +; 48dfc (12:4dfc) + +.MenuHeader: ; 0x48dfc + db MENU_BACKUP_TILES ; flags + menu_coords 6, 4, 12, 9 + dw .MenuData + db 1 ; default option +; 0x48e04 + +.MenuData: ; 0x48e04 + db STATICMENU_CURSOR | STATICMENU_WRAP | STATICMENU_DISABLE_B ; flags + db 2 ; items + db "Boy@" + db "Girl@" +; 0x48e0f + +TextJump_AreYouABoyOrAreYouAGirl: ; 0x48e0f + ; Are you a boy? Or are you a girl? + text_jump Text_AreYouABoyOrAreYouAGirl + db "@" +; 0x48e14 + +InitGenderScreen: ; 48e14 (12:4e14) + ld a, $10 + ld [wMusicFade], a + ld a, MUSIC_NONE + ld [wMusicFadeID], a + ld a, $0 + ld [wMusicFadeID + 1], a + ld c, 8 + call DelayFrames + call ClearBGPalettes + call InitCrystalData + call LoadFontsExtra + hlcoord 0, 0 + ld bc, SCREEN_HEIGHT * SCREEN_WIDTH + ld a, $0 + call ByteFill + hlcoord 0, 0, wAttrMap + ld bc, SCREEN_HEIGHT * SCREEN_WIDTH + xor a + call ByteFill + ret + +LoadGenderScreenPal: ; 48e47 (12:4e47) + ld hl, .Palette + ld de, wBGPals1 + ld bc, 1 palettes + ld a, BANK(wBGPals1) + call FarCopyWRAM + farcall ApplyPals + ret +; 48e5c (12:4e5c) + +.Palette: ; 48e5c +INCLUDE "gfx/new_game/gender_screen.pal" +; 48e64 + +LoadGenderScreenLightBlueTile: ; 48e64 (12:4e64) + ld de, .LightBlueTile + ld hl, vTiles2 tile $00 + lb bc, BANK(.LightBlueTile), 1 + call Get2bpp + ret +; 48e71 (12:4e71) + +.LightBlueTile: ; 48e71 +INCBIN "gfx/new_game/gender_screen.2bpp" diff --git a/engine/menus/intro_menu.asm b/engine/menus/intro_menu.asm new file mode 100644 index 000000000..af6e0c09e --- /dev/null +++ b/engine/menus/intro_menu.asm @@ -0,0 +1,1418 @@ +_MainMenu: ; 5ae8 + ld de, MUSIC_NONE + call PlayMusic + call DelayFrame + ld de, MUSIC_MAIN_MENU + ld a, e + ld [wMapMusic], a + call PlayMusic + farcall MainMenu + jp StartTitleScreen +; 5b04 + +; unused + ret +; 5b05 + +PrintDayOfWeek: ; 5b05 + push de + ld hl, .Days + ld a, b + call GetNthString + ld d, h + ld e, l + pop hl + call PlaceString + ld h, b + ld l, c + ld de, .Day + call PlaceString + ret +; 5b1c + +.Days: ; 5b1c + db "SUN@" + db "MON@" + db "TUES@" + db "WEDNES@" + db "THURS@" + db "FRI@" + db "SATUR@" +; 5b40 + +.Day: ; 5b40 + db "DAY@" +; 5b44 + +NewGame_ClearTileMapEtc: ; 5b44 + xor a + ld [hMapAnims], a + call ClearTileMap + call LoadFontsExtra + call LoadStandardFont + call ClearWindowData + ret +; 5b54 + +MysteryGift: ; 5b54 + call UpdateTime + farcall DoMysteryGiftIfDayHasPassed + farcall DoMysteryGift + ret +; 5b64 + +OptionsMenu: ; 5b64 + farcall _OptionsMenu + ret +; 5b6b + +NewGame: ; 5b6b + xor a + ld [wMonStatusFlags], a + call ResetWRAM + call NewGame_ClearTileMapEtc + call AreYouABoyOrAreYouAGirl + call OakSpeech + call InitializeWorld + ld a, 1 + ld [wPreviousLandmark], a + + ld a, SPAWN_HOME + ld [wDefaultSpawnpoint], a + + ld a, MAPSETUP_WARP + ld [hMapEntryMethod], a + jp FinishContinueFunction +; 5b8f + +AreYouABoyOrAreYouAGirl: ; 5b8f + farcall Mobile_AlwaysReturnNotCarry ; some mobile stuff + jr c, .ok + farcall InitGender + ret + +.ok + ld c, 0 + farcall InitMobileProfile ; mobile + ret +; 5ba7 + +ResetWRAM: ; 5ba7 + xor a + ld [hBGMapMode], a + call _ResetWRAM + ret +; 5bae + +_ResetWRAM: ; 5bae + + ld hl, wVirtualOAM + ld bc, wOptions - wVirtualOAM + xor a + call ByteFill + + ld hl, WRAM1_Begin + ld bc, wGameData - WRAM1_Begin + xor a + call ByteFill + + ld hl, wGameData + ld bc, wGameDataEnd - wGameData + xor a + call ByteFill + + ld a, [rLY] + ld [hSecondsBackup], a + call DelayFrame + ld a, [hRandomSub] + ld [wPlayerID], a + + ld a, [rLY] + ld [hSecondsBackup], a + call DelayFrame + ld a, [hRandomAdd] + ld [wPlayerID + 1], a + + call Random + ld [wSecretID], a + call DelayFrame + call Random + ld [wSecretID + 1], a + + ld hl, wPartyCount + call .InitList + + xor a + ld [wCurBox], a + ld [wSavedAtLeastOnce], a + + call SetDefaultBoxNames + + ld a, BANK(sBoxCount) + call GetSRAMBank + ld hl, sBoxCount + call .InitList + call CloseSRAM + + ld hl, wNumItems + call .InitList + + ld hl, wNumKeyItems + call .InitList + + ld hl, wNumBalls + call .InitList + + ld hl, wPCItems + call .InitList + + xor a + ld [wRoamMon1Species], a + ld [wRoamMon2Species], a + ld [wRoamMon3Species], a + ld a, -1 + ld [wRoamMon1MapGroup], a + ld [wRoamMon2MapGroup], a + ld [wRoamMon3MapGroup], a + ld [wRoamMon1MapNumber], a + ld [wRoamMon2MapNumber], a + ld [wRoamMon3MapNumber], a + + ld a, BANK(sMysteryGiftItem) + call GetSRAMBank + ld hl, sMysteryGiftItem + xor a + ld [hli], a + dec a + ld [hl], a + call CloseSRAM + + call LoadOrRegenerateLuckyIDNumber + call InitializeMagikarpHouse + + xor a + ld [wMonType], a + + ld [wJohtoBadges], a + ld [wKantoBadges], a + + ld [wCoins], a + ld [wCoins + 1], a + +if START_MONEY >= $10000 + ld a, HIGH(START_MONEY >> 8) +endc + ld [wMoney], a + ld a, HIGH(START_MONEY) ; mid + ld [wMoney + 1], a + ld a, LOW(START_MONEY) + ld [wMoney + 2], a + + xor a + ld [wWhichMomItem], a + + ld hl, wMomItemTriggerBalance + ld [hl], HIGH(MOM_MONEY >> 8) + inc hl + ld [hl], HIGH(MOM_MONEY) ; mid + inc hl + ld [hl], LOW(MOM_MONEY) + + call InitializeNPCNames + + farcall InitDecorations + + farcall DeletePartyMonMail + + farcall DeleteMobileEventIndex + + call ResetGameTime + ret +; 5ca1 + +.InitList: ; 5ca1 +; Loads 0 in the count and -1 in the first item or mon slot. + xor a + ld [hli], a + dec a + ld [hl], a + ret +; 5ca6 + +SetDefaultBoxNames: ; 5ca6 + ld hl, wBoxNames + ld c, 0 +.loop + push hl + ld de, .Box + call CopyName2 + dec hl + ld a, c + inc a + cp 10 + jr c, .less + sub 10 + ld [hl], "1" + inc hl + +.less + add "0" + ld [hli], a + ld [hl], "@" + pop hl + ld de, 9 + add hl, de + inc c + ld a, c + cp NUM_BOXES + jr c, .loop + ret + +.Box: + db "BOX@" +; 5cd3 + +InitializeMagikarpHouse: ; 5cd3 + ld hl, wBestMagikarpLengthFeet + ld a, $3 + ld [hli], a + ld a, $6 + ld [hli], a + ld de, .Ralph + call CopyName2 + ret +; 5ce3 + +.Ralph: ; 5ce3 + db "RALPH@" +; 5ce9 + +InitializeNPCNames: ; 5ce9 + ld hl, .Rival + ld de, wRivalName + call .Copy + + ld hl, .Mom + ld de, wMomsName + call .Copy + + ld hl, .Red + ld de, wRedsName + call .Copy + + ld hl, .Green + ld de, wGreensName + +.Copy: + ld bc, NAME_LENGTH + call CopyBytes + ret + +.Rival: db "???@" +.Red: db "RED@" +.Green: db "GREEN@" +.Mom: db "MOM@" +; 5d23 + +InitializeWorld: ; 5d23 + call ShrinkPlayer + farcall SpawnPlayer + farcall _InitializeStartDay + ret +; 5d33 + +LoadOrRegenerateLuckyIDNumber: ; 5d33 + ld a, BANK(sLuckyIDNumber) + call GetSRAMBank + ld a, [wCurDay] + inc a + ld b, a + ld a, [sLuckyNumberDay] + cp b + ld a, [sLuckyIDNumber + 1] + ld c, a + ld a, [sLuckyIDNumber] + jr z, .skip + ld a, b + ld [sLuckyNumberDay], a + call Random + ld c, a + call Random + +.skip + ld [wLuckyIDNumber], a + ld [sLuckyIDNumber], a + ld a, c + ld [wLuckyIDNumber + 1], a + ld [sLuckyIDNumber + 1], a + jp CloseSRAM +; 5d65 + +Continue: ; 5d65 + farcall TryLoadSaveFile + jr c, .FailToLoad + farcall _LoadData + call LoadStandardMenuHeader + call DisplaySaveInfoOnContinue + ld a, $1 + ld [hBGMapMode], a + ld c, 20 + call DelayFrames + call ConfirmContinue + jr nc, .Check1Pass + call CloseWindow + jr .FailToLoad + +.Check1Pass: + call Continue_CheckRTC_RestartClock + jr nc, .Check2Pass + call CloseWindow + jr .FailToLoad + +.Check2Pass: + ld a, $8 + ld [wMusicFade], a + ld a, LOW(MUSIC_NONE) + ld [wMusicFadeID], a + ld a, HIGH(MUSIC_NONE) + ld [wMusicFadeID + 1], a + call ClearBGPalettes + call Continue_MobileAdapterMenu + call CloseWindow + call ClearTileMap + ld c, 20 + call DelayFrames + farcall JumpRoamMons + farcall MysteryGift_CopyReceivedDecosToPC ; Mystery Gift + farcall Function140ae ; time-related + ld a, [wSpawnAfterChampion] + cp SPAWN_LANCE + jr z, .SpawnAfterE4 + ld a, MAPSETUP_CONTINUE + ld [hMapEntryMethod], a + jp FinishContinueFunction + +.FailToLoad: + ret + +.SpawnAfterE4: + ld a, SPAWN_NEW_BARK + ld [wDefaultSpawnpoint], a + call PostCreditsSpawn + jp FinishContinueFunction +; 5de2 + +SpawnAfterRed: ; 5de2 + ld a, SPAWN_MT_SILVER + ld [wDefaultSpawnpoint], a +; 5de7 + +PostCreditsSpawn: ; 5de7 + xor a + ld [wSpawnAfterChampion], a + ld a, MAPSETUP_WARP + ld [hMapEntryMethod], a + ret +; 5df0 + +Continue_MobileAdapterMenu: ; 5df0 + farcall Mobile_AlwaysReturnNotCarry ; mobile check + ret nc + +; the rest of this stuff is never reached because +; the previous function returns with carry not set + ld hl, wd479 + bit 1, [hl] + ret nz + ld a, 5 + ld [wMusicFade], a + ld a, LOW(MUSIC_MOBILE_ADAPTER_MENU) + ld [wMusicFadeID], a + ld a, HIGH(MUSIC_MOBILE_ADAPTER_MENU) + ld [wMusicFadeID + 1], a + ld c, 20 + call DelayFrames + ld c, $1 + farcall InitMobileProfile ; mobile + farcall _SaveData + ld a, 8 + ld [wMusicFade], a + ld a, LOW(MUSIC_NONE) + ld [wMusicFadeID], a + ld a, HIGH(MUSIC_NONE) + ld [wMusicFadeID + 1], a + ld c, 35 + call DelayFrames + ret +; 5e34 + +ConfirmContinue: ; 5e34 +.loop + call DelayFrame + call GetJoypad + ld hl, hJoyPressed + bit A_BUTTON_F, [hl] + jr nz, .PressA + bit B_BUTTON_F, [hl] + jr z, .loop + scf + ret + +.PressA: + ret +; 5e48 + +Continue_CheckRTC_RestartClock: ; 5e48 + call CheckRTCStatus + and %10000000 ; Day count exceeded 16383 + jr z, .pass + farcall RestartClock + ld a, c + and a + jr z, .pass + scf + ret + +.pass + xor a + ret +; 5e5d + +FinishContinueFunction: ; 5e5d +.loop + xor a + ld [wDontPlayMapMusicOnReload], a + ld [wLinkMode], a + ld hl, wGameTimerPause + set GAMETIMERPAUSE_TIMER_PAUSED_F, [hl] + res GAMETIMERPAUSE_MOBILE_7_F, [hl] + ld hl, wEnteredMapFromContinue + set 1, [hl] + farcall OverworldLoop + ld a, [wSpawnAfterChampion] + cp SPAWN_RED + jr z, .AfterRed + jp Reset + +.AfterRed: + call SpawnAfterRed + jr .loop +; 5e85 + +DisplaySaveInfoOnContinue: ; 5e85 + call CheckRTCStatus + and %10000000 + jr z, .clock_ok + lb de, 4, 8 + call DisplayContinueDataWithRTCError + ret + +.clock_ok + lb de, 4, 8 + call DisplayNormalContinueData + ret +; 5e9a + +DisplaySaveInfoOnSave: ; 5e9a + lb de, 4, 0 + jr DisplayNormalContinueData +; 5e9f + +DisplayNormalContinueData: ; 5e9f + call Continue_LoadMenuHeader + call Continue_DisplayBadgesDexPlayerName + call Continue_PrintGameTime + call LoadFontsExtra + call UpdateSprites + ret +; 5eaf + +DisplayContinueDataWithRTCError: ; 5eaf + call Continue_LoadMenuHeader + call Continue_DisplayBadgesDexPlayerName + call Continue_UnknownGameTime + call LoadFontsExtra + call UpdateSprites + ret +; 5ebf + +Continue_LoadMenuHeader: ; 5ebf + xor a + ld [hBGMapMode], a + ld hl, .MenuHeader_Dex + ld a, [wStatusFlags] + bit STATUSFLAGS_POKEDEX_F, a + jr nz, .show_menu + ld hl, .MenuHeader_NoDex + +.show_menu + call _OffsetMenuHeader + call MenuBox + call PlaceVerticalMenuItems + ret +; 5ed9 + +.MenuHeader_Dex: ; 5ed9 + db MENU_BACKUP_TILES ; flags + menu_coords 0, 0, 15, 9 + dw .MenuData_Dex + db 1 ; default option +; 5ee1 + +.MenuData_Dex: ; 5ee1 + db 0 ; flags + db 4 ; items + db "PLAYER@" + db "BADGES@" + db "#DEX@" + db "TIME@" +; 5efb + +.MenuHeader_NoDex: ; 5efb + db MENU_BACKUP_TILES ; flags + menu_coords 0, 0, 15, 9 + dw .MenuData_NoDex + db 1 ; default option +; 5f03 + +.MenuData_NoDex: ; 5f03 + db 0 ; flags + db 4 ; items + db "PLAYER <PLAYER>@" + db "BADGES@" + db " @" + db "TIME@" +; 5f1c + + +Continue_DisplayBadgesDexPlayerName: ; 5f1c + call MenuBoxCoord2Tile + push hl + decoord 13, 4, 0 + add hl, de + call Continue_DisplayBadgeCount + pop hl + push hl + decoord 12, 6, 0 + add hl, de + call Continue_DisplayPokedexNumCaught + pop hl + push hl + decoord 8, 2, 0 + add hl, de + ld de, .Player + call PlaceString + pop hl + ret + +.Player: + db "<PLAYER>@" +; 5f40 + +Continue_PrintGameTime: ; 5f40 + decoord 9, 8, 0 + add hl, de + call Continue_DisplayGameTime + ret +; 5f48 + +Continue_UnknownGameTime: ; 5f48 + decoord 9, 8, 0 + add hl, de + ld de, .three_question_marks + call PlaceString + ret + +.three_question_marks + db " ???@" +; 5f58 + +Continue_DisplayBadgeCount: ; 5f58 + push hl + ld hl, wJohtoBadges + ld b, 2 + call CountSetBits + pop hl + ld de, wd265 + lb bc, 1, 2 + jp PrintNum +; 5f6b + +Continue_DisplayPokedexNumCaught: ; 5f6b + ld a, [wStatusFlags] + bit STATUSFLAGS_POKEDEX_F, a + ret z + push hl + ld hl, wPokedexCaught +if NUM_POKEMON % 8 + ld b, NUM_POKEMON / 8 + 1 +else + ld b, NUM_POKEMON / 8 +endc + call CountSetBits + pop hl + ld de, wd265 + lb bc, 1, 3 + jp PrintNum +; 5f84 + +Continue_DisplayGameTime: ; 5f84 + ld de, wGameTimeHours + lb bc, 2, 3 + call PrintNum + ld [hl], "<COLON>" + inc hl + ld de, wGameTimeMinutes + lb bc, PRINTNUM_LEADINGZEROS | 1, 2 + jp PrintNum +; 5f99 + + +OakSpeech: ; 0x5f99 + farcall InitClock + call RotateFourPalettesLeft + call ClearTileMap + + ld de, MUSIC_ROUTE_30 + call PlayMusic + + call RotateFourPalettesRight + call RotateThreePalettesRight + xor a + ld [wCurPartySpecies], a + ld a, POKEMON_PROF + ld [wTrainerClass], a + call Intro_PrepTrainerPic + + ld b, SCGB_TRAINER_OR_MON_FRONTPIC_PALS + call GetSGBLayout + call Intro_RotatePalettesLeftFrontpic + + ld hl, OakText1 + call PrintText + call RotateThreePalettesRight + call ClearTileMap + + ld a, WOOPER + ld [wCurSpecies], a + ld [wCurPartySpecies], a + call GetBaseData + + hlcoord 6, 4 + call PrepMonFrontpic + + xor a + ld [wTempMonDVs], a + ld [wTempMonDVs + 1], a + + ld b, SCGB_TRAINER_OR_MON_FRONTPIC_PALS + call GetSGBLayout + call Intro_WipeInFrontpic + + ld hl, OakText2 + call PrintText + ld hl, OakText4 + call PrintText + call RotateThreePalettesRight + call ClearTileMap + + xor a + ld [wCurPartySpecies], a + ld a, POKEMON_PROF + ld [wTrainerClass], a + call Intro_PrepTrainerPic + + ld b, SCGB_TRAINER_OR_MON_FRONTPIC_PALS + call GetSGBLayout + call Intro_RotatePalettesLeftFrontpic + + ld hl, OakText5 + call PrintText + call RotateThreePalettesRight + call ClearTileMap + + xor a + ld [wCurPartySpecies], a + farcall DrawIntroPlayerPic + + ld b, SCGB_TRAINER_OR_MON_FRONTPIC_PALS + call GetSGBLayout + call Intro_RotatePalettesLeftFrontpic + + ld hl, OakText6 + call PrintText + call NamePlayer + ld hl, OakText7 + call PrintText + ret + +OakText1: ; 0x6045 + text_jump _OakText1 + db "@" + +OakText2: ; 0x604a + text_jump _OakText2 + start_asm + ld a, WOOPER + call PlayMonCry + call WaitSFX + ld hl, OakText3 + ret + +OakText3: ; 0x605b + text_jump _OakText3 + db "@" + +OakText4: ; 0x6060 + text_jump _OakText4 + db "@" + +OakText5: ; 0x6065 + text_jump _OakText5 + db "@" + +OakText6: ; 0x606a + text_jump _OakText6 + db "@" + +OakText7: ; 0x606f + text_jump _OakText7 + db "@" + +NamePlayer: ; 0x6074 + farcall MovePlayerPicRight + farcall ShowPlayerNamingChoices + ld a, [wMenuCursorY] + dec a + jr z, .NewName + call StorePlayerName + farcall ApplyMonOrTrainerPals + farcall MovePlayerPicLeft + ret + +.NewName: + ld b, 1 + ld de, wPlayerName + farcall NamingScreen + + call RotateThreePalettesRight + call ClearTileMap + + call LoadFontsExtra + call WaitBGMap + + xor a + ld [wCurPartySpecies], a + farcall DrawIntroPlayerPic + + ld b, SCGB_TRAINER_OR_MON_FRONTPIC_PALS + call GetSGBLayout + call RotateThreePalettesLeft + + ld hl, wPlayerName + ld de, .Chris + ld a, [wPlayerGender] + bit PLAYERGENDER_FEMALE_F, a + jr z, .Male + ld de, .Kris +.Male: + call InitName + ret + +.Chris: + db "CHRIS@@@@@@" +.Kris: + db "KRIS@@@@@@@" +; 60e9 + +Unreferenced_Function60e9: + call LoadMenuHeader + call VerticalMenu + ld a, [wMenuCursorY] + dec a + call CopyNameFromMenu + call CloseWindow + ret +; 60fa + +StorePlayerName: ; 60fa + ld a, "@" + ld bc, NAME_LENGTH + ld hl, wPlayerName + call ByteFill + ld hl, wPlayerName + ld de, wStringBuffer2 + call CopyName2 + ret +; 610f + +ShrinkPlayer: ; 610f + + ld a, [hROMBank] + push af + + ld a, 32 ; fade time + ld [wMusicFade], a + ld de, MUSIC_NONE + ld a, e + ld [wMusicFadeID], a + ld a, d + ld [wMusicFadeID + 1], a + + ld de, SFX_ESCAPE_ROPE + call PlaySFX + pop af + rst Bankswitch + + ld c, 8 + call DelayFrames + + ld hl, Shrink1Pic + ld b, BANK(Shrink1Pic) + call ShrinkFrame + + ld c, 8 + call DelayFrames + + ld hl, Shrink2Pic + ld b, BANK(Shrink2Pic) + call ShrinkFrame + + ld c, 8 + call DelayFrames + + hlcoord 6, 5 + ld b, 7 + ld c, 7 + call ClearBox + + ld c, 3 + call DelayFrames + + call Intro_PlacePlayerSprite + call LoadFontsExtra + + ld c, 50 + call DelayFrames + + call RotateThreePalettesRight + call ClearTileMap + ret +; 616a + +Intro_RotatePalettesLeftFrontpic: ; 616a + ld hl, IntroFadePalettes + ld b, IntroFadePalettes.End - IntroFadePalettes +.loop + ld a, [hli] + call DmgToCgbBGPals + ld c, 10 + call DelayFrames + dec b + jr nz, .loop + ret +; 617c + +IntroFadePalettes: ; 0x617c + db %01010100 + db %10101000 + db %11111100 + db %11111000 + db %11110100 + db %11100100 +.End +; 6182 + +Intro_WipeInFrontpic: ; 6182 + ld a, $77 + ld [hWX], a + call DelayFrame + ld a, %11100100 + call DmgToCgbBGPals +.loop + call DelayFrame + ld a, [hWX] + sub $8 + cp -1 + ret z + ld [hWX], a + jr .loop +; 619c + +Intro_PrepTrainerPic: ; 619c + ld de, vTiles2 + farcall GetTrainerPic + xor a + ld [hGraphicStartTile], a + hlcoord 6, 4 + lb bc, 7, 7 + predef PlaceGraphic + ret +; 61b4 + +ShrinkFrame: ; 61b4 + ld de, vTiles2 + ld c, 7 * 7 + predef DecompressGet2bpp + xor a + ld [hGraphicStartTile], a + hlcoord 6, 4 + lb bc, 7, 7 + predef PlaceGraphic + ret +; 61cd + +Intro_PlacePlayerSprite: ; 61cd + + farcall GetPlayerIcon + ld c, $c + ld hl, vTiles0 + call Request2bpp + + ld hl, wVirtualOAMSprite00 + ld de, .sprites + ld a, [de] + inc de + + ld c, a +.loop + ld a, [de] + inc de + ld [hli], a ; y + ld a, [de] + inc de + ld [hli], a ; x + ld a, [de] + inc de + ld [hli], a ; tile id + + ld b, PAL_OW_RED + ld a, [wPlayerGender] + bit PLAYERGENDER_FEMALE_F, a + jr z, .male + ld b, PAL_OW_BLUE +.male + ld a, b + + ld [hli], a + dec c + jr nz, .loop + ret +; 61fe + +.sprites ; 61fe + db 4 + ; y pxl, x pxl, tile offset + db 9 * 8 + 4, 9 * 8, 0 + db 9 * 8 + 4, 10 * 8, 1 + db 10 * 8 + 4, 9 * 8, 2 + db 10 * 8 + 4, 10 * 8, 3 +; 620b + + +CrystalIntroSequence: ; 620b + callfar Copyright_GFPresents + jr c, StartTitleScreen + farcall CrystalIntro + +StartTitleScreen: ; 6219 + ld a, [rSVBK] + push af + ld a, BANK(wBGPals1) + ld [rSVBK], a + + call .TitleScreen + call DelayFrame +.loop + call RunTitleScreen + jr nc, .loop + + call ClearSprites + call ClearBGPalettes + + pop af + ld [rSVBK], a + + ld hl, rLCDC + res rLCDC_SPRITE_SIZE, [hl] ; 8x8 + call ClearScreen + call WaitBGMap2 + xor a + ld [hLCDCPointer], a + ld [hSCX], a + ld [hSCY], a + ld a, $7 + ld [hWX], a + ld a, $90 + ld [hWY], a + ld b, SCGB_DIPLOMA + call GetSGBLayout + call UpdateTimePals + ld a, [wIntroSceneFrameCounter] + cp $5 + jr c, .ok + xor a +.ok + ld e, a + ld d, 0 + ld hl, .dw + add hl, de + add hl, de + ld a, [hli] + ld h, [hl] + ld l, a + jp hl +; 626a + +.dw + dw _MainMenu + dw DeleteSaveData + dw CrystalIntroSequence + dw CrystalIntroSequence + dw ResetClock +; 6274 + + +.TitleScreen: ; 6274 + farcall _TitleScreen + ret +; 627b + +RunTitleScreen: ; 627b + ld a, [wJumptableIndex] + bit 7, a + jr nz, .done_title + call TitleScreenScene + farcall SuicuneFrameIterator + call DelayFrame + and a + ret + +.done_title + scf + ret +; 6292 + +Unreferenced_Function6292: ; 6292 + ld a, [hVBlankCounter] + and $7 + ret nz + ld hl, wLYOverrides + $5f + ld a, [hl] + dec a + ld bc, 2 * SCREEN_WIDTH + call ByteFill + ret +; 62a3 + +TitleScreenScene: ; 62a3 + ld e, a + ld d, 0 + ld hl, .scenes + add hl, de + add hl, de + ld a, [hli] + ld h, [hl] + ld l, a + jp hl +; 62af + +.scenes + dw TitleScreenEntrance + dw TitleScreenTimer + dw TitleScreenMain + dw TitleScreenEnd +; 62b7 + +.Unreferenced_NextScene: + ld hl, wJumptableIndex + inc [hl] + ret +; 62bc + + +TitleScreenEntrance: ; 62bc + +; Animate the logo: +; Move each line by 4 pixels until our count hits 0. + ld a, [hSCX] + and a + jr z, .done + sub 4 + ld [hSCX], a + +; Lay out a base (all lines scrolling together). + ld e, a + ld hl, wLYOverrides + ld bc, 8 * 10 ; logo height + call ByteFill + +; Reversed signage for every other line's position. +; This is responsible for the interlaced effect. + ld a, e + xor $ff + inc a + + ld b, 8 * 10 / 2 ; logo height / 2 + ld hl, wLYOverrides + 1 +.loop + ld [hli], a + inc hl + dec b + jr nz, .loop + + farcall AnimateTitleCrystal + ret + +.done +; Next scene + ld hl, wJumptableIndex + inc [hl] + xor a + ld [hLCDCPointer], a + +; Play the title screen music. + ld de, MUSIC_TITLE + call PlayMusic + + ld a, $88 + ld [hWY], a + ret +; 62f6 + + +TitleScreenTimer: ; 62f6 + +; Next scene + ld hl, wJumptableIndex + inc [hl] + +; Start a timer + ld hl, wTitleScreenTimer + ld de, 73 * 60 + 36 + ld [hl], e + inc hl + ld [hl], d + ret +; 6304 + +TitleScreenMain: ; 6304 + +; Run the timer down. + ld hl, wTitleScreenTimer + ld e, [hl] + inc hl + ld d, [hl] + ld a, e + or d + jr z, .end + + dec de + ld [hl], d + dec hl + ld [hl], e + +; Save data can be deleted by pressing Up + B + Select. + call GetJoypad + ld hl, hJoyDown + ld a, [hl] + and D_UP + B_BUTTON + SELECT + cp D_UP + B_BUTTON + SELECT + jr z, .delete_save_data + +; To bring up the clock reset dialog: + +; Hold Down + B + Select to initiate the sequence. + ld a, [hClockResetTrigger] + cp $34 + jr z, .check_clock_reset + + ld a, [hl] + and D_DOWN + B_BUTTON + SELECT + cp D_DOWN + B_BUTTON + SELECT + jr nz, .check_start + + ld a, $34 + ld [hClockResetTrigger], a + jr .check_start + +; Keep Select pressed, and hold Left + Up. +; Then let go of Select. +.check_clock_reset + bit SELECT_F, [hl] + jr nz, .check_start + + xor a + ld [hClockResetTrigger], a + + ld a, [hl] + and D_LEFT + D_UP + cp D_LEFT + D_UP + jr z, .clock_reset + +; Press Start or A to start the game. +.check_start + ld a, [hl] + and START | A_BUTTON + jr nz, .incave + ret + +.incave + ld a, 0 + jr .done + +.delete_save_data + ld a, 1 + +.done + ld [wIntroSceneFrameCounter], a + +; Return to the intro sequence. + ld hl, wJumptableIndex + set 7, [hl] + ret + +.end +; Next scene + ld hl, wJumptableIndex + inc [hl] + +; Fade out the title screen music + xor a + ld [wMusicFadeID], a + ld [wMusicFadeID + 1], a + ld hl, wMusicFade + ld [hl], 8 ; 1 second + + ld hl, wTitleScreenTimer + inc [hl] + ret + +.clock_reset + ld a, 4 + ld [wIntroSceneFrameCounter], a + +; Return to the intro sequence. + ld hl, wJumptableIndex + set 7, [hl] + ret +; 6375 + +TitleScreenEnd: ; 6375 + +; Wait until the music is done fading. + + ld hl, wTitleScreenTimer + inc [hl] + + ld a, [wMusicFade] + and a + ret nz + + ld a, 2 + ld [wIntroSceneFrameCounter], a + +; Back to the intro. + ld hl, wJumptableIndex + set 7, [hl] + ret +; 6389 + +DeleteSaveData: ; 6389 + farcall _DeleteSaveData + jp Init +; 6392 + +ResetClock: ; 6392 + farcall _ResetClock + jp Init +; 639b + +Unreferenced_Function639b: + ; If bit 0 or 1 of [wTitleScreenTimer] is set, we don't need to be here. + ld a, [wTitleScreenTimer] + and %00000011 + ret nz + ld bc, wSpriteAnim10 + ld hl, SPRITEANIMSTRUCT_FRAME + add hl, bc ; over-the-top compicated way to load wc3ae into hl + ld l, [hl] + ld h, 0 + add hl, hl + add hl, hl + ld de, .Data63ca + add hl, de + ; If bit 2 of [wTitleScreenTimer] is set, get the second dw; else, get the first dw + ld a, [wTitleScreenTimer] + and %00000100 + srl a + srl a + ld e, a + ld d, 0 + add hl, de + add hl, de + ld a, [hli] + and a + ret z + ld e, a + ld d, [hl] + ld a, SPRITE_ANIM_INDEX_GS_TITLE_TRAIL + call _InitSpriteAnimStruct + ret +; 63ca + +.Data63ca: ; 63ca +; frame 0 y, x; frame 1 y, x + db 11 * 8 + 4, 10 * 8, 0 * 8, 0 * 8 + db 11 * 8 + 4, 13 * 8, 11 * 8 + 4, 11 * 8 + db 11 * 8 + 4, 13 * 8, 11 * 8 + 4, 15 * 8 + db 11 * 8 + 4, 17 * 8, 11 * 8 + 4, 15 * 8 + db 0 * 8, 0 * 8, 11 * 8 + 4, 15 * 8 + db 0 * 8, 0 * 8, 11 * 8 + 4, 11 * 8 +; 63e2 + +Copyright: ; 63e2 + call ClearTileMap + call LoadFontsExtra + ld de, CopyrightGFX + ld hl, vTiles2 tile $60 + lb bc, BANK(CopyrightGFX), 29 + call Request2bpp + hlcoord 2, 7 + ld de, CopyrightString + jp PlaceString +; 63fd + +CopyrightString: ; 63fd + ; ©1995-2001 Nintendo + db $60, $61, $62, $63, $64, $65, $66 + db $67, $68, $69, $6a, $6b, $6c + + ; ©1995-2001 Creatures inc. + next $60, $61, $62, $63, $64, $65, $66 + db $6d, $6e, $6f, $70, $71, $72, $7a, $7b, $7c + + ; ©1995-2001 GAME FREAK inc. + next $60, $61, $62, $63, $64, $65, $66 + db $73, $74, $75, $76, $77, $78, $79, $7a, $7b, $7c + + db "@" +; 642e + +GameInit:: ; 642e + farcall TryLoadSaveData + call ClearWindowData + call ClearBGPalettes + call ClearTileMap + ld a, HIGH(vBGMap0) + ld [hBGMapAddress + 1], a + xor a ; LOW(vBGMap0) + ld [hBGMapAddress], a + ld [hJoyDown], a + ld [hSCX], a + ld [hSCY], a + ld a, $90 + ld [hWY], a + call WaitBGMap + jp CrystalIntroSequence +; 6454 diff --git a/engine/menus/main_menu.asm b/engine/menus/main_menu.asm new file mode 100644 index 000000000..d83ce873b --- /dev/null +++ b/engine/menus/main_menu.asm @@ -0,0 +1,361 @@ +GFX_49c0c: ; 49c0c +INCBIN "gfx/unknown/049c0c.2bpp" +; 49cdc + +MainMenu: ; 49cdc + xor a + ld [wDisableTextAcceleration], a + call Function49ed0 + ld b, SCGB_DIPLOMA + call GetSGBLayout + call SetPalettes + ld hl, wGameTimerPause + res GAMETIMERPAUSE_TIMER_PAUSED_F, [hl] + call MainMenu_GetWhichMenu + ld [wWhichIndexSet], a + call MainMenu_PrintCurrentTimeAndDay + ld hl, .MenuHeader + call LoadMenuHeader + call MainMenuJoypadLoop + call CloseWindow + jr c, .quit + call ClearTileMap + ld a, [wMenuSelection] + ld hl, .Jumptable + rst JumpTable + jr MainMenu + +.quit + ret +; 49d14 + +.MenuHeader: ; 49d14 + db MENU_BACKUP_TILES ; flags + menu_coords 0, 0, 16, 7 + dw .MenuData + db 1 ; default option +; 49d1c + +.MenuData: ; 49d1c + db STATICMENU_CURSOR ; flags + db 0 ; items + dw MainMenuItems + dw PlaceMenuStrings + dw .Strings +; 49d20 + +.Strings: ; 49d24 + db "CONTINUE@" + db "NEW GAME@" + db "OPTION@" + db "MYSTERY GIFT@" + db "MOBILE@" + db "MOBILE STUDIUM@" + +.Jumptable: ; 0x49d60 + dw MainMenu_Continue + dw MainMenu_NewGame + dw MainMenu_Options + dw MainMenu_MysteryGift + dw MainMenu_Mobile + dw MainMenu_MobileStudium +; 0x49d6c + +CONTINUE EQU 0 +NEW_GAME EQU 1 +OPTION EQU 2 +MYSTERY_GIFT EQU 3 +MOBILE EQU 4 +MOBILE_STUDIUM EQU 5 + +MainMenuItems: + +NewGameMenu: ; 0x49d6c + db 2 + db NEW_GAME + db OPTION + db -1 + +ContinueMenu: ; 0x49d70 + db 3 + db CONTINUE + db NEW_GAME + db OPTION + db -1 + +MobileMysteryMenu: ; 0x49d75 + db 5 + db CONTINUE + db NEW_GAME + db OPTION + db MYSTERY_GIFT + db MOBILE + db -1 + +MobileMenu: ; 0x49d7c + db 4 + db CONTINUE + db NEW_GAME + db OPTION + db MOBILE + db -1 + +MobileStudiumMenu: ; 0x49d82 + db 5 + db CONTINUE + db NEW_GAME + db OPTION + db MOBILE + db MOBILE_STUDIUM + db -1 + +MysteryMobileStudiumMenu: ; 0x49d89 + db 6 + db CONTINUE + db NEW_GAME + db OPTION + db MYSTERY_GIFT + db MOBILE + db MOBILE_STUDIUM + db -1 + +MysteryMenu: ; 0x49d91 + db 4 + db CONTINUE + db NEW_GAME + db OPTION + db MYSTERY_GIFT + db -1 + +MysteryStudiumMenu: ; 0x49d97 + db 5 + db CONTINUE + db NEW_GAME + db OPTION + db MYSTERY_GIFT + db MOBILE_STUDIUM + db -1 + +StudiumMenu: ; 0x49d9e + db 4 + db CONTINUE + db NEW_GAME + db OPTION + db MOBILE_STUDIUM + db -1 + + +MainMenu_GetWhichMenu: ; 49da4 + nop + nop + nop + ld a, [wSaveFileExists] + and a + jr nz, .next + ld a, $0 ; New Game + ret + +.next + ld a, [hCGB] + cp $1 + ld a, $1 + ret nz + ld a, BANK(sNumDailyMysteryGiftPartnerIDs) + call GetSRAMBank + ld a, [sNumDailyMysteryGiftPartnerIDs] + cp -1 + call CloseSRAM + jr nz, .mystery_gift + ; This check makes no difference. + ld a, [wStatusFlags] + bit STATUSFLAGS_MAIN_MENU_MOBILE_CHOICES_F, a + ld a, $1 ; Continue + jr z, .ok + jr .ok + +.ok + jr .ok2 + +.ok2 + ld a, $1 ; Continue + ret + +.mystery_gift + ; This check makes no difference. + ld a, [wStatusFlags] + bit STATUSFLAGS_MAIN_MENU_MOBILE_CHOICES_F, a + jr z, .ok3 + jr .ok3 + +.ok3 + jr .ok4 + +.ok4 + ld a, $6 ; Mystery Gift + ret +; 49de4 + +MainMenuJoypadLoop: ; 49de4 + call SetUpMenu +.loop + call MainMenu_PrintCurrentTimeAndDay + ld a, [w2DMenuFlags1] + set 5, a + ld [w2DMenuFlags1], a + call GetScrollingMenuJoypad + ld a, [wMenuJoypad] + cp B_BUTTON + jr z, .b_button + cp A_BUTTON + jr z, .a_button + jr .loop + +.a_button + call PlayClickSFX + and a + ret + +.b_button + scf + ret +; 49e09 + +MainMenu_PrintCurrentTimeAndDay: ; 49e09 + ld a, [wSaveFileExists] + and a + ret z + xor a + ld [hBGMapMode], a + call .PlaceBox + ld hl, wOptions + ld a, [hl] + push af + set NO_TEXT_SCROLL, [hl] + call .PlaceTime + pop af + ld [wOptions], a + ld a, $1 + ld [hBGMapMode], a + ret +; 49e27 + + +.PlaceBox: ; 49e27 + call CheckRTCStatus + and $80 + jr nz, .TimeFail + hlcoord 0, 14 + ld b, 2 + ld c, 18 + call TextBox + ret + +.TimeFail: + call SpeechTextBox + ret +; 49e3d + + +.PlaceTime: ; 49e3d + ld a, [wSaveFileExists] + and a + ret z + call CheckRTCStatus + and $80 + jp nz, .PrintTimeNotSet + call UpdateTime + call GetWeekday + ld b, a + decoord 1, 15 + call .PlaceCurrentDay + decoord 4, 16 + ld a, [hHours] + ld c, a + farcall PrintHour + ld [hl], ":" + inc hl + ld de, hMinutes + lb bc, PRINTNUM_LEADINGZEROS | 1, 2 + call PrintNum + ret + +.min +; unused + db "min.@" +; 49e75 + +.PrintTimeNotSet: ; 49e75 + hlcoord 1, 14 + ld de, .TimeNotSet + call PlaceString + ret +; 49e7f + +.TimeNotSet: ; 49e7f + db "TIME NOT SET@" +; 49e8c + +.UnusedText: ; 49e8c + ; Clock time unknown + text_jump UnknownText_0x1c5182 + db "@" +; 49e91 + +.PlaceCurrentDay: ; 49e91 + push de + ld hl, .Days + ld a, b + call GetNthString + ld d, h + ld e, l + pop hl + call PlaceString + ld h, b + ld l, c + ld de, .Day + call PlaceString + ret +; 49ea8 + +.Days: + db "SUN@" + db "MON@" + db "TUES@" + db "WEDNES@" + db "THURS@" + db "FRI@" + db "SATUR@" +.Day: + db "DAY@" +; 49ed0 + +Function49ed0: ; 49ed0 + xor a + ld [hMapAnims], a + call ClearTileMap + call LoadFontsExtra + call LoadStandardFont + call ClearWindowData + ret +; 49ee0 + + +MainMenu_NewGame: ; 49ee0 + farcall NewGame + ret +; 49ee7 + +MainMenu_Options: ; 49ee7 + farcall OptionsMenu + ret +; 49eee + +MainMenu_Continue: ; 49eee + farcall Continue + ret +; 49ef5 + +MainMenu_MysteryGift: ; 49ef5 + farcall MysteryGift + ret +; 49efc diff --git a/engine/menus/menu.asm b/engine/menus/menu.asm new file mode 100644 index 000000000..51de2e1a4 --- /dev/null +++ b/engine/menus/menu.asm @@ -0,0 +1,841 @@ +_2DMenu_:: ; 2400e + ld hl, CopyMenuData + ld a, [wMenuData_2DMenuItemStringsBank] + rst FarCall + + call Draw2DMenu + call UpdateSprites + call ApplyTilemap + call Get2DMenuSelection + ret +; 24022 + +_InterpretBattleMenu:: ; 24022 + ld hl, CopyMenuData + ld a, [wMenuData_2DMenuItemStringsBank] + rst FarCall + + call Draw2DMenu + farcall MobileTextBorder + call UpdateSprites + call ApplyTilemap + call Get2DMenuSelection + ret +; 2403c + +_InterpretMobileMenu:: ; 2403c + ld hl, CopyMenuData + ld a, [wMenuData_2DMenuItemStringsBank] + rst FarCall + + call Draw2DMenu + farcall MobileTextBorder + call UpdateSprites + call ApplyTilemap + call Init2DMenuCursorPosition + ld hl, w2DMenuFlags1 + set 7, [hl] +.loop + call DelayFrame + farcall Function10032e + ld a, [wcd2b] + and a + jr nz, .quit + call MobileMenuJoypad + ld a, [wMenuJoypadFilter] + and c + jr z, .loop + call Mobile_GetMenuSelection + ret + +.quit + ld a, [w2DMenuNumCols] + ld c, a + ld a, [w2DMenuNumRows] + call SimpleMultiply + ld [wMenuCursorBuffer], a + and a + ret +; 24085 + + + +Draw2DMenu: ; 24085 + xor a + ld [hBGMapMode], a + call MenuBox + call Place2DMenuItemStrings + ret +; 2408f + +Get2DMenuSelection: ; 2408f + call Init2DMenuCursorPosition + call StaticMenuJoypad + call MenuClickSound +Mobile_GetMenuSelection: ; 24098 + ld a, [wMenuDataFlags] + bit 1, a + jr z, .skip + call GetMenuJoypad + bit SELECT_F, a + jr nz, .quit1 + +.skip + ld a, [wMenuDataFlags] + bit 0, a + jr nz, .skip2 + call GetMenuJoypad + bit B_BUTTON_F, a + jr nz, .quit2 + +.skip2 + ld a, [w2DMenuNumCols] + ld c, a + ld a, [wMenuCursorY] + dec a + call SimpleMultiply + ld c, a + ld a, [wMenuCursorX] + add c + ld [wMenuCursorBuffer], a + and a + ret + +.quit1 + scf + ret + +.quit2 + scf + ret +; 240cd + +Get2DMenuNumberOfColumns: ; 240cd + ld a, [wMenuData_2DMenuDimensions] + and $f + ret +; 240d3 + +Get2DMenuNumberOfRows: ; 240d3 + ld a, [wMenuData_2DMenuDimensions] + swap a + and $f + ret +; 240db + +Place2DMenuItemStrings: ; 240db + ld hl, wMenuData_2DMenuItemStringsAddr + ld e, [hl] + inc hl + ld d, [hl] + call GetMenuTextStartCoord + call Coord2Tile + call Get2DMenuNumberOfRows + ld b, a +.row + push bc + push hl + call Get2DMenuNumberOfColumns + ld c, a +.col + push bc + ld a, [wMenuData_2DMenuItemStringsBank] + call Place2DMenuItemName + inc de + ld a, [wMenuData_2DMenuSpacing] + ld c, a + ld b, 0 + add hl, bc + pop bc + dec c + jr nz, .col + pop hl + ld bc, 2 * SCREEN_WIDTH + add hl, bc + pop bc + dec b + jr nz, .row + ld hl, wMenuData_2DMenuFunctionAddr + ld a, [hli] + ld h, [hl] + ld l, a + or h + ret z + ld a, [wMenuData_2DMenuFunctionBank] + rst FarCall + ret +; 2411a + + +Init2DMenuCursorPosition: ; 2411a (9:411a) + call GetMenuTextStartCoord + ld a, b + ld [w2DMenuCursorInitY], a + dec c + ld a, c + ld [w2DMenuCursorInitX], a + call Get2DMenuNumberOfRows + ld [w2DMenuNumRows], a + call Get2DMenuNumberOfColumns + ld [w2DMenuNumCols], a + call .InitFlags_a + call .InitFlags_b + call .InitFlags_c + ld a, [w2DMenuNumCols] + ld e, a + ld a, [wMenuCursorBuffer] + ld b, a + xor a + ld d, 0 +.loop + inc d + add e + cp b + jr c, .loop + sub e + ld c, a + ld a, b + sub c + and a + jr z, .reset1 + cp e + jr z, .okay1 + jr c, .okay1 +.reset1 + ld a, 1 +.okay1 + ld [wMenuCursorX], a + ld a, [w2DMenuNumRows] + ld e, a + ld a, d + and a + jr z, .reset2 + cp e + jr z, .okay2 + jr c, .okay2 +.reset2 + ld a, 1 +.okay2 + ld [wMenuCursorY], a + xor a + ld [wCursorOffCharacter], a + ld [wCursorCurrentTile], a + ld [wCursorCurrentTile + 1], a + ret +; 24179 + +.InitFlags_a: ; 24179 + xor a + ld hl, w2DMenuFlags1 + ld [hli], a + ld [hld], a + ld a, [wMenuDataFlags] + bit 5, a + ret z + set 5, [hl] + set 4, [hl] + ret +; 2418a + +.InitFlags_b: ; 2418a + ld a, [wMenuData_2DMenuSpacing] + or $20 + ld [w2DMenuCursorOffsets], a + ret +; 24193 + +.InitFlags_c: ; 24193 + ld hl, wMenuDataFlags + ld a, A_BUTTON + bit 0, [hl] + jr nz, .skip + or B_BUTTON +.skip + bit 1, [hl] + jr z, .skip2 + or SELECT +.skip2 + ld [wMenuJoypadFilter], a + ret +; 241a8 + + +_StaticMenuJoypad:: ; 241a8 + call Place2DMenuCursor +_ScrollingMenuJoypad:: ; 241ab + ld hl, w2DMenuFlags2 + res 7, [hl] + ld a, [hBGMapMode] + push af + call MenuJoypadLoop + pop af + ld [hBGMapMode], a + ret +; 241ba + +MobileMenuJoypad: ; 241ba + ld hl, w2DMenuFlags2 + res 7, [hl] + ld a, [hBGMapMode] + push af + call Move2DMenuCursor + call Do2DMenuRTCJoypad + jr nc, .skip_joypad + call _2DMenuInterpretJoypad +.skip_joypad + pop af + ld [hBGMapMode], a + call GetMenuJoypad + ld c, a + ret +; 241d5 + + +Unreferenced_Function241d5: ; 241d5 + call Place2DMenuCursor +.loop + call Move2DMenuCursor + call HDMATransferTileMapToWRAMBank3 ; BUG: This function is in another bank. + ; Pointer in current bank (9) is bogus. + call .loop2 + jr nc, .done + call _2DMenuInterpretJoypad + jr c, .done + ld a, [w2DMenuFlags1] + bit 7, a + jr nz, .done + call GetMenuJoypad + ld c, a + ld a, [wMenuJoypadFilter] + and c + jr z, .loop + +.done + ret + +.loop2 + call Menu_WasButtonPressed + ret c + ld c, 1 + ld b, 3 + call AdvanceMobileInactivityTimerAndCheckExpired ; BUG: This function is in another bank. + ; Pointer in current bank (9) is bogus. + ret c + farcall Function100337 + ret c + ld a, [w2DMenuFlags1] + bit 7, a + jr z, .loop2 + and a + ret +; 24216 + + +MenuJoypadLoop: ; 24216 +.loop + call Move2DMenuCursor + call .BGMap_OAM + call Do2DMenuRTCJoypad + jr nc, .done + call _2DMenuInterpretJoypad + jr c, .done + ld a, [w2DMenuFlags1] + bit 7, a + jr nz, .done + call GetMenuJoypad + ld b, a + ld a, [wMenuJoypadFilter] + and b + jr z, .loop + +.done + ret +; 24238 + +.BGMap_OAM: ; 24238 + ld a, [hOAMUpdate] + push af + ld a, $1 + ld [hOAMUpdate], a + call WaitBGMap + pop af + ld [hOAMUpdate], a + xor a + ld [hBGMapMode], a + ret +; 24249 + +Do2DMenuRTCJoypad: ; 24249 +.loopRTC + call RTC + call Menu_WasButtonPressed + ret c + ld a, [w2DMenuFlags1] + bit 7, a + jr z, .loopRTC + and a + ret +; 24259 + +Menu_WasButtonPressed: ; 24259 + ld a, [w2DMenuFlags1] + bit 6, a + jr z, .skip_to_joypad + callfar PlaySpriteAnimationsAndDelayFrame + +.skip_to_joypad + call JoyTextDelay + call GetMenuJoypad + and a + ret z + scf + ret +; 24270 + +_2DMenuInterpretJoypad: ; 24270 + call GetMenuJoypad + bit A_BUTTON_F, a + jp nz, .a_b_start_select + bit B_BUTTON_F, a + jp nz, .a_b_start_select + bit SELECT_F, a + jp nz, .a_b_start_select + bit START_F, a + jp nz, .a_b_start_select + bit D_RIGHT_F, a + jr nz, .d_right + bit D_LEFT_F, a + jr nz, .d_left + bit D_UP_F, a + jr nz, .d_up + bit D_DOWN_F, a + jr nz, .d_down + and a + ret + +.set_bit_7 ; 24299 + ld hl, w2DMenuFlags2 + set 7, [hl] + scf + ret + +.d_down + ld hl, wMenuCursorY + ld a, [w2DMenuNumRows] + cp [hl] + jr z, .check_wrap_around_down + inc [hl] + xor a + ret + +.check_wrap_around_down + ld a, [w2DMenuFlags1] + bit 5, a + jr nz, .wrap_around_down + bit 3, a + jp nz, .set_bit_7 + xor a + ret + +.wrap_around_down + ld [hl], $1 + xor a + ret + +.d_up + ld hl, wMenuCursorY + ld a, [hl] + dec a + jr z, .check_wrap_around_up + ld [hl], a + xor a + ret + +.check_wrap_around_up + ld a, [w2DMenuFlags1] + bit 5, a + jr nz, .wrap_around_up + bit 2, a + jp nz, .set_bit_7 + xor a + ret + +.wrap_around_up + ld a, [w2DMenuNumRows] + ld [hl], a + xor a + ret + +.d_left + ld hl, wMenuCursorX + ld a, [hl] + dec a + jr z, .check_wrap_around_left + ld [hl], a + xor a + ret + +.check_wrap_around_left + ld a, [w2DMenuFlags1] + bit 4, a + jr nz, .wrap_around_left + bit 1, a + jp nz, .set_bit_7 + xor a + ret + +.wrap_around_left + ld a, [w2DMenuNumCols] + ld [hl], a + xor a + ret + +.d_right + ld hl, wMenuCursorX + ld a, [w2DMenuNumCols] + cp [hl] + jr z, .check_wrap_around_right + inc [hl] + xor a + ret + +.check_wrap_around_right + ld a, [w2DMenuFlags1] + bit 4, a + jr nz, .wrap_around_right + bit 0, a + jp nz, .set_bit_7 + xor a + ret + +.wrap_around_right + ld [hl], $1 + xor a + ret +; 24318 + +.a_b_start_select ; 24318 + xor a + ret +; 2431a + +Move2DMenuCursor: ; 2431a + ld hl, wCursorCurrentTile + ld a, [hli] + ld h, [hl] + ld l, a + ld a, [hl] + cp "▶" + jr nz, Place2DMenuCursor + ld a, [wCursorOffCharacter] + ld [hl], a +Place2DMenuCursor: ; 24329 + ld a, [w2DMenuCursorInitY] + ld b, a + ld a, [w2DMenuCursorInitX] + ld c, a + call Coord2Tile + ld a, [w2DMenuCursorOffsets] + swap a + and $f + ld c, a + ld a, [wMenuCursorY] + ld b, a + xor a + dec b + jr z, .got_row +.row_loop + add c + dec b + jr nz, .row_loop + +.got_row + ld c, SCREEN_WIDTH + call AddNTimes + ld a, [w2DMenuCursorOffsets] + and $f + ld c, a + ld a, [wMenuCursorX] + ld b, a + xor a + dec b + jr z, .got_col +.col_loop + add c + dec b + jr nz, .col_loop + +.got_col + ld c, a + add hl, bc + ld a, [hl] + cp "▶" + jr z, .cursor_on + ld [wCursorOffCharacter], a + ld [hl], "▶" + +.cursor_on + ld a, l + ld [wCursorCurrentTile], a + ld a, h + ld [wCursorCurrentTile + 1], a + ret +; 24374 + +_PushWindow:: ; 24374 + ld a, [rSVBK] + push af + ld a, BANK(wWindowStack) + ld [rSVBK], a + + ld hl, wWindowStackPointer + ld e, [hl] + inc hl + ld d, [hl] + push de + + ld b, $10 + ld hl, wMenuFlags +.loop + ld a, [hli] + ld [de], a + dec de + dec b + jr nz, .loop + +; If bit 6 or 7 of the menu flags is set, set bit 0 of the address +; at 7:[wWindowStackPointer], and draw the menu using the coordinates from the header. +; Otherwise, reset bit 0 of 7:[wWindowStackPointer]. + ld a, [wMenuFlags] + bit 6, a + jr nz, .bit_6 + bit 7, a + jr z, .not_bit_7 + +.bit_6 + ld hl, wWindowStackPointer + ld a, [hli] + ld h, [hl] + ld l, a + set 0, [hl] + call MenuBoxCoord2Tile + call .copy + call MenuBoxCoord2Attr + call .copy + jr .done + +.not_bit_7 + pop hl ; last-pushed register was de + push hl + ld a, [hld] + ld l, [hl] + ld h, a + res 0, [hl] + +.done + pop hl + call .ret ; empty function + ld a, h + ld [de], a + dec de + ld a, l + ld [de], a + dec de + ld hl, wWindowStackPointer + ld [hl], e + inc hl + ld [hl], d + + pop af + ld [rSVBK], a + ld hl, wWindowStackSize + inc [hl] + ret +; 243cd + +.copy ; 243cd + call GetMenuBoxDims + inc b + inc c + call .ret ; empty function + +.row + push bc + push hl + +.col + ld a, [hli] + ld [de], a + dec de + dec c + jr nz, .col + + pop hl + ld bc, SCREEN_WIDTH + add hl, bc + pop bc + dec b + jr nz, .row + + ret +; 243e7 + +.ret ; 243e7 + ret +; 243e8 + +_ExitMenu:: ; 243e8 + xor a + ld [hBGMapMode], a + + ld a, [rSVBK] + push af + ld a, BANK(wWindowStack) + ld [rSVBK], a + + call GetWindowStackTop + ld a, l + or h + jp z, Error_Cant_ExitMenu + ld a, l + ld [wWindowStackPointer], a + ld a, h + ld [wWindowStackPointer + 1], a + call PopWindow + ld a, [wMenuFlags] + bit 0, a + jr z, .loop + ld d, h + ld e, l + call RestoreTileBackup + +.loop + call GetWindowStackTop + ld a, h + or l + jr z, .done + call PopWindow + +.done + pop af + ld [rSVBK], a + ld hl, wWindowStackSize + dec [hl] + ret +; 24423 + +Unreferenced_Function24423: ; 24423 + ld a, [wVramState] + bit 0, a + ret z + xor a ; sScratch + call GetSRAMBank + hlcoord 0, 0 + ld de, sScratch + ld bc, SCREEN_WIDTH * SCREEN_HEIGHT + call CopyBytes + call CloseSRAM + call OverworldTextModeSwitch + xor a ; sScratch + call GetSRAMBank + ld hl, sScratch + decoord 0, 0 + ld bc, SCREEN_WIDTH * SCREEN_HEIGHT +.loop + ld a, [hl] + cp $61 + jr c, .next + ld [de], a +.next + inc hl + inc de + dec bc + ld a, c + or b + jr nz, .loop + call CloseSRAM + ret +; 2445d + +Error_Cant_ExitMenu: ; 2445d + ld hl, .Text_NoWindowsAvailableForPopping + call PrintText + call WaitBGMap +.InfiniteLoop: + jr .InfiniteLoop +; 24468 + +.Text_NoWindowsAvailableForPopping: ; 24468 + text_jump UnknownText_0x1c46b7 + db "@" +; 2446d + +_InitVerticalMenuCursor:: ; 2446d + ld a, [wMenuDataFlags] + ld b, a + ld hl, w2DMenuCursorInitY + ld a, [wMenuBorderTopCoord] + inc a + bit 6, b + jr nz, .skip_offset + inc a +.skip_offset + ld [hli], a +; w2DMenuCursorInitX + ld a, [wMenuBorderLeftCoord] + inc a + ld [hli], a +; w2DMenuNumRows + ld a, [wMenuDataItems] + ld [hli], a +; w2DMenuNumCols + ld a, 1 + ld [hli], a +; w2DMenuFlags1 + ld [hl], $0 + bit 5, b + jr z, .skip_bit_5 + set 5, [hl] +.skip_bit_5 + ld a, [wMenuFlags] + bit 4, a + jr z, .skip_bit_6 + set 6, [hl] +.skip_bit_6 + inc hl +; w2DMenuFlags2 + xor a + ld [hli], a +; w2DMenuCursorOffsets + ln a, 2, 0 + ld [hli], a +; wMenuJoypadFilter + ld a, A_BUTTON + bit 0, b + jr nz, .skip_bit_1 + add B_BUTTON +.skip_bit_1 + ld [hli], a +; wMenuCursorY + ld a, [wMenuCursorBuffer] + and a + jr z, .load_at_the_top + ld c, a + ld a, [wMenuDataItems] + cp c + jr nc, .load_position +.load_at_the_top + ld c, 1 +.load_position + ld [hl], c + inc hl +; wMenuCursorX + ld a, 1 + ld [hli], a +; wCursorOffCharacter, wCursorCurrentTile + xor a + ld [hli], a + ld [hli], a + ld [hli], a + ret +; 244c3 diff --git a/engine/menus/menu_2.asm b/engine/menus/menu_2.asm new file mode 100644 index 000000000..16cce5348 --- /dev/null +++ b/engine/menus/menu_2.asm @@ -0,0 +1,253 @@ +PlaceMenuItemName: ; 0x24ab4 + push de + ld a, [wMenuSelection] + ld [wNamedObjectIndexBuffer], a + call GetItemName + pop hl + call PlaceString + ret + +PlaceMenuItemQuantity: ; 0x24ac3 + push de + ld a, [wMenuSelection] + ld [wCurItem], a + farcall _CheckTossableItem + ld a, [wItemAttributeParamBuffer] + pop hl + and a + jr nz, .done + ld de, $15 + add hl, de + ld [hl], "×" + inc hl + ld de, wMenuSelectionQuantity + lb bc, 1, 2 + call PrintNum + +.done + ret + +PlaceMoneyTopRight: ; 24ae8 + ld hl, MenuHeader_0x24b15 + call CopyMenuHeader + jr PlaceMoneyTextBox + +PlaceMoneyBottomLeft: ; 24af0 + ld hl, MenuHeader_0x24b1d + call CopyMenuHeader + jr PlaceMoneyTextBox + +PlaceMoneyAtTopLeftOfTextbox: ; 24af8 + ld hl, MenuHeader_0x24b15 + lb de, 0, 11 + call OffsetMenuHeader + +PlaceMoneyTextBox: ; 24b01 + call MenuBox + call MenuBoxCoord2Tile + ld de, SCREEN_WIDTH + 1 + add hl, de + ld de, wMoney + lb bc, PRINTNUM_MONEY | 3, 6 + call PrintNum + ret + +MenuHeader_0x24b15: ; 0x24b15 + db MENU_BACKUP_TILES ; flags + menu_coords 11, 0, SCREEN_WIDTH - 1, 2 + dw NULL + db 1 ; default option + +MenuHeader_0x24b1d: ; 0x24b1d + db MENU_BACKUP_TILES ; flags + menu_coords 0, 11, 8, 13 + dw NULL + db 1 ; default option + +DisplayCoinCaseBalance: ; 24b25 + ; Place a text box of size 1x7 at 11, 0. + hlcoord 11, 0 + ld b, 1 + ld c, 7 + call TextBox + hlcoord 12, 0 + ld de, CoinString + call PlaceString + hlcoord 17, 1 + ld de, ShowMoney_TerminatorString + call PlaceString + ld de, wCoins + lb bc, 2, 4 + hlcoord 13, 1 + call PrintNum + ret + +DisplayMoneyAndCoinBalance: ; 24b4e + hlcoord 5, 0 + ld b, 3 + ld c, 13 + call TextBox + hlcoord 6, 1 + ld de, MoneyString + call PlaceString + hlcoord 12, 1 + ld de, wMoney + lb bc, PRINTNUM_MONEY | 3, 6 + call PrintNum + hlcoord 6, 3 + ld de, CoinString + call PlaceString + hlcoord 15, 3 + ld de, wCoins + lb bc, 2, 4 + call PrintNum + ret + +MoneyString: ; 24b83 + db "MONEY@" +CoinString: ; 24b89 + db "COIN@" +ShowMoney_TerminatorString: ; 24b8e + db "@" + +Unreferenced_Function24b8f: ; 24b8f +; related to safari? + ld hl, wOptions + ld a, [hl] + push af + set NO_TEXT_SCROLL, [hl] + hlcoord 0, 0 + ld b, 3 + ld c, 7 + call TextBox + hlcoord 1, 1 + ld de, wSafariTimeRemaining + lb bc, 2, 3 + call PrintNum + hlcoord 4, 1 + ld de, .slash_500 + call PlaceString + hlcoord 1, 3 + ld de, .booru_ko + call PlaceString + hlcoord 5, 3 + ld de, wSafariBallsRemaining + lb bc, 1, 2 + call PrintNum + pop af + ld [wOptions], a + ret + +.slash_500 ; 24bcf + db "/500@" +.booru_ko ; 24bd4 + db "ボール こ@" + +StartMenu_DrawBugContestStatusBox: ; 24bdc + hlcoord 0, 0 + ld b, 5 + ld c, 17 + call TextBox + ret + +StartMenu_PrintBugContestStatus: ; 24be7 + ld hl, wOptions + ld a, [hl] + push af + set NO_TEXT_SCROLL, [hl] + call StartMenu_DrawBugContestStatusBox + hlcoord 1, 5 + ld de, .Balls_EN + call PlaceString + hlcoord 8, 5 + ld de, wParkBallsRemaining + lb bc, PRINTNUM_RIGHTALIGN | 1, 2 + call PrintNum + hlcoord 1, 1 + ld de, .CAUGHT + call PlaceString + ld a, [wContestMon] + and a + ld de, .None + jr z, .no_contest_mon + ld [wd265], a + call GetPokemonName + +.no_contest_mon + hlcoord 8, 1 + call PlaceString + ld a, [wContestMon] + and a + jr z, .skip_level + hlcoord 1, 3 + ld de, .LEVEL + call PlaceString + ld a, [wContestMonLevel] + ld h, b + ld l, c + inc hl + ld c, 3 + call Print8BitNumRightAlign + +.skip_level + pop af + ld [wOptions], a + ret + +.Balls_JP: ; 24c43 + db "ボール こ@" +.CAUGHT: ; 24c4b + db "CAUGHT@" +.Balls_EN: ; 24c52 + db "BALLS:@" +.None: ; 24c59 + db "None@" +.LEVEL: ; 24c5e + db "LEVEL@" + +FindApricornsInBag: ; 24c64 +; Checks the bag for Apricorns. + ld hl, wBuffer1 + xor a + ld [hli], a + dec a + ld bc, 10 + call ByteFill + + ld hl, ApricornBalls +.loop + ld a, [hl] + cp -1 + jr z, .done + push hl + ld [wCurItem], a + ld hl, wNumItems + call CheckItem + pop hl + jr nc, .nope + ld a, [hl] + call .addtobuffer +.nope + inc hl + inc hl + jr .loop + +.done + ld a, [wBuffer1] + and a + ret nz + scf + ret + +.addtobuffer ; 24c94 + push hl + ld hl, wBuffer1 + inc [hl] + ld e, [hl] + ld d, 0 + add hl, de + ld [hl], a + pop hl + ret + +INCLUDE "data/items/apricorn_balls.asm" diff --git a/engine/menus/naming_screen.asm b/engine/menus/naming_screen.asm new file mode 100644 index 000000000..a958e10eb --- /dev/null +++ b/engine/menus/naming_screen.asm @@ -0,0 +1,1467 @@ +NAMINGSCREEN_CURSOR EQU $7e + +NAMINGSCREEN_BORDER EQUS "\"■\"" ; $60 +NAMINGSCREEN_MIDDLELINE EQUS "\"→\"" ; $eb +NAMINGSCREEN_UNDERLINE EQUS "\"<DOT>\"" ; $f2 + +_NamingScreen: ; 0x116b7 + call DisableSpriteUpdates + call NamingScreen + call ReturnToMapWithSpeechTextbox + ret + +; 0x116c1 + +NamingScreen: ; 116c1 + ld hl, wNamingScreenDestinationPointer + ld [hl], e + inc hl + ld [hl], d + ld hl, wNamingScreenType + ld [hl], b + ld hl, wOptions + ld a, [hl] + push af + set NO_TEXT_SCROLL, [hl] + ld a, [hMapAnims] + push af + xor a + ld [hMapAnims], a + ld a, [hInMenu] + push af + ld a, $1 + ld [hInMenu], a + call .SetUpNamingScreen + call DelayFrame +.loop + call NamingScreenJoypadLoop + jr nc, .loop + pop af + ld [hInMenu], a + pop af + ld [hMapAnims], a + pop af + ld [wOptions], a + call ClearJoypad + ret + +; 116f8 + +.SetUpNamingScreen: ; 116f8 + call ClearBGPalettes + ld b, SCGB_DIPLOMA + call GetSGBLayout + call DisableLCD + call LoadNamingScreenGFX + call NamingScreen_InitText + ld a, LCDC_DEFAULT + ld [rLCDC], a + call .GetNamingScreenSetup + call WaitBGMap + call WaitTop + call SetPalettes + call NamingScreen_InitNameEntry + ret + +; 1171d + +.GetNamingScreenSetup: ; 1171d + ld a, [wNamingScreenType] + and 7 + ld e, a + ld d, 0 + ld hl, .Jumptable + add hl, de + add hl, de + ld a, [hli] + ld h, [hl] + ld l, a + jp hl + +; 1172e + +.Jumptable: ; 1172e (4:572e) + dw .Pokemon + dw .Player + dw .Rival + dw .Mom + dw .Box + dw .Tomodachi + dw .Pokemon + dw .Pokemon + +.Pokemon: ; 1173e (4:573e) + ld a, [wCurPartySpecies] + ld [wd265], a + ld hl, LoadMenuMonIcon + ld a, BANK(LoadMenuMonIcon) + ld e, $1 + rst FarCall ; ; indirect jump to LoadMenuMonIcon (8e83f (23:683f)) + ld a, [wCurPartySpecies] + ld [wd265], a + call GetPokemonName + hlcoord 5, 2 + call PlaceString + ld l, c + ld h, b + ld de, .NicknameStrings + call PlaceString + inc de + hlcoord 5, 4 + call PlaceString + farcall GetGender + jr c, .genderless + ld a, "♂" + jr nz, .place_gender + ld a, "♀" +.place_gender + hlcoord 1, 2 + ld [hl], a +.genderless + call .StoreMonIconParams + ret + +; 11780 (4:5780) + +.NicknameStrings: ; 11780 + db "'S@" + db "NICKNAME?@" + +; 1178d + +.Player: ; 1178d (4:578d) + farcall GetPlayerIcon + call .LoadSprite + hlcoord 5, 2 + ld de, .PlayerNameString + call PlaceString + call .StoreSpriteIconParams + ret + +; 117a3 (4:57a3) + +.PlayerNameString: ; 117a3 + db "YOUR NAME?@" + +; 117ae + +.Rival: ; 117ae (4:57ae) + ld de, SilverSpriteGFX + ld b, BANK(SilverSpriteGFX) + call .LoadSprite + hlcoord 5, 2 + ld de, .RivalNameString + call PlaceString + call .StoreSpriteIconParams + ret + +; 117c3 (4:57c3) + +.RivalNameString: ; 117c3 + db "RIVAL'S NAME?@" + +; 117d1 + +.Mom: ; 117d1 (4:57d1) + ld de, MomSpriteGFX + ld b, BANK(MomSpriteGFX) + call .LoadSprite + hlcoord 5, 2 + ld de, .MomNameString + call PlaceString + call .StoreSpriteIconParams + ret + +; 117e6 (4:57e6) + +.MomNameString: ; 117e6 + db "MOTHER'S NAME?@" + +; 117f5 + +.Box: ; 117f5 (4:57f5) + ld de, PokeBallSpriteGFX + ld hl, vTiles0 tile $00 + lb bc, BANK(PokeBallSpriteGFX), 4 + call Request2bpp + xor a + ld hl, wSpriteAnimDict + ld [hli], a + ld [hl], a + depixel 4, 4, 4, 0 + ld a, SPRITE_ANIM_INDEX_RED_WALK + call _InitSpriteAnimStruct + ld hl, SPRITEANIMSTRUCT_FRAMESET_ID + add hl, bc + ld [hl], $0 + hlcoord 5, 2 + ld de, .BoxNameString + call PlaceString + call .StoreBoxIconParams + ret + +; 11822 (4:5822) + +.BoxNameString: ; 11822 + db "BOX NAME?@" + +; 1182c + +.Tomodachi: ; 1182c (4:582c) + hlcoord 3, 2 + ld de, .oTomodachi_no_namae_sutoringu + call PlaceString + call .StoreSpriteIconParams + ret + +; 11839 (4:5839) + +.oTomodachi_no_namae_sutoringu ; 11839 + db "おともだち の なまえは?@" + +; 11847 + +.LoadSprite: ; 11847 (4:5847) + push de + ld hl, vTiles0 tile $00 + ld c, $4 + push bc + call Request2bpp + pop bc + ld hl, 12 tiles + add hl, de + ld e, l + ld d, h + ld hl, vTiles0 tile $04 + call Request2bpp + xor a + ld hl, wSpriteAnimDict + ld [hli], a + ld [hl], a + pop de + ld b, SPRITE_ANIM_INDEX_RED_WALK + ld a, d + cp HIGH(KrisSpriteGFX) + jr nz, .not_kris + ld a, e + cp LOW(KrisSpriteGFX) + jr nz, .not_kris + ld b, SPRITE_ANIM_INDEX_BLUE_WALK +.not_kris + ld a, b + depixel 4, 4, 4, 0 + call _InitSpriteAnimStruct + ret + +.StoreMonIconParams: ; 1187b (4:587b) + ld a, MON_NAME_LENGTH - 1 + hlcoord 5, 6 + jr .StoreParams + +.StoreSpriteIconParams: ; 11882 (4:5882) + ld a, PLAYER_NAME_LENGTH - 1 + hlcoord 5, 6 + jr .StoreParams + +.StoreBoxIconParams: ; 11889 (4:5889) + ld a, BOX_NAME_LENGTH - 1 + hlcoord 5, 4 + jr .StoreParams + +.StoreParams: ; 11890 (4:5890) + ld [wNamingScreenMaxNameLength], a + ld a, l + ld [wNamingScreenStringEntryCoord], a + ld a, h + ld [wNamingScreenStringEntryCoord + 1], a + ret + +NamingScreen_IsTargetBox: ; 1189c + push bc + push af + ld a, [wNamingScreenType] + sub $3 + ld b, a + pop af + dec b + pop bc + ret + +; 118a8 + +NamingScreen_InitText: ; 118a8 + call WaitTop + hlcoord 0, 0 + ld bc, SCREEN_WIDTH * SCREEN_HEIGHT + ld a, NAMINGSCREEN_BORDER + call ByteFill + hlcoord 1, 1 + lb bc, 6, 18 + call NamingScreen_IsTargetBox + jr nz, .not_box + lb bc, 4, 18 + +.not_box + call ClearBox + ld de, NameInputUpper +NamingScreen_ApplyTextInputMode: ; 118ca + call NamingScreen_IsTargetBox + jr nz, .not_box + ld hl, BoxNameInputLower - NameInputLower + add hl, de + ld d, h + ld e, l + +.not_box + push de + hlcoord 1, 8 + lb bc, 7, 18 + call NamingScreen_IsTargetBox + jr nz, .not_box_2 + hlcoord 1, 6 + lb bc, 9, 18 + +.not_box_2 + call ClearBox + hlcoord 1, 16 + lb bc, 1, 18 + call ClearBox + pop de + hlcoord 2, 8 + ld b, $5 + call NamingScreen_IsTargetBox + jr nz, .row + hlcoord 2, 6 + ld b, $6 + +.row + ld c, $11 +.col + ld a, [de] + ld [hli], a + inc de + dec c + jr nz, .col + push de + ld de, 2 * SCREEN_WIDTH - $11 + add hl, de + pop de + dec b + jr nz, .row + ret + +; 11915 + +NamingScreenJoypadLoop: ; 11915 + call JoyTextDelay + ld a, [wJumptableIndex] + bit 7, a + jr nz, .quit + call .RunJumptable + farcall PlaySpriteAnimationsAndDelayFrame + call .UpdateStringEntry + call DelayFrame + and a + ret + +.quit + callfar ClearSpriteAnims + call ClearSprites + xor a + ld [hSCX], a + ld [hSCY], a + scf + ret + +; 11940 + +.UpdateStringEntry: ; 11940 + xor a + ld [hBGMapMode], a + hlcoord 1, 5 + call NamingScreen_IsTargetBox + jr nz, .got_coords + hlcoord 1, 3 + +.got_coords + lb bc, 1, 18 + call ClearBox + ld hl, wNamingScreenDestinationPointer + ld e, [hl] + inc hl + ld d, [hl] + ld hl, wNamingScreenStringEntryCoord + ld a, [hli] + ld h, [hl] + ld l, a + call PlaceString + ld a, $1 + ld [hBGMapMode], a + ret + +; 11968 + +.RunJumptable: ; 11968 + ld a, [wJumptableIndex] + ld e, a + ld d, $0 + ld hl, .Jumptable + add hl, de + add hl, de + ld a, [hli] + ld h, [hl] + ld l, a + jp hl + +; 11977 + +.Jumptable: ; 11977 (4:5977) + dw .InitCursor + dw .ReadButtons + +.InitCursor: ; 1197b (4:597b) + depixel 10, 3 + call NamingScreen_IsTargetBox + jr nz, .got_cursor_position + ld d, 8 * 8 +.got_cursor_position + ld a, SPRITE_ANIM_INDEX_NAMING_SCREEN_CURSOR + call _InitSpriteAnimStruct + ld a, c + ld [wNamingScreenCursorObjectPointer], a + ld a, b + ld [wNamingScreenCursorObjectPointer + 1], a + ld hl, SPRITEANIMSTRUCT_FRAMESET_ID + add hl, bc + ld a, [hl] + ld hl, SPRITEANIMSTRUCT_0E + add hl, bc + ld [hl], a + ld hl, wJumptableIndex + inc [hl] + ret + +.ReadButtons: ; 119a1 (4:59a1) + ld hl, hJoyPressed ; $ffa7 + ld a, [hl] + and A_BUTTON + jr nz, .a + ld a, [hl] + and B_BUTTON + jr nz, .b + ld a, [hl] + and START + jr nz, .start + ld a, [hl] + and SELECT + jr nz, .select + ret + +.a + call .GetCursorPosition + cp $1 + jr z, .select + cp $2 + jr z, .b + cp $3 + jr z, .end + call NamingScreen_GetLastCharacter + call NamingScreen_TryAddCharacter + ret nc + +.start + ld hl, wNamingScreenCursorObjectPointer + ld c, [hl] + inc hl + ld b, [hl] + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld [hl], $8 + ld hl, SPRITEANIMSTRUCT_0D + add hl, bc + ld [hl], $4 + call NamingScreen_IsTargetBox + ret nz + inc [hl] + ret + +.b + call NamingScreen_DeleteCharacter + ret + +.end + call NamingScreen_StoreEntry + ld hl, wJumptableIndex + set 7, [hl] + ret + +.select + ld hl, wNamingScreenLetterCase + ld a, [hl] + xor 1 + ld [hl], a + jr z, .upper + ld de, NameInputLower + call NamingScreen_ApplyTextInputMode + ret + +.upper + ld de, NameInputUpper + call NamingScreen_ApplyTextInputMode + ret + +.GetCursorPosition: ; 11a0b (4:5a0b) + ld hl, wNamingScreenCursorObjectPointer + ld c, [hl] + inc hl + ld b, [hl] + +NamingScreen_GetCursorPosition: ; 11a11 (4:5a11) + ld hl, SPRITEANIMSTRUCT_0D + add hl, bc + ld a, [hl] + push bc + ld b, $4 + call NamingScreen_IsTargetBox + jr nz, .not_box + inc b +.not_box + cp b + pop bc + jr nz, .not_bottom_row + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld a, [hl] + cp $3 + jr c, .case_switch + cp $6 + jr c, .delete + ld a, $3 + ret + +.case_switch + ld a, $1 + ret + +.delete + ld a, $2 + ret + +.not_bottom_row + xor a + ret + +NamingScreen_AnimateCursor: ; 11a3b (4:5a3b) + call .GetDPad + ld hl, SPRITEANIMSTRUCT_0D + add hl, bc + ld a, [hl] + ld e, a + swap e + ld hl, SPRITEANIMSTRUCT_YOFFSET + add hl, bc + ld [hl], e + ld d, $4 + call NamingScreen_IsTargetBox + jr nz, .ok + inc d +.ok + cp d + ld de, .LetterEntries + ld a, SPRITE_ANIM_FRAMESET_TEXT_ENTRY_CURSOR - SPRITE_ANIM_FRAMESET_TEXT_ENTRY_CURSOR ; 0 + jr nz, .ok2 + ld de, .CaseDelEnd + ld a, SPRITE_ANIM_FRAMESET_TEXT_ENTRY_CURSOR_BIG - SPRITE_ANIM_FRAMESET_TEXT_ENTRY_CURSOR ; 1 +.ok2 + ld hl, SPRITEANIMSTRUCT_0E + add hl, bc + add [hl] ; default SPRITE_ANIM_FRAMESET_TEXT_ENTRY_CURSOR + ld hl, SPRITEANIMSTRUCT_FRAMESET_ID + add hl, bc + ld [hl], a + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld l, [hl] + ld h, $0 + add hl, de + ld a, [hl] + ld hl, SPRITEANIMSTRUCT_XOFFSET + add hl, bc + ld [hl], a + ret + +; 11a79 (4:5a79) + +.LetterEntries: ; 11a79 + db $00, $10, $20, $30, $40, $50, $60, $70, $80 + +.CaseDelEnd: ; 11a82 + db $00, $00, $00, $30, $30, $30, $60, $60, $60 + +; 11a8b + +.GetDPad: ; 11a8b (4:5a8b) + ld hl, hJoyLast + ld a, [hl] + and D_UP + jr nz, .up + ld a, [hl] + and D_DOWN + jr nz, .down + ld a, [hl] + and D_LEFT + jr nz, .left + ld a, [hl] + and D_RIGHT + jr nz, .right + ret + +.right + call NamingScreen_GetCursorPosition + and a + jr nz, .asm_11ab7 + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld a, [hl] + cp $8 + jr nc, .asm_11ab4 + inc [hl] + ret + +.asm_11ab4 + ld [hl], $0 + ret + +.asm_11ab7 + cp $3 + jr nz, .asm_11abc + xor a +.asm_11abc + ld e, a + add a + add e + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld [hl], a + ret + +.left + call NamingScreen_GetCursorPosition + and a + jr nz, .asm_11ad8 + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld a, [hl] + and a + jr z, .asm_11ad5 + dec [hl] + ret + +.asm_11ad5 + ld [hl], $8 + ret + +.asm_11ad8 + cp $1 + jr nz, .asm_11ade + ld a, $4 +.asm_11ade + dec a + dec a + ld e, a + add a + add e + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld [hl], a + ret + +.down + ld hl, SPRITEANIMSTRUCT_0D + add hl, bc + ld a, [hl] + call NamingScreen_IsTargetBox + jr nz, .asm_11af9 + cp $5 + jr nc, .asm_11aff + inc [hl] + ret + +.asm_11af9 + cp $4 + jr nc, .asm_11aff + inc [hl] + ret + +.asm_11aff + ld [hl], $0 + ret + +.up + ld hl, SPRITEANIMSTRUCT_0D + add hl, bc + ld a, [hl] + and a + jr z, .asm_11b0c + dec [hl] + ret + +.asm_11b0c + ld [hl], $4 + call NamingScreen_IsTargetBox + ret nz + inc [hl] + ret + +NamingScreen_TryAddCharacter: ; 11b14 (4:5b14) + ld a, [wNamingScreenLastCharacter] ; lost +MailComposition_TryAddCharacter: ; 11b17 (4:5b17) + ld a, [wNamingScreenMaxNameLength] + ld c, a + ld a, [wNamingScreenCurrNameLength] + cp c + ret nc + + ld a, [wNamingScreenLastCharacter] + +NamingScreen_LoadNextCharacter: ; 11b23 + call NamingScreen_GetTextCursorPosition + ld [hl], a + +NamingScreen_AdvanceCursor_CheckEndOfString: ; 11b27 + ld hl, wNamingScreenCurrNameLength + inc [hl] + call NamingScreen_GetTextCursorPosition + ld a, [hl] + cp "@" + jr z, .end_of_string + ld [hl], NAMINGSCREEN_UNDERLINE + and a + ret + +.end_of_string + scf + ret + +; 11b39 (4:5b39) + +; unused + ld a, [wNamingScreenCurrNameLength] + and a + ret z + push hl + ld hl, wNamingScreenCurrNameLength + dec [hl] + call NamingScreen_GetTextCursorPosition + ld c, [hl] + pop hl + +.loop + ld a, [hli] + cp $ff + jr z, NamingScreen_AdvanceCursor_CheckEndOfString + cp c + jr z, .done + inc hl + jr .loop + +.done + ld a, [hl] + jr NamingScreen_LoadNextCharacter + +; 11b56 + +INCLUDE "data/text/unused_dakutens.asm" + +; 11bbc + +NamingScreen_DeleteCharacter: ; 11bbc (4:5bbc) + ld hl, wNamingScreenCurrNameLength + ld a, [hl] + and a + ret z + dec [hl] + call NamingScreen_GetTextCursorPosition + ld [hl], NAMINGSCREEN_UNDERLINE + inc hl + ld a, [hl] + cp NAMINGSCREEN_UNDERLINE + ret nz + ld [hl], NAMINGSCREEN_MIDDLELINE + ret + +NamingScreen_GetTextCursorPosition: ; 11bd0 (4:5bd0) + push af + ld hl, wNamingScreenDestinationPointer + ld a, [hli] + ld h, [hl] + ld l, a + ld a, [wNamingScreenCurrNameLength] + ld e, a + ld d, 0 + add hl, de + pop af + ret + +; 11be0 + +NamingScreen_InitNameEntry: ; 11be0 +; load NAMINGSCREEN_UNDERLINE, (NAMINGSCREEN_MIDDLELINE * [wNamingScreenMaxNameLength]), "@" into the dw address at wNamingScreenDestinationPointer + ld hl, wNamingScreenDestinationPointer + ld a, [hli] + ld h, [hl] + ld l, a + ld [hl], NAMINGSCREEN_UNDERLINE + inc hl + ld a, [wNamingScreenMaxNameLength] + dec a + ld c, a + ld a, NAMINGSCREEN_MIDDLELINE +.loop + ld [hli], a + dec c + jr nz, .loop + ld [hl], "@" + ret + +; 11bf7 + +NamingScreen_StoreEntry: ; 11bf7 (4:5bf7) + ld hl, wNamingScreenDestinationPointer + ld a, [hli] + ld h, [hl] + ld l, a + ld a, [wNamingScreenMaxNameLength] + ld c, a +.loop + ld a, [hl] + cp NAMINGSCREEN_MIDDLELINE + jr z, .terminator + cp NAMINGSCREEN_UNDERLINE + jr nz, .not_terminator +.terminator + ld [hl], "@" +.not_terminator + inc hl + dec c + jr nz, .loop + ret + +NamingScreen_GetLastCharacter: ; 11c11 (4:5c11) + ld hl, wNamingScreenCursorObjectPointer + ld c, [hl] + inc hl + ld b, [hl] + ld hl, SPRITEANIMSTRUCT_XOFFSET + add hl, bc + ld a, [hl] + ld hl, SPRITEANIMSTRUCT_XCOORD + add hl, bc + add [hl] + sub $8 + srl a + srl a + srl a + ld e, a + ld hl, SPRITEANIMSTRUCT_YOFFSET + add hl, bc + ld a, [hl] + ld hl, SPRITEANIMSTRUCT_YCOORD + add hl, bc + add [hl] + sub $10 + srl a + srl a + srl a + ld d, a + hlcoord 0, 0 + ld bc, SCREEN_WIDTH +.loop + ld a, d + and a + jr z, .done + add hl, bc + dec d + jr .loop + +.done + add hl, de + ld a, [hl] + ld [wNamingScreenLastCharacter], a + ret + +LoadNamingScreenGFX: ; 11c51 + call ClearSprites + callfar ClearSpriteAnims + call LoadStandardFont + call LoadFontsExtra + + ld de, NamingScreenGFX_MiddleLine + ld hl, vTiles0 tile NAMINGSCREEN_MIDDLELINE + lb bc, BANK(NamingScreenGFX_MiddleLine), 1 + call Get1bpp + + ld de, NamingScreenGFX_UnderLine + ld hl, vTiles0 tile NAMINGSCREEN_UNDERLINE + lb bc, BANK(NamingScreenGFX_UnderLine), 1 + call Get1bpp + + ld de, vTiles2 tile NAMINGSCREEN_BORDER + ld hl, NamingScreenGFX_Border + ld bc, 1 tiles + ld a, BANK(NamingScreenGFX_Border) + call FarCopyBytes + + ld de, vTiles0 tile NAMINGSCREEN_CURSOR + ld hl, NamingScreenGFX_Cursor + ld bc, 2 tiles + ld a, BANK(NamingScreenGFX_Cursor) + call FarCopyBytes + + ld a, $5 + ld hl, wSpriteAnimDict + 9 * 2 + ld [hli], a + ld [hl], NAMINGSCREEN_CURSOR + xor a + ld [hSCY], a + ld [wGlobalAnimYOffset], a + ld [hSCX], a + ld [wGlobalAnimXOffset], a + ld [wJumptableIndex], a + ld [wNamingScreenLetterCase], a + ld [hBGMapMode], a + ld [wNamingScreenCurrNameLength], a + ld a, $7 + ld [hWX], a + ret + +; 11cb7 + +NamingScreenGFX_Border: ; 11cb7 +INCBIN "gfx/naming_screen/border.2bpp" +; 11cc7 + +NamingScreenGFX_Cursor: ; 11cc7 +INCBIN "gfx/naming_screen/cursor.2bpp" +; 11ce7 + +INCLUDE "data/text/name_input_chars.asm" +; 11e5d + +NamingScreenGFX_End: ; unused +INCBIN "gfx/naming_screen/end.1bpp" +; 11e6d + +NamingScreenGFX_MiddleLine: +INCBIN "gfx/naming_screen/middle_line.1bpp" +; 11e6d + +NamingScreenGFX_UnderLine: ; 11e6d +INCBIN "gfx/naming_screen/underline.1bpp" +; 11e75 + +_ComposeMailMessage: ; 11e75 (mail?) + ld hl, wNamingScreenDestinationPointer + ld [hl], e + inc hl + ld [hl], d + ld a, [hMapAnims] + push af + xor a + ld [hMapAnims], a + ld a, [hInMenu] + push af + ld a, $1 + ld [hInMenu], a + call .InitBlankMail + call DelayFrame + +.loop + call .DoMailEntry + jr nc, .loop + + pop af + ld [hInMenu], a + pop af + ld [hMapAnims], a + ret + +.InitBlankMail: ; 11e9a (4:5e9a) + call ClearBGPalettes + call DisableLCD + call LoadNamingScreenGFX + ld de, vTiles0 tile $00 + ld hl, .MailIcon + ld bc, 8 tiles + ld a, BANK(.MailIcon) + call FarCopyBytes + xor a + ld hl, wSpriteAnimDict + ld [hli], a + ld [hl], a + + ; init mail icon + depixel 3, 2 + ld a, SPRITE_ANIM_INDEX_PARTY_MON + call _InitSpriteAnimStruct + + ld hl, SPRITEANIMSTRUCT_ANIM_SEQ_ID + add hl, bc + ld [hl], $0 + call .InitCharset + ld a, LCDC_DEFAULT + ld [rLCDC], a + call .initwNamingScreenMaxNameLength + ld b, SCGB_DIPLOMA + call GetSGBLayout + call WaitBGMap + call WaitTop + ld a, %11100100 + call DmgToCgbBGPals + ld a, %11100100 + call DmgToCgbObjPal0 + call NamingScreen_InitNameEntry + ld hl, wNamingScreenDestinationPointer + ld e, [hl] + inc hl + ld d, [hl] + ld hl, MAIL_LINE_LENGTH + add hl, de + ld [hl], "<NEXT>" + ret + +; 11ef4 (4:5ef4) + +.MailIcon: ; 11ef4 +INCBIN "gfx/icons/mail_big.2bpp" +; 11f74 + +.initwNamingScreenMaxNameLength ; 11f74 (4:5f74) + ld a, MAIL_MSG_LENGTH + 1 + ld [wNamingScreenMaxNameLength], a + ret + +; 11f7a (4:5f7a) + +.UnusedString11f7a: + db "メールを かいてね@" + +; 11f84 + +.InitCharset: ; 11f84 (4:5f84) + call WaitTop + hlcoord 0, 0 + ld bc, 6 * SCREEN_WIDTH + ld a, NAMINGSCREEN_BORDER + call ByteFill + hlcoord 0, 6 + ld bc, 12 * SCREEN_WIDTH + ld a, " " + call ByteFill + hlcoord 1, 1 + lb bc, 4, SCREEN_WIDTH - 2 + call ClearBox + ld de, MailEntry_Uppercase + +.PlaceMailCharset: ; 11fa9 (4:5fa9) + hlcoord 1, 7 + ld b, 6 +.next + ld c, SCREEN_WIDTH - 1 +.loop_ + ld a, [de] + ld [hli], a + inc de + dec c + jr nz, .loop_ + push de + ld de, SCREEN_WIDTH + 1 + add hl, de + pop de + dec b + jr nz, .next + ret + +.DoMailEntry: ; 11fc0 (4:5fc0) + call JoyTextDelay + ld a, [wJumptableIndex] + bit 7, a + jr nz, .exit_mail + call .DoJumptable + farcall PlaySpriteAnimationsAndDelayFrame + call .Update + call DelayFrame + and a + ret + +.exit_mail + callfar ClearSpriteAnims + call ClearSprites + xor a + ld [hSCX], a + ld [hSCY], a + scf + ret + +.Update: ; 11feb (4:5feb) + xor a + ld [hBGMapMode], a + hlcoord 1, 1 + lb bc, 4, 18 + call ClearBox + ld hl, wNamingScreenDestinationPointer + ld e, [hl] + inc hl + ld d, [hl] + hlcoord 2, 2 + call PlaceString + ld a, $1 + ld [hBGMapMode], a + ret + +.DoJumptable: ; 12008 (4:6008) + ld a, [wJumptableIndex] + ld e, a + ld d, 0 + ld hl, .Jumptable + add hl, de + add hl, de + ld a, [hli] + ld h, [hl] + ld l, a + jp hl + +.Jumptable: ; 12017 (4:6017) + dw .init_blinking_cursor + dw .process_joypad + +.init_blinking_cursor ; 1201b (4:601b) + depixel 9, 2 + ld a, SPRITE_ANIM_INDEX_COMPOSE_MAIL_CURSOR + call _InitSpriteAnimStruct + ld a, c + ld [wNamingScreenCursorObjectPointer], a + ld a, b + ld [wNamingScreenCursorObjectPointer + 1], a + ld hl, SPRITEANIMSTRUCT_FRAMESET_ID + add hl, bc + ld a, [hl] + ld hl, SPRITEANIMSTRUCT_0E + add hl, bc + ld [hl], a + ld hl, wJumptableIndex + inc [hl] + ret + +.process_joypad ; 1203a (4:603a) + ld hl, hJoyPressed ; $ffa7 + ld a, [hl] + and A_BUTTON + jr nz, .a + ld a, [hl] + and B_BUTTON + jr nz, .b + ld a, [hl] + and START + jr nz, .start + ld a, [hl] + and SELECT + jr nz, .select + ret + +.a + call NamingScreen_PressedA_GetCursorCommand + cp $1 + jr z, .select + cp $2 + jr z, .b + cp $3 + jr z, .finished + call NamingScreen_GetLastCharacter + call MailComposition_TryAddLastCharacter + jr c, .start + ld hl, wNamingScreenCurrNameLength + ld a, [hl] + cp MAIL_LINE_LENGTH + ret nz + inc [hl] + call NamingScreen_GetTextCursorPosition + ld [hl], NAMINGSCREEN_UNDERLINE + dec hl + ld [hl], "<NEXT>" + ret + +.start + ld hl, wNamingScreenCursorObjectPointer + ld c, [hl] + inc hl + ld b, [hl] + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld [hl], $9 + ld hl, SPRITEANIMSTRUCT_0D + add hl, bc + ld [hl], $5 + ret + +.b + call NamingScreen_DeleteCharacter + ld hl, wNamingScreenCurrNameLength + ld a, [hl] + cp MAIL_LINE_LENGTH + ret nz + dec [hl] + call NamingScreen_GetTextCursorPosition + ld [hl], NAMINGSCREEN_UNDERLINE + inc hl + ld [hl], "<NEXT>" + ret + +.finished + call NamingScreen_StoreEntry + ld hl, wJumptableIndex + set 7, [hl] + ret + +.select + ld hl, wNamingScreenLetterCase + ld a, [hl] + xor 1 + ld [hl], a + jr nz, .switch_to_lowercase + ld de, MailEntry_Uppercase + call .PlaceMailCharset + ret + +.switch_to_lowercase + ld de, MailEntry_Lowercase + call .PlaceMailCharset + ret + +; called from engine/sprite_anims.asm + +ComposeMail_AnimateCursor: ; 120c1 (4:60c1) + call .GetDPad + ld hl, SPRITEANIMSTRUCT_0D + add hl, bc + ld a, [hl] + ld e, a + swap e + ld hl, SPRITEANIMSTRUCT_YOFFSET + add hl, bc + ld [hl], e + cp $5 + ld de, .LetterEntries + ld a, 0 + jr nz, .got_pointer + ld de, .CaseDelEnd + ld a, 1 +.got_pointer + ld hl, SPRITEANIMSTRUCT_0E + add hl, bc + add [hl] + ld hl, SPRITEANIMSTRUCT_FRAMESET_ID + add hl, bc + ld [hl], a + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld l, [hl] + ld h, 0 + add hl, de + ld a, [hl] + ld hl, SPRITEANIMSTRUCT_XOFFSET + add hl, bc + ld [hl], a + ret + +; 120f8 (4:60f8) + +.LetterEntries: ; 120f8 + db $00, $10, $20, $30, $40, $50, $60, $70, $80, $90 + +.CaseDelEnd: ; 12102 + db $00, $00, $00, $30, $30, $30, $60, $60, $60, $60 + +; 1210c + +.GetDPad: ; 1210c (4:610c) + ld hl, hJoyLast + ld a, [hl] + and D_UP + jr nz, .up + ld a, [hl] + and D_DOWN + jr nz, .down + ld a, [hl] + and D_LEFT + jr nz, .left + ld a, [hl] + and D_RIGHT + jr nz, .right + ret + +.right + call ComposeMail_GetCursorPosition + and a + jr nz, .case_del_done_right + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld a, [hl] + cp $9 + jr nc, .wrap_around_letter_right + inc [hl] + ret + +.wrap_around_letter_right + ld [hl], $0 + ret + +.case_del_done_right + cp $3 + jr nz, .wrap_around_command_right + xor a +.wrap_around_command_right + ld e, a + add a + add e + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld [hl], a + ret + +.left + call ComposeMail_GetCursorPosition + and a + jr nz, .caps_del_done_left + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld a, [hl] + and a + jr z, .wrap_around_letter_left + dec [hl] + ret + +.wrap_around_letter_left + ld [hl], $9 + ret + +.caps_del_done_left + cp $1 + jr nz, .wrap_around_command_left + ld a, $4 +.wrap_around_command_left + dec a + dec a + ld e, a + add a + add e + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld [hl], a + ret + +.down + ld hl, SPRITEANIMSTRUCT_0D + add hl, bc + ld a, [hl] + cp $5 + jr nc, .wrap_around_down + inc [hl] + ret + +.wrap_around_down + ld [hl], $0 + ret + +.up + ld hl, SPRITEANIMSTRUCT_0D + add hl, bc + ld a, [hl] + and a + jr z, .wrap_around_up + dec [hl] + ret + +.wrap_around_up + ld [hl], $5 + ret + +NamingScreen_PressedA_GetCursorCommand: ; 12185 (4:6185) + ld hl, wNamingScreenCursorObjectPointer + ld c, [hl] + inc hl + ld b, [hl] + +ComposeMail_GetCursorPosition: ; 1218b (4:618b) + ld hl, SPRITEANIMSTRUCT_0D + add hl, bc + ld a, [hl] + cp $5 + jr nz, .letter + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld a, [hl] + cp $3 + jr c, .case + cp $6 + jr c, .del + ld a, $3 + ret + +.case + ld a, $1 + ret + +.del + ld a, $2 + ret + +.letter + xor a + ret + +MailComposition_TryAddLastCharacter: ; 121ac (4:61ac) + ld a, [wNamingScreenLastCharacter] + jp MailComposition_TryAddCharacter + +; 121b2 (4:61b2) + +; unused + ld a, [wNamingScreenCurrNameLength] + and a + ret z + cp $11 + jr nz, .asm_121c3 + push hl + ld hl, wNamingScreenCurrNameLength + dec [hl] + dec [hl] + jr .asm_121c8 + +.asm_121c3 + push hl + ld hl, wNamingScreenCurrNameLength + dec [hl] + +.asm_121c8 + call NamingScreen_GetTextCursorPosition + ld c, [hl] + pop hl +.asm_121cd + ld a, [hli] + cp $ff + jp z, NamingScreen_AdvanceCursor_CheckEndOfString + cp c + jr z, .asm_121d9 + inc hl + jr .asm_121cd + +.asm_121d9 + ld a, [hl] + jp NamingScreen_LoadNextCharacter + +; 121dd + +INCLUDE "data/text/mail_input_chars.asm" + +; 122c1 diff --git a/engine/menus/options_menu.asm b/engine/menus/options_menu.asm new file mode 100644 index 000000000..c0a255cb0 --- /dev/null +++ b/engine/menus/options_menu.asm @@ -0,0 +1,583 @@ +_OptionsMenu: ; e41d0 + ld hl, hInMenu + ld a, [hl] + push af + ld [hl], $1 + call ClearBGPalettes + hlcoord 0, 0 + ld b, 16 + ld c, 18 + call TextBox + hlcoord 2, 2 + ld de, StringOptions + call PlaceString + xor a + ld [wJumptableIndex], a + ld c, $6 ; number of items on the menu minus 1 (for cancel) + +.print_text_loop ; this next will display the settings of each option when the menu is opened + push bc + xor a + ld [hJoyLast], a + call GetOptionPointer + pop bc + ld hl, wJumptableIndex + inc [hl] + dec c + jr nz, .print_text_loop + + call UpdateFrame + xor a + ld [wJumptableIndex], a + inc a + ld [hBGMapMode], a + call WaitBGMap + ld b, SCGB_DIPLOMA + call GetSGBLayout + call SetPalettes + +.joypad_loop + call JoyTextDelay + ld a, [hJoyPressed] + and START | B_BUTTON + jr nz, .ExitOptions + call OptionsControl + jr c, .dpad + call GetOptionPointer + jr c, .ExitOptions + +.dpad + call Options_UpdateCursorPosition + ld c, 3 + call DelayFrames + jr .joypad_loop + +.ExitOptions: + ld de, SFX_TRANSACTION + call PlaySFX + call WaitSFX + pop af + ld [hInMenu], a + ret +; e4241 + +StringOptions: ; e4241 + db "TEXT SPEED<LNBRK>" + db " :<LNBRK>" + db "BATTLE SCENE<LNBRK>" + db " :<LNBRK>" + db "BATTLE STYLE<LNBRK>" + db " :<LNBRK>" + db "SOUND<LNBRK>" + db " :<LNBRK>" + db "PRINT<LNBRK>" + db " :<LNBRK>" + db "MENU ACCOUNT<LNBRK>" + db " :<LNBRK>" + db "FRAME<LNBRK>" + db " :TYPE<LNBRK>" + db "CANCEL@" +; e42d6 + + +GetOptionPointer: ; e42d6 + ld a, [wJumptableIndex] ; load the cursor position to a + ld e, a ; copy it to de + ld d, 0 + ld hl, .Pointers + add hl, de + add hl, de + ld a, [hli] + ld h, [hl] + ld l, a + jp hl ; jump to the code of the current highlighted item +; e42e5 + +.Pointers: + dw Options_TextSpeed + dw Options_BattleScene + dw Options_BattleStyle + dw Options_Sound + dw Options_Print + dw Options_MenuAccount + dw Options_Frame + dw Options_Cancel +; e42f5 + + + const_def + const OPT_TEXT_SPEED_FAST ; 0 + const OPT_TEXT_SPEED_MED ; 1 + const OPT_TEXT_SPEED_SLOW ; 2 + +Options_TextSpeed: ; e42f5 + call GetTextSpeed + ld a, [hJoyPressed] + bit D_LEFT_F, a + jr nz, .LeftPressed + bit D_RIGHT_F, a + jr z, .NonePressed + ld a, c ; right pressed + cp OPT_TEXT_SPEED_SLOW + jr c, .Increase + ld c, OPT_TEXT_SPEED_FAST + -1 + +.Increase: + inc c + ld a, e + jr .Save + +.LeftPressed: + ld a, c + and a + jr nz, .Decrease + ld c, OPT_TEXT_SPEED_SLOW + 1 + +.Decrease: + dec c + ld a, d + +.Save: + ld b, a + ld a, [wOptions] + and $f0 + or b + ld [wOptions], a + +.NonePressed: + ld b, 0 + ld hl, .Strings + add hl, bc + add hl, bc + ld e, [hl] + inc hl + ld d, [hl] + hlcoord 11, 3 + call PlaceString + and a + ret +; e4331 + +.Strings: +; entries correspond to OPT_TEXT_SPEED_* constants + dw .Fast + dw .Mid + dw .Slow + +.Fast: db "FAST@" +.Mid: db "MID @" +.Slow: db "SLOW@" +; e4346 + + +GetTextSpeed: ; e4346 +; converts TEXT_DELAY_* value in a to OPT_TEXT_SPEED_* value in c, +; with previous/next TEXT_DELAY_* values in d/e + ld a, [wOptions] + and $7 + cp TEXT_DELAY_SLOW + jr z, .slow + cp TEXT_DELAY_FAST + jr z, .fast + ; none of the above + ld c, OPT_TEXT_SPEED_MED + lb de, TEXT_DELAY_FAST, TEXT_DELAY_SLOW + ret + +.slow + ld c, OPT_TEXT_SPEED_SLOW + lb de, TEXT_DELAY_MED, TEXT_DELAY_FAST + ret + +.fast + ld c, OPT_TEXT_SPEED_FAST + lb de, TEXT_DELAY_SLOW, TEXT_DELAY_MED + ret +; e4365 + + +Options_BattleScene: ; e4365 + ld hl, wOptions + ld a, [hJoyPressed] + bit D_LEFT_F, a + jr nz, .LeftPressed + bit D_RIGHT_F, a + jr z, .NonePressed + bit BATTLE_SCENE, [hl] + jr nz, .ToggleOn + jr .ToggleOff + +.LeftPressed: + bit BATTLE_SCENE, [hl] + jr z, .ToggleOff + jr .ToggleOn + +.NonePressed: + bit BATTLE_SCENE, [hl] + jr z, .ToggleOn + jr .ToggleOff + +.ToggleOn: + res BATTLE_SCENE, [hl] + ld de, .On + jr .Display + +.ToggleOff: + set BATTLE_SCENE, [hl] + ld de, .Off + +.Display: + hlcoord 11, 5 + call PlaceString + and a + ret +; e4398 + +.On: db "ON @" +.Off: db "OFF@" +; e43a0 + + +Options_BattleStyle: ; e43a0 + ld hl, wOptions + ld a, [hJoyPressed] + bit D_LEFT_F, a + jr nz, .LeftPressed + bit D_RIGHT_F, a + jr z, .NonePressed + bit BATTLE_SHIFT, [hl] + jr nz, .ToggleShift + jr .ToggleSet + +.LeftPressed: + bit BATTLE_SHIFT, [hl] + jr z, .ToggleSet + jr .ToggleShift + +.NonePressed: + bit BATTLE_SHIFT, [hl] + jr nz, .ToggleSet + +.ToggleShift: + res BATTLE_SHIFT, [hl] + ld de, .Shift + jr .Display + +.ToggleSet: + set BATTLE_SHIFT, [hl] + ld de, .Set + +.Display: + hlcoord 11, 7 + call PlaceString + and a + ret +; e43d1 + +.Shift: db "SHIFT@" +.Set: db "SET @" +; e43dd + + +Options_Sound: ; e43dd + ld hl, wOptions + ld a, [hJoyPressed] + bit D_LEFT_F, a + jr nz, .LeftPressed + bit D_RIGHT_F, a + jr z, .NonePressed + bit STEREO, [hl] + jr nz, .SetMono + jr .SetStereo + +.LeftPressed: + bit STEREO, [hl] + jr z, .SetStereo + jr .SetMono + +.NonePressed: + bit STEREO, [hl] + jr nz, .ToggleStereo + jr .ToggleMono + +.SetMono: + res STEREO, [hl] + call RestartMapMusic + +.ToggleMono: + ld de, .Mono + jr .Display + +.SetStereo: + set STEREO, [hl] + call RestartMapMusic + +.ToggleStereo: + ld de, .Stereo + +.Display: + hlcoord 11, 9 + call PlaceString + and a + ret +; e4416 + +.Mono: db "MONO @" +.Stereo: db "STEREO@" +; e4424 + + + const_def + const OPT_PRINT_LIGHTEST ; 0 + const OPT_PRINT_LIGHTER ; 1 + const OPT_PRINT_NORMAL ; 2 + const OPT_PRINT_DARKER ; 3 + const OPT_PRINT_DARKEST ; 4 + +Options_Print: ; e4424 + call GetPrinterSetting + ld a, [hJoyPressed] + bit D_LEFT_F, a + jr nz, .LeftPressed + bit D_RIGHT_F, a + jr z, .NonePressed + ld a, c + cp OPT_PRINT_DARKEST + jr c, .Increase + ld c, OPT_PRINT_LIGHTEST - 1 + +.Increase: + inc c + ld a, e + jr .Save + +.LeftPressed: + ld a, c + and a + jr nz, .Decrease + ld c, OPT_PRINT_DARKEST + 1 + +.Decrease: + dec c + ld a, d + +.Save: + ld b, a + ld [wGBPrinter], a + +.NonePressed: + ld b, $0 + ld hl, .Strings + add hl, bc + add hl, bc + ld e, [hl] + inc hl + ld d, [hl] + hlcoord 11, 11 + call PlaceString + and a + ret +; e445a + +.Strings: +; entries correspond to OPT_PRINT_* constants + dw .Lightest + dw .Lighter + dw .Normal + dw .Darker + dw .Darkest + +.Lightest: db "LIGHTEST@" +.Lighter: db "LIGHTER @" +.Normal: db "NORMAL @" +.Darker: db "DARKER @" +.Darkest: db "DARKEST @" +; e4491 + + +GetPrinterSetting: ; e4491 +; converts GBPRINTER_* value in a to OPT_PRINT_* value in c, +; with previous/next GBPRINTER_* values in d/e + ld a, [wGBPrinter] + and a + jr z, .IsLightest + cp GBPRINTER_LIGHTER + jr z, .IsLight + cp GBPRINTER_DARKER + jr z, .IsDark + cp GBPRINTER_DARKEST + jr z, .IsDarkest + ; none of the above + ld c, OPT_PRINT_NORMAL + lb de, GBPRINTER_LIGHTER, GBPRINTER_DARKER + ret + +.IsLightest: + ld c, OPT_PRINT_LIGHTEST + lb de, GBPRINTER_DARKEST, GBPRINTER_LIGHTER + ret + +.IsLight: + ld c, OPT_PRINT_LIGHTER + lb de, GBPRINTER_LIGHTEST, GBPRINTER_NORMAL + ret + +.IsDark: + ld c, OPT_PRINT_DARKER + lb de, GBPRINTER_NORMAL, GBPRINTER_DARKEST + ret + +.IsDarkest: + ld c, OPT_PRINT_DARKEST + lb de, GBPRINTER_DARKER, GBPRINTER_LIGHTEST + ret +; e44c1 + +Options_MenuAccount: ; e44c1 + ld hl, wOptions2 + ld a, [hJoyPressed] + bit D_LEFT_F, a + jr nz, .LeftPressed + bit D_RIGHT_F, a + jr z, .NonePressed + bit MENU_ACCOUNT, [hl] + jr nz, .ToggleOff + jr .ToggleOn + +.LeftPressed: + bit MENU_ACCOUNT, [hl] + jr z, .ToggleOn + jr .ToggleOff + +.NonePressed: + bit MENU_ACCOUNT, [hl] + jr nz, .ToggleOn + +.ToggleOff: + res MENU_ACCOUNT, [hl] + ld de, .Off + jr .Display + +.ToggleOn: + set MENU_ACCOUNT, [hl] + ld de, .On + +.Display: + hlcoord 11, 13 + call PlaceString + and a + ret +; e44f2 + +.Off: db "OFF@" +.On: db "ON @" +; e44fa + + +Options_Frame: ; e44fa + ld hl, wTextBoxFrame + ld a, [hJoyPressed] + bit D_LEFT_F, a + jr nz, .LeftPressed + bit D_RIGHT_F, a + jr nz, .RightPressed + and a + ret + +.RightPressed: + ld a, [hl] + inc a + jr .Save + +.LeftPressed: + ld a, [hl] + dec a + +.Save: + and $7 + ld [hl], a +UpdateFrame: ; e4512 + ld a, [wTextBoxFrame] + hlcoord 16, 15 ; where on the screen the number is drawn + add "1" + ld [hl], a + call LoadFontsExtra + and a + ret +; e4520 + +Options_Cancel: ; e4520 + ld a, [hJoyPressed] + and A_BUTTON + jr nz, .Exit + and a + ret + +.Exit: + scf + ret +; e452a + +OptionsControl: ; e452a + ld hl, wJumptableIndex + ld a, [hJoyLast] + cp D_DOWN + jr z, .DownPressed + cp D_UP + jr z, .UpPressed + and a + ret + +.DownPressed: + ld a, [hl] ; load the cursor position to a + cp $7 ; maximum number of items in option menu + jr nz, .CheckFive + ld [hl], $0 + scf + ret + +.CheckFive: ; I have no idea why this exists... + cp $5 + jr nz, .Increase + ld [hl], $5 + +.Increase: + inc [hl] + scf + ret + +.UpPressed: + ld a, [hl] + cp $6 + jr nz, .NotSix + ld [hl], $5 ; Another thing where I'm not sure why it exists + scf + ret + +.NotSix: + and a + jr nz, .Decrease + ld [hl], $8 ; number of option items +1 + +.Decrease: + dec [hl] + scf + ret +; e455c + +Options_UpdateCursorPosition: ; e455c + hlcoord 1, 1 + ld de, SCREEN_WIDTH + ld c, $10 +.loop + ld [hl], " " + add hl, de + dec c + jr nz, .loop + hlcoord 1, 2 + ld bc, 2 * SCREEN_WIDTH + ld a, [wJumptableIndex] + call AddNTimes + ld [hl], "▶" + ret +; e4579 diff --git a/engine/menus/save.asm b/engine/menus/save.asm new file mode 100644 index 000000000..7984c1612 --- /dev/null +++ b/engine/menus/save.asm @@ -0,0 +1,1210 @@ +SaveMenu: ; 14a1a + call LoadStandardMenuHeader + farcall DisplaySaveInfoOnSave + call SpeechTextBox + call UpdateSprites + farcall SaveMenu_CopyTilemapAtOnce + ld hl, Text_WouldYouLikeToSaveTheGame + call SaveTheGame_yesorno + jr nz, .refused + call AskOverwriteSaveFile + jr c, .refused + call PauseGameLogic + call _SavingDontTurnOffThePower + call ResumeGameLogic + call ExitMenu + and a + ret + +.refused + call ExitMenu + call ret_d90 + farcall SaveMenu_CopyTilemapAtOnce + scf + ret + +SaveAfterLinkTrade: ; 14a58 + call PauseGameLogic + farcall StageRTCTimeForSave + farcall BackupMysteryGift + call SavePokemonData + call SaveChecksum + call SaveBackupPokemonData + call SaveBackupChecksum + farcall BackupPartyMonMail + farcall SaveRTC + call ResumeGameLogic + ret +; 14a83 + + +ChangeBoxSaveGame: ; 14a83 (5:4a83) + push de + ld hl, Text_SaveOnBoxSwitch + call MenuTextBox + call YesNoBox + call ExitMenu + jr c, .refused + call AskOverwriteSaveFile + jr c, .refused + call PauseGameLogic + call SavingDontTurnOffThePower + call SaveBox + pop de + ld a, e + ld [wCurBox], a + call LoadBox + call SavedTheGame + call ResumeGameLogic + and a + ret +.refused + pop de + ret + +Link_SaveGame: ; 14ab2 + call AskOverwriteSaveFile + jr c, .refused + call PauseGameLogic + call _SavingDontTurnOffThePower + call ResumeGameLogic + and a + +.refused + ret +; 14ac2 + +MoveMonWOMail_SaveGame: ; 14ac2 + call PauseGameLogic + push de + call SaveBox + pop de + ld a, e + ld [wCurBox], a + call LoadBox + call ResumeGameLogic + ret +; 14ad5 + +MoveMonWOMail_InsertMon_SaveGame: ; 14ad5 + call PauseGameLogic + push de + call SaveBox + pop de + ld a, e + ld [wCurBox], a + ld a, $1 + ld [wSaveFileExists], a + farcall StageRTCTimeForSave + farcall BackupMysteryGift + call ValidateSave + call SaveOptions + call SavePlayerData + call SavePokemonData + call SaveChecksum + call ValidateBackupSave + call SaveBackupOptions + call SaveBackupPlayerData + call SaveBackupPokemonData + call SaveBackupChecksum + farcall BackupPartyMonMail + farcall BackupMobileEventIndex + farcall SaveRTC + call LoadBox + call ResumeGameLogic + ld de, SFX_SAVE + call PlaySFX + ld c, 24 + call DelayFrames + ret +; 14b34 + +StartMoveMonWOMail_SaveGame: ; 14b34 + ld hl, Text_SaveOnMoveMonWOMail + call MenuTextBox + call YesNoBox + call ExitMenu + jr c, .refused + call AskOverwriteSaveFile + jr c, .refused + call PauseGameLogic + call _SavingDontTurnOffThePower + call ResumeGameLogic + and a + ret + +.refused + scf + ret +; 14b54 + +PauseGameLogic: ; 14b54 + ld a, $1 + ld [wGameLogicPaused], a + ret +; 14b5a + +ResumeGameLogic: ; 14b5a + xor a + ld [wGameLogicPaused], a + ret +; 14b5f + + +AddHallOfFameEntry: ; 14b5f + ld a, BANK(sHallOfFame) + call GetSRAMBank + ld hl, sHallOfFame + HOF_LENGTH * (NUM_HOF_TEAMS - 1) - 1 + ld de, sHallOfFame + HOF_LENGTH * NUM_HOF_TEAMS - 1 + ld bc, HOF_LENGTH * (NUM_HOF_TEAMS - 1) +.loop + ld a, [hld] + ld [de], a + dec de + dec bc + ld a, c + or b + jr nz, .loop + ld hl, wOverworldMap + ld de, sHallOfFame + ld bc, HOF_LENGTH + call CopyBytes + call CloseSRAM + ret +; 14b85 + +SaveGameData: ; 14b85 + call SaveGameData_ + ret +; 14b89 + +AskOverwriteSaveFile: ; 14b89 + ld a, [wSaveFileExists] + and a + jr z, .erase + call CompareLoadedAndSavedPlayerID + jr z, .yoursavefile + ld hl, Text_AnotherSaveFile + call SaveTheGame_yesorno + jr nz, .refused + jr .erase + +.yoursavefile + ld hl, Text_AlreadyASaveFile + call SaveTheGame_yesorno + jr nz, .refused + jr .ok + +.erase + call ErasePreviousSave + +.ok + and a + ret + +.refused + scf + ret +; 14baf + +SaveTheGame_yesorno: ; 14baf + ld b, BANK(Text_WouldYouLikeToSaveTheGame) + call MapTextbox + call LoadMenuTextBox + lb bc, 0, 7 + call PlaceYesNoBox + ld a, [wMenuCursorY] + dec a + call CloseWindow + push af + call ret_d90 + pop af + and a + ret +; 14bcb + +CompareLoadedAndSavedPlayerID: ; 14bcb + ld a, BANK(sPlayerData) + call GetSRAMBank + ld hl, sPlayerData + (wPlayerID - wPlayerData) + ld a, [hli] + ld c, [hl] + ld b, a + call CloseSRAM + ld a, [wPlayerID] + cp b + ret nz + ld a, [wPlayerID + 1] + cp c + ret +; 14be3 + +_SavingDontTurnOffThePower: ; 14be3 + call SavingDontTurnOffThePower +SavedTheGame: ; 14be6 + call SaveGameData_ + ; wait 32 frames + ld c, $20 + call DelayFrames + ; copy the original text speed setting to the stack + ld a, [wOptions] + push af + ; set text speed super slow + ld a, 3 + ld [wOptions], a + ; <PLAYER> saved the game! + ld hl, Text_PlayerSavedTheGame + call PrintText + ; restore the original text speed setting + pop af + ld [wOptions], a + ld de, SFX_SAVE + call WaitPlaySFX + call WaitSFX + ; wait 30 frames + ld c, $1e + call DelayFrames + ret +; 14c10 + + +SaveGameData_: ; 14c10 + ld a, 1 + ld [wSaveFileExists], a + farcall StageRTCTimeForSave + farcall BackupMysteryGift + call ValidateSave + call SaveOptions + call SavePlayerData + call SavePokemonData + call SaveBox + call SaveChecksum + call ValidateBackupSave + call SaveBackupOptions + call SaveBackupPlayerData + call SaveBackupPokemonData + call SaveBackupChecksum + call UpdateStackTop + farcall BackupPartyMonMail + farcall BackupMobileEventIndex + farcall SaveRTC + ld a, BANK(sBattleTowerChallengeState) + call GetSRAMBank + ld a, [sBattleTowerChallengeState] + cp BATTLETOWER_RECEIVED_REWARD + jr nz, .ok + xor a + ld [sBattleTowerChallengeState], a +.ok + call CloseSRAM + ret +; 14c6b + +UpdateStackTop: ; 14c6b +; sStackTop appears to be unused. +; It could have been used to debug stack overflow during saving. + call FindStackTop + ld a, BANK(sStackTop) + call GetSRAMBank + ld a, [sStackTop + 0] + ld e, a + ld a, [sStackTop + 1] + ld d, a + or e + jr z, .update + ld a, e + sub l + ld a, d + sbc h + jr c, .done + +.update + ld a, l + ld [sStackTop + 0], a + ld a, h + ld [sStackTop + 1], a + +.done + call CloseSRAM + ret +; 14c90 + +FindStackTop: ; 14c90 +; Find the furthest point that sp has traversed to. +; This is distinct from the current value of sp. + ld hl, wStack - $ff +.loop + ld a, [hl] + or a + ret nz + inc hl + jr .loop +; 14c99 + +SavingDontTurnOffThePower: ; 14c99 + ; Prevent joypad interrupts + xor a + ld [hJoypadReleased], a + ld [hJoypadPressed], a + ld [hJoypadSum], a + ld [hJoypadDown], a + ; Save the text speed setting to the stack + ld a, [wOptions] + push af + ; Set the text speed to super slow + ld a, $3 + ld [wOptions], a + ; SAVING... DON'T TURN OFF THE POWER. + ld hl, Text_SavingDontTurnOffThePower + call PrintText + ; Restore the text speed setting + pop af + ld [wOptions], a + ; Wait for 16 frames + ld c, $10 + call DelayFrames + ret +; 14cbb + + +ErasePreviousSave: ; 14cbb + call EraseBoxes + call EraseHallOfFame + call EraseLinkBattleStats + call EraseMysteryGift + call SaveData + call EraseBattleTowerStatus + ld a, BANK(sStackTop) + call GetSRAMBank + xor a + ld [sStackTop + 0], a + ld [sStackTop + 1], a + call CloseSRAM + ld a, $1 + ld [wSavedAtLeastOnce], a + ret +; 14ce2 + +EraseLinkBattleStats: ; 14ce2 + ld a, BANK(sLinkBattleStats) + call GetSRAMBank + ld hl, sLinkBattleStats + ld bc, sLinkBattleStatsEnd - sLinkBattleStats + xor a + call ByteFill + jp CloseSRAM +; 14cf4 + +EraseMysteryGift: ; 14cf4 + ld a, BANK(sBackupMysteryGiftItem) + call GetSRAMBank + ld hl, sBackupMysteryGiftItem + ld bc, sBackupMysteryGiftItemEnd - sBackupMysteryGiftItem + xor a + call ByteFill + jp CloseSRAM +; 14d06 + +EraseHallOfFame: ; 14d06 + ld a, BANK(sHallOfFame) + call GetSRAMBank + ld hl, sHallOfFame + ld bc, sHallOfFameEnd - sHallOfFame + xor a + call ByteFill + jp CloseSRAM +; 14d18 + +Unreferenced_Function14d18: ; 14d18 +; copy .Data to SRA4:a007 + ld a, 4 ; MBC30 bank used by JP Crystal; inaccessible by MBC3 + call GetSRAMBank + ld hl, .Data + ld de, $a007 ; address of MBC30 bank + ld bc, .DataEnd - .Data + call CopyBytes + jp CloseSRAM +; 14d2c + +.Data: ; 14d2c + db $0d, $02, $00, $05, $00, $00 + db $22, $02, $01, $05, $00, $00 + db $03, $04, $05, $08, $03, $05 + db $0e, $06, $03, $02, $00, $00 + db $39, $07, $07, $04, $00, $05 + db $04, $07, $01, $05, $00, $00 + db $0f, $05, $14, $07, $05, $05 + db $11, $0c, $0c, $06, $06, $04 +; 14d5c +.DataEnd + +EraseBattleTowerStatus: ; 14d5c + ld a, BANK(sBattleTowerChallengeState) + call GetSRAMBank + xor a + ld [sBattleTowerChallengeState], a + jp CloseSRAM +; 14d68 + +SaveData: ; 14d68 + call _SaveData + ret +; 14d6c + +Unreferenced_Function14d6c: ; 14d6c + ld a, 4 ; MBC30 bank used by JP Crystal; inaccessible by MBC3 + call GetSRAMBank + ld a, [$a60b] ; address of MBC30 bank + ld b, $0 + and a + jr z, .ok + ld b, $2 + +.ok + ld a, b + ld [$a60b], a ; address of MBC30 bank + call CloseSRAM + ret +; 14d83 + +Unreferenced_Function14d83: ; 14d83 + ld a, 4 ; MBC30 bank used by JP Crystal; inaccessible by MBC3 + call GetSRAMBank + xor a + ld [$a60c], a ; address of MBC30 bank + ld [$a60d], a ; address of MBC30 bank + call CloseSRAM + ret +; 14d93 + +Unreferenced_Function14d93: ; 14d93 + ld a, 7 ; MBC30 bank used by JP Crystal; inaccessible by MBC3 + call GetSRAMBank + xor a + ld [$a000], a ; address of MBC30 bank + call CloseSRAM + ret +; 14da0 + + +HallOfFame_InitSaveIfNeeded: ; 14da0 + ld a, [wSavedAtLeastOnce] + and a + ret nz + call ErasePreviousSave + ret +; 14da9 + +ValidateSave: ; 14da9 + ld a, BANK(sCheckValue1) ; BANK(sCheckValue2) + call GetSRAMBank + ld a, SAVE_CHECK_VALUE_1 + ld [sCheckValue1], a + ld a, SAVE_CHECK_VALUE_2 + ld [sCheckValue2], a + jp CloseSRAM +; 14dbb + +SaveOptions: ; 14dbb + ld a, BANK(sOptions) + call GetSRAMBank + ld hl, wOptions + ld de, sOptions + ld bc, wOptionsEnd - wOptions + call CopyBytes + ld a, [wOptions] + and $ff ^ (1 << NO_TEXT_SCROLL) + ld [sOptions], a + jp CloseSRAM +; 14dd7 + +SavePlayerData: ; 14dd7 + ld a, BANK(sPlayerData) + call GetSRAMBank + ld hl, wPlayerData + ld de, sPlayerData + ld bc, wPlayerDataEnd - wPlayerData + call CopyBytes + ld hl, wCurrMapData + ld de, sCurrMapData + ld bc, wCurrMapDataEnd - wCurrMapData + call CopyBytes + jp CloseSRAM +; 14df7 + +SavePokemonData: ; 14df7 + ld a, BANK(sPokemonData) + call GetSRAMBank + ld hl, wPokemonData + ld de, sPokemonData + ld bc, wPokemonDataEnd - wPokemonData + call CopyBytes + call CloseSRAM + ret +; 14e0c + +SaveBox: ; 14e0c + call GetBoxAddress + call SaveBoxAddress + ret +; 14e13 + +SaveChecksum: ; 14e13 + ld hl, sGameData + ld bc, sGameDataEnd - sGameData + ld a, BANK(sGameData) + call GetSRAMBank + call Checksum + ld a, e + ld [sChecksum + 0], a + ld a, d + ld [sChecksum + 1], a + call CloseSRAM + ret +; 14e2d + +ValidateBackupSave: ; 14e2d + ld a, BANK(sBackupCheckValue1) ; BANK(sBackupCheckValue2) + call GetSRAMBank + ld a, SAVE_CHECK_VALUE_1 + ld [sBackupCheckValue1], a + ld a, SAVE_CHECK_VALUE_2 + ld [sBackupCheckValue2], a + call CloseSRAM + ret +; 14e40 + +SaveBackupOptions: ; 14e40 + ld a, BANK(sBackupOptions) + call GetSRAMBank + ld hl, wOptions + ld de, sBackupOptions + ld bc, wOptionsEnd - wOptions + call CopyBytes + call CloseSRAM + ret +; 14e55 + +SaveBackupPlayerData: ; 14e55 + ld a, BANK(sBackupPlayerData) + call GetSRAMBank + ld hl, wPlayerData + ld de, sBackupPlayerData + ld bc, wPlayerDataEnd - wPlayerData + call CopyBytes + ld hl, wCurrMapData + ld de, sBackupCurrMapData + ld bc, wCurrMapDataEnd - wCurrMapData + call CopyBytes + call CloseSRAM + ret +; 14e76 + +SaveBackupPokemonData: ; 14e76 + ld a, BANK(sBackupPokemonData) + call GetSRAMBank + ld hl, wPokemonData + ld de, sBackupPokemonData + ld bc, wPokemonDataEnd - wPokemonData + call CopyBytes + call CloseSRAM + ret +; 14e8b + +SaveBackupChecksum: ; 14e8b + ld hl, sBackupGameData + ld bc, sBackupGameDataEnd - sBackupGameData + ld a, BANK(sBackupGameData) + call GetSRAMBank + call Checksum + ld a, e + ld [sBackupChecksum + 0], a + ld a, d + ld [sBackupChecksum + 1], a + call CloseSRAM + ret +; 14ea5 + + +TryLoadSaveFile: ; 14ea5 (5:4ea5) + call VerifyChecksum + jr nz, .backup + call LoadPlayerData + call LoadPokemonData + call LoadBox + farcall RestorePartyMonMail + farcall RestoreMobileEventIndex + farcall RestoreMysteryGift + call ValidateBackupSave + call SaveBackupOptions + call SaveBackupPlayerData + call SaveBackupPokemonData + call SaveBackupChecksum + and a + ret + +.backup + call VerifyBackupChecksum + jr nz, .corrupt + call LoadBackupPlayerData + call LoadBackupPokemonData + call LoadBox + farcall RestorePartyMonMail + farcall RestoreMobileEventIndex + farcall RestoreMysteryGift + call ValidateSave + call SaveOptions + call SavePlayerData + call SavePokemonData + call SaveChecksum + and a + ret + +.corrupt + ld a, [wOptions] + push af + set NO_TEXT_SCROLL, a + ld [wOptions], a + ld hl, Text_SaveFileCorrupted + call PrintText + pop af + ld [wOptions], a + scf + ret + + +TryLoadSaveData: ; 14f1c + xor a + ld [wSaveFileExists], a + call CheckPrimarySaveFile + ld a, [wSaveFileExists] + and a + jr z, .backup + + ld a, BANK(sPlayerData) + call GetSRAMBank + ld hl, sPlayerData + wStartDay - wPlayerData + ld de, wStartDay + ld bc, 8 + call CopyBytes + ld hl, sPlayerData + wStatusFlags - wPlayerData + ld de, wStatusFlags + ld a, [hl] + ld [de], a + call CloseSRAM + ret + +.backup + call CheckBackupSaveFile + ld a, [wSaveFileExists] + and a + jr z, .corrupt + + ld a, BANK(sBackupPlayerData) + call GetSRAMBank + ld hl, sBackupPlayerData + wStartDay - wPlayerData + ld de, wStartDay + ld bc, 8 + call CopyBytes + ld hl, sBackupPlayerData + wStatusFlags - wPlayerData + ld de, wStatusFlags + ld a, [hl] + ld [de], a + call CloseSRAM + ret + +.corrupt + ld hl, DefaultOptions + ld de, wOptions + ld bc, wOptionsEnd - wOptions + call CopyBytes + call PanicResetClock + ret +; 14f7c + + +INCLUDE "data/default_options.asm" + + +CheckPrimarySaveFile: ; 14f84 + ld a, BANK(sCheckValue1) ; BANK(sCheckValue2) + call GetSRAMBank + ld a, [sCheckValue1] + cp SAVE_CHECK_VALUE_1 + jr nz, .nope + ld a, [sCheckValue2] + cp SAVE_CHECK_VALUE_2 + jr nz, .nope + ld hl, sOptions + ld de, wOptions + ld bc, wOptionsEnd - wOptions + call CopyBytes + call CloseSRAM + ld a, $1 + ld [wSaveFileExists], a + +.nope + call CloseSRAM + ret +; 14faf + +CheckBackupSaveFile: ; 14faf + ld a, BANK(sBackupCheckValue1) ; BANK(sBackupCheckValue2) + call GetSRAMBank + ld a, [sBackupCheckValue1] + cp SAVE_CHECK_VALUE_1 + jr nz, .nope + ld a, [sBackupCheckValue2] + cp SAVE_CHECK_VALUE_2 + jr nz, .nope + ld hl, sBackupOptions + ld de, wOptions + ld bc, wOptionsEnd - wOptions + call CopyBytes + ld a, $2 + ld [wSaveFileExists], a + +.nope + call CloseSRAM + ret +; 14fd7 + + +LoadPlayerData: ; 14fd7 (5:4fd7) + ld a, BANK(sPlayerData) + call GetSRAMBank + ld hl, sPlayerData + ld de, wPlayerData + ld bc, wPlayerDataEnd - wPlayerData + call CopyBytes + ld hl, sCurrMapData + ld de, wCurrMapData + ld bc, wCurrMapDataEnd - wCurrMapData + call CopyBytes + call CloseSRAM + ld a, BANK(sBattleTowerChallengeState) + call GetSRAMBank + ld a, [sBattleTowerChallengeState] + cp BATTLETOWER_RECEIVED_REWARD + jr nz, .not_4 + ld a, BATTLETOWER_WON_CHALLENGE + ld [sBattleTowerChallengeState], a +.not_4 + call CloseSRAM + ret + +LoadPokemonData: ; 1500c + ld a, BANK(sPokemonData) + call GetSRAMBank + ld hl, sPokemonData + ld de, wPokemonData + ld bc, wPokemonDataEnd - wPokemonData + call CopyBytes + call CloseSRAM + ret +; 15021 + +LoadBox: ; 15021 (5:5021) + call GetBoxAddress + call LoadBoxAddress + ret + +VerifyChecksum: ; 15028 (5:5028) + ld hl, sGameData + ld bc, sGameDataEnd - sGameData + ld a, BANK(sGameData) + call GetSRAMBank + call Checksum + ld a, [sChecksum + 0] + cp e + jr nz, .fail + ld a, [sChecksum + 1] + cp d +.fail + push af + call CloseSRAM + pop af + ret + +LoadBackupPlayerData: ; 15046 (5:5046) + ld a, BANK(sBackupPlayerData) + call GetSRAMBank + ld hl, sBackupPlayerData + ld de, wPlayerData + ld bc, wPlayerDataEnd - wPlayerData + call CopyBytes + ld hl, sBackupCurrMapData + ld de, wCurrMapData + ld bc, wCurrMapDataEnd - wCurrMapData + call CopyBytes + call CloseSRAM + ret + +LoadBackupPokemonData: ; 15067 (5:5067) + ld a, BANK(sBackupPokemonData) + call GetSRAMBank + ld hl, sBackupPokemonData + ld de, wPokemonData + ld bc, wPokemonDataEnd - wPokemonData + call CopyBytes + call CloseSRAM + ret + +VerifyBackupChecksum: ; 1507c (5:507c) + ld hl, sBackupGameData + ld bc, sBackupGameDataEnd - sBackupGameData + ld a, BANK(sBackupGameData) + call GetSRAMBank + call Checksum + ld a, [sBackupChecksum + 0] + cp e + jr nz, .fail + ld a, [sBackupChecksum + 1] + cp d +.fail + push af + call CloseSRAM + pop af + ret + + +_SaveData: ; 1509a + ; This is called within two scenarios: + ; a) ErasePreviousSave (the process of erasing the save from a previous game file) + ; b) unused mobile functionality + ; It is not part of a regular save. + + ld a, BANK(sCrystalData) + call GetSRAMBank + ld hl, wCrystalData + ld de, sCrystalData + ld bc, wCrystalDataEnd - wCrystalData + call CopyBytes + + ; This block originally had some mobile functionality, but since we're still in + ; BANK(sCrystalData), it instead overwrites the sixteen wEventFlags starting at 1:a603 with + ; garbage from wd479. This isn't an issue, since ErasePreviousSave is followed by a regular + ; save that unwrites the garbage. + + ld hl, wd479 + ld a, [hli] + ld [$a60e + 0], a + ld a, [hli] + ld [$a60e + 1], a + + jp CloseSRAM + + +_LoadData: ; 150b9 + ld a, BANK(sCrystalData) + call GetSRAMBank + ld hl, sCrystalData + ld de, wCrystalData + ld bc, wCrystalDataEnd - wCrystalData + call CopyBytes + + ; This block originally had some mobile functionality to mirror _SaveData above, but instead it + ; (harmlessly) writes the aforementioned wEventFlags to the unused wd479. + + ld hl, wd479 + ld a, [$a60e + 0] + ld [hli], a + ld a, [$a60e + 1] + ld [hli], a + + jp CloseSRAM + + +GetBoxAddress: ; 150d8 + ld a, [wCurBox] + cp NUM_BOXES + jr c, .ok + xor a + ld [wCurBox], a + +.ok + ld e, a + ld d, 0 + ld hl, BoxAddresses +rept 5 + add hl, de +endr + ld a, [hli] + push af + ld a, [hli] + ld e, a + ld a, [hli] + ld d, a + ld a, [hli] + ld h, [hl] + ld l, a + pop af + ret +; 150f9 + +SaveBoxAddress: ; 150f9 +; Save box via wMisc. +; We do this in three steps because the size of wMisc is less than +; the size of sBox. + push hl +; Load the first part of the active box. + push af + push de + ld a, BANK(sBox) + call GetSRAMBank + ld hl, sBox + ld de, wMisc + ld bc, (wMiscEnd - wMisc) + call CopyBytes + call CloseSRAM + pop de + pop af +; Save it to the target box. + push af + push de + call GetSRAMBank + ld hl, wMisc + ld bc, (wMiscEnd - wMisc) + call CopyBytes + call CloseSRAM + +; Load the second part of the active box. + ld a, BANK(sBox) + call GetSRAMBank + ld hl, sBox + (wMiscEnd - wMisc) + ld de, wMisc + ld bc, (wMiscEnd - wMisc) + call CopyBytes + call CloseSRAM + pop de + pop af + + ld hl, (wMiscEnd - wMisc) + add hl, de + ld e, l + ld d, h +; Save it to the next part of the target box. + push af + push de + call GetSRAMBank + ld hl, wMisc + ld bc, (wMiscEnd - wMisc) + call CopyBytes + call CloseSRAM + +; Load the third and final part of the active box. + ld a, BANK(sBox) + call GetSRAMBank + ld hl, sBox + (wMiscEnd - wMisc) * 2 + ld de, wMisc + ld bc, sBoxEnd - (sBox + (wMiscEnd - wMisc) * 2) ; $8e + call CopyBytes + call CloseSRAM + pop de + pop af + + ld hl, (wMiscEnd - wMisc) + add hl, de + ld e, l + ld d, h +; Save it to the final part of the target box. + call GetSRAMBank + ld hl, wMisc + ld bc, sBoxEnd - (sBox + (wMiscEnd - wMisc) * 2) ; $8e + call CopyBytes + call CloseSRAM + + pop hl + ret +; 1517d + + +LoadBoxAddress: ; 1517d (5:517d) +; Load box via wMisc. +; We do this in three steps because the size of wMisc is less than +; the size of sBox. + push hl + ld l, e + ld h, d +; Load part 1 + push af + push hl + call GetSRAMBank + ld de, wMisc + ld bc, (wMiscEnd - wMisc) + call CopyBytes + call CloseSRAM + ld a, BANK(sBox) + call GetSRAMBank + ld hl, wMisc + ld de, sBox + ld bc, (wMiscEnd - wMisc) + call CopyBytes + call CloseSRAM + pop hl + pop af + + ld de, (wMiscEnd - wMisc) + add hl, de +; Load part 2 + push af + push hl + call GetSRAMBank + ld de, wMisc + ld bc, (wMiscEnd - wMisc) + call CopyBytes + call CloseSRAM + ld a, BANK(sBox) + call GetSRAMBank + ld hl, wMisc + ld de, sBox + (wMiscEnd - wMisc) + ld bc, (wMiscEnd - wMisc) + call CopyBytes + call CloseSRAM + pop hl + pop af +; Load part 3 + ld de, (wMiscEnd - wMisc) + add hl, de + call GetSRAMBank + ld de, wMisc + ld bc, sBoxEnd - (sBox + (wMiscEnd - wMisc) * 2) ; $8e + call CopyBytes + call CloseSRAM + ld a, BANK(sBox) + call GetSRAMBank + ld hl, wMisc + ld de, sBox + (wMiscEnd - wMisc) * 2 + ld bc, sBoxEnd - (sBox + (wMiscEnd - wMisc) * 2) ; $8e + call CopyBytes + call CloseSRAM + + pop hl + ret + + +EraseBoxes: ; 151fb + ld hl, BoxAddresses + ld c, NUM_BOXES +.next + push bc + ld a, [hli] + call GetSRAMBank + ld a, [hli] + ld e, a + ld a, [hli] + ld d, a + xor a + ld [de], a + inc de + ld a, -1 + ld [de], a + inc de + ld bc, sBoxEnd - (sBox + 2) +.clear + xor a + ld [de], a + inc de + dec bc + ld a, b + or c + jr nz, .clear + ld a, [hli] + ld e, a + ld a, [hli] + ld d, a + ld a, -1 + ld [de], a + inc de + xor a + ld [de], a + call CloseSRAM + pop bc + dec c + jr nz, .next + ret +; 1522d + +BoxAddresses: ; 1522d +; dbww bank, address, address + dbww BANK(sBox1), sBox1, sBox1End + dbww BANK(sBox2), sBox2, sBox2End + dbww BANK(sBox3), sBox3, sBox3End + dbww BANK(sBox4), sBox4, sBox4End + dbww BANK(sBox5), sBox5, sBox5End + dbww BANK(sBox6), sBox6, sBox6End + dbww BANK(sBox7), sBox7, sBox7End + dbww BANK(sBox8), sBox8, sBox8End + dbww BANK(sBox9), sBox9, sBox9End + dbww BANK(sBox10), sBox10, sBox10End + dbww BANK(sBox11), sBox11, sBox11End + dbww BANK(sBox12), sBox12, sBox12End + dbww BANK(sBox13), sBox13, sBox13End + dbww BANK(sBox14), sBox14, sBox14End +; 15273 + + +Checksum: ; 15273 + ld de, 0 +.loop + ld a, [hli] + add e + ld e, a + ld a, 0 + adc d + ld d, a + dec bc + ld a, b + or c + jr nz, .loop + ret +; 15283 + + +Text_WouldYouLikeToSaveTheGame: ; 0x15283 + ; Would you like to save the game? + text_jump UnknownText_0x1c454b + db "@" +; 0x15288 + +Text_SavingDontTurnOffThePower: ; 0x15288 + ; SAVING… DON'T TURN OFF THE POWER. + text_jump UnknownText_0x1c456d + db "@" +; 0x1528d + +Text_PlayerSavedTheGame: ; 0x1528d + ; saved the game. + text_jump UnknownText_0x1c4590 + db "@" +; 0x15292 + +Text_AlreadyASaveFile: ; 0x15292 + ; There is already a save file. Is it OK to overwrite? + text_jump UnknownText_0x1c45a3 + db "@" +; 0x15297 + +Text_AnotherSaveFile: ; 0x15297 + ; There is another save file. Is it OK to overwrite? + text_jump UnknownText_0x1c45d9 + db "@" +; 0x1529c + +Text_SaveFileCorrupted: ; 0x1529c + ; The save file is corrupted! + text_jump UnknownText_0x1c460d + db "@" +; 0x152a1 + +Text_SaveOnBoxSwitch: ; 0x152a1 + ; When you change a #MON BOX, data will be saved. OK? + text_jump UnknownText_0x1c462a + db "@" +; 0x152a6 + +Text_SaveOnMoveMonWOMail: ; 0x152a6 + ; Each time you move a #MON, data will be saved. OK? + text_jump UnknownText_0x1c465f + db "@" +; 0x152ab diff --git a/engine/menus/savemenu_copytilemapatonce.asm b/engine/menus/savemenu_copytilemapatonce.asm new file mode 100644 index 000000000..9b50494a4 --- /dev/null +++ b/engine/menus/savemenu_copytilemapatonce.asm @@ -0,0 +1,77 @@ +SaveMenu_CopyTilemapAtOnce: ; 4cf45 (13:4f45) + ld a, [hCGB] + and a + jp z, WaitBGMap + +; The following is a modified version of CopyTilemapAtOnce. + ld a, [hBGMapMode] + push af + xor a + ld [hBGMapMode], a + ld a, [hMapAnims] + push af + xor a + ld [hMapAnims], a +.WaitLY: + ld a, [rLY] + cp $60 + jr c, .WaitLY + + di + ld a, BANK(vBGMap2) + ld [rVBK], a + hlcoord 0, 0, wAttrMap + call .CopyTilemapAtOnce + ld a, BANK(vBGMap0) + ld [rVBK], a + hlcoord 0, 0 + call .CopyTilemapAtOnce +.WaitLY2: + ld a, [rLY] + cp $60 + jr c, .WaitLY2 + ei + + pop af + ld [hMapAnims], a + pop af + ld [hBGMapMode], a + ret + +.CopyTilemapAtOnce: ; 4cf80 (13:4f80) + ld [hSPBuffer], sp ; $ffd9 + ld sp, hl + ld a, [hBGMapAddress + 1] + ld h, a + ld l, 0 + ld a, SCREEN_HEIGHT + ld [hTilesPerCycle], a + ld b, 1 << 1 + ld c, LOW(rSTAT) + +.loop +rept SCREEN_WIDTH / 2 + pop de +.loop\@ + ld a, [$ff00+c] + and b + jr nz, .loop\@ + ld [hl], e + inc l + ld [hl], d + inc l +endr + + ld de, BG_MAP_WIDTH - SCREEN_WIDTH + add hl, de + ld a, [hTilesPerCycle] + dec a + ld [hTilesPerCycle], a + jr nz, .loop + + ld a, [hSPBuffer] + ld l, a + ld a, [hSPBuffer + 1] + ld h, a + ld sp, hl + ret diff --git a/engine/menus/scrolling_menu.asm b/engine/menus/scrolling_menu.asm new file mode 100644 index 000000000..3be3d839c --- /dev/null +++ b/engine/menus/scrolling_menu.asm @@ -0,0 +1,543 @@ +_InitScrollingMenu:: ; 245af + xor a + ld [wMenuJoypad], a + ld [hBGMapMode], a + inc a + ld [hInMenu], a + call InitScrollingMenuCursor + call ScrollingMenu_InitFlags + call ScrollingMenu_ValidateSwitchItem + call ScrollingMenu_InitDisplay + call ApplyTilemap + xor a + ld [hBGMapMode], a + ret +; 245cb + +_ScrollingMenu:: ; 245cb +.loop + call ScrollingMenuJoyAction + jp c, .exit + call z, .zero + jr .loop +; 245d6 + +.exit ; 245d6 + call MenuClickSound + ld [wMenuJoypad], a + ld a, 0 + ld [hInMenu], a + ret +; 245e1 + +.zero ; 245e1 + call ScrollingMenu_InitDisplay + ld a, 1 + ld [hBGMapMode], a + ld c, 3 + call DelayFrames + xor a + ld [hBGMapMode], a + ret +; 245f1 + +ScrollingMenu_InitDisplay: ; 245f1 + xor a + ld [hBGMapMode], a + ld hl, wOptions + ld a, [hl] + push af + set NO_TEXT_SCROLL, [hl] + call ScrollingMenu_UpdateDisplay + call ScrollingMenu_PlaceCursor + call ScrollingMenu_CheckCallFunction3 + pop af + ld [wOptions], a + ret +; 24609 + +ScrollingMenuJoyAction: ; 24609 +.loop + call ScrollingMenuJoypad + ld a, [hJoyLast] + and D_PAD + ld b, a + ld a, [hJoyPressed] + and BUTTONS + or b + bit A_BUTTON_F, a + jp nz, .a_button + bit B_BUTTON_F, a + jp nz, .b_button + bit SELECT_F, a + jp nz, .select + bit START_F, a + jp nz, .start + bit D_RIGHT_F, a + jp nz, .d_right + bit D_LEFT_F, a + jp nz, .d_left + bit D_UP_F, a + jp nz, .d_up + bit D_DOWN_F, a + jp nz, .d_down + jr .loop +; 24640 + +.unreferenced ; unused + ld a, -1 + and a + ret +; 24644 + +.a_button ; 24644 + call PlaceHollowCursor + ld a, [wMenuCursorY] + dec a + call ScrollingMenu_GetListItemCoordAndFunctionArgs + ld a, [wMenuSelection] + ld [wCurItem], a + ld a, [wMenuSelectionQuantity] + ld [wItemQuantityBuffer], a + call ScrollingMenu_GetCursorPosition + dec a + ld [wScrollingMenuCursorPosition], a + ld [wCurItemQuantity], a + ld a, [wMenuSelection] + cp -1 + jr z, .b_button + ld a, A_BUTTON + scf + ret +; 2466f + +.b_button ; 2466f + ld a, B_BUTTON + scf + ret +; 24673 + +.select ; 24673 + ld a, [wMenuDataFlags] + bit 7, a + jp z, xor_a_dec_a + ld a, [wMenuCursorY] + dec a + call ScrollingMenu_GetListItemCoordAndFunctionArgs + ld a, [wMenuSelection] + cp -1 + jp z, xor_a_dec_a + call ScrollingMenu_GetCursorPosition + dec a + ld [wScrollingMenuCursorPosition], a + ld a, SELECT + scf + ret +; 24695 + +.start ; 24695 + ld a, [wMenuDataFlags] + bit 6, a + jp z, xor_a_dec_a + ld a, START + scf + ret +; 246a1 + +.d_left ; 246a1 + ld hl, w2DMenuFlags2 + bit 7, [hl] + jp z, xor_a_dec_a + ld a, [wMenuDataFlags] + bit 3, a + jp z, xor_a_dec_a + ld a, D_LEFT + scf + ret +; 246b5 + +.d_right ; 246b5 + ld hl, w2DMenuFlags2 + bit 7, [hl] + jp z, xor_a_dec_a + ld a, [wMenuDataFlags] + bit 2, a + jp z, xor_a_dec_a + ld a, D_RIGHT + scf + ret +; 246c9 + +.d_up ; 246c9 + ld hl, w2DMenuFlags2 + bit 7, [hl] + jp z, xor_a + ld hl, wMenuScrollPosition + ld a, [hl] + and a + jr z, .xor_dec_up + dec [hl] + jp xor_a + +.xor_dec_up + jp xor_a_dec_a +; 246df + +.d_down ; 246df + ld hl, w2DMenuFlags2 + bit 7, [hl] + jp z, xor_a + ld hl, wMenuScrollPosition + ld a, [wMenuData_ScrollingMenuHeight] + add [hl] + ld b, a + ld a, [wScrollingMenuListSize] + cp b + jr c, .xor_dec_down + inc [hl] + jp xor_a + +.xor_dec_down + jp xor_a_dec_a +; 246fc + +ScrollingMenu_GetCursorPosition: ; 246fc + ld a, [wMenuScrollPosition] + ld c, a + ld a, [wMenuCursorY] + add c + ld c, a + ret +; 24706 + +ScrollingMenu_ClearLeftColumn: ; 24706 (9:4706) + call MenuBoxCoord2Tile + ld de, SCREEN_WIDTH + add hl, de + ld de, 2 * SCREEN_WIDTH + ld a, [wMenuData_ScrollingMenuHeight] +.loop + ld [hl], " " + add hl, de + dec a + jr nz, .loop + ret + +InitScrollingMenuCursor: ; 2471a + ld hl, wMenuData_ItemsPointerAddr + ld a, [hli] + ld h, [hl] + ld l, a + ld a, [wMenuData_ItemsPointerBank] + call GetFarByte + ld [wScrollingMenuListSize], a + ld a, [wMenuData_ScrollingMenuHeight] + ld c, a + ld a, [wMenuScrollPosition] + add c + ld c, a + ld a, [wScrollingMenuListSize] + inc a + cp c + jr nc, .skip + ld a, [wMenuData_ScrollingMenuHeight] + ld c, a + ld a, [wScrollingMenuListSize] + inc a + sub c + jr nc, .store + xor a + +.store + ld [wMenuScrollPosition], a + +.skip + ld a, [wMenuScrollPosition] + ld c, a + ld a, [wMenuCursorBuffer] + add c + ld b, a + ld a, [wScrollingMenuListSize] + inc a + cp b + jr c, .asm_2475a + jr nc, .asm_24763 + +.asm_2475a + xor a + ld [wMenuScrollPosition], a + ld a, $1 + ld [wMenuCursorBuffer], a + +.asm_24763 + ret +; 24764 + +ScrollingMenu_InitFlags: ; 24764 + ld a, [wMenuDataFlags] + ld c, a + ld a, [wScrollingMenuListSize] + ld b, a + ld a, [wMenuBorderTopCoord] + add 1 + ld [w2DMenuCursorInitY], a + ld a, [wMenuBorderLeftCoord] + add 0 + ld [w2DMenuCursorInitX], a + ld a, [wMenuData_ScrollingMenuHeight] + cp b + jr c, .no_extra_row + jr z, .no_extra_row + ld a, b + inc a +.no_extra_row + ld [w2DMenuNumRows], a + ld a, 1 + ld [w2DMenuNumCols], a + ld a, $8c + bit 2, c + jr z, .skip_set_0 + set 0, a + +.skip_set_0 + bit 3, c + jr z, .skip_set_1 + set 1, a + +.skip_set_1 + ld [w2DMenuFlags1], a + xor a + ld [w2DMenuFlags2], a + ld a, $20 + ld [w2DMenuCursorOffsets], a + ld a, A_BUTTON | B_BUTTON | D_UP | D_DOWN + bit 7, c + jr z, .disallow_select + add SELECT + +.disallow_select + bit 6, c + jr z, .disallow_start + add START + +.disallow_start + ld [wMenuJoypadFilter], a + ld a, [w2DMenuNumRows] + ld b, a + ld a, [wMenuCursorBuffer] + and a + jr z, .reset_cursor + cp b + jr z, .cursor_okay + jr c, .cursor_okay + +.reset_cursor + ld a, 1 + +.cursor_okay + ld [wMenuCursorY], a + ld a, 1 + ld [wMenuCursorX], a + xor a + ld [wCursorCurrentTile], a + ld [wCursorCurrentTile + 1], a + ld [wCursorOffCharacter], a + ret +; 247dd + +ScrollingMenu_ValidateSwitchItem: ; 247dd + ld a, [wScrollingMenuListSize] + ld c, a + ld a, [wSwitchItem] + and a + jr z, .done + dec a + cp c + jr c, .done + xor a + ld [wSwitchItem], a + +.done + ret +; 247f0 + +ScrollingMenu_UpdateDisplay: ; 247f0 + call ClearWholeMenuBox + ld a, [wMenuDataFlags] + bit 4, a ; place arrows + jr z, .okay + ld a, [wMenuScrollPosition] + and a + jr z, .okay + ld a, [wMenuBorderTopCoord] + ld b, a + ld a, [wMenuBorderRightCoord] + ld c, a + call Coord2Tile + ld [hl], "▲" + +.okay + call MenuBoxCoord2Tile + ld bc, SCREEN_WIDTH + 1 + add hl, bc + ld a, [wMenuData_ScrollingMenuHeight] + ld b, a + ld c, $0 +.loop + ld a, [wMenuScrollPosition] + add c + ld [wScrollingMenuCursorPosition], a + ld a, c + call ScrollingMenu_GetListItemCoordAndFunctionArgs + ld a, [wMenuSelection] + cp -1 + jr z, .cancel + push bc + push hl + call ScrollingMenu_CallFunctions1and2 + pop hl + ld bc, 2 * SCREEN_WIDTH + add hl, bc + pop bc + inc c + ld a, c + cp b + jr nz, .loop + ld a, [wMenuDataFlags] + bit 4, a ; place arrows + jr z, .done + ld a, [wMenuBorderBottomCoord] + ld b, a + ld a, [wMenuBorderRightCoord] + ld c, a + call Coord2Tile + ld [hl], "▼" + +.done + ret + +.cancel + ld a, [wMenuDataFlags] + bit 0, a ; call function on cancel + jr nz, .call_function + ld de, .string_2485f + call PlaceString + ret + +.string_2485f + db "CANCEL@" + +.call_function + ld d, h + ld e, l + ld hl, wMenuData_ScrollingMenuFunction1 + jp CallPointerAt +; 2486e + +ScrollingMenu_CallFunctions1and2: ; 2486e + push hl + ld d, h + ld e, l + ld hl, wMenuData_ScrollingMenuFunction1 + call CallPointerAt + pop hl + ld a, [wMenuData_ScrollingMenuWidth] + and a + jr z, .done + ld e, a + ld d, $0 + add hl, de + ld d, h + ld e, l + ld hl, wMenuData_ScrollingMenuFunction2 + call CallPointerAt + +.done + ret +; 2488b + +ScrollingMenu_PlaceCursor: ; 2488b + ld a, [wSwitchItem] + and a + jr z, .done + ld b, a + ld a, [wMenuScrollPosition] + cp b + jr nc, .done + ld c, a + ld a, [wMenuData_ScrollingMenuHeight] + add c + cp b + jr c, .done + ld a, b + sub c + dec a + add a + add $1 + ld c, a + ld a, [wMenuBorderTopCoord] + add c + ld b, a + ld a, [wMenuBorderLeftCoord] + add $0 + ld c, a + call Coord2Tile + ld [hl], "▷" + +.done + ret +; 248b8 + +ScrollingMenu_CheckCallFunction3: ; 248b8 + ld a, [wMenuDataFlags] + bit 5, a ; call function 3 + ret z + bit 1, a ; call function 3 if not switching items + jr z, .call + ld a, [wSwitchItem] + and a + ret nz + +.call + ld a, [wMenuCursorY] + dec a + call ScrollingMenu_GetListItemCoordAndFunctionArgs + ld hl, wMenuData_ScrollingMenuFunction3 + call CallPointerAt + ret +; 248d5 + +ScrollingMenu_GetListItemCoordAndFunctionArgs: ; 248d5 + push de + push hl + ld e, a + ld a, [wMenuScrollPosition] + add e + ld e, a + ld d, $0 + ld hl, wMenuData_ItemsPointerAddr + ld a, [hli] + ld h, [hl] + ld l, a + inc hl ; items + ld a, [wMenuData_ScrollingMenuSpacing] + cp 1 + jr z, .got_spacing + cp 2 + jr z, .pointless_jump +.pointless_jump + add hl, de +.got_spacing + add hl, de + ld a, [wMenuData_ItemsPointerBank] + call GetFarByte + ld [wMenuSelection], a + ld [wCurItem], a + inc hl + ld a, [wMenuData_ItemsPointerBank] + call GetFarByte + ld [wMenuSelectionQuantity], a + pop hl + pop de + ret +; 2490c diff --git a/engine/menus/start_menu.asm b/engine/menus/start_menu.asm new file mode 100644 index 000000000..037efd947 --- /dev/null +++ b/engine/menus/start_menu.asm @@ -0,0 +1,1993 @@ +; StartMenu.Items indexes + const_def + const STARTMENUITEM_POKEDEX ; 0 + const STARTMENUITEM_POKEMON ; 1 + const STARTMENUITEM_PACK ; 2 + const STARTMENUITEM_STATUS ; 3 + const STARTMENUITEM_SAVE ; 4 + const STARTMENUITEM_OPTION ; 5 + const STARTMENUITEM_EXIT ; 6 + const STARTMENUITEM_POKEGEAR ; 7 + const STARTMENUITEM_QUIT ; 8 + + +StartMenu:: ; 125cd + + call ClearWindowData + + ld de, SFX_MENU + call PlaySFX + + farcall ReanchorBGMap_NoOAMUpdate + + ld hl, wStatusFlags2 + bit STATUSFLAGS2_BUG_CONTEST_TIMER_F, [hl] + ld hl, .MenuHeader + jr z, .GotMenuData + ld hl, .ContestMenuHeader +.GotMenuData: + + call LoadMenuHeader + call .SetUpMenuItems + ld a, [wBattleMenuCursorBuffer] + ld [wMenuCursorBuffer], a + call .DrawMenuAccount_ + call DrawVariableLengthMenuBox + call .DrawBugContestStatusBox + call SafeUpdateSprites + call _OpenAndCloseMenu_HDMATransferTileMapAndAttrMap + farcall LoadFonts_NoOAMUpdate + call .DrawBugContestStatus + call UpdateTimePals + jr .Select + +.Reopen: + call UpdateSprites + call UpdateTimePals + call .SetUpMenuItems + ld a, [wBattleMenuCursorBuffer] + ld [wMenuCursorBuffer], a + +.Select: + call .GetInput + jr c, .Exit + call .DrawMenuAccount + ld a, [wMenuCursorBuffer] + ld [wBattleMenuCursorBuffer], a + call PlayClickSFX + call PlaceHollowCursor + call .OpenMenu + +; Menu items have different return functions. +; For example, saving exits the menu. + ld hl, .MenuReturns + ld e, a + ld d, 0 + add hl, de + add hl, de + ld a, [hli] + ld h, [hl] + ld l, a + jp hl + +.MenuReturns: + dw .Reopen + dw .Exit + dw .ExitMenuCallFuncCloseText + dw .ExitMenuRunScriptCloseText + dw .ExitMenuRunScript + dw .ReturnEnd + dw .ReturnRedraw + +.Exit: + ld a, [hOAMUpdate] + push af + ld a, 1 + ld [hOAMUpdate], a + call LoadFontsExtra + pop af + ld [hOAMUpdate], a +.ReturnEnd: + call ExitMenu +.ReturnEnd2: + call CloseText + call UpdateTimePals + ret + +.GetInput: +; Return carry on exit, and no-carry on selection. + xor a + ld [hBGMapMode], a + call .DrawMenuAccount + call SetUpMenu + ld a, $ff + ld [wMenuSelection], a +.loop + call .PrintMenuAccount + call GetScrollingMenuJoypad + ld a, [wMenuJoypad] + cp B_BUTTON + jr z, .b + cp A_BUTTON + jr z, .a + jr .loop +.a + call PlayClickSFX + and a + ret +.b + scf + ret +; 12691 + +.ExitMenuRunScript: ; 12691 + call ExitMenu + ld a, HMENURETURN_SCRIPT + ld [hMenuReturn], a + ret +; 12699 + +.ExitMenuRunScriptCloseText: ; 12699 + call ExitMenu + ld a, HMENURETURN_SCRIPT + ld [hMenuReturn], a + jr .ReturnEnd2 +; 126a2 + +.ExitMenuCallFuncCloseText: ; 126a2 + call ExitMenu + ld hl, wQueuedScriptAddr + ld a, [hli] + ld h, [hl] + ld l, a + ld a, [wQueuedScriptBank] + rst FarCall + jr .ReturnEnd2 +; 126b1 + +.ReturnRedraw: ; 126b1 + call .Clear + jp .Reopen +; 126b7 + +.Clear: ; 126b7 + call ClearBGPalettes + call Call_ExitMenu + call ReloadTilesetAndPalettes + call .DrawMenuAccount_ + call DrawVariableLengthMenuBox + call .DrawBugContestStatus + call UpdateSprites + call ret_d90 + call FinishExitMenu + ret +; 126d3 + + +.MenuHeader: + db MENU_BACKUP_TILES ; flags + menu_coords 10, 0, SCREEN_WIDTH - 1, SCREEN_HEIGHT - 1 + dw .MenuData + db 1 ; default selection + +.ContestMenuHeader: + db MENU_BACKUP_TILES ; flags + menu_coords 10, 2, SCREEN_WIDTH - 1, SCREEN_HEIGHT - 1 + dw .MenuData + db 1 ; default selection + +.MenuData: + db STATICMENU_CURSOR | STATICMENU_WRAP | STATICMENU_ENABLE_START ; flags + dn 0, 0 ; rows, columns + dw wMenuItemsList + dw .MenuString + dw .Items + +.Items: +; entries correspond to STARTMENUITEM_* constants + dw StartMenu_Pokedex, .PokedexString, .PokedexDesc + dw StartMenu_Pokemon, .PartyString, .PartyDesc + dw StartMenu_Pack, .PackString, .PackDesc + dw StartMenu_Status, .StatusString, .StatusDesc + dw StartMenu_Save, .SaveString, .SaveDesc + dw StartMenu_Option, .OptionString, .OptionDesc + dw StartMenu_Exit, .ExitString, .ExitDesc + dw StartMenu_Pokegear, .PokegearString, .PokegearDesc + dw StartMenu_Quit, .QuitString, .QuitDesc + +.PokedexString: db "#DEX@" +.PartyString: db "#MON@" +.PackString: db "PACK@" +.StatusString: db "<PLAYER>@" +.SaveString: db "SAVE@" +.OptionString: db "OPTION@" +.ExitString: db "EXIT@" +.PokegearString: db "<POKE>GEAR@" +.QuitString: db "QUIT@" + +.PokedexDesc: + db "#MON" + next "database@" + +.PartyDesc: + db "Party <PKMN>" + next "status@" + +.PackDesc: + db "Contains" + next "items@" + +.PokegearDesc: + db "Trainer's" + next "key device@" + +.StatusDesc: + db "Your own" + next "status@" + +.SaveDesc: + db "Save your" + next "progress@" + +.OptionDesc: + db "Change" + next "settings@" + +.ExitDesc: + db "Close this" + next "menu@" + +.QuitDesc: + db "Quit and" + next "be judged.@" + + +.OpenMenu: ; 127e5 + ld a, [wMenuSelection] + call .GetMenuAccountTextPointer + ld a, [hli] + ld h, [hl] + ld l, a + jp hl +; 127ef + +.MenuString: ; 127ef + push de + ld a, [wMenuSelection] + call .GetMenuAccountTextPointer + inc hl + inc hl + ld a, [hli] + ld d, [hl] + ld e, a + pop hl + call PlaceString + ret +; 12800 + +.MenuDesc: ; 12800 + push de + ld a, [wMenuSelection] + cp $ff + jr z, .none + call .GetMenuAccountTextPointer +rept 4 + inc hl +endr + ld a, [hli] + ld d, [hl] + ld e, a + pop hl + call PlaceString + ret +.none + pop de + ret +; 12819 + + +.GetMenuAccountTextPointer: ; 12819 + ld e, a + ld d, 0 + ld hl, wMenuDataPointerTableAddr + ld a, [hli] + ld h, [hl] + ld l, a +rept 6 + add hl, de +endr + ret +; 12829 + + +.SetUpMenuItems: ; 12829 + xor a + ld [wWhichIndexSet], a + call .FillMenuList + + ld hl, wStatusFlags + bit STATUSFLAGS_POKEDEX_F, [hl] + jr z, .no_pokedex + ld a, STARTMENUITEM_POKEDEX + call .AppendMenuList +.no_pokedex + + ld a, [wPartyCount] + and a + jr z, .no_pokemon + ld a, STARTMENUITEM_POKEMON + call .AppendMenuList +.no_pokemon + + ld a, [wLinkMode] + and a + jr nz, .no_pack + ld hl, wStatusFlags2 + bit STATUSFLAGS2_BUG_CONTEST_TIMER_F, [hl] + jr nz, .no_pack + ld a, STARTMENUITEM_PACK + call .AppendMenuList +.no_pack + + ld hl, wPokegearFlags + bit POKEGEAR_OBTAINED_F, [hl] + jr z, .no_pokegear + ld a, STARTMENUITEM_POKEGEAR + call .AppendMenuList +.no_pokegear + + ld a, STARTMENUITEM_STATUS + call .AppendMenuList + + ld a, [wLinkMode] + and a + jr nz, .no_save + ld hl, wStatusFlags2 + bit STATUSFLAGS2_BUG_CONTEST_TIMER_F, [hl] + ld a, STARTMENUITEM_QUIT + jr nz, .write + ld a, STARTMENUITEM_SAVE +.write + call .AppendMenuList +.no_save + + ld a, STARTMENUITEM_OPTION + call .AppendMenuList + ld a, STARTMENUITEM_EXIT + call .AppendMenuList + ld a, c + ld [wMenuItemsList], a + ret +; 1288d + + +.FillMenuList: ; 1288d + xor a + ld hl, wMenuItemsList + ld [hli], a + ld a, -1 + ld bc, wMenuItemsListEnd - (wMenuItemsList + 1) + call ByteFill + ld de, wMenuItemsList + 1 + ld c, 0 + ret +; 128a0 + +.AppendMenuList: ; 128a0 + ld [de], a + inc de + inc c + ret +; 128a4 + +.DrawMenuAccount_: ; 128a4 + jp .DrawMenuAccount +; 128a7 + +.PrintMenuAccount: ; 128a7 + call .IsMenuAccountOn + ret z + call .DrawMenuAccount + decoord 0, 14 + jp .MenuDesc +; 128b4 + +.DrawMenuAccount: ; 128b4 + call .IsMenuAccountOn + ret z + hlcoord 0, 13 + lb bc, 5, 10 + call ClearBox + hlcoord 0, 13 + ld b, 3 + ld c, 8 + jp TextBoxPalette +; 128cb + +.IsMenuAccountOn: ; 128cb + ld a, [wOptions2] + and 1 << MENU_ACCOUNT + ret +; 128d1 + +.DrawBugContestStatusBox: ; 128d1 + ld hl, wStatusFlags2 + bit STATUSFLAGS2_BUG_CONTEST_TIMER_F, [hl] + ret z + farcall StartMenu_DrawBugContestStatusBox + ret +; 128de + +.DrawBugContestStatus: ; 128de + ld hl, wStatusFlags2 + bit STATUSFLAGS2_BUG_CONTEST_TIMER_F, [hl] + jr nz, .contest + ret +.contest + farcall StartMenu_PrintBugContestStatus + ret +; 128ed + + +StartMenu_Exit: ; 128ed +; Exit the menu. + + ld a, 1 + ret +; 128f0 + + +StartMenu_Quit: ; 128f0 +; Retire from the bug catching contest. + + ld hl, .EndTheContestText + call StartMenuYesNo + jr c, .DontEndContest + ld a, BANK(BugCatchingContestReturnToGateScript) + ld hl, BugCatchingContestReturnToGateScript + call FarQueueScript + ld a, 4 + ret + +.DontEndContest: + ld a, 0 + ret + +.EndTheContestText: + text_jump UnknownText_0x1c1a6c + db "@" +; 1290b + + +StartMenu_Save: ; 1290b +; Save the game. + + call BufferScreen + farcall SaveMenu + jr nc, .asm_12919 + ld a, 0 + ret +.asm_12919 + ld a, 1 + ret +; 1291c + + +StartMenu_Option: ; 1291c +; Game options. + + call FadeToMenu + farcall OptionsMenu + ld a, 6 + ret +; 12928 + + +StartMenu_Status: ; 12928 +; Player status. + + call FadeToMenu + farcall TrainerCard + call CloseSubmenu + ld a, 0 + ret +; 12937 + + +StartMenu_Pokedex: ; 12937 + + ld a, [wPartyCount] + and a + jr z, .asm_12949 + + call FadeToMenu + farcall Pokedex + call CloseSubmenu + +.asm_12949 + ld a, 0 + ret +; 1294c + + +StartMenu_Pokegear: ; 1294c + + call FadeToMenu + farcall PokeGear + call CloseSubmenu + ld a, 0 + ret +; 1295b + + +StartMenu_Pack: ; 1295b + + call FadeToMenu + farcall Pack + ld a, [wPackUsedItem] + and a + jr nz, .used_item + call CloseSubmenu + ld a, 0 + ret + +.used_item + call ExitAllMenus + ld a, 4 + ret +; 12976 + + +StartMenu_Pokemon: ; 12976 + + ld a, [wPartyCount] + and a + jr z, .return + + call FadeToMenu + +.choosemenu + xor a + ld [wPartyMenuActionText], a ; Choose a POKéMON. + call ClearBGPalettes + +.menu + farcall LoadPartyMenuGFX + farcall InitPartyMenuWithCancel + farcall InitPartyMenuGFX + +.menunoreload + farcall WritePartyMenuTilemap + farcall PrintPartyMenuText + call WaitBGMap + call SetPalettes ; load regular palettes? + call DelayFrame + farcall PartyMenuSelect + jr c, .return ; if cancelled or pressed B + + call PokemonActionSubmenu + cp 3 + jr z, .menu + cp 0 + jr z, .choosemenu + cp 1 + jr z, .menunoreload + cp 2 + jr z, .quit + +.return + call CloseSubmenu + ld a, 0 + ret + +.quit + ld a, b + push af + call ExitAllMenus + pop af + ret +; 129d5 + +HasNoItems: ; 129d5 + ld a, [wNumItems] + and a + ret nz + ld a, [wNumKeyItems] + and a + ret nz + ld a, [wNumBalls] + and a + ret nz + ld hl, wTMsHMs + ld b, NUM_TMS + NUM_HMS +.loop + ld a, [hli] + and a + jr nz, .done + dec b + jr nz, .loop + scf + ret +.done + and a + ret + +TossItemFromPC: ; 129f4 + push de + call PartyMonItemName + farcall _CheckTossableItem + ld a, [wItemAttributeParamBuffer] + and a + jr nz, .key_item + ld hl, .TossHowMany + call MenuTextBox + farcall SelectQuantityToToss + push af + call CloseWindow + call ExitMenu + pop af + jr c, .quit + ld hl, .ConfirmToss + call MenuTextBox + call YesNoBox + push af + call ExitMenu + pop af + jr c, .quit + pop hl + ld a, [wCurItemQuantity] + call TossItem + call PartyMonItemName + ld hl, .TossedThisMany + call MenuTextBox + call ExitMenu + and a + ret + +.key_item + call .CantToss +.quit + pop hl + scf + ret + +.TossHowMany: + ; Toss out how many @ (S)? + text_jump UnknownText_0x1c1a90 + db "@" + +.ConfirmToss: + ; Throw away @ @ (S)? + text_jump UnknownText_0x1c1aad + db "@" + +.TossedThisMany: + ; Discarded @ (S). + text_jump UnknownText_0x1c1aca + db "@" + +.CantToss: + ld hl, .TooImportantToToss + call MenuTextBoxBackup + ret + +.TooImportantToToss: + ; That's too impor- tant to toss out! + text_jump UnknownText_0x1c1adf + db "@" +; 0x12a60 + +CantUseItem: ; 12a60 + ld hl, CantUseItemText + call MenuTextBoxWaitButton + ret +; 12a67 + +CantUseItemText: ; 12a67 + text_jump UnknownText_0x1c1b03 + db "@" +; 12a6c + + +PartyMonItemName: ; 12a6c + ld a, [wCurItem] + ld [wd265], a + call GetItemName + call CopyName1 + ret +; 12a79 + + +CancelPokemonAction: ; 12a79 + farcall InitPartyMenuWithCancel + farcall UnfreezeMonIcons + ld a, 1 + ret +; 12a88 + + +PokemonActionSubmenu: ; 12a88 + hlcoord 1, 15 + lb bc, 2, 18 + call ClearBox + farcall MonSubmenu + call GetCurNick + ld a, [wMenuSelection] + ld hl, .Actions + ld de, 3 + call IsInArray + jr nc, .nothing + + inc hl + ld a, [hli] + ld h, [hl] + ld l, a + jp hl + +.nothing + ld a, 0 + ret + +.Actions: + dbw MONMENUITEM_CUT, MonMenu_Cut + dbw MONMENUITEM_FLY, MonMenu_Fly + dbw MONMENUITEM_SURF, MonMenu_Surf + dbw MONMENUITEM_STRENGTH, MonMenu_Strength + dbw MONMENUITEM_FLASH, MonMenu_Flash + dbw MONMENUITEM_WHIRLPOOL, MonMenu_Whirlpool + dbw MONMENUITEM_DIG, MonMenu_Dig + dbw MONMENUITEM_TELEPORT, MonMenu_Teleport + dbw MONMENUITEM_SOFTBOILED, MonMenu_Softboiled_MilkDrink + dbw MONMENUITEM_MILKDRINK, MonMenu_Softboiled_MilkDrink + dbw MONMENUITEM_HEADBUTT, MonMenu_Headbutt + dbw MONMENUITEM_WATERFALL, MonMenu_Waterfall + dbw MONMENUITEM_ROCKSMASH, MonMenu_RockSmash + dbw MONMENUITEM_SWEETSCENT, MonMenu_SweetScent + dbw MONMENUITEM_STATS, OpenPartyStats + dbw MONMENUITEM_SWITCH, SwitchPartyMons + dbw MONMENUITEM_ITEM, GiveTakePartyMonItem + dbw MONMENUITEM_CANCEL, CancelPokemonAction + dbw MONMENUITEM_MOVE, ManagePokemonMoves + dbw MONMENUITEM_MAIL, MonMailAction +; 12aec + + +SwitchPartyMons: ; 12aec + +; Don't try if there's nothing to switch! + ld a, [wPartyCount] + cp 2 + jr c, .DontSwitch + + ld a, [wCurPartyMon] + inc a + ld [wSwitchMon], a + + farcall HoldSwitchmonIcon + farcall InitPartyMenuNoCancel + + ld a, PARTYMENUACTION_MOVE + ld [wPartyMenuActionText], a + farcall WritePartyMenuTilemap + farcall PrintPartyMenuText + + hlcoord 0, 1 + ld bc, SCREEN_WIDTH * 2 + ld a, [wSwitchMon] + dec a + call AddNTimes + ld [hl], "▷" + call WaitBGMap + call SetPalettes + call DelayFrame + + farcall PartyMenuSelect + bit 1, b + jr c, .DontSwitch + + farcall _SwitchPartyMons + + xor a + ld [wPartyMenuActionText], a + + farcall LoadPartyMenuGFX + farcall InitPartyMenuWithCancel + farcall InitPartyMenuGFX + + ld a, 1 + ret + +.DontSwitch: + xor a + ld [wPartyMenuActionText], a + call CancelPokemonAction + ret +; 12b60 + + +GiveTakePartyMonItem: ; 12b60 + +; Eggs can't hold items! + ld a, [wCurPartySpecies] + cp EGG + jr z, .cancel + + ld hl, GiveTakeItemMenuData + call LoadMenuHeader + call VerticalMenu + call ExitMenu + jr c, .cancel + + call GetCurNick + ld hl, wStringBuffer1 + ld de, wMonOrItemNameBuffer + ld bc, MON_NAME_LENGTH + call CopyBytes + ld a, [wMenuCursorY] + cp 1 + jr nz, .take + + call LoadStandardMenuHeader + call ClearPalettes + call .GiveItem + call ClearPalettes + call LoadFontsBattleExtra + call ExitMenu + ld a, 0 + ret + +.take + call TakePartyItem + ld a, 3 + ret + +.cancel + ld a, 3 + ret +; 12ba9 + + +.GiveItem: + + farcall DepositSellInitPackBuffers + +.loop + farcall DepositSellPack + + ld a, [wcf66] + and a + jr z, .quit + + ld a, [wcf65] + cp 2 + jr z, .next + + call CheckTossableItem + ld a, [wItemAttributeParamBuffer] + and a + jr nz, .next + + call TryGiveItemToPartymon + jr .quit + +.next + ld hl, CantBeHeldText + call MenuTextBoxBackup + jr .loop + +.quit + ret +; 12bd9 + + +TryGiveItemToPartymon: ; 12bd9 + + call SpeechTextBox + call PartyMonItemName + call GetPartyItemLocation + ld a, [hl] + and a + jr z, .give_item_to_mon + + push hl + ld d, a + farcall ItemIsMail + pop hl + jr c, .please_remove_mail + ld a, [hl] + jr .already_holding_item + +.give_item_to_mon + call GiveItemToPokemon + ld hl, MadeHoldText + call MenuTextBoxBackup + call GivePartyItem + ret + +.please_remove_mail + ld hl, PleaseRemoveMailText + call MenuTextBoxBackup + ret + +.already_holding_item + ld [wd265], a + call GetItemName + ld hl, SwitchAlreadyHoldingText + call StartMenuYesNo + jr c, .abort + + call GiveItemToPokemon + ld a, [wd265] + push af + ld a, [wCurItem] + ld [wd265], a + pop af + ld [wCurItem], a + call ReceiveItemFromPokemon + jr nc, .bag_full + + ld hl, TookAndMadeHoldText + call MenuTextBoxBackup + ld a, [wd265] + ld [wCurItem], a + call GivePartyItem + ret + +.bag_full + ld a, [wd265] + ld [wCurItem], a + call ReceiveItemFromPokemon + ld hl, ItemStorageIsFullText + call MenuTextBoxBackup + +.abort + ret +; 12c4c + + +GivePartyItem: ; 12c4c + + call GetPartyItemLocation + ld a, [wCurItem] + ld [hl], a + ld d, a + farcall ItemIsMail + jr nc, .done + call ComposeMailMessage + +.done + ret +; 12c60 + + +TakePartyItem: ; 12c60 + + call SpeechTextBox + call GetPartyItemLocation + ld a, [hl] + and a + jr z, .asm_12c8c + + ld [wCurItem], a + call ReceiveItemFromPokemon + jr nc, .asm_12c94 + + farcall ItemIsMail + call GetPartyItemLocation + ld a, [hl] + ld [wd265], a + ld [hl], NO_ITEM + call GetItemName + ld hl, TookFromText + call MenuTextBoxBackup + jr .asm_12c9a + +.asm_12c8c + ld hl, IsntHoldingAnythingText + call MenuTextBoxBackup + jr .asm_12c9a + +.asm_12c94 + ld hl, ItemStorageIsFullText + call MenuTextBoxBackup + +.asm_12c9a + ret +; 12c9b + + +GiveTakeItemMenuData: ; 12c9b + db MENU_SPRITE_ANIMS | MENU_BACKUP_TILES ; flags + menu_coords 12, 12, SCREEN_WIDTH - 1, SCREEN_HEIGHT - 1 + dw .Items + db 1 ; default option + +.Items: + db STATICMENU_CURSOR ; flags + db 2 ; # items + db "GIVE@" + db "TAKE@" +; 12caf + + +TookAndMadeHoldText: ; 12caf + text_jump UnknownText_0x1c1b2c + db "@" +; 12cb4 + +MadeHoldText: ; 12cb4 + text_jump UnknownText_0x1c1b57 + db "@" +; 12cb9 + +PleaseRemoveMailText: ; 12cb9 + text_jump UnknownText_0x1c1b6f + db "@" +; 12cbe + +IsntHoldingAnythingText: ; 12cbe + text_jump UnknownText_0x1c1b8e + db "@" +; 12cc3 + +ItemStorageIsFullText: ; 12cc3 + text_jump UnknownText_0x1c1baa + db "@" +; 12cc8 + +TookFromText: ; 12cc8 + text_jump UnknownText_0x1c1bc4 + db "@" +; 12ccd + +SwitchAlreadyHoldingText: ; 12ccd + text_jump UnknownText_0x1c1bdc + db "@" +; 12cd2 + +CantBeHeldText: ; 12cd2 + text_jump UnknownText_0x1c1c09 + db "@" +; 12cd7 + + +GetPartyItemLocation: ; 12cd7 + push af + ld a, MON_ITEM + call GetPartyParamLocation + pop af + ret +; 12cdf + + +ReceiveItemFromPokemon: ; 12cdf + ld a, 1 + ld [wItemQuantityChangeBuffer], a + ld hl, wNumItems + jp ReceiveItem +; 12cea + + +GiveItemToPokemon: ; 12cea (4:6cea) + ld a, 1 + ld [wItemQuantityChangeBuffer], a + ld hl, wNumItems + jp TossItem + +StartMenuYesNo: ; 12cf5 + call MenuTextBox + call YesNoBox + jp ExitMenu +; 12cfe + + +ComposeMailMessage: ; 12cfe (4:6cfe) + ld de, wTempMailMessage + farcall _ComposeMailMessage + ld hl, wPlayerName + ld de, wTempMailAuthor + ld bc, NAME_LENGTH - 1 + call CopyBytes + ld hl, wPlayerID + ld bc, 2 + call CopyBytes + ld a, [wCurPartySpecies] + ld [de], a + inc de + ld a, [wCurItem] + ld [de], a + ld a, [wCurPartyMon] + ld hl, sPartyMail + ld bc, MAIL_STRUCT_LENGTH + call AddNTimes + ld d, h + ld e, l + ld hl, wTempMail + ld bc, MAIL_STRUCT_LENGTH + ld a, BANK(sPartyMail) + call GetSRAMBank + call CopyBytes + call CloseSRAM + ret + +MonMailAction: ; 12d45 +; If in the time capsule or trade center, +; selecting the mail only allows you to +; read the mail. + ld a, [wLinkMode] + cp LINK_TIMECAPSULE + jr z, .read + cp LINK_TRADECENTER + jr z, .read + +; Show the READ/TAKE/QUIT menu. + ld hl, .MenuHeader + call LoadMenuHeader + call VerticalMenu + call ExitMenu + +; Interpret the menu. + jp c, .done + ld a, [wMenuCursorY] + cp $1 + jr z, .read + cp $2 + jr z, .take + jp .done + +.read + farcall ReadPartyMonMail + ld a, $0 + ret + +.take + ld hl, .sendmailtopctext + call StartMenuYesNo + jr c, .RemoveMailToBag + ld a, [wCurPartyMon] + ld b, a + farcall SendMailToPC + jr c, .MailboxFull + ld hl, .sentmailtopctext + call MenuTextBoxBackup + jr .done + +.MailboxFull: + ld hl, .mailboxfulltext + call MenuTextBoxBackup + jr .done + +.RemoveMailToBag: + ld hl, .mailwilllosemessagetext + call StartMenuYesNo + jr c, .done + call GetPartyItemLocation + ld a, [hl] + ld [wCurItem], a + call ReceiveItemFromPokemon + jr nc, .BagIsFull + call GetPartyItemLocation + ld [hl], $0 + call GetCurNick + ld hl, .tookmailfrommontext + call MenuTextBoxBackup + jr .done + +.BagIsFull: + ld hl, .bagfulltext + call MenuTextBoxBackup + jr .done + +.done + ld a, $3 + ret +; 12dc9 + + +.MenuHeader: + db MENU_BACKUP_TILES ; flags + menu_coords 12, 10, SCREEN_WIDTH - 1, SCREEN_HEIGHT - 1 + dw .MenuData + db 1 ; default option +; 0x12dd1 + +.MenuData: + db STATICMENU_CURSOR ; flags + db 3 ; items + db "READ@" + db "TAKE@" + db "QUIT@" +; 0x12de2 + + +.mailwilllosemessagetext +; The MAIL will lose its message. OK? + text_jump UnknownText_0x1c1c22 + db "@" +; 0x12de7 + +.tookmailfrommontext +; MAIL detached from <POKEMON>. + text_jump UnknownText_0x1c1c47 + db "@" +; 0x12dec + +.bagfulltext +; There's no space for removing MAIL. + text_jump UnknownText_0x1c1c62 + db "@" +; 0x12df1 + +.sendmailtopctext +; Send the removed MAIL to your PC? + text_jump UnknownText_0x1c1c86 + db "@" +; 0x12df6 + +.mailboxfulltext +; Your PC's MAILBOX is full. + text_jump UnknownText_0x1c1ca9 + db "@" +; 0x12dfb + +.sentmailtopctext +; The MAIL was sent to your PC. + text_jump UnknownText_0x1c1cc4 + db "@" +; 0x12e00 + + +OpenPartyStats: ; 12e00 + call LoadStandardMenuHeader + call ClearSprites +; PartyMon + xor a + ld [wMonType], a + call LowVolume + predef StatsScreenInit + call MaxVolume + call Call_ExitMenu + ld a, 0 + ret +; 12e1b + + +MonMenu_Cut: ; 12e1b + farcall CutFunction + ld a, [wFieldMoveSucceeded] + cp $1 + jr nz, .Fail + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret +; 12e30 + + +MonMenu_Fly: ; 12e30 + farcall FlyFunction + ld a, [wFieldMoveSucceeded] + cp $2 + jr z, .Fail + cp $0 + jr z, .Error + farcall StubbedTrainerRankings_Fly + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret + +.Error: + ld a, $0 + ret + +.Unreferenced: + ld a, $1 + ret +; 12e55 + +MonMenu_Flash: ; 12e55 + farcall OWFlash + ld a, [wFieldMoveSucceeded] + cp $1 + jr nz, .Fail + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret +; 12e6a + +MonMenu_Strength: ; 12e6a + farcall StrengthFunction + ld a, [wFieldMoveSucceeded] + cp $1 + jr nz, .Fail + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret +; 12e7f + +MonMenu_Whirlpool: ; 12e7f + farcall WhirlpoolFunction + ld a, [wFieldMoveSucceeded] + cp $1 + jr nz, .Fail + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret +; 12e94 + +MonMenu_Waterfall: ; 12e94 + farcall WaterfallFunction + ld a, [wFieldMoveSucceeded] + cp $1 + jr nz, .Fail + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret +; 12ea9 + +MonMenu_Teleport: ; 12ea9 + farcall TeleportFunction + ld a, [wFieldMoveSucceeded] + and a + jr z, .Fail + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret +; 12ebd + +MonMenu_Surf: ; 12ebd + farcall SurfFunction + ld a, [wFieldMoveSucceeded] + and a + jr z, .Fail + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret +; 12ed1 + +MonMenu_Dig: ; 12ed1 + farcall DigFunction + ld a, [wFieldMoveSucceeded] + cp $1 + jr nz, .Fail + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret +; 12ee6 + +MonMenu_Softboiled_MilkDrink: ; 12ee6 + call .CheckMonHasEnoughHP + jr nc, .NotEnoughHP + farcall Softboiled_MilkDrinkFunction + jr .finish + +.NotEnoughHP: + ld hl, .Text_NotEnoughHP + call PrintText + +.finish + xor a + ld [wPartyMenuActionText], a + ld a, $3 + ret +; 12f00 + +.Text_NotEnoughHP: + ; Not enough HP! + text_jump UnknownText_0x1c1ce3 + db "@" +; 0x12f05 + +.CheckMonHasEnoughHP: +; Need to have at least (MaxHP / 5) HP left. + ld a, MON_MAXHP + call GetPartyParamLocation + ld a, [hli] + ld [hDividend + 0], a + ld a, [hl] + ld [hDividend + 1], a + ld a, 5 + ld [hDivisor], a + ld b, 2 + call Divide + ld a, MON_HP + 1 + call GetPartyParamLocation + ld a, [hQuotient + 2] + sub [hl] + dec hl + ld a, [hQuotient + 1] + sbc [hl] + ret +; 12f26 + +MonMenu_Headbutt: ; 12f26 + farcall HeadbuttFunction + ld a, [wFieldMoveSucceeded] + cp $1 + jr nz, .Fail + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret +; 12f3b + +MonMenu_RockSmash: ; 12f3b + farcall RockSmashFunction + ld a, [wFieldMoveSucceeded] + cp $1 + jr nz, .Fail + ld b, $4 + ld a, $2 + ret + +.Fail: + ld a, $3 + ret +; 12f50 + +MonMenu_SweetScent: ; 12f50 + farcall SweetScentFromMenu + ld b, $4 + ld a, $2 + ret +; 12f5b + +ChooseMoveToDelete: ; 12f5b + ld hl, wOptions + ld a, [hl] + push af + set NO_TEXT_SCROLL, [hl] + call LoadFontsBattleExtra + call .ChooseMoveToDelete + pop bc + ld a, b + ld [wOptions], a + push af + call ClearBGPalettes + pop af + ret +; 12f73 + +.ChooseMoveToDelete + call SetUpMoveScreenBG + ld de, DeleteMoveScreenAttrs + call SetMenuAttributes + call SetUpMoveList + ld hl, w2DMenuFlags1 + set 6, [hl] + jr .enter_loop + +.loop + call ScrollingMenuJoypad + bit B_BUTTON_F, a + jp nz, .b_button + bit A_BUTTON_F, a + jp nz, .a_button + +.enter_loop + call PrepareToPlaceMoveData + call PlaceMoveData + jp .loop +; 12f9c + +.a_button + and a + jr .finish + +.b_button + scf + +.finish + push af + xor a + ld [wSwitchMon], a + ld hl, w2DMenuFlags1 + res 6, [hl] + call ClearSprites + call ClearTileMap + pop af + ret +; 12fb2 + +DeleteMoveScreenAttrs: ; 12fb2 + db 3, 1 + db 3, 1 + db $40, $00 + dn 2, 0 + db D_UP | D_DOWN | A_BUTTON | B_BUTTON +; 12fba + +ManagePokemonMoves: ; 12fba + ld a, [wCurPartySpecies] + cp EGG + jr z, .egg + ld hl, wOptions + ld a, [hl] + push af + set NO_TEXT_SCROLL, [hl] + call MoveScreenLoop + pop af + ld [wOptions], a + call ClearBGPalettes + +.egg + ld a, $0 + ret +; 12fd5 + +MoveScreenLoop: ; 12fd5 + ld a, [wCurPartyMon] + inc a + ld [wPartyMenuCursor], a + call SetUpMoveScreenBG + call Function132d3 + ld de, MoveScreenAttributes + call SetMenuAttributes +.loop + call SetUpMoveList + ld hl, w2DMenuFlags1 + set 6, [hl] + jr .skip_joy + +.joy_loop + call ScrollingMenuJoypad + bit 1, a + jp nz, .b_button + bit 0, a + jp nz, .a_button + bit 4, a + jp nz, .d_right + bit 5, a + jp nz, .d_left + +.skip_joy + call PrepareToPlaceMoveData + ld a, [wMoveSwapBuffer] + and a + jr nz, .moving_move + call PlaceMoveData + jp .joy_loop + +.moving_move + ld a, " " + hlcoord 1, 11 + ld bc, 5 + call ByteFill + hlcoord 1, 12 + lb bc, 5, SCREEN_WIDTH - 2 + call ClearBox + hlcoord 1, 12 + ld de, String_MoveWhere + call PlaceString + jp .joy_loop +.b_button + call PlayClickSFX + call WaitSFX + ld a, [wMoveSwapBuffer] + and a + jp z, .exit + + ld a, [wMoveSwapBuffer] + ld [wMenuCursorY], a + xor a + ld [wMoveSwapBuffer], a + hlcoord 1, 2 + lb bc, 8, SCREEN_WIDTH - 2 + call ClearBox + jp .loop +; 1305b + +.d_right + ld a, [wMoveSwapBuffer] + and a + jp nz, .joy_loop + + ld a, [wCurPartyMon] + ld b, a + push bc + call .cycle_right + pop bc + ld a, [wCurPartyMon] + cp b + jp z, .joy_loop + jp MoveScreenLoop + +.d_left + ld a, [wMoveSwapBuffer] + and a + jp nz, .joy_loop + ld a, [wCurPartyMon] + ld b, a + push bc + call .cycle_left + pop bc + ld a, [wCurPartyMon] + cp b + jp z, .joy_loop + jp MoveScreenLoop + +.cycle_right + ld a, [wCurPartyMon] + inc a + ld [wCurPartyMon], a + ld c, a + ld b, 0 + ld hl, wPartySpecies + add hl, bc + ld a, [hl] + cp -1 + jr z, .cycle_left + cp EGG + ret nz + jr .cycle_right + +.cycle_left + ld a, [wCurPartyMon] + and a + ret z +.cycle_left_loop + ld a, [wCurPartyMon] + dec a + ld [wCurPartyMon], a + ld c, a + ld b, 0 + ld hl, wPartySpecies + add hl, bc + ld a, [hl] + cp EGG + ret nz + ld a, [wCurPartyMon] + and a + jr z, .cycle_right + jr .cycle_left_loop +; 130c6 + +.a_button + call PlayClickSFX + call WaitSFX + ld a, [wMoveSwapBuffer] + and a + jr nz, .place_move + ld a, [wMenuCursorY] + ld [wMoveSwapBuffer], a + call PlaceHollowCursor + jp .moving_move + +.place_move + ld hl, wPartyMon1Moves + ld bc, PARTYMON_STRUCT_LENGTH + ld a, [wCurPartyMon] + call AddNTimes + push hl + call .copy_move + pop hl + ld bc, $15 + add hl, bc + call .copy_move + ld a, [wBattleMode] + jr z, .swap_moves + ld hl, wBattleMonMoves + ld bc, $20 + ld a, [wCurPartyMon] + call AddNTimes + push hl + call .copy_move + pop hl + ld bc, 6 + add hl, bc + call .copy_move + +.swap_moves + ld de, SFX_SWITCH_POKEMON + call PlaySFX + call WaitSFX + ld de, SFX_SWITCH_POKEMON + call PlaySFX + call WaitSFX + hlcoord 1, 2 + lb bc, 8, 18 + call ClearBox + hlcoord 10, 10 + lb bc, 1, 9 + call ClearBox + jp .loop +; 1313a + +.copy_move + push hl + ld a, [wMenuCursorY] + dec a + ld c, a + ld b, $0 + add hl, bc + ld d, h + ld e, l + pop hl + ld a, [wMoveSwapBuffer] + dec a + ld c, a + ld b, $0 + add hl, bc + ld a, [de] + ld b, [hl] + ld [hl], a + ld a, b + ld [de], a + ret +; 13154 + +.exit + xor a + ld [wMoveSwapBuffer], a + ld hl, w2DMenuFlags1 + res 6, [hl] + call ClearSprites + jp ClearTileMap +; 13163 + +MoveScreenAttributes: ; 13163 + db 3, 1 + db 3, 1 + db $40, $00 + dn 2, 0 + db D_UP | D_DOWN | D_LEFT | D_RIGHT | A_BUTTON | B_BUTTON +; 1316b + +String_MoveWhere: ; 1316b + db "Where?@" +; 13172 + +SetUpMoveScreenBG: ; 13172 + call ClearBGPalettes + call ClearTileMap + call ClearSprites + xor a + ld [hBGMapMode], a + farcall LoadStatsScreenPageTilesGFX + farcall ClearSpriteAnims2 + ld a, [wCurPartyMon] + ld e, a + ld d, $0 + ld hl, wPartySpecies + add hl, de + ld a, [hl] + ld [wd265], a + ld e, $2 + farcall LoadMenuMonIcon + hlcoord 0, 1 + ld b, 9 + ld c, 18 + call TextBox + hlcoord 0, 11 + ld b, 5 + ld c, 18 + call TextBox + hlcoord 2, 0 + lb bc, 2, 3 + call ClearBox + xor a + ld [wMonType], a + ld hl, wPartyMonNicknames + ld a, [wCurPartyMon] + call GetNick + hlcoord 5, 1 + call PlaceString + push bc + farcall CopyMonToTempMon + pop hl + call PrintLevel + ld hl, wPlayerHPPal + call SetHPPal + ld b, SCGB_MOVE_LIST + call GetSGBLayout + hlcoord 16, 0 + lb bc, 1, 3 + jp ClearBox +; 131ef + +SetUpMoveList: ; 131ef + xor a + ld [hBGMapMode], a + ld [wMoveSwapBuffer], a + ld [wMonType], a + predef CopyMonToTempMon + ld hl, wTempMonMoves + ld de, wListMoves_MoveIndicesBuffer + ld bc, NUM_MOVES + call CopyBytes + ld a, SCREEN_WIDTH * 2 + ld [wBuffer1], a + hlcoord 2, 3 + predef ListMoves + hlcoord 10, 4 + predef ListMovePP + call WaitBGMap + call SetPalettes + ld a, [wNumMoves] + inc a + ld [w2DMenuNumRows], a + hlcoord 0, 11 + ld b, 5 + ld c, 18 + jp TextBox +; 13235 + +PrepareToPlaceMoveData: ; 13235 + ld hl, wPartyMon1Moves + ld bc, PARTYMON_STRUCT_LENGTH + ld a, [wCurPartyMon] + call AddNTimes + ld a, [wMenuCursorY] + dec a + ld c, a + ld b, $0 + add hl, bc + ld a, [hl] + ld [wCurMove], a + hlcoord 1, 12 + lb bc, 5, 18 + jp ClearBox +; 13256 + +PlaceMoveData: ; 13256 + xor a + ld [hBGMapMode], a + hlcoord 0, 10 + ld de, String_MoveType_Top + call PlaceString + hlcoord 0, 11 + ld de, String_MoveType_Bottom + call PlaceString + hlcoord 12, 12 + ld de, String_MoveAtk + call PlaceString + ld a, [wCurMove] + ld b, a + hlcoord 2, 12 + predef PrintMoveType + ld a, [wCurMove] + dec a + ld hl, Moves + MOVE_POWER + ld bc, MOVE_LENGTH + call AddNTimes + ld a, BANK(Moves) + call GetFarByte + hlcoord 16, 12 + cp 2 + jr c, .no_power + ld [wd265], a + ld de, wd265 + lb bc, 1, 3 + call PrintNum + jr .description + +.no_power + ld de, String_MoveNoPower + call PlaceString + +.description + hlcoord 1, 14 + predef PrintMoveDesc + ld a, $1 + ld [hBGMapMode], a + ret +; 132ba + +String_MoveType_Top: ; 132ba + db "┌─────┐@" +; 132c2 +String_MoveType_Bottom: ; 132c2 + db "│TYPE/└@" +; 132ca +String_MoveAtk: ; 132ca + db "ATK/@" +; 132cf +String_MoveNoPower: ; 132cf + db "---@" +; 132d3 + +Function132d3: ; 132d3 + call Function132da + call Function132fe + ret +; 132da + +Function132da: ; 132da + ld a, [wCurPartyMon] + and a + ret z + ld c, a + ld e, a + ld d, 0 + ld hl, wPartyCount + add hl, de +.loop + ld a, [hl] + and a + jr z, .prev + cp EGG + jr z, .prev + cp NUM_POKEMON + 1 + jr c, .legal + +.prev + dec hl + dec c + jr nz, .loop + ret + +.legal + hlcoord 16, 0 + ld [hl], "◀" + ret +; 132fe + +Function132fe: ; 132fe + ld a, [wCurPartyMon] + inc a + ld c, a + ld a, [wPartyCount] + cp c + ret z + ld e, c + ld d, 0 + ld hl, wPartySpecies + add hl, de +.loop + ld a, [hl] + cp -1 + ret z + and a + jr z, .next + cp EGG + jr z, .next + cp NUM_POKEMON + 1 + jr c, .legal + +.next + inc hl + jr .loop + +.legal + hlcoord 18, 0 + ld [hl], "▶" + ret +; 13327 diff --git a/engine/menus/trainer_card.asm b/engine/menus/trainer_card.asm new file mode 100644 index 000000000..e84c1c9f3 --- /dev/null +++ b/engine/menus/trainer_card.asm @@ -0,0 +1,623 @@ +; TrainerCard.Jumptable indexes + const_def + const TRAINERCARDSTATE_PAGE1_LOADGFX ; 0 + const TRAINERCARDSTATE_PAGE1_JOYPAD ; 1 + const TRAINERCARDSTATE_PAGE2_LOADGFX ; 2 + const TRAINERCARDSTATE_PAGE2_JOYPAD ; 3 + const TRAINERCARDSTATE_PAGE3_LOADGFX ; 4 + const TRAINERCARDSTATE_PAGE3_JOYPAD ; 5 + const TRAINERCARDSTATE_QUIT ; 6 + +TrainerCard: ; 25105 + ld a, [wVramState] + push af + xor a + ld [wVramState], a + ld hl, wOptions + ld a, [hl] + push af + set NO_TEXT_SCROLL, [hl] + call .InitRAM +.loop + call UpdateTime + call JoyTextDelay + ld a, [wJumptableIndex] + bit 7, a + jr nz, .quit + ld a, [hJoyLast] + and B_BUTTON + jr nz, .quit + call .RunJumptable + call DelayFrame + jr .loop + +.quit + pop af + ld [wOptions], a + pop af + ld [wVramState], a + ret + +.InitRAM: ; 2513b (9:513b) + call ClearBGPalettes + call ClearSprites + call ClearTileMap + call DisableLCD + + farcall GetCardPic + + ld hl, CardRightCornerGFX + ld de, vTiles2 tile $1c + ld bc, 1 tiles + ld a, BANK(CardRightCornerGFX) + call FarCopyBytes + + ld hl, CardStatusGFX + ld de, vTiles2 tile $29 + ld bc, 86 tiles + ld a, BANK(CardStatusGFX) + call FarCopyBytes + + call TrainerCard_PrintTopHalfOfCard + + hlcoord 0, 8 + ld d, 6 + call TrainerCard_InitBorder + + call EnableLCD + call WaitBGMap + ld b, SCGB_TRAINER_CARD + call GetSGBLayout + call SetPalettes + call WaitBGMap + ld hl, wJumptableIndex + xor a ; TRAINERCARDSTATE_PAGE1_LOADGFX + ld [hli], a ; wJumptableIndex + ld [hli], a ; wTrainerCardBadgeFrameCounter + ld [hli], a ; wTrainerCardBadgeTileID + ld [hl], a ; wTrainerCardBadgeAttributes + ret + +.RunJumptable: ; 2518e (9:518e) + jumptable .Jumptable, wJumptableIndex + +.Jumptable: ; 2519d (9:519d) +; entries correspond to TRAINERCARDSTATE_* constants + dw TrainerCard_Page1_LoadGFX + dw TrainerCard_Page1_Joypad + dw TrainerCard_Page2_LoadGFX + dw TrainerCard_Page2_Joypad + dw TrainerCard_Page3_LoadGFX + dw TrainerCard_Page3_Joypad + dw TrainerCard_Quit + +TrainerCard_IncrementJumptable: ; 251ab (9:51ab) + ld hl, wJumptableIndex + inc [hl] + ret + +TrainerCard_Quit: ; 251b0 (9:51b0) + ld hl, wJumptableIndex + set 7, [hl] + ret + +TrainerCard_Page1_LoadGFX: ; 251b6 (9:51b6) + call ClearSprites + hlcoord 0, 8 + ld d, 6 + call TrainerCard_InitBorder + call WaitBGMap + ld de, CardStatusGFX + ld hl, vTiles2 tile $29 + lb bc, BANK(CardStatusGFX), 86 + call Request2bpp + call TrainerCard_Page1_PrintDexCaught_GameTime + call TrainerCard_IncrementJumptable + ret + +TrainerCard_Page1_Joypad: ; 251d7 (9:51d7) + call TrainerCard_Page1_PrintGameTime + ld hl, hJoyLast + ld a, [hl] + and D_RIGHT | A_BUTTON + jr nz, .pressed_right_a + ret + +.pressed_right_a + ld a, TRAINERCARDSTATE_PAGE2_LOADGFX + ld [wJumptableIndex], a + ret + +.Unreferenced_KantoCheck: + ld a, [wKantoBadges] + and a + ret z + ld a, TRAINERCARDSTATE_PAGE3_LOADGFX + ld [wJumptableIndex], a + ret + +; 251f4 + +TrainerCard_Page2_LoadGFX: ; 251f4 (9:51f4) + call ClearSprites + hlcoord 0, 8 + ld d, 6 + call TrainerCard_InitBorder + call WaitBGMap + ld de, LeaderGFX + ld hl, vTiles2 tile $29 + lb bc, BANK(LeaderGFX), 86 + call Request2bpp + ld de, BadgeGFX + ld hl, vTiles0 tile $00 + lb bc, BANK(BadgeGFX), 44 + call Request2bpp + call TrainerCard_Page2_3_InitObjectsAndStrings + call TrainerCard_IncrementJumptable + ret + +TrainerCard_Page2_Joypad: ; 25221 (9:5221) + ld hl, TrainerCard_JohtoBadgesOAM + call TrainerCard_Page2_3_AnimateBadges + ld hl, hJoyLast + ld a, [hl] + and A_BUTTON + jr nz, .Quit + ld a, [hl] + and D_LEFT + jr nz, .d_left + ret + +.d_left + ld a, TRAINERCARDSTATE_PAGE1_LOADGFX + ld [wJumptableIndex], a + ret + +.Unreferenced_KantoCheck: + ld a, [wKantoBadges] + and a + ret z + ld a, TRAINERCARDSTATE_PAGE3_LOADGFX + ld [wJumptableIndex], a + ret + +.Quit: + ld a, TRAINERCARDSTATE_QUIT + ld [wJumptableIndex], a + ret + +TrainerCard_Page3_LoadGFX: ; 2524c (9:524c) + call ClearSprites + hlcoord 0, 8 + ld d, 6 + call TrainerCard_InitBorder + call WaitBGMap + ld de, LeaderGFX2 + ld hl, vTiles2 tile $29 + lb bc, BANK(LeaderGFX2), 86 + call Request2bpp + ld de, BadgeGFX2 + ld hl, vTiles0 tile $00 + lb bc, BANK(BadgeGFX2), 44 + call Request2bpp + call TrainerCard_Page2_3_InitObjectsAndStrings + call TrainerCard_IncrementJumptable + ret + +TrainerCard_Page3_Joypad: ; 25279 (9:5279) + ld hl, TrainerCard_JohtoBadgesOAM + call TrainerCard_Page2_3_AnimateBadges + ld hl, hJoyLast + ld a, [hl] + and D_LEFT + jr nz, .left + ld a, [hl] + and D_RIGHT + jr nz, .right + ret + +.left + ld a, TRAINERCARDSTATE_PAGE2_LOADGFX + ld [wJumptableIndex], a + ret + +.right + ld a, TRAINERCARDSTATE_PAGE1_LOADGFX + ld [wJumptableIndex], a + ret + +TrainerCard_PrintTopHalfOfCard: ; 25299 (9:5299) + hlcoord 0, 0 + ld d, 5 + call TrainerCard_InitBorder + hlcoord 2, 2 + ld de, .Name_Money + call PlaceString + hlcoord 2, 4 + ld de, .ID_No + call TrainerCardSetup_PlaceTilemapString + hlcoord 7, 2 + ld de, wPlayerName + call PlaceString + hlcoord 5, 4 + ld de, wPlayerID + lb bc, PRINTNUM_LEADINGZEROS | 2, 5 + call PrintNum + hlcoord 7, 6 + ld de, wMoney + lb bc, PRINTNUM_MONEY | 3, 6 + call PrintNum + hlcoord 1, 3 + ld de, .HorizontalDivider + call TrainerCardSetup_PlaceTilemapString + hlcoord 14, 1 + lb bc, 5, 7 + xor a + ld [hGraphicStartTile], a + predef PlaceGraphic + ret + +; 252ec (9:52ec) + +.Name_Money: ; 252ec + db "NAME/" + next "" + next "MONEY@" + +.ID_No: ; 252f9 + db $27, $28, -1 ; ID NO + +.HorizontalDivider: ; 252fc + db $25, $25, $25, $25, $25, $25, $25, $25, $25, $25, $25, $25, $26, -1 ; ____________> +; 2530a + +TrainerCard_Page1_PrintDexCaught_GameTime: ; 2530a (9:530a) + hlcoord 2, 10 + ld de, .Dex_PlayTime + call PlaceString + hlcoord 10, 15 + ld de, .Badges + call PlaceString + ld hl, wPokedexCaught + ld b, wEndPokedexCaught - wPokedexCaught + call CountSetBits + ld de, wd265 + hlcoord 15, 10 + lb bc, 1, 3 + call PrintNum + call TrainerCard_Page1_PrintGameTime + hlcoord 2, 8 + ld de, .StatusTilemap + call TrainerCardSetup_PlaceTilemapString + ld a, [wStatusFlags] + bit STATUSFLAGS_POKEDEX_F, a + ret nz + hlcoord 1, 9 + lb bc, 2, 17 + call ClearBox + ret + +.Dex_PlayTime: + db "#DEX" + next "PLAY TIME@@" + +.Badges: + db " BADGES▶@" + +.StatusTilemap: ; 25366 + db $29, $2a, $2b, $2c, $2d, -1 +; 2536c + +TrainerCard_Page2_3_InitObjectsAndStrings: ; 2536c (9:536c) + hlcoord 2, 8 + ld de, .BadgesTilemap + call TrainerCardSetup_PlaceTilemapString + hlcoord 2, 10 + ld a, $29 + ld c, 4 +.loop + call TrainerCard_Page2_3_PlaceLeadersFaces +rept 4 + inc hl +endr + dec c + jr nz, .loop + hlcoord 2, 13 + ld a, $51 + ld c, 4 +.loop2 + call TrainerCard_Page2_3_PlaceLeadersFaces +rept 4 + inc hl +endr + dec c + jr nz, .loop2 + xor a + ld [wTrainerCardBadgeFrameCounter], a + ld hl, TrainerCard_JohtoBadgesOAM + call TrainerCard_Page2_3_OAMUpdate + ret + +; 253a2 (9:53a2) + +.BadgesTilemap: ; 253a2 + db $79, $7a, $7b, $7c, $7d, -1 ; "BADGES" +; 253a8 + +TrainerCardSetup_PlaceTilemapString: ; 253a8 (9:53a8) +.loop + ld a, [de] + cp -1 + ret z + ld [hli], a + inc de + jr .loop + +TrainerCard_InitBorder: ; 253b0 (9:53b0) + ld e, SCREEN_WIDTH +.loop1 + ld a, $23 + ld [hli], a + dec e + jr nz, .loop1 + + ld a, $23 + ld [hli], a + ld e, SCREEN_HEIGHT - 1 + ld a, " " +.loop2 + ld [hli], a + dec e + jr nz, .loop2 + + ld a, $1c + ld [hli], a + ld a, $23 + ld [hli], a +.loop3 + ld a, $23 + ld [hli], a + + ld e, SCREEN_HEIGHT + ld a, " " +.loop4 + ld [hli], a + dec e + jr nz, .loop4 + + ld a, $23 + ld [hli], a + dec d + jr nz, .loop3 + + ld a, $23 + ld [hli], a + ld a, $24 + ld [hli], a + + ld e, SCREEN_HEIGHT - 1 + ld a, " " +.loop5 + ld [hli], a + dec e + jr nz, .loop5 + ld a, $23 + ld [hli], a + ld e, SCREEN_WIDTH +.loop6 + ld a, $23 + ld [hli], a + dec e + jr nz, .loop6 + ret + +TrainerCard_Page2_3_PlaceLeadersFaces: ; 253f4 (9:53f4) + push de + push hl + ld [hli], a + inc a + ld [hli], a + inc a + ld [hli], a + inc a + ld [hli], a + inc a + ld de, SCREEN_WIDTH - 3 + add hl, de + ld [hli], a + inc a + ld [hli], a + inc a + ld [hli], a + inc a + ld de, SCREEN_WIDTH - 3 + add hl, de + ld [hli], a + inc a + ld [hli], a + inc a + ld [hli], a + inc a + pop hl + pop de + ret + +TrainerCard_Page1_PrintGameTime: ; 25415 (9:5415) + hlcoord 11, 12 + ld de, wGameTimeHours + lb bc, 2, 4 + call PrintNum + inc hl + ld de, wGameTimeMinutes + lb bc, PRINTNUM_LEADINGZEROS | 1, 2 + call PrintNum + ld a, [hVBlankCounter] + and $1f + ret nz + hlcoord 15, 12 + ld a, [hl] + xor " " ^ $2e ; alternate between space and small colon ($2e) tiles + ld [hl], a + ret + +TrainerCard_Page2_3_AnimateBadges: ; 25438 (9:5438) + ld a, [hVBlankCounter] + and %111 + ret nz + ld a, [wTrainerCardBadgeFrameCounter] + inc a + and %111 + ld [wTrainerCardBadgeFrameCounter], a + jr TrainerCard_Page2_3_OAMUpdate + +TrainerCard_Page2_3_OAMUpdate: ; 25448 (9:5448) +; copy flag array pointer + ld a, [hli] + ld e, a + ld a, [hli] +; get flag array + ld d, a + ld a, [de] + ld c, a + ld de, wVirtualOAMSprite00 + ld b, NUM_JOHTO_BADGES +.loop + srl c + push bc + jr nc, .skip_badge + push hl + ld a, [hli] ; y + ld b, a + ld a, [hli] ; x + ld c, a + ld a, [hli] ; pal + ld [wTrainerCardBadgeAttributes], a + ld a, [wTrainerCardBadgeFrameCounter] + add l + ld l, a + ld a, 0 + adc h + ld h, a + ld a, [hl] + ld [wTrainerCardBadgeTileID], a + call .PrepOAM + pop hl +.skip_badge + ld bc, $b ; 3 + 2 * 4 + add hl, bc + pop bc + dec b + jr nz, .loop + ret + +.PrepOAM: ; 2547b (9:547b) + ld a, [wTrainerCardBadgeTileID] + and 1 << 7 + jr nz, .xflip + ld hl, .facing1 + jr .loop2 + +.xflip + ld hl, .facing2 +.loop2 + ld a, [hli] + cp -1 + ret z + add b + ld [de], a ; y + inc de + + ld a, [hli] + add c + ld [de], a ; x + inc de + + ld a, [wTrainerCardBadgeTileID] + and $ff ^ (1 << 7) + add [hl] + ld [de], a ; tile id + inc hl + inc de + + ld a, [wTrainerCardBadgeAttributes] + add [hl] + ld [de], a ; attributes + inc hl + inc de + jr .loop2 + +; 254a7 (9:54a7) + +.facing1 ; 254a7 + dsprite 0, 0, 0, 0, $00, 0 + dsprite 0, 0, 1, 0, $01, 0 + dsprite 1, 0, 0, 0, $02, 0 + dsprite 1, 0, 1, 0, $03, 0 + db -1 + +.facing2 ; 254b8 + dsprite 0, 0, 0, 0, $01, 0 | X_FLIP + dsprite 0, 0, 1, 0, $00, 0 | X_FLIP + dsprite 1, 0, 0, 0, $03, 0 | X_FLIP + dsprite 1, 0, 1, 0, $02, 0 | X_FLIP + db -1 + +TrainerCard_JohtoBadgesOAM: ; 254c9 +; Template OAM data for each badge on the trainer card. +; Format: + ; y, x, palette + ; cycle 1: face tile, in1 tile, in2 tile, in3 tile + ; cycle 2: face tile, in1 tile, in2 tile, in3 tile + + dw wJohtoBadges + + ; Zephyrbadge + db $68, $18, 0 + db $00, $20, $24, $20 | (1 << 7) + db $00, $20, $24, $20 | (1 << 7) + + ; Hivebadge + db $68, $38, 0 + db $04, $20, $24, $20 | (1 << 7) + db $04, $20, $24, $20 | (1 << 7) + + ; Plainbadge + db $68, $58, 0 + db $08, $20, $24, $20 | (1 << 7) + db $08, $20, $24, $20 | (1 << 7) + + ; Fogbadge + db $68, $78, 0 + db $0c, $20, $24, $20 | (1 << 7) + db $0c, $20, $24, $20 | (1 << 7) + + ; Mineralbadge + db $80, $38, 0 + db $10, $20, $24, $20 | (1 << 7) + db $10, $20, $24, $20 | (1 << 7) + + ; Stormbadge + db $80, $18, 0 + db $14, $20, $24, $20 | (1 << 7) + db $14, $20, $24, $20 | (1 << 7) + + ; Glacierbadge + db $80, $58, 0 + db $18, $20, $24, $20 | (1 << 7) + db $18, $20, $24, $20 | (1 << 7) + + ; Risingbadge + ; X-flips on alternate cycles. + db $80, $78, 0 + db $1c, $20, $24, $20 | (1 << 7) + db $1c | (1 << 7), $20, $24, $20 | (1 << 7) +; 25523 + +CardStatusGFX: INCBIN "gfx/trainer_card/card_status.2bpp" + +LeaderGFX: INCBIN "gfx/trainer_card/leaders.2bpp" +LeaderGFX2: INCBIN "gfx/trainer_card/leaders.2bpp" +BadgeGFX: INCBIN "gfx/trainer_card/badges.2bpp" +BadgeGFX2: INCBIN "gfx/trainer_card/badges.2bpp" + +CardRightCornerGFX: INCBIN "gfx/trainer_card/card_right_corner.2bpp" |