_MemoryGame: call .LoadGFXAndPals call DelayFrame .loop call .JumptableLoop jr nc, .loop ret .LoadGFXAndPals: call DisableLCD ld b, CGB_DIPLOMA call GetCGBLayout callfar ClearSpriteAnims ld hl, MemoryGameLZ ld de, vTiles2 tile $00 call Decompress ld hl, MemoryGameGFX ld de, vTiles0 tile $00 ld bc, 4 tiles ld a, BANK(MemoryGameGFX) call FarCopyBytes ld a, SPRITE_ANIM_DICT_ARROW_CURSOR ld hl, wSpriteAnimDict ld [hli], a ld [hl], $00 hlcoord 0, 0 ld bc, SCREEN_HEIGHT * SCREEN_WIDTH xor a call ByteFill xor a ldh [hSCY], a ldh [hSCX], a ldh [rWY], a ld [wJumptableIndex], a ld a, $1 ldh [hBGMapMode], a ld a, LCDC_DEFAULT ldh [rLCDC], a ld a, $e4 call DmgToCgbBGPals ld a, $e0 call DmgToCgbObjPal0 ret .JumptableLoop: ld a, [wJumptableIndex] bit 7, a jr nz, .quit call .ExecuteJumptable callfar PlaySpriteAnimations 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 UnusedCursor_InterpretJoypad_AnimateCursor jr nc, .proceed ld hl, wJumptableIndex set 7, [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_OBJ_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, $7 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, $3 ld [wJumptableIndex], a ret .RevealAll: ldh a, [hJoypadPressed] 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 WaitPressAorB_BlinkCursor ld hl, wJumptableIndex inc [hl] .AskPlayAgain: call UnusedCursor_InterpretJoypad_AnimateCursor jr nc, .restart ld hl, wJumptableIndex set 7, [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 PrintText1bpp 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, MemoryGameDarnText call PrintText1bpp ret .VictoryText: text_asm push bc hlcoord 2, 13 call MemoryGame_PlaceCard ld hl, MemoryGameYeahText pop bc inc bc inc bc inc bc ret MemoryGameYeahText: text_far _MemoryGameYeahText text_end MemoryGameDarnText: text_far _MemoryGameDarnText text_end 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, .japstr1 call PlaceString hlcoord 15, 0 ld de, .japstr2 call PlaceString ld hl, .dummy_text call PrintText1bpp ret .dummy_text db "@" .japstr1 db "?????@" .japstr2 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_InterpretJoypad_AnimateCursor: ld a, [wJumptableIndex] cp $7 jr nc, .quit call JoyTextDelay ld hl, hJoypadPressed 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_VAR1 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_VAR1 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_VAR1 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_VAR1 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 1 tiles ld [hl], a ld hl, SPRITEANIMSTRUCT_VAR1 add hl, bc ld a, [hl] add 9 ld [hl], a ret MemoryGameLZ: INCBIN "gfx/memory_game/memory_game.2bpp.lz"