【问题标题】:Python Tkinter Canvas fail to bind keyboardPython Tkinter Canvas 无法绑定键盘
【发布时间】:2026-02-06 19:50:01
【问题描述】:

我一直在运行这样的小脚本

from Tkinter import *
root = Tk()
def callback(event):
    print "callback"
w = Canvas(root, width=300, height=300)
w.bind("<Key>", callback)
w.pack()
root.mainloop()

但是,在我的情况下没有处理键盘事件(我在窗口 7 上使用 python 2.7)

如果我使用

w.bind("<Button-1>", callback)

一切正常。

所以,这真的让我很困惑。 请任何人告诉我为什么会这样,提前谢谢。

【问题讨论】:

标签: python tkinter


【解决方案1】:

tkinter 中有一个名为“Enter”的便捷事件,它跟踪鼠标何时进入小部件。如果将它绑定到画布,并在该事件的绑定回调中使用 canvas.focus_set,那么只要鼠标在画布上,您就会获得焦点,因此键盘绑定将起作用。

即使画布失去焦点(例如通过在另一个小部件中输入文本),这也会起作用,因为当鼠标再次进入画布时,它将重新获得焦点。

【讨论】:

  • 这个答案用代码 sn-p 会更完整。
【解决方案2】:

为了避免“点击画布激活键绑定”,我在以下站点找到了更简单的代码:

http://ubuntuforums.org/showthread.php?t=1378609

他正在尝试绑定一个框架,但我在自己的代码中实现了它,并且画布小部件也能正常工作。您的代码将如下所示:

w.focus_set()
w.bind(<Key>, callback)

【讨论】:

    【解决方案3】:

    键绑定仅在具有键盘焦点的小部件获得键事件时触发。默认情况下,画布不会获得键盘焦点。您可以使用 focus_set 方法将其聚焦。通常,您会在鼠标按钮的绑定中执行此操作。

    将以下绑定添加到您的代码中,然后在画布中单击,您的键绑定将开始工作:

    w.bind("<1>", lambda event: w.focus_set())
    

    【讨论】:

    • 谢谢布莱恩,这是焦点问题。虽然代码有点不同。我通过内联 `w.focus_set() w.bind('', function)` 使它工作
    • @RobertBean:只是为了说清楚-您不必在绑定之前执行 focus_set 。 focus_set 必须在人们开始使用键盘之前完成。
    • 我也不明白为什么@BryanOakley 强调用 w.focus_set() 绑定鼠标点击,而不是使用内联 w.focus_set()。
    • @wsysuper:我没有强调它,我只是说它是典型的。你可以做任何一个。这主要取决于您在 UI 中是否有其他可以获取焦点的小部件。如果这样做,您可能需要设置一个绑定,以便用户可以在画布由于单击另一个可聚焦小部件而失去焦点时切换焦点。