Mercurial > hg > orthanc
comparison UnitTestsSources/FromDcmtkTests.cpp @ 3893:7a5fa8f307e9 transcoding
reorganization
author | Sebastien Jodogne <s.jodogne@gmail.com> |
---|---|
date | Wed, 06 May 2020 12:48:28 +0200 |
parents | 56ce23ba93b7 |
children | 8f7ad4989fec |
comparison
equal
deleted
inserted
replaced
3891:5571082a9df6 | 3893:7a5fa8f307e9 |
---|---|
1923 | 1923 |
1924 | 1924 |
1925 #if ORTHANC_ENABLE_DCMTK_TRANSCODING == 1 | 1925 #if ORTHANC_ENABLE_DCMTK_TRANSCODING == 1 |
1926 | 1926 |
1927 #include "../Core/DicomNetworking/DicomStoreUserConnection.h" | 1927 #include "../Core/DicomNetworking/DicomStoreUserConnection.h" |
1928 | 1928 #include "../Core/DicomParsing/DcmtkTranscoder.h" |
1929 #include <dcmtk/dcmjpeg/djrploss.h> // for DJ_RPLossy | |
1930 #include <dcmtk/dcmjpeg/djrplol.h> // for DJ_RPLossless | |
1931 #include <dcmtk/dcmjpls/djrparam.h> // for DJLSRepresentationParameter | |
1932 | |
1933 | |
1934 #if !defined(ORTHANC_ENABLE_DCMTK_JPEG) | |
1935 # error Macro ORTHANC_ENABLE_DCMTK_JPEG must be defined | |
1936 #endif | |
1937 | |
1938 #if !defined(ORTHANC_ENABLE_DCMTK_JPEG_LOSSLESS) | |
1939 # error Macro ORTHANC_ENABLE_DCMTK_JPEG_LOSSLESS must be defined | |
1940 #endif | |
1941 | |
1942 | |
1943 | |
1944 namespace Orthanc | |
1945 { | |
1946 /** | |
1947 * WARNING: This class might be called from several threads at | |
1948 * once. Make sure to implement proper locking. | |
1949 **/ | |
1950 | |
1951 class IDicomTranscoder : public boost::noncopyable | |
1952 { | |
1953 public: | |
1954 virtual ~IDicomTranscoder() | |
1955 { | |
1956 } | |
1957 | |
1958 virtual bool TranscodeToBuffer(std::string& target, | |
1959 const void* buffer, | |
1960 size_t size, | |
1961 const std::set<DicomTransferSyntax>& allowedSyntaxes, | |
1962 bool allowNewSopInstanceUid) = 0; | |
1963 | |
1964 /** | |
1965 * Transcoding flavor that creates a new parsed DICOM file. A | |
1966 * "std::set<>" is used to give the possible plugin the | |
1967 * possibility to do a single parsing for all the possible | |
1968 * transfer syntaxes. | |
1969 **/ | |
1970 virtual DcmFileFormat* TranscodeToParsed(const void* buffer, | |
1971 size_t size, | |
1972 const std::set<DicomTransferSyntax>& allowedSyntaxes, | |
1973 bool allowNewSopInstanceUid) = 0; | |
1974 | |
1975 virtual bool HasInplaceTranscode() const = 0; | |
1976 | |
1977 /** | |
1978 * In-place transcoding. This method is preferred for C-STORE. | |
1979 **/ | |
1980 virtual bool InplaceTranscode(DcmFileFormat& dicom, | |
1981 const std::set<DicomTransferSyntax>& allowedSyntaxes, | |
1982 bool allowNewSopInstanceUid) = 0; | |
1983 | |
1984 /** | |
1985 * Important: Transcoding over the DICOM protocol is only | |
1986 * implemented towards uncompressed transfer syntaxes. | |
1987 **/ | |
1988 static void Store(std::string& sopClassUid /* out */, | |
1989 std::string& sopInstanceUid /* out */, | |
1990 DicomStoreUserConnection& connection, | |
1991 IDicomTranscoder& transcoder, | |
1992 const void* buffer, | |
1993 size_t size, | |
1994 const std::string& moveOriginatorAET, | |
1995 uint16_t moveOriginatorID) | |
1996 { | |
1997 std::unique_ptr<DcmFileFormat> dicom(FromDcmtkBridge::LoadFromMemoryBuffer(buffer, size)); | |
1998 if (dicom.get() == NULL || | |
1999 dicom->getDataset() == NULL) | |
2000 { | |
2001 throw OrthancException(ErrorCode_NullPointer); | |
2002 } | |
2003 | |
2004 DicomTransferSyntax inputSyntax; | |
2005 connection.LookupParameters(sopClassUid, sopInstanceUid, inputSyntax, *dicom); | |
2006 | |
2007 std::set<DicomTransferSyntax> accepted; | |
2008 connection.LookupTranscoding(accepted, sopClassUid, inputSyntax); | |
2009 | |
2010 if (accepted.find(inputSyntax) != accepted.end()) | |
2011 { | |
2012 // No need for transcoding | |
2013 connection.Store(sopClassUid, sopInstanceUid, *dicom, moveOriginatorAET, moveOriginatorID); | |
2014 } | |
2015 else | |
2016 { | |
2017 // Transcoding is needed | |
2018 std::set<DicomTransferSyntax> uncompressedSyntaxes; | |
2019 | |
2020 if (accepted.find(DicomTransferSyntax_LittleEndianImplicit) != accepted.end()) | |
2021 { | |
2022 uncompressedSyntaxes.insert(DicomTransferSyntax_LittleEndianImplicit); | |
2023 } | |
2024 | |
2025 if (accepted.find(DicomTransferSyntax_LittleEndianExplicit) != accepted.end()) | |
2026 { | |
2027 uncompressedSyntaxes.insert(DicomTransferSyntax_LittleEndianExplicit); | |
2028 } | |
2029 | |
2030 if (accepted.find(DicomTransferSyntax_BigEndianExplicit) != accepted.end()) | |
2031 { | |
2032 uncompressedSyntaxes.insert(DicomTransferSyntax_BigEndianExplicit); | |
2033 } | |
2034 | |
2035 std::unique_ptr<DcmFileFormat> transcoded; | |
2036 | |
2037 if (transcoder.HasInplaceTranscode()) | |
2038 { | |
2039 if (transcoder.InplaceTranscode(*dicom, uncompressedSyntaxes, false)) | |
2040 { | |
2041 // In-place transcoding is supported and has succeeded | |
2042 transcoded.reset(dicom.release()); | |
2043 } | |
2044 } | |
2045 else | |
2046 { | |
2047 transcoded.reset(transcoder.TranscodeToParsed(buffer, size, uncompressedSyntaxes, false)); | |
2048 } | |
2049 | |
2050 // WARNING: The "dicom" variable must not be used below this | |
2051 // point. The "sopInstanceUid" might also have changed (if | |
2052 // using lossy compression). | |
2053 | |
2054 if (transcoded == NULL || | |
2055 transcoded->getDataset() == NULL) | |
2056 { | |
2057 throw OrthancException( | |
2058 ErrorCode_NotImplemented, | |
2059 "Cannot transcode from \"" + std::string(GetTransferSyntaxUid(inputSyntax)) + | |
2060 "\" to an uncompressed syntax for modality: " + | |
2061 connection.GetParameters().GetRemoteModality().GetApplicationEntityTitle()); | |
2062 } | |
2063 else | |
2064 { | |
2065 DicomTransferSyntax transcodedSyntax; | |
2066 | |
2067 // Sanity check | |
2068 if (!FromDcmtkBridge::LookupOrthancTransferSyntax(transcodedSyntax, *transcoded) || | |
2069 accepted.find(transcodedSyntax) == accepted.end()) | |
2070 { | |
2071 throw OrthancException(ErrorCode_InternalError); | |
2072 } | |
2073 else | |
2074 { | |
2075 connection.Store(sopClassUid, sopInstanceUid, *transcoded, moveOriginatorAET, moveOriginatorID); | |
2076 } | |
2077 } | |
2078 } | |
2079 } | |
2080 | |
2081 static void Store(std::string& sopClassUid /* out */, | |
2082 std::string& sopInstanceUid /* out */, | |
2083 DicomStoreUserConnection& connection, | |
2084 IDicomTranscoder& transcoder, | |
2085 const void* buffer, | |
2086 size_t size) | |
2087 { | |
2088 Store(sopClassUid, sopInstanceUid, connection, transcoder, | |
2089 buffer, size, "", 0 /* Not a C-MOVE */); | |
2090 } | |
2091 }; | |
2092 | |
2093 | |
2094 class DcmtkTranscoder : public IDicomTranscoder | |
2095 { | |
2096 private: | |
2097 unsigned int lossyQuality_; | |
2098 | |
2099 static uint16_t GetBitsStored(DcmDataset& dataset) | |
2100 { | |
2101 uint16_t bitsStored; | |
2102 if (dataset.findAndGetUint16(DCM_BitsStored, bitsStored).good()) | |
2103 { | |
2104 return bitsStored; | |
2105 } | |
2106 else | |
2107 { | |
2108 throw OrthancException(ErrorCode_BadFileFormat, | |
2109 "Missing \"Bits Stored\" tag in DICOM instance"); | |
2110 } | |
2111 } | |
2112 | |
2113 static std::string GetSopInstanceUid(DcmDataset& dataset) | |
2114 { | |
2115 const char* v = NULL; | |
2116 | |
2117 if (dataset.findAndGetString(DCM_SOPInstanceUID, v).good() && | |
2118 v != NULL) | |
2119 { | |
2120 return std::string(v); | |
2121 } | |
2122 else | |
2123 { | |
2124 throw OrthancException(ErrorCode_BadFileFormat, "File without SOP instance UID"); | |
2125 } | |
2126 } | |
2127 | |
2128 static void CheckSopInstanceUid(DcmFileFormat& dicom, | |
2129 const std::string& sopInstanceUid, | |
2130 bool mustEqual) | |
2131 { | |
2132 if (dicom.getDataset() == NULL) | |
2133 { | |
2134 throw OrthancException(ErrorCode_InternalError); | |
2135 } | |
2136 | |
2137 bool ok; | |
2138 | |
2139 if (mustEqual) | |
2140 { | |
2141 ok = (GetSopInstanceUid(*dicom.getDataset()) == sopInstanceUid); | |
2142 } | |
2143 else | |
2144 { | |
2145 ok = (GetSopInstanceUid(*dicom.getDataset()) != sopInstanceUid); | |
2146 } | |
2147 | |
2148 if (!ok) | |
2149 { | |
2150 throw OrthancException(ErrorCode_InternalError, | |
2151 mustEqual ? "The SOP instance UID has changed unexpectedly during transcoding" : | |
2152 "The SOP instance UID has not changed as expected during transcoding"); | |
2153 } | |
2154 } | |
2155 | |
2156 public: | |
2157 DcmtkTranscoder() : | |
2158 lossyQuality_(90) | |
2159 { | |
2160 } | |
2161 | |
2162 void SetLossyQuality(unsigned int quality) | |
2163 { | |
2164 if (quality <= 0 || | |
2165 quality > 100) | |
2166 { | |
2167 throw OrthancException(ErrorCode_ParameterOutOfRange); | |
2168 } | |
2169 else | |
2170 { | |
2171 lossyQuality_ = quality; | |
2172 } | |
2173 } | |
2174 | |
2175 unsigned int GetLossyQuality() const | |
2176 { | |
2177 return lossyQuality_; | |
2178 } | |
2179 | |
2180 virtual DcmFileFormat* TranscodeToParsed(const void* buffer, | |
2181 size_t size, | |
2182 const std::set<DicomTransferSyntax>& allowedSyntaxes, | |
2183 bool allowNewSopInstanceUid) ORTHANC_OVERRIDE | |
2184 { | |
2185 std::unique_ptr<DcmFileFormat> dicom(FromDcmtkBridge::LoadFromMemoryBuffer(buffer, size)); | |
2186 | |
2187 if (dicom.get() == NULL) | |
2188 { | |
2189 throw OrthancException(ErrorCode_InternalError); | |
2190 } | |
2191 | |
2192 if (InplaceTranscode(*dicom, allowedSyntaxes, allowNewSopInstanceUid)) | |
2193 { | |
2194 return dicom.release(); | |
2195 } | |
2196 else | |
2197 { | |
2198 return NULL; | |
2199 } | |
2200 } | |
2201 | |
2202 virtual bool HasInplaceTranscode() const | |
2203 { | |
2204 return true; | |
2205 } | |
2206 | |
2207 virtual bool InplaceTranscode(DcmFileFormat& dicom, | |
2208 const std::set<DicomTransferSyntax>& allowedSyntaxes, | |
2209 bool allowNewSopInstanceUid) ORTHANC_OVERRIDE | |
2210 { | |
2211 if (dicom.getDataset() == NULL) | |
2212 { | |
2213 throw OrthancException(ErrorCode_InternalError); | |
2214 } | |
2215 | |
2216 DicomTransferSyntax syntax; | |
2217 if (!FromDcmtkBridge::LookupOrthancTransferSyntax(syntax, dicom)) | |
2218 { | |
2219 throw OrthancException(ErrorCode_BadFileFormat, | |
2220 "Cannot determine the transfer syntax"); | |
2221 } | |
2222 | |
2223 const uint16_t bitsStored = GetBitsStored(*dicom.getDataset()); | |
2224 std::string sourceSopInstanceUid = GetSopInstanceUid(*dicom.getDataset()); | |
2225 | |
2226 if (allowedSyntaxes.find(syntax) != allowedSyntaxes.end()) | |
2227 { | |
2228 // No transcoding is needed | |
2229 return true; | |
2230 } | |
2231 | |
2232 if (allowedSyntaxes.find(DicomTransferSyntax_LittleEndianImplicit) != allowedSyntaxes.end() && | |
2233 FromDcmtkBridge::Transcode(dicom, DicomTransferSyntax_LittleEndianImplicit, NULL)) | |
2234 { | |
2235 CheckSopInstanceUid(dicom, sourceSopInstanceUid, true); | |
2236 return true; | |
2237 } | |
2238 | |
2239 if (allowedSyntaxes.find(DicomTransferSyntax_LittleEndianExplicit) != allowedSyntaxes.end() && | |
2240 FromDcmtkBridge::Transcode(dicom, DicomTransferSyntax_LittleEndianExplicit, NULL)) | |
2241 { | |
2242 CheckSopInstanceUid(dicom, sourceSopInstanceUid, true); | |
2243 return true; | |
2244 } | |
2245 | |
2246 if (allowedSyntaxes.find(DicomTransferSyntax_BigEndianExplicit) != allowedSyntaxes.end() && | |
2247 FromDcmtkBridge::Transcode(dicom, DicomTransferSyntax_BigEndianExplicit, NULL)) | |
2248 { | |
2249 CheckSopInstanceUid(dicom, sourceSopInstanceUid, true); | |
2250 return true; | |
2251 } | |
2252 | |
2253 if (allowedSyntaxes.find(DicomTransferSyntax_DeflatedLittleEndianExplicit) != allowedSyntaxes.end() && | |
2254 FromDcmtkBridge::Transcode(dicom, DicomTransferSyntax_DeflatedLittleEndianExplicit, NULL)) | |
2255 { | |
2256 CheckSopInstanceUid(dicom, sourceSopInstanceUid, true); | |
2257 return true; | |
2258 } | |
2259 | |
2260 #if ORTHANC_ENABLE_DCMTK_JPEG == 1 | |
2261 if (allowedSyntaxes.find(DicomTransferSyntax_JPEGProcess1) != allowedSyntaxes.end() && | |
2262 allowNewSopInstanceUid && | |
2263 bitsStored == 8) | |
2264 { | |
2265 // Check out "dcmjpeg/apps/dcmcjpeg.cc" | |
2266 DJ_RPLossy parameters(lossyQuality_); | |
2267 | |
2268 if (FromDcmtkBridge::Transcode(dicom, DicomTransferSyntax_JPEGProcess1, ¶meters)) | |
2269 { | |
2270 CheckSopInstanceUid(dicom, sourceSopInstanceUid, false); | |
2271 return true; | |
2272 } | |
2273 } | |
2274 #endif | |
2275 | |
2276 #if ORTHANC_ENABLE_DCMTK_JPEG == 1 | |
2277 if (allowedSyntaxes.find(DicomTransferSyntax_JPEGProcess2_4) != allowedSyntaxes.end() && | |
2278 allowNewSopInstanceUid && | |
2279 bitsStored <= 12) | |
2280 { | |
2281 // Check out "dcmjpeg/apps/dcmcjpeg.cc" | |
2282 DJ_RPLossy parameters(lossyQuality_); | |
2283 if (FromDcmtkBridge::Transcode(dicom, DicomTransferSyntax_JPEGProcess2_4, ¶meters)) | |
2284 { | |
2285 CheckSopInstanceUid(dicom, sourceSopInstanceUid, false); | |
2286 return true; | |
2287 } | |
2288 } | |
2289 #endif | |
2290 | |
2291 #if ORTHANC_ENABLE_DCMTK_JPEG == 1 | |
2292 if (allowedSyntaxes.find(DicomTransferSyntax_JPEGProcess14SV1) != allowedSyntaxes.end()) | |
2293 { | |
2294 // Check out "dcmjpeg/apps/dcmcjpeg.cc" | |
2295 DJ_RPLossless parameters(6 /* opt_selection_value */, | |
2296 0 /* opt_point_transform */); | |
2297 if (FromDcmtkBridge::Transcode(dicom, DicomTransferSyntax_JPEGProcess14SV1, ¶meters)) | |
2298 { | |
2299 CheckSopInstanceUid(dicom, sourceSopInstanceUid, true); | |
2300 return true; | |
2301 } | |
2302 } | |
2303 #endif | |
2304 | |
2305 #if ORTHANC_ENABLE_DCMTK_JPEG_LOSSLESS == 1 | |
2306 if (allowedSyntaxes.find(DicomTransferSyntax_JPEGLSLossless) != allowedSyntaxes.end()) | |
2307 { | |
2308 // Check out "dcmjpls/apps/dcmcjpls.cc" | |
2309 DJLSRepresentationParameter parameters(2 /* opt_nearlossless_deviation */, | |
2310 OFTrue /* opt_useLosslessProcess */); | |
2311 | |
2312 /** | |
2313 * WARNING: This call results in a segmentation fault if using | |
2314 * the DCMTK package 3.6.2 from Ubuntu 18.04. | |
2315 **/ | |
2316 if (FromDcmtkBridge::Transcode(dicom, DicomTransferSyntax_JPEGLSLossless, ¶meters)) | |
2317 { | |
2318 CheckSopInstanceUid(dicom, sourceSopInstanceUid, true); | |
2319 return true; | |
2320 } | |
2321 } | |
2322 #endif | |
2323 | |
2324 #if ORTHANC_ENABLE_DCMTK_JPEG_LOSSLESS == 1 | |
2325 if (allowNewSopInstanceUid && | |
2326 allowedSyntaxes.find(DicomTransferSyntax_JPEGLSLossy) != allowedSyntaxes.end()) | |
2327 { | |
2328 // Check out "dcmjpls/apps/dcmcjpls.cc" | |
2329 DJLSRepresentationParameter parameters(2 /* opt_nearlossless_deviation */, | |
2330 OFFalse /* opt_useLosslessProcess */); | |
2331 | |
2332 /** | |
2333 * WARNING: This call results in a segmentation fault if using | |
2334 * the DCMTK package 3.6.2 from Ubuntu 18.04. | |
2335 **/ | |
2336 if (FromDcmtkBridge::Transcode(dicom, DicomTransferSyntax_JPEGLSLossy, ¶meters)) | |
2337 { | |
2338 CheckSopInstanceUid(dicom, sourceSopInstanceUid, false); | |
2339 return true; | |
2340 } | |
2341 } | |
2342 #endif | |
2343 | |
2344 return false; | |
2345 } | |
2346 | |
2347 | |
2348 virtual bool TranscodeToBuffer(std::string& target, | |
2349 const void* buffer, | |
2350 size_t size, | |
2351 const std::set<DicomTransferSyntax>& allowedSyntaxes, | |
2352 bool allowNewSopInstanceUid) ORTHANC_OVERRIDE | |
2353 { | |
2354 std::unique_ptr<DcmFileFormat> transcoded( | |
2355 TranscodeToParsed(buffer, size, allowedSyntaxes, allowNewSopInstanceUid)); | |
2356 | |
2357 if (transcoded.get() == NULL) | |
2358 { | |
2359 return false; | |
2360 } | |
2361 else | |
2362 { | |
2363 if (transcoded->getDataset() == NULL) | |
2364 { | |
2365 throw OrthancException(ErrorCode_InternalError); | |
2366 } | |
2367 | |
2368 FromDcmtkBridge::SaveToMemoryBuffer(target, *transcoded->getDataset()); | |
2369 return true; | |
2370 } | |
2371 } | |
2372 }; | |
2373 | |
2374 | |
2375 | |
2376 class PluginDicomTranscoder: public IDicomTranscoder | |
2377 { | |
2378 private: | |
2379 bool tryDcmtk_; | |
2380 DcmtkTranscoder dcmtk_; | |
2381 | |
2382 protected: | |
2383 virtual bool TranscodeInternal(std::string& target, | |
2384 const void* buffer, | |
2385 size_t size, | |
2386 const std::set<DicomTransferSyntax>& allowedSyntaxes, | |
2387 bool allowNewSopInstanceUid) = 0; | |
2388 | |
2389 public: | |
2390 PluginDicomTranscoder(bool tryDcmtk) : | |
2391 tryDcmtk_(tryDcmtk) | |
2392 { | |
2393 } | |
2394 | |
2395 virtual bool TranscodeToBuffer(std::string& target, | |
2396 const void* buffer, | |
2397 size_t size, | |
2398 const std::set<DicomTransferSyntax>& allowedSyntaxes, | |
2399 bool allowNewSopInstanceUid) ORTHANC_OVERRIDE | |
2400 { | |
2401 if (tryDcmtk_) | |
2402 { | |
2403 return dcmtk_.TranscodeToBuffer(target, buffer, size, allowedSyntaxes, allowNewSopInstanceUid); | |
2404 } | |
2405 else | |
2406 { | |
2407 return TranscodeInternal(target, buffer, size, allowedSyntaxes, allowNewSopInstanceUid); | |
2408 } | |
2409 } | |
2410 | |
2411 virtual DcmFileFormat* TranscodeToParsed(const void* buffer, | |
2412 size_t size, | |
2413 const std::set<DicomTransferSyntax>& allowedSyntaxes, | |
2414 bool allowNewSopInstanceUid) ORTHANC_OVERRIDE | |
2415 { | |
2416 if (tryDcmtk_) | |
2417 { | |
2418 return dcmtk_.TranscodeToParsed(buffer, size, allowedSyntaxes, allowNewSopInstanceUid); | |
2419 } | |
2420 else | |
2421 { | |
2422 std::string transcoded; | |
2423 if (TranscodeInternal(transcoded, buffer, size, allowedSyntaxes, allowNewSopInstanceUid)) | |
2424 { | |
2425 return FromDcmtkBridge::LoadFromMemoryBuffer( | |
2426 transcoded.empty() ? NULL : transcoded.c_str(), transcoded.size()); | |
2427 } | |
2428 else | |
2429 { | |
2430 return NULL; | |
2431 } | |
2432 } | |
2433 } | |
2434 | |
2435 virtual bool HasInplaceTranscode() const ORTHANC_OVERRIDE | |
2436 { | |
2437 return tryDcmtk_; | |
2438 } | |
2439 | |
2440 virtual bool InplaceTranscode(DcmFileFormat& dicom, | |
2441 const std::set<DicomTransferSyntax>& allowedSyntaxes, | |
2442 bool allowNewSopInstanceUid) ORTHANC_OVERRIDE | |
2443 { | |
2444 if (tryDcmtk_) | |
2445 { | |
2446 return dcmtk_.InplaceTranscode(dicom, allowedSyntaxes, allowNewSopInstanceUid); | |
2447 } | |
2448 else | |
2449 { | |
2450 // "HasInplaceTranscode()" should have been called | |
2451 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
2452 } | |
2453 } | |
2454 }; | |
2455 } | |
2456 | |
2457 | 1929 |
2458 TEST(Toto, DISABLED_Transcode3) | 1930 TEST(Toto, DISABLED_Transcode3) |
2459 { | 1931 { |
2460 DicomAssociationParameters p; | 1932 DicomAssociationParameters p; |
2461 p.SetRemotePort(2000); | 1933 p.SetRemotePort(2000); |
2481 Orthanc::SystemToolbox::ReadFile(source, path); | 1953 Orthanc::SystemToolbox::ReadFile(source, path); |
2482 | 1954 |
2483 std::string c, i; | 1955 std::string c, i; |
2484 try | 1956 try |
2485 { | 1957 { |
2486 IDicomTranscoder::Store(c, i, scu, transcoder, source.c_str(), source.size()); | 1958 scu.Transcode(c, i, transcoder, source.c_str(), source.size()); |
2487 } | 1959 } |
2488 catch (OrthancException& e) | 1960 catch (OrthancException& e) |
2489 { | 1961 { |
2490 if (e.GetErrorCode() == ErrorCode_NotImplemented) | 1962 if (e.GetErrorCode() == ErrorCode_NotImplemented) |
2491 { | 1963 { |
2499 } | 1971 } |
2500 } | 1972 } |
2501 } | 1973 } |
2502 | 1974 |
2503 | 1975 |
2504 | |
2505 | |
2506 TEST(Toto, DISABLED_Transcode4) | 1976 TEST(Toto, DISABLED_Transcode4) |
2507 { | 1977 { |
2508 std::string source; | 1978 std::string source; |
2509 Orthanc::SystemToolbox::ReadFile(source, "/home/jodogne/Subversion/orthanc-tests/Database/KarstenHilbertRF.dcm"); | 1979 Orthanc::SystemToolbox::ReadFile(source, "/home/jodogne/Subversion/orthanc-tests/Database/KarstenHilbertRF.dcm"); |
2510 | 1980 |
2532 printf("SIZE: %lu\n", t.size()); | 2002 printf("SIZE: %lu\n", t.size()); |
2533 } | 2003 } |
2534 } | 2004 } |
2535 } | 2005 } |
2536 | 2006 |
2537 | |
2538 #endif | 2007 #endif |