Je pense que l'équivalent de l'ancien style gtk.gdk.threads_init()
est:
from gi.repository import Gdk
Gdk.threads_init()
Cependant, comme le FAQ warns, le filetage est pas un moyen propre pour atteindre cet objectif. Une meilleure façon est d'utiliser GObject.idle_add
pour exécuter une fonction à chaque fois que l'interface graphique est inactive.
"""Show a shell command's output in a gtk.TextView without freezing the UI"""
import os
import locale
import subprocess
import shlex
import gi.repository.Gtk as gtk
from gi.repository import GObject
PIPE = subprocess.PIPE
encoding = locale.getpreferredencoding()
def utf8conv(x):
return unicode(x, encoding).encode('utf8')
class MyWindow:
def __init__(self):
sw = gtk.ScrolledWindow()
sw.set_policy(gtk.PolicyType.AUTOMATIC, gtk.PolicyType.AUTOMATIC)
textview = gtk.TextView()
textbuffer = textview.get_buffer()
sw.add(textview)
win = gtk.Window()
win.resize(300, 500)
win.connect('delete-event', gtk.main_quit)
self.button_sim = gtk.Button(u"Press me!")
self.button_abort = gtk.Button("Abort")
self.button_quit = gtk.Button("Quit")
command = 'ls -R %s' % (os.getcwd(),)
self.button_sim.connect(
"clicked", self.on_button_clicked, textview, textbuffer, command)
self.button_abort.connect("clicked", self.on_abort)
self.button_quit.connect("clicked", self.main_quit)
vbox = gtk.VBox()
vbox.pack_start(self.button_sim, expand=False, fill=False, padding=0)
vbox.pack_start(self.button_abort, expand=False, fill=False, padding=0)
vbox.pack_start(self.button_quit, expand=False, fill=False, padding=0)
vbox.pack_start(sw, expand=True, fill=True, padding=0)
win.add(vbox)
win.show_all()
def read_output(self, view, buffer, command):
yield True # allow the UI to refresh
proc = subprocess.Popen(
shlex.split(command), stderr=PIPE, stdout=PIPE)
while True:
if self.job_aborted:
print('user aborted')
proc.terminate()
break
try:
line = proc.stdout.readline()
if line:
it = buffer.get_end_iter()
buffer.place_cursor(it)
buffer.insert(it, utf8conv(line))
view.scroll_to_mark(buffer.get_insert(), 0.1,
use_align=False, xalign=0.5, yalign=0.5)
except IOError:
pass
yield True
yield False
def on_button_clicked(self, button, view, buffer, command):
self.job_aborted = False
GObject.idle_add(self.read_output(view, buffer, command).next)
def on_abort(self, button):
self.job_aborted = True
def main_quit(self, obj):
self.job_aborted = True
gtk.main_quit()
if __name__ == "__main__":
app = MyWindow()
gtk.main()
quel est le point d'exiger pygtk et en ignorant l'exception lorsque "besoin" échoue? vous devriez décider si vous utilisez le vieux pygtk ou 'gi.repository' – user4815162342
C'est ce que je reçois de certains tutoriels. gi.repository est celui que j'utilise. J'avais essayé à la fois pygtk et gi.repository mais les deux n'ont pas de gdk, ce que je ne comprends pas pourquoi. J'ai passé en revue le manuel de documentation de gtk, lequel gdk devrait être là. – Kin
Vous confondez l'ancienne API 'pygtk' où l'on devrait' importer gtk' et ensuite accéder 'gtk. 'et' gtk.gdk. '. C'est ce que [l'entrée FAQ] (http://faq.pygtk.org/index.py?req=show&file=faq14.023.htp) que vous avez écrit dans le commentaire utilise. Pour GTK3, les liaisons pygtk ne sont plus maintenues et l'on est supposé passer à l'introspection gobject. C'est le 2ème style (* pas * mentionné dans la FAQ, qui est l'ancienne FAQ de PyGTK), 'de gi.repository importer Gtk, Gdk' et ensuite accéder' Gtk. 'et' Gdk. '. –
user4815162342