Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

docs: Improve documentation at Klondike Tutorial Step 5 #3078

Draft
wants to merge 9 commits into
base: main
Choose a base branch
from
135 changes: 135 additions & 0 deletions doc/tutorials/klondike/step5.md
Original file line number Diff line number Diff line change
Expand Up @@ -413,6 +413,141 @@ FlameGame. The new world contains (almost) everything we need to play the game a
re-created during each of the above actions.


### KlondikeWorld class

In Flame, a ```World``` is a type of ```Component``` that can contain other ```Components```,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These should only have a single back-tick, tripple back-ticks are for multi-line code

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure! Let me change this

such as Piles.

You can learn more about World in game programming here:

<https://media.worldbookonline.com/image/upload/v1467051964/asset/webquests/Electronic_Games_Advanced.pdf>
<https://docs.flame-engine.org/latest/flame/game.html>
We won't dive too deep into World here, just understand their purpose for now.


#### Creating KlondikeWorld

Let's create a ```World``` for our Klondike game, called ```KlondikeWorld```.
At the start of the game, we'll create a ```World```. Each new game will be represented by a new World.
Worlds are also created when the player restarts the game.
Each ```World``` is responsible for loading its own Components and dealing the cards accordingly.
Therefore, the ```onLoad()``` method will be moved from the ```KlondikeGame``` class to ```KlondikeWorld```.
First, let's modify the ```KlondikeGame``` class:

```dart
// KlondikeWorld is our new World
class KlondikeGame extends FlameGame<KlondikeWorld> {
// we keep all constant values here
KlondikeGame() : super(world: KlondikeWorld()); // init a World

// delete the onLoad() method

// keep below method
Sprite klondikeSprite(double x, double y, double width, double height) {
// ...
}
}

```

The code above shows that when ```FlameGame``` is initialized, a ```KlondikeWorld``` is
also initialized.
Previously, without the ```KlondikeWorld``` class, FlameGame would create a
default ```World``` upon
initialization. It's important to note that a Game can have multiple Worlds,
but only one World is displayed at a time.

We removed the ```onLoad()``` method from the ```KlondikeGame``` class and now
need to re-implement it in ```KlondikeWorld```.

First, create a file called ```klondike_world.dart``` in the lib folder and add
the following ```KlondikeWorld``` class:

```dart
class KlondikeWorld extends World with HasGameReference<KlondikeGame> {
final cardGap = KlondikeGame.cardGap;
final topGap = KlondikeGame.topGap;
final cardSpaceWidth = KlondikeGame.cardSpaceWidth;
final cardSpaceHeight = KlondikeGame.cardSpaceHeight;

final stock = StockPile(position: Vector2(0.0, 0.0));
final waste = WastePile(position: Vector2(0.0, 0.0));
final List<FoundationPile> foundations = [];
final List<TableauPile> tableauPiles = [];
final List<Card> cards = [];
@override
Future<void> onLoad() async {
// ...

}
}
```

In the above code we have changed a bit compared to KlondikeGame from step 4.
By declaring stock, waste, foundations, tableauPiles, cards,
we confirm that it is owned by the KlondikeWord class.
And so onLoad has also changed a bit

```dart
@override
Future<void> onLoad() async {
await Flame.images.load('klondike-sprites.png');
// set up the stock and waste piles
stock.position = Vector2(cardGap, topGap);
waste.position = Vector2(cardSpaceWidth + cardGap, topGap);

// set up the foundation piles
for (var i = 0; i < 4; i++) {
foundations.add(
FoundationPile(
i,
position: Vector2((i + 3) * cardSpaceWidth + cardGap, topGap),
),
);
}
// set up the tableau piles
for (var i = 0; i < 7; i++) {
tableauPiles.add(
TableauPile(
position: Vector2(
i * cardSpaceWidth + cardGap,
cardSpaceHeight + topGap,
),
),
);
}
// set up the cards
for (var rank = 1; rank <= 13; rank++) {
for (var suit = 0; suit < 4; suit++) {
final card = Card(rank, suit);
card.position = stock.position;
cards.add(card);
}
}
add(stock);
add(waste);
addAll(foundations);
addAll(tableauPiles);
addAll(cards);

}
```

This code only has the same settings from step 4 and
changes a few points as follows:

- The Piles have been declared before, so we just set
the position and add elements to the list
- there are 4 foundations, 7 tableaus, 52 cards
- replace world.add with add. because we are now in the World class


#### what properties?


#### what actions we should implement at this class


### A stripped-down KlondikeGame class

Here is the new code for the KlondikeGame class (what is left of it).
Expand Down
Loading