Magellan Linux

Contents of /trunk/gimp/patches/gimp-2.6.11-poppler018.patch

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1597 - (show annotations) (download)
Tue Dec 6 00:48:14 2011 UTC (12 years, 4 months ago) by niro
File size: 15588 byte(s)
-fix build against newer poppler
1 From 69f69eed816b89be9a01a48a1f0643d1fd496118 Mon Sep 17 00:00:00 2001
2 From: Nils Philippsen <nils@redhat.com>
3 Date: Fri, 6 May 2011 11:58:44 +0200
4 Subject: [PATCH] patch: poppler-0.17
5
6 Squashed commit of the following:
7
8 commit 529d940222dfc352d41fbf72de29134421aa4002
9 Author: Nils Philippsen <nils@redhat.com>
10 Date: Fri May 6 11:50:30 2011 +0200
11
12 use code based on pixbufs instead of cairo surfaces
13
14 this is done to avoid adding to libgimp, thanks to Mukund Sivaraman for
15 hints how to do this
16
17 commit f8671d8767d4cdab830dc06310e96c63a88ec0fd
18 Author: Mukund Sivaraman <muks@banu.com>
19 Date: Thu Apr 21 13:57:13 2011 +0530
20
21 file-pdf-load: Update attribution, removing bogus copyright
22 (cherry picked from commit e999122e0b20b6ccd6bde3ce039bb64068fc0019)
23
24 commit 89a78f2590d298dac2f42e6d9a3016fc5d672c70
25 Author: Nils Philippsen <nils@redhat.com>
26 Date: Thu Apr 21 13:52:18 2011 +0200
27
28 file-pdf-load: Use better API + cleanups
29
30 * fixes issues with poppler 0.17 completely
31 * uses new libgimp API to pass surfaces instead of pixbufs
32 * uses GTK+ 3 API to convert surfaces to pixbufs where available
33 (backported from commit 7bdadd80ba479d6ff904e276d805e16f6b940ee2)
34
35 commit 4e92302c4a14a961f112587a0ad86696c88da2f8
36 Author: Nils Philippsen <nils@redhat.com>
37 Date: Thu Apr 21 13:38:08 2011 +0200
38
39 file-pdf-load: Don't use deprecated API (bug #646947)
40
41 (cherry picked from commit 9b3e1c91fd2eac69da6947ec9c7fbf10096ba237)
42
43 Conflicts:
44
45 plug-ins/common/file-pdf.c
46 ---
47 plug-ins/common/file-pdf.c | 323 ++++++++++++++++++++++++++++++++++++++------
48 1 files changed, 283 insertions(+), 40 deletions(-)
49
50 diff --git a/plug-ins/common/file-pdf.c b/plug-ins/common/file-pdf.c
51 index a43b459..43c2b7d 100644
52 --- a/plug-ins/common/file-pdf.c
53 +++ b/plug-ins/common/file-pdf.c
54 @@ -4,6 +4,9 @@
55 *
56 * Copyright (C) 2005 Nathan Summers
57 *
58 + * Some code in render_page_to_surface() borrowed from
59 + * poppler.git/glib/poppler-page.cc.
60 + *
61 * This program is free software; you can redistribute it and/or modify
62 * it under the terms of the GNU General Public License as published by
63 * the Free Software Foundation; either version 2 of the License, or
64 @@ -80,16 +83,20 @@ static gboolean load_dialog (PopplerDocument *doc,
65 static PopplerDocument * open_document (const gchar *filename,
66 GError **error);
67
68 -static GdkPixbuf * get_thumbnail (PopplerDocument *doc,
69 +static cairo_surface_t * get_thumb_surface (PopplerDocument *doc,
70 + gint page,
71 + gint preferred_size);
72 +
73 +static GdkPixbuf * get_thumb_pixbuf (PopplerDocument *doc,
74 gint page,
75 gint preferred_size);
76
77 static gint32 layer_from_pixbuf (gint32 image,
78 - const gchar *layer_name,
79 - gint position,
80 - GdkPixbuf *buf,
81 - gdouble progress_start,
82 - gdouble progress_scale);
83 + const gchar *layer_name,
84 + gint position,
85 + GdkPixbuf *pixbuf,
86 + gdouble progress_start,
87 + gdouble progress_scale);
88
89 /**
90 ** the following was formerly part of
91 @@ -433,11 +440,12 @@ run (const gchar *name,
92 }
93 else
94 {
95 - gdouble width = 0;
96 - gdouble height = 0;
97 - gdouble scale;
98 - gint32 image = -1;
99 - GdkPixbuf *pixbuf = NULL;
100 + gdouble width = 0;
101 + gdouble height = 0;
102 + gdouble scale;
103 + gint32 image = -1;
104 + gint num_pages = 0;
105 + GdkPixbuf *pixbuf = NULL;
106
107 /* Possibly retrieve last settings */
108 gimp_get_data (LOAD_PROC, &loadvals);
109 @@ -455,7 +463,10 @@ run (const gchar *name,
110 g_object_unref (page);
111 }
112
113 - pixbuf = get_thumbnail (doc, 0, param[1].data.d_int32);
114 + num_pages = poppler_document_get_n_pages (doc);
115 +
116 + pixbuf = get_thumb_pixbuf (doc, 0, param[1].data.d_int32);
117 +
118 g_object_unref (doc);
119 }
120
121 @@ -548,6 +559,187 @@ open_document (const gchar *filename,
122 return doc;
123 }
124
125 +/* FIXME: Remove this someday when we depend fully on GTK+ >= 3 */
126 +
127 +#if (!GTK_CHECK_VERSION (3, 0, 0))
128 +
129 +static cairo_format_t
130 +gdk_cairo_format_for_content (cairo_content_t content)
131 +{
132 + switch (content)
133 + {
134 + case CAIRO_CONTENT_COLOR:
135 + return CAIRO_FORMAT_RGB24;
136 + case CAIRO_CONTENT_ALPHA:
137 + return CAIRO_FORMAT_A8;
138 + case CAIRO_CONTENT_COLOR_ALPHA:
139 + default:
140 + return CAIRO_FORMAT_ARGB32;
141 + }
142 +}
143 +
144 +static cairo_surface_t *
145 +gdk_cairo_surface_coerce_to_image (cairo_surface_t *surface,
146 + cairo_content_t content,
147 + int src_x,
148 + int src_y,
149 + int width,
150 + int height)
151 +{
152 + cairo_surface_t *copy;
153 + cairo_t *cr;
154 +
155 + copy = cairo_image_surface_create (gdk_cairo_format_for_content (content),
156 + width,
157 + height);
158 +
159 + cr = cairo_create (copy);
160 + cairo_set_operator (cr, CAIRO_OPERATOR_SOURCE);
161 + cairo_set_source_surface (cr, surface, -src_x, -src_y);
162 + cairo_paint (cr);
163 + cairo_destroy (cr);
164 +
165 + return copy;
166 +}
167 +
168 +static void
169 +convert_alpha (guchar *dest_data,
170 + int dest_stride,
171 + guchar *src_data,
172 + int src_stride,
173 + int src_x,
174 + int src_y,
175 + int width,
176 + int height)
177 +{
178 + int x, y;
179 +
180 + src_data += src_stride * src_y + src_x * 4;
181 +
182 + for (y = 0; y < height; y++) {
183 + guint32 *src = (guint32 *) src_data;
184 +
185 + for (x = 0; x < width; x++) {
186 + guint alpha = src[x] >> 24;
187 +
188 + if (alpha == 0)
189 + {
190 + dest_data[x * 4 + 0] = 0;
191 + dest_data[x * 4 + 1] = 0;
192 + dest_data[x * 4 + 2] = 0;
193 + }
194 + else
195 + {
196 + dest_data[x * 4 + 0] = (((src[x] & 0xff0000) >> 16) * 255 + alpha / 2) / alpha;
197 + dest_data[x * 4 + 1] = (((src[x] & 0x00ff00) >> 8) * 255 + alpha / 2) / alpha;
198 + dest_data[x * 4 + 2] = (((src[x] & 0x0000ff) >> 0) * 255 + alpha / 2) / alpha;
199 + }
200 + dest_data[x * 4 + 3] = alpha;
201 + }
202 +
203 + src_data += src_stride;
204 + dest_data += dest_stride;
205 + }
206 +}
207 +
208 +static void
209 +convert_no_alpha (guchar *dest_data,
210 + int dest_stride,
211 + guchar *src_data,
212 + int src_stride,
213 + int src_x,
214 + int src_y,
215 + int width,
216 + int height)
217 +{
218 + int x, y;
219 +
220 + src_data += src_stride * src_y + src_x * 4;
221 +
222 + for (y = 0; y < height; y++) {
223 + guint32 *src = (guint32 *) src_data;
224 +
225 + for (x = 0; x < width; x++) {
226 + dest_data[x * 3 + 0] = src[x] >> 16;
227 + dest_data[x * 3 + 1] = src[x] >> 8;
228 + dest_data[x * 3 + 2] = src[x];
229 + }
230 +
231 + src_data += src_stride;
232 + dest_data += dest_stride;
233 + }
234 +}
235 +
236 +/**
237 + * gdk_pixbuf_get_from_surface:
238 + * @surface: surface to copy from
239 + * @src_x: Source X coordinate within @surface
240 + * @src_y: Source Y coordinate within @surface
241 + * @width: Width in pixels of region to get
242 + * @height: Height in pixels of region to get
243 + *
244 + * Transfers image data from a #cairo_surface_t and converts it to an RGB(A)
245 + * representation inside a #GdkPixbuf. This allows you to efficiently read
246 + * individual pixels from cairo surfaces. For #GdkWindows, use
247 + * gdk_pixbuf_get_from_window() instead.
248 + *
249 + * This function will create an RGB pixbuf with 8 bits per channel.
250 + * The pixbuf will contain an alpha channel if the @surface contains one.
251 + *
252 + * Return value: (transfer full): A newly-created pixbuf with a reference
253 + * count of 1, or %NULL on error
254 + */
255 +static GdkPixbuf *
256 +gdk_pixbuf_get_from_surface (cairo_surface_t *surface,
257 + gint src_x,
258 + gint src_y,
259 + gint width,
260 + gint height)
261 +{
262 + cairo_content_t content;
263 + GdkPixbuf *dest;
264 +
265 + /* General sanity checks */
266 + g_return_val_if_fail (surface != NULL, NULL);
267 + g_return_val_if_fail (width > 0 && height > 0, NULL);
268 +
269 + content = cairo_surface_get_content (surface) | CAIRO_CONTENT_COLOR;
270 + dest = gdk_pixbuf_new (GDK_COLORSPACE_RGB,
271 + !!(content & CAIRO_CONTENT_ALPHA),
272 + 8,
273 + width, height);
274 +
275 + surface = gdk_cairo_surface_coerce_to_image (surface, content,
276 + src_x, src_y,
277 + width, height);
278 + cairo_surface_flush (surface);
279 + if (cairo_surface_status (surface) || dest == NULL)
280 + {
281 + cairo_surface_destroy (surface);
282 + return NULL;
283 + }
284 +
285 + if (gdk_pixbuf_get_has_alpha (dest))
286 + convert_alpha (gdk_pixbuf_get_pixels (dest),
287 + gdk_pixbuf_get_rowstride (dest),
288 + cairo_image_surface_get_data (surface),
289 + cairo_image_surface_get_stride (surface),
290 + 0, 0,
291 + width, height);
292 + else
293 + convert_no_alpha (gdk_pixbuf_get_pixels (dest),
294 + gdk_pixbuf_get_rowstride (dest),
295 + cairo_image_surface_get_data (surface),
296 + cairo_image_surface_get_stride (surface),
297 + 0, 0,
298 + width, height);
299 +
300 + cairo_surface_destroy (surface);
301 + return dest;
302 +}
303 +
304 +#endif
305 +
306 static gint32
307 layer_from_pixbuf (gint32 image,
308 const gchar *layer_name,
309 @@ -566,6 +758,54 @@ layer_from_pixbuf (gint32 image,
310 return layer;
311 }
312
313 +static cairo_surface_t *
314 +render_page_to_surface (PopplerPage *page,
315 + int width,
316 + int height,
317 + double scale)
318 +{
319 + cairo_surface_t *surface;
320 + cairo_t *cr;
321 +
322 + surface = cairo_image_surface_create (CAIRO_FORMAT_ARGB32, width, height);
323 + cr = cairo_create (surface);
324 +
325 + cairo_save (cr);
326 + cairo_translate (cr, 0.0, 0.0);
327 +
328 + if (scale != 1.0)
329 + cairo_scale (cr, scale, scale);
330 +
331 + poppler_page_render (page, cr);
332 + cairo_restore (cr);
333 +
334 + cairo_set_operator (cr, CAIRO_OPERATOR_DEST_OVER);
335 + cairo_set_source_rgb (cr, 1.0, 1.0, 1.0);
336 + cairo_paint (cr);
337 +
338 + cairo_destroy (cr);
339 +
340 + return surface;
341 +}
342 +
343 +static GdkPixbuf *
344 +render_page_to_pixbuf (PopplerPage *page,
345 + int width,
346 + int height,
347 + double scale)
348 +{
349 + GdkPixbuf *pixbuf;
350 + cairo_surface_t *surface;
351 +
352 + surface = render_page_to_surface (page, width, height, scale);
353 + pixbuf = gdk_pixbuf_get_from_surface (surface, 0, 0,
354 + cairo_image_surface_get_width (surface),
355 + cairo_image_surface_get_height (surface));
356 + cairo_surface_destroy (surface);
357 +
358 + return pixbuf;
359 +}
360 +
361 static gint32
362 load_image (PopplerDocument *doc,
363 const gchar *filename,
364 @@ -597,7 +837,7 @@ load_image (PopplerDocument *doc,
365 gdouble page_width;
366 gdouble page_height;
367
368 - GdkPixbuf *buf;
369 + GdkPixbuf *pixbuf;
370 gint width;
371 gint height;
372
373 @@ -627,15 +867,13 @@ load_image (PopplerDocument *doc,
374 gimp_image_set_resolution (image_ID, resolution, resolution);
375 }
376
377 - buf = gdk_pixbuf_new (GDK_COLORSPACE_RGB, FALSE, 8, width, height);
378 -
379 - poppler_page_render_to_pixbuf (page, 0, 0, width, height, scale, 0, buf);
380 + pixbuf = render_page_to_pixbuf (page, width, height, scale);
381
382 - layer_from_pixbuf (image_ID, page_label, i, buf,
383 + layer_from_pixbuf (image_ID, page_label, i, pixbuf,
384 doc_progress, 1.0 / pages->n_pages);
385
386 g_free (page_label);
387 - g_object_unref (buf);
388 + g_object_unref(pixbuf);
389
390 doc_progress = (double) (i + 1) / pages->n_pages;
391 gimp_progress_update (doc_progress);
392 @@ -676,30 +914,22 @@ load_image (PopplerDocument *doc,
393 return image_ID;
394 }
395
396 -static GdkPixbuf *
397 -get_thumbnail (PopplerDocument *doc,
398 - gint page_num,
399 - gint preferred_size)
400 +static cairo_surface_t *
401 +get_thumb_surface (PopplerDocument *doc,
402 + gint page_num,
403 + gint preferred_size)
404 {
405 PopplerPage *page;
406 - GdkPixbuf *pixbuf;
407 + cairo_surface_t *surface;
408
409 page = poppler_document_get_page (doc, page_num);
410
411 if (! page)
412 return NULL;
413
414 - /* XXX: Remove conditional when we depend on poppler 0.8.0, but also
415 - * add configure check to make sure POPPLER_WITH_GDK is enabled!
416 - */
417 -#ifdef POPPLER_WITH_GDK
418 - pixbuf = poppler_page_get_thumbnail_pixbuf (page);
419 -#else
420 - pixbuf = poppler_page_get_thumbnail (page);
421 -#endif
422 -
423 + surface = poppler_page_get_thumbnail (page);
424
425 - if (! pixbuf)
426 + if (! surface)
427 {
428 gdouble width;
429 gdouble height;
430 @@ -712,15 +942,28 @@ get_thumbnail (PopplerDocument *doc,
431 width *= scale;
432 height *= scale;
433
434 - pixbuf = gdk_pixbuf_new (GDK_COLORSPACE_RGB, FALSE, 8,
435 - width, height);
436 -
437 - poppler_page_render_to_pixbuf (page,
438 - 0, 0, width, height, scale, 0, pixbuf);
439 + surface = render_page_to_surface (page, width, height, scale);
440 }
441
442 g_object_unref (page);
443
444 + return surface;
445 +}
446 +
447 +static GdkPixbuf *
448 +get_thumb_pixbuf (PopplerDocument *doc,
449 + gint page_num,
450 + gint preferred_size)
451 +{
452 + cairo_surface_t *surface;
453 + GdkPixbuf *pixbuf;
454 +
455 + surface = get_thumb_surface (doc, page_num, preferred_size);
456 + pixbuf = gdk_pixbuf_get_from_surface (surface, 0, 0,
457 + cairo_image_surface_get_width (surface),
458 + cairo_image_surface_get_height (surface));
459 + cairo_surface_destroy (surface);
460 +
461 return pixbuf;
462 }
463
464 @@ -769,8 +1012,8 @@ thumbnail_thread (gpointer data)
465 idle_data->page_no = i;
466
467 /* FIXME get preferred size from somewhere? */
468 - idle_data->pixbuf = get_thumbnail (thread_data->document, i,
469 - THUMBNAIL_SIZE);
470 + idle_data->pixbuf = get_thumb_pixbuf (thread_data->document, i,
471 + THUMBNAIL_SIZE);
472
473 g_idle_add (idle_set_thumbnail, idle_data);
474
475 --
476 1.7.5