Interpolación¶
La interpolación es una operación muy básica en la programación de gráficos. Es bueno familiarizarse con ella para expandir tus horizontes como desarrollador de gráficos.
La idea básica es que quieres pasar de A a B. Un valor t
, representa los estados intermedios.
Por ejemplo, si t
es 0, entonces el estado es A. Si t
es 1, entonces el estado es B. Cualquier cosa intermedia es una interpolación.
Entre dos números reales , una simple interpolación suele describirse como:
interpolation = A * (1 - t) + B * t
Y a menudo simplificado:
interpolation = A + (B - A) * t
El nombre de este tipo de interpolación, que transforma un valor en otro a velocidad constante es "lineal ". Así que, cuando escuchas acerca de la Interpolación Lineal, sabes que se refieren a esta simple fórmula.
Hay otros tipos de interpolaciones, que no se tratarán aquí. Una lectura recomendada después es la página Bezier.
Interpolación de vectorial¶
Los tipos de vectores (Vector2 y Vector3) también pueden ser interpolados, vienen con funciones útiles para hacerlo Vector2.linear_interpolate() y Vector3.linear_interpolate().
Para la interpolación cúbica, también hay Vector2.cubic_interpolate() y Vector3.cubic_interpolate(), que hacen una interpolación de estilo Bezier.
Aquí hay un simple pseudo-código para ir del punto A al B usando la interpolación:
var t = 0.0
func _physics_process(delta):
t += delta * 0.4
$Sprite.position = $A.position.linear_interpolate($B.position, t)
private float _t = 0.0f;
public override void _PhysicsProcess(float delta)
{
_t += delta * 0.4f;
Position2D a = GetNode<Position2D>("A");
Position2D b = GetNode<Position2D>("B");
Sprite sprite = GetNode<Sprite>("Sprite");
sprite.Position = a.Position.LinearInterpolate(b.Position, _t);
}
Esto producirá el siguiente movimiento:

Interpolación de matriz de transformación¶
También es posible interpolar transformaciones enteras (asegurarse de que tienen una escala uniforme o, al menos, la misma escala no uniforme). Para ello, se puede utilizar la función Transform.interpolate_with().
Aquí hay un ejemplo de la transformación de un mono de la Posición1 a la Posición2:

Utilizando el siguiente pseudocódigo:
var t = 0.0
func _physics_process(delta):
t += delta
$Monkey.transform = $Position1.transform.interpolate_with($Position2.transform, t)
private float _t = 0.0f;
public override void _PhysicsProcess(float delta)
{
_t += delta;
Position3D p1 = GetNode<Position3D>("Position1");
Position3D p2 = GetNode<Position3D>("Position2");
CSGMesh monkey = GetNode<CSGMesh>("Monkey");
monkey.Transform = p1.Transform.InterpolateWith(p2.Transform, _t);
}
Y de nuevo, producirá el siguiente movimiento:

Suavizando el movimiento¶
La interpolación puede utilizarse para suavizar el movimiento, la rotación, etc. Aquí hay un ejemplo de un círculo que sigue al ratón usando un movimiento suavizado:
const FOLLOW_SPEED = 4.0
func _physics_process(delta):
var mouse_pos = get_local_mouse_position()
$Sprite.position = $Sprite.position.linear_interpolate(mouse_pos, delta * FOLLOW_SPEED)
private const float FollowSpeed = 4.0f;
public override void _PhysicsProcess(float delta)
{
Vector2 mousePos = GetLocalMousePosition();
Sprite sprite = GetNode<Sprite>("Sprite");
sprite.Position = sprite.Position.LinearInterpolate(mousePos, delta * FollowSpeed);
}
Así es cómo se ve:

Esto es útil para suavizar el movimiento de la cámara, para que los aliados te sigan (asegurándose de que se mantengan dentro de un cierto rango), y para muchos otros patrones de juego comunes.