I'm trying to code a Metroid style propulsion jump with a determined height but with no success. How can achieve this?

:information_source: Attention Topic was automatically imported from the old Question2Answer platform.
:bust_in_silhouette: Asked By Oni

Hello!

As the title says, I’m trying to code a jump that feels like the character is accelerating at the start, like a propulsion jet BUT with a pre determined height. I’m using Metroid Prime as reference:

It’s hard to notice on video but there is some sort of acceleration right after she starts jumping

Usually for a regular jump in fps you can simply set the velocity.y to the desired strength and then subtract it with gravity

func jump():
velocity.y = strength

func _physics_process(delta):
velocity.y -= gravity * _delta
move_and_slide()

Later I’ve found a method to use a defined height to determine the strength of the jump:

func jump():
velocity += sqrt(jump_height * 2 * gravity) * Vector3.UP

So if I set jump_height to 2 for example, the character will jump 2 meters

Now I’m trying to do the same thing but using a linear acceleration, like you are using a jetpack to jump 2 meters, so you gain the desired velocity over a short period of time. You don’t need to hold the jump button thought, just press it once.

How can I achieve this? How can I make my character jump accelerating to the desired velocity over a really short period of time to give this impression of weight/propulsion, but still constrain the jump to the defined height?

Thank you!

:bust_in_silhouette: Reply From: zeludtnecniv

Hi,
I figure it out in 2D so it can be easily move to 3D:

@export var Jump_Height = 500;     #Target Height
@export var Jump_start_power = 50; #Jump force
@export var Jump_boost_power = 30; #JetPack boost force
var jumping = null;
func jump():
    if (is_on_floor()):
	    jumping = null
    if Input.is_action_just_pressed("ui_accept") and is_on_floor():
	    jumping = position.y;
	    velocity += sqrt(Jump_start_power * 2 * gravity) * Vector2.UP
    if (jumping != null):
	
	    var maxacc = Jump_Height - velocity.y * velocity.y / gravity
	
	    if (jumping - position.y > Jump_start_power && (jumping - position.y) < maxacc && velocity.y < 0):
		    velocity.y += -Jump_boost_power

You need to call this jump function in _physics _process