修复函数StringVar_with history

2024-05-15 07:34:33 发布

您现在位置:Python中文网/ 问答频道 /正文

from tkinter import StringVar
class StringVar_WithHistory(StringVar):
    def __init__(self):
        self.history = []

    def set (self,value):
        if StringVar.get(self) != value:
            StringVar.set(self, value)
            self.history.append(value)

    def undo (self):
        StringVar.set(self,history[-1])
        self.history.pop()

from tkinter import OptionMenu
class OptionMenuUndo(OptionMenu):
    def __init__(self,parent,title,*option_tuple,**configs):
        self.result = StringVar_WithHistory()
        self.result.set(title)
        OptionMenu.__init__(self,parent,self.result,*option_tuple,**configs)


    def get(self):                
        return self.result.get()


    def undo(self):
        self.result.undo()     


    def simulate_selection(self,option):
        self.result.set(option)  

我正在处理StringVar_with history类,使其应用于optionmenundo类。StringVar_with history有三种方法。在

init(self):初始化基类;创建一个历史记录列表,用于存储调用的值集。在

set(self,value):如果值与当前值不同,则将StringVar设置为value并在历史记录列表中记住它(如果它与当前值相同,则不执行任何操作:无新选择)。在

undo(self):通过更新StringVar和历史列表来撤消最近选择的选项

我试图运行代码,但出现以下错误:

^{pr2}$

有人能告诉我怎样用历史来修复我的心灵吗?谢谢


Tags: fromself列表getinitvaluetkinterdef
2条回答

你忘了StringVar.__init__()

顺便说一句:您必须使用[-2]或第一个pop值。在

在获取元素之前,必须检查self.history的大小,因为它可能是空的。在

from tkinter import StringVar

class StringVar_WithHistory(StringVar):

    def __init__(self, **kwargs):
        StringVar.__init__(self, **kwargs)
        self.history = []

    def set(self, value):
        if StringVar.get(self) != value:
            StringVar.set(self, value)
            self.history.append(value)
        #print('DEBUG:', self.history)

    def undo(self):
        StringVar.set(self, self.history[-2])
        self.history.pop()
        #print('DEBUG:', self.history)

import tkinter as tk

root = tk.Tk()

a = StringVar_WithHistory(value='TEST')
print(a.get())
a.set('Hello')
print(a.get())
a.set('World')
print(a.get())
a.undo()
print(a.get())
a.undo() # error because self.history is empty

root.mainloop()

您忘记在子类的__init__()中调用StringVar.__init__(),因此实际上从未创建过该变量。在

这是个有趣的主意,但我不认为它会如你所期望的那样奏效。请记住,StringVar不是Python对象;它是存在于Tkinter嵌入的Tcl解释器中的Tcl对象。只有当有人从Python代码中执行var.set()操作时,才会调用重写的set()方法。由于Tk小部件的内置功能而对变量进行的任何更改都将直接影响Tcl变量;不涉及Python端的任何内容。您可以通过使用StringVar的跟踪功能来获得值更改的通知,而不是试图重写任何方法,从而挽救这种想法。在

相关问题 更多 >