source: sans/Dev/trunk/NCNR_User_Procedures/Reduction/SANS/ANSTO_DataReadWrite.ipf @ 575

Last change on this file since 575 was 575, checked in by srkline, 13 years ago

Added ANSTO files to the repository for SANS reduction

Changed #include files for each facility to have a #define SYMBOL at the top to allow small facility-specific changes in the main body of the code that are controlled with compiler directives

File size: 43.6 KB
Line 
1#pragma rtGlobals=1             // Use modern global access method.
2#pragma version=5.0
3#pragma IgorVersion = 6.1
4
5//**************************
6//
7// Vers. 1.2 092101
8// Vers. 5.0 29MAR07 - branched from main reduction to split out facility
9//                     specific calls
10//
11// functions for reading raw data files from the VAX
12// - RAW data files are read into the RAW folder - integer data from the detector
13//   is decompressed and given the proper orientation
14// - header information is placed into real,integer, or text waves in the order they appear
15//   in the file header
16//
17// Work data (DIV File) is read into the DIV folder
18//
19//*****************************
20
21//simple, main entry procedure that will load a RAW sans data file (not a work file)
22//into the RAW dataFolder. It is up to the calling procedure to display the file
23//
24// called by MainPanel.ipf and ProtocolAsPanel.ipf
25//
26Function LoadRawSANSData(msgStr)
27        String msgStr
28
29        String filename=""
30
31        //each routine is responsible for checking the current (displayed) data folder
32        //selecting it, and returning to root when done
33        PathInfo/S catPathName          //should set the next dialog to the proper path...
34        //get the filename, then read it in
35        filename = PromptForPath(msgStr)                //in SANS_Utils.ipf
36        //check for cancel from dialog
37        if(strlen(filename)==0)
38                //user cancelled, abort
39                SetDataFolder root:
40                DoAlert 0, "No file selected, action aborted"
41                return(1)
42        Endif
43
44        ReadHeaderAndData(filename)     //this is the full Path+file
45       
46        Return(0)
47End
48
49
50//function that does the guts of reading the binary data file
51//fname is the full path:name;vers required to open the file
52//
53// The final root:Packages:NIST:RAW:data wave is the real
54//neutron counts and can be directly operated on
55//
56// header information is put into three waves: integersRead, realsRead, and textRead
57// logicals in the header are currently skipped, since they are no use in the
58// data reduction process.
59//
60// The output is the three R/T/I waves that are filled at least with minimal values
61// and the detector data loaded into an array named "data"
62//
63// see documentation for the expected information in each element of the R/T/I waves
64// and the minimum set of information. These waves can be increased in length so that
65// more information can be accessed as needed (propagating changes...)
66//
67// called by multiple .ipfs (when the file name is known)
68//
69//
70// THIS FUNCTION DOES NOT NEED TO BE MODIFIED. ONLY THE DATA ACCESSORS NEED TO BE CONSTRUCTED
71//
72Function ReadHeaderAndData(fname)
73        String fname
74        //this function is for reading in RAW data only, so it will always put data in RAW folder
75        String curPath = "root:Packages:NIST:RAW"
76        SetDataFolder curPath           //use the full path, so it will always work
77        variable/g root:Packages:NIST:RAW:gIsLogScale = 0               //initial state is linear, keep this in RAW folder
78       
79        Variable refNum,integer,realval
80        String sansfname,textstr
81       
82        Make/D/O/N=23 $"root:Packages:NIST:RAW:IntegersRead"
83        Make/D/O/N=52 $"root:Packages:NIST:RAW:RealsRead"
84        Make/O/T/N=11 $"root:Packages:NIST:RAW:TextRead"
85        Make/O/N=7 $"root:Packages:NIST:RAW:LogicalsRead"
86
87        Wave intw=$"root:Packages:NIST:RAW:IntegersRead"
88        Wave realw=$"root:Packages:NIST:RAW:RealsRead"
89        Wave/T textw=$"root:Packages:NIST:RAW:TextRead"
90        Wave logw=$"root:Packages:NIST:RAW:LogicalsRead"
91       
92        // FILL IN 3 ARRAYS WITH HEADER INFORMATION FOR LATER USE
93        // THESE ARE JUST THE MINIMALLY NECESSARY VALUES
94       
95        // filename as stored in the file header
96        textw[0]= fname
97       
98        // date and time of collection
99        textw[1]= getFileCreationDate(fname)
100       
101        // run type identifier (this is a reader for RAW data)
102        textw[2]= "RAW"
103       
104        // user account identifier (currently used only for NCNR-specific operations)
105        textw[3]= ""
106
107        // sample label
108        textw[6]= getSampleLabel(fname)
109       
110        // identifier of detector type, useful for setting detector constants
111        //(currently used only for NCNR-specific operations)
112        textw[9]= ""
113
114        //total counting time in seconds
115        intw[2] = getCountTime(fname)
116       
117//      realw[1] = 0
118//      realw[6] = 0
119//      realw[7] = 0
120//      realw[8] = 0
121//      realw[9] = 0
122//      realw[19] = 0
123//      realw[22] = 0
124
125        // total monitor count
126        realw[0] = getMonitorCount(fname)
127       
128        // total detector count
129        realw[2] = getDetCount(fname)
130       
131        // attenuator number (NCNR-specific, your stub returns 0)
132        // may also be used to hold attenuator transmission (< 1)
133        realw[3] = getAttenNumber(fname)
134       
135        // sample transmission
136        realw[4] = getSampleTrans(fname)
137       
138        //sample thickness (cm)
139        realw[5] = getSampleThickness(fname)
140       
141        // following 6 values are for non-linear spatial corrections to a detector (RC timing)
142        // these values are set for a detctor that has a linear correspondence between
143        // pixel number and real-space distance
144        // 10 and 13 are the X and Y pixel dimensions, respectively (in mm!)
145        //(11,12 and 13,14 are set to values for a linear response, as from a new Ordela detector)
146        realw[10] = getDetectorPixelXSize(fname)
147        realw[11] = 10000
148        realw[12] = 0
149        realw[13] = getDetectorPixelYSize(fname)
150        realw[14] = 10000
151        realw[15] = 0
152       
153        // beam center X,Y on the detector (in units of pixel coordinates (1,N))
154        realw[16] = getBeamXPos(fname)
155        realw[17] = getBeamYPos(fname)
156       
157        // sample to detector distance (meters)
158        realw[18] = getSDD(fname)
159
160        // detector physical width (right now assumes square...) (in cm)
161        //realw[20] = 65
162        realw[20] = getPhysicalWidth(fname)
163       
164        // beam stop diameter (assumes circular) (in mm)
165        realw[21] = getBSDiameter(fname)
166       
167        // source aperture diameter (mm)
168        realw[23] = getSourceApertureDiam(fname)
169       
170        // sample aperture diameter (mm)
171        realw[24] = getSampleApertureDiam(fname)
172       
173        // source aperture to sample aperture distance
174        realw[25] = getSourceToSampleDist(fname)
175       
176        // wavelength (A)
177        realw[26] = getWavelength(fname)
178       
179        // wavelength spread (FWHM)
180        realw[27] = getWavelengthSpread(fname)
181       
182        // beam stop X-position (motor reading, approximate cm from zero position)
183        // currently NCNR-specific use to identify transmission measurements
184        // you return 0
185        realw[37] = 0
186
187// the actual data array, dimensions are set as globals in
188// InitFacilityGlobals()
189        NVAR XPix = root:myGlobals:gNPixelsX
190        NVAR YPix = root:myGlobals:gNPixelsX
191       
192        Make/D/O/N=(XPix,YPix) $"root:Packages:NIST:RAW:data"
193        WAVE data=$"root:Packages:NIST:RAW:data"
194
195        // fill the data array with the detector values
196        getDetectorData(fname,data)
197       
198        //keep a string with the filename in the RAW folder
199        String/G root:Packages:NIST:RAW:fileList = textw[0]
200       
201        Return 0
202
203End
204
205//****************
206//main entry procedure for reading a "WORK.DIV" file
207//displays a quick image of the  file, to check that it's correct
208//data is deposited in root:Packages:NIST:DIV data folder
209//
210// local, just for testing
211//
212Proc ReadWork_DIV()
213       
214        String fname = PromptForPath("Select detector sensitivity file")
215        ReadHeaderAndWork("DIV",fname)          //puts what is read in work.div
216       
217        String waveStr = "root:Packages:NIST:DIV:data"
218        NewImage/F/K=1/S=2 $waveStr
219        ModifyImage '' ctab= {*,*,YellowHot,0}
220       
221        String/G root:Packages:NIST:DIV:fileList = "WORK.DIV"
222       
223        SetDataFolder root:             //(redundant)
224End
225
226
227
228// Detector sensitivity files have the same header structure as RAW SANS data
229// as NCNR, just with a different data array (real, rather than integer data)
230//
231// So for your facility, make this reader specific to the format of whatever
232// file you use for a pixel-by-pixel division of the raw detector data
233// to correct for non-uniform sensitivities of the detector. This is typically a
234// measurement of water, plexiglas, or another uniform scattering sample.
235//
236// The data must be normalized to a mean value of 1
237//
238// called from ProtocolAsPanel.ipf
239//
240// type is "DIV" on input
241Function ReadHeaderAndWork(type,fname)
242        String type,fname
243       
244        //type is the desired folder to read the workfile to
245        //this data will NOT be automatically displayed
246        // gDataDisplayType is unchanged
247
248        String cur_folder = type
249        String curPath = "root:Packages:NIST:"+cur_folder
250        SetDataFolder curPath           //use the full path, so it will always work
251       
252        Variable refNum,integer,realval
253        String sansfname,textstr
254        Variable/G $(curPath + ":gIsLogScale") = 0              //initial state is linear, keep this in DIV folder
255       
256        Make/O/D/N=23 $(curPath + ":IntegersRead")
257        Make/O/D/N=52 $(curPath + ":RealsRead")
258        Make/O/T/N=11 $(curPath + ":TextRead")
259       
260        WAVE intw=$(curPath + ":IntegersRead")
261        WAVE realw=$(curPath + ":RealsRead")
262        WAVE/T textw=$(curPath + ":TextRead")
263       
264        // the actual data array, dimensions are set as globals in
265        // InitFacilityGlobals()
266        NVAR XPix = root:myGlobals:gNPixelsX
267        NVAR YPix = root:myGlobals:gNPixelsX
268
269        Make/O/D/N=(XPix,YPix) $(curPath + ":data")
270        WAVE data = $(curPath + ":data")
271       
272        // (1)
273        // fill in your reader for the header here so that intw, realw, and textW are filled in
274        // ? possibly a duplication of the raw data reader
275               
276        //(2)
277        // then fill in a reader for the data array that will DIVIDE your data
278        // to get the corrected values.
279        String dfName=""
280        variable err
281        err = hdfRead(fname, dfName)
282        Wave tempData = $dfName+":data:div"
283        data = tempData
284
285        //keep a string with the filename in the DIV folder
286        String/G $(curPath + ":fileList") = textw[0]
287       
288        //return the data folder to root
289        SetDataFolder root:
290       
291        Return(0)
292End
293
294Function WriteHeaderAndWork(type)
295        String type
296       
297        // your writer here
298        NVAR XPix = root:myGlobals:gNPixelsX
299        NVAR YPix = root:myGlobals:gNPixelsX   
300       
301        Wave wData=$("root:Packages:NIST:"+type+":data")
302       
303//      Variable refnum,ii=0,hdrBytes=516,a,b,offset
304        String fname=""
305//      Duplicate/O wData,tempData
306       
307        //changed for Quokka
308//      Redimension/S/N=(XPix*YPix) tempData
309//      tempData *= 4
310       
311        PathInfo/S catPathName
312        fname = DoSaveFileDialog("Save data as")          //won't actually open the file
313        If(cmpstr(fname,"")==0)
314                //user cancel, don't write out a file
315          Close/A
316          Abort "no data file was written"
317        Endif
318       
319        variable fileID
320        HDF5CreateFile /O fileID as fname
321       
322        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
323        //Make /N=(1,1) wTransmission
324        String groupName = "/data"
325        String varName = "div"
326        // your code returning value
327        variable err
328        err = hdfWrite(fname, groupName, varName, wData)
329
330        // KillWaves wData, tempData
331        return(0)
332End
333
334
335
336/////   ASC FORMAT READER  //////
337/////   FOR WORKFILE MATH PANEL //////
338//
339//function to read in the ASC output of SANS reduction
340// currently the file has 20 header lines, followed by a single column
341// of 16384 values, Data is written by row, starting with Y=1 and X=(1->128)
342//
343//returns 0 if read was ok
344//returns 1 if there was an error
345//
346// called by WorkFileUtils.ipf
347//
348//
349// If the ASC data was generated by the NCNR data writer, then
350// NOTHING NEEDS TO BE CHANGED HERE
351//
352Function ReadASCData(fname,destPath)
353        String fname, destPath
354        //this function is for reading in ASCII data so put data in user-specified folder
355        SetDataFolder "root:Packages:NIST:"+destPath
356
357        NVAR pixelsX = root:myGlobals:gNPixelsX
358        NVAR pixelsY = root:myGlobals:gNPixelsY
359        Variable refNum=0,ii,p1,p2,tot,num=pixelsX,numHdrLines=20
360        String str=""
361        //data is initially linear scale
362        Variable/G :gIsLogScale=0
363        Make/O/T/N=(numHdrLines) hdrLines
364        Make/O/D/N=(pixelsX*pixelsY) data                       //,linear_data
365       
366        //full filename and path is now passed in...
367        //actually open the file
368//      SetDataFolder destPath
369        Open/R/Z refNum as fname                // /Z flag means I must handle open errors
370        if(refnum==0)           //FNF error, get out
371                DoAlert 0,"Could not find file: "+fname
372                Close/A
373                SetDataFolder root:
374                return(1)
375        endif
376        if(V_flag!=0)
377                DoAlert 0,"File open error: V_flag="+num2Str(V_Flag)
378                Close/A
379                SetDataFolder root:
380                return(1)
381        Endif
382        //
383        for(ii=0;ii<numHdrLines;ii+=1)          //read (or skip) 18 header lines
384                FReadLine refnum,str
385                hdrLines[ii]=str
386        endfor
387        //     
388        Close refnum
389       
390//      SetDataFolder destPath
391        LoadWave/Q/G/D/N=temp fName
392        Wave/Z temp0=temp0
393        data=temp0
394        Redimension/N=(pixelsX,pixelsY) data            //,linear_data
395       
396        //linear_data = data
397       
398        KillWaves/Z temp0
399       
400        //return the data folder to root
401        SetDataFolder root:
402       
403        Return(0)
404End
405
406// fills the "default" fake header so that the SANS Reduction machinery does not have to be altered
407// pay attention to what is/not to be trusted due to "fake" information.
408// uses what it can from the header lines from the ASC file (hdrLines wave)
409//
410// destFolder is of the form "myGlobals:WorkMath:AAA"
411//
412//
413// called by WorkFileUtils.ipf
414//
415// If the ASC data was generated by the NCNR data writer, then
416// NOTHING NEEDS TO BE CHANGED HERE
417//
418Function FillFakeHeader_ASC(destFolder)
419        String destFolder
420        Make/O/D/N=23 $("root:Packages:NIST:"+destFolder+":IntegersRead")
421        Make/O/D/N=52 $("root:Packages:NIST:"+destFolder+":RealsRead")
422        Make/O/T/N=11 $("root:Packages:NIST:"+destFolder+":TextRead")
423       
424        Wave intw=$("root:Packages:NIST:"+destFolder+":IntegersRead")
425        Wave realw=$("root:Packages:NIST:"+destFolder+":RealsRead")
426        Wave/T textw=$("root:Packages:NIST:"+destFolder+":TextRead")
427       
428        //Put in appropriate "fake" values
429        //parse values as needed from headerLines
430        Wave/T hdr=$("root:Packages:NIST:"+destFolder+":hdrLines")
431        Variable monCt,lam,offset,sdd,trans,thick
432        Variable xCtr,yCtr,a1,a2,a1a2Dist,dlam,bsDiam
433        String detTyp=""
434        String tempStr="",formatStr="",junkStr=""
435        formatStr = "%g %g %g %g %g %g"
436        tempStr=hdr[3]
437        sscanf tempStr, formatStr, monCt,lam,offset,sdd,trans,thick
438//      Print monCt,lam,offset,sdd,trans,thick,avStr,step
439        formatStr = "%g %g %g %g %g %g %g %s"
440        tempStr=hdr[5]
441        sscanf tempStr,formatStr,xCtr,yCtr,a1,a2,a1a2Dist,dlam,bsDiam,detTyp
442//      Print xCtr,yCtr,a1,a2,a1a2Dist,dlam,bsDiam,detTyp
443       
444        realw[16]=xCtr          //xCtr(pixels)
445        realw[17]=yCtr  //yCtr (pixels)
446        realw[18]=sdd           //SDD (m)
447        realw[26]=lam           //wavelength (A)
448        //
449        // necessary values
450        realw[10]=5                     //detector calibration constants, needed for averaging
451        realw[11]=10000
452        realw[12]=0
453        realw[13]=5
454        realw[14]=10000
455        realw[15]=0
456        //
457        // used in the resolution calculation, ONLY here to keep the routine from crashing
458        realw[20]=65            //det size
459        realw[27]=dlam  //delta lambda
460        realw[21]=bsDiam        //BS size
461        realw[23]=a1            //A1
462        realw[24]=a2    //A2
463        realw[25]=a1a2Dist      //A1A2 distance
464        realw[4]=trans          //trans
465        realw[3]=0              //atten
466        realw[5]=thick          //thick
467        //
468        //
469        realw[0]=monCt          //def mon cts
470
471        // fake values to get valid deadtime and detector constants
472        //
473        textw[9]=detTyp+"  "            //6 characters 4+2 spaces
474        textw[3]="[NGxSANS00]"  //11 chars, NGx will return default values for atten trans, deadtime...
475       
476        //set the string values
477        formatStr="FILE: %s CREATED: %s"
478        sscanf hdr[0],formatStr,tempStr,junkStr
479//      Print tempStr
480//      Print junkStr
481        String/G $("root:Packages:NIST:"+destFolder+":fileList") = tempStr
482        textw[0] = tempStr              //filename
483        textw[1] = junkStr              //run date-time
484       
485        //file label = hdr[1]
486        tempStr = hdr[1]
487        tempStr = tempStr[0,strlen(tempStr)-2]          //clean off the last LF
488//      Print tempStr
489        textW[6] = tempStr      //sample label
490       
491        return(0)
492End
493
494
495///////// ACCESSORS FOR WRITING DATA TO HEADER  /////////
496/////
497
498// Write* routines all must:
499// (1) open file "fname". fname is a full file path and name to the file on disk
500// (2) write the specified value to the header at the correct location in the file
501// (3) close the file
502
503
504
505//whole transmission is NCNR-specific right now
506// leave this stub empty
507Function WriteWholeTransToHeader(fname,wholeTrans)
508        String fname
509        Variable wholeTrans
510       
511        String groupName = "/entry1/reduce"
512        variable err
513       
514        Wave wCounts
515        Make /N=(1,1) wWholeTrans
516               
517        wWholeTrans[0] = wholeTrans
518       
519        String varName = "wholeTransmission"   
520        err = hdfWrite(fname, groupName, varName,wWholeTrans)
521
522        KillWaves wWholeTrans
523       
524        //err not handled here
525        return(0)       
526End
527
528//box sum counts is a real value
529// used for transmission calculation module
530Function WriteBoxCountsToHeader(fname,counts)
531        String fname
532        Variable counts
533       
534        // do nothing if not using NCNR Transmission module
535       
536        String groupName = "/entry1/reduce"
537        variable err
538       
539        Wave wCounts
540        Make /N=(1,1) wCounts
541               
542        wCounts[0] = counts
543       
544        String varName = "boxCounts"   
545        err = hdfWrite(fname, groupName, varName,wCounts)
546
547        KillWaves wCounts
548       
549        //err not handled here
550        return(0)       
551End
552
553//beam stop X-position
554// used for transmission module to manually tag transmission files
555Function WriteBSXPosToHeader(fname,xpos)
556        String fname
557        Variable xpos
558       
559        // do nothing if not using NCNR Transmission module
560       
561        return(0)
562End
563
564
565
566
567
568//attenuator number (not its transmission)
569// if your beam attenuation is indexed in some way, use that number here
570// if not, write a 1 to the file here as a default
571//
572Function WriteAttenNumberToHeader(fname,num)
573        String fname
574        Variable num
575       
576        // your code here, default of 1
577       
578        return(0)
579End
580
581// total monitor count during data collection
582Function WriteMonitorCountToHeader(fname,num)
583        String fname
584        Variable num
585       
586        // your code here
587       
588        return(0)
589End
590
591//total detector count
592Function WriteDetectorCountToHeader(fname,num)
593        String fname
594        Variable num
595       
596        // your code here
597       
598        return(0)
599End
600
601//transmission detector count
602// (currently unused in data reduction)
603Function WriteTransDetCountToHeader(fname,num)
604        String fname
605        Variable num
606       
607        // do nothing for now
608       
609        return(0)
610End
611
612
613
614//temperature of the sample (C)
615Function WriteTemperatureToHeader(fname,num)
616        String fname
617        Variable num
618       
619        //  your code here
620       
621        return(0)
622End
623
624//magnetic field (Oe)
625Function WriteMagnFieldToHeader(fname,num)
626        String fname
627        Variable num
628       
629        // your code here
630       
631        return(0)
632End
633
634//lateral detector offset (centimeters)
635Function WriteDetectorOffsetToHeader(fname,num)
636        String fname
637        Variable num
638       
639        //your code here
640       
641        return(0)
642End
643
644
645
646
647// physical dimension of detector x-pixel (mm)
648Function WriteDetPixelXToHeader(fname,num)
649        String fname
650        Variable num
651       
652        //your code here
653       
654        return(0)
655end
656
657// physical dimension of detector y-pixel (mm)
658Function WriteDetPixelYToHeader(fname,num)
659        String fname
660        Variable num
661       
662        //your code here
663       
664        return(0)
665end
666
667// sample label string
668Function WriteSamLabelToHeader(fname,str)
669        String fname,str
670       
671        // your code here
672
673        return(0)
674End
675
676// total counting time (seconds)
677Function WriteCountTimeToHeader(fname,num)
678        String fname
679        Variable num
680       
681        // your code here
682       
683        return(0)
684End
685
686
687
688//////// ACCESSORS FOR READING DATA FROM THE HEADER  //////////////
689//
690// read specific bits of information from the header
691// each of these operations MUST take care of open/close on their own
692//
693// fname is the full path and filname to the file on disk
694// return values are either strings or real values as appropriate
695//
696//////
697
698
699// function that reads in the 2D detector data and fills the array
700// data[nx][ny] with the data values
701// fname is the full name and path to the data file for opening and closing
702//
703//
704Function getDetectorData(fname,data)
705        String fname
706        Wave data
707        NVAR XPix = root:myGlobals:gNPixelsX
708       
709        // your reader here
710        variable err
711        string dfName = ""
712        err = hdfRead(fname, dfName)
713        if(err)
714                return 0
715        endif
716
717        Wave hmm_xy = $(dfName+":entry1:data:hmm_xy")
718       
719        //redimension /I /N = (dimsize(hmm_xy, 2), dimsize(hmm_xy, 1)), data
720        //nha. Count arrays need to be floating point, since the data will be divided, normalised etc.
721        redimension /N = (dimsize(hmm_xy, 2), dimsize(hmm_xy, 1)), data
722        data[][] = hmm_xy[0][q][p]
723       
724        //nha workaround. for wrongly dimensioned Quokka data 191x192
725        variable x_dim = dimsize(data,0)
726        if (x_dim!=XPix)
727                //redimension to add an extra row(s) to the data
728                redimension /I /N = (XPix,-1) data
729                //copy row 190 to row 191
730                data[191][] = data[190][q]
731        endif   
732        // end workaround
733               
734        KillWaves hmm_xy
735       
736       
737        return(0)
738End
739
740// file suffix (NCNR data file name specific)
741// return null string
742Function/S getSuffix(fname)
743        String fname
744       
745        return("")
746End
747
748// associated file suffix (for transmission)
749// NCNR Transmission calculation specific
750// return null string
751Function/S getAssociatedFileSuffix(fname)
752        String fname
753       
754        return("")
755End
756
757// sample label
758Function/S getSampleLabel(fname)
759        String fname
760        String str
761       
762        // your code, returning str
763        variable err
764        string dfName = ""
765        err = hdfRead(fname, dfName)
766        //err not handled here
767       
768        Wave/T wSampleName = $dfname+":entry1:sample:name"
769        str = wSampleName[0]
770        KillWaves wSampleName
771       
772        return(str)
773End
774
775// file creation date
776Function/S getFileCreationDate(fname)
777        String fname
778        String str
779       
780        // your code, returning str
781        variable err
782        string dfName = ""
783        err = hdfRead(fname, dfName)
784        //err not handled here
785       
786        Wave/T wStartTime = $dfName+":entry1:start_time"
787        str = wStartTime[0]
788        KillWaves wStartTime
789       
790        return(str)
791End
792
793
794//monitor count
795Function getMonitorCount(fname)
796        String fname
797        Variable value
798       
799        // your code returning value
800        variable err
801        string dfName = ""
802        err = hdfRead(fname, dfName)
803        //err not handled here
804       
805        Wave wCounts = $dfName+":entry1:monitor:bm1_counts"
806        value = wCounts[0]
807        KillWaves wCounts
808       
809        return(value)
810end
811
812//saved monitor count
813// NCNR specific for pre-processed data, never used
814// return 0
815Function getSavMon(fname)
816        String fname
817       
818        Variable value
819       
820        // your code returning value
821        //??? to do. Is this required if 'never used'? nha
822       
823        return(0)
824end
825
826//total detector count
827Function getDetCount(fname)
828        String fname
829        Variable value
830       
831        // your code returning value
832        variable err
833        string dfName = ""
834        err = hdfRead(fname, dfName)
835        //err not handled here
836
837        Wave wCounts = $(dfName+":entry1:data:total_counts")
838        value = wCounts[0]
839        KillWaves wCounts
840       
841        return(value)
842end
843
844//Attenuator number, return 1 if your attenuators are not
845// indexed by number
846Function getAttenNumber(fname)
847        String fname
848        Variable value
849        Variable att, err
850        string dfName = ""
851               
852        err = hdfRead(fname, dfName)
853        //err not handled here
854
855        Wave wAttrotdeg = $(dfName+":entry1:instrument:parameters:derived_parameters:AttRotDeg")
856        value = wAttrotdeg[0]
857        att = round(value)/30
858        KillWaves wAttrotdeg
859        return(att)
860end
861
862//transmission
863Function getSampleTrans(fname)
864        String fname
865       
866        Variable value
867       
868        // your code returning value
869        variable err
870        string dfName = ""
871        err = hdfRead(fname, dfName)
872        //err not handled here
873
874        Wave wTransmission = $(dfName+":entry1:data:Transmission")
875        value = wTransmission[0]
876        KillWaves wTransmission
877               
878        return(value)
879end
880
881//sample transmission (0<T<=1)
882Function WriteTransmissionToHeader(fname,trans)
883        String fname
884        Variable trans
885       
886        // your writer here
887        Wave wTransmission
888        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
889        Make /N=(1,1) wTransmission
890        String groupName = "/entry1/data"
891        String varName = "Transmission"
892        wTransmission[0] = trans //
893        // your code returning value
894        variable err
895        err = hdfWrite(fname, groupName, varName, wTransmission)
896        KillWaves wTransmission
897        //err not handled here
898               
899        return(0)
900End
901
902//box counts from stored transmission calculation
903// return 0 if not using NCNR transmission module
904Function getBoxCounts(fname)
905        String fname
906        Variable value
907       
908        // do nothing if not using NCNR Transmission module
909        variable err
910        string dfName = ""
911        err = hdfRead(fname, dfName)
912        //err not handled here
913
914        Wave wBoxCounts = $(dfName+":entry1:reduce:boxCounts")
915        value = wBoxCounts[0]
916        KillWaves wBoxCounts
917       
918        return(value)
919end
920
921//whole detector transmission
922// return 0 if not using NCNR transmission module
923Function getSampleTransWholeDetector(fname)
924        String fname
925        Variable value
926       
927        // your code returning value
928        // ??? don't know what to put here. nha
929        value=0
930        return(value)
931end
932
933//SampleThickness in centimeters
934Function getSampleThickness(fname)
935        String fname
936        Variable value
937
938        // your code returning value
939       
940        variable err
941        string dfName = ""
942        err = hdfRead(fname, dfName)
943        //err not handled here
944
945        Wave wThickness = $(dfName+":entry1:sample:thickness") //does not exist ???
946        value = wThickness[0]
947        //value = 1 //??? temporary fix. nha
948        KillWaves wThickness
949       
950        return(value)
951end
952
953//sample thickness in cm
954Function WriteThicknessToHeader(fname,thickness)
955        String fname
956        Variable thickness
957       
958        // your writer here
959        Wave wThickness
960        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
961        Make /N=(1,1) wThickness
962        String groupName = "/entry1/sample"
963        String varName = "thickness"
964        wThickness[0] = thickness //
965        // your code returning value
966        variable err
967        err = hdfWrite(fname, groupName, varName, wThickness) //does not exist ???
968        KillWaves wThickness
969        //err not handled here
970               
971        return(0)
972End
973
974//Sample Rotation Angle (degrees)
975Function getSampleRotationAngle(fname)
976        String fname
977        Variable value
978       
979        // your code returning value
980        variable err
981        string dfName = ""
982        err = hdfRead(fname, dfName)
983        //err not handled here
984
985        Wave wSample_rotation_angle = $(dfName+":entry1:sample:sample_theta") //is this correct
986        value = wSample_rotation_angle[0]
987        KillWaves wSample_rotation_angle
988               
989        return(value)
990end
991
992//temperature (C)
993Function getTemperature(fname)
994        String fname
995       
996        Variable value
997       
998        // your code returning value
999       
1000        return(value)
1001end
1002
1003//field strength (Oe)
1004Function getFieldStrength(fname)
1005        String fname
1006       
1007        Variable value
1008       
1009        // your code returning value
1010       
1011        return(value)
1012end
1013
1014//center of beam xPos in pixel coordinates
1015Function getBeamXPos(fname)
1016        String fname
1017        Variable value
1018        // your code returning value
1019        variable err
1020        string dfName = ""
1021        err = hdfRead(fname, dfName)
1022        //err not handled here
1023
1024        Wave wBeamXPos = $(dfName+":entry1:instrument:parameters:BeamCenterX") //is this correct
1025        value = wBeamXPos[0]   
1026        KillWaves wBeamXPos
1027       
1028        return(value)   
1029
1030end
1031
1032//beam center X pixel location (detector coordinates)
1033Function WriteBeamCenterXToHeader(fname,beamCenterX)
1034        String fname
1035        Variable beamCenterX
1036       
1037        // your writer here
1038        Wave wBeamCenterX
1039        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1040        Make /N=(1,1) wBeamCenterX
1041        String groupName = "/entry1/instrument/parameters"
1042        String varName = "BeamCenterX"
1043        wBeamCenterX[0] = beamCenterX //
1044        // your code returning value
1045        variable err
1046        err = hdfWrite(fname, groupName, varName, wBeamCenterX)
1047        KillWaves wBeamCenterX
1048        //err not handled here
1049       
1050        return(0)
1051End
1052
1053//center of beam Y pos in pixel coordinates
1054Function getBeamYPos(fname)
1055        String fname
1056        Variable value
1057        // your code returning value
1058        variable err
1059        string dfName = ""
1060        err = hdfRead(fname, dfName)
1061        //err not handled here
1062
1063        Wave wBeamYPos = $(dfName+":entry1:instrument:parameters:BeamCenterZ") //is this correct
1064        value = wBeamYPos[0]   
1065        KillWaves wBeamYPos
1066               
1067        return(value)
1068end
1069
1070//beam center Y pixel location (detector coordinates)
1071Function WriteBeamCenterYToHeader(fname,beamCenterY)
1072        String fname
1073        Variable beamCenterY
1074       
1075        // your writer here
1076        Wave wBeamCenterY
1077        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1078        Make /N=(1,1) wBeamCenterY
1079        String groupName = "/entry1/instrument/parameters"
1080        String varName = "BeamCenterZ"
1081        wBeamCenterY[0] = beamCenterY //
1082        // your code returning value
1083        variable err
1084        err = hdfWrite(fname, groupName, varName, wBeamCenterY)
1085        KillWaves wBeamCenterY
1086        //err not handled here
1087
1088        return(0)
1089End
1090
1091
1092//sample to detector distance (meters)
1093Function getSDD(fname)
1094        String fname
1095        Variable value
1096        // your code returning value
1097        variable err
1098        string dfName = ""
1099        err = hdfRead(fname, dfName)
1100        //err not handled here
1101
1102        //workaround for bad HDF5 dataset
1103        String tempDF = dfName+":entry1:instrument:parameters:L2mm"
1104        if(Exists(tempDF))
1105                Wave wSourceToDetectorDist = $(dfName+":entry1:instrument:parameters:L2mm") //is this correct
1106        else
1107                Wave wSourceToDetectorDist = $(dfName+":entry1:instrument:parameters:derived_parameters:L2mm") //is this correct
1108        endif
1109       
1110        value = wSourceToDetectorDist[0]/1000   
1111        KillWaves wSourceToDetectorDist
1112               
1113        return(value)
1114end
1115
1116//sample to detector distance (meters)
1117Function WriteSDDToHeader(fname,sdd)
1118        String fname
1119        Variable sdd
1120       
1121// your writer here
1122        Wave wSDD
1123        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1124        Make /N=(1,1) wSDD
1125//      String groupName = "/entry1/instrument/parameters/derived_parameters"
1126        String groupName = "/entry1/instrument/parameters"
1127        String varName = "L2mm"
1128        wSDD[0] = sdd * 1000 //
1129        // your code returning value
1130        variable err
1131        err = hdfWrite(fname, groupName, varName, wSDD)
1132        KillWaves wSDD
1133        //err not handled here
1134       
1135        return(0)
1136End
1137
1138//lateral detector offset (centimeters)
1139Function getDetectorOffset(fname)
1140        String fname
1141        Variable value
1142        // your code returning value
1143        variable err
1144        string dfName = ""
1145        err = hdfRead(fname, dfName)
1146        //err not handled here
1147
1148        Wave wDetectorOffset = $(dfName+":entry1:instrument:detector:detector_x") //is this correct
1149        value = wDetectorOffset[0]/10
1150        KillWaves wDetectorOffset
1151       
1152        return(value)
1153end
1154
1155//Beamstop diameter (millimeters)
1156Function getBSDiameter(fname)
1157        String fname
1158        Variable value
1159        // your code returning value
1160        variable err
1161        string dfName = ""
1162        err = hdfRead(fname, dfName)
1163        //err not handled here
1164
1165        Wave wBSdiameter = $(dfName+":entry1:instrument:parameters:BSXmm") //is this correct
1166        value = wBSdiameter[0]
1167        KillWaves wBSdiameter
1168       
1169        return(value)   
1170end
1171
1172//beam stop diameter (millimeters)
1173Function WriteBeamStopDiamToHeader(fname,bs)
1174        String fname
1175        Variable bs     
1176       
1177        // your writer here
1178        Wave wBS
1179        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1180        Make /N=(1,1) wBS
1181        String groupName = "/entry1/instrument/parameters"
1182        String varName = "BSXmm"
1183        wBS[0] = bs //
1184        // your code returning value
1185        variable err
1186        err = hdfWrite(fname, groupName, varName, wBS)
1187        KillWaves wBS
1188        //err not handled here
1189        return(0)
1190End
1191
1192//source aperture diameter (millimeters)
1193Function getSourceApertureDiam(fname)
1194        String fname
1195        Variable value
1196        // your code returning value
1197        variable err
1198        string dfName = ""
1199        err = hdfRead(fname, dfName)
1200        //err not handled here
1201
1202        Wave wSourceApertureDiam = $(dfName+":entry1:instrument:parameters:derived_parameters:EApXmm") //is this correct
1203        value = wSourceApertureDiam[0]
1204        KillWaves wSourceApertureDiam
1205       
1206        return(value)
1207end
1208
1209//Source Aperture diameter (millimeters)
1210Function WriteSourceApDiamToHeader(fname,source)
1211        String fname
1212        Variable source
1213       
1214        // your writer here
1215        Wave wsource
1216        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1217        Make /N=(1,1) wsource
1218        String groupName = "/entry1/instrument/parameters/derived_parameters"
1219        String varName = "EApXmm"
1220        wsource[0] = source //
1221        // your code returning value
1222        variable err
1223        err = hdfWrite(fname, groupName, varName, wsource)
1224        KillWaves wsource
1225        //err not handled here
1226        return(0)
1227End
1228
1229//sample aperture diameter (millimeters)
1230Function getSampleApertureDiam(fname)
1231        String fname
1232        Variable value
1233        // your code returning value
1234        variable err
1235        string dfName = ""
1236        err = hdfRead(fname, dfName)
1237        //err not handled here
1238
1239        Wave wSampleApertureDiam = $(dfName+":entry1:instrument:sample_aperture:geometry:shape:SApXmm") //is this correct
1240        value = wSampleApertureDiam[0]
1241        KillWaves wSampleApertureDiam
1242
1243        return(value)   
1244end
1245
1246//Sample Aperture diameter (millimeters)
1247Function WriteSampleApDiamToHeader(fname,source)
1248        String fname
1249        Variable source
1250       
1251        // your writer here
1252        Wave wsource
1253        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1254        Make /N=(1,1) wsource
1255        String groupName = "/entry1/instrument/sample_aperture/geometry/shape"
1256        String varName = "SApXmm"
1257        wsource[0] = source //
1258        // your code returning value
1259        variable err
1260        err = hdfWrite(fname, groupName, varName, wsource)
1261        KillWaves wsource
1262        //err not handled here
1263        return(0)
1264End
1265
1266//source AP to Sample AP distance (meters)
1267Function getSourceToSampleDist(fname)
1268        String fname
1269       
1270        Variable value
1271       
1272        // your code returning value
1273        variable err
1274        string dfName = ""
1275               
1276        err = hdfRead(fname, dfName)
1277        //err not handled here
1278       
1279        //workaround for bad HDF5 dataset
1280        String tempDF = dfName+":entry1:instrument:parameters:L1mm"
1281        if(Exists(tempDF))
1282                Wave wSourceToSampleDist = $(dfName+":entry1:instrument:parameters:L1mm") //is this correct
1283        else
1284                Wave wSourceToSampleDist = $(dfName+":entry1:instrument:parameters:derived_parameters:L1mm") //is this correct
1285        endif
1286       
1287        value = wSourceToSampleDist[0]/1000
1288        KillWaves wSourceToSampleDist   
1289               
1290        return(value)
1291end
1292
1293//Source aperture to sample aperture distance (meters)
1294Function WriteSrcToSamDistToHeader(fname,SSD)
1295        String fname
1296        Variable SSD
1297       
1298// your writer here
1299        Wave wSSD
1300        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1301        Make /N=(1,1) wSSD
1302//      String groupName = "/entry1/instrument/parameters/derived_parameters"
1303        String groupName = "/entry1/instrument/parameters"
1304        String varName = "L1mm"
1305        wSSD[0] = SSD * 1000 //input in metres, converted to mm for saving to file.
1306        // your code returning value
1307        variable err
1308        err = hdfWrite(fname, groupName, varName, wSSD)
1309        KillWaves wSSD
1310        //err not handled here
1311       
1312        return(0)
1313End
1314
1315//wavelength (Angstroms)
1316Function getWavelength(fname)
1317        String fname
1318        Variable value
1319        // your code returning value
1320        variable err
1321        string dfName = ""
1322        err = hdfRead(fname, dfName)
1323        //err not handled here
1324
1325        Wave wWavelength = $(dfName+":entry1:data:LambdaA") //is this correct
1326        value = wWavelength[0] 
1327        KillWaves wWavelength
1328       
1329        return(value)
1330end
1331
1332//wavelength (Angstroms)
1333Function WriteWavelengthToHeader(fname,wavelength)
1334        String fname
1335        Variable wavelength
1336       
1337        // your writer here
1338        Wave wWavelength
1339        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1340        Make /N=(1,1) wWavelength
1341        String groupName = "/entry1/data"
1342        String varName = "LambdaA"
1343        wWavelength[0] = wavelength //
1344        // your code returning value
1345        variable err
1346        err = hdfWrite(fname, groupName, varName, wWavelength)
1347       
1348        //and because Bill Hamilton is not happy with the NeXus naming, we write it to 2 other places
1349        groupName = "/entry1/instrument/parameters"
1350        err = hdfWrite(fname, groupName, varName, wWavelength)
1351        //velocity_selector group causes Igor crash
1352        //groupName = "/entry1/instrument/velocity_selector"
1353        //err = hdfWrite(fname, groupName, varName, wWavelength)
1354       
1355        KillWaves wWavelength
1356        //err not handled here
1357
1358        return(0)
1359End
1360
1361
1362
1363//wavelength spread (FWHM)
1364Function getWavelengthSpread(fname)
1365        String fname
1366       
1367        Variable value
1368       
1369        // your code returning value
1370        variable err
1371        string dfName = ""
1372        err = hdfRead(fname, dfName)
1373        //err not handled here
1374       
1375        //velocity_selector group causes Igor crash
1376        //Wave wWavelengthSpread = $(dfName+":entry1:instrument:velocity_selector:LambdaResFWHM_percent") //is this correct
1377        Wave wWavelengthSpread = $(dfName+":entry1:instrument:parameters:LambdaResFWHM_percent") //is this correct
1378
1379        value = wWavelengthSpread[0]   
1380        KillWaves wWavelengthSpread
1381       
1382        return(value)
1383end
1384
1385//wavelength spread (FWHM)
1386Function WriteWavelengthDistrToHeader(fname,wavelengthSpread)
1387        String fname
1388        Variable wavelengthSpread
1389       
1390        // your writer here
1391        Wave wWavelengthSpread
1392        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1393        Make /N=(1,1) wWavelengthSpread
1394        //velocity_selector group causes Igor crash
1395        //String groupName = "/entry1/instrument/velocity_selector"
1396        String groupName = "/entry1/instrument/parameters"
1397        String varName = "LambdaResFWHM_percent"
1398
1399        wWavelengthSpread[0] = wavelengthSpread
1400        // your code returning value
1401        variable err
1402        err = hdfWrite(fname, groupName, varName, wWavelengthSpread)
1403        KillWaves wWavelengthSpread
1404        //err not handled here
1405               
1406        return(0)
1407End
1408
1409// physical x-dimension of a detector pixel, in mm
1410Function getDetectorPixelXSize(fname)
1411        String fname
1412        Variable value
1413       
1414        // your code here returning value
1415        variable err
1416        string dfName = ""
1417        err = hdfRead(fname, dfName)
1418        //err not handled here
1419
1420        Wave wActiveArea = $(dfName+":entry1:instrument:detector:active_height")
1421        Wave w_x_bin = $(dfName+":entry1:instrument:detector:x_bin")
1422        Variable numPixels = dimsize(w_x_bin, 0)
1423        value = wActiveArea[0]/numPixels
1424        KillWaves wActiveArea
1425        KillWaves w_x_bin
1426       
1427        return(value)
1428end
1429
1430// physical y-dimension of a detector pixel, in mm
1431Function getDetectorPixelYSize(fname)
1432        String fname
1433        Variable value
1434       
1435        // your code here returning value
1436        variable err
1437        string dfName = ""
1438        err = hdfRead(fname, dfName)
1439        //err not handled here
1440
1441        Wave wActiveArea = $(dfName+":entry1:instrument:detector:active_width")
1442        Wave w_y_bin = $(dfName+":entry1:instrument:detector:y_bin")
1443        Variable numPixels = dimsize(w_y_bin, 0)
1444        value = wActiveArea[0]/numPixels
1445        KillWaves wActiveArea
1446        KillWaves w_y_bin
1447                       
1448        return(value)
1449end
1450
1451//transmission detector count (unused, return 0)
1452//
1453Function getTransDetectorCounts(fname)
1454        String fname
1455       
1456        Variable value
1457       
1458        // your code returning value
1459       
1460        return(0)
1461end
1462
1463
1464//total count time (seconds)
1465Function getCountTime(fname)
1466        String fname
1467        Variable value
1468        // your code returning value
1469        variable err
1470        string dfName = ""
1471        err = hdfRead(fname, dfName)
1472        //err not handled here
1473
1474        Wave wTime1 = $(dfName+":entry1:monitor:bm1_time")
1475        value = wTime1[0]       
1476        KillWaves wTime1
1477       
1478        return(value)
1479end
1480
1481
1482Function getPhysicalWidth(fname)
1483        String fname
1484        Variable value
1485        // your code returning value
1486        variable err
1487        string dfName = ""
1488        err = hdfRead(fname, dfName)
1489        //err not handled here
1490
1491        Wave wPhysicalWidth = $(dfName+":entry1:instrument:detector:active_width")
1492        value = wPhysicalWidth[0]/10
1493        KillWaves wPhysicalWidth
1494               
1495        return(value)
1496end
1497
1498
1499//reads the wavelength from a reduced data file (not very reliable)
1500// - does not work with NSORTed files
1501// - only used in FIT/RPA (which itself is almost NEVER used...)
1502//
1503// DOES NOT NEED TO BE CHANGED IF USING NCNR DATA WRITER
1504Function GetLambdaFromReducedData(tempName)
1505        String tempName
1506       
1507        String junkString
1508        Variable lambdaFromFile, fileVar
1509        lambdaFromFile = 6.0
1510        Open/R/P=catPathName fileVar as tempName
1511        FReadLine fileVar, junkString
1512        FReadLine fileVar, junkString
1513        FReadLine fileVar, junkString
1514        if(strsearch(LowerStr(junkString),"lambda",0) != -1)
1515                FReadLine/N=11 fileVar, junkString
1516                FReadLine/N=10 fileVar, junkString
1517                lambdaFromFile = str2num(junkString)
1518        endif
1519        Close fileVar
1520       
1521        return(lambdaFromFile)
1522End
1523
1524/////   TRANSMISSION RELATED FUNCTIONS    ////////
1525//box coordinate are returned by reference
1526//
1527// box to sum over is bounded (x1,y1) to (x2,y2)
1528//
1529// this function returns the bounding coordinates as stored in
1530// the header
1531//
1532// if not using the NCNR Transmission module, this function default to
1533// returning 0000, and no changes needed
1534Function getXYBoxFromFile(fname,x1,x2,y1,y2)
1535        String fname
1536        Variable &x1,&x2,&y1,&y2
1537       
1538        // return your bounding box coordinates or default values of 0
1539        x1=0
1540        y1=0
1541        x2=0
1542        y2=0
1543
1544        // your code returning value
1545        variable err
1546        string dfName = ""
1547        err = hdfRead(fname, dfName)
1548        //err not handled here
1549
1550        Wave wX1 = $(dfName+":entry1:reduce:x1")
1551        x1 = wX1[0]
1552        Wave wX2 = $(dfName+":entry1:reduce:x2")
1553        x2 = wX2[0]
1554        Wave wY1 = $(dfName+":entry1:reduce:y1")
1555        y1 = wY1[0]
1556        Wave wY2 = $(dfName+":entry1:reduce:y2")
1557        y2 = wY2[0]
1558       
1559        KillWaves wX1, wX2, wY1, wY2
1560        return(0)
1561
1562End
1563
1564// Writes the coordinates of the box to the header after user input
1565//
1566// box to sum over bounded (x1,y1) to (x2,y2)
1567//
1568// if not using the NCNR Transmission module, this function is null
1569Function WriteXYBoxToHeader(fname,x1,x2,y1,y2)
1570        String fname
1571        Variable x1,x2,y1,y2
1572
1573        String groupName = "/entry1/reduce"
1574        variable err
1575       
1576        Wave wX1
1577        Make /N=(1,1) wX1
1578        Wave wX2
1579        Make /N=(1,1) wX2
1580        Wave wY1
1581        Make /N=(1,1) wY1
1582        Wave wY2
1583        Make /N=(1,1) wY2
1584               
1585        wX1[0] = x1
1586        wX2[0] = x2
1587        wY1[0] = y1
1588        wY2[0] = y2     
1589       
1590        String varName = "x1"   
1591        err = hdfWrite(fname, groupName, varName,wX1)
1592        varName = "x2"
1593        err = hdfWrite(fname, groupName, varName,wX2)
1594        varName = "y1"
1595        err = hdfWrite(fname, groupName, varName,wY1)
1596        varName = "y2"
1597        err = hdfWrite(fname, groupName, varName,wY2)   
1598       
1599        KillWaves wX1,wX2,wY1,wY2
1600       
1601        //err not handled here
1602        return(0)       
1603
1604End
1605
1606// for transmission calculation, writes an NCNR-specific alphanumeric identifier
1607// (suffix of the data file)
1608//
1609// if not using the NCNR Transmission module, this function is null
1610Function WriteAssocFileSuffixToHeader(trans_fname,empty_fname)
1611        String trans_fname, empty_fname
1612               
1613// your writer here
1614        Wave/T wEmpty_fname
1615        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1616        Make/T /N=(1,1) wEmpty_fname
1617        String groupName = "/entry1/reduce"
1618        String varName = "empty_beam_file_name"
1619
1620        wEmpty_fname[0] = empty_fname
1621        // your code returning value
1622        variable err
1623        err = hdfWrite(trans_fname, groupName, varName, wEmpty_fname)
1624        KillWaves wEmpty_fname
1625        //err not handled here
1626        return(0)
1627end
1628
1629Function WriteFileAssoc(fname,assoc_fname)
1630        String fname,assoc_fname
1631               
1632// your writer here
1633        Wave/T wAssoc_fname
1634        //nha ??? Should make this wave in our own DataFolder to avoid clashing names.
1635        Make/T /N=(1,1) wAssoc_fname
1636       
1637        String varName =""
1638        String groupName = "/entry1/reduce"
1639        if(isTransFile(fname))
1640                varName = "empty_beam_file_name"
1641        elseif(isScatFile(fname))
1642                varName = "transmission_file_name"
1643        endif
1644
1645        wAssoc_fname[0] = assoc_fname
1646        // your code returning value
1647        variable err
1648        err = hdfWrite(fname, groupName, varName, wAssoc_fname)
1649        KillWaves wAssoc_fname
1650        //err not handled here
1651        return(0)
1652end
1653
1654Function/S GetFileAssoc(fname)
1655        String fname
1656       
1657        String assoc_fname
1658        String groupName = ":entry1:reduce:"
1659       
1660        String varName = ""
1661        if(isTransFile(fname))
1662                varName = "empty_beam_file_name"
1663        elseif(isScatFile(fname))
1664                varName = "transmission_file_name"
1665        endif
1666       
1667        variable err
1668        string dfName = ""
1669        err = hdfRead(fname, dfName)
1670        //err not handled here
1671
1672        Wave/T wAssoc_fname = $(dfName+groupName+varName)
1673        assoc_fname =wAssoc_fname[0]   
1674        KillWaves wAssoc_fname
1675       
1676        return(assoc_fname)
1677end
1678
1679Function hdfRead(fname, dfName)
1680        //Reads hdf5 file into root:packages:quokka:fname
1681        //N. Hauser. 16/12/08
1682        // 29/1/09 - hdf file must have .nx.hdf or .div suffix
1683       
1684        String fname, &dfName
1685        variable err=0,fileID
1686        String cDF = getDataFolder(1), temp
1687        String fname_temp = ParseFilePath(0, fname, ":", 1, 0)
1688       
1689        String fileSuffix
1690        if(strsearch(fname_temp,".nx.hdf",0,2)>=0)
1691                fileSuffix=".nx.hdf"
1692        //elseif(strsearch(fname_temp,".div",0,2)>=0)
1693        //      fileSuffix=".div"
1694        else
1695                err = 1
1696                abort "unrecognised file suffix. Not .nx.hdf"
1697        endif
1698       
1699        dfName = "root:packages:quokka:"+removeending(fname_temp,fileSuffix)
1700       
1701        //if(!DataFolderExists(dfName))
1702        //      return err
1703        //else         
1704                newDataFolder /O root:packages
1705                newDataFolder /O /S root:packages:quokka
1706                newDataFolder /O /S $dfName
1707        //endif
1708       
1709        try     
1710                HDF5OpenFile /R /Z fileID  as fname
1711                if(!fileID)
1712                        err = 1
1713                        abort "couldn't load HDF5 file"
1714                endif
1715                HDF5LoadGroup /O /R /Z  :, fileID, "."
1716        catch
1717
1718        endtry
1719        if(fileID)
1720                HDF5CloseFile /Z fileID
1721        endif
1722
1723        setDataFolder $cDF
1724        return err
1725end
1726
1727Function hdfWrite(fname, groupName, varName, wav)
1728        //Write Wave 'wav' to hdf5 file 'fname'
1729        //N. Hauser. nha 8/1/09
1730               
1731        String fname, groupName, varName
1732        Wave wav
1733       
1734        variable err=0, fileID,groupID
1735        String cDF = getDataFolder(1), temp
1736        String fname_temp = ParseFilePath(0, fname, ":", 1, 0)
1737       
1738        try     
1739                HDF5OpenFile /Z fileID  as fname  //open file read-write
1740                if(!fileID)
1741                        err = 1
1742                        abort "HDF5 file does not exist"
1743                endif
1744                HDF5OpenGroup /Z fileID , groupName, groupID
1745
1746        //      !! At the moment, there is no entry for sample thickness in our data file
1747        //      therefore create new HDF5 group to enable write / patch command
1748        //      comment out the following group creation once thickness appears in revised file
1749       
1750                if(!groupID)
1751                        HDF5CreateGroup /Z fileID, groupName, groupID
1752                        //err = 1
1753                        //abort "HDF5 group does not exist"
1754                endif           
1755                HDF5SaveData /O /Z  wav, groupID, varName
1756                if (V_flag != 0)
1757                        err = 1
1758                        abort "Cannot save wave to HDF5 group"
1759                endif   
1760        catch
1761
1762        endtry
1763       
1764        if(groupID)
1765                HDF5CloseGroup /Z groupID
1766        endif
1767       
1768        if(fileID)
1769                HDF5CloseFile /Z fileID
1770        endif
1771
1772        setDataFolder $cDF
1773        return err
1774end
1775
1776Function DoEdgeCorrection(type)
1777        String type
1778        variable err = 0
1779       
1780        WAVE typeData=$("root:Packages:NIST:"+type+":data")
1781       
1782        //nha workaround for high counts on edges
1783        //copy second column to first column
1784        typeData[][0] = typeData[p][1]
1785        //copy second last column to last column
1786        typeData[][191] = typeData[p][190]
1787        //copy second row to first row
1788        typeData[0][] = typeData[1][q]
1789        //copy second last row to last row
1790        typeData[191][] = typeData[190][q]
1791       
1792        return err     
1793end
1794
1795////// OCT 2009, facility specific bits from ProDiv()
1796//"type" is the data folder that has the corrected, patched, and normalized DIV data array
1797//
1798// the header of this file is rather unimportant. Filling in a title at least would be helpful/
1799//
1800Function Write_DIV_File(type)
1801        String type
1802       
1803        // Your file writing function here. Don't try to duplicate the VAX binary format...
1804        WriteHeaderAndWork(type)
1805       
1806        return(0)
1807End
1808
1809////// OCT 2009, facility specific bits from MonteCarlo functions()
1810//"type" is the data folder that has the data array that is to be (re)written as a full
1811// data file, as if it was a raw data file
1812//
1813// not really necessary
1814//
1815Function Write_RawData_File(type,fullpath,dialog)
1816        String type,fullpath
1817        Variable dialog         //=1 will present dialog for name
1818       
1819        // Your file writing function here. Don't try to duplicate the VAX binary format...
1820        Print "Write_RawData_File stub"
1821       
1822        return(0)
1823End
Note: See TracBrowser for help on using the repository browser.