mirror of
https://github.com/slint-ui/slint.git
synced 2025-09-30 22:01:13 +00:00
Move the Rust tutorial into a sub-directory
To make room for the C++ version next to it :-)
This commit is contained in:
parent
a012809bd0
commit
7b95371c78
26 changed files with 10 additions and 10 deletions
74
docs/tutorial/rust/src/game_logic_in_rust.md
Normal file
74
docs/tutorial/rust/src/game_logic_in_rust.md
Normal file
|
@ -0,0 +1,74 @@
|
|||
# Game Logic In Rust
|
||||
|
||||
We'll implement the rules of the game in Rust as well. The general philosophy of SixtyFPS is that merely the user
|
||||
interface is implemented in the `.60` language and the business logic in your favorite programming
|
||||
language. The game rules shall enforce that at most two tiles have their curtain open. If the tiles match, then we
|
||||
consider them solved and they remain open. Otherwise we wait for a little while, so the player can memorize
|
||||
the location of the icons, and then close them again.
|
||||
|
||||
We'll modify the `.60` markup inside the `sixtyfps!` macro to signal to the Rust code when the user clicks on a tile.
|
||||
Two changes to `MainWindow` are needed: We need to add a way for the MainWindow to call to the Rust code that it should
|
||||
check if a pair of tiles has been solved. And we need to add a property that Rust code can toggle to disable further
|
||||
tile interaction, to prevent the player from opening more tiles than allowed. No cheating allowed! First, we paste
|
||||
the callback and property declarations into `MainWindow`:
|
||||
|
||||
|
||||
```60
|
||||
...
|
||||
MainWindow := Window {
|
||||
callback check_if_pair_solved(); // Added
|
||||
property <bool> disable_tiles; // Added
|
||||
|
||||
width: 326px;
|
||||
height: 326px;
|
||||
|
||||
property <[TileData]> memory_tiles: [
|
||||
{ image: img!"icons/at.png" },
|
||||
...
|
||||
```
|
||||
|
||||
The last change to the `.60` markup is to act when the `MemoryTile` signals that it was clicked on. We add the following handler:
|
||||
|
||||
```60
|
||||
...
|
||||
MainWindow := Window {
|
||||
...
|
||||
for tile[i] in memory_tiles : MemoryTile {
|
||||
x: mod(i, 4) * 74px;
|
||||
y: floor(i / 4) * 74px;
|
||||
width: 64px;
|
||||
height: 64px;
|
||||
icon: tile.image;
|
||||
open_curtain: tile.image_visible || tile.solved;
|
||||
// propagate the solved status from the model to the tile
|
||||
solved: tile.solved;
|
||||
|
||||
clicked => {
|
||||
// old: tile.image_visible = !tile.image_visible;
|
||||
// new:
|
||||
if (!root.disable_tiles) {
|
||||
tile.image_visible = !tile.image_visible;
|
||||
root.check_if_pair_solved();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
On the Rust side, we can now add an handler to the `check_if_pair_solved` callback, that will check if
|
||||
two tiles are opened. If they match, the `solved` property is set to true in the model. If they don't
|
||||
match, start a timer that will close them after one second. While the timer is running, we disable every tile so
|
||||
one cannot click anything during this time.
|
||||
|
||||
Insert this code before the `main_window.run()` call:
|
||||
|
||||
```rust,noplayground
|
||||
{{#include main_game_logic_in_rust.rs:game_logic}}
|
||||
```
|
||||
|
||||
Notice that we take a [Weak](https://sixtyfps.io/docs/rust/sixtyfps/struct.weak) pointer of our `main_window`. This is very
|
||||
important because capturing a copy of the `main_window` itself within the callback handler would result in a circular ownership.
|
||||
The `MainWindow` owns the callback handler, which itself owns a reference to the `MainWindow`, which must be weak
|
||||
instead of strong to avoid a memory leak.
|
||||
|
||||
And that's it, now we can run the game!
|
Loading…
Add table
Add a link
Reference in a new issue