The dialog is interrupted when using GtkBuilder to automatically connect signals, but it works when manually connecting signals

I want to have a dialog box where some buttons close the dialog and others do not. The way I do this is to use the response signal from Gtk.Dialog to call emit_stop_by_name('response') in the dialog box. (If someone knows the best way to do this, this may preempt the whole question.)

This worked when I used PyGTK. Now I go to PyGObject .. and it seems that this method will work only if I manually connect the response signal, and not using Gtk.Builder.connect_signals() .

But do not take my word for it. Here is a minimal example of my problem:

 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() 

When you run this, you get a window with a single button. When you click this button, a dialog box appears with two buttons, one with the inscription "Do not close the dialog", and the other - "Close the dialog." When you run the code above, both buttons will close the dialog.

But if you change the use of Gtk.Builder.connect_signals() to manually connect the signal, replacing

  self.builder.connect_signals(self) 

from

  self.dialog1.connect('response', self.on_response) 

then it starts working as programmed (the "Do not close dialog" button does not close the dialog).

But shouldn't these two lines be exactly functionally identical in this context? Is there a way to find out what is different between the two scenarios?

I can say that the signals are still connected in both situations, because the text is still printed in the CLI from DummyDialog.on_response . But it seems that the widget.emit_stop_by_name('response') stops working when I use GtkBuilder.

Even more perplexing is that if you take this exact code and run it on PyGTK (change from gi.repository import Gtk to import gtk as Gtk ), then it works correctly in both scenarios (using self.builder.connect_signals(self) or self.dialog1.connect('response', self.on_response) ).

+6
source share
1 answer

I would do it a little differently. Remove dialog1.destroy() in the button callback and change the on_response to:

  def on_response(self, widget, response, data=None): print 'response:', response if response < 0: self.dialog1.destroy() 
+2
source

Source: https://habr.com/ru/post/907192/


All Articles