exiv2 icon indicating copy to clipboard operation
exiv2 copied to clipboard

LangAlt value sorting

Open jim-easterbrook opened this issue 3 years ago • 2 comments

Describe the bug

According to https://developer.adobe.com/xmp/docs/XMPNamespaces/XMPDataTypes/#language-alternative the first item in a LangAlt array is the default language. Also it is legitimate for there not to be an "x-default" item. Exiv2 stores LangAlt data in a std::map, which gets sorted by key so the user no longer knows which was the first item in the file.

The LangAltValueComparator currently compares length before doing a character by character comparison, so "x-default" is only being stored first because it's longer than any legitimate RFC3066 language tag. Setting a nonsense tag (e.g. fr-FranceAndCanada) moves "x-default" to second place in the XMP file.

To Reproduce

Read an XMP LangAlt value that doesn't have an "x-default" item. Attempt to find the first item.

Expected behavior

I'd like to have the LangAlt items in the same order as in the XMP file. I realise this may not be possible without substantial changes to Exiv2.

Additional context

Consider this more as a discussion point than a bug report.

jim-easterbrook avatar Apr 23 '22 10:04 jim-easterbrook

I don't know much C++ but would using std::unordered_map help? This should allow the user to iterate over the (lang, text) pairs in the order they were read from the file.

jim-easterbrook avatar Apr 25 '22 10:04 jim-easterbrook

Answer: no it wouldn't. std::unordered_map has undefined/random element order.

As far as I can tell, the only solution is to change the container to a vector of key:value pairs, or to add a separate list of keys to preserve the item order.

jim-easterbrook avatar May 03 '22 08:05 jim-easterbrook