Switching players in multiplayer using Penaltea
Multiplayer games become more exciting when both players get equal chances to play.
In Penaltea every player takes turns shooting the ball while the other player waits for the next round.
A proper player switching system is important because it keeps the match fair and organized.
When beginners create multiplayer games they often focus only on movement scoring and animations.
However turn management is one of the most important systems inside a competitive game.
Without proper player switching the gameplay can feel broken confusing and frustrating.
Penaltea uses a simple multiplayer concept where Player One shoots first and then Player Two gets a chance.
After each shot the game changes the active player automatically.
This system creates balance and makes every round feel competitive.
In this tutorial you will learn how to create a clean multiplayer player switching system using Dart.
The logic is simple enough for beginners but powerful enough for real projects.
You will understand how to track turns manage scores update the interface and continue gameplay smoothly.
The best part about this method is that it works for many different multiplayer games.
You can use similar logic in football games board games strategy games card games and even quiz games.
Before writing code you should first understand what happens during a multiplayer turn.
-
One player becomes the active player
-
The active player performs an action
-
The game saves the result of the action
-
The game changes the active player
-
The next player gets control
This loop continues until the match ends.
In Penaltea the process repeats after every kick.
Creating player variables
The first step is creating variables for both players.
These variables help the game understand who is currently active.
int currentPlayer = 1;
int playerOneScore = 0;
int playerTwoScore = 0;
int totalTurns = 0;
Here the currentPlayer variable stores the active player number.
If the value is one then Player One is active.
If the value is two then Player Two is active.
The score variables track goals for each player.
The totalTurns variable helps count the number of shots taken during the match.
Displaying the current player
Multiplayer games should always show whose turn is active.
This improves clarity and helps players stay focused during gameplay.
String getCurrentPlayerText() {
if (currentPlayer == 1) {
return "Player One Turn";
}
return "Player Two Turn";
}
This function checks the active player and returns text for the screen.
You can display this text above the football field or near the score board.
Clear turn indicators improve user experience and reduce confusion.
Creating the shooting system
Every time a player shoots the game should process the result first.
After processing the result the game switches to the next player.
void shootBall(String direction) {
bool goalScored = checkGoal(direction);
if (goalScored) {
if (currentPlayer == 1) {
playerOneScore++;
} else {
playerTwoScore++;
}
}
totalTurns++;
switchPlayer();
}
The function above performs several important tasks.
-
The game checks if the shot becomes a goal
-
The correct player score increases
-
The turn counter updates
-
The game switches players
This structure keeps gameplay smooth and easy to manage.
Checking goals using goalkeeper logic
Penaltea becomes exciting because the goalkeeper moves randomly.
This creates unpredictability during every shot.
import 'dart:math';
Random random = Random();
bool checkGoal(String playerDirection) {
List<String> directions = [
"left",
"center",
"right"
];
String goalkeeperDirection =
directions[random.nextInt(directions.length)];
if (playerDirection == goalkeeperDirection) {
return false;
}
return true;
}
The game randomly selects a goalkeeper direction.
If the goalkeeper chooses the same direction as the player then the shot is saved.
Otherwise the player scores a goal.
This simple system creates tension and replay value.
Switching the active player
Now comes the most important part of the tutorial.
We need a function that changes the active player after every shot.
void switchPlayer() {
if (currentPlayer == 1) {
currentPlayer = 2;
} else {
currentPlayer = 1;
}
}
This function checks the current active player.
If Player One is active the game changes to Player Two.
Otherwise the game changes back to Player One.
The logic is extremely simple but very powerful.
Most turn based multiplayer games use a similar system.
Tracking match progress
Penaltea gives each player five turns before checking the winner.
This means the game needs to know when the match should end.
bool isMatchFinished() {
if (totalTurns >= 10) {
return true;
}
return false;
}
Since both players get five turns the total becomes ten shots.
Once ten turns are completed the game checks the final score.
Finding the winner
After all turns are completed the game should announce the winner.
String getWinner() {
if (playerOneScore > playerTwoScore) {
return "Player One Wins";
}
if (playerTwoScore > playerOneScore) {
return "Player Two Wins";
}
return "Sudden Death";
}
This function compares both scores and returns the result.
If both players have the same score then the game enters sudden death mode.
Creating sudden death gameplay
Sudden death is one of the most exciting parts of Penaltea.
One player scoring while the other misses immediately ends the match.
bool suddenDeath = false;
void checkSuddenDeath() {
if (playerOneScore == playerTwoScore &&
totalTurns >= 10) {
suddenDeath = true;
}
}
The suddenDeath variable activates the special gameplay mode.
During sudden death both players continue taking turns until a winner appears.
Managing sudden death rounds
The game should continue switching players normally during sudden death.
However the game now checks for instant victory conditions.
void processSuddenDeathRound(
bool playerOneGoal,
bool playerTwoGoal
) {
if (playerOneGoal && !playerTwoGoal) {
print("Player One Wins");
}
else if (!playerOneGoal && playerTwoGoal) {
print("Player Two Wins");
}
else {
print("Continue Sudden Death");
}
}
This system creates dramatic gameplay moments because every shot matters.
Updating the game interface
Multiplayer games should update the interface after every turn.
Players should instantly see score changes and active turn information.
void updateGameUI() {
print(getCurrentPlayerText());
print("Player One Score");
print(playerOneScore);
print("Player Two Score");
print(playerTwoScore);
}
In real Flutter games you would normally use setState or another state management solution.
However the main idea stays the same.
The interface refreshes after every action.
Preventing multiple turns
A common beginner mistake happens when players tap too quickly.
This can accidentally trigger multiple shots before the turn changes.
To avoid this problem you should temporarily disable controls while animations are running.
bool canShoot = true;
void shootBall(String direction) {
if (!canShoot) {
return;
}
canShoot = false;
bool goalScored = checkGoal(direction);
if (goalScored) {
if (currentPlayer == 1) {
playerOneScore++;
} else {
playerTwoScore++;
}
}
switchPlayer();
canShoot = true;
}
This small improvement makes the game feel much more professional.
Adding animations between turns
Multiplayer games feel smoother when transitions happen between turns.
Instead of instantly switching players you can show animations score effects or camera movement.
Future<void> nextTurnAnimation() async {
print("Preparing Next Turn");
await Future.delayed(
Duration(seconds: 2)
);
switchPlayer();
}
Delays help create rhythm and anticipation.
Small details like this improve gameplay quality significantly.
Resetting the game
After a match ends players usually want to play again.
Resetting all game data correctly is very important.
void resetGame() {
currentPlayer = 1;
playerOneScore = 0;
playerTwoScore = 0;
totalTurns = 0;
suddenDeath = false;
}
This function prepares the game for a completely new match.
Why player switching matters in multiplayer games
Good player switching systems improve fairness gameplay balance and overall enjoyment.
Players should always understand when their turn begins and ends.
In Penaltea the turn system creates pressure because every kick becomes important.
The constant back and forth gameplay also keeps both players engaged.
Many famous multiplayer games use similar turn management systems.
Even advanced competitive games rely on simple logic behind the scenes.
Expanding the system further
Once you understand basic player switching you can expand the system in many ways.
-
Add more than two players
-
Create tournament brackets
-
Add online multiplayer support
-
Create timed turns
-
Add player statistics
-
Add replay systems
The core logic remains almost identical.
You simply build more features around the main turn system.
Conclusion
Switching players correctly is one of the foundations of multiplayer game development.
Even simple games need strong turn management to feel polished and enjoyable.
Penaltea uses a clean and beginner friendly system where players alternate after every shot.
The game tracks turns updates scores and handles sudden death automatically.
By learning this system you now understand an important multiplayer mechanic used in many games.
You can improve the system further by adding animations sound effects online networking and advanced match logic.
The best way to master multiplayer systems is through practice.
Build small projects experiment with new ideas and continue improving your gameplay flow.
Simple systems built correctly often create the most enjoyable gaming experiences.