source: sasview/DataLoader/readers/abs_reader.py @ d3966c2

ESS_GUIESS_GUI_DocsESS_GUI_batch_fittingESS_GUI_bumps_abstractionESS_GUI_iss1116ESS_GUI_iss879ESS_GUI_iss959ESS_GUI_openclESS_GUI_orderingESS_GUI_sync_sascalccostrafo411magnetic_scattrelease-4.1.1release-4.1.2release-4.2.2release_4.0.1ticket-1009ticket-1094-headlessticket-1242-2d-resolutionticket-1243ticket-1249ticket885unittest-saveload
Last change on this file since d3966c2 was 148ad64, checked in by Jae Cho <jhjcho@…>, 15 years ago

Added a flexibility to read whole different formats of abs files (w/wo header).

  • Property mode set to 100644
File size: 12.1 KB
Line 
1"""
2This software was developed by the University of Tennessee as part of the
3Distributed Data Analysis of Neutron Scattering Experiments (DANSE)
4project funded by the US National Science Foundation.
5
6See the license text in license.txt
7
8copyright 2008, University of Tennessee
9"""
10
11import numpy
12import os
13from DataLoader.data_info import Data1D, Detector
14
15has_converter = True
16try:
17    from data_util.nxsunit import Converter
18except:
19    has_converter = False
20   
21class Reader:
22    """
23        Class to load IGOR reduced .ABS files
24    """
25    ## File type
26    type = ["IGOR 1D files (*.abs)|*.abs"]
27    ## List of allowed extensions
28    ext=['.abs', '.ABS'] 
29   
30    def read(self, path):
31        """
32            Load data file
33           
34            @param path: file path
35            @return: Data1D object, or None
36            @raise RuntimeError: when the file can't be opened
37            @raise ValueError: when the length of the data vectors are inconsistent
38        """
39        if os.path.isfile(path):
40            basename  = os.path.basename(path)
41            root, extension = os.path.splitext(basename)
42            if extension.lower() in self.ext:
43                try:
44                    input_f =  open(path,'r')
45                except :
46                    raise  RuntimeError, "abs_reader: cannot open %s" % path
47                buff = input_f.read()
48                lines = buff.split('\n')
49                x  = numpy.zeros(0)
50                y  = numpy.zeros(0)
51                dy = numpy.zeros(0)
52                dx = numpy.zeros(0)
53                output = Data1D(x, y, dy=dy, dx=dx)
54                detector = Detector()
55                output.detector.append(detector)
56                output.filename = basename
57               
58                is_info = False
59                is_center = False
60                is_data_started = False
61                right_line_is = -2
62                line_n = 0
63                col = 0
64               
65                data_conv_q = None
66                data_conv_i = None
67               
68                if has_converter == True and output.x_unit != '1/A':
69                    data_conv_q = Converter('1/A')
70                    # Test it
71                    data_conv_q(1.0, output.x_unit)
72                   
73                if has_converter == True and output.y_unit != '1/cm':
74                    data_conv_i = Converter('1/cm')
75                    # Test it
76                    data_conv_i(1.0, output.y_unit)
77               
78                for line in lines:
79                    #print "line",line
80                    # Information line 1
81                    if is_info==True:
82                        is_info = False
83                        line_toks = line.split()
84                       
85                        # Wavelength in Angstrom
86                        try:
87                            value = float(line_toks[1])
88                            if has_converter==True and output.source.wavelength_unit != 'A':
89                                conv = Converter('A')
90                                output.source.wavelength = conv(value, units=output.source.wavelength_unit)
91                            else:
92                                output.source.wavelength = value
93                        except:
94                            pass
95                            #raise ValueError,"IgorReader: can't read this file, missing wavelength"
96                       
97                        # Distance in meters
98                        try:
99                            value = float(line_toks[3])
100                            if has_converter==True and detector.distance_unit != 'm':
101                                conv = Converter('m')
102                                detector.distance = conv(value, units=detector.distance_unit)
103                            else:
104                                detector.distance = value
105                        except:
106                            pass
107                            #raise ValueError,"IgorReader: can't read this file, missing distance"
108                       
109                        # Transmission
110                        try:
111                            output.sample.transmission = float(line_toks[4])
112                        except:
113                            # Transmission is not a mandatory entry
114                            pass
115                   
116                        # Thickness in mm
117                        try:
118                            value = float(line_toks[5])
119                            if has_converter==True and output.sample.thickness_unit != 'cm':
120                                conv = Converter('cm')
121                                output.sample.thickness = conv(value, units=output.sample.thickness_unit)
122                            else:
123                                output.sample.thickness = value
124                        except:
125                            # Thickness is not a mandatory entry
126                            pass
127                       
128                        #MON CNT   LAMBDA   DET ANG   DET DIST   TRANS   THICK   AVE   STEP
129                        if line.count("LAMBDA")>0:
130                            is_info = True
131                           
132                        # Find center info line
133                        if is_center==True:
134                            is_center = False               
135                            line_toks = line.split()
136                            # Center in bin number
137                            center_x = float(line_toks[0])
138                            center_y = float(line_toks[1])
139                           
140                            # Bin size
141                            if has_converter==True and detector.pixel_size_unit != 'mm':
142                                conv = Converter('mm')
143                                detector.pixel_size.x = conv(5.0, units=detector.pixel_size_unit)
144                                detector.pixel_size.y = conv(5.0, units=detector.pixel_size_unit)
145                            else:
146                                detector.pixel_size.x = 5.0
147                                detector.pixel_size.y = 5.0
148                           
149                            # Store beam center in distance units
150                            # Det 640 x 640 mm
151                            if has_converter==True and detector.beam_center_unit != 'mm':
152                                conv = Converter('mm')
153                                detector.beam_center.x = conv(center_x*5.0, units=detector.beam_center_unit)
154                                detector.beam_center.y = conv(center_y*5.0, units=detector.beam_center_unit)
155                            else:
156                                detector.beam_center.x = center_x*5.0
157                                detector.beam_center.y = center_y*5.0
158                           
159                            # Detector type
160                            try:
161                                detector.name = line_toks[7]
162                            except:
163                                # Detector name is not a mandatory entry
164                                pass
165                       
166                        #BCENT(X,Y)   A1(mm)   A2(mm)   A1A2DIST(m)   DL/L   BSTOP(mm)   DET_TYP
167                        if line.count("BCENT")>0:
168                            is_center = True
169                       
170                    # Parse the data                   
171                    # Specify one line of data
172                    if len(lines)<2:
173                        colnum = 6
174                    else:
175                        colnum = len(line.split())
176                       
177                    #If # of row = # of data points
178                    if colnum == 0:
179                        rangeiter = 0
180                    #If # of row = 1
181                    else:
182                        rangeiter=numpy.ceil(len(line.split())/colnum)
183                       
184                    #If all data is in one line, chop the line by every 6 columns and read x, y, dy, dx data                         
185                    for col in range(0,rangeiter):
186                        #The 6 columns are | Q (1/A) | I(Q) (1/cm) | std. dev. I(Q) (1/cm) | sigmaQ | meanQ | ShadowFactor|
187                        #Check the file format whether or not  it read all header lines and if it has a header
188                        if line.count("The 6 columns")>0 or (output.source.wavelength==None):
189                            #if  it has a full header
190                            if line.count("The 6 columns")>0:
191                                right_line_is = line_n
192                            #If no header in the file
193                            else:
194                                right_line_is = 0 
195                            is_data_started = True
196                           
197                       
198                        # If on the of data, not header, read data
199                        if is_data_started==True and right_line_is >= 0: #and line_n > right_line_is
200                            #print "col",col
201                            toks = line.split()
202                            try: 
203                               
204                                if float(toks[col*6+0]) > 1:
205                                     continue
206                                else:
207                                    not_data_line = False
208                                   
209                                _x  = float(toks[col*6+0])
210                                _y  = float(toks[col*6+1]) 
211                                _dy = float(toks[col*6+2])
212                                _dx = float(toks[col*6+3])
213                               
214                               
215                                if data_conv_q is not None:
216                                    _x = data_conv_q(_x, units=output.x_unit)
217                                    _dx = data_conv_i(_dx, units=output.x_unit)
218                                   
219                                if data_conv_i is not None:
220                                    _y = data_conv_i(_y, units=output.y_unit)
221                                    _dy = data_conv_i(_dy, units=output.y_unit)
222
223                                x  =numpy.append(x,   _x) 
224                                y  = numpy.append(y,   _y)
225                                dy  = numpy.append(dy, _dy)
226                                dx  = numpy.append(dx, _dx)
227
228                            except:
229                                # Could not read this data line. If we are here
230                                # it is because we are in the data section. Just
231                                # skip it.
232                                pass
233                           
234                        line_n = line_n +1
235                # Sanity check
236                if not len(y) == len(dy):
237                    raise ValueError, "abs_reader: y and dy have different length"
238                if not len(x) == len(dx):
239                    raise ValueError, "abs_reader: x and dx have different length"
240
241                # If the data length is zero, consider this as
242                # though we were not able to read the file.
243                if len(x)==0:
244                    raise ValueError, "ascii_reader: could not load file"
245               
246                output.x = x
247                output.y = y
248                output.dy = dy
249                output.dx = dx
250                if data_conv_q is not None:
251                    output.xaxis("\\rm{Q}", output.x_unit)
252                else:
253                    output.xaxis("\\rm{Q}", 'A^{-1}')
254                if data_conv_i is not None:
255                    output.yaxis("\\{I(Q)}", output.y_unit)
256                else:
257                    output.yaxis("\\rm{I(Q)}","cm^{-1}")
258                #print " x,y,dx,dy", output.x,output.y,output.dy,output.dx
259                return output
260        else:
261            raise RuntimeError, "%s is not a file" % path
262        return None
263   
264if __name__ == "__main__": 
265    reader = Reader()
266    #print reader.read("../test/jan08002.ABS")
267   
268   
269           
Note: See TracBrowser for help on using the repository browser.