Commit 4f744bb9 authored by Leopold Keller's avatar Leopold Keller
Browse files

abc

parent 0d23f869
#include "piece.h"
class Bishop : public Piece{
public:
Bishop(const Color& color);
Bishop(const Piece& piece);
bool isMovePossible(const Board&, const Move&) override;
protected:
vector<Field> getPossibleMoves(const Board& board, const Move& move) const override;
};
\ No newline at end of file
#include <iostream>
#include <type_traits>
#include "pawn.h"
#include "bishop.h"
#include "king.h"
#include "knight.h"
#include "queen.h"
#include "rook.h"
#include "board.h"
#include "input.h"
#include "piece.h"
using namespace std;
Board::Board() : currentPlayer(Color::White){
for(int i = 0; i < size; i++){
gamefield.push_back(vector<Piece*>{});
Color c = (i == 0 || i == 1 ? Color::Black : Color::White);
for(int j = 0; j < size; j++){
if(j== 0 || j == 7){
gamefield[i].push_back(new Rook(c));
gamefield[i].push_back(new Knight(c));
gamefield[i].push_back(new Bishop(c));
gamefield[i].push_back(new Queen(c));
gamefield[i].push_back(new King(c));
gamefield[i].push_back(new Bishop(c));
gamefield[i].push_back(new Knight(c));
gamefield[i].push_back(new Rook(c));
break;
}else if (i == 1 || i == 6){
gamefield[i].push_back(new Pawn(c));
} else
gamefield[i].push_back(new Piece("-----", Color::Empty));
}
}
}
Board::Board(const Board& board) : currentPlayer(board.currentPlayer){
for(int i = 0; i < size; i++){
gamefield.push_back(vector<Piece*>{});
for (int j = 0; j < size; j++) {
Field field {row = (int) i, col = (int) j};
if(board.getPieceOnField(field)->toString() == Bishop(Color::White).toString() || board.getPieceOnField(field)->toString()== Bishop(Color::Black).toString()){
gamefield[i].push_back(new Bishop(*board.gamefield[i][j]));
} else if(board.getPieceOnField(field)->toString() == King(Color::White).toString() || board.getPieceOnField(field)->toString()== King(Color::Black).toString()){
gamefield[i].push_back(new King(*board.gamefield[i][j]));
} else if(board.getPieceOnField(field)->toString() == Knight(Color::White).toString() || board.getPieceOnField(field)->toString()== Knight(Color::Black).toString()){
gamefield[i].push_back(new Knight(*board.gamefield[i][j]));
} else if(board.getPieceOnField(field)->toString() == Pawn(Color::White).toString() || board.getPieceOnField(field)->toString()== Pawn(Color::Black).toString()){
gamefield[i].push_back(new Pawn(*board.gamefield[i][j]));
} else if(board.getPieceOnField(field)->toString() == Queen(Color::White).toString() || board.getPieceOnField(field)->toString()== Queen(Color::Black).toString()){
gamefield[i].push_back(new Queen(*board.gamefield[i][j]));
} else if(board.getPieceOnField(field)->toString() == Rook(Color::White).toString() || board.getPieceOnField(field)->toString()== Rook(Color::Black).toString()){
gamefield[i].push_back(new Rook(*board.gamefield[i][j]));
} else{
gamefield[i].push_back(new Piece(*board.gamefield[i][j]));
}
}
}
}
Board::~Board(){
for(int i = 0; i < size; i++){
for(int j = 0; j < size; j++){
if(gamefield[i][j] == 0) continue;
delete gamefield[i][j];
gamefield[i][j] = NULL;
}
gamefield[i].clear();
}
gamefield.clear();
}
bool Board::isMoveInBounds(const Move& move) const{
if(move.from.col >= 0 && move.from.col < size && move.from.row >= 0 && move.from.row < size && move.to.col >=0 && move.to.col < size && move.to.row >=0 && move.to.row < size) return true;
return false;
}
bool Board::isEnemy(const Field& field) const{
if((currentPlayer == Color::White && getPieceOnField(field)->isBlack()) || (currentPlayer == Color::Black && getPieceOnField(field)->isWhite())) return true;
return false;
}
void Board::play(){
while(true){
printBoard();
string player = (currentPlayer == Color::White ? "[White]" : "[Black]");
string standardOutput = player + "Geben Sie den gewünschten Zug an(Form a1-b2): ";
Move nextMove;
do{
cout << standardOutput << endl;
string input;
getline(cin, input);
if (!input.compare("quit")) return;
cout.flush();
cout.clear();
nextMove = convertConsoleToMove(input);
}
while(!checkMove(nextMove));
bool hasPlayerWon = MoveHandlerAndWinCheck(nextMove);
if(hasPlayerWon) return;
currentPlayer = (currentPlayer == Color::White ? Color::Black : Color::White);
cout << endl;
}
}
void Board:: printBoard() const{
int rowIndex = 0;
for(auto& row : gamefield){
cout << rowIndex+1 << " ";
for(auto& piece : row){
cout << piece-> toString() << " ";
}
cout << " " << rowIndex+1 << endl;
rowIndex++;
cout << endl;
}
}
bool Board::hasWon(const Field& enemy) const{
if(getPieceOnField(enemy)->toString() == King(Color::White).toString() || getPieceOnField(enemy)->toString() == King(Color::Black).toString()) return true;
}
int getSize() const{
return size;
}
bool Board::isFieldFree(const Field& field) const {
return getPieceOnField(field)->isEmpty();
}
bool Board::isFieldPossible(const Field& field) const{
if(isFieldFree(field) || isEnemy(field)) return true;
return false;
}
Piece* Board::getPieceOnField(const Field& field) const{
return gamefield[field.row][field.col];
}
bool Board::checkMove(const Move& move) const {
if(!isMoveInBounds(move)){
cout << "Please enter a Move that is valid!" << endl;
return false;
}
if(!getPieceOnField(move.from)->isMovePossible(*this, move)){
cout << "Move is not valid for " << getPieceOnField(move.from)->toString() << "!" << endl;
return false;
}
if(isFieldFree(move.from)){
cout << "Pls select a Field that is not empty!" << endl;
return false;
}
if(!isEnemy(move.from)){
cout << "Please select one of your own Pieces!" << endl;
return false;
}
if(!isEnemy(move.to) && !isFieldFree(move.to)){
cout << "Please select an enemy Piece to Attack!" << endl;
return false;
}
return true;
}
bool Board::MoveHandlerAndWinCheck(const Move &move){
if(isEnemy(move.to)){
cout << "You hit an enemy!" << endl;
if(hasWon(move.to)){
cout << "Congratulations you won the game!" << endl;
return true;
}
}
delete(gamefield[move.to.row][move.to.col]);
gamefield[move.to.row][move.to.col] = gamefield[move.from.row][move.from.col];
gamefield[move.from.row][move.from.col] = new Piece("-----", Color::Empty);
return false;
}
#include <vector>
enum class Color;
class Piece;
#include "piece.h"
using namespace std;
struct Field {
int row;
int col;
};
struct Move{
Field from;
Field to;
};
class Board{
public:
Board();
Board(const Board& board);
void play();
void printBoard() const;
bool isFieldPossible(const Field& position) const;
bool isFieldFree(const Field& position) const;
int getSize() const;
~Board();
private:
vector<vector<Piece*>> gamefield;
const int size = 8;
bool isMoveInBounds(const Move& move) const;
bool isEnemy(const Field& field) const;
Piece* getPieceOnField(const Field& field) const;
bool checkMove(const Move& move) const;
bool MoveHandlerAndWinCheck(const Move& move);
bool hasWon(const Field& enemyPosition) const;
Color currentPlayer;
};
\ No newline at end of file
#include "board.h"
int convertCharToInt(const char& c);
Move convertConsoleToMove(const string& input);
\ No newline at end of file
#include "king.h"
#include "board.h"
King::King(const Color& color) : Piece("King", color){
}
King::King(const Piece& piece) : Piece(piece){
}
bool King::isMovePossible(const Board&, const Move&){
return true;
}
vector<Field> King::getPossibleMoves(const Board&, const Move&) const {
vector<Field> fields;
return fields;
}
\ No newline at end of file
#include "piece.h"
class King : public Piece{
public:
King(const Color& color);
King(const Piece& piece);
bool isMovePossible(const Board&, const Move&) override;
protected:
vector<Field> getPossibleMoves(const Board& board, const Move& move) const override;
};
\ No newline at end of file
#include "knight.h"
#include "board.h"
Knight::Knight(const Color& color) : Piece("Knight", color){
}
Knight::Knight(const Piece& piece) : Piece(piece){
}
bool Knight::isMovePossible(const Board& b, const Move& m){
vector<Field> possibleMoves = getPossibleMoves(b,m);
for (auto pos : possibleMoves){
if(pos.row == m.to.row && pos.col == m.to.col) return true;
}
return false;
}
vector<Field> Knight::getPossibleMoves(const Board& board, const Move& move) const{
vector<Field> fields;
vector<Field> knightMoves {
Field {.row = -2, .col = -1}, Field{.row = -1, .col = -2},Field{.row = 1, .col = -2}, Field{.row = 2, .col = -1}, Field{.row = 2, .col = 1}, Field{.row = 1, .col = 2}, Field{.row = -1, .col = 2},Field{.row = -2, .col = 1}
};
for(Field knightMove : knightMoves){
Field tempField{ .row = (move.from.row + knightMove.row), .col = (move.from.col + knightMove.col)};
if(move.from.col + knightMove.col > board.getSize()-1 || move.from.col + knightMove.col <0) continue;
if(move.from.row + knightMove.row > board.getSize()-1 || move.from.row + knightMove.crow <0) continue;
if(board.isFieldPossible(tempField)) fields.push_back(tempField);
}
return fields;
}
\ No newline at end of file
#include "piece.h"
class Knight : public Piece{
public:
Knight(const Color& color);
Knight(const Piece& piece);
bool isMovePossible(const Board&, const Move&) override;
protected:
vector<Field> getPossibleMoves(const Board& board, const Move& move) const override;
};
\ No newline at end of file
#include <iostream>
#include "board.h"
using namespace std;
int main(){
Board gameboard1 = Board();
gameboard1.play();
return 0;
}
\ No newline at end of file
#include "piece.h"
#include "pawn.h"
#include "board.h"
Pawn::Pawn(const Color& color) : Piece(Pawn, color){
}
Pawn::Pawn(const Piece &piece) : Piece(piece){
}
bool Pawn::isMovePossible(const Board&, const Move& )
\ No newline at end of file
#include "piece.h"
class Pawn : public Piece{
public:
Pawn(const Color& color);
Pawn(const Piece& piece);
bool isMovePossible(const Board&, const Move&) override;
protected:
vector<Field> getPossibleMoves(const Board& board, const Move& move) const override;
};
\ No newline at end of file
#include "piece.h"
#include "board.h"
#include <string>
Piece::Piece(const string &displayString, Color color) : displayString(displayString), color(color){
}
bool Piece::isEmpty() const{
return Piece::color == Color::Empty;
}
bool Piece::isWhite() const{
return Piece::color == Color::White;
}
bool Piece::isBlack() const{
return Piece::color == Color::Black;
}
bool Piece::isMovePossible(const Board&, const Move&){
return true;
}
std::string Piece::toString() const{
if(color == Color::White){
return "W" + displayString;
}else if (color == Color::Black){
return "B" + displayString;
} else {
return displayString;
}
}
vector<Field> Piece::getPossibleMoves(const Board&, const Move&) const{
vector<Field> fields;
return fields;
}
\ No newline at end of file
#ifndef PIECE_H
#define PIECE_H
#include "board.h"
#include <string>
/**
* @brief The Color enum is used to represent the color of a piece.
*
* Since you are free to choose wether an empty field is represented by a piece
* object or simply a nullptr you are free to edit this enum if that is the case
* in your implementeation.
*/
enum class Color
{
White,
Black,
Empty
};
/**
* @brief The Piece class represents a single chess piece
*
* This class is the base class of all other chess pieces. Every distinct chess
* piece is implemented in it's own class. Header files for those classes are
* not part of the supplied code, so you will have to write your own.
* It is also possible to declare multiple classes in a single header, so you
* could also declare the needed classes here.
*
* Every piece object has a distinct \ref displayString which is the string
* representation of that particular piece. Subclasses of piece are supposed to
* set those string via constructor chaining.
*/
class Piece
{
public:
/**
* @brief Piece constructor
* @param displayString The string representation of this piece
* @param color The color of this piece
*/
Piece(const std::string& displayString, Color color);
/**
* @brief Piece destructor
*
* This is needed in **every** inheritance hierarchy and insures that the
* correct (subclass) destructor is always called when an object is deletet
* via a base class pointer.
*
* You do not need to implement anything special here, it is just important
* that the destructor is declared virtual.
*
* Setting the destructor to = default gives that destructor the default
* behaviour (which is: do nothing)
*/
virtual ~Piece() = default;
/**
* @brief isWhite return true if piece is White
* @return true if piece is White
*/
bool isWhite() const;
/**
* @brief isBlack return true if piece is Black
* @return true if piece is Black
*/
bool isBlack() const;
/**
* @brief isEmpty return true if this is an empty piece
* @return true if piece is an empty piece
*
* Note: You can choose whether you want to represent the concept of an "empty
* field" by a special type of object, or by having a nullptr for empty
* fields.
* When choosing the latter, you can omit this method.
*/
bool isEmpty() const;
/**
* @brief toString returns string representation of piece
* @return string representation pf piece
*/
std::string toString() const;
/**
* @brief isMovePossible checks if the supplied move is possible
* @return true if the move was possible
*
* This method need to be virtual because it is overwritten in certain
* subclasses. You can implement a "default version" in the piece class which
* just return true.
* The "virtual" keyword has the effect, that, for example,
* Rook::isMovePossible is called automagically when called on a piece* when
* that piece* is referencing a Rook object.
*/
virtual bool isMovePossible(const Board& /*b*/, const Board::Move& /*m*/);
private:
const std::string displayString;
const Color color;
};
#endif // PIECE_H
#include "queen.h"
#include "board.h"
Queen::Queen(const Color& color) : Piece("Queen", color){
}
Queen::Queen(const Piece& piece) : Piece(piece){
}
bool Queen::isMovePossible(const Board&, const Move&){
return true;
}
vector<Field> Queen::getPossibleMoves(const Board&, const Move&) const {
vector<Field> fields;
return fields;
}
\ No newline at end of file
#include "piece.h"
class Queen : public Piece{
public:
Queen(const Color& color);
Queen(const Piece& piece);
bool isMovePossible(const Board&, const Move&) override;
protected:
vector<Field> getPossibleMoves(const Board& board, const Move& move) const override;
};
\ No newline at end of file
#include "piece.h"
class Rook : public Piece{
public:
Rook(const Color& color);
Rook(const Piece& piece);
bool isMovePossible(const Board&, const Move&) override;
protected:
vector<Field> getPossibleMoves(const Board& board, const Move& move) const override;
};
\ No newline at end of file
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment