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

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

bits and tweaks to get 2D fitting to work. Most significant changes are the call to the 2D AAO function in the correct XY order and the FuncFit? /X={} flag which needs to be {y,x} rather than the expected {x,y}

File size: 24.5 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        Duplicate/O dataMat mask
528        Variable xDim, yDim
529        xDim = DimSize(dataMat,0)
530        yDim = DimSize(dataMat,1)
531        mask = 1
532        mask[][0] = 0
533        mask[][1] = 0
534        mask[][yDim-2] = 0
535        mask[][yDim-1] = 0
536        mask[0][] = 0
537        mask[1][] = 0
538        mask[xDim-2][] = 0
539        mask[xDim-1][] = 0
540        Redimension/N=(xDim*yDim) mask          //now 1D
541       
542       
543//      Duplicate/O yw $(DF+"FitYw")
544//      WAVE fitYw = $(DF+"FitYw")
545//      fitYw = NaN
546
547        //for now, use res will always be 0 for 2D functions   
548        Variable useRes=0
549        if(stringmatch(funcStr, "Smear*"))              // if it's a smeared function, need a struct
550                useRes=1
551        endif
552       
553        Make/O/T/N=0 constr
554        if(useConstr)
555                String constraintExpression
556                Variable i, nPnts=DimSize(lolim, 0),nextRow=0
557                for (i=0; i < nPnts; i += 1)
558                        if (strlen(lolim[i]) > 0)
559                                InsertPoints nextRow, 1, constr
560                                sprintf constraintExpression, "K%d > %s", i, lolim[i]
561                                constr[nextRow] = constraintExpression
562                                nextRow += 1
563                        endif
564                        if (strlen(hilim[i]) > 0)
565                                InsertPoints nextRow, 1, constr
566                                sprintf constraintExpression, "K%d < %s", i, hilim[i]
567                                constr[nextRow] = constraintExpression
568                                nextRow += 1
569                        endif
570                endfor
571        endif
572
573///// NO CURSORS for 2D waves
574        //if useCursors, and the data is USANS, need to feed a (reassigned) trimmed matrix to the fit
575//      Variable pt1,pt2,newN
576//      if(useCursors && (dimsize(resW,1) > 4) )
577//              if(pcsr(A) > pcsr(B))
578//                      pt1 = pcsr(B)
579//                      pt2 = pcsr(A)
580//              else
581//                      pt1 = pcsr(A)
582//                      pt2 = pcsr(B)
583//              endif
584//              newN = pt2 - pt1 + 1            // +1 includes both cursors in the fit
585//              Make/O/D/N=(newN,newN) $(DF+"crsrResW")
586//              WAVE crsrResW = $(DF+"crsrResW")
587//              crsrResW = resW[p+pt1][q+pt1]
588//              //assign to the struct
589//              WAVE fs.resW =  crsrResW               
590//      endif
591
592// create these variables so that FuncFit will set them on exit
593        Variable/G V_FitError=0                         //0=no err, 1=error,(2^1+2^0)=3=singular matrix
594        Variable/G V_FitQuitReason=0            //0=ok,1=maxiter,2=user stop,3=no chisq decrease
595       
596// don't use the auto-destination with no flag, it doesn't appear to work correctly
597// dispatch the fit
598        //      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
599
600// !!! /X={Qy,Qx} is correct !!! using {Qx,Qy} return jibberish for the chi^2 from the fit
601
602        do
603                if(useRes && useEps && useCursors && useConstr)         //do it all
604                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qy,Qx} /M=mask /W=sw /I=1 /D /E=eps /C=constr
605                        break
606                endif
607               
608                if(useRes && useEps && useCursors)              //no constr
609                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qy,Qx} /M=mask /W=sw /I=1 /D /E=eps
610                        break
611                endif
612               
613                if(useRes && useEps && useConstr)               //no crsr
614                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qy,Qx} /M=mask /W=sw /I=1 /D /E=eps /C=constr
615                        break
616                endif
617               
618                if(useRes && useCursors && useConstr)           //no eps
619                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qy,Qx} /M=mask /W=sw /I=1 /D /C=constr
620                        break
621                endif
622               
623                if(useRes && useCursors)                //no eps, no constr
624                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qy,Qx} /M=mask /W=sw /I=1 /D
625                        break
626                endif
627               
628                if(useRes && useEps)            //no crsr, no constr
629                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qy,Qx} /M=mask /W=sw /I=1 /D /E=eps
630                        break
631                endif
632       
633                if(useRes && useConstr)         //no crsr, no eps
634                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qy,Qx} /M=mask /W=sw /I=1 /D /C=constr
635                        break
636                endif
637               
638                if(useRes)              //just res
639                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qy,Qx} /M=mask /W=sw /I=1 /D
640                        break
641                endif
642               
643/////   same as above, but all without useRes (no /STRC flag)
644                if(useEps && useCursors && useConstr)           //do it all
645                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qy,Qx} /M=mask /W=sw /I=1 /D /E=eps /C=constr
646                        break
647                endif
648               
649                if(useEps && useCursors)                //no constr
650                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qy,Qx} /M=mask /W=sw /I=1 /D /E=eps
651                        break
652                endif
653               
654               
655                if(useEps && useConstr)         //no crsr
656                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qy,Qx} /M=mask /W=sw /I=1 /D /E=eps /C=constr
657                        break
658                endif
659               
660                if(useCursors && useConstr)             //no eps
661                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qy,Qx} /M=mask /W=sw /I=1 /D /C=constr
662                        break
663                endif
664               
665                if(useCursors)          //no eps, no constr
666                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten[pcsr(A),pcsr(B)] /X={Qy,Qx} /M=mask /W=sw /I=1 /D
667                        break
668                endif
669               
670                if(useEps)              //no crsr, no constr
671                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qy,Qx} /M=mask /W=sw /I=1 /D /E=eps
672                        break
673                endif
674       
675                if(useConstr)           //no crsr, no eps
676                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qy,Qx} /M=mask /W=sw /I=1 /D /C=constr
677                        break
678                endif
679               
680                //just a plain vanilla fit
681                        FuncFit/H=getHStr(hold) /NTHR=0 $funcStr cw, inten /X={Qy,Qx} /M=mask /W=sw /I=1 /D
682       
683        while(0)
684       
685        // append the fit
686        // need to manage duplicate copies
687        // Don't plot the full curve if cursors were used (set fitYw to NaN on entry...)
688//      String traces=TraceNameList("", ";", 1 )                //"" as first parameter == look on the target graph
689//      if(strsearch(traces,"FitYw",0) == -1)
690//              AppendToGraph FitYw vs xw
691//      else
692//              RemoveFromGraph FitYw
693//              AppendToGraph FitYw vs xw
694//      endif
695//      ModifyGraph lsize(FitYw)=2,rgb(FitYw)=(0,0,0)
696       
697//      DoUpdate                //force update of table and graph with fitted values (why doesn't this work? - the table still does not update)
698       
699        // report the results (to the panel?)
700        print "V_chisq = ",V_chisq
701        print cw
702        WAVE w_sigma
703        print w_sigma
704        String resultStr=""
705               
706        //now re-write the results
707        sprintf resultStr,"Chi^2 = %g  Sqrt(X^2/N) = %g",V_chisq,sqrt(V_chisq/V_Npnts)
708        resultStr = PadString(resultStr,63,0x20)
709        GroupBox grpBox_2 title=resultStr
710        ControlUpdate/W=WrapperPanel grpBox_2
711        sprintf resultStr,"FitErr = %s : FitQuit = %s",W_ErrorMessage(V_FitError),W_QuitMessage(V_FitQuitReason)
712        resultStr = PadString(resultStr,63,0x20)
713        GroupBox grpBox_3 title=resultStr
714        ControlUpdate/W=WrapperPanel grpBox_3
715       
716        Variable yesSave=0,yesReport=0
717        ControlInfo/W=WrapperPanel check_4
718        yesReport = V_Value
719        ControlInfo/W=WrapperPanel check_5
720        yesSave = V_Value
721       
722       
723        if(yesReport)
724                String parStr=GetWavesDataFolder(cw,1)+ WaveList("*param*"+suffix, "", "TEXT:1," )              //this is *hopefully* one wave
725                String topGraph= TopGizmoWindow()       //this is the topmost Gizmo (XOP) window
726               
727                DoUpdate                //force an update of the graph before making a copy of it for the report
728       
729                W_GenerateReport(funcStr,folderStr,$parStr,cw,yesSave,V_chisq,W_sigma,V_npnts,V_FitError,V_FitQuitReason,V_startRow,V_endRow,topGraph)
730        endif
731       
732        SetDataFolder root:
733        return(0)
734End
735
736
737// right now, there are only unsmeared models, but I want experimental points
738// for the QxQy of the calculation - so get the folder string
739Function Plot2DFunctionButtonProc(ba) : ButtonControl
740        STRUCT WMButtonAction &ba
741
742        String folderStr,funcStr,coefStr,cmdStr=""
743       
744        switch( ba.eventCode )
745                case 2: // mouse up
746                        ControlInfo/W=WrapperPanel popup_0
747                        folderStr=S_Value
748                       
749                        ControlInfo/W=WrapperPanel popup_1
750                        funcStr=S_Value
751                       
752                        // check for smeared or smeared function
753//                      if(stringmatch(funcStr, "Smear*" )==1)
754                                //it's a smeared model
755                                // check for the special case of RPA that has an extra parameter
756//                              if(strsearch(funcStr, "RPAForm", 0 ,0) == -1)
757                                        sprintf cmdStr, "Plot%s(\"%s\")",funcStr,folderStr              //not RPA
758//                              else
759//                                      sprintf cmdStr, "Plot%s(\"%s\",)",funcStr,folderStr             //yes RPA, leave a comma for input
760//                              endif
761//                      else
762//                              // it's not,                   
763//                              sprintf cmdStr, "Plot%s()",funcStr
764//                      endif
765                       
766                        //Print cmdStr
767                        Execute cmdStr
768                       
769                        //pop the function menu to set the proper coefficients
770                        DoWindow/F WrapperPanel
771                        STRUCT WMPopupAction pa
772                        pa.popStr = funcStr
773                        pa.eventcode = 2
774                        Function_PopMenuProc(pa)
775       
776                        break
777        endswitch
778
779        return 0
780End
781
782// unused - all of this functionality has been added to the Wrapper Panel
783Window Plot_2D_Controls() : Panel
784        PauseUpdate; Silent 1           // building window...
785        NewPanel /W=(950,44,1250,244)
786        Button button0,pos={172,37},size={70,20},proc=LogToggle2DButtonProc,title="Log/Lin"
787        Button button1,pos={146,9},size={100,20},proc=Plot2DButtonProc,title="Plot 2D Data"
788        Button button2,pos={164,118},size={120,20},proc=Append2DModelButtonProc,title="Append Model"
789        PopupMenu popup_1,pos={9,84},size={132,20},proc=Function_PopMenuProc,title="Function"
790        PopupMenu popup_1,mode=1,popvalue="Cylinder2D",value= #"W_FunctionPopupList()"
791        Button button3,pos={11,9},size={100,20},proc=Load2DDataButtonProc,title="Load 2D Data"
792        Button button4,pos={164,161},size={120,20},proc=Do2DFitButtonProc,title="Do 2D Fit"
793        Button button5,pos={164,85},size={120,20},proc=Plot2DFunctionButtonProc,title="Plot 2D Function"
794EndMacro
795
796
797Function/S TopGizmoWindow()
798        Return(StringFromList(0,WinList("*",";","WIN:4096")))
799end
800
801////
802//
803Macro Plot2DVsPointNumber(str)
804        String str
805        Prompt str,"Pick the data folder containing 2D data",popup,getAList(4)
806
807        PauseUpdate; Silent 1           // building window...
808        String fldrSav0= GetDataFolder(1)
809        SetDataFolder $("root:"+str)
810        Display /W=(241,352,810,842) $(str+"_i")
811        SetDataFolder fldrSav0
812        ModifyGraph mode=3
813        ModifyGraph marker=19
814        ModifyGraph lSize=2
815        ModifyGraph rgb($(str+"_i"))=(0,0,0)
816        ModifyGraph msize=1
817        ModifyGraph grid=1
818        ModifyGraph log(left)=1
819        ModifyGraph mirror=2
820        if(exists("root:"+str+":sw"))
821                ErrorBars/T=0 $(str+"_i") Y,wave=($("root:"+str+":sw"),$("root:"+str+":sw"))
822        endif
823        SetDataFolder fldrSav0
824EndMacro
825
826Macro CalculateChiSquared(str)
827        String str
828        Prompt str,"Pick the data folder containing 2D data",popup,getAList(4)
829
830
831        String fldrSav0= GetDataFolder(1)
832        SetDataFolder $("root:"+str)
833
834        Duplicate/O $(str+"_i") chi
835        chi = ((zwave_cyl2D_D - $(str+"_i"))/sw )^2
836       
837        chi = (mask == 1) ? chi : 0
838       
839        Print sum(chi,-inf,inf)
840       
841        SetDataFolder fldrSav0
842EndMacro
Note: See TracBrowser for help on using the repository browser.