Recently I've been developing a chess game in Python - using pygame - just as a project for myself. I have a class for each piece type, and in each class, I have a method called find_available_moves
which returns an array representing the board showing where the piece is legally allowed to move. I've accomplished this, but I feel like there is a lot of repetition and I'm unsure how to make my code more concise.
Here is the method from the Rook class for instance:
def find_available_moves(self, grid):
"""
:param grid: Grid class
:return list: The spaces where the rook can move to
"""
available_spaces = [[False] * grid.columns for i in range(grid.rows)]
# Check spaces to the right
for x in range(self.grid_position[0] + 1, grid.columns):
# Position to check
position = (x, self.grid_position[1])
# If there is nothing in the space it is available
if grid.board_layout[position[1]][position[0]] is None:
available_spaces[position[1]][position[0]] = True
# If there is a piece of the opposite colour in the space it is available, but further spaces are not
elif grid.board_layout[position[1]][position[0]]['colour'] != self.colour:
available_spaces[position[1]][position[0]] = True
break
# If there is a piece of the same colour in the space it is not available, neither are further spaces
else:
break
# Check spaces to the left
for x in range(self.grid_position[0] - 1, -1, -1):
# Position to check
position = (x, self.grid_position[1])
# If there is nothing in the space it is available
if grid.board_layout[position[1]][position[0]] is None:
available_spaces[position[1]][position[0]] = True
# If there is a piece of the opposite colour in the space it is available, but further spaces are not
elif grid.board_layout[position[1]][position[0]]['colour'] != self.colour:
available_spaces[position[1]][position[0]] = True
break
# If there is a piece of the same colour in the space it is not available, neither are further spaces
else:
break
# Check spaces below
for y in range(self.grid_position[1] + 1, grid.rows):
# Position to check
position = (self.grid_position[0], y)
# If there is nothing in the space it is available
if grid.board_layout[position[1]][position[0]] is None:
available_spaces[position[1]][position[0]] = True
# If there is a piece of the opposite colour in the space it is available, but further spaces are not
elif grid.board_layout[position[1]][position[0]]['colour'] != self.colour:
available_spaces[position[1]][position[0]] = True
break
# If there is a piece of the same colour in the space it is not available, neither are further spaces
else:
break
# Check spaces above
for y in range(self.grid_position[1] - 1, -1, -1):
# Position to check
position = (self.grid_position[0], y)
# If there is nothing in the space it is available
if grid.board_layout[position[1]][position[0]] is None:
available_spaces[position[1]][position[0]] = True
# If there is a piece of the opposite colour in the space it is available, but further spaces are not
elif grid.board_layout[position[1]][position[0]]['colour'] != self.colour:
available_spaces[position[1]][position[0]] = True
break
# If there is a piece of the same colour in the space it is not available, neither are further spaces
else:
break
return available_spaces
So is there any way that I can make this more simple, by perhaps using another method to test what is in each grid space? I'm just not sure how to go about implementing something like that.
Thank you for your help.
Variable definitions:
The
grid
variable is just a class which contains information on the current layout of the board and is responsible for drawing the pieces in the correct locations.grid.rows
andgrid.columns
are integers containing the dimensions of the board.grid.board_layout
is an array containing a dictionary of the form{'piece': 'rook', 'colour': 'white'}
where there is a piece and containingNone
where there isn't.Rook.grid_position
is a tuple containing the grid coordinates of the piece.