如何在此程序中将多线程与tkinter一起使用



这段代码接受用户输入作为音频并做出相应的响应,我想使用 tkinter 来显示对话。我尝试使用多线程,但它不起作用。请帮助我了解如何在此处使用多线程。 预期成果 :

  1. 代码应在窗口上打印对话
  2. 并同时倾听用户的声音

这是我的代码

import pyttsx3
import speech_recognition as sr
import datetime
import wikipedia
import webbrowser
import os
import smtplib
from tkinter import *
import threading
import time
root = Tk()
engine = pyttsx3.init('sapi5')
voices = engine.getProperty('voices')
# print(voices[0].id)
engine.setProperty('voice', voices[0].id)

def speak(audio):
engine.say(audio)
engine.runAndWait()
t = Text(root)
t.grid(row=0, column=0,
columnspan=2, rowspan=2, padx=5, pady=5)
t.insert(END, 'Genos says: ' + audio + 'n')

def wishme():
hour = int(datetime.datetime.now().hour)
if hour >= 0 and hour < 12:
speak("Good Morning sir")
elif hour >= 12 and hour < 18:
speak("Good Afternoon sir")
else:
speak("Good Evening sir")
speak("I am Genos. How can I Serve you?")
return
t = Text(root)
t.grid(row=0, column=0,
columnspan=2, rowspan=2, padx=5, pady=5)
t.insert(END, 'Genos says: ' + wishme() + 'n')

def takecommand():
# it takes mic input from the user and return string output
r = sr.Recognizer()
with sr.Microphone() as source:
print("Listening...")
r.pause_threshold = 1
audio = r.listen(source)
try:
print("Recognizing..")
query = r.recognize_google(audio, language='en-in')
print(f"user Said :{query}n")
except Exception as e:
print(e)
speak("Say that again please")
return "None"
t1 = Text(root)
t1.grid(row=0, column=2,
columnspan=2, rowspan=2, padx=5, pady=5)
t1.insert(END, 'user says: ' + query + 'n')
return query

def sendEmail(to, content):
server = smtplib.SMTP("smtp.gmail.com", 587)
server.ehlo()
server.starttls()
server.login('mail@gmail.com', '###')
server.sendmail('mail@gmail.com', to, content)
server.close()
return

if __name__ == "__main__":
wishme()
# while True:
for _ in range(10):
query = takecommand().lower()
# Logic for executing task based query
if 'wikipedia' in query:
speak('searching Wikipedia....')
query = query.replace("wikipedia", "")
results = wikipedia.summary(query, sentences=5)
speak("According to wikipedia")
print(results)
speak(results)
elif 'open youtube' in query:
webbrowser.open("youtube.com")
elif 'open google' in query:
webbrowser.open("google.com")
elif 'open stackoverflow' in query:
webbrowser.open("stackoverflow.com")
elif 'play music' in query:
music_dir = 'D:\SAHIL\$ONGS_MJ'
songs = os.listdir(music_dir)
print(songs)
os.startfile(os.path.join(music_dir, songs[0]))
elif 'the time' in query:
strTime = datetime.datetime.now().strftime("%H:%M:%S")
speak(f"Sir the time is {strTime}")
elif 'open code' in query:
codepath = "C:\Users\Sahil\AppData\Local\Programs\Microsoft VS Code 
Insiders\Code - Insiders.exe"
os.startfile(codepath)
elif 'email to sahil' in query:
try:
speak("What should i say ?")
content = takecommand()
to = "mail@gmail.com@gmail.com"
sendEmail(to, content)
speak("Email has been sent")
except Exception as e:
print(e)
speak("Could nott send the email ")
elif 'open mailbox' in query:
webbrowser.open("gmail.com");
elif 'how are you' in query:
speak("I am fine sir. How are you?")
continue
elif 'i am fine' in query:
speak("that's good to know, how can I help you")
continue
elif 'goodbye' in query:
speak("bye Sir")
exit()

root.mainloop()

我无法测试语音识别,但至少它会显示它窥视的文本。

我把你所有的循环都放在函数中,然后运行在Thread.我也向这个线程发送队列,所以它可以将文本(或像quit这样的命令(发送到主线程,主线程使用after定期(200ms(从队列中获取文本并显示Text

import os
import pyttsx3
import speech_recognition as sr
import datetime
import wikipedia
import webbrowser
import smtplib
import time
import threading
import queue
import tkinter as tk
# --- functions ---
def speak(text):
engine.say(text)
engine.runAndWait()
def wishme(queue):
hour = datetime.datetime.now().hour
if 0 <= hour < 12:
text = "Good Morning sir"
elif 12 <= hour < 18:
text = "Good Afternoon sir"
else:
text = "Good Evening sir"
queue.put(f'{text}.')
speak(text)
queue.put("I am Genos. How can I Serve you?n")
speak("I am Genos. How can I Serve you?")

def takecommand():
# it takes mic input from the user and return string output
r = sr.Recognizer()
with sr.Microphone() as source:
print("Listening...")
r.pause_threshold = 1
audio = r.listen(source)
try:
print("Recognizing..")
query = r.recognize_google(audio, language='en-in')
print(f"user Said :{query}n")
except Exception as e:
print(e)
speak("Say that again please")
return "None"
return query

def sendEmail(to, content):
server = smtplib.SMTP("smtp.gmail.com", 587)
server.ehlo()
server.starttls()
server.login('mail@gmail.com', '###')
server.sendmail('mail@gmail.com', to, content)
server.close()
return

def my_loop(queue):
wishme(queue)
while True:
query = takecommand().lower()
# Logic for executing task based query
if 'wikipedia' in query:
queue.put('searching Wikipedia....')
speak('searching Wikipedia....')
query = query.replace("wikipedia", "")
results = wikipedia.summary(query, sentences=5)
queue.put("According to wikipedia" + str(results))
speak("According to wikipedia")
print(results)
speak(results)
elif 'open youtube' in query:
queue.put("opening youtube.com")
webbrowser.open("youtube.com")
elif 'open google' in query:
queue.put("opening google.com")
webbrowser.open("google.com")
elif 'open stackoverflow' in query:
queue.put("opening stackoverflow.com")
webbrowser.open("stackoverflow.com")
elif 'open mailbox' in query:
webbrowser.open("gmail.com");

elif 'play music' in query:
music_dir = 'D:\SAHIL\$ONGS_MJ'
songs = os.listdir(music_dir)
queue.put(f"playing music {songs[0]}")
print(songs)
os.startfile(os.path.join(music_dir, songs[0]))
elif 'the time' in query:
strTime = datetime.datetime.now().strftime("%H:%M:%S")
speak(f"Sir the time is {strTime}", queue)
elif 'open code' in query:
codepath = "C:\Users\Sahil\AppData\Local\Programs\Microsoft VS Code Insiders\Code - Insiders.exe"
queue.put(f"opening code {codepath}")
os.startfile(codepath)
elif 'email to sahil' in query:
try:
queue.put("What should i say ?")
speak("What should i say ?")
content = takecommand()
to = "mail@gmail.com@gmail.com"
sendEmail(to, content)
queue.put(f"Email has been sent: {content}")
speak("Email has been sent")
except Exception as e:
print(e)
queue.put(f"Could nott send the email: {e}")
speak("Could nott send the email ")
elif 'how are you' in query:
queue.put("I am fine sir. How are you?")
speak("I am fine sir. How are you?")
elif 'i am fine' in query:
queue.put("that's good to know, how can I help you")
speak("that's good to know, how can I help you")
elif 'goodbye' in query:
queue.put("bye Sir")
speak("bye Sir")
queue.put("quit")
break # exit loop and thread will end                      
#exit()
def update_text():
if not queue.empty():
text = queue.get()
if text == 'quit':
root.destroy() # close window and stop `root.mainloop()`
return # don't run `after` again           
else:
t.insert('end', text)
root.after(200, update_text)
# --- main ---
if __name__ == "__main__":
engine = pyttsx3.init('sapi5') # Windows
#engine = pyttsx3.init('espeak') # Linux
voices = engine.getProperty('voices')
# print(voices[0].id)
engine.setProperty('voice', voices[0].id)
# --- 
root = tk.Tk()
t = tk.Text()
t.pack()
queue = queue.Queue()
update_text()
task = threading.Thread(target=my_loop, args=(queue,)) # it has to be `,` in `(queue,)` to create tuple with one value
task.start() # start thread
root.mainloop()
task.join() # wait for end of thread

相关内容

  • 没有找到相关文章

最新更新