egorFiNE
egorFiNE

Reputation: 302

How to use C blocks with Gtk callbacks?

Is there a way to use C blocks in Gtk+ callbacks? I was looking into something like that:

gboolean (^calledBack)(gpointer) = ^gboolean (gpointer data) {
    printf("Callback fired!\n");    
    return FALSE;
};

g_timeout_add(300, calledBack, NULL);

Upvotes: 3

Views: 414

Answers (2)

user4815162342
user4815162342

Reputation: 155326

Even though you can't pass the block to g_timeout_add directly, it is easy to set up a trampoline to do it for you. Here is a small test program that creates two closures using blocks and passes them off to g_timeout_add:

#include <glib.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <Block.h>

typedef gboolean (^callback_type)();

static gboolean trampoline(gpointer data) {
    callback_type callback = data;
    gboolean ret = callback();
    Block_release(callback);
    return ret;
}

void some_gtk_handler(int param)
{
  gboolean (^callback)() = ^gboolean () {
      printf("Callback fired: %d!\n", param);    
      return FALSE;
  };
  g_timeout_add(300, trampoline, Block_copy(callback));
}

int main()
{
  GMainLoop *ml = g_main_loop_new(NULL, FALSE);
  some_gtk_handler(0);
  some_gtk_handler(42);
  g_main_loop_run(ml);
  return 0;
}

The above code specifies a one-shot handler, so it can release the block in the trampoline. If you need blocks that are run multiple times, remove the call to Block_release from the trampoline and schedule them using g_timeout_add_full with a destroy notify callback:

g_timeout_add_full(G_PRIORITY_DEFAULT, 300, trampoline, Block_copy(callback),
                   release_callback);

...where release_callback is a utility function defined as:

static void release_callback(gpointer data) {
    Block_release(data);
}

Upvotes: 2

Alexander L. Belikoff
Alexander L. Belikoff

Reputation: 5721

ANSI C does not have any block facility. Do you mean Objective-C? In the latter case the answer is no, as Gtk+ is a pure C framework.

Upvotes: 0

Related Questions