1use std::fmt::{self, Display, Formatter};
2
3use crate::{
4 core::{Color, Position},
5 errors::PieceReprError,
6 utils::movements::{
7 diagonal_movement, l_movement, linear_movement, max_movement, movement_direction,
8 },
9};
10
11#[derive(Debug, PartialEq, Eq, Clone, Copy)]
14pub enum PieceType {
15 Pawn,
17 Knight,
19 Bishop,
21 Rook,
23 Queen,
25 King,
27}
28
29impl PieceType {
30 pub fn from_char(c: char) -> Option<PieceType> {
55 match c {
56 'P' | 'p' => Some(PieceType::Pawn),
57 'N' | 'n' => Some(PieceType::Knight),
58 'B' | 'b' => Some(PieceType::Bishop),
59 'R' | 'r' => Some(PieceType::Rook),
60 'Q' | 'q' => Some(PieceType::Queen),
61 'K' | 'k' => Some(PieceType::King),
62 _ => None,
63 }
64 }
65
66 pub fn to_char(&self) -> char {
84 match self {
85 PieceType::Pawn => 'P',
86 PieceType::Knight => 'N',
87 PieceType::Bishop => 'B',
88 PieceType::Rook => 'R',
89 PieceType::Queen => 'Q',
90 PieceType::King => 'K',
91 }
92 }
93}
94
95#[derive(Debug, Clone, Copy, PartialEq)]
109pub struct Piece {
110 pub color: Color,
112 pub piece_type: PieceType,
114}
115
116impl Piece {
117 pub fn new(color: Color, piece_type: PieceType) -> Piece {
136 Piece { color, piece_type }
137 }
138
139 pub fn from_fen(char: char) -> Result<Piece, PieceReprError> {
160 let color = match char.is_uppercase() {
161 true => Color::White,
162 false => Color::Black,
163 };
164
165 let piece_type = match char.to_lowercase().to_string().as_str() {
166 "p" => PieceType::Pawn,
167 "n" => PieceType::Knight,
168 "b" => PieceType::Bishop,
169 "r" => PieceType::Rook,
170 "q" => PieceType::Queen,
171 "k" => PieceType::King,
172 _ => return Err(PieceReprError::new(char)),
173 };
174
175 Ok(Piece::new(color, piece_type))
176 }
177}
178
179impl Display for Piece {
180 fn fmt(&self, f: &mut Formatter) -> fmt::Result {
181 let char = match self.piece_type {
182 PieceType::Pawn => "p",
183 PieceType::Knight => "n",
184 PieceType::Bishop => "b",
185 PieceType::Rook => "r",
186 PieceType::Queen => "q",
187 PieceType::King => "k",
188 }
189 .to_string();
190
191 match self.color {
192 Color::White => write!(f, "{}", char.to_uppercase()),
193 Color::Black => write!(f, "{}", char),
194 }
195 }
196}
197
198fn pawn_movement(color: Color, start_pos: &Position, end_pos: &Position) -> bool {
209 let direction;
210 let starting_row;
211
212 match color {
213 Color::White => {
214 direction = 1;
215 starting_row = 1;
216 }
217 Color::Black => {
218 direction = -1;
219 starting_row = 6;
220 }
221 }
222
223 if max_movement(start_pos, end_pos, 1) {
224 movement_direction(start_pos, end_pos, (0, direction))
225 || movement_direction(start_pos, end_pos, (1, direction))
226 || movement_direction(start_pos, end_pos, (-1, direction))
227 } else if max_movement(start_pos, end_pos, 2) {
228 movement_direction(start_pos, end_pos, (0, direction)) && start_pos.row == starting_row
229 } else {
230 false
231 }
232}
233
234fn knight_movement(start_pos: &Position, end_pos: &Position) -> bool {
244 l_movement(start_pos, end_pos)
245}
246
247fn bishop_movement(start_pos: &Position, end_pos: &Position) -> bool {
257 diagonal_movement(start_pos, end_pos)
258}
259
260fn rook_movement(start_pos: &Position, end_pos: &Position) -> bool {
270 linear_movement(start_pos, end_pos)
271}
272
273fn queen_movement(start_pos: &Position, end_pos: &Position) -> bool {
283 linear_movement(start_pos, end_pos) || diagonal_movement(start_pos, end_pos)
284}
285
286fn king_movement(start_pos: &Position, end_pos: &Position) -> bool {
296 max_movement(start_pos, end_pos, 1)
297}
298
299pub fn piece_movement(piece: &Piece, start_pos: &Position, end_pos: &Position) -> bool {
321 match piece.piece_type {
322 PieceType::Pawn => pawn_movement(piece.color, start_pos, end_pos),
323 PieceType::Knight => knight_movement(start_pos, end_pos),
324 PieceType::Bishop => bishop_movement(start_pos, end_pos),
325 PieceType::Rook => rook_movement(start_pos, end_pos),
326 PieceType::Queen => queen_movement(start_pos, end_pos),
327 PieceType::King => king_movement(start_pos, end_pos),
328 }
329}
330
331#[cfg(test)]
332mod tests {
333 use crate::core::{Color, PieceType, Position};
334
335 use super::*;
336
337 #[test]
338 fn test_from_char() {
339 assert_eq!(PieceType::from_char('p'), Some(PieceType::Pawn));
340 assert_eq!(PieceType::from_char('P'), Some(PieceType::Pawn));
341 assert_eq!(PieceType::from_char('N'), Some(PieceType::Knight));
342 assert_eq!(PieceType::from_char('n'), Some(PieceType::Knight));
343 assert_eq!(PieceType::from_char('B'), Some(PieceType::Bishop));
344 assert_eq!(PieceType::from_char('b'), Some(PieceType::Bishop));
345 assert_eq!(PieceType::from_char('R'), Some(PieceType::Rook));
346 assert_eq!(PieceType::from_char('r'), Some(PieceType::Rook));
347 assert_eq!(PieceType::from_char('Q'), Some(PieceType::Queen));
348 assert_eq!(PieceType::from_char('q'), Some(PieceType::Queen));
349 assert_eq!(PieceType::from_char('K'), Some(PieceType::King));
350 assert_eq!(PieceType::from_char('k'), Some(PieceType::King));
351
352 assert_eq!(PieceType::from_char('X'), None);
353 assert_eq!(PieceType::from_char('y'), None);
354 }
355
356 #[test]
357 fn test_to_char() {
358 assert_eq!(PieceType::Pawn.to_char(), 'P');
359 assert_eq!(PieceType::Knight.to_char(), 'N');
360 assert_eq!(PieceType::Bishop.to_char(), 'B');
361 assert_eq!(PieceType::Rook.to_char(), 'R');
362 assert_eq!(PieceType::Queen.to_char(), 'Q');
363 assert_eq!(PieceType::King.to_char(), 'K');
364 }
365
366 #[test]
367 fn test_pawn_movement() {
368 assert!(pawn_movement(
369 Color::White,
370 &Position::from_string("e2").unwrap(),
371 &Position::from_string("e3").unwrap()
372 ));
373 assert!(pawn_movement(
374 Color::White,
375 &Position::from_string("e2").unwrap(),
376 &Position::from_string("e4").unwrap()
377 ));
378 assert!(pawn_movement(
379 Color::White,
380 &Position::from_string("e2").unwrap(),
381 &Position::from_string("d3").unwrap()
382 ));
383 assert!(pawn_movement(
384 Color::White,
385 &Position::from_string("e2").unwrap(),
386 &Position::from_string("f3").unwrap()
387 ));
388 assert!(pawn_movement(
389 Color::Black,
390 &Position::from_string("e7").unwrap(),
391 &Position::from_string("e6").unwrap()
392 ));
393 assert!(pawn_movement(
394 Color::Black,
395 &Position::from_string("e7").unwrap(),
396 &Position::from_string("e5").unwrap()
397 ));
398 assert!(pawn_movement(
399 Color::Black,
400 &Position::from_string("e7").unwrap(),
401 &Position::from_string("d6").unwrap()
402 ));
403 assert!(pawn_movement(
404 Color::Black,
405 &Position::from_string("e7").unwrap(),
406 &Position::from_string("f6").unwrap()
407 ));
408 assert!(!pawn_movement(
409 Color::White,
410 &Position::from_string("e4").unwrap(),
411 &Position::from_string("e4").unwrap()
412 ));
413 assert!(!pawn_movement(
414 Color::White,
415 &Position::from_string("e2").unwrap(),
416 &Position::from_string("e5").unwrap()
417 ));
418 assert!(!pawn_movement(
419 Color::White,
420 &Position::from_string("e2").unwrap(),
421 &Position::from_string("d4").unwrap()
422 ));
423 assert!(!pawn_movement(
424 Color::White,
425 &Position::from_string("e2").unwrap(),
426 &Position::from_string("f4").unwrap()
427 ));
428 assert!(!pawn_movement(
429 Color::Black,
430 &Position::from_string("e4").unwrap(),
431 &Position::from_string("e4").unwrap()
432 ));
433 assert!(!pawn_movement(
434 Color::Black,
435 &Position::from_string("e7").unwrap(),
436 &Position::from_string("e4").unwrap()
437 ));
438 assert!(!pawn_movement(
439 Color::Black,
440 &Position::from_string("e7").unwrap(),
441 &Position::from_string("d5").unwrap()
442 ));
443 assert!(!pawn_movement(
444 Color::Black,
445 &Position::from_string("e7").unwrap(),
446 &Position::from_string("f5").unwrap()
447 ));
448 assert!(!pawn_movement(
449 Color::Black,
450 &Position::from_string("a6").unwrap(),
451 &Position::from_string("b7").unwrap()
452 ));
453 }
454
455 #[test]
456 fn test_knight_movement() {
457 assert!(knight_movement(
458 &Position::from_string("e4").unwrap(),
459 &Position::from_string("f6").unwrap()
460 ));
461 assert!(knight_movement(
462 &Position::from_string("e4").unwrap(),
463 &Position::from_string("g5").unwrap()
464 ));
465 assert!(knight_movement(
466 &Position::from_string("e4").unwrap(),
467 &Position::from_string("g3").unwrap()
468 ));
469 assert!(knight_movement(
470 &Position::from_string("e4").unwrap(),
471 &Position::from_string("f2").unwrap()
472 ));
473 assert!(knight_movement(
474 &Position::from_string("e4").unwrap(),
475 &Position::from_string("d2").unwrap()
476 ));
477 assert!(knight_movement(
478 &Position::from_string("e4").unwrap(),
479 &Position::from_string("c3").unwrap()
480 ));
481 assert!(knight_movement(
482 &Position::from_string("e4").unwrap(),
483 &Position::from_string("c5").unwrap()
484 ));
485 assert!(knight_movement(
486 &Position::from_string("e4").unwrap(),
487 &Position::from_string("d6").unwrap()
488 ));
489 assert!(!knight_movement(
490 &Position::from_string("e4").unwrap(),
491 &Position::from_string("e4").unwrap()
492 ));
493 assert!(!knight_movement(
494 &Position::from_string("e4").unwrap(),
495 &Position::from_string("e6").unwrap()
496 ));
497 assert!(!knight_movement(
498 &Position::from_string("e4").unwrap(),
499 &Position::from_string("g6").unwrap()
500 ));
501 assert!(!knight_movement(
502 &Position::from_string("e4").unwrap(),
503 &Position::from_string("g4").unwrap()
504 ));
505 assert!(!knight_movement(
506 &Position::from_string("e4").unwrap(),
507 &Position::from_string("f3").unwrap()
508 ));
509 assert!(!knight_movement(
510 &Position::from_string("e4").unwrap(),
511 &Position::from_string("d3").unwrap()
512 ));
513 }
514
515 #[test]
516 fn test_bishop_movement() {
517 assert!(bishop_movement(
518 &Position::from_string("e4").unwrap(),
519 &Position::from_string("f5").unwrap()
520 ));
521 assert!(bishop_movement(
522 &Position::from_string("e4").unwrap(),
523 &Position::from_string("g6").unwrap()
524 ));
525 assert!(bishop_movement(
526 &Position::from_string("e4").unwrap(),
527 &Position::from_string("h7").unwrap()
528 ));
529 assert!(bishop_movement(
530 &Position::from_string("e4").unwrap(),
531 &Position::from_string("f3").unwrap()
532 ));
533 assert!(bishop_movement(
534 &Position::from_string("e4").unwrap(),
535 &Position::from_string("g2").unwrap()
536 ));
537 assert!(bishop_movement(
538 &Position::from_string("e4").unwrap(),
539 &Position::from_string("h1").unwrap()
540 ));
541 assert!(bishop_movement(
542 &Position::from_string("e4").unwrap(),
543 &Position::from_string("d3").unwrap()
544 ));
545 assert!(bishop_movement(
546 &Position::from_string("e4").unwrap(),
547 &Position::from_string("c2").unwrap()
548 ));
549 assert!(bishop_movement(
550 &Position::from_string("e4").unwrap(),
551 &Position::from_string("b1").unwrap()
552 ));
553 assert!(bishop_movement(
554 &Position::from_string("e4").unwrap(),
555 &Position::from_string("d5").unwrap()
556 ));
557 assert!(bishop_movement(
558 &Position::from_string("e4").unwrap(),
559 &Position::from_string("c6").unwrap()
560 ));
561 assert!(bishop_movement(
562 &Position::from_string("e4").unwrap(),
563 &Position::from_string("b7").unwrap()
564 ));
565 assert!(!bishop_movement(
566 &Position::from_string("e4").unwrap(),
567 &Position::from_string("e4").unwrap()
568 ));
569 assert!(!bishop_movement(
570 &Position::from_string("e4").unwrap(),
571 &Position::from_string("e5").unwrap()
572 ));
573 assert!(!bishop_movement(
574 &Position::from_string("e4").unwrap(),
575 &Position::from_string("f6").unwrap()
576 ));
577 assert!(!bishop_movement(
578 &Position::from_string("e4").unwrap(),
579 &Position::from_string("g7").unwrap()
580 ));
581 }
582
583 #[test]
584 fn test_rook_movement() {
585 assert!(rook_movement(
586 &Position::from_string("e4").unwrap(),
587 &Position::from_string("e5").unwrap()
588 ));
589 assert!(rook_movement(
590 &Position::from_string("e4").unwrap(),
591 &Position::from_string("e6").unwrap()
592 ));
593 assert!(rook_movement(
594 &Position::from_string("e4").unwrap(),
595 &Position::from_string("e7").unwrap()
596 ));
597 assert!(rook_movement(
598 &Position::from_string("e4").unwrap(),
599 &Position::from_string("e8").unwrap()
600 ));
601 assert!(rook_movement(
602 &Position::from_string("e4").unwrap(),
603 &Position::from_string("e3").unwrap()
604 ));
605 assert!(rook_movement(
606 &Position::from_string("e4").unwrap(),
607 &Position::from_string("e2").unwrap()
608 ));
609 assert!(rook_movement(
610 &Position::from_string("e4").unwrap(),
611 &Position::from_string("e1").unwrap()
612 ));
613 assert!(rook_movement(
614 &Position::from_string("e4").unwrap(),
615 &Position::from_string("f4").unwrap()
616 ));
617 assert!(rook_movement(
618 &Position::from_string("e4").unwrap(),
619 &Position::from_string("g4").unwrap()
620 ));
621 assert!(rook_movement(
622 &Position::from_string("e4").unwrap(),
623 &Position::from_string("h4").unwrap()
624 ));
625 assert!(rook_movement(
626 &Position::from_string("e4").unwrap(),
627 &Position::from_string("d4").unwrap()
628 ));
629 assert!(rook_movement(
630 &Position::from_string("e4").unwrap(),
631 &Position::from_string("c4").unwrap()
632 ));
633 assert!(rook_movement(
634 &Position::from_string("e4").unwrap(),
635 &Position::from_string("b4").unwrap()
636 ));
637 assert!(rook_movement(
638 &Position::from_string("e4").unwrap(),
639 &Position::from_string("a4").unwrap()
640 ));
641 assert!(!rook_movement(
642 &Position::from_string("e4").unwrap(),
643 &Position::from_string("e4").unwrap()
644 ));
645 assert!(!rook_movement(
646 &Position::from_string("e4").unwrap(),
647 &Position::from_string("f5").unwrap()
648 ));
649 assert!(!rook_movement(
650 &Position::from_string("e4").unwrap(),
651 &Position::from_string("g6").unwrap()
652 ));
653 assert!(!rook_movement(
654 &Position::from_string("e4").unwrap(),
655 &Position::from_string("h7").unwrap()
656 ));
657 assert!(!rook_movement(
658 &Position::from_string("e4").unwrap(),
659 &Position::from_string("d3").unwrap()
660 ));
661 assert!(!rook_movement(
662 &Position::from_string("e4").unwrap(),
663 &Position::from_string("c2").unwrap()
664 ));
665 assert!(!rook_movement(
666 &Position::from_string("e4").unwrap(),
667 &Position::from_string("b1").unwrap()
668 ));
669 }
670
671 #[test]
672 fn test_queen_movement() {
673 assert!(queen_movement(
674 &Position::from_string("e4").unwrap(),
675 &Position::from_string("f5").unwrap()
676 ));
677 assert!(queen_movement(
678 &Position::from_string("e4").unwrap(),
679 &Position::from_string("g6").unwrap()
680 ));
681 assert!(queen_movement(
682 &Position::from_string("e4").unwrap(),
683 &Position::from_string("h7").unwrap()
684 ));
685 assert!(queen_movement(
686 &Position::from_string("e4").unwrap(),
687 &Position::from_string("f3").unwrap()
688 ));
689 assert!(queen_movement(
690 &Position::from_string("e4").unwrap(),
691 &Position::from_string("g2").unwrap()
692 ));
693 assert!(queen_movement(
694 &Position::from_string("e4").unwrap(),
695 &Position::from_string("h1").unwrap()
696 ));
697 assert!(queen_movement(
698 &Position::from_string("e4").unwrap(),
699 &Position::from_string("d3").unwrap()
700 ));
701 assert!(queen_movement(
702 &Position::from_string("e4").unwrap(),
703 &Position::from_string("c2").unwrap()
704 ));
705 assert!(queen_movement(
706 &Position::from_string("e4").unwrap(),
707 &Position::from_string("b1").unwrap()
708 ));
709 assert!(queen_movement(
710 &Position::from_string("e4").unwrap(),
711 &Position::from_string("d5").unwrap()
712 ));
713 assert!(queen_movement(
714 &Position::from_string("e4").unwrap(),
715 &Position::from_string("c6").unwrap()
716 ));
717 assert!(queen_movement(
718 &Position::from_string("e4").unwrap(),
719 &Position::from_string("b7").unwrap()
720 ));
721 assert!(queen_movement(
722 &Position::from_string("e4").unwrap(),
723 &Position::from_string("e5").unwrap()
724 ));
725 assert!(queen_movement(
726 &Position::from_string("e4").unwrap(),
727 &Position::from_string("e6").unwrap()
728 ));
729 assert!(queen_movement(
730 &Position::from_string("e4").unwrap(),
731 &Position::from_string("e7").unwrap()
732 ));
733 assert!(queen_movement(
734 &Position::from_string("e4").unwrap(),
735 &Position::from_string("e8").unwrap()
736 ));
737 assert!(queen_movement(
738 &Position::from_string("e4").unwrap(),
739 &Position::from_string("e3").unwrap()
740 ));
741 assert!(queen_movement(
742 &Position::from_string("e4").unwrap(),
743 &Position::from_string("e2").unwrap()
744 ));
745 assert!(queen_movement(
746 &Position::from_string("e4").unwrap(),
747 &Position::from_string("e1").unwrap()
748 ));
749 assert!(queen_movement(
750 &Position::from_string("e4").unwrap(),
751 &Position::from_string("f4").unwrap()
752 ));
753 assert!(queen_movement(
754 &Position::from_string("e4").unwrap(),
755 &Position::from_string("g4").unwrap()
756 ));
757 assert!(queen_movement(
758 &Position::from_string("e4").unwrap(),
759 &Position::from_string("h4").unwrap()
760 ));
761 assert!(queen_movement(
762 &Position::from_string("e4").unwrap(),
763 &Position::from_string("d4").unwrap()
764 ));
765 assert!(queen_movement(
766 &Position::from_string("e4").unwrap(),
767 &Position::from_string("c4").unwrap()
768 ));
769 assert!(queen_movement(
770 &Position::from_string("e4").unwrap(),
771 &Position::from_string("b4").unwrap()
772 ));
773 assert!(queen_movement(
774 &Position::from_string("e4").unwrap(),
775 &Position::from_string("a4").unwrap()
776 ));
777 assert!(!queen_movement(
778 &Position::from_string("e4").unwrap(),
779 &Position::from_string("e4").unwrap()
780 ));
781 assert!(!queen_movement(
782 &Position::from_string("e4").unwrap(),
783 &Position::from_string("d7").unwrap()
784 ));
785 assert!(!queen_movement(
786 &Position::from_string("e4").unwrap(),
787 &Position::from_string("d1").unwrap()
788 ));
789 assert!(!queen_movement(
790 &Position::from_string("e4").unwrap(),
791 &Position::from_string("f7").unwrap()
792 ));
793 assert!(!queen_movement(
794 &Position::from_string("e4").unwrap(),
795 &Position::from_string("f1").unwrap()
796 ));
797 assert!(!queen_movement(
798 &Position::from_string("e4").unwrap(),
799 &Position::from_string("g7").unwrap()
800 ));
801 assert!(!queen_movement(
802 &Position::from_string("e4").unwrap(),
803 &Position::from_string("g1").unwrap()
804 ));
805 assert!(!queen_movement(
806 &Position::from_string("e4").unwrap(),
807 &Position::from_string("h8").unwrap()
808 ));
809 }
810
811 #[test]
812 fn test_king_movement() {
813 assert!(king_movement(
814 &Position::from_string("e4").unwrap(),
815 &Position::from_string("f5").unwrap()
816 ));
817 assert!(king_movement(
818 &Position::from_string("e4").unwrap(),
819 &Position::from_string("e5").unwrap()
820 ));
821 assert!(king_movement(
822 &Position::from_string("e4").unwrap(),
823 &Position::from_string("d5").unwrap()
824 ));
825 assert!(king_movement(
826 &Position::from_string("e4").unwrap(),
827 &Position::from_string("d4").unwrap()
828 ));
829 assert!(king_movement(
830 &Position::from_string("e4").unwrap(),
831 &Position::from_string("d3").unwrap()
832 ));
833 assert!(king_movement(
834 &Position::from_string("e4").unwrap(),
835 &Position::from_string("e3").unwrap()
836 ));
837 assert!(king_movement(
838 &Position::from_string("e4").unwrap(),
839 &Position::from_string("f3").unwrap()
840 ));
841 assert!(king_movement(
842 &Position::from_string("e4").unwrap(),
843 &Position::from_string("f4").unwrap()
844 ));
845 assert!(!king_movement(
846 &Position::from_string("e4").unwrap(),
847 &Position::from_string("e4").unwrap()
848 ));
849 assert!(!king_movement(
850 &Position::from_string("e4").unwrap(),
851 &Position::from_string("e6").unwrap()
852 ));
853 assert!(!king_movement(
854 &Position::from_string("e4").unwrap(),
855 &Position::from_string("f6").unwrap()
856 ));
857 assert!(!king_movement(
858 &Position::from_string("e4").unwrap(),
859 &Position::from_string("g6").unwrap()
860 ));
861 assert!(!king_movement(
862 &Position::from_string("e4").unwrap(),
863 &Position::from_string("g5").unwrap()
864 ));
865 assert!(!king_movement(
866 &Position::from_string("e4").unwrap(),
867 &Position::from_string("g4").unwrap()
868 ));
869 assert!(!king_movement(
870 &Position::from_string("e4").unwrap(),
871 &Position::from_string("g3").unwrap()
872 ));
873 assert!(!king_movement(
874 &Position::from_string("e4").unwrap(),
875 &Position::from_string("f2").unwrap()
876 ));
877 assert!(!king_movement(
878 &Position::from_string("e4").unwrap(),
879 &Position::from_string("e2").unwrap()
880 ));
881 assert!(!king_movement(
882 &Position::from_string("e4").unwrap(),
883 &Position::from_string("d2").unwrap()
884 ));
885 assert!(!king_movement(
886 &Position::from_string("e4").unwrap(),
887 &Position::from_string("d6").unwrap()
888 ));
889 }
890
891 #[test]
892 fn test_from_fen() {
893 let wpawn = Piece::from_fen('P').unwrap();
894 assert_eq!(wpawn.color, Color::White);
895 assert_eq!(wpawn.piece_type, PieceType::Pawn);
896
897 let bpawn = Piece::from_fen('p').unwrap();
898 assert_eq!(bpawn.color, Color::Black);
899 assert_eq!(bpawn.piece_type, PieceType::Pawn);
900
901 let wrook = Piece::from_fen('R').unwrap();
902 assert_eq!(wrook.color, Color::White);
903 assert_eq!(wrook.piece_type, PieceType::Rook);
904
905 let brook = Piece::from_fen('r').unwrap();
906 assert_eq!(brook.color, Color::Black);
907 assert_eq!(brook.piece_type, PieceType::Rook);
908
909 let wknight = Piece::from_fen('N').unwrap();
910 assert_eq!(wknight.color, Color::White);
911 assert_eq!(wknight.piece_type, PieceType::Knight);
912
913 let bknight = Piece::from_fen('n').unwrap();
914 assert_eq!(bknight.color, Color::Black);
915 assert_eq!(bknight.piece_type, PieceType::Knight);
916
917 let wbishop = Piece::from_fen('B').unwrap();
918 assert_eq!(wbishop.color, Color::White);
919 assert_eq!(wbishop.piece_type, PieceType::Bishop);
920
921 let bbishop = Piece::from_fen('b').unwrap();
922 assert_eq!(bbishop.color, Color::Black);
923 assert_eq!(bbishop.piece_type, PieceType::Bishop);
924
925 let wqueen = Piece::from_fen('Q').unwrap();
926 assert_eq!(wqueen.color, Color::White);
927 assert_eq!(wqueen.piece_type, PieceType::Queen);
928
929 let bqueen = Piece::from_fen('q').unwrap();
930 assert_eq!(bqueen.color, Color::Black);
931 assert_eq!(bqueen.piece_type, PieceType::Queen);
932
933 let wking = Piece::from_fen('K').unwrap();
934 assert_eq!(wking.color, Color::White);
935 assert_eq!(wking.piece_type, PieceType::King);
936
937 let bking = Piece::from_fen('k').unwrap();
938 assert_eq!(bking.color, Color::Black);
939 assert_eq!(bking.piece_type, PieceType::King);
940 }
941
942 #[test]
943 fn test_from_fen_invalid() {
944 let result = Piece::from_fen('X');
945 assert!(result.is_err());
946 }
947
948 #[test]
949 fn test_to_fen() {
950 let wpawn = Piece {
951 color: Color::White,
952 piece_type: PieceType::Pawn,
953 };
954 assert_eq!(wpawn.to_string(), String::from("P"));
955
956 let bpawn = Piece {
957 color: Color::Black,
958 piece_type: PieceType::Pawn,
959 };
960 assert_eq!(bpawn.to_string(), String::from("p"));
961
962 let wrook = Piece {
963 color: Color::White,
964 piece_type: PieceType::Rook,
965 };
966 assert_eq!(wrook.to_string(), String::from("R"));
967
968 let brook = Piece {
969 color: Color::Black,
970 piece_type: PieceType::Rook,
971 };
972 assert_eq!(brook.to_string(), String::from("r"));
973
974 let wknight = Piece {
975 color: Color::White,
976 piece_type: PieceType::Knight,
977 };
978 assert_eq!(wknight.to_string(), String::from("N"));
979
980 let bknight = Piece {
981 color: Color::Black,
982 piece_type: PieceType::Knight,
983 };
984 assert_eq!(bknight.to_string(), String::from("n"));
985
986 let wbishop = Piece {
987 color: Color::White,
988 piece_type: PieceType::Bishop,
989 };
990 assert_eq!(wbishop.to_string(), String::from("B"));
991
992 let bbishop = Piece {
993 color: Color::Black,
994 piece_type: PieceType::Bishop,
995 };
996 assert_eq!(bbishop.to_string(), String::from("b"));
997
998 let wqueen = Piece {
999 color: Color::White,
1000 piece_type: PieceType::Queen,
1001 };
1002 assert_eq!(wqueen.to_string(), String::from("Q"));
1003
1004 let bqueen = Piece {
1005 color: Color::Black,
1006 piece_type: PieceType::Queen,
1007 };
1008 assert_eq!(bqueen.to_string(), String::from("q"));
1009
1010 let wking = Piece {
1011 color: Color::White,
1012 piece_type: PieceType::King,
1013 };
1014 assert_eq!(wking.to_string(), String::from("K"));
1015
1016 let bking = Piece {
1017 color: Color::Black,
1018 piece_type: PieceType::King,
1019 };
1020 assert_eq!(bking.to_string(), String::from("k"));
1021 }
1022}