【问题标题】:How to allow user input on tkinter?如何允许用户在 tkinter 上输入?
【发布时间】:2021-04-18 13:20:13
【问题描述】:

您好,我是 Python 的初学者,我正在使用 tkinter 开发一个聊天机器人界面。我遇到的问题是,在询问“您好,您叫什么名字?”后,我似乎无法在窗口中输入内容。相反,对话继续到下一行,说你好(第一个条目)你想买票吗?

有没有办法让用户输入他们的名字,然后说明输入?

例如:

用户:嗨

Bot:你好,你叫什么名字?

用户:汤姆

Bot:嗨,Tom,你要买票吗?

目前程序是这样的:

用户:嗨

Bot:你好,你叫什么名字?

Bot:你好,你要买票吗?

我不确定是什么导致 Bot 声明另一个语句,在允许用户输入之前,我曾考虑使用 StringVar() 将名称存储在 name_var 中,然后在下一行中使用该变量,但没有t 工作.. 任何想法如何解决这个问题?

这是我目前的代码:


# Representing the parent window
root = Tk() 

#Title of window
root.title('Chatbot') 

#Function to send the message 
def send(): 
send = "You =>" + entry.get() 
text.insert(END, "\n" + send) if(entry.get()=="Hi" or entry.get()=="hi" or entry.get()=="Hi there" or entry.get()=="hi there" or entry.get()=="Hello" or entry.get()== "hello"):
text.insert(END, "\n" + "Bot => Hi there, whats your name ?") 
name_var = str(StringVar()) 
text.insert(END, "\n" + "Bot => Hi " + name_var + " would you like to purchase a ticket?") 
else: 
text.insert(END, "\n" + "Bot => Sorry, I have no answer") 
entry.delete(0, END) text = Text(root) 

# Adding dimensions and send button of window 
text.grid(row=0, column=0, columnspan=2) 
entry = Entry(root, width=100) 
send = Button(root, text="Send", command=send).grid(row=1, column=1) entry.grid(row=1, column=0)
root.mainloop()```

【问题讨论】:

    标签: python tkinter


    【解决方案1】:

    在您的send 回调中,您只需依次添加两条消息,而无需等待用户输入。相反,您可以将其一分为二:一个生成器函数,yielding 复杂对话树中的下一行,而 send 消息只是关心将下一条消息放入文本字​​段:

    from tkinter import *
    
    def message_generator():
        if entry.get().lower() in ("hi", "hi there", "hello"):
            # ask for name
            yield "Hi there, whats your name ?"
            # greeting with name
            name_var = entry.get()
            yield "Hi " + name_var + " would you like to purchase a ticket?" 
            # more conversation, possibly with diverging branches
            # if entry.get() == "yes": ...
        else: 
            yield "Sorry, I have no answer"
    
    def send(): 
        text.insert(END, "\nYou =>" + entry.get())
        text.insert(END, "\nBot =>" + next(msg_gen))
        entry.delete(0, END)
    
    msg_gen = message_generator()
        
    root = Tk() 
    root.title('Chatbot') 
    text = Text(root) 
    text.grid(row=0, column=0, columnspan=2) 
    entry = Entry(root, width=100) 
    entry.grid(row=1, column=0)
    Button(root, text="Send", command=send).grid(row=1, column=1)
    root.mainloop()
    

    这里的重点是message_generator 不会被完全执行。当你第一次调用该函数时,它只是创建了一个生成器实例;然后当你在send 中调用next 时,它会执行生成器函数直到下一个yield 语句并在那里暂停,下次next 时从同一点开始执行调用,从而提供了一种很好的方式来跟踪对话的当前状态。

    【讨论】:

    • 感谢您的帮助,这是有道理的。那么最好总是在 Python 中创建单独的函数,而不是在对话期间多次重复 You=> 和 Bot=> 部分?对于 message_generator() 的第一行,“entry.get().lower()”是什么意思?就分歧分支而言,这是否意味着通过 if-else 语句继续对话,可能是为了提高可读性?
    • 这里,单独的函数并不是为了减少重复(虽然这是一个很好的副作用),但实际上是为了让一个可以成为 generator 函数,这不是完全执行,但在屈服后“暂停”,然后从那一点继续。也许我应该更多地强调这一点,因为这是这里的主要要点。是的,您可能会使用一堆可能嵌套的 if/else 语句来继续该功能。
    猜你喜欢
    • 2016-05-19
    • 2014-08-19
    • 1970-01-01
    • 1970-01-01
    • 2020-07-14
    • 2021-02-08
    • 2019-07-30
    • 1970-01-01
    • 2018-01-22
    相关资源
    最近更新 更多