我正在尝试从带有多个标签的 tkinter 对话框获取用户输入数据。我找到了一个网站,其中有一个与我的案例接近的示例here。
我希望用户输入 3 个数据:名字、姓氏和身份证号码。单击验证按钮后,我需要检查标识号是否仅由数字组成以及名称是否有效,并确保它以大写字母开头。如果满足这些条件,我将创建一个链接并将输入存储到文件中。
我根据我的情况调整了代码示例,但我无法让它工作。
这是我在
file1.py
中尝试过的:
from userDialogBox import UserDialogBox
# ask user to type their "id number", "first name", "last name"
user_dialog = UserDialogBox(None)
# if input data are valid
if user_dialog.validate():
# build link web page
pass
在
userDialogBox.py
:
import tkinter as tk
from tkinter import simpledialog
class UserDialogBox(simpledialog.Dialog):
def body(self, master):
self.title("Données utilisateur")
self.iconbitmap("logo_km.ico")
tk.Label(master, text="Matricule", font=('Arial', 15)).grid(row=0)
tk.Label(master, text="Prénom", font=('Arial', 15)).grid(row=1)
tk.Label(master, text="Nom", font=('Arial', 15)).grid(row=2)
self.matricule_entry = tk.Entry(master)
self.first_name_entry = tk.Entry(master)
self.last_name_entry = tk.Entry(master)
self.matricule_entry.grid(row=0, column=1)
self.first_name_entry.grid(row=1, column=1)
self.last_name_entry.grid(row=2, column=1)
def validate(self):
matricule = self.matricule_entry.get()
first_name = self.first_name_entry.get()
last_name = self.last_name_entry.get()
if not matricule.isdigit():
tk.messagebox.showerror("Erreur", "Matricule invalide.")
return False
if not first_name:
tk.messagebox.showerror("Erreur", "Prénom invalide.")
return False
if not last_name:
tk.messagebox.showerror("Erreur", "Nom invalide.")
return False
return True
def apply(self):
self.matricule = self.matricule_entry.get()
self.first_name = self.first_name_entry.get()
self.last_name = self.last_name_entry.get()
测试代码后,我收到以下错误消息:
matricule = self.matricule_entry.get()
File "C:\Python310\lib\tkinter\__init__.py", line 3082, in get
return self.tk.call(self._w, 'get')
_tkinter.TclError: invalid command name ".!userdialogbox.!frame.!entry"
我很少编写 Python 代码,因此我将非常感谢您提供的任何帮助。谢谢!
每次单击 OK 按钮时都会完成验证。如果您检查整个回溯(不仅仅是发布的片段),您可能会意识到您的错误是由您在
file1
中手动执行的验证调用触发的,这是在对话框被接受或取消之后。无论哪种方式,您尝试访问的小部件都会被销毁(请参阅下面 Dialog
中的功能):
def ok(self, event=None):
if not self.validate():
self.initial_focus.focus_set() # put focus back
return
self.withdraw()
self.update_idletasks()
try:
self.apply()
finally:
self.cancel()
def cancel(self, event=None):
# put focus back to the parent window
if self.parent is not None:
self.parent.focus_set()
self.destroy()
您可以在对话框中实现一个新的实例变量
valid
来保存输入是否被接受的信息。这是可以做到的:
import tkinter as tk
from tkinter import simpledialog
class UserDialogBox(simpledialog.Dialog):
def body(self, master):
self.valid = False # implement valid to check if input was provided
self.title("Données utilisateur")
self.iconbitmap("logo_km.ico")
tk.Label(master, text="Matricule", font=('Arial', 15)).grid(row=0)
tk.Label(master, text="Prénom", font=('Arial', 15)).grid(row=1)
tk.Label(master, text="Nom", font=('Arial', 15)).grid(row=2)
self.matricule_entry = tk.Entry(master)
self.first_name_entry = tk.Entry(master)
self.last_name_entry = tk.Entry(master)
self.matricule_entry.grid(row=0, column=1)
self.first_name_entry.grid(row=1, column=1)
self.last_name_entry.grid(row=2, column=1)
def validate(self):
matricule = self.matricule_entry.get()
first_name = self.first_name_entry.get()
last_name = self.last_name_entry.get()
if not matricule.isdigit():
tk.messagebox.showerror("Erreur", "Matricule invalide.")
return False
if not first_name:
tk.messagebox.showerror("Erreur", "Prénom invalide.")
return False
if not last_name:
tk.messagebox.showerror("Erreur", "Nom invalide.")
return False
self.valid = True # set valid to true if the input is correct
return True
def apply(self):
self.matricule = self.matricule_entry.get()
self.first_name = self.first_name_entry.get()
self.last_name = self.last_name_entry.get()
if __name__ == '__main__':
# ask user to type their "id number", "first name", "last name"
user_dialog = UserDialogBox(tk.Tk())
# if input data are valid
if user_dialog.valid: # check for valid instead of calling the validation again
# print data
print(user_dialog.matricule, user_dialog.first_name, user_dialog.last_name)