Tôi tin rằng bạn không nên thực hiện vòng lặp chính trên một chuỗi khác. AFAIK, vòng lặp chính sẽ được thực hiện trên cùng một luồng tạo tiện ích con.
Bộ công cụ GUI mà tôi quen thuộc (Tkinter, .NET Windows Forms) là như vậy: Bạn chỉ có thể thao tác GUI từ một chuỗi.
Trên Linux, mã của bạn đặt ra một ngoại lệ:
self.tk.mainloop(n)
RuntimeError: Calling Tcl from different appartment
Một trong những điều sau đây sẽ làm việc (không đề phụ):
if __name__ == '__main__':
t = tk.Tk()
t.iconbitmap('icon.ico')
b = tk.Button(text='test', command=exit)
b.grid(row=0)
t.mainloop()
Với chủ đề phụ:
def threadmain():
t = tk.Tk()
t.iconbitmap('icon.ico')
b = tk.Button(text='test', command=exit)
b.grid(row=0)
t.mainloop()
if __name__ == '__main__':
thread.start_new_thread(threadmain,())
while 1:
sleep(1)
Nếu bạn cần giao tiếp với tkinter từ bên ngoài sợi tkinter, tôi đề nghị bạn thiết lập một bộ đếm thời gian kiểm tra hàng đợi cho công việc.
Dưới đây là một ví dụ:
import Tkinter as tk
import thread
from time import sleep
import Queue
request_queue = Queue.Queue()
result_queue = Queue.Queue()
def submit_to_tkinter(callable, *args, **kwargs):
request_queue.put((callable, args, kwargs))
return result_queue.get()
t = None
def threadmain():
global t
def timertick():
try:
callable, args, kwargs = request_queue.get_nowait()
except Queue.Empty:
pass
else:
print "something in queue"
retval = callable(*args, **kwargs)
result_queue.put(retval)
t.after(500, timertick)
t = tk.Tk()
t.configure(width=640, height=480)
b = tk.Button(text='test', name='button', command=exit)
b.place(x=0, y=0)
timertick()
t.mainloop()
def foo():
t.title("Hello world")
def bar(button_text):
t.children["button"].configure(text=button_text)
def get_button_text():
return t.children["button"]["text"]
if __name__ == '__main__':
thread.start_new_thread(threadmain,())
trigger = 0
while 1:
trigger += 1
if trigger == 3:
submit_to_tkinter(foo)
if trigger == 5:
submit_to_tkinter(bar, "changed")
if trigger == 7:
print submit_to_tkinter(get_button_text)
sleep(1)
Vâng, bạn đã nhấn đinh trên đầu, nó hoạt động ... nhưng tôi đã phải chịu đựng từ việc không cung cấp đủ thông tin. Lý do của tôi là tôi muốn có thể làm những việc để tìm kiếm nơi vòng lặp trong ... Có một chút mới đối với SO, tôi có nên chấp nhận câu trả lời của bạn và hỏi một câu hỏi dài dòng hơn không? – burito
Xin chào, tôi đã cập nhật câu trả lời của tôi với một đề xuất và ví dụ mã để thực hiện điều này. Vòng lặp while bây giờ gọi một vài phương thức trên chuỗi tkinter, sử dụng hàng đợi yêu cầu/đáp ứng. – codeape
BTW, cho mã sản xuất Tôi đề nghị bạn đóng gói cửa sổ, chuỗi và hàng đợi Tkinter trong một lớp. Điều này để tránh các globals chúng ta có: request_queue, response_queue và t. Bạn cũng cần xử lý lỗi xung quanh có thể gọi (* args, ** kwargs). – codeape