diff --git a/src/constants/animation_constants.asm b/src/constants/animation_constants.asm index f17e1c9c..52e3382a 100644 --- a/src/constants/animation_constants.asm +++ b/src/constants/animation_constants.asm @@ -237,103 +237,103 @@ DEF NUM_SPRITE_ANIMS EQU const_value const_def ; Normal animations - const DUEL_ANIM_NONE ; $00 - const DUEL_ANIM_GLOW ; $01 - const DUEL_ANIM_PARALYSIS ; $02 - const DUEL_ANIM_SLEEP ; $03 - const DUEL_ANIM_CONFUSION ; $04 - const DUEL_ANIM_POISON ; $05 - const DUEL_ANIM_SINGLE_HIT ; $06 - const DUEL_ANIM_HIT ; $07 - const DUEL_ANIM_BIG_HIT ; $08 - const DUEL_ANIM_SHOW_DAMAGE ; $09 - const DUEL_ANIM_THUNDER_SHOCK ; $0a - const DUEL_ANIM_LIGHTNING ; $0b - const DUEL_ANIM_BORDER_SPARK ; $0c - const DUEL_ANIM_BIG_LIGHTNING ; $0d - const DUEL_ANIM_SMALL_FLAME ; $0e - const DUEL_ANIM_BIG_FLAME ; $0f - const DUEL_ANIM_FIRE_SPIN ; $10 - const DUEL_ANIM_DIVE_BOMB ; $11 - const DUEL_ANIM_WATER_JETS ; $12 - const DUEL_ANIM_WATER_GUN ; $13 - const DUEL_ANIM_WHIRLPOOL ; $14 - const DUEL_ANIM_HYDRO_PUMP ; $15 - const DUEL_ANIM_BLIZZARD ; $16 - const DUEL_ANIM_PSYCHIC ; $17 - const DUEL_ANIM_LEER ; $18 - const DUEL_ANIM_BEAM ; $19 - const DUEL_ANIM_HYPER_BEAM ; $1a - const DUEL_ANIM_ROCK_THROW ; $1b - const DUEL_ANIM_STONE_BARRAGE ; $1c - const DUEL_ANIM_PUNCH ; $1d - const DUEL_ANIM_THUNDERPUNCH ; $1e - const DUEL_ANIM_FIRE_PUNCH ; $1f - const DUEL_ANIM_STRETCH_KICK ; $20 - const DUEL_ANIM_SLASH ; $21 - const DUEL_ANIM_WHIP ; $22 - const DUEL_ANIM_SONICBOOM ; $23 - const DUEL_ANIM_FURY_SWIPES ; $24 - const DUEL_ANIM_DRILL ; $25 - const DUEL_ANIM_POT_SMASH ; $26 - const DUEL_ANIM_BONEMERANG ; $27 - const DUEL_ANIM_SEISMIC_TOSS ; $28 - const DUEL_ANIM_NEEDLES ; $29 - const DUEL_ANIM_WHITE_GAS ; $2a - const DUEL_ANIM_POWDER ; $2b - const DUEL_ANIM_GOO ; $2c - const DUEL_ANIM_BUBBLES ; $2d - const DUEL_ANIM_STRING_SHOT ; $2e - const DUEL_ANIM_BOYFRIENDS ; $2f - const DUEL_ANIM_LURE ; $30 - const DUEL_ANIM_TOXIC ; $31 - const DUEL_ANIM_CONFUSE_RAY ; $32 - const DUEL_ANIM_SING ; $33 - const DUEL_ANIM_SUPERSONIC ; $34 - const DUEL_ANIM_PETAL_DANCE ; $35 - const DUEL_ANIM_PROTECT ; $36 - const DUEL_ANIM_BARRIER ; $37 - const DUEL_ANIM_SPEED ; $38 - const DUEL_ANIM_WHIRLWIND ; $39 - const DUEL_ANIM_CRY ; $3a - const DUEL_ANIM_QUESTION_MARK ; $3b - const DUEL_ANIM_SELFDESTRUCT ; $3c - const DUEL_ANIM_BIG_SELFDESTRUCT_1 ; $3d - const DUEL_ANIM_HEAL ; $3e - const DUEL_ANIM_DRAIN ; $3f - const DUEL_ANIM_DARK_GAS ; $40 - const DUEL_ANIM_BIG_SELFDESTRUCT_2 ; $41 - const DUEL_ANIM_UNUSED_42 ; $42 - const DUEL_ANIM_UNUSED_43 ; $43 - const DUEL_ANIM_BENCH_THUNDER ; $44 - const DUEL_ANIM_QUICKFREEZE ; $45 - const DUEL_ANIM_BENCH_GLOW ; $46 - const DUEL_ANIM_FIREGIVER_START ; $47 - const DUEL_ANIM_UNUSED_48 ; $48 - const DUEL_ANIM_HEALING_WIND ; $49 - const DUEL_ANIM_BENCH_WHIRLWIND ; $4a - const DUEL_ANIM_EXPAND ; $4b - const DUEL_ANIM_CAT_PUNCH ; $4c - const DUEL_ANIM_THUNDER_WAVE ; $4d - const DUEL_ANIM_FIREGIVER_PLAYER ; $4e - const DUEL_ANIM_FIREGIVER_OPP ; $4f - const DUEL_ANIM_UNUSED_50 ; $50 - const DUEL_ANIM_PLAYER_SHUFFLE ; $51 - const DUEL_ANIM_OPP_SHUFFLE ; $52 - const DUEL_ANIM_BOTH_SHUFFLE ; $53 - const DUEL_ANIM_UNUSED_54 ; $54 - const DUEL_ANIM_BOTH_DRAW ; $55 - const DUEL_ANIM_PLAYER_DRAW ; $56 - const DUEL_ANIM_OPP_DRAW ; $57 - const DUEL_ANIM_COIN_SPIN ; $58 - const DUEL_ANIM_COIN_TOSS1 ; $59 - const DUEL_ANIM_COIN_TOSS2 ; $5a - const DUEL_ANIM_COIN_TAILS ; $5b - const DUEL_ANIM_COIN_HEADS ; $5c - const DUEL_ANIM_DUEL_WIN ; $5d - const DUEL_ANIM_DUEL_LOSS ; $5e - const DUEL_ANIM_DUEL_DRAW ; $5f - const DUEL_ANIM_UNUSED_60 ; $60 + const DUEL_ANIM_NONE ; $00 + const DUEL_ANIM_GLOW ; $01 + const DUEL_ANIM_PARALYSIS ; $02 + const DUEL_ANIM_SLEEP ; $03 + const DUEL_ANIM_CONFUSION ; $04 + const DUEL_ANIM_POISON ; $05 + const DUEL_ANIM_SINGLE_HIT ; $06 + const DUEL_ANIM_HIT ; $07 + const DUEL_ANIM_BIG_HIT ; $08 + const DUEL_ANIM_SHOW_DAMAGE ; $09 + const DUEL_ANIM_THUNDER_SHOCK ; $0a + const DUEL_ANIM_LIGHTNING ; $0b + const DUEL_ANIM_BORDER_SPARK ; $0c + const DUEL_ANIM_BIG_LIGHTNING ; $0d + const DUEL_ANIM_SMALL_FLAME ; $0e + const DUEL_ANIM_BIG_FLAME ; $0f + const DUEL_ANIM_FIRE_SPIN ; $10 + const DUEL_ANIM_DIVE_BOMB ; $11 + const DUEL_ANIM_WATER_JETS ; $12 + const DUEL_ANIM_WATER_GUN ; $13 + const DUEL_ANIM_WHIRLPOOL ; $14 + const DUEL_ANIM_HYDRO_PUMP ; $15 + const DUEL_ANIM_BLIZZARD ; $16 + const DUEL_ANIM_PSYCHIC ; $17 + const DUEL_ANIM_LEER ; $18 + const DUEL_ANIM_BEAM ; $19 + const DUEL_ANIM_HYPER_BEAM ; $1a + const DUEL_ANIM_ROCK_THROW ; $1b + const DUEL_ANIM_STONE_BARRAGE ; $1c + const DUEL_ANIM_PUNCH ; $1d + const DUEL_ANIM_THUNDERPUNCH ; $1e + const DUEL_ANIM_FIRE_PUNCH ; $1f + const DUEL_ANIM_STRETCH_KICK ; $20 + const DUEL_ANIM_SLASH ; $21 + const DUEL_ANIM_WHIP ; $22 + const DUEL_ANIM_SONICBOOM ; $23 + const DUEL_ANIM_FURY_SWIPES ; $24 + const DUEL_ANIM_DRILL ; $25 + const DUEL_ANIM_POT_SMASH ; $26 + const DUEL_ANIM_BONEMERANG ; $27 + const DUEL_ANIM_SEISMIC_TOSS ; $28 + const DUEL_ANIM_NEEDLES ; $29 + const DUEL_ANIM_WHITE_GAS ; $2a + const DUEL_ANIM_POWDER ; $2b + const DUEL_ANIM_GOO ; $2c + const DUEL_ANIM_BUBBLES ; $2d + const DUEL_ANIM_STRING_SHOT ; $2e + const DUEL_ANIM_BOYFRIENDS ; $2f + const DUEL_ANIM_LURE ; $30 + const DUEL_ANIM_TOXIC ; $31 + const DUEL_ANIM_CONFUSE_RAY ; $32 + const DUEL_ANIM_SING ; $33 + const DUEL_ANIM_SUPERSONIC ; $34 + const DUEL_ANIM_PETAL_DANCE ; $35 + const DUEL_ANIM_PROTECT ; $36 + const DUEL_ANIM_BARRIER ; $37 + const DUEL_ANIM_SPEED ; $38 + const DUEL_ANIM_WHIRLWIND ; $39 + const DUEL_ANIM_CRY ; $3a + const DUEL_ANIM_QUESTION_MARK ; $3b + const DUEL_ANIM_SELFDESTRUCT ; $3c + const DUEL_ANIM_BIG_SELFDESTRUCT_1 ; $3d + const DUEL_ANIM_HEAL ; $3e + const DUEL_ANIM_DRAIN ; $3f + const DUEL_ANIM_DARK_GAS ; $40 + const DUEL_ANIM_BIG_SELFDESTRUCT_2 ; $41 + const DUEL_ANIM_UNUSED_42 ; $42 + const DUEL_ANIM_UNUSED_43 ; $43 + const DUEL_ANIM_BENCH_THUNDER ; $44 + const DUEL_ANIM_QUICKFREEZE ; $45 + const DUEL_ANIM_BENCH_GLOW ; $46 + const DUEL_ANIM_FIREGIVER_START ; $47 + const DUEL_ANIM_UNUSED_48 ; $48 + const DUEL_ANIM_HEALING_WIND ; $49 + const DUEL_ANIM_BENCH_WHIRLWIND ; $4a + const DUEL_ANIM_EXPAND ; $4b + const DUEL_ANIM_CAT_PUNCH ; $4c + const DUEL_ANIM_THUNDER_WAVE ; $4d + const DUEL_ANIM_FIREGIVER_PLAYER ; $4e + const DUEL_ANIM_FIREGIVER_OPP ; $4f + const DUEL_ANIM_UNUSED_50 ; $50 + const DUEL_ANIM_PLAYER_SHUFFLE ; $51 + const DUEL_ANIM_OPP_SHUFFLE ; $52 + const DUEL_ANIM_BOTH_SHUFFLE ; $53 + const DUEL_ANIM_UNUSED_54 ; $54 + const DUEL_ANIM_BOTH_DRAW ; $55 + const DUEL_ANIM_PLAYER_DRAW ; $56 + const DUEL_ANIM_OPP_DRAW ; $57 + const DUEL_ANIM_COIN_SPIN ; $58 + const DUEL_ANIM_COIN_TOSS_GOING_HEADS ; $59 + const DUEL_ANIM_COIN_TOSS_GOING_TAILS ; $5a + const DUEL_ANIM_COIN_TAILS ; $5b + const DUEL_ANIM_COIN_HEADS ; $5c + const DUEL_ANIM_DUEL_WIN ; $5d + const DUEL_ANIM_DUEL_LOSS ; $5e + const DUEL_ANIM_DUEL_DRAW ; $5f + const DUEL_ANIM_UNUSED_60 ; $60 DEF NUM_REGULAR_DUEL_ANIMS EQU const_value diff --git a/src/constants/duel_constants.asm b/src/constants/duel_constants.asm index 0a73b4e5..94be780e 100644 --- a/src/constants/duel_constants.asm +++ b/src/constants/duel_constants.asm @@ -5,6 +5,10 @@ DEF HP_BAR_LENGTH EQU MAX_HP / 10 DEF STARTING_HAND_SIZE EQU 7 +; coin result constants +DEF TAILS EQU 0 +DEF HEADS EQU 1 + ; hWhoseTurn constants DEF PLAYER_TURN EQUS "HIGH(wPlayerDuelVariables)" DEF OPPONENT_TURN EQUS "HIGH(wOpponentDuelVariables)" diff --git a/src/data/duel/animations/duel_animations.asm b/src/data/duel/animations/duel_animations.asm index 701c07dc..aef84166 100644 --- a/src/data/duel/animations/duel_animations.asm +++ b/src/data/duel/animations/duel_animations.asm @@ -713,7 +713,7 @@ Animations: db SFX_STOP ; sfx id db NONE ; handler function - ; DUEL_ANIM_COIN_TOSS1 + ; DUEL_ANIM_COIN_TOSS_GOING_HEADS db SPRITE_DUEL_COIN ; sprite ID db PALETTE_92 ; palette ID db SPRITE_ANIM_168 ; anim ID @@ -721,7 +721,7 @@ Animations: db SFX_COIN_TOSS ; sfx id db NONE ; handler function - ; DUEL_ANIM_COIN_TOSS2 + ; DUEL_ANIM_COIN_TOSS_GOING_TAILS db SPRITE_DUEL_COIN ; sprite ID db PALETTE_92 ; palette ID db SPRITE_ANIM_169 ; anim ID diff --git a/src/engine/duel/core.asm b/src/engine/duel/core.asm index cdbe02d5..49a8d40c 100644 --- a/src/engine/duel/core.asm +++ b/src/engine/duel/core.asm @@ -7844,6 +7844,7 @@ _TossCoin:: ld a, [wDuelDisplayedScreen] cp COIN_TOSS jr z, .print_text + xor a ld [wCoinTossNumTossed], a call EmptyScreen @@ -7858,7 +7859,7 @@ _TossCoin:: ld [wDuelDisplayedScreen], a lb de, 0, 12 lb bc, 20, 6 - ld hl, $0000 + ld hl, NULL call DrawLabeledTextBox call EnableLCD lb de, 1, 14 @@ -7885,11 +7886,11 @@ _TossCoin:: xor a ld [wCoinTossNumHeads], a -.print_coin_tally +.toss_next_coin ; skip printing text if it's only one coin toss ld a, [wCoinTossTotalNum] cp 2 - jr c, .asm_7223 + jr c, .skip_print_coin_tally ; write "#coin/#total coins" lb bc, 15, 11 @@ -7903,30 +7904,31 @@ _TossCoin:: ld a, [wCoinTossTotalNum] call WriteTwoDigitNumberInTxSymbolFormat -.asm_7223 +.skip_print_coin_tally call ResetAnimationQueue ld a, DUEL_ANIM_COIN_SPIN call PlayDuelAnimation ld a, [wCoinTossDuelistType] or a - jr z, .asm_7236 - call Func_7324 - jr .asm_723c - -.asm_7236 + jr z, .player_tossing ; DUELIST_TYPE_PLAYER +; opponent tossing + call .WaitForOpponent + jr .generate_coin_result +.player_tossing + ; wait for input, and send byte when player is ready to toss call WaitForWideTextBoxInput - call Func_72ff + call .SendSerialByte -.asm_723c +.generate_coin_result call ResetAnimationQueue - ld d, DUEL_ANIM_COIN_TOSS2 - ld e, $0 ; tails + ld d, DUEL_ANIM_COIN_TOSS_GOING_TAILS + ld e, TAILS call UpdateRNGSources rra jr c, .got_result - ld d, DUEL_ANIM_COIN_TOSS1 - ld e, $1 ; heads + ld d, DUEL_ANIM_COIN_TOSS_GOING_HEADS + ld e, HEADS .got_result ; already decided on coin toss result, @@ -7936,11 +7938,13 @@ _TossCoin:: call PlayDuelAnimation ld a, [wCoinTossDuelistType] or a - jr z, .wait_anim + jr z, .wait_anim ; player tossing +; opponent tossing ld a, e - call Func_7310 - ld e, a + call .GetOpponentCoinResult + ld e, a ; coin result from opponent jr .done_toss_anim + .wait_anim push de call DoFrame @@ -7948,7 +7952,7 @@ _TossCoin:: pop de jr c, .wait_anim ld a, e - call Func_72ff + call .SendSerialByte .done_toss_anim ld b, DUEL_ANIM_COIN_HEADS @@ -7996,7 +8000,7 @@ _TossCoin:: ld e, 0 ld a, [wCoinTossNumTossed] ; calculate the offset to draw the circle/cross -.asm_72a3 +.loop_get_offset ; if < 10, then the offset is simply calculated ; from wCoinTossNumTossed * 2... cp 10 @@ -8005,7 +8009,7 @@ _TossCoin:: inc e inc e sub 10 - jr .asm_72a3 + jr .loop_get_offset .got_offset add a @@ -8021,29 +8025,39 @@ _TossCoin:: ld a, [wCoinTossDuelistType] or a - jr z, .asm_72dc + jr z, .player_tossing_next_coin + ; wait for input if we are finished, that is + ; if wCoinTossNumTossed == wCoinTossTotalNum ld a, [hl] ld hl, wCoinTossTotalNum cp [hl] call z, WaitForWideTextBoxInput - call Func_7324 + + ; delay/wait for link opp input + call .WaitForOpponent + + ; if we are "tossing until tails", + ; (i.e. wCoinTossTotalNum == 0) + ; and we got no heads, wait for input ld a, [wCoinTossTotalNum] ld hl, wCoinTossNumHeads or [hl] - jr nz, .asm_72e2 + jr nz, .check_if_finished call z, WaitForWideTextBoxInput - jr .asm_72e2 + jr .check_if_finished -.asm_72dc +.player_tossing_next_coin call WaitForWideTextBoxInput - call Func_72ff + call .SendSerialByte -.asm_72e2 +.check_if_finished call FinishQueuedAnimations + + ; we're finished if wCoinTossNumTossed == wCoinTossTotalNum ld a, [wCoinTossNumTossed] ld hl, wCoinTossTotalNum cp [hl] - jp c, .print_coin_tally + jp c, .toss_next_coin call ExchangeRNG call FinishQueuedAnimations call ResetAnimationQueue @@ -8055,58 +8069,71 @@ _TossCoin:: scf ret -Func_72ff: +; input: +; - a = byte to send through serial +.SendSerialByte: ldh [hff96], a ld a, [wDuelType] cp DUELTYPE_LINK - ret nz + ret nz ; not link duel ldh a, [hff96] call SerialSendByte - call Func_7344 + call .CheckTransmissionError ret -Func_7310: +; if opponent is AI, then wait for animation and +; use the result generated beforehand (input register a) +; if link opponent, then wait for serial byte which +; gives the coin result +; input: +; - a = coin result to use for AI (HEADS or TAILS) +; output: +; - a = coin result (HEADS or TAILS) +.GetOpponentCoinResult: ldh [hff96], a ld a, [wDuelType] cp DUELTYPE_LINK - jr z, Func_7338 -.loop_anim + jr z, .wait_serial_byte_recv +.wait_anim_ai call DoFrame call CheckAnyAnimationPlaying - jr c, .loop_anim + jr c, .wait_anim_ai ldh a, [hff96] ret -Func_7324: +; waits for opponent +; AI delays for 30 frames +; link opponent sends byte through serial when ready +.WaitForOpponent: ldh [hff96], a ld a, [wDuelType] cp DUELTYPE_LINK - jr z, Func_7338 + jr z, .wait_serial_byte_recv ; delay coin flip for AI opponent ld a, 30 -.asm_732f +.ai_coin_toss_delay call DoFrame dec a - jr nz, .asm_732f + jr nz, .ai_coin_toss_delay ldh a, [hff96] ret -Func_7338: +.wait_serial_byte_recv call DoFrame call SerialRecvByte - jr c, Func_7338 - call Func_7344 + jr c, .wait_serial_byte_recv + call .CheckTransmissionError ret -Func_7344: +.CheckTransmissionError: push af ld a, [wSerialFlags] or a - jr nz, .asm_734d + jr nz, .transmission_error pop af ret -.asm_734d +.transmission_error call FinishQueuedAnimations call DuelTransmissionError ret diff --git a/src/engine/duel/effect_functions.asm b/src/engine/duel/effect_functions.asm index 643229a0..51fe1322 100644 --- a/src/engine/duel/effect_functions.asm +++ b/src/engine/duel/effect_functions.asm @@ -415,10 +415,12 @@ PrintDevolvedCardNameAndLevelText: pop de ret +; input: +; - a = PLAY_AREA_* constant of Bench Pokémon to switch to HandleSwitchDefendingPokemonEffect: ld e, a cp $ff - ret z + ret z ; none selected ; check Defending Pokemon's HP ld a, DUELVARS_ARENA_CARD_HP @@ -433,7 +435,7 @@ HandleSwitchDefendingPokemonEffect: .switch call HandleNoDamageOrEffect - ret c + ret c ; no effect ; attack was successful, switch Defending Pokemon call SwapTurn