source: sans/Dev/trunk/NCNR_User_Procedures/Reduction/VSANS/V_PatchFiles.ipf @ 1203

Last change on this file since 1203 was 1203, checked in by srkline, 3 years ago

Corrected attenuator table for VSANS to include the range 4.52->19. Patching of the attenuation factor is disabled since the factor is always calculated rather than read from the file.

Added a few help links in preparation for the full help file integration

Added a "super" white beam distribution definition and a single model function for testing of this new mode. Still need the normalization and mean wavelength for the distribution + a way to identify it in the file metadata.

  • Property svn:executable set to *
File size: 83.8 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//
8// TODO --  January 2107
9//
10// This is experimental, making the patch work with list boxes as "groups" of the Nexus file structure
11//
12// some of the groupings are more natural, some will need to be re-organized for the
13// more natural needs of what will typically be patched in the most common cases.
14//
15///////////////////////////////
16
17// TODOs have been inserted to comment out all of the calls that don't compile and need to be replaced
18
19// TODO
20// x- not all of the functions here have been prefixed with "V_", especially the action procedures from the panel
21//   so this cannot be opened with the SANS Reduction, or there will be clashes
22// -- same file load/reload issue as with other operations that read a field from the file. ANY read requires
23//   that the entire file is read in, even just to check and see if it's raw data... then there is a local
24//   copy present to confuse matters of what was actually written
25//
26// -- for the batch entering of fields, when all of the proper beam center values are determined, then
27//    all (2 x 9 = 18) of these values will need to be entered in all of the data files that "match" this
28//    "configuration" - however a configuration is to be defined and differentiated from other configurations.
29//
30// -- there may be other situations where batch entering needs are
31//               different, and this may lead to different interface choices
32//
33// -- need to add some mechanism (new panel?) to enter:
34//    -- box coordinates
35//    -- ABS parameters
36//    -- averaging options -- these will have new options versus SANS (binning panels, slit mode, etc.)
37//
38//
39// TODO:
40// V_fPatch_GroupID_catTable()
41//      V_fPatch_Purpose_catTable()
42//      V_fPatch_Intent_catTable()
43/// -- these three functions are part of a growing list for faster patching. edit the file catalog, and
44//    write out the contents of the column (vs. filename)
45// -- make a simple panel w/buttons (like the sort panel) to call these functions
46//
47
48//**************************
49//
50//procedures required to allow patching of raw vSANS data headers
51//information for the Patch Panel is stored in the root:Packages:NIST:VSANS:Globals:Patch subfolder
52//
53// writes changes directly to the raw data headers as requested
54// * note that if a data file is currently in a work folder, the (real) header on disk
55// will be updated, but the data in the (WORK) folder will not reflect these changes, unless
56// the data folder is first cleared and the data is re-loaded
57//
58//**************************
59
60//main entry procedure for displaying the Patch Panel
61//
62Proc V_PatchFiles()
63       
64        DoWindow/F V_Patch_Panel
65        If(V_flag == 0)
66                V_InitializePatchPanel()
67                //draw panel
68                V_Patch_Panel()
69        Endif
70End
71
72//initialization of the panel, creating the necessary data folder and global
73//variables if necessary -
74//
75// root:Packages:NIST:VSANS:Globals:
76Proc V_InitializePatchPanel()
77        //create the global variables needed to run the Patch Panel
78        //all are kept in root:Packages:NIST:VSANS:Globals:Patch
79        If( ! (DataFolderExists("root:Packages:NIST:VSANS:Globals:Patch"))  )
80                //create the data folder and the globals for BOTH the Patch and Trans panels
81                NewDataFolder/O root:Packages:NIST:VSANS:Globals:Patch
82        Endif
83        V_CreatePatchGlobals()          //re-create them every time (so text and radio buttons are correct)
84End
85
86//the data folder root:Packages:NIST:VSANS:Globals:Patch must exist
87//
88Proc V_CreatePatchGlobals()
89        //ok, create the globals
90        String/G root:Packages:NIST:VSANS:Globals:Patch:gPatchMatchStr = "*"
91        String/G root:Packages:NIST:VSANS:Globals:Patch:gPatchCurLabel = "no file selected"
92       
93        PathInfo catPathName
94        If(V_flag==1)
95                String dum = S_path
96                String/G root:Packages:NIST:VSANS:Globals:Patch:gCatPathStr = dum
97        else
98                String/G root:Packages:NIST:VSANS:Globals:Patch:gCatPathStr = "no path selected"
99        endif
100        String/G root:Packages:NIST:VSANS:Globals:Patch:gPatchList = "none"
101
102        Variable/G root:Packages:NIST:VSANS:Globals:Patch:gRadioVal = 1
103       
104
105        SetDataFolder root:Packages:NIST:VSANS:Globals:Patch:   
106        Make/O/T/N=(10,3) PP_ListWave
107        Make/O/B/N=(10,3) PP_SelWave
108        Make/O/T/N=3 PP_TitleWave
109       
110        PP_TitleWave = {"Ch?","Label","Value"}
111       
112        PP_SelWave[][0] = 2^5           // checkboxes
113        PP_SelWave[][2] = 2^1           // 3rd column editable
114       
115       
116        SetDataFolder root:
117       
118End
119
120
121//panel recreation macro for the PatchPanel...
122//
123Proc V_Patch_Panel()
124        PauseUpdate; Silent 1      // building window...
125        NewPanel /W=(533,50,1140,588)/K=2 as "Patch Raw VSANS Data Files"
126        DoWindow/C V_Patch_Panel
127//      ShowTools/A
128        SetDataFolder root:Packages:NIST:VSANS:Globals:Patch:
129
130       
131        ModifyPanel cbRGB=(11291,48000,3012)
132        ModifyPanel fixedSize=1
133        SetDrawLayer UserBack
134        DrawLine 7,30,422,30
135
136       
137        SetVariable PathDisplay,pos={77,7},size={310,13},title="Path"
138        SetVariable PathDisplay,help={"This is the path to the folder that will be used to find the SANS data while patching. If no files appear in the popup, make sure that this folder is set correctly"}
139        SetVariable PathDisplay,font="Courier",fSize=10
140        SetVariable PathDisplay,limits={-Inf,Inf,0},value= root:Packages:NIST:VSANS:Globals:Patch:gCatPathStr
141        Button PathButton,pos={2,3},size={70,20},proc=V_PickPathButton,title="Pick Path"
142        Button PathButton,help={"Select the folder containing the raw SANS data files"}
143        Button helpButton,pos={400,3},size={25,20},proc=V_ShowPatchHelp,title="?"
144        Button helpButton,help={"Show the help file for patching raw data headers"}
145        PopupMenu PatchPopup,pos={4,37},size={156,19},proc=V_PatchPopMenuProc,title="File(s) to Patch"
146        PopupMenu PatchPopup,help={"The displayed file is the one that will be edited. The entire list will be edited if \"Change All..\" is selected. \r If no items, or the wrong items appear, click on the popup to refresh. \r List items are selected from the file based on MatchString"}
147        PopupMenu PatchPopup,mode=1,popvalue="none",value= #"root:Packages:NIST:VSANS:Globals:Patch:gPatchList"
148
149        Button CHButton,pos={314,37},size={110,20},proc=V_ChangeHeaderButtonProc,title="Change Header"
150        Button CHButton,help={"This will change the checked values (ONLY) in the single file selected in the popup."}
151        SetVariable PMStr,pos={6,63},size={174,13},proc=V_SetMatchStrProc,title="Match String"
152        SetVariable PMStr,help={"Enter the search string to narrow the list of files. \"*\" is the wildcard character. After entering, \"pop\" the menu to refresh the file list."}
153        SetVariable PMStr,font="Courier",fSize=10
154        SetVariable PMStr,limits={-Inf,Inf,0},value= root:Packages:NIST:VSANS:Globals:Patch:gPatchMatchStr
155        Button ChAllButton,pos={245,60},size={180,20},proc=V_ChAllHeadersButtonProc,title="Change All Headers in List"
156        Button ChAllButton,help={"This will change the checked values (ONLY) in ALL of the files in the popup list, not just the top file. If the \"change\" checkbox for the item is not checked, nothing will be changed for that item."}
157        Button DoneButton,pos={450,60},size={110,20},proc=V_DoneButtonProc,title="Done Patching"
158        Button DoneButton,help={"When done Patching files, this will close this control panel."}
159        CheckBox check0,pos={18,80},size={40,15},title="Run #",value= 1,mode=1,proc=V_MatchCheckProc
160        CheckBox check1,pos={78,80},size={40,15},title="Text",value= 0,mode=1,proc=V_MatchCheckProc
161        CheckBox check2,pos={138,80},size={40,15},title="Group_ID",value= 0,mode=1,proc=V_MatchCheckProc
162
163        SetVariable curStr,pos={50,112},size={350,20},title="File Label:"
164        SetVariable curStr,help={"Label of current file in popup list"}
165        SetVariable curStr,font="Courier",fSize=10
166        SetVariable curStr,limits={-Inf,Inf,0},value= root:Packages:NIST:VSANS:Globals:Patch:gPatchCurLabel
167       
168        PopupMenu popup_0,pos={450,112},size={109,20},title="Detector Panel",proc=V_PatchPopMenuProc
169        PopupMenu popup_0,mode=1,popvalue="FL",value= #"\"FL;FR;FT;FB;ML;MR;MT;MB;B;\""
170
171
172        TabControl PatchTab,pos={20,140},size={570,380}
173        TabControl PatchTab,tabLabel(0)="Control",tabLabel(1)="Reduction",tabLabel(2)="Sample"
174        TabControl PatchTab,tabLabel(3)="Instrument",tabLabel(4)="Detectors",tabLabel(5)="PolSANS"
175        TabControl PatchTab,value=0,labelBack=(47748,57192,54093),proc=V_PatchTabProc
176
177
178        ListBox list0,pos={30,170.00},size={550.00,330},proc=V_PatchListBoxProc,frame=1
179        ListBox list0,fSize=10,userColumnResize= 1,listWave=PP_ListWave,selWave=PP_SelWave,titleWave=PP_TitleWave
180        ListBox list0,mode=2,widths={30,200}
181
182
183// put these in a tabbed? section for the 9 different panels
184// will it be able to patch all "FL" with the proper values, then all "FR", etc. to batchwise correct files?
185
186// TODO: add functions for these, make the intent a popup (since it's an enumerated type)
187
188//      PopupMenu popup_1,pos={42,base+14*step},size={109,20},title="File intent"
189//      PopupMenu popup_1,mode=1,popvalue="SCATTER",value= #"\"SCATTER;EMPTY;BLOCKED BEAM;TRANS;EMPTY BEAM;\""
190
191
192
193        SetDataFolder root:
194End
195
196//
197// function to control the display of the list box, based on the selection of the tab
198//
199Function V_PatchTabProc(name,tab)
200        String name
201        Variable tab
202       
203//      Print "name,number",name,tab
204        SetDataFolder root:Packages:NIST:VSANS:Globals:Patch:
205       
206        Wave/T PP_listWave = PP_ListWave
207        Wave PP_selWave = PP_selWave
208       
209        //clear the listWave and SelWave
210        PP_ListWave = ""
211        PP_SelWave = 0
212       
213        Variable nRows=1
214        // switch based on the tab number
215        switch(tab)     
216                case 0:
217                        //Print "tab 0 = CONTROL"
218                       
219                        V_FillListBox0(PP_ListWave,PP_SelWave)
220                        break           
221                case 1:
222                        //Print "tab 1 = REDUCTION"
223                       
224                        V_FillListBox1(PP_ListWave,PP_SelWave)
225                        break
226                case 2:
227                        //Print "tab 2 = SAMPLE"
228                       
229                        V_FillListBox2(PP_ListWave,PP_SelWave)
230                        break
231                case 3:
232                        //Print "tab 3 = INSTRUMENT"
233                       
234                        V_FillListBox3(PP_ListWave,PP_SelWave)
235                        break
236                case 4:
237                        //Print "tab 4 = DETECTORS"
238                       
239                        V_FillListBox4(PP_ListWave,PP_SelWave)
240                        break
241                case 5:
242                        //Print "tab 5 = POL_SANS"
243
244                        V_FillListBox5(PP_ListWave,PP_SelWave)
245                        break
246                default:                        // optional default expression executed
247                        SetDataFolder root:
248                        Abort "No tab found -- PatchTabProc"            // when no case matches
249        endswitch
250
251
252        SetDataFolder root:
253        return(0)
254End
255
256// fill list boxes based on the tab
257//
258// *** if the number of elements is changed, then be sure that the variable nRows is updated
259//    * this is the same procedure for all of the tabs
260//    * then be sure that the new listWave assignments are properly indexed
261//
262// CONTROL
263//
264Function V_FillListBox0(listWave,selWave)
265        Wave/T listWave
266        Wave selWave
267       
268        // trust that I'm getting a valid raw data file name from the popup
269        String fname
270        ControlInfo/W=V_Patch_Panel PatchPopup
271        If(strlen(S_value)==0 || cmpstr(S_Value,"none")==0)
272                Abort "no file selected in popup menu"          //null selection
273        else
274                fname = S_value                         //selection not null
275        Endif
276        //prepend path for read routine
277        PathInfo catPathName
278        fname = S_path + fname
279
280        Variable nRows = 3
281        Redimension/N=(nRows,3) ListWave
282        Redimension/N=(nRows,3) selWave
283        // clear the contents
284        listWave = ""
285        selWave = 0
286        SelWave[][0] = 2^5              // checkboxes
287        SelWave[][2] = 2^1              // 3rd column editable
288       
289       
290       
291        listWave[0][1] = "count_time (s)"
292        listWave[0][2] = num2str(V_getCount_time(fname))
293       
294        listWave[1][1] = "detector_counts"
295        listWave[1][2] = num2str(V_getDetector_counts(fname))
296       
297        listWave[2][1] = "monitor_counts"
298//      listWave[2][2] = num2str(V_getControlMonitorCount(fname))
299        listWave[2][2] = num2str(V_getBeamMonNormData(fname))
300       
301        return(0)
302End
303
304// fill list boxes based on the tab
305//
306// REDUCTION items
307//
308Function V_FillListBox1(listWave,selWave)
309        Wave/T listWave
310        Wave selWave
311
312        // trust that I'm getting a valid raw data file name from the popup
313        String fname
314        ControlInfo/W=V_Patch_Panel PatchPopup
315        If(strlen(S_value)==0 || cmpstr(S_Value,"none")==0)
316                Abort "no file selected in popup menu"          //null selection
317        else
318                fname = S_value                         //selection not null
319        Endif
320        //prepend path for read routine
321        PathInfo catPathName
322        fname = S_path + fname
323
324        Variable nRows = 14
325        Redimension/N=(nRows,3) ListWave
326        Redimension/N=(nRows,3) selWave
327        // clear the contents
328        listWave = ""
329        selWave = 0
330        SelWave[][0] = 2^5              // checkboxes
331        SelWave[][2] = 2^1              // 3rd column editable
332       
333       
334        listWave[0][1] = "empty_beam_file_name"
335        listWave[0][2] = V_getEmptyBeamFileName(fname)
336       
337        listWave[1][1] = "background_file_name"
338        listWave[1][2] = V_getBackgroundFileName(fname)
339       
340        listWave[2][1] = "empty_file_name"
341        listWave[2][2] = V_getEmptyFileName(fname)
342       
343        listWave[3][1] = "sensitivity_file_name"
344        listWave[3][2] = V_getSensitivityFileName(fname)
345       
346        listWave[4][1] = "mask_file_name"
347        listWave[4][2] = V_getMaskFileName(fname)
348       
349        listWave[5][1] = "transmission_file_name"
350        listWave[5][2] = V_getTransmissionFileName(fname)
351       
352        listWave[6][1] = "intent"
353        listWave[6][2] = V_getReduction_intent(fname)
354       
355        listWave[7][1] = "file_purpose"
356        listWave[7][2] = V_getReduction_purpose(fname)
357       
358        listWave[8][1] = "group_id (sample)"
359        listWave[8][2] = num2str(V_getSample_groupID(fname))
360       
361        listWave[9][1] = "Box Coordinates"
362        WAVE boxCoord = V_getBoxCoordinates(fname)
363        listWave[9][2] = V_NumWave2List(boxCoord,";")
364
365        listWave[10][1] = "box_count"
366        listWave[10][2] = num2str(V_getBoxCounts(fname))
367       
368        listWave[11][1] = "box_count_error"
369        listWave[11][2] = num2str(V_getBoxCountsError(fname))
370       
371        listWave[12][1] = "whole_trans"
372        listWave[12][2] = num2str(V_getSampleTransWholeDetector(fname))
373       
374        listWave[13][1] = "whole_trans_error"
375        listWave[13][2] = num2str(V_getSampleTransWholeDetErr(fname))   
376               
377       
378
379        return(0)
380End
381
382// fill list boxes based on the tab
383//
384// SAMPLE
385//
386Function V_FillListBox2(listWave,selWave)
387        Wave/T listWave
388        Wave selWave
389       
390        // trust that I'm getting a valid raw data file name from the popup
391        String fname
392        ControlInfo/W=V_Patch_Panel PatchPopup
393        If(strlen(S_value)==0 || cmpstr(S_Value,"none")==0)
394                Abort "no file selected in popup menu"          //null selection
395        else
396                fname = S_value                         //selection not null
397        Endif
398        //prepend path for read routine
399        PathInfo catPathName
400        fname = S_path + fname
401
402        Variable nRows = 4
403        Redimension/N=(nRows,3) ListWave
404        Redimension/N=(nRows,3) selWave
405        // clear the contents
406        listWave = ""
407        selWave = 0
408        SelWave[][0] = 2^5              // checkboxes
409        SelWave[][2] = 2^1              // 3rd column editable
410       
411       
412        listWave[0][1] = "description"
413        listWave[0][2] = V_getSampleDescription(fname)
414       
415        listWave[1][1] = "thickness [cm]"
416        listWave[1][2] = num2str(V_getSampleThickness(fname))
417       
418        listWave[2][1] = "transmission"
419        listWave[2][2] = num2str(V_getSampleTransmission(fname))
420       
421        listWave[3][1] = "transmission_error"
422        listWave[3][2] = num2str(V_getSampleTransError(fname))
423       
424
425
426        return(0)
427End
428
429// fill list boxes based on the tab
430//
431// INSTRUMENT
432//
433Function V_FillListBox3(listWave,selWave)
434        Wave/T listWave
435        Wave selWave
436       
437        // trust that I'm getting a valid raw data file name from the popup
438        String fname
439        ControlInfo/W=V_Patch_Panel PatchPopup
440        If(strlen(S_value)==0 || cmpstr(S_Value,"none")==0)
441                Abort "no file selected in popup menu"          //null selection
442        else
443                fname = S_value                         //selection not null
444        Endif
445        //prepend path for read routine
446        PathInfo catPathName
447        fname = S_path + fname
448
449        Variable nRows = 17
450        Redimension/N=(nRows,3) ListWave
451        Redimension/N=(nRows,3) selWave
452        // clear the contents
453        listWave = ""
454        selWave = 0
455        SelWave[][0] = 2^5              // checkboxes
456        SelWave[][2] = 2^1              // 3rd column editable
457
458//
459// TODO - the attenuation factor is always calculated from the table. How do I devise a method to
460// overrride this behavior if a factor needs to be forced to a new value (old table, lambda out of range, etc.)?
461//     
462// currently, this simply prevents anyone from "patching" the header, which really doesn't work as intended
463//
464        SelWave[0][0] += 2^7            // disable the checkbox for attenuator
465        SelWave[1][0] += 2^7            // disable the checkbox for attenuator_err
466       
467        listWave[0][1] = "attenuator_transmission"
468        listWave[0][2] = num2str(V_getAttenuator_transmission(fname))   
469       
470        listWave[1][1] = "attenuator_transmission_error"
471        listWave[1][2] = num2str(V_getAttenuator_trans_err(fname))     
472
473        listWave[2][1] = "monochromator type"
474        listWave[2][2] = V_getMonochromatorType(fname)
475       
476        listWave[3][1] = "wavelength (A)"
477        listWave[3][2] = num2str(V_getWavelength(fname))       
478       
479        listWave[4][1] = "wavelength_spread"
480        listWave[4][2] = num2str(V_getWavelength_spread(fname))
481       
482        listWave[5][1] = "Number of Guides OR COLLIMATION"
483        listWave[5][2] = V_getNumberOfGuides(fname)
484
485        listWave[6][1] = "distance (source aperture to GV) [cm]"
486        listWave[6][2] = num2str(V_getSourceAp_distance(fname))         
487
488        listWave[7][1] = "source aperture size [mm]"
489        listWave[7][2] = V_getSourceAp_size(fname)
490       
491        listWave[8][1] = "sample aperture size (internal) [mm]"
492        listWave[8][2] = V_getSampleAp_size(fname)
493
494        listWave[9][1] = "sample aperture(2) SHAPE (external)"
495        listWave[9][2] = V_getSampleAp2_shape(fname)
496               
497        listWave[10][1] = "sample aperture(2) diam (external) [cm]"
498        listWave[10][2] = num2str(V_getSampleAp2_size(fname))   
499       
500        listWave[11][1] = "sample aperture(2) height (external) [cm]"
501        listWave[11][2] = num2str(V_getSampleAp2_height(fname))
502
503        listWave[12][1] = "sample aperture(2) width (external) [cm]"
504        listWave[12][2] = num2str(V_getSampleAp2_width(fname)) 
505
506        listWave[13][1] = "beam stop diameter (Middle) [mm]"
507//      listWave[13][2] = num2str(V_getBeamStopC2_size(fname)) 
508        listWave[13][2] = num2str(V_IdentifyBeamstopDiameter(fname,"MR"))       
509       
510        listWave[14][1] = "beam stop diameter (Back) [mm]"
511//      listWave[14][2] = num2str(V_getBeamStopC3_size(fname)) 
512        listWave[14][2] = num2str(V_IdentifyBeamstopDiameter(fname,"B"))       
513
514        listWave[15][1] = "sample aperture(2) to gate valve [cm]"
515        listWave[15][2] = num2str(V_getSampleAp2_distance(fname))       
516
517        listWave[16][1] = "sample to gate valve [cm]"
518        listWave[16][2] = num2str(V_getSampleTableOffset(fname))       
519
520                               
521        return(0)
522End
523
524
525// fill list boxes based on the tab
526//
527// TODO -- is this all of the fields that I want to edit?
528//
529// DETECTORS
530//
531Function V_FillListBox4(listWave,selWave)
532        Wave/T listWave
533        Wave selWave
534       
535        // trust that I'm getting a valid raw data file name from the popup
536        String fname
537        ControlInfo/W=V_Patch_Panel PatchPopup
538        If(strlen(S_value)==0 || cmpstr(S_Value,"none")==0)
539                Abort "no file selected in popup menu"          //null selection
540        else
541                fname = S_value                         //selection not null
542        Endif
543        //prepend path for read routine
544        PathInfo catPathName
545        fname = S_path + fname
546
547        Variable nRows = 13
548        Redimension/N=(nRows,3) ListWave
549        Redimension/N=(nRows,3) selWave
550        // clear the contents
551        listWave = ""
552        selWave = 0
553        SelWave[][0] = 2^5              // checkboxes
554        SelWave[][2] = 2^1              // 3rd column editable
555       
556        ControlInfo popup_0                     // which detector panel?
557        String detStr = S_value
558       
559        listWave[0][1] = "beam_center_x [cm]"
560        listWave[0][2] = num2str(V_getDet_Beam_center_x(fname,detStr)) 
561
562        listWave[1][1] = "beam_center_y [cm]"
563        listWave[1][2] = num2str(V_getDet_Beam_center_y(fname,detStr)) 
564
565        listWave[2][1] = "distance (nominal) [cm]"
566        listWave[2][2] = num2str(V_getDet_NominalDistance(fname,detStr))       
567
568        listWave[3][1] = "integrated_count"
569        listWave[3][2] = num2str(V_getDet_IntegratedCount(fname,detStr))       
570
571        listWave[4][1] = "pixel_fwhm_x [cm]"
572        listWave[4][2] = num2str(V_getDet_pixel_fwhm_x(fname,detStr))   
573
574        listWave[5][1] = "pixel_fwhm_y [cm]"
575        listWave[5][2] = num2str(V_getDet_pixel_fwhm_y(fname,detStr))   
576
577        listWave[6][1] = "pixel_num_x"
578        listWave[6][2] = num2str(V_getDet_pixel_num_x(fname,detStr))   
579
580        listWave[7][1] = "pixel_num_y"
581        listWave[7][2] = num2str(V_getDet_pixel_num_y(fname,detStr))   
582
583        listWave[8][1] = "setback [cm]"
584        listWave[8][2] = num2str(V_getDet_TBSetback(fname,detStr))     
585
586        if(cmpstr(detStr,"B") == 0 ||cmpstr(detStr,"FR") == 0 || cmpstr(detStr,"FL") == 0 || cmpstr(detStr,"MR") == 0 || cmpstr(detStr,"ML") == 0)
587                listWave[9][1] = "lateral_offset [cm]"                  // "B" detector drops here
588                listWave[9][2] = num2str(V_getDet_LateralOffset(fname,detStr)) 
589        else   
590                listWave[9][1] = "vertical_offset [cm]"
591                listWave[9][2] = num2str(V_getDet_VerticalOffset(fname,detStr))
592        endif   
593
594        listWave[10][1] = "x_pixel_size [mm]"
595        listWave[10][2] = num2str(V_getDet_x_pixel_size(fname,detStr)) 
596
597        listWave[11][1] = "y_pixel_size [mm]"
598        listWave[11][2] = num2str(V_getDet_y_pixel_size(fname,detStr)) 
599
600        listWave[12][1] = "dead time (s) (back only)"
601        listWave[12][2] = num2str(V_getDetector_deadtime_B(fname,detStr))                       //returns 0 if not "B"
602
603        return(0)
604End
605
606
607// fill list boxes based on the tab
608//
609// TODO -- this all needs to be filled in, once I figure out what is needed
610//
611// PolSANS
612//
613Function V_FillListBox5(listWave,selWave)
614        Wave/T listWave
615        Wave selWave
616       
617        // trust that I'm getting a valid raw data file name from the popup
618        String fname
619        ControlInfo/W=V_Patch_Panel PatchPopup
620        If(strlen(S_value)==0 || cmpstr(S_Value,"none")==0)
621                Abort "no file selected in popup menu"          //null selection
622        else
623                fname = S_value                         //selection not null
624        Endif
625        //prepend path for read routine
626        PathInfo catPathName
627        fname = S_path + fname
628
629        Variable nRows = 3
630        Redimension/N=(nRows,3) ListWave
631        Redimension/N=(nRows,3) selWave
632        // clear the contents
633        listWave = ""
634        selWave = 0
635        SelWave[][0] = 2^5              // checkboxes
636        SelWave[][2] = 2^1              // 3rd column editable
637       
638       
639        listWave[0][1] = "count_time (s)"
640        listWave[0][2] = num2str(V_getCount_time(fname))       
641
642        return(0)
643End
644
645
646// TODO -- determine if I really need this --- I don't
647//  think I really have any reason to respond to events from list box actions
648//  or edits. the final action of patching is done with the button
649//
650Function V_PatchListBoxProc(lba) : ListBoxControl
651        STRUCT WMListboxAction &lba
652
653        Variable row = lba.row
654        Variable col = lba.col
655        WAVE/T/Z listWave = lba.listWave
656        WAVE/Z selWave = lba.selWave
657
658        switch( lba.eventCode )
659                case -1: // control being killed
660                        break
661                case 1: // mouse down
662                        break
663                case 3: // double click
664                        break
665                case 4: // cell selection
666                case 5: // cell selection plus shift key
667                        break
668                case 6: // begin edit
669                        break
670                case 7: // finish edit
671                        break
672                case 13: // checkbox clicked (Igor 6.2 or later)
673                        break
674        endswitch
675
676        return 0
677End
678
679
680
681
682
683
684//button action procedure to select the local path to the folder that
685//contains the vSANS data
686//sets catPathName, updates the path display and the popup of files (in that folder)
687//
688Function V_PickPathButton(PathButton) : ButtonControl
689        String PathButton
690       
691        // call the main procedure to set the data path
692        V_PickPath()
693       
694        //set the global string to the selected pathname
695        //set a local copy of the path for Patch
696        PathInfo/S catPathName
697   String dum = S_path
698        if (V_flag == 0)
699                //path does not exist - no folder selected
700                String/G root:Packages:NIST:VSANS:Globals:Patch:gCatPathStr = "no folder selected"
701        else
702                String/G root:Packages:NIST:VSANS:Globals:Patch:gCatPathStr = dum
703        endif
704       
705        //Update the pathStr variable box
706        ControlUpdate/W=V_Patch_Panel $"PathDisplay"
707       
708        //then update the popup list
709        // (don't update the list - not until someone enters a search critera) -- Jul09
710        //
711       
712        STRUCT WMSetVariableAction sva
713        sva.eventCode = 2       
714        V_SetMatchStrProc(sva)          //this is equivalent to finding everything, typical startup case
715
716        return(0)
717End
718
719//
720//returns a list of valid files (raw data, no version numbers, no averaged files)
721//that is semicolon delimited, and is suitable for display in a popup menu
722//
723Function/S V_xGetValidPatchPopupList()
724
725        //make sure that path exists
726        PathInfo catPathName
727        String path = S_path
728        if (V_flag == 0)
729                Abort "folder path does not exist - use Pick Path button"
730        Endif
731       
732        String newList = ""
733
734        newList = V_GetRawDataFileList()
735
736        //trim list to include only selected files
737        SVAR match = root:Packages:NIST:VSANS:Globals:Patch:gPatchMatchStr
738        if(strlen(match) == 0)          //if nothing is entered for a match string, return everything, rather than nothing
739                match = "*"
740        endif
741
742        newlist = V_MyMatchList(match,newlist,";")
743       
744        newList = SortList(newList,";",0)
745        Return(newList)
746End
747
748
749
750//
751// TODO:
752// -- test all of the filters to be sure they actually work properly.
753//   Run # filter works
754//   Text filter works
755//
756// -- SDD filter does not apply -- what is a better filter choice?
757// -- can I filter intent? group_id?
758// -- can't just search for "sample" - this returns everything
759//
760//
761//
762//
763//
764//returns a list of valid files (raw data, no version numbers, no averaged files)
765//that is semicolon delimited, and is suitable for display in a popup menu
766//
767// Uses Grep to look through the any text in the file, which includes the sample label
768// can be very slow across the network, as it re-pops the menu on a selection (since some folks don't hit
769// enter when inputing a filter string)
770//
771// - or -
772// a list or range of run numbers
773// - or -
774// a SDD (to within 0.001m)
775// - or -
776// * to get everything
777//
778//      NVAR gRadioVal= root:Packages:NIST:VSANS:Globals:Patch:gRadioVal
779 // 1== Run # (comma range OK)
780 // 2== Grep the text (SLOW)
781 // 3== filter by SDD (within 0.001 m)
782Function/S V_GetValidPatchPopupList()
783
784        //make sure that path exists
785        PathInfo catPathName
786        String path = S_path
787        if (V_flag == 0)
788                Abort "folder path does not exist - use Pick Path button"
789        Endif
790       
791        String newList = ""
792
793        newList = V_GetRawDataFileList()
794
795        //trim list to include only selected files
796        SVAR match = root:Packages:NIST:VSANS:Globals:Patch:gPatchMatchStr
797        if(strlen(match) == 0 || cmpstr(match,"*")==0)          //if nothing or "*" entered for a match string, return everything, rather than nothing
798                match = "*"
799        // old way, with simply a wildcard
800                newlist = V_MyMatchList(match,newlist,";")
801                newList = SortList(newList,";",0)
802                return(newList)
803        endif
804       
805        //loop through all of the files as needed
806
807       
808        String list="",item="",fname,runList="",numStr=""
809        Variable ii,num=ItemsInList(newList),val,group_id
810        NVAR gRadioVal= root:Packages:NIST:VSANS:Globals:Patch:gRadioVal
811       
812        // run number list
813        if(gRadioVal == 1)
814                       
815                list = V_ExpandNumRanges(match)         //now simply comma delimited
816                num=ItemsInList(list,",")
817                for(ii=0;ii<num;ii+=1)
818                        item = StringFromList(ii,list,",")
819                        val=str2num(item)
820
821                        runList += V_GetFileNameFromPathNoSemi(V_FindFileFromRunNumber(val)) + ";"             
822                endfor
823                newlist = runList
824               
825        endif
826       
827        //grep through what text I can find in the VAX binary
828        // Grep Note: the \\b sequences limit matches to a word boundary before and after
829        // "boondoggle", so "boondoggles" and "aboondoggle" won't match.
830        if(gRadioVal == 2)
831                for(ii=0;ii<num;ii+=1)
832                        item=StringFromList(ii, newList , ";")
833//                      Grep/P=catPathName/Q/E=("(?i)\\b"+match+"\\b") item
834                        Grep/P=catPathName/Q/E=("(?i)"+match) item
835                        if( V_value )   // at least one instance was found
836//                              Print "found ", item,ii
837                                list += item + ";"
838                        endif
839                endfor
840
841                newList = list
842        endif
843       
844        // group_id
845        // replace this with: V_getSample_GroupID(fname)
846        Variable pos
847        String IDStr=""
848        if(gRadioVal == 3)
849                pos = strsearch(match, "*", 0)
850                if(pos == -1)           //no wildcard
851                        val = str2num(match)
852                else
853                        val = str2num(match[0,pos-1])
854                endif
855               
856//              print val
857                for(ii=0;ii<num;ii+=1)
858                        item=StringFromList(ii, newList , ";")
859                        fname = path + item
860                        group_id = V_getSample_GroupID(fname)
861                        if(group_id == val)
862                                list += item + ";"
863                        endif
864       
865                endfor
866               
867                newList = list
868        endif
869
870        newList = SortList(newList,";",0)
871        Return(newList)
872End
873
874
875
876
877// -- no longer refreshes the list - this seems redundant, and can be slow if grepping
878//
879//updates the popup list when the menu is "popped" so the list is
880//always fresh, then automatically displays the header of the popped file
881//value of match string is used in the creation of the list - use * to get
882//all valid files
883//
884Function V_PatchPopMenuProc(PatchPopup,popNum,popStr) : PopupMenuControl
885        String PatchPopup
886        Variable popNum
887        String popStr
888
889       
890//      String/G root:Packages:NIST:VSANS:Globals:Patch:gPatchList = list
891//      ControlUpdate PatchPopup
892        V_ShowHeaderButtonProc("SHButton")
893       
894        return(0)
895End
896
897
898//when text is entered in the match string, the popup list is refined to
899//include only the selected files, useful for trimming a lengthy list, or selecting
900//a range of files to patch
901//only one wildcard (*) is allowed
902//
903//change the contents of gPatchList that is displayed
904//based on selected Path, match str, and
905//further trim list to include only RAW SANS files
906//this will exclude version numbers, .AVE, .ABS files, etc. from the popup (which can't be patched)
907Function V_SetMatchStrProc(sva) : SetVariableControl
908        STRUCT WMSetVariableAction &sva
909
910        switch( sva.eventCode )
911                case 1: // mouse up
912                case 2: // Enter key
913                case 8:         // edit end
914                        Variable dval = sva.dval
915                        String sval = sva.sval
916                       
917                        String list = V_GetValidPatchPopupList()
918       
919                        String/G root:Packages:NIST:VSANS:Globals:Patch:gPatchList = list
920                        ControlUpdate PatchPopup
921                        PopupMenu PatchPopup,mode=1
922                       
923                        if(strlen(list) > 0)
924                                V_ShowHeaderButtonProc("SHButton")
925                        endif
926                case 3: // Live update
927
928                        break
929                case -1: // control being killed
930                        break
931        endswitch
932
933        return 0
934End
935
936//displays the header of the selected file (top in the popup) when the button is clicked
937//sort of a redundant button, since the procedure is automatically called (as if it were
938//clicked) when a new file is chosen from the popup
939//
940// TODO - make sure this is tab-aware
941//
942Function V_ShowHeaderButtonProc(SHButton) : ButtonControl
943        String SHButton
944
945        //displays (editable) header information about current file in popup control
946        //putting the values in the SetVariable displays (resetting the global variables)
947       
948        //get the popup string
949        String partialName, tempName
950        Variable ok
951        ControlInfo/W=V_Patch_Panel PatchPopup
952        If(strlen(S_value)==0 || cmpstr(S_Value,"none")==0)
953                //null selection
954                Abort "no file selected in popup menu"
955        else
956                //selection not null
957                partialName = S_value
958                //Print partialName
959        Endif
960        //get a valid file based on this partialName and catPathName
961        tempName = V_FindValidFilename(partialName)
962       
963        //prepend path to tempName for read routine
964        PathInfo catPathName
965        tempName = S_path + tempName
966       
967        //make sure the file is really a RAW data file
968        ok = V_CheckIfRawData(tempName)                 //--- This loads the whole file to read the instrument string
969        if (!ok)
970                Abort "this file is not recognized as a RAW SANS data file"
971        Endif
972       
973        //Print tempName
974       
975        V_ReadHeaderForPatch(tempName)
976       
977        ControlUpdate/A/W=V_Patch_Panel
978       
979        // no matter what tab is selected, show the file label
980        SVAR fileLabel = root:Packages:NIST:VSANS:Globals:Patch:gPatchCurLabel
981        fileLabel = V_getSampleDescription(tempName)
982       
983        return(0)
984End
985
986
987
988//simple function to get the string value from the popup list of filenames
989//returned string is only the text in the popup, a partial name with no path
990//or VAX version number.
991//
992Function/S V_GetPatchPopupString()
993
994        String str=""
995       
996        ControlInfo patchPopup
997        If(cmpstr(S_value,"")==0)
998                //null selection
999                Abort "no file selected in popup menu"
1000        else
1001                //selection not null
1002                str = S_value
1003                //Print str
1004        Endif
1005       
1006        Return str
1007End
1008
1009//Changes (writes to disk!) the specified changes to the (single) file selected in the popup
1010//reads the checkboxes to determine which (if any) values need to be written
1011//
1012// This currently makes sure the name is valid,
1013// determines the active tab,
1014// and dispatches to the correct (numbered) writer
1015//
1016Function V_ChangeHeaderButtonProc(CHButton) : ButtonControl
1017        String CHButton
1018
1019        String partialName="", tempName = ""
1020        Variable ok
1021        //get the popup string
1022        partialName = V_GetPatchPopupString()
1023       
1024        //get a valid file based on this partialName and catPathName
1025        tempName = V_FindValidFilename(partialName)
1026       
1027        //prepend path to tempName for read routine
1028        PathInfo catPathName
1029        tempName = S_path + tempName
1030       
1031        //make sure the file is really a RAW data file
1032        ok = V_CheckIfRawData(tempName)
1033        if (!ok)
1034                Abort "this file is not recognized as a RAW SANS data file"
1035        Endif
1036       
1037        // which tab is active?
1038        ControlInfo/W=V_Patch_Panel PatchTab
1039       
1040        switch(V_Value) // numeric switch
1041                case 0: // execute if case matches expression
1042                        V_WriteHeaderForPatch_0(tempName)               //control
1043                        break           // exit from switch
1044                case 1:
1045                        V_WriteHeaderForPatch_1(tempName)               //reduction
1046                        break
1047                case 2:
1048                        V_WriteHeaderForPatch_2(tempName)               // sample
1049                        break
1050                case 3:
1051                        V_WriteHeaderForPatch_3(tempName)               // instrument
1052                        break
1053                case 4:
1054                        V_WriteHeaderForPatch_4(tempName)               //detectors
1055                        break
1056                case 5:
1057                        V_WriteHeaderForPatch_5(tempName)               // polSANS
1058                        break
1059                default:                        // optional default expression executed
1060                        Abort "Tab not found - V_ChangeHeaderButtonProc"
1061        endswitch
1062
1063       
1064        //after writing the changes to the file
1065        // clean up, to force a reload from disk
1066        V_CleanupData_w_Progress(0,1)
1067       
1068        return(0)
1069End
1070
1071//     
1072//*****this function actually writes the data to disk*****
1073//
1074// DONE x- re-write a series of these function to mirror the "fill" functions
1075//   specific to each tab
1076//
1077// DONE x- clear out the old data and force a re-load from disk, or the old data
1078//    will be read in from the RawVSANS folder, and it will look like nothing was written
1079//                      (done in the calling function)
1080//
1081// currently, all errors are printed out by the writer, but ignored here
1082//
1083Function V_WriteHeaderForPatch_0(fname)
1084        String fname
1085       
1086        Variable val,err
1087        String textstr
1088               
1089        Wave/T listWave = root:Packages:NIST:VSANS:Globals:Patch:PP_ListWave
1090        Wave selWave = root:Packages:NIST:VSANS:Globals:Patch:PP_selWave
1091
1092        // test bit 4 to see if the checkbox is selected
1093        if ((selWave[0][0] & 2^4) != 0)         // Test if bit 4 is set
1094                val = str2num(listWave[0][2])
1095                err = V_writeCount_time(fname,val)              // count_time
1096        endif
1097
1098        if ((selWave[1][0] & 2^4) != 0)         // "detector_counts"
1099                val = str2num(listWave[1][2])
1100                err = V_writeDetector_counts(fname,val)
1101        endif   
1102       
1103        if ((selWave[2][0] & 2^4) != 0)         //"monitor_counts"
1104                val = str2num(listWave[2][2])
1105//              err = V_writeControlMonitorCount(fname,val)
1106                err = V_writeBeamMonNormData(fname,val)
1107        endif   
1108       
1109
1110
1111
1112        Return(0)
1113End
1114
1115//
1116// tab 1
1117//
1118Function V_WriteHeaderForPatch_1(fname)
1119        String fname
1120
1121        Variable val,err
1122        String str
1123               
1124        Wave/T listWave = root:Packages:NIST:VSANS:Globals:Patch:PP_ListWave
1125        Wave selWave = root:Packages:NIST:VSANS:Globals:Patch:PP_selWave
1126
1127        // test bit 4 to see if the checkbox is selected
1128        if ((selWave[0][0] & 2^4) != 0)         // Test if bit 4 is set
1129                str = listWave[0][2]                    // empty_beam_file_name
1130                err = V_writeEmptyBeamFileName(fname,str)               
1131        endif
1132
1133        if ((selWave[1][0] & 2^4) != 0)         // "background_file_name"
1134                str = listWave[1][2]
1135                err = V_writeBackgroundFileName(fname,str)
1136        endif   
1137       
1138        if ((selWave[2][0] & 2^4) != 0)         //"empty_file_name"
1139                str = listWave[2][2]
1140                err = V_writeEmptyFileName(fname,str)
1141        endif   
1142       
1143        if ((selWave[3][0] & 2^4) != 0)         //"sensitivity_file_name"
1144                str = listWave[3][2]
1145                err = V_writeSensitivityFileName(fname,str)
1146        endif   
1147       
1148        if ((selWave[4][0] & 2^4) != 0)         //"mask_file_name"
1149                str = listWave[4][2]
1150                err = V_writeMaskFileName(fname,str)
1151        endif   
1152       
1153        if ((selWave[5][0] & 2^4) != 0)         //"transmission_file_name"
1154                str = listWave[5][2]
1155                err = V_writeTransmissionFileName(fname,str)
1156        endif   
1157
1158        if ((selWave[6][0] & 2^4) != 0)         //"intent"
1159                str = listWave[6][2]
1160                err = V_writeReductionIntent(fname,str)
1161        endif   
1162       
1163        if ((selWave[7][0] & 2^4) != 0)         //"file_purpose"
1164                str = listWave[7][2]
1165                err = V_writeReduction_purpose(fname,str)
1166        endif           
1167
1168        if ((selWave[8][0] & 2^4) != 0)         //"group_id (sample)"
1169                val = str2num(listWave[8][2])
1170                err = V_writeSample_GroupID(fname,val)
1171        endif   
1172
1173
1174
1175        if ((selWave[9][0] & 2^4) != 0)         //"box coordinates"
1176                str = listWave[9][2]
1177                err = V_writeBoxCoordinates(fname,V_List2NumWave(str,";","inW"))
1178        endif   
1179       
1180
1181       
1182        if ((selWave[10][0] & 2^4) != 0)                //"box_count"
1183                val = str2num(listWave[10][2])
1184                err = V_writeBoxCounts(fname,val)
1185        endif   
1186       
1187        if ((selWave[11][0] & 2^4) != 0)                //"box_count_error"
1188                val = str2num(listWave[11][2])
1189                err = V_writeBoxCountsError(fname,val)
1190        endif   
1191       
1192        if ((selWave[12][0] & 2^4) != 0)                //"whole_trans"
1193                val = str2num(listWave[12][2])
1194                err = V_writeSampleTransWholeDetector(fname,val)
1195        endif   
1196       
1197        if ((selWave[13][0] & 2^4) != 0)                //"whole_trans_error"
1198                val = str2num(listWave[13][2])
1199                err = V_writeSampleTransWholeDetErr(fname,val)
1200        endif   
1201       
1202       
1203               
1204               
1205        return(0)
1206End
1207
1208// SAMPLE
1209Function V_WriteHeaderForPatch_2(fname)
1210        String fname
1211       
1212        Variable val,err
1213        String str
1214               
1215        Wave/T listWave = root:Packages:NIST:VSANS:Globals:Patch:PP_ListWave
1216        Wave selWave = root:Packages:NIST:VSANS:Globals:Patch:PP_selWave
1217
1218        // test bit 4 to see if the checkbox is selected
1219        if ((selWave[0][0] & 2^4) != 0)         // Test if bit 4 is set
1220                str = listWave[0][2]                    // "description"
1221                err = V_writeSampleDescription(fname,str)               
1222        endif
1223
1224        if ((selWave[1][0] & 2^4) != 0)         // "thickness"
1225                val = str2num(listWave[1][2])
1226                err = V_writeSampleThickness(fname,val)
1227        endif   
1228       
1229        if ((selWave[2][0] & 2^4) != 0)         //"transmission"
1230                val = str2num(listWave[2][2])
1231                err = V_writeSampleTransmission(fname,val)
1232        endif   
1233       
1234        if ((selWave[3][0] & 2^4) != 0)         //"transmission_error"
1235                val = str2num(listWave[3][2])
1236                err = V_writeSampleTransError(fname,val)
1237        endif   
1238       
1239        return(0)
1240End
1241
1242// INSTRUMENT
1243Function V_WriteHeaderForPatch_3(fname)
1244        String fname
1245
1246        Variable val,err
1247        String str
1248               
1249        Wave/T listWave = root:Packages:NIST:VSANS:Globals:Patch:PP_ListWave
1250        Wave selWave = root:Packages:NIST:VSANS:Globals:Patch:PP_selWave
1251
1252        // test bit 4 to see if the checkbox is selected
1253        if ((selWave[0][0] & 2^4) != 0)         // Test if bit 4 is set
1254                val = str2num(listWave[0][2])                   // "attenuator_transmission"
1255                err = V_writeAttenuator_transmission(fname,val)         
1256        endif
1257
1258        if ((selWave[1][0] & 2^4) != 0)         // "attenuator_transmission_error"
1259                val = str2num(listWave[1][2])
1260                err = V_writeAttenuator_trans_err(fname,val)
1261        endif   
1262       
1263        if ((selWave[2][0] & 2^4) != 0)         //"monochromator type"
1264                str = listWave[2][2]
1265                err = V_writeMonochromatorType(fname,str)
1266        endif   
1267       
1268        if ((selWave[3][0] & 2^4) != 0)         //"wavelength"
1269                val = str2num(listWave[3][2])
1270                err = V_writeWavelength(fname,val)
1271        endif   
1272
1273        if ((selWave[4][0] & 2^4) != 0)         //"wavelength_spread"
1274                val = str2num(listWave[4][2])
1275                err = V_writeWavelength_spread(fname,val)
1276        endif   
1277
1278        if ((selWave[5][0] & 2^4) != 0)         //"number of guides (a string value)"
1279                str = listWave[5][2]
1280                err = V_writeNumberOfGuides(fname,str)
1281        endif           
1282       
1283        if ((selWave[6][0] & 2^4) != 0)         //"distance (source aperture)"
1284                val = str2num(listWave[6][2])
1285                err = V_writeSourceAp_distance(fname,val)
1286        endif           
1287
1288        if ((selWave[7][0] & 2^4) != 0)         //"source aperture size [mm]" (a string with units)
1289                str = listWave[7][2]
1290                err = V_writeSourceAp_size(fname,str)
1291        endif           
1292
1293        if ((selWave[8][0] & 2^4) != 0)         //"sample aperture size (internal) [mm]" (a string with units)
1294                str = listWave[8][2]
1295                err = V_writeSampleAp_size(fname,str)
1296        endif   
1297
1298        if ((selWave[9][0] & 2^4) != 0)         //"sample aperture SHAPE (external) [cm]"
1299                str = listWave[9][2]
1300                err = V_writeSampleAp2_shape(fname,str)
1301        endif           
1302       
1303        if ((selWave[10][0] & 2^4) != 0)                //"sample aperture diam (external) [cm]"
1304                val = str2num(listWave[10][2])
1305                err = V_writeSampleAp2_size(fname,val)
1306        endif           
1307       
1308        if ((selWave[11][0] & 2^4) != 0)                //"sample aperture height (external) [cm]"
1309                val = str2num(listWave[11][2])
1310                err = V_writeSampleAp2_height(fname,val)
1311        endif           
1312               
1313        if ((selWave[12][0] & 2^4) != 0)                //"sample aperture width (external) [cm]"
1314                val = str2num(listWave[12][2])
1315                err = V_writeSampleAp2_width(fname,val)
1316        endif           
1317
1318        if ((selWave[13][0] & 2^4) != 0)                //"beam stop diameter (Middle) [mm]"
1319                val = str2num(listWave[13][2])
1320                err = V_writeBeamStopC2_size(fname,val)
1321        endif           
1322       
1323        if ((selWave[14][0] & 2^4) != 0)                //"beam stop diameter (Back) [mm]"
1324                val = str2num(listWave[14][2])
1325                err = V_writeBeamStopC3_size(fname,val)
1326        endif           
1327
1328        if ((selWave[15][0] & 2^4) != 0)                //"sample aperture to gate valve [cm]"
1329                val = str2num(listWave[15][2])
1330                err = V_writeSampleAp_distance(fname,val)
1331        endif   
1332
1333        if ((selWave[16][0] & 2^4) != 0)                //"sample to gate valve [cm]"
1334                val = str2num(listWave[16][2])
1335                err = V_writeSampleTableOffset(fname,val)
1336        endif           
1337       
1338        return(0)
1339End
1340
1341// DETECTOR
1342Function V_WriteHeaderForPatch_4(fname)
1343        String fname
1344
1345        Variable val,err
1346        String str
1347               
1348        Wave/T listWave = root:Packages:NIST:VSANS:Globals:Patch:PP_ListWave
1349        Wave selWave = root:Packages:NIST:VSANS:Globals:Patch:PP_selWave
1350
1351        ControlInfo popup_0
1352        String detStr = S_Value
1353
1354        // test bit 4 to see if the checkbox is selected
1355        if ((selWave[0][0] & 2^4) != 0)         // Test if bit 4 is set
1356                val = str2num(listWave[0][2])                   // "beam_center_x"
1357                err = V_writeDet_beam_center_x(fname,detStr,val)       
1358        endif
1359
1360        if ((selWave[1][0] & 2^4) != 0)         // "beam_center_y"
1361                val = str2num(listWave[1][2])
1362                err = V_writeDet_beam_center_y(fname,detStr,val)
1363        endif   
1364       
1365        if ((selWave[2][0] & 2^4) != 0)         //"distance (nominal)"
1366                val = str2num(listWave[2][2])
1367                err = V_writeDet_distance(fname,detStr,val)
1368        endif   
1369       
1370        if ((selWave[3][0] & 2^4) != 0)         //"integrated_count"
1371                val = str2num(listWave[3][2])
1372                err = V_writeDet_IntegratedCount(fname,detStr,val)
1373        endif   
1374       
1375        if ((selWave[4][0] & 2^4) != 0)         //"pixel_fwhm_x"
1376                val = str2num(listWave[4][2])
1377                err = V_writeDet_pixel_fwhm_x(fname,detStr,val)
1378        endif   
1379       
1380        if ((selWave[5][0] & 2^4) != 0)         //"pixel_fwhm_y"
1381                val = str2num(listWave[5][2])
1382                err = V_writeDet_pixel_fwhm_y(fname,detStr,val)
1383        endif   
1384
1385        if ((selWave[6][0] & 2^4) != 0)         //"pixel_num_x"
1386                val = str2num(listWave[6][2])
1387                err = V_writeDet_pixel_num_x(fname,detStr,val)
1388        endif   
1389       
1390        if ((selWave[7][0] & 2^4) != 0)         //"pixel_num_y"
1391                val = str2num(listWave[7][2])
1392                err = V_writeDet_pixel_num_y(fname,detStr,val)
1393        endif           
1394       
1395        if ((selWave[8][0] & 2^4) != 0)         //"setback" -- only for TB detectors
1396                val = str2num(listWave[8][2])
1397                if(cmpstr(detStr,"FT") == 0 || cmpstr(detStr,"FB") == 0 || cmpstr(detStr,"MT") == 0 || cmpstr(detStr,"MB") == 0)
1398                        err = V_writeDet_TBSetback(fname,detStr,val)
1399                endif
1400        endif   
1401
1402        if ((selWave[9][0] & 2^4) != 0)         //"lateral_offset" or "vertical_offset"
1403                val = str2num(listWave[9][2])
1404                if(cmpstr(detStr,"B") == 0 ||cmpstr(detStr,"FR") == 0 || cmpstr(detStr,"FL") == 0 || cmpstr(detStr,"MR") == 0 || cmpstr(detStr,"ML") == 0)
1405                        err = V_writeDet_LateralOffset(fname,detStr,val)
1406                else
1407                        err = V_writeDet_VerticalOffset(fname,detStr,val)
1408                endif
1409        endif   
1410       
1411        if ((selWave[10][0] & 2^4) != 0)                //"x_pixel_size"
1412                val = str2num(listWave[10][2])
1413                err = V_writeDet_x_pixel_size(fname,detStr,val)
1414        endif   
1415       
1416        if ((selWave[11][0] & 2^4) != 0)                //"y_pixel_size"
1417                val = str2num(listWave[11][2])
1418                err = V_writeDet_y_pixel_size(fname,detStr,val)
1419        endif   
1420       
1421        if ((selWave[12][0] & 2^4) != 0)                //"dead time, "B" only"
1422                val = str2num(listWave[12][2])
1423                if(cmpstr(detStr,"B") == 0)
1424                        err = V_writeDetector_deadtime_B(fname,detStr,val)
1425                endif
1426        endif   
1427
1428       
1429        return(0)
1430End
1431
1432// TODO -- not yet implemented
1433Function V_WriteHeaderForPatch_5(fname)
1434        String fname
1435       
1436        return(0)
1437End
1438
1439
1440// control the display of the radio buttons
1441Function V_MatchCheckProc(name,value)
1442        String name
1443        Variable value
1444       
1445        NVAR gRadioVal= root:Packages:NIST:VSANS:Globals:Patch:gRadioVal
1446       
1447        strswitch (name)
1448                case "check0":
1449                        gRadioVal= 1
1450                        break
1451                case "check1":
1452                        gRadioVal= 2
1453                        break
1454                case "check2":
1455                        gRadioVal= 3
1456                        break
1457        endswitch
1458        CheckBox check0,value= gRadioVal==1
1459        CheckBox check1,value= gRadioVal==2
1460        CheckBox check2,value= gRadioVal==3
1461        return(0)
1462End
1463
1464//This function will read only the selected values editable in the patch panel
1465//
1466// DONE
1467// x- re-write this to be tab-aware. ShowHeaderForPatch() calls this, but does nothing
1468//    to update the tab content. Figure out which function is in charge, and update the content.
1469//
1470Function V_ReadHeaderForPatch(fname)
1471        String fname
1472       
1473       
1474        // figure out which is the active tab, then let PatchTabProc fill it in
1475        ControlInfo/W=V_Patch_Panel PatchTab
1476        V_PatchTabProc("",V_Value)     
1477       
1478        Return 0
1479End
1480
1481Function V_ShowPatchHelp(ctrlName) : ButtonControl
1482        String ctrlName
1483//      DisplayHelpTopic/Z/K=1 "VSANS Data Reduction Tutorial[Patch File Headers]"
1484//      if(V_flag !=0)
1485                DoAlert 0,"The VSANS Data Reduction Tutorial Help file could not be found"
1486//      endif
1487        return(0)
1488End
1489
1490//button action procedure to change the selected information (checked values)
1491//in each file in the popup list. This will change multiple files, and as such,
1492//the user is given a chance to bail out before the whole list of files
1493//is modified
1494//useful for patching a series of runs with the same beamcenters, or transmissions
1495//
1496Function V_ChAllHeadersButtonProc(ctrlName) : ButtonControl
1497        String ctrlName
1498       
1499        String msg
1500        msg = "Do you really want to write all of these values to each data file in the popup list? "
1501        msg += "- clicking NO will leave all files unchanged"
1502        DoAlert 1,msg
1503        If(V_flag == 2)
1504                Abort "no files were changed"
1505        Endif
1506       
1507        //this will change (checked) values in ALL of the headers in the popup list
1508        SVAR list = root:Packages:NIST:VSANS:Globals:Patch:gPatchList
1509        Variable numitems,ii
1510        String partialName="", tempName = ""
1511        Variable ok
1512       
1513        numitems = ItemsInList(list,";")
1514       
1515        if(numitems == 0)
1516                Abort "no items in list for multiple patch"
1517        Endif
1518       
1519        // loop through all of the files
1520        ii=0
1521        do
1522                //get current item in the list
1523                partialName = StringFromList(ii, list, ";")
1524                   
1525                //get a valid file based on this partialName and catPathName
1526                tempName = V_FindValidFilename(partialName)
1527       
1528                //prepend path to tempName for read routine
1529                PathInfo catPathName
1530                tempName = S_path + tempName
1531       
1532                //make sure the file is really a RAW data file
1533                ok = V_CheckIfRawData(tempName)
1534                if (!ok)
1535                   Print "this file is not recognized as a RAW SANS data file = ",tempName
1536                else
1537                   //go write the changes to the file
1538                        // which tab is active?
1539                        ControlInfo/W=V_Patch_Panel PatchTab
1540                       
1541                        switch(V_Value) // numeric switch
1542                                case 0: // execute if case matches expression
1543                                        V_WriteHeaderForPatch_0(tempName)
1544                                        break           // exit from switch
1545                                case 1:
1546                                        V_WriteHeaderForPatch_1(tempName)
1547                                        break
1548                                case 2:
1549                                        V_WriteHeaderForPatch_2(tempName)
1550                                        break
1551                                case 3:
1552                                        V_WriteHeaderForPatch_3(tempName)
1553                                        break
1554                                case 4:
1555                                        V_WriteHeaderForPatch_4(tempName)
1556                                        break
1557                                case 5:
1558                                        V_WriteHeaderForPatch_5(tempName)
1559                                        break
1560                                default:                        // optional default expression executed
1561                                        Abort "Tab not found - V_ChAllHeadersButtonProc"
1562                        endswitch
1563                Endif
1564               
1565                ii+=1
1566        while(ii<numitems)
1567
1568
1569        //after writing the changes to the file
1570        // clean up, to force a reload from disk
1571        V_CleanupData_w_Progress(0,1)
1572
1573        return(0)
1574End
1575
1576
1577//simple action for button to close the panel
1578//
1579// cleans out the RawVSANS folder on closing
1580//
1581Function V_DoneButtonProc(ctrlName) : ButtonControl
1582        String ctrlName
1583
1584        DoWindow/K V_Patch_Panel
1585
1586//      V_CleanOutRawVSANS()
1587// present a progress window
1588        V_CleanupData_w_Progress(0,1)   
1589       
1590        return(0)
1591End
1592
1593
1594
1595////////////////////////////////////////////////////////////////////////////////////////////////////////////////
1596////////////////////////////////////////////////////////////////////////////////////////////////////////////////
1597///////////////
1598//
1599// this is a block to patch DEADTIME waves to the file headers, and can patch multiple files
1600//
1601// uses a simple panel to show what the table of values is.
1602// "read" will read only the first run number contents.
1603//
1604// TODO -- need to clear out the contents from RawVSANS, or else re-reading to check the values
1605//        will read locally, and it will look like nothing was written. Executing "save" will also
1606//        trigger a cleanout.
1607//
1608// TODO -- link this to a panel somewhere - a button? menu item? will there be a lot more of these little panels?
1609//
1610// TODO -- currently, this does not patch the deadtime for the back "B" detector. it is a single
1611//        value, not a wave see V_WritePerfectDeadTime(filename) for how the perfect (fake) values is written.
1612//
1613//
1614Proc V_PatchDetectorDeadtime(firstFile,lastFile,detStr,deadtimeStr)
1615        Variable firstFile=1,lastFile=100
1616        String detStr = "FL",deadtimeStr="deadTimeWave"
1617
1618        V_fPatchDetectorDeadtime(firstFile,lastFile,detStr,$deadtimeStr)
1619
1620End
1621
1622Proc V_ReadDetectorDeadtime(firstFile,lastFile,detStr)
1623        Variable firstFile=1,lastFile=100
1624        String detStr = "FL"
1625       
1626        V_fReadDetectorDeadtime(firstFile,lastFile,detStr)
1627       
1628End
1629
1630// simple utility to patch the detector deadtime in the file headers
1631// lo is the first file number
1632// hi is the last file number (inclusive)
1633//
1634Function V_fPatchDetectorDeadtime(lo,hi,detStr,deadtimeW)
1635        Variable lo,hi
1636        String detStr
1637        Wave deadtimeW
1638       
1639        Variable ii
1640        String fname
1641       
1642        // check the dimensions of the deadtimeW/N=48
1643        if (DimSize(deadtimeW, 0) != 48 )
1644                Abort "dead time wave is not of proper dimension (48)"
1645        endif
1646       
1647        //loop over all files
1648        for(ii=lo;ii<=hi;ii+=1)
1649                fname = V_FindFileFromRunNumber(ii)
1650                if(strlen(fname) != 0)
1651                        V_writeDetector_deadtime(fname,detStr,deadtimeW)                       
1652                else
1653                        printf "run number %d not found\r",ii
1654                endif
1655        endfor
1656       
1657        return(0)
1658End
1659
1660// simple utility to read the detector deadtime stored in the file header
1661Function V_fReadDetectorDeadtime(lo,hi,detStr)
1662        Variable lo,hi
1663        String detStr
1664       
1665        String fname
1666        Variable ii
1667       
1668        for(ii=lo;ii<=hi;ii+=1)
1669                fname = V_FindFileFromRunNumber(ii)
1670                if(strlen(fname) != 0)
1671                        Wave deadtimeW = V_getDetector_deadtime(fname,detStr)
1672                        Duplicate/O deadTimeW root:Packages:NIST:VSANS:Globals:Patch:deadtimeWave
1673//                      printf "File %d:  Detector Dead time (s) = %g\r",ii,deadtime
1674                else
1675                        printf "run number %d not found\r",ii
1676                endif
1677        endfor
1678       
1679        return(0)
1680End
1681
1682
1683
1684Proc V_PatchDetectorDeadtimePanel()
1685        DoWindow/F DeadtimePanel
1686        if(V_flag==0)
1687       
1688                NewDataFolder/O/S root:Packages:NIST:VSANS:Globals:Patch
1689
1690                Make/O/D/N=48 deadTimeWave
1691                Variable/G gFileNum_Lo,gFileNum_Hi
1692               
1693                SetDataFolder root:
1694               
1695                Execute "V_DeadtimePatchPanel()"
1696        endif
1697End
1698
1699
1700// TODO:
1701// x- add method for generating "perfect" dead time to write
1702// x- check deadtime wave dimension before writing (check for bad paste operation)
1703// -- load from file? different ways to import?
1704// -- Dead time constants for "B" are different, and not handled here (yet)
1705// -- add help button/file
1706// -- add done button
1707// -- adjust after user testing
1708//
1709Proc V_DeadtimePatchPanel() : Panel
1710        PauseUpdate; Silent 1           // building window...
1711
1712
1713        NewPanel /W=(600,400,1000,1000)/N=DeadtimePanel /K=1
1714//      ShowTools/A
1715        ModifyPanel cbRGB=(16266,47753,2552,23355)
1716
1717        SetDrawLayer UserBack
1718        DrawText 85,99,"Current Values"
1719        DrawText 21,258,"Write to all files (inlcusive)"
1720        SetDrawEnv fsize= 14,fstyle= 1
1721        DrawText 209,30,"Dead Time Constants"
1722        DrawText 20,133,"Run Number(s)"
1723       
1724        PopupMenu popup_0,pos={20,40},size={109,20},title="Detector Panel"
1725        PopupMenu popup_0,mode=1,popvalue="FL",value= #"\"FL;FR;FT;FB;ML;MR;MT;MB;\""
1726       
1727        Button button0,pos={20,81},size={50.00,20.00},proc=V_ReadDTButtonProc,title="Read"
1728        Button button0_1,pos={20,220},size={50.00,20.00},proc=V_WriteDTButtonProc,title="Write"
1729        Button button0_2,pos={18.00,336.00},size={140.00,20.00},proc=V_GeneratePerfDTButton,title="Perfect Dead Time"
1730        Button button0_3,pos={18.00,370.00},size={140.00,20.00},proc=V_LoadCSVDTButton,title="Load Dead Time CSV"
1731        Button button0_4,pos={18.00,400.00},size={140.00,20.00},proc=V_WriteCSVDTButton,title="Write Dead Time CSV"
1732       
1733        SetVariable setvar0,pos={20,141},size={100.00,14.00},title="first"
1734        SetVariable setvar0,value= root:Packages:NIST:VSANS:Globals:Patch:gFileNum_Lo
1735        SetVariable setvar1,pos={20.00,167},size={100.00,14.00},title="last"
1736        SetVariable setvar1,value= root:Packages:NIST:VSANS:Globals:Patch:gFileNum_Hi
1737
1738
1739// display the wave     
1740        Edit/W=(180,40,380,550)/HOST=#  root:Packages:NIST:VSANS:Globals:Patch:deadTimeWave
1741        ModifyTable width(Point)=40
1742        ModifyTable width(root:Packages:NIST:VSANS:Globals:Patch:deadTimeWave)=120
1743        RenameWindow #,T0
1744        SetActiveSubwindow ##
1745
1746       
1747EndMacro
1748
1749
1750Function V_LoadCSVDTButton(ba) : ButtonControl
1751        STRUCT WMButtonAction &ba
1752
1753        switch( ba.eventCode )
1754                case 2: // mouse up
1755                        // click code here
1756
1757                        LoadWave/J/A/D/O/W/E=1/K=0                              //will prompt for the file, auto name
1758                       
1759                        break
1760                case -1: // control being killed
1761                        break
1762        endswitch
1763
1764        return 0
1765End
1766
1767//TODO
1768// -- currently this skips detector "B", since its dead time is not like the tubes
1769// -- fails miserably if the deadtime_** waves don't exist
1770// -- the writing may take a long time. Warn the user.
1771// -- if the data files are not "cleaned up", re-reading will pick up the rawVSANS copy and it
1772//    will look like nothing was written
1773//
1774// writes the entire content of the CSV file (all 8 panels) to each detector entry in each data file
1775// as specified by the run number range
1776//
1777Function V_WriteCSVDTButton(ba) : ButtonControl
1778        STRUCT WMButtonAction &ba
1779
1780        Variable ii
1781        String detStr
1782       
1783        switch( ba.eventCode )
1784                case 2: // mouse up
1785                        // click code here
1786                       
1787//                      ControlInfo popup_0
1788//                      String detStr = S_Value
1789                        ControlInfo setvar0
1790                        Variable lo=V_Value
1791                        ControlInfo setvar1
1792                        Variable hi=V_Value
1793                        Wave deadTimeW = root:Packages:NIST:VSANS:Globals:Patch:deadTimeWave
1794                       
1795                        for(ii=0;ii<ItemsInList(ksDetectorListNoB);ii+=1)
1796                                detStr = StringFromList(ii, ksDetectorListNoB, ";")
1797                                Wave tmpW = $("root:deadtime_"+detStr)
1798                                deadTimeW = tmpW
1799                                V_fPatchDetectorDeadtime(lo,hi,detStr,deadtimeW)
1800                        endfor
1801                       
1802                        break
1803                case -1: // control being killed
1804                        break
1805        endswitch
1806
1807        // TODO
1808        // -- clear out the data folders (from lo to hi?)
1809//
1810// root:Packages:NIST:VSANS:RawVSANS:sans1301:
1811        for(ii=lo;ii<=hi;ii+=1)
1812                KillDataFolder/Z $("root:Packages:NIST:VSANS:RawVSANS:sans"+num2istr(ii))
1813        endfor
1814        return 0
1815End
1816
1817
1818Function V_GeneratePerfDTButton(ba) : ButtonControl
1819        STRUCT WMButtonAction &ba
1820
1821        switch( ba.eventCode )
1822                case 2: // mouse up
1823                        // click code here
1824
1825                        WAVE deadTimeWave = root:Packages:NIST:VSANS:Globals:Patch:deadTimeWave
1826                        ControlInfo popup_0
1827                        strswitch(S_Value)
1828                                case "FR":
1829                                case "FL":
1830                                case "MR":
1831                                case "ML":
1832                                case "FT":
1833                                case "FB":
1834                                case "MT":
1835                                case "MB":
1836                                        deadTimeWave = 1e-18
1837
1838                                        break
1839                                default:
1840                                        Print "Det type not found: V_GeneratePerfDTButton()"
1841                        endswitch
1842                       
1843                        break
1844                case -1: // control being killed
1845                        break
1846        endswitch
1847
1848        return 0
1849End
1850
1851
1852
1853
1854Function V_ReadDTButtonProc(ba) : ButtonControl
1855        STRUCT WMButtonAction &ba
1856
1857        switch( ba.eventCode )
1858                case 2: // mouse up
1859                        // click code here
1860                       
1861                        ControlInfo popup_0
1862                        String detStr = S_Value
1863                        ControlInfo setvar0
1864                        Variable lo=V_Value
1865                        Variable hi=lo
1866                       
1867                        V_fReadDetectorDeadtime(lo,hi,detStr)
1868                       
1869                        break
1870                case -1: // control being killed
1871                        break
1872        endswitch
1873
1874        return 0
1875End
1876
1877Function V_WriteDTButtonProc(ba) : ButtonControl
1878        STRUCT WMButtonAction &ba
1879
1880        switch( ba.eventCode )
1881                case 2: // mouse up
1882                        // click code here
1883                       
1884                        ControlInfo popup_0
1885                        String detStr = S_Value
1886                        ControlInfo setvar0
1887                        Variable lo=V_Value
1888                        ControlInfo setvar1
1889                        Variable hi=V_Value
1890                        Wave deadTimeW = root:Packages:NIST:VSANS:Globals:Patch:deadTimeWave
1891                       
1892                        V_fPatchDetectorDeadtime(lo,hi,detStr,deadtimeW)
1893                       
1894                        break
1895                case -1: // control being killed
1896                        break
1897        endswitch
1898
1899        return 0
1900End
1901
1902//////////////////////////////////////////////////////////////////////////////////////////////////
1903//////////////////////////////////////////////////////////////////////////////////////////////////
1904// this is a block to patch CALIBRATION waves to the file headers, and can patch multiple files
1905//
1906// uses a simple panel to show what the table of values is.
1907// "read" will read only the first run number contents.
1908//
1909// TODO -- need to clear out the contents from RawVSANS, or else re-reading to check the values
1910//        will read locally, and it will look like nothing was written. Executing "save" will also
1911//        trigger a cleanout.
1912//
1913// TODO -- link this to a panel somewhere - a button? menu item? will there be a lot more of these little panels?
1914//
1915// TODO -- currently this does not handle the back detector "B". see V_WritePerfectSpatialCalib(filename)
1916//         for how fake data is written to the files
1917//
1918// TODO -- verify that the calibration waves are not transposed
1919//
1920Proc V_PatchDetectorCalibration(firstFile,lastFile,detStr,calibStr)
1921        Variable firstFile=1,lastFile=100
1922        String detStr = "FL",calibStr="calibrationWave"
1923
1924        V_fPatchDetectorCalibration(firstFile,lastFile,detStr,$calibStr)
1925
1926End
1927
1928Proc V_ReadDetectorCalibration(firstFile,lastFile,detStr)
1929        Variable firstFile=1,lastFile=100
1930        String detStr = "FL"
1931       
1932        V_fReadDetectorCalibration(firstFile,lastFile,detStr)
1933End
1934
1935// simple utility to patch the detector calibration wave in the file headers
1936// lo is the first file number
1937// hi is the last file number (inclusive)
1938//
1939Function V_fPatchDetectorCalibration(lo,hi,detStr,calibW)
1940        Variable lo,hi
1941        String detStr
1942        Wave calibW
1943       
1944        Variable ii
1945        String fname
1946       
1947        // check the dimensions of the calibW (3,48)
1948        if (DimSize(calibW, 0) != 3 || DimSize(calibW, 1) != 48 )
1949                Abort "Calibration wave is not of proper dimension (3,48)"
1950        endif
1951       
1952        //loop over all files
1953        for(ii=lo;ii<=hi;ii+=1)
1954                fname = V_FindFileFromRunNumber(ii)
1955                if(strlen(fname) != 0)
1956                        V_writeDetTube_spatialCalib(fname,detStr,calibW)                       
1957                else
1958                        printf "run number %d not found\r",ii
1959                endif
1960        endfor
1961       
1962        return(0)
1963End
1964
1965// simple utility to read the detector deadtime stored in the file header
1966Function V_fReadDetectorCalibration(lo,hi,detStr)
1967        Variable lo,hi
1968        String detStr
1969       
1970        String fname
1971        Variable ii
1972       
1973        for(ii=lo;ii<=hi;ii+=1)
1974                fname = V_FindFileFromRunNumber(ii)
1975                if(strlen(fname) != 0)
1976                        Wave calibW = V_getDetTube_spatialCalib(fname,detStr)
1977                        Duplicate/O calibW root:Packages:NIST:VSANS:Globals:Patch:calibrationWave
1978                else
1979                        printf "run number %d not found\r",ii
1980                endif
1981        endfor
1982       
1983        return(0)
1984End
1985
1986
1987Proc V_PatchDetectorCalibrationPanel()
1988        DoWindow/F CalibrationPanel
1989        if(V_flag==0)
1990       
1991                NewDataFolder/O/S root:Packages:NIST:VSANS:Globals:Patch
1992
1993                Make/O/D/N=(3,48) calibrationWave
1994               
1995                Variable/G gFileNum_Lo,gFileNum_Hi
1996                SetDataFolder root:
1997               
1998                Execute "V_CalibrationPatchPanel()"
1999        endif
2000End
2001
2002
2003//
2004// TODO:
2005// x- add method for generating "perfect" calibration to write
2006// x- check Nx3 dimension before writing (check for bad paste operation)
2007// -- load from file? different ways to import?
2008// -- calibration constants for "B" are different, and not handled here (yet)
2009// -- add help button/file
2010// -- add done button
2011// -- adjust after user testing
2012//
2013Proc V_CalibrationPatchPanel() : Panel
2014        PauseUpdate; Silent 1           // building window...
2015
2016
2017        NewPanel /W=(600,400,1200,1000)/N=CalibrationPanel /K=1
2018//      ShowTools/A
2019        ModifyPanel cbRGB=(16266,47753,2552,23355)
2020
2021        SetDrawLayer UserBack
2022        DrawText 85,99,"Current Values"
2023        DrawText 21,258,"Write to all files (inlcusive)"
2024        SetDrawEnv fsize= 14,fstyle= 1
2025        DrawText 227,28,"Quadratic Calibration Constants per Tube"
2026        DrawText 20,133,"Run Number(s)"
2027               
2028        PopupMenu popup_0,pos={20,40},size={109,20},title="Detector Panel"
2029        PopupMenu popup_0,mode=1,popvalue="FL",value= #"\"FL;FR;FT;FB;ML;MR;MT;MB;\""
2030       
2031        Button button0,pos={20,81},size={50.00,20.00},proc=V_ReadCalibButtonProc,title="Read"
2032        Button button0_1,pos={20,220},size={50.00,20.00},proc=V_WriteCalibButtonProc,title="Write"
2033        Button button0_2,pos={18.00,336.00},size={140.00,20.00},proc=V_GeneratePerfCalibButton,title="Perfect Calibration"
2034        Button button0_3,pos={18.00,370.00},size={140.00,20.00},proc=V_LoadCSVCalibButton,title="Load Calibration CSV"
2035        Button button0_4,pos={18.00,400.00},size={140.00,20.00},proc=V_WriteCSVCalibButton,title="Write Calibration CSV"
2036               
2037        SetVariable setvar0,pos={20,141},size={100.00,14.00},title="first"
2038        SetVariable setvar0,value= root:Packages:NIST:VSANS:Globals:Patch:gFileNum_Lo
2039        SetVariable setvar1,pos={20.00,167},size={100.00,14.00},title="last"
2040        SetVariable setvar1,value= root:Packages:NIST:VSANS:Globals:Patch:gFileNum_Hi
2041
2042
2043// display the wave     
2044        Edit/W=(180,40,580,550)/HOST=#  root:Packages:NIST:VSANS:Globals:Patch:calibrationWave
2045        ModifyTable width(Point)=40
2046        ModifyTable width(root:Packages:NIST:VSANS:Globals:Patch:calibrationWave)=110
2047        // the elements() command transposes the view in the table, but does not transpose the wave
2048        ModifyTable elements(root:Packages:NIST:VSANS:Globals:Patch:calibrationWave) = (-3, -2)
2049        RenameWindow #,T0
2050        SetActiveSubwindow ##
2051
2052       
2053EndMacro
2054
2055
2056Function V_LoadCSVCalibButton(ba) : ButtonControl
2057        STRUCT WMButtonAction &ba
2058
2059        switch( ba.eventCode )
2060                case 2: // mouse up
2061                        // click code here
2062
2063                        LoadWave/J/A/D/O/W/E=1/K=0                              //will prompt for the file, auto name
2064                       
2065                        break
2066                case -1: // control being killed
2067                        break
2068        endswitch
2069
2070        return 0
2071End
2072
2073//TODO
2074// -- currently this skips detector "B", since its calibration is not like the tubes
2075// -- fails miserably if the a,b,c_** waves don't exist
2076// -- the writing may take a long time. Warn the user.
2077// -- if the data files are not "cleaned up", re-reading will pick up the rawVSANS copy and it
2078//    will look like nothing was written
2079//
2080// writes the entire content of the CSV file (all 8 panels) to each detector entry in each data file
2081// as specified by the run number range
2082//
2083Function V_WriteCSVCalibButton(ba) : ButtonControl
2084        STRUCT WMButtonAction &ba
2085
2086        Variable ii
2087        String detStr
2088       
2089        switch( ba.eventCode )
2090                case 2: // mouse up
2091                        // click code here
2092                       
2093//                      ControlInfo popup_0
2094//                      String detStr = S_Value
2095                        ControlInfo setvar0
2096                        Variable lo=V_Value
2097                        ControlInfo setvar1
2098                        Variable hi=V_Value
2099                        WAVE calibrationWave = root:Packages:NIST:VSANS:Globals:Patch:calibrationWave
2100                       
2101                        for(ii=0;ii<ItemsInList(ksDetectorListNoB);ii+=1)
2102                                detStr = StringFromList(ii, ksDetectorListNoB, ";")
2103                                Wave tmp_a = $("root:a_"+detStr)
2104                                Wave tmp_b = $("root:b_"+detStr)
2105                                Wave tmp_c = $("root:c_"+detStr)
2106                                calibrationWave[0][] = tmp_a[q]
2107                                calibrationWave[1][] = tmp_b[q]
2108                                calibrationWave[2][] = tmp_c[q]
2109                                V_fPatchDetectorCalibration(lo,hi,detStr,calibrationWave)
2110                        endfor
2111                       
2112                        break
2113                case -1: // control being killed
2114                        break
2115        endswitch
2116
2117        // TODO
2118        // -- clear out the data folders (from lo to hi?)
2119//
2120// root:Packages:NIST:VSANS:RawVSANS:sans1301:
2121        for(ii=lo;ii<=hi;ii+=1)
2122                KillDataFolder/Z $("root:Packages:NIST:VSANS:RawVSANS:sans"+num2istr(ii))
2123        endfor
2124        return 0
2125End
2126
2127
2128
2129//      // and for the back detector "B"
2130//      Make/O/D/N=3 tmpCalib
2131//      tmpCalib[0] = 1
2132//      tmpCalib[1] = 1
2133//      tmpcalib[2] = 10000
2134//      V_writeDet_cal_x(filename,"B",tmpCalib)
2135//      V_writeDet_cal_y(filename,"B",tmpCalib)
2136//
2137// "Perfect" values here are from Phil (2/2018)
2138//
2139Function V_GeneratePerfCalibButton(ba) : ButtonControl
2140        STRUCT WMButtonAction &ba
2141
2142        switch( ba.eventCode )
2143                case 2: // mouse up
2144                        // click code here
2145
2146                        WAVE calibrationWave = root:Packages:NIST:VSANS:Globals:Patch:calibrationWave
2147                        ControlInfo popup_0
2148                        strswitch(S_Value)
2149                                case "FR":
2150                                case "FL":
2151                                case "MR":
2152                                case "ML":
2153                                        //      // for the "tall" L/R banks
2154                                        calibrationWave[0][] = -521
2155                                        calibrationWave[1][] = 8.14
2156                                        calibrationWave[2][] = 0
2157                                        break
2158                                case "FT":
2159                                case "FB":
2160                                case "MT":
2161                                case "MB":
2162                                        //      // for the "short" T/B banks
2163                                        calibrationWave[0][] = -266
2164                                        calibrationWave[1][] = 4.16
2165                                        calibrationWave[2][] = 0
2166
2167                                        break
2168                                default:
2169                                        Print "Det type not found: V_GeneratePerfCalibButton()"
2170                        endswitch
2171
2172
2173                       
2174                        break
2175                case -1: // control being killed
2176                        break
2177        endswitch
2178
2179        return 0
2180End
2181
2182
2183Function V_ReadCalibButtonProc(ba) : ButtonControl
2184        STRUCT WMButtonAction &ba
2185
2186        switch( ba.eventCode )
2187                case 2: // mouse up
2188                        // click code here
2189                       
2190                        ControlInfo popup_0
2191                        String detStr = S_Value
2192                        ControlInfo setvar0
2193                        Variable lo=V_Value
2194                        Variable hi=lo
2195                       
2196                        V_fReadDetectorCalibration(lo,hi,detStr)
2197                       
2198                        break
2199                case -1: // control being killed
2200                        break
2201        endswitch
2202
2203        return 0
2204End
2205
2206Function V_WriteCalibButtonProc(ba) : ButtonControl
2207        STRUCT WMButtonAction &ba
2208
2209        switch( ba.eventCode )
2210                case 2: // mouse up
2211                        // click code here
2212                       
2213                        ControlInfo popup_0
2214                        String detStr = S_Value
2215                        ControlInfo setvar0
2216                        Variable lo=V_Value
2217                        ControlInfo setvar1
2218                        Variable hi=V_Value
2219                        Wave calibW = root:Packages:NIST:VSANS:Globals:Patch:calibrationWave
2220                       
2221                        V_fPatchDetectorCalibration(lo,hi,detStr,calibW)
2222                       
2223                        break
2224                case -1: // control being killed
2225                        break
2226        endswitch
2227
2228        return 0
2229End
2230
2231
2232
2233//////////////////////////////////////////////////////////////////////////////////////////////////
2234//////////////////////////////////////////////////////////////////////////////////////////////////
2235
2236
2237
2238////////////////////////////////////////////////////////////////////////////////////////////////////////////////
2239////////////////////////////////////////////////////////////////////////////////////////////////////////////////
2240///////////////
2241//
2242// this is a block to patch beam centers to the file headers
2243// it will patch the headers for all 9 detectors
2244// and can patch multiple files
2245//
2246// uses a simple panel to show what the table of values is.
2247// "read" will read only the first run number contents. this is the "good" set of XY
2248//  that you want to write out to other files.
2249//
2250// TODO -- need to clear out the contents from RawVSANS, or else re-reading to check the values
2251//        will read locally, and it will look like nothing was written. Executing "save" will also
2252//        trigger a cleanout.
2253//
2254// TODO - link this to a panel somewhere - a button? menu item? will there be a lot more of these little panels?
2255//
2256Proc V_PatchDet_xyCenters(firstFile,lastFile)
2257        Variable firstFile=1,lastFile=100
2258
2259        V_fPatchDet_xyCenters(firstFile,lastFile)
2260
2261End
2262
2263Proc V_ReadDet_xyCenters(firstFile,lastFile)
2264        Variable firstFile=1,lastFile=100
2265
2266       
2267        V_fReadDet_xyCenters(firstFile,lastFile)
2268End
2269
2270// simple utility to patch the xy center in the file headers
2271// lo is the first file number
2272// hi is the last file number (inclusive)
2273//
2274//
2275//              added in May 2019 -- kill the same numbered files from RawVSANS to force a re-read since the XY
2276//  has been changed
2277Function V_fPatchDet_xyCenters(lo,hi)
2278        Variable lo,hi
2279
2280       
2281        Variable ii,jj
2282        String fname,detStr
2283       
2284        Wave xCtr_cm = root:Packages:NIST:VSANS:Globals:Patch:xCtr_cm
2285        Wave yCtr_cm = root:Packages:NIST:VSANS:Globals:Patch:yCtr_cm
2286        Wave/T panelW = root:Packages:NIST:VSANS:Globals:Patch:panelW
2287       
2288        // check the dimensions of the waves (9)
2289        if (DimSize(xCtr_cm, 0) != 9 || DimSize(yCtr_cm, 0) != 9 || DimSize(panelW, 0) != 9)
2290                Abort "waves are not of proper dimension (9)"
2291        endif
2292       
2293        //loop over all files
2294        for(jj=lo;jj<=hi;jj+=1)
2295                fname = V_FindFileFromRunNumber(jj)
2296                if(strlen(fname) != 0)
2297               
2298                        for(ii=0;ii<ItemsInList(ksDetectorListAll);ii+=1)
2299                                detStr = panelW[ii]
2300                                V_writeDet_beam_center_x(fname,detStr,xCtr_cm[ii])
2301                                V_writeDet_beam_center_y(fname,detStr,yCtr_cm[ii])             
2302                        endfor 
2303               
2304                // then delete the file from RawVSANS
2305                        V_KillNamedDataFolder(fname)
2306                       
2307                else
2308                        printf "run number %d not found\r",jj
2309                endif
2310        endfor
2311       
2312        return(0)
2313End
2314
2315// simple utility to read the detector xy centers stored in the file header
2316Function V_fReadDet_xyCenters(lo,hi)
2317        Variable lo,hi
2318
2319       
2320        String fname,detStr
2321        Variable ii,jj
2322       
2323        Wave xCtr_cm = root:Packages:NIST:VSANS:Globals:Patch:xCtr_cm
2324        Wave yCtr_cm = root:Packages:NIST:VSANS:Globals:Patch:yCtr_cm
2325        Wave/T panelW = root:Packages:NIST:VSANS:Globals:Patch:panelW
2326       
2327        for(jj=lo;jj<=hi;jj+=1)
2328                fname = V_FindFileFromRunNumber(jj)
2329                if(strlen(fname) != 0)
2330               
2331                        for(ii=0;ii<ItemsInList(ksDetectorListAll);ii+=1)
2332                                detStr = StringFromList(ii, ksDetectorListAll, ";")
2333                                panelW[ii] = detStr
2334                                xCtr_cm[ii] = V_getDet_beam_center_x(fname,detStr)              //these values are in cm, not pixels
2335                                yCtr_cm[ii] = V_getDet_beam_center_y(fname,detStr)
2336                        endfor
2337               
2338               
2339                else
2340                        printf "run number %d not found\r",jj
2341                endif
2342               
2343        endfor
2344
2345       
2346        return(0)
2347End
2348
2349
2350
2351Proc V_PatchDet_xyCenters_Panel()
2352        DoWindow/F Patch_XY_Panel
2353        if(V_flag==0)
2354       
2355                NewDataFolder/O/S root:Packages:NIST:VSANS:Globals:Patch
2356
2357                Make/O/D/N=9 xCtr_cm,yCtr_cm
2358                Make/O/T/N=9 panelW
2359               
2360                Variable/G gFileNum_Lo,gFileNum_Hi
2361               
2362                SetDataFolder root:
2363               
2364                Execute "V_Patch_xyCtr_Panel()"
2365        endif
2366End
2367
2368
2369// TODO:
2370// -- add method to read (import) from beam center panel
2371// x- check wave dimensions before writing (check for bad paste operation)
2372// -- load from file? different ways to import?
2373// -- add help button/file
2374// -- add done button
2375// -- adjust after user testing
2376//
2377Proc V_Patch_xyCtr_Panel() : Panel
2378        PauseUpdate; Silent 1           // building window...
2379
2380
2381        NewPanel /W=(600,400,1150,800)/N=Patch_XY_Panel /K=1
2382//      ShowTools/A
2383       
2384        ModifyPanel cbRGB=(16266,47753,2552,23355)
2385
2386        SetDrawLayer UserBack
2387        DrawText 85,99,"Current Values"
2388        DrawText 21,258,"Write to all files (inlcusive)"
2389        SetDrawEnv fsize= 14,fstyle= 1
2390        DrawText 262,30,"Beam Center [cm]"
2391        DrawText 20,133,"Run Number(s)"
2392       
2393        Button button0,pos={20,81},size={50.00,20.00},proc=V_ReadXYButtonProc,title="Read"
2394        Button button0_1,pos={20,220},size={50.00,20.00},proc=V_WriteXYButtonProc,title="Write"
2395        SetVariable setvar0,pos={20,141},size={100.00,14.00},title="first"
2396        SetVariable setvar0,value= root:Packages:NIST:VSANS:Globals:Patch:gFileNum_Lo
2397        SetVariable setvar1,pos={20.00,167},size={100.00,14.00},title="last"
2398        SetVariable setvar1,value= root:Packages:NIST:VSANS:Globals:Patch:gFileNum_Hi
2399
2400       
2401        SetDataFolder root:Packages:NIST:VSANS:Globals:Patch
2402// display the wave     
2403        Edit/W=(180,40,500,370)/HOST=#  panelW,xCtr_cm,yCtr_cm
2404        ModifyTable width(Point)=0
2405        ModifyTable width(panelW)=80
2406        ModifyTable width(xCtr_cm)=100
2407        ModifyTable width(yCtr_cm)=100
2408        RenameWindow #,T0
2409        SetActiveSubwindow ##
2410
2411        SetDataFolder root:
2412       
2413EndMacro
2414
2415
2416Function V_ReadXYButtonProc(ba) : ButtonControl
2417        STRUCT WMButtonAction &ba
2418
2419        switch( ba.eventCode )
2420                case 2: // mouse up
2421                        // click code here
2422                       
2423//                      ControlInfo popup_0
2424//                      String detStr = S_Value
2425                        ControlInfo setvar0
2426                        Variable lo=V_Value
2427                        Variable hi=lo
2428                       
2429                        V_fReadDet_xyCenters(lo,hi)
2430                       
2431                        break
2432                case -1: // control being killed
2433                        break
2434        endswitch
2435
2436        return 0
2437End
2438
2439Function V_WriteXYButtonProc(ba) : ButtonControl
2440        STRUCT WMButtonAction &ba
2441
2442        switch( ba.eventCode )
2443                case 2: // mouse up
2444                        // click code here
2445                       
2446//                      ControlInfo popup_0
2447//                      String detStr = S_Value
2448                        ControlInfo setvar0
2449                        Variable lo=V_Value
2450                        ControlInfo setvar1
2451                        Variable hi=V_Value
2452//                      Wave deadTimeW = root:Packages:NIST:VSANS:Globals:Patch:deadTimeWave
2453
2454// this function will write the new centers to the file and then delete the file from
2455// RawVSANS to force a re-read of the data                     
2456                        V_fPatchDet_xyCenters(lo,hi)
2457
2458                        break
2459                case -1: // control being killed
2460                        break
2461        endswitch
2462
2463        return 0
2464End
2465
2466//////////////////////////////////////////////////////////////////////////////////////////////////
2467//////////////////////////////////////////////////////////////////////////////////////////////////
2468
2469
2470Proc V_PatchDet_Offset(lo,hi)
2471        Variable lo,hi
2472       
2473        V_fPatchDet_Offset(lo,hi)
2474End
2475
2476Proc V_MarkLeftRightFlip_Done(lo,hi)
2477        Variable lo,hi
2478       
2479        V_fWriteFlipState(lo,hi,1)      // value == 1 means flip done
2480End
2481
2482Proc V_MarkLeftRightFlip_Not_Done(lo,hi)
2483        Variable lo,hi
2484       
2485        V_fWriteFlipState(lo,hi,-999999)        // value == -999999 means flip not done
2486End
2487
2488
2489Proc V_Patch_GroupID_catTable()
2490        V_fPatch_GroupID_catTable()
2491end
2492
2493Proc V_Patch_Purpose_catTable()
2494        V_fPatch_Purpose_catTable()
2495end
2496
2497Proc V_Patch_Intent_catTable()
2498        V_fPatch_Intent_catTable()
2499end
2500
2501Proc V_PatchDet_Gap(lo,hi)
2502        Variable lo,hi
2503       
2504        V_fPatchDet_Gap(lo,hi)
2505End
2506
2507Proc V_ReadDet_Gap(lo,hi)
2508        Variable lo,hi
2509       
2510        V_fReadDet_Gap(lo,hi)
2511End
2512
2513Proc V_PatchDet_Distance(lo,hi,dist_f,dist_m,dist_b)
2514        Variable lo,hi,dist_f=400,dist_m=1900,dist_b=2200
2515       
2516        V_fPatchDet_distance(lo,hi,dist_f,dist_m,dist_b)
2517End
2518
2519Proc V_Patch_Back_Detector(lo,hi)
2520        Variable lo,hi
2521       
2522        V_fPatch_BackDetector(lo,hi)
2523End
2524
2525
2526Proc V_Patch_XYPixelSize(lo,hi)
2527        Variable lo,hi
2528       
2529        V_fPatch_XYPixelSize(lo,hi)
2530End
2531
2532// simple utility to patch the offset values in the file headers
2533//
2534// Swaps only the L/R detector values
2535// lo is the first file number
2536// hi is the last file number (inclusive)
2537//
2538//              V_getLeftRightFlipDone(fname)
2539//
2540//
2541// updated the function to check for the "already done" flag
2542// - if already done, report this and do nothing.
2543// - if not done, do the flip and set the flag
2544//
2545Function V_fPatchDet_Offset(lo,hi)
2546        Variable lo,hi
2547
2548       
2549        Variable ii,jj,flipDone=0
2550        String fname,detStr
2551       
2552        Variable offset_ML,offset_MR,offset_FL,offset_FR
2553
2554       
2555        //loop over all files
2556        for(jj=lo;jj<=hi;jj+=1)
2557                fname = V_FindFileFromRunNumber(jj)
2558                if(strlen(fname) != 0)
2559               
2560                        flipDone = V_getLeftRightFlipDone(fname)
2561                        if(flipDone == 1)
2562                                printf "run number %d already flipped - nothing done\r",jj
2563                        else
2564                                offset_FL = V_getDet_LateralOffset(fname,"FL")
2565                                offset_FR = V_getDet_LateralOffset(fname,"FR")
2566       
2567                                offset_ML = V_getDet_LateralOffset(fname,"ML")
2568                                offset_MR = V_getDet_LateralOffset(fname,"MR")
2569                       
2570                        // swap L/R offset values
2571                                V_WriteDet_LateralOffset(fname,"FL",-offset_FR)
2572                                V_WriteDet_LateralOffset(fname,"FR",-offset_FL)
2573                               
2574                                V_WriteDet_LateralOffset(fname,"ML",-offset_MR)
2575                                V_WriteDet_LateralOffset(fname,"MR",-offset_ML)
2576                       
2577                        // set the flag
2578                                V_writeLeftRightFlipDone(fname,1)               // value == 1 means the flip was done
2579                                Print fname
2580                                Print "swapped FL, FR = ",-offset_FR,-offset_FL
2581                                Print "swapped ML, MR = ",-offset_MR,-offset_ML
2582                       
2583                        endif
2584               
2585                else
2586                        printf "run number %d not found\r",jj
2587                endif
2588               
2589        endfor
2590       
2591        return(0)
2592End
2593
2594//  utility to reset the flip state in the file headers
2595//
2596// lo is the first file number
2597// hi is the last file number (inclusive)
2598//
2599// setting value == 1 means done
2600// setting value == -999999 means not done (mimics a missing /entry)
2601//
2602Function V_fWriteFlipState(lo,hi,val)
2603        Variable lo,hi,val
2604
2605       
2606        Variable ii,jj,flipDone=0
2607        String fname,detStr
2608       
2609        Variable offset_ML,offset_MR,offset_FL,offset_FR
2610
2611        //loop over all files
2612        for(jj=lo;jj<=hi;jj+=1)
2613                fname = V_FindFileFromRunNumber(jj)
2614                if(strlen(fname) != 0)
2615       
2616                // set the flag
2617                        V_writeLeftRightFlipDone(fname,val)             //
2618                        Print fname
2619                        printf "run number %d flag reset to %d\r",jj,val
2620                       
2621                else
2622                        printf "run number %d not found\r",jj
2623                endif
2624               
2625        endfor
2626       
2627        return(0)
2628End
2629
2630
2631
2632// simple utility to read the detector offset stored in the file header
2633Function V_fReadDet_Offset(lo,hi)
2634        Variable lo,hi
2635
2636        String fname,detStr
2637        Variable jj
2638        Variable offset_ML,offset_MR,offset_FL,offset_FR
2639       
2640        for(jj=lo;jj<=hi;jj+=1)
2641                fname = V_FindFileFromRunNumber(jj)
2642                if(strlen(fname) != 0)
2643               
2644                        offset_FL = V_getDet_LateralOffset(fname,"FL")
2645                        offset_FR = V_getDet_LateralOffset(fname,"FR")
2646
2647                        offset_ML = V_getDet_LateralOffset(fname,"ML")
2648                        offset_MR = V_getDet_LateralOffset(fname,"MR")
2649               
2650                        Print fname
2651                        Print "FL, FR = ",offset_FL,offset_FR
2652                        Print "ML, MR = ",offset_ML,offset_MR
2653               
2654               
2655                else
2656                        printf "run number %d not found\r",jj
2657                endif
2658               
2659        endfor
2660
2661       
2662        return(0)
2663End
2664
2665
2666// patches the group_ID, based on whatever is in the catTable
2667//
2668Function V_fPatch_GroupID_catTable()
2669        Variable lo,hi
2670
2671       
2672        Variable ii,jj,num
2673       
2674        Wave id = root:Packages:NIST:VSANS:CatVSHeaderInfo:Group_ID
2675        Wave/T fileNameW = root:Packages:NIST:VSANS:CatVSHeaderInfo:Filenames
2676
2677        num = numpnts(id)       
2678        //loop over all files
2679        for(jj=0;jj<num;jj+=1)
2680                Print "update file ",jj,fileNameW[jj]
2681                V_writeSample_GroupID(fileNameW[jj],id[jj])     
2682        endfor
2683       
2684        return(0)
2685End
2686
2687
2688// patches the Purpose, based on whatever is in the catTable
2689//
2690Function V_fPatch_Purpose_catTable()
2691        Variable lo,hi
2692
2693       
2694        Variable ii,jj,num
2695       
2696        Wave/T purpose = root:Packages:NIST:VSANS:CatVSHeaderInfo:Purpose
2697        Wave/T fileNameW = root:Packages:NIST:VSANS:CatVSHeaderInfo:Filenames
2698
2699        num = numpnts(purpose) 
2700        //loop over all files
2701        for(jj=0;jj<num;jj+=1)
2702                Print "update file ",jj,fileNameW[jj]
2703                V_writeReduction_Purpose(fileNameW[jj],purpose[jj])     
2704        endfor
2705       
2706        return(0)
2707End
2708
2709// patches the Intent, based on whatever is in the catTable
2710//
2711Function V_fPatch_Intent_catTable()
2712        Variable lo,hi
2713
2714       
2715        Variable ii,jj,num
2716       
2717        Wave/T intent = root:Packages:NIST:VSANS:CatVSHeaderInfo:Intent
2718        Wave/T fileNameW = root:Packages:NIST:VSANS:CatVSHeaderInfo:Filenames
2719
2720        num = numpnts(intent)   
2721        //loop over all files
2722        for(jj=0;jj<num;jj+=1)
2723                Print "update file ",jj,fileNameW[jj]
2724                V_writeReductionIntent(fileNameW[jj],intent[jj])       
2725        endfor
2726       
2727        return(0)
2728End
2729
2730
2731
2732// simple utility to patch the detector gap values in the file headers
2733//
2734// values are measured values in [mm], not estimated
2735//
2736// lo is the first file number
2737// hi is the last file number (inclusive)
2738//
2739Function V_fPatchDet_Gap(lo,hi)
2740        Variable lo,hi
2741
2742       
2743        Variable ii,jj
2744        String fname,detStr
2745               
2746        //loop over all files
2747        for(jj=lo;jj<=hi;jj+=1)
2748                fname = V_FindFileFromRunNumber(jj)
2749                if(strlen(fname) != 0)
2750               
2751                // write gap values
2752                        V_writeDet_panel_gap(fname,"FL",3.5)
2753                        V_writeDet_panel_gap(fname,"FR",3.5)
2754
2755                        V_writeDet_panel_gap(fname,"FT",3.3)
2756                        V_writeDet_panel_gap(fname,"FB",3.3)
2757
2758                        V_writeDet_panel_gap(fname,"ML",5.9)
2759                        V_writeDet_panel_gap(fname,"MR",5.9)
2760
2761                        V_writeDet_panel_gap(fname,"MT",18.3)
2762                        V_writeDet_panel_gap(fname,"MB",18.3)           
2763               
2764                else
2765                        printf "run number %d not found\r",jj
2766                endif
2767        endfor
2768       
2769        return(0)
2770End
2771
2772// simple utility to read the detector gap values stored in the file header
2773Function V_fReadDet_Gap(lo,hi)
2774        Variable lo,hi
2775
2776        String fname,detStr
2777        Variable jj
2778        Variable gap_FL,gap_FR,gap_FT,gap_FB,gap_ML,gap_MR,gap_MT,gap_MB
2779       
2780        for(jj=lo;jj<=hi;jj+=1)
2781                fname = V_FindFileFromRunNumber(jj)
2782                if(strlen(fname) != 0)
2783               
2784                        gap_FL = V_getDet_panel_gap(fname,"FL")
2785                        gap_FR = V_getDet_panel_gap(fname,"FR")
2786                        gap_FT = V_getDet_panel_gap(fname,"FT")
2787                        gap_FB = V_getDet_panel_gap(fname,"FB")
2788
2789                        gap_ML = V_getDet_panel_gap(fname,"ML")
2790                        gap_MR = V_getDet_panel_gap(fname,"MR")
2791                        gap_MT = V_getDet_panel_gap(fname,"MT")
2792                        gap_MB = V_getDet_panel_gap(fname,"MB")
2793                       
2794                        print fname     
2795                        Print "FL, FR, FT, FB = ",gap_FL,gap_FR,gap_FT,gap_FB
2796                        Print "ML, MR, MT, MB = ",gap_ML,gap_MR,gap_MT,gap_MB
2797               
2798               
2799                else
2800                        printf "run number %d not found\r",jj
2801                endif
2802               
2803        endfor
2804
2805       
2806        return(0)
2807End
2808
2809
2810// simple utility to patch the detector distance values in the file headers
2811//
2812// values are in [cm]
2813//
2814// lo is the first file number
2815// hi is the last file number (inclusive)
2816//
2817Function V_fPatchDet_distance(lo,hi,d_f,d_m,d_b)
2818        Variable lo,hi,d_f,d_m,d_b
2819
2820       
2821        Variable ii,jj
2822        String fname,detStr
2823               
2824        //loop over all files
2825        for(jj=lo;jj<=hi;jj+=1)
2826                fname = V_FindFileFromRunNumber(jj)
2827                if(strlen(fname) != 0)
2828               
2829                // write gap values
2830                        V_writeDet_distance(fname,"FL",d_f)
2831                        V_writeDet_distance(fname,"FR",d_f)
2832                        V_writeDet_distance(fname,"FT",d_f)
2833                        V_writeDet_distance(fname,"FB",d_f)
2834
2835                        V_writeDet_distance(fname,"ML",d_m)
2836                        V_writeDet_distance(fname,"MR",d_m)
2837                        V_writeDet_distance(fname,"MT",d_m)
2838                        V_writeDet_distance(fname,"MB",d_m)             
2839
2840                        V_writeDet_distance(fname,"B",d_b)             
2841               
2842                else
2843                        printf "run number %d not found\r",jj
2844                endif
2845        endfor
2846       
2847        return(0)
2848End
2849
2850
2851//
2852// simple utility to patch all of the values associated with the back detector
2853//
2854//
2855//
2856//
2857//
2858// lo is the first file number
2859// hi is the last file number (inclusive)
2860//
2861Function V_fPatch_BackDetector(lo,hi)
2862        Variable lo,hi
2863
2864       
2865        Variable ii,jj
2866        String fname,detStr
2867       
2868        detStr = "B"
2869       
2870        Make/O/D/N=3 cal_x,cal_y
2871        cal_x[0] = VCALC_getPixSizeX(detStr)                    // pixel size in VCALC_getPixSizeX(detStr) is [cm]
2872        cal_x[1] = 1
2873        cal_x[2] = 10000
2874        cal_y[0] = VCALC_getPixSizeY(detStr)                    // pixel size in VCALC_getPixSizeX(detStr) is [cm]
2875        cal_y[1] = 1
2876        cal_y[2] = 10000
2877       
2878        Make/O/I/N=(680,1656) tmpData=1
2879       
2880        //loop over all files
2881        for(jj=lo;jj<=hi;jj+=1)
2882                fname = V_FindFileFromRunNumber(jj)
2883                if(strlen(fname) != 0)
2884               
2885                // patch cal_x and cal_y
2886                        V_writeDet_cal_x(fname,detStr,cal_x)
2887                        V_writeDet_cal_y(fname,detStr,cal_y)
2888               
2889                // patch n_pix_x and y
2890                        V_writeDet_pixel_num_x(fname,detStr,680)
2891                        V_writeDet_pixel_num_y(fname,detStr,1656)
2892                       
2893                // patch pixel size x and y [cm]
2894                        V_writeDet_x_pixel_size(fname,detStr,0.034)
2895                        V_writeDet_y_pixel_size(fname,detStr,0.034)
2896                       
2897                // patch dead time
2898                // TODO: enter a proper value here once it's actually measured
2899                        V_writeDetector_deadtime_B(fname,detStr,1e-20)
2900               
2901                // patch fwhm_x and y
2902                // TODO: verify the values once they are measured, and also the UNITS!!! [cm]???
2903                        V_writeDet_pixel_fwhm_x(fname,detStr,0.034)
2904                        V_writeDet_pixel_fwhm_y(fname,detStr,0.034)
2905               
2906                // patch beam center (nominal x,y) [cm] values
2907                        V_writeDet_beam_center_x(fname,detStr,11)
2908                        V_writeDet_beam_center_y(fname,detStr,25)
2909               
2910                // fake data
2911//                      V_writeDetectorData(fname,detStr,tmpData)
2912                       
2913                       
2914                else
2915                        printf "run number %d not found\r",jj
2916                endif
2917        endfor
2918       
2919        KillWaves/Z cal_x,cal_y,tmpData
2920        return(0)
2921End
2922
2923//
2924// simple utility to patch all of the pixel sizes
2925// - in the header, the Y size for LR panels was grossly wrong (4 mm)
2926// and all of the values are slightly off from the true values
2927//
2928// data collected after 10/3/18 should not need this patch since the
2929// config.js file was updated
2930//
2931//
2932//
2933// lo is the first file number
2934// hi is the last file number (inclusive)
2935//
2936Function V_fPatch_XYPixelSize(lo,hi)
2937        Variable lo,hi
2938
2939       
2940        Variable ii,jj
2941        String fname,detStr
2942       
2943       
2944        //loop over all files
2945        for(jj=lo;jj<=hi;jj+=1)
2946                fname = V_FindFileFromRunNumber(jj)
2947                if(strlen(fname) != 0)
2948                       
2949                // patch pixel size x and y [cm] L/R panels
2950                        V_writeDet_x_pixel_size(fname,"FL",8.4)
2951                        V_writeDet_y_pixel_size(fname,"FL",8.14)
2952
2953                        V_writeDet_x_pixel_size(fname,"FR",8.4)
2954                        V_writeDet_y_pixel_size(fname,"FR",8.14)                       
2955
2956                        V_writeDet_x_pixel_size(fname,"ML",8.4)
2957                        V_writeDet_y_pixel_size(fname,"ML",8.14)
2958
2959                        V_writeDet_x_pixel_size(fname,"MR",8.4)
2960                        V_writeDet_y_pixel_size(fname,"MR",8.14)
2961                       
2962                // patch pixel size x and y [cm] T/B panels
2963                        V_writeDet_x_pixel_size(fname,"FT",4.16)
2964                        V_writeDet_y_pixel_size(fname,"FT",8.4)
2965
2966                        V_writeDet_x_pixel_size(fname,"FB",4.16)
2967                        V_writeDet_y_pixel_size(fname,"FB",8.4)                 
2968
2969                        V_writeDet_x_pixel_size(fname,"MT",4.16)
2970                        V_writeDet_y_pixel_size(fname,"MT",8.4)
2971
2972                        V_writeDet_x_pixel_size(fname,"MB",4.16)
2973                        V_writeDet_y_pixel_size(fname,"MB",8.4)                 
2974                       
2975                else
2976                        printf "run number %d not found\r",jj
2977                endif
2978        endfor
2979       
2980        return(0)
2981End
2982
2983
2984Proc V_Patch_Guide_SSD_Aperture(lo,hi,numGuideStr,sourceDiam_mm)
2985        Variable lo,hi
2986        String numGuideStr="CONV_BEAMS"
2987        Variable sourceDiam_mm=30
2988       
2989        V_fPatch_Guide_SSD_Aperture(lo,hi,numGuideStr,sourceDiam_mm)
2990End
2991
2992
2993
2994// simple utility to patch all three at once, since they are all linked and typically
2995/// are all incorrectly entered by NICE if the number of guides can't be determined
2996//
2997// Number of guides
2998// source aperture to gate valve distance [cm]
2999// source aperture diameter [mm]
3000//
3001// the source aperture is assumed to be circular and the diameter in mm
3002//
3003// the value for the A1_to_GV is from tabulated values.  (see VC_calcSSD)
3004// This is the Source aperture to Gate Valve distance
3005//
3006//
3007// lo is the first file number
3008// hi is the last file number (inclusive)
3009//
3010Function V_fPatch_Guide_SSD_Aperture(lo,hi,numGuideStr,sourceDiam_mm)
3011        Variable lo,hi
3012        String numGuideStr
3013        Variable sourceDiam_mm
3014
3015       
3016        Variable ii,jj,A1_to_GV
3017        String fname,detStr
3018
3019        strswitch(numGuideStr)
3020                case "CONV_BEAMS":
3021                case "NARROW_SLITS":
3022                case "0":
3023                                A1_to_GV = 2441
3024                        break
3025                case "1":
3026                                A1_to_GV = 2157
3027                        break
3028                case "2":
3029                                A1_to_GV = 1976
3030                        break
3031                case "3":
3032                                A1_to_GV = 1782
3033                        break                   
3034                case "4":
3035                                A1_to_GV = 1582
3036                        break                   
3037                case "5":
3038                                A1_to_GV = 1381
3039                        break                   
3040                case "6":
3041                                A1_to_GV = 1181
3042                        break                   
3043                case "7":
3044                                A1_to_GV = 980
3045                        break                   
3046                case "8":
3047                                A1_to_GV = 780
3048                        break                   
3049                case "9":
3050                                A1_to_GV = 579
3051                        break                   
3052                default:
3053                        Print "Error - using default A1_to_GV value"
3054                        A1_to_GV = 2441
3055        endswitch
3056
3057               
3058        //loop over all files
3059        for(jj=lo;jj<=hi;jj+=1)
3060                fname = V_FindFileFromRunNumber(jj)
3061                if(strlen(fname) != 0)
3062               
3063                // write values
3064                V_writeNumberOfGuides(fname,numGuideStr)
3065
3066                V_writeSourceAp_distance(fname,A1_to_GV)
3067
3068                V_writeSourceAp_shape(fname,"CIRCLE")
3069                V_writeSourceAp_size(fname,num2str(sourceDiam_mm))
3070
3071                else
3072                        printf "run number %d not found\r",jj
3073                endif
3074        endfor
3075       
3076        return(0)
3077End
3078
3079
3080//
3081// pick the carriage, beamstop number, beamstop shape, and beamstop diameter
3082// or height and width
3083Proc V_Patch_BeamStop(lo,hi,carriageStr,bs_num,bsShapeStr,bs_diam,bs_width,bs_height)
3084        Variable lo,hi
3085        String carriageStr="B"
3086        Variable bs_num=2
3087        String bsShapeStr="CIRCLE"
3088        Variable bs_diam=12,bs_width=12,bs_height=300
3089       
3090        V_fPatch_BeamStop(lo,hi,carriageStr,bs_num,bsShapeStr,bs_diam,bs_width,bs_height)
3091End
3092
3093
3094//
3095// lo is the first file number
3096// hi is the last file number (inclusive)
3097//
3098Function V_fPatch_BeamStop(lo,hi,carriageStr,bs_num,bsShapeStr,bs_diam,bs_width,bs_height)
3099        Variable lo,hi
3100        String carriageStr
3101        Variable bs_num
3102        String bsShapeStr
3103        Variable bs_diam,bs_width,bs_height
3104
3105       
3106        Variable ii,jj,A1_to_GV
3107        String fname,detStr
3108
3109               
3110        //loop over all files
3111        for(jj=lo;jj<=hi;jj+=1)
3112                fname = V_FindFileFromRunNumber(jj)
3113                if(strlen(fname) != 0)
3114
3115                        if(cmpstr("F",carriageStr) == 0)
3116                                Print "front carriage has no beamstops"
3117                        endif
3118                       
3119                        if(cmpstr("M",carriageStr) == 0)
3120                                // middle carriage (2)
3121                                V_writeBeamStopC2num_stop(fname,bs_num)
3122                                V_writeBeamStopC2_shape(fname,bsShapeStr)
3123                                if(cmpstr("CIRCLE",bsShapeStr)==0)
3124                                        V_writeBeamStopC2_size(fname,bs_diam)
3125                                else
3126                                        V_writeBeamStopC2_height(fname,bs_height)
3127                                        V_writeBeamStopC2_width(fname,bs_width)
3128                                endif
3129                        endif
3130               
3131                        if(cmpstr("B",carriageStr) == 0)
3132                                // back carriage (3)
3133                                V_writeBeamStopC3num_stop(fname,bs_num)
3134                                V_writeBeamStopC3_shape(fname,bsShapeStr)
3135                                if(cmpstr("CIRCLE",bsShapeStr)==0)
3136                                        V_writeBeamStopC3_size(fname,bs_diam)
3137                                else
3138                                        V_writeBeamStopC3_height(fname,bs_height)
3139                                        V_writeBeamStopC3_width(fname,bs_width)                         
3140                                endif
3141                        endif   
3142
3143                else
3144                        printf "run number %d not found\r",jj
3145                endif
3146        endfor
3147       
3148       
3149        return(0)
3150End
3151
3152
3153Proc V_Patch_SampleAperture2(lo,hi,ShapeStr,diam,width,height)
3154        Variable lo,hi
3155        String shapeStr="CIRCLE"
3156        Variable diam,width,height
3157       
3158        V_fPatch_SampleAperture2(lo,hi,ShapeStr,diam,width,height)
3159End
3160
3161//
3162// lo is the first file number
3163// hi is the last file number (inclusive)
3164//
3165// Patches sample aperture (2), the external aperture
3166//
3167// dimensions are expected to be in [cm]
3168//
3169Function V_fPatch_SampleAperture2(lo,hi,ShapeStr,diam,width,height)
3170        Variable lo,hi
3171        String ShapeStr
3172        Variable diam,width,height
3173
3174        Variable jj
3175        String fname,detStr
3176
3177               
3178        //loop over all files
3179        for(jj=lo;jj<=hi;jj+=1)
3180                fname = V_FindFileFromRunNumber(jj)
3181                if(strlen(fname) != 0)
3182               
3183                        V_writeSampleAp2_shape(fname,ShapeStr)
3184                        if(cmpstr("CIRCLE",ShapeStr)==0)
3185                                V_writeSampleAp2_size(fname,diam)
3186                        else
3187                                //RECTANGLE
3188                                V_writeSampleAp2_height(fname,height)
3189                                V_writeSampleAp2_width(fname,width)                             
3190                        endif
3191
3192                else
3193                        printf "run number %d not found\r",jj
3194                endif
3195        endfor
3196       
3197       
3198        return(0)
3199End
3200
3201
Note: See TracBrowser for help on using the repository browser.