所以简单地说我希望我的代码在每次按键时调用OnKeyPress(“Keyname”)等事件。我不想使用tkinter。
我有一个Update方法,它在父类中被调用20次 我有几个子函数调用该函数。在其中一些我想要使用按键事件来制作我正在移动的机器人的部分。(例如:当我按下向上箭头时机器人将移动前言)tkinter很好不是为此设计的更多在屏幕上绘制内容,我想让我的代码更有效率。我也希望拥有自己的,然后使用预制的,这样我就可以更好地了解它是如何工作的。
答案 0 :(得分:1)
我敦促你重新考虑不使用tkinter。忽略GUI的东西,它有一个经过测试的,跨平台的, asynchonous 事件循环系统,可以处理预定(定时)事件和按键和释放事件。它是用C语言编写的,随着平台的变化而更新。 (请参阅@Ty引用有关平台更改的配方的注释。)您会发现在Python中重现相同的设施非常困难。
用法将从
开始import tkinter
root = tkinter.Tk()
root.withdraw() # make the window invisible
此后,可以忽略GUI内容并仅使用root.bind(键事件,函数)和root.after(milleseconds,function,* args)。 (与此同时,将来使用图形与机器人交互的选项仍然存在。)
鉴于现有的move_forward和stop_move函数,以下是如何在按下向上箭头的同时让机器人移动。
root.bind('<KeyPress-Up>', move_forward)
root.bind('<keyRelease-Up>' stop_move)
关于异步(非阻塞)的重要性:我假设您通过在每次更新之间调用time.sleep(.05)来每秒调用20次更新函数。这是一个阻止调用,在此期间您的代码被冻结。它无能为力,也无法回应事件。
假设您为机器人开发了两个或更多动画:例如一个用于手臂,一个用于头部(或任何适合您的机器人)。每个命令都包含一系列时间命令,由root.after调用实现。现在假设您想要并行运行两个或更多动画。假设每个只需要一小部分CPU时间,这对于tkinter来说是微不足道的,因为每个都会异步运行而不会阻止程序执行其他操作。使用阻塞事件系统,您必须为每个组合编写一个新动画。
答案 1 :(得分:0)
这应该有效
class _GetchUnix:
def init(self):
import tty, sys
def call(self):
import sys, tty, termios
fd = sys.stdin.fileno()
old_settings = termios.tcgetattr(fd)
try:
tty.setraw(sys.stdin.fileno())
ch = sys.stdin.read(1)
finally:
termios.tcsetattr(fd, termios.TCSADRAIN, old_settings)
return ch
class _GetchWindows:
def init(self):
import msvcrt
def call(self):
import msvcrt
return msvcrt.getch()
class _Getch:
def init(self):
try:
self.impl = _GetchWindows()
except ImportError:
self.impl = _GetchUnix()
def __call__(self): return self.impl()
getch = _Getch()
while True:
if getch.impl():
print getch.impl()
您需要的while
循环之前的所有内容。然后,当你调用getch.impl()
时,它将等待输入,但如果没有,它将继续。这就是我使用while
循环
<强>声明强>
这不是我的代码,请查看:
http://code.activestate.com/recipes/134892/