]> Creatis software - gdcm.git/blob - src/gdcmFile.cxx
gcdmPutDataHere
[gdcm.git] / src / gdcmFile.cxx
1 // gdcmFile.cxx
2
3 #include "gdcm.h"
4
5 static void _Swap(void* im, int swap, int lgr, int nb);
6
7 /////////////////////////////////////////////////////////////////
8 /**
9  * \ingroup   gdcmFile
10  * \brief Constructor dedicated to writing a new DICOMV3 part10 compliant
11  * \file (see SetFileName, SetDcmTag and Write)
12  * \Opens (in read only and when possible) an existing file and checks
13  * \for DICOM compliance. Returns NULL on failure.
14  * \Note: the in-memory representation of all available tags found in
15  * \the DICOM header is post-poned to first header information access.
16  * \This avoid a double parsing of public part of the header when
17  * \one sets an a posteriori shadow dictionary (efficiency can be
18  * \seen as a side effect).   
19  *
20  * @param 
21  *
22  * @return      
23  */
24  
25 gdcmFile::gdcmFile(string & filename)
26         :gdcmHeader(filename.c_str())
27 {
28 }
29
30
31 /////////////////////////////////////////////////////////////////
32 /**
33  * \ingroup   gdcmFile
34  * \brief     Renvoie la longueur A ALLOUER pour recevoir les pixels de l'image
35  * \            ou DES images dans le cas d'un multiframe
36  * \            ATTENTION : il ne s'agit PAS de la longueur du groupe des Pixels        
37  * \            (dans le cas d'images compressees, elle n'a pas de sens).
38  *
39  * @param void  Rien en entree
40  *
41  * @return      longueur a allouer 
42  */
43
44 size_t gdcmFile::GetImageDataSize(void) {
45         int nbLignes, nbCol, nbFrames, nb;
46         string str_nbFrames, str_nb;
47         // Nombre de Lignes     
48         nbLignes=atoi(gdcmHeader::GetPubElValByNumber(0x0028,0x0010).c_str());
49         // Nombre de Colonnes   
50         nbCol   =atoi(gdcmHeader::GetPubElValByNumber(0x0028,0x0011).c_str());
51
52         // Nombre de Frames     
53         str_nbFrames=gdcmHeader::GetPubElValByNumber(0x0028,0x0008);
54         
55         if (str_nbFrames == "UNFOUND" ) {
56                 nbFrames = 1;
57         } else {
58                 nbFrames = atoi(str_nbFrames.c_str() );
59         }
60         
61         // Nombre de Bits Alloues pour le stockage d'un Pixel   
62         str_nb=gdcmHeader::GetPubElValByNumber(0x0028,0x0100);
63
64         if (str_nb == "UNFOUND" ) {
65                 nb = 16;
66         } else {
67                 nb = atoi(str_nb.c_str() );
68         }
69
70         size_t lgrTotale = nbFrames*nbLignes*nbCol*(nb/8);
71         return (lgrTotale);
72
73 }
74
75 /////////////////////////////////////////////////////////////////
76 /**
77  * \ingroup   gdcmFile
78  * \brief amene en mémoire les Pixels d'une image NON COMPRESSEE
79  * \Aucun test n'est fait pour le moment sur le caractere compresse ou non de l'image
80  *
81  * @param rien
82  *
83  * @return      Pointeur sur la zone mémoire contenant les Pixels lus
84  */
85
86 void * gdcmFile::GetImageData (void) {
87         
88         char* Pixels;
89         int nbLignes, nbCol;
90
91         int nbFrames, nb, nbu, highBit, signe;
92         string str_nbFrames, str_nb, str_nbu, str_highBit, str_signe;
93         
94         unsigned short int mask = 0xffff;
95                 
96         // Nombre de Lignes     
97         nbLignes=atoi(GetPubElValByNumber(0x0028,0x0010).c_str());
98         // Nombre de Colonnes   
99         nbCol   =atoi(GetPubElValByNumber(0x0028,0x0011).c_str());
100
101         // Nombre de Frames     
102         str_nbFrames=GetPubElValByNumber(0x0028,0x0008);
103
104         
105         if (str_nbFrames == "UNFOUND" ) {
106                 nbFrames = 1;
107         } else {
108                 nbFrames = atoi(str_nbFrames.c_str() );
109         }
110         
111         // Nombre de Bits Alloues       
112         str_nb=GetPubElValByNumber(0x0028,0x0100);
113
114         if (str_nb == "UNFOUND" ) {
115                 nb = 16;
116         } else {
117                 nb = atoi(str_nb.c_str() );
118         }
119         
120         // Nombre de Bits Utilises      
121         str_nbu=GetPubElValByNumber(0x0028,0x0101);
122
123         if (str_nbu == "UNFOUND" ) {
124                 nbu = nb;
125         } else {
126                 nbu = atoi(str_nbu.c_str() );
127         }       
128         
129         // Position du Bit de Poids Fort        
130         str_highBit=GetPubElValByNumber(0x0028,0x0102);
131
132         if (str_highBit == "UNFOUND" ) {
133                 highBit = nb - 1;
134         } else {
135                 highBit = atoi(str_highBit.c_str() );
136         }
137                 
138         // Signe des Pixels 
139         str_signe=GetPubElValByNumber(0x0028,0x0103);
140
141         if (str_signe == "UNFOUND" ) {
142                 signe = 1;
143         } else {
144                 signe = atoi(str_signe.c_str() );
145         }
146         
147         // Longueur en Octets des Pixels a lire
148         size_t lgrTotale = nbFrames*nbLignes*nbCol*(nb/8);
149         
150         //Pixels = (char *) g_malloc(lgrTotale);
151         Pixels = (char *) malloc(lgrTotale);
152         
153         GetPixels(lgrTotale, Pixels);
154
155         // On remet les Octets dans le bon ordre si besoin est
156         if (nb != 8) {
157                 int _sw = GetSwapCode();
158
159                 _Swap (Pixels, _sw, lgrTotale, nb);
160         }
161         
162         // On remet les Bits des Octets dans le bon ordre si besoin est
163         //
164         // ATTENTION :  Jamais confronté a des pixels stockes sur 32 bits 
165         //                      avec moins de 32 bits utilises
166         //                      et dont le bit de poids fort ne serait pas la ou on l'attend ...
167         //                      --> ne marchera pas dans ce cas 
168         if (nbu!=nb){
169                 mask = mask >> (nb-nbu);
170                 int l=(int)lgrTotale/(nb/8);
171                 unsigned short *deb = (unsigned short *)Pixels;
172                 for(int i=0;i<l;i++) {
173                                 *deb = (*deb >> (nbu-highBit-1)) & mask;
174                                 deb ++;
175                 }
176         }
177                 
178         printf ("on est sorti\n");
179         
180         // VOIR s'il ne faudrait pas l'affecter à un champ du dcmHeader
181         
182         return (Pixels);                
183 }
184
185
186 /////////////////////////////////////////////////////////////////
187 /**
188  * \ingroup   gdcmFile
189  * \brief amene en mémoire dans une zone précisee par l'utilisateur
190  * \les Pixels d'une image NON COMPRESSEE
191  * \Aucun test n'est fait pour le moment sur le caractere compresse ou non de l'image
192  *
193  * @param 
194  *
195  * @return      
196  */
197
198 int gdcmFile::PutImageDataHere (void* destination, size_t MaxSize) {
199         
200         void * Pixels = destination;  // pour garder le code identique avec GetImageData
201         int nbLignes, nbCol;
202
203         int nbFrames, nb, nbu, highBit, signe;
204         string str_nbFrames, str_nb, str_nbu, str_highBit, str_signe;
205         
206         unsigned short int mask = 0xffff;
207                 
208         // Nombre de Lignes     
209         nbLignes=atoi(GetPubElValByNumber(0x0028,0x0010).c_str());
210         // Nombre de Colonnes   
211         nbCol   =atoi(GetPubElValByNumber(0x0028,0x0011).c_str());
212
213         // Nombre de Frames     
214         str_nbFrames=GetPubElValByNumber(0x0028,0x0008);
215
216         
217         if (str_nbFrames == "UNFOUND" ) {
218                 nbFrames = 1;
219         } else {
220                 nbFrames = atoi(str_nbFrames.c_str() );
221         }
222         
223         // Nombre de Bits Alloues       
224         str_nb=GetPubElValByNumber(0x0028,0x0100);
225
226         if (str_nb == "UNFOUND" ) {
227                 nb = 16;
228         } else {
229                 nb = atoi(str_nb.c_str() );
230         }
231         
232         // Nombre de Bits Utilises      
233         str_nbu=GetPubElValByNumber(0x0028,0x0101);
234
235         if (str_nbu == "UNFOUND" ) {
236                 nbu = nb;
237         } else {
238                 nbu = atoi(str_nbu.c_str() );
239         }       
240         
241         // Position du Bit de Poids Fort        
242         str_highBit=GetPubElValByNumber(0x0028,0x0102);
243
244         if (str_highBit == "UNFOUND" ) {
245                 highBit = nb - 1;
246         } else {
247                 highBit = atoi(str_highBit.c_str() );
248         }
249                 
250         // Signe des Pixels 
251         str_signe=GetPubElValByNumber(0x0028,0x0103);
252
253         if (str_signe == "UNFOUND" ) {
254                 signe = 1;
255         } else {
256                 signe = atoi(str_signe.c_str() );
257         }
258         
259         // Longueur en Octets des Pixels a lire
260         size_t lgrTotale = nbFrames*nbLignes*nbCol*(nb/8);
261         
262         // si lgrTotale < MaxSize ==> Gros pb . A VOIR
263         
264         lgrTotale = MaxSize;                                    // pour garder le code identique avec GetImageData
265         //Pixels = (char *) malloc(lgrTotale);  // pour garder le code identique avec GetImageData
266         
267         GetPixels(lgrTotale, Pixels);
268
269         // On remet les Octets dans le bon ordre si besoin est
270         if (nb != 8) {
271                 int _sw = GetSwapCode();
272
273                 _Swap (Pixels, _sw, lgrTotale, nb);
274         }
275         
276         // On remet les Bits des Octets dans le bon ordre si besoin est
277         //
278         // ATTENTION :  Jamais confronté a des pixels stockes sur 32 bits 
279         //                      avec moins de 32 bits utilises
280         //                      et dont le bit de poids fort ne serait pas la ou on l'attend ...
281         //                      --> ne marchera pas dans ce cas 
282         if (nbu!=nb){
283                 mask = mask >> (nb-nbu);
284                 int l=(int)lgrTotale/(nb/8);
285                 unsigned short *deb = (unsigned short *)Pixels;
286                 for(int i=0;i<l;i++) {
287                                 *deb = (*deb >> (nbu-highBit-1)) & mask;
288                                 deb ++;
289                 }
290         }
291                 
292         printf ("on est sorti\n");
293         
294         // VOIR s'il ne faudrait pas l'affecter à un champ du dcmHeader
295         
296         //return (Pixels);                              // pour garder le code identique avec GetImageData      
297         return 1; 
298 }
299
300 //
301 // Je laisse le code integral, au cas ça puisse etre reutilise ailleurs
302 //
303
304 static void _Swap(void* im, int swap, int lgr, int nb) {                     
305 guint32 s32;
306 guint16 fort,faible;
307 int i;
308
309 if(nb == 16)
310     
311         switch(swap) {
312                 case 0:
313                 case 12:
314                 case 1234:
315                         break;
316                 
317                 case 21:
318                 case 3412:
319                 case 2143:
320                 case 4321:
321
322                         for(i=0;i<lgr;i++)
323                                 ((unsigned short int*)im)[i]= ((((unsigned short int*)im)[i])>>8)
324                                                 | ((((unsigned short int*)im)[i])<<8);
325                         break;
326                         
327                 default:
328                         printf("valeur de SWAP (16 bits) non autorisee : %d\n", swap);
329         } 
330  
331 if( nb == 32 )
332
333         switch (swap) {
334                 case 0:
335                 case 1234:
336                          break;
337
338                 case 4321:
339                          for(i=0;i<lgr;i++) {
340                                 faible=  ((unsigned long int*)im)[i]&0x0000ffff;    /* 4321 */
341                                 fort  =((unsigned long int*)im)[i]>>16;
342                                 fort=  (fort>>8)   | (fort<<8);
343                                 faible=(faible>>8) | (faible<<8);
344                                 s32=faible;
345                                 ((unsigned long int*)im)[i]=(s32<<16)|fort;
346                         }
347                         break;
348
349                 case 2143:
350                         for(i=0;i<lgr;i++) {
351                                 faible=  ((unsigned long int*)im)[i]&0x0000ffff;    /* 2143 */
352                                 fort=((unsigned long int*)im)[i]>>16;
353                                 fort=  (fort>>8)   | (fort<<8);
354                                 faible=(faible>>8) | (faible<<8);
355                                 s32=fort; 
356                                 ((unsigned long int*)im)[i]=(s32<<16)|faible;
357                         }
358                         break;
359   
360                 case 3412:
361                         for(i=0;i<lgr;i++) {
362                                 faible=  ((unsigned long int*)im)[i]&0x0000ffff;    /* 3412 */
363                                 fort=((unsigned long int*)im)[i]>>16;                  
364                                 s32=faible; 
365                                 ((unsigned long int*)im)[i]=(s32<<16)|fort;
366                         }                 
367                         break; 
368                                 
369                 default:
370                         printf("valeur de SWAP (32 bits) non autorisee : %d\n", swap);
371         } 
372 return;
373 }
374
375
376