Пример #1
0
 def __init__(self, x1, y1, x2, y2, color=(255, 255, 255)):
     self.p1 = Vector2D(x1, y1)
     self.p2 = Vector2D(x2, y2)
     self.vec = self.p2 - self.p1
     #print self.vec
     self.color = color
     self.thickness = 1
Пример #2
0
 def step(self, op: str, value: int) -> None:
     if op in DIRECTIONS:
         self.waypoint += value * DIRECTIONS[op]
     elif op == "R":
         angle = radians(-1 * value)
         self.waypoint = Vector2D(
             round(
                 self.waypoint.x * cos(angle) -
                 self.waypoint.y * sin(angle), 6),
             round(
                 self.waypoint.x * sin(angle) +
                 self.waypoint.y * cos(angle), 6))
     elif op == "L":
         angle = radians(value)
         self.waypoint = Vector2D(
             round(
                 self.waypoint.x * cos(angle) -
                 self.waypoint.y * sin(angle), 6),
             round(
                 self.waypoint.x * sin(angle) +
                 self.waypoint.y * cos(angle), 6))
     elif op == "F":
         self.pos += value * self.waypoint
     else:
         raise ValueError(f"Unrecognised operation: {op}")
 def add_rocket(self):
     rocket = Rocket(self.cwidth, self.cheight)
     rocket.rotation_speed = random.uniform(-.3,.3)
     rocket.engine_throttle = 1
     rocket.position = Vector2D((random.randint(-self.cwidth/2,self.cwidth/2), random.randint(0,self.cheight)))
     rocket.velocity = Vector2D((random.uniform(-10,10), random.uniform(-4,4)))
     self.rockets.append(rocket)
Пример #4
0
    def assignJump(self, bot, ballPred, game, action):
        mfhTime = self.maxFlightHalfTime
        count = int(mfhTime / 0.01)  # точность моделирования
        gameStub = copy.deepcopy(game)
        states = []
        for i in range(count):
            t = i * 0.01
            ballState = ballPred.predictedBall(game.ball, t)
            gameStub.ball = ballState
            strikePoint = self.getStrikePoint(gameStub)
            strikePt2D = Vector2D(strikePoint.x, strikePoint.z)
            botPt2D = Vector2D(bot.x + bot.velocity_x * t,
                               bot.z + bot.velocity_z * t)
            dst = (strikePt2D - botPt2D).len()
            states.append([t, strikePoint, dst])

        def elemVal(elem):
            return elem[2]

        minState = min(states, key=elemVal)

        if (minState[2] < 0.55):  # можно попробовать
            requiredY = minState[1].y
            print(minState, requiredY, end=' ')
            if (requiredY > self.maxReachableZ):
                return
            requiredVelY = ( requiredY - self.rules.ROBOT_MIN_RADIUS \
                             + self.rules.GRAVITY * minState[0] ** 2 / 2 ) / t
            #print(requiredVelY)
            if (requiredVelY > self.rules.ROBOT_MAX_JUMP_SPEED):
                return
            action.jump_speed = requiredVelY
Пример #5
0
 def setSize(self, width=0, height=0, radius=None):
     if radius:
         self.radius = radius
         self.size = Vector2D()
     else:
         self.size = Vector2D(width, height)
         self.max = self.min + self.size
         self.radius = None
Пример #6
0
    def draw_calls(self):
        def call(method, *vargs, **kwargs):
            return method, vargs, kwargs

        calls = []
        screen_offset = Vector2D((self.world_width / 2, 10))
        screen_offset += self.position
        scale = 6
        # rotate and position the rocket
        points = [Vector2D(xy) for xy in self.rocket_vertices]
        points = [
            v.rotate_around(self.rotation_point, self.rotation) for v in points
        ]
        points = [scale * v + screen_offset for v in points]
        points = [(v.x, self.world_height - v.y) for v in points]
        calls.append(
            call("create_polygon", points, fill="blue", outline="lightgrey"))
        if self.engine_throttle:
            # rotate and position the engine flame
            points = [
                Vector2D((x, y * self.engine_throttle))
                for x, y in self.engine_flame_vertices
            ]
            points = [
                v.rotate_around(self.rotation_point, self.rotation)
                for v in points
            ]
            points = [scale * v + screen_offset for v in points]
            points = [(v.x, self.world_height - v.y) for v in points]
            calls.append(
                call("create_polygon", points, outline="orange",
                     fill="yellow"))
        # rotate and position the left and right thrusters
        points = [Vector2D(xy) for xy in self.thruster_positions]
        points = [
            v.rotate_around(self.rotation_point, self.rotation) for v in points
        ]
        points = [scale * v + screen_offset for v in points]
        points = [(v.x, self.world_height - v.y) for v in points]
        if self.left_thruster_on:
            calls.append(
                call("create_oval",
                     points[0][0] - 3,
                     points[0][1] - 3,
                     points[0][0] + 3,
                     points[0][1] + 3,
                     outline="orange",
                     fill="yellow"))
        if self.right_thruster_on:
            calls.append(
                call("create_oval",
                     points[1][0] - 3,
                     points[1][1] - 3,
                     points[1][0] + 3,
                     points[1][1] + 3,
                     outline="orange",
                     fill="yellow"))
        return calls
Пример #7
0
 def __init__(self, x, y, ship_angle, screen):
     self.screen = screen
     self.speed = 16
     self.direction = ship_angle;
     self.velocity = Vector2D().create_from_angle(self.direction, self.speed, return_instance=True)
     self.pos = Vector2D(x, y)
     self.color = colors.green
     self.size = 4
     self.box = (0, 0, 0, 0)
Пример #8
0
 def nearest_coin(self):
     min_coin = None
     min_dist = Vector2D.magnitude(self.pacman.pos - Vector2D(self.coins[0].pos[0], self.coins[0].pos[1]))
     for c in self.coins:
         dist = Vector2D.magnitude(self.pacman.pos - Vector2D(c.pos[0], c.pos[1]))
         if dist <= min_dist:
             min_coin = c
             min_dist = dist
     return min_coin
Пример #9
0
 def nearest_ghost(self):
     min_ghost = None
     min_dist = Vector2D.magnitude(self.pacman.pos - self.ghosts[0].pos)
     for g in self.ghosts:
         dist = Vector2D.magnitude(self.pacman.pos - g.pos)
         if dist <= 128.0 and dist <= min_dist:
             min_ghost = g
             min_dist = dist
     return min_ghost
Пример #10
0
 def __init__(self, screen, pos=Vector2D(0, 0), size=24, vert_count=10):
     self.screen = screen
     self.pos = pos
     self.size = size
     self.color = colors.green
     self.velocity = Vector2D(0, 0)
     self.points = []
     self.generate_random_shape(vert_count)
     self.type = 1
Пример #11
0
    def doDecideJump(self, ballTrajectory, game, bot, action):
        if (ballTrajectory[0].tick != game.current_tick):
            print('doDecideJump(): trajectory error')
            return

        #pdb.set_trace()

        if (bot.z > game.ball.z or bot.touch == False):
            return

        # полагая, что робот прыгнет прям сейчас
        botMovePerTick = Vector2D(bot.velocity_x * self.tik,
                                  bot.velocity_z * self.tik)
        botStartRVec = Vector2D(bot.x, bot.z)
        radiusSum = self.rules.ROBOT_MIN_RADIUS + self.rules.BALL_RADIUS

        collisionTick = None

        for i in range(1, 32):
            botPos2d = botStartRVec + botMovePerTick * i
            ballPos2d = Vector2D(ballTrajectory[i].x, ballTrajectory[i].z)
            dst2d = (ballPos2d - botPos2d).len()
            if (dst2d < radiusSum):
                collisionTick = i
                break

        if (collisionTick == None):
            #pdb.set_trace()
            return

        # требуемая высота
        minDeltaH = (radiusSum**2 - dst2d**2)**0.5
        if (minDeltaH < 0):
            print('doDecideJump(): minDeltaH error')
            return
        #standardBotCY = game.ball.y - radiusSum + 0.5
        standardBotCY = ballTrajectory[i].y - radiusSum + 0.5
        if (standardBotCY < self.rules.ROBOT_MIN_RADIUS):
            # прыжок не требуется
            #pdb.set_trace()
            return
        # needed bot center y
        needBotCY = min(
            ballTrajectory[i].y - minDeltaH,  #max?
            standardBotCY)
        if (needBotCY > self.maxReachableZ):
            # не допрыгнем
            #pdb.set_trace()
            return
        jumpTicks, v0 = self.calculateJump(needBotCY)  # check
        #print(jumpTicks, v0)
        #if (jumpTicks == collisionTick):
        if (jumpTicks in [collisionTick, collisionTick - 1,
                          collisionTick + 1]):
            action.jump_speed = v0
Пример #12
0
 def set_touchdown_position(self, x_position):
     self.position = Vector2D((x_position, 0))
     self.velocity = Vector2D((0, 0))
     self.acceleration = Vector2D((0, 0))
     self.rotation = 0.0
     self.rotation_speed = 0.0
     self.rotation_acceleration = 0.0
     self.crashed = False
     self.touchdown = True
     self.engine_throttle = 0.0
     self.right_thruster_on = False
     self.left_thruster_on = False
Пример #13
0
    def __init__(self, x, y):
        self.ID = None
        #Position vectors that describe the shape of the box
        self.min = Vector2D(x, y)
        self.size = Vector2D()
        self.max = self.min + self.size
        self.radius = None

        #self.position = Vector2D(x, y)
        self.velocity = Vector2D()
        self.acceleration = Vector2D()
        self.Fnet = Vector2D()
Пример #14
0
 def __init__(self, x, y, screen):
     self.screen = screen
     self.pos = Vector2D(x, y)
     self.size = 18
     self.color = colors.green
     self.rotation = 0
     self.points = [
         (-self.size, self.size),
         (0, self.size / 3),
         (self.size, self.size),
         (0, -self.size)
     ]
     self.translate((self.pos.x, self.pos.y))
     self.velocity = Vector2D(0, 0)
     self.projectiles = []
Пример #15
0
 def __init__(self, pos, width, height):
     self.x, self.y = (pos)
     #self.coord = (self.x*width*1.0, self.y*height*1.0)
     self.position = Vector2D(self.x * width, self.y * height)
     self.neighbors = []
     self.target = None
     self.directions = []
Пример #16
0
    def __init__(self, position, drawer):

        self._matrix = [(None, None, 1, None), (None, None, 1, None),
                        (None, None, 1, None), (None, None, 1, None)]

        self._drawer = drawer
        self.position = Vector2D(position)
Пример #17
0
 def __init__(self, x, y):
     self.name = "pellet"
     self.position = Vector2D(x, y)
     self.color = YELLOW
     self.radius = 2
     self.value = 10
     self.draw = True
Пример #18
0
    def collide(self, other):
        # Exit early for optimization
        if (self.position - other.position).length() > max(self.width, self.height) + max(other.width, other.height):
            return False, None, None

        def project(vertices, axis):
            dots = [vertex.dot(axis) for vertex in vertices]
            return Vector2D(min(dots), max(dots))

        collision_depth = sys.maxsize
        collision_normal = None

        for edge in self.edges + other.edges:
            axis = Vector2D(edge).orthogonal().normalize()
            projection_1 = project(self.vertices, axis)
            projection_2 = project(other.vertices, axis)
            min_intersection = max(min(projection_1), min(projection_2))
            max_intersection = min(max(projection_1), max(projection_2))
            overlapping = min_intersection <= max_intersection
            if not overlapping:
                return False, None, None
            else:
                overlap = max_intersection - min_intersection
                if overlap < collision_depth:
                    collision_depth = overlap
                    collision_normal = axis
        return True, collision_depth, collision_normal
Пример #19
0
 def move_to(self, position):
     """
     Moves object to a target position
     :param position: an absolute target position
     """
     self._last_position = self.position
     self.position = Vector2D(position)
Пример #20
0
    def move(self, pacnode, nodelist, alg):
        new_node = self.find_node(nodelist)
        if (new_node):
            self.currentnode = new_node
            self.moving = False
        if (not self.moving):
            node = self.currentnode
            keyerrorFlag = False
            #this is to catch keyerror exception, as child key is not present always
            try:
                map = search_pacnode_by_alg(node, pacnode, alg)
                child = pacnode
                parent = pacnode
                while True:
                    parent = map[child]
                    if (parent == node):
                        break
                    else:
                        child = parent
            except:
                keyerrorFlag = True

            if not keyerrorFlag:
                direct = child.position - parent.position
                direct = direct.normalize()
                self.direction = direct
            else:
                self.direction = Vector2D(0, 0)
            self.moving = True

        self.pos += self.direction * self.speed
Пример #21
0
 def AddSegment(self, segment):
     '''Turn segment into unit vector perpendicular to segment'''
     self.segments.append(segment)
     if self.direction is None:
         d = Vector2D(segment.vec.y, segment.vec.x * -1)
         d = d.norm()
         self.direction = d
Пример #22
0
 def __init__(self, row, column):
     self.row, self.column = row, column
     self.position = Vector2D(column*WIDTH, row*HEIGHT)
     self.neighbors = {UP:None, DOWN:None, LEFT:None, RIGHT:None}
     self.portalNode = None
     self.home = False
     self.nowayUp = False
Пример #23
0
    def update_manual(self, nodelist):
        #if pacman position is same as any node then detect for key pressing
        node = self.find_node(nodelist)
        if (node):
            self.currentnode = node
            key_pressed = pygame.key.get_pressed()
            if (key_pressed[K_UP] and UP in node.directions):
                self.pos = node.position
                self.direction = UP
            elif (key_pressed[K_DOWN] and DOWN in node.directions):
                self.pos = node.position
                self.direction = DOWN
            elif (key_pressed[K_LEFT] and LEFT in node.directions):
                self.pos = node.position
                self.direction = LEFT
            elif (key_pressed[K_RIGHT] and RIGHT in node.directions):
                self.pos = node.position
                self.direction = RIGHT
            #if no key is pressed and current direction is not available..
            elif (self.direction not in node.directions):
                self.pos = node.position
                self.direction = Vector2D(0, 0)

        #code to update position
        self.pos += self.direction * self.speed
Пример #24
0
    def __init__(self, nodes, spritesheet, row):
        MazeRunner.__init__(self, nodes, spritesheet)
        self.name = "ghost"
        self.color = PINK
        self.goal = Vector2D()
        self.modeStack = self.setup_mode_stack()
        self.mode = self.modeStack.pop()
        self.modeTimer = 0
        self.spawnNode = self.find_spawn_node()
        self.set_guide_stack()
        self.set_start_position()
        self.points = 200
        self.released = True
        self.pelletsForRelease = 0
        self.bannedDirections = []
        self.speed = GHOST_SPEED

        self.animate = AnimationGroup()
        self.animateName = "left"
        self.define_animations(row)
        self.animate.set_animation(self.animateName, 0)
        self.image = self.animate.get_image()
        self.previousDirection = self.direction
        self.started = True
        self.hide = True
Пример #25
0
 def __init__(self, node, dim, pos=(0, 0)):
     AbstractEntity.__init__(self, dim, pos)
     self.COLOR = (255, 255, 0)
     self.direction = Vector2D(0, 0)
     self.speed = 3.2
     self.currentnode = node
     self.moving = False
     self.count_pacman_animate = 1
Пример #26
0
 def vertices(self):
     return [
         self.position + Vector2D(v).rotate(-self.angle) for v in (
             (-self.width / 2, -self.height / 2),
             (self.width / 2, -self.height / 2),
             (self.width / 2, self.height / 2),
             (-self.width / 2, self.height / 2)
         )
     ]
Пример #27
0
 def edges(self):
     return [
         Vector2D(v).rotate(self.angle) for v in (
             (self.width, 0),
             (0, self.height),
             (-self.width, 0),
             (0, -self.height),
         )
     ]
Пример #28
0
 def __init__(self, speed, node, color, dim, pos=(0, 0)):
     AbstractEntity.__init__(self, dim, pos)
     self.COLOR = color
     self.direction = Vector2D(0, 0)
     self.speed = speed
     self.currentnode = node
     self.moving = False
     self.scatter = False
     self.rand_move_count = 1
Пример #29
0
    def boost(self):
        # print(self.velocity.x, ',', self.velocity.y)
        force = Vector2D().create_from_angle(self.rotation, 0.1, True)

        # Limits the speed
        if (((self.velocity.x <= 4) and (self.velocity.x >= -4))
                or
                ((self.velocity.y <= 4) and (self.velocity.y >= -4))):
            self.velocity.add(force)
Пример #30
0
 def moveHomeNodes(self):
     nodeA = self.getNode(*MAZEDATA[self.level]["home"],
                          nodeList=self.nodeList)
     nodeB = nodeA.neighbors[LEFT]
     mid = (nodeA.position + nodeB.position) / 2.0
     mid = Vector2D(int(mid.x), int(mid.y))
     vec = Vector2D(self.homeList[0].position.x,
                    self.homeList[0].position.y)
     for node in self.homeList:
         node.position -= vec
         node.position += mid
     nodeA.neighbors[LEFT] = self.homeList[0]
     nodeB.neighbors[RIGHT] = self.homeList[0]
     self.homeList[0].neighbors[RIGHT] = nodeA
     self.homeList[0].neighbors[LEFT] = nodeB
     self.homeList[0].home = True
     ghostHome = self.homeList[0].neighbors[DOWN]
     MAZEDATA[self.level]["start"]["ghost"] = ghostHome.position.toTuple()
Пример #31
0
    def botToPoint(self, targetPoint, bot, action):
        # TODO добавить параметров
        botVec = Vector2D(bot.x, bot.z)
        vecToTarget = targetPoint - botVec

        velocityVec = vecToTarget.normalize(
        ) * self.rules.ROBOT_MAX_GROUND_SPEED
        action.target_velocity_x = velocityVec.x
        action.target_velocity_z = velocityVec.z
Пример #32
0
    def approxTimeToPoint(self, targetPoint, game, bot, timeAsTicks=True):
        botVec = Vector2D(bot.x, bot.z)
        vecToTarget = targetPoint - botVec

        # составляющие скорости мяча: проекция скорости на вектор, направленный
        # на целевую точку, и перпендикулярная ей составляющая
        # ( работаем только с направленной на точку )
        botVelocity = Vector2D(bot.velocity_x, bot.velocity_z)
        velTgtScalar = botVelocity.scalarProjectOn(vecToTarget)

        tToTarget = 0.0
        # время разворота
        if (velTgtScalar < 0):
            tToTarget += 2 * abs(velTgtScalar) / self.rules.ROBOT_ACCELERATION
            velTgtScalar = -velTgtScalar
        dst = vecToTarget.len()

        # время разгона
        tAccel = (self.rules.ROBOT_MAX_GROUND_SPEED - velTgtScalar) / \
                 self.rules.ROBOT_ACCELERATION
        sAccel = velTgtScalar * tAccel + \
                 self.rules.ROBOT_ACCELERATION * tAccel  ** 2 / 2
        #pdb.set_trace()
        if (sAccel < dst):
            tToTarget += tAccel + \
                            (dst - sAccel) / self.rules.ROBOT_MAX_GROUND_SPEED
        else:
            # придется потиково, ничего не поделать
            tik = 1 / self.rules.TICKS_PER_SECOND
            auxVelocity = self.rules.ROBOT_MAX_GROUND_SPEED
            while (sAccel < dst):
                auxVelocity -= tik * self.rules.ROBOT_ACCELERATION
                ds = auxVelocity * tik + \
                     self.rules.ROBOT_ACCELERATION * tik ** 2 / 2
                sAccel -= ds
                tAccel -= tik
                if (tAccel < 0):
                    print('approxTimeToPoint() unexpected behavior')
                    return tik if (timeAsTicks == False) else 1
            tToTarget = tAccel
        if (timeAsTicks == True):
            return round(tToTarget / self.tik)
        else:
            return tToTarget
Пример #33
0
    def make_key(self):
        s0 = 0
        s1 = 0
        s2 = 0
        s3 = 0
        s4 = 0
        s5 = 0
        s6 = 0
        s7 = 0
        s8 = 0
        s9 = 0
        directions  = self.pacman.currentnode.directions
        if Vector2D(-1, 0) in directions:
            global s0
            s0 = 1
        if Vector2D(1, 0) in directions:
            global s1
            s1 = 1
        if Vector2D(0, -1) in directions:
            global s2
            s2 = 1
        if Vector2D(0, 1) in directions:
            global s3
            s3 = 1
        #labels for directions
        avail_dirs = {(-1, 0):1, (1, 0):2, (0, -1):3, (0, 1):4}
        g = self.nearest_ghost()
        #if nearest ghost exists(distance lesser than some specified value)
        if g:
            global s4
            dmax = 64
            index = 0
            for i in range(len(self.pacman.currentnode.neighbors)):
                n = self.pacman.currentnode.neighbors[i]
                mdist = Vector2D.magnitude(n.position-g.pos)
                if (mdist >= dmax):
                    index = i
                    dmax = mdist
            preferred_direction = self.pacman.currentnode.directions[index]
            s4 = avail_dirs[(preferred_direction.x, preferred_direction.y)]
        else:
            c = self.nearest_coin()
            coinVector = Vector2D(c.pos[0], c.pos[1])
            global s4
            dmin = Vector2D.magnitude(self.pacman.pos - coinVector)
            index = 0
            for i in range(len(self.pacman.currentnode.neighbors)):
                n = self.pacman.currentnode.neighbors[i]
                mdist = Vector2D.magnitude(n.position-coinVector)
                if (mdist <= dmin):
                    index = i
                    dmin = mdist
            preferred_direction = self.pacman.currentnode.directions[index]

            s4 = avail_dirs[(preferred_direction.x, preferred_direction.y)]
        #following block to see from which direction ghost approaches
        for g in self.ghosts:
            if Vector2D(-1, 0).dotpro(g.direction) == -1 and \
                            (self.pacman.currentnode.position-g.currentnode.position).normalize().dotpro(g.direction) == 1:
                global s5
                s5 = 1
            if Vector2D(1, 0).dotpro(g.direction) == -1 and \
                            (self.pacman.currentnode.position-g.currentnode.position).normalize().dotpro(g.direction) == 1:
                global s6
                s6 = 1
            if Vector2D(0, -1).dotpro(g.direction) == -1 and \
                            (self.pacman.currentnode.position-g.currentnode.position).normalize().dotpro(g.direction) == 1:
                global s7
                s7 = 1
            if Vector2D(0, 1).dotpro(g.direction) == -1 and \
                            (self.pacman.currentnode.position-g.currentnode.position).normalize().dotpro(g.direction) == 1:
                global s8
                s8 = 1

        traplist = []
        if Vector2D(-1, 0) in directions:
            global s5
            traplist.append(s5)
        if Vector2D(1, 0) in directions:
            global s6
            traplist.append(s6)
        if Vector2D(0, -1) in directions:
            global s7
            traplist.append(s7)
        if Vector2D(0, 1) in directions:
            traplist.append(s8)

        if len(traplist) == sum(traplist):
            global s9
            s9 = 1

        key = [str(s0), str(s1), str(s2), str(s3), str(s4), str(s5), str(s6), str(s7), str(s8), str(s9)]
        return ''.join(key)
Пример #34
0
 def find_node(self, nodelist):
     for n in nodelist:
        if Vector2D.magnitude(self.pos-n.position) <= 0.1:
            return n
     return None