using System; using System.Collections.Generic; using System.Drawing; using ChessPanel; using System.Linq; using System.Windows; namespace Chess { public enum PieceColor { White, Black }; public enum PieceTeam { Enemy, Ally }; public enum PieceType { King, Queen, Bishop, Rook, Knight, Pawn }; public enum MoveMode { Any, Attack, Movement }; /// /// Figur /// public abstract class Piece { public PieceColor color; public PieceType type; public Image image; public bool HasMoved = false; public Field field; private Vector virtualPosition;//? public bool EnPassantPossible = false; // Only in Pawn Class. Signs that this Piece has virtually not jumped two pieces, but one, reflective meaning: This.Figure can be attacked using Enpassant if this.type is Pawn public override string ToString() { return type.ToString(); } public Piece(Vector position, Grid fields) { this.field = fields[position]; fields[position].CurrentPiece = this; } internal void removeTargetFieldsWhereKingIsEndangered(Grid fields, Dictionary targetFields) { Field ownKingLocation = fields.GetKing(this.color).field; foreach (var virtualTargetField in targetFields) { if (fields.IsFieldVirtuallyEndagered(ownKingLocation, (this.color == PieceColor.Black ? PieceColor.White : PieceColor.Black), this, virtualTargetField.Key)) targetFields.Remove(virtualTargetField.Key); } } /// /// Tests if the Move will leave your King endangered. /// /// GameField /// Location of Piece to move /// Location to move Piece to /// Color of Piece to move /// Bool /* internal static bool MoveWillEndangerOwnKing(Grid fields, Vector pieceLocation, Vector simulatedLocation, PieceColor color) { // fields[simulateLocation].currentPiece = fields[pieceLocation].currentPiece; // fields[pieceLocation].currentPiece = null; // Check if own king is endangered return FieldIsEndangered(fields, simulatedLocation, kingLocation, color, dontTestKingDanger: true); }*/ /// /// Checks if a specific field can be reached by the figure while a virtual move is simulated /// /// Piece that virtually got moved /// Field that the movePiece virtually moved to /// Field that should be checked /// Current Game Grid /// internal abstract bool EndageresFieldWithVirtualMove(Grid fields, Field possibleEndageredField, Piece movePiece, Field targetPos); internal void Move(Field newPieceField) { this.field.CurrentPiece = null; // Remove piece from previous position this.field = newPieceField; // Set pieces location to new field newPieceField.CurrentPiece = this; // Set new fields piece to this } /// /// Tests if the Move will leave your movedPiece endangered. /// /// GameField /// Location of Piece to move /// Location to move Piece to /// Color of Piece to move /// Bool //internal static bool MoveWillEndangerPiece(Grid fields, Vector pieceLocation, Vector testLocation, PieceColor color) //{ // return false; // //Grid simulatedField = fields; // //simulatedField[(int)pieceLocation.X, (int)pieceLocation.Y].currentPiece = null; // //return FieldIsEndangered(fields simulatedField, testLocation, color); //} /// /// Tests if your King is currently endangered. /// /// GameField /// Kings color /// //private static bool KingIsEndangered(Grid fields, PieceColor color) => FieldIsEndangered(fields, GetKingLocation(fields, color), color, dontTestKingDanger: true); /// /// Tests if the testLocation is endangered by an enemy. /// /// GameField /// Ally Color /// Location to test /// Bool //private static bool FieldIsEndangered(Grid fields, Vector simulatedLocation, Vector testLocation, PieceColor color, bool dontTestKingDanger = false) //{ // foreach (Field field in fields) // { // if (field.location != simulatedLocation // && field.currentPiece != null // && field.currentPiece.color != color // && field.currentPiece.GetValidTargetFields(fields, dontTestKingDanger: dontTestKingDanger).ContainsKey(testLocation)) // return true; // } // return false; //} /*internal static bool IsEndangeredLocationForPiece(Grid fields, Vector pieceLocation, Vector testLocation, PieceColor color) { bool returnValue = false; Piece p = fields[(int)pieceLocation.X, (int)pieceLocation.Y].currentPiece; fields[(int)pieceLocation.X, (int)pieceLocation.Y].currentPiece = null; foreach (var field in fields) { if (field.currentPiece != null) if (field.currentPiece.color != color) if (field.currentPiece.GetValidTargetFields(fields, field.location, true).ContainsKey(testLocation)) { returnValue = true; break; } } fields[(int)pieceLocation.X, (int)pieceLocation.Y].currentPiece = p; return returnValue; }*/ /* internal static bool MoveWillEndangerKing(Grid fields, Vector pieceLocation, Vector pieceMovedLocation, PieceColor color) // This does not test if it is a valid move spot { bool returnValue = false; Piece p1 = fields[(int)pieceLocation.X, (int)pieceLocation.Y].currentPiece; Piece p2 = fields[(int)pieceMovedLocation.X, (int)pieceMovedLocation.Y].currentPiece; fields[(int)pieceLocation.X, (int)pieceLocation.Y].currentPiece = null; fields[(int)pieceMovedLocation.X, (int)pieceMovedLocation.Y].currentPiece = p1; returnValue = KingIsEndangered(fields, color); fields[(int)pieceLocation.X, (int)pieceLocation.Y].currentPiece = p1; fields[(int)pieceMovedLocation.X, (int)pieceMovedLocation.Y].currentPiece = p2; return returnValue; }*/ /* private static bool KingIsEndangered(Grid fields, PieceColor color) { Vector kingLocation = GetKingLocation(fields, color); foreach (var field in fields) { if (field.currentPiece == null || field.currentPiece.color != color) continue; if (field.currentPiece.GetValidTargetFields(fields, field.location, dontTestKingDanger: true).ContainsKey(kingLocation)) { return true; } } return false; }*/ /// /// Searches for the King of the given color. /// /// GameField /// Kings color /// King location as Vector private static Vector GetKingLocation(Grid fields, PieceColor color) { foreach (Field field in fields) if (!field.IsEmpty && field.currentPiece.type == PieceType.King && field.currentPiece.color == color) return field.location; throw new Exception("King not found!"); } virtual internal Dictionary GetValidTargetFields(Grid fields, MoveMode mode = MoveMode.Any, bool dontTestKingDanger = false) { var targetFields = GetTargetFields(fields, field, this.color); if (!dontTestKingDanger) { Field kinglocation = fields.GetKing(this.color).field; List remove = new List(); foreach (var item in targetFields.Keys) { if (fields.IsFieldVirtuallyEndagered(kinglocation, (this.color == PieceColor.Black ? PieceColor.White : PieceColor.Black), this, item)) remove.Add(item); } foreach (var item in remove) { targetFields.Remove(item); } } return targetFields; } internal abstract Dictionary GetTargetFields(Grid fields, Field field, PieceColor color); internal static bool FieldIsVirtuallyEmpty(Field targetPos, Field skipField, Field possibleTargetField) { return (possibleTargetField.IsEmpty && possibleTargetField != targetPos) || possibleTargetField == skipField; } internal static bool checkFieldCanBeReached(Field possibleEndageredField, Field targetPos, Piece movePiece, Field possibleTargetField, PieceColor color, out bool breakIt) { breakIt = false; var skipField = movePiece.field; if (FieldIsVirtuallyEmpty(targetPos, skipField, possibleTargetField)) { if (possibleTargetField == possibleEndageredField) return true; } else { var checkPiece = possibleTargetField == targetPos ? movePiece : possibleTargetField.CurrentPiece; if (checkPiece.color != color && possibleTargetField == possibleEndageredField) return true; breakIt=true; } return false; } //internal abstract Dictionary GetValidTargetFields(Grid fields, MoveMode mode = MoveMode.Any, bool dontTestKingDanger = false); } }