Exemplo n.º 1
0
 def handleEvent(self, event):
     if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
         m_pos = screenspace_to_worldspace(event.pos)
         shapes = World.instance.space.point_query(
             [float(v) for v in m_pos], 0.0,
             pymunk.ShapeFilter(mask=DYNAMIC_CATEGORY))
         if shapes:
             max_z = max(pq.shape.obj.clickZ for pq in shapes)
             shapes = [pq for pq in shapes if pq.shape.obj.clickZ == max_z]
             self.obj = shapes[0].shape.obj
             if getattr(self.obj, "clickable", True):
                 self.obj.body.velocity = [0.0, 0.0]
                 self.obj_grabbed = True
                 self.obj_rel_pos = self.obj.position - m_pos
                 self.obj_m_pos = m_pos
     if event.type == pygame.MOUSEBUTTONUP and event.button == 1 and self.obj_grabbed:
         self.obj_grabbed = False
         # Give velocity based on previous mouse positions.
         if self.position_length != 0:
             differences = sum(
                 (x + 1) / self.position_length *
                 (self.positions[
                     (self.position_index + x + 1) % self.TOTAL_POSITIONS] -
                  self.positions[
                      (self.position_index + x) % self.TOTAL_POSITIONS])
                 for x in range(self.position_length - 1))
             # Sum will return 0 if position length is 0 - we need to handle this.
             if isinstance(differences, int):
                 differences = np.array([0, 0])
             self.obj.body.velocity = [
                 self.VELOCITY_MULT * d for d in differences
             ]
     if event.type == pygame.MOUSEMOTION and self.obj_grabbed:
         self.obj_m_pos = screenspace_to_worldspace(event.pos)
Exemplo n.º 2
0
    def handleEvent(self, event):
        if event.type == pygame.KEYDOWN and event.key == pygame.K_p:
            # Toggle pause state.
            World.instance.paused = not World.instance.paused

        if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
            m_pos = screenspace_to_worldspace(event.pos)
            shapes = World.instance.space.point_query(
                m_pos, 0.0,
                pymunk.ShapeFilter(mask=pymunk.ShapeFilter.ALL_MASKS
                                   ^ DYNAMIC_CATEGORY))
            if shapes:
                max_z = max(pq.shape.obj.clickZ for pq in shapes)
                shapes = [pq for pq in shapes if pq.shape.obj.clickZ == max_z]
            for shape in shapes:
                if shape.shape.obj.key == "controlsPause":
                    self._pressed = True

        if event.type == pygame.MOUSEBUTTONUP and event.button == 1:
            m_pos = screenspace_to_worldspace(event.pos)
            shapes = World.instance.space.point_query(
                m_pos, 0.0,
                pymunk.ShapeFilter(mask=pymunk.ShapeFilter.ALL_MASKS
                                   ^ DYNAMIC_CATEGORY))
            if shapes:
                max_z = max(pq.shape.obj.clickZ for pq in shapes)
                shapes = [pq for pq in shapes if pq.shape.obj.clickZ == max_z]
            for shape in shapes:
                if (shape.shape.obj.key == "controlsPause") & self._pressed:
                    # Toggle pause state.
                    World.instance.paused = not World.instance.paused
                self._pressed = False
            if len(shapes) == 0:
                self._pressed = False
Exemplo n.º 3
0
    def handleEvent(self, event):
        if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
            m_pos = screenspace_to_worldspace(event.pos)
            shapes = World.instance.space.point_query(
                m_pos, 0.0, pymunk.ShapeFilter(mask=STATIC_CATEGORY))
            for shape in shapes:
                for team in range(len(self.names)):
                    if shape.shape.obj.key.startswith(f"score{team+1}"):
                        action = shape.shape.obj.key.split(str(team + 1))[1]
                        if action == "Plus":
                            self.team_scores[team] += 1
                        elif action == "Minus":
                            if self.team_scores[team] > 0:
                                self.team_scores[team] -= 1
                        else:
                            raise ValueError(f"Unknown team action {action}")
                        self.updateScoreText()
                if shape.shape.obj.key == "controlsReset":
                    self._pressed = True

        if event.type == pygame.MOUSEBUTTONUP and event.button == 1:
            m_pos = screenspace_to_worldspace(event.pos)
            shapes = World.instance.space.point_query(
                m_pos, 0.0, pymunk.ShapeFilter(mask=STATIC_CATEGORY))
            for shape in shapes:
                if (shape.shape.obj.key == "controlsReset") & self._pressed:
                    self.reset()
                self._pressed = False
            if len(shapes) == 0:
                self._pressed = False
Exemplo n.º 4
0
    def handleEvent(self, event):
        if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
            m_pos = screenspace_to_worldspace(event.pos)
            shapes = World.instance.space.point_query(
                m_pos, 0.0, pymunk.ShapeFilter(mask=STATIC_CATEGORY))
            for shape in shapes:
                for team in range(len(self.names)):
                    if shape.shape.obj.key.startswith(f"score{team+1}"):
                        action = shape.shape.obj.key.split(str(team + 1))[1]
                        if action == "Plus":
                            self.team_scores[team] += 1
                        elif action == "Minus":
                            if self.team_scores[team] > 0:
                                self.team_scores[team] -= 1
                        else:
                            raise ValueError(f"Unknown team action {action}")
                        self.updateScoreText()
                    for index in range(self.BOTS_PER_TEAM):
                        if team * self.BOTS_PER_TEAM + index < len(
                                self.robots):
                            if shape.shape.obj.key == f"UI-penalty-{team * self.BOTS_PER_TEAM + index}":
                                self.finishPenalty(team * self.BOTS_PER_TEAM +
                                                   index)
                if shape.shape.obj.key == "controlsReset":
                    self._pressed = True

        if event.type == pygame.MOUSEMOTION:
            m_pos = screenspace_to_worldspace(event.pos)
            shapes = World.instance.space.point_query(
                m_pos, 0.0, pymunk.ShapeFilter(mask=STATIC_CATEGORY))
            for team in range(len(self.names)):
                for index in range(self.BOTS_PER_TEAM):
                    for shape in shapes:
                        if shape.shape.obj.key == f"UI-penalty-{team * self.BOTS_PER_TEAM + index}":
                            shape.shape.obj.visual.fill = "penalty_ui_bg_hover"
                            break
                    else:
                        key = f"UI-penalty-{team * self.BOTS_PER_TEAM + index}"
                        if key in ScriptLoader.instance.object_map:
                            ScriptLoader.instance.object_map[
                                key].visual.fill = "penalty_ui_bg"

        if event.type == pygame.MOUSEBUTTONUP and event.button == 1:
            m_pos = screenspace_to_worldspace(event.pos)
            shapes = World.instance.space.point_query(
                m_pos, 0.0, pymunk.ShapeFilter(mask=STATIC_CATEGORY))
            for shape in shapes:
                if (shape.shape.obj.key == "controlsReset") & self._pressed:
                    self.reset()
                self._pressed = False
            if len(shapes) == 0:
                self._pressed = False
Exemplo n.º 5
0
 def calculatePoints(self):
     relative_scale = ScreenObjectManager.instance.relativeScreenScale()
     new_size = [int(self.image.get_size()[0] * self.scale * relative_scale[0]), int(self.image.get_size()[1] * self.scale * relative_scale[1])]
     scaled = pygame.transform.scale(self.image, new_size)
     self.rotated = pygame.transform.rotate(scaled, self.rotation * 180 / np.pi)
     self.rotated.fill(self.fill, special_flags=pygame.BLEND_ADD)
     self.screen_location = utils.worldspace_to_screenspace(self.position)
     self.screen_size = self.rotated.get_size()
     if self.hAlignment == 'l':
         pass
     elif self.hAlignment == 'm':
         self.screen_location -= np.array([self.screen_size[0] / 2, 0.0])
     elif self.hAlignment == 'r':
         self.screen_location -= np.array([self.screen_size[0], 0.0])
     else:
         raise ValueError(f'hAlignment is incorrect: {self.hAlignment}')
     if self.vAlignment == 't':
         pass
     elif self.vAlignment == 'm':
         self.screen_location -= np.array([0.0, self.screen_size[1] / 2])
     elif self.vAlignment == 'b':
         self.screen_location -= np.array([0.0, self.screen_size[1]])
     else:
         raise ValueError(f'vAlignment is incorrect: {self.vAlignment}')
     from ev3sim.visual.utils import screenspace_to_worldspace
     physics_size = screenspace_to_worldspace([ScreenObjectManager.instance.screen_width / 2 + self.screen_size[0], ScreenObjectManager.instance.screen_height / 2 + self.screen_size[1]])
     self.verts = [
         (physics_size[0]/2, physics_size[1]/2),
         (physics_size[0]/2, -physics_size[1]/2),
         (-physics_size[0]/2, -physics_size[1]/2),
         (-physics_size[0]/2, physics_size[1]/2),
     ]
Exemplo n.º 6
0
    def getPositionAnchorOffset(self):
        res = np.array([0.0, 0.0])
        from ev3sim.visual.utils import screenspace_to_worldspace

        physics_size = screenspace_to_worldspace(
            [
                ScreenObjectManager.instance._SCREEN_WIDTH_ACTUAL / 2 + self.screen_size[0],
                ScreenObjectManager.instance._SCREEN_HEIGHT_ACTUAL / 2 + self.screen_size[1],
            ]
        )
        if self.hAlignment == "l":
            res += np.array([physics_size[0] / 2, 0.0])
        elif self.hAlignment == "m":
            pass
        elif self.hAlignment == "r":
            res -= np.array([physics_size[0] / 2, 0.0])
        else:
            raise ValueError(f"hAlignment is incorrect: {self.hAlignment}")
        if self.vAlignment == "t":
            res += np.array([0.0, physics_size[1] / 2])
        elif self.vAlignment == "m":
            pass
        elif self.vAlignment == "b":
            res -= np.array([0.0, physics_size[1] / 2])
        else:
            raise ValueError(f"vAlignment is incorrect: {self.vAlignment}")
        return res
Exemplo n.º 7
0
 def toTilePos(self, mpos):
     new_pos = utils.screenspace_to_worldspace(mpos, self.customMap)
     new_pos = [
         new_pos[0] - self.tile_offset[0], new_pos[1] - self.tile_offset[1]
     ]
     return int((new_pos[0] + 105) // 30 -
                3), int((new_pos[1] + 105) // 30 - 3)
 def handleEvent(self, event):
     super().handleEvent(event)
     if event.type == EV3SIM_PRINT:
         m = event.message.rstrip()
         if m.endswith("Prize!"):
             try:
                 result = m.split()[0]
                 for i, response in enumerate(self.RESPONSES):
                     if response == result:
                         ScriptLoader.instance.object_map["prize_box"].fill = f"area_{i+1}_color"
                         ScriptLoader.instance.object_map["prize_output"].text = response
                 else:
                     pass
             except:
                 pass
     if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
         m_pos = screenspace_to_worldspace(event.pos)
         shapes = World.instance.space.point_query(
             [float(v) for v in m_pos], 0.0, pymunk.ShapeFilter(mask=STATIC_CATEGORY)
         )
         if shapes:
             max_z = max(pq.shape.obj.clickZ for pq in shapes)
             shapes = [pq for pq in shapes if pq.shape.obj.clickZ == max_z]
         for shape in shapes:
             if shape.shape.obj.key == "drop":
                 self.dropBall(m_pos)
Exemplo n.º 9
0
 def handleEvent(self, event):
     if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
         m_pos = screenspace_to_worldspace(event.pos)
         shapes = World.instance.space.point_query(
             m_pos, 0.0,
             pymunk.ShapeFilter(mask=pymunk.ShapeFilter.ALL_MASKS
                                ^ STATIC_CATEGORY))
         if shapes:
             max_z = max(pq.shape.obj.clickZ for pq in shapes)
             shapes = [pq for pq in shapes if pq.shape.obj.clickZ == max_z]
             self.obj = shapes[0].shape.obj
             if getattr(self.obj, "clickable", True):
                 self.obj.body.velocity = np.array([0.0, 0.0])
                 self.obj_grabbed = True
                 self.obj_rel_pos = self.obj.position - m_pos
                 self.obj_m_pos = m_pos
     if event.type == pygame.MOUSEBUTTONDOWN and event.button == 3:
         # If a robot is right clicked, copy it's ID for use in the attach script.
         m_pos = screenspace_to_worldspace(event.pos)
         shapes = World.instance.space.point_query(
             m_pos, 0.0,
             pymunk.ShapeFilter(mask=pymunk.ShapeFilter.ALL_MASKS
                                ^ STATIC_CATEGORY))
         if shapes:
             max_z = max(pq.shape.obj.clickZ for pq in shapes)
             shapes = [pq for pq in shapes if pq.shape.obj.clickZ == max_z]
             self.obj = shapes[0].shape.obj
             if hasattr(self.obj, "robot_class"):
                 pyperclip.copy(self.obj.robot_class.ID)
     if event.type == pygame.MOUSEBUTTONUP and event.button == 1 and self.obj_grabbed:
         self.obj_grabbed = False
         # Give velocity based on previous mouse positions.
         if self.position_length != 0:
             differences = sum(
                 (x + 1) / self.position_length *
                 (self.positions[
                     (self.position_index + x + 1) % self.TOTAL_POSITIONS] -
                  self.positions[
                      (self.position_index + x) % self.TOTAL_POSITIONS])
                 for x in range(self.position_length - 1))
             # Sum will return 0 if position length is 0 - we need to handle this.
             if isinstance(differences, int):
                 differences = np.array([0, 0])
             self.obj.body.velocity = self.VELOCITY_MULT * differences
     if event.type == pygame.MOUSEMOTION and self.obj_grabbed:
         self.obj_m_pos = screenspace_to_worldspace(event.pos)
Exemplo n.º 10
0
 def handleEvent(self, event):
     if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
         m_pos = screenspace_to_worldspace(event.pos)
         shapes = World.instance.space.point_query(
             [float(v) for v in m_pos], 0.0, pymunk.ShapeFilter(mask=STATIC_CATEGORY)
         )
         for shape in shapes:
             if shape.shape.obj.key == "controlsReset":
                 self._pressed = True
             words = shape.shape.obj.key.split("-")
             if len(words) == 3 and words[0] == "Tile" and words[2] == "UI":
                 tile_index = int(words[1])
                 self.spawnAt(tile_index)
     if event.type == pygame.MOUSEBUTTONUP and event.button == 1:
         m_pos = screenspace_to_worldspace(event.pos)
         shapes = World.instance.space.point_query(
             [float(v) for v in m_pos], 0.0, pymunk.ShapeFilter(mask=STATIC_CATEGORY)
         )
         for shape in shapes:
             if (shape.shape.obj.key == "controlsReset") & self._pressed:
                 self.reset()
         self._pressed = False
     if event.type == pygame.MOUSEMOTION:
         m_pos = screenspace_to_worldspace(event.pos)
         shapes = World.instance.space.point_query(
             [float(v) for v in m_pos], 0.0, pymunk.ShapeFilter(mask=STATIC_CATEGORY)
         )
         for shape in shapes:
             words = shape.shape.obj.key.split("-")
             if len(words) == 3 and words[0] == "Tile" and words[2] == "UI":
                 tile_index = int(words[1])
                 # Highlight at tile.
                 if self.hover_rect.key not in ScreenObjectManager.instance.objects:
                     ScreenObjectManager.instance.registerVisual(self.hover_rect, self.hover_rect.key)
                 self.hover_rect.position = self.tiles[tile_index]["world_pos"]
                 break
         else:
             if self.hover_rect.key in ScreenObjectManager.instance.objects:
                 ScreenObjectManager.instance.unregisterVisual(self.hover_rect.key)
Exemplo n.º 11
0
 def handleEvent(self, event):
     if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
         m_pos = screenspace_to_worldspace(event.pos)
         shapes = World.instance.space.point_query(
             m_pos, 0.0, pymunk.ShapeFilter(mask=DYNAMIC_CATEGORY))
         if shapes:
             max_z = max(pq.shape.obj.clickZ for pq in shapes)
             shapes = [pq for pq in shapes if pq.shape.obj.clickZ == max_z]
             for pq in shapes:
                 if pq.shape.obj.key == self.generated[0].key:
                     self.device_class.pressed = True
                     self.generated[
                         0].visual.fill = "BUTTON_back_color_press"
     if event.type == pygame.MOUSEBUTTONUP and event.button == 1:
         self.device_class.pressed = False
         self.generated[0].visual.fill = "BUTTON_back_color_release"
Exemplo n.º 12
0
    def calculatePoints(self):
        relative_scale = ScreenObjectManager.instance.relativeScreenScale()
        # In order to have a reasonably sized image at all resolutions, calculate the scale to use based on the starting screen scale as well.
        relative_scale = relative_scale * ScreenObjectManager.instance.original_SCREEN_WIDTH / 1280
        new_size = [
            int(self.image.get_size()[0] * self.scale * relative_scale),
            int(self.image.get_size()[1] * self.scale * relative_scale),
        ]
        scaled = pygame.transform.scale(self.image, new_size)
        self.rotated = pygame.transform.rotate(scaled, self.rotation * 180 / np.pi)
        self.rotated.fill(self.fill, special_flags=pygame.BLEND_ADD)
        self.screen_location = utils.worldspace_to_screenspace(self.position)
        self.screen_size = self.rotated.get_size()
        if self.hAlignment == "l":
            pass
        elif self.hAlignment == "m":
            self.screen_location -= np.array([self.screen_size[0] / 2, 0.0])
        elif self.hAlignment == "r":
            self.screen_location -= np.array([self.screen_size[0], 0.0])
        else:
            raise ValueError(f"hAlignment is incorrect: {self.hAlignment}")
        if self.vAlignment == "t":
            pass
        elif self.vAlignment == "m":
            self.screen_location -= np.array([0.0, self.screen_size[1] / 2])
        elif self.vAlignment == "b":
            self.screen_location -= np.array([0.0, self.screen_size[1]])
        else:
            raise ValueError(f"vAlignment is incorrect: {self.vAlignment}")
        from ev3sim.visual.utils import screenspace_to_worldspace

        physics_size = screenspace_to_worldspace(
            [
                ScreenObjectManager.instance._SCREEN_WIDTH_ACTUAL / 2 + self.screen_size[0],
                ScreenObjectManager.instance._SCREEN_HEIGHT_ACTUAL / 2 + self.screen_size[1],
            ]
        )
        self.verts = [
            (physics_size[0] / 2, physics_size[1] / 2),
            (physics_size[0] / 2, -physics_size[1] / 2),
            (-physics_size[0] / 2, -physics_size[1] / 2),
            (-physics_size[0] / 2, physics_size[1] / 2),
        ]
Exemplo n.º 13
0
 def getPositionAnchorOffset(self):
     res = np.array([.0, .0])
     from ev3sim.visual.utils import screenspace_to_worldspace
     physics_size = screenspace_to_worldspace([ScreenObjectManager.instance.screen_width / 2 + self.screen_size[0], ScreenObjectManager.instance.screen_height / 2 + self.screen_size[1]])
     if self.hAlignment == 'l':
         res += np.array([physics_size[0] / 2, 0.0])
     elif self.hAlignment == 'm':
         pass
     elif self.hAlignment == 'r':
         res -= np.array([physics_size[0] / 2, 0.0])
     else:
         raise ValueError(f'hAlignment is incorrect: {self.hAlignment}')
     if self.vAlignment == 't':
         res += np.array([0.0, physics_size[1] / 2])
     elif self.vAlignment == 'm':
         pass
     elif self.vAlignment == 'b':
         res -= np.array([0.0, physics_size[1] / 2])
     else:
         raise ValueError(f'vAlignment is incorrect: {self.vAlignment}')
     return res
Exemplo n.º 14
0
 def handleEvent(self, event):
     if self.mode == self.MODE_NORMAL or self.mode == self.MODE_CAN_DRAGGING:
         button_filter = lambda x: True
     else:
         button_filter = lambda x: False
     super().handleEvent(event, button_filter=button_filter)
     if self.mode == self.MODE_NORMAL:
         if event.type == pygame.MOUSEMOTION:
             self.current_mpos = event.pos
         elif event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
             world_mpos = utils.screenspace_to_worldspace(
                 self.current_mpos, self.customMap)
             vec = [
                 self.can_obj.position[0] - world_mpos[0],
                 self.can_obj.position[1] - world_mpos[1],
             ]
             d = magnitude_sq(vec)
             if d <= pow(2.5, 2):
                 self.mode = self.MODE_CAN_DRAGGING
                 self.rel_pos = vec
                 return
             if self.current_mpos[0] > self.side_width:
                 self.selectTile(self.toTilePos(self.current_mpos))
         elif event.type == pygame.MOUSEWHEEL:
             for attr, conv, inc in [
                 ("rotation_entry", int, 90),
             ]:
                 if hasattr(self, attr):
                     rect = getattr(self, attr).get_relative_rect()
                     if (rect.left <= self.current_mpos[0] <= rect.right
                             and rect.top <= self.current_mpos[1] <=
                             rect.bottom):
                         try:
                             val = conv(getattr(self, attr).text)
                             val += event.y * inc
                             getattr(self, attr).set_text(str(val))
                         except:
                             pass
         elif event.type == pygame.KEYDOWN:
             if event.key == pygame.K_BACKSPACE or event.key == pygame.K_DELETE:
                 # Check that no entry is focused.
                 good = True
                 for attr in [
                         "rotation_entry",
                 ]:
                     if hasattr(self, attr) and getattr(self,
                                                        attr).is_focused:
                         good = False
                 if good:
                     self.removeSelected()
     elif self.mode == self.MODE_CAN_DRAGGING:
         if event.type == pygame.MOUSEBUTTONUP and event.button == 1:
             self.mode = self.MODE_NORMAL
             return
         elif event.type == pygame.MOUSEMOTION:
             self.current_mpos = event.pos
             world_mpos = utils.screenspace_to_worldspace(
                 self.current_mpos, self.customMap)
             self.can_obj.position = [
                 self.rel_pos[0] + world_mpos[0],
                 self.rel_pos[1] + world_mpos[1],
             ]
             self.previous_info["settings"]["rescue"][
                 "CAN_SPAWN_POSITION"] = [
                     float(self.can_obj.position[0] - self.tile_offset[0]),
                     float(self.can_obj.position[1] - self.tile_offset[1]),
                 ]
Exemplo n.º 15
0
    def handleEvent(self, event):
        if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
            m_pos = screenspace_to_worldspace(event.pos)
            shapes = World.instance.space.point_query(
                [float(v) for v in m_pos], 0.0,
                pymunk.ShapeFilter(mask=STATIC_CATEGORY))
            for shape in shapes:
                for team in range(len(SoccerUIInteractor.instance.names)):
                    # Goal change functionality
                    if shape.shape.obj.key.startswith(f"score{team+1}"):
                        action = shape.shape.obj.key.split(str(team + 1))[1]
                        if action == "Plus":
                            SoccerLogicInteractor.instance.team_scores[
                                team] += 1
                        elif action == "Minus":
                            if SoccerLogicInteractor.instance.team_scores[
                                    team] > 0:
                                SoccerLogicInteractor.instance.team_scores[
                                    team] -= 1
                        else:
                            raise ValueError(f"Unhandled team action {action}")
                        SoccerUIInteractor.instance.updateScoreText(
                            SoccerLogicInteractor.instance.team_scores)
                    # Early penalty end
                    for index in range(
                            SoccerLogicInteractor.instance.BOTS_PER_TEAM):
                        actual_index = team + index * len(
                            SoccerUIInteractor.instance.names)
                        if actual_index < len(self.robots):
                            if shape.shape.obj.key == f"UI-penalty-{actual_index}":
                                SoccerLogicInteractor.instance.finishPenalty(
                                    actual_index)
                if shape.shape.obj.key == "controlsReset":
                    SoccerUIInteractor.instance.onResetPressed()

        if event.type == pygame.MOUSEMOTION:
            m_pos = screenspace_to_worldspace(event.pos)
            shapes = World.instance.space.point_query(
                [float(v) for v in m_pos], 0.0,
                pymunk.ShapeFilter(mask=STATIC_CATEGORY))
            # Penalty UI hover colour.
            for team in range(len(SoccerUIInteractor.instance.names)):
                for index in range(
                        SoccerLogicInteractor.instance.BOTS_PER_TEAM):
                    actual_index = team + index * len(
                        SoccerUIInteractor.instance.names)
                    for shape in shapes:
                        if shape.shape.obj.key == f"UI-penalty-{team + index * len(SoccerUIInteractor.instance.names)}":
                            shape.shape.obj.visual.fill = "penalty_ui_bg_hover"
                            break
                    else:
                        key = f"UI-penalty-{team + index * len(SoccerUIInteractor.instance.names)}"
                        if key in ScriptLoader.instance.object_map:
                            ScriptLoader.instance.object_map[
                                key].visual.fill = "penalty_ui_bg"

        if event.type == pygame.MOUSEBUTTONUP and event.button == 1:
            m_pos = screenspace_to_worldspace(event.pos)
            shapes = World.instance.space.point_query(
                [float(v) for v in m_pos], 0.0,
                pymunk.ShapeFilter(mask=STATIC_CATEGORY))
            reset_hovered = False
            for shape in shapes:
                if shape.shape.obj.key == "controlsReset":
                    reset_hovered = True
            SoccerUIInteractor.instance.onResetReleased(reset_hovered)