尝试使用多线程接收套接字数据

时间:2018-03-15 14:00:58

标签: python select tkinter

编辑:我的计划改变后(布莱恩说我无法使用'选择'库为TkInter) 我尝试使用多线程,并且我输入了似乎不起作用的东西:

def receive_data():
    try:
        (client_socket, address) = server_socket.accept()
        print client_socket.recv(1024)
    except socket.error:
        print 'error'


def server_window():
    window = Tk()
    data = ''
    activate_window(window, 666, 666)
    b1 = Button(window, text='RECEIVE DATA', fg='sienna', bg='khaki', command=lambda info=data: handle_waiter(info))
    b1.grid(sticky='W', row=2, column=0, columnspan=1)
    b1 = Button(window, text='ORDERS',  fg='sienna', bg='khaki', command=orders_window)
    b1.grid(sticky='W', row=1, column=0, columnspan=1)
    thread = threading.Thread(target=receive_data())
    thread.start()

    window.mainloop()

然而,我所做的似乎是阻止了GUI ......如果有人能帮助我,我会很高兴

2 个答案:

答案 0 :(得分:1)

问题是线程的target是可调用的。 另一方面,您传递给Thread的内容不是receive_data,而是receive_data()

长话短说,当你到达receive_data构造函数的参数评估点时,会在当前线程上调用Thread函数,并保持在它内部直到它结束。

您只需删除括号,然后按如下方式创建线程:

thread = threading.Thread(target=receive_data)

答案 1 :(得分:1)

一段时间后,我设法使用select而不阻塞我的TKinter代码,

现在我配置了一些随机按钮(b5)来发送消息(应该阻止)

def rms_window(waiter):
    """MAIN WAITER'S WINDOW"""
    window = waiter.get_window()  # Main window called from the waiter class.
    activate_window(window, 600, 482)  # 600x482

    bg_icon = ImageTk.PhotoImage(Image.open('bg_icon.png'))  # Image background picture.
    bg_label = Label(window, height=482, width=600, image=bg_icon)  # Create an image label for the window background.
    bg_label.place(x=0, y=0)

    order_list = Listbox(window, height=10, width=30, bg='white', fg='brown')  # Order list ListBox.
    sort_gui(window, order_list)  # sort scrollbar, labels and order list inside the waiter's window.

    menu_icon = ImageTk.PhotoImage(Image.open('menu_icon.png'))  # Image of the menu button.
    b1 = Button(window, image=menu_icon)  # Append button to the main window and apply picture.
    set_gui(b1, 'Menu', 'cyan', 'cyan')
    b1.configure(command=lambda i=waiter.get_socket(): open_menu(waiter, order_list))  # on click - open menu window.
    b1.grid(row=0, column=0)

    t1 = Text(window, width=25, height=1, bg='brown')  # Simple text box used to read bill number in the bill button
    t1.grid(row=14, column=0)

    b2 = Button(window)  # Bill button - reads text from variable t1 and sends the bill of the number given.
    set_gui(b2, 'Bill', 'pale goldenrod', 'chocolate')
    b2.configure(command=lambda i=waiter.get_socket(): send_bill('BILL ' + t1.get(1.0, END), i))
    b2.grid(row=15, column=0)  # Sends the bill to the server once you type an order number inside the textbox.

    b3 = Button(window)
    set_gui(b3, 'SEND ORDER', 'brown', 'chocolate')
    b3.configure(command=lambda i=waiter: i.send_order(order_list))  # On click send the whole order list to the server.
    b3.grid(row=10, column=0)  # Send the order listed in the list box widget.

    chat_icon = ImageTk.PhotoImage(Image.open("chat_icon.png"))
    b4 = Button(window, image=chat_icon)  # Apply chat icon image to waiters chatting button.
    set_gui(b4, 'WAITERS CHAT', 'green', 'green')
    b4.configure(command=lambda i=waiter: waiters_chat(i))  # On click - opens the chat service.
    b4.grid(row=0, column=1, sticky='W')

    b5 = Button(window)
    set_gui(b5, 'TESTER', 'green', 'green')
    b5.configure(command=test_cmd(messages_to_send, waiter.get_socket()))
    b5.grid(row=5, column=5)

    read_list, write_list, x_list = select.select([waiter.get_socket()], [waiter.get_socket()], [])
    send_waiting_messages(write_list, messages_to_send)
    others_messages(read_list)

虽然功能是:

def others_messages(read_list):
    for current_socket in read_list:
        try:
            data = current_socket.recv(1024)
            print data
        except:
            print "Connection with server closed."
            current_socket.close()


def send_waiting_messages(write_list, m_to_send):
    for message in m_to_send:
        (client_socket, data) = message
        if client_socket in write_list:
            print data
            client_socket.send(data)
            m_to_send.remove(message)