use super::Position;
use crate::board::parser::{PositionState, SfenError, generate_sfen_with_ply, parse_sfen};
use crate::types::{Color, EnteringKingRule, Piece};
impl Position {
pub fn from_sfen(sfen: &str) -> Result<Self, SfenError> {
let mut pos = Self::empty();
pos.set_sfen(sfen)?;
Ok(pos)
}
pub fn set_sfen(&mut self, sfen: &str) -> Result<(), SfenError> {
let state = parse_sfen(sfen)?;
self.apply_position_state(&state);
Ok(())
}
pub fn set_position_state(&mut self, state: &PositionState) {
self.apply_position_state(state);
}
pub fn set_hirate(&mut self) {
self.set_sfen(crate::board::STARTPOS_SFEN).expect("Invalid startpos SFEN");
}
fn apply_position_state(&mut self, state: &PositionState) {
self.board = state.board;
self.hands = state.hands;
self.set_side_to_move(state.side_to_move);
self.ply = state.ply;
self.entering_king_rule = EnteringKingRule::None;
self.entering_king_point = [0, 0];
self.rebuild_bitboards();
let keys = self.compute_keys();
let (board_key, hand_key) = (keys.board_key, keys.hand_key);
self.board_key = board_key;
self.hand_key = hand_key;
self.zobrist = board_key ^ hand_key;
self.reset_state_stack_to_current_position();
self.debug_assert_partial_keys_consistent();
}
#[must_use]
pub fn to_sfen(&self, game_ply: Option<i32>) -> String {
let ply = game_ply.unwrap_or_else(|| i32::from(self.ply));
let ply = if ply < 0 { None } else { Some(ply) };
generate_sfen_with_ply(self, ply)
}
#[must_use]
pub fn to_sfen_flipped(&self, game_ply: Option<i32>) -> String {
let mut flipped = Self::empty();
for (sq, piece) in self.board.iter() {
if piece.is_empty() {
continue;
}
let flipped_piece = Piece::from_parts(piece.color().flip(), piece.piece_type());
flipped.board.set(sq.flip(), flipped_piece);
}
flipped.hands[Color::BLACK.to_index()] = self.hands[Color::WHITE.to_index()];
flipped.hands[Color::WHITE.to_index()] = self.hands[Color::BLACK.to_index()];
flipped.set_side_to_move(self.turn().flip());
flipped.ply = self.ply;
let ply = game_ply.unwrap_or_else(|| i32::from(self.ply));
let ply = if ply < 0 { None } else { Some(ply) };
generate_sfen_with_ply(&flipped, ply)
}
}