Medical Imaging Interaction Toolkit  2025.12.02
Medical Imaging Interaction Toolkit
mitkDicomSeriesReader.h
Go to the documentation of this file.
1 /*============================================================================
2 
3 The Medical Imaging Interaction Toolkit (MITK)
4 
5 Copyright (c) German Cancer Research Center (DKFZ)
6 All rights reserved.
7 
8 Use of this source code is governed by a 3-clause BSD license that can be
9 found in the LICENSE file.
10 
11 ============================================================================*/
12 
13 #ifndef mitkDicomSeriesReader_h
14 #define mitkDicomSeriesReader_h
15 
16 #include "mitkConfig.h"
17 #include "mitkDataNode.h"
18 
19 #include <itkGDCMImageIO.h>
20 
21 #include <itkCommand.h>
22 #include <itkImageSeriesReader.h>
23 
24 #ifdef NOMINMAX
25 #define DEF_NOMINMAX
26 #undef NOMINMAX
27 #endif
28 
29 #include <gdcmConfigure.h>
30 
31 #ifdef DEF_NOMINMAX
32 #ifndef NOMINMAX
33 #define NOMINMAX
34 #endif
35 #undef DEF_NOMINMAX
36 #endif
37 
38 #include <gdcmDataSet.h>
39 #include <gdcmScanner.h>
40 
41 namespace mitk
42 {
344  class Image;
345 
347  {
348  public:
352  typedef std::vector<std::string> StringContainer;
353 
357  typedef void (*UpdateCallBackMethod)(float);
358 
369  typedef enum {
376 
382  typedef enum {
387 
396  {
397  public:
400 
402  std::string GetImageBlockUID() const;
403 
405  std::string GetSeriesInstanceUID() const;
406 
408  std::string GetModality() const;
409 
411  std::string GetSOPClassUIDAsString() const;
412 
414  std::string GetSOPClassUID() const;
415 
418 
421 
427  bool PixelSpacingIsUnknown() const;
428 
431 
433  bool HasMultipleTimePoints() const;
434 
436  bool IsMultiFrameImage() const;
437 
440 
441  private:
442  friend class DicomSeriesReader;
443 
445 
446  void AddFile(const std::string &file);
447  void AddFiles(const StringContainer &files);
448 
449  void SetImageBlockUID(const std::string &uid);
450 
451  void SetSeriesInstanceUID(const std::string &uid);
452 
453  void SetModality(const std::string &modality);
454 
455  void SetNumberOfFrames(const std::string &);
456 
457  void SetSOPClassUID(const std::string &mediaStorageSOPClassUID);
458 
459  void SetHasGantryTiltCorrected(bool);
460 
461  void SetPixelSpacingInformation(const std::string &pixelSpacing, const std::string &imagerPixelSpacing);
462 
463  void SetHasMultipleTimePoints(bool);
464 
465  void GetDesiredMITKImagePixelSpacing(ScalarType &spacingX, ScalarType &spacingY) const;
466 
467  StringContainer m_Filenames;
468  std::string m_ImageBlockUID;
469  std::string m_SeriesInstanceUID;
470  std::string m_Modality;
471  std::string m_SOPClassUID;
472  bool m_HasGantryTiltCorrected;
473  std::string m_PixelSpacing;
474  std::string m_ImagerPixelSpacing;
475  bool m_HasMultipleTimePoints;
476  bool m_IsMultiFrameImage;
477  };
478 
479  typedef std::map<std::string, ImageBlockDescriptor> FileNamesGrouping;
480 
487  static std::string GetConfigurationString();
488 
492  static bool IsDicom(const std::string &filename);
493 
499  static FileNamesGrouping GetSeries(const std::string &dir,
500  bool groupImagesWithGantryTilt,
501  const StringContainer &restrictions = StringContainer());
502 
511  static StringContainer GetSeries(const std::string &dir,
512  const std::string &series_uid,
513  bool groupImagesWithGantryTilt,
514  const StringContainer &restrictions = StringContainer());
515 
541  bool sortTo3DPlust,
542  bool groupImagesWithGantryTilt,
543  const StringContainer &restrictions = StringContainer());
544 
551  bool groupImagesWithGantryTilt,
552  const StringContainer &restrictions = StringContainer());
553 
565  static DataNode::Pointer LoadDicomSeries(const StringContainer &filenames,
566  bool sort = true,
567  bool load4D = true,
568  bool correctGantryTilt = true,
569  UpdateCallBackMethod callback = nullptr,
570  itk::SmartPointer<Image> preLoadedImageBlock = nullptr);
571 
585  static bool LoadDicomSeries(const StringContainer &filenames,
586  DataNode &node,
587  bool sort = true,
588  bool load4D = true,
589  bool correctGantryTilt = true,
590  UpdateCallBackMethod callback = nullptr,
591  itk::SmartPointer<Image> preLoadedImageBlock = nullptr);
592 
593  protected:
606  {
607  public:
609 
614 
619 
624 
628  void AddFileToSortedBlock(const std::string &filename);
629 
633  void AddFileToUnsortedBlock(const std::string &filename);
634  void AddFilesToUnsortedBlock(const StringContainer &filenames);
635 
641 
646 
647  protected:
650 
652  };
653 
666  {
667  public:
668  // two types to avoid any rounding errors
669  typedef itk::Point<double, 3> Point3Dd;
670  typedef itk::Vector<double, 3> Vector3Dd;
671 
676 
694  const Point3D &origin2,
695  const Vector3D &right,
696  const Vector3D &up,
697  unsigned int numberOfSlicesApart);
698 
704  bool IsSheared() const;
705 
715  bool IsRegularGantryTilt() const;
716 
721 
725  double GetRealZSpacing() const;
726 
733 
737  double GetTiltAngleInDegrees() const;
738 
739  protected:
743  Point3D projectPointOnLine(Point3Dd p, Point3Dd lineOrigin, Vector3Dd lineDirection);
744 
745  double m_ShiftUp;
746  double m_ShiftRight;
749  unsigned int m_NumberOfSlicesApart;
750  };
751 
755  typedef std::pair<StringContainer, StringContainer> TwoStringContainers;
756 
760  typedef std::map<std::string, std::string> TagToPropertyMapType;
761 
778  const StringContainer &files, bool groupsOfSimilarImages, const gdcm::Scanner::MappingType &tagValueMappings_);
779 
783  static std::string ConstCharStarToString(const char *s);
784 
788  static bool DICOMStringToSpacing(const std::string &s, ScalarType &spacingX, ScalarType &spacingY);
789 
798  static Point3D DICOMStringToPoint3D(const std::string &s, bool &successful);
799 
808  static void DICOMStringToOrientationVectors(const std::string &s, Vector3D &right, Vector3D &up, bool &successful);
809 
810  template <typename ImageType>
811  static typename ImageType::Pointer
812  // TODO this is NOT inplace!
813  InPlaceFixUpTiltedGeometry(ImageType *input, const GantryTiltInformation &tiltInfo);
814 
834  static StringContainer SortSeriesSlices(const StringContainer &unsortedFilenames);
835 
836  public:
840  static bool IsPhilips3DDicom(const std::string &filename);
841 
842  static std::string ReaderImplementationLevelToString(const ReaderImplementationLevel &enumValue);
844 
845  protected:
849  static bool ReadPhilips3DDicom(const std::string &filename, itk::SmartPointer<Image> output_image);
850 
854  static std::string CreateMoreUniqueSeriesIdentifier(gdcm::Scanner::TagToValue &tagValueMap);
855 
859  static std::string CreateSeriesIdentifierPart(gdcm::Scanner::TagToValue &tagValueMap, const gdcm::Tag &tag);
860 
864  static std::string IDifyTagValue(const std::string &value);
865 
866  typedef itk::GDCMImageIO DcmIoType;
867 
871  class CallbackCommand : public itk::Command
872  {
873  public:
875  void Execute(const itk::Object *caller, const itk::EventObject &) override
876  {
877  (*this->m_Callback)(static_cast<const itk::ProcessObject *>(caller)->GetProgress());
878  }
879 
880  void Execute(itk::Object *caller, const itk::EventObject &) override
881  {
882  (*this->m_Callback)(static_cast<itk::ProcessObject *>(caller)->GetProgress());
883  }
884 
885  protected:
887  };
888 
889  static void FixSpacingInformation(Image *image, const ImageBlockDescriptor &imageBlockDescriptor);
890 
894  static void ScanForSliceInformation(const StringContainer &filenames, gdcm::Scanner &scanner);
895 
899  static void LoadDicom(const StringContainer &filenames,
900  DataNode &node,
901  bool sort,
902  bool check_4d,
903  bool correctTilt,
904  UpdateCallBackMethod callback,
905  itk::SmartPointer<Image> preLoadedImageBlock);
906 
916  template <typename PixelType>
918  bool correctTilt,
919  const GantryTiltInformation &tiltInfo,
920  DcmIoType::Pointer &io,
921  CallbackCommand *command,
922  itk::SmartPointer<Image> preLoadedImageBlock);
923 
925  bool correctTilt,
926  const GantryTiltInformation &tiltInfo,
927  DcmIoType::Pointer &io,
928  CallbackCommand *command,
929  itk::SmartPointer<Image> preLoadedImageBlock);
930 
932  bool correctTilt,
933  const GantryTiltInformation &tiltInfo,
934  DcmIoType::Pointer &io,
935  CallbackCommand *command,
936  itk::SmartPointer<Image> preLoadedImageBlock);
937 
939  bool correctTilt,
940  const GantryTiltInformation &tiltInfo,
941  DcmIoType::Pointer &io,
942  CallbackCommand *command,
943  itk::SmartPointer<Image> preLoadedImageBlock);
944 
945  template <typename PixelType>
946  static itk::SmartPointer<Image> LoadDICOMByITK4D(std::list<StringContainer> &imageBlocks,
947  ImageBlockDescriptor imageBlockDescriptor,
948  bool correctTilt,
949  const GantryTiltInformation &tiltInfo,
950  DcmIoType::Pointer &io,
951  CallbackCommand *command,
952  itk::SmartPointer<Image> preLoadedImageBlock);
953 
954  static itk::SmartPointer<Image> MultiplexLoadDICOMByITK4D(std::list<StringContainer> &imageBlocks,
955  ImageBlockDescriptor imageBlockDescriptor,
956  bool correctTilt,
957  const GantryTiltInformation &tiltInfo,
958  DcmIoType::Pointer &io,
959  CallbackCommand *command,
960  itk::SmartPointer<Image> preLoadedImageBlock);
961 
962  static itk::SmartPointer<Image> MultiplexLoadDICOMByITK4DScalar(std::list<StringContainer> &imageBlocks,
963  ImageBlockDescriptor imageBlockDescriptor,
964  bool correctTilt,
965  const GantryTiltInformation &tiltInfo,
966  DcmIoType::Pointer &io,
967  CallbackCommand *command,
968  itk::SmartPointer<Image> preLoadedImageBlock);
969 
970  static itk::SmartPointer<Image> MultiplexLoadDICOMByITK4DRGBPixel(std::list<StringContainer> &imageBlocks,
971  ImageBlockDescriptor imageBlockDescriptor,
972  bool correctTilt,
973  const GantryTiltInformation &tiltInfo,
974  DcmIoType::Pointer &io,
975  CallbackCommand *command,
976  itk::SmartPointer<Image> preLoadedImageBlock);
977 
992  static std::list<StringContainer> SortIntoBlocksFor3DplusT(const StringContainer &presortedFilenames,
993  const gdcm::Scanner::MappingType &tagValueMappings_,
994  bool sort,
995  bool &canLoadAs4D);
996 
1003  static bool GdcmSortFunction(const gdcm::DataSet &ds1, const gdcm::DataSet &ds2);
1004 
1011  const gdcm::Scanner::MappingType &tagValueMappings_,
1012  DcmIoType *io,
1013  const ImageBlockDescriptor &blockInfo,
1014  Image *image);
1015  static void CopyMetaDataToImageProperties(std::list<StringContainer> imageBlock,
1016  const gdcm::Scanner::MappingType &tagValueMappings_,
1017  DcmIoType *io,
1018  const ImageBlockDescriptor &blockInfo,
1019  Image *image);
1020 
1030  };
1031 }
1032 
1033 #endif
Class for nodes of the DataTree.
Definition: mitkDataNode.h:64
Progress callback for DicomSeriesReader.
void Execute(const itk::Object *caller, const itk::EventObject &) override
void Execute(itk::Object *caller, const itk::EventObject &) override
CallbackCommand(UpdateCallBackMethod callback)
GantryTiltInformation(const Point3D &origin1, const Point3D &origin2, const Vector3D &right, const Vector3D &up, unsigned int numberOfSlicesApart)
THE constructor, which does all the calculations.
double GetRealZSpacing() const
The z / inter-slice spacing. Needed to correct ImageSeriesReader's result.
bool IsSheared() const
Whether the slices were sheared.
double GetTiltCorrectedAdditionalSize() const
The shift between first and last slice in mm.
double GetMatrixCoefficientForCorrectionInWorldCoordinates() const
The offset distance in Y direction for each slice in mm (describes the tilt result).
GantryTiltInformation()
Just so we can create empty instances for assigning results later.
Point3D projectPointOnLine(Point3Dd p, Point3Dd lineOrigin, Vector3Dd lineDirection)
Projection of point p onto line through lineOrigin in direction of lineDirection.
double GetTiltAngleInDegrees() const
Calculated tilt angle in degrees.
bool IsRegularGantryTilt() const
Whether the shearing is a gantry tilt or more complicated.
Return type of GetSeries, describes a logical group of files.
ReaderImplementationLevel GetReaderImplementationLevel() const
Confidence of the reader that this block can be read successfully.
bool IsMultiFrameImage() const
Multi-frame image(s) or not.
std::string GetImageBlockUID() const
A unique ID describing this bloc (enhanced Series Instance UID).
std::string GetSOPClassUID() const
SOP Class UID as DICOM UID.
bool PixelSpacingRelatesToDetector() const
Whether or not mitk::Image spacing relates to the detector surface.
bool HasGantryTiltCorrected() const
Whether or not the block contains a gantry tilt which will be "corrected" during loading.
std::string GetModality() const
Series Modality (CT, MR, etc.)
std::string GetSeriesInstanceUID() const
The Series Instance UID.
std::string GetSOPClassUIDAsString() const
SOP Class UID as readable string (Computed Tomography Image Storage, Secondary Capture Image Storage,...
PixelSpacingInterpretation GetPixelSpacingType() const
How the mitk::Image spacing can meaningfully be interpreted.
bool PixelSpacingRelatesToPatient() const
Whether or not mitk::Image spacing relates to the patient.
bool PixelSpacingIsUnknown() const
Whether or not mitk::Image spacing is of unknown origin.
StringContainer GetFilenames() const
List of files in this group.
Return type of DicomSeriesReader::AnalyzeFileForITKImageSeriesReaderSpacingAssumption.
void AddFileToUnsortedBlock(const std::string &filename)
Meant for internal use by AnalyzeFileForITKImageSeriesReaderSpacingAssumption only.
StringContainer GetUnsortedFilenames()
Remaining files, which could not be grouped.
void AddFileToSortedBlock(const std::string &filename)
Meant for internal use by AnalyzeFileForITKImageSeriesReaderSpacingAssumption only.
void UndoPrematureGrouping()
Only meaningful for use by AnalyzeFileForITKImageSeriesReaderSpacingAssumption.
bool ContainsGantryTilt()
Whether or not the grouped result contain a gantry tilt.
void FlagGantryTilt()
Meant for internal use by AnalyzeFileForITKImageSeriesReaderSpacingAssumption only.
void AddFilesToUnsortedBlock(const StringContainer &filenames)
StringContainer GetBlockFilenames()
Grouping result, all same origin-to-origin distance w/o gaps.
static itk::SmartPointer< Image > LoadDICOMByITK(const StringContainer &, bool correctTilt, const GantryTiltInformation &tiltInfo, DcmIoType::Pointer &io, CallbackCommand *command, itk::SmartPointer< Image > preLoadedImageBlock)
Feed files into itk::ImageSeriesReader and retrieve a 3D MITK image.
static Point3D DICOMStringToPoint3D(const std::string &s, bool &successful)
Convert DICOM string describing a point to Point3D.
static std::string ConstCharStarToString(const char *s)
Safely convert const char* to std::string.
std::vector< std::string > StringContainer
Lists of filenames.
static std::string PixelSpacingInterpretationToString(const PixelSpacingInterpretation &enumValue)
PixelSpacingInterpretation
How the mitk::Image spacing should be interpreted.
@ PixelSpacingInterpretation_SpacingUnknown
distances are mm at detector surface
@ PixelSpacingInterpretation_SpacingAtDetector
distances are mm within a patient
static bool ReadPhilips3DDicom(const std::string &filename, itk::SmartPointer< Image > output_image)
Read a Philips3D ultrasound DICOM file and put into an mitk::Image.
static itk::SmartPointer< Image > MultiplexLoadDICOMByITK4D(std::list< StringContainer > &imageBlocks, ImageBlockDescriptor imageBlockDescriptor, bool correctTilt, const GantryTiltInformation &tiltInfo, DcmIoType::Pointer &io, CallbackCommand *command, itk::SmartPointer< Image > preLoadedImageBlock)
static void FixSpacingInformation(Image *image, const ImageBlockDescriptor &imageBlockDescriptor)
static FileNamesGrouping GetSeries(const StringContainer &files, bool sortTo3DPlust, bool groupImagesWithGantryTilt, const StringContainer &restrictions=StringContainer())
PREFERRED version of this method - scan and sort DICOM files.
static FileNamesGrouping GetSeries(const std::string &dir, bool groupImagesWithGantryTilt, const StringContainer &restrictions=StringContainer())
see other GetSeries().
static void DICOMStringToOrientationVectors(const std::string &s, Vector3D &right, Vector3D &up, bool &successful)
Convert DICOM string describing a point two Vector3D.
static std::string IDifyTagValue(const std::string &value)
Helper for CreateMoreUniqueSeriesIdentifier.
ReaderImplementationLevel
Describes how well the reader is tested for a certain file type.
@ ReaderImplementationLevel_Unsupported
loader code is implemented but not accompanied by tests
@ ReaderImplementationLevel_PartlySupported
loader code and tests are established
void(* UpdateCallBackMethod)(float)
Interface for the progress callback.
static void LoadDicom(const StringContainer &filenames, DataNode &node, bool sort, bool check_4d, bool correctTilt, UpdateCallBackMethod callback, itk::SmartPointer< Image > preLoadedImageBlock)
Performs actual loading of a series and creates an image having the specified pixel type.
static std::string CreateMoreUniqueSeriesIdentifier(gdcm::Scanner::TagToValue &tagValueMap)
Construct a UID that takes into account sorting criteria from GetSeries().
static std::string GetConfigurationString()
Provide combination of preprocessor defines that was active during compilation.
static DataNode::Pointer LoadDicomSeries(const StringContainer &filenames, bool sort=true, bool load4D=true, bool correctGantryTilt=true, UpdateCallBackMethod callback=nullptr, itk::SmartPointer< Image > preLoadedImageBlock=nullptr)
static itk::SmartPointer< Image > MultiplexLoadDICOMByITKScalar(const StringContainer &, bool correctTilt, const GantryTiltInformation &tiltInfo, DcmIoType::Pointer &io, CallbackCommand *command, itk::SmartPointer< Image > preLoadedImageBlock)
static bool LoadDicomSeries(const StringContainer &filenames, DataNode &node, bool sort=true, bool load4D=true, bool correctGantryTilt=true, UpdateCallBackMethod callback=nullptr, itk::SmartPointer< Image > preLoadedImageBlock=nullptr)
See LoadDicomSeries! Just a slightly different interface.
static bool GdcmSortFunction(const gdcm::DataSet &ds1, const gdcm::DataSet &ds2)
Defines spatial sorting for sorting by GDCM 2.
std::map< std::string, std::string > TagToPropertyMapType
Maps DICOM tags to MITK properties.
static std::string CreateSeriesIdentifierPart(gdcm::Scanner::TagToValue &tagValueMap, const gdcm::Tag &tag)
Helper for CreateMoreUniqueSeriesIdentifier.
static std::list< StringContainer > SortIntoBlocksFor3DplusT(const StringContainer &presortedFilenames, const gdcm::Scanner::MappingType &tagValueMappings_, bool sort, bool &canLoadAs4D)
Sort files into time step blocks of a 3D+t image.
static bool IsPhilips3DDicom(const std::string &filename)
Checks if a specific file is a Philips3D ultrasound DICOM file.
static void CopyMetaDataToImageProperties(StringContainer filenames, const gdcm::Scanner::MappingType &tagValueMappings_, DcmIoType *io, const ImageBlockDescriptor &blockInfo, Image *image)
Copy information about files and DICOM tags from ITK's MetaDataDictionary and from the list of input ...
static std::string ReaderImplementationLevelToString(const ReaderImplementationLevel &enumValue)
static itk::SmartPointer< Image > LoadDICOMByITK4D(std::list< StringContainer > &imageBlocks, ImageBlockDescriptor imageBlockDescriptor, bool correctTilt, const GantryTiltInformation &tiltInfo, DcmIoType::Pointer &io, CallbackCommand *command, itk::SmartPointer< Image > preLoadedImageBlock)
static FileNamesGrouping GetSeries(const StringContainer &files, bool groupImagesWithGantryTilt, const StringContainer &restrictions=StringContainer())
See other GetSeries().
static StringContainer GetSeries(const std::string &dir, const std::string &series_uid, bool groupImagesWithGantryTilt, const StringContainer &restrictions=StringContainer())
see other GetSeries().
static itk::SmartPointer< Image > MultiplexLoadDICOMByITK4DScalar(std::list< StringContainer > &imageBlocks, ImageBlockDescriptor imageBlockDescriptor, bool correctTilt, const GantryTiltInformation &tiltInfo, DcmIoType::Pointer &io, CallbackCommand *command, itk::SmartPointer< Image > preLoadedImageBlock)
static ImageType::Pointer InPlaceFixUpTiltedGeometry(ImageType *input, const GantryTiltInformation &tiltInfo)
static StringContainer SortSeriesSlices(const StringContainer &unsortedFilenames)
static itk::SmartPointer< Image > MultiplexLoadDICOMByITK4DRGBPixel(std::list< StringContainer > &imageBlocks, ImageBlockDescriptor imageBlockDescriptor, bool correctTilt, const GantryTiltInformation &tiltInfo, DcmIoType::Pointer &io, CallbackCommand *command, itk::SmartPointer< Image > preLoadedImageBlock)
static const TagToPropertyMapType & GetDICOMTagsToMITKPropertyMap()
Map between DICOM tags and MITK properties.
static bool IsDicom(const std::string &filename)
Checks if a specific file contains DICOM data.
std::pair< StringContainer, StringContainer > TwoStringContainers
for internal sorting.
static void CopyMetaDataToImageProperties(std::list< StringContainer > imageBlock, const gdcm::Scanner::MappingType &tagValueMappings_, DcmIoType *io, const ImageBlockDescriptor &blockInfo, Image *image)
static void ScanForSliceInformation(const StringContainer &filenames, gdcm::Scanner &scanner)
Scan for slice image information.
static itk::SmartPointer< Image > MultiplexLoadDICOMByITKRGBPixel(const StringContainer &, bool correctTilt, const GantryTiltInformation &tiltInfo, DcmIoType::Pointer &io, CallbackCommand *command, itk::SmartPointer< Image > preLoadedImageBlock)
std::map< std::string, ImageBlockDescriptor > FileNamesGrouping
static SliceGroupingAnalysisResult AnalyzeFileForITKImageSeriesReaderSpacingAssumption(const StringContainer &files, bool groupsOfSimilarImages, const gdcm::Scanner::MappingType &tagValueMappings_)
Ensure an equal z-spacing for a group of files.
static bool DICOMStringToSpacing(const std::string &s, ScalarType &spacingX, ScalarType &spacingY)
Safely convert a string into pixel spacing x and y.
static itk::SmartPointer< Image > MultiplexLoadDICOMByITK(const StringContainer &, bool correctTilt, const GantryTiltInformation &tiltInfo, DcmIoType::Pointer &io, CallbackCommand *command, itk::SmartPointer< Image > preLoadedImageBlock)
Image class for storing images.
Definition: mitkImage.h:70
class ITK_EXPORT Image
Find image slices visible on a given plane.
double ScalarType