You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

165 lines
2.4 KiB

INCLUDE "oam.inc"
SECTION "Collision", ROM0
DEF COLLF_WALK EQU (1 << 0)
DEF COLLF_LADDER EQU (1 << 1)
DEF COLLF_PORTAL EQU (1 << 2)
; Determines if player has hit the background
; @return NZ = false, Z = true
player_bg_collides::
; C = MAP X = PLAYER X / 8 + CAMERA X
ld a, [PLAYER_X]
call get_tile_coord
ld c, a
ld a, [CURRENT_CAMERA_X]
add c
ld c, a
; C < 0
ld a, c
cpl
bit 7, a
ret z
; C >= MAP WIDTH
ld a, [CURRENT_MAP_WIDTH]
cp c
jr nz, .load_y
ret
.load_y:
; B = MAP Y = PLAYER Y / 8 + CAMERA Y
ld a, [PLAYER_Y]
call get_tile_coord
ld b, a
ld a, [CURRENT_CAMERA_Y]
add b
ld b, a
; B < 0
ld a, b
cpl
bit 7, a
ret z
; B >= MAP HEIGHT
ld a, [CURRENT_MAP_HEIGHT]
cp b
jr nz, .check_tiles
; Set NZ
or $ff
ret
.check_tiles:
; top left
call can_move_to
ret z
; top right
inc c
call can_move_to
ret z
; bottom left
dec c
inc b
call can_move_to
ret z
; bottom right
inc c
call can_move_to
ret
; Check if the player is in mid-air
; @note NZ = true, Z = false
player_in_air::
; c = x % 8 == 0 ? x/8 : x/8 + 1
ld a, [PLAYER_X]
call get_tile_coord
ld c, a
ld a, [CURRENT_CAMERA_X]
add c
ld c, a
ld a, [PLAYER_Y]
call get_tile_coord
ld b, a
ld a, [CURRENT_CAMERA_Y]
add b
ld b, a
; check underneath player (2 tiles down from top-left sprite)
inc b
inc b
call can_move_to
ret z
inc c
call can_move_to
ret
; Check whether the location can be moved to or not
; @param b y-coordinate
; @param c x-coordinate
; @destroy a, d, e
; @note NZ = true, Z = false
can_move_to:
push bc
push hl
ld a, [CURRENT_MAP_COLLISION]
ld l, a
ld a, [CURRENT_MAP_COLLISION + 1]
ld h, a
ld a, [CURRENT_MAP_WIDTH]
ld d, 0
ld e, a
; compute map index (HL + B * (CURRENT_MAP_WIDTH + 1) + C)
.mul_y_width:
add hl, de
dec b
jr nz, .mul_y_width
add hl, bc
ld a, [hl]
and COLLF_WALK
pop hl
pop bc
ret
; Convert from pixel space to tile space
; @param a Screen pixel coordinate
; @destroys hl
; @returns Screen tile coordinate in A
get_tile_coord:
ld hl, sp - 1
ld [hl], a
and %111
ld a, [hl]
jr z, .skip_inc
add 8
.skip_inc:
srl a
srl a
srl a
ret