我做这个游戏是为了躲避来自不同方向的物体。我试图实现的是让这个对象(由计算机控制的“player”类)能够像用户控制的播放器那样躲闪。
我已经尝试使用pygame提供的基本冲突处理(当然,阅读一些关于它是如何工作的文档,以及我可以做什么来解决问题)。我所做的基本上是检查一个物体的右直角位置是否与‘玩家’的左直角重叠,反之亦然,因此它向相反的方向移动以避免碰撞。
TITLE = "Dodging-IA Attempt";
WIDTH = 320; HEIGHT = 400;
FPS = 60;
BLACK = (0,0,0); WHITE = (255,255,255);
RED = (255,0,0); GREEN = (0,255,0); BLUE = (0,0,255);
import pygame as pg;
import random, math;
class Game():
def __init__(self):
self.screen = pg.display.set_mode((WIDTH,HEIGHT));
self.clock = pg.time.Clock(); self.dt = FPS/1000;
self.running = True;
self.all_sprites = pg.sprite.Group();
self.bullets = pg.sprite.Group();
self.other_sprites = pg.sprite.Group();
self.player = Player(); self.all_sprites.add(self.player);
self.bullet_spawn = BulletSpawn(); self.other_sprites.add(self.bullet_spawn);
class Player(pg.sprite.Sprite):
def __init__(self):
pg.sprite.Sprite.__init__(self);
self.image = pg.Surface((16,32)); self.image.fill(GREEN);
self.rect = self.image.get_rect();
self.rect.centerx = WIDTH//2;
self.rect.y = HEIGHT*3//4;
self.vx = self.vy = 300;
def update(self,dt):
pass;
class Bullet(pg.sprite.Sprite):
def __init__(self,x):
pg.sprite.Sprite.__init__(self);
self.image = pg.Surface((16,16)); self.image.fill(RED);
self.rect = self.image.get_rect();
self.rect.centerx = x;
self.rect.bottom = 0;
self.vy = 70;
def update(self,dt):
self.rect.y += self.vy * dt;
if self.rect.top > HEIGHT:
self.kill();
class BulletSpawn(pg.sprite.Sprite):
def __init__(self):
pg.sprite.Sprite.__init__(self);
self.image = pg.Surface((1,1)); self.rect = self.image.get_rect();
self.new_bullet = pg.time.get_ticks();
def update(self):
now = pg.time.get_ticks();
if now - self.new_bullet > 500:
self.new_bullet = now;
for i in range(5):
bullet = Bullet(random.randint(8,WIDTH-8));
game.bullets.add(bullet);
game.all_sprites.add(bullet);
pg.init();
pg.display.set_caption(TITLE);
game = Game();
while game.running:
game.dt = game.clock.tick(FPS)/1000;
for event in pg.event.get():
if event.type == pg.QUIT:
game.running = False;
hits = pg.sprite.spritecollide(game.player,game.bullets,False)
for hit in hits:
if hit.rect.right > game.player.rect.left: #dodge moving to left
game.player.rect.x += game.player.vx*game.dt
print("DODGED TO LEFT")
if hit.rect.left < game.player.rect.right: #dodge moving to right
game.player.rect.x -= game.player.vx*game.dt
print("DODGED TO RIGHT")
game.all_sprites.update(game.dt);
game.other_sprites.update();
game.screen.fill(BLUE);
game.all_sprites.draw(game.screen)
game.other_sprites.draw(game.screen)
pg.display.flip();
pg.quit();因此,“玩家”总是向一个和唯一的一个方向移动,不管它是否在它的路径上碰撞,而不是实际上水平地避开掉下的物体。我能做什么才能得到这个?也许我得重新描述一下碰撞的条件?非常感谢你抽出时间。
发布于 2019-07-06 23:58:35
检查框边是否在播放器的范围内是这样做的一种方法。如果您使检查包括在内,玩家应该回避,即使只有边缘是对齐的。
if hit.rect.right >= game.player.rect.left and hit.rect.left <= game.player.rect.left:
game.player.rect.x += game.player.vx*game.dt
print("DODGED TO LEFT")
elif hit.rect.left <= game.player.rect.right and hit.rect.right >= game.player.rect.right:
game.player.rect.x -= game.player.vx*game.dt
print("DODGED TO RIGHT")发布于 2019-07-06 19:24:26
无论球员和子弹在碰撞时刻的位置如何,bullet.rect.right总是比player.rect.left多,bullet.rect.left总是小于player.rect.right。如果你在纸上画画,你就会看到它。这里最好检查移动侧推杆中心。这段代码:
if hit.rect.right > game.player.rect.left: #dodge moving to left
game.player.rect.x += game.player.vx*game.dt
print("DODGED TO LEFT")
if hit.rect.left < game.player.rect.right: #dodge moving to right
game.player.rect.x -= game.player.vx*game.dt
print("DODGED TO RIGHT")你可以改变它:
if hit.rect.center > game.player.rect.center:
game.player.rect.x -= game.player.vx*game.dt
elif hit.rect.center < game.player.rect.center:
game.player.rect.x += game.player.vx*game.dt你可以做一些优化来缓解抽搐,但我认为错误的本质是显而易见的。
https://stackoverflow.com/questions/56911478
复制相似问题