Godot Version
v4.4.1.stable.official [49a5bc7b6]
Question
If I try to implement coyote time, the game lets me do a double jump (a janky triple jump because I have my own double jump).
extends CharacterBody2D
## 75 is my fps
# How fast you accelerate while on the ground
const grndaccel: float = 30 * 75
# How fast you decelerate while on the ground
const grnddecel: float = 65 * 75
# How fast you accelerate in the air
const airaccel: float = 15 * 75
# Speed cap
const maxspeed: float = 300
# How high you jump
const jumpvelocity: float = -400
# How high you double jump
const doublejumpvelocity: float = -300
# Gravity
const gravity: float = 750
# How fast you can fall
const maxfallspeed: float = 1000
# TODO How much knockback is applied on hit (100/value)
const weight: float = 100
@export var playerstates: Array = ["grounded", "airborne", "something else"]
@export var state: String = playerstates[1]
@export var candoublejump: bool = false
@export var canjump: bool = false
func _physics_process(delta: float) -> void:
var direction = Input.get_axis("left", "right")
if state == playerstates[0]:
_grounded_physics(delta, direction)
if state == playerstates[1]:
_airborne_physics(delta, direction)
%Label.text = str(canjump)
move_and_slide()
func _grounded_physics(delta: float, direction: float) -> void:
velocity.x = move_toward(velocity.x, maxspeed * direction, grndaccel * delta)
%Coyotetime.start()
# refresh jump and double jump
canjump = true
candoublejump = true # irrelevant double jump not the one that im talking about
if Input.is_action_just_pressed("jump"):
velocity.y = jumpvelocity
state = playerstates[1] # sets player state to airborne
canjump = false
if !is_on_floor():
state = playerstates[1]
## canjump = false
# FIXME If i put this line here, I can't do coyote time,
# but if I don't, then the game only sets it to false for
# one frame, and then back to true again, until %Coyotetime
# times out and sets it back to false.
func _airborne_physics(delta: float, direction: float) -> void:
# if a direction is held mid-air, accelerate to that
# will not decelerate you if no button is held
# FIXME might decelerate you if you get launched with speed higher than maxspeed
# and hold in the same direction, probably wont happen often
if direction:
velocity.x = move_toward(velocity.x, maxspeed * direction, airaccel * delta)
if Input.is_action_just_pressed("jump"):
# coyote time
# FIXME seems to behave weirdly, for some reason you can do
# a second regular jump until the timer runs out
if canjump == true:
velocity.y = jumpvelocity
canjump = false
# double jump
elif candoublejump == true:
velocity.y = doublejumpvelocity
candoublejump = false
# gravity
# should probably use move_toward()
if velocity.y < maxfallspeed:
velocity.y += gravity * delta
if is_on_floor():
state = playerstates[0]
func _on_coyotetime_timeout() -> void:
canjump = false