Autoconnecting signals in GTK4

,

Hi there, I am currently trying to adapt the GTK4 Hello World program to use GTK Builder. I have made the .ui file and imported it however when running the program I get the error “failed to add UI from file: No function named print_hello”. From reading documentation it seems like it may be an issue with the current object set however I am unsure what that should be.

#include <gtk-4.0/gtk/gtk.h>

static void print_hello (GtkWidget *widget, gpointer data) {
  g_print("Hello World\n");
}

static void activate(GtkApplication *app, gpointer user_data) {
  GError *error = NULL;
  GtkBuilder *builder;

  GtkWindow *window;
  GtkButton *button;

  builder = gtk_builder_new();

  gtk_builder_set_current_object(builder, G_OBJECT(app));

  if (!gtk_builder_add_from_file(builder, "application.ui", &error))
    g_error("failed to add UI from file: %s", error->message);

  window = GTK_WINDOW(gtk_builder_get_object(builder, "window"));
  gtk_application_add_window(app, window);

  gtk_window_present(window);
}

int main(int argc, char **argv) {
  GtkApplication *app;
  int status;

  app = gtk_application_new("org.gtk.example", G_APPLICATION_DEFAULT_FLAGS);
  g_signal_connect(app, "activate", G_CALLBACK(activate), NULL);
  status = g_application_run(G_APPLICATION(app), argc, argv);
  g_object_unref(app);

  return status;
}
<?xml version='1.0' encoding='UTF-8'?>
<!-- Created with Cambalache 0.96.1 -->
<interface>
  <requires lib="gtk" version="4.12"/>
  <object class="GtkApplicationWindow" id="window">
    <property name="default-height">200</property>
    <property name="default-width">200</property>
    <property name="title">Hello</property>
    <child>
      <object class="GtkButton" id="button">
        <property name="label">Hello World</property>
        <signal name="clicked" handler="print_hello" object="button"/>
      </object>
    </child>
  </object>
</interface>

I am using the following command to compile: gcc $(pkg-config --cflags gtk4 gmodule-export-2.0) -Wl,--export-dynamic -o hello-world-gtk main.c $(pkg-config --libs gtk4 gmodule-export-2.0)

I have tried using gtk_builder_new_from_file but that has the same error.

Assistance would be much appreciated, if there is any additional information required I am happy to provide it.

Hi,

From reading documentation it seems like it may be an issue with the current object set however I am unsure what that should be.

no, you shouldn’t have to call gtk_builder_set_current_object. But you should expose the function to the builder using gtk_builder_cscope_add_callback, like so:

  GtkBuilderScope *scope;

  scope = gtk_builder_get_scope(builder);
  gtk_builder_cscope_add_callback(scope, print_hello);

With these lines added, your application runs, and prints “Hello world” when the button is clicked.

Please note that a more modern way to structure your application & use GtkBuilder is through composite widget templates. In that case, you’d expose callbacks using gtk_widget_class_bind_template_callback instead. Please let me know if you’d like an example of that.

2 Likes

Thank you very much for your assistance, I understand how it works much better now. I am fairly confident that I can get the template binding to work and there seems to much more information available for them.

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.