diff options
author | YamaArashi <shadow962@live.com> | 2012-01-26 10:31:04 -0800 |
---|---|---|
committer | YamaArashi <shadow962@live.com> | 2012-01-26 10:31:04 -0800 |
commit | 96db7d1cd78232f345eb74bc2c91ad5698d1b11f (patch) | |
tree | ca61ed99461ed151f95b97acdd9bf4aee86f6619 | |
parent | 3f61e9bd0e07a7930b81911efb098c105e9d32f8 (diff) |
diasm of some bank 0 code (mostly menu related)
hg-commit-id: f22d2b2ca017
-rw-r--r-- | constants.asm | 31 | ||||
-rw-r--r-- | main.asm | 333 |
2 files changed, 363 insertions, 1 deletions
diff --git a/constants.asm b/constants.asm index 56301a4b..8fab2fb9 100644 --- a/constants.asm +++ b/constants.asm @@ -89,9 +89,36 @@ TX_RAM: MACRO ; wram locations +; coordinates of the position of the cursor for the top menu item (id 0) +W_TOPMENUITEMY EQU $CC24 +W_TOPMENUITEMX EQU $CC25 + +; the id of the currently selected menu item +; the top item has id 0, the one below that has id 1, etc. +W_CURMENUITEMID EQU $CC26 + +; the tile that was behind the menu cursor's current location +W_TILEBEHINDCURSOR EQU $CC27 + +W_MAXMENUITEMID EQU $CC28 ; id of the bottom menu item + +W_MENUWATCHEDKEYS EQU $CC29 ; bit mask of keys that the menu will respond to + +W_OLDMENUITEMID EQU $CC2A ; id of previously selected menu item + +; how many times should HandleMenuInput poll the joypad state before it returns? +W_MENUJOYPADPOLLCOUNT EQU $CC34 + W_PLAYERMOVELISTINDEX EQU $CC2E W_PLAYERMONNUMBER EQU $CC2F +; the address of the menu cursor's current location within C3A0-C507 +W_MENUCURSORLOCATION EQU $CC30 ; 2 bytes + +; set to 1 if you can go from the bottom to the top or top to bottom of a menu +; set to 0 if you can't go past the top or bottom of the menu +W_MENUWRAPPINGENABLED EQU $CC4A + ; current HP of player and enemy substitutes W_PLAYERSUBSITUTEHP EQU $CCD7 W_ENEMYSUBSITUTEHP EQU $CCD8 @@ -699,6 +726,10 @@ W_BOXITEM50QTY EQU $D59E W_SAFARITIMER1 EQU $D70D ; use 01 for maximum W_SAFARITIMER2 EQU $D70E ; use F4 for maximum +; counters for blinking down arrow +H_DOWNARROWBLINKCNT1 EQU $FF8B +H_DOWNARROWBLINKCNT2 EQU $FF8C + ; Note: the following multiplication and division addresses are used for multiple purposes ; and so they overlap with each other @@ -4847,7 +4847,338 @@ AddNTimes: ; 3A87 jr nz,.loop\@ ret -INCBIN "baserom.gbc",$3A8E,$3C49 - $3A8E +; Compare strings, c bytes in length, at de and hl. +; Often used to compare big endian numbers in battle calculations. +StringCmp: ; 3A8E + ld a,[de] + cp [hl] + ret nz + inc de + inc hl + dec c + jr nz,StringCmp + ret + +; INPUT: +; a = oam block index (each block is 4 oam entries) +; b = Y coordinate of upper left corner of sprite +; c = X coordinate of upper left corner of sprite +; de = base address of 4 tile number and attribute pairs +WriteOAMBlock: ; 3A97 + ld h,$c3 + swap a ; multiply by 16 + ld l,a + call .writeOneEntry\@ ; upper left + push bc + ld a,8 + add c + ld c,a + call .writeOneEntry\@ ; upper right + pop bc + ld a,8 + add b + ld b,a + call .writeOneEntry\@ ; lower left + ld a,8 + add c + ld c,a + ; lower right +.writeOneEntry\@ + ld [hl],b ; Y coordinate + inc hl + ld [hl],c ; X coordinate + inc hl + ld a,[de] ; tile number + inc de + ld [hli],a + ld a,[de] ; attribute + inc de + ld [hli],a + ret + +HandleMenuInput: ; 3ABE + xor a + ld [$d09b],a + +HandleMenuInputPokemonSelection: ; 3AC2 + ld a,[H_DOWNARROWBLINKCNT1] + push af + ld a,[H_DOWNARROWBLINKCNT2] + push af ; save existing values on stack + xor a + ld [H_DOWNARROWBLINKCNT1],a ; blinking down arrow timing value 1 + ld a,$06 + ld [H_DOWNARROWBLINKCNT2],a ; blinking down arrow timing value 2 +.loop1\@ + xor a + ld [$d08b],a ; counter for pokemon shaking animation + call PlaceMenuCursor + call Delay3 +.loop2\@ + push hl + ld a,[$d09b] + and a ; is it a pokemon selection menu? + jr z,.getJoypadState\@ + ld b,$1c + ld hl,$56ff ; shake mini sprite of selected pokemon + call Bankswitch +.getJoypadState\@ + pop hl + call GetJoypadStateLowSensitivity + ld a,[$ffb5] + and a ; was a key pressed? + jr nz,.keyPressed\@ + push hl + FuncCoord 18,11 ; coordinates of blinking down arrow in some menus + ld hl,Coord + call $3c04 ; blink down arrow (if any) + pop hl + ld a,[W_MENUJOYPADPOLLCOUNT] + dec a + jr z,.giveUpWaiting\@ + jr .loop2\@ +.giveUpWaiting\@ +; if a key wasn't pressed within the specified number of checks + pop af + ld [H_DOWNARROWBLINKCNT2],a + pop af + ld [H_DOWNARROWBLINKCNT1],a ; restore previous values + xor a + ld [W_MENUWRAPPINGENABLED],a ; disable menu wrapping + ret +.keyPressed\@ + xor a + ld [$cc4b],a + ld a,[$ffb5] + ld b,a + bit 6,a ; pressed Up key? + jr z,.checkIfDownPressed\@ +.upPressed\@ + ld a,[W_CURMENUITEMID] ; selected menu item + and a ; already at the top of the menu? + jr z,.alreadyAtTop\@ +.notAtTop\@ + dec a + ld [W_CURMENUITEMID],a ; move selected menu item up one space + jr .checkOtherKeys\@ +.alreadyAtTop\@ + ld a,[W_MENUWRAPPINGENABLED] + and a ; is wrapping around enabled? + jr z,.noWrappingAround\@ + ld a,[W_MAXMENUITEMID] + ld [W_CURMENUITEMID],a ; wrap to the bottom of the menu + jr .checkOtherKeys\@ +.checkIfDownPressed\@ + bit 7,a + jr z,.checkOtherKeys\@ +.downPressed\@ + ld a,[W_CURMENUITEMID] + inc a + ld c,a + ld a,[W_MAXMENUITEMID] + cp c + jr nc,.notAtBottom\@ +.alreadyAtBottom\@ + ld a,[W_MENUWRAPPINGENABLED] + and a ; is wrapping around enabled? + jr z,.noWrappingAround\@ + ld c,$00 ; wrap from bottom to top +.notAtBottom\@ + ld a,c + ld [W_CURMENUITEMID],a +.checkOtherKeys\@ + ld a,[W_MENUWATCHEDKEYS] + and b ; does the menu care about any of the pressed keys? + jp z,.loop1\@ +.checkIfAButtonOrBButtonPressed\@ + ld a,[$ffb5] + and a,%00000011 ; pressed A button or B button? + jr z,.skipPlayingSound\@ +.AButtonOrBButtonPressed\@ + push hl + ld hl,$cd60 + bit 5,[hl] + pop hl + jr nz,.skipPlayingSound\@ + ld a,$90 + call $23b1 ; play sound +.skipPlayingSound\@ + pop af + ld [H_DOWNARROWBLINKCNT2],a + pop af + ld [H_DOWNARROWBLINKCNT1],a ; restore previous values + xor a + ld [W_MENUWRAPPINGENABLED],a ; disable menu wrapping + ld a,[$ffb5] + ret +.noWrappingAround\@ + ld a,[$cc37] + and a ; should we return if the user tried to go past the top or bottom? + jr z,.checkOtherKeys\@ + jr .checkIfAButtonOrBButtonPressed\@ + +PlaceMenuCursor: ; 3B7C + ld a,[W_TOPMENUITEMY] + and a ; is the y coordinate 0? + jr z,.adjustForXCoord\@ + ld hl,$c3a0 + ld bc,20 ; screen width +.topMenuItemLoop\@ + add hl,bc + dec a + jr nz,.topMenuItemLoop\@ +.adjustForXCoord\@ + ld a,[W_TOPMENUITEMX] + ld b,$00 + ld c,a + add hl,bc + push hl + ld a,[W_OLDMENUITEMID] + and a ; was the previous menu id 0? + jr z,.checkForArrow1\@ + push af + ld a,[$fff6] + bit 1,a ; is the menu double spaced? + jr z,.doubleSpaced1\@ + ld bc,20 + jr .getOldMenuItemScreenPosition\@ +.doubleSpaced1\@ + ld bc,40 +.getOldMenuItemScreenPosition\@ + pop af +.oldMenuItemLoop\@ + add hl,bc + dec a + jr nz,.oldMenuItemLoop\@ +.checkForArrow1\@ + ld a,[hl] + cp a,$ed ; was an arrow next to the previously selected menu item? + jr nz,.skipClearingArrow\@ +.clearArrow\@ + ld a,[W_TILEBEHINDCURSOR] + ld [hl],a +.skipClearingArrow\@ + pop hl + ld a,[W_CURMENUITEMID] + and a + jr z,.checkForArrow2\@ + push af + ld a,[$fff6] + bit 1,a ; is the menu double spaced? + jr z,.doubleSpaced2\@ + ld bc,20 + jr .getCurrentMenuItemScreenPosition\@ +.doubleSpaced2\@ + ld bc,40 +.getCurrentMenuItemScreenPosition\@ + pop af +.currentMenuItemLoop\@ + add hl,bc + dec a + jr nz,.currentMenuItemLoop\@ +.checkForArrow2\@ + ld a,[hl] + cp a,$ed ; has the right arrow already been placed? + jr z,.skipSavingTile\@ ; if so, don't lose the saved tile + ld [W_TILEBEHINDCURSOR],a ; save tile before overwriting with right arrow +.skipSavingTile\@ + ld a,$ed ; place right arrow + ld [hl],a + ld a,l + ld [W_MENUCURSORLOCATION],a + ld a,h + ld [W_MENUCURSORLOCATION + 1],a + ld a,[W_CURMENUITEMID] + ld [W_OLDMENUITEMID],a + ret + +; Used when swapping positions of items in a list menu. +; The item that the user selects first is marked with an outline of a right arrow +; to distinguish it from the arrow being used to select the second item. +PlaceUnfilledArrowMenuCursor: ; 3BEC + ld b,a + ld a,[W_MENUCURSORLOCATION] + ld l,a + ld a,[W_MENUCURSORLOCATION + 1] + ld h,a + ld [hl],$ec ; outline of right arrow + ld a,b + ret + +; Replaces the menu cursor with a blank space. +EraseMenuCursor: ; 3BF9 + ld a,[W_MENUCURSORLOCATION] + ld l,a + ld a,[W_MENUCURSORLOCATION + 1] + ld h,a + ld [hl],$7f ; blank space + ret + +; This toggles a blinking down arrow at hl on and off after a delay has passed. +; This is often called even when no blinking is occurring. +; The reason is that most functions that call this initialize H_DOWNARROWBLINKCNT1 to 0. +; The effect is that if the tile at hl is initialized with a down arrow, +; this function will toggle that down arrow on and off, but if the tile isn't +; initliazed with a down arrow, this function does nothing. +; That allows this to be called without worrying about if a down arrow should +; be blinking. +HandleDownArrowBlinkTiming: ; 3C04 + ld a,[hl] + ld b,a + ld a,$ee ; down arrow + cp b + jr nz,.downArrowOff\@ +.downArrowOn\@ + ld a,[H_DOWNARROWBLINKCNT1] + dec a + ld [H_DOWNARROWBLINKCNT1],a + ret nz + ld a,[H_DOWNARROWBLINKCNT2] + dec a + ld [H_DOWNARROWBLINKCNT2],a + ret nz + ld a,$7f ; blank space + ld [hl],a + ld a,$ff + ld [H_DOWNARROWBLINKCNT1],a + ld a,$06 + ld [H_DOWNARROWBLINKCNT2],a + ret +.downArrowOff\@ + ld a,[H_DOWNARROWBLINKCNT1] + and a + ret z + dec a + ld [H_DOWNARROWBLINKCNT1],a + ret nz + dec a + ld [H_DOWNARROWBLINKCNT1],a + ld a,[H_DOWNARROWBLINKCNT2] + dec a + ld [H_DOWNARROWBLINKCNT2],a + ret nz + ld a,$06 + ld [H_DOWNARROWBLINKCNT2],a + ld a,$ee ; down arrow + ld [hl],a + ret + +; The following code either enables or disables the automatic drawing of +; text boxes by DisplayTextID. Both functions cause DisplayTextID to wait +; for a button press after displaying text (unless [$cc47] is set). + +EnableAutoTextBoxDrawing: ; 3C3C + xor a + jr AutoTextBoxDrawingCommon + +DisableAutoTextBoxDrawing: ; 3C3F + ld a,$01 + +AutoTextBoxDrawingCommon: ; 3C41 + ld [$cf0c],a ; control text box drawing + xor a + ld [$cc3c],a ; make DisplayTextID wait for button press + ret PrintText: ; 3C49 ; given a pointer in hl, print the text there |