Daniel
Daniel

Reputation: 607

Threading in a Python Gtk Application

I am trying to create a program that displays the positional data from a gyroscope. I have been using the threading.Thread module for this purpose. I also have to use the time.sleep() to prevent it from crashing right off the bat. My problem is after it has been running for a while the program will sometimes freeze. It is implemented something like this:

def get_gyro_data():
    return <the data from the gyro>

class Handler:
    def __init__(self):
        self.label = builder.get_object("my_label")
        threading.Thread(target=self.pos_data_update).start()

    def pos_data_update(self, *args):
        while True:
            self.label.set_text(get_gyro_data())
            time.sleep(.5)

Any suggestions? Also is there a way I can do this without using time.sleep?

Upvotes: 1

Views: 228

Answers (1)

Aran-Fey
Aran-Fey

Reputation: 43296

Gtk is not thread safe. All changes to the GUI should be made from the main thread (the one that runs the mainloop).

I like to use the following function:

import gi
gi.require_version('Gtk', '3.0')
from gi.repository import Gtk, Gdk, GLib

def mainloop_do(callback, *args, **kwargs):
    def cb(_None):
        callback(*args, **kwargs)
        return False
    Gdk.threads_add_idle(GLib.PRIORITY_DEFAULT, cb, None)

This allows you to pass the work to the main thread with minimal changes to your code:

def pos_data_update(self, *args):
    while True:
        mainloop_do(self.label.set_text, get_gyro_data())
        time.sleep(.5)

Upvotes: 1

Related Questions