Skip to content

此步骤将随机放置游戏图块。

src/main.cpp 中的 main 函数和头文件更改如下:

C++
#include <random> // Added
int main(){    auto main_window = MainWindow::create();    auto old_tiles = main_window->get_memory_tiles();    std::vector<TileData> new_tiles;    new_tiles.reserve(old_tiles->row_count() * 2);    for (int i = 0; i < old_tiles->row_count(); ++i) {        new_tiles.push_back(*old_tiles->row_data(i));        new_tiles.push_back(*old_tiles->row_data(i));    }    std::default_random_engine rng {};    std::shuffle(new_tiles.begin(), new_tiles.end(), rng);    auto tiles_model = std::make_shared<slint::VectorModel<TileData>>(new_tiles);    main_window->set_memory_tiles(tiles_model);
    main_window->run();}

这段代码取出图块列表,对其进行复制并打乱顺序,通过 C++ 代码访问 memory_tiles 属性。

对于每个顶级属性,Slint 会生成一个 getter 和一个 setter 函数。在本例中为 get_memory_tilesset_memory_tiles。 由于 memory_tiles 是一个 Slint 数组,它被表示为 std::shared_ptr<slint::Model>

你无法更改 Slint 生成的模型,但你可以从中提取图块,并将它们 放入一个继承自 Modelslint::VectorModel 中。 VectorModel 允许你进行修改,你可以使用它来替换静态生成的模型。

main.js 更改为如下内容:

js
import * as slint from "slint-ui";const ui = slint.loadFile(new URL("./ui/app-window.slint", import.meta.url));const mainWindow = new ui.MainWindow();
const initial_tiles = mainWindow.memory_tiles;const tiles = initial_tiles.concat(    initial_tiles.map((tile) => Object.assign({}, tile)),
);
for (let i = tiles.length - 1; i > 0; i--) {    const j = Math.floor(Math.random() * i);    [tiles[i], tiles[j]] = [tiles[j], tiles[i]];}
const model = new slint.ArrayModel(tiles);mainWindow.memory_tiles = model;
await mainWindow.run();

这段代码取出图块列表,对其进行复制并打乱顺序,通过 JavaScript 代码访问 memory_tiles 属性。

由于 memory_tiles 是一个数组,它被表示为 JavaScript Array。 你无法更改 Slint 生成的模型,但你可以从中提取图块,并将它们 放入一个实现了 Model 接口的 slint.ArrayModel.html 中。 ArrayModel 允许你进行修改,你可以使用它来替换静态生成的模型。

该代码使用 rand 依赖项来进行随机化。使用 cargo 命令将其添加到 Cargo.toml 文件中。

Terminal window

bash
cargo add [email protected]

将 main 函数更改为如下内容:

rust
fn main() {    use slint::Model;
    let main_window = MainWindow::new().unwrap();
    // Fetch the tiles from the model
    let mut tiles: Vec<TileData> = main_window.get_memory_tiles().iter().collect();    // Duplicate them to ensure that we have pairs
    tiles.extend(tiles.clone());
    // Randomly mix the tiles
    use rand::seq::SliceRandom;    let mut rng = rand::rng();    tiles.shuffle(&mut rng);
    // Assign the shuffled Vec to the model property
    let tiles_model = std::rc::Rc::new(slint::VecModel::from(tiles));    main_window.set_memory_tiles(tiles_model.clone().into());
    main_window.run().unwrap();}

这段代码取出图块列表,对其进行复制并打乱顺序,通过 Rust 代码访问 memory_tiles 属性。

对于每个顶级属性, Slint 会生成一个 getter 和一个 setter 函数。在本例中为 get_memory_tilesset_memory_tiles。 由于 memory_tiles 是一个表示为 Rc<dyn slint::Model> 的 Slint 数组。

你无法更改 Slint 生成的模型,但你可以从中提取图块,并将它们 放入一个实现了 Model trait 的 VecModel 中。 VecModel 允许你进行修改,你可以使用它来替换静态生成的模型。

main.py 更改为如下内容:

python
import slintimport sysimport osimport randomimport itertoolsimport copyimport datetime

class MainWindow(slint.loader.ui.app_window.MainWindow):    def __init__(self):        super().__init__()        initial_tiles = self.memory_tiles        tiles = slint.ListModel(            itertools.chain(                map(copy.copy, initial_tiles), map(copy.copy, initial_tiles)            )        )        random.shuffle(tiles)        self.memory_tiles = tiles

main_window = MainWindow()main_window.show()main_window.run()

这段代码取出图块列表,对其进行复制并打乱顺序,通过 Python 代码访问 memory_tiles 属性。

由于 memory_tiles 是一个数组,它被表示为 Slint ListModel。 你无法更改 Slint 生成的模型,但你可以从中提取图块,并将它们 放入一个继承自 Model 接口的 slint.ListModel 中。 ListModel 允许你进行修改,你可以使用它来替换静态生成的模型。

运行此代码会打开一个窗口,现在窗口中显示一个 4×4 的矩形网格,当玩家点击图块时, 这些图标会显示或隐藏。

现在还差最后一个方面——游戏的规则。

基于 MIT 协议发布