Index: glib/poppler-page.cc =================================================================== RCS file: /cvs/poppler/poppler/glib/poppler-page.cc,v retrieving revision 1.51 diff -u -u -r1.51 poppler-page.cc --- glib/poppler-page.cc 21 Sep 2006 22:40:53 -0000 1.51 +++ glib/poppler-page.cc 29 Nov 2006 18:13:02 -0000 @@ -300,15 +300,15 @@ **/ void poppler_page_render (PopplerPage *page, - cairo_t *cairo) + cairo_t *cairo) { CairoOutputDev *output_dev; g_return_if_fail (POPPLER_IS_PAGE (page)); - + output_dev = page->document->output_dev; output_dev->setCairo (cairo); - + page->page->displaySlice(output_dev, 72.0, 72.0, 0, gFalse, /* useMediaBox */ @@ -318,14 +318,88 @@ (int) ceil (page->page->getCropHeight ()), NULL, /* links */ page->document->doc->getCatalog ()); + + output_dev->setCairo (NULL); +} + +/** + * poppler_page_render_surface: + * @page: the page to render from + * @src_x: x coordinate of upper left corner + * @src_y: y coordinate of upper left corner + * @src_width: width of rectangle to render + * @src_height: height of rectangle to render + * @scale: scale specified as pixels per point + * @rotation: rotate the document by the specified degree + * + * Render the page to a cairo surface. + * + * Return value: a newly allocated #cairo_surface_t + **/ +cairo_surface_t * +poppler_page_render_to_surface (PopplerPage *page, + int src_x, int src_y, + int src_width, int src_height, + double scale, + int rotation) +{ + CairoOutputDev *output_dev; + cairo_surface_t *surface; + double width, height; + int cairo_width, cairo_height, cairo_rowstride, rotate; + unsigned char *cairo_data; + static cairo_user_data_key_t key; + cairo_t *cr; + + g_return_val_if_fail (POPPLER_IS_PAGE (page), NULL); + + rotate = rotation + page->page->getRotate (); + if (rotate == 90 || rotate == 270) { + height = page->page->getCropWidth (); + width = page->page->getCropHeight (); + } else { + width = page->page->getCropWidth (); + height = page->page->getCropHeight (); + } + + cairo_width = (int) ceil (width * scale); + cairo_height = (int) ceil (height * scale); + + cairo_rowstride = cairo_width * 4; + cairo_data = (guchar *) g_malloc (cairo_height * cairo_rowstride); + memset (cairo_data, 0xff, cairo_height * cairo_rowstride); + + surface = cairo_image_surface_create_for_data (cairo_data, + CAIRO_FORMAT_ARGB32, + src_width, src_height, + cairo_rowstride); + cairo_surface_set_user_data (surface, &key, cairo_data, + (cairo_destroy_func_t)g_free); + + cr = cairo_create (surface); + output_dev = page->document->output_dev; + output_dev->setCairo (cr); + cairo_destroy (cr); + + page->page->displaySlice(output_dev, + 72.0 * scale, 72.0 * scale, + rotation, + gFalse, /* useMediaBox */ + gTrue, /* Crop */ + src_x, src_y, + src_width, src_height, + NULL, /* links */ + page->document->doc->getCatalog ()); output_dev->setCairo (NULL); + + return surface; } #endif /** - * poppler_page_render: + * poppler_page_render_to_pixbuf: * @page: the page to render from * @src_x: x coordinate of upper left corner * @src_y: y coordinate of upper left corner Index: glib/poppler-page.h =================================================================== RCS file: /cvs/poppler/poppler/glib/poppler-page.h,v retrieving revision 1.21 diff -u -u -r1.21 poppler-page.h --- glib/poppler-page.h 12 Apr 2006 02:07:07 -0000 1.21 +++ glib/poppler-page.h 29 Nov 2006 18:13:02 -0000 @@ -38,7 +38,7 @@ #define POPPLER_IS_PAGE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), POPPLER_TYPE_PAGE)) -GType poppler_page_get_type (void) G_GNUC_CONST; +GType poppler_page_get_type (void) G_GNUC_CONST; void poppler_page_render_to_pixbuf (PopplerPage *page, int src_x, int src_y, @@ -50,7 +50,14 @@ #ifdef POPPLER_HAS_CAIRO void poppler_page_render (PopplerPage *page, - cairo_t *cairo); + cairo_t *cr); +cairo_surface_t *poppler_page_render_to_surface (PopplerPage *page, + int src_x, + int src_y, + int src_width, + int src_height, + double scale, + int rotation); #endif void poppler_page_get_size (PopplerPage *page,