source: trunk/ReadMarCCDFrame.py @ 939

Last change on this file since 939 was 939, checked in by toby, 9 years ago

fix & cleanup unit tests; add/change doc strings for sphinx; add all G2 py files to sphinx

File size: 29.6 KB
Line 
1#!/usr/bin/env python
2'''
3*ReadMarCCDFrame: Read Mar Files*
4---------------------------------
5
6'''
7"""
8  from /opt/marccd/documentation/header.txt
9
10   MarCCD Header Documentataion
11
12   from C code in frame.h  and types.h
13
14   Documentation updated by R. Doyle Mon Mar 22 15:04:00 CDT 2010
15   Documentation updated by M. Blum Tue Oct 11 11:49:20 CDT 2005
16
17   Description documents marccd v0.20.0
18
19
20   Summary of file structure:
21   |-- 1024 bytes TIFF HEADER -------------|
22   |-- 3072 byte frame_header structure ---|
23   |-- nfast*nslow*depth byte image -------|
24
25   The full header, as written to the file, is a TIFF header.
26   The initial 1024 bytes are a minimal TIFF header with a standard
27   TIFF TAG pointing to the image data and a private TIFF TAG
28   pointing to this header structure.  As written by mmx/marccd, the
29   frame_header structure always begins at byte 1024 and is 3072 bytes long
30   making the full header 4096 bytes.
31
32   immediately following the header is the image - it is of arbitrary size defined
33   by the header fields nfast, nslow and depth. The total size is
34   nfast * nslow * depth bytes.
35
36   The meanings of the data types should be self evident:
37   (example:  UINT32 is an unsigned 32 bit integer)
38   The exact C language definition is machine dependent but these
39   are the most common definitions on a 32bit architecture cpu.
40#define UINT16  unsigned short
41#define INT16   short
42#define UINT32  unsigned int
43#define INT32   int
44
45   Currently frames are always written as defined below:
46         origin=UPPER_LEFT
47         orientation=HFAST
48         view_direction=FROM_SOURCE
49
50
51/* This number is  written into the byte_order fields in the
52   native byte order of the machine writing the file */
53#define LITTLE_ENDIAN   1234
54#define BIG_ENDIAN      4321
55
56/* possible orientations of frame data (stored in orienation field) */
57#define HFAST                   0        /* Horizontal axis is fast */
58#define VFAST                   1        /* Vertical axis is fast */
59
60/* possible origins of frame data (stored in origin field) */
61#define UPPER_LEFT              0
62#define LOWER_LEFT              1
63#define UPPER_RIGHT             2
64#define LOWER_RIGHT             3
65
66/* possible view directions of frame data for
67   the given orientation and origin (stored in view_direction field) */
68#define FROM_SOURCE             0
69#define TOWARD_SOURCE           1
70
71/* possible types of data (in data_type field) */
72#define DATA_UNSIGNED_INTEGER   0
73#define DATA_SIGNED_INTEGER     1
74#define DATA_FLOAT              2
75
76#define MAXIMAGES 9
77#define MAXSUBIMAGES 4096
78#define MAXFRAMEDIMENSION       8192
79
80typedef struct frame_header_type {
81        /* File/header format parameters (256 bytes) */
82        UINT32        header_type;      /* flag for header type  (can be used as magic number) */
83        char header_name[16];           /* header name (MARCCD) */
84        UINT32        header_major_version;     /* header_major_version (n.) */
85        UINT32        header_minor_version;     /* header_minor_version (.n) */
86        UINT32        header_byte_order;/* BIG_ENDIAN (Motorola,MIPS); LITTLE_ENDIAN (DEC, Intel) */
87        UINT32        data_byte_order;  /* BIG_ENDIAN (Motorola,MIPS); LITTLE_ENDIAN (DEC, Intel) */
88        UINT32        header_size;      /* in bytes                     */
89        UINT32        frame_type;       /* flag for frame type */
90        UINT32        magic_number;     /* to be used as a flag - usually to indicate new file */
91        UINT32        compression_type; /* type of image compression    */
92        UINT32        compression1;     /* compression parameter 1 */
93        UINT32        compression2;     /* compression parameter 2 */
94        UINT32        compression3;     /* compression parameter 3 */
95        UINT32        compression4;     /* compression parameter 4 */
96        UINT32        compression5;     /* compression parameter 4 */
97        UINT32        compression6;     /* compression parameter 4 */
98        UINT32        nheaders;         /* total number of headers      */
99        UINT32        nfast;            /* number of pixels in one line */
100        UINT32        nslow;            /* number of lines in image     */
101        UINT32        depth;            /* number of bytes per pixel    */
102        UINT32        record_length;    /* number of pixels between succesive rows */
103        UINT32        signif_bits;      /* true depth of data, in bits  */
104        UINT32        data_type;        /* (signed,unsigned,float...) */
105        UINT32        saturated_value;  /* value marks pixel as saturated */
106        UINT32        sequence;         /* TRUE or FALSE */
107        UINT32        nimages;          /* total number of images - size of each is nfast*(nslow/nimages) */
108        UINT32        origin;           /* corner of origin             */
109        UINT32        orientation;      /* direction of fast axis       */
110        UINT32        view_direction;   /* direction to view frame      */
111        UINT32        overflow_location;/* FOLLOWING_HEADER, FOLLOWING_DATA */
112        UINT32        over_8_bits;      /* # of pixels with counts > 255 */
113        UINT32        over_16_bits;     /* # of pixels with count > 65535 */
114        UINT32        multiplexed;      /* multiplex flag */
115        UINT32        nfastimages;      /* # of images in fast direction */
116        UINT32        nslowimages;      /* # of images in slow direction */
117        UINT32        darkcurrent_applied; /* flags correction has been applied - hold magic number ? */
118        UINT32        bias_applied;       /* flags correction has been applied - hold magic number ? */
119        UINT32        flatfield_applied;  /* flags correction has been applied - hold magic number ? */
120        UINT32        distortion_applied; /* flags correction has been applied - hold magic number ? */
121        UINT32        original_header_type;     /* Header/frame type from file that frame is read from */
122        UINT32        file_saved;         /* Flag that file has been saved, should be zeroed if modified */
123        UINT32        n_valid_pixels;     /* Number of pixels holding valid data - first N pixels */
124        UINT32        defectmap_applied; /* flags correction has been applied - hold magic number ? */
125        UINT32        subimage_nfast;       /* when divided into subimages (eg. frameshifted) */
126        UINT32        subimage_nslow;       /* when divided into subimages (eg. frameshifted) */
127        UINT32        subimage_origin_fast; /* when divided into subimages (eg. frameshifted) */
128        UINT32        subimage_origin_slow; /* when divided into subimages (eg. frameshifted) */
129        UINT32        readout_pattern;      /* BIT Code - 1 = A, 2 = B, 4 = C, 8 = D */
130        UINT32        saturation_level;     /* at this value and above, data are not reliable */
131        UINT32        orientation_code;     /* Describes how this frame needs to be rotated to make it "right" */
132        UINT32        frameshift_multiplexed;  /* frameshift multiplex flag */
133        UINT32        prescan_nfast;            /* Number of non-image pixels preceeding imaging pixels - fast direction */
134        UINT32        prescan_nslow;            /* Number of non-image pixels preceeding imaging pixels - slow direction */
135        UINT32        postscan_nfast;           /* Number of non-image pixels followng imaging pixels - fast direction */
136        UINT32        postscan_nslow;           /* Number of non-image pixels followng imaging pixels - slow direction */
137        UINT32        prepost_trimmed;          /* trimmed==1 means pre and post scan pixels have been removed */
138        char reserve1[(64-55)*sizeof(INT32)-16];
139
140        /* Data statistics (128) */
141        UINT32        total_counts[2];  /* 64 bit integer range = 1.85E19*/
142        UINT32        special_counts1[2];
143        UINT32        special_counts2[2];
144        UINT32        min;
145        UINT32        max;
146        INT32        mean;                      /* mean * 1000 */
147        UINT32        rms;                      /* rms * 1000 */
148        UINT32        n_zeros;                  /* number of pixels with 0 value  - not included in stats in unsigned data */
149        UINT32        n_saturated;              /* number of pixels with saturated value - not included in stats */
150        UINT32        stats_uptodate;           /* Flag that stats OK - ie data not changed since last calculation */
151        UINT32        pixel_noise[MAXIMAGES];           /* 1000*base noise value (ADUs) */
152        char reserve2[(32-13-MAXIMAGES)*sizeof(INT32)];
153
154        /* Sample Changer info */
155        char          barcode[16];
156        UINT32        barcode_angle;
157        UINT32        barcode_status;
158        /* Pad to 256 bytes */
159        char reserve2a[(64-6)*sizeof(INT32)];
160
161        /* Goniostat parameters (128 bytes) */
162        INT32 xtal_to_detector;         /* 1000*distance in millimeters */
163        INT32 beam_x;                   /* 1000*x beam position (pixels) */
164        INT32 beam_y;                   /* 1000*y beam position (pixels) */
165        INT32 integration_time;         /* integration time in milliseconds */
166        INT32 exposure_time;            /* exposure time in milliseconds */
167        INT32 readout_time;             /* readout time in milliseconds */
168        INT32 nreads;                   /* number of readouts to get this image */
169        INT32 start_twotheta;           /* 1000*two_theta angle */
170        INT32 start_omega;              /* 1000*omega angle */
171        INT32 start_chi;                        /* 1000*chi angle */
172        INT32 start_kappa;              /* 1000*kappa angle */
173        INT32 start_phi;                        /* 1000*phi angle */
174        INT32 start_delta;              /* 1000*delta angle */
175        INT32 start_gamma;              /* 1000*gamma angle */
176        INT32 start_xtal_to_detector;   /* 1000*distance in mm (dist in um)*/
177        INT32 end_twotheta;             /* 1000*two_theta angle */
178        INT32 end_omega;                        /* 1000*omega angle */
179        INT32 end_chi;                  /* 1000*chi angle */
180        INT32 end_kappa;                        /* 1000*kappa angle */
181        INT32 end_phi;                  /* 1000*phi angle */
182        INT32 end_delta;                        /* 1000*delta angle */
183        INT32 end_gamma;                        /* 1000*gamma angle */
184        INT32 end_xtal_to_detector;     /* 1000*distance in mm (dist in um)*/
185        INT32 rotation_axis;            /* active rotation axis (index into above ie. 0=twotheta,1=omega...) */
186        INT32 rotation_range;           /* 1000*rotation angle */
187        INT32 detector_rotx;            /* 1000*rotation of detector around X */
188        INT32 detector_roty;            /* 1000*rotation of detector around Y */
189        INT32 detector_rotz;            /* 1000*rotation of detector around Z */
190        INT32 total_dose;               /* Hz-sec (counts) integrated over full exposure */
191        char reserve3[(32-29)*sizeof(INT32)]; /* Pad Gonisotat parameters to 128 bytes */
192
193        /* Detector parameters (128 bytes) */
194        INT32 detector_type;            /* detector type */
195        INT32 pixelsize_x;              /* pixel size (nanometers) */
196        INT32 pixelsize_y;              /* pixel size (nanometers) */
197        INT32 mean_bias;                        /* 1000*mean bias value */
198        INT32 photons_per_100adu;       /* photons / 100 ADUs */
199        INT32 measured_bias[MAXIMAGES]; /* 1000*mean bias value for each image*/
200        INT32 measured_temperature[MAXIMAGES];  /* Temperature of each detector in milliKelvins */
201        INT32 measured_pressure[MAXIMAGES];     /* Pressure of each chamber in microTorr */
202        /* Retired reserve4 when MAXIMAGES set to 9 from 16 and two fields removed, and temp and pressure added
203        char reserve4[(32-(5+3*MAXIMAGES))*sizeof(INT32)];
204        */
205
206        /* X-ray source and optics parameters (128 bytes) */
207        /* X-ray source parameters (14*4 bytes) */
208        INT32 source_type;              /* (code) - target, synch. etc */
209        INT32 source_dx;                        /* Optics param. - (size microns) */
210        INT32 source_dy;                        /* Optics param. - (size microns) */
211        INT32 source_wavelength;                /* wavelength (femtoMeters) */
212        INT32 source_power;             /* (Watts) */
213        INT32 source_voltage;           /* (Volts) */
214        INT32 source_current;           /* (microAmps) */
215        INT32 source_bias;              /* (Volts) */
216        INT32 source_polarization_x;    /* () */
217        INT32 source_polarization_y;    /* () */
218        INT32 source_intensity_0;       /* (arbitrary units) */
219        INT32 source_intensity_1;       /* (arbitrary units) */
220        char reserve_source[2*sizeof(INT32)];
221
222        /* X-ray optics_parameters (8*4 bytes) */
223        INT32 optics_type;              /* Optics type (code)*/
224        INT32 optics_dx;                        /* Optics param. - (size microns) */
225        INT32 optics_dy;                        /* Optics param. - (size microns) */
226        INT32 optics_wavelength;                /* Optics param. - (size microns) */
227        INT32 optics_dispersion;                /* Optics param. - (*10E6) */
228        INT32 optics_crossfire_x;       /* Optics param. - (microRadians) */
229        INT32 optics_crossfire_y;       /* Optics param. - (microRadians) */
230        INT32 optics_angle;             /* Optics param. - (monoch. 2theta - microradians) */
231        INT32 optics_polarization_x;    /* () */
232        INT32 optics_polarization_y;    /* () */
233        char reserve_optics[4*sizeof(INT32)];
234
235        char reserve5[((32-28)*sizeof(INT32))]; /* Pad X-ray parameters to 128 bytes */
236
237        /* File parameters (1024 bytes) */
238        char filetitle[128];            /* Title                                */
239        char filepath[128];             /* path name for data file              */
240        char filename[64];              /* name of data file                    */
241        char acquire_timestamp[32];     /* date and time of acquisition         */
242        char header_timestamp[32];      /* date and time of header update       */
243        char save_timestamp[32];        /* date and time file saved             */
244        char file_comment[512]; /* comments  - can be used as desired   */
245        char reserve6[1024-(128+128+64+(3*32)+512)]; /* Pad File parameters to 1024 bytes */
246
247        /* Dataset parameters (512 bytes) */
248        char dataset_comment[512];      /* comments  - can be used as desired   */
249
250        /* Reserved for user definable data - will not be used by Mar! */
251        char user_data[512];
252
253        /* char pad[----] USED UP! */     /* pad out to 3072 bytes */
254
255        } frame_header;
256"""
257
258import struct as st
259import array as ar
260import string, re
261
262MAXIMAGES=9
263
264class marFrame():
265    '''A class to extract correct mar header and image info from a MarCCD file
266
267    :param str File: file object [from open()]
268    :param byteOrd: '<' (default) or '>' 
269    :param dict IFD: ?
270    '''
271    def __init__(self,File,byteOrd='<',IFD={}):
272        # simple TIFF header info
273        self.TIFFsizeX = IFD[256][2][0]
274        self.TIFFsizeY = IFD[257][2][0]
275        self.TIFFbitDepth = IFD[258][2][0]
276        self.TIFFcompression = IFD[259][2][0] # 1 = no compression
277        self.TIFFphotometricInterpretation = IFD[262][2][0] # 1 = bilevel or grayscale where 0 is imaged as black
278        self.TIFFstripOffsets = IFD[273][2][0] # seems to be 4096 for marCCD
279        self.TIFForientation = IFD[274][2][0] # 1 = 0th row it top, 0th column is left
280        self.TIFFrowsPerStrip = IFD[278][2][0] # varies based on image size
281        self.TIFFstripByteCounts = IFD[279][2][0] # number of bytes in a strip also varies based on size
282        self.TIFFxResolution = IFD[282][2][0] # pixels per resolutionUnit in X direction (ImageWidth direction)
283        self.TIFFyResolution = IFD[283][2][0] # pixels per resolutionUnit in Y direction (ImageLength direction
284        self.TIFFresolutionUnit = IFD[296][2][0] # 3 = centimeter
285        self.byteDepth = self.TIFFbitDepth/8
286        self.arrayTypeCode = ['','B','H','L'][self.byteDepth]
287        # MarCCD specific header info
288        File.seek(IFD[34710][2][0])
289        self.headerType = st.unpack(byteOrd+'I',File.read(4))[0] #/* flag for header type  (can be used as magic number) */
290        self.headerName = re.sub(r'\x00','',string.join(st.unpack(byteOrd+16*'c',File.read(16)),''))
291        self.headerMajorVersion = st.unpack(byteOrd+'I',File.read(4))[0] #/* header_major_version (n.) */
292        self.headerMinorVersion = st.unpack(byteOrd+'I',File.read(4))[0] #/* header_minor_version (.n) */
293        self.headerByteOrder = st.unpack(byteOrd+'I',File.read(4))[0] #/* BIG_ENDIAN (Motorola,MIPS); LITTLE_ENDIAN (DEC, Intel) */
294        self.dataByteOrder = st.unpack(byteOrd+'I',File.read(4))[0] #/* BIG_ENDIAN (Motorola,MIPS); LITTLE_ENDIAN (DEC, Intel) */
295        self.headerSize = st.unpack(byteOrd+'I',File.read(4))[0] #/* in bytes                   */
296        self.frameType = st.unpack(byteOrd+'I',File.read(4))[0] #/* flag for frame type */
297        self.magicNumber = st.unpack(byteOrd+'I',File.read(4))[0] #/* to be used as a flag - usually to indicate new file */
298        self.compressionType = st.unpack(byteOrd+'I',File.read(4))[0] #/* type of image compression    */
299        self.compression1 = st.unpack(byteOrd+'I',File.read(4))[0] #/* compression parameter 1 */
300        self.compression2 = st.unpack(byteOrd+'I',File.read(4))[0] #/* compression parameter 2 */
301        self.compression3 = st.unpack(byteOrd+'I',File.read(4))[0] #/* compression parameter 3 */
302        self.compression4 = st.unpack(byteOrd+'I',File.read(4))[0] #/* compression parameter 4 */
303        self.compression5 = st.unpack(byteOrd+'I',File.read(4))[0] #/* compression parameter 4 */
304        self.compression6 = st.unpack(byteOrd+'I',File.read(4))[0] #/* compression parameter 4 */
305        self.nheaders = st.unpack(byteOrd+'I',File.read(4))[0] #/* total number of headers      */
306        self.nfast = st.unpack(byteOrd+'I',File.read(4))[0] #/* number of pixels in one line */
307        self.nslow = st.unpack(byteOrd+'I',File.read(4))[0] #/* number of lines in image     */
308        self.depth = st.unpack(byteOrd+'I',File.read(4))[0] #/* number of bytes per pixel    */
309        self.recordLength = st.unpack(byteOrd+'I',File.read(4))[0] #/* number of pixels between succesive rows */
310        self.signifBits = st.unpack(byteOrd+'I',File.read(4))[0] #/* true depth of data, in bits  */
311        self.dataType = st.unpack(byteOrd+'I',File.read(4))[0] #/* (signed,unsigned,float...) */
312        self.saturatedValue = st.unpack(byteOrd+'I',File.read(4))[0] #/* value marks pixel as saturated */
313        self.sequence = st.unpack(byteOrd+'I',File.read(4))[0] #/* TRUE or FALSE */
314        self.nimages = st.unpack(byteOrd+'I',File.read(4))[0] #/* total number of images - size of each is nfast*(nslow/nimages) */
315        self.origin = st.unpack(byteOrd+'I',File.read(4))[0] #/* corner of origin               */
316        self.orientation = st.unpack(byteOrd+'I',File.read(4))[0] #/* direction of fast axis    */
317        self.viewDirection = st.unpack(byteOrd+'I',File.read(4))[0] #/* direction to view frame      */
318        self.overflowLocation = st.unpack(byteOrd+'I',File.read(4))[0] #/* FOLLOWING_HEADER, FOLLOWING_DATA */
319        self.over8Bits = st.unpack(byteOrd+'I',File.read(4))[0] #/* # of pixels with counts > 255 */
320        self.over16Bits = st.unpack(byteOrd+'I',File.read(4))[0] #/* # of pixels with count > 65535 */
321        self.multiplexed = st.unpack(byteOrd+'I',File.read(4))[0] #/* multiplex flag */
322        self.nfastimages = st.unpack(byteOrd+'I',File.read(4))[0] #/* # of images in fast direction */
323        self.nslowimages = st.unpack(byteOrd+'I',File.read(4))[0] #/* # of images in slow direction */
324        self.darkcurrentApplied = st.unpack(byteOrd+'I',File.read(4))[0] #/* flags correction has been applied - hold magic number ? */
325        self.biasApplied = st.unpack(byteOrd+'I',File.read(4))[0] #/* flags correction has been applied - hold magic number ? */
326        self.flatfieldApplied = st.unpack(byteOrd+'I',File.read(4))[0] #/* flags correction has been applied - hold magic number ? */
327        self.distortionApplied = st.unpack(byteOrd+'I',File.read(4))[0] #/* flags correction has been applied - hold magic number ? */
328        self.originalHeaderType = st.unpack(byteOrd+'I',File.read(4))[0] #/* Header/frame type from file that frame is read from */
329        self.fileSaved = st.unpack(byteOrd+'I',File.read(4))[0] #/* Flag that file has been saved, should be zeroed if modified */
330        self.nValidPixels = st.unpack(byteOrd+'I',File.read(4))[0] #/* Number of pixels holding valid data - first N pixels */
331        self.defectmapApplied = st.unpack(byteOrd+'I',File.read(4))[0] #/* flags correction has been applied - hold magic number ? */
332        self.subimageNfast = st.unpack(byteOrd+'I',File.read(4))[0] #/* when divided into subimages (eg. frameshifted) */
333        self.subimageNslow = st.unpack(byteOrd+'I',File.read(4))[0] #/* when divided into subimages (eg. frameshifted) */
334        self.subimageOriginFast = st.unpack(byteOrd+'I',File.read(4))[0] #/* when divided into subimages (eg. frameshifted) */
335        self.subimageOriginSlow = st.unpack(byteOrd+'I',File.read(4))[0] #/* when divided into subimages (eg. frameshifted) */
336        self.readoutPattern = st.unpack(byteOrd+'I',File.read(4))[0] #/* BIT Code - 1 = A, 2 = B, 4 = C, 8 = D */
337        self.saturationLevel = st.unpack(byteOrd+'I',File.read(4))[0] #/* at this value and above, data are not reliable */
338        self.orientationCode = st.unpack(byteOrd+'I',File.read(4))[0] #/* Describes how this frame needs to be rotated to make it "right" */
339        self.frameshiftMultiplexed = st.unpack(byteOrd+'I',File.read(4))[0] #/* frameshift multiplex flag */
340        self.prescanNfast = st.unpack(byteOrd+'I',File.read(4))[0] #/* Number of non-image pixels preceeding imaging pixels - fast direction */
341        self.prescanNslow = st.unpack(byteOrd+'I',File.read(4))[0] #/* Number of non-image pixels preceeding imaging pixels - slow direction */
342        self.postscanNfast = st.unpack(byteOrd+'I',File.read(4))[0] #/* Number of non-image pixels followng imaging pixels - fast direction */
343        self.postscanNslow = st.unpack(byteOrd+'I',File.read(4))[0] #/* Number of non-image pixels followng imaging pixels - slow direction */
344        self.prepostTrimmed = st.unpack(byteOrd+'I',File.read(4))[0] #/* trimmed==1 means pre and post scan pixels have been removed */
345
346        File.seek(IFD[34710][2][0]+256)
347        #self.totalCounts = st.unpack(byteOrd+'Q',File.read(8))[0] # /* 64 bit integer range = 1.85E19*/
348        #self.specialCounts1 = st.unpack(byteOrd+'Q',File.read(8))[0]
349        #self.specialCounts2 = st.unpack(byteOrd+'Q',File.read(8))[0]
350        self.totalCounts = st.unpack(byteOrd+'II',File.read(8))
351        self.specialCounts1 = st.unpack(byteOrd+'II',File.read(8))
352        self.specialCounts2 = st.unpack(byteOrd+'II',File.read(8))
353        self.min = st.unpack(byteOrd+'I',File.read(4))[0]
354        self.max = st.unpack(byteOrd+'I',File.read(4))[0]
355        self.mean = st.unpack(byteOrd+'i',File.read(4))[0] # /* mean * 1000 */
356        self.rms = st.unpack(byteOrd+'I',File.read(4))[0] #/* rms * 1000 */
357        self.nZeros = st.unpack(byteOrd+'I',File.read(4))[0] #/* number of pixels with 0 value  - not included in stats in unsigned data */
358        self.nSaturated = st.unpack(byteOrd+'I',File.read(4))[0] #/* number of pixels with saturated value - not included in stats */
359        self.statsUptodate = st.unpack(byteOrd+'I',File.read(4))[0] #/* Flag that stats OK - ie data not changed since last calculation */
360        self.pixelNoise = st.unpack(byteOrd+'I'*MAXIMAGES,File.read(4*MAXIMAGES)) # /* 1000*base noise value (ADUs) */
361
362        File.seek(IFD[34710][2][0]+256+128)
363        self.barcode = re.sub(r'\x00','',string.join(st.unpack(byteOrd+16*'c',File.read(16)),''))
364        self.barcodeAngle = st.unpack(byteOrd+'I',File.read(4))[0]
365        self.barcodeStatus = st.unpack(byteOrd+'I',File.read(4))[0]
366
367        File.seek(IFD[34710][2][0]+256+128+256)
368        self.xtalToDetector = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*distance in millimeters */
369        self.beamX = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*x beam position (pixels) */
370        self.beamY = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*y beam position (pixels) */
371        self.integrationTime = st.unpack(byteOrd+'i',File.read(4))[0] #/* integration time in milliseconds */
372        self.exposureTime = st.unpack(byteOrd+'i',File.read(4))[0] #/* exposure time in milliseconds */
373        self.readoutTime = st.unpack(byteOrd+'i',File.read(4))[0] #/* readout time in milliseconds */
374        self.nreads = st.unpack(byteOrd+'i',File.read(4))[0] #/* number of readouts to get this image */
375        self.startTwotheta = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*two_theta angle */
376        self.startOmega = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*omega angle */
377        self.startChi = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*chi angle */
378        self.startKappa = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*kappa angle */
379        self.startPhi = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*phi angle */
380        self.startDelta = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*delta angle */
381        self.startGamma = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*gamma angle */
382        self.startXtalToDetector = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*distance in mm (dist in um)*/
383        self.endTwotheta = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*two_theta angle */
384        self.endOmega = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*omega angle */
385        self.endChi = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*chi angle */
386        self.endKappa = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*kappa angle */
387        self.endPhi = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*phi angle */
388        self.endDelta = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*delta angle */
389        self.endGamma = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*gamma angle */
390        self.endXtalToDetector = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*distance in mm (dist in um)*/
391        self.rotationAxis = st.unpack(byteOrd+'i',File.read(4))[0] #/* active rotation axis (index into above ie. 0=twotheta,1=omega...) */
392        self.rotationRange = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*rotation angle */
393        self.detectorRotx = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*rotation of detector around X */
394        self.detectorRoty = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*rotation of detector around Y */
395        self.detectorRotz = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*rotation of detector around Z */
396        self.totalDose = st.unpack(byteOrd+'i',File.read(4))[0] #/* Hz-sec (counts) integrated over full exposure */
397
398        File.seek(IFD[34710][2][0]+256+128+256+128)
399        self.detectorType = st.unpack(byteOrd+'i',File.read(4))[0] #/* detector type */
400        self.pixelsizeX = st.unpack(byteOrd+'i',File.read(4))[0] #/* pixel size (nanometers) */
401        self.pixelsizeY = st.unpack(byteOrd+'i',File.read(4))[0] #/* pixel size (nanometers) */
402        self.meanBias = st.unpack(byteOrd+'i',File.read(4))[0] #/* 1000*mean bias value */
403        self.photonsPer100adu = st.unpack(byteOrd+'i',File.read(4))[0] #/* photons / 100 ADUs */
404        self.measuredBias = st.unpack(byteOrd+'i'*MAXIMAGES,File.read(4*MAXIMAGES)) # /* 1000*mean bias value for each image*/
405        self.measuredTemperature = st.unpack(byteOrd+'i'*MAXIMAGES,File.read(4*MAXIMAGES)) # /* Temperature of each detector in milliKelvins */
406        self.measuredPressure = st.unpack(byteOrd+'i'*MAXIMAGES,File.read(4*MAXIMAGES)) # /* Pressure of each chamber in microTorr */
407
408        File.seek(IFD[34710][2][0]+256+128+256+128+128)
409        self.sourceType = st.unpack(byteOrd+'i',File.read(4))[0] #/* (code) - target, synch. etc */
410        self.sourceDx = st.unpack(byteOrd+'i',File.read(4))[0] #/* Optics param. - (size microns) */
411        self.sourceDy = st.unpack(byteOrd+'i',File.read(4))[0] #/* Optics param. - (size microns) */
412        self.sourceWavelength = st.unpack(byteOrd+'i',File.read(4))[0] #/* wavelength (femtoMeters) */
413        self.sourcePower = st.unpack(byteOrd+'i',File.read(4))[0] #/* (Watts) */
414        self.sourceVoltage = st.unpack(byteOrd+'i',File.read(4))[0] #/* (Volts) */
415        self.sourceCurrent = st.unpack(byteOrd+'i',File.read(4))[0] #/* (microAmps) */
416        self.sourceBias = st.unpack(byteOrd+'i',File.read(4))[0] #/* (Volts) */
417        self.sourcePolarizationX = st.unpack(byteOrd+'i',File.read(4))[0] #/* () */
418        self.sourcePolarizationY = st.unpack(byteOrd+'i',File.read(4))[0] #/* () */
419        self.sourceIntensity0 = st.unpack(byteOrd+'i',File.read(4))[0] #/* (arbitrary units) */
420        self.sourceIntensity1 = st.unpack(byteOrd+'i',File.read(4))[0] #/* (arbitrary units) */
421
422        File.seek(IFD[34710][2][0]+256+128+256+128+128+14*4)
423        self.opticsType = st.unpack(byteOrd+'i',File.read(4))[0] #/* Optics type (code)*/
424        self.opticsDx = st.unpack(byteOrd+'i',File.read(4))[0] #/* Optics param. - (size microns) */
425        self.opticsDy = st.unpack(byteOrd+'i',File.read(4))[0] #/* Optics param. - (size microns) */
426        self.opticsWavelength = st.unpack(byteOrd+'i',File.read(4))[0] #/* Optics param. - (size microns) */
427        self.opticsDispersion = st.unpack(byteOrd+'i',File.read(4))[0] #/* Optics param. - (*10E6) */
428        self.opticsCrossfireX = st.unpack(byteOrd+'i',File.read(4))[0] #/* Optics param. - (microRadians) */
429        self.opticsCrossfireY = st.unpack(byteOrd+'i',File.read(4))[0] #/* Optics param. - (microRadians) */
430        self.opticsAngle = st.unpack(byteOrd+'i',File.read(4))[0] #/* Optics param. - (monoch. 2theta - microradians) */
431        self.opticsPolarizationX = st.unpack(byteOrd+'i',File.read(4))[0] #/* () */
432        self.opticsPolarizationY = st.unpack(byteOrd+'i',File.read(4))[0] #/* () */
433
434        File.seek(IFD[34710][2][0]+256+128+256+128+128+128)
435        self.filetitle = re.sub(r'\x00','',string.join(st.unpack(byteOrd+128*'c',File.read(128)),''))
436        self.filepath = re.sub(r'\x00','',string.join(st.unpack(byteOrd+'c'*128,File.read(128)),'')) #/* path name for data file*/
437        self.filename = re.sub(r'\x00','',string.join(st.unpack(byteOrd+'c'*64,File.read(64)),'')) #/* name of data file*/
438        self.acquireTimestamp = re.sub(r'\x00','',string.join(st.unpack(byteOrd+'c'*32,File.read(32)),'')) #/* date and time of acquisition*/
439        self.headerTimestamp = re.sub(r'\x00','',string.join(st.unpack(byteOrd+'c'*32,File.read(32)),'')) #/* date and time of header update*/
440        self.saveTimestamp = re.sub(r'\x00','',string.join(st.unpack(byteOrd+'c'*32,File.read(32)),'')) #/* date and time file saved */
441        self.fileComment = re.sub(r'\x00','',string.join(st.unpack(byteOrd+'c'*512,File.read(512)),'')) #/* comments  - can be used as desired */
442        self.datasetComment = re.sub(r'\x00','',string.join(st.unpack(byteOrd+'c'*512,File.read(512)),'')) #/* comments  - can be used as desired */
443
444        self.userData = re.sub(r'\x00','',string.join(st.unpack(byteOrd+'c'*512,File.read(512)),''))
445
446        File.seek(4096)
447        self.image = ar.array(self.arrayTypeCode,File.read(self.byteDepth*self.TIFFsizeX*self.TIFFsizeY))
448        # reverse the array so if can have the same view as is read in marccd
449        # also switch the view direction
450        self.image.reverse()
451        self.viewDirection = abs(self.viewDirection - 1)
452
453    def outputHead(self):
454        myHead = []
455        for curAttr in dir(self):
456            if ( curAttr != '__doc__' and \
457                 curAttr != '__init__' and \
458                 curAttr != '__module__' and \
459                 curAttr != 'outputHead' and \
460                 curAttr != 'image' ):
461                myHead.append(" %s = %s" % (curAttr,getattr(self,curAttr)))
462        return myHead
Note: See TracBrowser for help on using the repository browser.