【问题标题】:Entry Tkinter is not allowing to erase data if selected all and pressed delete or backspace button如果选择全部并按下删除或退格按钮,则条目 Tkinter 不允许擦除数据
【发布时间】:2025-11-30 13:15:02
【问题描述】:

我已经为条目小部件编写了一个代码,该小部件不允许使用字母并将位数限制为 7。但我无法在输入框中选择所有内容并使用删除或退格键删除它们,有人可以帮助我吗这个。

我的代码sn-p:

self.DelayLabel = ttk.Label(self) self.DelayLabel["text"] = "timeout" vcmd = (root.register(self.IntLength_Delay), '%P', '%S") self.Delay = ttk.Entry(self, width = '5', validate = 'key', validatecommand = vcmd)

def IntLenght_Delay(self,value,text):
   if text in '0123456789':
       if len(value)<7:
          return True
       else:
           return False
   else:
       return False

【问题讨论】:

    标签: python tkinter widget tkinter-entry


    【解决方案1】:

    在这里回答一个较老的问题,但我遇到了一个非常相似的问题,最终找到了一个不错的解决方案。 @Bryan Oakley 的回答很有用,但没有提供示例,而这正是我在这里的目标。

    导入Tkintertkinter(取决于你的Python版本)as tk后,首先定义初始验证命令:

    val_cmd = (master.register(self.validate), '%P')  # master is root in thie case.
    

    接下来,每当您有一个需要验证的输入框时,我发现这是一种写出来的好方法:

    self.entry = tk.Entry(your_frame_of_choice)
    self.entry.insert('end', 100)  # Inserts 100 as an initial value.
    self.entry.config(validate='key', validatecommand=val_cmd)
    

    这会在验证开始之前插入一个值。我最初有类似self.entry = tk.Entry(your_frame_of_choice, validate='key', validatecommand=val_cmd) 的东西,但是如果验证在insert 之前,我玩弄的验证函数的各种迭代拒绝了插入代码。下面列出的无关紧要,但我以这种方式保留了entry 代码,因为我觉得它更美观。

    最后是实际功能:

    def validate(self, input_text):
        if not input_text:
            return True
        try:
            float(input_text)
            return True
        except ValueError:
            return False
    

    这将检查floats,但您可以根据需要轻松将其更改为ints。而且,最重要的是,它允许您删除和覆盖输入框中任何突出显示的文本

    我确定最初的问题早已不复存在,但我希望将来有人会发现这对您有所帮助!

    【讨论】:

      【解决方案2】:

      遵循逻辑。假设您输入了“987”。您现在选择它并尝试删除它。在您的验证函数中text(当前值)将是"987"。您的代码没有为此做好准备,因此它将使第一个 if 语句失败。由于失败,验证返回 False,不允许编辑。

      您需要为 Tkinter 传递给您的函数的内容做好准备(在删除的情况下为长字符串),并且您需要在编辑后明确允许空值。

      【讨论】:

      • 谢谢你。使用 -----if text in '0123456789' 或 " ":----- 解决了它
      • 但我发现这将允许输入文本。我不想在我的代码中......
      • @user3420572:你明白吗,在删除文本的情况下,传入的文本是要删除的整个字符串,而不是单个字符。所以使用“in”可能不是你想要做的,因为“876”不在“1234567890”中
      【解决方案3】:

      在 python 3.8 中工作。

      %d == '0' -> 删除文本 | %d == '-1' -> 选择文本

      import tkinter as tk
      window = tk.Tk()
      window.title('tkinter Entry')
      
      def IntLength_Delay(action, key, content, value):
          return True if not action == '1' or len(value) < 7 and (content != '' and key == '0' or key in '123456789') else False
      
      vcmd=window.register(IntLength_Delay)
      
      txt = tk.Entry(window,width=10,validate='key',validatecommand=(vcmd,'%d','%S','%s', '%P'))
      txt.grid(column=1,row=1,sticky='news')
      
      window.mainloop()
      

      【讨论】: