diff options
author | Adrian Johnson <ajohnson@redneon.com> | 2010-11-02 22:39:57 +1030 |
---|---|---|
committer | Adrian Johnson <ajohnson@redneon.com> | 2010-11-23 00:13:02 +1030 |
commit | 9862c38fc71c6dcd444da3b079e5404cd14594c3 (patch) | |
tree | 33f6ec24b8c2dacb26500a122083b96953601258 | |
parent | 3445401ae6bc8687fc76f690016cc281c388005d (diff) |
Add unique_id mime type
to ensure surfaces with the same unique_id mime type are not embedded
more than once in PDF files.
-rw-r--r-- | src/cairo-pdf-surface-private.h | 2 | ||||
-rw-r--r-- | src/cairo-pdf-surface.c | 38 | ||||
-rw-r--r-- | src/cairo-surface.c | 8 | ||||
-rw-r--r-- | src/cairo.h | 1 |
4 files changed, 47 insertions, 2 deletions
diff --git a/src/cairo-pdf-surface-private.h b/src/cairo-pdf-surface-private.h index 221418ec9..5c70ef973 100644 --- a/src/cairo-pdf-surface-private.h +++ b/src/cairo-pdf-surface-private.h @@ -67,6 +67,8 @@ typedef struct _cairo_pdf_group_resources { typedef struct _cairo_pdf_source_surface_entry { cairo_hash_entry_t base; unsigned int id; + const unsigned char *unique_id; + unsigned long unique_id_length; cairo_bool_t interpolate; cairo_pdf_resource_t surface_res; int width; diff --git a/src/cairo-pdf-surface.c b/src/cairo-pdf-surface.c index ae70a47b4..f048dc885 100644 --- a/src/cairo-pdf-surface.c +++ b/src/cairo-pdf-surface.c @@ -1039,13 +1039,24 @@ _cairo_pdf_source_surface_equal (const void *key_a, const void *key_b) const cairo_pdf_source_surface_entry_t *a = key_a; const cairo_pdf_source_surface_entry_t *b = key_b; - return (a->id == b->id) && (a->interpolate == b->interpolate); + if (a->interpolate != b->interpolate) + return FALSE; + + if (a->unique_id && b->unique_id && a->unique_id_length == b->unique_id_length) + return (memcmp (a->unique_id, b->unique_id, a->unique_id_length) == 0); + + return (a->id == b->id); } static void _cairo_pdf_source_surface_init_key (cairo_pdf_source_surface_entry_t *key) { - key->base.hash = key->id; + if (key->unique_id && key->unique_id_length > 0) { + key->base.hash = _cairo_hash_bytes (_CAIRO_HASH_INIT_VALUE, + key->unique_id, key->unique_id_length); + } else { + key->base.hash = key->id; + } } static cairo_int_status_t @@ -1146,6 +1157,8 @@ _cairo_pdf_surface_add_source_surface (cairo_pdf_surface_t *surface, cairo_pdf_source_surface_entry_t *surface_entry; cairo_status_t status; cairo_bool_t interpolate; + const unsigned char *unique_id; + unsigned long unique_id_length; switch (filter) { default: @@ -1163,6 +1176,8 @@ _cairo_pdf_surface_add_source_surface (cairo_pdf_surface_t *surface, surface_key.id = source->unique_id; surface_key.interpolate = interpolate; + cairo_surface_get_mime_data (source, CAIRO_MIME_TYPE_UNIQUE_ID, + &surface_key.unique_id, &surface_key.unique_id_length); _cairo_pdf_source_surface_init_key (&surface_key); surface_entry = _cairo_hash_table_lookup (surface->all_surfaces, &surface_key.base); if (surface_entry) { @@ -1179,6 +1194,22 @@ _cairo_pdf_surface_add_source_surface (cairo_pdf_surface_t *surface, surface_entry->id = surface_key.id; surface_entry->interpolate = interpolate; + cairo_surface_get_mime_data (source, CAIRO_MIME_TYPE_UNIQUE_ID, + &unique_id, &unique_id_length); + if (unique_id && unique_id_length > 0) { + surface_entry->unique_id = malloc (unique_id_length); + if (surface_entry->unique_id == NULL) { + cairo_surface_destroy (source); + free (surface_entry); + return _cairo_error (CAIRO_STATUS_NO_MEMORY); + } + + surface_entry->unique_id_length = unique_id_length; + memcpy (surface_entry->unique_id, unique_id, unique_id_length); + } else { + surface_entry->unique_id = NULL; + surface_entry->unique_id_length = 0; + } _cairo_pdf_source_surface_init_key (surface_entry); src_surface.hash_entry = surface_entry; @@ -1631,6 +1662,9 @@ _cairo_pdf_source_surface_entry_pluck (void *entry, void *closure) cairo_hash_table_t *patterns = closure; _cairo_hash_table_remove (patterns, &surface_entry->base); + if (surface_entry->unique_id) + free (surface_entry->unique_id); + free (surface_entry); } diff --git a/src/cairo-surface.c b/src/cairo-surface.c index 2293991f8..76f644716 100644 --- a/src/cairo-surface.c +++ b/src/cairo-surface.c @@ -892,6 +892,14 @@ _cairo_mime_data_destroy (void *ptr) */ /** + * CAIRO_MIME_TYPE_UNIQUE_ID: + * + * Unique identifier for a surface (cairo specific MIME type). + * + * @Since: 1.12 + */ + +/** * cairo_surface_set_mime_data: * @surface: a #cairo_surface_t * @mime_type: the MIME type of the image data diff --git a/src/cairo.h b/src/cairo.h index 136c5dbf2..a45bf1489 100644 --- a/src/cairo.h +++ b/src/cairo.h @@ -2155,6 +2155,7 @@ cairo_surface_set_user_data (cairo_surface_t *surface, #define CAIRO_MIME_TYPE_PNG "image/png" #define CAIRO_MIME_TYPE_JP2 "image/jp2" #define CAIRO_MIME_TYPE_URI "text/x-uri" +#define CAIRO_MIME_TYPE_UNIQUE_ID "application/x-cairo.uuid" cairo_public void cairo_surface_get_mime_data (cairo_surface_t *surface, |