使其功能在两次或更多次按下时执行

时间:2019-07-19 13:24:34

标签: python turtle-graphics onkeypress

我是Python的新手,我需要一些帮助。 如何使它在2次或更多次按键后执行功能? 我正在尝试使用类似于Minicraft的乌龟制作游戏(2D自上而下的动作游戏),在这里您可以使用从石头和木头中得到的材料来制作各种不同的物品。代码尚未完成。

代码,我需要帮助:

stone = turtle.Turtle()
stone.shape("circle")
stone.color("gray")
stone.penup()
stone.setposition(-220, 180)
stone.shapesize(stretch_wid=2, stretch_len=3)

def stonebreak():
    stone = turtle.Turtle ()
    stone.shape ("circle")
    stone.color ("gray")
    stone.penup ()
    stone.setposition (-220, 180)
    stone.shapesize (stretch_wid=2, stretch_len=3)
    stone.speed("slow")
    stone.hideturtle()
    stone = 0
    stone += 9
    stonestring = "Stone: %s" % stone
    penstone1.write (stonestring, False, align="left", font=("system", 15, "normal"))
    penstone1.clear()
    penstone1.write (stonestring, False, align="left", font=("system", 15, "normal"))


if isCollision(player, stone):
    wn.onkeypress(stonebreak, "space")
    stone.hideturtle()

完整代码:

import turtle
import random
import math
import time
turtle.tracer(5)
score = 0

# Turtles

wn = turtle.Screen()
wn.tracer(0)
wn.bgcolor("black")
wn.title("Catcher")
wn.setup(800, 600)


penwood1 = turtle.Turtle()
penwood1.penup()
penwood1.color("white")
penwood1.hideturtle()
penwood1.goto(-280, 275)
wood = 0
woodstring = "Wood: %s" %wood
penwood1.write(woodstring, False, align ="left", font = ("system", 15, "normal"))

penstone1 = turtle.Turtle()
penstone1.penup()
penstone1.color("white")
penstone1.hideturtle()
penstone1.goto(-200, 275)
stone = 0
stonestring = "Stone: %s" %stone
penstone1.write(stonestring, False, align ="left", font = ("system", 15, "normal"))

player = turtle. Turtle()
player.hideturtle()
player.color("white")
player.shape("triangle")
player.penup()
player.setheading(180)
player.setposition(180, 0)
player.showturtle()
player.penup()
player.speed(0)

pen = turtle.Turtle()
pen.color("white")
pen.shape("circle")
pen.hideturtle()
pen.penup()
pen.setposition(360, 275)
pen.pendown()
pen.setposition(360, -275)
pen.setposition(-360, -275)
pen.setposition(-360, 275)
pen.setposition(360, 275)
pen.shapesize(stretch_wid=3, stretch_len=3)


pen1 = turtle.Turtle()
pen1.color("white")
pen1.shape("circle")
pen1.hideturtle()
pen1.penup()
pen1.goto(-360, 275)
scorestring = "Score: %s" %score
pen1.write(scorestring, False, align = "left", font = ("system", 15, "normal"))


tree = turtle.Turtle()
tree.shape("circle")
tree.color("green")
tree.penup()
tree.setposition(200, 140)

stone1 = turtle.Turtle ()
stone1.shape ("circle")
stone1.color ("gray")
stone1.penup ()
stone1.setposition (-200, 140)
stone1.shapesize (stretch_wid=2, stretch_len=3)
stone1.speed ("slow")

stone = turtle.Turtle()
stone.shape("circle")
stone.color("gray")
stone.penup()
stone.setposition(-220, 180)
stone.shapesize(stretch_wid=2, stretch_len=3)

# ______________________________________________________
treedown = turtle.Turtle()
treedown.shape("circle")
treedown.color("green")
treedown.penup()
treedown.setposition(-250, -140)



# Movement features

def pleft():
    player.setheading(180)
    x = player.xcor()
    x -= 20
    if x < -360:
        x = - 360

    player.setx(x)

def pright():
    player.setheading(0)
    x = player.xcor()
    x += 20
    if x > 360:
        x = + 360

    player.setx(x)

def pdown():
    player.setheading(270)
    y = player.ycor()
    y -= 20
    if y < -275:
        y = - 275

    player.sety(y)

def pup():
    player.setheading(90)
    y = player.ycor()
    y += 20
    if y > 275:
        y = + 275

    player.sety(y)


wn.listen()
wn.onkeypress(pleft, "Left")
wn.onkeypress(pright, "Right")
wn.onkeypress(pup, "Up")
wn.onkeypress(pdown, "Down")



while True:
    wn.update()


    def treebreak():
        tree.speed("slow")
        tree.hideturtle()
        wood = 0
        wood += 2
        woodstring = "Wood: %s" % wood
        penwood1.write (woodstring, False, align="left", font=("system", 15, "normal"))
        penwood1.clear()
        penwood1.write (woodstring, False, align="left", font=("system", 15, "normal"))

        def treebbreak():
            treedown.speed ("slow")
            treedown.hideturtle ()
            wood = 2
            wood += 3
            woodstring = "Wood: %s" % wood
            penwood1.write (woodstring, False, align="left", font=("system", 15, "normal"))
            penwood1.clear ()
            penwood1.write (woodstring, False, align="left", font=("system", 15, "normal"))

        if player.xcor () == -240 and player.ycor () == -140:
            wn.onkeypress (treebbreak, "space")


    if player.xcor() == 180 and player.ycor() == 140:
        wn.onkeypress(treebreak, "space")

    if player.xcor() == 200 and player.ycor() == 120:
        wn.onkeypress(treebreak, "space")

    if player.xcor() == 200 and player.ycor() == 160:
        wn.onkeypress(treebreak, "space")

    if player.xcor() == 221 and player.ycor() == 141:
        wn.onkeypress(treebreak, "space")

    def isCollision(t1, t2):
        distance = math.sqrt(math.pow(t1.xcor()-t2.xcor(),2)+math.pow(t1.ycor()-t2.ycor(),2))
        if distance < 25:
            return True
        else:
            return False

    def stonebreak():
        stone = turtle.Turtle ()
        stone.shape ("circle")
        stone.color ("gray")
        stone.penup ()
        stone.setposition (-220, 180)
        stone.shapesize (stretch_wid=2, stretch_len=3)
        stone.speed("slow")
        stone.hideturtle()
        stone = 0
        stone += 9
        stonestring = "Stone: %s" % stone
        penstone1.write (stonestring, False, align="left", font=("system", 15, "normal"))
        penstone1.clear()
        penstone1.write (stonestring, False, align="left", font=("system", 15, "normal"))


    if isCollision(player, stone):
        wn.onkeypress(stonebreak, "space")
        stone.hideturtle()

    def stone1break():
        stone1 = turtle.Turtle ()
        stone1.shape ("circle")
        stone1.color ("gray")
        stone1.penup ()
        stone1.setposition (-200, 140)
        stone1.shapesize (stretch_wid=2, stretch_len=3)
        stone1.speed("slow")
        stone1.hideturtle()
        stone = 0
        stone += 9
        stonestring = "Stone: %s" % stone
        penstone1.write (stonestring, False, align="left", font=("system", 15, "normal"))
        penstone1.clear()
        penstone1.write (stonestring, False, align="left", font=("system", 15, "normal"))


    if isCollision(player, stone1):
        wn.onkeypress(stone1break, "space")
        stone1.hideturtle()



wn.mainloop()

我正在努力做到这一点,以便您在目标被 2次或多次击中后获得材料。

2 个答案:

答案 0 :(得分:1)

首先,您不应在每次发生碰撞时都设置onkeypress()事件处理程序。尝试以其他方式处理它:

function checkCollisions():
    if isCollision(player, stone1):
        stone1break()
    if isCollision(player, stone2):
        stone2break()
    ...

wn.onkeypress(checkCollisions, "space")

此代码和所有函数定义应放在主(while True:)循环之前。

然后,您将需要一些游戏对象的状态。简单的方法是添加变量stone1strength = 2,stone2strength = 2,...,并在coresponding stonebreak()函数中将其减小,然后在强度低于1时清除石材。

我非常喜欢你的努力。这使我想起了我的第一个游戏编程步骤。 :)

下一步可能是重写代码以将石头对象存储到列表中并对其进行迭代,而不是处理数十个stoneX变量...

答案 1 :(得分:0)

首先,我没有看到每次检测到冲突时都设置onkeypress()处理程序的问题。其次,您的代码一团糟!例如,您有两个名称相同的不相关全局变量,stone得分值和stone乌龟:

stone = 0
# ...
stone = turtle.Turtle()

shapeshapesize()的{​​{1}}乌龟从不可见。而这里发生了什么:

pen

发生多次,使您的分数保持固定值而不是增加。试图在精确位置上检测到乌龟是徒劳的:

wood = 2
wood += 3

随着玩家一次移动20个像素,这是一个浮点平面。乌龟有一种 if player.xcor() == 180 and player.ycor() == 140: 方法,没有理由重新发明它。

我相信@BoboDarph的状态机建议是一个很好的建议。以下是我对您的代码的重做和简化,它们使事情变得更简单。第一次触摸石头或树木时,它只会改变颜色。之后,您开始赚取积分:

distance()

待办事项

  • 优美地融合了多棵树木和石头。

  • from turtle import Screen, Turtle FONT = ('system', 15, 'normal') # Movement features def player_left(): player.setheading(180) x = player.xcor() - 20 if x < -360: x = -360 player.setx(x) def player_right(): player.setheading(0) x = player.xcor() + 20 if x > 360: x = + 360 player.setx(x) def player_down(): player.setheading(270) y = player.ycor() - 20 if y < -275: y = - 275 player.sety(y) def player_up(): player.setheading(90) y = player.ycor() + 20 if y > 275: y = + 275 player.sety(y) def isCollision(t1, t2): return t1.distance(t2) < 25 def tree_touch(): tree.color('dark green') tree.touched = True def tree_break(): global wood screen.onkeypress(None, 'space') tree.color('brown') wood += 2 woodstring = "Wood: %s" % wood pen_wood.clear() pen_wood.write(woodstring, align='left', font=FONT) def stone_touch(): rock.color('gray') rock.touched = True def stone_break(): global stone screen.onkeypress(None, 'space') rock.color('light gray') stone += 9 stonestring = "Stone: %s" % stone pen_stone.clear() pen_stone.write(stonestring, align='left', font=FONT) # Turtles screen = Screen() screen.setup(800, 600) screen.bgcolor('black') screen.title("Catcher") screen.tracer(0) pen_wood = Turtle() pen_wood.hideturtle() pen_wood.color('white') pen_wood.penup() pen_wood.goto(-280, 275) wood = 0 wood_string = "Wood: %s" %wood pen_wood.write(wood_string, align='left', font=FONT) pen_stone = Turtle() pen_stone.hideturtle() pen_stone.color('white') pen_stone.penup() pen_stone.goto(-200, 275) stone = 0 stone_string = "Stone: %s" %stone pen_stone.write(stone_string, align='left', font=FONT) pen = Turtle() pen.hideturtle() pen.shape('circle') pen.color('white') pen.penup() pen.setposition(360, 275) pen.pendown() pen.setposition(360, -275) pen.setposition(-360, -275) pen.setposition(-360, 275) pen.setposition(360, 275) rock = Turtle() rock.shape('circle') rock.color('dark gray') rock.penup() rock.setposition(-220, 180) rock.shapesize(stretch_wid=2, stretch_len=3) rock.touched = False tree = Turtle() tree.shape('circle') tree.color('green') tree.penup() tree.setposition(200, 140) tree.touched = False player = Turtle() player.hideturtle() player.shape('triangle') player.speed('fastest') player.color('white') player.setheading(180) player.penup() player.setx(180) player.showturtle() screen.onkeypress(player_left, 'Left') screen.onkeypress(player_right, 'Right') screen.onkeypress(player_up, 'Up') screen.onkeypress(player_down, 'Down') screen.listen() while True: if isCollision(player, tree): if tree.touched: screen.onkeypress(tree_break, "space") else: screen.onkeypress(tree_touch, "space") elif isCollision(player, rock): if rock.touched: screen.onkeypress(stone_break, "space") else: screen.onkeypress(stone_touch, "space") else: screen.onkeypress(None, "space") screen.update() screen.mainloop() # never reached 中的固定值25更改为计算得出的值 基于对象的isCollision()

  • 用函数和定时事件替换shapesize()循环。