Я хочу иметь диалоговое окно, в котором некоторые кнопки закрывают диалог, а другие нет.Я делаю это, используя сигнал response
от Gtk.Dialog
для вызова emit_stop_by_name('response')
в диалоговом окне.(Если кто-то знает о лучшем способе сделать это, это может упредить весь остальной вопрос.)
Это сработало, когда я использовал PyGTK.Я перехожу к PyGObject сейчас ... и кажется, что этот метод будет работать только , если я вручную подключусь к ответному сигналу вместо использования Gtk.Builder.connect_signals()
.
Но не беритемое слово для этого.Вот минимальный пример моей проблемы:
from gi.repository import Gtk
xml = """<interface>
<object class="GtkDialog" id="dialog1">
<signal name="response" handler="on_response"/>
<child internal-child="vbox">
<object class="GtkBox" id="dialog-vbox1">
<child internal-child="action_area">
<object class="GtkButtonBox" id="dialog-action_area1">
<child>
<object class="GtkButton" id="button1">
<property name="label">Don't Close Dialog</property>
<property name="visible">True</property>
</object>
</child>
<child>
<object class="GtkButton" id="button2">
<property name="label">Close Dialog</property>
<property name="visible">True</property>
</object>
</child>
</object>
</child>
</object>
</child>
<action-widgets>
<action-widget response="0">button1</action-widget>
<action-widget response="-6">button2</action-widget>
</action-widgets>
</object>
</interface>
"""
def on_button_clicked(widget):
d = DummyDialog()
d.dialog1.run()
d.dialog1.destroy()
class DummyDialog:
def __init__(self):
self.builder = Gtk.Builder()
self.builder.add_from_string(xml)
self.dialog1 = self.builder.get_object('dialog1')
self.builder.connect_signals(self)
def on_response(self, widget, response, data=None):
print 'response:', response
if response >= 0:
widget.emit_stop_by_name('response')
w = Gtk.Window()
w.connect('destroy', Gtk.main_quit)
b = Gtk.Button('Open Dialog')
b.connect('clicked', on_button_clicked)
w.add(b)
w.show_all()
Gtk.main()
Когда вы запустите это, вы получите окно с одной кнопкой.Когда вы нажимаете эту кнопку, появляется диалоговое окно с двумя кнопками, одна с надписью «Не закрывать диалог», а другая с надписью «Закрыть диалог».При выполнении приведенного выше кода обе кнопки закроют диалоговое окно.
Но если вы переключитесь с использования Gtk.Builder.connect_signals()
на ручное подключение сигнала, заменив
self.builder.connect_signals(self)
на
self.dialog1.connect('response', self.on_response)
затем он начинает работать, как задумано (кнопка «Не закрывать диалог» не закрывает диалоговое окно).
Но не должны ли эти две строки быть абсолютно функционально идентичными в данном контексте?Есть ли какой-нибудь способ выяснить, что отличается между этими двумя сценариями?
Я могу сказать, что сигналы все еще связаны в обеих ситуациях, потому что текст все еще печатается в CLI из DummyDialog.on_response
.Но кажется, что часть widget.emit_stop_by_name('response')
перестает работать, когда я использую GtkBuilder.
Еще большее недоумение вызывает то, что если вы возьмете этот точный код и запустите его на PyGTK (измените from gi.repository import Gtk
на import gtk as Gtk
), тогдаон работает правильно в обоих сценариях (с использованием self.builder.connect_signals(self)
или self.dialog1.connect('response', self.on_response)
).