Files

166 lines
4.6 KiB
Python

import pytest
from game import constants
from tests.support import makeWorld, settle
from game.sim.inputCommand import InputCommand
ledgeLevel = [
" ",
" ",
" p ",
"XXX ",
]
flatLevel = [
" p ",
" ",
"XXXXXXXX",
]
wallLevel = [
" #",
" #",
" #",
" #",
"XXXXX",
]
def walkOffLedge(world):
for _ in range(40):
world.step(InputCommand(right=True, run=True))
if not world.player.onGround:
return True
return False
def test_coyoteJumpKeepsAirJump():
world = makeWorld(ledgeLevel)
assert walkOffLedge(world)
world.step(InputCommand(right=True, jump=True, jumpHeld=True))
player = world.player
assert player.vy == pytest.approx(constants.jumpVelocity + constants.gravity)
assert player.airJumps == constants.maxAirJumps
def test_afterCoyoteExpiresJumpIsDoubleJump():
world = makeWorld(ledgeLevel)
assert walkOffLedge(world)
for _ in range(constants.coyoteFrames + 2):
world.step(InputCommand())
world.step(InputCommand(jump=True, jumpHeld=True))
player = world.player
assert player.airJumps == 0
assert player.vy == pytest.approx(constants.doubleJumpVelocity + constants.gravity)
def test_doubleJumpConsumesAirJump():
world = makeWorld(flatLevel)
settle(world, 20)
world.step(InputCommand(jump=True, jumpHeld=True))
assert world.player.vy < 0
assert world.player.airJumps == constants.maxAirJumps
for _ in range(3):
world.step(InputCommand(jumpHeld=True))
world.step(InputCommand(jump=True, jumpHeld=True))
assert world.player.airJumps == 0
assert world.player.vy == pytest.approx(constants.doubleJumpVelocity + constants.gravity)
def test_jumpBufferFiresOnLanding():
world = makeWorld(flatLevel)
player = world.player
player.airJumps = 0
player.coyoteTimer = 0
player.onGround = False
player.y = 2 * constants.tileSize - player.h - 5.0
world.step(InputCommand(jump=True))
minVy = 0.0
grounded = False
for _ in range(14):
world.step(InputCommand())
grounded = grounded or world.player.onGround
minVy = min(minVy, world.player.vy)
assert grounded
assert minVy == pytest.approx(constants.jumpVelocity + constants.gravity)
def test_noBufferNoRejump():
world = makeWorld(flatLevel)
player = world.player
player.airJumps = 0
player.coyoteTimer = 0
player.onGround = False
player.y = 2 * constants.tileSize - player.h - 5.0
minVy = 0.0
for _ in range(14):
world.step(InputCommand())
minVy = min(minVy, world.player.vy)
assert minVy >= 0.0
def test_dashLaunchesAndCoolsDown():
world = makeWorld(flatLevel)
settle(world, 20)
world.step(InputCommand(right=True, dash=True))
player = world.player
assert player.vx == pytest.approx(constants.dashSpeed)
assert player.dashTimer == constants.dashFrames - 1
assert player.vy == 0.0
assert player.dashCooldown > 0
def test_wallSlideClampsFallSpeed():
world = makeWorld(wallLevel)
player = world.player
player.x = 4 * constants.tileSize - player.w
player.y = constants.tileSize
player.vy = 5.0
player.onGround = False
world.step(InputCommand(right=True))
assert player.wallSliding
assert player.vy == pytest.approx(constants.wallSlideSpeed)
def test_noWallSlideWhenNotPressingIntoWall():
world = makeWorld(wallLevel)
player = world.player
player.x = 4 * constants.tileSize - player.w
player.y = constants.tileSize
player.vy = 5.0
player.onGround = False
world.step(InputCommand(left=True))
assert not player.wallSliding
assert player.vy > constants.wallSlideSpeed
def test_wallJumpPushesAway():
world = makeWorld(wallLevel)
player = world.player
player.x = 4 * constants.tileSize - player.w
player.y = constants.tileSize
player.vy = 2.0
player.onGround = False
world.step(InputCommand(right=True, jump=True, jumpHeld=True))
assert player.vx == pytest.approx(-constants.wallJumpVelocityX)
assert player.vy == pytest.approx(constants.wallJumpVelocityY + constants.gravity)
def test_variableJumpCutReducesRise():
holdWorld = makeWorld(flatLevel)
settle(holdWorld, 20)
holdWorld.step(InputCommand(jump=True, jumpHeld=True))
holdWorld.step(InputCommand(jumpHeld=True))
holdVy = holdWorld.player.vy
cutWorld = makeWorld(flatLevel)
settle(cutWorld, 20)
cutWorld.step(InputCommand(jump=True, jumpHeld=True))
cutWorld.step(InputCommand(jumpHeld=False))
cutVy = cutWorld.player.vy
assert holdVy < -6.0
assert cutVy > -4.0
assert cutVy > holdVy