"""
Generated by Statechart compiler by Glenn De Jonghe, Joeri Exelmans, Simon Van Mierlo, and Yentl Van Tendeloo (for the inspiration)

Date:   Thu Nov 10 14:05:46 2016

Model author: Glenn De Jonghe
Model name:   AI Tank
Model description:
Handling the npc tank.
"""

from sccd.runtime.statecharts_core import *
from AIMap import AIMap
import math
from mymath import D1, D45, D360

# package "AI Tank"

class Main(RuntimeClassBase):
    def __init__(self, controller, tank):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # user defined attributes
        self.tank = None
        self.map = None
        
        # call user defined constructor
        Main.user_defined_constructor(self, tank)
    
    def user_defined_constructor(self, tank):
        self.tank = tank
        self.map = AIMap(tank.field.level)
    
    def user_defined_destructor(self):
        pass
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /error
        self.states["/error"] = State(1, "/error", self)
        
        # state /creation
        self.states["/creation"] = State(2, "/creation", self)
        
        # state /creation/state_1
        self.states["/creation/state_1"] = State(3, "/creation/state_1", self)
        
        # state /creation/state_2
        self.states["/creation/state_2"] = State(4, "/creation/state_2", self)
        
        # state /creation/state_3
        self.states["/creation/state_3"] = State(5, "/creation/state_3", self)
        
        # state /creation/state_4
        self.states["/creation/state_4"] = State(6, "/creation/state_4", self)
        
        # state /creation/state_5
        self.states["/creation/state_5"] = State(7, "/creation/state_5", self)
        
        # state /creation/state_6
        self.states["/creation/state_6"] = State(8, "/creation/state_6", self)
        
        # state /creation/state_7
        self.states["/creation/state_7"] = State(9, "/creation/state_7", self)
        
        # state /creation/state_8
        self.states["/creation/state_8"] = State(10, "/creation/state_8", self)
        
        # state /creation/state_9
        self.states["/creation/state_9"] = State(11, "/creation/state_9", self)
        
        # state /creation/state_10
        self.states["/creation/state_10"] = State(12, "/creation/state_10", self)
        
        # state /creation/state_11
        self.states["/creation/state_11"] = State(13, "/creation/state_11", self)
        
        # state /creation/state_12
        self.states["/creation/state_12"] = State(14, "/creation/state_12", self)
        
        # state /creation/state_13
        self.states["/creation/state_13"] = State(15, "/creation/state_13", self)
        
        # state /creation/state_14
        self.states["/creation/state_14"] = State(16, "/creation/state_14", self)
        
        # state /creation/state_15
        self.states["/creation/state_15"] = State(17, "/creation/state_15", self)
        
        # state /creation/state_16
        self.states["/creation/state_16"] = State(18, "/creation/state_16", self)
        
        # state /creation/state_17
        self.states["/creation/state_17"] = State(19, "/creation/state_17", self)
        
        # state /creation/state_18
        self.states["/creation/state_18"] = State(20, "/creation/state_18", self)
        
        # state /creation/state_19
        self.states["/creation/state_19"] = State(21, "/creation/state_19", self)
        
        # state /creation/state_20
        self.states["/creation/state_20"] = State(22, "/creation/state_20", self)
        
        # state /creation/state_21
        self.states["/creation/state_21"] = State(23, "/creation/state_21", self)
        
        # state /creation/end
        self.states["/creation/end"] = State(24, "/creation/end", self)
        
        # add children
        self.states[""].addChild(self.states["/error"])
        self.states[""].addChild(self.states["/creation"])
        self.states["/creation"].addChild(self.states["/creation/state_1"])
        self.states["/creation"].addChild(self.states["/creation/state_2"])
        self.states["/creation"].addChild(self.states["/creation/state_3"])
        self.states["/creation"].addChild(self.states["/creation/state_4"])
        self.states["/creation"].addChild(self.states["/creation/state_5"])
        self.states["/creation"].addChild(self.states["/creation/state_6"])
        self.states["/creation"].addChild(self.states["/creation/state_7"])
        self.states["/creation"].addChild(self.states["/creation/state_8"])
        self.states["/creation"].addChild(self.states["/creation/state_9"])
        self.states["/creation"].addChild(self.states["/creation/state_10"])
        self.states["/creation"].addChild(self.states["/creation/state_11"])
        self.states["/creation"].addChild(self.states["/creation/state_12"])
        self.states["/creation"].addChild(self.states["/creation/state_13"])
        self.states["/creation"].addChild(self.states["/creation/state_14"])
        self.states["/creation"].addChild(self.states["/creation/state_15"])
        self.states["/creation"].addChild(self.states["/creation/state_16"])
        self.states["/creation"].addChild(self.states["/creation/state_17"])
        self.states["/creation"].addChild(self.states["/creation/state_18"])
        self.states["/creation"].addChild(self.states["/creation/state_19"])
        self.states["/creation"].addChild(self.states["/creation/state_20"])
        self.states["/creation"].addChild(self.states["/creation/state_21"])
        self.states["/creation"].addChild(self.states["/creation/end"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/creation"]
        self.states["/creation"].default_state = self.states["/creation/state_1"]
        
        # transition /creation/state_1
        _creation_state_1_0 = Transition(self, self.states["/creation/state_1"], [self.states["/creation/state_2"]])
        _creation_state_1_0.setAction(self._creation_state_1_0_exec)
        _creation_state_1_0.setTrigger(None)
        self.states["/creation/state_1"].addTransition(_creation_state_1_0)
        
        # transition /creation/state_2
        _creation_state_2_0 = Transition(self, self.states["/creation/state_2"], [self.states["/creation/state_3"]])
        _creation_state_2_0.setTrigger(Event("instance_created", None))
        self.states["/creation/state_2"].addTransition(_creation_state_2_0)
        
        # transition /creation/state_3
        _creation_state_3_0 = Transition(self, self.states["/creation/state_3"], [self.states["/creation/state_4"]])
        _creation_state_3_0.setAction(self._creation_state_3_0_exec)
        _creation_state_3_0.setTrigger(None)
        self.states["/creation/state_3"].addTransition(_creation_state_3_0)
        
        # transition /creation/state_4
        _creation_state_4_0 = Transition(self, self.states["/creation/state_4"], [self.states["/creation/state_5"]])
        _creation_state_4_0.setTrigger(Event("instance_created", None))
        self.states["/creation/state_4"].addTransition(_creation_state_4_0)
        
        # transition /creation/state_5
        _creation_state_5_0 = Transition(self, self.states["/creation/state_5"], [self.states["/creation/state_6"]])
        _creation_state_5_0.setAction(self._creation_state_5_0_exec)
        _creation_state_5_0.setTrigger(None)
        self.states["/creation/state_5"].addTransition(_creation_state_5_0)
        
        # transition /creation/state_6
        _creation_state_6_0 = Transition(self, self.states["/creation/state_6"], [self.states["/creation/state_7"]])
        _creation_state_6_0.setTrigger(Event("instance_created", None))
        self.states["/creation/state_6"].addTransition(_creation_state_6_0)
        
        # transition /creation/state_7
        _creation_state_7_0 = Transition(self, self.states["/creation/state_7"], [self.states["/creation/state_8"]])
        _creation_state_7_0.setAction(self._creation_state_7_0_exec)
        _creation_state_7_0.setTrigger(None)
        self.states["/creation/state_7"].addTransition(_creation_state_7_0)
        
        # transition /creation/state_8
        _creation_state_8_0 = Transition(self, self.states["/creation/state_8"], [self.states["/creation/state_9"]])
        _creation_state_8_0.setTrigger(Event("instance_created", None))
        self.states["/creation/state_8"].addTransition(_creation_state_8_0)
        
        # transition /creation/state_9
        _creation_state_9_0 = Transition(self, self.states["/creation/state_9"], [self.states["/creation/state_10"]])
        _creation_state_9_0.setAction(self._creation_state_9_0_exec)
        _creation_state_9_0.setTrigger(None)
        self.states["/creation/state_9"].addTransition(_creation_state_9_0)
        
        # transition /creation/state_10
        _creation_state_10_0 = Transition(self, self.states["/creation/state_10"], [self.states["/creation/state_11"]])
        _creation_state_10_0.setTrigger(Event("instance_created", None))
        self.states["/creation/state_10"].addTransition(_creation_state_10_0)
        
        # transition /creation/state_11
        _creation_state_11_0 = Transition(self, self.states["/creation/state_11"], [self.states["/creation/state_12"]])
        _creation_state_11_0.setAction(self._creation_state_11_0_exec)
        _creation_state_11_0.setTrigger(None)
        self.states["/creation/state_11"].addTransition(_creation_state_11_0)
        
        # transition /creation/state_12
        _creation_state_12_0 = Transition(self, self.states["/creation/state_12"], [self.states["/creation/state_13"]])
        _creation_state_12_0.setTrigger(Event("instance_created", None))
        self.states["/creation/state_12"].addTransition(_creation_state_12_0)
        
        # transition /creation/state_13
        _creation_state_13_0 = Transition(self, self.states["/creation/state_13"], [self.states["/creation/state_14"]])
        _creation_state_13_0.setAction(self._creation_state_13_0_exec)
        _creation_state_13_0.setTrigger(None)
        self.states["/creation/state_13"].addTransition(_creation_state_13_0)
        
        # transition /creation/state_14
        _creation_state_14_0 = Transition(self, self.states["/creation/state_14"], [self.states["/creation/state_15"]])
        _creation_state_14_0.setTrigger(Event("instance_created", None))
        self.states["/creation/state_14"].addTransition(_creation_state_14_0)
        
        # transition /creation/state_15
        _creation_state_15_0 = Transition(self, self.states["/creation/state_15"], [self.states["/creation/state_16"]])
        _creation_state_15_0.setAction(self._creation_state_15_0_exec)
        _creation_state_15_0.setTrigger(None)
        self.states["/creation/state_15"].addTransition(_creation_state_15_0)
        
        # transition /creation/state_16
        _creation_state_16_0 = Transition(self, self.states["/creation/state_16"], [self.states["/creation/state_17"]])
        _creation_state_16_0.setTrigger(Event("instance_created", None))
        self.states["/creation/state_16"].addTransition(_creation_state_16_0)
        
        # transition /creation/state_17
        _creation_state_17_0 = Transition(self, self.states["/creation/state_17"], [self.states["/creation/state_18"]])
        _creation_state_17_0.setAction(self._creation_state_17_0_exec)
        _creation_state_17_0.setTrigger(None)
        self.states["/creation/state_17"].addTransition(_creation_state_17_0)
        
        # transition /creation/state_18
        _creation_state_18_0 = Transition(self, self.states["/creation/state_18"], [self.states["/creation/state_19"]])
        _creation_state_18_0.setTrigger(Event("instance_created", None))
        self.states["/creation/state_18"].addTransition(_creation_state_18_0)
        
        # transition /creation/state_19
        _creation_state_19_0 = Transition(self, self.states["/creation/state_19"], [self.states["/creation/state_20"]])
        _creation_state_19_0.setAction(self._creation_state_19_0_exec)
        _creation_state_19_0.setTrigger(None)
        self.states["/creation/state_19"].addTransition(_creation_state_19_0)
        
        # transition /creation/state_20
        _creation_state_20_0 = Transition(self, self.states["/creation/state_20"], [self.states["/creation/state_21"]])
        _creation_state_20_0.setTrigger(Event("instance_created", None))
        self.states["/creation/state_20"].addTransition(_creation_state_20_0)
        
        # transition /creation/state_21
        _creation_state_21_0 = Transition(self, self.states["/creation/state_21"], [self.states["/creation/end"]])
        _creation_state_21_0.setAction(self._creation_state_21_0_exec)
        _creation_state_21_0.setTrigger(None)
        self.states["/creation/state_21"].addTransition(_creation_state_21_0)
        
        # transition /creation
        _creation_0 = Transition(self, self.states["/creation"], [self.states["/error"]])
        _creation_0.setAction(self._creation_0_exec)
        _creation_0.setTrigger(Event("instance_creation_error", None))
        self.states["/creation"].addTransition(_creation_0)
        _creation_1 = Transition(self, self.states["/creation"], [self.states["/error"]])
        _creation_1.setAction(self._creation_1_exec)
        _creation_1.setTrigger(Event("instance_association_error", None))
        self.states["/creation"].addTransition(_creation_1)
    
    def _creation_0_exec(self, parameters):
        print "Instance creation error!"
    
    def _creation_1_exec(self, parameters):
        print "Instance association error!"
    
    def _creation_state_1_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("create_instance", None, [self, 'turret_control', 'TurretControl', self.tank]))
    
    def _creation_state_3_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("create_instance", None, [self, 'motor_control', 'MotorControl', self.tank]))
    
    def _creation_state_5_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("create_instance", None, [self, 'turret_steering', 'TurretSteering', self.tank]))
    
    def _creation_state_7_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("create_instance", None, [self, 'steering', 'Steering', self.tank, self.map]))
    
    def _creation_state_9_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("create_instance", None, [self, 'path_finder', 'PathFinder', self.tank, self.map]))
    
    def _creation_state_11_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("create_instance", None, [self, 'attack_planner', 'AttackPlanner']))
    
    def _creation_state_13_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("create_instance", None, [self, 'explore_planner', 'ExplorePlanner', self.tank, self.map]))
    
    def _creation_state_15_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("create_instance", None, [self, 'pilot_strategy', 'PilotStrategy']))
    
    def _creation_state_17_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("create_instance", None, [self, 'enemy_tracker', 'EnemyTracker']))
    
    def _creation_state_19_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("create_instance", None, [self, 'radar', 'Radar', self.tank]))
    
    def _creation_state_21_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("start_instance", None, [self, 'turret_control']))
        self.big_step.outputEventOM(Event("start_instance", None, [self, 'motor_control']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'turret_control', 'turret_steering/turret_control']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'attack_planner', 'turret_steering/attack_planner']))
        self.big_step.outputEventOM(Event("start_instance", None, [self, 'turret_steering']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'motor_control', 'steering/motor_control']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'path_finder', 'steering/path_finder']))
        self.big_step.outputEventOM(Event("start_instance", None, [self, 'steering']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'steering', 'path_finder/steering']))
        self.big_step.outputEventOM(Event("start_instance", None, [self, 'path_finder']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'turret_steering', 'attack_planner/turret_steering']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'turret_control', 'attack_planner/turret_control']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'path_finder', 'attack_planner/path_finder']))
        self.big_step.outputEventOM(Event("start_instance", None, [self, 'attack_planner']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'path_finder', 'explore_planner/path_finder']))
        self.big_step.outputEventOM(Event("start_instance", None, [self, 'explore_planner']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'explore_planner', 'pilot_strategy/explore_planner']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'attack_planner', 'pilot_strategy/attack_planner']))
        self.big_step.outputEventOM(Event("start_instance", None, [self, 'pilot_strategy']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'pilot_strategy', 'enemy_tracker/pilot_strategy']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'attack_planner', 'enemy_tracker/attack_planner']))
        self.big_step.outputEventOM(Event("start_instance", None, [self, 'enemy_tracker']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'pilot_strategy', 'radar/pilot_strategy']))
        self.big_step.outputEventOM(Event("associate_instance", None, [self, 'enemy_tracker', 'radar/enemy_tracker']))
        self.big_step.outputEventOM(Event("start_instance", None, [self, 'radar']))
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/creation"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class Radar(RuntimeClassBase):
    def __init__(self, controller, tank):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # user defined attributes
        self.tank = None
        self.range = 2000
        
        # call user defined constructor
        Radar.user_defined_constructor(self, tank)
    
    def user_defined_constructor(self, tank):
        self.tank = tank
    
    def user_defined_destructor(self):
        pass
    
    
    # user defined method
    def isEnemyVisible(self):
        sighted_list = self.tank.field.getSightedEnemies(self.tank, self.range)
        if len(sighted_list) > 0 :
            return True
        return False
    
    
    # user defined method
    def getEnemyPos(self):
        sighted_list = self.tank.field.getSightedEnemies(self.tank, self.range)
        if len(sighted_list) > 0 :
            sighted_list.sort(key=lambda x: x[1])
            return sighted_list[0][0]
        else :
            return (-1,-1)
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /no_enemy
        self.states["/no_enemy"] = State(1, "/no_enemy", self)
        
        # state /enemy_in_sight
        self.states["/enemy_in_sight"] = State(2, "/enemy_in_sight", self)
        
        # add children
        self.states[""].addChild(self.states["/no_enemy"])
        self.states[""].addChild(self.states["/enemy_in_sight"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/no_enemy"]
        
        # transition /no_enemy
        _no_enemy_0 = Transition(self, self.states["/no_enemy"], [self.states["/enemy_in_sight"]])
        _no_enemy_0.setAction(self._no_enemy_0_exec)
        _no_enemy_0.setTrigger(None)
        _no_enemy_0.setGuard(self._no_enemy_0_guard)
        self.states["/no_enemy"].addTransition(_no_enemy_0)
        
        # transition /enemy_in_sight
        _enemy_in_sight_0 = Transition(self, self.states["/enemy_in_sight"], [self.states["/no_enemy"]])
        _enemy_in_sight_0.setAction(self._enemy_in_sight_0_exec)
        _enemy_in_sight_0.setTrigger(None)
        _enemy_in_sight_0.setGuard(self._enemy_in_sight_0_guard)
        self.states["/enemy_in_sight"].addTransition(_enemy_in_sight_0)
        _enemy_in_sight_1 = Transition(self, self.states["/enemy_in_sight"], [self.states["/enemy_in_sight"]])
        _enemy_in_sight_1.setAction(self._enemy_in_sight_1_exec)
        _enemy_in_sight_1.setTrigger(Event("update", "engine"))
        _enemy_in_sight_1.setGuard(self._enemy_in_sight_1_guard)
        self.states["/enemy_in_sight"].addTransition(_enemy_in_sight_1)
    
    def _no_enemy_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'enemy_tracker', Event("enemy_sighted", None, [self.getEnemyPos()])]))
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'pilot_strategy', Event("enemy_sighted", None, [self.getEnemyPos()])]))
    
    def _no_enemy_0_guard(self, parameters):
        return self.isEnemyVisible()
    
    def _enemy_in_sight_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'enemy_tracker', Event("enemy_out_of_sight", None, [])]))
    
    def _enemy_in_sight_0_guard(self, parameters):
        return not self.isEnemyVisible()
    
    def _enemy_in_sight_1_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'enemy_tracker', Event("enemy_pos", None, [self.getEnemyPos()])]))
    
    def _enemy_in_sight_1_guard(self, parameters):
        return self.isEnemyVisible()
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/no_enemy"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class EnemyTracker(RuntimeClassBase):
    def __init__(self, controller):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # user defined attributes
        self.enemy_pos = None
        
        # call user defined constructor
        EnemyTracker.user_defined_constructor(self)
    
    def user_defined_constructor(self):
        pass
    
    def user_defined_destructor(self):
        pass
    
    
    # user defined method
    def hasEnemyMoved(self, new_position):
        return new_position != self.enemy_pos
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /no_enemy
        self.states["/no_enemy"] = State(1, "/no_enemy", self)
        
        # state /enemy_pos_known
        self.states["/enemy_pos_known"] = State(2, "/enemy_pos_known", self)
        
        # state /enemy_pos_unsure
        self.states["/enemy_pos_unsure"] = State(3, "/enemy_pos_unsure", self)
        
        # add children
        self.states[""].addChild(self.states["/no_enemy"])
        self.states[""].addChild(self.states["/enemy_pos_known"])
        self.states[""].addChild(self.states["/enemy_pos_unsure"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/no_enemy"]
        
        # transition /no_enemy
        _no_enemy_0 = Transition(self, self.states["/no_enemy"], [self.states["/enemy_pos_known"]])
        _no_enemy_0.setAction(self._no_enemy_0_exec)
        _no_enemy_0.setTrigger(Event("enemy_sighted", None))
        self.states["/no_enemy"].addTransition(_no_enemy_0)
        
        # transition /enemy_pos_known
        _enemy_pos_known_0 = Transition(self, self.states["/enemy_pos_known"], [self.states["/enemy_pos_known"]])
        _enemy_pos_known_0.setAction(self._enemy_pos_known_0_exec)
        _enemy_pos_known_0.setTrigger(Event("enemy_pos", None))
        _enemy_pos_known_0.setGuard(self._enemy_pos_known_0_guard)
        self.states["/enemy_pos_known"].addTransition(_enemy_pos_known_0)
        _enemy_pos_known_1 = Transition(self, self.states["/enemy_pos_known"], [self.states["/enemy_pos_unsure"]])
        _enemy_pos_known_1.setAction(self._enemy_pos_known_1_exec)
        _enemy_pos_known_1.setTrigger(Event("enemy_out_of_sight", None))
        self.states["/enemy_pos_known"].addTransition(_enemy_pos_known_1)
        
        # transition /enemy_pos_unsure
        _enemy_pos_unsure_0 = Transition(self, self.states["/enemy_pos_unsure"], [self.states["/no_enemy"]])
        _enemy_pos_unsure_0.setAction(self._enemy_pos_unsure_0_exec)
        _enemy_pos_unsure_0.setTrigger(Event("destination_reached", None))
        self.states["/enemy_pos_unsure"].addTransition(_enemy_pos_unsure_0)
        _enemy_pos_unsure_1 = Transition(self, self.states["/enemy_pos_unsure"], [self.states["/enemy_pos_known"]])
        _enemy_pos_unsure_1.setAction(self._enemy_pos_unsure_1_exec)
        _enemy_pos_unsure_1.setTrigger(Event("enemy_sighted", None))
        self.states["/enemy_pos_unsure"].addTransition(_enemy_pos_unsure_1)
    
    def _no_enemy_0_exec(self, parameters):
        enemy_position = parameters[0]
        self.enemy_pos = enemy_position
    
    def _enemy_pos_known_0_exec(self, parameters):
        position = parameters[0]
        self.enemy_pos = position
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'attack_planner', Event("enemy_pos_changed", None, [self.enemy_pos])]))
    
    def _enemy_pos_known_0_guard(self, parameters):
        position = parameters[0]
        return self.hasEnemyMoved(position)
    
    def _enemy_pos_known_1_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'attack_planner', Event("enemy_out_of_sight", None, [])]))
    
    def _enemy_pos_unsure_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'pilot_strategy', Event("enemy_lost", None, [])]))
        print "raise enemy_lost"
    
    def _enemy_pos_unsure_1_exec(self, parameters):
        position = parameters[0]
        self.enemy_pos = position
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/no_enemy"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class PilotStrategy(RuntimeClassBase):
    def __init__(self, controller):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # call user defined constructor
        PilotStrategy.user_defined_constructor(self)
    
    def user_defined_constructor(self):
        pass
    
    def user_defined_destructor(self):
        pass
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /exploring
        self.states["/exploring"] = State(1, "/exploring", self)
        self.states["/exploring"].setEnter(self._exploring_enter)
        self.states["/exploring"].setExit(self._exploring_exit)
        
        # state /attacking
        self.states["/attacking"] = State(2, "/attacking", self)
        self.states["/attacking"].setExit(self._attacking_exit)
        
        # add children
        self.states[""].addChild(self.states["/exploring"])
        self.states[""].addChild(self.states["/attacking"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/exploring"]
        
        # transition /exploring
        _exploring_0 = Transition(self, self.states["/exploring"], [self.states["/attacking"]])
        _exploring_0.setAction(self._exploring_0_exec)
        _exploring_0.setTrigger(Event("enemy_sighted", None))
        self.states["/exploring"].addTransition(_exploring_0)
        
        # transition /attacking
        _attacking_0 = Transition(self, self.states["/attacking"], [self.states["/exploring"]])
        _attacking_0.setAction(self._attacking_0_exec)
        _attacking_0.setTrigger(Event("enemy_lost", None))
        self.states["/attacking"].addTransition(_attacking_0)
    
    def _exploring_enter(self):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'explore_planner', Event("explore", None, [])]))
    
    def _exploring_exit(self):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'explore_planner', Event("stop_exploring", None, [])]))
    
    def _attacking_exit(self):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'attack_planner', Event("stop_attacking", None, [])]))
        print "raise stop_attacking"
    
    def _exploring_0_exec(self, parameters):
        position = parameters[0]
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'attack_planner', Event("attack", None, [position])]))
    
    def _attacking_0_exec(self, parameters):
        print "received enemy lost"
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/exploring"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class ExplorePlanner(RuntimeClassBase):
    def __init__(self, controller, tank, aimap):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # user defined attributes
        self.map = None
        self.tank = None
        
        # call user defined constructor
        ExplorePlanner.user_defined_constructor(self, tank, aimap)
    
    def user_defined_constructor(self, tank, aimap):
        self.tank = tank
        self.map = aimap
    
    def user_defined_destructor(self):
        pass
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /idle
        self.states["/idle"] = State(1, "/idle", self)
        
        # state /exploring
        self.states["/exploring"] = State(2, "/exploring", self)
        
        # state /exploring/no_destination
        self.states["/exploring/no_destination"] = State(3, "/exploring/no_destination", self)
        
        # state /exploring/destination_set
        self.states["/exploring/destination_set"] = State(4, "/exploring/destination_set", self)
        
        # add children
        self.states[""].addChild(self.states["/idle"])
        self.states[""].addChild(self.states["/exploring"])
        self.states["/exploring"].addChild(self.states["/exploring/no_destination"])
        self.states["/exploring"].addChild(self.states["/exploring/destination_set"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/idle"]
        self.states["/exploring"].default_state = self.states["/exploring/no_destination"]
        
        # transition /idle
        _idle_0 = Transition(self, self.states["/idle"], [self.states["/exploring"]])
        _idle_0.setTrigger(Event("explore", None))
        self.states["/idle"].addTransition(_idle_0)
        
        # transition /exploring/no_destination
        _exploring_no_destination_0 = Transition(self, self.states["/exploring/no_destination"], [self.states["/exploring/destination_set"]])
        _exploring_no_destination_0.setAction(self._exploring_no_destination_0_exec)
        _exploring_no_destination_0.setTrigger(None)
        self.states["/exploring/no_destination"].addTransition(_exploring_no_destination_0)
        
        # transition /exploring/destination_set
        _exploring_destination_set_0 = Transition(self, self.states["/exploring/destination_set"], [self.states["/exploring/no_destination"]])
        _exploring_destination_set_0.setTrigger(Event("destination_reached", None))
        self.states["/exploring/destination_set"].addTransition(_exploring_destination_set_0)
        
        # transition /exploring
        _exploring_0 = Transition(self, self.states["/exploring"], [self.states["/idle"]])
        _exploring_0.setAction(self._exploring_0_exec)
        _exploring_0.setTrigger(Event("stop_exploring", None))
        self.states["/exploring"].addTransition(_exploring_0)
    
    def _exploring_0_exec(self, parameters):
        print "stop_exploring received"
    
    def _exploring_no_destination_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'path_finder', Event("new_destination", None, [self.map.getNewExplore(self.tank.getPosition(),self.tank.getAngle())])]))
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/idle"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class AttackPlanner(RuntimeClassBase):
    def __init__(self, controller):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # call user defined constructor
        AttackPlanner.user_defined_constructor(self)
    
    def user_defined_constructor(self):
        pass
    
    def user_defined_destructor(self):
        pass
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /idle
        self.states["/idle"] = State(1, "/idle", self)
        
        # state /action
        self.states["/action"] = ParallelState(2, "/action", self)
        
        # state /action/movement
        self.states["/action/movement"] = State(3, "/action/movement", self)
        
        # state /action/movement/following
        self.states["/action/movement/following"] = State(4, "/action/movement/following", self)
        
        # state /action/shooting
        self.states["/action/shooting"] = State(5, "/action/shooting", self)
        
        # state /action/shooting/loaded
        self.states["/action/shooting/loaded"] = State(6, "/action/shooting/loaded", self)
        
        # state /action/shooting/reloading
        self.states["/action/shooting/reloading"] = State(7, "/action/shooting/reloading", self)
        self.states["/action/shooting/reloading"].setEnter(self._action_shooting_reloading_enter)
        self.states["/action/shooting/reloading"].setExit(self._action_shooting_reloading_exit)
        
        # add children
        self.states[""].addChild(self.states["/idle"])
        self.states[""].addChild(self.states["/action"])
        self.states["/action"].addChild(self.states["/action/movement"])
        self.states["/action"].addChild(self.states["/action/shooting"])
        self.states["/action/movement"].addChild(self.states["/action/movement/following"])
        self.states["/action/shooting"].addChild(self.states["/action/shooting/loaded"])
        self.states["/action/shooting"].addChild(self.states["/action/shooting/reloading"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/idle"]
        self.states["/action/movement"].default_state = self.states["/action/movement/following"]
        self.states["/action/shooting"].default_state = self.states["/action/shooting/loaded"]
        
        # transition /idle
        _idle_0 = Transition(self, self.states["/idle"], [self.states["/action"]])
        _idle_0.setAction(self._idle_0_exec)
        _idle_0.setTrigger(Event("attack", None))
        self.states["/idle"].addTransition(_idle_0)
        
        # transition /action/movement/following
        _action_movement_following_0 = Transition(self, self.states["/action/movement/following"], [self.states["/action/movement/following"]])
        _action_movement_following_0.setAction(self._action_movement_following_0_exec)
        _action_movement_following_0.setTrigger(Event("enemy_pos_changed", None))
        self.states["/action/movement/following"].addTransition(_action_movement_following_0)
        _action_movement_following_1 = Transition(self, self.states["/action/movement/following"], [self.states["/action/movement/following"]])
        _action_movement_following_1.setAction(self._action_movement_following_1_exec)
        _action_movement_following_1.setTrigger(Event("enemy_out_of_sight", None))
        self.states["/action/movement/following"].addTransition(_action_movement_following_1)
        
        # transition /action/shooting/loaded
        _action_shooting_loaded_0 = Transition(self, self.states["/action/shooting/loaded"], [self.states["/action/shooting/reloading"]])
        _action_shooting_loaded_0.setAction(self._action_shooting_loaded_0_exec)
        _action_shooting_loaded_0.setTrigger(Event("ready_to_shoot", None))
        self.states["/action/shooting/loaded"].addTransition(_action_shooting_loaded_0)
        
        # transition /action/shooting/reloading
        _action_shooting_reloading_0 = Transition(self, self.states["/action/shooting/reloading"], [self.states["/action/shooting/loaded"]])
        _action_shooting_reloading_0.setTrigger(Event("_0after"))
        self.states["/action/shooting/reloading"].addTransition(_action_shooting_reloading_0)
        
        # transition /action
        _action_0 = Transition(self, self.states["/action"], [self.states["/idle"]])
        _action_0.setAction(self._action_0_exec)
        _action_0.setTrigger(Event("stop_attacking", None))
        self.states["/action"].addTransition(_action_0)
    
    def _action_shooting_reloading_enter(self):
        self.addTimer(0, 0.5)
    
    def _action_shooting_reloading_exit(self):
        self.removeTimer(0)
    
    def _action_0_exec(self, parameters):
        print "received stop attack"
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'turret_steering', Event("stop_aiming", None, [])]))
    
    def _idle_0_exec(self, parameters):
        enemy_pos = parameters[0]
        print "received attack"
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'path_finder', Event("new_destination", None, [enemy_pos])]))
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'turret_steering', Event("aim_at", None, [enemy_pos])]))
    
    def _action_movement_following_0_exec(self, parameters):
        enemy_pos = parameters[0]
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'path_finder', Event("new_destination", None, [enemy_pos])]))
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'turret_steering', Event("aim_at", None, [enemy_pos])]))
    
    def _action_movement_following_1_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'turret_steering', Event("stop_aiming", None, [])]))
    
    def _action_shooting_loaded_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'turret_control', Event("shoot", None, [])]))
        print "raise shoot"
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/idle"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class PathFinder(RuntimeClassBase):
    def __init__(self, controller, tank, aimap):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # user defined attributes
        self.waypoints = []
        self.destination = (-1,-1)
        self.map = None
        self.tank = None
        
        # call user defined constructor
        PathFinder.user_defined_constructor(self, tank, aimap)
    
    def user_defined_constructor(self, tank, aimap):
        self.tank = tank
        self.map = aimap
    
    def user_defined_destructor(self):
        pass
    
    
    # user defined method
    def calculatePath(self):
        return self.map.calculatePath(self.tank.getPosition(), self.destination)
    
    
    # user defined method
    def requiresNewPath(self, new_destination):
        return self.map.calculateCell(self.destination) != self.map.calculateCell(new_destination)
    
    
    # user defined method
    def morePoints(self):
        return len(self.waypoints) > 0
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /idle
        self.states["/idle"] = State(1, "/idle", self)
        
        # state /check_points
        self.states["/check_points"] = State(2, "/check_points", self)
        
        # add children
        self.states[""].addChild(self.states["/idle"])
        self.states[""].addChild(self.states["/check_points"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/idle"]
        
        # transition /idle
        _idle_0 = Transition(self, self.states["/idle"], [self.states["/check_points"]])
        _idle_0.setTrigger(Event("waypoint_reached", None))
        self.states["/idle"].addTransition(_idle_0)
        _idle_1 = Transition(self, self.states["/idle"], [self.states["/check_points"]])
        _idle_1.setAction(self._idle_1_exec)
        _idle_1.setTrigger(Event("new_destination", None))
        _idle_1.setGuard(self._idle_1_guard)
        self.states["/idle"].addTransition(_idle_1)
        
        # transition /check_points
        _check_points_0 = Transition(self, self.states["/check_points"], [self.states["/idle"]])
        _check_points_0.setAction(self._check_points_0_exec)
        _check_points_0.setTrigger(None)
        _check_points_0.setGuard(self._check_points_0_guard)
        self.states["/check_points"].addTransition(_check_points_0)
        _check_points_1 = Transition(self, self.states["/check_points"], [self.states["/idle"]])
        _check_points_1.setAction(self._check_points_1_exec)
        _check_points_1.setTrigger(None)
        _check_points_1.setGuard(self._check_points_1_guard)
        self.states["/check_points"].addTransition(_check_points_1)
    
    def _idle_1_exec(self, parameters):
        destination = parameters[0]
        self.destination = destination
        self.waypoints = self.calculatePath()
    
    def _idle_1_guard(self, parameters):
        destination = parameters[0]
        return self.requiresNewPath(destination)
    
    def _check_points_0_exec(self, parameters):
        next_waypoint = self.waypoints.pop(0)
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'steering', Event("new_waypoint", None, [next_waypoint])]))
    
    def _check_points_0_guard(self, parameters):
        return self.morePoints()
    
    def _check_points_1_exec(self, parameters):
        self.big_step.outputEventOM(Event("broad_cast", None, [Event("destination_reached", None, [])]))
    
    def _check_points_1_guard(self, parameters):
        return not self.morePoints()
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/idle"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class Steering(RuntimeClassBase):
    def __init__(self, controller, tank, aimap):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # user defined attributes
        self.dest_waypoint = (-1,-1)
        self.dest_cell = (-1,-1)
        self.reaction_time = 0.05
        self.tank = None
        self.map = None
        self.margin = 0.2
        
        # call user defined constructor
        Steering.user_defined_constructor(self, tank, aimap)
    
    def user_defined_constructor(self, tank, aimap):
        self.tank = tank
        self.map = aimap
    
    def user_defined_destructor(self):
        pass
    
    
    # user defined method
    def pointReached(self):
        cell = self.map.calculateCell((self.tank.x, self.tank.y))
        return cell == self.dest_cell
    
    
    # user defined method
    def pointAhead(self):
        goal_angle = self.tank.angleToDest(self.dest_waypoint)
        diff = math.fabs(self.tank.angle - goal_angle)
        if diff <= (D45) :
            #self.tank.moveSpeed = int(math.ceil(((D45 - diff) / D45) * self.maxMoveSpeed))
            return True
        elif diff >= (D360 - D45) :
            #self.tank.moveSpeed = int(math.ceil(((diff - (D360 - D45)) / D45) * self.maxMoveSpeed))
            return True
        return False
    
    
    # user defined method
    def pointBehind(self):
        goal_angle = self.tank.angleToDest(self.dest_waypoint)
        diff = math.fabs(self.tank.angle - goal_angle)
        if diff <= (D45) or diff >= (D360 - D45) :
            return False
        return True
    
    
    # user defined method
    def pointRight(self):
        goal_angle = self.tank.angleToDest(self.dest_waypoint)
        diff = (self.tank.angle - goal_angle) % D360
        if diff >= self.margin and diff <= math.pi:
            return True
        return False
    
    
    # user defined method
    def pointLeft(self):
        goal_angle = self.tank.angleToDest(self.dest_waypoint)
        diff = (goal_angle - self.tank.angle) % D360
        if diff >= self.margin and diff <= math.pi:
            return True
        return False
    
    
    # user defined method
    def pointStraight(self):
        goal_angle = self.tank.angleToDest(self.dest_waypoint)
        diff = math.fabs(self.tank.angle - goal_angle)
        if diff < self.margin or diff > (D360- self.margin) :
            return True
        return False
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /idle
        self.states["/idle"] = State(1, "/idle", self)
        
        # state /steering
        self.states["/steering"] = State(2, "/steering", self)
        
        # state /steering/forward_backward
        self.states["/steering/forward_backward"] = State(3, "/steering/forward_backward", self)
        
        # state /steering/left_right
        self.states["/steering/left_right"] = State(4, "/steering/left_right", self)
        
        # state /steering/wait
        self.states["/steering/wait"] = State(5, "/steering/wait", self)
        self.states["/steering/wait"].setEnter(self._steering_wait_enter)
        self.states["/steering/wait"].setExit(self._steering_wait_exit)
        
        # add children
        self.states[""].addChild(self.states["/idle"])
        self.states[""].addChild(self.states["/steering"])
        self.states["/steering"].addChild(self.states["/steering/forward_backward"])
        self.states["/steering"].addChild(self.states["/steering/left_right"])
        self.states["/steering"].addChild(self.states["/steering/wait"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/idle"]
        self.states["/steering"].default_state = self.states["/steering/forward_backward"]
        
        # transition /idle
        _idle_0 = Transition(self, self.states["/idle"], [self.states["/steering"]])
        _idle_0.setAction(self._idle_0_exec)
        _idle_0.setTrigger(Event("new_waypoint", None))
        self.states["/idle"].addTransition(_idle_0)
        
        # transition /steering/forward_backward
        _steering_forward_backward_0 = Transition(self, self.states["/steering/forward_backward"], [self.states["/steering/left_right"]])
        _steering_forward_backward_0.setAction(self._steering_forward_backward_0_exec)
        _steering_forward_backward_0.setTrigger(None)
        _steering_forward_backward_0.setGuard(self._steering_forward_backward_0_guard)
        self.states["/steering/forward_backward"].addTransition(_steering_forward_backward_0)
        _steering_forward_backward_1 = Transition(self, self.states["/steering/forward_backward"], [self.states["/steering/left_right"]])
        _steering_forward_backward_1.setAction(self._steering_forward_backward_1_exec)
        _steering_forward_backward_1.setTrigger(None)
        _steering_forward_backward_1.setGuard(self._steering_forward_backward_1_guard)
        self.states["/steering/forward_backward"].addTransition(_steering_forward_backward_1)
        
        # transition /steering/left_right
        _steering_left_right_0 = Transition(self, self.states["/steering/left_right"], [self.states["/steering/wait"]])
        _steering_left_right_0.setAction(self._steering_left_right_0_exec)
        _steering_left_right_0.setTrigger(None)
        _steering_left_right_0.setGuard(self._steering_left_right_0_guard)
        self.states["/steering/left_right"].addTransition(_steering_left_right_0)
        _steering_left_right_1 = Transition(self, self.states["/steering/left_right"], [self.states["/steering/wait"]])
        _steering_left_right_1.setAction(self._steering_left_right_1_exec)
        _steering_left_right_1.setTrigger(None)
        _steering_left_right_1.setGuard(self._steering_left_right_1_guard)
        self.states["/steering/left_right"].addTransition(_steering_left_right_1)
        _steering_left_right_2 = Transition(self, self.states["/steering/left_right"], [self.states["/steering/wait"]])
        _steering_left_right_2.setAction(self._steering_left_right_2_exec)
        _steering_left_right_2.setTrigger(None)
        _steering_left_right_2.setGuard(self._steering_left_right_2_guard)
        self.states["/steering/left_right"].addTransition(_steering_left_right_2)
        
        # transition /steering/wait
        _steering_wait_0 = Transition(self, self.states["/steering/wait"], [self.states["/steering/forward_backward"]])
        _steering_wait_0.setTrigger(Event("_0after"))
        self.states["/steering/wait"].addTransition(_steering_wait_0)
        
        # transition /steering
        _steering_0 = Transition(self, self.states["/steering"], [self.states["/idle"]])
        _steering_0.setAction(self._steering_0_exec)
        _steering_0.setTrigger(None)
        _steering_0.setGuard(self._steering_0_guard)
        self.states["/steering"].addTransition(_steering_0)
    
    def _steering_wait_enter(self):
        self.addTimer(0, self.reaction_time)
    
    def _steering_wait_exit(self):
        self.removeTimer(0)
    
    def _steering_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'path_finder', Event("waypoint_reached", None, [])]))
    
    def _steering_0_guard(self, parameters):
        return self.pointReached()
    
    def _idle_0_exec(self, parameters):
        dest_waypoint = parameters[0]
        self.dest_waypoint = dest_waypoint
        self.dest_cell = self.map.calculateCell(dest_waypoint)
    
    def _steering_forward_backward_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'motor_control', Event("forward", None, [])]))
    
    def _steering_forward_backward_0_guard(self, parameters):
        return self.pointAhead()
    
    def _steering_forward_backward_1_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'motor_control', Event("stop", None, [])]))
    
    def _steering_forward_backward_1_guard(self, parameters):
        return self.pointBehind()
    
    def _steering_left_right_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'motor_control', Event("stop_turning", None, [])]))
    
    def _steering_left_right_0_guard(self, parameters):
        return self.pointStraight()
    
    def _steering_left_right_1_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'motor_control', Event("turn_left", None, [])]))
    
    def _steering_left_right_1_guard(self, parameters):
        return self.pointLeft()
    
    def _steering_left_right_2_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'motor_control', Event("turn_right", None, [])]))
    
    def _steering_left_right_2_guard(self, parameters):
        return self.pointRight()
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/idle"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class TurretSteering(RuntimeClassBase):
    def __init__(self, controller, tank):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # user defined attributes
        self.reaction_time = 0.05
        self.tank = None
        self.margin = None
        
        # call user defined constructor
        TurretSteering.user_defined_constructor(self, tank)
    
    def user_defined_constructor(self, tank):
        self.tank = tank
        self.margin = tank.cannonSpeed * D1
    
    def user_defined_destructor(self):
        pass
    
    
    # user defined method
    def pointRight(self):
        goal_angle = self.tank.angleToDest(self.target)
        diff = (self.tank.cannonAngle - goal_angle) % D360
        if diff >= self.margin and diff <= math.pi:
            return True
        return False
    
    
    # user defined method
    def pointLeft(self):
        goal_angle = self.tank.angleToDest(self.target)
        diff = (goal_angle - self.tank.cannonAngle) % D360
        if diff >= self.margin and diff <= math.pi:
            return True
        return False
    
    
    # user defined method
    def pointCorrect(self):
        goal_angle = self.tank.angleToDest(self.target)
        diff = math.fabs(goal_angle - self.tank.cannonAngle)
        if diff < self.margin or diff > (D360- self.margin):
            return True
        return False
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /idle
        self.states["/idle"] = State(1, "/idle", self)
        
        # state /aiming
        self.states["/aiming"] = State(2, "/aiming", self)
        
        # state /aiming/adjust
        self.states["/aiming/adjust"] = State(3, "/aiming/adjust", self)
        
        # state /aiming/wait
        self.states["/aiming/wait"] = State(4, "/aiming/wait", self)
        self.states["/aiming/wait"].setEnter(self._aiming_wait_enter)
        self.states["/aiming/wait"].setExit(self._aiming_wait_exit)
        
        # add children
        self.states[""].addChild(self.states["/idle"])
        self.states[""].addChild(self.states["/aiming"])
        self.states["/aiming"].addChild(self.states["/aiming/adjust"])
        self.states["/aiming"].addChild(self.states["/aiming/wait"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/idle"]
        self.states["/aiming"].default_state = self.states["/aiming/adjust"]
        
        # transition /idle
        _idle_0 = Transition(self, self.states["/idle"], [self.states["/aiming"]])
        _idle_0.setAction(self._idle_0_exec)
        _idle_0.setTrigger(Event("aim_at", None))
        self.states["/idle"].addTransition(_idle_0)
        
        # transition /aiming/adjust
        _aiming_adjust_0 = Transition(self, self.states["/aiming/adjust"], [self.states["/aiming/wait"]])
        _aiming_adjust_0.setAction(self._aiming_adjust_0_exec)
        _aiming_adjust_0.setTrigger(None)
        _aiming_adjust_0.setGuard(self._aiming_adjust_0_guard)
        self.states["/aiming/adjust"].addTransition(_aiming_adjust_0)
        _aiming_adjust_1 = Transition(self, self.states["/aiming/adjust"], [self.states["/aiming/wait"]])
        _aiming_adjust_1.setAction(self._aiming_adjust_1_exec)
        _aiming_adjust_1.setTrigger(None)
        _aiming_adjust_1.setGuard(self._aiming_adjust_1_guard)
        self.states["/aiming/adjust"].addTransition(_aiming_adjust_1)
        _aiming_adjust_2 = Transition(self, self.states["/aiming/adjust"], [self.states["/aiming/wait"]])
        _aiming_adjust_2.setAction(self._aiming_adjust_2_exec)
        _aiming_adjust_2.setTrigger(None)
        _aiming_adjust_2.setGuard(self._aiming_adjust_2_guard)
        self.states["/aiming/adjust"].addTransition(_aiming_adjust_2)
        
        # transition /aiming/wait
        _aiming_wait_0 = Transition(self, self.states["/aiming/wait"], [self.states["/aiming/adjust"]])
        _aiming_wait_0.setTrigger(Event("_0after"))
        self.states["/aiming/wait"].addTransition(_aiming_wait_0)
        
        # transition /aiming
        _aiming_0 = Transition(self, self.states["/aiming"], [self.states["/idle"]])
        _aiming_0.setAction(self._aiming_0_exec)
        _aiming_0.setTrigger(Event("stop_aiming", None))
        self.states["/aiming"].addTransition(_aiming_0)
        _aiming_1 = Transition(self, self.states["/aiming"], [self.states["/aiming"]])
        _aiming_1.setAction(self._aiming_1_exec)
        _aiming_1.setTrigger(Event("aim_at", None))
        self.states["/aiming"].addTransition(_aiming_1)
    
    def _aiming_wait_enter(self):
        self.addTimer(0, self.reaction_time)
    
    def _aiming_wait_exit(self):
        self.removeTimer(0)
    
    def _aiming_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'turret_control', Event("stop_turning", None, [])]))
    
    def _aiming_1_exec(self, parameters):
        target = parameters[0]
        self.target = target
    
    def _idle_0_exec(self, parameters):
        target = parameters[0]
        self.target = target
    
    def _aiming_adjust_0_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'turret_control', Event("turn_right", None, [])]))
    
    def _aiming_adjust_0_guard(self, parameters):
        return self.pointRight()
    
    def _aiming_adjust_1_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'turret_control', Event("turn_left", None, [])]))
    
    def _aiming_adjust_1_guard(self, parameters):
        return self.pointLeft()
    
    def _aiming_adjust_2_exec(self, parameters):
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'turret_control', Event("stop_turning", None, [])]))
        self.big_step.outputEventOM(Event("narrow_cast", None, [self, 'attack_planner', Event("ready_to_shoot", None, [])]))
    
    def _aiming_adjust_2_guard(self, parameters):
        return self.pointCorrect()
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/idle"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class MotorControl(RuntimeClassBase):
    def __init__(self, controller, tank):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # user defined attributes
        self.tank = None
        
        # call user defined constructor
        MotorControl.user_defined_constructor(self, tank)
    
    def user_defined_constructor(self, tank):
        self.tank = tank
    
    def user_defined_destructor(self):
        pass
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /control
        self.states["/control"] = ParallelState(1, "/control", self)
        
        # state /control/left_right
        self.states["/control/left_right"] = State(2, "/control/left_right", self)
        
        # state /control/left_right/stop
        self.states["/control/left_right/stop"] = State(3, "/control/left_right/stop", self)
        
        # state /control/left_right/going_forward
        self.states["/control/left_right/going_forward"] = State(4, "/control/left_right/going_forward", self)
        
        # state /control/left_right/going_backward
        self.states["/control/left_right/going_backward"] = State(5, "/control/left_right/going_backward", self)
        
        # state /control/forward_backward
        self.states["/control/forward_backward"] = State(6, "/control/forward_backward", self)
        
        # state /control/forward_backward/straight
        self.states["/control/forward_backward/straight"] = State(7, "/control/forward_backward/straight", self)
        
        # state /control/forward_backward/turning_left
        self.states["/control/forward_backward/turning_left"] = State(8, "/control/forward_backward/turning_left", self)
        
        # state /control/forward_backward/turning_right
        self.states["/control/forward_backward/turning_right"] = State(9, "/control/forward_backward/turning_right", self)
        
        # add children
        self.states[""].addChild(self.states["/control"])
        self.states["/control"].addChild(self.states["/control/left_right"])
        self.states["/control"].addChild(self.states["/control/forward_backward"])
        self.states["/control/left_right"].addChild(self.states["/control/left_right/stop"])
        self.states["/control/left_right"].addChild(self.states["/control/left_right/going_forward"])
        self.states["/control/left_right"].addChild(self.states["/control/left_right/going_backward"])
        self.states["/control/forward_backward"].addChild(self.states["/control/forward_backward/straight"])
        self.states["/control/forward_backward"].addChild(self.states["/control/forward_backward/turning_left"])
        self.states["/control/forward_backward"].addChild(self.states["/control/forward_backward/turning_right"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/control"]
        self.states["/control/left_right"].default_state = self.states["/control/left_right/stop"]
        self.states["/control/forward_backward"].default_state = self.states["/control/forward_backward/straight"]
        
        # transition /control/left_right/stop
        _control_left_right_stop_0 = Transition(self, self.states["/control/left_right/stop"], [self.states["/control/left_right/going_forward"]])
        _control_left_right_stop_0.setTrigger(Event("forward", None))
        self.states["/control/left_right/stop"].addTransition(_control_left_right_stop_0)
        _control_left_right_stop_1 = Transition(self, self.states["/control/left_right/stop"], [self.states["/control/left_right/going_backward"]])
        _control_left_right_stop_1.setTrigger(Event("backward", None))
        self.states["/control/left_right/stop"].addTransition(_control_left_right_stop_1)
        
        # transition /control/left_right/going_forward
        _control_left_right_going_forward_0 = Transition(self, self.states["/control/left_right/going_forward"], [self.states["/control/left_right/stop"]])
        _control_left_right_going_forward_0.setTrigger(Event("stop", None))
        self.states["/control/left_right/going_forward"].addTransition(_control_left_right_going_forward_0)
        _control_left_right_going_forward_1 = Transition(self, self.states["/control/left_right/going_forward"], [self.states["/control/left_right/going_backward"]])
        _control_left_right_going_forward_1.setTrigger(Event("backward", None))
        self.states["/control/left_right/going_forward"].addTransition(_control_left_right_going_forward_1)
        _control_left_right_going_forward_2 = Transition(self, self.states["/control/left_right/going_forward"], [self.states["/control/left_right/going_forward"]])
        _control_left_right_going_forward_2.setAction(self._control_left_right_going_forward_2_exec)
        _control_left_right_going_forward_2.setTrigger(Event("update", "engine"))
        self.states["/control/left_right/going_forward"].addTransition(_control_left_right_going_forward_2)
        
        # transition /control/left_right/going_backward
        _control_left_right_going_backward_0 = Transition(self, self.states["/control/left_right/going_backward"], [self.states["/control/left_right/stop"]])
        _control_left_right_going_backward_0.setTrigger(Event("stop", None))
        self.states["/control/left_right/going_backward"].addTransition(_control_left_right_going_backward_0)
        _control_left_right_going_backward_1 = Transition(self, self.states["/control/left_right/going_backward"], [self.states["/control/left_right/going_forward"]])
        _control_left_right_going_backward_1.setTrigger(Event("forward", None))
        self.states["/control/left_right/going_backward"].addTransition(_control_left_right_going_backward_1)
        _control_left_right_going_backward_2 = Transition(self, self.states["/control/left_right/going_backward"], [self.states["/control/left_right/going_backward"]])
        _control_left_right_going_backward_2.setAction(self._control_left_right_going_backward_2_exec)
        _control_left_right_going_backward_2.setTrigger(Event("update", "engine"))
        self.states["/control/left_right/going_backward"].addTransition(_control_left_right_going_backward_2)
        
        # transition /control/forward_backward/straight
        _control_forward_backward_straight_0 = Transition(self, self.states["/control/forward_backward/straight"], [self.states["/control/forward_backward/turning_right"]])
        _control_forward_backward_straight_0.setTrigger(Event("turn_right", None))
        self.states["/control/forward_backward/straight"].addTransition(_control_forward_backward_straight_0)
        _control_forward_backward_straight_1 = Transition(self, self.states["/control/forward_backward/straight"], [self.states["/control/forward_backward/turning_left"]])
        _control_forward_backward_straight_1.setTrigger(Event("turn_left", None))
        self.states["/control/forward_backward/straight"].addTransition(_control_forward_backward_straight_1)
        
        # transition /control/forward_backward/turning_left
        _control_forward_backward_turning_left_0 = Transition(self, self.states["/control/forward_backward/turning_left"], [self.states["/control/forward_backward/straight"]])
        _control_forward_backward_turning_left_0.setTrigger(Event("stop_turning", None))
        self.states["/control/forward_backward/turning_left"].addTransition(_control_forward_backward_turning_left_0)
        _control_forward_backward_turning_left_1 = Transition(self, self.states["/control/forward_backward/turning_left"], [self.states["/control/forward_backward/turning_right"]])
        _control_forward_backward_turning_left_1.setTrigger(Event("turn_right", None))
        self.states["/control/forward_backward/turning_left"].addTransition(_control_forward_backward_turning_left_1)
        _control_forward_backward_turning_left_2 = Transition(self, self.states["/control/forward_backward/turning_left"], [self.states["/control/forward_backward/turning_left"]])
        _control_forward_backward_turning_left_2.setAction(self._control_forward_backward_turning_left_2_exec)
        _control_forward_backward_turning_left_2.setTrigger(Event("update", "engine"))
        self.states["/control/forward_backward/turning_left"].addTransition(_control_forward_backward_turning_left_2)
        
        # transition /control/forward_backward/turning_right
        _control_forward_backward_turning_right_0 = Transition(self, self.states["/control/forward_backward/turning_right"], [self.states["/control/forward_backward/straight"]])
        _control_forward_backward_turning_right_0.setTrigger(Event("stop_turning", None))
        self.states["/control/forward_backward/turning_right"].addTransition(_control_forward_backward_turning_right_0)
        _control_forward_backward_turning_right_1 = Transition(self, self.states["/control/forward_backward/turning_right"], [self.states["/control/forward_backward/turning_left"]])
        _control_forward_backward_turning_right_1.setTrigger(Event("turn_left", None))
        self.states["/control/forward_backward/turning_right"].addTransition(_control_forward_backward_turning_right_1)
        _control_forward_backward_turning_right_2 = Transition(self, self.states["/control/forward_backward/turning_right"], [self.states["/control/forward_backward/turning_right"]])
        _control_forward_backward_turning_right_2.setAction(self._control_forward_backward_turning_right_2_exec)
        _control_forward_backward_turning_right_2.setTrigger(Event("update", "engine"))
        self.states["/control/forward_backward/turning_right"].addTransition(_control_forward_backward_turning_right_2)
    
    def _control_left_right_going_forward_2_exec(self, parameters):
        self.tank.moveUp()
    
    def _control_left_right_going_backward_2_exec(self, parameters):
        self.tank.moveDown()
    
    def _control_forward_backward_turning_left_2_exec(self, parameters):
        self.tank.turnLeft()
    
    def _control_forward_backward_turning_right_2_exec(self, parameters):
        self.tank.turnRight()
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/control"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class TurretControl(RuntimeClassBase):
    def __init__(self, controller, tank):
        RuntimeClassBase.__init__(self, controller)
        
        self.semantics.big_step_maximality = StatechartSemantics.TakeMany
        self.semantics.internal_event_lifeline = StatechartSemantics.Queue
        self.semantics.input_event_lifeline = StatechartSemantics.FirstComboStep
        self.semantics.priority = StatechartSemantics.SourceParent
        self.semantics.concurrency = StatechartSemantics.Single
        
        # build Statechart structure
        self.build_statechart_structure()
        
        # user defined attributes
        self.tank = None
        
        # call user defined constructor
        TurretControl.user_defined_constructor(self, tank)
    
    def user_defined_constructor(self, tank):
        self.tank = tank
    
    def user_defined_destructor(self):
        pass
    
    
    # builds Statechart structure
    def build_statechart_structure(self):
        
        # state <root>
        self.states[""] = State(0, "", self)
        
        # state /turret
        self.states["/turret"] = ParallelState(1, "/turret", self)
        
        # state /turret/rotation
        self.states["/turret/rotation"] = State(2, "/turret/rotation", self)
        
        # state /turret/rotation/none
        self.states["/turret/rotation/none"] = State(3, "/turret/rotation/none", self)
        
        # state /turret/rotation/turning_left
        self.states["/turret/rotation/turning_left"] = State(4, "/turret/rotation/turning_left", self)
        
        # state /turret/rotation/turning_right
        self.states["/turret/rotation/turning_right"] = State(5, "/turret/rotation/turning_right", self)
        
        # state /turret/shooting
        self.states["/turret/shooting"] = State(6, "/turret/shooting", self)
        
        # state /turret/shooting/polling
        self.states["/turret/shooting/polling"] = State(7, "/turret/shooting/polling", self)
        
        # add children
        self.states[""].addChild(self.states["/turret"])
        self.states["/turret"].addChild(self.states["/turret/rotation"])
        self.states["/turret"].addChild(self.states["/turret/shooting"])
        self.states["/turret/rotation"].addChild(self.states["/turret/rotation/none"])
        self.states["/turret/rotation"].addChild(self.states["/turret/rotation/turning_left"])
        self.states["/turret/rotation"].addChild(self.states["/turret/rotation/turning_right"])
        self.states["/turret/shooting"].addChild(self.states["/turret/shooting/polling"])
        self.states[""].fixTree()
        self.states[""].default_state = self.states["/turret"]
        self.states["/turret/rotation"].default_state = self.states["/turret/rotation/none"]
        self.states["/turret/shooting"].default_state = self.states["/turret/shooting/polling"]
        
        # transition /turret/rotation/none
        _turret_rotation_none_0 = Transition(self, self.states["/turret/rotation/none"], [self.states["/turret/rotation/turning_right"]])
        _turret_rotation_none_0.setTrigger(Event("turn_right", None))
        self.states["/turret/rotation/none"].addTransition(_turret_rotation_none_0)
        _turret_rotation_none_1 = Transition(self, self.states["/turret/rotation/none"], [self.states["/turret/rotation/turning_left"]])
        _turret_rotation_none_1.setTrigger(Event("turn_left", None))
        self.states["/turret/rotation/none"].addTransition(_turret_rotation_none_1)
        
        # transition /turret/rotation/turning_left
        _turret_rotation_turning_left_0 = Transition(self, self.states["/turret/rotation/turning_left"], [self.states["/turret/rotation/none"]])
        _turret_rotation_turning_left_0.setTrigger(Event("stop_turning", None))
        self.states["/turret/rotation/turning_left"].addTransition(_turret_rotation_turning_left_0)
        _turret_rotation_turning_left_1 = Transition(self, self.states["/turret/rotation/turning_left"], [self.states["/turret/rotation/turning_right"]])
        _turret_rotation_turning_left_1.setTrigger(Event("turn_right", None))
        self.states["/turret/rotation/turning_left"].addTransition(_turret_rotation_turning_left_1)
        _turret_rotation_turning_left_2 = Transition(self, self.states["/turret/rotation/turning_left"], [self.states["/turret/rotation/turning_left"]])
        _turret_rotation_turning_left_2.setAction(self._turret_rotation_turning_left_2_exec)
        _turret_rotation_turning_left_2.setTrigger(Event("update", "engine"))
        self.states["/turret/rotation/turning_left"].addTransition(_turret_rotation_turning_left_2)
        
        # transition /turret/rotation/turning_right
        _turret_rotation_turning_right_0 = Transition(self, self.states["/turret/rotation/turning_right"], [self.states["/turret/rotation/none"]])
        _turret_rotation_turning_right_0.setTrigger(Event("stop_turning", None))
        self.states["/turret/rotation/turning_right"].addTransition(_turret_rotation_turning_right_0)
        _turret_rotation_turning_right_1 = Transition(self, self.states["/turret/rotation/turning_right"], [self.states["/turret/rotation/turning_left"]])
        _turret_rotation_turning_right_1.setTrigger(Event("turn_left", None))
        self.states["/turret/rotation/turning_right"].addTransition(_turret_rotation_turning_right_1)
        _turret_rotation_turning_right_2 = Transition(self, self.states["/turret/rotation/turning_right"], [self.states["/turret/rotation/turning_right"]])
        _turret_rotation_turning_right_2.setAction(self._turret_rotation_turning_right_2_exec)
        _turret_rotation_turning_right_2.setTrigger(Event("update", "engine"))
        self.states["/turret/rotation/turning_right"].addTransition(_turret_rotation_turning_right_2)
        
        # transition /turret/shooting/polling
        _turret_shooting_polling_0 = Transition(self, self.states["/turret/shooting/polling"], [self.states["/turret/shooting/polling"]])
        _turret_shooting_polling_0.setAction(self._turret_shooting_polling_0_exec)
        _turret_shooting_polling_0.setTrigger(Event("shoot", None))
        self.states["/turret/shooting/polling"].addTransition(_turret_shooting_polling_0)
    
    def _turret_rotation_turning_left_2_exec(self, parameters):
        self.tank.turnCannonLeft()
    
    def _turret_rotation_turning_right_2_exec(self, parameters):
        self.tank.turnCannonRight()
    
    def _turret_shooting_polling_0_exec(self, parameters):
        self.tank.shoot()
    
    def initializeStatechart(self):
        # enter default state
        self.default_targets = self.states["/turret"].getEffectiveTargetStates()
        RuntimeClassBase.initializeStatechart(self)

class ObjectManager(ObjectManagerBase):
    def __init__(self, controller):
        ObjectManagerBase.__init__(self, controller)
    
    def instantiate(self, class_name, construct_params):
        if class_name == "Main":
            instance = Main(self.controller, construct_params[0])
            instance.associations = {}
            instance.associations["radar"] = Association("Radar", 1, 1)
            instance.associations["enemy_tracker"] = Association("EnemyTracker", 1, 1)
            instance.associations["pilot_strategy"] = Association("PilotStrategy", 1, 1)
            instance.associations["explore_planner"] = Association("ExplorePlanner", 1, 1)
            instance.associations["attack_planner"] = Association("AttackPlanner", 1, 1)
            instance.associations["path_finder"] = Association("PathFinder", 1, 1)
            instance.associations["steering"] = Association("Steering", 1, 1)
            instance.associations["turret_steering"] = Association("TurretSteering", 1, 1)
            instance.associations["motor_control"] = Association("MotorControl", 1, 1)
            instance.associations["turret_control"] = Association("TurretControl", 1, 1)
        elif class_name == "Radar":
            instance = Radar(self.controller, construct_params[0])
            instance.associations = {}
            instance.associations["enemy_tracker"] = Association("EnemyTracker", 1, 1)
            instance.associations["pilot_strategy"] = Association("PilotStrategy", 1, 1)
        elif class_name == "EnemyTracker":
            instance = EnemyTracker(self.controller)
            instance.associations = {}
            instance.associations["pilot_strategy"] = Association("PilotStrategy", 1, 1)
            instance.associations["attack_planner"] = Association("AttackPlanner", 1, 1)
        elif class_name == "PilotStrategy":
            instance = PilotStrategy(self.controller)
            instance.associations = {}
            instance.associations["explore_planner"] = Association("ExplorePlanner", 1, 1)
            instance.associations["attack_planner"] = Association("AttackPlanner", 1, 1)
        elif class_name == "ExplorePlanner":
            instance = ExplorePlanner(self.controller, construct_params[0], construct_params[1])
            instance.associations = {}
            instance.associations["path_finder"] = Association("PathFinder", 1, 1)
        elif class_name == "AttackPlanner":
            instance = AttackPlanner(self.controller)
            instance.associations = {}
            instance.associations["turret_steering"] = Association("TurretSteering", 1, 1)
            instance.associations["path_finder"] = Association("PathFinder", 1, 1)
            instance.associations["turret_control"] = Association("TurretControl", 1, 1)
        elif class_name == "PathFinder":
            instance = PathFinder(self.controller, construct_params[0], construct_params[1])
            instance.associations = {}
            instance.associations["steering"] = Association("Steering", 1, 1)
        elif class_name == "Steering":
            instance = Steering(self.controller, construct_params[0], construct_params[1])
            instance.associations = {}
            instance.associations["motor_control"] = Association("MotorControl", 1, 1)
            instance.associations["path_finder"] = Association("PathFinder", 1, 1)
        elif class_name == "TurretSteering":
            instance = TurretSteering(self.controller, construct_params[0])
            instance.associations = {}
            instance.associations["turret_control"] = Association("TurretControl", 1, 1)
            instance.associations["attack_planner"] = Association("AttackPlanner", 1, 1)
        elif class_name == "MotorControl":
            instance = MotorControl(self.controller, construct_params[0])
            instance.associations = {}
        elif class_name == "TurretControl":
            instance = TurretControl(self.controller, construct_params[0])
            instance.associations = {}
        else:
            raise Exception("Cannot instantiate class " + class_name)
        return instance

class Controller(EventLoopControllerBase):
    def __init__(self, tank, event_loop_callbacks, finished_callback = None, behind_schedule_callback = None):
        if finished_callback == None: finished_callback = None
        if behind_schedule_callback == None: behind_schedule_callback = None
        EventLoopControllerBase.__init__(self, ObjectManager(self), event_loop_callbacks, finished_callback, behind_schedule_callback)
        self.addInputPort("engine")
        self.object_manager.createInstance("Main", [tank])