Move系统
本章将讨论move_system
的实现,它用于在棋盘上重新定位棋子。
move_system
是什么?
下棋时,玩家必须移动棋盘上的棋子。由于我们用Square实体来表示棋子的位置,因此 move_system
会以 (x,y) 的形式获取当前位置。它还会以 (x,y) 的形式获取下一个位置,并将当前位置方格中的棋子视为要移动到下一个位置的目标。
需求
复制下面的单元测试,并将其粘贴到systems/move.cairo
文件的底部。
- 在系统中编写一个
execute
函数,输入如下内容:
fn execute(
ctx: Context,
curr_position: (u32, u32),
next_position: (u32, u32),
caller: ContractAddress,
game_id: felt252
)
-
更新带有
next_position
的方格,使其包含新棋子,并确保带有curr_position
的方格不再包含棋子。 -
运行
sozo test
并确保所有测试通过。
测试流程
- 跟随上一章中
test_initiate
的逻辑。 - 通过
move_system
把White Knight从(1,0) 移动到 (2,2) - 获取更新之后的位置并且验证棋子成功移动到了新位置。
单元测试
#[cfg(test)]
mod tests {
use starknet::ContractAddress;
use dojo::test_utils::spawn_test_world;
use dojo_chess::components::{Game, game, GameTurn, game_turn, Square, square, PieceType};
use dojo_chess::systems::initiate_system;
use dojo_chess::systems::move_system;
use array::ArrayTrait;
use core::traits::Into;
use dojo::world::IWorldDispatcherTrait;
use core::array::SpanTrait;
#[test]
#[available_gas(3000000000000000)]
fn test_move() {
let white = starknet::contract_address_const::<0x01>();
let black = starknet::contract_address_const::<0x02>();
// components
let mut components = array::ArrayTrait::new();
components.append(game::TEST_CLASS_HASH);
components.append(game_turn::TEST_CLASS_HASH);
components.append(square::TEST_CLASS_HASH);
//systems
let mut systems = array::ArrayTrait::new();
systems.append(initiate_system::TEST_CLASS_HASH);
systems.append(move_system::TEST_CLASS_HASH);
let world = spawn_test_world(components, systems);
// initiate
let mut calldata = array::ArrayTrait::<core::felt252>::new();
calldata.append(white.into());
calldata.append(black.into());
world.execute('initiate_system'.into(), calldata);
let game_id = pedersen(white.into(), black.into());
//White Knight is in (1,0)
let b1 = get!(world, (game_id, 1, 0), (Square));
match b1.piece {
Option::Some(piece) => {
assert(piece == PieceType::WhiteKnight, 'should be White Knight in (1,0)');
},
Option::None(_) => assert(false, 'should have piece in (1,0)'),
};
// Move White Knight (1,0) -> (2,2)
let mut move_calldata = array::ArrayTrait::<core::felt252>::new();
move_calldata.append(1);
move_calldata.append(0);
move_calldata.append(2);
move_calldata.append(2);
move_calldata.append(white.into());
move_calldata.append(game_id);
world.execute('move_system'.into(), move_calldata);
//White Knight is in (2,2)
let c3 = get!(world, (game_id, 2, 2), (Square));
match c3.piece {
Option::Some(piece) => {
assert(piece == PieceType::WhiteKnight, 'should be White Knight in (2,2)');
},
Option::None(_) => assert(false, 'should have piece in (2,2)'),
};
}
}
需要帮助?
如果您遇到困难,请随时到 Dojo 社区 提问!