From e415aeeb4f0e0bf7a622328ee9a2b36804c50d29 Mon Sep 17 00:00:00 2001 From: Edgard Lima Date: Mon, 3 Dec 2007 16:14:01 +0000 Subject: Muxer writes (in jpeg only) whole IPTC chunk sent as tag. Muxer implemets GstTagSetter interface. Original commit message from CVS: Muxer writes (in jpeg only) whole IPTC chunk sent as tag. Muxer implemets GstTagSetter interface. --- ext/metadata/gstmetadatamux.c | 60 +++++++++++++++++++++++++----------------- ext/metadata/gstmetadatamux.h | 1 - ext/metadata/metadataexif.c | 4 +-- ext/metadata/metadataexif.h | 2 +- ext/metadata/metadataiptc.c | 17 ++++++++++-- ext/metadata/metadataiptc.h | 2 +- ext/metadata/metadatamuxjpeg.c | 25 +++++++++++++++++- ext/metadata/metadataxmp.c | 4 +-- ext/metadata/metadataxmp.h | 2 +- 9 files changed, 82 insertions(+), 35 deletions(-) (limited to 'ext') diff --git a/ext/metadata/gstmetadatamux.c b/ext/metadata/gstmetadatamux.c index a31d072f..ce2b2ac4 100644 --- a/ext/metadata/gstmetadatamux.c +++ b/ext/metadata/gstmetadatamux.c @@ -104,8 +104,17 @@ static GstStaticPadTemplate src_factory = GST_STATIC_PAD_TEMPLATE ("src", GST_STATIC_CAPS ("image/jpeg; " "image/png") ); -GST_BOILERPLATE (GstMetadataMux, gst_metadata_mux, GstElement, - GST_TYPE_ELEMENT); +static void +gst_metadata_mux_add_interfaces (GType type) +{ + static const GInterfaceInfo tag_setter_info = { NULL, NULL, NULL }; + + g_type_add_interface_static (type, GST_TYPE_TAG_SETTER, &tag_setter_info); +} + + +GST_BOILERPLATE_FULL (GstMetadataMux, gst_metadata_mux, GstElement, + GST_TYPE_ELEMENT, gst_metadata_mux_add_interfaces); static GstMetadataMuxClass *metadata_parent_class = NULL; @@ -526,9 +535,11 @@ gst_metadata_mux_sink_event (GstPad * pad, GstEvent * event) case GST_EVENT_TAG: { GstTagList *taglist = NULL; + GstTagSetter *setter = GST_TAG_SETTER (filter); gst_event_parse_tag (event, &taglist); - gst_tag_list_insert (filter->taglist, taglist, GST_TAG_MERGE_REPLACE); + gst_tag_setter_merge_tags (setter, taglist, GST_TAG_MERGE_REPLACE); + } break; default: @@ -578,11 +589,6 @@ gst_metadata_mux_dispose_members (GstMetadataMux * filter) filter->adapter_holding = NULL; } - if (filter->taglist) { - gst_tag_list_free (filter->taglist); - filter->taglist = NULL; - } - if (filter->append_buffer) { gst_buffer_unref (filter->append_buffer); filter->append_buffer = NULL; @@ -602,7 +608,6 @@ gst_metadata_mux_init_members (GstMetadataMux * filter) filter->iptc = FALSE; filter->xmp = FALSE; - filter->taglist = NULL; filter->adapter_parsing = NULL; filter->adapter_holding = NULL; filter->next_offset = 0; @@ -801,24 +806,29 @@ gst_metadata_create_chunks_from_tags (GstMetadataMux * filter) { GstMessage *msg; - GstTagList *taglist; + GstTagSetter *setter = GST_TAG_SETTER (filter); + const GstTagList *taglist = gst_tag_setter_get_tag_list (setter); GstEvent *event; guint8 *buf = NULL; guint32 size = 0; - if (META_DATA_OPTION (filter->mux_data) & META_OPT_EXIF) { - metadatamux_exif_create_chunk_from_tag_list (&buf, &size, filter->taglist); - gst_metadata_update_segment (filter, &buf, &size, MD_CHUNK_EXIF); - } + if (taglist) { - if (META_DATA_OPTION (filter->mux_data) & META_OPT_IPTC) { - metadatamux_iptc_create_chunk_from_tag_list (&buf, &size, filter->taglist); - gst_metadata_update_segment (filter, &buf, &size, MD_CHUNK_IPTC); - } + if (META_DATA_OPTION (filter->mux_data) & META_OPT_EXIF) { + metadatamux_exif_create_chunk_from_tag_list (&buf, &size, taglist); + gst_metadata_update_segment (filter, &buf, &size, MD_CHUNK_EXIF); + } + + if (META_DATA_OPTION (filter->mux_data) & META_OPT_IPTC) { + metadatamux_iptc_create_chunk_from_tag_list (&buf, &size, taglist); + gst_metadata_update_segment (filter, &buf, &size, MD_CHUNK_IPTC); + } + + if (META_DATA_OPTION (filter->mux_data) & META_OPT_XMP) { + metadatamux_xmp_create_chunk_from_tag_list (&buf, &size, taglist); + gst_metadata_update_segment (filter, &buf, &size, MD_CHUNK_XMP); + } - if (META_DATA_OPTION (filter->mux_data) & META_OPT_XMP) { - metadatamux_xmp_create_chunk_from_tag_list (&buf, &size, filter->taglist); - gst_metadata_update_segment (filter, &buf, &size, MD_CHUNK_XMP); } metadata_chunk_array_remove_zero_size (&filter->mux_data.inject_chunks); @@ -900,8 +910,8 @@ gst_metadata_mux_calculate_offsets (GstMetadataMux * filter) guint32 bytes_striped, bytes_inject; MetadataChunk *strip = filter->mux_data.strip_chunks.chunk; MetadataChunk *inject = filter->mux_data.inject_chunks.chunk; - const gsize strip_len = filter->mux_data.strip_chunks.len; - const gsize inject_len = filter->mux_data.inject_chunks.len; + gsize strip_len; + gsize inject_len; if (filter->state != MT_STATE_MUXED) return FALSE; @@ -910,6 +920,9 @@ gst_metadata_mux_calculate_offsets (GstMetadataMux * filter) metadata_lazy_update (&filter->mux_data); + strip_len = filter->mux_data.strip_chunks.len; + inject_len = filter->mux_data.inject_chunks.len; + bytes_striped = 0; bytes_inject = 0; @@ -1755,7 +1768,6 @@ gst_metadata_mux_change_state (GstElement * element, GstStateChange transition) case GST_STATE_CHANGE_NULL_TO_READY: gst_metadata_mux_init_members (filter); filter->adapter_parsing = gst_adapter_new (); - filter->taglist = gst_tag_list_new (); metadata_init (&filter->mux_data, FALSE); break; default: diff --git a/ext/metadata/gstmetadatamux.h b/ext/metadata/gstmetadatamux.h index a044ba41..adfe65ee 100644 --- a/ext/metadata/gstmetadatamux.h +++ b/ext/metadata/gstmetadatamux.h @@ -98,7 +98,6 @@ struct _GstMetadataMux gboolean need_more_data; - GstTagList *taglist; gboolean need_calculate_offset; /* mux need to calculate offsets of insert chunks */ }; diff --git a/ext/metadata/metadataexif.c b/ext/metadata/metadataexif.c index 135bedd2..4bc8d4bf 100644 --- a/ext/metadata/metadataexif.c +++ b/ext/metadata/metadataexif.c @@ -65,7 +65,7 @@ metadataparse_exif_tag_list_add (GstTagList * taglist, GstTagMergeMode mode, void metadatamux_exif_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, - GstTagList * taglist) + const GstTagList * taglist) { /* do nothing */ } @@ -203,7 +203,7 @@ exif_content_foreach_entry_func (ExifEntry * entry, void *user_data) void metadatamux_exif_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, - GstTagList * taglist) + const GstTagList * taglist) { ExifData *ed = NULL; GstBuffer *exif_chunk = NULL; diff --git a/ext/metadata/metadataexif.h b/ext/metadata/metadataexif.h index cc53c87a..71cd6511 100644 --- a/ext/metadata/metadataexif.h +++ b/ext/metadata/metadataexif.h @@ -56,7 +56,7 @@ metadataparse_exif_tag_list_add (GstTagList * taglist, GstTagMergeMode mode, extern void metadatamux_exif_create_chunk_from_tag_list (guint8 ** buf, guint32 *size, - GstTagList * taglist); + const GstTagList * taglist); G_END_DECLS #endif /* __GST_METADATAPARSE_EXIF_H__ */ diff --git a/ext/metadata/metadataiptc.c b/ext/metadata/metadataiptc.c index 7af879ef..7009cc04 100644 --- a/ext/metadata/metadataiptc.c +++ b/ext/metadata/metadataiptc.c @@ -66,7 +66,7 @@ metadataparse_iptc_tag_list_add (GstTagList * taglist, GstTagMergeMode mode, void metadatamux_iptc_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, - GstTagList * taglist) + const GstTagList * taglist) { /* do nothing */ } @@ -133,8 +133,11 @@ iptc_data_foreach_dataset_func (IptcDataSet * dataset, void *user_data) void metadatamux_iptc_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, - GstTagList * taglist) + const GstTagList * taglist) { + GstBuffer *iptc_chunk = NULL; + const GValue *val = NULL; + if (!(buf && size)) goto done; if (*buf) { @@ -143,6 +146,16 @@ metadatamux_iptc_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, } *size = 0; + val = gst_tag_list_get_value_index (taglist, GST_TAG_IPTC, 0); + if (val) { + iptc_chunk = gst_value_get_buffer (val); + if (iptc_chunk) { + *size = GST_BUFFER_SIZE (iptc_chunk); + *buf = g_new (guint8, *size); + memcpy (*buf, GST_BUFFER_DATA (iptc_chunk), *size); + } + } + done: return; diff --git a/ext/metadata/metadataiptc.h b/ext/metadata/metadataiptc.h index a8fa6de8..0fa0a4d7 100644 --- a/ext/metadata/metadataiptc.h +++ b/ext/metadata/metadataiptc.h @@ -56,7 +56,7 @@ metadataparse_iptc_tag_list_add (GstTagList * taglist, GstTagMergeMode mode, extern void metadatamux_iptc_create_chunk_from_tag_list (guint8 ** buf, guint32 *size, - GstTagList * taglist); + const GstTagList * taglist); G_END_DECLS #endif /* __GST_METADATAPARSE_IPTC_H__ */ diff --git a/ext/metadata/metadatamuxjpeg.c b/ext/metadata/metadatamuxjpeg.c index 50844a48..25a9f6b6 100644 --- a/ext/metadata/metadatamuxjpeg.c +++ b/ext/metadata/metadatamuxjpeg.c @@ -77,6 +77,7 @@ void metadatamux_jpeg_lazy_update (JpegMuxData * jpeg_data) { gsize i; + gboolean has_exif = FALSE; for (i = 0; i < jpeg_data->inject_chunks->len; ++i) { if (jpeg_data->inject_chunks->chunk[i].size > 0 && @@ -85,6 +86,28 @@ metadatamux_jpeg_lazy_update (JpegMuxData * jpeg_data) case MD_CHUNK_EXIF: metadatamux_wrap_chunk (&jpeg_data->inject_chunks->chunk[i], NULL, 0, 0xFF, 0xE1); + has_exif = TRUE; + break; + case MD_CHUNK_IPTC: + { + unsigned int size = jpeg_data->inject_chunks->chunk[i].size + 256; + unsigned char *buf = g_new (guint8, size); + + size = iptc_jpeg_ps3_save_iptc (NULL, 0, + jpeg_data->inject_chunks->chunk[i].data, + jpeg_data->inject_chunks->chunk[i].size, buf, size); + if (size > 0) { + g_free (jpeg_data->inject_chunks->chunk[i].data); + jpeg_data->inject_chunks->chunk[i].data = buf; + jpeg_data->inject_chunks->chunk[i].size = size; + metadatamux_wrap_chunk (&jpeg_data->inject_chunks->chunk[i], NULL, + 0, 0xFF, 0xED); + } else { + GST_ERROR ("Invalid IPTC chunk\n"); + g_free (buf); + /* FIXME: remove entry from list */ + } + } break; case MD_CHUNK_XMP: { @@ -99,7 +122,7 @@ metadatamux_jpeg_lazy_update (JpegMuxData * jpeg_data) } } } - if (i == jpeg_data->inject_chunks->len) { + if (!has_exif) { /* EXIF not injected so not strip JFIF anymore */ metadata_chunk_array_clear (jpeg_data->strip_chunks); } diff --git a/ext/metadata/metadataxmp.c b/ext/metadata/metadataxmp.c index f153ed25..ba24d4a7 100644 --- a/ext/metadata/metadataxmp.c +++ b/ext/metadata/metadataxmp.c @@ -76,7 +76,7 @@ metadataparse_xmp_dispose (void) void metadatamux_xmp_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, - GstTagList * taglist) + const GstTagList * taglist) { /* do nothing */ } @@ -248,7 +248,7 @@ metadataparse_xmp_iter (XmpPtr xmp, XmpIteratorPtr iter) void metadatamux_xmp_create_chunk_from_tag_list (guint8 ** buf, guint32 * size, - GstTagList * taglist) + const GstTagList * taglist) { GstBuffer *xmp_chunk = NULL; const GValue *val = NULL; diff --git a/ext/metadata/metadataxmp.h b/ext/metadata/metadataxmp.h index 6cb635d3..73a53241 100644 --- a/ext/metadata/metadataxmp.h +++ b/ext/metadata/metadataxmp.h @@ -60,7 +60,7 @@ extern void metadataparse_xmp_dispose (void); extern void metadatamux_xmp_create_chunk_from_tag_list (guint8 ** buf, guint32 *size, - GstTagList * taglist); + const GstTagList * taglist); G_END_DECLS #endif /* __GST_METADATAPARSE_XMP_H__ */ -- cgit v1.2.1