]> Creatis software - gdcm.git/blob - Example/ReWriteExtended.cxx
Add ReWriteExtended.cxx to show the result of the new
[gdcm.git] / Example / ReWriteExtended.cxx
1 /*=========================================================================
2                                                                                 
3   Program:   gdcm
4   Module:    $RCSfile: ReWriteExtended.cxx,v $
5   Language:  C++
6   Date:      $Date: 2006/03/17 14:40:47 $
7   Version:   $Revision: 1.1 $
8                                                                                 
9   Copyright (c) CREATIS (Centre de Recherche et d'Applications en Traitement de
10   l'Image). All rights reserved. See Doc/License.txt or
11   http://www.creatis.insa-lyon.fr/Public/Gdcm/License.html for details.
12                                                                                 
13      This software is distributed WITHOUT ANY WARRANTY; without even
14      the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15      PURPOSE.  See the above copyright notices for more information.
16                                                                                 
17 =========================================================================*/
18 #include "gdcmFile.h"
19 #include "gdcmFileHelper.h"
20 #include "gdcmDebug.h"
21 #include "gdcmUtil.h"
22 #include "gdcmArgMgr.h"
23
24 #include <iostream>
25
26 int main(int argc, char *argv[])
27 {
28    START_USAGE(usage)
29    " \n ReWriteExtended :\n",
30    " Re write a full gdcm-readable Dicom image                              ",
31    "     (usefull when the file header is not very straight).               ",
32    "                                                                        ",
33    " usage: ReWriteExtended filein=inputFileName fileout=outputFileName     ",
34    "      filecontent = 1 : USER_OWN_IMAGE                                  ",
35    "                  = 2 : FILTERED_IMAGE                                  ",
36    "                  = 3 : CREATED_IMAGE                                   ",
37    "                  = 4 : UNMODIFIED_PIXELS_IMAGE                         ", 
38    "       [mode=write mode] [noshadow] [noseq][debug]                      ", 
39    "                                                                        ",
40    "        mode = a (ACR), x (Explicit VR Dicom), r (RAW : only pixels)    ",
41    "        noshadowseq: user doesn't want to load Private Sequences        ",
42    "        noshadow : user doesn't want to load Private groups (odd number)",
43    "        noseq    : user doesn't want to load Sequences                  ",
44    "        rgb      : user wants to transform LUT (if any) to RGB pixels   ",
45    "        debug    : user wants to run the program in 'debug mode'        ",
46    FINISH_USAGE
47
48    // ----- Initialize Arguments Manager ------   
49    gdcm::ArgMgr *am = new gdcm::ArgMgr(argc, argv);
50   
51    if (argc == 1 || am->ArgMgrDefined("usage")) 
52    {
53       am->ArgMgrUsage(usage); // Display 'usage'
54       delete am;
55       return 0;
56    }
57    char *fileName = am->ArgMgrWantString("filein",usage);
58    if ( fileName == NULL )
59    {
60       std::cout << "'filein= ...' is mandatory" << std::endl;
61       delete am;
62       return 0;
63    }
64
65    char *outputFileName = am->ArgMgrWantString("fileout",usage);
66    if ( outputFileName == NULL )
67    {
68       std::cout << "'fileout= ...' is mandatory" << std::endl;
69       delete am;
70       return 0;
71    }
72
73    const char *mode = am->ArgMgrGetString("mode","X");
74    
75    int filecontent =  am->ArgMgrGetInt("filecontent", gdcm::UNMODIFIED_PIXELS_IMAGE);
76    
77    int loadMode = gdcm::LD_ALL;
78    if ( am->ArgMgrDefined("noshadowseq") )
79       loadMode |= gdcm::LD_NOSHADOWSEQ;
80    else 
81    {
82    if ( am->ArgMgrDefined("noshadow") )
83          loadMode |= gdcm::LD_NOSHADOW;
84       if ( am->ArgMgrDefined("noseq") )
85          loadMode |= gdcm::LD_NOSEQ;
86    }
87
88    bool rgb = ( 0 != am->ArgMgrDefined("RGB") );
89
90    if (am->ArgMgrDefined("debug"))
91       gdcm::Debug::DebugOn();
92  
93    // if unused Params we give up
94    if ( am->ArgMgrPrintUnusedLabels() )
95    { 
96       am->ArgMgrUsage(usage);
97       delete am;
98       return 0;
99    }
100
101    delete am;  // we don't need Argument Manager any longer
102
103    // ----------- End Arguments Manager ---------
104
105    gdcm::File *f = gdcm::File::New();
106    f->SetLoadMode( loadMode );
107    f->SetFileName( fileName );
108    bool res = f->Load();  
109    if ( !res )
110    {
111       f->Delete();
112       return 0;
113    }
114   
115    if (!f->IsReadable())
116    {
117        std::cerr << "Sorry, not a Readable DICOM / ACR File"  <<std::endl;
118        f->Delete();
119        return 0;
120    }
121    
122    gdcm::FileHelper *fh = gdcm::FileHelper::New(f);
123    void *imageData; 
124    int dataSize;
125   
126    if (rgb)
127    {
128       dataSize  = fh->GetImageDataSize();
129       imageData = fh->GetImageData(); // somewhat important... can't remember
130       fh->SetWriteModeToRGB();
131    }
132    else
133    {
134       dataSize  = fh->GetImageDataRawSize();
135       imageData = fh->GetImageDataRaw();// somewhat important... can't remember
136       fh->SetWriteModeToRaw();
137    }
138
139    if ( imageData == 0 ) // to avoid warning
140    {
141       std::cout << "Was unable to read pixels " << std::endl;
142    }
143    std::cout <<std::endl <<" dataSize " << dataSize << std::endl;
144    int nX,nY,nZ,sPP,planarConfig;
145    std::string pixelType, transferSyntaxName;
146    nX=f->GetXSize();
147    nY=f->GetYSize();
148    nZ=f->GetZSize();
149    std::cout << " DIMX=" << nX << " DIMY=" << nY << " DIMZ=" << nZ << std::endl;
150
151    pixelType    = f->GetPixelType();
152    sPP          = f->GetSamplesPerPixel();
153    planarConfig = f->GetPlanarConfiguration();
154    
155    std::cout << " pixelType="           << pixelType 
156              << " SampleserPixel="      << sPP
157              << " PlanarConfiguration=" << planarConfig 
158              << " PhotometricInterpretation=" 
159              << f->GetEntryString(0x0028,0x0004) 
160              << std::endl;
161
162    int numberOfScalarComponents=f->GetNumberOfScalarComponents();
163    std::cout << "NumberOfScalarComponents " << numberOfScalarComponents 
164              <<std::endl;
165    transferSyntaxName = f->GetTransferSyntaxName();
166    std::cout << " TransferSyntaxName= [" << transferSyntaxName << "]" 
167              << std::endl;
168
169
170    // We trust user. (just an example; *never* trust an user !)  
171    fh->SetContentType((gdcm::ImageContentType)filecontent);
172    
173    /// \todo Here, give the detail of operations a 'decent' user should perform,
174    ///       according to what *he* wants to do.
175
176
177    // an user shouldn't add images to a 'native' serie.
178    // He is allowed to create his own Serie, within a 'native' Study :
179    // if he wants to do so, he has to call gdcm::Util::GetUniqueUID 
180    // only once for a given image set, belonging to a single 'user Serie'
181    
182    std::string SerieInstanceUID;   
183    switch(filecontent)
184    {
185       case gdcm::USER_OWN_IMAGE :
186          SerieInstanceUID = gdcm::Util::CreateUniqueUID();
187          f->SetEntryString(SerieInstanceUID,0x0020,0x000e);
188       break;
189       
190       case gdcm::FILTERED_IMAGE :
191       /// \todo : to be finished!
192       break;      
193
194       case gdcm::CREATED_IMAGE :
195       /// \todo : to be finished!
196       break;
197
198       case gdcm::UNMODIFIED_PIXELS_IMAGE :
199       /// \todo : to be finished!
200       break;      
201    }
202
203    switch (mode[0])
204    {
205       case 'A' :
206       case 'a' :
207       // Writting an ACR file
208       // from a full gdcm readable File
209          std::cout << "WriteACR" << std::endl;
210          fh->WriteAcr(outputFileName);
211          break;
212
213       case 'D' : // Not documented in the 'usage', because the method 
214       case 'd' : //                             is known to be bugged. 
215       // Writting a DICOM Implicit VR file
216       // from a full gdcm readable File
217          std::cout << "WriteDCM Implicit VR" << std::endl;
218          fh->WriteDcmImplVR(outputFileName);
219          break;
220
221       case 'X' :
222       case 'x' :
223       // writting a DICOM Explicit VR 
224       // from a full gdcm readable File
225          std::cout << "WriteDCM Explicit VR" << std::endl;
226          // fh->WriteDcmExplVR(outputFileName);
227          // Try this one :
228          fh->SetWriteTypeToDcmExplVR();
229          fh->Write(outputFileName);
230          break;
231
232       case 'R' :
233       case 'r' :
234       //  Writting a Raw File, 
235          std::cout << "WriteRaw" << std::endl;
236          fh->WriteRawData(outputFileName);
237          break;
238  
239  // Just for fun :
240  // Write a 'Video inverse' version of the file.
241  // *Not* described, on purpose,  in the USAGE  
242       case 'V' :
243       case 'v' :
244          if ( fh->GetFile()->GetBitsAllocated() == 8)
245          {
246             std::cout << "videoinv for 8 bits" << std::endl;
247             for (int i=0; i<dataSize; i++) 
248             {
249                ((uint8_t*)imageData)[i] = 255 - ((uint8_t*)imageData)[i];
250             }
251          }
252          else
253          {
254             std::cout << "videoinv for 16 bits" << std::endl;    
255             for (int i=0; i<dataSize/2; i++) 
256             {
257                ((uint16_t*)imageData)[i] =  65535 - ((uint16_t*)imageData)[i];
258             }
259          }
260          std::cout << "WriteDCM Explicit VR + VideoInv" << std::endl;
261          fh->WriteDcmExplVR(outputFileName);
262          break;
263    }
264
265    f->Delete();
266    fh->Delete();
267    return 0;
268 }
269