Entry.delete 在 Tkinter 中未清除

Entry.delete in Tkinter not clearing

我尝试制作一个简单的数字检查器来显示数字是否正确。 在草草写了一些原型代码后,我无法清除字段。 我研究了有关此主题的许多问题,但找不到答案。 我的尝试是 show_result()

我做错了什么?

它应该接受数字,并且是最后一个数字;核实。如果正确,则显示接受图像,否则显示拒绝图像并在输入错误后清除条目。 3 秒后删除图像。

我怀疑 num_limit() 函数搞砸了,但我不知道是什么。

所有其他文件都可以在这里找到:https://bytebitten.stackstorage.com/s/JeRD33P92Us4a1Li

from tkinter import *
import time

#####
# Variables
code_check = 0
codeLength = 4
list3 = 123, 456
list4 = 2345, 3452

#####
# System

root = Tk()
root.title('Code Verifier')
root.attributes('-fullscreen', True)
root.bind('<Escape>',lambda e: root.quit())

#####
# Functions

# Input limiter function (WIP)
def num_limit(p, this_field):
    global codeLength
    print("Entry" + this_field + ": " + p)
    
    this_field = int(this_field)
    
    entries = [entry1, entry2, entry3, entry4]
    
    next_field = entries[this_field]
    
    # Check if it's a number
    if p.isdigit():
        if this_field < codeLength:
            # Set focus on next field
            next_field.focus_set()
            pass
        else:
            code_checker()
        return True
    else:
        # Check if it's Backspace or del/home/end/PgUp/PgDn
        if p!="\x08" and p!="":
            return False
        else:
            if this_field < codeLength:
                next_field.focus_set()
            else:
                return True

def code_checker():
    global code_check
    global codeLength
    print("== Code Check ==")
    
    enteredCode = ''
    
    enteredCode += entry1.get()
    enteredCode += entry2.get()
    enteredCode += entry3.get()
    
    if codeLength == 3:
        if enteredCode in list3:
            code_check = 1
        else:
            code_check = 2
    if codeLength == 4:
        enteredCode += entry4.get()
        if enteredCode in list4:
            code_check = 1
        else:
            code_check = 2
    show_result()

def show_result():
    global code_check
    print("== Show Result ==")
    print(code_check)
    # If code is correct
    if code_check == 1:
        # Image code accepted
        main_canvas.create_image(width/2, 750, anchor=N, image=codeAccepted)
    # If code is wrong
    elif code_check == 2:
        # Image code denied
        main_canvas.create_image(width/2, 750, anchor=N, image=codeDenied)
        
        # Clear fields
        entry1.delete(0, END)
        entry2.delete(0, END)
        entry3.delete(0, END)
        entry4.delete(0, END)
        
        # Set focus to first field
        entry1.focus_set()
    else:
        pass

#####
# Screen items

# Load images
codeDenied = PhotoImage(file='Assets/code_denied.png')
codeAccepted = PhotoImage(file='Assets/code_accepted.png')

# Set fullscreen canvas
main_canvas = Canvas(root, bg="#000000", bd=0, highlightthickness=0)
main_canvas.pack(fill="both", expand=True)

width = root.winfo_screenwidth()
height = root.winfo_screenheight()

# Input num limiter command
vcmd = root.register(func=num_limit)

# 3-6 single-digit input fields
entry1 = Entry(root, validate='key', validatecommand=(vcmd, '%P', 1), font=("Helvetica", 100), fg="#000000", bg="#ffffff", width=1, bd=0)
entry2 = Entry(root, validate='key', validatecommand=(vcmd, '%P', 2), font=("Helvetica", 100), fg="#000000", bg="#ffffff", width=1, bd=0)
entry3 = Entry(root, validate='key', validatecommand=(vcmd, '%P', 3), font=("Helvetica", 100), fg="#000000", bg="#ffffff", width=1, bd=0)
entry4 = Entry(root, validate='key', validatecommand=(vcmd, '%P', 4), font=("Helvetica", 100), fg="#000000", bg="#ffffff", width=1, bd=0)

# Entry position adjust
field1 = -100
field2 = 0
field3 = 100
field4 = 150

# Entry placing
if codeLength == 3:
    entry_window1 = main_canvas.create_window(width+field1, 500, anchor=N, window=entry1)
    entry_window2 = main_canvas.create_window(width+field2, 500, anchor=N, window=entry2)
    entry_window3 = main_canvas.create_window(width+field3, 500, anchor=N, window=entry3)
elif codeLength == 4:
    field1 = field1-50
    field2 = field2-50
    field3 = field3-50
    entry_window1 = main_canvas.create_window(width/2+field1, 500, anchor=N, window=entry1)
    entry_window2 = main_canvas.create_window(width/2+field2, 500, anchor=N, window=entry2)
    entry_window3 = main_canvas.create_window(width/2+field3, 500, anchor=N, window=entry3)
    entry_window4 = main_canvas.create_window(width/2+field4, 500, anchor=N, window=entry4)
else:
    pass

#####

root.mainloop()

num_limit()里面,要检查Entry的内容是否为空,如果为空return则为真。如果没有此验证,您将无法删除 Entry 的内容,因为空字符串不是有效输入。

您还在验证函数 return 之前调用了 code_checker(),因此您将从 code_checker() 中的 Entry4 获得空字符串。在验证后使用 after() 安排 code_checker() 的执行。

最后,list3list4是整数列表,但是enteredCode是字符串,所以检查结果总是2。之前将enteredCode转换为整数检查。

下面修改num_limit()code_checker()

def num_limit(p, this_field):
    global codeLength

    ### check for empty string
    if p == "": return True

    print("Entry" + this_field + ": " + p)
    
    this_field = int(this_field)
    
    entries = [entry1, entry2, entry3, entry4]
    
    if this_field < codeLength:
        next_field = entries[this_field]
    
    # Check if it's a number
    if p.isdigit():
        if this_field < codeLength:
            # Set focus on next field
            next_field.focus_set()
        else:
            # schedule execution of code_checker() after validation
            root.after(100, code_checker)
        return True
    else:
        # Check if it's Backspace or del/home/end/PgUp/PgDn
        if p!="\x08" and p!="":
            return False
        else:
            if this_field < codeLength:
                next_field.focus_set()
            else:
                return True

def code_checker():
    global code_check
    global codeLength
    print("== Code Check ==")
    
    enteredCode = ''
    
    enteredCode += entry1.get()
    enteredCode += entry2.get()
    enteredCode += entry3.get()
    
    if codeLength == 3:
        if int(enteredCode) in list3:  # convert enteredCode to integer
            code_check = 1
        else:
            code_check = 2
    if codeLength == 4:
        enteredCode += entry4.get()
        if int(enteredCode) in list4:  # convert enteredCode to integer
            code_check = 1
        else:
            code_check = 2
    show_result()