Tkinter / TTK - 防止字符串转换为ButtonPress

时间:2017-09-30 18:55:50

标签: python tkinter treeview ttk

我正在编写一个简单的脚本来创建一个ttk Exception in Tkinter callback Traceback (most recent call last): File "C:\Users\Maicol\AppData\Local\Programs\Python\Python36\lib\tkinter\__init__.py", line 1699, in __call__ return self.func(*args) File "C:\Users\Maicol\Documents\Projects\App_WINDOWS\School_Life_Diary\note.py", line 195, in <lambda> lambda f=nt[x]["URIallegato"]: os.startfile(str(f))) FileNotFoundError: [WinError 2] Can't find the specified file: '<ButtonPress event state=Mod1 num=1 x=677 y=37>' (用作表格),当你双击它时,它会打开一个文件(路径保存在字典中)。但是,当您双击某行时,您将收到此错误:

t.bind("<Double-1>", lambda f=nt[x]["URIallegato"]: os.startfile(str(f)))

问题是这段代码:

Treeview

允许双击并打开文件。

以下是完整的t=Treeview(w) t.pack(padx=10,pady=10) for x in list(nt.keys()): t.insert("",x,text=nt[x]["allegati"]) if nt[x]["allegati"]!="": t.bind("<Double-1>", lambda f=nt[x]["URIallegato"]: os.startfile(str(f))) 代码:

{{1}}

2 个答案:

答案 0 :(得分:1)

主要问题是在循环中为Treeview创建绑定。

只有一个双击事件可以为树声明和触发,而不是逐行,并且在这里你将在每次迭代中覆盖它。

已知这个lambda模式为for / loop中的小部件声明了命令,它可以正常工作:

lambda f=nt[x]["URIallegato"]: os.startfile(str(f))

但是在这里你声明了一个默认参数f,并且lambda将使用事件绑定给出的event参数执行,这就是你在异常中得到的结果:<ButtonPress event state=Mod1... < / p>

无论如何,我们发现即使您使用第二个参数修复lambda以接受event而不替换默认值f,这也不适用于您的情况。

我建议使用每行的values字段来存储信息URIallegato",而不在树中显示该列。

然后,您可以将一般事件绑定到Treeview,方法是使用focus()获取所选项目,然后提取值以获取URI。

t=Treeview(w)
t.pack(padx=10,pady=10)

def open_item(event):
    item = t.item(t.focus())
    if item['text']:
        os.startfile(item['values'][0])

for x in list(nt.keys()):
    value = ''
    if nt[x]["allegati"]:
        value = str(nt[x]["URIallegato"])
    t.insert("",x,text=nt[x]["allegati"], values=value)

t.bind("<Double-1>", open_item)

如果你想检查是否有要打开的URI,这里很难使用lambda。

答案 1 :(得分:0)

当事件触发时,tkinter将传递一个事件对象。您正在尝试打开该事件对象,就好像它是一个文件一样。

为什么?让我们重新开始你的lambda作为一个合适的函数。你的lambda相当于这个函数:

def handle_event(f=default_value):
    os.startfile(str(default_value))

当事件触发时,它会完成相同的操作:

handle_event(event)

您的脚本被赋予一个位置参数event,该参数被分配给第一个关键字参数。因此fevent相同。

解决方案是确保您的lambda接受该事件,它可以忽略:

lambda event, f=nt[x]["URIallegato"]: os.startfile(str(f)))

通过上述内容,event对象将与event参数相关联,f的默认值将作为f传递。