Skip to content

Commit 6d2aebf

Browse files
authored
export iptc metadata tags (#18724)
* export iptc metadata tags
1 parent 39b5e36 commit 6d2aebf

File tree

1 file changed

+80
-41
lines changed

1 file changed

+80
-41
lines changed

src/common/exif.cc

Lines changed: 80 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -342,7 +342,7 @@ void dt_exif_set_exiv2_taglist()
342342
_get_xmp_tags("expressionmedia", &exiv2_taglist);
343343
_get_xmp_tags("MicrosoftPhoto", &exiv2_taglist);
344344
}
345-
catch (Exiv2::AnyError& e)
345+
catch(const Exiv2::AnyError& e)
346346
{
347347
const char *errstring = e.what();
348348
dt_print(DT_DEBUG_IMAGEIO, "[exiv2 taglist] %s", errstring);
@@ -486,7 +486,7 @@ static void _deleteXmpTag(Exiv2::XmpData &xmp, const char *tag)
486486
pos = xmp.erase(pos);
487487
}
488488
}
489-
catch(Exiv2::AnyError &e)
489+
catch(const Exiv2::AnyError &e)
490490
{
491491
// The only exception we may get is "invalid" tag, which is not
492492
// important enough to either stop the function, or even display
@@ -528,7 +528,7 @@ static void _remove_exif_keys(Exiv2::ExifData &exif,
528528
while((pos = exif.findKey(Exiv2::ExifKey(keys[i]))) != exif.end())
529529
exif.erase(pos);
530530
}
531-
catch(Exiv2::AnyError &e)
531+
catch(const Exiv2::AnyError &e)
532532
{
533533
// The only exception we may get is "invalid" tag, which is not
534534
// important enough to either stop the function, or even display
@@ -550,7 +550,7 @@ static void _remove_xmp_keys(Exiv2::XmpData &xmp,
550550
while((pos = xmp.findKey(Exiv2::XmpKey(keys[i]))) != xmp.end())
551551
xmp.erase(pos);
552552
}
553-
catch(Exiv2::AnyError &e)
553+
catch(const Exiv2::AnyError &e)
554554
{
555555
// The only exception we may get is "invalid" tag, which is not
556556
// important enough to either stop the function, or even display
@@ -569,7 +569,7 @@ static bool _exif_read_xmp_tag(Exiv2::XmpData &xmpData,
569569
return (*pos = xmpData.findKey(Exiv2::XmpKey(key))) != xmpData.end()
570570
&& (*pos)->size();
571571
}
572-
catch(Exiv2::AnyError &e)
572+
catch(const Exiv2::AnyError &e)
573573
{
574574
const char *errstring = e.what();
575575
dt_print(DT_DEBUG_IMAGEIO, "[exiv2 read_xmp_tag] %s", errstring);
@@ -734,7 +734,7 @@ static bool _exif_decode_xmp_data(dt_image_t *img,
734734
imgs = NULL;
735735
return true;
736736
}
737-
catch(Exiv2::AnyError &e)
737+
catch(const Exiv2::AnyError &e)
738738
{
739739
if(imgs) g_list_free(imgs);
740740
imgs = NULL;
@@ -756,7 +756,7 @@ static bool _exif_read_iptc_tag(Exiv2::IptcData &iptcData,
756756
return (*pos = iptcData.findKey(Exiv2::IptcKey(key)))
757757
!= iptcData.end() && (*pos)->size();
758758
}
759-
catch(Exiv2::AnyError &e)
759+
catch(const Exiv2::AnyError &e)
760760
{
761761
const char *errstring = e.what();
762762
dt_print(DT_DEBUG_IMAGEIO, "[exiv2 read_iptc_tag] %s", errstring);
@@ -840,7 +840,7 @@ static bool _exif_decode_iptc_data(dt_image_t *img,
840840

841841
return true;
842842
}
843-
catch(Exiv2::AnyError &e)
843+
catch(const Exiv2::AnyError &e)
844844
{
845845
const char *errstring = e.what();
846846
dt_print(DT_DEBUG_IMAGEIO,
@@ -860,7 +860,7 @@ static bool _exif_read_exif_tag(Exiv2::ExifData &exifData,
860860
return (*pos = exifData.findKey(Exiv2::ExifKey(key)))
861861
!= exifData.end() && (*pos)->size();
862862
}
863-
catch(Exiv2::AnyError &e)
863+
catch(const Exiv2::AnyError &e)
864864
{
865865
const char *errstring = e.what();
866866
dt_print(DT_DEBUG_IMAGEIO, "[exiv2 read_exif_tag] %s", errstring);
@@ -1147,7 +1147,7 @@ void dt_exif_img_check_additional_tags(dt_image_t *img,
11471147
}
11481148
return;
11491149
}
1150-
catch(Exiv2::AnyError &e)
1150+
catch(const Exiv2::AnyError &e)
11511151
{
11521152
const char *errstring = e.what();
11531153
dt_print(DT_DEBUG_IMAGEIO, "[exiv2 reading additional exif tags] %s: %s", filename, errstring);
@@ -2208,7 +2208,7 @@ static bool _exif_decode_exif_data(dt_image_t *img, Exiv2::ExifData &exifData)
22082208
img->exif_inited = TRUE;
22092209
return true;
22102210
}
2211-
catch(Exiv2::AnyError &e)
2211+
catch(const Exiv2::AnyError &e)
22122212
{
22132213
const char *errstring = e.what();
22142214
dt_print(DT_DEBUG_IMAGEIO, "[exiv2 _exif_decode_exif_data] %s: %s", img->filename, errstring);
@@ -2297,7 +2297,7 @@ gboolean dt_exif_read_from_blob(dt_image_t *img,
22972297
dt_exif_apply_default_metadata(img);
22982298
return res ? FALSE : TRUE;
22992299
}
2300-
catch(Exiv2::AnyError &e)
2300+
catch(const Exiv2::AnyError &e)
23012301
{
23022302
const char *errstring = e.what();
23032303
dt_print(DT_DEBUG_IMAGEIO, "[exiv2 dt_exif_read_from_blob] %s: %s", img->filename, errstring);
@@ -2354,7 +2354,7 @@ gboolean dt_exif_get_thumbnail(const char *path,
23542354

23552355
return FALSE;
23562356
}
2357-
catch(Exiv2::AnyError &e)
2357+
catch(const Exiv2::AnyError &e)
23582358
{
23592359
dt_print(DT_DEBUG_IMAGEIO,
23602360
"[exiv2 dt_exif_get_thumbnail] %s: %s",
@@ -2437,7 +2437,7 @@ gboolean dt_exif_read(dt_image_t *img,
24372437

24382438
return res ? FALSE : TRUE;
24392439
}
2440-
catch(Exiv2::AnyError &e)
2440+
catch(const Exiv2::AnyError &e)
24412441
{
24422442
dt_print(DT_DEBUG_IMAGEIO,
24432443
"[exiv2 dt_exif_read] %s: %s",
@@ -2499,7 +2499,7 @@ int dt_exif_write_blob(uint8_t *blob,
24992499
imgExifData.sortByTag();
25002500
image->writeMetadata();
25012501
}
2502-
catch(Exiv2::AnyError &e)
2502+
catch(const Exiv2::AnyError &e)
25032503
{
25042504
dt_print(DT_DEBUG_IMAGEIO,
25052505
"[exiv2 dt_exif_write_blob] %s: %s",
@@ -2893,7 +2893,7 @@ int dt_exif_read_blob(uint8_t **buf,
28932893
memcpy(*buf, &(blob[0]), length);
28942894
return length;
28952895
}
2896-
catch(Exiv2::AnyError &e)
2896+
catch(const Exiv2::AnyError &e)
28972897
{
28982898
// std::cerr.rdbuf(savecerr);
28992899
dt_print(DT_DEBUG_IMAGEIO,
@@ -4473,7 +4473,7 @@ gboolean dt_exif_xmp_read(dt_image_t *img,
44734473
}
44744474

44754475
}
4476-
catch(Exiv2::AnyError &e)
4476+
catch(const Exiv2::AnyError &e)
44774477
{
44784478
// Actually nobody's interested in that if the file doesn't exist:
44794479
// std::string s(e.what());
@@ -4859,21 +4859,28 @@ static void _set_xmp_dt_metadata(Exiv2::XmpData &xmpData,
48594859
{
48604860
int keyid = sqlite3_column_int(stmt, 0);
48614861
const dt_metadata_t *metadata = dt_metadata_get_metadata_by_keyid(keyid);
4862-
if(metadata)
4862+
if(metadata && g_str_has_prefix(metadata->tagname, "Xmp."))
48634863
{
4864-
if(export_flag
4865-
&& !metadata->internal)
4864+
try
48664865
{
4867-
if(metadata->visible && !metadata->priv)
4868-
xmpData[metadata->tagname] = sqlite3_column_text(stmt, 1);
4869-
else
4866+
if(export_flag
4867+
&& !metadata->internal)
48704868
{
4871-
Exiv2::XmpData::iterator pos = xmpData.findKey(Exiv2::XmpKey(metadata->tagname));
4872-
if(pos != xmpData.end()) xmpData.erase(pos);
4869+
if(metadata->visible && !metadata->priv)
4870+
xmpData[metadata->tagname] = sqlite3_column_text(stmt, 1);
4871+
else
4872+
{
4873+
Exiv2::XmpData::iterator pos = xmpData.findKey(Exiv2::XmpKey(metadata->tagname));
4874+
if(pos != xmpData.end()) xmpData.erase(pos);
4875+
}
48734876
}
4877+
else
4878+
xmpData[metadata->tagname] = sqlite3_column_text(stmt, 1);
4879+
}
4880+
catch(const Exiv2::AnyError &e)
4881+
{
4882+
// ignore invalid tags
48744883
}
4875-
else
4876-
xmpData[metadata->tagname] = sqlite3_column_text(stmt, 1);
48774884
}
48784885
}
48794886
dt_pthread_mutex_unlock(&darktable.metadata_threadsafe);
@@ -5243,7 +5250,7 @@ char *dt_exif_xmp_read_string(const dt_imgid_t imgid)
52435250
}
52445251
return g_strdup(xmpPacket.c_str());
52455252
}
5246-
catch(Exiv2::AnyError &e)
5253+
catch(const Exiv2::AnyError &e)
52475254
{
52485255
dt_print(DT_DEBUG_IMAGEIO,
52495256
"[xmp_read_blob] caught exiv2 exception '%s'",
@@ -5261,7 +5268,7 @@ static void _remove_xmp_key(Exiv2::XmpData &xmp,
52615268
if(pos != xmp.end())
52625269
xmp.erase(pos);
52635270
}
5264-
catch(Exiv2::AnyError &e)
5271+
catch(const Exiv2::AnyError &e)
52655272
{
52665273
}
52675274
}
@@ -5280,7 +5287,7 @@ static void _remove_xmp_keys(Exiv2::XmpData &xmpData,
52805287
++i;
52815288
}
52825289
}
5283-
catch(Exiv2::AnyError &e)
5290+
catch(const Exiv2::AnyError &e)
52845291
{
52855292
}
52865293
}
@@ -5294,7 +5301,7 @@ static void _remove_exif_key(Exiv2::ExifData &exif,
52945301
if(pos != exif.end())
52955302
exif.erase(pos);
52965303
}
5297-
catch(Exiv2::AnyError &e)
5304+
catch(const Exiv2::AnyError &e)
52985305
{
52995306
}
53005307
}
@@ -5308,7 +5315,7 @@ static void _remove_iptc_key(Exiv2::IptcData &iptc,
53085315
while((pos = iptc.findKey(Exiv2::IptcKey(key))) != iptc.end())
53095316
iptc.erase(pos);
53105317
}
5311-
catch(Exiv2::AnyError &e)
5318+
catch(const Exiv2::AnyError &e)
53125319
{
53135320
}
53145321
}
@@ -5561,7 +5568,7 @@ gboolean dt_exif_xmp_attach_export(const dt_imgid_t imgid,
55615568
img->setXmpData(input_image->xmpData());
55625569
}
55635570
}
5564-
catch(Exiv2::AnyError &e)
5571+
catch(const Exiv2::AnyError &e)
55655572
{
55665573
dt_print(DT_DEBUG_IMAGEIO,
55675574
"[xmp_attach] %s: caught exiv2 exception '%s'",
@@ -5628,6 +5635,38 @@ gboolean dt_exif_xmp_attach_export(const dt_imgid_t imgid,
56285635

56295636
Exiv2::IptcData &iptcData = img->iptcData();
56305637

5638+
// now add all exif and iptc metadata from the metadata editor.
5639+
// xmp metadata is already processed.
5640+
sqlite3_stmt *stmt;
5641+
DT_DEBUG_SQLITE3_PREPARE_V2(dt_database_get(darktable.db),
5642+
"SELECT key, value FROM main.meta_data WHERE id = ?1",
5643+
-1, &stmt, NULL);
5644+
DT_DEBUG_SQLITE3_BIND_INT(stmt, 1, imgid);
5645+
5646+
dt_pthread_mutex_lock(&darktable.metadata_threadsafe);
5647+
while(sqlite3_step(stmt) == SQLITE_ROW)
5648+
{
5649+
int keyid = sqlite3_column_int(stmt, 0);
5650+
const dt_metadata_t *md = dt_metadata_get_metadata_by_keyid(keyid);
5651+
if(md && md->visible && !md->priv && !md->internal)
5652+
{
5653+
const char *value = (char *)sqlite3_column_text(stmt, 1);
5654+
try
5655+
{
5656+
if(g_str_has_prefix(md->tagname, "Iptc."))
5657+
iptcData[md->tagname] = value;
5658+
else if(g_str_has_prefix(md->tagname, "Exif."))
5659+
exifData[md->tagname] = value;
5660+
}
5661+
catch(const Exiv2::AnyError &e)
5662+
{
5663+
// ignore invalid tags
5664+
}
5665+
}
5666+
}
5667+
dt_pthread_mutex_unlock(&darktable.metadata_threadsafe);
5668+
sqlite3_finalize(stmt);
5669+
56315670
if(!(m->flags & DT_META_GEOTAG))
56325671
_remove_exif_geotag(exifData);
56335672

@@ -5763,7 +5802,7 @@ gboolean dt_exif_xmp_attach_export(const dt_imgid_t imgid,
57635802
{
57645803
img->writeMetadata();
57655804
}
5766-
catch(Exiv2::AnyError &e)
5805+
catch(const Exiv2::AnyError &e)
57675806
{
57685807
if(e.code() == Exiv2::ErrorCode::kerTooLargeJpegSegment)
57695808
{
@@ -5775,7 +5814,7 @@ gboolean dt_exif_xmp_attach_export(const dt_imgid_t imgid,
57755814
{
57765815
img->writeMetadata();
57775816
}
5778-
catch(Exiv2::AnyError &e2)
5817+
catch(const Exiv2::AnyError &e2)
57795818
{
57805819
dt_print(DT_DEBUG_IMAGEIO,
57815820
"[dt_exif_xmp_attach_export] without history %s: caught exiv2 exception '%s'",
@@ -5789,7 +5828,7 @@ gboolean dt_exif_xmp_attach_export(const dt_imgid_t imgid,
57895828
}
57905829
return FALSE;
57915830
}
5792-
catch(Exiv2::AnyError &e)
5831+
catch(const Exiv2::AnyError &e)
57935832
{
57945833
dt_print(DT_DEBUG_IMAGEIO,
57955834
"[dt_exif_xmp_attach_export] %s: caught exiv2 exception '%s'",
@@ -5901,7 +5940,7 @@ gboolean dt_exif_xmp_write(const dt_imgid_t imgid,
59015940

59025941
return FALSE;
59035942
}
5904-
catch(Exiv2::AnyError &e)
5943+
catch(const Exiv2::AnyError &e)
59055944
{
59065945
dt_print(DT_DEBUG_IMAGEIO,
59075946
"[dt_exif_xmp_write] %s: caught exiv2 exception '%s'",
@@ -5951,7 +5990,7 @@ dt_colorspaces_color_profile_type_t dt_exif_get_color_space(const uint8_t *data,
59515990

59525991
return DT_COLORSPACE_DISPLAY; // nothing embedded
59535992
}
5954-
catch(Exiv2::AnyError &e)
5993+
catch(const Exiv2::AnyError &e)
59555994
{
59565995
dt_print(DT_DEBUG_IMAGEIO,
59575996
"[exiv2 dt_exif_get_color_space] %s",
@@ -5974,7 +6013,7 @@ void dt_exif_get_basic_data(const uint8_t *data,
59746013
_find_datetime_taken(exifData, pos, basic_exif->datetime);
59756014
_find_exif_makermodel(exifData, pos, basic_exif);
59766015
}
5977-
catch(Exiv2::AnyError &e)
6016+
catch(const Exiv2::AnyError &e)
59786017
{
59796018
dt_print(DT_DEBUG_IMAGEIO,
59806019
"[exiv2 dt_exif_get_basic_data] %s",
@@ -6012,7 +6051,7 @@ void dt_exif_init()
60126051
{
60136052
Exiv2::XmpProperties::propertyList("lr");
60146053
}
6015-
catch(Exiv2::AnyError &e)
6054+
catch(const Exiv2::AnyError &e)
60166055
{
60176056
// If Lightroom is not known register it.
60186057
Exiv2::XmpProperties::registerNs("http://ns.adobe.com/lightroom/1.0/", "lr");
@@ -6021,7 +6060,7 @@ void dt_exif_init()
60216060
{
60226061
Exiv2::XmpProperties::propertyList("exifEX");
60236062
}
6024-
catch(Exiv2::AnyError &e)
6063+
catch(const Exiv2::AnyError &e)
60256064
{
60266065
// If exifEX is not known register it.
60276066
Exiv2::XmpProperties::registerNs("http://cipa.jp/exif/1.0/", "exifEX");

0 commit comments

Comments
 (0)