【发布时间】:2019-06-20 19:40:58
【问题描述】:
我一直致力于将我使用 CodeSkulptor 为在线 Python 课程构建的游戏“Pong”翻译成使用 Tkinter 的“桌面”python 脚本,作为一种自学如何使用 Tkinter 的方法.除了左侧(玩家 1)桨外,我已经设法让整个游戏正常运行。我认为我的键绑定正确,因为右侧(玩家 2)桨按预期工作,因为当您按住“向上”或“向下”箭头键时,桨移动直到它达到上限或下限画布,或在任何一个键被释放时停止。我将按键传递给 keydown 和 keyup 处理程序,在那里我检查哪个键被按下/释放,并采取相应的行动。令我困惑的是,如果我将左桨移动映射到不同的键(例如“a”或“d”,或者“向上”或“向下”箭头),它会按预期工作,但它拒绝当我映射了“w”和“s”键时工作。有谁知道为什么会这样,或者我做错了什么?
我在下面提供的代码是我放在一起的一个基本示例,它演示了这个问题,以及我试图实现的桨运动(它几乎反映了我的 Pong 项目)。右侧桨叶正确移动,而左侧桨叶没有。提前感谢您的帮助!
from Tkinter import *
import random
WIDTH = 500
HEIGHT = 500
PAD_WIDTH = 10
PAD_HEIGHT = 80
HALF_PAD_WIDTH = PAD_WIDTH / 2
HALF_PAD_HEIGHT = PAD_HEIGHT / 2
class Example(Frame, object):
def __init__(self, master):
super(Example, self).__init__(master)
self._paddle1_pos = 200
self._paddle2_pos = 200
self._paddle1_vel = 0
self._paddle2_vel = 0
self.initUI()
def initUI(self):
scn_cent_height = self.master.winfo_screenheight() // 2 - HEIGHT // 2
scn_cent_width = self.master.winfo_screenwidth() // 2 - WIDTH // 2
self.master.geometry("%sx%s+%s+%s" % (WIDTH, HEIGHT, scn_cent_width, scn_cent_height))
self.master.minsize(WIDTH, HEIGHT)
self.master.title("Example Pong Paddles")
self._canvasFrame = Frame(self.master)
self._canvasFrame.pack(expand=True, fill=BOTH)
self._canvas = Canvas(self._canvasFrame, bg="black", highlightthickness=0, bd=0)
self._canvas.pack(fill=BOTH, expand=True)
self.update_idletasks()
# Key handlers
self.master.bind("<KeyPress>", self.keydown)
self.master.bind("<KeyRelease>", self.keyup)
while True:
self._canvas.after(1)
self._canvas.delete("all")
self.draw()
self._canvas.update()
def draw(self):
self._cheight = self._canvasFrame.winfo_height()
self._cwidth = self._canvasFrame.winfo_width()
# Draw mid line and gutters
self._rline = self._canvas.create_line(self._cwidth / 2, 0, self._cwidth / 2, self._cheight, width=1, fill="White")
self._mline = self._canvas.create_line(PAD_WIDTH, 0, PAD_WIDTH, self._cheight, width=1, fill="White")
self._lline = self._canvas.create_line(self._cwidth - PAD_WIDTH, 0, self._cwidth - PAD_WIDTH, self._cheight, width=1, fill="White")
# Update paddle's vertical position, keep paddle on the screen
# Paddle 1 - Check height and update position
if self._paddle1_pos + self._paddle1_vel >= HALF_PAD_HEIGHT and self._paddle1_pos + self._paddle1_vel <= HEIGHT - HALF_PAD_HEIGHT:
self._paddle1_pos += self._paddle1_vel
# Paddle 2 - Check height and update position
if self._paddle2_pos + self._paddle2_vel >= HALF_PAD_HEIGHT and self._paddle2_pos + self._paddle2_vel <= HEIGHT - HALF_PAD_HEIGHT:
self._paddle2_pos += self._paddle2_vel
# Draw paddles
self._p1paddle = self._canvas.create_line([HALF_PAD_WIDTH, self._paddle1_pos - HALF_PAD_HEIGHT],
[HALF_PAD_WIDTH, self._paddle1_pos + HALF_PAD_HEIGHT], width=PAD_WIDTH, fill="White")
self._p2paddle = self._canvas.create_line([self._cwidth - HALF_PAD_WIDTH, self._paddle2_pos - HALF_PAD_HEIGHT],
[self._cwidth - HALF_PAD_WIDTH, self._paddle2_pos + HALF_PAD_HEIGHT], width=PAD_WIDTH, fill="White")
# Draw paddles
self._p1paddle = self._canvas.create_line([HALF_PAD_WIDTH, self._paddle1_pos - HALF_PAD_HEIGHT],
[HALF_PAD_WIDTH, self._paddle1_pos + HALF_PAD_HEIGHT], width=PAD_WIDTH, fill="White")
self._p2paddle = self._canvas.create_line([self._cwidth - HALF_PAD_WIDTH, self._paddle2_pos - HALF_PAD_HEIGHT],
[self._cwidth - HALF_PAD_WIDTH, self._paddle2_pos + HALF_PAD_HEIGHT], width=PAD_WIDTH, fill="White")
def keydown(self, key):
key = key.keysym
if key == "w":
self._paddle1_vel = -10
elif key == "s":
self._paddle1_vel = 10
elif key == "Up":
self._paddle2_vel = -10
elif key == "Down":
self._paddle2_vel = 10
def keyup(self, key):
key = key.keysym
if key == "w":
self._paddle1_vel = 0
elif key == "s":
self._paddle1_vel = 0
elif key == "Up":
self._paddle2_vel = 0
elif key == "Down":
self._paddle2_vel = 0
def main():
root = Tk()
example = Example(root)
root.mainloop()
if __name__ == '__main__':
main()
【问题讨论】:
-
你有大写锁定吗?如果是这样,
'w'和'W'就不一样了。 -
你的代码对我来说工作得很好(Linux,python3.6)。
-
我只是做了一个理智的检查以确保我之前没有使用大写锁定,并且得到了相同的结果。作为另一个健全性检查,我还尝试使用命令行(而不是 Spyder)运行它,并且在那里也得到了相同的结果。我在 MacOSX Mojave (10.14.3) 上运行 python 2.7,顺便说一句。也许 MacOS 有点奇怪? Fwiw,我的笔记本电脑上还连接了一个 Apple 无线魔术键盘,尽管我在该键盘和笔记本电脑的内置键盘上都对其进行了测试,没有任何区别。
-
你确定是 2.7 吗?您的 tkinter 导入适用于 python3。如果您安装了诸如
six之类的兼容性包,则可以按照您拥有它们的方式使用它们。 -
@Novel,你说得对,我不小心打错了导入语句。谢谢你抓住那个。我在上面的代码中修复了它,并重新测试了它,但我仍然遇到了同样的问题。仅作为背景,我使用 Anaconda,我的根 python 安装是 2.7。
标签: python python-2.7 tkinter