-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathCannon.py
113 lines (99 loc) · 4.82 KB
/
Cannon.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
from MasterPiece import MasterPiece
class Cannon(MasterPiece):
"""
Represents a cannon piece. Inherits from MasterPiece. Will be instantiated in the Game class and contained
in the Board class.
"""
def __init__(self, color: str, name: str, type: str, location: tuple):
"""
Uses MasterPiece method to initialize the piece.
"""
super().__init__(color, name, type, location)
def valid_move(self, next_loc: tuple) -> bool:
"""
Returns whether or not the piece can move from the current location to the next location. Only
handles whether the space can be moved to by movement rules of the piece. Does not handle
whether the space is occupied, etc.
param next_loc: space to move to
return: True if space is within reach, else False
"""
cur_loc = self._location
# any strictly horizontal or vertical moves are legal
if (cur_loc[0] - next_loc[0] == 0 and abs(cur_loc[1] - next_loc[1]) > 1) \
or (cur_loc[1] - next_loc[1] == 0 and abs(cur_loc[0] - next_loc[0]) > 1):
return True
blue_palace_x = [(7, 3), (7, 5), (9, 3), (9, 5)]
red_palace_x = [(0, 3), (0, 5), (2, 3), (2, 5)]
if (cur_loc in blue_palace_x and next_loc in blue_palace_x) or (cur_loc in red_palace_x \
and next_loc in red_palace_x):
return True
return False
def is_blocked(self, next_loc: tuple, board) -> bool:
"""
Determines whether a piece is blocked from moving to it's desired location. Does not take in to account
if the space is a valid move for the piece.
param next_loc: desired move-to location of the piece
param board: the current game board
return: True if piece is blocked, else False
"""
if board.get_piece(next_loc) is not None and board.get_piece(next_loc).get_color() == self._color:
return True
# cannot capture another cannon
elif board.get_piece(next_loc) is not None and board.get_piece(next_loc).get_type() == 'cannon':
return True
cur_loc = self._location
# set up counter to count pieces between spaces
counter = 0
# loop through each space and check for occupation
# if occupied by a cannon we can stop, the piece is blocked
# otherwise increment the counter
# when counter is 1 piece can be moved, otherwise False
# check horizontal movements
if cur_loc[0] == next_loc[0]:
# increment or decrement value and check each space for occupation
if cur_loc[1] < next_loc[1]:
cur_loc = (cur_loc[0], cur_loc[1] + 1)
else:
cur_loc = (cur_loc[0], cur_loc[1] - 1)
while cur_loc[1] != next_loc[1]:
if board.get_piece(cur_loc) is not None and board.get_piece(cur_loc).get_type() == 'cannon':
return True
elif board.get_piece(cur_loc) is not None:
counter += 1
if cur_loc[1] < next_loc[1]:
cur_loc = (cur_loc[0], cur_loc[1] + 1)
else:
cur_loc = (cur_loc[0], cur_loc[1] - 1)
if counter == 1:
return False
return True
# check vertical movements
if cur_loc[1] == next_loc[1]:
# increment or decrement value and check each space for occupation
if cur_loc[0] < next_loc[0]:
cur_loc = (cur_loc[0] + 1, cur_loc[1])
else:
cur_loc = (cur_loc[0] - 1, cur_loc[1])
while cur_loc[0] != next_loc[0]:
if board.get_piece(cur_loc) is not None and board.get_piece(cur_loc).get_type() == 'cannon':
return True
elif board.get_piece(cur_loc) is not None:
counter += 1
if cur_loc[0] < next_loc[0]:
cur_loc = (cur_loc[0] + 1, cur_loc[1])
else:
cur_loc = (cur_loc[0] - 1, cur_loc[1])
if counter == 1:
return False
return True
blue_palace_x = [(7, 3), (7, 5), (9, 3), (9, 5)]
red_palace_x = [(0, 3), (0, 5), (2, 3), (2, 5)]
# handle traversing the palace diagonals
# can jump over occupied center space so long as it isn't occupied by cannon
if cur_loc in red_palace_x and next_loc in red_palace_x and board.get_piece((1, 4)) is not None \
and board.get_piece((1, 4)).get_type() != 'cannon':
return False
if cur_loc in blue_palace_x and next_loc in blue_palace_x and board.get_piece((8, 4)) is not None \
and board.get_piece((8, 4)).get_type() != 'cannon':
return False
return True