2D movement
CharacterBody2D: input and obstacle collisions.
Top-down movement without gravity. Requires a C# project: setup.
1. Create a 2D document
Create a document, choose an Entity2D root, name it World2D and save as World2D.rscene. If the editor created a 3D root, start an empty document and choose the root type manually.
World2D (Entity2D)
├── Player (CharacterBody2D)
│ ├── Visual (Polygon2D)
│ └── CollisionShape2D
└── Wall (StaticBody2D)
├── Visual (Polygon2D)
└── CollisionShape2DIn 2D, X increases rightward and Y downward. Positions use game-window pixels before scaling. This lesson needs no camera: objects sit near the origin in the visible window area. You can set a 640 × 360 viewport under Project Settings → Display → Window for testing.
2. Set up the shapes
Set Player → Position to (160, 160). In its Visual → Polygon property, enter four points: (-16, -16), (16, -16), (16, 16), (-16, 16). This makes a 32 × 32 square. Choose a light Color.
For Player/CollisionShape2D, create a RectangleShape2D with Size: (32, 32). Keep both children's local positions at (0, 0).
Set Wall → Position to (320, 160). Its Visual uses points (-16, -80), (16, -80), (16, 80), (-16, 80) and a different color. Give its CollisionShape2D a RectangleShape2D with Size: (32, 160).
Leave collision layers and masks at their defaults. Polygon2D is visible but does not block a character by itself; that requires a Shape within a physics body.
3. Configure input
Under Project → Project Settings → Input Map, add move_left, move_right, move_up, move_down and bind A/D/W/S or the corresponding arrow keys. Reuse the left and right actions if you made them in the 3D lesson. The vertical actions here are named move_up and move_down.
4. Add Player2D.cs
Attach Scripts/Player2D.cs to Player, using CharacterBody2D as its base:
using Reckfell;
public partial class Player2D : CharacterBody2D
{
[Export] public float Speed { get; set; } = 220.0f;
public override void _PhysicsProcess(double delta)
{
Vector2 direction = Input.GetVector("move_left", "move_right", "move_up", "move_down");
Velocity = direction * Speed;
MoveAndSlide();
}
}Save, build C# and press F6. Click the game window. The square should move and stop against the wall.
Speed and collisions
Speed is measured in pixels per second in 2D world coordinates. This is a different scale from the 4 units per second in the 3D lesson. MoveAndSlide() already accounts for the physics interval, so do not multiply velocity by delta.
There is no gravity here: movement works equally in every direction. A platformer needs separate vertical velocity, gravity and floor checks, similar to the 3D controller but using the 2D API.
For invisible objects, check Polygon, opacity and position. For missing collisions, check both bodies’ Shapes. Troubleshooting.