Pygame吃豆子-敌人随机运动

福西特-福西特

我已经使用python和pygame制作了一个吃豆人游戏,而我有一个只在迷宫中随机移动的幽灵之一。有谁知道我是否有办法使随机敌人受到更多AI的控制?我仍然希望它是随机的,但是目前我拥有的随机移动代码可以使幽灵有时卡在幽灵开始的盒子中,或者只是从一个地方来回到另一个地方。

这是我拥有的随机运动方法:

def get_random_direction(self):
            while True:
                number = random.randint(-2, 1)
                if number == -2:
                    x_dir, y_dir = 1, 0
                elif number == -1:
                    x_dir, y_dir = 0, 1
                elif number == 0:
                    x_dir, y_dir = -1, 0
                else:
                    x_dir, y_dir = 0, -1
                next_pos = vec(self.grid_pos.x + x_dir, self.grid_pos.y + y_dir)
                if next_pos not in self.app.walls:
                    break
            return vec(x_dir, y_dir)

我假设上面的代码是我需要编辑以更改随机运动的部分,我只是不知道该怎么做才能对其进行更改。

这是我的敌人的完整课程,其中包含敌人使用的所有代码:

        import pygame
    import random
    from settings import *

    vec = pygame.math.Vector2


    class Enemy:
        def __init__(self, app, pos, number):
            self.app = app
            self.grid_pos = pos
            self.starting_pos = [pos.x, pos.y]
            self.pix_pos = self.get_pix_pos()
            self.radius = int(self.app.cell_width//2.3)
            self.number = number
            self.colour = self.set_colour()
            self.direction = vec(0, 0)
            self.personality = self.set_personality()
            self.target = None
            self.speed = self.set_speed()

        def update(self):
            self.target = self.set_target()
            if self.target != self.grid_pos:
                self.pix_pos += self.direction * self.speed
                if self.time_to_move():
                    self.move()

            # Setting grid position in reference to pix position
            self.grid_pos[0] = (self.pix_pos[0]-TOP_BOTTOM_BUFFER +
                                self.app.cell_width//2)//self.app.cell_width+1
            self.grid_pos[1] = (self.pix_pos[1]-TOP_BOTTOM_BUFFER +
                                self.app.cell_height//2)//self.app.cell_height+1

        def draw(self):
            pygame.draw.circle(self.app.screen, self.colour,
                               (int(self.pix_pos.x), int(self.pix_pos.y)), self.radius)

        def set_speed(self):
            if self.personality in ["rapid", "frightened"]:
                speed = 1
            else:
                speed = 0.90
            return speed

        def set_target(self):
            if self.personality == "rapid" or self.personality == "sluggish":
                return self.app.player.grid_pos
            else:
                if self.app.player.grid_pos[0] > COLS//2 and self.app.player.grid_pos[1] > ROWS//2:
                    return vec(1, 1)
                if self.app.player.grid_pos[0] > COLS//2 and self.app.player.grid_pos[1] < ROWS//2:
                    return vec(1, ROWS-2)
                if self.app.player.grid_pos[0] < COLS//2 and self.app.player.grid_pos[1] > ROWS//2:
                    return vec(COLS-2, 1)
                else:
                    return vec(COLS-2, ROWS-2)

        def time_to_move(self):
            if int(self.pix_pos.x+TOP_BOTTOM_BUFFER//2) % self.app.cell_width == 0:
                if self.direction == vec(1, 0) or self.direction == vec(-1, 0) or self.direction == vec(0, 0):
                    return True
            if int(self.pix_pos.y+TOP_BOTTOM_BUFFER//2) % self.app.cell_height == 0:
                if self.direction == vec(0, 1) or self.direction == vec(0, -1) or self.direction == vec(0, 0):
                    return True
            return False

        def move(self):
            if self.personality == "random":
                self.direction = self.get_random_direction()
            if self.personality == "sluggish":
                self.direction = self.get_path_direction(self.target)
            if self.personality == "rapid":
                self.direction = self.get_path_direction(self.target)
            if self.personality == "frightened":
                self.direction = self.get_path_direction(self.target)

        def get_path_direction(self, target):
            next_cell = self.find_next_cell_in_path(target)
            xdir = next_cell[0] - self.grid_pos[0]
            ydir = next_cell[1] - self.grid_pos[1]
            return vec(xdir, ydir)

        def find_next_cell_in_path(self, target):
            path = self.BFS([int(self.grid_pos.x), int(self.grid_pos.y)], [
                            int(target[0]), int(target[1])])
            return path[1]

        def BFS(self, start, target):
            grid = [[0 for x in range(28)] for x in range(30)]
            for cell in self.app.walls:
                if cell.x < 28 and cell.y < 30:
                    grid[int(cell.y)][int(cell.x)] = 1
            queue = [start]
            path = []
            visited = []
            while queue:
                current = queue[0]
                queue.remove(queue[0])
                visited.append(current)
                if current == target:
                    break
                else:
                    neighbours = [[0, -1], [1, 0], [0, 1], [-1, 0]]
                    for neighbour in neighbours:
                        if neighbour[0]+current[0] >= 0 and neighbour[0] + current[0] < len(grid[0]):
                            if neighbour[1]+current[1] >= 0 and neighbour[1] + current[1] < len(grid):
                                next_cell = [neighbour[0] + current[0], neighbour[1] + current[1]]
                                if next_cell not in visited:
                                    if grid[next_cell[1]][next_cell[0]] != 1:
                                        queue.append(next_cell)
                                        path.append({"Current": current, "Next": next_cell})
            shortest = [target]
            while target != start:
                for step in path:
                    if step["Next"] == target:
                        target = step["Current"]
                        shortest.insert(0, step["Current"])
            return shortest

        def get_random_direction(self):
            while True:
                number = random.randint(-2, 1)
                if number == -2:
                    x_dir, y_dir = 1, 0
                elif number == -1:
                    x_dir, y_dir = 0, 1
                elif number == 0:
                    x_dir, y_dir = -1, 0
                else:
                    x_dir, y_dir = 0, -1
                next_pos = vec(self.grid_pos.x + x_dir, self.grid_pos.y + y_dir)
                if next_pos not in self.app.walls:
                    break
            return vec(x_dir, y_dir)

        def get_pix_pos(self):
            return vec((self.grid_pos.x*self.app.cell_width)+TOP_BOTTOM_BUFFER//2+self.app.cell_width//2,
                       (self.grid_pos.y*self.app.cell_height)+TOP_BOTTOM_BUFFER//2 +
                       self.app.cell_height//2)

        def set_colour(self):
            if self.number == 0:
                return (52, 235, 61)
            if self.number == 1:
                return (3, 242, 255)
            if self.number == 2:
                return (255, 158, 3)
            if self.number == 3:
                return (255, 3, 3)

        def set_personality(self):
            if self.number == 0:
                return "rapid"
            elif self.number == 1:
                return "sluggish"
            elif self.number == 2:
                return "random"
            else:
                return "frightened"
拉比德76

可能的改进是将方向保持一定距离。添加当前方向和步数的属性。只要还有脚步并且敌人没有撞墙,就保持方向:

class Enemy:
    def __init__(self):
        # [...]

        self.dir = (0, 0)
        self.steps = 0

    def get_random_direction(self):
        self.steps -= 1
        if self.steps > 0:
            next_pos = vec(self.grid_pos.x + self.dir[0], self.grid_pos.y + self.dir[1])
            if next_pos not in self.app.walls:
                return vec(self.dir)

        possible_directions = []
        for dir_x, dir_y in [(1, 0), (0, 1), (-1, 0), (0, -1)]:
            next_pos = vec(self.grid_pos.x + dir_x, self.grid_pos.y + dir_y)
            if next_pos not in self.app.walls:
                possible_directions.append((dir_x, dir_y))

        self.steps = random.randint(3, 10)
        self.dir = random.choice(possible_directions)
        return vec(self.dir)

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

随机运动pygame

来自分类Dev

Pygame 吃豆子鬼,随机改变方向

来自分类Dev

Pygame中的随机运动

来自分类Dev

pygame随机移动敌人

来自分类Dev

随机生成敌人pygame

来自分类Dev

随机运动角度

来自分类Dev

随机运动/湍流-SWIFT

来自分类Dev

Pygame 简单运动:敌人模仿玩家运动并回溯步骤

来自分类Dev

吃豆子游戏-如何让吃豆子自动移动

来自分类Dev

pygame中的随机系统运动

来自分类Dev

pygame-及时将敌人随机掉落

来自分类Dev

Pygame Platformer 2D中的敌人运动

来自分类Dev

吃豆子选项对每个问题都假设“是”?

来自分类Dev

吃豆子:“错误:找不到目标”

来自分类Dev

不透明度的随机计时+随机运动

来自分类Dev

我将如何在 pygame 中创建平滑的相机运动?

来自分类Dev

pygame敌人向玩家的2维运动,如何计算x和y速度?

来自分类Dev

pygame敌人向玩家的2维运动,如何计算x和y速度?

来自分类Dev

吃豆子:错误:数据库条目重复

来自分类Dev

升级时吃豆子总是失败(未知信任)

来自分类Dev

吃豆子钩子:将目标传递到钩子脚本

来自分类Dev

检查吃豆人运动

来自分类Dev

Canvas JS - 如何用加速度做随机运动

来自分类Dev

吃豆子:当要求更换包装时,如何选择默认选择?

来自分类Dev

吃豆子说没有更新,但是豆豆说有一些?

来自分类Dev

敌人老板运动AI

来自分类Dev

随机运行命令

来自分类Dev

在python乌龟中,当我想显示球的随机运动时,它们没有从屏幕边缘弹起

来自分类Dev

敌人有射击敌人的问题吗?pygame