Tkinter焦点在askstring后丢失

时间:2017-08-10 19:41:45

标签: python tkinter focus

我目前正在实现一个使用许多tkinter帧的程序,而子帧正在打开时我希望为用户锁定超帧(否则事情将无法解决)。经过一些研究,我发现了grab_set和grab_release方法,它运行得很好。

然而,一旦子帧(由Toplevel实例化)调用astring,抓取就会“丢失”,用户可以再次与超级窗口进行交互。一个例子就是这个(非常简化的代码):

import tkinter as tk
import tkinter.simpledialog

root = tk.Tk()
def open_sublevel():
    tl = tk.Toplevel(root)
    def ask():
        print(tk.simpledialog.askstring("askstring", "askstring"))
    tk.Button(tl, text="ask", command=ask).pack()
    tl.grab_set()
    root.wait_window(tl)
    tl.grab_release()
    print("release")


tk.Button(root, text="asdf", command=open_sublevel).pack()
tk.mainloop()

一旦用户通过单击“asdf”打开子帧,包含“asdf”的帧将在子帧打开时被锁定一段时间。然而,一旦用户在子帧中选择“询问”-Button,这种“锁定”就会以某种方式消失。

2 个答案:

答案 0 :(得分:1)

根据tkinter库中的注释:

  

抓取将所有事件定向到应用程序中的此窗口小部件和后代窗口小部件。

到目前为止,我无法找到任何可以解释为什么grab_set()在您提交完askstring之后就会失败的文档但是我会对其进行成像是因为一旦小部件消失了{ {1}}脱落。就像你要关闭grab_set()窗口一样。

在这种情况下,当窗口关闭时,抓取释放似乎不需要Toplevel

如果您在tl.grab_release()完成后重置grab_set(),我测试的内容仍可正常运行。

您只需在askstring下面添加tl.grab_set()

以下修改后的代码:

print(tk.simpledialog.askstring("askstring", "askstring"))

答案 1 :(得分:0)

为simpledialog设置父级将使simpledialog成为焦点

x = simpledialog(parent = window_x,title = z等)

这将确保x成为焦点而不是撤回