Flame: The world, bodies, shapes, and fixtures
The world
Every game using Forge2D needs a world. The world object is what holds all your physics objects/bodies and simulates the reactions between them.
Maybe you did not notice it, but in the previous article, we already created a world.
1- In Flame, to create a world, we must extend the class Forge2DGame
, and internally it will create the world.
class MyGame extends Forge2DGame {
}
2- We must define the gravity of our world:
MyGame() : super(gravity: Vector2(0, 15));
Gravity affects every dynamic body in the world. x=0
means there is no horizontal gravity and y=15
means objects will be pulled downwards like in real life. These values can be anything you like, but remember to stick to a constant scale. In Forge2D 1 unit = 1 meter
If you want a world without gravity, then the code will look like this:
MyGame() : super(gravity: Vector2(0, 0));
Bodies
In Forge2D, our objects are called bodies and they are the fundamental objects in the world. Anything you can move or interact with is a body.
There are different body types: static, dynamic, and kinematic.
Bodies can have different shapes: circular, rectangular, or any kind of polygon.
Also, bodies can have different attributes: density, friction, restitution, velocity, position, etc.
In Flame, to create a Body, we need to create a class and extend
from BodyComponent.
class Ball extends BodyComponent {
@override
Body createBody() {
}
}
Inside the function createBody()
, we create a BodyDef
that will hold the data needed to create the body:
final bodyDef = BodyDef(
position: Vector2(worldSize.x / 2, 0),
type: BodyType.dynamic,
);
We can see that this will be a dynamic body, positioned vertically at the screen's top and horizontally centered.
Shapes
In Forge2D, bodies must have a shape; it can be circular, rectangular, or any kind of polygon.
Let's create a circular shape for our body:
final shape = CircleShape()..radius = .35;
We created a CircleShape
and set a radius of .35
Fixtures
A fixture has a shape, density, friction, and restitution attached to it.
- Density is the mass per square meter
- Friction is the amount of opposing force when the object rubs/slides along something
- Restitution is how bouncy the body is
Let's create the fixture of our body:
final fixtureDef = FixtureDef(shape);
We created the fixture and attached the circular shape to it. This time we did not add any other attribute to it.
Adding the body to the World
Now we must add the body to the world, so we will use the bodyDef
and fixtureDef
that we created previously:
world.createBody(bodyDef)..createFixture(fixtureDef);
Putting all the code together, the Ball
class will look like this:
class Ball extends BodyComponent {
@override
Body createBody() {
final bodyDef = BodyDef(
position: Vector2(worldSize.x / 2, 0),
type: BodyType.dynamic,
);
final shape = CircleShape()..radius = .35;
final fixtureDef = FixtureDef(shape);
return world.createBody(bodyDef)..createFixture(fixtureDef);
}
}
Adding the Ball to the Game
Finally, we have to add the Ball
to the game. So let's create a new class, GameLesson01.
class GameLesson01 extends MyGame {
@override
Future<void> onLoad() async {
super.onLoad();
add(Ball());
}
}
Now we can run this code, and we will see a ball falling from the top to the bottom of the screen:
You can do some experimentation. Try changing the gravity values, the radius of the ball, etc.
Conclusion
This article taught us about the Forge2D world and how to add bodies to it. We also learned that a body could have different shapes and attributes.
Remember the source code of all tutorials is available on Github, and you can try all the examples in your browser: