From 88103181a95bbcdb0d729f0a9ee8a249855fa2ae Mon Sep 17 00:00:00 2001 From: hamidrezakamkari Date: Sat, 18 Jan 2020 16:42:29 +0330 Subject: [PATCH 01/10] some of the interface function moved from game to world --- AI.py | 2 + controller.py | 1 - game.py | 191 ------------------------------------- network.py | 1 - world.py | 254 +++++++++++++++++++++++++++++++++----------------- 5 files changed, 172 insertions(+), 277 deletions(-) diff --git a/AI.py b/AI.py index f5c1f31..d75be81 100644 --- a/AI.py +++ b/AI.py @@ -3,6 +3,8 @@ class AI: def pick(self, world): print("pick") world.choose_deck([1, 2, 3 , 4]) + print("this is the position") + print(world.get_player_position(world.get_my_id()).row) def turn(self, world): print("turn") diff --git a/controller.py b/controller.py index a1a490c..d940fef 100644 --- a/controller.py +++ b/controller.py @@ -26,7 +26,6 @@ def __init__(self): # change with switcher def handle_message(self, message): - print("got message") if message[ServerConstants.KEY_TYPE] == ServerConstants.MESSAGE_TYPE_INIT: self.world._handle_init_message(message[ServerConstants.KEY_INFO]) new_world = World(world=self.world) diff --git a/game.py b/game.py index 8726d95..70750da 100644 --- a/game.py +++ b/game.py @@ -5,197 +5,6 @@ class Game(World): - # in the first turn 'deck picking' give unit_ids or list of unit names to pick in that turn - - def choose_deck(self, type_ids=None, base_units=None): - print("----------GI---------------") - message = Message(type="pick", turn=self.get_current_turn(), info=None) - if type_ids is not None: - message.info = {"units" : type_ids} - elif base_units is not None: - message.info = {"units": [unit.type_id for unit in base_units]} - print(message.__dict__) - return message - - def get_my_id(self): - return self.player.player_id - - def get_friend_id(self): - return self.player_friend.player_id - - def get_friend_by_id(self, player_id): - if self.player.player_id == player_id: - return self.player_friend - elif self.player_friend.player_id == player_id: - return self.player - elif self.player_first_enemy.player_id == player_id: - return self.player_second_enemy - elif self.player_second_enemy.player_id == player_id: - return self.player_first_enemy - else: - return None - - def get_first_enemy_id(self): - return self.player_first_enemy.player_id - - def get_second_enemy_id(self): - return self.player_second_enemy.player_id - - # returns a cell that is the fortress of player with player_id - def get_player_position(self, player_id): - player = self.get_player_by_id(player_id) - if player is not None: - return player.king.center - - # return a list of paths starting from the fortress of player with player_id - # the beginning is from player_id fortress cell - def get_paths_from_player(self, player_id): - paths = [] - player_king_cell = self.get_player_position(player_id) - for p in self.map.paths: - first_cell = p.cells[0] - last_cell = p.cells[len(p.cells) - 1] - if first_cell == player_king_cell: - paths.append(p) - continue - if last_cell == player_king_cell: - p.cells.reverse() - paths.append(p) - continue - - # returns the path from player_id to its friend beginning from player_id's fortress - def get_path_to_friend(self, player_id): - player_king_cell = self.get_player_position(player_id) - friend_king_cell = self.get_player_position(self.get_friend_by_id(player_id)) - for p in self.map.paths: - first_cell = p.cells[0] - last_cell = p.cells[len(p.cells) - 1] - if first_cell == player_king_cell and last_cell == friend_king_cell: - return p - if last_cell == player_king_cell and first_cell == friend_king_cell: - p.cells.reverse() - return p - - def get_map_row_num(self): - return self.map.row_count - - def get_map_col_num(self): - return self.map.column_count - - # return a list of paths crossing one cell - def get_paths_crossing_cell(self, cell=None, row=None, col=None): - if cell is None: - if row is None or col is None: - return - cell = Cell(row, col) - - paths = [] - for p in self.map.paths: - if cell in p.cells: - paths.append(p) - return paths - - # return units of player that are currently in map - def get_player_units(self, player_id): - player = self.get_player_by_id(player_id) - return player.units - - # return a list of units in a cell - def get_cell_units(self, cell): - return cell.units - - # return the shortest path from player_id fortress to cell - # this path is in the available path list - # path may cross from friend - def get_shortest_path_to_cell(self, player_id, cell=None, row=None, col=None): - if cell is None: - if row is None or col is None: - return - cell = Cell(row, col) - - shortest_path_to_cell = self.shortest_path.get(player_id) - if shortest_path_to_cell[cell.row][cell.col] == -1: - return None - return shortest_path_to_cell[cell.row][cell.col] - - # returns the limit of ap for each player - def get_max_ap(self): - return self.game_constants.max_ap - - # get remaining ap - def get_remaining_ap(self): - return self.player.ap - - # returns a list of units in hand - def get_hand(self): - return self.player.hand - - # returns a list of units in deck - def get_deck(self): - return self.player.deck - - # place unit with type_id in path_id - def put_unit(self, type_id=None, path_id=None, base_unit=None, path=None): - if base_unit is not None: - type_id = base_unit.type_id - if path is not None: - path_id = path.path_id - if path_id is None or type_id is None: - return - e = Event("putUnit", [type_id, path_id]) - self.queue.put(e) - - # return the number of turns passed - def get_current_turn(self): - return self.current_turn - - # return the limit of turns - def get_max_turns(self): - return self.game_constants.max_turns - - # return the time left to pick units and put in deck in the first turn - def get_pick_timeout(self): - return self.game_constants.pick_timeout - - # a constant limit for each turn - def get_turn_timeout(self): - return self.game_constants.turn_timeout - - # returns the time left for turn (miliseconds) - def get_remaining_time(self, ): - return self.get_turn_timeout() - self.get_time_past() - - # returns the health point remaining for each player - def get_player_hp(self, player_id): - player = self.get_player_by_id(player_id) - return player.king.hp - - # put unit_id in path_id in position 'index' all spells of one kind have the same id - def cast_unit_spell(self, unit_id, path_id, index, spell=None, spell_id=None): - path = None - for p in self.map.paths: - if p.path_id == path_id: - path = p - break - cell = path.cells[index] - if spell is None: - spell = self.get_spell_by_type_id(spell_id) - e = Message(type="castSpell", turn=self.get_current_turn() - , info=[spell.type, [cell.row, cell.col], unit_id, path_id]) - self.queue.put(e) - - # cast spell in the cell 'center' - def cast_area_spell(self, center=None, row=None, col=None, spell=None, spell_id=None): - if spell is None: - spell = self.get_spell_by_type_id(spell_id) - if row is not None and col is not None: - e = Message(type="castSpell", turn=self.get_current_turn() - , info=[spell.type, [row, col], -1, -1]) - self.queue.put(e) - elif center is not None: - e = Message(type="castSpell", turn=self.get_current_turn() - , info=[spell.type, [center.row, center.col], -1, -1]) - self.queue.put(e) # returns a list of units the spell casts effects on def get_area_spell_targets(self, center, row=None, col=None, spell=None, spell_id=None): diff --git a/network.py b/network.py index ef6fb50..ee7d753 100644 --- a/network.py +++ b/network.py @@ -53,7 +53,6 @@ def send(self, message): def receive(self): while self.receive_flag: - # print("received") self.result += self.s.recv(1024) if b'\x00' in self.result: ans = json.loads(self.result[:self.result.index(b'\x00')].decode('UTF-8')) diff --git a/world.py b/world.py index 9d6bbb4..c3aaf2b 100644 --- a/world.py +++ b/world.py @@ -258,134 +258,220 @@ def choose_deck(self, type_ids=None, base_units=None): self.queue.put(message) def get_my_id(self): - pass + return self.player.player_id def get_friend_id(self): - pass + return self.player_friend.player_id + + def get_friend_by_id(self, player_id): + if self.player.player_id == player_id: + return self.player_friend + elif self.player_friend.player_id == player_id: + return self.player + elif self.player_first_enemy.player_id == player_id: + return self.player_second_enemy + elif self.player_second_enemy.player_id == player_id: + return self.player_first_enemy + else: + return None def get_first_enemy_id(self): - pass + return self.player_first_enemy.player_id def get_second_enemy_id(self): - pass - - # returns a cell that is the fortress of player with player_id + return self.player_second_enemy.player_id + # returns a cell that is the fortress of player with player_id def get_player_position(self, player_id): - pass - - # return a list of paths starting from the fortress of player with player_id - # the beginning is from player_id fortress cell + player = self.get_player_by_id(player_id) + if player is not None: + return player.king.center + # return a list of paths starting from the fortress of player with player_id + # the beginning is from player_id fortress cell def get_paths_from_player(self, player_id): - pass - - # returns the path from player_id to its friend beginning from player_id's fortress - + paths = [] + player_king_cell = self.get_player_position(player_id) + for p in self.map.paths: + first_cell = p.cells[0] + last_cell = p.cells[len(p.cells) - 1] + if first_cell == player_king_cell: + paths.append(p) + continue + if last_cell == player_king_cell: + p.cells.reverse() + paths.append(p) + continue + return paths + + # returns the path from player_id to its friend beginning from player_id's fortress def get_path_to_friend(self, player_id): - pass - - def get_map_height(self): - pass - - def get_map_width(self): - pass - + player_king_cell = self.get_player_position(player_id) + friend_king_cell = self.get_player_position(self.get_friend_by_id(player_id)) + for p in self.map.paths: + first_cell = p.cells[0] + last_cell = p.cells[len(p.cells) - 1] + if first_cell == player_king_cell and last_cell == friend_king_cell: + return p + if last_cell == player_king_cell and first_cell == friend_king_cell: + p.cells.reverse() + return p + + def get_map_row_num(self): + return self.map.row_count + + def get_map_col_num(self): + return self.map.column_count # return a list of paths crossing one cell - def get_paths_crossing_cell(self, cell): - pass - - # return units of player that are currently in map - - def get_player_units(self, player_id): - pass - - # return a list of units in a cell - - def get_cell_units(self, cell): - pass - # return the shortest path from player_id fortress to cell - # this path is in the available path list - # path may cross from friend + # return a list of paths crossing one cell + def get_paths_crossing_cell(self, cell=None, row=None, col=None): + if cell is None: + if row is None or col is None: + return + cell = self.map.get_cell(row, col) - def get_shortest_path_to_cell(self, player_id, cell): - pass - - # returns the limit of ap for each player + paths = [] + for p in self.map.paths: + if cell in p.cells: + paths.append(p) + return paths + # return units of player that are currently in map + def get_player_units(self, player_id): + player = self.get_player_by_id(player_id) + return player.units + + # return a list of units in a cell + def get_cell_units(self, cell=None, row=None, col=None): + if cell == None: + if row == None and col == None: + return None + cell = self.map.get_cell(row, col) + return cell.units + + # return the shortest path from player_id fortress to cell + # this path is in the available path list + # path may cross from friend + def get_shortest_path_to_cell(self, player_id, cell=None, row=None, col=None): + if cell is None: + if row is None or col is None: + return + cell = Cell(row, col) + + shortest_path_to_cell = self.shortest_path.get(player_id) + if shortest_path_to_cell[cell.row][cell.col] == -1: + return None + return shortest_path_to_cell[cell.row][cell.col] + + # returns the limit of ap for each player def get_max_ap(self): - pass - - # get remaining ap + return self.game_constants.max_ap + # get remaining ap def get_remaining_ap(self): - pass - - # returns a list of units in hand + return self.player.ap + # returns a list of units in hand def get_hand(self): - pass - - # returns a list of units in deck + return self.player.hand + # returns a list of units in deck def get_deck(self): - pass - - # place unit with type_id in path_id - - def put_unit(self, type_id, path_id): - - pass + return self.player.deck + + # place unit with type_id in path_id + def put_unit(self, type_id=None, path_id=None, base_unit=None, path=None): + if base_unit is not None: + type_id = base_unit.type_id + if path is not None: + path_id = path.path_id + if path_id is None or type_id is None: + return + message = Message(turn=self.get_current_turn(), + type="putUnit", + info={ + "typeId" : type_id, + "pathId" : path_id + }) + self.queue.put(message) - # return the number of turns passed + # return the number of turns passed def get_current_turn(self): return self.current_turn - # return the limit of turns - + # return the limit of turns def get_max_turns(self): - pass - - # return the time left to pick units and put in deck in the first turn + return self.game_constants.max_turns + # return the time left to pick units and put in deck in the first turn def get_pick_timeout(self): - pass - - # a constant limit for each turn + return self.game_constants.pick_timeout + # a constant limit for each turn def get_turn_timeout(self): - pass - - # returns the time left for turn (miliseconds) + return self.game_constants.turn_timeout + # returns the time left for turn (miliseconds) def get_remaining_time(self): - pass - - # returns the health point remaining for each player + return self.get_turn_timeout() - self.get_time_past() + # returns the health point remaining for each player def get_player_hp(self, player_id): - pass + player = self.get_player_by_id(player_id) + return player.king.hp - # put unit_id in path_id in position 'index' all spells of one kind have the same id + # put unit_id in path_id in position 'index' all spells of one kind have the same id def cast_unit_spell(self, unit_id, path_id, index, spell=None, spell_id=None): - pass - - # cast spell in the cell 'center' - - def cast_area_spell(self, center, row=None, col=None, spell=None, spell_id=None): - pass - - # returns a list of units the spell casts effects on + path = None + for p in self.map.paths: + if p.path_id == path_id: + path = p + break + cell = path.cells[index] + if spell is None: + spell = self.get_spell_by_type_id(spell_id) + message = Message(type="castSpell", turn=self.get_current_turn(), + info={ + "typeId" : spell.type, + "cell" : { + "row" : cell.row, + "col" : cell.col + }, + "unitId" : unit_id, + "pathId" : path_id + }) + self.queue.put(message) + # cast spell in the cell 'center' + def cast_area_spell(self, center=None, row=None, col=None, spell=None, spell_id=None): + if spell is None: + spell = self.get_spell_by_type_id(spell_id) + if row is not None and col is not None: + center = self.map.get_cell(row, col) + + if center is not None: + message = Message(type="castSpell", + turn=self.get_current_turn(), + info={ + "typeId" : spell.type, + "cell" : { + "row" : center.row, + "col" : center.col + }, + "unitId" : -1, + "pathId" : -1 + }) + self.queue.put(message) + + # returns a list of units the spell casts effects on def get_area_spell_targets(self, center, row=None, col=None, spell=None, spell_id=None): pass - # every once in a while you can upgrade, this returns the remaining time for upgrade - + # every once in a while you can upgrade, this returns the remaining time for upgrade def get_remaining_turns_to_upgrade(self): pass From 74845d8f08d79e93157491d0ce213bbd8981a1f8 Mon Sep 17 00:00:00 2001 From: hamidrezakamkari Date: Sat, 18 Jan 2020 17:10:59 +0330 Subject: [PATCH 02/10] game deleted and all functions moved to world --- game.py | 166 -------------------------------------------------- world.py | 180 ++++++++++++++++++++++++++++++++++++++++++------------- 2 files changed, 140 insertions(+), 206 deletions(-) delete mode 100644 game.py diff --git a/game.py b/game.py deleted file mode 100644 index 70750da..0000000 --- a/game.py +++ /dev/null @@ -1,166 +0,0 @@ -import copy - -from model import CastUnitSpell, CastAreaSpell, Message, Cell -from world import World - - -class Game(World): - - # returns a list of units the spell casts effects on - def get_area_spell_targets(self, center, row=None, col=None, spell=None, spell_id=None): - if spell is None: - if spell_id is not None: - spell = self.get_cast_spell_by_type(spell_id) - if center is not None: - pass - - # every once in a while you can upgrade, this returns the remaining time for upgrade - def get_remaining_turns_to_upgrade(self): - return self.game_constants.turns_to_upgrade - - # every once in a while a spell is given this remains the remaining time to get new spell - def get_remaining_turns_to_get_spell(self): - return self.game_constants.turns_to_spell - - # returns area spells that are casted in last turn and returns other players spells also - def get_cast_area_spell(self, player_id): - return [cast_spell_i for cast_spell_i in self.cast_spell.values() - if cast_spell_i.caster_id and isinstance(cast_spell_i, CastAreaSpell)] - - # returns unit spells that are casted in last turn and returns other players spells also - def get_cast_unit_spell(self, player_id): - return [cast_spell_i for cast_spell_i in self.cast_spell.values() - if cast_spell_i.caster_id and isinstance(cast_spell_i, CastUnitSpell)] - - def get_cast_spells_on_unit(self, unit=None, unit_id=None): - pass - - # def get_active_poisons_on_unit(self, unit_id=None, unit=None): - # temp_unit = unit - # if unit_id is not None: - # temp_unit = self.get_unit_by_id(unit_id) - # if isinstance(temp_unit, Unit): - # return temp_unit.active_poisons - # return None - - # returns a list of spells casted on a cell - def get_range_upgrade_number(self, player_id): - return self.turn_updates.available_range_upgrade - - def get_damage_upgrade_number(self, player_id): - return self.turn_updates.available_damage_upgrade - - def get_spells_list(self): - return self.player.spells - - # get current available spells as a dictionary - def get_spells(self): - return_dict = dict() - for spell in self.player.spells: - if spell in return_dict: - return_dict[spell] += 1 - else: - return_dict[spell] = 1 - return return_dict - - # returns the spell given in that turn - def get_received_spell(self): - spell_type_id = self.turn_updates.received_spell - if spell_type_id == -1: - return None - else: - return self.get_spell_by_type_id(spell_type_id) - - # returns the spell given in that turn to friend - def get_friend_received_spell(self): - spell_type_id = self.turn_updates.friend_received_spell - if spell_type_id == -1: - return None - else: - return self.get_spell_by_type_id(spell_type_id) - - def upgrade_unit_range(self, unit=None, unit_id=None): - if unit is not None: - self.queue.put(Message(type="rangeUpgrade", turn=self.get_current_turn() - , info=[unit.unit_id])) - elif unit_id is not None: - self.queue.put(Message(type="rangeUpgrade", turn=self.get_current_turn() - , info=unit_id)) - - def upgrade_unit_damage(self, unit=None, unit_id=None): - if unit is not None: - self.queue.put(Message(type="damageUpgrade", turn=self.get_current_turn(), info={ - "unitId": unit.unit_id - })) - elif unit_id is not None: - self.queue.put(Message(type="damageUpgrade", turn=self.get_current_turn(), info={ - "unitId": unit.unit_id - })) - - def get_player_duplicate_unit(self, player_id): - unit_list = [] - for u in self.get_player_by_id(player_id).units: - if u.is_clone: - unit_list.append(u) - return unit_list - - def get_player_hasted_units(self, player_id): - return [unit for unit in self.get_player_by_id(player_id=player_id).units if unit.is_hasted > 0] - - def get_player_played_units(self, player_id): - return [unit for unit in self.get_player_by_id(player_id=player_id).units if unit.was_played_this_turn] - - def get_unit_target(self, unit=None, unit_id=None): - if unit_id is None: - if unit is None: - return None - unit_id = unit.unit_id - - target_id = self.get_unit_by_id(unit_id).target_id - unit = self.get_unit_by_id(target_id) - return unit - - def get_unit_target_cell(self, unit=None, unit_id=None): - if unit_id is None: - if unit is None: - return None - unit_id = unit.unit_id - - target_id = self.get_unit_by_id(unit_id).target_id - cell = self.get_unit_by_id(unit_id).target_cell - unit = self.get_unit_by_id(target_id) - if unit is None: - return None - - return cell - - def get_king_target(self, player_id): - king = self.get_player_by_id(player_id).king - return self.get_unit_by_id(king.target_id) - - def get_king_target_cell(self, player_id): - king = self.get_player_by_id(player_id).king - return king.target_cell - - def get_king_unit_is_attacking_to(self, unit=None, unit_id=None): - if unit is not None: - unit_id = unit.unit_id - unit = self.get_unit_by_id(unit_id) - for p in self.players: - if unit.target_id == p.player_id: - return p.player_id - return -1 - - def get_all_base_unit(self): - return copy.deepcopy(self.base_units) - - def get_all_spells(self): - return copy.deepcopy(self.spells) - -# def get_player_clone_units(self, player_id): -# return [unit for unit in self.get_player_by_id(player_id=player_id) if unit.is_clone > 0] -# - -# def get_player_poisoned_units(self, player_id): -# return [unit for unit in self.get_player_by_id(player_id=player_id) if unit.active_poisons > 0] -# diff --git a/world.py b/world.py index c3aaf2b..579380e 100644 --- a/world.py +++ b/world.py @@ -1,3 +1,4 @@ +import copy import time from abc import ABC @@ -468,76 +469,175 @@ def cast_area_spell(self, center=None, row=None, col=None, spell=None, spell_id= self.queue.put(message) # returns a list of units the spell casts effects on + # + # + # + # + # NOT COMPLETE: + # + # + # + # def get_area_spell_targets(self, center, row=None, col=None, spell=None, spell_id=None): + if spell is None: + if spell_id is not None: + spell = self.get_cast_spell_by_type(spell_id) + if center is not None: + pass + + def get_cast_spells_on_unit(self, unit=None, unit_id=None): pass + # + # + # + # + # + # + # + # + # + # every once in a while you can upgrade, this returns the remaining time for upgrade def get_remaining_turns_to_upgrade(self): - pass - - # every once in a while a spell is given this remains the remaining time to get new spell + return self.game_constants.turns_to_upgrade + # every once in a while a spell is given this remains the remaining time to get new spell def get_remaining_turns_to_get_spell(self): - pass - - # returns area spells that are casted in last turn and returns other players spells also + return self.game_constants.turns_to_spell + # returns area spells that are casted in last turn and returns other players spells also def get_cast_area_spell(self, player_id): - pass - - # returns unit spells that are casted in last turn and returns other players spells also + return [cast_spell_i for cast_spell_i in self.cast_spells + if cast_spell_i.caster_id and isinstance(cast_spell_i, CastAreaSpell)] + # returns unit spells that are casted in last turn and returns other players spells also def get_cast_unit_spell(self, player_id): - pass - - def get_active_poisons_on_unit(self, unit_id=None, unit=None): - pass - - # returns a list of spells casted on a cell + return [cast_spell_i for cast_spell_i in self.cast_spells + if cast_spell_i.caster_id and isinstance(cast_spell_i, CastUnitSpell)] + # returns a list of spells casted on a cell def get_range_upgrade_number(self, player_id): - pass + return self.turn_updates.available_range_upgrade def get_damage_upgrade_number(self, player_id): - pass - - # returns the token of the upgrade you can do - - def get_upgrade_token_number(self): - pass + return self.turn_updates.available_damage_upgrade def get_spells_list(self): - pass - - # get current available spells + return self.player.spells + # get current available spells as a dictionary def get_spells(self): - pass - - # returns the spell given in that turn - + return_dict = dict() + for spell in self.player.spells: + if spell in return_dict: + return_dict[spell] += 1 + else: + return_dict[spell] = 1 + return return_dict + + # returns the spell given in that turn def get_received_spell(self): - pass - - # returns the spell given in that turn to friend + spell_type_id = self.turn_updates.received_spell + if spell_type_id == -1: + return None + else: + return self.get_spell_by_type_id(spell_type_id) + # returns the spell given in that turn to friend def get_friend_received_spell(self): - pass + spell_type_id = self.turn_updates.friend_received_spell + if spell_type_id == -1: + return None + else: + return self.get_spell_by_type_id(spell_type_id) def upgrade_unit_range(self, unit=None, unit_id=None): - pass + if unit is not None: + unit_id = unit.unit_id + + elif unit_id is not None: + self.queue.put(Message(type="rangeUpgrade", + turn=self.get_current_turn(), + info={ + "unitId": unit_id + })) def upgrade_unit_damage(self, unit=None, unit_id=None): - pass + if unit is not None: + unit_id = unit.unit_id + + elif unit_id is not None: + self.queue.put(Message(type="damageUpgrade", + turn=self.get_current_turn(), + info={ + "unitId": unit_id + })) + + def get_player_duplicate_unit(self, player_id): + unit_list = [] + for u in self.get_player_by_id(player_id).units: + if u.is_clone: + unit_list.append(u) + return unit_list - def get_player_clone_units(self, player_id): - pass def get_player_hasted_units(self, player_id): - pass + return [unit for unit in self.get_player_by_id(player_id=player_id).units if unit.is_hasted > 0] - def get_player_poisoned_units(self, player_id): + def get_player_played_units(self, player_id): + return [unit for unit in self.get_player_by_id(player_id=player_id).units if unit.was_played_this_turn] + + def get_unit_target(self, unit=None, unit_id=None): + if unit_id is None: + if unit is None: + return None + unit_id = unit.unit_id + + target_id = self.get_unit_by_id(unit_id).target_id + unit = self.get_unit_by_id(target_id) + return unit + + def get_unit_target_cell(self, unit=None, unit_id=None): + if unit_id is None: + if unit is None: + return None + unit_id = unit.unit_id + + target_id = self.get_unit_by_id(unit_id).target_id + cell = self.get_unit_by_id(unit_id).target_cell + unit = self.get_unit_by_id(target_id) + if unit is None: + return None + + return cell + + def get_king_target(self, player_id): + king = self.get_player_by_id(player_id).king + return self.get_unit_by_id(king.target_id) + + def get_king_target_cell(self, player_id): + king = self.get_player_by_id(player_id).king + return king.target_cell + + def get_king_unit_is_attacking_to(self, unit=None, unit_id=None): + if unit is not None: + unit_id = unit.unit_id + unit = self.get_unit_by_id(unit_id) + for p in self.players: + if unit.target_id == p.player_id: + return p.player_id + return -1 + + def get_all_base_unit(self): + return copy.deepcopy(self.base_units) + + def get_all_spells(self): + return copy.deepcopy(self.spells) + + def get_player_clone_units(self, player_id): pass - def get_player_played_units(self, player_id): + + def get_player_poisoned_units(self, player_id): pass From 061a1ab52ea3a51041a45c8cb5fc121067147fc7 Mon Sep 17 00:00:00 2001 From: hamidrezakamkari Date: Sat, 18 Jan 2020 18:26:03 +0330 Subject: [PATCH 03/10] get path to friend debugged! --- AI.py | 9 +++++++-- model.py | 44 ++++++++++++++++++++------------------------ world.py | 19 ++++++++----------- 3 files changed, 35 insertions(+), 37 deletions(-) diff --git a/AI.py b/AI.py index d75be81..2ace1ea 100644 --- a/AI.py +++ b/AI.py @@ -3,8 +3,13 @@ class AI: def pick(self, world): print("pick") world.choose_deck([1, 2, 3 , 4]) - print("this is the position") - print(world.get_player_position(world.get_my_id()).row) + print(world.get_player_by_id(world.get_my_id())) + print(world.get_player_by_id(world.get_friend_id())) + for p in world.map.paths: + print(p) + print("------------") + + print(world.get_path_to_friend(world.get_my_id())) def turn(self, world): print("turn") diff --git a/model.py b/model.py index e61be4a..57df6f6 100644 --- a/model.py +++ b/model.py @@ -2,20 +2,19 @@ class Map: - def __init__(self, row_count, column_count, paths, kings): + def __init__(self, row_count, column_count, paths, kings, cells): self.row_count = row_count self.column_count = column_count self.paths = paths self.units = [] self.kings = kings - self._cells = [[Cell(row=row, col=col) for col in range(column_count)] for row in range(row_count)] + self.cells = cells def get_cell(self, row, column): - return self._cells[row][column] - + return self.cells[row][column] def clear_units(self): - for row in self._cells: + for row in self.cells: for cell in row: cell.clear_units() @@ -26,7 +25,7 @@ def get_path_by_id(self, path_id): return None def add_unit_in_cell(self, row, column, unit): - self._cells[row][column].add_unit(unit) + self.cells[row][column].add_unit(unit) class Player: @@ -40,6 +39,11 @@ def __init__(self, player_id, king): self.king = king self.units = [] + def __str__(self): + return "".format(self.player_id, self.king.center.row, self.king.center.col) + class Unit: def __init__(self, unit_id, base_unit, cell, path, hp, is_hasted, is_clone, damage_level, @@ -64,11 +68,11 @@ def __init__(self, unit_id, base_unit, cell, path, hp, is_hasted, is_clone, dama self.target_cell = target_cell - class SpellTarget(Enum): SELF = 1 ALLIED = 2 ENEMY = 3 + @staticmethod def get_value(string): if string == "SELF": @@ -84,6 +88,7 @@ class SpellType(Enum): TELE = 2 DUPLICATE = 3 HASTE = 4 + @staticmethod def get_value(string): if string == "HP": @@ -126,6 +131,9 @@ def __eq__(self, other): return self.col == other.col and self.row == other.row + def __str__(self): + return "".format(self.row, self.col) + def clear_units(self): self.units.clear() @@ -140,6 +148,11 @@ def __init__(self, path_id=0, cells=None): self.cells = cells self.path_id = path_id + def __str__(self): + return "".format(self.path_id, ["({}, {})".format(cell.row, cell.col) for cell in self.cells]) + class Deck: def __init__(self): @@ -165,29 +178,12 @@ def __init__(self, target_id, center=None, hp=0, attack=0, range=0): self.range = range self.target_id = target_id -# -# class AreaSpell(Spell): -# def __init__(self, type_id, turn_effect, range, power, is_damaging): -# super().__init__(type_id=type_id, turn_effect=turn_effect) -# self.range = range -# self.power = power -# self.is_damaging = is_damaging -# -# -# class UnitSpell(Spell): -# def __init__(self, type_id, turn_effect): -# super().__init__(type_id=type_id, turn_effect=turn_effect) -# class Message: - def __init__(self, turn, type, info): self.type = type self.info = info self.turn = turn - # - # def add_arg(self, arg): - # self.args.append(arg) class CastSpell: diff --git a/world.py b/world.py index 579380e..2360894 100644 --- a/world.py +++ b/world.py @@ -85,9 +85,12 @@ def _game_constant_init(self, game_constants_msg): def _map_init(self, map_msg): row_num = map_msg["rows"] col_num = map_msg["cols"] - paths = [Path(path["id"], [Cell(cell["row"], cell["col"]) for cell in path["cells"]] + + input_cells = [[Cell(row=row, col=col) for col in range(col_num)] for row in range(row_num)] + + paths = [Path(path["id"], [input_cells[cell["row"]][cell["col"]] for cell in path["cells"]] ) for path in map_msg["paths"]] - kings = [King(center=Cell(king["center"]["row"], king["center"]["col"]), hp=king["hp"], + kings = [King(center=input_cells[king["center"]["row"]][king["center"]["col"]], hp=king["hp"], attack=king["attack"], range=king["range"], target_id=-1) for king in map_msg["kings"]] self.players = [Player(player_id=map_msg["kings"][i]["playerId"], king=kings[i]) for i in range(4)] @@ -95,7 +98,7 @@ def _map_init(self, map_msg): self.player_friend = self.players[1] self.player_first_enemy = self.players[2] self.player_second_enemy = self.players[3] - self.map = Map(row_count=row_num, column_count=col_num, paths=paths, kings=kings) + self.map = Map(row_count=row_num, column_count=col_num, paths=paths, kings=kings, cells=input_cells) def get_unit_by_id(self, unit_id): for unit in self.map.units: @@ -308,7 +311,8 @@ def get_paths_from_player(self, player_id): # returns the path from player_id to its friend beginning from player_id's fortress def get_path_to_friend(self, player_id): player_king_cell = self.get_player_position(player_id) - friend_king_cell = self.get_player_position(self.get_friend_by_id(player_id)) + friend_king_cell = self.get_friend_by_id(player_id).king.center + for p in self.map.paths: first_cell = p.cells[0] last_cell = p.cells[len(p.cells) - 1] @@ -634,10 +638,3 @@ def get_all_base_unit(self): def get_all_spells(self): return copy.deepcopy(self.spells) - - def get_player_clone_units(self, player_id): - pass - - - def get_player_poisoned_units(self, player_id): - pass From 7966120994831167ed96db787a4cfdd3257cf56d Mon Sep 17 00:00:00 2001 From: hamidrezakamkari Date: Sat, 18 Jan 2020 18:31:16 +0330 Subject: [PATCH 04/10] debugged get shortest path to cell --- world.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/world.py b/world.py index 2360894..1a64a0e 100644 --- a/world.py +++ b/world.py @@ -363,7 +363,7 @@ def get_shortest_path_to_cell(self, player_id, cell=None, row=None, col=None): if cell is None: if row is None or col is None: return - cell = Cell(row, col) + cell = self.map.get_cell(row, col) shortest_path_to_cell = self.shortest_path.get(player_id) if shortest_path_to_cell[cell.row][cell.col] == -1: From 7dd7d37f5ac9398e164a3621334e73369f79eabb Mon Sep 17 00:00:00 2001 From: ErfanFaravani Date: Mon, 20 Jan 2020 15:02:44 +0330 Subject: [PATCH 05/10] get area spell target is added --- AI.py | 2 +- controller.py | 2 -- model.py | 1 + network.py | 2 +- world.py | 89 +++++++++++++++++++++++++++------------------------ 5 files changed, 51 insertions(+), 45 deletions(-) diff --git a/AI.py b/AI.py index 2ace1ea..a8ea284 100644 --- a/AI.py +++ b/AI.py @@ -2,7 +2,7 @@ class AI: def pick(self, world): print("pick") - world.choose_deck([1, 2, 3 , 4]) + world.choose_deck([1, 2, 3, 4]) print(world.get_player_by_id(world.get_my_id())) print(world.get_player_by_id(world.get_friend_id())) for p in world.map.paths: diff --git a/controller.py b/controller.py index d940fef..3cfe65b 100644 --- a/controller.py +++ b/controller.py @@ -1,4 +1,3 @@ -import json import os import sys import threading @@ -64,7 +63,6 @@ def run(): World.LOG_FILE_POINTER.write('------send message to server-----\n ' + message.__str__()) self.network.send(message) - Thread(target=run, daemon=True).start() def read_settings(self): diff --git a/model.py b/model.py index 57df6f6..ffa41af 100644 --- a/model.py +++ b/model.py @@ -83,6 +83,7 @@ def get_value(string): return SpellTarget.ENEMY return None + class SpellType(Enum): HP = 1 TELE = 2 diff --git a/network.py b/network.py index ee7d753..be9d793 100644 --- a/network.py +++ b/network.py @@ -27,7 +27,7 @@ def connect(self): connected = True self.send(Message(type=ServerConstants.CONFIG_KEY_TOKEN, turn=0, - info={ServerConstants.CONFIG_KEY_TOKEN:self.token} + info={ServerConstants.CONFIG_KEY_TOKEN: self.token} )) init = self.receive() if init[ServerConstants.KEY_TYPE] == "wrong token": diff --git a/world.py b/world.py index 1a64a0e..4f48903 100644 --- a/world.py +++ b/world.py @@ -190,11 +190,11 @@ def _handle_turn_cast_spells(self, msg): affected_units=affected_units)) elif cast_spell.is_unit_spell(): self.cast_spells.append(CastUnitSpell(type_id=cast_spell.type_id, caster_id=cast_spell_msg["casterId"], - target_cell=cell, unit_id=cast_spell_msg["unitId"], - path_id=cast_spell_msg["pathId"], - was_cast_this_turn=cast_spell_msg["wasCastThisTurn"], - remaining_turns=cast_spell_msg["remainingTurns"], - affected_units=affected_units)) + target_cell=cell, unit_id=cast_spell_msg["unitId"], + path_id=cast_spell_msg["pathId"], + was_cast_this_turn=cast_spell_msg["wasCastThisTurn"], + remaining_turns=cast_spell_msg["remainingTurns"], + affected_units=affected_units)) def get_cast_spell_by_type_id(self, type_id): for cast_spell in self.cast_spells: @@ -256,7 +256,7 @@ def path_count(path): def choose_deck(self, type_ids=None, base_units=None): message = Message(type="pick", turn=self.get_current_turn(), info=None) if type_ids is not None: - message.info = {"units" : type_ids} + message.info = {"units": type_ids} elif base_units is not None: message.info = {"units": [unit.type_id for unit in base_units]} self.queue.put(message) @@ -329,7 +329,6 @@ def get_map_col_num(self): return self.map.column_count # return a list of paths crossing one cell - # return a list of paths crossing one cell def get_paths_crossing_cell(self, cell=None, row=None, col=None): if cell is None: @@ -397,12 +396,11 @@ def put_unit(self, type_id=None, path_id=None, base_unit=None, path=None): message = Message(turn=self.get_current_turn(), type="putUnit", info={ - "typeId" : type_id, - "pathId" : path_id + "typeId": type_id, + "pathId": path_id }) self.queue.put(message) - # return the number of turns passed def get_current_turn(self): return self.current_turn @@ -428,7 +426,6 @@ def get_player_hp(self, player_id): player = self.get_player_by_id(player_id) return player.king.hp - # put unit_id in path_id in position 'index' all spells of one kind have the same id def cast_unit_spell(self, unit_id, path_id, index, spell=None, spell_id=None): path = None @@ -441,13 +438,13 @@ def cast_unit_spell(self, unit_id, path_id, index, spell=None, spell_id=None): spell = self.get_spell_by_type_id(spell_id) message = Message(type="castSpell", turn=self.get_current_turn(), info={ - "typeId" : spell.type, - "cell" : { - "row" : cell.row, - "col" : cell.col + "typeId": spell.type, + "cell": { + "row": cell.row, + "col": cell.col }, - "unitId" : unit_id, - "pathId" : path_id + "unitId": unit_id, + "pathId": path_id }) self.queue.put(message) @@ -462,17 +459,45 @@ def cast_area_spell(self, center=None, row=None, col=None, spell=None, spell_id= message = Message(type="castSpell", turn=self.get_current_turn(), info={ - "typeId" : spell.type, - "cell" : { - "row" : center.row, - "col" : center.col + "typeId": spell.type, + "cell": { + "row": center.row, + "col": center.col }, - "unitId" : -1, - "pathId" : -1 + "unitId": -1, + "pathId": -1 }) self.queue.put(message) # returns a list of units the spell casts effects on + def get_area_spell_targets(self, center, row=None, col=None, spell=None, type_id=None): + if spell is None: + if type_id is not None: + spell = self.get_cast_spell_by_type_id(type_id) + if not spell.is_area_spell: + return [] + if center is None: + center = Cell(row, col) + ls = [] + for i in range(max(0, center.row - spell.range), min(center.row + spell.range, self.map.row_count)): + for j in range(max(0, center.col - spell.range), min(center.col + spell.range, self.map.column_count)): + cell = self.map.get_cell(i, j) + for u in cell.units: + if self._is_unit_targeted(u, spell.target): + ls.append(u) + + def _is_unit_targeted(self, unit, spell_target): + if spell_target == 1: + if unit in self.player.units: + return True + elif spell_target == 2: + if unit in self.player_friend or unit in self.player.units: + return True + elif spell_target == 3: + if unit in self.player_first_enemy or unit in self.player_second_enemy: + return True + return False + # # # @@ -482,25 +507,8 @@ def cast_area_spell(self, center=None, row=None, col=None, spell=None, spell_id= # # # - def get_area_spell_targets(self, center, row=None, col=None, spell=None, spell_id=None): - if spell is None: - if spell_id is not None: - spell = self.get_cast_spell_by_type(spell_id) - if center is not None: - pass - def get_cast_spells_on_unit(self, unit=None, unit_id=None): pass - # - # - # - # - # - # - # - # - # - # every once in a while you can upgrade, this returns the remaining time for upgrade def get_remaining_turns_to_upgrade(self): @@ -585,7 +593,6 @@ def get_player_duplicate_unit(self, player_id): unit_list.append(u) return unit_list - def get_player_hasted_units(self, player_id): return [unit for unit in self.get_player_by_id(player_id=player_id).units if unit.is_hasted > 0] From a9efa7fd89663758794d518309065a413c7bbd41 Mon Sep 17 00:00:00 2001 From: hamidrezakamkari Date: Mon, 20 Jan 2020 16:12:15 +0330 Subject: [PATCH 06/10] add dead units --- model.py | 1 + world.py | 21 +++++++++++++++------ 2 files changed, 16 insertions(+), 6 deletions(-) diff --git a/model.py b/model.py index 57df6f6..039919e 100644 --- a/model.py +++ b/model.py @@ -38,6 +38,7 @@ def __init__(self, player_id, king): self.upgrade_tokens = 0 self.king = king self.units = [] + self.dead_units = [] def __str__(self): return " Date: Mon, 20 Jan 2020 19:41:46 +0330 Subject: [PATCH 07/10] v4 added function --- AI.py | 11 ++++------- world.py | 22 ++++++++++++++++++++++ 2 files changed, 26 insertions(+), 7 deletions(-) diff --git a/AI.py b/AI.py index a8ea284..0237baa 100644 --- a/AI.py +++ b/AI.py @@ -3,13 +3,10 @@ class AI: def pick(self, world): print("pick") world.choose_deck([1, 2, 3, 4]) - print(world.get_player_by_id(world.get_my_id())) - print(world.get_player_by_id(world.get_friend_id())) - for p in world.map.paths: - print(p) - print("------------") - - print(world.get_path_to_friend(world.get_my_id())) + for i in world.base_units: + print(i.type_id) + for i in world.spells: + print(i.type_id) def turn(self, world): print("turn") diff --git a/world.py b/world.py index 4f48903..aa4eadb 100644 --- a/world.py +++ b/world.py @@ -645,3 +645,25 @@ def get_all_base_unit(self): def get_all_spells(self): return copy.deepcopy(self.spells) + + def get_spell_by_id(self, spell_id): + for i in self.spells: + if spell_id == i.type_id: + return i + + return None + + def get_base_unit_by_id(self, type_id): + for bu in self.base_units: + if bu.type_id == type_id: + return bu + return None + + def get_player_died_units(self, player_id): + pass + + def has_player_used_ranged_upgrade(self, player_id): + pass + + def has_player_used_damage_upgrade(self, player_id): + pass From a5c8c4885443375b0097925961e0ed7a8fbb5e4e Mon Sep 17 00:00:00 2001 From: ErfanFaravani Date: Mon, 20 Jan 2020 19:52:54 +0330 Subject: [PATCH 08/10] v4 added function --- world.py | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/world.py b/world.py index 9faefd8..4d9af3a 100644 --- a/world.py +++ b/world.py @@ -669,10 +669,14 @@ def get_base_unit_by_id(self, type_id): return None def get_player_died_units(self, player_id): - pass + return self.get_player_by_id(player_id).dead_units def has_player_used_ranged_upgrade(self, player_id): - pass + if self.turn_updates.got_range_upgrade is not None: + return True + return False def has_player_used_damage_upgrade(self, player_id): - pass + if self.turn_updates.got_damage_upgrade is not None: + return True + return False From 64c9430329ff0b9f30478f1e1f2ec554a9d2f6b8 Mon Sep 17 00:00:00 2001 From: ErfanFaravani Date: Tue, 21 Jan 2020 03:10:53 +0330 Subject: [PATCH 09/10] v4 two function left --- AI.py | 5 +---- world.py | 32 ++++++++++++++++++-------------- 2 files changed, 19 insertions(+), 18 deletions(-) diff --git a/AI.py b/AI.py index 0237baa..7038975 100644 --- a/AI.py +++ b/AI.py @@ -3,10 +3,7 @@ class AI: def pick(self, world): print("pick") world.choose_deck([1, 2, 3, 4]) - for i in world.base_units: - print(i.type_id) - for i in world.spells: - print(i.type_id) + print(world.get_shortest_path_to_cell(player_id=world.get_my_id(), row=10, col=10)) def turn(self, world): print("turn") diff --git a/world.py b/world.py index 4d9af3a..2dd0554 100644 --- a/world.py +++ b/world.py @@ -216,7 +216,7 @@ def _handle_turn_message(self, msg): self.player.hand = [self._get_base_unit_by_id(hand_type_id) for hand_type_id in msg["hand"]] self._handle_turn_kings(msg["kings"]) self._handle_turn_units(msg["units"]) - self._handle_turn_units(msg["diedUnits"], is_dead_unit=True) + # self._handle_turn_units(msg["diedUnits"], is_dead_unit=True) self._handle_turn_cast_spells(msg["castSpells"]) self.turn_updates = TurnUpdates(received_spell=msg["receivedSpell"], @@ -231,14 +231,14 @@ def _handle_turn_message(self, msg): self.start_time = self.get_current_time_millis() - def pre_process_shortest_path(self): + def _pre_process_shortest_path(self): def path_count(path): shortest_path_to_cell = [] shortest_path_to_cell_num = [] - for i in range(len(self.map.row_count)): + for i in range(self.map.row_count): l = [] s = [] - for j in range(len(self.map.column_count)): + for j in range(self.map.column_count): l.append(-1) s.append(-1) shortest_path_to_cell.append(l) @@ -368,14 +368,20 @@ def get_cell_units(self, cell=None, row=None, col=None): # this path is in the available path list # path may cross from friend def get_shortest_path_to_cell(self, player_id, cell=None, row=None, col=None): + if len(list(self.shortest_path.values())) == 0: + self._pre_process_shortest_path() + if cell is None: if row is None or col is None: return cell = self.map.get_cell(row, col) shortest_path_to_cell = self.shortest_path.get(player_id) + print(shortest_path_to_cell) + if shortest_path_to_cell[cell.row][cell.col] == -1: return None + return shortest_path_to_cell[cell.row][cell.col] # returns the limit of ap for each player @@ -507,17 +513,15 @@ def _is_unit_targeted(self, unit, spell_target): return True return False - # - # - # - # - # NOT COMPLETE: - # - # - # - # def get_cast_spells_on_unit(self, unit=None, unit_id=None): - pass + ls = [] + if unit_id is None: + unit_id = unit.unit_id + for cast_spell in self.cast_spells: + if cast_spell is isinstance(CastUnitSpell): + if unit_id == cast_spell.unit_id: + ls.append(unit_id) + return ls # every once in a while you can upgrade, this returns the remaining time for upgrade def get_remaining_turns_to_upgrade(self): From c0e965f706532e60534ed8685640713721fca0f1 Mon Sep 17 00:00:00 2001 From: ErfanFaravani Date: Tue, 21 Jan 2020 05:08:48 +0330 Subject: [PATCH 10/10] v4 added function --- AI.py | 10 +++++++++- world.py | 2 -- 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/AI.py b/AI.py index 7038975..3208bf6 100644 --- a/AI.py +++ b/AI.py @@ -1,9 +1,17 @@ +from random import Random + + class AI: def pick(self, world): + self.r = Random() print("pick") world.choose_deck([1, 2, 3, 4]) - print(world.get_shortest_path_to_cell(player_id=world.get_my_id(), row=10, col=10)) + print(world.put_unit(type_id=1, path=world.map.paths[self.r.randint(1, 4)])) + if len(world.player.units) > 0: + print(world.player.units[0].cell) def turn(self, world): print("turn") + if len(world.player.units) > 0: + print(world.player.units[0].cell) diff --git a/world.py b/world.py index 2dd0554..c30fab1 100644 --- a/world.py +++ b/world.py @@ -377,8 +377,6 @@ def get_shortest_path_to_cell(self, player_id, cell=None, row=None, col=None): cell = self.map.get_cell(row, col) shortest_path_to_cell = self.shortest_path.get(player_id) - print(shortest_path_to_cell) - if shortest_path_to_cell[cell.row][cell.col] == -1: return None