# Path: oscar/agent/commander/context_save_commender.py
# class ContextSaveCommander(BaseCommander):
#     def __init__(self, subordinates: list):
#         super().__init__(subordinates=subordinates)
#         self._subordinate_context = {}
#         self._is_changing_context = False
#         self.add_shared('env', Env())
#         self.add_shared('camera', Camera())
# 
#     def step(self, obs, locked_choice=None):
#         self._shared['env'].timestamp += 1
# 
#         if locked_choice is None:
#             locked_choice = self._locked_choice
# 
#         # if we were changing context do not ask for choosing a subordinate
#         if self._is_changing_context:
#             self._is_changing_context = False
#             playing_subordinate = self._playing_subordinate
#         else:
#             playing_subordinate = self.choose_subordinate(obs, locked_choice)
# 
#         # if we are changing active subordinate, save and restore context (require one action)
#         if playing_subordinate is not self._playing_subordinate and self._playing_subordinate is not None:
#             self.save_context(obs)
#             play = self.restore_context(playing_subordinate, obs)
#             self._playing_subordinate = playing_subordinate
#         else:
#             self._playing_subordinate = playing_subordinate
#             play = self._playing_subordinate.step(obs, locked_choice)
#             if "locked_choice" in play:
#                 self._locked_choice = play["locked_choice"]
#             else:
#                 self._locked_choice = False
#         return play
# 
#     def restore_context(self, subordinate, obs):
#         if subordinate not in self._subordinate_context:
#             context = AgentContext()
#             location = self._shared['camera'].location(obs=obs, shared=self._shared)
#             context.camera = location
#         else:
#             context = self._subordinate_context[subordinate]
#         play = {}
#         play['actions'] = [actions.FunctionCall(MOVE_CAMERA, [context.camera.to_array()])]
#         play['locked_choice'] = True
#         self._is_changing_context = True
#         return play
# 
#     def save_context(self, obs):
#         context = AgentContext()
#         location = self._shared['camera'].location(obs=obs, shared=self._shared)
#         context.camera = location
#         self._subordinate_context[self._playing_subordinate] = context
# 
#     @abstractmethod
#     def choose_subordinate(self, obs, locked_choice):
#         """
#         Choose a subordinate among the list of subordinates, and make it play.
#         :return: A subordinate among the list of subordinates.
#         """
# 
#     def reset(self):
#         super().reset()
#         self._subordinate_context = {}
#         self._is_changing_context = False
#         self.add_shared('env', Env())
#         self.add_shared('camera', Camera())
# 
# Path: oscar/agent/scripted/idle_scv.py
# class IdleSCVManagerBasic(CustomAgent):
#     def __init__(self):
#         super().__init__()
#         self.command_center_pos = None
#         self.add_shared('env', Env())
#         self.add_shared('camera', Camera())
# 
#     def step(self, obs, locked_choice=None):
#         self._shared['env'].timestamp += 1
#         if self._shared['env'].timestamp == 1:
#             self.command_center_pos = self._shared['camera'].location(obs=obs, shared=self._shared)
#         play = {}
#         # if a scv is already selected it was most probably selected during last call
#         # but in case we just queue the harvest order
#         if obs.observation['single_select'][0][0] == TERRAN_SCV:
#             try:
#                 play['actions'] = harvest_mineral(obs, queued=True)
#             except NoUnitError:
#                 # if we get here, chance are that no more command center exist, send scv to attack !
#                 play['actions'] = attack_minimap(obs, queued=True)
#             # select a new idle scv to prevent looping on the same
#             try:
#                 play['actions'] += select_idle_scv(obs)
#             except NoValidSCVError:
#                 pass
#         elif SELECT_IDLE_WORKER in obs.observation['available_actions']:
#             play['actions'] = select_idle_scv(obs)
#             try:
#                 # if we still have a command center somewhere
#                 if obs.observation[PLAYER][FOOD_CAP] % 8 != 0:
#                     play['actions'] += harvest_mineral(obs)
#                 else:
#                     play['actions'] += attack_minimap(obs, queued=True)
#             except NoUnitError:
#                 play['actions'] += [actions.FunctionCall(MOVE_CAMERA, [self.command_center_pos.to_array()])]
#                 play['locked_choice'] = True
#         else:
#             play['actions'] = [actions.FunctionCall(NO_OP, [])]
# 
#         return play
# 
#     def reset(self):
#         super().reset()
#         self.command_center_pos = None
#         self.add_shared('env', Env())
#         self.add_shared('camera', Camera())


from oscar.agent.commander.context_save_commender import ContextSaveCommander
from oscar.agent.scripted.idle_scv import IdleSCVManagerBasic
from oscar.constants import *


class CollectIdleScvCommander(ContextSaveCommander):
    def __init__(self, subordinates: list):
        super().__init__(subordinates)
        if len(subordinates) != 2:
            raise ValueError("CollectIdleScvCommander can only manage two subordinate")
        self.idle_manager = None
        self.other_subordinate = None
        for a in subordinates:

# Path: oscar/agent/commander/context_save_commender.py
# class ContextSaveCommander(BaseCommander):
#     def __init__(self, subordinates: list):
#         super().__init__(subordinates=subordinates)
#         self._subordinate_context = {}
#         self._is_changing_context = False
#         self.add_shared('env', Env())
#         self.add_shared('camera', Camera())
# 
#     def step(self, obs, locked_choice=None):
#         self._shared['env'].timestamp += 1
# 
#         if locked_choice is None:
#             locked_choice = self._locked_choice
# 
#         # if we were changing context do not ask for choosing a subordinate
#         if self._is_changing_context:
#             self._is_changing_context = False
#             playing_subordinate = self._playing_subordinate
#         else:
#             playing_subordinate = self.choose_subordinate(obs, locked_choice)
# 
#         # if we are changing active subordinate, save and restore context (require one action)
#         if playing_subordinate is not self._playing_subordinate and self._playing_subordinate is not None:
#             self.save_context(obs)
#             play = self.restore_context(playing_subordinate, obs)
#             self._playing_subordinate = playing_subordinate
#         else:
#             self._playing_subordinate = playing_subordinate
#             play = self._playing_subordinate.step(obs, locked_choice)
#             if "locked_choice" in play:
#                 self._locked_choice = play["locked_choice"]
#             else:
#                 self._locked_choice = False
#         return play
# 
#     def restore_context(self, subordinate, obs):
#         if subordinate not in self._subordinate_context:
#             context = AgentContext()
#             location = self._shared['camera'].location(obs=obs, shared=self._shared)
#             context.camera = location
#         else:
#             context = self._subordinate_context[subordinate]
#         play = {}
#         play['actions'] = [actions.FunctionCall(MOVE_CAMERA, [context.camera.to_array()])]
#         play['locked_choice'] = True
#         self._is_changing_context = True
#         return play
# 
#     def save_context(self, obs):
#         context = AgentContext()
#         location = self._shared['camera'].location(obs=obs, shared=self._shared)
#         context.camera = location
#         self._subordinate_context[self._playing_subordinate] = context
# 
#     @abstractmethod
#     def choose_subordinate(self, obs, locked_choice):
#         """
#         Choose a subordinate among the list of subordinates, and make it play.
#         :return: A subordinate among the list of subordinates.
#         """
# 
#     def reset(self):
#         super().reset()
#         self._subordinate_context = {}
#         self._is_changing_context = False
#         self.add_shared('env', Env())
#         self.add_shared('camera', Camera())
# 
# Path: oscar/agent/scripted/idle_scv.py
# class IdleSCVManagerBasic(CustomAgent):
#     def __init__(self):
#         super().__init__()
#         self.command_center_pos = None
#         self.add_shared('env', Env())
#         self.add_shared('camera', Camera())
# 
#     def step(self, obs, locked_choice=None):
#         self._shared['env'].timestamp += 1
#         if self._shared['env'].timestamp == 1:
#             self.command_center_pos = self._shared['camera'].location(obs=obs, shared=self._shared)
#         play = {}
#         # if a scv is already selected it was most probably selected during last call
#         # but in case we just queue the harvest order
#         if obs.observation['single_select'][0][0] == TERRAN_SCV:
#             try:
#                 play['actions'] = harvest_mineral(obs, queued=True)
#             except NoUnitError:
#                 # if we get here, chance are that no more command center exist, send scv to attack !
#                 play['actions'] = attack_minimap(obs, queued=True)
#             # select a new idle scv to prevent looping on the same
#             try:
#                 play['actions'] += select_idle_scv(obs)
#             except NoValidSCVError:
#                 pass
#         elif SELECT_IDLE_WORKER in obs.observation['available_actions']:
#             play['actions'] = select_idle_scv(obs)
#             try:
#                 # if we still have a command center somewhere
#                 if obs.observation[PLAYER][FOOD_CAP] % 8 != 0:
#                     play['actions'] += harvest_mineral(obs)
#                 else:
#                     play['actions'] += attack_minimap(obs, queued=True)
#             except NoUnitError:
#                 play['actions'] += [actions.FunctionCall(MOVE_CAMERA, [self.command_center_pos.to_array()])]
#                 play['locked_choice'] = True
#         else:
#             play['actions'] = [actions.FunctionCall(NO_OP, [])]
# 
#         return play
# 
#     def reset(self):
#         super().reset()
#         self.command_center_pos = None
#         self.add_shared('env', Env())
#         self.add_shared('camera', Camera())


# Path: oscar/agent/commander/collect_idle_scv_commander.py
from oscar.agent.commander.context_save_commender import ContextSaveCommander
from oscar.agent.scripted.idle_scv import IdleSCVManagerBasic
from oscar.constants import *



class CollectIdleScvCommander(ContextSaveCommander):
    def __init__(self, subordinates: list):
        super().__init__(subordinates)
        if len(subordinates) != 2:
            raise ValueError("CollectIdleScvCommander can only manage two subordinate")
        self.idle_manager = None
        self.other_subordinate = None
        for a in subordinates:

            if type(a) == IdleSCVManagerBasic: