diff options
Diffstat (limited to 'engine/games/memory_minigame.asm')
-rw-r--r-- | engine/games/memory_minigame.asm | 626 |
1 files changed, 626 insertions, 0 deletions
diff --git a/engine/games/memory_minigame.asm b/engine/games/memory_minigame.asm new file mode 100644 index 0000000..6462106 --- /dev/null +++ b/engine/games/memory_minigame.asm @@ -0,0 +1,626 @@ +INCLUDE "constants.asm" + +SECTION "engine/games/memory_minigame.asm", ROMX + +; MemoryMinigame.Jumptable indices + const_def + const MEMORYGAME_RESTART_GAME + const MEMORYGAME_RESTART_BOARD + const MEMORYGAME_INIT_BOARD_AND_CURSOR + const MEMORYGAME_CHECK_TRIES_REMAINING + const MEMORYGAME_PICK_CARD_1 + const MEMORYGAME_PICK_CARD_2 + const MEMORYGAME_DELAY_PICK_AGAIN + const MEMORYGAME_REVEAL_ALL + const MEMORYGAME_ASK_PLAY_AGAIN +MEMORYGAME_END_LOOP_F EQU 7 + +MEMORYGAME_STARTING_COINS EQU 256 + +MemoryMinigame: +; Always start off with 256 coins + ld hl, wCoins + ld [hl], HIGH(MEMORYGAME_STARTING_COINS) + inc hl + ld [hl], LOW(MEMORYGAME_STARTING_COINS) + + call .LoadGFXAndPals + call DelayFrame +.loop + call .JumptableLoop + jr nc, .loop + ret + +.LoadGFXAndPals: + call DisableLCD + ld b, SGB_DIPLOMA + call GetSGBLayout + callab InitEffectObject + + ld hl, MemoryGameGFX + ld de, vChars2 + ld bc, $70 tiles + ld a, BANK(MemoryGameGFX) + call FarCopyData + + ld hl, PointerGFX + ld de, vSprites + ld bc, $4 tiles + ld a, BANK(PointerGFX) + call FarCopyData + + ld a, SPRITE_ANIM_DICT_29 + ld hl, wSpriteAnimDict + ld [hli], a + ld [hl], 0 + + hlcoord 0, 0 + ld bc, SCREEN_WIDTH * SCREEN_HEIGHT + xor a + call ByteFill + + xor a + ldh [hSCY], a + ldh [hSCX], a + ld [rWY], a + ld [wJumptableIndex], a + ld a, 1 + ldh [hBGMapMode], a + ld a, %11100011 + ld [rLCDC], a + ld a, %11100100 + ld [rBGP], a + ld a, %11100000 + ld [rOBP0], a + ret + +.JumptableLoop: + ld a, [wJumptableIndex] + bit MEMORYGAME_END_LOOP_F, a + jr nz, .quit + call .ExecuteJumptable + callab EffectObjectJumpNoDelay + call DelayFrame + and a + ret + +.quit + scf + ret + +.ExecuteJumptable: + jumptable .Jumptable, wJumptableIndex + +.Jumptable: + dw .RestartGame + dw .ResetBoard + dw .InitBoardTilemapAndCursorObject + dw .CheckTriesRemaining + dw .PickCard1 + dw .PickCard2 + dw .DelayPickAgain + dw .RevealAll + dw .AskPlayAgain + +.RestartGame: + call MemoryGame_InitStrings + ld hl, wJumptableIndex + inc [hl] + ret + +.ResetBoard: + call Cursor_AnimateCursor + jr nc, .proceed + ld hl, wJumptableIndex + set MEMORYGAME_END_LOOP_F, [hl] + ret + +.proceed + call MemoryGame_InitBoard + ld hl, wJumptableIndex + inc [hl] + xor a + ld [wMemoryGameCounter], a + ld hl, wMemoryGameLastMatches +rept 4 + ld [hli], a +endr + ld [hl], a + ld [wMemoryGameNumCardsMatched], a + +.InitBoardTilemapAndCursorObject: + ld hl, wMemoryGameCounter + ld a, [hl] + cp 45 + jr nc, .spawn_object + inc [hl] + call MemoryGame_Card2Coord + xor a + ld [wMemoryGameLastCardPicked], a + call MemoryGame_PlaceCard + ret + +.spawn_object + depixel 6, 3, 4, 4 + ld a, SPRITE_ANIM_INDEX_MEMORY_GAME_CURSOR + call InitSpriteAnimStruct + ld a, 5 + ld [wMemoryGameNumberTriesRemaining], a + ld hl, wJumptableIndex + inc [hl] + ret + +.CheckTriesRemaining: + ld a, [wMemoryGameNumberTriesRemaining] + hlcoord 17, 0 + add "0" + ld [hl], a + ld hl, wMemoryGameNumberTriesRemaining + ld a, [hl] + and a + jr nz, .next_try + ld a, MEMORYGAME_REVEAL_ALL + ld [wJumptableIndex], a + ret + +.next_try + dec [hl] + xor a + ld [wMemoryGameCardChoice], a + ld hl, wJumptableIndex + inc [hl] + +.PickCard1: + ld a, [wMemoryGameCardChoice] + and a + ret z + dec a + ld e, a + ld d, 0 + ld hl, wMemoryGameCards + add hl, de + ld a, [hl] + cp -1 + ret z + ld [wMemoryGameLastCardPicked], a + ld [wMemoryGameCard1], a + ld a, e + ld [wMemoryGameCard1Location], a + call MemoryGame_Card2Coord + call MemoryGame_PlaceCard + xor a + ld [wMemoryGameCardChoice], a + ld hl, wJumptableIndex + inc [hl] + ret + +.PickCard2: + ld a, [wMemoryGameCardChoice] + and a + ret z + dec a + ld hl, wMemoryGameCard1Location + cp [hl] + ret z + ld e, a + ld d, 0 + ld hl, wMemoryGameCards + add hl, de + ld a, [hl] + cp -1 + ret z + ld [wMemoryGameLastCardPicked], a + ld [wMemoryGameCard2], a + ld a, e + ld [wMemoryGameCard2Location], a + call MemoryGame_Card2Coord + call MemoryGame_PlaceCard + ld a, 64 + ld [wMemoryGameCounter], a + ld hl, wJumptableIndex + inc [hl] + +.DelayPickAgain: + ld hl, wMemoryGameCounter + ld a, [hl] + and a + jr z, .PickAgain + dec [hl] + ret + +.PickAgain: + call MemoryGame_CheckMatch + ld a, MEMORYGAME_CHECK_TRIES_REMAINING + ld [wJumptableIndex], a + ret + +.RevealAll: + ldh a, [hJoypadDown] + and A_BUTTON + ret z + xor a + ld [wMemoryGameCounter], a + +.RevelationLoop: + ld hl, wMemoryGameCounter + ld a, [hl] + cp 45 + jr nc, .finish_round + inc [hl] + push af + call MemoryGame_Card2Coord + pop af + push hl + ld e, a + ld d, 0 + ld hl, wMemoryGameCards + add hl, de + ld a, [hl] + pop hl + cp -1 + jr z, .RevelationLoop + ld [wMemoryGameLastCardPicked], a + call MemoryGame_PlaceCard + jr .RevelationLoop + +.finish_round + call TextboxWaitPressAorB_BlinkCursor + ld hl, wJumptableIndex + inc [hl] + +.AskPlayAgain: + call Cursor_InterpretJoypad + jr nc, .restart + ld hl, wJumptableIndex + set MEMORYGAME_END_LOOP_F, [hl] + ret + +.restart + xor a + ld [wJumptableIndex], a + ret + +MemoryGame_CheckMatch: + ld hl, wMemoryGameCard1 + ld a, [hli] + cp [hl] + jr nz, .no_match + + ld a, [wMemoryGameCard1Location] + call MemoryGame_Card2Coord + call MemoryGame_DeleteCard + + ld a, [wMemoryGameCard2Location] + call MemoryGame_Card2Coord + call MemoryGame_DeleteCard + + ld a, [wMemoryGameCard1Location] + ld e, a + ld d, 0 + ld hl, wMemoryGameCards + add hl, de + ld [hl], -1 + + ld a, [wMemoryGameCard2Location] + ld e, a + ld d, 0 + ld hl, wMemoryGameCards + add hl, de + ld [hl], -1 + + ld hl, wMemoryGameLastMatches +.find_empty_slot + ld a, [hli] + and a + jr nz, .find_empty_slot + dec hl + ld a, [wMemoryGameCard1] + ld [hl], a + ld [wMemoryGameLastCardPicked], a + ld hl, wMemoryGameNumCardsMatched + ld e, [hl] + inc [hl] + inc [hl] + ld d, 0 + hlcoord 5, 0 + add hl, de + call MemoryGame_PlaceCard + ld hl, .VictoryText + call PrintText + ret + +.no_match + xor a + ld [wMemoryGameLastCardPicked], a + + ld a, [wMemoryGameCard1Location] + call MemoryGame_Card2Coord + call MemoryGame_PlaceCard + + ld a, [wMemoryGameCard2Location] + call MemoryGame_Card2Coord + call MemoryGame_PlaceCard + + ld hl, .DarnText + call PrintText + ret + +.VictoryText: + start_asm + push bc + hlcoord 2, 13 + call MemoryGame_PlaceCard + ld hl, .YeahText + pop bc + inc bc + inc bc + inc bc + ret + +.YeahText: + text " いただき!" + done + +.DarnText: + text "ざんねん⋯⋯" + done + +MemoryGame_InitBoard: + ld hl, wMemoryGameCards + ld bc, wMemoryGameCardsEnd - wMemoryGameCards + xor a + call ByteFill + call MemoryGame_GetDistributionOfTiles + + ld c, 2 + ld b, [hl] + call MemoryGame_SampleTilePlacement + + ld c, 8 + ld b, [hl] + call MemoryGame_SampleTilePlacement + + ld c, 4 + ld b, [hl] + call MemoryGame_SampleTilePlacement + + ld c, 7 + ld b, [hl] + call MemoryGame_SampleTilePlacement + + ld c, 3 + ld b, [hl] + call MemoryGame_SampleTilePlacement + + ld c, 6 + ld b, [hl] + call MemoryGame_SampleTilePlacement + + ld c, 1 + ld b, [hl] + call MemoryGame_SampleTilePlacement + + ld c, 5 + ld hl, wMemoryGameCards + ld b, wMemoryGameCardsEnd - wMemoryGameCards +.loop + ld a, [hl] + and a + jr nz, .no_load + ld [hl], c +.no_load + inc hl + dec b + jr nz, .loop + ret + + +MemoryGame_SampleTilePlacement: + push hl + ld de, wMemoryGameCards +.loop + call Random + and %00111111 + cp 45 + jr nc, .loop + ld l, a + ld h, 0 + add hl, de + ld a, [hl] + and a + jr nz, .loop + ld [hl], c + dec b + jr nz, .loop + pop hl + inc hl + ret + +MemoryGame_GetDistributionOfTiles: + ld a, [wMenuCursorY] + dec a + ld l, a + ld h, 0 + add hl, hl + add hl, hl + add hl, hl + ld de, .distributions + add hl, de + ret + +.distributions + db $02, $03, $06, $06, $06, $08, $08, $06 + db $02, $02, $04, $06, $06, $08, $08, $09 + db $02, $02, $02, $04, $07, $08, $08, $0c + +MemoryGame_PlaceCard: + ld a, [wMemoryGameLastCardPicked] + sla a + sla a + add 4 + ld [hli], a + inc a + ld [hld], a + inc a + ld bc, SCREEN_WIDTH + add hl, bc + ld [hli], a + inc a + ld [hl], a + ld c, 3 + call DelayFrames + ret + +MemoryGame_DeleteCard: + ld a, 1 + ld [hli], a + ld [hld], a + ld bc, SCREEN_WIDTH + add hl, bc + ld [hli], a + ld [hl], a + ld c, 3 + call DelayFrames + ret + +MemoryGame_InitStrings: + hlcoord 0, 0 + ld bc, SCREEN_WIDTH * SCREEN_HEIGHT + ld a, 1 + call ByteFill + hlcoord 0, 0 + ld de, .str1 + call PlaceString + hlcoord 15, 0 + ld de, .str2 + call PlaceString + ld hl, .dummy_text + call PrintText + ret + +.dummy_text + db "@" +.str1 + db "とったもの@" +.str2 + db "あと かい@" + +MemoryGame_Card2Coord: + ld d, 0 +.find_row + sub 9 + jr c, .found_row + inc d + jr .find_row + +.found_row + add 9 + ld e, a + hlcoord 1, 2 + ld bc, 2 * SCREEN_WIDTH +.loop2 + ld a, d + and a + jr z, .done + add hl, bc + dec d + jr .loop2 + +.done + sla e + add hl, de + ret + +MemoryGame_AnimateCursor: ; Called from sprite animation routine? + ld a, [wJumptableIndex] + cp MEMORYGAME_REVEAL_ALL + jr nc, .quit + call GetJoypadDebounced + ld hl, hJoypadDown + ld a, [hl] + and A_BUTTON + jr nz, .pressed_a + ld a, [hl] + and D_LEFT + jr nz, .pressed_left + ld a, [hl] + and D_RIGHT + jr nz, .pressed_right + ld a, [hl] + and D_UP + jr nz, .pressed_up + ld a, [hl] + and D_DOWN + jr nz, .pressed_down + ret + +.quit + ld hl, SPRITEANIMSTRUCT_INDEX + add hl, bc + ld [hl], 0 + ret + +.pressed_a + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld a, [hl] + inc a + ld [wMemoryGameCardChoice], a + ret + +.pressed_left + ld hl, SPRITEANIMSTRUCT_XOFFSET + add hl, bc + ld a, [hl] + and a + ret z + sub 1 tiles + ld [hl], a + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + dec [hl] + ret + +.pressed_right + ld hl, SPRITEANIMSTRUCT_XOFFSET + add hl, bc + ld a, [hl] + cp (9 - 1) tiles + ret z + add 1 tiles + ld [hl], a + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + inc [hl] + ret + +.pressed_up + ld hl, SPRITEANIMSTRUCT_YOFFSET + add hl, bc + ld a, [hl] + and a + ret z + sub 1 tiles + ld [hl], a + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld a, [hl] + sub 9 + ld [hl], a + ret + +.pressed_down + ld hl, SPRITEANIMSTRUCT_YOFFSET + add hl, bc + ld a, [hl] + cp (5 - 1) tiles + ret z + add a, $10 + ld [hl], a + ld hl, SPRITEANIMSTRUCT_0C + add hl, bc + ld a, [hl] + add a, 9 + ld [hl], a + ret + |