首页 > 解决方案 > 用作类对象时出现 tkinter Listbox 错误

问题描述

我想创建一个Listbox对象类,以便它可以在任何需要的地方使用,但它会引发TypeError错误,这是我的代码:

import tkinter as tk

class cls_list(tk.Listbox):
    def __init__(self, master, callfrom):
        tk.Listbox.__init__(self, master, callfrom)

        callfrom.bind("<KeyRelease>", self.show_list)

    def show_list(self, event):
        x = callfrom.winfo_x()
        y = callfrom.winfo_y()
        h = callfrom.winfo_height()
        self.place(x = x, y = y+h)
        self.insert('end',*('Banana','Orange','Apple','Mango'))

if __name__ == '__main__':
    root = tk.Tk()
    ent = tk.Entry(root, font = (None, 20))
    lst = cls_list(root, ent)
    ent.pack()
    root.mainloop()

有人可以纠正我做错了什么吗?这是发生的完整异常:

  File "/home/waheed/env_pinpoint/lib/python3.9/site-packages/test_listbox.py", line 5, in __init__
    tk.Listbox.__init__(self, master, callfrom)
  File "/usr/lib/python3.9/tkinter/__init__.py", line 3162, in __init__
    Widget.__init__(self, master, 'listbox', cnf, kw)
  File "/usr/lib/python3.9/tkinter/__init__.py", line 2566, in __init__
    BaseWidget._setup(self, master, cnf)
  File "/usr/lib/python3.9/tkinter/__init__.py", line 2537, in _setup
    if 'name' in cnf:
  File "/usr/lib/python3.9/tkinter/__init__.py", line 1652, in cget
    return self.tk.call(self._w, 'cget', '-' + key)
TypeError: can only concatenate str (not "int") to str

这是我迄今为止所取得的成就。

import tkinter as tk

if __name__ == '__main__':
    root = tk.Tk()
    root.geometry('400x400')
    ent = tk.Entry(root, font = (None, 20))
    lst = tk.Listbox(root, font = (None, 20))
    ent.pack()
    ent.focus_set()

    def hide_list(event):
        index = int(lst.curselection()[0])
        val = lst.get(index)
        ent.delete(0,'end')
        ent.insert(0,val)
        lst.place_forget()

    def show_list(event):
        ent.update_idletasks()
        x = ent.winfo_x()
        y = ent.winfo_y()
        h = ent.winfo_height()
        lst.place(x = x, y = y+h)
        items = ['Banana','Orange','Apple','Mango']
        searchkey = ent.get()
        lst.delete(0, "end")
        for item in items:
            if searchkey.lower() in item.lower():
                lst.insert("end", item)
        n = lst.size()
        if n < 15:
            lst.config(height = 0)
        else:
            lst.config(height = 15)

    ent.bind("<KeyRelease>", show_list)
    lst.bind("<<ListboxSelect>>", hide_list)
    root.mainloop()

现在我想让它成为一个在多个脚本中使用的对象(单独的类)。

我希望现在我已经正确解释了我的问题。

标签: pythonpython-3.xtkinter

解决方案


您要询问的具体错误是因为您在callfrom此处经过而引起的:tk.Listbox.__init__(self, master, callfrom).

列表框小部件不知道如何处理callfrom,它希望第二个位置参数是字典。

初始化类的正确方法是不使用callfrom. 如果需要callfrom__init__.

def __init__(self, master, callfrom):
    tk.Listbox.__init__(self, master)
    self.callfrom = callfrom
    ...


def show_list(self, event):
    x = self.callfrom.winfo_x()
    y = self.callfrom.winfo_y()
    h = self.callfrom.winfo_height()
    ...

推荐阅读