AgentStack
SKILL verified Apache-2.0 Self-run

Godot 2d Movement

skill-gamedev-skills-awesome-gamedev-agent-skills-godot-2d-movement · by gamedev-skills

>

No reviews yet
0 installs
12 views
0.0% view→install

Install

$ agentstack add skill-gamedev-skills-awesome-gamedev-agent-skills-godot-2d-movement

✓ scanned · ✓ verified — works with Claude Code, Cursor, and more.

Security review

✓ Passed

No issues found. Passed automated security review. · v0.1.0 How review works →

  • Prompt-injection patterns
  • Secret / credential exfiltration
  • Dangerous shell & filesystem operations
  • Untrusted network calls
  • Known-malicious package signatures

What it can access

  • Network access No
  • Filesystem access No
  • Shell / process execution No
  • Environment & secrets No
  • Dynamic code execution No

From automated source analysis of v0.1.0. “Used” means the capability is present in the source — more access means more to trust, not that it’s unsafe.

Are you the author of Godot 2d Movement? Claim this listing to set pricing, connect Stripe payouts, and keep 70% of every sale.
Sign up to claim

About

Godot 2D Movement (4.x)

Build responsive 2D character controllers with CharacterBody2D and the argument-less move_and_slide(). Targets Godot 4.3+.

When to use

  • Use when scripting a 2D player/enemy that moves and collides: platformer (gravity +

jump) or top-down (free 8-direction), slope walking, or wall/floor detection.

  • Use when move_and_slide() "does nothing", the character sinks through floors, or

is_on_floor() is always false.

**When not to use:** dynamic rigid bodies, areas, raycasts, collision layers → godot-physics; tile-based levels → godot-tilemap; full platformer game template → the platformer genre skill; engine-agnostic feel tuning → physics-tuning.

Core workflow

  1. Use CharacterBody2D with a CollisionShape2D child. It is script-driven: it

does not fall or react to forces on its own.

  1. Set the velocity property, then call move_and_slide() (no arguments in 4.x).

The method reads velocity, moves the body, slides along surfaces, and updates velocity to reflect what actually happened.

  1. Do it in _physics_process(delta)move_and_slide() uses the physics step's

delta internally, so do not multiply velocity by delta yourself.

  1. Platformer: add gravity to velocity.y each tick, jump by setting velocity.y

negative when is_on_floor().

  1. Top-down: build a direction from input and scale by speed; set

motion_mode = MOTION_MODE_FLOATING so there is no "floor/wall" distinction.

  1. Read results with is_on_floor(), is_on_wall(), get_wall_normal(), and

get_slide_collision(i) after the call.

Patterns

1. Platformer controller (gravity, jump, slopes)

extends CharacterBody2D

@export var speed := 200.0
@export var jump_velocity := -400.0
@export var gravity := 1200.0          # pixels/sec^2 (tune to taste)

func _physics_process(delta: float) -> void:
    # Apply gravity while airborne.
    if not is_on_floor():
        velocity.y += gravity * delta

    # Jump only when grounded (Input action set in Project Settings > Input Map).
    if Input.is_action_just_pressed("jump") and is_on_floor():
        velocity.y = jump_velocity

    # Horizontal input: -1, 0, or 1.
    var dir := Input.get_axis("move_left", "move_right")
    if dir != 0.0:
        velocity.x = dir * speed
    else:
        velocity.x = move_toward(velocity.x, 0.0, speed)   # decelerate to a stop

    move_and_slide()   # 4.x: no arguments; uses and updates `velocity`

2. Top-down 8-direction movement

extends CharacterBody2D

@export var speed := 220.0

func _ready() -> void:
    motion_mode = CharacterBody2D.MOTION_MODE_FLOATING  # no floor/ceiling concept

func _physics_process(_delta: float) -> void:
    # get_vector returns a normalized-ish Vector2 from four input actions.
    var input := Input.get_vector("move_left", "move_right", "move_up", "move_down")
    velocity = input * speed
    move_and_slide()

3. Reading slide collisions after moving

func _physics_process(delta: float) -> void:
    # ... set velocity ...
    move_and_slide()
    for i in get_slide_collision_count():
        var c := get_slide_collision(i)
        var other := c.get_collider()
        if other and other.is_in_group("enemies"):
            take_damage(1)        # touched an enemy while moving

4. Coyote time (forgiving jump just after leaving a ledge)

@export var coyote_time := 0.1
var _coyote := 0.0

func _physics_process(delta: float) -> void:
    if not is_on_floor():
        velocity.y += gravity * delta
        _coyote -= delta
    else:
        _coyote = coyote_time

    if Input.is_action_just_pressed("jump") and _coyote > 0.0:
        velocity.y = jump_velocity
        _coyote = 0.0
    # ... horizontal input + move_and_slide() ...

Pitfalls

  • 3.x signature is gone. move_and_slide(velocity) (returning the new velocity) was

removed. In 4.x set the velocity property and call move_and_slide() with no args. move_and_slide(velocity, Vector2.UP) will not parse.

  • Multiplying velocity by delta. move_and_slide() already accounts for the physics

delta. Setting velocity = dir * speed * delta makes the body crawl.

  • Movement in _process instead of _physics_process causes frame-rate-dependent,

jittery motion. Always move in _physics_process.

  • is_on_floor() always false when up_direction is wrong (default Vector2.UP),

there is no CollisionShape2D, or you never called move_and_slide() this frame.

  • Sinking through floors usually means the collision shape is missing/zero-sized, the

floor body is on a layer this body's mask doesn't include, or you moved the body via position += instead of velocity + move_and_slide().

  • Slope slipping while idle: keep floor_stop_on_slope = true (default) and set a

floor_snap_length so the body sticks to downward slopes.

References

  • For one-way platforms, moving platforms, jump buffering, variable jump height, and

move_and_collide() (manual collision response), read references/controller-recipes.md.

Related skills

  • godot-physics — collision layers/masks, areas, raycasts, rigid bodies.
  • godot-tilemap — building the levels this character walks on.
  • godot-animation — driving sprite/skeletal animation from movement state.
  • camera-systems — follow camera, deadzone, and look-ahead that track this character.
  • platformer / input-systems — full genre template and rebindable input.

Source & license

This open-source skill is cataloged on AgentStack and links to its original source — we do not rehost the code.

Install and usage instructions live in the source repository linked above.

Reviews

No reviews yet — be the first.

Versions

  • v0.1.0 Imported from the upstream source.