You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python Turtle双人追逐游戏:碰撞检测与计分功能异常求助

问题根源

你的碰撞检测代码只在程序启动时执行了一次,之后玩家移动过程中不会再检查角色与goal的位置关系,所以触发不了计分和goal随机移动的逻辑。原代码里的if判断写在wn.mainloop()之前,只会在初始化阶段运行一次,此时玩家还没开始移动,自然不会触发碰撞事件。

修复步骤
  1. 把碰撞检测逻辑封装成独立函数,同时处理两名玩家的碰撞判定
  2. 用turtle.Screen().ontimer()定时调用检测函数,让游戏运行时持续检查碰撞
  3. 调整碰撞判定的距离阈值(原代码的5太小,turtle默认角色尺寸约20像素,设为20更容易触发合理的碰撞)
修复后的完整代码
import turtle as trtl
import random as rand

# 初始化游戏窗口
wn = trtl.Screen()

# 创建玩家1:红色乌龟
player1 = trtl.Turtle()
player1.shape('turtle')
player1.fillcolor('red')
player1.penup()
player1.goto(rand.randint(-100,100), rand.randint(-100,100))

# 创建玩家2:蓝色三角形
player2 = trtl.Turtle()
player2.shape('triangle')
player2.fillcolor('blue')
player2.penup()
player2.goto(rand.randint(-100,100), rand.randint(-100,100))

# 创建目标:黄色圆形
goal = trtl.Turtle()
goal.shape('circle')
goal.fillcolor('yellow')
goal.penup()
# 修正原代码的错误:原第二个randint参数相同,导致y轴固定在-150
goal.goto(rand.randint(-200,200), rand.randint(-150,150))

# 初始化计分
player1_score = 0
player2_score = 0

# 玩家移动控制函数
def player1_up():
    player1.setheading(90)
    player1.forward(10)

def player2_up():
    player2.setheading(90)
    player2.forward(10)

def player1_down():
    player1.setheading(270)
    player1.forward(10)

def player2_down():
    player2.setheading(270)
    player2.forward(10)

def player1_right():
    player1.setheading(0)
    player1.forward(10)

def player2_right():
    player2.setheading(0)
    player2.forward(10)

def player1_left():
    player1.setheading(180)
    player1.forward(10)

def player2_left():
    player2.setheading(180)
    player2.forward(10)

# 碰撞检测函数
def check_collision():
    global player1_score, player2_score
    
    # 检测玩家1与目标的碰撞
    if abs(player1.xcor() - goal.xcor()) < 20 and abs(player1.ycor() - goal.ycor()) < 20:
        player1_score += 1
        print(f"玩家1得分: {player1_score}")
        goal.goto(rand.randint(-200,200), rand.randint(-150,150))
    
    # 检测玩家2与目标的碰撞
    if abs(player2.xcor() - goal.xcor()) < 20 and abs(player2.ycor() - goal.ycor()) < 20:
        player2_score += 1
        print(f"玩家2得分: {player2_score}")
        goal.goto(rand.randint(-200,200), rand.randint(-150,150))
    
    # 每隔50毫秒重复调用检测函数,实现持续检测
    wn.ontimer(check_collision, 50)

# 绑定按键事件
wn.onkeypress(player1_up, "w")
wn.onkeypress(player2_up, "i")
wn.onkeypress(player1_down, "s")
wn.onkeypress(player2_down, "k")
wn.onkeypress(player1_right, "d")
wn.onkeypress(player2_right, "l")
wn.onkeypress(player1_left, "a")
wn.onkeypress(player2_left, "j")

wn.listen()
# 启动碰撞检测循环
check_collision()
wn.mainloop()
额外优化说明
  • 修正了原代码中goal初始位置的bug:原代码rand.randint(-150,-150)会让goal固定在y=-150,改为rand.randint(-150,150)让目标随机分布在合理区域
  • 调整碰撞判定距离为20,匹配turtle默认角色的尺寸,避免因阈值太小导致碰撞难以触发
  • 使用global关键字在函数内部修改全局计分变量,确保计分能正常更新

内容的提问来源于stack exchange,提问作者Tim_Beranek

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 06:20:29