Up to date
This page is up to date for Godot 4.2
.
If you still find outdated information, please open an issue.
Visão geral de movimento 2D¶
Introdução¶
Todo iniciante está lá: "Como faço para mover meu personagem?" Dependendo do estilo de jogo que você está fazendo, você pode ter requisitos especiais, mas em geral o movimento na maioria dos jogos 2D é baseado em um pequeno número de designs.
We'll use CharacterBody2D for these examples, but the principles will apply to other node types (Area2D, RigidBody2D) as well.
Configurar¶
Each example below uses the same scene setup. Start with a CharacterBody2D
with two
children: Sprite2D
and CollisionShape2D
. You can use the Godot icon ("icon.png")
for the Sprite2D's texture or use any other 2D image you have.
Abra Projeto -> Configurações do Projeto
e selecione a guia "Mapa de Entrada". Adicione as seguintes ações de entrada (consulte InputEvent para obter detalhes):
Movimento em 8 direções¶
Neste cenário, você quer que o usuário pressione as quatro teclas direcionais (para cima/esquerda/baixo/direita ou W/A/S/D) e se mova na direção selecionada. O nome "movimento em 8 direções" vem do fato de que o jogador pode se mover diagonalmente pressionando duas teclas ao mesmo tempo.
Add a script to the character body and add the following code:
extends CharacterBody2D
@export var speed = 400
func get_input():
var input_direction = Input.get_vector("left", "right", "up", "down")
velocity = input_direction * speed
func _physics_process(delta):
get_input()
move_and_slide()
using Godot;
public partial class Movement : CharacterBody2D
{
[Export]
public int Speed { get; set; } = 400;
public void GetInput()
{
Vector2 inputDirection = Input.GetVector("left", "right", "up", "down");
Velocity = inputDirection * Speed;
}
public override void _PhysicsProcess(double delta)
{
GetInput();
MoveAndSlide();
}
}
In the get_input()
function, we use Input get_vector()
to check for the
four key events and sum return a direction vector.
We can then set our velocity by multiplying this direction vector, which has a
length of 1
, by our desired speed.
Dica
Se você nunca usou matemática vetorial antes, ou precisa de uma atualização, você pode ver uma explicação sobre o uso de vetores no Godot em Matemática vetorial.
Nota
Se o código acima não faz nada quando você pressiona as teclas, verifique se você configurou as ações de entrada corretamente conforme descrito na parte Configurar deste tutorial.
Rotação + movimento¶
Esse tipo de movimento às vezes é chamado de "estilo Asteroids" porque se assemelha a como o clássico jogo de arcade que funcionava assim. Pressionar a esquerda/direita gira o caractere, enquanto para cima/para baixo o move para frente ou para trás em qualquer direção que esteja voltado.
extends CharacterBody2D
@export var speed = 400
@export var rotation_speed = 1.5
var rotation_direction = 0
func get_input():
rotation_direction = Input.get_axis("left", "right")
velocity = transform.x * Input.get_axis("down", "up") * speed
func _physics_process(delta):
get_input()
rotation += rotation_direction * rotation_speed * delta
move_and_slide()
using Godot;
public partial class Movement : CharacterBody2D
{
[Export]
public int Speed { get; set; } = 400;
[Export]
public float RotationSpeed { get; set; } = 1.5f;
private float _rotationDirection;
public void GetInput()
{
_rotationDirection = Input.GetAxis("left", "right");
Velocity = Transform.X * Input.GetAxis("down", "up") * Speed;
}
public override void _PhysicsProcess(double delta)
{
GetInput();
Rotation += _rotationDirection * RotationSpeed * (float)delta;
MoveAndSlide();
}
}
Here we've added two variables to track our rotation direction and speed.
The rotation is applied directly to the body's rotation
property.
To set the velocity, we use the body's transform.x
which is a vector pointing
in the body's "forward" direction, and multiply that by the speed.
Rotação + movimento (mouse)¶
Este estilo de movimento é uma variação do anterior. Desta vez, a direção é definida pela posição do mouse em vez do teclado. O personagem sempre "olhará" para o ponteiro do mouse. No entanto, as entradas para a frente/para trás permanecem as mesmas.
extends CharacterBody2D
@export var speed = 400
func get_input():
look_at(get_global_mouse_position())
velocity = transform.x * Input.get_axis("down", "up") * speed
func _physics_process(delta):
get_input()
move_and_slide()
using Godot;
public partial class Movement : CharacterBody2D
{
[Export]
public int Speed { get; set; } = 400;
public void GetInput()
{
LookAt(GetGlobalMousePosition());
Velocity = Transform.X * Input.GetAxis("down", "up") * Speed;
}
public override void _PhysicsProcess(double delta)
{
GetInput();
MoveAndSlide();
}
}
Here we're using the Node2D look_at()
method to
point the player towards the mouse's position. Without this function, you
could get the same effect by setting the angle like this:
rotation = get_global_mouse_position().angle_to_point(position)
var rotation = GetGlobalMousePosition().AngleToPoint(Position);
Clique e mova¶
Este último exemplo usa apenas o mouse para controlar o personagem. Clicar na tela fará com que o jogador se mova para o local de destino.
extends CharacterBody2D
@export var speed = 400
var target = position
func _input(event):
if event.is_action_pressed("click"):
target = get_global_mouse_position()
func _physics_process(delta):
velocity = position.direction_to(target) * speed
# look_at(target)
if position.distance_to(target) > 10:
move_and_slide()
using Godot;
public partial class Movement : CharacterBody2D
{
[Export]
public int Speed { get; set; } = 400;
private Vector2 _target;
public override void _Input(InputEvent @event)
{
if (@event.IsActionPressed("click"))
{
_target = GetGlobalMousePosition();
}
}
public override void _PhysicsProcess(double delta)
{
Velocity = Position.DirectionTo(_target) * Speed;
// LookAt(target);
if (Position.DistanceTo(_target) > 10)
{
MoveAndSlide();
}
}
}
Observe a verificação distance_to()
que fazemos antes do movimento. Sem esse teste, o corpo "tremeria" ao atingir a posição-alvo, pois se moveria um pouco além da posição e tentaria voltar, apenas para se afastar demais e repetir.
Descomentar a linha look_at()
também irá virar o corpo para apontar em sua direção de movimento, se você preferir.
Dica
Essa técnica também pode ser usada como base para um personagem "seguidor". A posição target
pode ser a de qualquer objeto para o qual você deseja mover.
Resumo¶
Você pode achar esses exemplos de código úteis como pontos de partida para seus próprios projetos. Sinta-se livre para usá-los e experimentá-los para ver o que você pode fazer.
You can download this sample project here: 2d_movement_starter.zip