source: sans/Analysis/branches/ajj_23APR07/IGOR_Package_Files/Put in User Procedures/SANS_Models_v3.00/Packages/PlotUtils2D.ipf @ 198

Last change on this file since 198 was 198, checked in by srkline, 15 years ago

Adding three new 2D functions, the easy ones that use a Gaussian distribution of parameters.

Changed the parsing of constraints to only build a constraint wave for those parameters that are not being held. failing to do so results in an "unknown error" from curve fitting. This fix was done in both the 1D and 2D wrappers.

Changed the default mask that was two pixels all around to now mask out the beamstop for 2D data sets. 8 pixel radius is currently hard-wired in PlotUtils2D - and is generated as the fit is dispatched, automatically determining the beam center from the data set.

File size: 25.1 KB
Line 
1#pragma rtGlobals=1             // Use modern global access method.
2#pragma IgorVersion=6.0
3
4//
5// WARNING: there are a lot of assumptions that went into this code at the first pass
6// that will need to be made generic before a release to the wild
7//
8//
9// - some manipulations assume a square matrix
10// - naming schemes are assumed (to be documented)
11//
12//
13
14
15//
16//
17Proc LoadQxQy()
18
19        LoadWave/G/D/W/A
20        String fileName = S_fileName
21        Variable numCols = V_flag
22
23        String w0,w1,w2,n0,n1,n2
24               
25        // put the names of the three loaded waves into local names
26        n0 = StringFromList(0, S_waveNames ,";" )
27        n1 = StringFromList(1, S_waveNames ,";" )
28        n2 = StringFromList(2, S_waveNames ,";" )
29       
30        //remove the semicolon AND period from files from the VAX
31        w0 = CleanupName((S_fileName + "_qx"),0)
32        w1 = CleanupName((S_fileName + "_qy"),0)
33        w2 = CleanupName((S_fileName + "_i"),0)
34       
35        String baseStr=w1[0,strlen(w1)-4]
36        if(DataFolderExists("root:"+baseStr))
37                        DoAlert 1,"The file "+S_filename+" has already been loaded. Do you want to load the new data file, overwriting the data in memory?"
38                        if(V_flag==2)   //user selected No, don't load the data
39                                SetDataFolder root:
40                                KillWaves $n0,$n1,$n2           // kill the default waveX that were loaded
41                                //if(DataFolderExists("root:myGlobals"))
42                                //      String/G root:myGlobals:gLastFileName = filename
43                                //endif
44                                return          //quits the macro
45                        endif
46                        SetDataFolder $("root:"+baseStr)
47        else
48                NewDataFolder/S $("root:"+baseStr)
49        endif
50       
51        ////overwrite the existing data, if it exists
52        Duplicate/O $("root:"+n0), $w0
53        Duplicate/O $("root:"+n1), $w1
54        Duplicate/O $("root:"+n2), $w2
55       
56        Variable/G gIsLogScale = 0
57       
58        Variable num=numpnts($w0)
59        // assume that the Q-grid is "uniform enough" for DISPLAY ONLY
60        // use the 3 original waves for all of the fitting...
61        ConvertQxQy2Mat($w0,$w1,$w2,baseStr+"_mat")
62        Duplicate/O $(baseStr+"_mat"),$(baseStr+"_lin")                 //keep a linear-scaled version of the data
63       
64        PlotQxQy(baseStr)               //this sets the data folder back to root:!!
65       
66        //don't create the triplet - not really of much use
67//      Make/D/O/N=(num,3) $(baseStr+"_tri")
68//      $(baseStr+"_tri")[][0] = $w0[p]         // Qx
69//      $(baseStr+"_tri")[][1] = $w1[p]         // Qy
70//      $(baseStr+"_tri")[][2] = $w2[p]         // Intensity
71
72        //clean up             
73        SetDataFolder root:
74        KillWaves/Z $n0,$n1,$n2
75EndMacro
76
77//does not seem to need to be flipped at all from the standard QxQy output
78//
79// plots the data, as surface0, YellowHot color table
80//
81Proc PlotQxQy(str)
82        String str
83        Prompt str,"Pick the data folder containing 2D data",popup,getAList(4)
84
85        PauseUpdate; Silent 1   // Building Gizmo 6 window...
86
87        // Do nothing if the Gizmo XOP is not available.
88        if(exists("NewGizmo")!=4)
89                DoAlert 0, "Gizmo XOP must be installed"
90                return
91        endif
92
93        String data = "root:"+str+":"+str+"_mat"
94       
95        NewGizmo/N=$str/T=str /W=(169,44,495,359)
96        ModifyGizmo startRecMacro
97        AppendToGizmo Surface=$data,name=surface0
98
99        // for constant color (data is a blue color, lighter on the bottom)
100//      ModifyGizmo ModifyObject=surface0 property={ surfaceColorType,1}
101//      ModifyGizmo ModifyObject=surface0 property={ srcMode,0}
102//      ModifyGizmo ModifyObject=surface0 property={ frontColor,0.749996,0.811093,1,1}
103//      ModifyGizmo ModifyObject=surface0 property={ backColor,0.250019,0.433326,1,1}
104        //e constant color
105       
106        //for color table       
107        ModifyGizmo ModifyObject=surface0 property={ srcMode,0}
108//      ModifyGizmo ModifyObject=surface0 property={ surfaceCTab,Blue}
109        ModifyGizmo ModifyObject=surface0 property={ surfaceCTab,ColdWarm}
110        ModifyGizmo ModifyObject=surface0 property={ SurfaceCTABScaling,4}
111        //e color table
112       
113        AppendToGizmo Axes=boxAxes,name=axes0
114        ModifyGizmo ModifyObject=axes0,property={0,axisRange,-1,-1,-1,1,-1,-1}
115        ModifyGizmo ModifyObject=axes0,property={1,axisRange,-1,-1,-1,-1,1,-1}
116        ModifyGizmo ModifyObject=axes0,property={2,axisRange,-1,-1,-1,-1,-1,1}
117        ModifyGizmo ModifyObject=axes0,property={3,axisRange,-1,1,-1,-1,1,1}
118        ModifyGizmo ModifyObject=axes0,property={4,axisRange,1,1,-1,1,1,1}
119        ModifyGizmo ModifyObject=axes0,property={5,axisRange,1,-1,-1,1,-1,1}
120        ModifyGizmo ModifyObject=axes0,property={6,axisRange,-1,-1,1,-1,1,1}
121        ModifyGizmo ModifyObject=axes0,property={7,axisRange,1,-1,1,1,1,1}
122        ModifyGizmo ModifyObject=axes0,property={8,axisRange,1,-1,-1,1,1,-1}
123        ModifyGizmo ModifyObject=axes0,property={9,axisRange,-1,1,-1,1,1,-1}
124        ModifyGizmo ModifyObject=axes0,property={10,axisRange,-1,1,1,1,1,1}
125        ModifyGizmo ModifyObject=axes0,property={11,axisRange,-1,-1,1,1,-1,1}
126        ModifyGizmo ModifyObject=axes0,property={-1,axisScalingMode,1}
127        ModifyGizmo ModifyObject=axes0,property={-1,axisColor,0,0,0,1}
128        ModifyGizmo ModifyObject=axes0,property={0,ticks,3}
129        ModifyGizmo ModifyObject=axes0,property={1,ticks,3}
130        ModifyGizmo ModifyObject=axes0,property={2,ticks,3}
131        ModifyGizmo ModifyObject=axes0,property={0,fontScaleFactor,1.5}
132        ModifyGizmo ModifyObject=axes0,property={1,fontScaleFactor,1.5}
133        ModifyGizmo ModifyObject=axes0,property={2,fontScaleFactor,1.5}
134        ModifyGizmo setDisplayList=0, opName=clearColor0, operation=clearColor, data={1,0.917,0.75,1}
135        ModifyGizmo setDisplayList=1, object=surface0
136        ModifyGizmo setDisplayList=2, object=axes0
137        ModifyGizmo SETQUATERNION={0.521287,-0.097088,-0.138769,0.836408}
138        ModifyGizmo autoscaling=1
139        ModifyGizmo currentGroupObject=""
140        ModifyGizmo compile
141
142        ModifyGizmo NamedHook={GizmoContours,WMGizmoContoursNamedHook}
143        ModifyGizmo endRecMacro
144       
145// don't bother with the flat image plot right now
146       
147//      Display $yw vs $xw
148//      modifygraph log=0
149//      ModifyGraph mode=3,marker=16,zColor($yw)={$zw,*,*,YellowHot,0}
150//      ModifyGraph standoff=0
151//      ModifyGraph width={Aspect,1}
152//      ModifyGraph lowTrip=0.001
153
154End
155
156Macro FakeQxQy(minQx,maxQx,minQy,maxQy,numPix,dataFolder)
157        Variable minQx=-0.1,maxQx=0.1,minQy=-0.1,maxQy=0.1
158        Variable numPix=64
159        String dataFolder="fake2DData"
160
161        String baseStr=dataFolder
162       
163
164        if(DataFolderExists("root:"+baseStr))
165                        DoAlert 1,"Fake data "+baseStr+" has already been created. Do you want to overwrite this fake data set?"
166                        if(V_flag==2)   //user selected No, don't load the data
167                                SetDataFolder root:
168                                return          //quits the macro
169                        endif
170                        SetDataFolder $("root:"+baseStr)
171        else
172                NewDataFolder/S $("root:"+baseStr)
173        endif
174
175        Make/O/D/N=(numPix*numPix) $(baseStr+"_qx"),$(baseStr+"_qy"),$(baseStr+"_i")
176       
177        $(baseStr+"_i") = 1
178       
179        Make/O/D/N=(numPix) tmpX,tmpY
180       
181        variable delX,delY
182        delX = (maxQx - minQx)/numPix
183        delY = (maxQy - minQy)/numPix
184        tmpX = minQx + x*delX
185        tmpY = minQy + x*delY
186       
187        // get rid of Q=0 values in the waves (may be a bad actor in model calculations)
188        //
189        tmpX = (tmpX == 0) ? 1e-6 : tmpX
190        tmpY = (tmpY == 0) ? 1e-6 : tmpY
191       
192        // X wave varies more rapidly
193        // Y wave is blocks of values
194        Variable ii=0
195        do
196                $(baseStr+"_qy")[ii*numPix,(ii+1)*numPix] = tmpY[ii]
197                ii+=1
198        while(ii<numPix)
199       
200        $(baseStr+"_qx") = tmpX[mod(p,numPix)]
201       
202        Variable/G gIsLogScale = 0
203       
204        // assume that the Q-grid is "uniform enough" for DISPLAY ONLY
205        // use the 3 original waves for all of the fitting...
206        ConvertQxQy2Mat($(baseStr+"_qx"),$(baseStr+"_qy"),$(baseStr+"_i"),baseStr+"_mat")
207        Duplicate/O $(baseStr+"_mat"),$(baseStr+"_lin")                 //keep a linear-scaled version of the data
208       
209        PlotQxQy(baseStr)               //this sets the data folder back to root:!!
210
211        //clean up             
212        SetDataFolder root:
213       
214EndMacro
215
216// this assumes that:
217// --QxQy data was written out in the format specified by the Igor macros, that is the x varies most rapidly
218// --the matrix is square!
219//
220// probably some other stuff...
221//
222Function UpdateQxQy2Mat(Qx,Qy,inten,linMat,mat)
223        Wave Qx,Qy,inten,linMat,mat
224       
225        Variable xrows=DimSize(mat, 0 )                 //assumes square matrix!!
226       
227        String folderStr=GetWavesDataFolder(Qx,1)
228        NVAR gIsLogScale=$(folderStr+"gIsLogScale")
229       
230        linMat = inten[q*xrows+p]
231       
232        if(gIsLogScale)
233                mat = log(linMat)
234        else
235                mat = linMat
236        endif
237       
238        return(0)
239End
240
241// this assumes that:
242// --QxQy data was written out in the format specified by the Igor macros, that is the x varies most rapidly
243// --the matrix is square!
244//
245// probably some other stuff...
246//
247Function ConvertQxQy2Mat(Qx,Qy,inten,matStr)
248        Wave Qx,Qy,inten
249        String matStr
250       
251        String folderStr=GetWavesDataFolder(Qx,1)
252       
253        Variable num=sqrt(numpnts(Qx))          //assumes square matrix, Qx = num x num points long
254        Make/O/D/N=(num,num) $(folderStr + matStr)
255        Wave mat=$matStr
256       
257        WaveStats/Q Qx
258        SetScale/I x, V_min, V_max, "", mat
259        WaveStats/Q Qy
260        SetScale/I y, V_min, V_max, "", mat
261       
262        Variable xrows=num
263       
264        mat = inten[q*xrows+p]
265       
266        return(0)
267End
268
269
270//str is the full path to the surface to append
271Proc AppendSurfaceToGizmo(str)
272        String str
273       
274        PauseUpdate; Silent 1   // Building Gizmo 6 window...
275
276        AppendToGizmo/Z Surface=$str,name=surface1
277       
278        // for a constant color (model is darker on top, lighter on the bottom)
279        //need these two lines, plus a color
280        ModifyGizmo ModifyObject=surface1 property={ surfaceColorType,1}
281        ModifyGizmo ModifyObject=surface1 property={ srcMode,0}
282        //green
283        ModifyGizmo ModifyObject=surface1 property={ frontColor,0.528923,0.882353,0.321584,1}
284        ModifyGizmo ModifyObject=surface1 property={ backColor,0.300221,0.6,1.5259e-05,1}
285        //red
286//      ModifyGizmo ModifyObject=surface1 property={ frontColor,1,0.749996,0.749996,1}
287//      ModifyGizmo ModifyObject=surface1 property={ backColor,1,0.250019,0.250019,1}
288
289        ModifyGizmo ModifyObject=surface1 property={ SurfaceCTABScaling,4}
290       
291        // for a color table (maybe not a good choice for vizualization if data uses a color table)
292//      ModifyGizmo ModifyObject=surface1 property={ srcMode,0}
293//      ModifyGizmo ModifyObject=surface1 property={ surfaceCTab,Red}
294       
295//      ModifyGizmo setDisplayList=0, object=surface0
296//      ModifyGizmo setDisplayList=1, object=axes0
297        ModifyGizmo setDisplayList=3, object=surface1
298        ModifyGizmo SETQUATERNION={0.565517,-0.103105,-0.139134,0.806350}
299//      ModifyGizmo autoscaling=1
300//      ModifyGizmo currentGroupObject=""
301        ModifyGizmo compile
302
303//      ModifyGizmo endRecMacro
304End
305
306Macro AdjustColorTables()
307
308        ModifyGizmo ModifyObject=surface1 property={ srcMode,0}
309        ModifyGizmo ModifyObject=surface1 property={ surfaceCTab,Rainbow}
310        ModifyGizmo setDisplayList=3, object=surface1
311//      ModifyGizmo SETQUATERNION={0.565517,-0.103105,-0.139134,0.806350}
312        ModifyGizmo autoscaling=1
313        ModifyGizmo currentGroupObject=""
314        ModifyGizmo compile
315       
316end
317
318Function LogToggle2DButtonProc(ba) : ButtonControl
319        STRUCT WMButtonAction &ba
320
321        switch( ba.eventCode )
322                case 2: // mouse up
323                        // click code here
324                        String winStr=TopGizmoWindow()
325                        if(strlen(winstr)==0)
326                                Print "no gizmo window"
327                                break
328                        endif
329                        // the winStr is also the data folder
330                        // toggle everything in the data folder
331                        ToggleFolderScaling(winStr)             
332                        break
333        endswitch
334
335        return 0
336End
337
338Function Plot2DButtonProc(ba) : ButtonControl
339        STRUCT WMButtonAction &ba
340
341        switch( ba.eventCode )
342                case 2: // mouse up
343                        // click code here
344                        Execute "PlotQxQy()"
345                        break
346        endswitch
347
348        return 0
349End
350
351Function Append2DModelButtonProc(ba) : ButtonControl
352        STRUCT WMButtonAction &ba
353
354        switch( ba.eventCode )
355                case 2: // mouse up
356                        // click code here
357                        //str is the full path to the surface to append
358                        String DF=TopGizmoWindow()
359                        String str,funcStr,suffix
360                        ControlInfo/W=WrapperPanel popup_1
361                        funcStr = S_Value
362                        suffix = getModelSuffix(getFunctionCoef(funcStr))
363                        str = "root:"+DF+":"+suffix+"_mat"
364                       
365                        Execute "AppendSurfaceToGizmo(\""+str+"\")"
366//                      Print str
367                        break
368        endswitch
369
370        return 0
371End
372
373// toggle the scaling of every matrix in the folder
374Function ToggleFolderScaling(DF)
375        String DF
376
377        // look for waves DF+"_mat" (the data)
378        // and models prefix + "_mat"
379        SetDataFolder $("root:"+DF)
380        //check the global to see the state of the data
381        NVAR gIsLogScale = gIsLogScale
382       
383        String matrixList=WaveList("*_mat",";",""),item
384        Variable ii=0,num=itemsinlist(matrixlist,";"),len
385       
386        for(ii=0;ii<num;ii+=1)
387                        item = StringFromList(ii,matrixList,";")
388                        len = strlen(item)
389                        Wave w = $item
390                        Wave linW = $(item[0,len-5]+"_lin")
391                        if(gisLogScale)
392                                //make linear
393                                w=linW
394                        else   
395                                //make log scale
396                                w=log(linW)
397                        endif
398        endfor 
399       
400        // toggle the global
401        gIsLogScale = !gIsLogScale
402       
403        SetDataFolder root:
404        return(0)
405End
406
407
408Function Load2DDataButtonProc(ba) : ButtonControl
409        STRUCT WMButtonAction &ba
410
411        switch( ba.eventCode )
412                case 2: // mouse up
413                        // click code here
414                        Execute "LoadQxQy()"
415                        break
416        endswitch
417
418        return 0
419End
420
421
422// dispatch the fit
423Function Do2DFitButtonProc(ba) : ButtonControl
424        STRUCT WMButtonAction &ba
425
426        String folderStr,funcStr,coefStr
427        Variable useCursors,useEps,useConstr
428       
429        switch( ba.eventCode )
430                case 2: // mouse up
431                        ControlInfo/W=WrapperPanel popup_0
432                        folderStr=S_Value
433                       
434                        ControlInfo/W=WrapperPanel popup_1
435                        funcStr=S_Value
436                       
437                        ControlInfo/W=WrapperPanel popup_2
438                        coefStr=S_Value
439                       
440                        ControlInfo/W=WrapperPanel check_0
441                        useCursors=V_Value
442                        //
443                        // NO CURSORS for 2D waves - force to zero
444                        //
445                        useCursors = 0
446                        //
447                        ControlInfo/W=WrapperPanel check_1
448                        useEps=V_Value
449                        ControlInfo/W=WrapperPanel check_2
450                        useConstr=V_Value
451                       
452                        if(!CheckFunctionAndCoef(funcStr,coefStr))
453                                DoAlert 0,"The coefficients and function type do not match. Please correct the selections in the popup menus."
454                                break
455                        endif
456                       
457                        FitWrapper2D(folderStr,funcStr,coefStr,useCursors,useEps,useConstr)
458                       
459                        //      DoUpdate (does not work!)
460                        //?? why do I need to force an update ??
461                        if(!exists("root:"+folderStr+":"+coefStr))
462                                Wave w=$coefStr
463                        else
464                                Wave w=$("root:"+folderStr+":"+coefStr) //smeared coefs in data folder
465                        endif
466                        w[0] += 1e-6
467                        w[0] -= 1e-6
468       
469                        break
470        endswitch
471
472        return 0
473End
474
475// wrapper to do the desired fit, pretty much a clone of FitWrapper, the 1D version
476//
477// folderStr is the data folder for the desired data set
478//
479// Currently the limitations are:
480// - I have no error waves for the intensity
481// - There is no smeared model
482// - Cursors can't be used
483// - the report *probably* won't work
484Function FitWrapper2D(folderStr,funcStr,coefStr,useCursors,useEps,useConstr)
485        String folderStr,funcStr,coefStr
486        Variable useCursors,useEps,useConstr
487
488        String suffix=getModelSuffix(coefStr)
489       
490        SetDataFolder $("root:"+folderStr)
491        if(!exists(coefStr))
492                // must be unsmeared model, work in the root folder
493                SetDataFolder root:                             
494                if(!exists(coefStr))            //this should be fine if the coef filter is working, but check anyhow
495                        DoAlert 0,"the coefficient and data sets do not match"
496                        return 0
497                endif
498        endif
499               
500        WAVE cw=$(coefStr)     
501        Wave hold=$("Hold_"+suffix)
502        Wave/T lolim=$("LoLim_"+suffix)
503        Wave/T hilim=$("HiLim_"+suffix)
504        Wave eps=$("epsilon_"+suffix)
505       
506// fill a struct instance whether I need one or not
507        String DF="root:"+folderStr+":"
508       
509        Struct ResSmearAAOStruct fs
510//      WAVE resW = $(DF+folderStr+"_res")             
511//      WAVE fs.resW =  resW
512        WAVE inten=$(DF+folderStr+"_i")
513        WAVE Qx=$(DF+folderStr+"_qx")
514        WAVE Qy=$(DF+folderStr+"_qy")
515//      Wave fs.coefW = cw
516//      Wave fs.yW = yw
517//      Wave fs.xW = xw
518       
519        // generate my own error wave for I(qx,qy)
520        Duplicate/O inten sw
521        sw = sqrt(sw)           //assumes Poisson statistics for each cell (counter)
522//      sw = 0.05*sw            // uniform 5% error? tends to favor the low intensity too strongly
523
524        // generate my own mask wave - as a matrix first, then redimension to N*N vector
525        // default mask is two pixels all the way around, (0 is excluded, 1 is included)
526        WAVE DataMat=$(DF+folderStr+"_lin")
527        if(exists(DF+"mask") == 0)
528                Duplicate/O dataMat mask
529                Variable bsRadius=8             //pixels?
530                MakeBSMask(mask,bsRadius)
531        Endif
532       
533
534       
535//      Duplicate/O yw $(DF+"FitYw")
536//      WAVE fitYw = $(DF+"FitYw")
537//      fitYw = NaN
538
539        //for now, use res will always be 0 for 2D functions   
540        Variable useRes=0
541        if(stringmatch(funcStr, "Smear*"))              // if it's a smeared function, need a struct
542                useRes=1
543        endif
544       
545        // do not construct constraints for any of the coefficients that are being held
546        // -- this will generate an "unknown error" from the curve fitting
547        Make/O/T/N=0 constr
548        if(useConstr)
549                String constraintExpression
550                Variable i, nPnts=DimSize(lolim, 0),nextRow=0
551                for (i=0; i < nPnts; i += 1)
552                        if (strlen(lolim[i]) > 0 && hold[i] == 0)
553                                InsertPoints nextRow, 1, constr
554                                sprintf constraintExpression, "K%d > %s", i, lolim[i]
555                                constr[nextRow] = constraintExpression
556                                nextRow += 1
557                        endif
558                        if (strlen(hilim[i]) > 0 && hold[i] == 0)
559                                InsertPoints nextRow, 1, constr
560                                sprintf constraintExpression, "K%d < %s", i, hilim[i]
561                                constr[nextRow] = constraintExpression
562                                nextRow += 1
563                        endif
564                endfor
565        endif
566
567///// NO CURSORS for 2D waves
568        //if useCursors, and the data is USANS, need to feed a (reassigned) trimmed matrix to the fit
569//      Variable pt1,pt2,newN
570//      if(useCursors && (dimsize(resW,1) > 4) )
571//              if(pcsr(A) > pcsr(B))
572//                      pt1 = pcsr(B)
573//                      pt2 = pcsr(A)
574//              else
575//                      pt1 = pcsr(A)
576//                      pt2 = pcsr(B)
577//              endif
578//              newN = pt2 - pt1 + 1            // +1 includes both cursors in the fit
579//              Make/O/D/N=(newN,newN) $(DF+"crsrResW")
580//              WAVE crsrResW = $(DF+"crsrResW")
581//              crsrResW = resW[p+pt1][q+pt1]
582//              //assign to the struct
583//              WAVE fs.resW =  crsrResW               
584//      endif
585
586// create these variables so that FuncFit will set them on exit
587        Variable/G V_FitError=0                         //0=no err, 1=error,(2^1+2^0)=3=singular matrix
588        Variable/G V_FitQuitReason=0            //0=ok,1=maxiter,2=user stop,3=no chisq decrease
589       
590// don't use the auto-destination with no flag, it doesn't appear to work correctly
591// dispatch the fit
592        //      FuncFit/H="11110111111"/NTHR=0 Cylinder2D_D :cyl2d_c_txt:coef_Cyl2D_D  :cyl2d_c_txt:cyl2d_c_txt_i /X={:cyl2d_c_txt:cyl2d_c_txt_qy,:cyl2d_c_txt:cyl2d_c_txt_qx} /W=:cyl2d_c_txt:sw /I=1 /M=:cyl2d_c_txt:mask /D
593
594        do
595                if(useRes && useEps && useCursors && useConstr)         //do it all
596                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qx,Qy} /M=mask /W=sw /I=1 /D /E=eps /C=constr
597                        break
598                endif
599               
600                if(useRes && useEps && useCursors)              //no constr
601                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qx,Qy} /M=mask /W=sw /I=1 /D /E=eps
602                        break
603                endif
604               
605                if(useRes && useEps && useConstr)               //no crsr
606                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qx,Qy} /M=mask /W=sw /I=1 /D /E=eps /C=constr
607                        break
608                endif
609               
610                if(useRes && useCursors && useConstr)           //no eps
611                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qx,Qy} /M=mask /W=sw /I=1 /D /C=constr
612                        break
613                endif
614               
615                if(useRes && useCursors)                //no eps, no constr
616                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qx,Qy} /M=mask /W=sw /I=1 /D
617                        break
618                endif
619               
620                if(useRes && useEps)            //no crsr, no constr
621                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qx,Qy} /M=mask /W=sw /I=1 /D /E=eps
622                        break
623                endif
624       
625                if(useRes && useConstr)         //no crsr, no eps
626                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qx,Qy} /M=mask /W=sw /I=1 /D /C=constr
627                        break
628                endif
629               
630                if(useRes)              //just res
631                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qx,Qy} /M=mask /W=sw /I=1 /D
632                        break
633                endif
634               
635/////   same as above, but all without useRes (no /STRC flag)
636                if(useEps && useCursors && useConstr)           //do it all
637                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qx,Qy} /M=mask /W=sw /I=1 /D /E=eps /C=constr
638                        break
639                endif
640               
641                if(useEps && useCursors)                //no constr
642                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qx,Qy} /M=mask /W=sw /I=1 /D /E=eps
643                        break
644                endif
645               
646               
647                if(useEps && useConstr)         //no crsr
648                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qx,Qy} /M=mask /W=sw /I=1 /D /E=eps /C=constr
649                        break
650                endif
651               
652                if(useCursors && useConstr)             //no eps
653                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qx,Qy} /M=mask /W=sw /I=1 /D /C=constr
654                        break
655                endif
656               
657                if(useCursors)          //no eps, no constr
658                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qx,Qy} /M=mask /W=sw /I=1 /D
659                        break
660                endif
661               
662                if(useEps)              //no crsr, no constr
663                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qx,Qy} /M=mask /W=sw /I=1 /D /E=eps
664                        break
665                endif
666       
667                if(useConstr)           //no crsr, no eps
668                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qx,Qy} /M=mask /W=sw /I=1 /D /C=constr
669                        break
670                endif
671               
672                //just a plain vanilla fit
673                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qx,Qy} /M=mask /W=sw /I=1 /D
674       
675        while(0)
676       
677        // append the fit
678        // need to manage duplicate copies
679        // Don't plot the full curve if cursors were used (set fitYw to NaN on entry...)
680//      String traces=TraceNameList("", ";", 1 )                //"" as first parameter == look on the target graph
681//      if(strsearch(traces,"FitYw",0) == -1)
682//              AppendToGraph FitYw vs xw
683//      else
684//              RemoveFromGraph FitYw
685//              AppendToGraph FitYw vs xw
686//      endif
687//      ModifyGraph lsize(FitYw)=2,rgb(FitYw)=(0,0,0)
688       
689//      DoUpdate                //force update of table and graph with fitted values (why doesn't this work? - the table still does not update)
690       
691        // report the results (to the panel?)
692        print "V_chisq = ",V_chisq
693        print cw
694        WAVE w_sigma
695        print w_sigma
696        String resultStr=""
697               
698        //now re-write the results
699        sprintf resultStr,"Chi^2 = %g  Sqrt(X^2/N) = %g",V_chisq,sqrt(V_chisq/V_Npnts)
700        resultStr = PadString(resultStr,63,0x20)
701        GroupBox grpBox_2 title=resultStr
702        ControlUpdate/W=WrapperPanel grpBox_2
703        sprintf resultStr,"FitErr = %s : FitQuit = %s",W_ErrorMessage(V_FitError),W_QuitMessage(V_FitQuitReason)
704        resultStr = PadString(resultStr,63,0x20)
705        GroupBox grpBox_3 title=resultStr
706        ControlUpdate/W=WrapperPanel grpBox_3
707       
708        Variable yesSave=0,yesReport=0
709        ControlInfo/W=WrapperPanel check_4
710        yesReport = V_Value
711        ControlInfo/W=WrapperPanel check_5
712        yesSave = V_Value
713       
714       
715        if(yesReport)
716                String parStr=GetWavesDataFolder(cw,1)+ WaveList("*param*"+suffix, "", "TEXT:1," )              //this is *hopefully* one wave
717                String topGraph= TopGizmoWindow()       //this is the topmost Gizmo (XOP) window
718               
719                DoUpdate                //force an update of the graph before making a copy of it for the report
720       
721                W_GenerateReport(funcStr,folderStr,$parStr,cw,yesSave,V_chisq,W_sigma,V_npnts,V_FitError,V_FitQuitReason,V_startRow,V_endRow,topGraph)
722        endif
723       
724        SetDataFolder root:
725        return(0)
726End
727
728
729// right now, there are only unsmeared models, but I want experimental points
730// for the QxQy of the calculation - so get the folder string
731Function Plot2DFunctionButtonProc(ba) : ButtonControl
732        STRUCT WMButtonAction &ba
733
734        String folderStr,funcStr,coefStr,cmdStr=""
735       
736        switch( ba.eventCode )
737                case 2: // mouse up
738                        ControlInfo/W=WrapperPanel popup_0
739                        folderStr=S_Value
740                       
741                        ControlInfo/W=WrapperPanel popup_1
742                        funcStr=S_Value
743                       
744                        // check for smeared or smeared function
745//                      if(stringmatch(funcStr, "Smear*" )==1)
746                                //it's a smeared model
747                                // check for the special case of RPA that has an extra parameter
748//                              if(strsearch(funcStr, "RPAForm", 0 ,0) == -1)
749                                        sprintf cmdStr, "Plot%s(\"%s\")",funcStr,folderStr              //not RPA
750//                              else
751//                                      sprintf cmdStr, "Plot%s(\"%s\",)",funcStr,folderStr             //yes RPA, leave a comma for input
752//                              endif
753//                      else
754//                              // it's not,                   
755//                              sprintf cmdStr, "Plot%s()",funcStr
756//                      endif
757                       
758                        //Print cmdStr
759                        Execute cmdStr
760                       
761                        //pop the function menu to set the proper coefficients
762                        DoWindow/F WrapperPanel
763                        STRUCT WMPopupAction pa
764                        pa.popStr = funcStr
765                        pa.eventcode = 2
766                        Function_PopMenuProc(pa)
767       
768                        break
769        endswitch
770
771        return 0
772End
773
774// unused - all of this functionality has been added to the Wrapper Panel
775Window Plot_2D_Controls() : Panel
776        PauseUpdate; Silent 1           // building window...
777        NewPanel /W=(950,44,1250,244)
778        Button button0,pos={172,37},size={70,20},proc=LogToggle2DButtonProc,title="Log/Lin"
779        Button button1,pos={146,9},size={100,20},proc=Plot2DButtonProc,title="Plot 2D Data"
780        Button button2,pos={164,118},size={120,20},proc=Append2DModelButtonProc,title="Append Model"
781        PopupMenu popup_1,pos={9,84},size={132,20},proc=Function_PopMenuProc,title="Function"
782        PopupMenu popup_1,mode=1,popvalue="Cylinder2D",value= #"W_FunctionPopupList()"
783        Button button3,pos={11,9},size={100,20},proc=Load2DDataButtonProc,title="Load 2D Data"
784        Button button4,pos={164,161},size={120,20},proc=Do2DFitButtonProc,title="Do 2D Fit"
785        Button button5,pos={164,85},size={120,20},proc=Plot2DFunctionButtonProc,title="Plot 2D Function"
786EndMacro
787
788
789Function/S TopGizmoWindow()
790        Return(StringFromList(0,WinList("*",";","WIN:4096")))
791end
792
793////
794//
795Macro Plot2DVsPointNumber(str)
796        String str
797        Prompt str,"Pick the data folder containing 2D data",popup,getAList(4)
798
799        PauseUpdate; Silent 1           // building window...
800        String fldrSav0= GetDataFolder(1)
801        SetDataFolder $("root:"+str)
802        Display /W=(241,352,810,842) $(str+"_i")
803        SetDataFolder fldrSav0
804        ModifyGraph mode=3
805        ModifyGraph marker=19
806        ModifyGraph lSize=2
807        ModifyGraph rgb($(str+"_i"))=(0,0,0)
808        ModifyGraph msize=1
809        ModifyGraph grid=1
810        ModifyGraph log(left)=1
811        ModifyGraph mirror=2
812        if(exists("root:"+str+":sw"))
813                ErrorBars/T=0 $(str+"_i") Y,wave=($("root:"+str+":sw"),$("root:"+str+":sw"))
814        endif
815        SetDataFolder fldrSav0
816EndMacro
817
818//Macro CalculateChiSquared(str)
819//      String str
820//      Prompt str,"Pick the data folder containing 2D data",popup,getAList(4)
821//
822//
823//      String fldrSav0= GetDataFolder(1)
824//      SetDataFolder $("root:"+str)
825//
826//      Duplicate/O $(str+"_i") chi
827//      chi = ((zwave_cyl2D_D - $(str+"_i"))/sw )^2
828//     
829//      chi = (mask == 1) ? chi : 0
830//     
831//      Print sum(chi,-inf,inf)
832//     
833//      SetDataFolder fldrSav0
834//EndMacro
835
836
837Function MakeBSMask(mask,rad)
838        Wave mask
839        Variable rad
840
841
842// find the center based on the wave scaling
843        Variable xCtr,yCtr,Qzero=0
844        xCtr = (Qzero - DimOffset(Mask, 0))/DimDelta(Mask,0)
845        yCtr = (Qzero - DimOffset(Mask, 1))/DimDelta(Mask,1)
846
847        Print xctr,yctr
848
849//      Variable center = sqrt(numpnts(mask))/2 -0.5
850
851        mask = (sqrt((p-xCtr)^2+(q-yCtr)^2) < rad) ? 0 : 1
852
853        Variable xDim, yDim
854        xDim = DimSize(mask,0)
855        yDim = DimSize(mask,1)
856        mask[][0] = 0
857        mask[][1] = 0
858        mask[][yDim-2] = 0
859        mask[][yDim-1] = 0
860        mask[0][] = 0
861        mask[1][] = 0
862        mask[xDim-2][] = 0
863        mask[xDim-1][] = 0
864       
865        Redimension/N=(xDim*yDim) mask          //now 1D
866       
867       
868End
Note: See TracBrowser for help on using the repository browser.