# HG changeset patch # User Sebastien Jodogne # Date 1773995298 -3600 # Node ID dfa66ab964c9fe6aad44d6f6cbba61382c63c5a9 # Parent 71400f1c614328f37371a3d3cf31fcc4dd597bab improved support for OL value representation diff -r 71400f1c6143 -r dfa66ab964c9 NEWS --- a/NEWS Wed Mar 18 12:13:09 2026 +0100 +++ b/NEWS Fri Mar 20 09:28:18 2026 +0100 @@ -22,7 +22,7 @@ * New option "Utf8" available in the "{...}/archive" and "/tools/create-archive" routes to use UTF-8 filenames in the generated ZIP archives. It defaults to the value of the new configuration option "ZipUseUtf8". -* Support for OF and OD value representations in "/instances/{...}/file" with content type +* Support for OD, OF, and OL value representations in "/instances/{...}/file" with content type "application/dicom+json" (i.e. DICOMweb) and in "/instances/{...}/tags" (contribution by Yusuf Sayıta, Philips). * New "Content.Resources" field in "DicomModalityStore", "OrthancPeerStore" and "ResourceModification" diff -r 71400f1c6143 -r dfa66ab964c9 OrthancFramework/Sources/DicomParsing/FromDcmtkBridge.cpp --- a/OrthancFramework/Sources/DicomParsing/FromDcmtkBridge.cpp Wed Mar 18 12:13:09 2026 +0100 +++ b/OrthancFramework/Sources/DicomParsing/FromDcmtkBridge.cpp Fri Mar 20 09:28:18 2026 +0100 @@ -932,6 +932,35 @@ } #endif +#if DCMTK_VERSION_NUMBER >= 362 + case EVR_OL: // other long - binary array of 32-bit unsigned integers (new in Orthanc 1.12.11) + { + /** + * OL stores a binary array of 32-bit unsigned integers. Like OF/OD, + * getVM() returns 1 for OL (the entire binary blob is one "value"). + * We must use getUint32Array() to access the raw buffer. + * The resulting string is formatted as in ApplyDcmtkToCTypeConverter(). + **/ + DcmUnsignedLong& content = dynamic_cast(element); + Uint32* uint32Array = NULL; + if (content.getUint32Array(uint32Array).good() && uint32Array != NULL) + { + const unsigned long numValues = element.getLength() / sizeof(Uint32); + std::string result; + for (unsigned long i = 0; i < numValues; i++) + { + if (i > 0) + { + result += "\\"; + } + result += boost::lexical_cast(uint32Array[i]); + } + return new DicomValue(result, false); + } + return new DicomValue; + } +#endif + /** * Attribute tag. @@ -3052,9 +3081,6 @@ } case EVR_UL: // unsigned long -#if DCMTK_VERSION_NUMBER >= 362 - case EVR_OL: -#endif { DcmUnsignedLong& content = dynamic_cast(element); @@ -3192,6 +3218,36 @@ } #endif +#if DCMTK_VERSION_NUMBER >= 362 + case EVR_OL: // other long - binary array of 32-bit unsigned integers (new in Orthanc 1.12.11) + { + /** + * OL stores a binary array of 32-bit unsigned integers. Like OF/OD, + * getVM() returns 1 for OL (the entire binary blob is one "value"). + * We must use getUint32Array() to access the raw buffer, then iterate + * over all values based on element length. + **/ + DcmUnsignedLong& content = dynamic_cast(element); + + std::vector values; + + Uint32* uint32Array = NULL; + if (content.getUint32Array(uint32Array).good() && uint32Array != NULL) + { + const unsigned long numValues = static_cast(element.getLength() / sizeof(Uint32)); + values.reserve(numValues); + + for (unsigned long i = 0; i < numValues; i++) + { + values.push_back(static_cast(uint32Array[i])); + } + } + + action = visitor.VisitIntegers(parentTags, parentIndexes, tag, vr, values); + break; + } +#endif + /** * Attribute tag.