From c03b64731b3ff407004829b9e88d1955f9b9b717 Mon Sep 17 00:00:00 2001 From: Robert Osfield Date: Mon, 29 Sep 2008 17:00:38 +0000 Subject: [PATCH] Improved the dicom plugins handling of different slice positions --- src/osgPlugins/dicom/ReaderWriterDICOM.cpp | 253 ++++++++++++++++----- 1 file changed, 195 insertions(+), 58 deletions(-) diff --git a/src/osgPlugins/dicom/ReaderWriterDICOM.cpp b/src/osgPlugins/dicom/ReaderWriterDICOM.cpp index a9627afa9..f9253c3e4 100644 --- a/src/osgPlugins/dicom/ReaderWriterDICOM.cpp +++ b/src/osgPlugins/dicom/ReaderWriterDICOM.cpp @@ -236,7 +236,7 @@ class ReaderWriterDICOM : public osgDB::ReaderWriter ++itr) { std::string localFile = path + "/" + *itr; - std::cout<<"contents = "< FileInfoList; + FileInfoList fileInfoList; + + typedef std::map DistanceFileInfoMap; + typedef std::map OrientationFileInfoMap; + OrientationFileInfoMap orientationFileInfoMap; + for(Files::iterator itr = files.begin(); itr != files.end(); ++itr) { - std::auto_ptr dcmImage(new DicomImage((*itr).c_str())); + DcmFileFormat fileformat; + OFCondition status = fileformat.loadFile((*itr).c_str()); + if(!status.good()) return ReadResult::ERROR_IN_READING_FILE; + + FileInfo fileInfo; + fileInfo.filename = *itr; + + double pixelSize_y = 1.0; + if (fileformat.getDataset()->findAndGetFloat64(DCM_PixelSpacing, pixelSize_y,0).good()) + { + fileInfo.matrix(1,1) = pixelSize_y; + } + + double pixelSize_x = 1.0; + if (fileformat.getDataset()->findAndGetFloat64(DCM_PixelSpacing, pixelSize_x,1).good()) + { + fileInfo.matrix(0,0) = pixelSize_x; + } + + // Get slice thickness + double sliceThickness = 1.0; + if (fileformat.getDataset()->findAndGetFloat64(DCM_SliceThickness, sliceThickness).good()) + { + fileInfo.matrix(2,2) = sliceThickness; + } + + double imagePositionPatient[3] = {0, 0, 0}; + + // patient position + for(int i=0; i<3; ++i) + { + if (fileformat.getDataset()->findAndGetFloat64(DCM_ImagePositionPatient, imagePositionPatient[i],i).good()) + { + osg::notify(osg::INFO)<<"Read DCM_ImagePositionPatient["<findAndGetFloat64(DCM_ImageOrientationPatient, imageOrientationPatient[i],i).good()) + { + osg::notify(osg::INFO)<<"Read imageOrientationPatient["<second; + if (dfim.empty()) return 0; + + for(DistanceFileInfoMap::iterator ditr = dfim.begin(); + ditr != dfim.end(); + ++ditr) + { + FileInfo& fileInfo = ditr->second; + fileInfoList.push_back(fileInfo); + osg::notify(osg::INFO)<<" d = "<first - dfim.begin()->first; + double averageThickness = dfim.size()<=1 ? 1.0 : totalDistance / double(dfim.size()-1); + + osg::notify(osg::INFO)<<"Average thickness "< dcmImage(new DicomImage(fileInfo.filename.c_str())); if (dcmImage.get()) { if (dcmImage->getStatus()==EIS_Normal) @@ -313,60 +455,6 @@ class ReaderWriterDICOM : public osgDB::ReaderWriter if (!image) { - // read dicom file format to extra spacing info - DcmFileFormat fileformat; - OFCondition status = fileformat.loadFile((*itr).c_str()); - if(!status.good()) return ReadResult::ERROR_IN_READING_FILE; - - double pixelSize_y = 1.0; - if (fileformat.getDataset()->findAndGetFloat64(DCM_PixelSpacing, pixelSize_y,0).good()) - { - (*matrix)(1,1) = pixelSize_y; - } - - double pixelSize_x = 1.0; - if (fileformat.getDataset()->findAndGetFloat64(DCM_PixelSpacing, pixelSize_x,1).good()) - { - (*matrix)(0,0) = pixelSize_x; - } - - // Get slice thickness - double sliceThickness = 1.0; - if (fileformat.getDataset()->findAndGetFloat64(DCM_SliceThickness, sliceThickness).good()) - { - (*matrix)(2,2) = sliceThickness; - } - - double imagePositionPatient[3] = {0}; - - // patient position - for(int i=0; i<3; ++i) - { - if (fileformat.getDataset()->findAndGetFloat64(DCM_ImagePositionPatient, imagePositionPatient[i],i).good()) - { - osg::notify(osg::NOTICE)<<"Read DCM_ImagePositionPatient["<findAndGetFloat64(DCM_ImageOrientationPatient, imageOrientationPatient[i],i).good()) - { - osg::notify(osg::NOTICE)<<"Read imageOrientationPatient["<getWidth() = "<getWidth()<getHeight() = "<getHeight()<getFrameCount() = "<getFrameCount()<setUserData(matrix.get()); image->setFileName(fileName.c_str()); image->allocateImage(dcmImage->getWidth(), dcmImage->getHeight(), files.size() * dcmImage->getFrameCount(), pixelFormat, dataType); + + + osg::notify(osg::NOTICE)<<"Image dimensions = "<s()<<", "<t()<<", "<r()<getPlanes()==numPlanes && @@ -481,6 +582,42 @@ class ReaderWriterDICOM : public osgDB::ReaderWriter } #endif + struct FileInfo + { + FileInfo(): + numX(0), + numY(0), + numSlices(0), + distance(0.0) {} + + FileInfo(const FileInfo& rhs): + filename(rhs.filename), + matrix(rhs.matrix), + numX(rhs.numX), + numY(rhs.numY), + numSlices(rhs.numSlices), + distance(distance) {} + + FileInfo& operator = (const FileInfo& rhs) + { + if (&rhs == this) return *this; + + filename = rhs.filename; + matrix = rhs.matrix; + numX = rhs.numX; + numY = rhs.numY; + numSlices = rhs.numSlices; + distance = rhs.distance; + } + + std::string filename; + osg::Matrixd matrix; + unsigned int numX; + unsigned int numY; + unsigned int numSlices; + double distance; + }; + }; // now register with Registry to instantiate the above