The beauty of using Flame to build Flutter games is in the ability to combine pixel-level freedom to build any movement you want with the wonderful Flutter widgets and development process.
In the example above, the GAME OVER and MAGIC text are standard Flutter Text widgets with the Flutter TextStyle
syntax for color, size, and font family.
The gems are SpriteComponents
from the Flame game framework.
When the player Leena collides with a gem, the MAGIC score is increased.
In the onCollision
method of the Gem SpriteComponent
, the integer value for MAGIC moves from 0 to 1. This is handled by magicLevel += 1
inside of the Flame game. As we’re passing the entire game to the Flutter widget tree, the Flutter Text widget can access the variable with game.magicLevel
.
Let’s take a closer look at how the game object with the variables such as magicLevel
is passed to the Flutter widget tree.
Communication Between the Game and Flutter Widgets
You can communicate between the Flutter widgets such as a button or a piece of text for a score and the game variables with many techniques. The easiest technique is to hold the state of a variable such as score or timer inside of the game and then pass the entire game state over to the Flutter widget tree.
For example, I collect magic points every time I get a gem. I want to display the magic level on my game screen.
class LeenaGame extends FlameGame {
int magicLevel = 0;
To get the instantiated object of LeenaGame()
over to the Flutter widget, I’m using a the overlayBuilderMap
property that is part of the Flame GameWidget class. This is the overlay syntax.
void main() {
runApp(
MaterialApp(
home: Scaffold(
body: GameWidget(
game: LeenaGame(),
overlayBuilderMap: {
'DashboardOverlay': (BuildContext context, LeenaGame game) {
return Dashboard(
game: game,
);
}
},
),
),
),
);
}
overlayBuilderMap
Normally, the Flame GameWidget
is the main widget passed to Flutter runApp
. The GameWidget
from Flame also accepts a parameter, overlayBuilderMap
. To the right of the colon, you specify a Dart map in the form key:value. The key is a human-readable key that makes it easy for the programmer to remember. In the example above, the key is DashboardOverlay
. This is a name I made up for my dashboard. It is not a keyword in the Flame overlay system.
To the right of the key is the value, which is a function that runs when the GameWidget()
runs. In the example above, the function returns the Flutter widget Dashboard
that I created.
Flutter Game Dashboard
The Dashboard is a Flutter StatelessWidget
. You can put any type of Flutter widget in this dashboard.
Notify Flutter Dashboard of Changes
In my example, the dashboard is a StatelessWidget
. It will not update unless you tell it to update. The Dashboard is updated when the game notifies the listener for the Flutter widgets. In the example below, the magic gem has a method from Flame called, onCollision
. At the time of collision, the magicLevel
is increased by 1. To change the new score on the Flutter Text widget, you notify the overlay of the change and then the Flutter widget rebuilds.
Additional Step-by-Step Tutorials
These videos will give you a more detailed, step-by-step overview, of the Flutter overlay system for Flame games.
26 Video Flame Tutorial Series to Build Flutter Platformer Game
A free 26 video tutorial series on using Flame 1.1.1 is available below. In addition to Flutter overlays on Flame games, the tutorial series covers animation, character velocity, and collision. The collision syntax was recently updated in Flame 1.1.