You can also create a cairo surface of the pixbuf through
cairo_image_surface_create_for_data() like this:

  int img_width = gdk_pixbuf_get_width(pixbuf);
  int img_height = gdk_pixbuf_get_height(pixbuf);

  cairo_surface_t *surface
    = cairo_image_surface_create_for_data(gdk_pixbuf_get_pixels(pixbuf),
                                          CAIRO_FORMAT_RGB24,
                                          img_width,
                                          img_height,
                                          gdk_pixbuf_get_rowstride(pixbuf));


but beware that you will need to swap R and B when drawing. See the
cairo-circles.c example at:

http://giv.sourceforge.net/gtk-image-viewer/gtkimageviewer_tutorial.html

Regards,
Dov

2009/2/22 Tadej Borovšak <[email protected]>

> Hi.
>
> I missed list the first time (sorry Roei for spamming you).
>
> ---------- Forwarded message ----------
> From: Tadej Borovšak <[email protected]>
> Date: 2009/2/22
> Subject: Re: cairo_surface_t to pixbuf
> To: Roei Azachi <[email protected]>
>
>
> 2009/2/22 Roei Azachi <[email protected]>:
> > Hi,
> > I was wondering if there is a way of converting cairo_surface_t to pixbuf
> > currently I am doing:
> > cairo_surface_write_to_png(oimg2, "tmp.png");
> > pixbuf = gdk_pixbuf_new_from_file("tmp.png", &g_err);
> > I'm sure there is a way, but I don't know how...
> > Thanks,
> > Roei
> > _______________________________________________
> > gtk-list mailing list
> > [email protected]
> > http://mail.gnome.org/mailman/listinfo/gtk-list
> >
>
> Hi.
>
> I only converted cairo's image surfaces to PPM images. I did this by
> obtaining surface's width, height, rowstride and format, then manually
> copied pixel values from surface to PPM.
>
> Simple function for converting surface to pixbuf would look something like
> this:
>
> ------- CODE --------
> GdkPixbuf *
> convert( cairo_surface_t *surface )
> {
>       GdkPixbuf *pixbuf;
>       gint width  = cairo_image_surface_get_width( surface );
>       gint height = cairo_image_surface_get_height( surface );
>       gint stride = cairo_image_surface_get_stride( surface );
>       cairo_format_t format = cairo_image_surface_get_format( surface );
>       guchar *data = cairo_image_surface_get_data( surface );
>       gint row, col;
>
>       if( format == CAIRO_FORMAT_ARGB32 )
>       {
>               guchar *pixels;
>               gint    pix_stride;
>
>               /* Temporary pointers for iterating. */
>               guchar *p_dat, *p_pix;
>
>               pixbuf = gdk_pixbuf_new( GDK_COLORSPACE_RGB, TRUE, 8,
> width, height );
>               pixels = gdk_pixbuf_get_pixels( pixbuf );
>               pix_stride = gdk_pixbuf_get_rowstride( pixbuf );
>
>               p_dat = data;
>               p_pix = pixels;
>
>               for( row = 0; row < height; row++ )
>               {
>                       p_pix = pixels + row * pix_stride;
>                       p_dat = data + row * stride;
>
>                       for( col = 0; col < width; col++ )
>                       {
>                               /* Copy now. Cairo image surfaces use
> pre-multiplied
>                                * alpha, this is why we need to
> calculate RGB values. */
>                               p_pix[0] = p_dat[1] / p_dat[0] * 0xff;
>                               p_pix[1] = p_dat[2] / p_dat[0] * 0xff;
>                               p_pix[2] = p_dat[3] / p_dat[0] * 0xff;
>                               p_pix[3] = p_dat[0];
>
>                               p_pix += 4;
>                               p_dat += 4;
>                       }
>               }
>       }
>       else if( format == CAIRO_FORMAT_RGB24 )
>       {
>               guchar *pixels;
>               gint    pix_stride;
>
>               /* Temporary pointers for iterating. */
>               guchar *p_dat, *p_pix;
>
>               pixbuf = gdk_pixbuf_new( GDK_COLORSPACE_RGB, FALSE, 8,
> width, height );
>               pixels = gdk_pixbuf_get_pixels( pixbuf );
>               pix_stride = gdk_pixbuf_get_rowstride( pixbuf );
>
>               p_dat = data;
>               p_pix = pixels;
>
>               for( row = 0; row < height; row++ )
>               {
>                       p_pix = pixels + row * pix_stride;
>                       p_dat = data + row * stride;
>
>                       for( col = 0; col < width; col++ )
>                       {
>                               p_pix[0] = p_dat[0];
>                               p_pix[1] = p_dat[1];
>                               p_pix[2] = p_dat[2];
>
>                               p_pix += 3;
>                               p_dat += 4;
>                       }
>               }
>       }
>
>       return( pixbuf );
> }
> -------- CODE ---------
>
> Note though that I haven't tested this function, so test it before
> using in real application.
>
> --
> Tadej Borovšak
> [email protected]
> [email protected]
>
>
>
> --
> Tadej Borovšak
> [email protected]
> [email protected]
> _______________________________________________
> gtk-list mailing list
> [email protected]
> http://mail.gnome.org/mailman/listinfo/gtk-list
>
_______________________________________________
gtk-list mailing list
[email protected]
http://mail.gnome.org/mailman/listinfo/gtk-list

Reply via email to