Search code examples
cgtk3

get a snapshot of GtkDrawingArea with GTK3, bug on WIndows?


I'm looking for the best way to get pixbuf from a GtkDrawingArea. I see two methods to do that.

  • First I can use gdk_pixbuf_get_from_surface. It could be easy with that but I just get the picture mapped in the GtkDrawingArea, not the painting made with cairo.
  • Second, gdk_pixbuf_get_from_window. This is the way I choose because I think it fits my needs. Indeed, what I want is just to make a quick snapshot of my drawing area with all labels and painting drawn on the picture.

My following code works as expected on GNU/Linux, but on Windows that gives me black png. Does someone could help me to fix the issue?

gtk_widget_get_allocation(widget, &allocation_w);
GdkWindow *window = gtk_widget_get_parent_window(widget);
if (window) {
    pixbuf = gdk_pixbuf_get_from_window(window, allocation_w.x, allocation_w.y, allocation_w.width, allocation_w.height);
    if (pixbuf) {
        file = g_file_new_build_filename(com.wd, filename, NULL);
        g_free(filename);
        stream = (GOutputStream*) g_file_replace(file, NULL, FALSE, G_FILE_CREATE_NONE, NULL, &error);
        if (stream == NULL) {
            if (error != NULL) {
                g_warning("%s\n", error->message);
                g_clear_error(&error);
            }
            g_object_unref(pixbuf);
            g_object_unref(file);
            return;
        }
        gdk_pixbuf_save_to_stream_async(pixbuf, stream, "png", NULL,
                snapshot_callback, (gpointer) g_file_get_basename(file), NULL);

        g_object_unref(stream);
        g_object_unref(pixbuf);
        g_object_unref(file);
    }
}

Solution

  • I have now the answer.

    The API to get a pixbuf from a window is pretty much a remnant of the time when GTK was X11-only. So don't expect to make it work outside of the GNU/Linux X11 environment. The function is removed from the GTK4 API too.

    So, the best way is to use gdk_pixbuf_get_from_surface and to redraw what I need.

    I think I could use GtkOffscreenWindow too but I did not fund any example of use.