Вставка значения по умолчанию в tkinter Entry останавливает проверку

Я следил за проверкой ящиков для ввода отсюда. Код ниже взят из ответа с дополнительным условием, что если введенное значение 'Q' тогда программа добавляет 'test' к началу значения Entry.

Однако, как только это значение будет вставлено, вся проверка, по-видимому, выйдет за пределы окна, и Entry разрешит значения в верхнем регистре. Некоторое тестирование моей программы показывает команду проверки (OnValidate в этом случае) не вызывается при любых дальнейших событиях Entry (ключ, focusin / out и т. д.).

import Tkinter as tk
class MyApp():
    def __init__(self):
        self.root = tk.Tk()
        vcmd = (self.root.register(self.OnValidate), 
                '%d', '%i', '%P', '%s', '%S', '%v', '%V', '%W')
        self.entry = tk.Entry(self.root, validate="key", 
                              validatecommand=vcmd)
        self.entry.pack()
        self.root.mainloop()

    def OnValidate(self, d, i, P, s, S, v, V, W):
        if S == "Q":
            self.entry.insert(0,"test")
        # only allow if the string is lowercase
        return (S.lower() == S)

app=MyApp()

Причина, по которой я это делаю, заключается в том, что я хочу, чтобы запись отображала значение по умолчанию, если его значение остается пустым после любых изменений, внесенных пользователем. (т.е. мое состояние будет if not P в фокусе)

Любые идеи о том, как реализовать это или что идет не так в вышесказанном высоко ценится.

2 ответа

Решение

Я собираюсь ответить полностью на основе:

Причина, по которой я это делаю, заключается в том, что я хочу, чтобы запись отображала значение по умолчанию, если его значение остается пустым после любых изменений, внесенных пользователем.

и надеюсь, что этот пример указывает на то, что вы хотите:

import Tkinter as tk

def analyze(event=None):
    content = entry_contents.get()
    if content == "":
        entry_contents.set("default")

lord = tk.Tk()

entry_contents = tk.StringVar()
aEntry = tk.Entry(lord, textvariable=entry_contents)
aEntry.grid()

aText = tk.Text(lord, font=("Georgia", "12"))
aText.grid()

aEntry.bind("<FocusOut>", analyze)

lord.mainloop()

или если управляющая переменная не будет вам полезна:

import Tkinter as tk

def analyze(event=None):
    content = aEntry.get()
    if content == "":
        aEntry.insert(0, "default")

lord = tk.Tk()

aEntry = tk.Entry(lord)
aEntry.grid()

aText = tk.Text(lord, font=("Arial", "12", "bold"))
aText.grid()

aEntry.bind("<FocusOut>", analyze)

lord.mainloop()

validatecommand Опция предназначена только для проверки, а не для выполнения других действий. Поведение, которое вы видите, является задокументированным поведением.

Согласно официальной тк документации по валидации:

... Параметр validate также будет установлен в none, когда вы редактируете виджет записи изнутри validateCommand или invalidCommand.

(примечание: tkinter - это всего лишь оболочка для реализации tcl в tcl. По этой причине документацию по tcl / tk можно использовать как полное руководство по поведению Tkinter)

Другие вопросы по тегам