Fuerzas, impulsos y velocidad lineal
En Forge2D la fuerza, el impulso y la velocidad lineal son conceptos fundamentales para simular el movimiento y la interacción de los cuerpos, y la mejor forma de aprender la diferencia entre de cada uno de ellos es con un ejemplo práctico.
En este ejemplo, agregaremos 3 pelotas al mundo. A la primera le aplicaremos una fuerza, a la segunda un impulso y a la tercera una velocidad lineal. De esta manera, podremos observar el comportamiento de cada uno.
Comenzaremos creando la clase Ball
, que recibirá la posición en el eje X:
class Ball extends BodyComponent {
final double positionX;
Ball(this.positionX);
Body createBody() {
final bodyDef = BodyDef(
position: Vector2(positionX, worldSize.y - 1),
type: BodyType.dynamic,
);
final shape = CircleShape()..radius = .35;
final fixtureDef = FixtureDef(shape)
..density = 5
..friction = .5
..restitution = .5;
return world.createBody(bodyDef)..createFixture(fixtureDef);
}
}
A continuación, agregaremos las pelotas al juego. Sin embargo, como queremos hacer un seguimiento de las pelotas para poder aplicar una fuerza cada vez que se hace clic en la pantalla, almacenaremos los objetos de las bolas en una lista. También crearemos un vector llamado speed que contendrá el valor que aplicaremos en el eje Y.
class GameLesson04 extends MyGame with TapDetector {
// Almacenamos las pelotas en una lista
final balls = [Ball(2), Ball(6), Ball(10)];
// Contiene el valor que aplicaremos en el eje Y
final speed = Vector2(0, -9);
Future<void> onLoad() async {
super.onLoad();
add(Floor());
addAll(balls);
}
void onTapDown(TapDownInfo info) {
super.onTapDown(info);
// Cada vez que se presiona la pantalla
// aplicamos las diferentes fuerzas a las pelotas
balls[0].body.applyForce(speed);
balls[1].body.applyLinearImpulse(speed);
balls[2].body.linearVelocity = speed;
}
}
La lista balls
contiene tres pelotas ubicadas horizontalmente en las posiciones X = 2
, X = 6
y X = 10
.
El vector speed
representa el valor que utilizaremos para aplicar una fuerza al cuerpo. En este caso, el cuerpo se
moverá únicamente verticalmente porque el valor en el eje Y es -9, mientras que el valor en el eje X es 0, lo
que significa que el cuerpo no se moverá horizontalmente.
Estamos utilizando TapDetector
y sobreescribiendo la función onTapDown()
, de manera que cada vez que se hace clic
en la pantalla, interactuamos con los cuerpos.
En Flame, las coordenadas (0, 0) se encuentran en la parte superior izquierda de la pantalla. Por lo tanto, un valor
negativo de Y en el vector speed
hace que los cuerpos se muevan hacia arriba.
Después de ejecutar el código, el resultado será el siguiente:
Aplicando fuerzas
Vamos a interactuar con las bolas, tocamos o hacemos clic en la pantalla. Se ejecutará el siguiente código:
balls[0].body.applyForce(speed);
balls[1].body.applyLinearImpulse(speed);
balls[2].body.linearVelocity = speed;
Y el resultado se verá así:
Podemos observar que el movimiento de cada una de las pelotas es diferente. Veamos la diferencia entre cada una de las fuerzas:
applyForce: A la pelota de la izquierda, le estamos aplicando una fuerza. Las fuerzas cambian la velocidad de un cuerpo gradualmente con el tiempo. Por ejemplo, si empujamos una roca de manera constante, se moverá lentamente y con el tiempo alcanzará la velocidad deseada.
applyLinearImpulse: A la pelota del medio, le aplicamos un impulso lineal. Los impulsos realizan cambios inmediatos en la velocidad del cuerpo. Por ejemplo, patear un balón de fútbol cambiará inmediatamente la velocidad del balón y lo hará moverse lejos, pero ¿qué sucede si pateas una roca?, probablemente no se moverá muy lejos.
linearVelocity: A la pelota de la derecha, le establecemos la velocidad, por lo que no importa el tamaño ni la masa del cuerpo, simplemente la pelota se va a mover a la velocidad deseada.
Por defecto, estas fuerzas se aplican en el centro de los cuerpos, por lo que se moverán hacia arriba y no rotarán.
Conclusión
En este artículo aprendimos la diferencia entre la fuerza, el impulso y la velocidad lineal en Forge2D. Más adelante podremos usar estos conceptos para hacer que los personajes de nuestros juegos se muevan dentro del mundo.