added undo/redo functionality
This commit is contained in:
@@ -4,13 +4,12 @@ use gdk4::cairo::{Context as CairoContext, Matrix, Rectangle};
|
||||
use glib::ExitCode;
|
||||
use gtk4::glib::{MainContext, Propagation};
|
||||
use gtk4::{self as gtk, gdk::ffi::GDK_BUTTON_PRIMARY};
|
||||
use gtk4::{Application, DrawingArea, prelude::*};
|
||||
use gtk4::{Application, Button, DrawingArea, HeaderBar, prelude::*};
|
||||
use rdraught::{
|
||||
DraughtsBoard, DraughtsGame, Move, Piece, Player, Position, RDraughtApplication,
|
||||
RectangularBoard,
|
||||
};
|
||||
use rsvg::SvgHandle;
|
||||
use std::thread;
|
||||
const SQUARE_SIZE: f64 = 1.0;
|
||||
|
||||
use super::final_dialog;
|
||||
@@ -244,14 +243,64 @@ fn create_game_window(
|
||||
.default_width(800)
|
||||
.default_height(800)
|
||||
.build();
|
||||
let header_bar = HeaderBar::new();
|
||||
window.set_titlebar(Some(&header_bar));
|
||||
|
||||
let undo_button = Button::new();
|
||||
undo_button.set_icon_name("edit-undo-symbolic");
|
||||
undo_button.set_sensitive(false);
|
||||
|
||||
let redo_button = Button::new();
|
||||
redo_button.set_icon_name("edit-redo-symbolic");
|
||||
redo_button.set_sensitive(false);
|
||||
|
||||
let selected_piece: SharedMutable<Option<Position>> = new_shared_mut(None);
|
||||
let available_moves = new_shared_mut_ref(Vec::<Move>::new());
|
||||
// Create a DrawingArea widget where we will draw the chessboard.
|
||||
let drawing_area = DrawingArea::new();
|
||||
// Add the drawing area to the window.
|
||||
window.set_child(Some(&drawing_area));
|
||||
|
||||
let selected_piece: SharedMutable<Option<Position>> = new_shared_mut(None);
|
||||
let available_moves = new_shared_mut_ref(Vec::<Move>::new());
|
||||
header_bar.pack_start(&undo_button);
|
||||
{
|
||||
let da = drawing_area.clone();
|
||||
let rd = rd.clone();
|
||||
let undo_btn_clone = undo_button.clone();
|
||||
let redo_btn_clone = redo_button.clone();
|
||||
let selected_piece = selected_piece.clone();
|
||||
let available_moves = available_moves.clone();
|
||||
undo_button.connect_clicked(move |_| {
|
||||
let mut rd = rd.borrow_mut();
|
||||
if rd.can_undo() {
|
||||
rd.undo().ok();
|
||||
redo_btn_clone.set_sensitive(rd.can_redo());
|
||||
undo_btn_clone.set_sensitive(rd.can_undo());
|
||||
selected_piece.set(None);
|
||||
available_moves.borrow_mut().clear();
|
||||
da.queue_draw();
|
||||
}
|
||||
});
|
||||
}
|
||||
header_bar.pack_start(&redo_button);
|
||||
{
|
||||
let da = drawing_area.clone();
|
||||
let rd = rd.clone();
|
||||
let undo_btn_clone = undo_button.clone();
|
||||
let redo_btn_clone = redo_button.clone();
|
||||
let selected_piece = selected_piece.clone();
|
||||
let available_moves = available_moves.clone();
|
||||
redo_button.connect_clicked(move |_| {
|
||||
let mut rd = rd.borrow_mut();
|
||||
if rd.can_redo() {
|
||||
rd.redo().ok();
|
||||
redo_btn_clone.set_sensitive(rd.can_redo());
|
||||
undo_btn_clone.set_sensitive(rd.can_undo());
|
||||
selected_piece.set(None);
|
||||
available_moves.borrow_mut().clear();
|
||||
da.queue_draw();
|
||||
}
|
||||
});
|
||||
}
|
||||
// Get the allocation information for the widget.
|
||||
let board_width = SQUARE_SIZE * DraughtsBoard::rows() as f64;
|
||||
let board_height = SQUARE_SIZE * DraughtsBoard::columns() as f64;
|
||||
@@ -429,6 +478,8 @@ fn create_game_window(
|
||||
let drawing_area = drawing_area.clone();
|
||||
let available_moves = available_moves.clone();
|
||||
let window = window.clone();
|
||||
let undo_btn_clone = undo_button.clone();
|
||||
let redo_btn_clone = redo_button.clone();
|
||||
gesture.connect_pressed(move |gesture, _, x, y| {
|
||||
gesture.set_state(gtk::EventSequenceState::Claimed);
|
||||
if let Some(winner) = rd.borrow().game().winner() {
|
||||
@@ -455,7 +506,7 @@ fn create_game_window(
|
||||
(8.0 - p.x() / SQUARE_SIZE) as u8,
|
||||
),
|
||||
};
|
||||
println!("Selected position: {:?}", position);
|
||||
// println!("Selected position: {:?}", position);
|
||||
let piece = {
|
||||
let rd = rd.borrow();
|
||||
let draughts_game = rd.game();
|
||||
@@ -471,7 +522,7 @@ fn create_game_window(
|
||||
for mv in am.into_iter() {
|
||||
if mv.get_end_position() == pos {
|
||||
let mut rd_app = rd.borrow_mut();
|
||||
println!("Applied move: {:?}", mv);
|
||||
// println!("Applied move: {:?}", mv);
|
||||
rd_app.apply_move(mv).unwrap();
|
||||
// let game_copy = rd_app.game().clone();
|
||||
// thread::spawn(move || {
|
||||
@@ -491,6 +542,9 @@ fn create_game_window(
|
||||
}
|
||||
if move_applied {
|
||||
selected_piece.set(None);
|
||||
let rd = rd.borrow();
|
||||
undo_btn_clone.set_sensitive(rd.can_undo());
|
||||
redo_btn_clone.set_sensitive(rd.can_redo());
|
||||
}
|
||||
}
|
||||
if !move_applied {
|
||||
|
Reference in New Issue
Block a user