00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #include "gdcmSerieHelper.h"
00020 #include "gdcmDirList.h"
00021 #include "gdcmFile.h"
00022 #include "gdcmDebug.h"
00023
00024 #include <math.h>
00025 #include <vector>
00026 #include <algorithm>
00027
00028 namespace gdcm
00029 {
00030
00031
00032
00036 SerieHelper::SerieHelper()
00037 {
00038
00039 GdcmFileList *l = GetFirstCoherentFileList();
00040 while (l)
00041 {
00042
00043 for (GdcmFileList::iterator it = l->begin();
00044 it != l->end();
00045 ++it)
00046 {
00047 delete *it;
00048 }
00049 l->clear();
00050 delete l;;
00051 l = GetNextCoherentFileList();
00052 }
00053 }
00054
00058 SerieHelper::~SerieHelper()
00059 {
00060
00061 GdcmFileList *l = GetFirstCoherentFileList();
00062 while (l)
00063 {
00064
00065 for (GdcmFileList::iterator it = l->begin();
00066 it != l->end();
00067 ++it)
00068 {
00069 delete *it;
00070 }
00071 l->clear();
00072 delete l;
00073 l = GetNextCoherentFileList();
00074 }
00075 }
00076
00077
00078
00079
00080
00081
00086 void SerieHelper::AddFileName(std::string const &filename)
00087 {
00088
00089 File *header = new File( filename );
00090 if( header->IsReadable() )
00091 {
00092
00093 std::string uid = header->GetEntryValue (0x0020, 0x000e);
00094
00095
00096
00097 if ( CoherentGdcmFileListHT.count(uid) == 0 )
00098 {
00099 gdcmWarningMacro(" New Serie UID :[" << uid << "]");
00100
00101 CoherentGdcmFileListHT[uid] = new GdcmFileList;
00102 }
00103
00104 CoherentGdcmFileListHT[uid]->push_back( header );
00105 }
00106 else
00107 {
00108 gdcmWarningMacro("Could not read file: " << filename );
00109 delete header;
00110 }
00111 }
00112
00118 void SerieHelper::SetDirectory(std::string const &dir, bool recursive)
00119 {
00120 DirList dirList(dir, recursive);
00121
00122 DirListType filenames_list = dirList.GetFilenames();
00123 for( DirListType::const_iterator it = filenames_list.begin();
00124 it != filenames_list.end(); ++it)
00125 {
00126 AddFileName( *it );
00127 }
00128 }
00129
00136 void SerieHelper::OrderGdcmFileList(GdcmFileList *CoherentGdcmFileList)
00137 {
00138 if( ImagePositionPatientOrdering( CoherentGdcmFileList ) )
00139 {
00140 return ;
00141 }
00142 else if( ImageNumberOrdering(CoherentGdcmFileList ) )
00143 {
00144 return ;
00145 }
00146 else
00147 {
00148 FileNameOrdering(CoherentGdcmFileList );
00149 }
00150 }
00151
00156 GdcmFileList *SerieHelper::GetFirstCoherentFileList()
00157 {
00158 ItListHt = CoherentGdcmFileListHT.begin();
00159 if( ItListHt != CoherentGdcmFileListHT.end() )
00160 return ItListHt->second;
00161 return NULL;
00162 }
00163
00169 GdcmFileList *SerieHelper::GetNextCoherentFileList()
00170 {
00171 gdcmAssertMacro (ItListHt != CoherentGdcmFileListHT.end());
00172
00173 ++ItListHt;
00174 if ( ItListHt != CoherentGdcmFileListHT.end() )
00175 return ItListHt->second;
00176 return NULL;
00177 }
00178
00184 GdcmFileList *SerieHelper::GetCoherentFileList(std::string SerieUID)
00185 {
00186 if ( CoherentGdcmFileListHT.count(SerieUID) == 0 )
00187 return 0;
00188 return CoherentGdcmFileListHT[SerieUID];
00189 }
00190
00191
00192
00193
00194
00195
00205 bool SerieHelper::ImagePositionPatientOrdering( GdcmFileList *fileList )
00206
00207 {
00208
00209 float cosines[6];
00210 float normal[3];
00211 float ipp[3];
00212 float dist;
00213 float min = 0, max = 0;
00214 bool first = true;
00215 int n=0;
00216 std::vector<float> distlist;
00217
00219 for ( GdcmFileList::const_iterator
00220 it = fileList->begin();
00221 it != fileList->end(); ++it )
00222 {
00223 if( first )
00224 {
00225 (*it)->GetImageOrientationPatient( cosines );
00226
00227
00228
00229
00230
00231 normal[0] = cosines[1]*cosines[5] - cosines[2]*cosines[4];
00232 normal[1] = cosines[2]*cosines[3] - cosines[0]*cosines[5];
00233 normal[2] = cosines[0]*cosines[4] - cosines[1]*cosines[3];
00234
00235 ipp[0] = (*it)->GetXOrigin();
00236 ipp[1] = (*it)->GetYOrigin();
00237 ipp[2] = (*it)->GetZOrigin();
00238
00239 dist = 0;
00240 for ( int i = 0; i < 3; ++i )
00241 {
00242 dist += normal[i]*ipp[i];
00243 }
00244
00245 if( dist == 0 )
00246 {
00247 return false;
00248 }
00249
00250 distlist.push_back( dist );
00251
00252 max = min = dist;
00253 first = false;
00254 }
00255 else
00256 {
00257 ipp[0] = (*it)->GetXOrigin();
00258 ipp[1] = (*it)->GetYOrigin();
00259 ipp[2] = (*it)->GetZOrigin();
00260
00261 dist = 0;
00262 for ( int i = 0; i < 3; ++i )
00263 {
00264 dist += normal[i]*ipp[i];
00265 }
00266
00267 if( dist == 0 )
00268 {
00269 return false;
00270 }
00271
00272 distlist.push_back( dist );
00273
00274 min = (min < dist) ? min : dist;
00275 max = (max > dist) ? max : dist;
00276 }
00277 ++n;
00278 }
00279
00280
00281
00282
00283 GdcmFileVector CoherentGdcmFileVector(n);
00284
00285 CoherentGdcmFileVector.resize( n );
00286
00287
00288 float step = (max - min)/(n - 1);
00289 int pos;
00290 n = 0;
00291
00292
00293 for (GdcmFileList::const_iterator it2 = fileList->begin();
00294 it2 != fileList->end(); ++it2, ++n)
00295 {
00296
00297
00298 pos = (int)( fabs( (distlist[n]-min)/step) + .5 );
00299
00300
00301
00302
00303
00304 if (CoherentGdcmFileVector[pos]==NULL)
00305 CoherentGdcmFileVector[pos] = *it2;
00306 else
00307 {
00308 gdcmWarningMacro( "2 files same position");
00309 return false;
00310 }
00311 }
00312
00313 fileList->clear();
00314
00315
00316 for (GdcmFileVector::const_iterator it3 = CoherentGdcmFileVector.begin();
00317 it3 != CoherentGdcmFileVector.end(); ++it3)
00318 {
00319 fileList->push_back( *it3 );
00320 }
00321
00322 distlist.clear();
00323 CoherentGdcmFileVector.clear();
00324
00325 return true;
00326 }
00327
00328 bool SerieHelper::ImageNumberLessThan(File *file1, File *file2)
00329 {
00330 return file1->GetImageNumber() < file2->GetImageNumber();
00331 }
00332
00341 bool SerieHelper::ImageNumberOrdering(GdcmFileList *fileList)
00342 {
00343 int min, max, pos;
00344 int n = fileList->size();
00345
00346 GdcmFileList::const_iterator it = fileList->begin();
00347 min = max = (*it)->GetImageNumber();
00348
00349 for (; it != fileList->end(); ++it, ++n)
00350 {
00351 pos = (*it)->GetImageNumber();
00352 min = (min < pos) ? min : pos;
00353 max = (max > pos) ? max : pos;
00354 }
00355
00356
00357 if( min == max || max == 0 || max >= (n+min))
00358 return false;
00359
00360 std::sort(fileList->begin(), fileList->end(), SerieHelper::ImageNumberLessThan );
00361
00362 return true;
00363 }
00364
00365 bool SerieHelper::FileNameLessThan(File *file1, File *file2)
00366 {
00367 return file1->GetFileName() < file2->GetFileName();
00368 }
00369
00375 bool SerieHelper::FileNameOrdering(GdcmFileList *fileList)
00376 {
00377 std::sort(fileList->begin(), fileList->end(), SerieHelper::FileNameLessThan);
00378 return true;
00379 }
00380
00381
00382
00386 void SerieHelper::Print(std::ostream &os, std::string const & indent)
00387 {
00388
00389 CoherentFileListmap::iterator itl = CoherentGdcmFileListHT.begin();
00390 if ( itl == CoherentGdcmFileListHT.end() )
00391 {
00392 gdcmWarningMacro( "No Coherent File list found" );
00393 return;
00394 }
00395 while (itl != CoherentGdcmFileListHT.end())
00396 {
00397 os << "Serie UID :[" << itl->first << "]" << std::endl;
00398
00399
00400 for (GdcmFileList::iterator it = (itl->second)->begin();
00401 it != (itl->second)->end();
00402 ++it)
00403 {
00404 os << indent << " --- " << (*it)->GetFileName() << std::endl;
00405 }
00406 ++itl;
00407 }
00408 }
00409
00410
00411 }