Python 为什么当我没有(有意地)执行任何多线程时会出现错误“主线程不在主循环中”?
我正在尝试使用Tkinter制作一个类似于MS-DOS的GUI。除了按钮上的文字居中对齐外,尽管我尽了最大努力使其左对齐,它看起来很棒。我希望能够使用“回车”键选择菜单选项,通过上下箭头键来浏览我的菜单。Enter可以正常工作,但当我使用任意一个箭头键时,会出现以下错误:Python 为什么当我没有(有意地)执行任何多线程时会出现错误“主线程不在主循环中”?,python,multithreading,tkinter,Python,Multithreading,Tkinter,我正在尝试使用Tkinter制作一个类似于MS-DOS的GUI。除了按钮上的文字居中对齐外,尽管我尽了最大努力使其左对齐,它看起来很棒。我希望能够使用“回车”键选择菜单选项,通过上下箭头键来浏览我的菜单。Enter可以正常工作,但当我使用任意一个箭头键时,会出现以下错误: Unhandled exception in listener callback Traceback (most recent call last): File "C:\Users\******\AppData\Local
Unhandled exception in listener callback
Traceback (most recent call last):
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\site-packages\pynput\_util\__init__.py", line 162, in inner
return f(self, *args, **kwargs)
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\site-packages\pynput\keyboard\_win32.py", line 280, in _process
self.on_press(key)
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\site-packages\pynput\_util\__init__.py", line 78, in inner
if f(*args) is False:
File "paltoydMockGUI.py", line 27, in on_press
globals()[names[currentBtn + 1]]['state'] = 'active'
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\tkinter\__init__.py", line 1492, in __setitem__
self.configure({key: value})
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\tkinter\__init__.py", line 1485, in configure
return self._configure('configure', cnf, kw)
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\tkinter\__init__.py", line 1476, in _configure
self.tk.call(_flatten((self._w, cmd)) + self._options(cnf))
RuntimeError: main thread is not in main loop
Traceback (most recent call last):
File "paltoydMockGUI.py", line 59, in <module>
listener.join()
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\site-packages\pynput\_util\__init__.py", line 210, in join
six.reraise(exc_type, exc_value, exc_traceback)
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\site-packages\six.py", line 702, in reraise
raise value.with_traceback(tb)
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\site-packages\pynput\_util\__init__.py", line 162, in inner
return f(self, *args, **kwargs)
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\site-packages\pynput\keyboard\_win32.py", line 280, in _process
self.on_press(key)
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\site-packages\pynput\_util\__init__.py", line 78, in inner
if f(*args) is False:
File "paltoydMockGUI.py", line 27, in on_press
globals()[names[currentBtn + 1]]['state'] = 'active'
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\tkinter\__init__.py", line 1492, in __setitem__
self.configure({key: value})
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\tkinter\__init__.py", line 1485, in configure
return self._configure('configure', cnf, kw)
File "C:\Users\******\AppData\Local\Programs\Python\Python37\lib\tkinter\__init__.py", line 1476, in _configure
self.tk.call(_flatten((self._w, cmd)) + self._options(cnf))
RuntimeError: main thread is not in main loop
到目前为止,它所做的只是创建一个带有白色边框的矩形的全屏应用程序,其中包含根据名称列表标记的5个按钮,以及pynput键盘侦听器。我现在所需要的只是带箭头键的导航,但我遇到了那个讨厌的错误
任何帮助都将不胜感激 这在我的电脑里起作用了
import tkinter as tk
from pynput import keyboard
names = ['documents', 'research', 'I forgot the other buttons', 'button 4', 'button 5']
currentBtn = 0
def mkBtn(names):
for i in range (len(names)):
globals()[names[i]] = tk.Button (frame, justify = 'left', font = 'Unifont', bd = 0, bg = 'black', activebackground = 'white', text = str(names[i]), relief = 'flat', activeforeground = 'black', foreground = 'white', width = 200)
globals()[names[i]].grid(row = i, column = 0, sticky = 'W')
def on_press(key):
if key == keyboard.Key.esc:
return False # stop listener
try:
k = key.char # single-char keys
except:
k = key.name # other keys
if k in ['up', 'down', 'enter']: # keys of interest
global currentBtn
if k == 'up' and currentBtn != 0:
globals()[names[currentBtn - 1]]['state'] = 'active'
globals()[names[currentBtn]]['state'] = 'normal'
currentBtn -= 1
elif k == 'down' and currentBtn != len(names) - 1:
globals()[names[currentBtn + 1]]['state'] = 'active'
globals()[names[currentBtn]]['state'] = 'normal'
currentBtn += 1
else:
print('works')
print(k)
root = tk.Tk()
root.attributes("-fullscreen", True)
root.title("Test")
root.geometry('1920x1080')
root.configure(bg='black')
canvas = tk.Canvas(root, width = 1920, height = 1080, bd = '-2' , bg = 'black')
canvas.pack()
canvas.create_rectangle(71, 40, 1849, 1040, outline = 'white', fill = 'black', width = 4)
#main menu frame
frame = tk.Frame(root, bg='black');
frame.place(relx = .045, rely = .05, relwidth = .909, relheight = .9)
#labeling main menu
mkBtn(names)
documents['state'] = 'active'
listener = keyboard.Listener(on_press=on_press)
listener.start()
root.mainloop()
为什么在代码中使用块线程和while循环?Read和所有Tcl命令都需要来自同一线程。
import tkinter as tk
from pynput import keyboard
names = ['documents', 'research', 'I forgot the other buttons', 'button 4', 'button 5']
currentBtn = 0
def mkBtn(names):
for i in range (len(names)):
globals()[names[i]] = tk.Button (frame, justify = 'left', font = 'Unifont', bd = 0, bg = 'black', activebackground = 'white', text = str(names[i]), relief = 'flat', activeforeground = 'black', foreground = 'white', width = 200)
globals()[names[i]].grid(row = i, column = 0, sticky = 'W')
def on_press(key):
if key == keyboard.Key.esc:
return False # stop listener
try:
k = key.char # single-char keys
except:
k = key.name # other keys
if k in ['up', 'down', 'enter']: # keys of interest
global currentBtn
if k == 'up' and currentBtn != 0:
globals()[names[currentBtn - 1]]['state'] = 'active'
globals()[names[currentBtn]]['state'] = 'normal'
currentBtn -= 1
elif k == 'down' and currentBtn != len(names) - 1:
globals()[names[currentBtn + 1]]['state'] = 'active'
globals()[names[currentBtn]]['state'] = 'normal'
currentBtn += 1
else:
print('works')
print(k)
root = tk.Tk()
root.attributes("-fullscreen", True)
root.title("Test")
root.geometry('1920x1080')
root.configure(bg='black')
canvas = tk.Canvas(root, width = 1920, height = 1080, bd = '-2' , bg = 'black')
canvas.pack()
canvas.create_rectangle(71, 40, 1849, 1040, outline = 'white', fill = 'black', width = 4)
#main menu frame
frame = tk.Frame(root, bg='black');
frame.place(relx = .045, rely = .05, relwidth = .909, relheight = .9)
#labeling main menu
mkBtn(names)
documents['state'] = 'active'
listener = keyboard.Listener(on_press=on_press)
listener.start()
root.mainloop()