diff --git a/doc/html/anglescan-processing_8dox.html b/doc/html/anglescan-processing_8dox.html new file mode 100644 index 0000000..33b064c --- /dev/null +++ b/doc/html/anglescan-processing_8dox.html @@ -0,0 +1,100 @@ + + + + + + + +PEARL Procedures: anglescan-processing.dox File Reference + + + + + + + + + + + + + + +
+
+ + + + + + +
+
PEARL Procedures +  rev-distro-2.0.2-0-g3235d52 +
+
Igor procedures for the analysis of PEARL data
+
+
+ + + + + + + +
+
+ +
+
+
+ +
+ +
+
+ + +
+ +
+ +
+
+
anglescan-processing.dox File Reference
+
+
+
+
+ + + + diff --git a/doc/html/dir_fe5dc42579d4b99403482a3a637d9f7d.html b/doc/html/dir_fe5dc42579d4b99403482a3a637d9f7d.html index 33a950c..b4d5f0a 100644 --- a/doc/html/dir_fe5dc42579d4b99403482a3a637d9f7d.html +++ b/doc/html/dir_fe5dc42579d4b99403482a3a637d9f7d.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl Directory Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
- + - - + + + +
-
-
fermi-edge-analysis.ipf File Reference
+
fermi-edge-analysis.ipf File Reference
-

tools for analysing the Fermi edge measured by the Scienta EW4000 analyser. -More...

-
#include "pearl-area-profiles"
-

Go to the source code of this file.

- - - - - - - - - - - - - - - - - - - -

-Functions

variable analyse_curved_edge (wave data)
 
variable record_results (variable index)
 
variable integrate_curved_edge (wave data, wave data_sig)
 
variable slit_correction (wave data, wave data_out, variable epass)
 
threadsafe variable FermiFuncLinDOS2D_corr (variable w, threadsafe x, wave y)
 
threadsafe variable slit_shift (variable ypix, variable epass)
 
variable show_shift (wave data)
 
variable analyser_energy_resolution (variable epass, variable slit)
 calculate the energy resolution of the analyser More...
 
- - - - - - - - - - - - - -

-Variables

static const variable mcp_radius_pix = 555
 MCP radius seen by the camera in pixels. More...
 
static const variable mcp_radius_mm = 20
 physical size (radius) of the MCP in mm More...
 
static const variable hemi_radius_mm = 200
 physical size (radius) of the hemisphere in mm More...
 
static const variable mcp_radius_epass = 0.04
 energy range imaged on MCP relative to the pass energy More...
 
-

Detailed Description

-

tools for analysing the Fermi edge measured by the Scienta EW4000 analyser.

-

proposed procedure

- -
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
-
-thomas dienel
- - -

Definition in file fermi-edge-analysis.ipf.

-

Function Documentation

- -
-
- - - - - - - - -
variable analyse_curved_edge (wave data)
-
- -

Definition at line 27 of file fermi-edge-analysis.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable analyser_energy_resolution (variable epass,
variable slit 
)
-
- -

calculate the energy resolution of the analyser

-
Parameters
- - - -
epasspass energy in eV
slitanalyser entrance slit in mm
-
-
-
Returns
energy resolution (FWHM)
- -

Definition at line 306 of file fermi-edge-analysis.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe variable FermiFuncLinDOS2D_corr (variable w,
threadsafe x,
wave y 
)
-
- -

Definition at line 216 of file fermi-edge-analysis.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable integrate_curved_edge (wave data,
wave data_sig 
)
-
- -

Definition at line 116 of file fermi-edge-analysis.ipf.

- -
-
- -
-
- - - - - - - - -
variable record_results (variable index)
-
- -

Definition at line 98 of file fermi-edge-analysis.ipf.

- -
-
- -
-
- - - - - - - - -
variable show_shift (wave data)
-
- -

Definition at line 284 of file fermi-edge-analysis.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable slit_correction (wave data,
wave data_out,
variable epass 
)
-
- -

Definition at line 173 of file fermi-edge-analysis.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
threadsafe variable slit_shift (variable ypix,
variable epass 
)
-
- -

Definition at line 267 of file fermi-edge-analysis.ipf.

- -
-
-

Variable Documentation

- -
-
- - - - - -
- - - - -
const variable hemi_radius_mm = 200
-
-static
-
- -

physical size (radius) of the hemisphere in mm

- -

Definition at line 263 of file fermi-edge-analysis.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable mcp_radius_epass = 0.04
-
-static
-
- -

energy range imaged on MCP relative to the pass energy

- -

Definition at line 265 of file fermi-edge-analysis.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable mcp_radius_mm = 20
-
-static
-
- -

physical size (radius) of the MCP in mm

- -

Definition at line 261 of file fermi-edge-analysis.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable mcp_radius_pix = 555
-
-static
-
- -

MCP radius seen by the camera in pixels.

- -

Definition at line 259 of file fermi-edge-analysis.ipf.

- -
-
diff --git a/doc/html/fermi-edge-analysis_8ipf_source.html b/doc/html/fermi-edge-analysis_8ipf_source.html index 853cb4b..0b543ac 100644 --- a/doc/html/fermi-edge-analysis_8ipf_source.html +++ b/doc/html/fermi-edge-analysis_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: fermi-edge-analysis.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #include "pearl-area-profiles"
3 
4 // $Id$
5 
25 
26 
27 variable analyse_curved_edge(wave data){
28  wave data// 2D counts data, x-scale = kinetic energy, y-scale = analyser angle
29  variable guess_EF// initial guess of the Fermi level
30 
31  dfref savedf = GetDataFolderDFR()
32  dfref datadf = GetWavesDataFolderDFR(data)
33  setdatafolder datadf
34 
35  make /n=5 /d /o w_coef_int
36  make /n=7 /d /o w_coef_curved
37 
38  // 1) integrate data
39  wave xint = ad_profile_x(data, -inf, inf, "", noavg=1)
40  duplicate /free xint, xint_sig
41  xint_sig = sqrt(xint * 4) / 4
42  variable xmin = wavemin(xint)
43  variable xmax = wavemax(xint)
44  variable xmean = mean(xint)
45 
46  // 2) fit integrated data for reference
47  w_coef_int[0] = xmin
48  w_coef_int[1] = 0
49  w_coef_int[2] = xmax - xmin
50  w_coef_int[3] = dimoffset(xint, 0) + dimdelta(xint, 0) * dimsize(xint, 0) / 2
51  w_coef_int[4] = 100
52  FuncFit /NTHR=0 FermiFuncLinDOS w_coef_int xint /D /I=1 /W=xint_sig
53  wave w_sigma
54  duplicate /o w_sigma, w_sigma_int
55 
56  // 3) normalize data
57  wave yavg = ad_profile_y(data, -inf, inf, "")
58  variable ymean = mean(yavg)
59 
60  duplicate /o data, data_norm, data_sig
61  data_sig = sqrt(data * 4) / 4
62  data_norm = data_norm * ymean / yavg[q]
63  data_sig = data_sig * ymean / yavg[q]
64 
65  // 4) fit normalized data
66  wave xavg = ad_profile_x(data, -inf, inf, "")
67  xmin = wavemin(xavg)
68  xmax = wavemax(xavg)
69  xmean = mean(xavg)
70 
71  w_coef_curved[0] = {0, 0, 1, 95.5, 100, 0, -0.0001}
72  w_coef_curved[0] = xmin
73  w_coef_curved[2] = xmax - xmin
74  w_coef_curved[3] = w_coef_int[3]
75  w_coef_curved[4] = w_coef_int[4]
76 
77  //variable box = min(11, numpnts(xavg) / 5)
78  //FindLevel /B=(box) /EDGE=2 /Q xavg, (xmin + xmax) / 2
79  //if (v_flag == 0)
80  // w_coef_curved[3] = v_levelx
81  //else
82  // w_coef_curved[3] = dimoffset(data, 0) + dimdelta(data, 0) * dimsize(data, 0) / 2
83  //endif
84 
85  duplicate /o data_norm, fit_data_norm
86  FuncFitMD /X=1 /NTHR=0 FermiFuncLinDOS_2Dcorr w_coef_curved data_norm /D=fit_data_norm /I=1 /W=data_sig
87  wave w_sigma
88  duplicate /o w_sigma, w_sigma_curved
89 
90  display /k=1; appendimage data_norm
91  ModifyImage data_norm ctab= {xmin,xmax,Grays,0}
92  AppendMatrixContour fit_data_norm
93 
94  setdatafolder savedf
95  return 0
96 };
97 
98 variable record_results(variable index){
99  variable index
100 
101  dfref savedf = GetDataFolderDFR()
102  wave /sdfr=root: Tint, Tint_sig, Tcurv, Tcurv_sig, EFcurv, EFcurv_sig
103  wave w_coef_int, w_coef_curved
104  wave w_sigma_int, w_sigma_curved
105 
106  Tint[index] = w_coef_int[4]
107  Tint_sig[index] = w_sigma_int[4]
108  Tcurv[index] = w_coef_curved[4]
109  Tcurv_sig[index] = w_sigma_curved[4]
110  EFcurv[index] = w_coef_curved[3]
111  EFcurv_sig[index] = w_sigma_curved[3]
112 
113  setdatafolder savedf
114 };
115 
116 variable integrate_curved_edge(wave data, wave data_sig){
117  wave data
118  wave /z data_sig
119  //wave coef
120 
121  string name = nameofwave(data)
122 
123  duplicate /o data, data_out
124  redimension /n=(dimsize(data,0)) data_out
125  data_out = 0
126 
127  if (waveexists(data_sig))
128  duplicate /o data_sig, sig_out
129  redimension /n=(dimsize(data,0)) sig_out
130  sig_out = 0
131  endif
132 
133  wave ywgt = ad_profile_y(data, -inf, inf, "", noavg=1)
134  ywgt = 1 / ywgt / 4
135  //ywgt = 1 / 4
136  variable sum_ywgt = sum(ywgt)
137 
138  variable nx = dimsize(data, 0)
139  variable ny = dimsize(data, 1)
140  variable iy
141  variable yy
142  variable dx
143  variable dy
144  variable dp
145  variable dp_min = 0
146 
147  wave PassEnergy = :attr:PassEnergy
148  wave NumSlices = :attr:NumSlices
149 
150  for (iy = 0; iy < ny; iy += 1)
151  dy = dimoffset(data, 1) + dimdelta(data, 1) * iy
152  dy = dy / dimdelta(data, 1)
153  dx = slit_shift(dy * 902 / NumSlices[0], PassEnergy[0])
154  dp = round(dx / dimdelta(data, 0))// <= 0
155  dp_min = min(dp_min, dp)
156 
157  data_out[] = p+dp >= 0 ? data_out + data[p+dp][iy] * ywgt[iy] : data_out
158 
159  if (waveexists(data_sig))
160  sig_out = p+dp >= 0 ? sig_out + data_sig[p+dp][iy] * ywgt[iy] : sig_out
161  endif
162  endfor
163 
164  data_out /= sum_ywgt
165  data_out[0, -dp_min][] = nan
166 
167  if (waveexists(sig_out))
168  sig_out /= sum_ywgt
169  //sig_out[0, -dp_min] = nan
170  endif
171 };
172 
173 variable slit_correction(wave data, wave data_out, variable epass){
174  wave data// must be image with original dimensions (no cropping!)
175  wave /z data_out// 2D or 1D wave to receive the result
176  // X dimension must be identical to the one of data
177  // if 2D, Y dimension must be either identical to the one of data
178  // if 1D, the result will be the sum of the corrected slices
179  variable epass// pass energy
180 
181  if (!WaveExists(data_out))
182  string name = nameofwave(data) + "_corr"
183  duplicate /o data, $name
184  wave data_out = $name
185  //redimension /n=(dimsize(data,0)) data_out
186  endif
187  data_out = 0
188 
189  variable nx = dimsize(data, 0)
190  variable ny = dimsize(data, 1)
191  variable iy
192  variable yy
193  variable dx
194  variable dy
195  variable dp
196  variable dp_min = 0
197 
198  for (iy = 0; iy < ny; iy += 1)
199  dy = dimoffset(data, 1) + dimdelta(data, 1) * iy
200  dy = dy / dimdelta(data, 1)
201  dx = slit_shift(dy * 902 / ny, epass)
202  dp = round(dx / dimdelta(data, 0))// <= 0
203  dp_min = min(dp_min, dp)
204 
205  if (wavedims(data_out) >= 2)
206  data_out[][iy] = p+dp >= 0 ? data_out + data[p+dp][iy] : data_out
207  else
208  data_out = p+dp >= 0 ? data_out + data[p+dp][iy] : data_out
209  endif
210  endfor
211 
212  data_out[0, -dp_min][] = nan
213 };
214 
215 //------------------------------------------------------------------------------
216 threadsafe variable FermiFuncLinDOS2D_corr(variable w, threadsafe x, wave y){
217 // linear density of states below Fermi level
218 // 2D data with corrections:
219 // - straight slit (slit shift)
220 // - transmission function (polynomial)
221 //------------------------------------------------------------------------------
222  Wave w; Variable x; variable y
223  // w[0] = background far above the fermi level
224  // w[1] = slope of the linear background
225  // w[2] = amplitude
226  // w[3] = fermi level in eV
227  // w[4] = temperature in K
228  // w[5] = transmission - linear term
229  // w[6] = transmission - quadratic term
230  // w[7] = transmission - cubic term
231  // w[8] = pass energy (hold this value)
232  // w[9] = y scale: pixels / unit of y
233 
234  variable pos = w[3] + slit_shift(y * w[9], w[8])
235  variable transm = 1 + w[5] * y + w[6] * y^2 + w[7] * y^3
236  variable fermi = (w[1] * min(x - pos, 0) + w[2]) / ( exp( (x - pos) / (kBoltzmann * w[4]) ) + 1.0 )
237  return transm * (fermi + w[0])
238 end
239 
240 //------------------------------------------------------------------------------
241 threadsafe Function FermiFuncLinDOS_2Dcorr_old(w,x,y) : FitFunc
242 // linear density of states below Fermi level
243 // 2D data with a polynomial shift of the Fermi level in the second dimension
244 //------------------------------------------------------------------------------
245  Wave w; Variable x; variable y
246  // w[0] = background far above the fermi level
247  // w[1] = slope of the linear background
248  // w[2] = amplitude
249  // w[3] = fermi level in eV
250  // w[4] = temperature in K
251  // w[5] = shift - linear term
252  // w[6] = shift - quadratic term
253 
254  variable pos = w[3] + w[5] * y + w[6] * y^2
255  return w[0] + (w[1] * min(x - pos, 0) + w[2]) / ( exp( (x - pos) / (kBoltzmann * w[4]) ) + 1.0 )
256 };
257 
259 static const variable mcp_radius_pix = 555;
261 static const variable mcp_radius_mm = 20;
263 static const variable hemi_radius_mm = 200;
265 static const variable mcp_radius_epass = 0.04;
266 
267 threadsafe variable slit_shift(variable ypix, variable epass){
268  // calculates the energy shift due to straight slit
269  // the radius of the curve is 1/2 of the hemisphere radius
270  variable ypix// vertical (angle/position) pixels distance from center
271  // = slice coordinate * 902 / number of slices
272  variable epass// pass energy
273 
274  variable rpix = mcp_radius_pix * hemi_radius_mm / mcp_radius_mm
275  //variable rpix = mcp_radius_pix * hemi_radius_mm / 2 / mcp_radius_mm
276  variable rene = epass * mcp_radius_epass * hemi_radius_mm / 2 / mcp_radius_mm
277 
278  variable isin = asin(ypix / rpix)
279  variable dene = rene * (cos(isin) - 1)
280 
281  return dene
282 };
283 
284 variable show_shift(wave data){
285  wave data
286  variable epass
287 
288  variable ny = dimsize(data, 1)
289  make /o /n=(ny) shift_x
290  setscale /i x -ny/2, ny/2, "", shift_x
291  wave PassEnergy = :attr:PassEnergy
292  wave NumSlices = :attr:NumSlices
293 
294  shift_x = slit_shift(x * 902 / NumSlices[0], PassEnergy[0])
295 
296  variable ecenter = dimoffset(data, 0) + dimdelta(data, 0) * dimsize(data, 0) / 2
297  shift_x += ecenter
298 };
299 
306 variable analyser_energy_resolution(variable epass, variable slit){
307  variable epass
308  variable slit
309 
310  variable respow
311  if (epass < 4)
312  respow = 1110
313  else if (epass < 8)
314  respow = 1400
315  else
316  respow = 1750
317  endif
318 
319  return epass * max(0.2, slit) / 0.2 / respow
320 };
321 
threadsafe variable FermiFuncLinDOS2D_corr(variable w, threadsafe x, wave y)
-
threadsafe variable slit_shift(variable ypix, variable epass)
-
static const variable mcp_radius_pix
MCP radius seen by the camera in pixels.
-
static const variable mcp_radius_mm
physical size (radius) of the MCP in mm
-
threadsafe wave ad_profile_y(wave dataset, variable p1, variable p2, string destname, variable noavg=defaultValue)
1D cut through 2D dataset along Y dimension, new destination wave.
-
variable analyse_curved_edge(wave data)
-
static const variable hemi_radius_mm
physical size (radius) of the hemisphere in mm
-
variable analyser_energy_resolution(variable epass, variable slit)
calculate the energy resolution of the analyser
-
variable slit_correction(wave data, wave data_out, variable epass)
-
static const variable mcp_radius_epass
energy range imaged on MCP relative to the pass energy
-
variable integrate_curved_edge(wave data, wave data_sig)
-
variable show_shift(wave data)
-
threadsafe wave ad_profile_x(wave dataset, variable q1, variable q2, string destname, variable noavg=defaultValue)
1D cut through 2D dataset along X dimension, new destination wave.
-
variable record_results(variable index)
-
+Go to the documentation of this file.
diff --git a/doc/html/files.html b/doc/html/files.html index 3e2b87a..117b219 100644 --- a/doc/html/files.html +++ b/doc/html/files.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: File List @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
- + - + + + +
+

Table of Contents

+ +

Introduction

PEARL Procedures is a suite of Igor Pro procedures developed for data acquisition and data processing at the PEARL beamline at the Swiss Light Source.

@@ -112,7 +98,7 @@ Installation

PEARL Procedures should be installed according to the regular Igor Pro guidelines. Please read the Igor help About Igor Pro User Files for details.

@@ -120,7 +106,7 @@ Installation License Information

An open distribution of PEARL Procedures is available under the Apache License, Version 2.0 at https://git.psi.ch/pearl-public/igor-procs. Users of PEARL Procedures are requested to coordinate and share the development of the code with the original author. Please read and respect the respective license agreements.

Author
Matthias Muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
-
Version
This documentation is compiled from version rev-distro-2.0.0-0-gfda49c3-dirty.
+
Version
This documentation is compiled from version rev-distro-2.0.2-0-g3235d52.
@@ -129,9 +115,9 @@ Licensed under the Apache L diff --git a/doc/html/jquery.js b/doc/html/jquery.js index d52a1c7..f5343ed 100644 --- a/doc/html/jquery.js +++ b/doc/html/jquery.js @@ -1,4 +1,4 @@ -/* +/*! * jQuery JavaScript Library v1.7.1 * http://jquery.com/ * @@ -14,13 +14,13 @@ * Date: Mon Nov 21 21:11:03 2011 -0500 */ (function(bb,L){var av=bb.document,bu=bb.navigator,bl=bb.location;var b=(function(){var bF=function(b0,b1){return new bF.fn.init(b0,b1,bD)},bU=bb.jQuery,bH=bb.$,bD,bY=/^(?:[^#<]*(<[\w\W]+>)[^>]*$|#([\w\-]*)$)/,bM=/\S/,bI=/^\s+/,bE=/\s+$/,bA=/^<(\w+)\s*\/?>(?:<\/\1>)?$/,bN=/^[\],:{}\s]*$/,bW=/\\(?:["\\\/bfnrt]|u[0-9a-fA-F]{4})/g,bP=/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g,bJ=/(?:^|:|,)(?:\s*\[)+/g,by=/(webkit)[ \/]([\w.]+)/,bR=/(opera)(?:.*version)?[ \/]([\w.]+)/,bQ=/(msie) ([\w.]+)/,bS=/(mozilla)(?:.*? rv:([\w.]+))?/,bB=/-([a-z]|[0-9])/ig,bZ=/^-ms-/,bT=function(b0,b1){return(b1+"").toUpperCase()},bX=bu.userAgent,bV,bC,e,bL=Object.prototype.toString,bG=Object.prototype.hasOwnProperty,bz=Array.prototype.push,bK=Array.prototype.slice,bO=String.prototype.trim,bv=Array.prototype.indexOf,bx={};bF.fn=bF.prototype={constructor:bF,init:function(b0,b4,b3){var b2,b5,b1,b6;if(!b0){return this}if(b0.nodeType){this.context=this[0]=b0;this.length=1;return this}if(b0==="body"&&!b4&&av.body){this.context=av;this[0]=av.body;this.selector=b0;this.length=1;return this}if(typeof b0==="string"){if(b0.charAt(0)==="<"&&b0.charAt(b0.length-1)===">"&&b0.length>=3){b2=[null,b0,null]}else{b2=bY.exec(b0)}if(b2&&(b2[1]||!b4)){if(b2[1]){b4=b4 instanceof bF?b4[0]:b4;b6=(b4?b4.ownerDocument||b4:av);b1=bA.exec(b0);if(b1){if(bF.isPlainObject(b4)){b0=[av.createElement(b1[1])];bF.fn.attr.call(b0,b4,true)}else{b0=[b6.createElement(b1[1])]}}else{b1=bF.buildFragment([b2[1]],[b6]);b0=(b1.cacheable?bF.clone(b1.fragment):b1.fragment).childNodes}return bF.merge(this,b0)}else{b5=av.getElementById(b2[2]);if(b5&&b5.parentNode){if(b5.id!==b2[2]){return b3.find(b0)}this.length=1;this[0]=b5}this.context=av;this.selector=b0;return this}}else{if(!b4||b4.jquery){return(b4||b3).find(b0)}else{return this.constructor(b4).find(b0)}}}else{if(bF.isFunction(b0)){return b3.ready(b0)}}if(b0.selector!==L){this.selector=b0.selector;this.context=b0.context}return bF.makeArray(b0,this)},selector:"",jquery:"1.7.1",length:0,size:function(){return this.length},toArray:function(){return bK.call(this,0)},get:function(b0){return b0==null?this.toArray():(b0<0?this[this.length+b0]:this[b0])},pushStack:function(b1,b3,b0){var b2=this.constructor();if(bF.isArray(b1)){bz.apply(b2,b1)}else{bF.merge(b2,b1)}b2.prevObject=this;b2.context=this.context;if(b3==="find"){b2.selector=this.selector+(this.selector?" ":"")+b0}else{if(b3){b2.selector=this.selector+"."+b3+"("+b0+")"}}return b2},each:function(b1,b0){return bF.each(this,b1,b0)},ready:function(b0){bF.bindReady();bC.add(b0);return this},eq:function(b0){b0=+b0;return b0===-1?this.slice(b0):this.slice(b0,b0+1)},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},slice:function(){return this.pushStack(bK.apply(this,arguments),"slice",bK.call(arguments).join(","))},map:function(b0){return this.pushStack(bF.map(this,function(b2,b1){return b0.call(b2,b1,b2)}))},end:function(){return this.prevObject||this.constructor(null)},push:bz,sort:[].sort,splice:[].splice};bF.fn.init.prototype=bF.fn;bF.extend=bF.fn.extend=function(){var b9,b2,b0,b1,b6,b7,b5=arguments[0]||{},b4=1,b3=arguments.length,b8=false;if(typeof b5==="boolean"){b8=b5;b5=arguments[1]||{};b4=2}if(typeof b5!=="object"&&!bF.isFunction(b5)){b5={}}if(b3===b4){b5=this;--b4}for(;b40){return}bC.fireWith(av,[bF]);if(bF.fn.trigger){bF(av).trigger("ready").off("ready")}}},bindReady:function(){if(bC){return}bC=bF.Callbacks("once memory");if(av.readyState==="complete"){return setTimeout(bF.ready,1)}if(av.addEventListener){av.addEventListener("DOMContentLoaded",e,false);bb.addEventListener("load",bF.ready,false)}else{if(av.attachEvent){av.attachEvent("onreadystatechange",e);bb.attachEvent("onload",bF.ready);var b0=false;try{b0=bb.frameElement==null}catch(b1){}if(av.documentElement.doScroll&&b0){bw()}}}},isFunction:function(b0){return bF.type(b0)==="function"},isArray:Array.isArray||function(b0){return bF.type(b0)==="array"},isWindow:function(b0){return b0&&typeof b0==="object"&&"setInterval" in b0},isNumeric:function(b0){return !isNaN(parseFloat(b0))&&isFinite(b0)},type:function(b0){return b0==null?String(b0):bx[bL.call(b0)]||"object"},isPlainObject:function(b2){if(!b2||bF.type(b2)!=="object"||b2.nodeType||bF.isWindow(b2)){return false}try{if(b2.constructor&&!bG.call(b2,"constructor")&&!bG.call(b2.constructor.prototype,"isPrototypeOf")){return false}}catch(b1){return false}var b0;for(b0 in b2){}return b0===L||bG.call(b2,b0)},isEmptyObject:function(b1){for(var b0 in b1){return false}return true},error:function(b0){throw new Error(b0)},parseJSON:function(b0){if(typeof b0!=="string"||!b0){return null}b0=bF.trim(b0);if(bb.JSON&&bb.JSON.parse){return bb.JSON.parse(b0)}if(bN.test(b0.replace(bW,"@").replace(bP,"]").replace(bJ,""))){return(new Function("return "+b0))()}bF.error("Invalid JSON: "+b0)},parseXML:function(b2){var b0,b1;try{if(bb.DOMParser){b1=new DOMParser();b0=b1.parseFromString(b2,"text/xml")}else{b0=new ActiveXObject("Microsoft.XMLDOM");b0.async="false";b0.loadXML(b2)}}catch(b3){b0=L}if(!b0||!b0.documentElement||b0.getElementsByTagName("parsererror").length){bF.error("Invalid XML: "+b2)}return b0},noop:function(){},globalEval:function(b0){if(b0&&bM.test(b0)){(bb.execScript||function(b1){bb["eval"].call(bb,b1)})(b0)}},camelCase:function(b0){return b0.replace(bZ,"ms-").replace(bB,bT)},nodeName:function(b1,b0){return b1.nodeName&&b1.nodeName.toUpperCase()===b0.toUpperCase()},each:function(b3,b6,b2){var b1,b4=0,b5=b3.length,b0=b5===L||bF.isFunction(b3);if(b2){if(b0){for(b1 in b3){if(b6.apply(b3[b1],b2)===false){break}}}else{for(;b40&&b0[0]&&b0[b1-1])||b1===0||bF.isArray(b0));if(b3){for(;b21?aJ.call(arguments,0):bG;if(!(--bw)){bC.resolveWith(bC,bx)}}}function bz(bF){return function(bG){bB[bF]=arguments.length>1?aJ.call(arguments,0):bG;bC.notifyWith(bE,bB)}}if(e>1){for(;bv
a";bI=bv.getElementsByTagName("*");bF=bv.getElementsByTagName("a")[0];if(!bI||!bI.length||!bF){return{}}bG=av.createElement("select");bx=bG.appendChild(av.createElement("option"));bE=bv.getElementsByTagName("input")[0];bJ={leadingWhitespace:(bv.firstChild.nodeType===3),tbody:!bv.getElementsByTagName("tbody").length,htmlSerialize:!!bv.getElementsByTagName("link").length,style:/top/.test(bF.getAttribute("style")),hrefNormalized:(bF.getAttribute("href")==="/a"),opacity:/^0.55/.test(bF.style.opacity),cssFloat:!!bF.style.cssFloat,checkOn:(bE.value==="on"),optSelected:bx.selected,getSetAttribute:bv.className!=="t",enctype:!!av.createElement("form").enctype,html5Clone:av.createElement("nav").cloneNode(true).outerHTML!=="<:nav>",submitBubbles:true,changeBubbles:true,focusinBubbles:false,deleteExpando:true,noCloneEvent:true,inlineBlockNeedsLayout:false,shrinkWrapBlocks:false,reliableMarginRight:true};bE.checked=true;bJ.noCloneChecked=bE.cloneNode(true).checked;bG.disabled=true;bJ.optDisabled=!bx.disabled;try{delete bv.test}catch(bC){bJ.deleteExpando=false}if(!bv.addEventListener&&bv.attachEvent&&bv.fireEvent){bv.attachEvent("onclick",function(){bJ.noCloneEvent=false});bv.cloneNode(true).fireEvent("onclick")}bE=av.createElement("input");bE.value="t";bE.setAttribute("type","radio");bJ.radioValue=bE.value==="t";bE.setAttribute("checked","checked");bv.appendChild(bE);bD=av.createDocumentFragment();bD.appendChild(bv.lastChild);bJ.checkClone=bD.cloneNode(true).cloneNode(true).lastChild.checked;bJ.appendChecked=bE.checked;bD.removeChild(bE);bD.appendChild(bv);bv.innerHTML="";if(bb.getComputedStyle){bA=av.createElement("div");bA.style.width="0";bA.style.marginRight="0";bv.style.width="2px";bv.appendChild(bA);bJ.reliableMarginRight=(parseInt((bb.getComputedStyle(bA,null)||{marginRight:0}).marginRight,10)||0)===0}if(bv.attachEvent){for(by in {submit:1,change:1,focusin:1}){bB="on"+by;bw=(bB in bv);if(!bw){bv.setAttribute(bB,"return;");bw=(typeof bv[bB]==="function")}bJ[by+"Bubbles"]=bw}}bD.removeChild(bv);bD=bG=bx=bA=bv=bE=null;b(function(){var bM,bU,bV,bT,bN,bO,bL,bS,bR,e,bP,bQ=av.getElementsByTagName("body")[0];if(!bQ){return}bL=1;bS="position:absolute;top:0;left:0;width:1px;height:1px;margin:0;";bR="visibility:hidden;border:0;";e="style='"+bS+"border:5px solid #000;padding:0;'";bP="
";bM=av.createElement("div");bM.style.cssText=bR+"width:0;height:0;position:static;top:0;margin-top:"+bL+"px";bQ.insertBefore(bM,bQ.firstChild);bv=av.createElement("div");bM.appendChild(bv);bv.innerHTML="
t
";bz=bv.getElementsByTagName("td");bw=(bz[0].offsetHeight===0);bz[0].style.display="";bz[1].style.display="none";bJ.reliableHiddenOffsets=bw&&(bz[0].offsetHeight===0);bv.innerHTML="";bv.style.width=bv.style.paddingLeft="1px";b.boxModel=bJ.boxModel=bv.offsetWidth===2;if(typeof bv.style.zoom!=="undefined"){bv.style.display="inline";bv.style.zoom=1;bJ.inlineBlockNeedsLayout=(bv.offsetWidth===2);bv.style.display="";bv.innerHTML="
";bJ.shrinkWrapBlocks=(bv.offsetWidth!==2)}bv.style.cssText=bS+bR;bv.innerHTML=bP;bU=bv.firstChild;bV=bU.firstChild;bN=bU.nextSibling.firstChild.firstChild;bO={doesNotAddBorder:(bV.offsetTop!==5),doesAddBorderForTableAndCells:(bN.offsetTop===5)};bV.style.position="fixed";bV.style.top="20px";bO.fixedPosition=(bV.offsetTop===20||bV.offsetTop===15);bV.style.position=bV.style.top="";bU.style.overflow="hidden";bU.style.position="relative";bO.subtractsBorderForOverflowNotVisible=(bV.offsetTop===-5);bO.doesNotIncludeMarginInBodyOffset=(bQ.offsetTop!==bL);bQ.removeChild(bM);bv=bM=null;b.extend(bJ,bO)});return bJ})();var aS=/^(?:\{.*\}|\[.*\])$/,aA=/([A-Z])/g;b.extend({cache:{},uuid:0,expando:"jQuery"+(b.fn.jquery+Math.random()).replace(/\D/g,""),noData:{embed:true,object:"clsid:D27CDB6E-AE6D-11cf-96B8-444553540000",applet:true},hasData:function(e){e=e.nodeType?b.cache[e[b.expando]]:e[b.expando];return !!e&&!S(e)},data:function(bx,bv,bz,by){if(!b.acceptData(bx)){return}var bG,bA,bD,bE=b.expando,bC=typeof bv==="string",bF=bx.nodeType,e=bF?b.cache:bx,bw=bF?bx[bE]:bx[bE]&&bE,bB=bv==="events";if((!bw||!e[bw]||(!bB&&!by&&!e[bw].data))&&bC&&bz===L){return}if(!bw){if(bF){bx[bE]=bw=++b.uuid}else{bw=bE}}if(!e[bw]){e[bw]={};if(!bF){e[bw].toJSON=b.noop}}if(typeof bv==="object"||typeof bv==="function"){if(by){e[bw]=b.extend(e[bw],bv)}else{e[bw].data=b.extend(e[bw].data,bv)}}bG=bA=e[bw];if(!by){if(!bA.data){bA.data={}}bA=bA.data}if(bz!==L){bA[b.camelCase(bv)]=bz}if(bB&&!bA[bv]){return bG.events}if(bC){bD=bA[bv];if(bD==null){bD=bA[b.camelCase(bv)]}}else{bD=bA}return bD},removeData:function(bx,bv,by){if(!b.acceptData(bx)){return}var bB,bA,bz,bC=b.expando,bD=bx.nodeType,e=bD?b.cache:bx,bw=bD?bx[bC]:bC;if(!e[bw]){return}if(bv){bB=by?e[bw]:e[bw].data;if(bB){if(!b.isArray(bv)){if(bv in bB){bv=[bv]}else{bv=b.camelCase(bv);if(bv in bB){bv=[bv]}else{bv=bv.split(" ")}}}for(bA=0,bz=bv.length;bA-1){return true}}return false},val:function(bx){var e,bv,by,bw=this[0];if(!arguments.length){if(bw){e=b.valHooks[bw.nodeName.toLowerCase()]||b.valHooks[bw.type];if(e&&"get" in e&&(bv=e.get(bw,"value"))!==L){return bv}bv=bw.value;return typeof bv==="string"?bv.replace(aU,""):bv==null?"":bv}return}by=b.isFunction(bx);return this.each(function(bA){var bz=b(this),bB;if(this.nodeType!==1){return}if(by){bB=bx.call(this,bA,bz.val())}else{bB=bx}if(bB==null){bB=""}else{if(typeof bB==="number"){bB+=""}else{if(b.isArray(bB)){bB=b.map(bB,function(bC){return bC==null?"":bC+""})}}}e=b.valHooks[this.nodeName.toLowerCase()]||b.valHooks[this.type];if(!e||!("set" in e)||e.set(this,bB,"value")===L){this.value=bB}})}});b.extend({valHooks:{option:{get:function(e){var bv=e.attributes.value;return !bv||bv.specified?e.value:e.text}},select:{get:function(e){var bA,bv,bz,bx,by=e.selectedIndex,bB=[],bC=e.options,bw=e.type==="select-one";if(by<0){return null}bv=bw?by:0;bz=bw?by+1:bC.length;for(;bv=0});if(!e.length){bv.selectedIndex=-1}return e}}},attrFn:{val:true,css:true,html:true,text:true,data:true,width:true,height:true,offset:true},attr:function(bA,bx,bB,bz){var bw,e,by,bv=bA.nodeType;if(!bA||bv===3||bv===8||bv===2){return}if(bz&&bx in b.attrFn){return b(bA)[bx](bB)}if(typeof bA.getAttribute==="undefined"){return b.prop(bA,bx,bB)}by=bv!==1||!b.isXMLDoc(bA);if(by){bx=bx.toLowerCase();e=b.attrHooks[bx]||(ao.test(bx)?aY:be)}if(bB!==L){if(bB===null){b.removeAttr(bA,bx);return}else{if(e&&"set" in e&&by&&(bw=e.set(bA,bB,bx))!==L){return bw}else{bA.setAttribute(bx,""+bB);return bB}}}else{if(e&&"get" in e&&by&&(bw=e.get(bA,bx))!==null){return bw}else{bw=bA.getAttribute(bx);return bw===null?L:bw}}},removeAttr:function(bx,bz){var by,bA,bv,e,bw=0;if(bz&&bx.nodeType===1){bA=bz.toLowerCase().split(af);e=bA.length;for(;bw=0)}}})});var bd=/^(?:textarea|input|select)$/i,n=/^([^\.]*)?(?:\.(.+))?$/,J=/\bhover(\.\S+)?\b/,aO=/^key/,bf=/^(?:mouse|contextmenu)|click/,T=/^(?:focusinfocus|focusoutblur)$/,U=/^(\w*)(?:#([\w\-]+))?(?:\.([\w\-]+))?$/,Y=function(e){var bv=U.exec(e);if(bv){bv[1]=(bv[1]||"").toLowerCase();bv[3]=bv[3]&&new RegExp("(?:^|\\s)"+bv[3]+"(?:\\s|$)")}return bv},j=function(bw,e){var bv=bw.attributes||{};return((!e[1]||bw.nodeName.toLowerCase()===e[1])&&(!e[2]||(bv.id||{}).value===e[2])&&(!e[3]||e[3].test((bv["class"]||{}).value)))},bt=function(e){return b.event.special.hover?e:e.replace(J,"mouseenter$1 mouseleave$1")};b.event={add:function(bx,bC,bJ,bA,by){var bD,bB,bK,bI,bH,bF,e,bG,bv,bz,bw,bE;if(bx.nodeType===3||bx.nodeType===8||!bC||!bJ||!(bD=b._data(bx))){return}if(bJ.handler){bv=bJ;bJ=bv.handler}if(!bJ.guid){bJ.guid=b.guid++}bK=bD.events;if(!bK){bD.events=bK={}}bB=bD.handle;if(!bB){bD.handle=bB=function(bL){return typeof b!=="undefined"&&(!bL||b.event.triggered!==bL.type)?b.event.dispatch.apply(bB.elem,arguments):L};bB.elem=bx}bC=b.trim(bt(bC)).split(" ");for(bI=0;bI=0){bG=bG.slice(0,-1);bw=true}if(bG.indexOf(".")>=0){bx=bG.split(".");bG=bx.shift();bx.sort()}if((!bA||b.event.customEvent[bG])&&!b.event.global[bG]){return}bv=typeof bv==="object"?bv[b.expando]?bv:new b.Event(bG,bv):new b.Event(bG);bv.type=bG;bv.isTrigger=true;bv.exclusive=bw;bv.namespace=bx.join(".");bv.namespace_re=bv.namespace?new RegExp("(^|\\.)"+bx.join("\\.(?:.*\\.)?")+"(\\.|$)"):null;by=bG.indexOf(":")<0?"on"+bG:"";if(!bA){e=b.cache;for(bC in e){if(e[bC].events&&e[bC].events[bG]){b.event.trigger(bv,bD,e[bC].handle.elem,true)}}return}bv.result=L;if(!bv.target){bv.target=bA}bD=bD!=null?b.makeArray(bD):[];bD.unshift(bv);bF=b.event.special[bG]||{};if(bF.trigger&&bF.trigger.apply(bA,bD)===false){return}bB=[[bA,bF.bindType||bG]];if(!bJ&&!bF.noBubble&&!b.isWindow(bA)){bI=bF.delegateType||bG;bH=T.test(bI+bG)?bA:bA.parentNode;bz=null;for(;bH;bH=bH.parentNode){bB.push([bH,bI]);bz=bH}if(bz&&bz===bA.ownerDocument){bB.push([bz.defaultView||bz.parentWindow||bb,bI])}}for(bC=0;bCbA){bH.push({elem:this,matches:bz.slice(bA)})}for(bC=0;bC0?this.on(e,null,bx,bw):this.trigger(e)};if(b.attrFn){b.attrFn[e]=true}if(aO.test(e)){b.event.fixHooks[e]=b.event.keyHooks}if(bf.test(e)){b.event.fixHooks[e]=b.event.mouseHooks}}); -/* +/*! * Sizzle CSS Selector Engine * Copyright 2011, The Dojo Foundation * Released under the MIT, BSD, and GPL Licenses. * More information: http://sizzlejs.com/ */ -(function(){var bH=/((?:\((?:\([^()]+\)|[^()]+)+\)|\[(?:\[[^\[\]]*\]|['"][^'"]*['"]|[^\[\]'"]+)+\]|\\.|[^ >+~,(\[\\]+)+|[>+~])(\s*,\s*)?((?:.|\r|\n)*)/g,bC="sizcache"+(Math.random()+"").replace(".",""),bI=0,bL=Object.prototype.toString,bB=false,bA=true,bK=/\\/g,bO=/\r\n/g,bQ=/\W/;[0,0].sort(function(){bA=false;return 0});var by=function(bV,e,bY,bZ){bY=bY||[];e=e||av;var b1=e;if(e.nodeType!==1&&e.nodeType!==9){return[]}if(!bV||typeof bV!=="string"){return bY}var bS,b3,b6,bR,b2,b5,b4,bX,bU=true,bT=by.isXML(e),bW=[],b0=bV;do{bH.exec("");bS=bH.exec(b0);if(bS){b0=bS[3];bW.push(bS[1]);if(bS[2]){bR=bS[3];break}}}while(bS);if(bW.length>1&&bD.exec(bV)){if(bW.length===2&&bE.relative[bW[0]]){b3=bM(bW[0]+bW[1],e,bZ)}else{b3=bE.relative[bW[0]]?[e]:by(bW.shift(),e);while(bW.length){bV=bW.shift();if(bE.relative[bV]){bV+=bW.shift()}b3=bM(bV,b3,bZ)}}}else{if(!bZ&&bW.length>1&&e.nodeType===9&&!bT&&bE.match.ID.test(bW[0])&&!bE.match.ID.test(bW[bW.length-1])){b2=by.find(bW.shift(),e,bT);e=b2.expr?by.filter(b2.expr,b2.set)[0]:b2.set[0]}if(e){b2=bZ?{expr:bW.pop(),set:bF(bZ)}:by.find(bW.pop(),bW.length===1&&(bW[0]==="~"||bW[0]==="+")&&e.parentNode?e.parentNode:e,bT);b3=b2.expr?by.filter(b2.expr,b2.set):b2.set;if(bW.length>0){b6=bF(b3)}else{bU=false}while(bW.length){b5=bW.pop();b4=b5;if(!bE.relative[b5]){b5=""}else{b4=bW.pop()}if(b4==null){b4=e}bE.relative[b5](b6,b4,bT)}}else{b6=bW=[]}}if(!b6){b6=b3}if(!b6){by.error(b5||bV)}if(bL.call(b6)==="[object Array]"){if(!bU){bY.push.apply(bY,b6)}else{if(e&&e.nodeType===1){for(bX=0;b6[bX]!=null;bX++){if(b6[bX]&&(b6[bX]===true||b6[bX].nodeType===1&&by.contains(e,b6[bX]))){bY.push(b3[bX])}}}else{for(bX=0;b6[bX]!=null;bX++){if(b6[bX]&&b6[bX].nodeType===1){bY.push(b3[bX])}}}}}else{bF(b6,bY)}if(bR){by(bR,b1,bY,bZ);by.uniqueSort(bY)}return bY};by.uniqueSort=function(bR){if(bJ){bB=bA;bR.sort(bJ);if(bB){for(var e=1;e0};by.find=function(bX,e,bY){var bW,bS,bU,bT,bV,bR;if(!bX){return[]}for(bS=0,bU=bE.order.length;bS":function(bW,bR){var bV,bU=typeof bR==="string",bS=0,e=bW.length;if(bU&&!bQ.test(bR)){bR=bR.toLowerCase();for(;bS=0)){if(!bS){e.push(bV)}}else{if(bS){bR[bU]=false}}}}return false},ID:function(e){return e[1].replace(bK,"")},TAG:function(bR,e){return bR[1].replace(bK,"").toLowerCase()},CHILD:function(e){if(e[1]==="nth"){if(!e[2]){by.error(e[0])}e[2]=e[2].replace(/^\+|\s*/g,"");var bR=/(-?)(\d*)(?:n([+\-]?\d*))?/.exec(e[2]==="even"&&"2n"||e[2]==="odd"&&"2n+1"||!/\D/.test(e[2])&&"0n+"+e[2]||e[2]);e[2]=(bR[1]+(bR[2]||1))-0;e[3]=bR[3]-0}else{if(e[2]){by.error(e[0])}}e[0]=bI++;return e},ATTR:function(bU,bR,bS,e,bV,bW){var bT=bU[1]=bU[1].replace(bK,"");if(!bW&&bE.attrMap[bT]){bU[1]=bE.attrMap[bT]}bU[4]=(bU[4]||bU[5]||"").replace(bK,"");if(bU[2]==="~="){bU[4]=" "+bU[4]+" "}return bU},PSEUDO:function(bU,bR,bS,e,bV){if(bU[1]==="not"){if((bH.exec(bU[3])||"").length>1||/^\w/.test(bU[3])){bU[3]=by(bU[3],null,null,bR)}else{var bT=by.filter(bU[3],bR,bS,true^bV);if(!bS){e.push.apply(e,bT)}return false}}else{if(bE.match.POS.test(bU[0])||bE.match.CHILD.test(bU[0])){return true}}return bU},POS:function(e){e.unshift(true);return e}},filters:{enabled:function(e){return e.disabled===false&&e.type!=="hidden"},disabled:function(e){return e.disabled===true},checked:function(e){return e.checked===true},selected:function(e){if(e.parentNode){e.parentNode.selectedIndex}return e.selected===true},parent:function(e){return !!e.firstChild},empty:function(e){return !e.firstChild},has:function(bS,bR,e){return !!by(e[3],bS).length},header:function(e){return(/h\d/i).test(e.nodeName)},text:function(bS){var e=bS.getAttribute("type"),bR=bS.type;return bS.nodeName.toLowerCase()==="input"&&"text"===bR&&(e===bR||e===null)},radio:function(e){return e.nodeName.toLowerCase()==="input"&&"radio"===e.type},checkbox:function(e){return e.nodeName.toLowerCase()==="input"&&"checkbox"===e.type},file:function(e){return e.nodeName.toLowerCase()==="input"&&"file"===e.type},password:function(e){return e.nodeName.toLowerCase()==="input"&&"password"===e.type},submit:function(bR){var e=bR.nodeName.toLowerCase();return(e==="input"||e==="button")&&"submit"===bR.type},image:function(e){return e.nodeName.toLowerCase()==="input"&&"image"===e.type},reset:function(bR){var e=bR.nodeName.toLowerCase();return(e==="input"||e==="button")&&"reset"===bR.type},button:function(bR){var e=bR.nodeName.toLowerCase();return e==="input"&&"button"===bR.type||e==="button"},input:function(e){return(/input|select|textarea|button/i).test(e.nodeName)},focus:function(e){return e===e.ownerDocument.activeElement}},setFilters:{first:function(bR,e){return e===0},last:function(bS,bR,e,bT){return bR===bT.length-1},even:function(bR,e){return e%2===0},odd:function(bR,e){return e%2===1},lt:function(bS,bR,e){return bRe[3]-0},nth:function(bS,bR,e){return e[3]-0===bR},eq:function(bS,bR,e){return e[3]-0===bR}},filter:{PSEUDO:function(bS,bX,bW,bY){var e=bX[1],bR=bE.filters[e];if(bR){return bR(bS,bW,bX,bY)}else{if(e==="contains"){return(bS.textContent||bS.innerText||bw([bS])||"").indexOf(bX[3])>=0}else{if(e==="not"){var bT=bX[3];for(var bV=0,bU=bT.length;bV=0)}}},ID:function(bR,e){return bR.nodeType===1&&bR.getAttribute("id")===e},TAG:function(bR,e){return(e==="*"&&bR.nodeType===1)||!!bR.nodeName&&bR.nodeName.toLowerCase()===e},CLASS:function(bR,e){return(" "+(bR.className||bR.getAttribute("class"))+" ").indexOf(e)>-1},ATTR:function(bV,bT){var bS=bT[1],e=by.attr?by.attr(bV,bS):bE.attrHandle[bS]?bE.attrHandle[bS](bV):bV[bS]!=null?bV[bS]:bV.getAttribute(bS),bW=e+"",bU=bT[2],bR=bT[4];return e==null?bU==="!=":!bU&&by.attr?e!=null:bU==="="?bW===bR:bU==="*="?bW.indexOf(bR)>=0:bU==="~="?(" "+bW+" ").indexOf(bR)>=0:!bR?bW&&e!==false:bU==="!="?bW!==bR:bU==="^="?bW.indexOf(bR)===0:bU==="$="?bW.substr(bW.length-bR.length)===bR:bU==="|="?bW===bR||bW.substr(0,bR.length+1)===bR+"-":false},POS:function(bU,bR,bS,bV){var e=bR[2],bT=bE.setFilters[e];if(bT){return bT(bU,bS,bR,bV)}}}};var bD=bE.match.POS,bx=function(bR,e){return"\\"+(e-0+1)};for(var bz in bE.match){bE.match[bz]=new RegExp(bE.match[bz].source+(/(?![^\[]*\])(?![^\(]*\))/.source));bE.leftMatch[bz]=new RegExp(/(^(?:.|\r|\n)*?)/.source+bE.match[bz].source.replace(/\\(\d+)/g,bx))}var bF=function(bR,e){bR=Array.prototype.slice.call(bR,0);if(e){e.push.apply(e,bR);return e}return bR};try{Array.prototype.slice.call(av.documentElement.childNodes,0)[0].nodeType}catch(bP){bF=function(bU,bT){var bS=0,bR=bT||[];if(bL.call(bU)==="[object Array]"){Array.prototype.push.apply(bR,bU)}else{if(typeof bU.length==="number"){for(var e=bU.length;bS";e.insertBefore(bR,e.firstChild);if(av.getElementById(bS)){bE.find.ID=function(bU,bV,bW){if(typeof bV.getElementById!=="undefined"&&!bW){var bT=bV.getElementById(bU[1]);return bT?bT.id===bU[1]||typeof bT.getAttributeNode!=="undefined"&&bT.getAttributeNode("id").nodeValue===bU[1]?[bT]:L:[]}};bE.filter.ID=function(bV,bT){var bU=typeof bV.getAttributeNode!=="undefined"&&bV.getAttributeNode("id");return bV.nodeType===1&&bU&&bU.nodeValue===bT}}e.removeChild(bR);e=bR=null})();(function(){var e=av.createElement("div");e.appendChild(av.createComment(""));if(e.getElementsByTagName("*").length>0){bE.find.TAG=function(bR,bV){var bU=bV.getElementsByTagName(bR[1]);if(bR[1]==="*"){var bT=[];for(var bS=0;bU[bS];bS++){if(bU[bS].nodeType===1){bT.push(bU[bS])}}bU=bT}return bU}}e.innerHTML="";if(e.firstChild&&typeof e.firstChild.getAttribute!=="undefined"&&e.firstChild.getAttribute("href")!=="#"){bE.attrHandle.href=function(bR){return bR.getAttribute("href",2)}}e=null})();if(av.querySelectorAll){(function(){var e=by,bT=av.createElement("div"),bS="__sizzle__";bT.innerHTML="

";if(bT.querySelectorAll&&bT.querySelectorAll(".TEST").length===0){return}by=function(b4,bV,bZ,b3){bV=bV||av;if(!b3&&!by.isXML(bV)){var b2=/^(\w+$)|^\.([\w\-]+$)|^#([\w\-]+$)/.exec(b4);if(b2&&(bV.nodeType===1||bV.nodeType===9)){if(b2[1]){return bF(bV.getElementsByTagName(b4),bZ)}else{if(b2[2]&&bE.find.CLASS&&bV.getElementsByClassName){return bF(bV.getElementsByClassName(b2[2]),bZ)}}}if(bV.nodeType===9){if(b4==="body"&&bV.body){return bF([bV.body],bZ)}else{if(b2&&b2[3]){var bY=bV.getElementById(b2[3]);if(bY&&bY.parentNode){if(bY.id===b2[3]){return bF([bY],bZ)}}else{return bF([],bZ)}}}try{return bF(bV.querySelectorAll(b4),bZ)}catch(b0){}}else{if(bV.nodeType===1&&bV.nodeName.toLowerCase()!=="object"){var bW=bV,bX=bV.getAttribute("id"),bU=bX||bS,b6=bV.parentNode,b5=/^\s*[+~]/.test(b4);if(!bX){bV.setAttribute("id",bU)}else{bU=bU.replace(/'/g,"\\$&")}if(b5&&b6){bV=bV.parentNode}try{if(!b5||b6){return bF(bV.querySelectorAll("[id='"+bU+"'] "+b4),bZ)}}catch(b1){}finally{if(!bX){bW.removeAttribute("id")}}}}}return e(b4,bV,bZ,b3)};for(var bR in e){by[bR]=e[bR]}bT=null})()}(function(){var e=av.documentElement,bS=e.matchesSelector||e.mozMatchesSelector||e.webkitMatchesSelector||e.msMatchesSelector;if(bS){var bU=!bS.call(av.createElement("div"),"div"),bR=false;try{bS.call(av.documentElement,"[test!='']:sizzle")}catch(bT){bR=true}by.matchesSelector=function(bW,bY){bY=bY.replace(/\=\s*([^'"\]]*)\s*\]/g,"='$1']");if(!by.isXML(bW)){try{if(bR||!bE.match.PSEUDO.test(bY)&&!/!=/.test(bY)){var bV=bS.call(bW,bY);if(bV||!bU||bW.document&&bW.document.nodeType!==11){return bV}}}catch(bX){}}return by(bY,null,null,[bW]).length>0}}})();(function(){var e=av.createElement("div");e.innerHTML="
";if(!e.getElementsByClassName||e.getElementsByClassName("e").length===0){return}e.lastChild.className="e";if(e.getElementsByClassName("e").length===1){return}bE.order.splice(1,0,"CLASS");bE.find.CLASS=function(bR,bS,bT){if(typeof bS.getElementsByClassName!=="undefined"&&!bT){return bS.getElementsByClassName(bR[1])}};e=null})();function bv(bR,bW,bV,bZ,bX,bY){for(var bT=0,bS=bZ.length;bT0){bU=e;break}}}e=e[bR]}bZ[bT]=bU}}}if(av.documentElement.contains){by.contains=function(bR,e){return bR!==e&&(bR.contains?bR.contains(e):true)}}else{if(av.documentElement.compareDocumentPosition){by.contains=function(bR,e){return !!(bR.compareDocumentPosition(e)&16)}}else{by.contains=function(){return false}}}by.isXML=function(e){var bR=(e?e.ownerDocument||e:0).documentElement;return bR?bR.nodeName!=="HTML":false};var bM=function(bS,e,bW){var bV,bX=[],bU="",bY=e.nodeType?[e]:e;while((bV=bE.match.PSEUDO.exec(bS))){bU+=bV[0];bS=bS.replace(bE.match.PSEUDO,"")}bS=bE.relative[bS]?bS+"*":bS;for(var bT=0,bR=bY.length;bT0){for(bB=bA;bB=0:b.filter(e,this).length>0:this.filter(e).length>0)},closest:function(by,bx){var bv=[],bw,e,bz=this[0];if(b.isArray(by)){var bB=1;while(bz&&bz.ownerDocument&&bz!==bx){for(bw=0;bw-1:b.find.matchesSelector(bz,by)){bv.push(bz);break}else{bz=bz.parentNode;if(!bz||!bz.ownerDocument||bz===bx||bz.nodeType===11){break}}}}bv=bv.length>1?b.unique(bv):bv;return this.pushStack(bv,"closest",by)},index:function(e){if(!e){return(this[0]&&this[0].parentNode)?this.prevAll().length:-1}if(typeof e==="string"){return b.inArray(this[0],b(e))}return b.inArray(e.jquery?e[0]:e,this)},add:function(e,bv){var bx=typeof e==="string"?b(e,bv):b.makeArray(e&&e.nodeType?[e]:e),bw=b.merge(this.get(),bx);return this.pushStack(C(bx[0])||C(bw[0])?bw:b.unique(bw))},andSelf:function(){return this.add(this.prevObject)}});function C(e){return !e||!e.parentNode||e.parentNode.nodeType===11}b.each({parent:function(bv){var e=bv.parentNode;return e&&e.nodeType!==11?e:null},parents:function(e){return b.dir(e,"parentNode")},parentsUntil:function(bv,e,bw){return b.dir(bv,"parentNode",bw)},next:function(e){return b.nth(e,2,"nextSibling")},prev:function(e){return b.nth(e,2,"previousSibling")},nextAll:function(e){return b.dir(e,"nextSibling")},prevAll:function(e){return b.dir(e,"previousSibling")},nextUntil:function(bv,e,bw){return b.dir(bv,"nextSibling",bw)},prevUntil:function(bv,e,bw){return b.dir(bv,"previousSibling",bw)},siblings:function(e){return b.sibling(e.parentNode.firstChild,e)},children:function(e){return b.sibling(e.firstChild)},contents:function(e){return b.nodeName(e,"iframe")?e.contentDocument||e.contentWindow.document:b.makeArray(e.childNodes)}},function(e,bv){b.fn[e]=function(by,bw){var bx=b.map(this,bv,by);if(!ab.test(e)){bw=by}if(bw&&typeof bw==="string"){bx=b.filter(bw,bx)}bx=this.length>1&&!ay[e]?b.unique(bx):bx;if((this.length>1||a9.test(bw))&&aq.test(e)){bx=bx.reverse()}return this.pushStack(bx,e,P.call(arguments).join(","))}});b.extend({filter:function(bw,e,bv){if(bv){bw=":not("+bw+")"}return e.length===1?b.find.matchesSelector(e[0],bw)?[e[0]]:[]:b.find.matches(bw,e)},dir:function(bw,bv,by){var e=[],bx=bw[bv];while(bx&&bx.nodeType!==9&&(by===L||bx.nodeType!==1||!b(bx).is(by))){if(bx.nodeType===1){e.push(bx)}bx=bx[bv]}return e},nth:function(by,e,bw,bx){e=e||1;var bv=0;for(;by;by=by[bw]){if(by.nodeType===1&&++bv===e){break}}return by},sibling:function(bw,bv){var e=[];for(;bw;bw=bw.nextSibling){if(bw.nodeType===1&&bw!==bv){e.push(bw)}}return e}});function aG(bx,bw,e){bw=bw||0;if(b.isFunction(bw)){return b.grep(bx,function(bz,by){var bA=!!bw.call(bz,by,bz);return bA===e})}else{if(bw.nodeType){return b.grep(bx,function(bz,by){return(bz===bw)===e})}else{if(typeof bw==="string"){var bv=b.grep(bx,function(by){return by.nodeType===1});if(bp.test(bw)){return b.filter(bw,bv,!e)}else{bw=b.filter(bw,bv)}}}}return b.grep(bx,function(bz,by){return(b.inArray(bz,bw)>=0)===e})}function a(e){var bw=aR.split("|"),bv=e.createDocumentFragment();if(bv.createElement){while(bw.length){bv.createElement(bw.pop())}}return bv}var aR="abbr|article|aside|audio|canvas|datalist|details|figcaption|figure|footer|header|hgroup|mark|meter|nav|output|progress|section|summary|time|video",ag=/ jQuery\d+="(?:\d+|null)"/g,ar=/^\s+/,R=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/ig,d=/<([\w:]+)/,w=/",""],legend:[1,"
","
"],thead:[1,"","
"],tr:[2,"","
"],td:[3,"","
"],col:[2,"","
"],area:[1,"",""],_default:[0,"",""]},ac=a(av);ax.optgroup=ax.option;ax.tbody=ax.tfoot=ax.colgroup=ax.caption=ax.thead;ax.th=ax.td;if(!b.support.htmlSerialize){ax._default=[1,"div
","
"]}b.fn.extend({text:function(e){if(b.isFunction(e)){return this.each(function(bw){var bv=b(this);bv.text(e.call(this,bw,bv.text()))})}if(typeof e!=="object"&&e!==L){return this.empty().append((this[0]&&this[0].ownerDocument||av).createTextNode(e))}return b.text(this)},wrapAll:function(e){if(b.isFunction(e)){return this.each(function(bw){b(this).wrapAll(e.call(this,bw))})}if(this[0]){var bv=b(e,this[0].ownerDocument).eq(0).clone(true);if(this[0].parentNode){bv.insertBefore(this[0])}bv.map(function(){var bw=this;while(bw.firstChild&&bw.firstChild.nodeType===1){bw=bw.firstChild}return bw}).append(this)}return this},wrapInner:function(e){if(b.isFunction(e)){return this.each(function(bv){b(this).wrapInner(e.call(this,bv))})}return this.each(function(){var bv=b(this),bw=bv.contents();if(bw.length){bw.wrapAll(e)}else{bv.append(e)}})},wrap:function(e){var bv=b.isFunction(e);return this.each(function(bw){b(this).wrapAll(bv?e.call(this,bw):e)})},unwrap:function(){return this.parent().each(function(){if(!b.nodeName(this,"body")){b(this).replaceWith(this.childNodes)}}).end()},append:function(){return this.domManip(arguments,true,function(e){if(this.nodeType===1){this.appendChild(e)}})},prepend:function(){return this.domManip(arguments,true,function(e){if(this.nodeType===1){this.insertBefore(e,this.firstChild)}})},before:function(){if(this[0]&&this[0].parentNode){return this.domManip(arguments,false,function(bv){this.parentNode.insertBefore(bv,this)})}else{if(arguments.length){var e=b.clean(arguments);e.push.apply(e,this.toArray());return this.pushStack(e,"before",arguments)}}},after:function(){if(this[0]&&this[0].parentNode){return this.domManip(arguments,false,function(bv){this.parentNode.insertBefore(bv,this.nextSibling)})}else{if(arguments.length){var e=this.pushStack(this,"after",arguments);e.push.apply(e,b.clean(arguments));return e}}},remove:function(e,bx){for(var bv=0,bw;(bw=this[bv])!=null;bv++){if(!e||b.filter(e,[bw]).length){if(!bx&&bw.nodeType===1){b.cleanData(bw.getElementsByTagName("*"));b.cleanData([bw])}if(bw.parentNode){bw.parentNode.removeChild(bw)}}}return this},empty:function(){for(var e=0,bv;(bv=this[e])!=null;e++){if(bv.nodeType===1){b.cleanData(bv.getElementsByTagName("*"))}while(bv.firstChild){bv.removeChild(bv.firstChild)}}return this},clone:function(bv,e){bv=bv==null?false:bv;e=e==null?bv:e;return this.map(function(){return b.clone(this,bv,e)})},html:function(bx){if(bx===L){return this[0]&&this[0].nodeType===1?this[0].innerHTML.replace(ag,""):null}else{if(typeof bx==="string"&&!ae.test(bx)&&(b.support.leadingWhitespace||!ar.test(bx))&&!ax[(d.exec(bx)||["",""])[1].toLowerCase()]){bx=bx.replace(R,"<$1>");try{for(var bw=0,bv=this.length;bw1&&bw0?this.clone(true):this).get();b(bC[bA])[bv](by);bz=bz.concat(by)}return this.pushStack(bz,e,bC.selector)}}});function bg(e){if(typeof e.getElementsByTagName!=="undefined"){return e.getElementsByTagName("*")}else{if(typeof e.querySelectorAll!=="undefined"){return e.querySelectorAll("*")}else{return[]}}}function az(e){if(e.type==="checkbox"||e.type==="radio"){e.defaultChecked=e.checked}}function E(e){var bv=(e.nodeName||"").toLowerCase();if(bv==="input"){az(e)}else{if(bv!=="script"&&typeof e.getElementsByTagName!=="undefined"){b.grep(e.getElementsByTagName("input"),az)}}}function al(e){var bv=av.createElement("div");ac.appendChild(bv);bv.innerHTML=e.outerHTML;return bv.firstChild}b.extend({clone:function(by,bA,bw){var e,bv,bx,bz=b.support.html5Clone||!ah.test("<"+by.nodeName)?by.cloneNode(true):al(by);if((!b.support.noCloneEvent||!b.support.noCloneChecked)&&(by.nodeType===1||by.nodeType===11)&&!b.isXMLDoc(by)){ai(by,bz);e=bg(by);bv=bg(bz);for(bx=0;e[bx];++bx){if(bv[bx]){ai(e[bx],bv[bx])}}}if(bA){t(by,bz);if(bw){e=bg(by);bv=bg(bz);for(bx=0;e[bx];++bx){t(e[bx],bv[bx])}}}e=bv=null;return bz},clean:function(bw,by,bH,bA){var bF;by=by||av;if(typeof by.createElement==="undefined"){by=by.ownerDocument||by[0]&&by[0].ownerDocument||av}var bI=[],bB;for(var bE=0,bz;(bz=bw[bE])!=null;bE++){if(typeof bz==="number"){bz+=""}if(!bz){continue}if(typeof bz==="string"){if(!W.test(bz)){bz=by.createTextNode(bz)}else{bz=bz.replace(R,"<$1>");var bK=(d.exec(bz)||["",""])[1].toLowerCase(),bx=ax[bK]||ax._default,bD=bx[0],bv=by.createElement("div");if(by===av){ac.appendChild(bv)}else{a(by).appendChild(bv)}bv.innerHTML=bx[1]+bz+bx[2];while(bD--){bv=bv.lastChild}if(!b.support.tbody){var e=w.test(bz),bC=bK==="table"&&!e?bv.firstChild&&bv.firstChild.childNodes:bx[1]===""&&!e?bv.childNodes:[];for(bB=bC.length-1;bB>=0;--bB){if(b.nodeName(bC[bB],"tbody")&&!bC[bB].childNodes.length){bC[bB].parentNode.removeChild(bC[bB])}}}if(!b.support.leadingWhitespace&&ar.test(bz)){bv.insertBefore(by.createTextNode(ar.exec(bz)[0]),bv.firstChild)}bz=bv.childNodes}}var bG;if(!b.support.appendChecked){if(bz[0]&&typeof(bG=bz.length)==="number"){for(bB=0;bB=0){return bx+"px"}}else{return bx}}}});if(!b.support.opacity){b.cssHooks.opacity={get:function(bv,e){return au.test((e&&bv.currentStyle?bv.currentStyle.filter:bv.style.filter)||"")?(parseFloat(RegExp.$1)/100)+"":e?"1":""},set:function(by,bz){var bx=by.style,bv=by.currentStyle,e=b.isNumeric(bz)?"alpha(opacity="+bz*100+")":"",bw=bv&&bv.filter||bx.filter||"";bx.zoom=1;if(bz>=1&&b.trim(bw.replace(ak,""))===""){bx.removeAttribute("filter");if(bv&&!bv.filter){return}}bx.filter=ak.test(bw)?bw.replace(ak,e):bw+" "+e}}}b(function(){if(!b.support.reliableMarginRight){b.cssHooks.marginRight={get:function(bw,bv){var e;b.swap(bw,{display:"inline-block"},function(){if(bv){e=Z(bw,"margin-right","marginRight")}else{e=bw.style.marginRight}});return e}}}});if(av.defaultView&&av.defaultView.getComputedStyle){aI=function(by,bw){var bv,bx,e;bw=bw.replace(z,"-$1").toLowerCase();if((bx=by.ownerDocument.defaultView)&&(e=bx.getComputedStyle(by,null))){bv=e.getPropertyValue(bw);if(bv===""&&!b.contains(by.ownerDocument.documentElement,by)){bv=b.style(by,bw)}}return bv}}if(av.documentElement.currentStyle){aX=function(bz,bw){var bA,e,by,bv=bz.currentStyle&&bz.currentStyle[bw],bx=bz.style;if(bv===null&&bx&&(by=bx[bw])){bv=by}if(!bc.test(bv)&&bn.test(bv)){bA=bx.left;e=bz.runtimeStyle&&bz.runtimeStyle.left;if(e){bz.runtimeStyle.left=bz.currentStyle.left}bx.left=bw==="fontSize"?"1em":(bv||0);bv=bx.pixelLeft+"px";bx.left=bA;if(e){bz.runtimeStyle.left=e}}return bv===""?"auto":bv}}Z=aI||aX;function p(by,bw,bv){var bA=bw==="width"?by.offsetWidth:by.offsetHeight,bz=bw==="width"?an:a1,bx=0,e=bz.length;if(bA>0){if(bv!=="border"){for(;bx)<[^<]*)*<\/script>/gi,q=/^(?:select|textarea)/i,h=/\s+/,br=/([?&])_=[^&]*/,K=/^([\w\+\.\-]+:)(?:\/\/([^\/?#:]*)(?::(\d+))?)?/,A=b.fn.load,aa={},r={},aE,s,aV=["*/"]+["*"];try{aE=bl.href}catch(aw){aE=av.createElement("a");aE.href="";aE=aE.href}s=K.exec(aE.toLowerCase())||[];function f(e){return function(by,bA){if(typeof by!=="string"){bA=by;by="*"}if(b.isFunction(bA)){var bx=by.toLowerCase().split(h),bw=0,bz=bx.length,bv,bB,bC;for(;bw=0){var e=bw.slice(by,bw.length);bw=bw.slice(0,by)}var bx="GET";if(bz){if(b.isFunction(bz)){bA=bz;bz=L}else{if(typeof bz==="object"){bz=b.param(bz,b.ajaxSettings.traditional);bx="POST"}}}var bv=this;b.ajax({url:bw,type:bx,dataType:"html",data:bz,complete:function(bC,bB,bD){bD=bC.responseText;if(bC.isResolved()){bC.done(function(bE){bD=bE});bv.html(e?b("
").append(bD.replace(a6,"")).find(e):bD)}if(bA){bv.each(bA,[bD,bB,bC])}}});return this},serialize:function(){return b.param(this.serializeArray())},serializeArray:function(){return this.map(function(){return this.elements?b.makeArray(this.elements):this}).filter(function(){return this.name&&!this.disabled&&(this.checked||q.test(this.nodeName)||aZ.test(this.type))}).map(function(e,bv){var bw=b(this).val();return bw==null?null:b.isArray(bw)?b.map(bw,function(by,bx){return{name:bv.name,value:by.replace(bs,"\r\n")}}):{name:bv.name,value:bw.replace(bs,"\r\n")}}).get()}});b.each("ajaxStart ajaxStop ajaxComplete ajaxError ajaxSuccess ajaxSend".split(" "),function(e,bv){b.fn[bv]=function(bw){return this.on(bv,bw)}});b.each(["get","post"],function(e,bv){b[bv]=function(bw,by,bz,bx){if(b.isFunction(by)){bx=bx||bz;bz=by;by=L}return b.ajax({type:bv,url:bw,data:by,success:bz,dataType:bx})}});b.extend({getScript:function(e,bv){return b.get(e,L,bv,"script")},getJSON:function(e,bv,bw){return b.get(e,bv,bw,"json")},ajaxSetup:function(bv,e){if(e){am(bv,b.ajaxSettings)}else{e=bv;bv=b.ajaxSettings}am(bv,e);return bv},ajaxSettings:{url:aE,isLocal:aM.test(s[1]),global:true,type:"GET",contentType:"application/x-www-form-urlencoded",processData:true,async:true,accepts:{xml:"application/xml, text/xml",html:"text/html",text:"text/plain",json:"application/json, text/javascript","*":aV},contents:{xml:/xml/,html:/html/,json:/json/},responseFields:{xml:"responseXML",text:"responseText"},converters:{"* text":bb.String,"text html":true,"text json":b.parseJSON,"text xml":b.parseXML},flatOptions:{context:true,url:true}},ajaxPrefilter:f(aa),ajaxTransport:f(r),ajax:function(bz,bx){if(typeof bz==="object"){bx=bz;bz=L}bx=bx||{};var bD=b.ajaxSetup({},bx),bS=bD.context||bD,bG=bS!==bD&&(bS.nodeType||bS instanceof b)?b(bS):b.event,bR=b.Deferred(),bN=b.Callbacks("once memory"),bB=bD.statusCode||{},bC,bH={},bO={},bQ,by,bL,bE,bI,bA=0,bw,bK,bJ={readyState:0,setRequestHeader:function(bT,bU){if(!bA){var e=bT.toLowerCase();bT=bO[e]=bO[e]||bT;bH[bT]=bU}return this},getAllResponseHeaders:function(){return bA===2?bQ:null},getResponseHeader:function(bT){var e;if(bA===2){if(!by){by={};while((e=aD.exec(bQ))){by[e[1].toLowerCase()]=e[2]}}e=by[bT.toLowerCase()]}return e===L?null:e},overrideMimeType:function(e){if(!bA){bD.mimeType=e}return this},abort:function(e){e=e||"abort";if(bL){bL.abort(e)}bF(0,e);return this}};function bF(bZ,bU,b0,bW){if(bA===2){return}bA=2;if(bE){clearTimeout(bE)}bL=L;bQ=bW||"";bJ.readyState=bZ>0?4:0;var bT,b4,b3,bX=bU,bY=b0?bj(bD,bJ,b0):L,bV,b2;if(bZ>=200&&bZ<300||bZ===304){if(bD.ifModified){if((bV=bJ.getResponseHeader("Last-Modified"))){b.lastModified[bC]=bV}if((b2=bJ.getResponseHeader("Etag"))){b.etag[bC]=b2}}if(bZ===304){bX="notmodified";bT=true}else{try{b4=G(bD,bY);bX="success";bT=true}catch(b1){bX="parsererror";b3=b1}}}else{b3=bX;if(!bX||bZ){bX="error";if(bZ<0){bZ=0}}}bJ.status=bZ;bJ.statusText=""+(bU||bX);if(bT){bR.resolveWith(bS,[b4,bX,bJ])}else{bR.rejectWith(bS,[bJ,bX,b3])}bJ.statusCode(bB);bB=L;if(bw){bG.trigger("ajax"+(bT?"Success":"Error"),[bJ,bD,bT?b4:b3])}bN.fireWith(bS,[bJ,bX]);if(bw){bG.trigger("ajaxComplete",[bJ,bD]);if(!(--b.active)){b.event.trigger("ajaxStop")}}}bR.promise(bJ);bJ.success=bJ.done;bJ.error=bJ.fail;bJ.complete=bN.add;bJ.statusCode=function(bT){if(bT){var e;if(bA<2){for(e in bT){bB[e]=[bB[e],bT[e]]}}else{e=bT[bJ.status];bJ.then(e,e)}}return this};bD.url=((bz||bD.url)+"").replace(bq,"").replace(c,s[1]+"//");bD.dataTypes=b.trim(bD.dataType||"*").toLowerCase().split(h);if(bD.crossDomain==null){bI=K.exec(bD.url.toLowerCase());bD.crossDomain=!!(bI&&(bI[1]!=s[1]||bI[2]!=s[2]||(bI[3]||(bI[1]==="http:"?80:443))!=(s[3]||(s[1]==="http:"?80:443))))}if(bD.data&&bD.processData&&typeof bD.data!=="string"){bD.data=b.param(bD.data,bD.traditional)}aW(aa,bD,bx,bJ);if(bA===2){return false}bw=bD.global;bD.type=bD.type.toUpperCase();bD.hasContent=!aQ.test(bD.type);if(bw&&b.active++===0){b.event.trigger("ajaxStart")}if(!bD.hasContent){if(bD.data){bD.url+=(M.test(bD.url)?"&":"?")+bD.data;delete bD.data}bC=bD.url;if(bD.cache===false){var bv=b.now(),bP=bD.url.replace(br,"$1_="+bv);bD.url=bP+((bP===bD.url)?(M.test(bD.url)?"&":"?")+"_="+bv:"")}}if(bD.data&&bD.hasContent&&bD.contentType!==false||bx.contentType){bJ.setRequestHeader("Content-Type",bD.contentType)}if(bD.ifModified){bC=bC||bD.url;if(b.lastModified[bC]){bJ.setRequestHeader("If-Modified-Since",b.lastModified[bC])}if(b.etag[bC]){bJ.setRequestHeader("If-None-Match",b.etag[bC])}}bJ.setRequestHeader("Accept",bD.dataTypes[0]&&bD.accepts[bD.dataTypes[0]]?bD.accepts[bD.dataTypes[0]]+(bD.dataTypes[0]!=="*"?", "+aV+"; q=0.01":""):bD.accepts["*"]);for(bK in bD.headers){bJ.setRequestHeader(bK,bD.headers[bK])}if(bD.beforeSend&&(bD.beforeSend.call(bS,bJ,bD)===false||bA===2)){bJ.abort();return false}for(bK in {success:1,error:1,complete:1}){bJ[bK](bD[bK])}bL=aW(r,bD,bx,bJ);if(!bL){bF(-1,"No Transport")}else{bJ.readyState=1;if(bw){bG.trigger("ajaxSend",[bJ,bD])}if(bD.async&&bD.timeout>0){bE=setTimeout(function(){bJ.abort("timeout")},bD.timeout)}try{bA=1;bL.send(bH,bF)}catch(bM){if(bA<2){bF(-1,bM)}else{throw bM}}}return bJ},param:function(e,bw){var bv=[],by=function(bz,bA){bA=b.isFunction(bA)?bA():bA;bv[bv.length]=encodeURIComponent(bz)+"="+encodeURIComponent(bA)};if(bw===L){bw=b.ajaxSettings.traditional}if(b.isArray(e)||(e.jquery&&!b.isPlainObject(e))){b.each(e,function(){by(this.name,this.value)})}else{for(var bx in e){v(bx,e[bx],bw,by)}}return bv.join("&").replace(k,"+")}});function v(bw,by,bv,bx){if(b.isArray(by)){b.each(by,function(bA,bz){if(bv||ap.test(bw)){bx(bw,bz)}else{v(bw+"["+(typeof bz==="object"||b.isArray(bz)?bA:"")+"]",bz,bv,bx)}})}else{if(!bv&&by!=null&&typeof by==="object"){for(var e in by){v(bw+"["+e+"]",by[e],bv,bx)}}else{bx(bw,by)}}}b.extend({active:0,lastModified:{},etag:{}});function bj(bD,bC,bz){var bv=bD.contents,bB=bD.dataTypes,bw=bD.responseFields,by,bA,bx,e;for(bA in bw){if(bA in bz){bC[bw[bA]]=bz[bA]}}while(bB[0]==="*"){bB.shift();if(by===L){by=bD.mimeType||bC.getResponseHeader("content-type")}}if(by){for(bA in bv){if(bv[bA]&&bv[bA].test(by)){bB.unshift(bA);break}}}if(bB[0] in bz){bx=bB[0]}else{for(bA in bz){if(!bB[0]||bD.converters[bA+" "+bB[0]]){bx=bA;break}if(!e){e=bA}}bx=bx||e}if(bx){if(bx!==bB[0]){bB.unshift(bx)}return bz[bx]}}function G(bH,bz){if(bH.dataFilter){bz=bH.dataFilter(bz,bH.dataType)}var bD=bH.dataTypes,bG={},bA,bE,bw=bD.length,bB,bC=bD[0],bx,by,bF,bv,e;for(bA=1;bA=bw.duration+this.startTime){this.now=this.end;this.pos=this.state=1;this.update();bw.animatedProperties[this.prop]=true;for(bA in bw.animatedProperties){if(bw.animatedProperties[bA]!==true){e=false}}if(e){if(bw.overflow!=null&&!b.support.shrinkWrapBlocks){b.each(["","X","Y"],function(bC,bD){bz.style["overflow"+bD]=bw.overflow[bC]})}if(bw.hide){b(bz).hide()}if(bw.hide||bw.show){for(bA in bw.animatedProperties){b.style(bz,bA,bw.orig[bA]);b.removeData(bz,"fxshow"+bA,true);b.removeData(bz,"toggle"+bA,true)}}bv=bw.complete;if(bv){bw.complete=false;bv.call(bz)}}return false}else{if(bw.duration==Infinity){this.now=bx}else{bB=bx-this.startTime;this.state=bB/bw.duration;this.pos=b.easing[bw.animatedProperties[this.prop]](this.state,bB,0,1,bw.duration);this.now=this.start+((this.end-this.start)*this.pos)}this.update()}return true}};b.extend(b.fx,{tick:function(){var bw,bv=b.timers,e=0;for(;e").appendTo(e),bw=bv.css("display");bv.remove();if(bw==="none"||bw===""){if(!a8){a8=av.createElement("iframe");a8.frameBorder=a8.width=a8.height=0}e.appendChild(a8);if(!m||!a8.createElement){m=(a8.contentWindow||a8.contentDocument).document;m.write((av.compatMode==="CSS1Compat"?"":"")+"");m.close()}bv=m.createElement(bx);m.body.appendChild(bv);bw=b.css(bv,"display");e.removeChild(a8)}Q[bx]=bw}return Q[bx]}var V=/^t(?:able|d|h)$/i,ad=/^(?:body|html)$/i;if("getBoundingClientRect" in av.documentElement){b.fn.offset=function(bI){var by=this[0],bB;if(bI){return this.each(function(e){b.offset.setOffset(this,bI,e)})}if(!by||!by.ownerDocument){return null}if(by===by.ownerDocument.body){return b.offset.bodyOffset(by)}try{bB=by.getBoundingClientRect()}catch(bF){}var bH=by.ownerDocument,bw=bH.documentElement;if(!bB||!b.contains(bw,by)){return bB?{top:bB.top,left:bB.left}:{top:0,left:0}}var bC=bH.body,bD=aK(bH),bA=bw.clientTop||bC.clientTop||0,bE=bw.clientLeft||bC.clientLeft||0,bv=bD.pageYOffset||b.support.boxModel&&bw.scrollTop||bC.scrollTop,bz=bD.pageXOffset||b.support.boxModel&&bw.scrollLeft||bC.scrollLeft,bG=bB.top+bv-bA,bx=bB.left+bz-bE;return{top:bG,left:bx}}}else{b.fn.offset=function(bF){var bz=this[0];if(bF){return this.each(function(bG){b.offset.setOffset(this,bF,bG)})}if(!bz||!bz.ownerDocument){return null}if(bz===bz.ownerDocument.body){return b.offset.bodyOffset(bz)}var bC,bw=bz.offsetParent,bv=bz,bE=bz.ownerDocument,bx=bE.documentElement,bA=bE.body,bB=bE.defaultView,e=bB?bB.getComputedStyle(bz,null):bz.currentStyle,bD=bz.offsetTop,by=bz.offsetLeft;while((bz=bz.parentNode)&&bz!==bA&&bz!==bx){if(b.support.fixedPosition&&e.position==="fixed"){break}bC=bB?bB.getComputedStyle(bz,null):bz.currentStyle;bD-=bz.scrollTop;by-=bz.scrollLeft;if(bz===bw){bD+=bz.offsetTop;by+=bz.offsetLeft;if(b.support.doesNotAddBorder&&!(b.support.doesAddBorderForTableAndCells&&V.test(bz.nodeName))){bD+=parseFloat(bC.borderTopWidth)||0;by+=parseFloat(bC.borderLeftWidth)||0}bv=bw;bw=bz.offsetParent}if(b.support.subtractsBorderForOverflowNotVisible&&bC.overflow!=="visible"){bD+=parseFloat(bC.borderTopWidth)||0;by+=parseFloat(bC.borderLeftWidth)||0}e=bC}if(e.position==="relative"||e.position==="static"){bD+=bA.offsetTop;by+=bA.offsetLeft}if(b.support.fixedPosition&&e.position==="fixed"){bD+=Math.max(bx.scrollTop,bA.scrollTop);by+=Math.max(bx.scrollLeft,bA.scrollLeft)}return{top:bD,left:by}}}b.offset={bodyOffset:function(e){var bw=e.offsetTop,bv=e.offsetLeft;if(b.support.doesNotIncludeMarginInBodyOffset){bw+=parseFloat(b.css(e,"marginTop"))||0;bv+=parseFloat(b.css(e,"marginLeft"))||0}return{top:bw,left:bv}},setOffset:function(bx,bG,bA){var bB=b.css(bx,"position");if(bB==="static"){bx.style.position="relative"}var bz=b(bx),bv=bz.offset(),e=b.css(bx,"top"),bE=b.css(bx,"left"),bF=(bB==="absolute"||bB==="fixed")&&b.inArray("auto",[e,bE])>-1,bD={},bC={},bw,by;if(bF){bC=bz.position();bw=bC.top;by=bC.left}else{bw=parseFloat(e)||0;by=parseFloat(bE)||0}if(b.isFunction(bG)){bG=bG.call(bx,bA,bv)}if(bG.top!=null){bD.top=(bG.top-bv.top)+bw}if(bG.left!=null){bD.left=(bG.left-bv.left)+by}if("using" in bG){bG.using.call(bx,bD)}else{bz.css(bD)}}};b.fn.extend({position:function(){if(!this[0]){return null}var bw=this[0],bv=this.offsetParent(),bx=this.offset(),e=ad.test(bv[0].nodeName)?{top:0,left:0}:bv.offset();bx.top-=parseFloat(b.css(bw,"marginTop"))||0;bx.left-=parseFloat(b.css(bw,"marginLeft"))||0;e.top+=parseFloat(b.css(bv[0],"borderTopWidth"))||0;e.left+=parseFloat(b.css(bv[0],"borderLeftWidth"))||0;return{top:bx.top-e.top,left:bx.left-e.left}},offsetParent:function(){return this.map(function(){var e=this.offsetParent||av.body;while(e&&(!ad.test(e.nodeName)&&b.css(e,"position")==="static")){e=e.offsetParent}return e})}});b.each(["Left","Top"],function(bv,e){var bw="scroll"+e;b.fn[bw]=function(bz){var bx,by;if(bz===L){bx=this[0];if(!bx){return null}by=aK(bx);return by?("pageXOffset" in by)?by[bv?"pageYOffset":"pageXOffset"]:b.support.boxModel&&by.document.documentElement[bw]||by.document.body[bw]:bx[bw]}return this.each(function(){by=aK(this);if(by){by.scrollTo(!bv?bz:b(by).scrollLeft(),bv?bz:b(by).scrollTop())}else{this[bw]=bz}})}});function aK(e){return b.isWindow(e)?e:e.nodeType===9?e.defaultView||e.parentWindow:false}b.each(["Height","Width"],function(bv,e){var bw=e.toLowerCase();b.fn["inner"+e]=function(){var bx=this[0];return bx?bx.style?parseFloat(b.css(bx,bw,"padding")):this[bw]():null};b.fn["outer"+e]=function(by){var bx=this[0];return bx?bx.style?parseFloat(b.css(bx,bw,by?"margin":"border")):this[bw]():null};b.fn[bw]=function(bz){var bA=this[0];if(!bA){return bz==null?null:this}if(b.isFunction(bz)){return this.each(function(bE){var bD=b(this);bD[bw](bz.call(this,bE,bD[bw]()))})}if(b.isWindow(bA)){var bB=bA.document.documentElement["client"+e],bx=bA.document.body;return bA.document.compatMode==="CSS1Compat"&&bB||bx&&bx["client"+e]||bB}else{if(bA.nodeType===9){return Math.max(bA.documentElement["client"+e],bA.body["scroll"+e],bA.documentElement["scroll"+e],bA.body["offset"+e],bA.documentElement["offset"+e])}else{if(bz===L){var bC=b.css(bA,bw),by=parseFloat(bC);return b.isNumeric(by)?by:bC}else{return this.css(bw,typeof bz==="string"?bz:bz+"px")}}}}});bb.jQuery=bb.$=b;if(typeof define==="function"&&define.amd&&define.amd.jQuery){define("jquery",[],function(){return b})}})(window);/* +(function(){var bH=/((?:\((?:\([^()]+\)|[^()]+)+\)|\[(?:\[[^\[\]]*\]|['"][^'"]*['"]|[^\[\]'"]+)+\]|\\.|[^ >+~,(\[\\]+)+|[>+~])(\s*,\s*)?((?:.|\r|\n)*)/g,bC="sizcache"+(Math.random()+"").replace(".",""),bI=0,bL=Object.prototype.toString,bB=false,bA=true,bK=/\\/g,bO=/\r\n/g,bQ=/\W/;[0,0].sort(function(){bA=false;return 0});var by=function(bV,e,bY,bZ){bY=bY||[];e=e||av;var b1=e;if(e.nodeType!==1&&e.nodeType!==9){return[]}if(!bV||typeof bV!=="string"){return bY}var bS,b3,b6,bR,b2,b5,b4,bX,bU=true,bT=by.isXML(e),bW=[],b0=bV;do{bH.exec("");bS=bH.exec(b0);if(bS){b0=bS[3];bW.push(bS[1]);if(bS[2]){bR=bS[3];break}}}while(bS);if(bW.length>1&&bD.exec(bV)){if(bW.length===2&&bE.relative[bW[0]]){b3=bM(bW[0]+bW[1],e,bZ)}else{b3=bE.relative[bW[0]]?[e]:by(bW.shift(),e);while(bW.length){bV=bW.shift();if(bE.relative[bV]){bV+=bW.shift()}b3=bM(bV,b3,bZ)}}}else{if(!bZ&&bW.length>1&&e.nodeType===9&&!bT&&bE.match.ID.test(bW[0])&&!bE.match.ID.test(bW[bW.length-1])){b2=by.find(bW.shift(),e,bT);e=b2.expr?by.filter(b2.expr,b2.set)[0]:b2.set[0]}if(e){b2=bZ?{expr:bW.pop(),set:bF(bZ)}:by.find(bW.pop(),bW.length===1&&(bW[0]==="~"||bW[0]==="+")&&e.parentNode?e.parentNode:e,bT);b3=b2.expr?by.filter(b2.expr,b2.set):b2.set;if(bW.length>0){b6=bF(b3)}else{bU=false}while(bW.length){b5=bW.pop();b4=b5;if(!bE.relative[b5]){b5=""}else{b4=bW.pop()}if(b4==null){b4=e}bE.relative[b5](b6,b4,bT)}}else{b6=bW=[]}}if(!b6){b6=b3}if(!b6){by.error(b5||bV)}if(bL.call(b6)==="[object Array]"){if(!bU){bY.push.apply(bY,b6)}else{if(e&&e.nodeType===1){for(bX=0;b6[bX]!=null;bX++){if(b6[bX]&&(b6[bX]===true||b6[bX].nodeType===1&&by.contains(e,b6[bX]))){bY.push(b3[bX])}}}else{for(bX=0;b6[bX]!=null;bX++){if(b6[bX]&&b6[bX].nodeType===1){bY.push(b3[bX])}}}}}else{bF(b6,bY)}if(bR){by(bR,b1,bY,bZ);by.uniqueSort(bY)}return bY};by.uniqueSort=function(bR){if(bJ){bB=bA;bR.sort(bJ);if(bB){for(var e=1;e0};by.find=function(bX,e,bY){var bW,bS,bU,bT,bV,bR;if(!bX){return[]}for(bS=0,bU=bE.order.length;bS":function(bW,bR){var bV,bU=typeof bR==="string",bS=0,e=bW.length;if(bU&&!bQ.test(bR)){bR=bR.toLowerCase();for(;bS=0)){if(!bS){e.push(bV)}}else{if(bS){bR[bU]=false}}}}return false},ID:function(e){return e[1].replace(bK,"")},TAG:function(bR,e){return bR[1].replace(bK,"").toLowerCase()},CHILD:function(e){if(e[1]==="nth"){if(!e[2]){by.error(e[0])}e[2]=e[2].replace(/^\+|\s*/g,"");var bR=/(-?)(\d*)(?:n([+\-]?\d*))?/.exec(e[2]==="even"&&"2n"||e[2]==="odd"&&"2n+1"||!/\D/.test(e[2])&&"0n+"+e[2]||e[2]);e[2]=(bR[1]+(bR[2]||1))-0;e[3]=bR[3]-0}else{if(e[2]){by.error(e[0])}}e[0]=bI++;return e},ATTR:function(bU,bR,bS,e,bV,bW){var bT=bU[1]=bU[1].replace(bK,"");if(!bW&&bE.attrMap[bT]){bU[1]=bE.attrMap[bT]}bU[4]=(bU[4]||bU[5]||"").replace(bK,"");if(bU[2]==="~="){bU[4]=" "+bU[4]+" "}return bU},PSEUDO:function(bU,bR,bS,e,bV){if(bU[1]==="not"){if((bH.exec(bU[3])||"").length>1||/^\w/.test(bU[3])){bU[3]=by(bU[3],null,null,bR)}else{var bT=by.filter(bU[3],bR,bS,true^bV);if(!bS){e.push.apply(e,bT)}return false}}else{if(bE.match.POS.test(bU[0])||bE.match.CHILD.test(bU[0])){return true}}return bU},POS:function(e){e.unshift(true);return e}},filters:{enabled:function(e){return e.disabled===false&&e.type!=="hidden"},disabled:function(e){return e.disabled===true},checked:function(e){return e.checked===true},selected:function(e){if(e.parentNode){e.parentNode.selectedIndex}return e.selected===true},parent:function(e){return !!e.firstChild},empty:function(e){return !e.firstChild},has:function(bS,bR,e){return !!by(e[3],bS).length},header:function(e){return(/h\d/i).test(e.nodeName)},text:function(bS){var e=bS.getAttribute("type"),bR=bS.type;return bS.nodeName.toLowerCase()==="input"&&"text"===bR&&(e===bR||e===null)},radio:function(e){return e.nodeName.toLowerCase()==="input"&&"radio"===e.type},checkbox:function(e){return e.nodeName.toLowerCase()==="input"&&"checkbox"===e.type},file:function(e){return e.nodeName.toLowerCase()==="input"&&"file"===e.type},password:function(e){return e.nodeName.toLowerCase()==="input"&&"password"===e.type},submit:function(bR){var e=bR.nodeName.toLowerCase();return(e==="input"||e==="button")&&"submit"===bR.type},image:function(e){return e.nodeName.toLowerCase()==="input"&&"image"===e.type},reset:function(bR){var e=bR.nodeName.toLowerCase();return(e==="input"||e==="button")&&"reset"===bR.type},button:function(bR){var e=bR.nodeName.toLowerCase();return e==="input"&&"button"===bR.type||e==="button"},input:function(e){return(/input|select|textarea|button/i).test(e.nodeName)},focus:function(e){return e===e.ownerDocument.activeElement}},setFilters:{first:function(bR,e){return e===0},last:function(bS,bR,e,bT){return bR===bT.length-1},even:function(bR,e){return e%2===0},odd:function(bR,e){return e%2===1},lt:function(bS,bR,e){return bRe[3]-0},nth:function(bS,bR,e){return e[3]-0===bR},eq:function(bS,bR,e){return e[3]-0===bR}},filter:{PSEUDO:function(bS,bX,bW,bY){var e=bX[1],bR=bE.filters[e];if(bR){return bR(bS,bW,bX,bY)}else{if(e==="contains"){return(bS.textContent||bS.innerText||bw([bS])||"").indexOf(bX[3])>=0}else{if(e==="not"){var bT=bX[3];for(var bV=0,bU=bT.length;bV=0)}}},ID:function(bR,e){return bR.nodeType===1&&bR.getAttribute("id")===e},TAG:function(bR,e){return(e==="*"&&bR.nodeType===1)||!!bR.nodeName&&bR.nodeName.toLowerCase()===e},CLASS:function(bR,e){return(" "+(bR.className||bR.getAttribute("class"))+" ").indexOf(e)>-1},ATTR:function(bV,bT){var bS=bT[1],e=by.attr?by.attr(bV,bS):bE.attrHandle[bS]?bE.attrHandle[bS](bV):bV[bS]!=null?bV[bS]:bV.getAttribute(bS),bW=e+"",bU=bT[2],bR=bT[4];return e==null?bU==="!=":!bU&&by.attr?e!=null:bU==="="?bW===bR:bU==="*="?bW.indexOf(bR)>=0:bU==="~="?(" "+bW+" ").indexOf(bR)>=0:!bR?bW&&e!==false:bU==="!="?bW!==bR:bU==="^="?bW.indexOf(bR)===0:bU==="$="?bW.substr(bW.length-bR.length)===bR:bU==="|="?bW===bR||bW.substr(0,bR.length+1)===bR+"-":false},POS:function(bU,bR,bS,bV){var e=bR[2],bT=bE.setFilters[e];if(bT){return bT(bU,bS,bR,bV)}}}};var bD=bE.match.POS,bx=function(bR,e){return"\\"+(e-0+1)};for(var bz in bE.match){bE.match[bz]=new RegExp(bE.match[bz].source+(/(?![^\[]*\])(?![^\(]*\))/.source));bE.leftMatch[bz]=new RegExp(/(^(?:.|\r|\n)*?)/.source+bE.match[bz].source.replace(/\\(\d+)/g,bx))}var bF=function(bR,e){bR=Array.prototype.slice.call(bR,0);if(e){e.push.apply(e,bR);return e}return bR};try{Array.prototype.slice.call(av.documentElement.childNodes,0)[0].nodeType}catch(bP){bF=function(bU,bT){var bS=0,bR=bT||[];if(bL.call(bU)==="[object Array]"){Array.prototype.push.apply(bR,bU)}else{if(typeof bU.length==="number"){for(var e=bU.length;bS";e.insertBefore(bR,e.firstChild);if(av.getElementById(bS)){bE.find.ID=function(bU,bV,bW){if(typeof bV.getElementById!=="undefined"&&!bW){var bT=bV.getElementById(bU[1]);return bT?bT.id===bU[1]||typeof bT.getAttributeNode!=="undefined"&&bT.getAttributeNode("id").nodeValue===bU[1]?[bT]:L:[]}};bE.filter.ID=function(bV,bT){var bU=typeof bV.getAttributeNode!=="undefined"&&bV.getAttributeNode("id");return bV.nodeType===1&&bU&&bU.nodeValue===bT}}e.removeChild(bR);e=bR=null})();(function(){var e=av.createElement("div");e.appendChild(av.createComment(""));if(e.getElementsByTagName("*").length>0){bE.find.TAG=function(bR,bV){var bU=bV.getElementsByTagName(bR[1]);if(bR[1]==="*"){var bT=[];for(var bS=0;bU[bS];bS++){if(bU[bS].nodeType===1){bT.push(bU[bS])}}bU=bT}return bU}}e.innerHTML="";if(e.firstChild&&typeof e.firstChild.getAttribute!=="undefined"&&e.firstChild.getAttribute("href")!=="#"){bE.attrHandle.href=function(bR){return bR.getAttribute("href",2)}}e=null})();if(av.querySelectorAll){(function(){var e=by,bT=av.createElement("div"),bS="__sizzle__";bT.innerHTML="

";if(bT.querySelectorAll&&bT.querySelectorAll(".TEST").length===0){return}by=function(b4,bV,bZ,b3){bV=bV||av;if(!b3&&!by.isXML(bV)){var b2=/^(\w+$)|^\.([\w\-]+$)|^#([\w\-]+$)/.exec(b4);if(b2&&(bV.nodeType===1||bV.nodeType===9)){if(b2[1]){return bF(bV.getElementsByTagName(b4),bZ)}else{if(b2[2]&&bE.find.CLASS&&bV.getElementsByClassName){return bF(bV.getElementsByClassName(b2[2]),bZ)}}}if(bV.nodeType===9){if(b4==="body"&&bV.body){return bF([bV.body],bZ)}else{if(b2&&b2[3]){var bY=bV.getElementById(b2[3]);if(bY&&bY.parentNode){if(bY.id===b2[3]){return bF([bY],bZ)}}else{return bF([],bZ)}}}try{return bF(bV.querySelectorAll(b4),bZ)}catch(b0){}}else{if(bV.nodeType===1&&bV.nodeName.toLowerCase()!=="object"){var bW=bV,bX=bV.getAttribute("id"),bU=bX||bS,b6=bV.parentNode,b5=/^\s*[+~]/.test(b4);if(!bX){bV.setAttribute("id",bU)}else{bU=bU.replace(/'/g,"\\$&")}if(b5&&b6){bV=bV.parentNode}try{if(!b5||b6){return bF(bV.querySelectorAll("[id='"+bU+"'] "+b4),bZ)}}catch(b1){}finally{if(!bX){bW.removeAttribute("id")}}}}}return e(b4,bV,bZ,b3)};for(var bR in e){by[bR]=e[bR]}bT=null})()}(function(){var e=av.documentElement,bS=e.matchesSelector||e.mozMatchesSelector||e.webkitMatchesSelector||e.msMatchesSelector;if(bS){var bU=!bS.call(av.createElement("div"),"div"),bR=false;try{bS.call(av.documentElement,"[test!='']:sizzle")}catch(bT){bR=true}by.matchesSelector=function(bW,bY){bY=bY.replace(/\=\s*([^'"\]]*)\s*\]/g,"='$1']");if(!by.isXML(bW)){try{if(bR||!bE.match.PSEUDO.test(bY)&&!/!=/.test(bY)){var bV=bS.call(bW,bY);if(bV||!bU||bW.document&&bW.document.nodeType!==11){return bV}}}catch(bX){}}return by(bY,null,null,[bW]).length>0}}})();(function(){var e=av.createElement("div");e.innerHTML="
";if(!e.getElementsByClassName||e.getElementsByClassName("e").length===0){return}e.lastChild.className="e";if(e.getElementsByClassName("e").length===1){return}bE.order.splice(1,0,"CLASS");bE.find.CLASS=function(bR,bS,bT){if(typeof bS.getElementsByClassName!=="undefined"&&!bT){return bS.getElementsByClassName(bR[1])}};e=null})();function bv(bR,bW,bV,bZ,bX,bY){for(var bT=0,bS=bZ.length;bT0){bU=e;break}}}e=e[bR]}bZ[bT]=bU}}}if(av.documentElement.contains){by.contains=function(bR,e){return bR!==e&&(bR.contains?bR.contains(e):true)}}else{if(av.documentElement.compareDocumentPosition){by.contains=function(bR,e){return !!(bR.compareDocumentPosition(e)&16)}}else{by.contains=function(){return false}}}by.isXML=function(e){var bR=(e?e.ownerDocument||e:0).documentElement;return bR?bR.nodeName!=="HTML":false};var bM=function(bS,e,bW){var bV,bX=[],bU="",bY=e.nodeType?[e]:e;while((bV=bE.match.PSEUDO.exec(bS))){bU+=bV[0];bS=bS.replace(bE.match.PSEUDO,"")}bS=bE.relative[bS]?bS+"*":bS;for(var bT=0,bR=bY.length;bT0){for(bB=bA;bB=0:b.filter(e,this).length>0:this.filter(e).length>0)},closest:function(by,bx){var bv=[],bw,e,bz=this[0];if(b.isArray(by)){var bB=1;while(bz&&bz.ownerDocument&&bz!==bx){for(bw=0;bw-1:b.find.matchesSelector(bz,by)){bv.push(bz);break}else{bz=bz.parentNode;if(!bz||!bz.ownerDocument||bz===bx||bz.nodeType===11){break}}}}bv=bv.length>1?b.unique(bv):bv;return this.pushStack(bv,"closest",by)},index:function(e){if(!e){return(this[0]&&this[0].parentNode)?this.prevAll().length:-1}if(typeof e==="string"){return b.inArray(this[0],b(e))}return b.inArray(e.jquery?e[0]:e,this)},add:function(e,bv){var bx=typeof e==="string"?b(e,bv):b.makeArray(e&&e.nodeType?[e]:e),bw=b.merge(this.get(),bx);return this.pushStack(C(bx[0])||C(bw[0])?bw:b.unique(bw))},andSelf:function(){return this.add(this.prevObject)}});function C(e){return !e||!e.parentNode||e.parentNode.nodeType===11}b.each({parent:function(bv){var e=bv.parentNode;return e&&e.nodeType!==11?e:null},parents:function(e){return b.dir(e,"parentNode")},parentsUntil:function(bv,e,bw){return b.dir(bv,"parentNode",bw)},next:function(e){return b.nth(e,2,"nextSibling")},prev:function(e){return b.nth(e,2,"previousSibling")},nextAll:function(e){return b.dir(e,"nextSibling")},prevAll:function(e){return b.dir(e,"previousSibling")},nextUntil:function(bv,e,bw){return b.dir(bv,"nextSibling",bw)},prevUntil:function(bv,e,bw){return b.dir(bv,"previousSibling",bw)},siblings:function(e){return b.sibling(e.parentNode.firstChild,e)},children:function(e){return b.sibling(e.firstChild)},contents:function(e){return b.nodeName(e,"iframe")?e.contentDocument||e.contentWindow.document:b.makeArray(e.childNodes)}},function(e,bv){b.fn[e]=function(by,bw){var bx=b.map(this,bv,by);if(!ab.test(e)){bw=by}if(bw&&typeof bw==="string"){bx=b.filter(bw,bx)}bx=this.length>1&&!ay[e]?b.unique(bx):bx;if((this.length>1||a9.test(bw))&&aq.test(e)){bx=bx.reverse()}return this.pushStack(bx,e,P.call(arguments).join(","))}});b.extend({filter:function(bw,e,bv){if(bv){bw=":not("+bw+")"}return e.length===1?b.find.matchesSelector(e[0],bw)?[e[0]]:[]:b.find.matches(bw,e)},dir:function(bw,bv,by){var e=[],bx=bw[bv];while(bx&&bx.nodeType!==9&&(by===L||bx.nodeType!==1||!b(bx).is(by))){if(bx.nodeType===1){e.push(bx)}bx=bx[bv]}return e},nth:function(by,e,bw,bx){e=e||1;var bv=0;for(;by;by=by[bw]){if(by.nodeType===1&&++bv===e){break}}return by},sibling:function(bw,bv){var e=[];for(;bw;bw=bw.nextSibling){if(bw.nodeType===1&&bw!==bv){e.push(bw)}}return e}});function aG(bx,bw,e){bw=bw||0;if(b.isFunction(bw)){return b.grep(bx,function(bz,by){var bA=!!bw.call(bz,by,bz);return bA===e})}else{if(bw.nodeType){return b.grep(bx,function(bz,by){return(bz===bw)===e})}else{if(typeof bw==="string"){var bv=b.grep(bx,function(by){return by.nodeType===1});if(bp.test(bw)){return b.filter(bw,bv,!e)}else{bw=b.filter(bw,bv)}}}}return b.grep(bx,function(bz,by){return(b.inArray(bz,bw)>=0)===e})}function a(e){var bw=aR.split("|"),bv=e.createDocumentFragment();if(bv.createElement){while(bw.length){bv.createElement(bw.pop())}}return bv}var aR="abbr|article|aside|audio|canvas|datalist|details|figcaption|figure|footer|header|hgroup|mark|meter|nav|output|progress|section|summary|time|video",ag=/ jQuery\d+="(?:\d+|null)"/g,ar=/^\s+/,R=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/ig,d=/<([\w:]+)/,w=/
",""],legend:[1,"
","
"],thead:[1,"
","
"],tr:[2,"","
"],td:[3,"","
"],col:[2,"","
"],area:[1,"",""],_default:[0,"",""]},ac=a(av);ax.optgroup=ax.option;ax.tbody=ax.tfoot=ax.colgroup=ax.caption=ax.thead;ax.th=ax.td;if(!b.support.htmlSerialize){ax._default=[1,"div
","
"]}b.fn.extend({text:function(e){if(b.isFunction(e)){return this.each(function(bw){var bv=b(this);bv.text(e.call(this,bw,bv.text()))})}if(typeof e!=="object"&&e!==L){return this.empty().append((this[0]&&this[0].ownerDocument||av).createTextNode(e))}return b.text(this)},wrapAll:function(e){if(b.isFunction(e)){return this.each(function(bw){b(this).wrapAll(e.call(this,bw))})}if(this[0]){var bv=b(e,this[0].ownerDocument).eq(0).clone(true);if(this[0].parentNode){bv.insertBefore(this[0])}bv.map(function(){var bw=this;while(bw.firstChild&&bw.firstChild.nodeType===1){bw=bw.firstChild}return bw}).append(this)}return this},wrapInner:function(e){if(b.isFunction(e)){return this.each(function(bv){b(this).wrapInner(e.call(this,bv))})}return this.each(function(){var bv=b(this),bw=bv.contents();if(bw.length){bw.wrapAll(e)}else{bv.append(e)}})},wrap:function(e){var bv=b.isFunction(e);return this.each(function(bw){b(this).wrapAll(bv?e.call(this,bw):e)})},unwrap:function(){return this.parent().each(function(){if(!b.nodeName(this,"body")){b(this).replaceWith(this.childNodes)}}).end()},append:function(){return this.domManip(arguments,true,function(e){if(this.nodeType===1){this.appendChild(e)}})},prepend:function(){return this.domManip(arguments,true,function(e){if(this.nodeType===1){this.insertBefore(e,this.firstChild)}})},before:function(){if(this[0]&&this[0].parentNode){return this.domManip(arguments,false,function(bv){this.parentNode.insertBefore(bv,this)})}else{if(arguments.length){var e=b.clean(arguments);e.push.apply(e,this.toArray());return this.pushStack(e,"before",arguments)}}},after:function(){if(this[0]&&this[0].parentNode){return this.domManip(arguments,false,function(bv){this.parentNode.insertBefore(bv,this.nextSibling)})}else{if(arguments.length){var e=this.pushStack(this,"after",arguments);e.push.apply(e,b.clean(arguments));return e}}},remove:function(e,bx){for(var bv=0,bw;(bw=this[bv])!=null;bv++){if(!e||b.filter(e,[bw]).length){if(!bx&&bw.nodeType===1){b.cleanData(bw.getElementsByTagName("*"));b.cleanData([bw])}if(bw.parentNode){bw.parentNode.removeChild(bw)}}}return this},empty:function(){for(var e=0,bv;(bv=this[e])!=null;e++){if(bv.nodeType===1){b.cleanData(bv.getElementsByTagName("*"))}while(bv.firstChild){bv.removeChild(bv.firstChild)}}return this},clone:function(bv,e){bv=bv==null?false:bv;e=e==null?bv:e;return this.map(function(){return b.clone(this,bv,e)})},html:function(bx){if(bx===L){return this[0]&&this[0].nodeType===1?this[0].innerHTML.replace(ag,""):null}else{if(typeof bx==="string"&&!ae.test(bx)&&(b.support.leadingWhitespace||!ar.test(bx))&&!ax[(d.exec(bx)||["",""])[1].toLowerCase()]){bx=bx.replace(R,"<$1>");try{for(var bw=0,bv=this.length;bw1&&bw0?this.clone(true):this).get();b(bC[bA])[bv](by);bz=bz.concat(by)}return this.pushStack(bz,e,bC.selector)}}});function bg(e){if(typeof e.getElementsByTagName!=="undefined"){return e.getElementsByTagName("*")}else{if(typeof e.querySelectorAll!=="undefined"){return e.querySelectorAll("*")}else{return[]}}}function az(e){if(e.type==="checkbox"||e.type==="radio"){e.defaultChecked=e.checked}}function E(e){var bv=(e.nodeName||"").toLowerCase();if(bv==="input"){az(e)}else{if(bv!=="script"&&typeof e.getElementsByTagName!=="undefined"){b.grep(e.getElementsByTagName("input"),az)}}}function al(e){var bv=av.createElement("div");ac.appendChild(bv);bv.innerHTML=e.outerHTML;return bv.firstChild}b.extend({clone:function(by,bA,bw){var e,bv,bx,bz=b.support.html5Clone||!ah.test("<"+by.nodeName)?by.cloneNode(true):al(by);if((!b.support.noCloneEvent||!b.support.noCloneChecked)&&(by.nodeType===1||by.nodeType===11)&&!b.isXMLDoc(by)){ai(by,bz);e=bg(by);bv=bg(bz);for(bx=0;e[bx];++bx){if(bv[bx]){ai(e[bx],bv[bx])}}}if(bA){t(by,bz);if(bw){e=bg(by);bv=bg(bz);for(bx=0;e[bx];++bx){t(e[bx],bv[bx])}}}e=bv=null;return bz},clean:function(bw,by,bH,bA){var bF;by=by||av;if(typeof by.createElement==="undefined"){by=by.ownerDocument||by[0]&&by[0].ownerDocument||av}var bI=[],bB;for(var bE=0,bz;(bz=bw[bE])!=null;bE++){if(typeof bz==="number"){bz+=""}if(!bz){continue}if(typeof bz==="string"){if(!W.test(bz)){bz=by.createTextNode(bz)}else{bz=bz.replace(R,"<$1>");var bK=(d.exec(bz)||["",""])[1].toLowerCase(),bx=ax[bK]||ax._default,bD=bx[0],bv=by.createElement("div");if(by===av){ac.appendChild(bv)}else{a(by).appendChild(bv)}bv.innerHTML=bx[1]+bz+bx[2];while(bD--){bv=bv.lastChild}if(!b.support.tbody){var e=w.test(bz),bC=bK==="table"&&!e?bv.firstChild&&bv.firstChild.childNodes:bx[1]===""&&!e?bv.childNodes:[];for(bB=bC.length-1;bB>=0;--bB){if(b.nodeName(bC[bB],"tbody")&&!bC[bB].childNodes.length){bC[bB].parentNode.removeChild(bC[bB])}}}if(!b.support.leadingWhitespace&&ar.test(bz)){bv.insertBefore(by.createTextNode(ar.exec(bz)[0]),bv.firstChild)}bz=bv.childNodes}}var bG;if(!b.support.appendChecked){if(bz[0]&&typeof(bG=bz.length)==="number"){for(bB=0;bB=0){return bx+"px"}}else{return bx}}}});if(!b.support.opacity){b.cssHooks.opacity={get:function(bv,e){return au.test((e&&bv.currentStyle?bv.currentStyle.filter:bv.style.filter)||"")?(parseFloat(RegExp.$1)/100)+"":e?"1":""},set:function(by,bz){var bx=by.style,bv=by.currentStyle,e=b.isNumeric(bz)?"alpha(opacity="+bz*100+")":"",bw=bv&&bv.filter||bx.filter||"";bx.zoom=1;if(bz>=1&&b.trim(bw.replace(ak,""))===""){bx.removeAttribute("filter");if(bv&&!bv.filter){return}}bx.filter=ak.test(bw)?bw.replace(ak,e):bw+" "+e}}}b(function(){if(!b.support.reliableMarginRight){b.cssHooks.marginRight={get:function(bw,bv){var e;b.swap(bw,{display:"inline-block"},function(){if(bv){e=Z(bw,"margin-right","marginRight")}else{e=bw.style.marginRight}});return e}}}});if(av.defaultView&&av.defaultView.getComputedStyle){aI=function(by,bw){var bv,bx,e;bw=bw.replace(z,"-$1").toLowerCase();if((bx=by.ownerDocument.defaultView)&&(e=bx.getComputedStyle(by,null))){bv=e.getPropertyValue(bw);if(bv===""&&!b.contains(by.ownerDocument.documentElement,by)){bv=b.style(by,bw)}}return bv}}if(av.documentElement.currentStyle){aX=function(bz,bw){var bA,e,by,bv=bz.currentStyle&&bz.currentStyle[bw],bx=bz.style;if(bv===null&&bx&&(by=bx[bw])){bv=by}if(!bc.test(bv)&&bn.test(bv)){bA=bx.left;e=bz.runtimeStyle&&bz.runtimeStyle.left;if(e){bz.runtimeStyle.left=bz.currentStyle.left}bx.left=bw==="fontSize"?"1em":(bv||0);bv=bx.pixelLeft+"px";bx.left=bA;if(e){bz.runtimeStyle.left=e}}return bv===""?"auto":bv}}Z=aI||aX;function p(by,bw,bv){var bA=bw==="width"?by.offsetWidth:by.offsetHeight,bz=bw==="width"?an:a1,bx=0,e=bz.length;if(bA>0){if(bv!=="border"){for(;bx)<[^<]*)*<\/script>/gi,q=/^(?:select|textarea)/i,h=/\s+/,br=/([?&])_=[^&]*/,K=/^([\w\+\.\-]+:)(?:\/\/([^\/?#:]*)(?::(\d+))?)?/,A=b.fn.load,aa={},r={},aE,s,aV=["*/"]+["*"];try{aE=bl.href}catch(aw){aE=av.createElement("a");aE.href="";aE=aE.href}s=K.exec(aE.toLowerCase())||[];function f(e){return function(by,bA){if(typeof by!=="string"){bA=by;by="*"}if(b.isFunction(bA)){var bx=by.toLowerCase().split(h),bw=0,bz=bx.length,bv,bB,bC;for(;bw=0){var e=bw.slice(by,bw.length);bw=bw.slice(0,by)}var bx="GET";if(bz){if(b.isFunction(bz)){bA=bz;bz=L}else{if(typeof bz==="object"){bz=b.param(bz,b.ajaxSettings.traditional);bx="POST"}}}var bv=this;b.ajax({url:bw,type:bx,dataType:"html",data:bz,complete:function(bC,bB,bD){bD=bC.responseText;if(bC.isResolved()){bC.done(function(bE){bD=bE});bv.html(e?b("
").append(bD.replace(a6,"")).find(e):bD)}if(bA){bv.each(bA,[bD,bB,bC])}}});return this},serialize:function(){return b.param(this.serializeArray())},serializeArray:function(){return this.map(function(){return this.elements?b.makeArray(this.elements):this}).filter(function(){return this.name&&!this.disabled&&(this.checked||q.test(this.nodeName)||aZ.test(this.type))}).map(function(e,bv){var bw=b(this).val();return bw==null?null:b.isArray(bw)?b.map(bw,function(by,bx){return{name:bv.name,value:by.replace(bs,"\r\n")}}):{name:bv.name,value:bw.replace(bs,"\r\n")}}).get()}});b.each("ajaxStart ajaxStop ajaxComplete ajaxError ajaxSuccess ajaxSend".split(" "),function(e,bv){b.fn[bv]=function(bw){return this.on(bv,bw)}});b.each(["get","post"],function(e,bv){b[bv]=function(bw,by,bz,bx){if(b.isFunction(by)){bx=bx||bz;bz=by;by=L}return b.ajax({type:bv,url:bw,data:by,success:bz,dataType:bx})}});b.extend({getScript:function(e,bv){return b.get(e,L,bv,"script")},getJSON:function(e,bv,bw){return b.get(e,bv,bw,"json")},ajaxSetup:function(bv,e){if(e){am(bv,b.ajaxSettings)}else{e=bv;bv=b.ajaxSettings}am(bv,e);return bv},ajaxSettings:{url:aE,isLocal:aM.test(s[1]),global:true,type:"GET",contentType:"application/x-www-form-urlencoded",processData:true,async:true,accepts:{xml:"application/xml, text/xml",html:"text/html",text:"text/plain",json:"application/json, text/javascript","*":aV},contents:{xml:/xml/,html:/html/,json:/json/},responseFields:{xml:"responseXML",text:"responseText"},converters:{"* text":bb.String,"text html":true,"text json":b.parseJSON,"text xml":b.parseXML},flatOptions:{context:true,url:true}},ajaxPrefilter:f(aa),ajaxTransport:f(r),ajax:function(bz,bx){if(typeof bz==="object"){bx=bz;bz=L}bx=bx||{};var bD=b.ajaxSetup({},bx),bS=bD.context||bD,bG=bS!==bD&&(bS.nodeType||bS instanceof b)?b(bS):b.event,bR=b.Deferred(),bN=b.Callbacks("once memory"),bB=bD.statusCode||{},bC,bH={},bO={},bQ,by,bL,bE,bI,bA=0,bw,bK,bJ={readyState:0,setRequestHeader:function(bT,bU){if(!bA){var e=bT.toLowerCase();bT=bO[e]=bO[e]||bT;bH[bT]=bU}return this},getAllResponseHeaders:function(){return bA===2?bQ:null},getResponseHeader:function(bT){var e;if(bA===2){if(!by){by={};while((e=aD.exec(bQ))){by[e[1].toLowerCase()]=e[2]}}e=by[bT.toLowerCase()]}return e===L?null:e},overrideMimeType:function(e){if(!bA){bD.mimeType=e}return this},abort:function(e){e=e||"abort";if(bL){bL.abort(e)}bF(0,e);return this}};function bF(bZ,bU,b0,bW){if(bA===2){return}bA=2;if(bE){clearTimeout(bE)}bL=L;bQ=bW||"";bJ.readyState=bZ>0?4:0;var bT,b4,b3,bX=bU,bY=b0?bj(bD,bJ,b0):L,bV,b2;if(bZ>=200&&bZ<300||bZ===304){if(bD.ifModified){if((bV=bJ.getResponseHeader("Last-Modified"))){b.lastModified[bC]=bV}if((b2=bJ.getResponseHeader("Etag"))){b.etag[bC]=b2}}if(bZ===304){bX="notmodified";bT=true}else{try{b4=G(bD,bY);bX="success";bT=true}catch(b1){bX="parsererror";b3=b1}}}else{b3=bX;if(!bX||bZ){bX="error";if(bZ<0){bZ=0}}}bJ.status=bZ;bJ.statusText=""+(bU||bX);if(bT){bR.resolveWith(bS,[b4,bX,bJ])}else{bR.rejectWith(bS,[bJ,bX,b3])}bJ.statusCode(bB);bB=L;if(bw){bG.trigger("ajax"+(bT?"Success":"Error"),[bJ,bD,bT?b4:b3])}bN.fireWith(bS,[bJ,bX]);if(bw){bG.trigger("ajaxComplete",[bJ,bD]);if(!(--b.active)){b.event.trigger("ajaxStop")}}}bR.promise(bJ);bJ.success=bJ.done;bJ.error=bJ.fail;bJ.complete=bN.add;bJ.statusCode=function(bT){if(bT){var e;if(bA<2){for(e in bT){bB[e]=[bB[e],bT[e]]}}else{e=bT[bJ.status];bJ.then(e,e)}}return this};bD.url=((bz||bD.url)+"").replace(bq,"").replace(c,s[1]+"//");bD.dataTypes=b.trim(bD.dataType||"*").toLowerCase().split(h);if(bD.crossDomain==null){bI=K.exec(bD.url.toLowerCase());bD.crossDomain=!!(bI&&(bI[1]!=s[1]||bI[2]!=s[2]||(bI[3]||(bI[1]==="http:"?80:443))!=(s[3]||(s[1]==="http:"?80:443))))}if(bD.data&&bD.processData&&typeof bD.data!=="string"){bD.data=b.param(bD.data,bD.traditional)}aW(aa,bD,bx,bJ);if(bA===2){return false}bw=bD.global;bD.type=bD.type.toUpperCase();bD.hasContent=!aQ.test(bD.type);if(bw&&b.active++===0){b.event.trigger("ajaxStart")}if(!bD.hasContent){if(bD.data){bD.url+=(M.test(bD.url)?"&":"?")+bD.data;delete bD.data}bC=bD.url;if(bD.cache===false){var bv=b.now(),bP=bD.url.replace(br,"$1_="+bv);bD.url=bP+((bP===bD.url)?(M.test(bD.url)?"&":"?")+"_="+bv:"")}}if(bD.data&&bD.hasContent&&bD.contentType!==false||bx.contentType){bJ.setRequestHeader("Content-Type",bD.contentType)}if(bD.ifModified){bC=bC||bD.url;if(b.lastModified[bC]){bJ.setRequestHeader("If-Modified-Since",b.lastModified[bC])}if(b.etag[bC]){bJ.setRequestHeader("If-None-Match",b.etag[bC])}}bJ.setRequestHeader("Accept",bD.dataTypes[0]&&bD.accepts[bD.dataTypes[0]]?bD.accepts[bD.dataTypes[0]]+(bD.dataTypes[0]!=="*"?", "+aV+"; q=0.01":""):bD.accepts["*"]);for(bK in bD.headers){bJ.setRequestHeader(bK,bD.headers[bK])}if(bD.beforeSend&&(bD.beforeSend.call(bS,bJ,bD)===false||bA===2)){bJ.abort();return false}for(bK in {success:1,error:1,complete:1}){bJ[bK](bD[bK])}bL=aW(r,bD,bx,bJ);if(!bL){bF(-1,"No Transport")}else{bJ.readyState=1;if(bw){bG.trigger("ajaxSend",[bJ,bD])}if(bD.async&&bD.timeout>0){bE=setTimeout(function(){bJ.abort("timeout")},bD.timeout)}try{bA=1;bL.send(bH,bF)}catch(bM){if(bA<2){bF(-1,bM)}else{throw bM}}}return bJ},param:function(e,bw){var bv=[],by=function(bz,bA){bA=b.isFunction(bA)?bA():bA;bv[bv.length]=encodeURIComponent(bz)+"="+encodeURIComponent(bA)};if(bw===L){bw=b.ajaxSettings.traditional}if(b.isArray(e)||(e.jquery&&!b.isPlainObject(e))){b.each(e,function(){by(this.name,this.value)})}else{for(var bx in e){v(bx,e[bx],bw,by)}}return bv.join("&").replace(k,"+")}});function v(bw,by,bv,bx){if(b.isArray(by)){b.each(by,function(bA,bz){if(bv||ap.test(bw)){bx(bw,bz)}else{v(bw+"["+(typeof bz==="object"||b.isArray(bz)?bA:"")+"]",bz,bv,bx)}})}else{if(!bv&&by!=null&&typeof by==="object"){for(var e in by){v(bw+"["+e+"]",by[e],bv,bx)}}else{bx(bw,by)}}}b.extend({active:0,lastModified:{},etag:{}});function bj(bD,bC,bz){var bv=bD.contents,bB=bD.dataTypes,bw=bD.responseFields,by,bA,bx,e;for(bA in bw){if(bA in bz){bC[bw[bA]]=bz[bA]}}while(bB[0]==="*"){bB.shift();if(by===L){by=bD.mimeType||bC.getResponseHeader("content-type")}}if(by){for(bA in bv){if(bv[bA]&&bv[bA].test(by)){bB.unshift(bA);break}}}if(bB[0] in bz){bx=bB[0]}else{for(bA in bz){if(!bB[0]||bD.converters[bA+" "+bB[0]]){bx=bA;break}if(!e){e=bA}}bx=bx||e}if(bx){if(bx!==bB[0]){bB.unshift(bx)}return bz[bx]}}function G(bH,bz){if(bH.dataFilter){bz=bH.dataFilter(bz,bH.dataType)}var bD=bH.dataTypes,bG={},bA,bE,bw=bD.length,bB,bC=bD[0],bx,by,bF,bv,e;for(bA=1;bA=bw.duration+this.startTime){this.now=this.end;this.pos=this.state=1;this.update();bw.animatedProperties[this.prop]=true;for(bA in bw.animatedProperties){if(bw.animatedProperties[bA]!==true){e=false}}if(e){if(bw.overflow!=null&&!b.support.shrinkWrapBlocks){b.each(["","X","Y"],function(bC,bD){bz.style["overflow"+bD]=bw.overflow[bC]})}if(bw.hide){b(bz).hide()}if(bw.hide||bw.show){for(bA in bw.animatedProperties){b.style(bz,bA,bw.orig[bA]);b.removeData(bz,"fxshow"+bA,true);b.removeData(bz,"toggle"+bA,true)}}bv=bw.complete;if(bv){bw.complete=false;bv.call(bz)}}return false}else{if(bw.duration==Infinity){this.now=bx}else{bB=bx-this.startTime;this.state=bB/bw.duration;this.pos=b.easing[bw.animatedProperties[this.prop]](this.state,bB,0,1,bw.duration);this.now=this.start+((this.end-this.start)*this.pos)}this.update()}return true}};b.extend(b.fx,{tick:function(){var bw,bv=b.timers,e=0;for(;e").appendTo(e),bw=bv.css("display");bv.remove();if(bw==="none"||bw===""){if(!a8){a8=av.createElement("iframe");a8.frameBorder=a8.width=a8.height=0}e.appendChild(a8);if(!m||!a8.createElement){m=(a8.contentWindow||a8.contentDocument).document;m.write((av.compatMode==="CSS1Compat"?"":"")+"");m.close()}bv=m.createElement(bx);m.body.appendChild(bv);bw=b.css(bv,"display");e.removeChild(a8)}Q[bx]=bw}return Q[bx]}var V=/^t(?:able|d|h)$/i,ad=/^(?:body|html)$/i;if("getBoundingClientRect" in av.documentElement){b.fn.offset=function(bI){var by=this[0],bB;if(bI){return this.each(function(e){b.offset.setOffset(this,bI,e)})}if(!by||!by.ownerDocument){return null}if(by===by.ownerDocument.body){return b.offset.bodyOffset(by)}try{bB=by.getBoundingClientRect()}catch(bF){}var bH=by.ownerDocument,bw=bH.documentElement;if(!bB||!b.contains(bw,by)){return bB?{top:bB.top,left:bB.left}:{top:0,left:0}}var bC=bH.body,bD=aK(bH),bA=bw.clientTop||bC.clientTop||0,bE=bw.clientLeft||bC.clientLeft||0,bv=bD.pageYOffset||b.support.boxModel&&bw.scrollTop||bC.scrollTop,bz=bD.pageXOffset||b.support.boxModel&&bw.scrollLeft||bC.scrollLeft,bG=bB.top+bv-bA,bx=bB.left+bz-bE;return{top:bG,left:bx}}}else{b.fn.offset=function(bF){var bz=this[0];if(bF){return this.each(function(bG){b.offset.setOffset(this,bF,bG)})}if(!bz||!bz.ownerDocument){return null}if(bz===bz.ownerDocument.body){return b.offset.bodyOffset(bz)}var bC,bw=bz.offsetParent,bv=bz,bE=bz.ownerDocument,bx=bE.documentElement,bA=bE.body,bB=bE.defaultView,e=bB?bB.getComputedStyle(bz,null):bz.currentStyle,bD=bz.offsetTop,by=bz.offsetLeft;while((bz=bz.parentNode)&&bz!==bA&&bz!==bx){if(b.support.fixedPosition&&e.position==="fixed"){break}bC=bB?bB.getComputedStyle(bz,null):bz.currentStyle;bD-=bz.scrollTop;by-=bz.scrollLeft;if(bz===bw){bD+=bz.offsetTop;by+=bz.offsetLeft;if(b.support.doesNotAddBorder&&!(b.support.doesAddBorderForTableAndCells&&V.test(bz.nodeName))){bD+=parseFloat(bC.borderTopWidth)||0;by+=parseFloat(bC.borderLeftWidth)||0}bv=bw;bw=bz.offsetParent}if(b.support.subtractsBorderForOverflowNotVisible&&bC.overflow!=="visible"){bD+=parseFloat(bC.borderTopWidth)||0;by+=parseFloat(bC.borderLeftWidth)||0}e=bC}if(e.position==="relative"||e.position==="static"){bD+=bA.offsetTop;by+=bA.offsetLeft}if(b.support.fixedPosition&&e.position==="fixed"){bD+=Math.max(bx.scrollTop,bA.scrollTop);by+=Math.max(bx.scrollLeft,bA.scrollLeft)}return{top:bD,left:by}}}b.offset={bodyOffset:function(e){var bw=e.offsetTop,bv=e.offsetLeft;if(b.support.doesNotIncludeMarginInBodyOffset){bw+=parseFloat(b.css(e,"marginTop"))||0;bv+=parseFloat(b.css(e,"marginLeft"))||0}return{top:bw,left:bv}},setOffset:function(bx,bG,bA){var bB=b.css(bx,"position");if(bB==="static"){bx.style.position="relative"}var bz=b(bx),bv=bz.offset(),e=b.css(bx,"top"),bE=b.css(bx,"left"),bF=(bB==="absolute"||bB==="fixed")&&b.inArray("auto",[e,bE])>-1,bD={},bC={},bw,by;if(bF){bC=bz.position();bw=bC.top;by=bC.left}else{bw=parseFloat(e)||0;by=parseFloat(bE)||0}if(b.isFunction(bG)){bG=bG.call(bx,bA,bv)}if(bG.top!=null){bD.top=(bG.top-bv.top)+bw}if(bG.left!=null){bD.left=(bG.left-bv.left)+by}if("using" in bG){bG.using.call(bx,bD)}else{bz.css(bD)}}};b.fn.extend({position:function(){if(!this[0]){return null}var bw=this[0],bv=this.offsetParent(),bx=this.offset(),e=ad.test(bv[0].nodeName)?{top:0,left:0}:bv.offset();bx.top-=parseFloat(b.css(bw,"marginTop"))||0;bx.left-=parseFloat(b.css(bw,"marginLeft"))||0;e.top+=parseFloat(b.css(bv[0],"borderTopWidth"))||0;e.left+=parseFloat(b.css(bv[0],"borderLeftWidth"))||0;return{top:bx.top-e.top,left:bx.left-e.left}},offsetParent:function(){return this.map(function(){var e=this.offsetParent||av.body;while(e&&(!ad.test(e.nodeName)&&b.css(e,"position")==="static")){e=e.offsetParent}return e})}});b.each(["Left","Top"],function(bv,e){var bw="scroll"+e;b.fn[bw]=function(bz){var bx,by;if(bz===L){bx=this[0];if(!bx){return null}by=aK(bx);return by?("pageXOffset" in by)?by[bv?"pageYOffset":"pageXOffset"]:b.support.boxModel&&by.document.documentElement[bw]||by.document.body[bw]:bx[bw]}return this.each(function(){by=aK(this);if(by){by.scrollTo(!bv?bz:b(by).scrollLeft(),bv?bz:b(by).scrollTop())}else{this[bw]=bz}})}});function aK(e){return b.isWindow(e)?e:e.nodeType===9?e.defaultView||e.parentWindow:false}b.each(["Height","Width"],function(bv,e){var bw=e.toLowerCase();b.fn["inner"+e]=function(){var bx=this[0];return bx?bx.style?parseFloat(b.css(bx,bw,"padding")):this[bw]():null};b.fn["outer"+e]=function(by){var bx=this[0];return bx?bx.style?parseFloat(b.css(bx,bw,by?"margin":"border")):this[bw]():null};b.fn[bw]=function(bz){var bA=this[0];if(!bA){return bz==null?null:this}if(b.isFunction(bz)){return this.each(function(bE){var bD=b(this);bD[bw](bz.call(this,bE,bD[bw]()))})}if(b.isWindow(bA)){var bB=bA.document.documentElement["client"+e],bx=bA.document.body;return bA.document.compatMode==="CSS1Compat"&&bB||bx&&bx["client"+e]||bB}else{if(bA.nodeType===9){return Math.max(bA.documentElement["client"+e],bA.body["scroll"+e],bA.documentElement["scroll"+e],bA.body["offset"+e],bA.documentElement["offset"+e])}else{if(bz===L){var bC=b.css(bA,bw),by=parseFloat(bC);return b.isNumeric(by)?by:bC}else{return this.css(bw,typeof bz==="string"?bz:bz+"px")}}}}});bb.jQuery=bb.$=b;if(typeof define==="function"&&define.amd&&define.amd.jQuery){define("jquery",[],function(){return b})}})(window);/*! * jQuery UI 1.8.18 * * Copyright 2011, AUTHORS.txt (http://jqueryui.com/about) @@ -29,7 +29,7 @@ * * http://docs.jquery.com/UI */ -(function(a,d){a.ui=a.ui||{};if(a.ui.version){return}a.extend(a.ui,{version:"1.8.18",keyCode:{ALT:18,BACKSPACE:8,CAPS_LOCK:20,COMMA:188,COMMAND:91,COMMAND_LEFT:91,COMMAND_RIGHT:93,CONTROL:17,DELETE:46,DOWN:40,END:35,ENTER:13,ESCAPE:27,HOME:36,INSERT:45,LEFT:37,MENU:93,NUMPAD_ADD:107,NUMPAD_DECIMAL:110,NUMPAD_DIVIDE:111,NUMPAD_ENTER:108,NUMPAD_MULTIPLY:106,NUMPAD_SUBTRACT:109,PAGE_DOWN:34,PAGE_UP:33,PERIOD:190,RIGHT:39,SHIFT:16,SPACE:32,TAB:9,UP:38,WINDOWS:91}});a.fn.extend({propAttr:a.fn.prop||a.fn.attr,_focus:a.fn.focus,focus:function(e,f){return typeof e==="number"?this.each(function(){var g=this;setTimeout(function(){a(g).focus();if(f){f.call(g)}},e)}):this._focus.apply(this,arguments)},scrollParent:function(){var e;if((a.browser.msie&&(/(static|relative)/).test(this.css("position")))||(/absolute/).test(this.css("position"))){e=this.parents().filter(function(){return(/(relative|absolute|fixed)/).test(a.curCSS(this,"position",1))&&(/(auto|scroll)/).test(a.curCSS(this,"overflow",1)+a.curCSS(this,"overflow-y",1)+a.curCSS(this,"overflow-x",1))}).eq(0)}else{e=this.parents().filter(function(){return(/(auto|scroll)/).test(a.curCSS(this,"overflow",1)+a.curCSS(this,"overflow-y",1)+a.curCSS(this,"overflow-x",1))}).eq(0)}return(/fixed/).test(this.css("position"))||!e.length?a(document):e},zIndex:function(h){if(h!==d){return this.css("zIndex",h)}if(this.length){var f=a(this[0]),e,g;while(f.length&&f[0]!==document){e=f.css("position");if(e==="absolute"||e==="relative"||e==="fixed"){g=parseInt(f.css("zIndex"),10);if(!isNaN(g)&&g!==0){return g}}f=f.parent()}}return 0},disableSelection:function(){return this.bind((a.support.selectstart?"selectstart":"mousedown")+".ui-disableSelection",function(e){e.preventDefault()})},enableSelection:function(){return this.unbind(".ui-disableSelection")}});a.each(["Width","Height"],function(g,e){var f=e==="Width"?["Left","Right"]:["Top","Bottom"],h=e.toLowerCase(),k={innerWidth:a.fn.innerWidth,innerHeight:a.fn.innerHeight,outerWidth:a.fn.outerWidth,outerHeight:a.fn.outerHeight};function j(m,l,i,n){a.each(f,function(){l-=parseFloat(a.curCSS(m,"padding"+this,true))||0;if(i){l-=parseFloat(a.curCSS(m,"border"+this+"Width",true))||0}if(n){l-=parseFloat(a.curCSS(m,"margin"+this,true))||0}});return l}a.fn["inner"+e]=function(i){if(i===d){return k["inner"+e].call(this)}return this.each(function(){a(this).css(h,j(this,i)+"px")})};a.fn["outer"+e]=function(i,l){if(typeof i!=="number"){return k["outer"+e].call(this,i)}return this.each(function(){a(this).css(h,j(this,i,true,l)+"px")})}});function c(g,e){var j=g.nodeName.toLowerCase();if("area"===j){var i=g.parentNode,h=i.name,f;if(!g.href||!h||i.nodeName.toLowerCase()!=="map"){return false}f=a("img[usemap=#"+h+"]")[0];return !!f&&b(f)}return(/input|select|textarea|button|object/.test(j)?!g.disabled:"a"==j?g.href||e:e)&&b(g)}function b(e){return !a(e).parents().andSelf().filter(function(){return a.curCSS(this,"visibility")==="hidden"||a.expr.filters.hidden(this)}).length}a.extend(a.expr[":"],{data:function(g,f,e){return !!a.data(g,e[3])},focusable:function(e){return c(e,!isNaN(a.attr(e,"tabindex")))},tabbable:function(g){var e=a.attr(g,"tabindex"),f=isNaN(e);return(f||e>=0)&&c(g,!f)}});a(function(){var e=document.body,f=e.appendChild(f=document.createElement("div"));f.offsetHeight;a.extend(f.style,{minHeight:"100px",height:"auto",padding:0,borderWidth:0});a.support.minHeight=f.offsetHeight===100;a.support.selectstart="onselectstart" in f;e.removeChild(f).style.display="none"});a.extend(a.ui,{plugin:{add:function(f,g,j){var h=a.ui[f].prototype;for(var e in j){h.plugins[e]=h.plugins[e]||[];h.plugins[e].push([g,j[e]])}},call:function(e,g,f){var j=e.plugins[g];if(!j||!e.element[0].parentNode){return}for(var h=0;h0){return true}h[e]=1;g=(h[e]>0);h[e]=0;return g},isOverAxis:function(f,e,g){return(f>e)&&(f<(e+g))},isOver:function(j,f,i,h,e,g){return a.ui.isOverAxis(j,i,e)&&a.ui.isOverAxis(f,h,g)}})})(jQuery);/* +(function(a,d){a.ui=a.ui||{};if(a.ui.version){return}a.extend(a.ui,{version:"1.8.18",keyCode:{ALT:18,BACKSPACE:8,CAPS_LOCK:20,COMMA:188,COMMAND:91,COMMAND_LEFT:91,COMMAND_RIGHT:93,CONTROL:17,DELETE:46,DOWN:40,END:35,ENTER:13,ESCAPE:27,HOME:36,INSERT:45,LEFT:37,MENU:93,NUMPAD_ADD:107,NUMPAD_DECIMAL:110,NUMPAD_DIVIDE:111,NUMPAD_ENTER:108,NUMPAD_MULTIPLY:106,NUMPAD_SUBTRACT:109,PAGE_DOWN:34,PAGE_UP:33,PERIOD:190,RIGHT:39,SHIFT:16,SPACE:32,TAB:9,UP:38,WINDOWS:91}});a.fn.extend({propAttr:a.fn.prop||a.fn.attr,_focus:a.fn.focus,focus:function(e,f){return typeof e==="number"?this.each(function(){var g=this;setTimeout(function(){a(g).focus();if(f){f.call(g)}},e)}):this._focus.apply(this,arguments)},scrollParent:function(){var e;if((a.browser.msie&&(/(static|relative)/).test(this.css("position")))||(/absolute/).test(this.css("position"))){e=this.parents().filter(function(){return(/(relative|absolute|fixed)/).test(a.curCSS(this,"position",1))&&(/(auto|scroll)/).test(a.curCSS(this,"overflow",1)+a.curCSS(this,"overflow-y",1)+a.curCSS(this,"overflow-x",1))}).eq(0)}else{e=this.parents().filter(function(){return(/(auto|scroll)/).test(a.curCSS(this,"overflow",1)+a.curCSS(this,"overflow-y",1)+a.curCSS(this,"overflow-x",1))}).eq(0)}return(/fixed/).test(this.css("position"))||!e.length?a(document):e},zIndex:function(h){if(h!==d){return this.css("zIndex",h)}if(this.length){var f=a(this[0]),e,g;while(f.length&&f[0]!==document){e=f.css("position");if(e==="absolute"||e==="relative"||e==="fixed"){g=parseInt(f.css("zIndex"),10);if(!isNaN(g)&&g!==0){return g}}f=f.parent()}}return 0},disableSelection:function(){return this.bind((a.support.selectstart?"selectstart":"mousedown")+".ui-disableSelection",function(e){e.preventDefault()})},enableSelection:function(){return this.unbind(".ui-disableSelection")}});a.each(["Width","Height"],function(g,e){var f=e==="Width"?["Left","Right"]:["Top","Bottom"],h=e.toLowerCase(),k={innerWidth:a.fn.innerWidth,innerHeight:a.fn.innerHeight,outerWidth:a.fn.outerWidth,outerHeight:a.fn.outerHeight};function j(m,l,i,n){a.each(f,function(){l-=parseFloat(a.curCSS(m,"padding"+this,true))||0;if(i){l-=parseFloat(a.curCSS(m,"border"+this+"Width",true))||0}if(n){l-=parseFloat(a.curCSS(m,"margin"+this,true))||0}});return l}a.fn["inner"+e]=function(i){if(i===d){return k["inner"+e].call(this)}return this.each(function(){a(this).css(h,j(this,i)+"px")})};a.fn["outer"+e]=function(i,l){if(typeof i!=="number"){return k["outer"+e].call(this,i)}return this.each(function(){a(this).css(h,j(this,i,true,l)+"px")})}});function c(g,e){var j=g.nodeName.toLowerCase();if("area"===j){var i=g.parentNode,h=i.name,f;if(!g.href||!h||i.nodeName.toLowerCase()!=="map"){return false}f=a("img[usemap=#"+h+"]")[0];return !!f&&b(f)}return(/input|select|textarea|button|object/.test(j)?!g.disabled:"a"==j?g.href||e:e)&&b(g)}function b(e){return !a(e).parents().andSelf().filter(function(){return a.curCSS(this,"visibility")==="hidden"||a.expr.filters.hidden(this)}).length}a.extend(a.expr[":"],{data:function(g,f,e){return !!a.data(g,e[3])},focusable:function(e){return c(e,!isNaN(a.attr(e,"tabindex")))},tabbable:function(g){var e=a.attr(g,"tabindex"),f=isNaN(e);return(f||e>=0)&&c(g,!f)}});a(function(){var e=document.body,f=e.appendChild(f=document.createElement("div"));f.offsetHeight;a.extend(f.style,{minHeight:"100px",height:"auto",padding:0,borderWidth:0});a.support.minHeight=f.offsetHeight===100;a.support.selectstart="onselectstart" in f;e.removeChild(f).style.display="none"});a.extend(a.ui,{plugin:{add:function(f,g,j){var h=a.ui[f].prototype;for(var e in j){h.plugins[e]=h.plugins[e]||[];h.plugins[e].push([g,j[e]])}},call:function(e,g,f){var j=e.plugins[g];if(!j||!e.element[0].parentNode){return}for(var h=0;h0){return true}h[e]=1;g=(h[e]>0);h[e]=0;return g},isOverAxis:function(f,e,g){return(f>e)&&(f<(e+g))},isOver:function(j,f,i,h,e,g){return a.ui.isOverAxis(j,i,e)&&a.ui.isOverAxis(f,h,g)}})})(jQuery);/*! * jQuery UI Widget 1.8.18 * * Copyright 2011, AUTHORS.txt (http://jqueryui.com/about) @@ -38,7 +38,7 @@ * * http://docs.jquery.com/UI/Widget */ -(function(b,d){if(b.cleanData){var c=b.cleanData;b.cleanData=function(f){for(var g=0,h;(h=f[g])!=null;g++){try{b(h).triggerHandler("remove")}catch(j){}}c(f)}}else{var a=b.fn.remove;b.fn.remove=function(e,f){return this.each(function(){if(!f){if(!e||b.filter(e,[this]).length){b("*",this).add([this]).each(function(){try{b(this).triggerHandler("remove")}catch(g){}})}}return a.call(b(this),e,f)})}}b.widget=function(f,h,e){var g=f.split(".")[0],j;f=f.split(".")[1];j=g+"-"+f;if(!e){e=h;h=b.Widget}b.expr[":"][j]=function(k){return !!b.data(k,f)};b[g]=b[g]||{};b[g][f]=function(k,l){if(arguments.length){this._createWidget(k,l)}};var i=new h();i.options=b.extend(true,{},i.options);b[g][f].prototype=b.extend(true,i,{namespace:g,widgetName:f,widgetEventPrefix:b[g][f].prototype.widgetEventPrefix||f,widgetBaseClass:j},e);b.widget.bridge(f,b[g][f])};b.widget.bridge=function(f,e){b.fn[f]=function(i){var g=typeof i==="string",h=Array.prototype.slice.call(arguments,1),j=this;i=!g&&h.length?b.extend.apply(null,[true,i].concat(h)):i;if(g&&i.charAt(0)==="_"){return j}if(g){this.each(function(){var k=b.data(this,f),l=k&&b.isFunction(k[i])?k[i].apply(k,h):k;if(l!==k&&l!==d){j=l;return false}})}else{this.each(function(){var k=b.data(this,f);if(k){k.option(i||{})._init()}else{b.data(this,f,new e(i,this))}})}return j}};b.Widget=function(e,f){if(arguments.length){this._createWidget(e,f)}};b.Widget.prototype={widgetName:"widget",widgetEventPrefix:"",options:{disabled:false},_createWidget:function(f,g){b.data(g,this.widgetName,this);this.element=b(g);this.options=b.extend(true,{},this.options,this._getCreateOptions(),f);var e=this;this.element.bind("remove."+this.widgetName,function(){e.destroy()});this._create();this._trigger("create");this._init()},_getCreateOptions:function(){return b.metadata&&b.metadata.get(this.element[0])[this.widgetName]},_create:function(){},_init:function(){},destroy:function(){this.element.unbind("."+this.widgetName).removeData(this.widgetName);this.widget().unbind("."+this.widgetName).removeAttr("aria-disabled").removeClass(this.widgetBaseClass+"-disabled ui-state-disabled")},widget:function(){return this.element},option:function(f,g){var e=f;if(arguments.length===0){return b.extend({},this.options)}if(typeof f==="string"){if(g===d){return this.options[f]}e={};e[f]=g}this._setOptions(e);return this},_setOptions:function(f){var e=this;b.each(f,function(g,h){e._setOption(g,h)});return this},_setOption:function(e,f){this.options[e]=f;if(e==="disabled"){this.widget()[f?"addClass":"removeClass"](this.widgetBaseClass+"-disabled ui-state-disabled").attr("aria-disabled",f)}return this},enable:function(){return this._setOption("disabled",false)},disable:function(){return this._setOption("disabled",true)},_trigger:function(e,f,g){var j,i,h=this.options[e];g=g||{};f=b.Event(f);f.type=(e===this.widgetEventPrefix?e:this.widgetEventPrefix+e).toLowerCase();f.target=this.element[0];i=f.originalEvent;if(i){for(j in i){if(!(j in f)){f[j]=i[j]}}}this.element.trigger(f,g);return !(b.isFunction(h)&&h.call(this.element[0],f,g)===false||f.isDefaultPrevented())}}})(jQuery);/* +(function(b,d){if(b.cleanData){var c=b.cleanData;b.cleanData=function(f){for(var g=0,h;(h=f[g])!=null;g++){try{b(h).triggerHandler("remove")}catch(j){}}c(f)}}else{var a=b.fn.remove;b.fn.remove=function(e,f){return this.each(function(){if(!f){if(!e||b.filter(e,[this]).length){b("*",this).add([this]).each(function(){try{b(this).triggerHandler("remove")}catch(g){}})}}return a.call(b(this),e,f)})}}b.widget=function(f,h,e){var g=f.split(".")[0],j;f=f.split(".")[1];j=g+"-"+f;if(!e){e=h;h=b.Widget}b.expr[":"][j]=function(k){return !!b.data(k,f)};b[g]=b[g]||{};b[g][f]=function(k,l){if(arguments.length){this._createWidget(k,l)}};var i=new h();i.options=b.extend(true,{},i.options);b[g][f].prototype=b.extend(true,i,{namespace:g,widgetName:f,widgetEventPrefix:b[g][f].prototype.widgetEventPrefix||f,widgetBaseClass:j},e);b.widget.bridge(f,b[g][f])};b.widget.bridge=function(f,e){b.fn[f]=function(i){var g=typeof i==="string",h=Array.prototype.slice.call(arguments,1),j=this;i=!g&&h.length?b.extend.apply(null,[true,i].concat(h)):i;if(g&&i.charAt(0)==="_"){return j}if(g){this.each(function(){var k=b.data(this,f),l=k&&b.isFunction(k[i])?k[i].apply(k,h):k;if(l!==k&&l!==d){j=l;return false}})}else{this.each(function(){var k=b.data(this,f);if(k){k.option(i||{})._init()}else{b.data(this,f,new e(i,this))}})}return j}};b.Widget=function(e,f){if(arguments.length){this._createWidget(e,f)}};b.Widget.prototype={widgetName:"widget",widgetEventPrefix:"",options:{disabled:false},_createWidget:function(f,g){b.data(g,this.widgetName,this);this.element=b(g);this.options=b.extend(true,{},this.options,this._getCreateOptions(),f);var e=this;this.element.bind("remove."+this.widgetName,function(){e.destroy()});this._create();this._trigger("create");this._init()},_getCreateOptions:function(){return b.metadata&&b.metadata.get(this.element[0])[this.widgetName]},_create:function(){},_init:function(){},destroy:function(){this.element.unbind("."+this.widgetName).removeData(this.widgetName);this.widget().unbind("."+this.widgetName).removeAttr("aria-disabled").removeClass(this.widgetBaseClass+"-disabled ui-state-disabled")},widget:function(){return this.element},option:function(f,g){var e=f;if(arguments.length===0){return b.extend({},this.options)}if(typeof f==="string"){if(g===d){return this.options[f]}e={};e[f]=g}this._setOptions(e);return this},_setOptions:function(f){var e=this;b.each(f,function(g,h){e._setOption(g,h)});return this},_setOption:function(e,f){this.options[e]=f;if(e==="disabled"){this.widget()[f?"addClass":"removeClass"](this.widgetBaseClass+"-disabled ui-state-disabled").attr("aria-disabled",f)}return this},enable:function(){return this._setOption("disabled",false)},disable:function(){return this._setOption("disabled",true)},_trigger:function(e,f,g){var j,i,h=this.options[e];g=g||{};f=b.Event(f);f.type=(e===this.widgetEventPrefix?e:this.widgetEventPrefix+e).toLowerCase();f.target=this.element[0];i=f.originalEvent;if(i){for(j in i){if(!(j in f)){f[j]=i[j]}}}this.element.trigger(f,g);return !(b.isFunction(h)&&h.call(this.element[0],f,g)===false||f.isDefaultPrevented())}}})(jQuery);/*! * jQuery UI Mouse 1.8.18 * * Copyright 2011, AUTHORS.txt (http://jqueryui.com/about) @@ -50,7 +50,7 @@ * Depends: * jquery.ui.widget.js */ -(function(b,c){var a=false;b(document).mouseup(function(d){a=false});b.widget("ui.mouse",{options:{cancel:":input,option",distance:1,delay:0},_mouseInit:function(){var d=this;this.element.bind("mousedown."+this.widgetName,function(e){return d._mouseDown(e)}).bind("click."+this.widgetName,function(e){if(true===b.data(e.target,d.widgetName+".preventClickEvent")){b.removeData(e.target,d.widgetName+".preventClickEvent");e.stopImmediatePropagation();return false}});this.started=false},_mouseDestroy:function(){this.element.unbind("."+this.widgetName)},_mouseDown:function(f){if(a){return}(this._mouseStarted&&this._mouseUp(f));this._mouseDownEvent=f;var e=this,g=(f.which==1),d=(typeof this.options.cancel=="string"&&f.target.nodeName?b(f.target).closest(this.options.cancel).length:false);if(!g||d||!this._mouseCapture(f)){return true}this.mouseDelayMet=!this.options.delay;if(!this.mouseDelayMet){this._mouseDelayTimer=setTimeout(function(){e.mouseDelayMet=true},this.options.delay)}if(this._mouseDistanceMet(f)&&this._mouseDelayMet(f)){this._mouseStarted=(this._mouseStart(f)!==false);if(!this._mouseStarted){f.preventDefault();return true}}if(true===b.data(f.target,this.widgetName+".preventClickEvent")){b.removeData(f.target,this.widgetName+".preventClickEvent")}this._mouseMoveDelegate=function(h){return e._mouseMove(h)};this._mouseUpDelegate=function(h){return e._mouseUp(h)};b(document).bind("mousemove."+this.widgetName,this._mouseMoveDelegate).bind("mouseup."+this.widgetName,this._mouseUpDelegate);f.preventDefault();a=true;return true},_mouseMove:function(d){if(b.browser.msie&&!(document.documentMode>=9)&&!d.button){return this._mouseUp(d)}if(this._mouseStarted){this._mouseDrag(d);return d.preventDefault()}if(this._mouseDistanceMet(d)&&this._mouseDelayMet(d)){this._mouseStarted=(this._mouseStart(this._mouseDownEvent,d)!==false);(this._mouseStarted?this._mouseDrag(d):this._mouseUp(d))}return !this._mouseStarted},_mouseUp:function(d){b(document).unbind("mousemove."+this.widgetName,this._mouseMoveDelegate).unbind("mouseup."+this.widgetName,this._mouseUpDelegate);if(this._mouseStarted){this._mouseStarted=false;if(d.target==this._mouseDownEvent.target){b.data(d.target,this.widgetName+".preventClickEvent",true)}this._mouseStop(d)}return false},_mouseDistanceMet:function(d){return(Math.max(Math.abs(this._mouseDownEvent.pageX-d.pageX),Math.abs(this._mouseDownEvent.pageY-d.pageY))>=this.options.distance)},_mouseDelayMet:function(d){return this.mouseDelayMet},_mouseStart:function(d){},_mouseDrag:function(d){},_mouseStop:function(d){},_mouseCapture:function(d){return true}})})(jQuery);(function(c,d){c.widget("ui.resizable",c.ui.mouse,{widgetEventPrefix:"resize",options:{alsoResize:false,animate:false,animateDuration:"slow",animateEasing:"swing",aspectRatio:false,autoHide:false,containment:false,ghost:false,grid:false,handles:"e,s,se",helper:false,maxHeight:null,maxWidth:null,minHeight:10,minWidth:10,zIndex:1000},_create:function(){var f=this,k=this.options;this.element.addClass("ui-resizable");c.extend(this,{_aspectRatio:!!(k.aspectRatio),aspectRatio:k.aspectRatio,originalElement:this.element,_proportionallyResizeElements:[],_helper:k.helper||k.ghost||k.animate?k.helper||"ui-resizable-helper":null});if(this.element[0].nodeName.match(/canvas|textarea|input|select|button|img/i)){this.element.wrap(c('
').css({position:this.element.css("position"),width:this.element.outerWidth(),height:this.element.outerHeight(),top:this.element.css("top"),left:this.element.css("left")}));this.element=this.element.parent().data("resizable",this.element.data("resizable"));this.elementIsWrapper=true;this.element.css({marginLeft:this.originalElement.css("marginLeft"),marginTop:this.originalElement.css("marginTop"),marginRight:this.originalElement.css("marginRight"),marginBottom:this.originalElement.css("marginBottom")});this.originalElement.css({marginLeft:0,marginTop:0,marginRight:0,marginBottom:0});this.originalResizeStyle=this.originalElement.css("resize");this.originalElement.css("resize","none");this._proportionallyResizeElements.push(this.originalElement.css({position:"static",zoom:1,display:"block"}));this.originalElement.css({margin:this.originalElement.css("margin")});this._proportionallyResize()}this.handles=k.handles||(!c(".ui-resizable-handle",this.element).length?"e,s,se":{n:".ui-resizable-n",e:".ui-resizable-e",s:".ui-resizable-s",w:".ui-resizable-w",se:".ui-resizable-se",sw:".ui-resizable-sw",ne:".ui-resizable-ne",nw:".ui-resizable-nw"});if(this.handles.constructor==String){if(this.handles=="all"){this.handles="n,e,s,w,se,sw,ne,nw"}var l=this.handles.split(",");this.handles={};for(var g=0;g
');if(/sw|se|ne|nw/.test(j)){h.css({zIndex:++k.zIndex})}if("se"==j){h.addClass("ui-icon ui-icon-gripsmall-diagonal-se")}this.handles[j]=".ui-resizable-"+j;this.element.append(h)}}this._renderAxis=function(q){q=q||this.element;for(var n in this.handles){if(this.handles[n].constructor==String){this.handles[n]=c(this.handles[n],this.element).show()}if(this.elementIsWrapper&&this.originalElement[0].nodeName.match(/textarea|input|select|button/i)){var o=c(this.handles[n],this.element),p=0;p=/sw|ne|nw|se|n|s/.test(n)?o.outerHeight():o.outerWidth();var m=["padding",/ne|nw|n/.test(n)?"Top":/se|sw|s/.test(n)?"Bottom":/^e$/.test(n)?"Right":"Left"].join("");q.css(m,p);this._proportionallyResize()}if(!c(this.handles[n]).length){continue}}};this._renderAxis(this.element);this._handles=c(".ui-resizable-handle",this.element).disableSelection();this._handles.mouseover(function(){if(!f.resizing){if(this.className){var i=this.className.match(/ui-resizable-(se|sw|ne|nw|n|e|s|w)/i)}f.axis=i&&i[1]?i[1]:"se"}});if(k.autoHide){this._handles.hide();c(this.element).addClass("ui-resizable-autohide").hover(function(){if(k.disabled){return}c(this).removeClass("ui-resizable-autohide");f._handles.show()},function(){if(k.disabled){return}if(!f.resizing){c(this).addClass("ui-resizable-autohide");f._handles.hide()}})}this._mouseInit()},destroy:function(){this._mouseDestroy();var e=function(g){c(g).removeClass("ui-resizable ui-resizable-disabled ui-resizable-resizing").removeData("resizable").unbind(".resizable").find(".ui-resizable-handle").remove()};if(this.elementIsWrapper){e(this.element);var f=this.element;f.after(this.originalElement.css({position:f.css("position"),width:f.outerWidth(),height:f.outerHeight(),top:f.css("top"),left:f.css("left")})).remove()}this.originalElement.css("resize",this.originalResizeStyle);e(this.originalElement);return this},_mouseCapture:function(f){var g=false;for(var e in this.handles){if(c(this.handles[e])[0]==f.target){g=true}}return !this.options.disabled&&g},_mouseStart:function(g){var j=this.options,f=this.element.position(),e=this.element;this.resizing=true;this.documentScroll={top:c(document).scrollTop(),left:c(document).scrollLeft()};if(e.is(".ui-draggable")||(/absolute/).test(e.css("position"))){e.css({position:"absolute",top:f.top,left:f.left})}this._renderProxy();var k=b(this.helper.css("left")),h=b(this.helper.css("top"));if(j.containment){k+=c(j.containment).scrollLeft()||0;h+=c(j.containment).scrollTop()||0}this.offset=this.helper.offset();this.position={left:k,top:h};this.size=this._helper?{width:e.outerWidth(),height:e.outerHeight()}:{width:e.width(),height:e.height()};this.originalSize=this._helper?{width:e.outerWidth(),height:e.outerHeight()}:{width:e.width(),height:e.height()};this.originalPosition={left:k,top:h};this.sizeDiff={width:e.outerWidth()-e.width(),height:e.outerHeight()-e.height()};this.originalMousePosition={left:g.pageX,top:g.pageY};this.aspectRatio=(typeof j.aspectRatio=="number")?j.aspectRatio:((this.originalSize.width/this.originalSize.height)||1);var i=c(".ui-resizable-"+this.axis).css("cursor");c("body").css("cursor",i=="auto"?this.axis+"-resize":i);e.addClass("ui-resizable-resizing");this._propagate("start",g);return true},_mouseDrag:function(e){var h=this.helper,g=this.options,m={},q=this,j=this.originalMousePosition,n=this.axis;var r=(e.pageX-j.left)||0,p=(e.pageY-j.top)||0;var i=this._change[n];if(!i){return false}var l=i.apply(this,[e,r,p]),k=c.browser.msie&&c.browser.version<7,f=this.sizeDiff;this._updateVirtualBoundaries(e.shiftKey);if(this._aspectRatio||e.shiftKey){l=this._updateRatio(l,e)}l=this._respectSize(l,e);this._propagate("resize",e);h.css({top:this.position.top+"px",left:this.position.left+"px",width:this.size.width+"px",height:this.size.height+"px"});if(!this._helper&&this._proportionallyResizeElements.length){this._proportionallyResize()}this._updateCache(l);this._trigger("resize",e,this.ui());return false},_mouseStop:function(h){this.resizing=false;var i=this.options,m=this;if(this._helper){var g=this._proportionallyResizeElements,e=g.length&&(/textarea/i).test(g[0].nodeName),f=e&&c.ui.hasScroll(g[0],"left")?0:m.sizeDiff.height,k=e?0:m.sizeDiff.width;var n={width:(m.helper.width()-k),height:(m.helper.height()-f)},j=(parseInt(m.element.css("left"),10)+(m.position.left-m.originalPosition.left))||null,l=(parseInt(m.element.css("top"),10)+(m.position.top-m.originalPosition.top))||null;if(!i.animate){this.element.css(c.extend(n,{top:l,left:j}))}m.helper.height(m.size.height);m.helper.width(m.size.width);if(this._helper&&!i.animate){this._proportionallyResize()}}c("body").css("cursor","auto");this.element.removeClass("ui-resizable-resizing");this._propagate("stop",h);if(this._helper){this.helper.remove()}return false},_updateVirtualBoundaries:function(g){var j=this.options,i,h,f,k,e;e={minWidth:a(j.minWidth)?j.minWidth:0,maxWidth:a(j.maxWidth)?j.maxWidth:Infinity,minHeight:a(j.minHeight)?j.minHeight:0,maxHeight:a(j.maxHeight)?j.maxHeight:Infinity};if(this._aspectRatio||g){i=e.minHeight*this.aspectRatio;f=e.minWidth/this.aspectRatio;h=e.maxHeight*this.aspectRatio;k=e.maxWidth/this.aspectRatio;if(i>e.minWidth){e.minWidth=i}if(f>e.minHeight){e.minHeight=f}if(hl.width),s=a(l.height)&&i.minHeight&&(i.minHeight>l.height);if(h){l.width=i.minWidth}if(s){l.height=i.minHeight}if(t){l.width=i.maxWidth}if(m){l.height=i.maxHeight}var f=this.originalPosition.left+this.originalSize.width,p=this.position.top+this.size.height;var k=/sw|nw|w/.test(q),e=/nw|ne|n/.test(q);if(h&&k){l.left=f-i.minWidth}if(t&&k){l.left=f-i.maxWidth}if(s&&e){l.top=p-i.minHeight}if(m&&e){l.top=p-i.maxHeight}var n=!l.width&&!l.height;if(n&&!l.left&&l.top){l.top=null}else{if(n&&!l.top&&l.left){l.left=null}}return l},_proportionallyResize:function(){var k=this.options;if(!this._proportionallyResizeElements.length){return}var g=this.helper||this.element;for(var f=0;f');var e=c.browser.msie&&c.browser.version<7,g=(e?1:0),h=(e?2:-1);this.helper.addClass(this._helper).css({width:this.element.outerWidth()+h,height:this.element.outerHeight()+h,position:"absolute",left:this.elementOffset.left-g+"px",top:this.elementOffset.top-g+"px",zIndex:++i.zIndex});this.helper.appendTo("body").disableSelection()}else{this.helper=this.element}},_change:{e:function(g,f,e){return{width:this.originalSize.width+f}},w:function(h,f,e){var j=this.options,g=this.originalSize,i=this.originalPosition;return{left:i.left+f,width:g.width-f}},n:function(h,f,e){var j=this.options,g=this.originalSize,i=this.originalPosition;return{top:i.top+e,height:g.height-e}},s:function(g,f,e){return{height:this.originalSize.height+e}},se:function(g,f,e){return c.extend(this._change.s.apply(this,arguments),this._change.e.apply(this,[g,f,e]))},sw:function(g,f,e){return c.extend(this._change.s.apply(this,arguments),this._change.w.apply(this,[g,f,e]))},ne:function(g,f,e){return c.extend(this._change.n.apply(this,arguments),this._change.e.apply(this,[g,f,e]))},nw:function(g,f,e){return c.extend(this._change.n.apply(this,arguments),this._change.w.apply(this,[g,f,e]))}},_propagate:function(f,e){c.ui.plugin.call(this,f,[e,this.ui()]);(f!="resize"&&this._trigger(f,e,this.ui()))},plugins:{},ui:function(){return{originalElement:this.originalElement,element:this.element,helper:this.helper,position:this.position,size:this.size,originalSize:this.originalSize,originalPosition:this.originalPosition}}});c.extend(c.ui.resizable,{version:"1.8.18"});c.ui.plugin.add("resizable","alsoResize",{start:function(f,g){var e=c(this).data("resizable"),i=e.options;var h=function(j){c(j).each(function(){var k=c(this);k.data("resizable-alsoresize",{width:parseInt(k.width(),10),height:parseInt(k.height(),10),left:parseInt(k.css("left"),10),top:parseInt(k.css("top"),10)})})};if(typeof(i.alsoResize)=="object"&&!i.alsoResize.parentNode){if(i.alsoResize.length){i.alsoResize=i.alsoResize[0];h(i.alsoResize)}else{c.each(i.alsoResize,function(j){h(j)})}}else{h(i.alsoResize)}},resize:function(g,i){var f=c(this).data("resizable"),j=f.options,h=f.originalSize,l=f.originalPosition;var k={height:(f.size.height-h.height)||0,width:(f.size.width-h.width)||0,top:(f.position.top-l.top)||0,left:(f.position.left-l.left)||0},e=function(m,n){c(m).each(function(){var q=c(this),r=c(this).data("resizable-alsoresize"),p={},o=n&&n.length?n:q.parents(i.originalElement[0]).length?["width","height"]:["width","height","top","left"];c.each(o,function(s,u){var t=(r[u]||0)+(k[u]||0);if(t&&t>=0){p[u]=t||null}});q.css(p)})};if(typeof(j.alsoResize)=="object"&&!j.alsoResize.nodeType){c.each(j.alsoResize,function(m,n){e(m,n)})}else{e(j.alsoResize)}},stop:function(e,f){c(this).removeData("resizable-alsoresize")}});c.ui.plugin.add("resizable","animate",{stop:function(i,n){var p=c(this).data("resizable"),j=p.options;var h=p._proportionallyResizeElements,e=h.length&&(/textarea/i).test(h[0].nodeName),f=e&&c.ui.hasScroll(h[0],"left")?0:p.sizeDiff.height,l=e?0:p.sizeDiff.width;var g={width:(p.size.width-l),height:(p.size.height-f)},k=(parseInt(p.element.css("left"),10)+(p.position.left-p.originalPosition.left))||null,m=(parseInt(p.element.css("top"),10)+(p.position.top-p.originalPosition.top))||null;p.element.animate(c.extend(g,m&&k?{top:m,left:k}:{}),{duration:j.animateDuration,easing:j.animateEasing,step:function(){var o={width:parseInt(p.element.css("width"),10),height:parseInt(p.element.css("height"),10),top:parseInt(p.element.css("top"),10),left:parseInt(p.element.css("left"),10)};if(h&&h.length){c(h[0]).css({width:o.width,height:o.height})}p._updateCache(o);p._propagate("resize",i)}})}});c.ui.plugin.add("resizable","containment",{start:function(f,r){var t=c(this).data("resizable"),j=t.options,l=t.element;var g=j.containment,k=(g instanceof c)?g.get(0):(/parent/.test(g))?l.parent().get(0):g;if(!k){return}t.containerElement=c(k);if(/document/.test(g)||g==document){t.containerOffset={left:0,top:0};t.containerPosition={left:0,top:0};t.parentData={element:c(document),left:0,top:0,width:c(document).width(),height:c(document).height()||document.body.parentNode.scrollHeight}}else{var n=c(k),i=[];c(["Top","Right","Left","Bottom"]).each(function(p,o){i[p]=b(n.css("padding"+o))});t.containerOffset=n.offset();t.containerPosition=n.position();t.containerSize={height:(n.innerHeight()-i[3]),width:(n.innerWidth()-i[1])};var q=t.containerOffset,e=t.containerSize.height,m=t.containerSize.width,h=(c.ui.hasScroll(k,"left")?k.scrollWidth:m),s=(c.ui.hasScroll(k)?k.scrollHeight:e);t.parentData={element:k,left:q.left,top:q.top,width:h,height:s}}},resize:function(g,q){var t=c(this).data("resizable"),i=t.options,f=t.containerSize,p=t.containerOffset,m=t.size,n=t.position,r=t._aspectRatio||g.shiftKey,e={top:0,left:0},h=t.containerElement;if(h[0]!=document&&(/static/).test(h.css("position"))){e=p}if(n.left<(t._helper?p.left:0)){t.size.width=t.size.width+(t._helper?(t.position.left-p.left):(t.position.left-e.left));if(r){t.size.height=t.size.width/i.aspectRatio}t.position.left=i.helper?p.left:0}if(n.top<(t._helper?p.top:0)){t.size.height=t.size.height+(t._helper?(t.position.top-p.top):t.position.top);if(r){t.size.width=t.size.height*i.aspectRatio}t.position.top=t._helper?p.top:0}t.offset.left=t.parentData.left+t.position.left;t.offset.top=t.parentData.top+t.position.top;var l=Math.abs((t._helper?t.offset.left-e.left:(t.offset.left-e.left))+t.sizeDiff.width),s=Math.abs((t._helper?t.offset.top-e.top:(t.offset.top-p.top))+t.sizeDiff.height);var k=t.containerElement.get(0)==t.element.parent().get(0),j=/relative|absolute/.test(t.containerElement.css("position"));if(k&&j){l-=t.parentData.left}if(l+t.size.width>=t.parentData.width){t.size.width=t.parentData.width-l;if(r){t.size.height=t.size.width/t.aspectRatio}}if(s+t.size.height>=t.parentData.height){t.size.height=t.parentData.height-s;if(r){t.size.width=t.size.height*t.aspectRatio}}},stop:function(f,n){var q=c(this).data("resizable"),g=q.options,l=q.position,m=q.containerOffset,e=q.containerPosition,i=q.containerElement;var j=c(q.helper),r=j.offset(),p=j.outerWidth()-q.sizeDiff.width,k=j.outerHeight()-q.sizeDiff.height;if(q._helper&&!g.animate&&(/relative/).test(i.css("position"))){c(this).css({left:r.left-e.left-m.left,width:p,height:k})}if(q._helper&&!g.animate&&(/static/).test(i.css("position"))){c(this).css({left:r.left-e.left-m.left,width:p,height:k})}}});c.ui.plugin.add("resizable","ghost",{start:function(g,h){var e=c(this).data("resizable"),i=e.options,f=e.size;e.ghost=e.originalElement.clone();e.ghost.css({opacity:0.25,display:"block",position:"relative",height:f.height,width:f.width,margin:0,left:0,top:0}).addClass("ui-resizable-ghost").addClass(typeof i.ghost=="string"?i.ghost:"");e.ghost.appendTo(e.helper)},resize:function(f,g){var e=c(this).data("resizable"),h=e.options;if(e.ghost){e.ghost.css({position:"relative",height:e.size.height,width:e.size.width})}},stop:function(f,g){var e=c(this).data("resizable"),h=e.options;if(e.ghost&&e.helper){e.helper.get(0).removeChild(e.ghost.get(0))}}});c.ui.plugin.add("resizable","grid",{resize:function(e,m){var p=c(this).data("resizable"),h=p.options,k=p.size,i=p.originalSize,j=p.originalPosition,n=p.axis,l=h._aspectRatio||e.shiftKey;h.grid=typeof h.grid=="number"?[h.grid,h.grid]:h.grid;var g=Math.round((k.width-i.width)/(h.grid[0]||1))*(h.grid[0]||1),f=Math.round((k.height-i.height)/(h.grid[1]||1))*(h.grid[1]||1);if(/^(se|s|e)$/.test(n)){p.size.width=i.width+g;p.size.height=i.height+f}else{if(/^(ne)$/.test(n)){p.size.width=i.width+g;p.size.height=i.height+f;p.position.top=j.top-f}else{if(/^(sw)$/.test(n)){p.size.width=i.width+g;p.size.height=i.height+f;p.position.left=j.left-g}else{p.size.width=i.width+g;p.size.height=i.height+f;p.position.top=j.top-f;p.position.left=j.left-g}}}}});var b=function(e){return parseInt(e,10)||0};var a=function(e){return !isNaN(parseInt(e,10))}})(jQuery);/* +(function(b,c){var a=false;b(document).mouseup(function(d){a=false});b.widget("ui.mouse",{options:{cancel:":input,option",distance:1,delay:0},_mouseInit:function(){var d=this;this.element.bind("mousedown."+this.widgetName,function(e){return d._mouseDown(e)}).bind("click."+this.widgetName,function(e){if(true===b.data(e.target,d.widgetName+".preventClickEvent")){b.removeData(e.target,d.widgetName+".preventClickEvent");e.stopImmediatePropagation();return false}});this.started=false},_mouseDestroy:function(){this.element.unbind("."+this.widgetName)},_mouseDown:function(f){if(a){return}(this._mouseStarted&&this._mouseUp(f));this._mouseDownEvent=f;var e=this,g=(f.which==1),d=(typeof this.options.cancel=="string"&&f.target.nodeName?b(f.target).closest(this.options.cancel).length:false);if(!g||d||!this._mouseCapture(f)){return true}this.mouseDelayMet=!this.options.delay;if(!this.mouseDelayMet){this._mouseDelayTimer=setTimeout(function(){e.mouseDelayMet=true},this.options.delay)}if(this._mouseDistanceMet(f)&&this._mouseDelayMet(f)){this._mouseStarted=(this._mouseStart(f)!==false);if(!this._mouseStarted){f.preventDefault();return true}}if(true===b.data(f.target,this.widgetName+".preventClickEvent")){b.removeData(f.target,this.widgetName+".preventClickEvent")}this._mouseMoveDelegate=function(h){return e._mouseMove(h)};this._mouseUpDelegate=function(h){return e._mouseUp(h)};b(document).bind("mousemove."+this.widgetName,this._mouseMoveDelegate).bind("mouseup."+this.widgetName,this._mouseUpDelegate);f.preventDefault();a=true;return true},_mouseMove:function(d){if(b.browser.msie&&!(document.documentMode>=9)&&!d.button){return this._mouseUp(d)}if(this._mouseStarted){this._mouseDrag(d);return d.preventDefault()}if(this._mouseDistanceMet(d)&&this._mouseDelayMet(d)){this._mouseStarted=(this._mouseStart(this._mouseDownEvent,d)!==false);(this._mouseStarted?this._mouseDrag(d):this._mouseUp(d))}return !this._mouseStarted},_mouseUp:function(d){b(document).unbind("mousemove."+this.widgetName,this._mouseMoveDelegate).unbind("mouseup."+this.widgetName,this._mouseUpDelegate);if(this._mouseStarted){this._mouseStarted=false;if(d.target==this._mouseDownEvent.target){b.data(d.target,this.widgetName+".preventClickEvent",true)}this._mouseStop(d)}return false},_mouseDistanceMet:function(d){return(Math.max(Math.abs(this._mouseDownEvent.pageX-d.pageX),Math.abs(this._mouseDownEvent.pageY-d.pageY))>=this.options.distance)},_mouseDelayMet:function(d){return this.mouseDelayMet},_mouseStart:function(d){},_mouseDrag:function(d){},_mouseStop:function(d){},_mouseCapture:function(d){return true}})})(jQuery);(function(c,d){c.widget("ui.resizable",c.ui.mouse,{widgetEventPrefix:"resize",options:{alsoResize:false,animate:false,animateDuration:"slow",animateEasing:"swing",aspectRatio:false,autoHide:false,containment:false,ghost:false,grid:false,handles:"e,s,se",helper:false,maxHeight:null,maxWidth:null,minHeight:10,minWidth:10,zIndex:1000},_create:function(){var f=this,k=this.options;this.element.addClass("ui-resizable");c.extend(this,{_aspectRatio:!!(k.aspectRatio),aspectRatio:k.aspectRatio,originalElement:this.element,_proportionallyResizeElements:[],_helper:k.helper||k.ghost||k.animate?k.helper||"ui-resizable-helper":null});if(this.element[0].nodeName.match(/canvas|textarea|input|select|button|img/i)){this.element.wrap(c('
').css({position:this.element.css("position"),width:this.element.outerWidth(),height:this.element.outerHeight(),top:this.element.css("top"),left:this.element.css("left")}));this.element=this.element.parent().data("resizable",this.element.data("resizable"));this.elementIsWrapper=true;this.element.css({marginLeft:this.originalElement.css("marginLeft"),marginTop:this.originalElement.css("marginTop"),marginRight:this.originalElement.css("marginRight"),marginBottom:this.originalElement.css("marginBottom")});this.originalElement.css({marginLeft:0,marginTop:0,marginRight:0,marginBottom:0});this.originalResizeStyle=this.originalElement.css("resize");this.originalElement.css("resize","none");this._proportionallyResizeElements.push(this.originalElement.css({position:"static",zoom:1,display:"block"}));this.originalElement.css({margin:this.originalElement.css("margin")});this._proportionallyResize()}this.handles=k.handles||(!c(".ui-resizable-handle",this.element).length?"e,s,se":{n:".ui-resizable-n",e:".ui-resizable-e",s:".ui-resizable-s",w:".ui-resizable-w",se:".ui-resizable-se",sw:".ui-resizable-sw",ne:".ui-resizable-ne",nw:".ui-resizable-nw"});if(this.handles.constructor==String){if(this.handles=="all"){this.handles="n,e,s,w,se,sw,ne,nw"}var l=this.handles.split(",");this.handles={};for(var g=0;g');if(/sw|se|ne|nw/.test(j)){h.css({zIndex:++k.zIndex})}if("se"==j){h.addClass("ui-icon ui-icon-gripsmall-diagonal-se")}this.handles[j]=".ui-resizable-"+j;this.element.append(h)}}this._renderAxis=function(q){q=q||this.element;for(var n in this.handles){if(this.handles[n].constructor==String){this.handles[n]=c(this.handles[n],this.element).show()}if(this.elementIsWrapper&&this.originalElement[0].nodeName.match(/textarea|input|select|button/i)){var o=c(this.handles[n],this.element),p=0;p=/sw|ne|nw|se|n|s/.test(n)?o.outerHeight():o.outerWidth();var m=["padding",/ne|nw|n/.test(n)?"Top":/se|sw|s/.test(n)?"Bottom":/^e$/.test(n)?"Right":"Left"].join("");q.css(m,p);this._proportionallyResize()}if(!c(this.handles[n]).length){continue}}};this._renderAxis(this.element);this._handles=c(".ui-resizable-handle",this.element).disableSelection();this._handles.mouseover(function(){if(!f.resizing){if(this.className){var i=this.className.match(/ui-resizable-(se|sw|ne|nw|n|e|s|w)/i)}f.axis=i&&i[1]?i[1]:"se"}});if(k.autoHide){this._handles.hide();c(this.element).addClass("ui-resizable-autohide").hover(function(){if(k.disabled){return}c(this).removeClass("ui-resizable-autohide");f._handles.show()},function(){if(k.disabled){return}if(!f.resizing){c(this).addClass("ui-resizable-autohide");f._handles.hide()}})}this._mouseInit()},destroy:function(){this._mouseDestroy();var e=function(g){c(g).removeClass("ui-resizable ui-resizable-disabled ui-resizable-resizing").removeData("resizable").unbind(".resizable").find(".ui-resizable-handle").remove()};if(this.elementIsWrapper){e(this.element);var f=this.element;f.after(this.originalElement.css({position:f.css("position"),width:f.outerWidth(),height:f.outerHeight(),top:f.css("top"),left:f.css("left")})).remove()}this.originalElement.css("resize",this.originalResizeStyle);e(this.originalElement);return this},_mouseCapture:function(f){var g=false;for(var e in this.handles){if(c(this.handles[e])[0]==f.target){g=true}}return !this.options.disabled&&g},_mouseStart:function(g){var j=this.options,f=this.element.position(),e=this.element;this.resizing=true;this.documentScroll={top:c(document).scrollTop(),left:c(document).scrollLeft()};if(e.is(".ui-draggable")||(/absolute/).test(e.css("position"))){e.css({position:"absolute",top:f.top,left:f.left})}this._renderProxy();var k=b(this.helper.css("left")),h=b(this.helper.css("top"));if(j.containment){k+=c(j.containment).scrollLeft()||0;h+=c(j.containment).scrollTop()||0}this.offset=this.helper.offset();this.position={left:k,top:h};this.size=this._helper?{width:e.outerWidth(),height:e.outerHeight()}:{width:e.width(),height:e.height()};this.originalSize=this._helper?{width:e.outerWidth(),height:e.outerHeight()}:{width:e.width(),height:e.height()};this.originalPosition={left:k,top:h};this.sizeDiff={width:e.outerWidth()-e.width(),height:e.outerHeight()-e.height()};this.originalMousePosition={left:g.pageX,top:g.pageY};this.aspectRatio=(typeof j.aspectRatio=="number")?j.aspectRatio:((this.originalSize.width/this.originalSize.height)||1);var i=c(".ui-resizable-"+this.axis).css("cursor");c("body").css("cursor",i=="auto"?this.axis+"-resize":i);e.addClass("ui-resizable-resizing");this._propagate("start",g);return true},_mouseDrag:function(e){var h=this.helper,g=this.options,m={},q=this,j=this.originalMousePosition,n=this.axis;var r=(e.pageX-j.left)||0,p=(e.pageY-j.top)||0;var i=this._change[n];if(!i){return false}var l=i.apply(this,[e,r,p]),k=c.browser.msie&&c.browser.version<7,f=this.sizeDiff;this._updateVirtualBoundaries(e.shiftKey);if(this._aspectRatio||e.shiftKey){l=this._updateRatio(l,e)}l=this._respectSize(l,e);this._propagate("resize",e);h.css({top:this.position.top+"px",left:this.position.left+"px",width:this.size.width+"px",height:this.size.height+"px"});if(!this._helper&&this._proportionallyResizeElements.length){this._proportionallyResize()}this._updateCache(l);this._trigger("resize",e,this.ui());return false},_mouseStop:function(h){this.resizing=false;var i=this.options,m=this;if(this._helper){var g=this._proportionallyResizeElements,e=g.length&&(/textarea/i).test(g[0].nodeName),f=e&&c.ui.hasScroll(g[0],"left")?0:m.sizeDiff.height,k=e?0:m.sizeDiff.width;var n={width:(m.helper.width()-k),height:(m.helper.height()-f)},j=(parseInt(m.element.css("left"),10)+(m.position.left-m.originalPosition.left))||null,l=(parseInt(m.element.css("top"),10)+(m.position.top-m.originalPosition.top))||null;if(!i.animate){this.element.css(c.extend(n,{top:l,left:j}))}m.helper.height(m.size.height);m.helper.width(m.size.width);if(this._helper&&!i.animate){this._proportionallyResize()}}c("body").css("cursor","auto");this.element.removeClass("ui-resizable-resizing");this._propagate("stop",h);if(this._helper){this.helper.remove()}return false},_updateVirtualBoundaries:function(g){var j=this.options,i,h,f,k,e;e={minWidth:a(j.minWidth)?j.minWidth:0,maxWidth:a(j.maxWidth)?j.maxWidth:Infinity,minHeight:a(j.minHeight)?j.minHeight:0,maxHeight:a(j.maxHeight)?j.maxHeight:Infinity};if(this._aspectRatio||g){i=e.minHeight*this.aspectRatio;f=e.minWidth/this.aspectRatio;h=e.maxHeight*this.aspectRatio;k=e.maxWidth/this.aspectRatio;if(i>e.minWidth){e.minWidth=i}if(f>e.minHeight){e.minHeight=f}if(hl.width),s=a(l.height)&&i.minHeight&&(i.minHeight>l.height);if(h){l.width=i.minWidth}if(s){l.height=i.minHeight}if(t){l.width=i.maxWidth}if(m){l.height=i.maxHeight}var f=this.originalPosition.left+this.originalSize.width,p=this.position.top+this.size.height;var k=/sw|nw|w/.test(q),e=/nw|ne|n/.test(q);if(h&&k){l.left=f-i.minWidth}if(t&&k){l.left=f-i.maxWidth}if(s&&e){l.top=p-i.minHeight}if(m&&e){l.top=p-i.maxHeight}var n=!l.width&&!l.height;if(n&&!l.left&&l.top){l.top=null}else{if(n&&!l.top&&l.left){l.left=null}}return l},_proportionallyResize:function(){var k=this.options;if(!this._proportionallyResizeElements.length){return}var g=this.helper||this.element;for(var f=0;f');var e=c.browser.msie&&c.browser.version<7,g=(e?1:0),h=(e?2:-1);this.helper.addClass(this._helper).css({width:this.element.outerWidth()+h,height:this.element.outerHeight()+h,position:"absolute",left:this.elementOffset.left-g+"px",top:this.elementOffset.top-g+"px",zIndex:++i.zIndex});this.helper.appendTo("body").disableSelection()}else{this.helper=this.element}},_change:{e:function(g,f,e){return{width:this.originalSize.width+f}},w:function(h,f,e){var j=this.options,g=this.originalSize,i=this.originalPosition;return{left:i.left+f,width:g.width-f}},n:function(h,f,e){var j=this.options,g=this.originalSize,i=this.originalPosition;return{top:i.top+e,height:g.height-e}},s:function(g,f,e){return{height:this.originalSize.height+e}},se:function(g,f,e){return c.extend(this._change.s.apply(this,arguments),this._change.e.apply(this,[g,f,e]))},sw:function(g,f,e){return c.extend(this._change.s.apply(this,arguments),this._change.w.apply(this,[g,f,e]))},ne:function(g,f,e){return c.extend(this._change.n.apply(this,arguments),this._change.e.apply(this,[g,f,e]))},nw:function(g,f,e){return c.extend(this._change.n.apply(this,arguments),this._change.w.apply(this,[g,f,e]))}},_propagate:function(f,e){c.ui.plugin.call(this,f,[e,this.ui()]);(f!="resize"&&this._trigger(f,e,this.ui()))},plugins:{},ui:function(){return{originalElement:this.originalElement,element:this.element,helper:this.helper,position:this.position,size:this.size,originalSize:this.originalSize,originalPosition:this.originalPosition}}});c.extend(c.ui.resizable,{version:"1.8.18"});c.ui.plugin.add("resizable","alsoResize",{start:function(f,g){var e=c(this).data("resizable"),i=e.options;var h=function(j){c(j).each(function(){var k=c(this);k.data("resizable-alsoresize",{width:parseInt(k.width(),10),height:parseInt(k.height(),10),left:parseInt(k.css("left"),10),top:parseInt(k.css("top"),10)})})};if(typeof(i.alsoResize)=="object"&&!i.alsoResize.parentNode){if(i.alsoResize.length){i.alsoResize=i.alsoResize[0];h(i.alsoResize)}else{c.each(i.alsoResize,function(j){h(j)})}}else{h(i.alsoResize)}},resize:function(g,i){var f=c(this).data("resizable"),j=f.options,h=f.originalSize,l=f.originalPosition;var k={height:(f.size.height-h.height)||0,width:(f.size.width-h.width)||0,top:(f.position.top-l.top)||0,left:(f.position.left-l.left)||0},e=function(m,n){c(m).each(function(){var q=c(this),r=c(this).data("resizable-alsoresize"),p={},o=n&&n.length?n:q.parents(i.originalElement[0]).length?["width","height"]:["width","height","top","left"];c.each(o,function(s,u){var t=(r[u]||0)+(k[u]||0);if(t&&t>=0){p[u]=t||null}});q.css(p)})};if(typeof(j.alsoResize)=="object"&&!j.alsoResize.nodeType){c.each(j.alsoResize,function(m,n){e(m,n)})}else{e(j.alsoResize)}},stop:function(e,f){c(this).removeData("resizable-alsoresize")}});c.ui.plugin.add("resizable","animate",{stop:function(i,n){var p=c(this).data("resizable"),j=p.options;var h=p._proportionallyResizeElements,e=h.length&&(/textarea/i).test(h[0].nodeName),f=e&&c.ui.hasScroll(h[0],"left")?0:p.sizeDiff.height,l=e?0:p.sizeDiff.width;var g={width:(p.size.width-l),height:(p.size.height-f)},k=(parseInt(p.element.css("left"),10)+(p.position.left-p.originalPosition.left))||null,m=(parseInt(p.element.css("top"),10)+(p.position.top-p.originalPosition.top))||null;p.element.animate(c.extend(g,m&&k?{top:m,left:k}:{}),{duration:j.animateDuration,easing:j.animateEasing,step:function(){var o={width:parseInt(p.element.css("width"),10),height:parseInt(p.element.css("height"),10),top:parseInt(p.element.css("top"),10),left:parseInt(p.element.css("left"),10)};if(h&&h.length){c(h[0]).css({width:o.width,height:o.height})}p._updateCache(o);p._propagate("resize",i)}})}});c.ui.plugin.add("resizable","containment",{start:function(f,r){var t=c(this).data("resizable"),j=t.options,l=t.element;var g=j.containment,k=(g instanceof c)?g.get(0):(/parent/.test(g))?l.parent().get(0):g;if(!k){return}t.containerElement=c(k);if(/document/.test(g)||g==document){t.containerOffset={left:0,top:0};t.containerPosition={left:0,top:0};t.parentData={element:c(document),left:0,top:0,width:c(document).width(),height:c(document).height()||document.body.parentNode.scrollHeight}}else{var n=c(k),i=[];c(["Top","Right","Left","Bottom"]).each(function(p,o){i[p]=b(n.css("padding"+o))});t.containerOffset=n.offset();t.containerPosition=n.position();t.containerSize={height:(n.innerHeight()-i[3]),width:(n.innerWidth()-i[1])};var q=t.containerOffset,e=t.containerSize.height,m=t.containerSize.width,h=(c.ui.hasScroll(k,"left")?k.scrollWidth:m),s=(c.ui.hasScroll(k)?k.scrollHeight:e);t.parentData={element:k,left:q.left,top:q.top,width:h,height:s}}},resize:function(g,q){var t=c(this).data("resizable"),i=t.options,f=t.containerSize,p=t.containerOffset,m=t.size,n=t.position,r=t._aspectRatio||g.shiftKey,e={top:0,left:0},h=t.containerElement;if(h[0]!=document&&(/static/).test(h.css("position"))){e=p}if(n.left<(t._helper?p.left:0)){t.size.width=t.size.width+(t._helper?(t.position.left-p.left):(t.position.left-e.left));if(r){t.size.height=t.size.width/i.aspectRatio}t.position.left=i.helper?p.left:0}if(n.top<(t._helper?p.top:0)){t.size.height=t.size.height+(t._helper?(t.position.top-p.top):t.position.top);if(r){t.size.width=t.size.height*i.aspectRatio}t.position.top=t._helper?p.top:0}t.offset.left=t.parentData.left+t.position.left;t.offset.top=t.parentData.top+t.position.top;var l=Math.abs((t._helper?t.offset.left-e.left:(t.offset.left-e.left))+t.sizeDiff.width),s=Math.abs((t._helper?t.offset.top-e.top:(t.offset.top-p.top))+t.sizeDiff.height);var k=t.containerElement.get(0)==t.element.parent().get(0),j=/relative|absolute/.test(t.containerElement.css("position"));if(k&&j){l-=t.parentData.left}if(l+t.size.width>=t.parentData.width){t.size.width=t.parentData.width-l;if(r){t.size.height=t.size.width/t.aspectRatio}}if(s+t.size.height>=t.parentData.height){t.size.height=t.parentData.height-s;if(r){t.size.width=t.size.height*t.aspectRatio}}},stop:function(f,n){var q=c(this).data("resizable"),g=q.options,l=q.position,m=q.containerOffset,e=q.containerPosition,i=q.containerElement;var j=c(q.helper),r=j.offset(),p=j.outerWidth()-q.sizeDiff.width,k=j.outerHeight()-q.sizeDiff.height;if(q._helper&&!g.animate&&(/relative/).test(i.css("position"))){c(this).css({left:r.left-e.left-m.left,width:p,height:k})}if(q._helper&&!g.animate&&(/static/).test(i.css("position"))){c(this).css({left:r.left-e.left-m.left,width:p,height:k})}}});c.ui.plugin.add("resizable","ghost",{start:function(g,h){var e=c(this).data("resizable"),i=e.options,f=e.size;e.ghost=e.originalElement.clone();e.ghost.css({opacity:0.25,display:"block",position:"relative",height:f.height,width:f.width,margin:0,left:0,top:0}).addClass("ui-resizable-ghost").addClass(typeof i.ghost=="string"?i.ghost:"");e.ghost.appendTo(e.helper)},resize:function(f,g){var e=c(this).data("resizable"),h=e.options;if(e.ghost){e.ghost.css({position:"relative",height:e.size.height,width:e.size.width})}},stop:function(f,g){var e=c(this).data("resizable"),h=e.options;if(e.ghost&&e.helper){e.helper.get(0).removeChild(e.ghost.get(0))}}});c.ui.plugin.add("resizable","grid",{resize:function(e,m){var p=c(this).data("resizable"),h=p.options,k=p.size,i=p.originalSize,j=p.originalPosition,n=p.axis,l=h._aspectRatio||e.shiftKey;h.grid=typeof h.grid=="number"?[h.grid,h.grid]:h.grid;var g=Math.round((k.width-i.width)/(h.grid[0]||1))*(h.grid[0]||1),f=Math.round((k.height-i.height)/(h.grid[1]||1))*(h.grid[1]||1);if(/^(se|s|e)$/.test(n)){p.size.width=i.width+g;p.size.height=i.height+f}else{if(/^(ne)$/.test(n)){p.size.width=i.width+g;p.size.height=i.height+f;p.position.top=j.top-f}else{if(/^(sw)$/.test(n)){p.size.width=i.width+g;p.size.height=i.height+f;p.position.left=j.left-g}else{p.size.width=i.width+g;p.size.height=i.height+f;p.position.top=j.top-f;p.position.left=j.left-g}}}}});var b=function(e){return parseInt(e,10)||0};var a=function(e){return !isNaN(parseInt(e,10))}})(jQuery);/*! * jQuery hashchange event - v1.3 - 7/21/2010 * http://benalman.com/projects/jquery-hashchange-plugin/ * @@ -58,11 +58,30 @@ * Dual licensed under the MIT and GPL licenses. * http://benalman.com/about/license/ */ -(function($,e,b){var c="hashchange",h=document,f,g=$.event.special,i=h.documentMode,d="on"+c in e&&(i===b||i>7);function a(j){j=j||location.href;return"#"+j.replace(/^[^#]*#?(.*)$/,"$1")}$.fn[c]=function(j){return j?this.bind(c,j):this.trigger(c)};$.fn[c].delay=50;g[c]=$.extend(g[c],{setup:function(){if(d){return false}$(f.start)},teardown:function(){if(d){return false}$(f.stop)}});f=(function(){var j={},p,m=a(),k=function(q){return q},l=k,o=k;j.start=function(){p||n()};j.stop=function(){p&&clearTimeout(p);p=b};function n(){var r=a(),q=o(m);if(r!==m){l(m=r,q);$(e).trigger(c)}else{if(q!==m){location.href=location.href.replace(/#.*/,"")+q}}p=setTimeout(n,$.fn[c].delay)}$.browser.msie&&!d&&(function(){var q,r;j.start=function(){if(!q){r=$.fn[c].src;r=r&&r+a();q=$(' + + +
+
+
Angle-scan processing
+
+
+ +

+Introduction

+

This page describes the data processing steps of angle-scans using the PEARL Procedures. The description relies on using the command line regardless of available GUIs.

+

+Data reduction

+

The goal of this step is to import raw data and at the same time eliminate the energy dimension. We want a two-dimensional wave where the first dimension is the angle axis of the detector and the second dimension is the sequence of measurements, scanning one or multiple manipulator angles. The second dimension requires additional one-dimensional waves that describe the polar, tilt and azimuthal angle setting of the manipulator for each dimension index.

+

The processing steps depend on the complexity of the measured spectrum. The user may have to adopt one of the predefined or a custom procedure accordingly. Here, we describe two procedures that may cover many generic cases or that can serve as a starting point for a refined, customized procedure. However, any procedure that produces the datasets mentioned above is, of course, a valid approach. For instance, you could load the complete three-dimensional ScientaImage dataset, and generate the two-dimensional dataset using your own procedures.

+

+Basic steps

+

The central import functions are psh5_load_reduced and psh5_load_dataset_reduced. The first form is sufficient if the file contains just one scan and region. Further regions/scans need to be loaded using the second form. The first form is also exposed in the PEARL data explorer window.

+

The functions require a data reduction function and processing parameters as arguments. Some particular reduction functions are described further below. More can be found in the source code (or obtained from other users). A list of functions that look like reduction functions can be got from adh5_list_reduction_funcs.

+

The basic call sequence looks as follows. Substitute the arguments in angle brackets as necessary. You may have to analyse a reference spectrum or the complete ScientaImage to figure out the processing parameters beforehand.

+

First form:

+
setdatafolder root:
string sparam
sparam = "<param1=1.5;param2=test;>"
psh5_load_reduced("<igor-datafolder>", "<igor-filepath>", "<filename>", <reduction_function>, sparam)

Second form:

+
// open the file
setdatafolder root: // or other parent folder
variable fid
string sparam
fid = psh5_open_file("<igor-datafolder>", "<igor-filepath>", "<filename>")
// load metadata for scaling
psh5_load_scan_meta(fileID, "<scan 1>")
newdatafolder /s /o attr
psh5_load_scan_attrs(fileID, "<scan 1>")
setdatafolder ::
// load and reduce dataset
sparam = "<param1=1.5;param2=test;>"
psh5_load_dataset_reduced(fid, "<scan 1/region1>", "<ScientaImage>", <reduction_function>, sparam)
// close the file
psh5_close_file(fid)
fid = 0

+Peak integration over linear background

+

The int_linbg_reduction function converts a two-dimensional Scienta image I(angle, energy) into a one-dimensional angle distribution I(angle). For each angle slice, it calculates a linear background. Then, it integrates the difference between the original data and the background over a specified interval.

+

The function requires the following, fixed parameters:

+
+ + + + + + + + + + + + + + +
Parameter Description Typical value
Lcrop size of the low-energy cropping region 0.11 (fixed mode)
Lsize size of the low-energy background region 0.2
Hcrop size of the high-energy cropping region 0.11
Hsize size of the high-energy background region 0.2
Cpos position of the peak center 0.5
Csize size of the center region 0.3
+

All parameters are relative to the size of the image (length of the energy interval) and must be in the range from 0 to 1.

+

The cropping region is cut away from the image for the rest of the processing. This is necessary to remove the dark corners in fixed mode but can be neglected in swept mode (cropping size = 0).

+

The low and high background regions are adjacent to the cropping regions on either side. The function calculates two fix points of the linear background in the center of each background region. The intensity value of each fix point is the average intensity in the background region.

+

The peak region is integrated over the integral given by the Csize parameter centered at Cpos.

+

The background-subtracted peak integral is returned in ReducedData1. ReducedData2 receives the error estimate of the peak integral (assuming Poisson statistics).

+

+Peak fitting

+

The gauss4_reduction function converts a two-dimensional Scienta image I(angle, energy) into a one-dimensional angle distribution I(angle). For each angle slice, it performs a Gaussian curve fit with up to four components on a linear background.

+

To improve the stability of the fit, the peak positions and widths are kept fixed while the amplitudes of the peaks and the background parameters are variable but constrained to reasonable values (positive amplitude). Furthermore, the function can optionally do a box averaging over three slices.

+

The function requires the following, fixed parameters:

+ + + + + + + + + + + + + + + + + + + + + + + + + + + +
Parameter Description
rngl lower limit of the fit interval
rngh upper limit of the fit interval
npeaks number of components
pos1 center energy of peak 1
wid1 width of peak 1
pos2 center energy of peak 2
wid2 width of peak 2
pos3 center energy of peak 3
wid3 width of peak 3
pos4 center energy of peak 3
wid4 width of peak 3
ybox box size of slice averaging (1 or 3)
+

The peak parameters should be determined beforehand from fitting a reference spectrum, or the angle-scan integrated over all angles. Peak positions and widths have to be specified only up to the given number of peaks.

+

The data reduction procedure returns the peak integrals (amplitude times width times square root of 2) in waves named ReducedDataN where N is a numeric index from 1 to npeaks. The waves starting with an index of npeaks+1 contain the corresponding error estimate of the peak integral.

+

+Custom reduction functions

+

See the documentation and source code of int_linbg_reduction, gauss4_reduction and adh5_default_reduction for help on writing custom reduction functions. To integrate your function with the PEARL data explorer, you have to provide an additional function that prompts for reduction parameters such as prompt_int_linbg_reduction, for example. Since reduction functions cannot be called from the command line, it is redommended to also write an adapter function for testing.

+

+Normalization

+

The goal of the data normalization is to get a (still two-dimensional) dataset that ideally contains intensity variations due to diffraction features and statistical fluctuations only. In particular, instrumental variations should be removed. In some cases, it may be necessary to preserve the overall polar dependence of the intensity. Note that this latter case is not properly treated with the methods described here.

+

Depending on the quality of the measured data, only some of the following processing steps are necessary. Use your own judgement.

+

+Preparations

+

Start by creating a new copy of the data and inspecting it:

duplicate ReducedData1, NormData1
ad_display_profiles(NormData1)

To update the display after changes to NormData1:

ad_update_profiles(NormData1)

+Detector angle range

+

Crop the detector angle axis to a useful range (usually about -25 to +25 degrees):

crop_strip(NormData1, -25, 25)

+Normalize detector angle

+

Remove inhomogeneity of the detector in the detector angle axis. This component may also include a contribution from the sample. If your raw data shows a flat distribution, this step is not necessary.

+
normalize_strip_x(NormData1, smooth_method=4, smooth_factor=0.15, check=2)

Note that the argument check=2 causes the function to generate two check waves but not to modify the original data. To inspect the check waves:

display check_dist, check_smoo
ModifyGraph rgb(check_dist)=(0,0,0)

Vary the smooth_factor (between 0.1 and 1.0) until it follows the instrumental curve but does not affect diffraction features. Then set check=1 to apply the normalization to NormData1.

+

+Azimuthal variation (wobble)

+

Reduce the effect of azimuthal wobble (misaligned surface) on intensity. A misaligned surface may cause a sinusoidal variation of the intensity as a function of azimuthal angle with a 360 period. A strong azimuthal variation may affect the polar normalization in the next step. The azimuthal normalization can be based on a restricted range of polar angles (theta range). You have to find out which value works best for your sample.

+
normalize_strip_phi(NormData1, :attr:ManipulatorTheta, :attr:ManipulatorPhi, theta_offset=-8.8, theta_range=10, check=2)

Note, however, that his function does not correct for angle shifts induced by the misalignment!

+

+Polar dependence

+

Remove the polar angle dependence (matrix element and excitation/detection geometry).

+
normalize_strip_theta(NormData1, :attr:ManipulatorTheta, theta_offset=-8.8, smooth_method=4, smooth_factor=0.5, check=2)

Use the check waves and the check argument as described above.

+

+Binning and plotting

+

+Basic steps

+

You can bin and plot the data in one step:

+
pizza_service(NormData1, "Nickname1", -8.8, 0.5, 6)

or two steps:

+
pizza_service(NormData1, "Nickname2", -8.8, 0.5, 6, nograph=1)
display_hemi_scan("Nickname2")

The benefit of the latter is that you have more control over the graph through optional arguments. In particular, you can select the projection or hide the ticks and grids. See display_hemi_scan for details.

+

The pizza_service function requires the waves with manipulator positions in a specific place, namely :attr:ManipulatorTheta (for the polar angle), and the normal emission values as function arguments. If you have moved the waves, or if you have subtracted the offsets yourself, use the alternative pizza_service_2 function.

+

Additional parameters of the pizza_service function allow for rotational averaging, larger angle steps (default 1 degree), or the creation of metadata including a notebook for xpdPlot.

+

Note there is currently a bug in the nick name argument of some of the following functions. If the lines shown below do not work, try to switch to the data folder that contains the generated polar plot data, and call the function with an empty nickname "".

+

+Refinements

+

To remove high polar angles above θ = 80 from the plot (and data):

+
trim_hemi_scan("Nickname1", 80)

Modify the pseudocolor scale by changing the polarY0 trace:

+
ModifyGraph zColor(polarY0)={mod_values, *, *, BlueGreenOrange, 0}
ModifyGraph zColor(polarY0)={mod_values, -0.2, 0.2, BlueGreenOrange, 0}

To set the contrast to clip specified percentiles of the data points, use the

    +
  • set_contrast function:
  • +
+
set_contrast(2, 2, graphname="graph_Nickname1", colortable="BlueGreenOrange")

+Interpolation

+

Polar plots can also be interpolated to a rectangular matrix, which may in some cases produce nicer images:

+
interpolate_hemi_scan("Nickname1")
display_hemi_scan("Nickname1", graphtype=3, graphname="intp")
matrix = sqrt(x^2 + y^2) <= calc_graph_radius(80) ? matrix : nan
ModifyImage matrix ctab= {*,*,BlueGreenOrange,0}

The matrix = line optionally removes artefacts at high polar angles. Replace the cut-off angle with your own.

+

+Modulation function

+

To calculate the modulation function and substitute it in the graph:

+
setdatafolder Nickname1
calc_modulation(values, factor1=pol, factor2=az)
ModifyGraph zColor(polarY0)={mod_values,-0.2,0.2,BlueGreenOrange,0}

+Data export

+

+Export picture

+

The following line is an example of how to export a graph window. Click on the desired graph window, then issue the following command, substituting the file path and file name as appropriate.

+
SavePICT/P=home/E=-5/B=144/O as "some_filename.png"

+Export processed data

+

The following line saves the dataset to an Igor text file. The file contains all data necessary to recreate a polar plot without further processing.

+
save_hemi_scan("Nickname1", "home", "some_filename")

For structural optimization using the PMSCO software, it is necessary to generate an ETPI file. There is currently no special function for this. Instead, you have to create and set an energy wave,

+
duplicate pol, en
en = 123.4 // kinetic energy of the photoelectron

and write the four waves en, pol, az, values to a general text file. Be careful about the ordering of the waves! You will also have to rename the file to the .etpi extension because Igor always saves with .txt extension. If you have a wave with statistical errors, add a fifth column and use the .etpis extension.

+
Save /G /M="\n" /O /P=home en, pol, az, values, sig as "Nickname1.etpis.txt"
+ + + + + diff --git a/doc/html/pages.html b/doc/html/pages.html index e2db0be..ec0d4bb 100644 --- a/doc/html/pages.html +++ b/doc/html/pages.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: Related Pages @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,35 +38,19 @@ - + - + + + +
- + - - + + + +
-
-
pearl-anglescan-panel.ipf File Reference
+
pearl-anglescan-panel.ipf File Reference
-

interactive processing of angle scanned XPD data. -More...

-
#include "pearl-anglescan-process"
-#include "pearl-pmsco-import"
-

Go to the source code of this file.

- - - - - -

-Namespaces

 PearlAnglescanPanel
 interactive processing of angle scanned XPD data.
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

static variable AfterCompiledHook ()
 initialize package data once when the procedure is first loaded More...
 
static variable init_package ()
 
static variable save_prefs ()
 save persistent package data to the preferences file. More...
 
static variable load_prefs ()
 load persistent package data from the preferences file. More...
 
variable asp_import_raw (wave raw_data)
 import raw data More...
 
variable asp_display_previews ()
 display a graph window of the processed data. More...
 
variable asp_display_dist_check (variable xdist, variable ydist)
 display a graph window of the distribution checks. More...
 
static variable do_init_process (variable check)
 initialize the process data with a copy of the raw data. More...
 
static variable do_crop_alpha (variable check, variable force=defaultValue)
 alpha-crop the process data. More...
 
static variable do_norm_alpha (variable check, variable force=defaultValue)
 alpha-normalize the process data. More...
 
static variable do_norm_phi (variable check, variable force=defaultValue)
 phi-normalize the process data. More...
 
static variable do_norm_theta (variable check, variable force=defaultValue)
 theta-normalize the process data. More...
 
static variable do_norm_thetaphi (variable check, variable force=defaultValue)
 theta,phi-normalize the process data. More...
 
variable asp_calculate_output ()
 calculate the output using all enabled processing filters. More...
 
variable asp_display_output ()
 display the output diffractogram in a new graph More...
 
variable asp_update_graph ()
 update graphs with new color table or contrast More...
 
variable asp_close_graphs ()
 close all graphs created by the angle scan panel More...
 
variable asp_duplicate_output (string dest_name)
 copy the output data to a new folder More...
 
variable asp_save_output_itx ()
 save the output diffractogram to an igor text file More...
 
variable asp_save_output_etpi (variable ekin)
 save the output diffractogram to a PMSCO ETPI file More...
 
static variable check_norm_alpha ()
 
static variable check_norm_phi ()
 
static variable check_norm_theta ()
 
static variable check_norm_thetaphi ()
 
static variable preview_crop_alpha ()
 
static variable preview_norm_alpha ()
 
static variable preview_norm_phi ()
 
static variable preview_norm_theta ()
 
static variable preview_norm_thetaphi ()
 
variable asp_show_panel ()
 create the angle scan processing panel More...
 
static variable arrange_controls ()
 
static variable update_menus ()
 update the popup menus to reflect the values of the global variables More...
 
static variable bp_source_select (WMButtonAction *ba)
 
static variable bp_norm_alpha_check (WMButtonAction *ba)
 
static variable bp_norm_theta_check (WMButtonAction *ba)
 
static variable bp_norm_phi_check (WMButtonAction *ba)
 
static variable bp_norm_thetaphi_check (WMButtonAction *ba)
 
static variable bp_crop_alpha_preview (WMButtonAction *ba)
 
static variable bp_norm_alpha_preview (WMButtonAction *ba)
 
static variable bp_norm_phi_preview (WMButtonAction *ba)
 
static variable bp_norm_theta_preview (WMButtonAction *ba)
 
static variable bp_norm_thetaphi_preview (WMButtonAction *ba)
 
static variable bp_output_calc (WMButtonAction *ba)
 
static variable bp_output_duplicate (WMButtonAction *ba)
 
static variable bp_output_etpi (WMButtonAction *ba)
 
static variable bp_output_itx (WMButtonAction *ba)
 
static variable bp_graph_update (WMButtonAction *ba)
 
static variable bp_graph_png (WMButtonAction *ba)
 
static variable pmp_norm_alpha_mode (WMPopupAction *pa)
 
static variable pmp_norm_theta_mode (WMPopupAction *pa)
 
static variable pmp_norm_thetaphi_mode (WMPopupAction *pa)
 
static variable pmp_graph_mode (WMPopupAction *pa)
 
static variable pmp_graph_projection (WMPopupAction *pa)
 
static variable pmp_graph_colortable (WMPopupAction *pa)
 
- - - - - - - - - - -

-Variables

static const string package_name = "pearl_anglescan_panel"
 package name is used as data folder name More...
 
static const string package_path = "root:packages:pearl_anglescan_panel:"
 data folder path More...
 
static const string prefs_objects = "theta_offset;tilt_offset;phi_offset;alpha_offset;crop_alpha_enable;crop_alpha_value;norm_alpha_enable;norm_alpha_mode;norm_alpha_smoothing;norm_phi_enable;norm_phi_mode;norm_phi_thetarange;norm_theta_enable;norm_theta_mode;norm_theta_smoothing;norm_thetaphi_enable;norm_thetaphi_mode;norm_theta_smoothing;output_folding;output_horizon;graph_mode;graph_projection;graph_colortable;graph_contrast;"
 semicolon-separated list of persistent variable, string, and wave names More...
 
-

Detailed Description

-

interactive processing of angle scanned XPD data.

-

steps to process a hemispherical scan into a diffractogram:

    -
  1. load the scan file in data reduction mode.
  2. -
  3. open the angle scan panel by calling asp_show_panel().
  4. -
  5. select the dataset.
  6. -
  7. set the processing parameters.
  8. -
  9. start the processing and display the result.
  10. -
  11. refine parameters and repeat steps 4-5.
  12. -
  13. export the result in the desired form.
  14. -
-
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
- - -

Definition in file pearl-anglescan-panel.ipf.

-

Function Documentation

- -
-
- - - - - -
- - - - - - - -
static variable AfterCompiledHook ()
-
-static
-
- -

initialize package data once when the procedure is first loaded

- -

Definition at line 52 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable arrange_controls ()
-
-static
-
- -

Definition at line 908 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - -
variable asp_calculate_output ()
-
- -

calculate the output using all enabled processing filters.

-

the diffractogram is calculated, to display the graph, call asp_display_graph.

- -

Definition at line 542 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - -
variable asp_close_graphs ()
-
- -

close all graphs created by the angle scan panel

- -

Definition at line 615 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable asp_display_dist_check (variable xdist,
variable ydist 
)
-
- -

display a graph window of the distribution checks.

-

if the window exists, it is updated and brought to the front of the window stack.

-
Parameters
- - - -
xdist1: display the x-distribution; 0: don't.
ydist1: display the y-distribution; 0: don't.
-
-
- -

Definition at line 266 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - -
variable asp_display_output ()
-
- -

display the output diffractogram in a new graph

- -

Definition at line 577 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - -
variable asp_display_previews ()
-
- -

display a graph window of the processed data.

-

if the window exists, it is updated and brought to the front of the window stack.

- -

Definition at line 242 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - - -
variable asp_duplicate_output (string dest_name)
-
- -

copy the output data to a new folder

-
Parameters
- - -
dest_namename of destination folder. can contain a relative (starting with a colon) or absolute (starting with "root:") path. folders in the path must exist except for the last one. the destination folder does not need to exist. existing data in the destination folder is overwritten.
-
-
- -

Definition at line 650 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - - -
variable asp_import_raw (wave raw_data)
-
- -

import raw data

-

the raw data are copied into the package data folder, and the process waves are initialized.

-
Parameters
- - -
raw_data2D intensity distribution. the x dimension is the detection angle. the y dimension is an arbitrary sequence of manipulator scan positions. ManipulatorTheta, ManipulatorPilt and ManipulatorPhi waves that indicate the manipulator angles for each y position must be present in the :attr sub-folder next to the raw data wave.
-
-
- -

Definition at line 197 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - - -
variable asp_save_output_etpi (variable ekin)
-
- -

save the output diffractogram to a PMSCO ETPI file

-
Parameters
- - -
ekinkinetic energy in eV
-
-
- -

Definition at line 687 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - -
variable asp_save_output_itx ()
-
- -

save the output diffractogram to an igor text file

- -

Definition at line 672 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - -
variable asp_show_panel ()
-
- -

create the angle scan processing panel

- -

Definition at line 771 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - - - -
variable asp_update_graph ()
-
- -

update graphs with new color table or contrast

-

applies to the preview graph and the diffractogram.

- -

Definition at line 597 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_crop_alpha_preview (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1162 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_graph_png (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1316 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_graph_update (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1302 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_norm_alpha_check (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1106 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_norm_alpha_preview (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1176 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_norm_phi_check (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1134 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_norm_phi_preview (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1190 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_norm_theta_check (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1120 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_norm_theta_preview (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1204 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_norm_thetaphi_check (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1148 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_norm_thetaphi_preview (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1218 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_output_calc (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1232 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_output_duplicate (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1247 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_output_etpi (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1266 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_output_itx (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1288 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_source_select (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1080 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable check_norm_alpha ()
-
-static
-
- -

Definition at line 707 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable check_norm_phi ()
-
-static
-
- -

Definition at line 714 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable check_norm_theta ()
-
-static
-
- -

Definition at line 721 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable check_norm_thetaphi ()
-
-static
-
- -

Definition at line 728 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static variable do_crop_alpha (variable check,
variable force = defaultValue 
)
-
-static
-
- -

alpha-crop the process data.

-
Parameters
- - - -
[in]checkselect which output to generate (currently not used).
    -
  • 0 (default) process data, don't calculate check waves.
  • -
  • 1 process data and calculate check waves.
  • -
  • 2 calculate check waves only, do not calculate process data.
  • -
-
[in]forceoverride the global enable flag.
    -
  • 0 (default) apply this filter only if its global enable flag is set.
  • -
  • 1 apply this filter even if it is not enabled.
  • -
-
-
-
- -

Definition at line 351 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable do_init_process (variable check)
-
-static
-
- -

initialize the process data with a copy of the raw data.

-

applies the angle offsets.

-
Parameters
- - -
[in]checkselect which output to generate (currently not used).
    -
  • 0 (default) process data, don't calculate check waves.
  • -
  • 1 process data and calculate check waves.
  • -
  • 2 calculate check waves only, do not calculate process data.
  • -
-
-
-
- -

Definition at line 311 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static variable do_norm_alpha (variable check,
variable force = defaultValue 
)
-
-static
-
- -

alpha-normalize the process data.

-
Parameters
- - - -
[in]checkselect which output to generate.
    -
  • 0 (default) process data, don't calculate check waves.
  • -
  • 1 process data and calculate check waves.
  • -
  • 2 calculate check waves only, do not calculate process data.
  • -
-
[in]forceoverride the global enable flag.
    -
  • 0 (default) apply this filter only if its global enable flag is set.
  • -
  • 1 apply this filter even if it is not enabled.
  • -
-
-
-
- -

Definition at line 380 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static variable do_norm_phi (variable check,
variable force = defaultValue 
)
-
-static
-
- -

phi-normalize the process data.

-
Parameters
- - - -
[in]checkselect which output to generate.
    -
  • 0 (default) process data, don't calculate check waves.
  • -
  • 1 process data and calculate check waves.
  • -
  • 2 calculate check waves only, do not calculate process data.
  • -
-
[in]forceoverride the global enable flag.
    -
  • 0 (default) apply this filter only if its global enable flag is set.
  • -
  • 1 apply this filter even if it is not enabled.
  • -
-
-
-
- -

Definition at line 421 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static variable do_norm_theta (variable check,
variable force = defaultValue 
)
-
-static
-
- -

theta-normalize the process data.

-
Parameters
- - - -
[in]checkselect which output to generate.
    -
  • 0 (default) process data, don't calculate check waves.
  • -
  • 1 process data and calculate check waves.
  • -
  • 2 calculate check waves only, do not calculate process data.
  • -
-
[in]forceoverride the global enable flag.
    -
  • 0 (default) apply this filter only if its global enable flag is set.
  • -
  • 1 apply this filter even if it is not enabled.
  • -
-
-
-
- -

Definition at line 464 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static variable do_norm_thetaphi (variable check,
variable force = defaultValue 
)
-
-static
-
- -

theta,phi-normalize the process data.

-
Parameters
- - - -
[in]checkselect which output to generate.
    -
  • 0 (default) process data, don't calculate check waves.
  • -
  • 1 process data and calculate check waves.
  • -
  • 2 calculate check waves only, do not calculate process data.
  • -
-
[in]forceoverride the global enable flag.
    -
  • 0 (default) apply this filter only if its global enable flag is set.
  • -
  • 1 apply this filter even if it is not enabled.
  • -
-
-
-
- -

Definition at line 506 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable init_package ()
-
-static
-
- -

Definition at line 77 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable load_prefs ()
-
-static
-
- -

load persistent package data from the preferences file.

-

the preferences file is an Igor packed experiment file in a special preferences folder.

-

this function is called automatically when the procedure is first compiled, or whenever the user clicks the corresponding button.

- -

Definition at line 161 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_graph_colortable (WMPopupAction * pa)
-
-static
-
- -

Definition at line 1415 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_graph_mode (WMPopupAction * pa)
-
-static
-
- -

Definition at line 1383 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_graph_projection (WMPopupAction * pa)
-
-static
-
- -

Definition at line 1399 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_norm_alpha_mode (WMPopupAction * pa)
-
-static
-
- -

Definition at line 1335 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_norm_theta_mode (WMPopupAction * pa)
-
-static
-
- -

Definition at line 1351 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_norm_thetaphi_mode (WMPopupAction * pa)
-
-static
-
- -

Definition at line 1367 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable preview_crop_alpha ()
-
-static
-
- -

Definition at line 735 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable preview_norm_alpha ()
-
-static
-
- -

Definition at line 741 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable preview_norm_phi ()
-
-static
-
- -

Definition at line 748 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable preview_norm_theta ()
-
-static
-
- -

Definition at line 755 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable preview_norm_thetaphi ()
-
-static
-
- -

Definition at line 762 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable save_prefs ()
-
-static
-
- -

save persistent package data to the preferences file.

-

this function is called when the user clicks the corresponding button.

- -

Definition at line 137 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable update_menus ()
-
-static
-
- -

update the popup menus to reflect the values of the global variables

- -

Definition at line 1054 of file pearl-anglescan-panel.ipf.

- -
-
-

Variable Documentation

- -
-
- - - - - -
- - - - -
const string package_name = "pearl_anglescan_panel"
-
-static
-
- -

package name is used as data folder name

- -

Definition at line 45 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string package_path = "root:packages:pearl_anglescan_panel:"
-
-static
-
- -

data folder path

- -

Definition at line 47 of file pearl-anglescan-panel.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string prefs_objects = "theta_offset;tilt_offset;phi_offset;alpha_offset;crop_alpha_enable;crop_alpha_value;norm_alpha_enable;norm_alpha_mode;norm_alpha_smoothing;norm_phi_enable;norm_phi_mode;norm_phi_thetarange;norm_theta_enable;norm_theta_mode;norm_theta_smoothing;norm_thetaphi_enable;norm_thetaphi_mode;norm_theta_smoothing;output_folding;output_horizon;graph_mode;graph_projection;graph_colortable;graph_contrast;"
-
-static
-
- -

semicolon-separated list of persistent variable, string, and wave names

- -

Definition at line 49 of file pearl-anglescan-panel.ipf.

- -
-
diff --git a/doc/html/pearl-anglescan-panel_8ipf_source.html b/doc/html/pearl-anglescan-panel_8ipf_source.html index 11aa782..c644d7a 100644 --- a/doc/html/pearl-anglescan-panel_8ipf_source.html +++ b/doc/html/pearl-anglescan-panel_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-anglescan-panel.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma version = 1.7
3 #pragma IgorVersion = 6.2
4 #pragma ModuleName = PearlAnglescanPanel
5 #include "pearl-anglescan-process"
6 #include "pearl-pmsco-import"
7 
8 // copyright (c) 2018 Paul Scherrer Institut
9 //
10 // Licensed under the Apache License, Version 2.0 (the "License");
11 // you may not use this file except in compliance with the License.
12 // You may obtain a copy of the License at
13 // http:///www.apache.org/licenses/LICENSE-2.0
14 //
15 // Please acknowledge the use of this code.
16 
38 
43 
45 static const string package_name = "pearl_anglescan_panel";
47 static const string package_path = "root:packages:pearl_anglescan_panel:";
49 static const string prefs_objects = "theta_offset;tilt_offset;phi_offset;alpha_offset;crop_alpha_enable;crop_alpha_value;norm_alpha_enable;norm_alpha_mode;norm_alpha_smoothing;norm_phi_enable;norm_phi_mode;norm_phi_thetarange;norm_theta_enable;norm_theta_mode;norm_theta_smoothing;norm_thetaphi_enable;norm_thetaphi_mode;norm_theta_smoothing;output_folding;output_horizon;graph_mode;graph_projection;graph_colortable;graph_contrast;";
50 
52 static variable AfterCompiledHook(){
53 
54  dfref savedf = GetDataFolderDFR()
55  variable do_init = 1
56  if (DataFolderExists(package_path))
57  setdatafolder $(package_path)
58  nvar /z init_done
59  if (nvar_exists(init_done))
60  if (init_done)
61  do_init = 0
62  endif
63  endif
64  endif
65 
66  if (do_init)
67  init_package()
68  load_prefs()
69  setdatafolder $(package_path)
70  variable /g init_done = 1
71  endif
72 
73  setdatafolder savedf
74  return 0
75 };
76 
77 static variable init_package(){
78  dfref savedf = getdatafolderdfr()
79  setdatafolder root:
80  newdatafolder /o/s packages
81  newdatafolder /o/s $package_name
82 
83  // configuration (persistent)
84  string /g graphname = "graph_anglescan_panel"
85 
86  // recently used (persistent)
87  variable /g theta_offset = 0
88  variable /g tilt_offset = 0
89  variable /g phi_offset = 0
90  variable /g alpha_offset = 0
91  variable /g crop_alpha_enable = 0
92  variable /g crop_alpha_value = 25
93  variable /g norm_alpha_enable = 0
94  variable /g norm_alpha_mode = 4
95  variable /g norm_alpha_smoothing = 0.25
96  variable /g norm_theta_enable = 0
97  variable /g norm_theta_mode = 4
98  variable /g norm_theta_smoothing = 0.25
99  variable /g norm_thetaphi_enable = 0
100  variable /g norm_thetaphi_mode = 4
101  variable /g norm_thetaphi_smoothing = 0.25
102  variable /g norm_phi_enable = 0
103  variable /g norm_phi_mode = 4
104  variable /g norm_phi_thetarange = 20
105  string /g output_name = "holo1"
106  variable /g output_folding = 1
107  variable /g output_horizon = 88
108  variable /g graph_mode = 1
109  variable /g graph_projection = kProjStereo
110  string /g graph_colortable = "grays"
111  variable /g graph_contrast = 2
112 
113  // recently used (volatile)
114  string /g source_path = ""
115  string /g export_folderpath = "root:"
116  variable /g export_format = 1
117 
118  // administrative data (volatile)
119  string /g panel_name = ""
120  string /g preview_graphname = ""
121  string /g dist_x_graphname = ""
122  string /g dist_y_graphname = ""
123  string /g output_graphname = ""
124 
125  // data (volatile)
126  make /n=(10,10) /o raw_data, process_data
127  make /o dist_x, dist_x_smoo
128  make /o dist_y, dist_y_smoo
129 
130  setdatafolder savedf
131 };
132 
137 static variable save_prefs(){
138  dfref saveDF = GetDataFolderDFR()
139 
140  string fullPath = SpecialDirPath("Packages", 0, 0, 0)
141  fullPath += package_name
142  NewPath/O/C/Q tempPackagePrefsPath, fullPath
143  fullPath += ":preferences.pxp"
144 
145  SetDataFolder root:packages
146  SetDataFolder $package_name
147  SaveData /O /Q /J=prefs_objects fullPath
148 
149  KillPath/Z tempPackagePrefsPath
150 
151  SetDataFolder saveDF
152 };
153 
161 static variable load_prefs(){
162  dfref saveDF = GetDataFolderDFR()
163 
164  variable result = -1
165  setdatafolder root:
166  NewDataFolder /O/S packages
167  NewDataFolder /O/S $package_name
168  string fullPath = SpecialDirPath("Packages", 0, 0, 0)
169  fullPath += package_name
170 
171  GetFileFolderInfo /Q /Z fullPath
172  if (V_Flag == 0)// Disk directory exists?
173  fullPath += ":preferences.pxp"
174  GetFileFolderInfo /Q /Z fullPath
175  if (V_Flag == 0)// Preference file exist?
176  LoadData /O /R /Q fullPath
177  result = 0
178  endif
179  endif
180 
181  SetDataFolder saveDF
182  return result
183 };
184 
197 variable asp_import_raw(wave raw_data){
198  wave raw_data
199 
200  dfref saveDF = GetDataFolderDFR()
201  dfref datadf = GetWavesDataFolderDFR(raw_data)
202  dfref attrdf = datadf:attr
203  if (!DataFolderRefStatus(attrdf))
204  setdatafolder datadf
205  setdatafolder ::
206  dfref parentdf = GetDataFolderDFR()
207  dfref attrdf = parentdf:attr
208  endif
209  setdatafolder $(package_path)
210 
211  // todo : check dimensions and scales
212 
213  svar source_path
214  source_path = GetWavesDataFolder(raw_data, 2)
215 
216  duplicate /o raw_data, raw, process_data
217 
218  wave /sdfr=attrdf /z ManipulatorTheta
219  wave /sdfr=attrdf /z ManipulatorTilt
220  wave /sdfr=attrdf /z ManipulatorPhi
221  if (WaveExists(ManipulatorTheta) && WaveExists(ManipulatorTilt) && WaveExists(ManipulatorPhi))
222  duplicate /o attrdf:ManipulatorTheta, raw_theta, process_theta
223  duplicate /o attrdf:ManipulatorTilt, raw_tilt, process_tilt
224  duplicate /o attrdf:ManipulatorPhi, raw_phi, process_phi
225  else
226  DoAlert 0, "Can't find manipulator angle waves.\rCheck that the attr folder exists, or provide values in the following table."
227  make /n=(dimsize(raw_data, 1)) /o raw_theta, raw_tilt, raw_phi
228  make /n=(dimsize(raw_data, 1)) /o process_theta, process_tilt, process_phi
229  edit /k=1 raw_theta, raw_tilt, raw_phi
230  endif
231 
232  make /o /n=(dimsize(raw_data, 0)) dist_x, dist_x_smoo
233  make /o /n=(dimsize(raw_data, 1)) dist_y, dist_y_smoo
234 
235  SetDataFolder saveDF
236 };
237 
243  dfref df = $(package_path)
244  wave /sdfr=df process_data
245  svar /sdfr=df preview_graphname
246 
247  if (strlen(preview_graphname) && (wintype(preview_graphname) == 1))
248  ad_update_profiles(process_data)
249  DoWindow /F $preview_graphname
250  else
251  preview_graphname = ad_display_profiles(process_data)
252  endif
253 
254  nvar /sdfr=df graph_contrast
255  svar /sdfr=df graph_colortable
256  set_contrast(graph_contrast, graph_contrast, graphname=preview_graphname, colortable=graph_colortable)
257 };
258 
266 variable asp_display_dist_check(variable xdist, variable ydist){
267  variable xdist, ydist
268 
269  dfref df = $(package_path)
270  wave /sdfr=df dist_x
271  wave /sdfr=df dist_y
272  wave /sdfr=df dist_x_smoo
273  wave /sdfr=df dist_y_smoo
274  svar /sdfr=df dist_x_graphname
275  svar /sdfr=df dist_y_graphname
276 
277  if (xdist)
278  if (strlen(dist_x_graphname) && (wintype(dist_x_graphname) == 1))
279  DoWindow /F $dist_x_graphname
280  else
281  display /k=1 /n=graph_asp_dist_x dist_x, dist_x_smoo
282  dist_x_graphname = s_name
283  ModifyGraph /w=$dist_x_graphname mode(dist_x)=2
284  ModifyGraph /w=$dist_x_graphname lsize(dist_x)=2
285  ModifyGraph /w=$dist_x_graphname rgb(dist_x)=(0,0,0)
286  endif
287  endif
288 
289  if (ydist)
290  if (strlen(dist_y_graphname) && (wintype(dist_y_graphname) == 1))
291  DoWindow /F $dist_y_graphname
292  else
293  display /k=1 /n=graph_asp_dist_y dist_y, dist_y_smoo
294  dist_y_graphname = s_name
295  ModifyGraph /w=$dist_y_graphname mode(dist_y)=2
296  ModifyGraph /w=$dist_y_graphname lsize(dist_y)=2
297  ModifyGraph /w=$dist_y_graphname rgb(dist_y)=(0,0,0)
298  endif
299  endif
300 };
301 
311 static variable do_init_process(variable check){
312  variable check
313 
314  dfref df = $(package_path)
315  wave /sdfr=df raw
316  wave /sdfr=df raw_theta
317  wave /sdfr=df raw_tilt
318  wave /sdfr=df raw_phi
319  nvar /sdfr=df theta_offset
320  nvar /sdfr=df tilt_offset
321  nvar /sdfr=df phi_offset
322  nvar /sdfr=df alpha_offset
323 
324  duplicate /o raw, df:process_data
325  duplicate /o raw_theta, df:process_theta
326  duplicate /o raw_tilt, df:process_tilt
327  duplicate /o raw_phi, df:process_phi
328 
329  wave /sdfr=df process_data
330  wave /sdfr=df process_theta
331  wave /sdfr=df process_tilt
332  wave /sdfr=df process_phi
333 
334  process_theta = raw_theta - theta_offset
335  process_tilt = raw_tilt - tilt_offset
336  process_phi = raw_phi - phi_offset
337  setscale /p x dimoffset(raw, 0) - alpha_offset, dimdelta(raw, 0), waveunits(raw, 0), process_data
338 };
339 
351 static variable do_crop_alpha(variable check, variable force = defaultValue){
352  variable check
353  variable force
354 
355  if (ParamIsDefault(force))
356  force = 0
357  endif
358 
359  dfref df = $(package_path)
360  wave /sdfr=df process_data
361  nvar /sdfr=df crop_alpha_enable
362  nvar /sdfr=df crop_alpha_value
363 
364  if ((force || crop_alpha_enable) && (crop_alpha_value > abs(dimdelta(process_data, 0))))
365  crop_strip(process_data, -crop_alpha_value, +crop_alpha_value)
366  endif
367 };
368 
380 static variable do_norm_alpha(variable check, variable force = defaultValue){
381  variable check
382  variable force
383 
384  if (ParamIsDefault(force))
385  force = 0
386  endif
387 
388  dfref saveDF = GetDataFolderDFR()
389  dfref df = $(package_path)
390  wave /sdfr=df process_data
391  nvar /sdfr=df norm_alpha_enable
392  nvar /sdfr=df norm_alpha_mode
393  nvar /sdfr=df norm_alpha_smoothing
394 
395  if (force || norm_alpha_enable)
396  dfref temp_df = newfreedatafolder()
397  setdatafolder temp_df
398  normalize_strip_x(process_data, smooth_method=norm_alpha_mode, smooth_factor=norm_alpha_smoothing, check=check)
399  if (check)
400  wave check_dist
401  wave check_smoo
402  duplicate /o check_dist, df:dist_x
403  duplicate /o check_smoo, df:dist_x_smoo
404  endif
405  endif
406 
407  SetDataFolder saveDF
408 };
409 
421 static variable do_norm_phi(variable check, variable force = defaultValue){
422  variable check
423  variable force
424 
425  if (ParamIsDefault(force))
426  force = 0
427  endif
428 
429  dfref saveDF = GetDataFolderDFR()
430  dfref df = $(package_path)
431  wave /sdfr=df process_data
432  wave /sdfr=df process_theta
433  wave /sdfr=df process_phi
434  nvar /sdfr=df norm_phi_enable
435  nvar /sdfr=df norm_phi_mode
436  nvar /sdfr=df norm_phi_thetarange
437 
438  if (force || norm_phi_enable)
439  dfref temp_df = newfreedatafolder()
440  setdatafolder temp_df
441  normalize_strip_phi(process_data, process_theta, process_phi, theta_range=norm_phi_thetarange, check=check)
442  if (check)
443  wave check_dist
444  wave check_smoo
445  duplicate /o check_dist, df:dist_y
446  duplicate /o check_smoo, df:dist_y_smoo
447  endif
448  endif
449 
450  SetDataFolder saveDF
451 };
452 
464 static variable do_norm_theta(variable check, variable force = defaultValue){
465  variable check
466  variable force
467 
468  if (ParamIsDefault(force))
469  force = 0
470  endif
471 
472  dfref saveDF = GetDataFolderDFR()
473  dfref df = $(package_path)
474  wave /sdfr=df process_data
475  wave /sdfr=df process_theta
476  nvar /sdfr=df norm_theta_enable
477  nvar /sdfr=df norm_theta_mode
478  nvar /sdfr=df norm_theta_smoothing
479 
480  if (force || norm_theta_enable)
481  dfref temp_df = newfreedatafolder()
482  setdatafolder temp_df
483  normalize_strip_theta(process_data, process_theta, smooth_method=norm_theta_mode, smooth_factor=norm_theta_smoothing, check=check)
484  if (check)
485  wave check_dist
486  wave check_smoo
487  duplicate /o check_dist, df:dist_y
488  duplicate /o check_smoo, df:dist_y_smoo
489  endif
490  endif
491 
492  SetDataFolder saveDF
493 };
494 
506 static variable do_norm_thetaphi(variable check, variable force = defaultValue){
507  variable check
508  variable force
509 
510  if (ParamIsDefault(force))
511  force = 0
512  endif
513 
514  dfref saveDF = GetDataFolderDFR()
515  dfref df = $(package_path)
516  wave /sdfr=df process_data
517  wave /sdfr=df process_theta
518  wave /sdfr=df process_phi
519  nvar /sdfr=df norm_thetaphi_enable
520  nvar /sdfr=df norm_thetaphi_mode
521  nvar /sdfr=df norm_thetaphi_smoothing
522 
523  if (force || norm_thetaphi_enable)
524  dfref temp_df = newfreedatafolder()
525  setdatafolder temp_df
526  normalize_strip_thetaphi(process_data, process_theta, process_phi, smooth_method=norm_thetaphi_mode, smooth_factor=norm_thetaphi_smoothing, check=check)
527  if (check)
528  wave check_dist
529  wave check_smoo
530  duplicate /o check_dist, df:dist_y
531  duplicate /o check_smoo, df:dist_y_smoo
532  endif
533  endif
534 
535  SetDataFolder saveDF
536 };
537 
543  dfref saveDF = GetDataFolderDFR()
544  setdatafolder $(package_path)
545 
546  svar output_name
547 
548  wave process_data
549  wave process_theta
550  wave process_tilt
551  wave process_phi
552 
553  nvar folding=output_folding
554  nvar horizon=output_horizon
555 
556  do_init_process(0)
557  do_crop_alpha(0)
558  do_norm_alpha(0)
559  do_norm_phi(0)
560  do_norm_theta(0)
562 
563  pizza_service_2(process_data, output_name, process_theta, process_tilt, process_phi, folding=folding, nograph=1)
564 
565  setdatafolder $output_name
566  wave values
567  wave pol
568  if (horizon > 0)
569  values = pol <= horizon ? values : nan
570  endif
571 
572  SetDataFolder saveDF
573 };
574 
578  dfref df = $(package_path)
579 
580  svar /sdfr=df output_name
581  svar /sdfr=df output_graphname
582  nvar /sdfr=df graph_projection
583  nvar /sdfr=df graph_mode
584 
585  dfref saveDF = GetDataFolderDFR()
586  setdatafolder $(package_path)
587  output_graphname = output_name
588  output_graphname = display_hemi_scan(output_name, projection=graph_projection, graphtype=graph_mode, graphname=output_graphname)
589  SetDataFolder saveDF
591 };
592 
597 variable asp_update_graph(){
598  dfref df = $(package_path)
599 
600  svar /sdfr=df preview_graphname
601  svar /sdfr=df output_graphname
602  svar /sdfr=df graph_colortable
603  nvar /sdfr=df graph_contrast
604 
605  if (strlen(preview_graphname) && (wintype(preview_graphname) == 1))
606  set_contrast(graph_contrast, graph_contrast, graphname=preview_graphname, colortable=graph_colortable)
607  endif
608  if (strlen(output_graphname) && (wintype(output_graphname) == 1))
609  set_contrast(graph_contrast, graph_contrast, graphname=output_graphname, colortable=graph_colortable)
610  endif
611 };
612 
615 variable asp_close_graphs(){
616  dfref df = $(package_path)
617 
618  svar /sdfr=df preview_graphname
619  svar /sdfr=df output_graphname
620  svar /sdfr=df dist_x_graphname
621  svar /sdfr=df dist_y_graphname
622 
623  if (strlen(preview_graphname) && (wintype(preview_graphname) == 1))
624  killwindow $preview_graphname
625  endif
626  if (strlen(output_graphname) && (wintype(output_graphname) == 1))
627  killwindow $output_graphname
628  endif
629  if (strlen(dist_x_graphname) && (wintype(dist_x_graphname) == 1))
630  killwindow $dist_x_graphname
631  endif
632  if (strlen(dist_y_graphname) && (wintype(dist_y_graphname) == 1))
633  killwindow $dist_y_graphname
634  endif
635 
636  preview_graphname = ""
637  output_graphname = ""
638  dist_x_graphname = ""
639  dist_y_graphname = ""
640 };
641 
650 variable asp_duplicate_output(string dest_name){
651  string dest_name
652 
653  dfref df = $(package_path)
654  svar /sdfr=df source_path
655  svar /sdfr=df output_name
656  svar /sdfr=df output_graphname
657  wave raw_data = $source_path
658 
659  dfref saveDF = GetDataFolderDFR()
660  dfref dest_df = GetWavesDataFolderDFR(raw_data)
661  setdatafolder dest_df
662  newdatafolder /o /s $dest_name
663  dfref dest_df = GetDataFolderDFR()
664  setdatafolder df
665  duplicate_hemi_scan(output_name, dest_df, "")
666 
667  SetDataFolder saveDF
668 };
669 
673  dfref df = $(package_path)
674  svar /sdfr=df output_name
675 
676  dfref saveDF = GetDataFolderDFR()
677  setdatafolder df
678  save_hemi_scan(output_name, "", "")
679 
680  SetDataFolder saveDF
681 };
682 
687 variable asp_save_output_etpi(variable ekin){
688  variable ekin
689 
690  dfref df = $(package_path)
691  svar /sdfr=df output_name
692  wave /sdfr=df process_data
693 
694  dfref saveDF = GetDataFolderDFR()
695  setdatafolder df
696  string s_prefix = ""
697  string s_int = "values"
698  dfref data_df = find_hemi_data(output_name, s_prefix, s_int)
699  string s_polar = s_prefix + "pol"
700  string s_azim = s_prefix + "az"
701 
702  pmsco_save_scan("", "", num2str(ekin), s_polar, s_azim, "", s_int, "", sdfr=data_df)
703 
704  SetDataFolder saveDF
705 };
706 
707 static variable check_norm_alpha(){
708  do_init_process(0)
709  do_crop_alpha(0)
710  do_norm_alpha(2, force=1)
712 };
713 
714 static variable check_norm_phi(){
715  do_init_process(0)
716  do_crop_alpha(0)
717  do_norm_phi(2, force=1)
719 };
720 
721 static variable check_norm_theta(){
722  do_init_process(0)
723  do_crop_alpha(0)
724  do_norm_theta(2, force=1)
726 };
727 
728 static variable check_norm_thetaphi(){
729  do_init_process(0)
730  do_crop_alpha(0)
731  do_norm_thetaphi(2, force=1)
733 };
734 
735 static variable preview_crop_alpha(){
736  do_init_process(0)
737  do_crop_alpha(0, force=1)
739 };
740 
741 static variable preview_norm_alpha(){
742  do_init_process(0)
743  do_crop_alpha(0)
744  do_norm_alpha(1, force=1)
746 };
747 
748 static variable preview_norm_phi(){
749  do_init_process(0)
750  do_crop_alpha(0)
751  do_norm_phi(1, force=1)
753 };
754 
755 static variable preview_norm_theta(){
756  do_init_process(0)
757  do_crop_alpha(0)
758  do_norm_theta(1, force=1)
760 };
761 
762 static variable preview_norm_thetaphi(){
763  do_init_process(0)
764  do_crop_alpha(0)
765  do_norm_thetaphi(1, force=1)
767 };
768 
771 variable asp_show_panel(){
772  dfref df = $(package_path)
773  svar /sdfr=df panel_name
774 
775  if (strlen(panel_name) && (wintype(panel_name) == 7))
776  DoWindow /F $panel_name
777  return 0
778  endif
779 
780  NewPanel /K=1 /N=anglescan_panel /W=(200,100,479,1027) as "angle scan processing"
781  panel_name = s_name
782 
783  GroupBox gb_source, title="data source"
784  Button b_source_select, size={50,20},proc=PearlAnglescanPanel#bp_source_select,title="select..."
785  Button b_source_select, help={"select the source wave, e.g. ReducedData1. it must be in the original scan data folder along with the attr folder and the manipulator positions."}
786  TitleBox tb_source_path, size={240,21}
787  TitleBox tb_source_path,variable= root:packages:pearl_anglescan_panel:source_path
788 
789  GroupBox gb_offsets, title="offsets"
790  SetVariable sv_theta_offset, size={88,16},bodyWidth=60,title="theta"
791  SetVariable sv_theta_offset,value= root:packages:pearl_anglescan_panel:theta_offset
792  SetVariable sv_theta_offset, help={"manipulator theta value that corresponds to normal emission."}
793  SetVariable sv_tilt_offset, size={74,16},bodyWidth=60,title="tilt"
794  SetVariable sv_tilt_offset,value= root:packages:pearl_anglescan_panel:tilt_offset
795  SetVariable sv_tilt_offset, help={"manipulator tilt value that corresponds to normal emission."}
796  SetVariable sv_phi_offset, size={78,16},bodyWidth=60,title="phi"
797  SetVariable sv_phi_offset,value= root:packages:pearl_anglescan_panel:phi_offset
798  SetVariable sv_phi_offset, help={"manipulator phi value that should map to the 3 o'clock angle."}
799  SetVariable sv_alpha_offset, size={90,16},bodyWidth=60,title="alpha"
800  SetVariable sv_alpha_offset,value= root:packages:pearl_anglescan_panel:alpha_offset
801  SetVariable sv_alpha_offset, help={"alpha value that corresponds to normal emission (if the sample normal is properly aligned)."}
802 
803  GroupBox gb_crop_alpha, title="crop alpha"
804  CheckBox cb_crop_alpha_enable, size={50,14}, title="enable"
805  CheckBox cb_crop_alpha_enable, help={"enable cropping at +/- alpha"}
806  CheckBox cb_crop_alpha_enable,variable= root:packages:pearl_anglescan_panel:crop_alpha_enable
807  SetVariable sv_crop_alpha_value, size={90,16},bodyWidth=60,title="angle"
808  SetVariable sv_crop_alpha_value,limits={0,30,1},value= root:packages:pearl_anglescan_panel:crop_alpha_value
809  SetVariable sv_crop_alpha_value, help={"alpha (detection angle) cropping angle"}
810  Button b_crop_alpha_preview, size={80,20},proc=PearlAnglescanPanel#bp_crop_alpha_preview,title="preview"
811  Button b_crop_alpha_preview, help={"show a preview of the cropped dataset."}
812 
813  GroupBox gb_norm_alpha, title="normalize alpha"
814  CheckBox cb_norm_alpha_enable, size={50,14}, title="enable"
815  CheckBox cb_norm_alpha_enable,variable= root:packages:pearl_anglescan_panel:norm_alpha_enable
816  CheckBox cb_norm_alpha_enable, help={"enable normalization of the alpha distribution"}
817  PopupMenu pm_norm_alpha_mode, size={138,21}, bodyWidth=100, proc=PearlAnglescanPanel#pmp_norm_alpha_mode,title="method"
818  PopupMenu pm_norm_alpha_mode, mode=5, popvalue="loess", value= #"\"none;binomial;boxcar;scienta;loess;\""
819  PopupMenu pm_norm_alpha_mode, help={"alpha normalization method. recommended: loess"}
820  SetVariable sv_norm_alpha_smoothing, size={112,16}, bodyWidth=60, title="smoothing"
821  SetVariable sv_norm_alpha_smoothing, limits={0,1,0.05}, value= root:packages:pearl_anglescan_panel:norm_alpha_smoothing
822  SetVariable sv_norm_alpha_smoothing, help={"smoothing parameter (depends on the normalization method)."}
823  Button b_norm_alpha_check, size={80,20}, proc=PearlAnglescanPanel#bp_norm_alpha_check,title="check"
824  Button b_norm_alpha_check, help={"show a graph of the normalization function"}
825  Button b_norm_alpha_preview, size={80,20}, proc=PearlAnglescanPanel#bp_norm_alpha_preview,title="preview"
826  Button b_norm_alpha_preview, help={"show a preview of the normalized dataset (without other normalizations)."}
827 
828  GroupBox gb_norm_phi, title="normalize phi"
829  CheckBox cb_norm_phi_enable, size={50,14}, title="enable"
830  CheckBox cb_norm_phi_enable,variable= root:packages:pearl_anglescan_panel:norm_phi_enable
831  CheckBox cb_norm_phi_enable, help={"enable normalization of the phi distribution to reduce the effect of wobble"}
832  SetVariable sv_norm_phi_range, size={118,16}, bodyWidth=60, title="theta range"
833  SetVariable sv_norm_phi_range, limits={0,90,1}, value= root:packages:pearl_anglescan_panel:norm_phi_thetarange
834  SetVariable sv_norm_phi_range, help={"theta range (from normal) to factor into the normalization function"}
835  Button b_norm_phi_check, size={80,20}, proc=PearlAnglescanPanel#bp_norm_phi_check, title="check"
836  Button b_norm_phi_check, help={"show a graph of the normalization function"}
837  Button b_norm_phi_preview, size={80,20}, proc=PearlAnglescanPanel#bp_norm_phi_preview, title="preview"
838  Button b_norm_phi_preview, help={"show a preview of the normalized dataset (without other normalizations)."}
839 
840  GroupBox gb_norm_theta, title="normalize theta"
841  CheckBox cb_norm_theta_enable, size={50,14},title="enable"
842  CheckBox cb_norm_theta_enable, variable= root:packages:pearl_anglescan_panel:norm_theta_enable
843  CheckBox cb_norm_theta_enable, help={"enable normalization of the theta distribution (integrated over phi)"}
844  PopupMenu pm_norm_theta_mode, size={138,21},bodyWidth=100,proc=PearlAnglescanPanel#pmp_norm_theta_mode,title="method"
845  PopupMenu pm_norm_theta_mode,mode=5,popvalue="loess",value= #"\"none;binomial;boxcar;polynomial;loess;\""
846  PopupMenu pm_norm_theta_mode, help={"theta normalization method. recommended: loess"}
847  SetVariable sv_norm_theta_smoothing, size={112,16}, bodyWidth=60, title="smoothing"
848  SetVariable sv_norm_theta_smoothing, limits={0,1,0.05}, value= root:packages:pearl_anglescan_panel:norm_theta_smoothing
849  SetVariable sv_norm_theta_smoothing, help={"smoothing parameter (depends on the normalization method)."}
850  Button b_norm_theta_check, size={80,20}, proc=PearlAnglescanPanel#bp_norm_theta_check, title="check"
851  Button b_norm_theta_check, help={"show a graph of the normalization function"}
852  Button b_norm_theta_preview, size={80,20}, proc=PearlAnglescanPanel#bp_norm_theta_preview, title="preview"
853  Button b_norm_theta_preview, help={"show a preview of the normalized dataset (without other normalizations)."}
854 
855  GroupBox gb_norm_thetaphi, size={272,97},title="normalize (theta,phi)"
856  CheckBox cb_norm_thetaphi_enable, size={50,14},title="enable"
857  CheckBox cb_norm_thetaphi_enable, variable= root:packages:pearl_anglescan_panel:norm_thetaphi_enable
858  CheckBox cb_norm_thetaphi_enable, help={"enable normalization of the (theta, phi) distribution."}
859  PopupMenu pm_norm_thetaphi_mode, size={138,21}, bodyWidth=100, proc=PearlAnglescanPanel#pmp_norm_thetaphi_mode,title="method"
860  PopupMenu pm_norm_thetaphi_mode, mode=5, popvalue="loess", value= #"\"none;none;none;none;loess;\""
861  PopupMenu pm_norm_thetaphi_mode, help={"theta normalization method. recommended: loess"}
862  SetVariable sv_norm_thetaphi_smoothing, size={112,16}, bodyWidth=60, title="smoothing"
863  SetVariable sv_norm_thetaphi_smoothing, limits={0,1,0.05}, value= root:packages:pearl_anglescan_panel:norm_thetaphi_smoothing
864  SetVariable sv_norm_thetaphi_smoothing, help={"smoothing parameter (depends on the normalization method)."}
865  Button b_norm_thetaphi_check, size={80,20}, proc=PearlAnglescanPanel#bp_norm_thetaphi_check, title="check"
866  Button b_norm_thetaphi_check, help={"show a graph of the normalization function"}
867  Button b_norm_thetaphi_preview, size={80,20}, proc=PearlAnglescanPanel#bp_norm_thetaphi_preview, title="preview"
868  Button b_norm_thetaphi_preview, help={"show a preview of the normalized dataset (without other normalizations)."}
869 
870  GroupBox gb_output, title="output"
871  SetVariable sv_output_folding, size={95,16}, bodyWidth=60, title="folding"
872  SetVariable sv_output_folding, limits={1,20,1}, value= root:packages:pearl_anglescan_panel:output_folding
873  SetVariable sv_output_folding, help={"n-fold rotational average. 1=no averaging."}
874  SetVariable sv_output_horizon, size={98,16}, bodyWidth=60, title="horizon"
875  SetVariable sv_output_horizon, limits={1,90,1}, value= root:packages:pearl_anglescan_panel:output_horizon
876  SetVariable sv_output_horizon, help={"highest theta to display"}
877  PopupMenu pm_graph_projection, size={149,21}, bodyWidth=100, proc=PearlAnglescanPanel#pmp_graph_projection, title="projection"
878  PopupMenu pm_graph_projection, mode=2, popvalue="stereographic", value= #"\"equidistant;stereographic;equal area;gnomonic;orthographic;\""
879  PopupMenu pm_graph_projection, help={"projection (theta mapping) mode"}
880  PopupMenu pm_graph_mode, size={129,21}, bodyWidth=100, proc=PearlAnglescanPanel#pmp_graph_mode,title="mode"
881  PopupMenu pm_graph_mode, mode=2, popvalue="polar plot", value= #"\"none;polar plot;none;image;\""
882  PopupMenu pm_graph_mode, help={"graph mode"}
883  Button b_output_calc, size={80,20}, proc=PearlAnglescanPanel#bp_output_calc, title="calc + display"
884  Button b_output_calc, help={"execute data processing with the enabled filters and display the diffractogram."}
885  Button b_output_duplicate, size={80,20}, proc=PearlAnglescanPanel#bp_output_duplicate, title="duplicate ..."
886  Button b_output_duplicate, help={"copy the result to an arbitrary data folder."}
887  Button b_output_itx, size={80,20}, proc=PearlAnglescanPanel#bp_output_itx, title="save ITX ..."
888  Button b_output_itx, help={"save the result to an igor text file (itx)."}
889  Button b_output_etpi, size={80,20}, proc=PearlAnglescanPanel#bp_output_etpi, title="save ETPI ..."
890  Button b_output_etpi, help={"save the result to a pmsco angle scan file (etpi)."}
891 
892  GroupBox gb_graph, title="graph"
893  PopupMenu pm_graph_colortable, size={152,21}, bodyWidth=100, proc=PearlAnglescanPanel#pmp_graph_colortable, title="color table"
894  PopupMenu pm_graph_colortable, mode=0, value= #"\"*COLORTABLEPOPNONAMES*\""
895  PopupMenu pm_graph_colortable, help={"color table to use in pseudocolor graphs."}
896  SetVariable sv_graph_contrast, size={119,16}, bodyWidth=60, title="contrast (%)"
897  SetVariable sv_graph_contrast, limits={0,25,1}, value= root:packages:pearl_anglescan_panel:graph_contrast
898  SetVariable sv_graph_contrast, help={"contrast value (percentile)."}
899  Button b_graph_update, size={80,20}, proc=PearlAnglescanPanel#bp_graph_update, title="update"
900  Button b_graph_update, help={"update the existing graph."}
901  Button b_graph_png, size={80,20}, proc=PearlAnglescanPanel#bp_graph_png, title="save PNG ..."
902  Button b_graph_png, help={"save the graph in png format."}
903 
905  update_menus()
906 };
907 
908 static variable arrange_controls(){
909  dfref df = $(package_path)
910  svar /sdfr=df panel_name
911 
912  variable gb_space = 2
913  variable gb_internal_top = 20
914  variable gb_internal_bot = 8
915  variable line_space = 26
916 
917  variable cb_adj = 2
918  variable sv_adj = 2
919  variable pm_adj = 0
920  variable b_adj = 0
921  variable tb_adj = 0
922 
923  variable gb_top = 4
924  variable gb_ht = 0
925 
926  // ht = line + 30
927  // gb = gb + ht + 2
928  // cb = gb + 18
929  // pm = gb + 38
930  // line += 26
931  // sv = line + 2
932 
933  GroupBox gb_source,pos={4,gb_top}
934  gb_ht = gb_internal_top
935  Button b_source_select,pos={17, gb_top + gb_ht + b_adj},size={50,20}
936  gb_ht += line_space
937  TitleBox tb_source_path,pos={18, gb_top + gb_ht + tb_adj},size={240,21}
938  gb_ht += line_space
939  gb_ht += gb_internal_bot
940  GroupBox gb_source, size={272,gb_ht}
941 
942  gb_top += gb_ht + gb_space
943  GroupBox gb_offsets,pos={4,gb_top}
944  gb_ht = gb_internal_top
945  SetVariable sv_theta_offset,pos={46, gb_top + gb_ht + sv_adj},size={88,16}
946  gb_ht += line_space
947  SetVariable sv_tilt_offset,pos={60, gb_top + gb_ht + sv_adj},size={74,16}
948  gb_ht += line_space
949  SetVariable sv_phi_offset,pos={56, gb_top + gb_ht + sv_adj},size={78,16}
950  gb_ht += line_space
951  SetVariable sv_alpha_offset,pos={44, gb_top + gb_ht + sv_adj},size={90,16}
952  gb_ht += line_space
953  gb_ht += gb_internal_bot
954  GroupBox gb_offsets, size={272,gb_ht}
955 
956  gb_top += gb_ht + gb_space
957  GroupBox gb_crop_alpha,pos={4,gb_top}
958  gb_ht = gb_internal_top
959  CheckBox cb_crop_alpha_enable,pos={73, gb_top + gb_ht + cb_adj},size={50,14}
960  gb_ht += line_space
961  SetVariable sv_crop_alpha_value,pos={44, gb_top + gb_ht + sv_adj},size={90,16}
962  Button b_crop_alpha_preview,pos={186, gb_top + gb_ht + b_adj},size={80,20}
963  gb_ht += line_space
964  gb_ht += gb_internal_bot
965  GroupBox gb_crop_alpha, size={272,gb_ht}
966 
967  gb_top += gb_ht + gb_space
968  GroupBox gb_norm_alpha,pos={4,gb_top}
969  gb_ht = gb_internal_top
970  CheckBox cb_norm_alpha_enable,pos={73, gb_top + gb_ht + cb_adj},size={50,14}
971  gb_ht += line_space
972  PopupMenu pm_norm_alpha_mode,pos={36, gb_top + gb_ht + pm_adj},size={138,21}
973  Button b_norm_alpha_check,pos={186, gb_top + gb_ht + b_adj},size={80,20}
974  gb_ht += line_space
975  SetVariable sv_norm_alpha_smoothing,pos={22, gb_top + gb_ht + sv_adj},size={112,16}
976  Button b_norm_alpha_preview,pos={186, gb_top + gb_ht + b_adj},size={80,20}
977  gb_ht += line_space
978  gb_ht += gb_internal_bot
979  GroupBox gb_norm_alpha, size={272,gb_ht}
980 
981  gb_top += gb_ht + gb_space
982  GroupBox gb_norm_phi,pos={4,gb_top}
983  gb_ht = gb_internal_top
984  CheckBox cb_norm_phi_enable,pos={73, gb_top + gb_ht + cb_adj},size={50,14}
985  Button b_norm_phi_check,pos={186, gb_top + gb_ht + b_adj},size={80,20}
986  gb_ht += line_space
987  SetVariable sv_norm_phi_range,pos={15, gb_top + gb_ht + sv_adj},size={118,16}
988  Button b_norm_phi_preview,pos={186, gb_top + gb_ht + b_adj},size={80,20}
989  gb_ht += line_space
990  gb_ht += gb_internal_bot
991  GroupBox gb_norm_phi, size={272,gb_ht}
992 
993  gb_top += gb_ht + gb_space
994  GroupBox gb_norm_theta,pos={4,gb_top}
995  gb_ht = gb_internal_top
996  CheckBox cb_norm_theta_enable,pos={73, gb_top + gb_ht + cb_adj},size={50,14}
997  gb_ht += line_space
998  PopupMenu pm_norm_theta_mode,pos={35, gb_top + gb_ht + pm_adj},size={138,21}
999  Button b_norm_theta_check,pos={186, gb_top + gb_ht + b_adj},size={80,20}
1000  gb_ht += line_space
1001  SetVariable sv_norm_theta_smoothing,pos={21, gb_top + gb_ht + sv_adj},size={112,16}
1002  Button b_norm_theta_preview,pos={186, gb_top + gb_ht + b_adj},size={80,20}
1003  gb_ht += line_space
1004  gb_ht += gb_internal_bot
1005  GroupBox gb_norm_theta, size={272,gb_ht}
1006 
1007  gb_top += gb_ht + gb_space
1008  GroupBox gb_norm_thetaphi,pos={4,gb_top}
1009  gb_ht = gb_internal_top
1010  CheckBox cb_norm_thetaphi_enable,pos={73, gb_top + gb_ht + cb_adj},size={50,14}
1011  gb_ht += line_space
1012  PopupMenu pm_norm_thetaphi_mode,pos={35, gb_top + gb_ht + pm_adj},size={138,21}
1013  Button b_norm_thetaphi_check,pos={186, gb_top + gb_ht + b_adj},size={80,20}
1014  gb_ht += line_space
1015  SetVariable sv_norm_thetaphi_smoothing,pos={21, gb_top + gb_ht + sv_adj},size={112,16}
1016  Button b_norm_thetaphi_preview,pos={186, gb_top + gb_ht + b_adj},size={80,20}
1017  gb_ht += line_space
1018  gb_ht += gb_internal_bot
1019  GroupBox gb_norm_thetaphi, size={272,gb_ht}
1020 
1021  gb_top += gb_ht + gb_space
1022  GroupBox gb_output,pos={4,gb_top}
1023  gb_ht = gb_internal_top
1024  SetVariable sv_output_folding,pos={38, gb_top + gb_ht + sv_adj},size={95,16}
1025  Button b_output_calc,pos={186, gb_top + gb_ht + b_adj},size={80,20}
1026  gb_ht += line_space
1027  SetVariable sv_output_horizon,pos={35, gb_top + gb_ht + sv_adj},size={98,16}
1028  Button b_output_duplicate,pos={186, gb_top + gb_ht + b_adj},size={80,20}
1029  gb_ht += line_space
1030  PopupMenu pm_graph_projection,pos={24, gb_top + gb_ht + pm_adj},size={149,21}
1031  Button b_output_itx,pos={186, gb_top + gb_ht + b_adj},size={80,20}
1032  gb_ht += line_space
1033  PopupMenu pm_graph_mode,pos={44, gb_top + gb_ht + pm_adj},size={129,21}
1034  Button b_output_etpi,pos={186, gb_top + gb_ht + b_adj},size={80,20}
1035  gb_ht += line_space
1036  gb_ht += gb_internal_bot
1037  GroupBox gb_output, size={272,gb_ht}
1038 
1039  gb_top += gb_ht + gb_space
1040  GroupBox gb_graph,pos={4,gb_top}
1041  gb_ht = gb_internal_top
1042  PopupMenu pm_graph_colortable,pos={21, gb_top + gb_ht + pm_adj},size={152,21}
1043  Button b_graph_update,pos={186, gb_top + gb_ht + b_adj},size={80,20}
1044  gb_ht += line_space
1045  SetVariable sv_graph_contrast,pos={14, gb_top + gb_ht + sv_adj},size={119,16}
1046  Button b_graph_png,pos={186, gb_top + gb_ht + b_adj},size={80,20}
1047  gb_ht += line_space
1048  gb_ht += gb_internal_bot
1049  GroupBox gb_graph, size={272,gb_ht}
1050 };
1051 
1054 static variable update_menus(){
1055  dfref df = $(package_path)
1056  svar /sdfr=df panel_name
1057  if (wintype(panel_name) == 7)
1058  variable m
1059  nvar /sdfr=df norm_alpha_mode
1060  m = norm_alpha_mode + 1
1061  PopupMenu pm_norm_alpha_mode win=$panel_name, mode=m
1062  nvar /sdfr=df norm_theta_mode
1063  m = norm_theta_mode + 1
1064  PopupMenu pm_norm_theta_mode win=$panel_name, mode=m
1065  nvar /sdfr=df norm_thetaphi_mode
1066  m = norm_thetaphi_mode + 1
1067  PopupMenu pm_norm_thetaphi_mode win=$panel_name, mode=m
1068  nvar /sdfr=df graph_mode
1069  m = graph_mode + 1
1070  PopupMenu pm_graph_mode win=$panel_name, mode=m
1071  nvar /sdfr=df graph_projection
1072  m = graph_projection + 1
1073  PopupMenu pm_graph_projection win=$panel_name, mode=m
1074  svar /sdfr=df graph_colortable
1075  m = 1 + WhichListItem(graph_colortable, CTabList())
1076  PopupMenu pm_graph_colortable win=$panel_name, mode=m
1077  endif
1078 };
1079 
1080 static variable bp_source_select(WMButtonAction* ba){
1081  STRUCT WMButtonAction &ba
1082 
1083  switch( ba.eventCode )
1084  case 2:// mouse up
1085  dfref dfBefore = GetDataFolderDFR()
1086  Execute /q/z "CreateBrowser prompt=\"Select 2D holo scan wave\", showWaves=1, showVars=0, showStrs=0"
1087  dfref dfAfter = GetDataFolderDFR()
1088  SetDataFolder dfBefore
1089 
1090  SVAR list = S_BrowserList
1091  NVAR flag = V_Flag
1092  if ((flag != 0) && (ItemsInList(list) >= 1))
1093  string wname = StringFromList(0, list)
1094  wave w = $wname
1095  asp_import_raw(w)
1096  endif
1097 
1098  break
1099  case -1:// control being killed
1100  break
1101  endswitch
1102 
1103  return 0
1104 };
1105 
1106 static variable bp_norm_alpha_check(WMButtonAction* ba){
1107  STRUCT WMButtonAction &ba
1108 
1109  switch( ba.eventCode )
1110  case 2:// mouse up
1112  break
1113  case -1:// control being killed
1114  break
1115  endswitch
1116 
1117  return 0
1118 };
1119 
1120 static variable bp_norm_theta_check(WMButtonAction* ba){
1121  STRUCT WMButtonAction &ba
1122 
1123  switch( ba.eventCode )
1124  case 2:// mouse up
1126  break
1127  case -1:// control being killed
1128  break
1129  endswitch
1130 
1131  return 0
1132 };
1133 
1134 static variable bp_norm_phi_check(WMButtonAction* ba){
1135  STRUCT WMButtonAction &ba
1136 
1137  switch( ba.eventCode )
1138  case 2:// mouse up
1139  check_norm_phi()
1140  break
1141  case -1:// control being killed
1142  break
1143  endswitch
1144 
1145  return 0
1146 };
1147 
1148 static variable bp_norm_thetaphi_check(WMButtonAction* ba){
1149  STRUCT WMButtonAction &ba
1150 
1151  switch( ba.eventCode )
1152  case 2:// mouse up
1154  break
1155  case -1:// control being killed
1156  break
1157  endswitch
1158 
1159  return 0
1160 };
1161 
1162 static variable bp_crop_alpha_preview(WMButtonAction* ba){
1163  STRUCT WMButtonAction &ba
1164 
1165  switch( ba.eventCode )
1166  case 2:// mouse up
1168  break
1169  case -1:// control being killed
1170  break
1171  endswitch
1172 
1173  return 0
1174 };
1175 
1176 static variable bp_norm_alpha_preview(WMButtonAction* ba){
1177  STRUCT WMButtonAction &ba
1178 
1179  switch( ba.eventCode )
1180  case 2:// mouse up
1182  break
1183  case -1:// control being killed
1184  break
1185  endswitch
1186 
1187  return 0
1188 };
1189 
1190 static variable bp_norm_phi_preview(WMButtonAction* ba){
1191  STRUCT WMButtonAction &ba
1192 
1193  switch( ba.eventCode )
1194  case 2:// mouse up
1196  break
1197  case -1:// control being killed
1198  break
1199  endswitch
1200 
1201  return 0
1202 };
1203 
1204 static variable bp_norm_theta_preview(WMButtonAction* ba){
1205  STRUCT WMButtonAction &ba
1206 
1207  switch( ba.eventCode )
1208  case 2:// mouse up
1210  break
1211  case -1:// control being killed
1212  break
1213  endswitch
1214 
1215  return 0
1216 };
1217 
1218 static variable bp_norm_thetaphi_preview(WMButtonAction* ba){
1219  STRUCT WMButtonAction &ba
1220 
1221  switch( ba.eventCode )
1222  case 2:// mouse up
1224  break
1225  case -1:// control being killed
1226  break
1227  endswitch
1228 
1229  return 0
1230 };
1231 
1232 static variable bp_output_calc(WMButtonAction* ba){
1233  STRUCT WMButtonAction &ba
1234 
1235  switch( ba.eventCode )
1236  case 2:// mouse up
1239  break
1240  case -1:// control being killed
1241  break
1242  endswitch
1243 
1244  return 0
1245 };
1246 
1247 static variable bp_output_duplicate(WMButtonAction* ba){
1248  STRUCT WMButtonAction &ba
1249 
1250  switch( ba.eventCode )
1251  case 2:// mouse up
1252  string dest_folder
1253  prompt dest_folder, "destination folder name (relative to data source)"
1254  doprompt "duplicate", dest_folder
1255  if (!v_flag)
1256  asp_duplicate_output(dest_folder)
1257  endif
1258  break
1259  case -1:// control being killed
1260  break
1261  endswitch
1262 
1263  return 0
1264 };
1265 
1266 static variable bp_output_etpi(WMButtonAction* ba){
1267  STRUCT WMButtonAction &ba
1268 
1269  switch( ba.eventCode )
1270  case 2:// mouse up
1271  dfref df = $(package_path)
1272  wave /sdfr=df process_data
1273  variable ekin
1274  ekin = NumberByKey("KineticEnergy", note(process_data), "=", "\r")
1275  prompt ekin, "kinetic energy"
1276  doprompt "save etpi", ekin
1277  if (!v_flag)
1278  asp_save_output_etpi(ekin)
1279  endif
1280  break
1281  case -1:// control being killed
1282  break
1283  endswitch
1284 
1285  return 0
1286 };
1287 
1288 static variable bp_output_itx(WMButtonAction* ba){
1289  STRUCT WMButtonAction &ba
1290 
1291  switch( ba.eventCode )
1292  case 2:// mouse up
1294  break
1295  case -1:// control being killed
1296  break
1297  endswitch
1298 
1299  return 0
1300 };
1301 
1302 static variable bp_graph_update(WMButtonAction* ba){
1303  STRUCT WMButtonAction &ba
1304 
1305  switch( ba.eventCode )
1306  case 2:// mouse up
1308  break
1309  case -1:// control being killed
1310  break
1311  endswitch
1312 
1313  return 0
1314 };
1315 
1316 static variable bp_graph_png(WMButtonAction* ba){
1317  STRUCT WMButtonAction &ba
1318 
1319  switch( ba.eventCode )
1320  case 2:// mouse up
1321  dfref df = $(package_path)
1322  svar /sdfr=df source_path
1323  svar /sdfr=df output_graphname
1324  if (WinType(output_graphname) == 1)
1325  SavePICT /WIN=$output_graphname /E=-5 /B=144 /TRAN=0
1326  endif
1327  break
1328  case -1:// control being killed
1329  break
1330  endswitch
1331 
1332  return 0
1333 };
1334 
1335 static variable pmp_norm_alpha_mode(WMPopupAction* pa){
1336  STRUCT WMPopupAction &pa
1337 
1338  switch( pa.eventCode )
1339  case 2:// mouse up
1340  dfref df = $(package_path)
1341  nvar /sdfr=df norm_alpha_mode
1342  norm_alpha_mode = pa.popNum - 1
1343  break
1344  case -1:// control being killed
1345  break
1346  endswitch
1347 
1348  return 0
1349 };
1350 
1351 static variable pmp_norm_theta_mode(WMPopupAction* pa){
1352  STRUCT WMPopupAction &pa
1353 
1354  switch( pa.eventCode )
1355  case 2:// mouse up
1356  dfref df = $(package_path)
1357  nvar /sdfr=df norm_theta_mode
1358  norm_theta_mode = pa.popNum - 1
1359  break
1360  case -1:// control being killed
1361  break
1362  endswitch
1363 
1364  return 0
1365 };
1366 
1367 static variable pmp_norm_thetaphi_mode(WMPopupAction* pa){
1368  STRUCT WMPopupAction &pa
1369 
1370  switch( pa.eventCode )
1371  case 2:// mouse up
1372  dfref df = $(package_path)
1373  nvar /sdfr=df norm_thetaphi_mode
1374  norm_thetaphi_mode = pa.popNum - 1
1375  break
1376  case -1:// control being killed
1377  break
1378  endswitch
1379 
1380  return 0
1381 };
1382 
1383 static variable pmp_graph_mode(WMPopupAction* pa){
1384  STRUCT WMPopupAction &pa
1385 
1386  switch( pa.eventCode )
1387  case 2:// mouse up
1388  dfref df = $(package_path)
1389  nvar /sdfr=df graph_mode
1390  graph_mode = pa.popNum - 1
1391  break
1392  case -1:// control being killed
1393  break
1394  endswitch
1395 
1396  return 0
1397 };
1398 
1399 static variable pmp_graph_projection(WMPopupAction* pa){
1400  STRUCT WMPopupAction &pa
1401 
1402  switch( pa.eventCode )
1403  case 2:// mouse up
1404  dfref df = $(package_path)
1405  nvar /sdfr=df graph_projection
1406  graph_projection = pa.popNum - 1
1407  break
1408  case -1:// control being killed
1409  break
1410  endswitch
1411 
1412  return 0
1413 };
1414 
1415 static variable pmp_graph_colortable(WMPopupAction* pa){
1416  STRUCT WMPopupAction &pa
1417 
1418  switch( pa.eventCode )
1419  case 2:// mouse up
1420  dfref df = $(package_path)
1421  svar /sdfr=df graph_colortable
1422  graph_colortable = StringFromList(pa.popNum - 1, CTabList())
1424  break
1425  case -1:// control being killed
1426  break
1427  endswitch
1428 
1429  return 0
1430 };
1431 
static variable bp_norm_phi_preview(WMButtonAction *ba)
-
variable pizza_service_2(wave data, string nickname, wave m_theta, wave m_tilt, wave m_phi, variable npolar=defaultValue, variable nograph=defaultValue, variable folding=defaultValue, variable xpdplot=defaultValue)
create a pizza plot from a measured (energy-integrated) data strip
-
variable normalize_strip_theta(wave strip, wave theta, variable theta_offset=defaultValue, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
divide the strip by the average polar distribution.
-
static variable do_init_process(variable check)
initialize the process data with a copy of the raw data.
-
static variable preview_norm_alpha()
-
variable asp_calculate_output()
calculate the output using all enabled processing filters.
-
static variable check_norm_alpha()
-
variable asp_import_raw(wave raw_data)
import raw data
-
variable crop_strip(wave strip, variable xlo, variable xhi)
crop a strip at the sides.
-
variable ad_update_profiles(wave image)
update a profiles graph with new data.
-
variable asp_duplicate_output(string dest_name)
copy the output data to a new folder
-
variable asp_save_output_itx()
save the output diffractogram to an igor text file
-
string display_hemi_scan(string nickname, variable projection=defaultValue, variable graphtype=defaultValue, variable do_ticks=defaultValue, variable do_grids=defaultValue, string graphname=defaultValue)
display a plot of a hemispherical angle scan.
-
static variable pmp_graph_colortable(WMPopupAction *pa)
-
static variable save_prefs()
save persistent package data to the preferences file.
-
static variable bp_graph_update(WMButtonAction *ba)
-
dfr find_hemi_data(string nickname, string *prefix, string *intwave)
finds the folder, prefix and name of holo waves given their nick name
-
static variable bp_norm_alpha_preview(WMButtonAction *ba)
-
static variable preview_crop_alpha()
-
static variable pmp_norm_alpha_mode(WMPopupAction *pa)
-
static variable init_package()
-
static variable preview_norm_theta()
-
static variable bp_norm_thetaphi_check(WMButtonAction *ba)
-
static variable bp_norm_theta_preview(WMButtonAction *ba)
-
static variable do_crop_alpha(variable check, variable force=defaultValue)
alpha-crop the process data.
-
static const string package_path
data folder path
-
static variable bp_crop_alpha_preview(WMButtonAction *ba)
-
static variable do_norm_thetaphi(variable check, variable force=defaultValue)
theta,phi-normalize the process data.
-
static variable bp_output_etpi(WMButtonAction *ba)
-
variable asp_display_dist_check(variable xdist, variable ydist)
display a graph window of the distribution checks.
-
static variable bp_graph_png(WMButtonAction *ba)
-
static variable pmp_graph_mode(WMPopupAction *pa)
-
static variable preview_norm_phi()
-
static variable pmp_norm_theta_mode(WMPopupAction *pa)
-
static variable do_norm_phi(variable check, variable force=defaultValue)
phi-normalize the process data.
-
static variable bp_norm_thetaphi_preview(WMButtonAction *ba)
-
static variable do_norm_theta(variable check, variable force=defaultValue)
theta-normalize the process data.
-
static variable check_norm_phi()
-
static const string prefs_objects
semicolon-separated list of persistent variable, string, and wave names
-
variable asp_show_panel()
create the angle scan processing panel
-
static variable bp_output_calc(WMButtonAction *ba)
-
static variable arrange_controls()
-
static variable bp_norm_theta_check(WMButtonAction *ba)
-
variable save_hemi_scan(string nickname, string pathname, string filename)
save a hemispherical scan to an Igor text file
-
variable normalize_strip_phi(wave strip, wave theta, wave phi, variable theta_offset=defaultValue, variable theta_range=defaultValue, variable check=defaultValue)
divide the strip by a sine function in phi (wobble correction).
-
variable normalize_strip_thetaphi(wave strip, wave theta, wave phi, variable theta_offset=defaultValue, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
divide the strip by a smooth polar-azimuthal distribution.
-
const variable kProjStereo
-
static variable update_menus()
update the popup menus to reflect the values of the global variables
-
static variable bp_output_itx(WMButtonAction *ba)
-
variable asp_close_graphs()
close all graphs created by the angle scan panel
-
static variable do_norm_alpha(variable check, variable force=defaultValue)
alpha-normalize the process data.
-
string ad_display_profiles(wave image, string filter=defaultValue)
open a new profiles graph window.
-
static variable load_prefs()
load persistent package data from the preferences file.
-
static variable check_norm_theta()
-
variable set_contrast(variable pcmin, variable pcmax, string graphname=defaultValue, string colortable=defaultValue)
set the pseudocolor contrast by percentile.
-
variable asp_display_previews()
display a graph window of the processed data.
-
variable asp_save_output_etpi(variable ekin)
save the output diffractogram to a PMSCO ETPI file
-
static variable bp_output_duplicate(WMButtonAction *ba)
-
static variable bp_norm_alpha_check(WMButtonAction *ba)
-
static variable check_norm_thetaphi()
-
static variable bp_norm_phi_check(WMButtonAction *ba)
-
static variable bp_source_select(WMButtonAction *ba)
-
static variable AfterCompiledHook()
initialize package data once when the procedure is first loaded
-
variable asp_display_output()
display the output diffractogram in a new graph
-
variable duplicate_hemi_scan(string source_nickname, dfref dest_folder, string dest_nickname, variable xpdplot=defaultValue)
duplicate a hemispherical scan dataset.
-
static variable pmp_norm_thetaphi_mode(WMPopupAction *pa)
-
static variable preview_norm_thetaphi()
-
static const string package_name
package name is used as data folder name
-
variable asp_update_graph()
update graphs with new color table or contrast
-
interactive processing of angle scanned XPD data.
-
static variable pmp_graph_projection(WMPopupAction *pa)
-
variable normalize_strip_x(wave strip, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
divide the strip by the average X distribution.
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-anglescan-process_8ipf.html b/doc/html/pearl-anglescan-process_8ipf.html index 4710a90..6aa8286 100644 --- a/doc/html/pearl-anglescan-process_8ipf.html +++ b/doc/html/pearl-anglescan-process_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-anglescan-process.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
-
pearl-anglescan-process.ipf File Reference
+
pearl-anglescan-process.ipf File Reference
-

processing and holographic mapping of angle scanned XPD data. -More...

-
#include "pearl-vector-operations"
-#include "pearl-polar-coordinates"
-#include <New Polar Graphs>
-

Go to the source code of this file.

- - - - - -

-Namespaces

 PearlAnglescanProcess
 processing and holographic mapping of angle scanned XPD data.
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

variable strip_delete_frames (wave strip, variable qlo, variable qhi, wave theta, wave tilt, wave phi)
 delete a contiguous range of frames from a strip. More...
 
variable normalize_strip_x (wave strip, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
 divide the strip by the average X distribution. More...
 
variable normalize_strip_phi (wave strip, wave theta, wave phi, variable theta_offset=defaultValue, variable theta_range=defaultValue, variable check=defaultValue)
 divide the strip by a sine function in phi (wobble correction). More...
 
variable normalize_strip_theta (wave strip, wave theta, variable theta_offset=defaultValue, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
 divide the strip by the average polar distribution. More...
 
variable normalize_strip_thetaphi (wave strip, wave theta, wave phi, variable theta_offset=defaultValue, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
 divide the strip by a smooth polar-azimuthal distribution. More...
 
variable normalize_strip_2d (wave strip, wave theta, variable theta_offset=defaultValue, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
 divide the strip by a two-dimensional normalization function. More...
 
variable crop_strip (wave strip, variable xlo, variable xhi)
 crop a strip at the sides. More...
 
variable pizza_service (wave data, string nickname, variable theta_offset, variable tilt_offset, variable phi_offset, variable npolar=defaultValue, variable nograph=defaultValue, variable folding=defaultValue, variable xpdplot=defaultValue)
 create a pizza plot from a measured (energy-integrated) data strip More...
 
variable pizza_service_2 (wave data, string nickname, wave m_theta, wave m_tilt, wave m_phi, variable npolar=defaultValue, variable nograph=defaultValue, variable folding=defaultValue, variable xpdplot=defaultValue)
 create a pizza plot from a measured (energy-integrated) data strip More...
 
variable show_analyser_line (variable theta, variable tilt, variable phi, variable theta_offset, variable tilt_offset, variable phi_offset, variable npolar=defaultValue, variable nograph=defaultValue, variable xpdplot=defaultValue)
 calculate and display the line seen by the analyser for a specific emission angle More...
 
variable convert_angles_ttpd2polar (wave theta, wave tilt, wave phi, wave data, wave polar, wave azi)
 convert angles from TTPA (theta-tilt-phi-analyser) scheme to polar coordinates. More...
 
variable convert_angles_ttpa2polar (wave theta, wave tilt, wave phi, wave analyser, wave polar, wave azi)
 convert angles from TTPA (theta-tilt-phi-analyser) scheme to polar coordinates. More...
 
static variable line_average (wave source, wave dest)
 
static variable calc_nth (variable Theta_st, variable Theta_in, variable th, variable Phi_ran, variable Phi_ref, string Holomode)
 calculate the number of phis for a given theta More...
 
static variable calc_phi_step (variable Theta_in, variable th, variable Theta_st, variable Phi_ran, variable Phi_ref, string Holomode)
 calculate delta-phi for a given theta More...
 
static variable Calc_The_step (variable th, variable Theta_st, string Holomode)
 calculate delta-theta for a given theta More...
 
static variable CalcN_Theta (string HoloMode, variable Theta_in, variable Theta_ran, variable Theta_st)
 calculate the number of thetas for a pattern More...
 
variable make_hemi_grid (variable npol, string nickname, variable xpdplot=defaultValue)
 create a hemispherical, constant solid angle grid More...
 
string get_hemi_nickname (wave w)
 finds the nick name given any hemi wave More...
 
string get_hemi_prefix (wave w)
 finds the prefix given any hemi wave More...
 
dfr find_hemi_data (string nickname, string *prefix, string *intwave)
 finds the folder, prefix and name of holo waves given their nick name More...
 
variable clear_hemi_grid (string nickname)
 clear a hemispherical scan grid More...
 
variable duplicate_hemi_scan (string source_nickname, dfref dest_folder, string dest_nickname, variable xpdplot=defaultValue)
 duplicate a hemispherical scan dataset. More...
 
variable rotate_hemi_scan (string nickname, variable angle)
 azimuthally rotate a hemispherical scan dataset. More...
 
string display_hemi_scan (string nickname, variable projection=defaultValue, variable graphtype=defaultValue, variable do_ticks=defaultValue, variable do_grids=defaultValue, string graphname=defaultValue)
 display a plot of a hemispherical angle scan. More...
 
static string display_polar_graph (string graphname, variable angle_offset=defaultValue, variable do_ticks=defaultValue)
 displays an empty polar graph More...
 
static string draw_hemi_axes (string graphname, variable do_grids=defaultValue)
 draw polar and azimuthal grids in an existing polar graph. More...
 
variable draw_diffraction_cone (string graphname, string groupname, variable theta_axis, variable theta_inner, variable phi)
 draw the circle of a diffraction cone in a stereographic polar graph. More...
 
string display_scanlines (string nickname, variable alpha_lo, variable alpha_hi, wave m_theta, wave m_tilt, wave m_phi, variable folding=defaultValue, variable projection=defaultValue)
 display a polar graph with lines indicating the angles covered by an angle scan. More...
 
threadsafe variable calc_graph_radius (variable polar, variable projection=defaultValue)
 calculate the projected polar angle More...
 
threadsafe variable calc_graph_polar (variable x, variable y, variable projection=defaultValue)
 calculate polar angle from Cartesian coordinate More...
 
threadsafe variable calc_graph_azi (variable x, variable y, variable projection=defaultValue, variable zeroAngle=defaultValue)
 calculate azimuthal angle from Cartesian coordinate More...
 
static variable update_polar_info (string graphname)
 update the angles info based on cursors A and B of a given polar graph window More...
 
static variable polar_graph_hook (WMWinHookStruct *s)
 polar graph window hook More...
 
variable set_polar_graph_cursor (string nickname, string cursorname, variable polar_angle, variable azim_angle, string graphname=defaultValue)
 
variable hemi_add_anglescan (string nickname, wave values, wave polar, wave azi, wave weights=defaultValue)
 add an arbitrary angle scan to a hemispherical scan grid. More...
 
variable hemi_add_aziscan (string nickname, wave values, variable polar, wave azi, wave weights=defaultValue)
 add an azimuthal scan to a hemispherical scan grid. More...
 
variable interpolate_hemi_scan (string nickname)
 interpolate a hemispherical scan onto a rectangular grid More...
 
variable quick_pizza_image (wave data, string nickname, variable theta_offset, variable tilt_offset, variable phi_offset, variable npolar=defaultValue, variable nograph=defaultValue, variable folding=defaultValue)
 map angle scan data onto a rectangular grid in stereographic projection More...
 
variable save_hemi_scan (string nickname, string pathname, string filename)
 save a hemispherical scan to an Igor text file More...
 
variable load_hemi_scan (string nickname, string pathname, string filename)
 load a hemispherical scan from an Igor text file More...
 
variable import_tpi_scan (string nickname, wave theta, wave phi, wave intensity, variable folding=defaultValue, variable npolar=defaultValue, variable nograph=defaultValue, variable xpdplot=defaultValue)
 import a hemispherical scan from theta-phi-intensity waves and display it More...
 
variable trim_hemi_scan (string nickname, variable theta_max)
 trim a hemispherical scan at grazing angle More...
 
wave hemi_polar_cut (string nickname, variable azim)
 extract a polar cut from a hemispherical scan. More...
 
wave hemi_azi_cut (string nickname, variable pol)
 extract an azimuthal cut from a hemispherical scan More...
 
static variable check_contrast (wave values, variable pcmin, variable pcmax, variable *vmin, variable *vmax)
 
variable set_contrast (variable pcmin, variable pcmax, string graphname=defaultValue, string colortable=defaultValue)
 set the pseudocolor contrast by percentile. More...
 
- - - - - - - - - - - - - - - - - - - - - -

-Variables

const variable kProjDist = 0
 
const variable kProjStereo = 1
 
const variable kProjArea = 2
 
const variable kProjGnom = 3
 
const variable kProjOrtho = 4
 
static const variable kProjScaleDist = 2
 
static const variable kProjScaleStereo = 2
 
static const variable kProjScaleArea = 2
 
static const variable kProjScaleGnom = 0.06744519021
 
static const variable kProjScaleOrtho = 2
 
-

Detailed Description

-

processing and holographic mapping of angle scanned XPD data.

-

the functions in this file map angle scanned data measured at PEARL onto a hemispherical angle grid which is compatible with XPDplot. the resulting data are in a canonical polar coordinate system (normal emission <=> polar angle = 0, azimuthal axis right-handed) which is anchored in the sample surface. the orientation of polar graphs (phi = 0 at 3 o'clock) created by this procedure corresponds to a top view of the sample surface at normal emission, and the handle of the sample plate pointing to the left (phi = 180). this is the canonical orientation of a spherical coordinate system where phi = 0 corresponds to the positive part of the x axis.

-
Note
the orientation of the sample coordinate system has changed in version 1.6. the change was necessary for compatibility with other data analysis software and calculation programs.
-
-data imported with version 1.5 and earlier, must be offset by 180 deg in phi to be compatible with the new version. data imported and displayed by the same code version will give the same picture but with different azimuthal axis. the new graph functions shows a warning if they are applied to code imported with earlier versions.
-

the measurement geometry is hard-coded but may be parametrized in the future. the theta rotation axis is perpendicular to the scattering plane. the angle dispersive axis of the analyser is parallel to the theta rotation axis. the tilt rotation axis is in the scattering plane. it rotates with theta. at normal emission it is perpendicular to the axis of the lens stack of the analyser. the phi rotation axis corresponds to the surface normal of the sample. it rotates with theta and with tilt. at normal emission it is parallel to the axis of the lens stack of the analyser.

-

coordinate transformations: (to be revised - v1.6)

*      theta_sample = theta_manipulator - theta_offset
-*      phi_sample = phi_manipulator - phi_offset
-* 

valid for theta_manipulator = normal emission only: (to be revised - v1.6)

*      theta_sample = | -(tilt_manipulator - tilt_offset) |
-*      phi_sample = 270 if tilt_manipulator - tilt_offset > 0
-*      phi_sample = 90 if tilt_manipulator - tilt_offset < 0
-* 
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
- -
Version
1.8 canonical orientation of spherical coordinate system.
- -

Definition in file pearl-anglescan-process.ipf.

-

Function Documentation

- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe variable calc_graph_azi (variable x,
variable y,
variable projection = defaultValue,
variable zeroAngle = defaultValue 
)
-
- -

calculate azimuthal angle from Cartesian coordinate

-
Parameters
- - - - -
x,yprojected Cartesian coordinate
projectionmapping function from polar to cartesian coordinates. all supported projections are azimuthal, they have no effect on the azimuthal coordinate. see Projections for details.
    -
  • kProjDist = 0 azimuthal equidistant
  • -
  • kProjStereo = 1 stereographic (default)
  • -
  • kProjArea = 2 azimuthal equal-area
  • -
  • kProjGnom = 3 gnomonic (0 <= polar < 90)
  • -
  • kProjOrtho = 4 orthographic
  • -
-
zeroAnglezeroAngleWhere parameter of polar graphs
    -
  • 0 (default) zero is at the 3 o'clock position
  • -
  • 180 zero is at the 9 o'clock position
  • -
  • other values not tested
  • -
-
-
-
-
Returns
polar angle in degrees
- -

Definition at line 2203 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe variable calc_graph_polar (variable x,
variable y,
variable projection = defaultValue 
)
-
- -

calculate polar angle from Cartesian coordinate

-

this is the reverse mapping to calc_graph_radius()

-
Parameters
- - - -
x,yprojected Cartesian coordinate
projectionmapping function from polar to cartesian coordinates. see Projections for details.
    -
  • kProjDist = 0 azimuthal equidistant
  • -
  • kProjStereo = 1 stereographic (default)
  • -
  • kProjArea = 2 azimuthal equal-area
  • -
  • kProjGnom = 3 gnomonic (0 <= polar < 90)
  • -
  • kProjOrtho = 4 orthographic
  • -
-
-
-
-
Returns
polar angle in degrees
- -

Definition at line 2150 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
threadsafe variable calc_graph_radius (variable polar,
variable projection = defaultValue 
)
-
- -

calculate the projected polar angle

-
Parameters
- - - -
polarpolar angle in degrees
projectionmapping function from polar to cartesian coordinates. see Projections for details.
    -
  • kProjDist = 0 azimuthal equidistant
  • -
  • kProjStereo = 1 stereographic (default)
  • -
  • kProjArea = 2 azimuthal equal-area
  • -
  • kProjGnom = 3 gnomonic (0 <= polar < 90)
  • -
  • kProjOrtho = 4 orthographic
  • -
-
-
-
-
Returns
projected radius. the radius is scaled such that grazing emission maps to 2.
- -

Definition at line 2105 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable calc_nth (variable Theta_st,
variable Theta_in,
variable th,
variable Phi_ran,
variable Phi_ref,
string Holomode 
)
-
-static
-
- -

calculate the number of phis for a given theta

-

adapted from XPDplot 8.03

- -

Definition at line 1018 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable calc_phi_step (variable Theta_in,
variable th,
variable Theta_st,
variable Phi_ran,
variable Phi_ref,
string Holomode 
)
-
-static
-
- -

calculate delta-phi for a given theta

-

adapted from XPDplot 8.03

- -

Definition at line 1047 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - -
static variable Calc_The_step (variable th,
variable Theta_st,
string Holomode 
)
-
-static
-
- -

calculate delta-theta for a given theta

-

adapted from XPDplot 8.03

- -

Definition at line 1091 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable CalcN_Theta (string HoloMode,
variable Theta_in,
variable Theta_ran,
variable Theta_st 
)
-
-static
-
- -

calculate the number of thetas for a pattern

-

adapted from XPDplot 8.03

- -

Definition at line 1122 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable check_contrast (wave values,
variable pcmin,
variable pcmax,
variable * vmin,
variable * vmax 
)
-
-static
-
- -

Definition at line 3001 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - -
variable clear_hemi_grid (string nickname)
-
- -

clear a hemispherical scan grid

-

values and weights waves are set to zero. the intensity wave is set to NaN.

-
Parameters
- - -
nicknamefolder name or name prefix of holo waves. may be empty.
-
-
- -

Definition at line 1401 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable convert_angles_ttpa2polar (wave theta,
wave tilt,
wave phi,
wave analyser,
wave polar,
wave azi 
)
-
- -

convert angles from TTPA (theta-tilt-phi-analyser) scheme to polar coordinates.

-

the angles are in the manipulator coordinate system.

-
Parameters
- - - - - - - -
[in]thetaoffset-corrected theta angle, normal emission = 0, grazing emission = 90. one dimensional wave.
[in]tiltoffset-corrected tilt angle, normal emission = 0 same dimension size and scale as theta
[in]phiphi angle, range -360 < phi < +360 offset correction is optional as long as the angles lie in the accepted range. same dimension size and scale as theta
[in]analyseranalyser angle scale corresponding to the slices scale of Scienta. one dimensional wave. this values are constant regardless of manipulator angle.
[out]polarwave to receive the polar coordinates.
[out]aziwave to receive the azimuthal coordinates.
-
-
-

for the output parameters polar and azi, you need to pass in existing numeric waves. dimension size does not matter, the waves are redimensioned by the function so that they have the same dimensions as the intensity data set. X dimension = analyser scale, Y dimension = manipulator scan.

- -

Definition at line 957 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable convert_angles_ttpd2polar (wave theta,
wave tilt,
wave phi,
wave data,
wave polar,
wave azi 
)
-
- -

convert angles from TTPA (theta-tilt-phi-analyser) scheme to polar coordinates.

-

similar to convert_angles_ttpa2polar() but reads the analyser angles from the X scale of data

- -

Definition at line 918 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable crop_strip (wave strip,
variable xlo,
variable xhi 
)
-
- -

crop a strip at the sides.

-

the strip is cropped in place, data outside the region of interest is lost.

-
Parameters
- - - - -
[in,out]strip2D data, X-axis = analyser angle, Y-axis = arbitrary manipulator scan
[in]xlolowest analyser angle to keep (will be rounded to nearest existing point)
[in]xhihighest analyser angle to keep (will be rounded to nearest existing point)
-
-
-
Remarks
cropping should be done after smoothing and normalization operations to reduce artefacts.
- -

Definition at line 578 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string display_hemi_scan (string nickname,
variable projection = defaultValue,
variable graphtype = defaultValue,
variable do_ticks = defaultValue,
variable do_grids = defaultValue,
string graphname = defaultValue 
)
-
- -

display a plot of a hemispherical angle scan.

-

the scan data must exist in the current data folder. azimuth = 0 should be at 9 o'clock. then the orientation is the same as the sample at normal emission and phi = 0, the handle of the sample plate pointing to the left.

-
Parameters
- - - - - - - -
nicknamename prefix of holo waves. may be empty.
projectionmapping function from polar to cartesian coordinates. see Projections for details.
    -
  • kProjDist = 0 azimuthal equidistant
  • -
  • kProjStereo = 1 stereographic (default)
  • -
  • kProjArea = 2 azimuthal equal-area
  • -
  • kProjGnom = 3 gnomonic (0 <= polar < 90)
  • -
  • kProjOrtho = 4 orthographic
  • -
-
graphtypetype of graph
    -
  • 1 (pol, az) trace in Igor "New Polar" (default).
  • -
  • 2 XPDplot (reserved, not implemented).
  • -
  • 3 matrix in Igor "New Polar". the matrix wave is a 2D wave with X and Y scaling corresponding to the selected projection. matrix waves can be created by interpolate_hemi_scan(). note: the pol and az waves are required as well.
  • -
-
do_ticksselect which ticks to draw. value must be the arithmetic OR of all selected items. default: 3
    -
  • 0 none
  • -
  • 1 major azimuthal
  • -
  • 2 minor azimuthal S
  • -
-
do_gridsselect which grids to draw. value must be the arithmetic OR of all selected items. default: 3
    -
  • 0 none
  • -
  • 1 radius at 0 and 90 degree azimuth
  • -
  • 2 circle at 30 and 60 degree polar
  • -
-
graphnamename of graph window. default: nickname if empty, a default name is assigned. if a window with this name is existing, the function brings it to the front, and does nothing else.
-
-
-
Returns
the name of the graph window
- -

Definition at line 1601 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - -
static string display_polar_graph (string graphname,
variable angle_offset = defaultValue,
variable do_ticks = defaultValue 
)
-
-static
-
- -

displays an empty polar graph

-

the graph is drawn using Wavemetrics "New Polar Graphs.ipf".

-

initially the graph is empty. hemispherical scans are displayed by adding a trace that coveres the whole plot area, and setting the trace color to a function of the intensity. traces are added by calling WMPolarAppendTrace.

-

the following items of the graph > packages menu might be useful:

    -
  • modify polar graph
  • -
  • color table control
  • -
  • show polar cursors
  • -
  • polar graph legend
  • -
-

parameters can be changed programmatically as shown in the code of this function. after programmatic parameter changes, call WMPolarAxesRedrawGraphNow(graphname).

-
Parameters
- - - - -
graphnamerequested name of new graph window. if empty, a default name is assigned. if a window with this name is existing, the function brings it to the front, and does nothing else.
angle_offsetazimuth (on screen) where angle 0 is plotted (zeroAngleWhere parameter of polar graphs). starting with version 1.6, the default is 0. for hemi grids created with earlier versions, it should be set to 180 for correct orientation.
do_ticksselect which ticks to draw. value must be the arithmetic OR of all selected items. default: 3
    -
  • 0 none
  • -
  • 1 major azimuthal
  • -
  • 2 minor azimuthal
  • -
-
-
-
-
Returns
the name of the graph window.
-
Version
1.7 interface change: the trace drawing code is moved to display_hemi_scan, so that this function can be reused by other graph types, e.g. display_scanlines.
- -

Definition at line 1739 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string display_scanlines (string nickname,
variable alpha_lo,
variable alpha_hi,
wave m_theta,
wave m_tilt,
wave m_phi,
variable folding = defaultValue,
variable projection = defaultValue 
)
-
- -

display a polar graph with lines indicating the angles covered by an angle scan.

-
Parameters
- - - - - - - - - -
nicknamenick name for output data. this will become the name of a child folder containing the output.
alpha_lolow limit of the analyser angle.
alpha_hihigh limit of the analyser angle.
m_thetamanipulator theta angles, 0 = normal emission. size = dimsize(data, 1)
m_tiltmanipulator tilt angles, 0 = normal emission. size = dimsize(data, 1)
m_phimanipulator phi angles, 0 = azimuthal origin. size = dimsize(data, 1)
foldingrotational averaging, default = 1
projectionmapping function from polar to cartesian coordinates. see calc_graph_radius().
-
-
-
Remarks
this function is extremely slow.
- -

Definition at line 1990 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable draw_diffraction_cone (string graphname,
string groupname,
variable theta_axis,
variable theta_inner,
variable phi 
)
-
- -

draw the circle of a diffraction cone in a stereographic polar graph.

-

the diffraction cone consists of a circle marking the diffraction ring, and a dot marking the axis. the cone is drawn as a group of draw objects on the UserFront layer. the objects can be edited interactively.

-
Parameters
- - - - - - -
graphnamename of graph window (not implemented yet).
groupnamename of a drawing group. if the group exists (from a previous cone) it is replaced. if the group doesn't exist, a new one is created.
theta_axispolar angle of the cone axis in degrees.
theta_innerpolar angle of the innermost point of the circle in degrees.
phiazimuthal angle of the cone axis in degrees.
-
-
-
Warning
EXPERIMENTAL! this function is under development. the interface and behaviour of this function may change significantly in future versions.
- -

Definition at line 1926 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static string draw_hemi_axes (string graphname,
variable do_grids = defaultValue 
)
-
-static
-
- -

draw polar and azimuthal grids in an existing polar graph.

-

the function adds the following draw objects to a polar graph:

    -
  • concentric circles at polar angles 0, 30, and 60 degrees with labels.
  • -
  • radial axes at 0 and 90 degree azimuth.
  • -
-

the objects are added to the ProgFront drawing layer and will appear in front of the data trace. in interactive drawing mode, you can select the active drawing layer by clicking the tree icon while holding the Alt key.

-

the graph must have been created by display_polar_graph(). the function reads the projection mode from the window user data "projection".

-
Parameters
- - - -
graphnamename of graph window.
do_gridsselect which optional grids to draw. value must be the arithmetic OR of all selected items. default: 3
    -
  • 0 none
  • -
  • 1 radius at 0 and 90 degree azimuth
  • -
  • 2 circle at 30 and 60 degree polar
  • -
-
-
-
-
Warning
EXPERIMENTAL! this function is under development. the interface and behaviour of this function may change significantly in future versions.
- -

Definition at line 1854 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable duplicate_hemi_scan (string source_nickname,
dfref dest_folder,
string dest_nickname,
variable xpdplot = defaultValue 
)
-
- -

duplicate a hemispherical scan dataset.

-

this function works only for hemi scans created by make_hemi_grid() (or compatible functions). the angle grid is recreated rather than copied point-by-point. the new dataset is independent from the original one.

-

if the version of the source dataset is pre 1.6, it is converted to version 1.6.

-
Parameters
- - - - - -
source_nicknamename prefix for waves. source data must be in current data folder.
dest_folderdestination folder. folder must exist.
dest_nicknamename prefix for destination waves. must be unique in the current data folder. otherwise existing waves get overwritten. may be empty.
xpdplotXPDplot compatibility
    -
  • 0 (default) create the data structures required by this module
  • -
  • 1 create additional waves and notebook required by XPDplot
  • -
-
-
-
- -

Definition at line 1448 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
dfr find_hemi_data (string nickname,
string * prefix,
string * intwave 
)
-
- -

finds the folder, prefix and name of holo waves given their nick name

-

the function looks for holo waves in the following order:

    -
  1. if nickname is empty, check for prefix-less waves in current folder.
  2. -
  3. if nickname is the name of a child folder in the current data folder, clear the (prefix-less) waves in the child folder.
  4. -
  5. nickname is prefix of waves in current folder.
  6. -
  7. nickname is prefix of waves in root folder.
  8. -
-
Parameters
- - - - -
[in]nicknamefolder name or name prefix of holo waves. may be empty.
[out]prefixname prefix of waves. may be empty.
[out]intwavename of intensity/values wave
-
-
-
Returns
reference of the data folder which contains the waves
- -

Definition at line 1367 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - -
string get_hemi_nickname (wave w)
-
- -

finds the nick name given any hemi wave

-

the nick name is either the name of a child folder in the current data folder (PEARL specification), or a prefix of the hemi wave names (XPDplot specification).

-
Returns
the nick name
- -

Definition at line 1311 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - -
string get_hemi_prefix (wave w)
-
- -

finds the prefix given any hemi wave

-

the prefix is the part of the wave name before the first underscore. the prefix is used by XPDplot where it is identical to the nick name. the prefix is empty in the PEARL specification.

-
Returns
the prefix
- -

Definition at line 1336 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable hemi_add_anglescan (string nickname,
wave values,
wave polar,
wave azi,
wave weights = defaultValue 
)
-
- -

add an arbitrary angle scan to a hemispherical scan grid.

-

the hemi grid must have been created in the current data folder by the make_hemi_grid function. the function determines the bin size at the given polar angle, and adds all data points which fall into a bin. a point which lies exactly on the upper boundary falls into the next bin. this function does not clear previous values before adding new data. values are added to the _tot wave, weights to the _wt wave. the intensity (_i) wave is calculated as _tot / _wt.

- -

Definition at line 2348 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable hemi_add_aziscan (string nickname,
wave values,
variable polar,
wave azi,
wave weights = defaultValue 
)
-
- -

add an azimuthal scan to a hemispherical scan grid.

-

the hemi grid must have been created in the current data folder by the make_hemi_grid function. the function determines the bin size at the given polar angle, and calculates the mean values of the data points which fall into a bin. a point which lies exactly on the upper boundary falls into the next bin.

- -

Definition at line 2418 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
wave hemi_azi_cut (string nickname,
variable pol 
)
-
- -

extract an azimuthal cut from a hemispherical scan

-

the function extracts all azimuthal angles that are present for the given polar angle.

-

the hemi grid must have been created in the current data folder by the make_hemi_grid function. correct ordering is required.

-
Parameters
- - - -
nicknamename of the scan dataset. can be empty if no prefix is used. the dataset must be in the current datafolder.
polpolar angle in degrees
-
-
-
Returns
reference of the created wave. the wave has the same name as the intensity wave of the dataset with the suffix "_azi" and the azimuthal angle rounded to integer. it is created in the same datafolder as the original data.
- -

Definition at line 2948 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
wave hemi_polar_cut (string nickname,
variable azim 
)
-
- -

extract a polar cut from a hemispherical scan.

-

for each polar angle, the function first extracts all azimuthal angles. the intensity is then interpolated between the nearest neighbours of the given azimuth.

-

the hemi grid must have been created in the current data folder by the make_hemi_grid function. correct ordering is required.

-
Parameters
- - - -
nicknamename of the scan dataset. can be empty if no prefix is used. the dataset must be in the current datafolder.
azimazimuthal angle in degrees
-
-
-
Returns
reference of the created wave. the wave has the same name as the intensity wave of the dataset with the suffix "_azi" and the azimuthal angle rounded to integer. it is created in the same datafolder as the original data.
- -

Definition at line 2862 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable import_tpi_scan (string nickname,
wave theta,
wave phi,
wave intensity,
variable folding = defaultValue,
variable npolar = defaultValue,
variable nograph = defaultValue,
variable xpdplot = defaultValue 
)
-
- -

import a hemispherical scan from theta-phi-intensity waves and display it

-

in the tpi format, the hemi scan data is represented by a triple of flat one-dimensional waves corresponding to the polar angle (theta), azimuthal angle (phi) and intensity. no specific sort order is required.

-
Parameters
- - - - - - - - - -
nicknamenick name for output data
    -
  • in default mode, this will become the name of a child folder containing the output.
  • -
  • in XPDplot mode, this will become a prefix of the generated data in the root folder.
  • -
-
thetatheta angles, 0 = normal emission.
phiphi angles, 0 = azimuthal origin. size = dimsize(data, 1)
intensityintensity wave, see requirements above.
npolarnumber of polar angles, determines polar and azimuthal step size. default = 91 (1 degree steps)
foldingrotational averaging. example: 3 = average to 3-fold symmetry. default = 1.
nographdisplay a new graph window?
    -
  • 0 (default) display a new polar graph
  • -
  • 1 don't display a new graph
  • -
-
xpdplotXPDplot compatibility
    -
  • 0 (default) create waves in child folder $nickname
  • -
  • 1 create waves in root folder (compatible with XPDplot)
  • -
-
-
-
- -

Definition at line 2774 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - -
variable interpolate_hemi_scan (string nickname)
-
- -

interpolate a hemispherical scan onto a rectangular grid

-

the interpolated data is written to a new two-dimensional wave "matrix". the wave has a fixed size of 181 x 181 points optimized for 1-degree polar steps.

-

the function requires the ster_x and ster_y waves that are created by display_hemi_scan, and thus implicitly uses the same projection.

-

missing values (nan) are interpolated. this works well only if the missing values are reasonable sparse. the function also applies a gaussian filter to smooth the image. empty rings at high polar angles map are preserved.

-

to display the result call display_hemi_scan() with graphtype=3.

- -

Definition at line 2524 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static variable line_average (wave source,
wave dest 
)
-
-static
-
- -

Definition at line 1000 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable load_hemi_scan (string nickname,
string pathname,
string filename 
)
-
- -

load a hemispherical scan from an Igor text file

-
Todo:
function not implemented
- -

Definition at line 2725 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable make_hemi_grid (variable npol,
string nickname,
variable xpdplot = defaultValue 
)
-
- -

create a hemispherical, constant solid angle grid

-

all necessary waves are created in the current data folder with step size 90 / (npol - 1)

-

adapted from XPDplot 8.03

-
Parameters
- - - - -
npolnumber of polar angles, determines polar and azimuthal step size. recommended 91 for 1-degree steps.
nicknamename prefix for waves. nick name must be unique in the current data folder. otherwise existing waves get overwritten. may be empty.
xpdplotXPDplot compatibility
    -
  • 0 (default) create the data structures required by this module
  • -
  • 1 create additional waves and notebook required by XPDplot
  • -
-
-
-
- -

Definition at line 1160 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable normalize_strip_2d (wave strip,
wave theta,
variable theta_offset = defaultValue,
variable smooth_method = defaultValue,
variable smooth_factor = defaultValue,
variable check = defaultValue 
)
-
- -

divide the strip by a two-dimensional normalization function.

-
Warning
experimental. this function is under development.
-
Parameters
- - -
checkenable output of intermediate results
    -
  • 0 (default) don't create additional waves
  • -
  • 1 create check waves in the current folder
  • -
  • 2 calculate check waves only, do not modify strip
  • -
-
-
-
-
Returns
if check waves are enabled, the following waves are created (overwritten if existing):
    -
  • check_dist average theta distribution
  • -
  • check_smoo smoothed distribution used to normalize the strip
  • -
-
- -

Definition at line 518 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable normalize_strip_phi (wave strip,
wave theta,
wave phi,
variable theta_offset = defaultValue,
variable theta_range = defaultValue,
variable check = defaultValue 
)
-
- -

divide the strip by a sine function in phi (wobble correction).

-

the sine function is a curve fit to the intensity integrated over detector angle with a period of 360.

-

this normalization may be useful if the intensity varies with a 360 periodicity in the azimuthal angle, e.g. due to misalignment of the surface normal and the azimuthal rotation axis of the manipulator (wobble). note, however, that this function does not correct other effects of wobble such as angle shifts.

-

the strip is normalized in place, previous data is overwritten.

-
Parameters
- - - - - - - -
[in,out]strip2D data, X-axis = analyser angle, Y-axis = arbitrary manipulator scan
[in]thetapolar manipulator angle.
[in]phiazimuthal manipulator angle, arbitrary offset.
[in]theta_offsettheta value corresponding to normal emission (default 0).
[in]theta_rangemaximum (offset corrected) theta to consider in the sine fit (default 10).
checkenable output of intermediate results
    -
  • 0 (default) don't create additional waves
  • -
  • 1 create check waves in the current folder
  • -
  • 2 calculate check waves only, do not modify strip
  • -
-
-
-
-
Returns
if check waves are enabled, the following waves are created (overwritten if existing):
    -
  • check_dist average theta distribution
  • -
  • check_smoo smoothed distribution used to normalize the strip
  • -
-
- -

Definition at line 270 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable normalize_strip_theta (wave strip,
wave theta,
variable theta_offset = defaultValue,
variable smooth_method = defaultValue,
variable smooth_factor = defaultValue,
variable check = defaultValue 
)
-
- -

divide the strip by the average polar distribution.

-

this is a simple way to remove the polar angle dependence. the strip is normalized in place, previous data is overwritten.

Parameters
- - - - - - - -
[in,out]strip2D data, X-axis = analyser angle, Y-axis = arbitrary manipulator scan
[in]thetapolar manipulator angle, 0 = normal emission, 90 = grazing emission
[in]theta_offset
[in]smooth_methodsmoothing method
    -
  • 0 none
  • -
  • 1 binomial (requires monotonic theta), see Igor's Smooth operation
  • -
  • 2 boxcar (requires monotonic theta), see Igor's Smooth operation
  • -
  • 3 polynomial fit per slice
  • -
  • 4 (default) Loess, see Igor's Loess operation
  • -
-caution: binomial and boxcar smoothing are not aware of theta. this may give unpredictable results if theta is non-monotonic.
[in]smooth_factorsmoothing parameter, depends on smooth_method
    -
  • binomial/boxcar: see Igor's Smooth operation
  • -
  • loess: see Igor's Loess operation, 0 <= smooth_factor <= 1, default 0.5
  • -
  • polynomial fit: polynomial degree, 1 = linear (default), 2 = quadratic
  • -
-
checkenable output of intermediate results
    -
  • 0 (default) don't create additional waves
  • -
  • 1 create check waves in the current folder
  • -
  • 2 calculate check waves only, do not modify strip
  • -
-
-
-
-
Returns
if check waves are enabled, the following waves are created (overwritten if existing):
    -
  • check_dist average theta distribution
  • -
  • check_smoo smoothed distribution used to normalize the strip
  • -
-
- -

Definition at line 353 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable normalize_strip_thetaphi (wave strip,
wave theta,
wave phi,
variable theta_offset = defaultValue,
variable smooth_method = defaultValue,
variable smooth_factor = defaultValue,
variable check = defaultValue 
)
-
- -

divide the strip by a smooth polar-azimuthal distribution.

-

this is a simple way to remove the polar angle dependence. in contrast to normalize_strip_theta this function also removes a smooth variation over azimuthal angles.

-

the strip is normalized in place, previous data is overwritten.

-
Warning
experimental. this function is under development.
-
Parameters
- - - - - - - - -
[in,out]strip2D data, X-axis = analyser angle, Y-axis = arbitrary manipulator scan
[in]thetapolar manipulator angle, 0 = normal emission, 90 = grazing emission
[in]phiazimuthal manipulator angle.
[in]theta_offset
[in]smooth_methodsmoothing method
    -
  • 0 none
  • -
  • 4 (default) Loess, see Igor's Loess operation
  • -
-
[in]smooth_factorsmoothing parameter, depends on smooth_method
    -
  • loess: see Igor's Loess operation, 0 <= smooth_factor <= 1, default 0.5
  • -
-
checkenable output of intermediate results
    -
  • 0 (default) don't create additional waves
  • -
  • 1 create check waves in the current folder
  • -
  • 2 calculate check waves only, do not modify strip
  • -
-
-
-
-
Returns
if check waves are enabled, the following waves are created (overwritten if existing):
    -
  • check_dist average theta distribution
  • -
  • check_smoo smoothed distribution used to normalize the strip
  • -
-
- -

Definition at line 451 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable normalize_strip_x (wave strip,
variable smooth_method = defaultValue,
variable smooth_factor = defaultValue,
variable check = defaultValue 
)
-
- -

divide the strip by the average X distribution.

-

this is a simple way to remove the effect of the angle-dependence of the analyser transmission function. the strip is normalized in place, previous data is overwritten.

-
Parameters
- - - - - -
[in,out]strip2D data, X-axis = analyser angle, Y-axis = arbitrary manipulator scan
[in]smooth_methodsmoothing method
    -
  • 0 none
  • -
  • 1 binomial, see Igor's Smooth operation
  • -
  • 2 boxcar, see Igor's Smooth operation
  • -
  • 3 scienta_ang_transm() function fit
  • -
  • 4 (default) LOESS smoothing, see Igor's Loess operation
  • -
-
[in]smooth_factornum parameter of Igor's Smooth operation. the default value depends on smooth_method. it is 0.5 for LOESS smoothing, 2 otherwise.
[in]checkenable output of intermediate results
    -
  • 0 (default) don't create additional waves
  • -
  • 1 create check waves in the current folder
  • -
  • 2 calculate check waves only, do not modify strip
  • -
-
-
-
-
Returns
if check waves are enabled, the following waves are created (overwritten if existing):
    -
  • check_dist average X distribution
  • -
  • check_smoo smoothed distribution used to normalize the strip
  • -
-
- -

Definition at line 185 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable pizza_service (wave data,
string nickname,
variable theta_offset,
variable tilt_offset,
variable phi_offset,
variable npolar = defaultValue,
variable nograph = defaultValue,
variable folding = defaultValue,
variable xpdplot = defaultValue 
)
-
- -

create a pizza plot from a measured (energy-integrated) data strip

-

accepts angle-scan data as returned by adh5_load_reduced(), maps them onto a hemispherical scan grid, and displays a polar graph.

-
Parameters
- - - - - - - - - - -
data2D intensity wave, see requirements above
    -
  • X-axis analyser angle
  • -
  • Y-axis manipulator scan. no specific ordering required. manipulator angle waves (ManipulatorTheta, ManipulatorTilt, ManipulatorPhi) must be in the subfolder attr below the data wave.
  • -
-
nicknamenick name for output data
    -
  • in default mode, this will become the name of a child folder containing the output.
  • -
  • in XPDplot mode, this will become a prefix of the generated data in the root folder.
  • -
-
theta_offsetmanipulator theta angle corresponding to normal emission. the offset is subtracted from the ManipulatorTheta wave before processing.
tilt_offsetmanipulator tilt angle corresponding to normal emission the offset is subtracted from the ManipulatorTilt wave before processing.
phi_offsetmanipulator phi angle corresponding to phi_result = 0 the offset is subtracted from the ManipulatorPhi wave before processing.
npolarnumber of polar angles, determines polar and azimuthal step size. default = 91 (1 degree steps)
foldingrotational averaging, default = 1
nographdisplay a new graph window?
    -
  • 0 (default) display a new polar graph
  • -
  • 1 don't display a new graph
  • -
-
xpdplotXPDplot compatibility
    -
  • 0 (default) create waves in child folder $nickname
  • -
  • 1 create waves in root folder (compatible with XPDplot)
  • -
-
-
-
-
Attention
if you modify the structure of the data wave, e.g. delete some angles, this function cannot be used because the manipulator settings do not correspond to the original manipulator waves! instead, create your own manipulator waves and use pizza_service_2().
- -

Definition at line 638 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable pizza_service_2 (wave data,
string nickname,
wave m_theta,
wave m_tilt,
wave m_phi,
variable npolar = defaultValue,
variable nograph = defaultValue,
variable folding = defaultValue,
variable xpdplot = defaultValue 
)
-
- -

create a pizza plot from a measured (energy-integrated) data strip

-

accepts angle-scan data as returned by adh5_load_reduced(), maps them onto a hemispherical scan grid, and displays a polar graph.

-

the behaviour of this function is the same as pizza_service() except that the manipulator waves are specified explicitly.

-
Parameters
- - - - - - - - - - -
data2D intensity wave, see requirements above
    -
  • X-axis analyser angle
  • -
  • Y-axis manipulator scan. no specific ordering required. manipulator angle waves (ManipulatorTheta, ManipulatorTilt, ManipulatorPhi) must be in the subfolder attr below the data wave.
  • -
-
nicknamenick name for output data
    -
  • in default mode, this will become the name of a child folder containing the output.
  • -
  • in XPDplot mode, this will become a prefix of the generated data in the root folder.
  • -
-
m_thetamanipulator theta angles, 0 = normal emission. size = dimsize(data, 1)
m_tiltmanipulator tilt angles, 0 = normal emission. size = dimsize(data, 1)
m_phimanipulator phi angles, 0 = azimuthal origin. size = dimsize(data, 1)
npolarnumber of polar angles, determines polar and azimuthal step size. default = 91 (1 degree steps)
foldingrotational averaging, default = 1
nographdisplay a new graph window?
    -
  • 0 (default) display a new polar graph
  • -
  • 1 don't display a new graph
  • -
-
xpdplotXPDplot compatibility
    -
  • 0 (default) create waves in child folder $nickname
  • -
  • 1 create waves in root folder (compatible with XPDplot)
  • -
-
-
-
- -

Definition at line 731 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable polar_graph_hook (WMWinHookStruct * s)
-
-static
-
- -

polar graph window hook

-

this hook converts the cursor positions to polar coordinates and displays them in a text box on the graph. the text box is visible while the cursor info box is visible.

- -

Definition at line 2283 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable quick_pizza_image (wave data,
string nickname,
variable theta_offset,
variable tilt_offset,
variable phi_offset,
variable npolar = defaultValue,
variable nograph = defaultValue,
variable folding = defaultValue 
)
-
- -

map angle scan data onto a rectangular grid in stereographic projection

-

accepts angle-scan data as returned by adh5_load_reduced, maps them onto a rectangular grid in stereographic projection

-
Parameters
- - -
data2D data wave, X-axis = analyser angle, Y-axis = manipulator scan (no specific ordering required)
-
-
-
Precondition
manipulator angles as attributes in attr folder next to the data wave
-
Warning
EXPERIMENTAL
- -

Definition at line 2581 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable rotate_hemi_scan (string nickname,
variable angle 
)
-
- -

azimuthally rotate a hemispherical scan dataset.

-

this function works only for hemi scans created by make_hemi_grid() (or compatible functions).

-
Parameters
- - - -
nicknamename prefix for waves. source data must be in current data folder.
angleazimuthal rotation angle in degrees.
-
-
- -

Definition at line 1523 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable save_hemi_scan (string nickname,
string pathname,
string filename 
)
-
- -

save a hemispherical scan to an Igor text file

- -

Definition at line 2692 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable set_contrast (variable pcmin,
variable pcmax,
string graphname = defaultValue,
string colortable = defaultValue 
)
-
- -

set the pseudocolor contrast by percentile.

-

set the minimum and maximum values of the pseudocolor scale such that a specified percentile of the distribution lies outside the limits.

-

the new contrast is applied to traces and images of the selected graph that have pseudocolor tables.

-

the function is not specific to angle scans. it can be used for any pseudocolor trace or image plots except contour plots.

-
Parameters
- - - - - -
pcminpercentile below the minimum color (0-100).
pcmaxpercentile above the maximum color (0-100).
graphnamename of graph. default: top graph.
colortablename of new colortable. default: keep current table.
-
-
- -

Definition at line 3037 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable set_polar_graph_cursor (string nickname,
string cursorname,
variable polar_angle,
variable azim_angle,
string graphname = defaultValue 
)
-
- -

Definition at line 2303 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable show_analyser_line (variable theta,
variable tilt,
variable phi,
variable theta_offset,
variable tilt_offset,
variable phi_offset,
variable npolar = defaultValue,
variable nograph = defaultValue,
variable xpdplot = defaultValue 
)
-
- -

calculate and display the line seen by the analyser for a specific emission angle

-

this can be used to compare to an hemispherical plot and check the manipulator angle.

-
Parameters
- - - - - - - - - - -
thetamanipulator theta angle
tiltmanipulator tilt angle
phimanipulator phi angle
theta_offsetmanipulator theta angle corresponding to normal emission
tilt_offsetmanipulator tilt angle corresponding to normal emission
phi_offsetmanipulator phi angle corresponding to phi_result = 0
npolarnumber of polar angles, determines polar and azimuthal step size. default = 91 (1 degree steps)
nographdisplay a new graph window?
    -
  • 0 (default) display a new polar graph
  • -
  • 1 don't display a new graph
  • -
-
xpdplotXPDplot compatibility
    -
  • 0 (default) create waves in child folder $nickname
  • -
  • 1 create waves in root folder (compatible with XPDplot)
  • -
-
-
-
-
Remarks
the function creates angle scan data under the nickname analyser.
- -

Definition at line 848 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable strip_delete_frames (wave strip,
variable qlo,
variable qhi,
wave theta,
wave tilt,
wave phi 
)
-
- -

delete a contiguous range of frames from a strip.

-

this can be used to remove a region of bad frames due to, e.g., measurement problems. the function operates on 2D intensity data and manipulator coordinates at the same time.

-
Parameters
- - - - - - - -
[in,out]strip2D data, X-axis = analyser angle, Y-axis = arbitrary manipulator scan. the result is written to the original wave.
[in,out]theta1D data, manipulator scan. the result is written to the original wave.
[in,out]tilt1D data, manipulator scan. the result is written to the original wave.
[in,out]phi1D data, manipulator scan. the result is written to the original wave.
[in]qlopoint index of first frame to delete.
[in]qhipoint index of last frame to delete. qhi must be greater or equal than qlo.
-
-
- -

Definition at line 105 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable trim_hemi_scan (string nickname,
variable theta_max 
)
-
- -

trim a hemispherical scan at grazing angle

-

the function recalaculates the values wave from totals and weights but sets elements above a given polar angle to nan.

-
Parameters
- - - -
nicknamename of the scan dataset. can be empty if no prefix is used. the dataset must be in the current datafolder.
theta_maxhighest polar angle to keep (0...90 degrees).
-
-
- -

Definition at line 2823 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable update_polar_info (string graphname)
-
-static
-
- -

update the angles info based on cursors A and B of a given polar graph window

-

the function reads the projection mode from the user data of the graph window and the zeroAngleWhere variable from the associated WMPolarGraph data folder.

-

the calculated angles are written to the csrA_theta, csrA_phi, csrB_theta, and csrB_phi global variables in the polar graph data folder. the angles text box of the graph updates from to these variables dynamically.

-
Parameters
- - -
graphnamename of polar graph window
-
-
- -

Definition at line 2248 of file pearl-anglescan-process.ipf.

- -
-
-

Variable Documentation

- -
-
- - - - -
const variable kProjArea = 2
-
- -

Definition at line 2080 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - -
const variable kProjDist = 0
-
- -

Definition at line 2078 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - -
const variable kProjGnom = 3
-
- -

Definition at line 2081 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - -
const variable kProjOrtho = 4
-
- -

Definition at line 2082 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kProjScaleArea = 2
-
-static
-
- -

Definition at line 2086 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kProjScaleDist = 2
-
-static
-
- -

Definition at line 2084 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kProjScaleGnom = 0.06744519021
-
-static
-
- -

Definition at line 2088 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kProjScaleOrtho = 2
-
-static
-
- -

Definition at line 2089 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kProjScaleStereo = 2
-
-static
-
- -

Definition at line 2085 of file pearl-anglescan-process.ipf.

- -
-
- -
-
- - - - -
const variable kProjStereo = 1
-
- -

Definition at line 2079 of file pearl-anglescan-process.ipf.

- -
-
diff --git a/doc/html/pearl-anglescan-process_8ipf_source.html b/doc/html/pearl-anglescan-process_8ipf_source.html index 759cd5b..585166d 100644 --- a/doc/html/pearl-anglescan-process_8ipf_source.html +++ b/doc/html/pearl-anglescan-process_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-anglescan-process.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma version = 1.8
3 #pragma IgorVersion = 6.2
4 #pragma ModuleName = PearlAnglescanProcess
5 #include "pearl-vector-operations"
6 #include "pearl-polar-coordinates"
7 #include <New Polar Graphs>
8 
9 // copyright (c) 2013-17 Paul Scherrer Institut
10 //
11 // Licensed under the Apache License, Version 2.0 (the "License");
12 // you may not use this file except in compliance with the License.
13 // You may obtain a copy of the License at
14 // http:///www.apache.org/licenses/LICENSE-2.0
15 //
16 // Please acknowledge the use of this code.
17 
76 
81 
82 
105 variable strip_delete_frames(wave strip, variable qlo, variable qhi, wave theta, wave tilt, wave phi){
106  wave strip// 2D data, X-axis = analyser angle, Y-axis = arbitrary manipulator scan
107  variable qlo
108  variable qhi
109  wave theta
110  wave tilt
111  wave phi
112 
113  if (qlo > qhi)
114  return -1
115  endif
116 
117  // source indices
118  variable snx = dimsize(strip, 0)
119  variable sny = dimsize(strip, 1)
120  variable sq1lo = 0
121  variable sq1hi = max(qlo-1, 0)
122  variable sq2lo = min(qhi+1, sny - 1)
123  variable sq2hi = dimsize(strip, 1) - 1
124 
125  // dest indices
126  variable dnx = snx
127  variable dny = sny - (sq2lo - sq1hi + 1)
128  variable dq1lo = 0
129  variable dq1hi = sq1hi
130  variable dq2lo = dq1hi + 1
131  variable dq2hi = dny - 1
132  variable q1ofs = sq1lo - dq1lo
133  variable q2ofs = sq2lo - dq2lo
134 
135  duplicate /free strip, strip_copy
136  redimension /n=(dnx,dny) strip
137  strip[][dq1lo,dq1hi] = strip_copy[p][q + q1ofs]
138  strip[][dq2lo,dq2hi] = strip_copy[p][q + q2ofs]
139 
140  duplicate /free theta, theta_copy
141  redimension /n=(dny) theta
142  theta[dq1lo,dq1hi] = theta_copy[p + q1ofs]
143  theta[dq2lo,dq2hi] = theta_copy[p + q2ofs]
144 
145  duplicate /free tilt, tilt_copy
146  redimension /n=(dny) tilt
147  tilt[dq1lo,dq1hi] = tilt_copy[p + q1ofs]
148  tilt[dq2lo,dq2hi] = tilt_copy[p + q2ofs]
149 
150  duplicate /free phi, phi_copy
151  redimension /n=(dny) phi
152  phi[dq1lo,dq1hi] = phi_copy[p + q1ofs]
153  phi[dq2lo,dq2hi] = phi_copy[p + q2ofs]
154 
155  return 0
156 };
157 
185 variable normalize_strip_x(wave strip, variable smooth_method = defaultValue, variable smooth_factor = defaultValue, variable check = defaultValue){
186  wave strip
187  variable smooth_method
188  variable smooth_factor
189  variable check
190 
191  if (ParamIsDefault(smooth_method))
192  smooth_method = 4
193  endif
194  if (ParamIsDefault(smooth_factor))
195  switch(smooth_method)
196  case 4:
197  smooth_factor = 0.5
198  break
199  default:
200  smooth_factor = 2
201  endswitch
202  endif
203  if (ParamIsDefault(check))
204  check = 0
205  endif
206 
207  // average over all scan positions
208  wave dist = ad_profile_x(strip, -inf, inf, "")
209  variable div = mean(dist)
210  dist /= div
211 
212  if (check)
213  duplicate /o dist, check_dist
214  endif
215 
216  // smooth distribution function
217  switch(smooth_method)
218  case 1:
219  Smooth /B /E=3 smooth_factor, dist
220  break
221  case 2:
222  Smooth /E=3 smooth_factor, dist
223  break
224  case 3:
225  make /n=1 /d /free fit_params
226  fit_scienta_ang_transm(dist, fit_params)
227  dist = scienta_ang_transm(fit_params, x)
228  break
229  case 4:
230  loess /smth=(smooth_factor) srcWave=dist
231  break
232  endswitch
233 
234  if (check)
235  duplicate /o dist, check_smoo
236  endif
237 
238  // divide
239  if (check != 2)
240  strip /= dist[p]
241  endif
242 };
243 
270 variable normalize_strip_phi(wave strip, wave theta, wave phi, variable theta_offset = defaultValue, variable theta_range = defaultValue, variable check = defaultValue){
271  wave strip
272  wave theta
273  wave phi
274  variable theta_offset
275  variable theta_range
276  variable check
277 
278  if (ParamIsDefault(check))
279  check = 0
280  endif
281  if (ParamIsDefault(theta_offset))
282  theta_offset = 0
283  endif
284  if (ParamIsDefault(theta_range))
285  theta_offset = 10
286  endif
287 
288  // average over analyser angles
289  wave dist = ad_profile_y(strip, -inf, inf, "")
290 
291  // smooth distribution function
292  duplicate /free dist, dist_smoo
293  duplicate /free theta, theta_int
294  theta_int = theta - theta_offset
295  duplicate /free phi, phi_int
296  setscale /p x phi_int[0], phi_int[1] - phi_int[0], waveunits(phi, -1), dist, dist_smoo
297 
298  extract /free /indx dist, red_idx, theta_int < theta_range
299  duplicate /free red_idx, red_dist, red_phi
300  red_dist = dist[red_idx]
301  red_phi = phi_int[red_idx]
302 
303  variable wavg = mean(red_dist)
304  make /n=4 /d /free coef
305  coef[0] = {wavg, wavg/100, pi/180, 0}
306  CurveFit /q /h="0010" /g /w=2 sin, kwcWave=coef, red_dist /x=red_phi
307  dist_smoo = coef[0] + coef[1] * sin(coef[2] * phi_int[p] + coef[3])
308 
309  // divide
310  if (check != 2)
311  strip = strip / dist_smoo[q] * coef[0]
312  endif
313 
314  // check
315  if (check)
316  duplicate /o dist, check_dist
317  duplicate /o dist_smoo, check_smoo
318  setscale /p x dimoffset(dist,0), dimdelta(dist,0), waveunits(dist,0), check_dist, check_smoo
319  endif
320 };
321 
353 variable normalize_strip_theta(wave strip, wave theta, variable theta_offset = defaultValue, variable smooth_method = defaultValue, variable smooth_factor = defaultValue, variable check = defaultValue){
354  wave strip
355  wave theta
356  variable theta_offset
357  variable smooth_method
358  variable smooth_factor
359  variable check
360 
361  if (ParamIsDefault(check))
362  check = 0
363  endif
364  if (ParamIsDefault(theta_offset))
365  theta_offset = 0
366  endif
367  if (ParamIsDefault(smooth_method))
368  smooth_method = 4
369  endif
370  if (ParamIsDefault(smooth_factor))
371  smooth_factor = 0.5
372  endif
373 
374  // average over analyser angles
375  wave dist = ad_profile_y(strip, -inf, inf, "")
376 
377  // smooth distribution function
378  duplicate /free dist, dist_smoo
379  duplicate /free theta, theta_int
380  theta_int = theta - theta_offset
381  setscale /p x theta_int[0], theta_int[1] - theta_int[0], waveunits(theta,-1), dist, dist_smoo
382  variable nx = dimsize(strip, 0)
383  variable ix
384 
385  switch(smooth_method)
386  case 1:
387  Smooth /B /E=3 smooth_factor, dist_smoo
388  break
389  case 2:
390  Smooth /E=3 smooth_factor, dist_smoo
391  break
392  case 4:
393  loess /dest=dist_smoo /smth=(smooth_factor) srcWave=dist, factors={theta_int}
394  break
395  case 3:
396  for (ix = 0; ix < nx; ix += 1)
397  dist = strip[ix][p]
398  if (smooth_factor > 1)
399  CurveFit /nthr=0 /q /w=2 poly smooth_factor+1, dist /x=theta_int /d=dist_smoo
400  else
401  CurveFit /nthr=0 /q /w=2 line, dist /x=theta_int /d=dist_smoo
402  endif
403  strip[ix,ix][] /= dist_smoo[q]
404  endfor
405  dist_smoo = 1
406  break
407  endswitch
408 
409  // divide
410  if (check != 2)
411  strip /= dist_smoo[q]
412  endif
413 
414  // check
415  if (check)
416  duplicate /o dist, check_dist
417  duplicate /o dist_smoo, check_smoo
418  setscale /p x dimoffset(dist,0), dimdelta(dist,0), waveunits(dist,0), check_dist, check_smoo
419  endif
420 };
421 
451 variable normalize_strip_thetaphi(wave strip, wave theta, wave phi, variable theta_offset = defaultValue, variable smooth_method = defaultValue, variable smooth_factor = defaultValue, variable check = defaultValue){
452  wave strip
453  wave theta
454  wave phi
455  variable theta_offset
456  variable smooth_method
457  variable smooth_factor
458  variable check
459 
460  if (ParamIsDefault(check))
461  check = 0
462  endif
463  if (ParamIsDefault(theta_offset))
464  theta_offset = 0
465  endif
466  if (ParamIsDefault(smooth_method))
467  smooth_method = 4
468  endif
469  if (ParamIsDefault(smooth_factor))
470  smooth_factor = 0.5
471  endif
472 
473  // average over analyser angles
474  wave dist = ad_profile_y(strip, -inf, inf, "")
475 
476  // smooth distribution function
477  duplicate /free dist, dist_smoo
478  duplicate /free theta, theta_int
479  theta_int = theta - theta_offset
480  setscale /p x theta_int[0], theta_int[1] - theta_int[0], waveunits(theta,-1), dist, dist_smoo
481  variable nx = dimsize(strip, 0)
482  variable ix
483 
484  switch(smooth_method)
485  case 4:
486  loess /dest=dist_smoo /smth=(smooth_factor) srcWave=dist, factors={theta_int, phi}
487  break
488  default:
489  abort "smooth method not supported"
490  endswitch
491 
492  // divide
493  if (check != 2)
494  strip /= dist_smoo[q]
495  endif
496 
497  // check
498  if (check)
499  duplicate /o dist, check_dist
500  duplicate /o dist_smoo, check_smoo
501  setscale /p x dimoffset(dist,0), dimdelta(dist,0), waveunits(dist,0), check_dist, check_smoo
502  endif
503 };
504 
518 variable normalize_strip_2d(wave strip, wave theta, variable theta_offset = defaultValue, variable smooth_method = defaultValue, variable smooth_factor = defaultValue, variable check = defaultValue){
519  wave strip
520  wave theta
521  variable theta_offset
522  variable smooth_method
523  variable smooth_factor
524  variable check
525 
526  if (ParamIsDefault(check))
527  check = 0
528  endif
529  if (ParamIsDefault(theta_offset))
530  theta_offset = 0
531  endif
532  if (ParamIsDefault(smooth_method))
533  smooth_method = 4
534  endif
535  if (ParamIsDefault(smooth_factor))
536  smooth_factor = 0.5
537  endif
538 
539  variable nx = dimsize(strip, 0)
540  variable ny = dimsize(strip, 1)
541 
542  duplicate /free strip, dist, alpha_int, theta_int
543  theta_int = theta[q] - theta_offset
544  alpha_int = dimoffset(strip, 0) + p * dimdelta(strip, 0)
545  redimension /n=(nx * ny) dist, alpha_int, theta_int
546 
547  switch(smooth_method)
548  case 4:
549  loess /dest=dist_smoo /smth=(smooth_factor) srcWave=dist, factors={alpha_int, theta_int}
550  redimension /n=(nx, ny) dist_smoo
551  break
552  default:
553  Abort "undefined smooth method"
554  break
555  endswitch
556 
557  // divide
558  if (check != 2)
559  strip /= dist_smoo
560  endif
561 
562  // check
563  if (check)
564  //duplicate /o dist, check_dist
565  duplicate /o dist_smoo, check_smoo
566  endif
567 };
568 
578 variable crop_strip(wave strip, variable xlo, variable xhi){
579  wave strip
580  variable xlo
581  variable xhi
582 
583  variable plo = round((xlo - dimoffset(strip, 0)) / dimdelta(strip, 0))
584  variable phi = round((xhi - dimoffset(strip, 0)) / dimdelta(strip, 0))
585  xlo = plo * dimdelta(strip, 0) + dimoffset(strip, 0)
586  xhi = phi * dimdelta(strip, 0) + dimoffset(strip, 0)
587  variable nx = phi - plo + 1
588  variable ny = dimsize(strip, 1)
589 
590  duplicate /free strip, strip_copy
591  redimension /n=(nx,ny) strip
592  strip = strip_copy[p + plo][q]
593  setscale /i x xlo, xhi, waveunits(strip, 0), strip
594 };
595 
638 variable pizza_service(wave data, string nickname, variable theta_offset, variable tilt_offset, variable phi_offset, variable npolar = defaultValue, variable nograph = defaultValue, variable folding = defaultValue, variable xpdplot = defaultValue){
639  wave data
640  string nickname
641  variable theta_offset
642  variable tilt_offset
643  variable phi_offset
644  variable npolar
645  variable nograph
646  variable folding
647  variable xpdplot
648 
649  if (ParamIsDefault(npolar))
650  npolar = 91
651  endif
652  if (ParamIsDefault(nograph))
653  nograph = 0
654  endif
655  if (ParamIsDefault(folding))
656  folding = 1
657  endif
658  if (ParamIsDefault(xpdplot))
659  xpdplot = 0
660  endif
661 
662  // sort out data folder structure
663  dfref saveDF = GetDataFolderDFR()
664  dfref dataDF = GetWavesDataFolderDFR(data)
665  setdatafolder dataDF
666  if (DataFolderExists(":attr"))
667  setdatafolder :attr
668  endif
669  dfref attrDF = GetDataFolderDFR()
670 
671  wave /sdfr=attrDF ManipulatorTheta
672  wave /sdfr=attrDF ManipulatorTilt
673  wave /sdfr=attrDF ManipulatorPhi
674 
675  if ((dimsize(ManipulatorTheta, 0) != dimsize(data, 1)) || (dimsize(ManipulatorTilt, 0) != dimsize(data, 1)) || (dimsize(ManipulatorPhi, 0) != dimsize(data, 1)))
676  Abort "Warning: The dimension size of the manipulator waves does not match the Y dimension of the data wave!\rIf you restructured the data wave, please use pizza_service_2 with properly scaled manipulator waves."
677  endif
678 
679  duplicate /free ManipulatorTheta, m_theta
680  duplicate /free ManipulatorTilt, m_tilt
681  duplicate /free ManipulatorPhi, m_phi
682 
683  m_theta -= theta_offset
684  m_tilt -= tilt_offset
685  m_phi -= phi_offset
686 
687  pizza_service_2(data, nickname, m_theta, m_tilt, m_phi, npolar=npolar, nograph=nograph, folding=folding, xpdplot=xpdplot)
688 
689  setdatafolder saveDF
690 };
691 
731 variable pizza_service_2(wave data, string nickname, wave m_theta, wave m_tilt, wave m_phi, variable npolar = defaultValue, variable nograph = defaultValue, variable folding = defaultValue, variable xpdplot = defaultValue){
732  wave data
733  string nickname
734  wave m_theta
735  wave m_tilt
736  wave m_phi
737  variable npolar
738  variable nograph
739  variable folding
740  variable xpdplot
741 
742  if (ParamIsDefault(npolar))
743  npolar = 91
744  endif
745  if (ParamIsDefault(nograph))
746  nograph = 0
747  endif
748  if (ParamIsDefault(folding))
749  folding = 1
750  endif
751  if (ParamIsDefault(xpdplot))
752  xpdplot = 0
753  endif
754 
755  if ((dimsize(m_theta, 0) != dimsize(data, 1)) || (dimsize(m_tilt, 0) != dimsize(data, 1)) || (dimsize(m_phi, 0) != dimsize(data, 1)))
756  Abort "Warning: The dimension size of the manipulator waves does not match the Y dimension of the data wave!"
757  endif
758 
759  string graphname = "graph_" + nickname
760  string outprefix = nickname
761 
762  // sort out data folder structure
763  dfref saveDF = GetDataFolderDFR()
764  dfref dataDF = GetWavesDataFolderDFR(data)
765  setdatafolder dataDF
766 
767  if (xpdplot)
768  setdatafolder root:
769  outprefix = nickname
770  else
771  setdatafolder dataDF
772  newdatafolder /s/o $nickname
773  outprefix = ""
774  endif
775  dfref destDF = GetDataFolderDFR()
776 
777  // performance monitoring
778  variable timerRefNum
779  variable /g pol_perf_secs
780  timerRefNum = startMSTimer
781 
782  duplicate /free m_tilt, corr_tilt
783  duplicate /free m_phi, corr_phi
784  corr_tilt = -m_tilt// checked 140702
785  corr_phi = m_phi// checked 140702
786 
787  make /n=1/d/free d_polar, d_azi
788 
789  convert_angles_ttpd2polar(m_theta, corr_tilt, corr_phi, data, d_polar, d_azi)
790  d_azi += 180// changed 151030 (v1.6)
791  make_hemi_grid(npolar, outprefix, xpdplot=xpdplot)
792  variable ifold
793  for (ifold = 0; ifold < folding; ifold += 1)
794  d_azi = d_azi >= 360 ? d_azi - 360 : d_azi
795  hemi_add_anglescan(outprefix, data, d_polar, d_azi)
796  d_azi += 360 / folding
797  endfor
798 
799  // normalize folding
800  if (strlen(outprefix))
801  string s_prefix = outprefix + "_"
802  string s_int = s_prefix + "i"
803  else
804  s_prefix = ""
805  s_int = "values"
806  endif
807  if (folding > 1)
808  wave values = $s_int
809  values /= folding
810  endif
811 
812  if (!nograph)
813  display_hemi_scan(outprefix, graphname = graphname)
814  endif
815 
816  if (timerRefNum >= 0)
817  pol_perf_secs = stopMSTimer(timerRefNum) / 1e6
818  endif
819 
820  setdatafolder saveDF
821 };
822 
848 variable show_analyser_line(variable theta, variable tilt, variable phi, variable theta_offset, variable tilt_offset, variable phi_offset, variable npolar = defaultValue, variable nograph = defaultValue, variable xpdplot = defaultValue){
849  variable theta
850  variable tilt
851  variable phi
852  variable theta_offset
853  variable tilt_offset
854  variable phi_offset
855  variable npolar
856  variable nograph
857  variable xpdplot
858 
859  string nickname = "analyser"
860 
861  if (ParamIsDefault(npolar))
862  npolar = 91
863  endif
864  if (ParamIsDefault(nograph))
865  nograph = 0
866  endif
867  if (ParamIsDefault(xpdplot))
868  xpdplot = 0
869  endif
870  string graphname = "graph_" + nickname
871  string outprefix = nickname
872 
873  // sort out data folder structure
874  dfref saveDF = GetDataFolderDFR()
875  dfref dataDF = saveDF
876  if (xpdplot)
877  setdatafolder root:
878  outprefix = nickname
879  else
880  setdatafolder dataDF
881  newdatafolder /s/o $nickname
882  outprefix = ""
883  endif
884  dfref destDF = GetDataFolderDFR()
885 
886  make /n=1 /free m_theta
887  make /n=1 /free m_tilt
888  make /n=1 /free m_phi
889  m_theta = theta - theta_offset
890  m_tilt = tilt - tilt_offset
891  m_tilt *= -1// checked 140702
892  m_phi = phi - phi_offset
893  //m_phi *= -1 // checked 140702
894 
895  make /n=60 /free data
896  setscale /i x -30, 30, data
897  data = x
898  make /n=1/d/free d_polar, d_azi
899 
900  convert_angles_ttpa2polar(m_theta, m_tilt, m_phi, data, d_polar, d_azi)
901  d_azi += 180// changed 151030 (v1.6)
902  d_azi = d_azi >= 360 ? d_azi - 360 : d_azi
903  make_hemi_grid(npolar, outprefix, xpdplot=xpdplot)
904  hemi_add_anglescan(outprefix, data, d_polar, d_azi)
905 
906  if (!nograph)
907  display_hemi_scan(outprefix, graphname = graphname)
908  endif
909 
910  setdatafolder saveDF
911 };
912 
917 
918 variable convert_angles_ttpd2polar(wave theta, wave tilt, wave phi, wave data, wave polar, wave azi){
919  wave theta, tilt, phi// see convert_angles_ttpa2polar
920  wave data// in, 1D or 2D
921  // X-scale must be set to analyser angle scale
922  wave polar, azi// see convert_angles_ttpa2polar
923 
924  make /n=(dimsize(data, 0)) /d /free ana
925  setscale /p x dimoffset(data, 0), dimdelta(data, 0), waveunits(data, 0), ana
926  ana = x
927  convert_angles_ttpa2polar(theta, tilt, phi, ana, polar, azi)
928 };
929 
957 variable convert_angles_ttpa2polar(wave theta, wave tilt, wave phi, wave analyser, wave polar, wave azi){
958  wave theta
959  wave tilt
960  wave phi
961  wave analyser
962  wave polar, azi
963 
964  variable nn = numpnts(theta)
965  variable na = numpnts(analyser)
966  redimension /n=(na, nn) polar, azi
967 
968  variable radius = 1// don't need to specify - everything is scalable
969 
970  // step 1: calculate cartesian detection vectors at normal emission
971  // this is simply a polar-cartesian mapping, independent of the manipulator
972  // phi=0 is in the polar rotation plane
973  make /n=(3,na) /d /free w_orig_polar, w_orig_cart, w_rot_cart, w_rot_polar
974  w_orig_polar[0][] = radius
975  w_orig_polar[1][] = analyser[q]
976  w_orig_polar[2][] = 0
977  polar2cart_wave(w_orig_polar, w_orig_cart)
978  // if the angle-dispersive axis was horizontal, we'd need to rotate the detector
979  //rotate_z_wave(w_orig_cart, 90)
980 
981  variable ii
982  for (ii = 0; ii < nn; ii += 1)
983  // step 2: rotate the detection vectors according to the manipulator angles
984  // the order of rotations is important because we rotate about fixed axes
985  // y-axis = tilt rotation axis
986  // x-axis = polar rotation axis
987  // z-axis = normal emission = azimuthal rotation axis
988  w_rot_cart = w_orig_cart
989  rotate_y_wave(w_rot_cart, -tilt[ii])
990  rotate_x_wave(w_rot_cart, -theta[ii])
991  rotate_z_wave(w_rot_cart, -phi[ii] - 90)
992  // map the vectors back to the sample coordinate system
993  cart2polar_wave(w_rot_cart, w_rot_polar)
994  // copy to output
995  polar[][ii] = w_rot_polar[1][p]
996  azi[][ii] = w_rot_polar[2][p]
997  endfor
998 };
999 
1000 static variable line_average(wave source, wave dest){
1001  // is this function used?
1002  wave source
1003  wave dest
1004 
1005  variable ii
1006  variable nn = dimsize(source, 1)
1007  make /n=(dimsize(source, 0))/d/free line
1008  for (ii = 0; ii < nn; ii += 1)
1009  line = source[p][ii]
1010  wavestats /q line
1011  dest[][ii] = line[p] / v_max
1012  endfor
1013 };
1014 
1018 static variable calc_nth(variable Theta_st, variable Theta_in, variable th, variable Phi_ran, variable Phi_ref, string Holomode){
1019  Variable Theta_st, Theta_in, th, Phi_ran, Phi_ref
1020  String Holomode
1021  Variable The_step
1022  Variable deg2rad=0.01745329
1023 
1024  if ( cmpstr(Holomode, "Stereographic") == 0)
1025  The_step =trunc( Phi_ran*sin(th*deg2rad)*Phi_ref/Theta_st )
1026  if(th==90)
1027  The_step =trunc( Phi_ran*sin(th*pi/180)*Phi_ref/Theta_st )
1028  endif
1029  else
1030  if (cmpstr(Holomode, "Parallel") == 0)
1031  The_step=trunc( Phi_ran*tan(th*deg2rad)*Phi_ref/Theta_st )
1032  else
1033  if ( cmpstr(Holomode, "h") == 0)
1034  The_step=trunc( th/Theta_in*Phi_ran/Theta_st )
1035  else
1036  //altro
1037  endif
1038  endif
1039  endif
1040 
1041  return(The_step)
1042 };
1043 
1047 static variable calc_phi_step(variable Theta_in, variable th, variable Theta_st, variable Phi_ran, variable Phi_ref, string Holomode){
1048  Variable Theta_in, th, Theta_st, Phi_ran, Phi_ref
1049  String Holomode
1050 
1051  Variable Phi_st
1052  Variable deg2rad=0.01745329
1053 
1054  if ( cmpstr(Holomode, "Stereographic") == 0 )
1055  if ((th < 0.5) || (trunc(Phi_ran*sin(th*deg2rad)*Phi_ref/Theta_st) == 0))
1056  Phi_st=0.0
1057  else
1058  Phi_st=Phi_ran/(trunc(Phi_ran*sin(th*deg2rad)*Phi_ref/Theta_st))
1059  endif
1060  if(th==90)
1061  Phi_st=2.0
1062  endif
1063  endif
1064 
1065  if ( cmpstr(Holomode, "Parallel") == 0 )
1066  if((th < 0.5) || (trunc(Phi_ran*tan(th*deg2rad)*Phi_ref/Theta_st) == 0))
1067  Phi_st=0.0
1068  else
1069  Phi_st=Phi_ran/(trunc(Phi_ran*tan(th*deg2rad)*Phi_ref/Theta_st))
1070  endif
1071  endif
1072 
1073  if ( cmpstr(Holomode, "h") == 0 )
1074  if((th < 0.5) || (trunc(Phi_ran*sin(th*deg2rad)*Phi_ref/Theta_st) == 0))
1075  Phi_st=0.0
1076  else
1077  Phi_st=Phi_ran/trunc(th/Theta_in*Phi_ran/Theta_st)
1078  endif
1079  endif
1080 
1081  if (Phi_st==0)
1082  Phi_st=360
1083  endif
1084 
1085  return(Phi_st)
1086 };
1087 
1091 static variable Calc_The_step(variable th, variable Theta_st, string Holomode){
1092  String Holomode
1093  Variable th, Theta_st
1094 
1095  Variable deg2rad=0.01745329, dt_loc,The_step
1096 
1097  if ( (cmpstr(Holomode, "Stereographic")) ==0 )
1098  The_step=Theta_st
1099  endif
1100 
1101  if ( (cmpstr(Holomode, "h")) ==0 )
1102  The_step=Theta_st
1103  endif
1104 
1105  if ( cmpstr(Holomode, "Parallel") == 0 )
1106  if(th < 89.5)
1107  dt_loc = Theta_st/cos(th*deg2rad)
1108  if(dt_loc > 10)
1109  dt_loc=10
1110  endif
1111  The_step=dt_loc
1112  else
1113  The_step=10
1114  endif
1115  endif
1116  return(The_step)
1117 };
1118 
1122 static variable CalcN_Theta(string HoloMode, variable Theta_in, variable Theta_ran, variable Theta_st){
1123  String HoloMode
1124  Variable Theta_in,Theta_ran,Theta_st
1125  Variable n_theta, aux, aux1,ii
1126 
1127  aux = Theta_in
1128  aux1= Theta_in - Theta_ran
1129  ii = 0
1130  do
1131  aux = aux - Calc_The_step(aux, Theta_st, HoloMode)
1132  if(aux<=Theta_in-Theta_ran)
1133  aux=Theta_in-Theta_ran
1134  endif
1135  ii = ii+1
1136  while((aux>aux1)%&(Theta_in-aux<=Theta_ran))//
1137  n_theta=ii+1
1138  Return(n_theta)
1139 };
1140 
1160 variable make_hemi_grid(variable npol, string nickname, variable xpdplot = defaultValue){
1161  variable npol
1162  string nickname
1163  variable xpdplot
1164 
1165  if (ParamIsDefault(xpdplot))
1166  xpdplot = 0
1167  endif
1168 
1169  string HoloMode = "h"
1170  variable Theta_in = 90
1171  variable Theta_ran = 90
1172  variable Theta_st = 90 / (npol - 1)
1173  variable Phi_ran = 360
1174  variable Phi_ref = 1
1175  variable Phi_in = 0
1176 
1177  variable n_theta = CalcN_Theta(HoloMode, Theta_in, Theta_ran, Theta_st)
1178 
1179  // wave names
1180  if (strlen(nickname))
1181  string s_prefix = nickname + "_"
1182  string s_int = s_prefix + "i"// Intensity wave (counts/sec)
1183  else
1184  s_prefix = ""
1185  s_int = "values"// "i" is not a valid wave name
1186  endif
1187  string s_polar = s_prefix + "pol"// thetas for each int-point of the holo
1188  string s_azim = s_prefix + "az"// phis for each int-point of the holo
1189 
1190  string s_index = s_prefix + "index"// starting index for each theta
1191  string s_theta = s_prefix + "th"// theta values
1192  string s_dphi = s_prefix + "dphi"// delta phis at each theta
1193  string s_nphis = s_prefix + "nphis"// number of phis at each theta
1194 
1195  string s_HoloData = s_prefix + "data"// All holo exp.- parameter information
1196  string s_HoloInfo = s_prefix + "info"
1197 
1198  // the following two waves are used by the pearl-anglescan procedures but not by XPDplot
1199  string s_tot = s_prefix + "tot"// accumulated counts at each point
1200  string s_weight = s_prefix + "wt"// total accumulation time at each point (arb. units)
1201 
1202  make /O/D/n=(n_theta) $s_index /wave=index
1203  make /O/D/n=(n_theta) $s_theta /wave=theta
1204  make /O/D/n=(n_theta) $s_dphi /wave=dphi
1205  make /O/D/n=(n_theta) $s_nphis /wave=nphis
1206 
1207  //---------- calculate phi-step-size for this theta:
1208  variable aux = Calc_The_step(Theta_in, Theta_st, HoloMode)
1209  dphi[0] = calc_phi_step(Theta_in, Theta_in, aux, Phi_ran, Phi_ref, HoloMode)
1210  Theta[0] = Theta_in
1211  nphis[0] = calc_nth(aux, Theta_in, Theta_in, Phi_ran, Phi_ref, HoloMode)
1212  Index[0] = nphis[0]
1213 
1214  //---------- calculate number of phis, phi-step, and starting-index for each theta:
1215  variable ii = 1
1216  do
1217  Theta[ii] = Theta[ii-1] - aux
1218  if(Theta[ii] <= Theta_in-Theta_ran)
1219  Theta[ii] = Theta_in-Theta_ran
1220  endif
1221  aux = Calc_The_step(Theta[ii], Theta_st, HoloMode)
1222  dphi[ii] = calc_phi_step(Theta_in, Theta[ii], aux, Phi_ran, Phi_ref, HoloMode)
1223  nphis[ii] = calc_nth(aux, Theta_in, Theta[ii], Phi_ran, Phi_ref, HoloMode)
1224  Index[ii] = Index[ii-1] + nphis[ii]
1225  ii=ii+1
1226  while(ii < n_theta)
1227 
1228  if (Index[n_theta-1]==Index[n_theta-2])
1229  Index[n_theta-1]=Index[n_theta-2]+1
1230  nphis[n_theta-1]=1
1231  endif
1232 
1233  variable NumPoints = sum(nphis, 0, numpnts(nphis))
1234 
1235  //---------- calculate theta and phi for each data point:
1236  make /O/D/N=(NumPoints) $s_polar /wave=polar, $s_azim /wave=azim
1237  note azim, "version=1.6"
1238 
1239  ii = 0
1240  variable StartIndex = 0
1241  variable EndIndex
1242  do
1243  EndIndex=Index[ii]
1244  Polar[StartIndex, EndIndex-1]=Theta[ii]
1245  Azim[StartIndex, EndIndex-1]= mod(Phi_ran+(x-StartIndex)*dphi[ii]+Phi_in,Phi_ran)
1246  ii = ii + 1
1247  StartIndex = EndIndex
1248  while(ii < n_theta)
1249 
1250  duplicate /o azim, $s_int /wave=values
1251  duplicate /o azim, $s_tot /wave=totals
1252  duplicate /o azim, $s_weight /wave=weights
1253  values = nan
1254  totals = 0
1255  weights = 0
1256 
1257  // XPDplot metadata
1258  if (xpdplot)
1259  string s_FileName = ""
1260  string s_Comment = "created by pearl-anglescan-process.ipf"
1261  string s_HoloMode = "Stereographic"
1262  variable /g gb_SpectraFile = 0
1263 
1264  Make/O/D/n=22 $s_HoloData /wave=HoloData
1265  HoloData[0] = NaN// v_StartKE
1266  HoloData[1] = NaN// v_StoppKE
1267  HoloData[6] = NumPoints
1268  HoloData[7] = Theta_in
1269  HoloData[8] = Theta_ran
1270  HoloData[9] = Theta_st
1271  HoloData[11] = Phi_in
1272  HoloData[12] = Phi_ran
1273  HoloData[13] = Theta_st
1274  HoloData[15] = Phi_ref
1275  HoloData[16] = Phi_ran
1276  HoloData[17] = 0// v_HoloBit (stereographic)
1277 
1278  Make/O/T/n=22 $s_HoloInfo /wave=HoloInfo
1279  HoloInfo[0] = s_FileName
1280  HoloInfo[1] = s_Comment
1281  HoloInfo[10] = s_HoloMode
1282  HoloInfo[11] = ""// s_MeasuringMode
1283 
1284  // notebook for XPDplot
1285  if (WinType(NickName) == 5)
1286  Notebook $NickName selection={startOfFile, endOfFile}
1287  Notebook $NickName text=""
1288  else
1289  NewNotebook /F=0 /K=1 /N=$NickName /W=(5,40,341,260)
1290  Notebook $NickName defaultTab=140
1291  Notebook $NickName statusWidth=300
1292  Notebook $NickName backRGB=(56797,56797,56797)
1293  Notebook $NickName pageMargins={80,80,80,80}
1294  Notebook $NickName fSize=10
1295  Notebook $NickName fStyle=0,textRGB=(65535,0,26214)
1296  Notebook $NickName textRGB=(65535,0,26214)
1297  endif
1298  Notebook $NickName text = "File:\t" + s_FileName + "\r"
1299  Notebook $NickName text = "*** " + s_Comment + " ***\r\r"
1300  Notebook $NickName text = "Angle-Mode:\t" + s_HoloMode + "\r"
1301  Notebook $NickName text = "XPDplot Nickname:\t" + NickName + "\r"
1302  endif
1303 };
1304 
1311 string get_hemi_nickname(wave w){
1312  wave w
1313 
1314  string prefix = get_hemi_prefix(w)
1315  string wname = nameofwave(w)
1316  string nickname
1317 
1318  if (strlen(prefix))
1319  nickname = prefix
1320  else
1321  string s_wave_df = GetWavesDataFolder(w, 1)
1322  dfref parent_df = $(s_wave_df + "::")
1323  nickname = GetDataFolder(0, parent_df)
1324  endif
1325 
1326  return nickname
1327 };
1328 
1336 string get_hemi_prefix(wave w){
1337  wave w
1338 
1339  string wname = nameofwave(w)
1340  string prefix
1341  if (ItemsInList(wname, "_") >= 2)
1342  prefix = StringFromList(0, wname, "_")
1343  else
1344  prefix = ""
1345  endif
1346 
1347  return prefix
1348 };
1349 
1367 dfr find_hemi_data(string nickname, string* prefix, string* intwave){
1368  string nickname
1369  string &prefix
1370  string &intwave
1371 
1372  dfref datadf
1373  prefix = ""
1374  intwave = "values"
1375  if (strlen(nickname))
1376  if (DataFolderExists(nickname))
1377  datadf = $nickname
1378  else
1379  datadf = getdatafolderdfr()
1380  prefix = nickname + "_"
1381  intwave = prefix + "i"
1382  if (exists(intwave) != 1)
1383  datadf = root:
1384  endif
1385  endif
1386  else
1387  datadf = getdatafolderdfr()
1388  prefix = ""
1389  intwave = "values"
1390  endif
1391  return datadf
1392 };
1393 
1401 variable clear_hemi_grid(string nickname){
1402  string nickname
1403 
1404  dfref datadf
1405  string s_prefix
1406  string s_int
1407  datadf = find_hemi_data(nickname, s_prefix, s_int)
1408 
1409  string s_totals = s_prefix + "tot"
1410  string s_weights = s_prefix + "wt"
1411 
1412  wave /sdfr=datadf /z w_values = $s_int
1413  wave /sdfr=datadf /z w_totals = $s_totals
1414  wave /sdfr=datadf /z w_weights = $s_weights
1415 
1416  if (waveexists(w_totals))
1417  w_totals = 0
1418  endif
1419  if (waveexists(w_weights))
1420  w_weights = 0
1421  endif
1422  if (waveexists(w_values))
1423  w_values = nan
1424  endif
1425 };
1426 
1448 variable duplicate_hemi_scan(string source_nickname, dfref dest_folder, string dest_nickname, variable xpdplot = defaultValue){
1449  string source_nickname
1450  dfref dest_folder
1451  string dest_nickname
1452  variable xpdplot
1453 
1454  if (ParamIsDefault(xpdplot))
1455  xpdplot = 0
1456  endif
1457 
1458  dfref savedf = getdatafolderdfr()
1459 
1460  // source data
1461  string s_prefix = ""
1462  string s_int = "values"
1463  dfref source_df = find_hemi_data(source_nickname, s_prefix, s_int)
1464  string s_polar = s_prefix + "pol"
1465  string s_azim = s_prefix + "az"
1466  string s_theta = s_prefix + "th"
1467  string s_tot = s_prefix + "tot"
1468  string s_weight = s_prefix + "wt"
1469  string s_matrix = s_prefix + "matrix"
1470 
1471  wave /sdfr=source_df theta1 = $s_theta
1472  wave /sdfr=source_df polar1 = $s_polar
1473  wave /sdfr=source_df azim1 = $s_azim
1474  wave /sdfr=source_df tot1 = $s_tot
1475  wave /sdfr=source_df weight1 = $s_weight
1476  wave /sdfr=source_df values1 = $s_int
1477  wave /sdfr=source_df /z matrix1 = $s_matrix
1478 
1479  variable npol = numpnts(theta1)
1480 
1481  setdatafolder dest_folder
1482  make_hemi_grid(npol, dest_nickname, xpdplot=xpdplot)
1483 
1484  // dest data
1485  dfref dest_df = find_hemi_data(dest_nickname, s_prefix, s_int)
1486  s_polar = s_prefix + "pol"
1487  s_azim = s_prefix + "az"
1488  s_theta = s_prefix + "th"
1489  s_tot = s_prefix + "tot"
1490  s_weight = s_prefix + "wt"
1491  s_matrix = s_prefix + "matrix"
1492 
1493  wave /sdfr=dest_df theta2 = $s_theta
1494  wave /sdfr=dest_df polar2 = $s_polar
1495  wave /sdfr=dest_df azim2 = $s_azim
1496  wave /sdfr=dest_df tot2 = $s_tot
1497  wave /sdfr=dest_df weight2 = $s_weight
1498  wave /sdfr=dest_df values2 = $s_int
1499 
1500  tot2 = tot1
1501  weight2 = weight1
1502  values2 = values1
1503  if (waveexists(matrix1))
1504  setdatafolder dest_df
1505  duplicate /o matrix1, $s_matrix
1506  endif
1507 
1508  if (!(NumberByKey("version", note(azim1), "=", "\r") >= 1.6))
1509  azim2 += 180// changed 151030 (v1.6)
1510  azim2 = azim2 >= 360 ? azim2 - 360 : azim2
1511  endif
1512 
1513  setdatafolder saveDF
1514 };
1515 
1523 variable rotate_hemi_scan(string nickname, variable angle){
1524  string nickname
1525  variable angle
1526 
1527  dfref savedf = getdatafolderdfr()
1528 
1529  string s_prefix = ""
1530  string s_int = "values"
1531  dfref df = find_hemi_data(nickname, s_prefix, s_int)
1532 
1533  string s_polar = s_prefix + "pol"
1534  string s_azim = s_prefix + "az"
1535  string s_tot = s_prefix + "tot"
1536  string s_weight = s_prefix + "wt"
1537 
1538  wave /sdfr=df polar = $s_polar
1539  wave /sdfr=df azim = $s_azim
1540  wave /sdfr=df tot = $s_tot
1541  wave /sdfr=df weight = $s_weight
1542  wave /sdfr=df values = $s_int
1543 
1544  azim += angle
1545  azim = azim < 0 ? azim + 360 : azim
1546  azim = azim >= 360 ? azim - 360 : azim
1547 
1548  duplicate /free polar, neg_polar
1549  neg_polar = -polar
1550  sort {neg_polar, azim}, polar, azim, tot, weight, values
1551 
1552  setdatafolder saveDF
1553 };
1554 
1601 string display_hemi_scan(string nickname, variable projection = defaultValue, variable graphtype = defaultValue, variable do_ticks = defaultValue, variable do_grids = defaultValue, string graphname = defaultValue){
1602  string nickname
1603  variable projection
1604  variable graphtype
1605  variable do_ticks
1606  variable do_grids
1607  string graphname
1608 
1609  dfref savedf = getdatafolderdfr()
1610 
1611  if (ParamIsDefault(projection))
1612  projection = 1
1613  endif
1614  if (ParamIsDefault(graphtype))
1615  graphtype = 1
1616  endif
1617  if (ParamIsDefault(do_ticks))
1618  do_ticks = 3
1619  endif
1620  if (ParamIsDefault(do_grids))
1621  do_grids = 3
1622  endif
1623  if (ParamIsDefault(graphname))
1624  if (strlen(nickname) > 0)
1625  graphname = nickname
1626  else
1627  graphname = GetDataFolder(0)
1628  endif
1629  endif
1630 
1631  // hemi grid waves
1632  string s_prefix = ""
1633  string s_int = "values"
1634  dfref df = find_hemi_data(nickname, s_prefix, s_int)
1635 
1636  string s_polar = s_prefix + "pol"
1637  string s_azim = s_prefix + "az"
1638  string s_matrix = s_prefix + "matrix"
1639 
1640  wave /sdfr=df /z values = $s_int
1641  wave /sdfr=df /z azim = $s_azim
1642  wave /sdfr=df /z polar = $s_polar
1643  wave /sdfr=df /z matrix = $s_matrix
1644 
1645  setdatafolder df
1646  string s_ster_rad = s_prefix + "ster_rad"
1647  duplicate /o polar, $s_ster_rad /wave=ster_rad
1648  ster_rad = calc_graph_radius(polar, projection=projection)
1649 
1650  string s_ster_x = s_prefix + "ster_x"
1651  string s_ster_y = s_prefix + "ster_y"
1652  duplicate /o azim, $s_ster_x /wave=ster_x, $s_ster_y /wave=ster_y
1653  ster_x = ster_rad * cos(azim * pi / 180)
1654  ster_y = ster_rad * sin(azim * pi / 180)
1655 
1656  variable azim_offset = 0
1657  if (!(NumberByKey("version", note(azim), "=", "\r") >= 1.6))
1658  DoAlert /T="display hemi scan" 0, "your dataset doesn't include the version 1.6 flag. if it was created with an earlier version that might be okay. please check that the orientation is correct!"
1659  azim_offset = 180// changed 151030 (v1.6)
1660  endif
1661 
1662  string s_trace
1663  switch(graphtype)
1664  case 1:
1665  graphname = display_polar_graph(graphname, angle_offset=azim_offset, do_ticks=do_ticks)
1666 
1667  s_trace = WMPolarAppendTrace(graphname, ster_rad, azim, 360)
1668  ModifyGraph /W=$graphname mode($s_trace)=2, lsize($s_trace)=2
1669  ModifyGraph /W=$graphname zColor($s_trace)={values,*,*,BlueGreenOrange,0}
1670 
1671  ColorScale /W=$graphname /C /N=text0 /E=2 /F=0 /B=1 /A=RB /X=0.00 /Y=0.00 trace=polarY0
1672  ColorScale /W=$graphname /C /N=text0 side=2, width=5, heightPct=40, frame=0.50, lblMargin=0
1673  ColorScale /W=$graphname /C /N=text0 nticks=2, minor=1, tickLen=4.00, tickThick=0.50
1674 
1675  SetWindow $graphname, userdata(projection)=num2str(projection)
1676  draw_hemi_axes(graphname, do_grids=do_grids)
1677  break
1678  case 3:
1679  graphname = display_polar_graph(graphname, angle_offset=azim_offset, do_ticks=do_ticks)
1680 
1681  s_trace = WMPolarAppendTrace(graphname, ster_rad, azim, 360)
1682  ModifyGraph /W=$graphname mode($s_trace)=0, lsize($s_trace)=0
1683  AppendImage /L=VertCrossing /B=HorizCrossing matrix
1684 
1685  ColorScale /W=$graphname /C /N=text0 /E=2 /F=0 /B=1 /A=RB /X=0.00 /Y=0.00 image=$s_matrix
1686  ColorScale /W=$graphname /C /N=text0 side=2, width=5, heightPct=40, frame=0.50, lblMargin=0
1687  ColorScale /W=$graphname /C /N=text0 nticks=2, minor=1, tickLen=4.00, tickThick=0.50
1688 
1689  SetWindow $graphname, userdata(projection)=num2str(projection)
1690  draw_hemi_axes(graphname, do_grids=do_grids)
1691  break
1692  endswitch
1693 
1694  setdatafolder savedf
1695  return graphname
1696 };
1697 
1739 static string display_polar_graph(string graphname, variable angle_offset = defaultValue, variable do_ticks = defaultValue){
1740 
1741  string graphname
1742  variable angle_offset
1743  variable do_ticks
1744 
1745  dfref savedf = GetDataFolderDFR()
1746 
1747  if (ParamIsDefault(angle_offset))
1748  angle_offset = 0
1749  endif
1750  if (ParamIsDefault(do_ticks))
1751  do_ticks = 3
1752  endif
1753 
1754  if ((strlen(graphname) == 0) || (wintype(graphname) == 0))
1755  Display /k=1 /W=(10,45,360,345)
1756  DoWindow /C $graphname
1757  graphname = WMNewPolarGraph("", graphname)
1758  WMPolarGraphSetVar(graphname, "zeroAngleWhere", angle_offset)
1759 
1760  WMPolarGraphSetVar(graphname, "angleAxisThick", 0.5)
1761  WMPolarGraphSetStr(graphname, "doMajorAngleTicks", "manual")
1762  WMPolarGraphSetVar(graphname, "majorAngleInc", 30)// major ticks in 30 deg steps
1763  WMPolarGraphSetVar(graphname, "minorAngleTicks", 2)// minor ticks in 10 deg steps
1764  WMPolarGraphSetStr(graphname, "angleTicksLocation", "Outside")
1765  WMPolarGraphSetVar(graphname, "doAngleTickLabelSubRange", 1)
1766  WMPolarGraphSetVar(graphname, "angleTickLabelRangeStart", 0)
1767  WMPolarGraphSetVar(graphname, "angleTickLabelRangeExtent", 90)
1768  WMPolarGraphSetStr(graphname, "angleTickLabelNotation", "%g")
1769 
1770  WMPolarGraphSetVar(graphname, "doPolarGrids", 0)
1771  WMPolarGraphSetVar(graphname, "doRadiusTickLabels", 0)
1772  WMPolarGraphSetStr(graphname, "radiusAxesWhere", " Off")// note the leading spaces, cf. WMPolarAnglesForRadiusAxes
1773  WMPolarGraphSetStr(graphname, "radiusTicksLocation", "Off")
1774 
1775  WMPolarGraphSetVar(graphname, "majorTickLength", 2)
1776  WMPolarGraphSetVar(graphname, "majorTickThick", 0.5)
1777  WMPolarGraphSetVar(graphname, "minorTickLength", 1)
1778  WMPolarGraphSetVar(graphname, "minorTickThick", 0.5)
1779  WMPolarGraphSetVar(graphname, "tickLabelOpaque", 0)
1780  WMPolarGraphSetVar(graphname, "tickLabelFontSize", 7)
1781 
1782  // changes
1783  if (do_ticks & 1)
1784  WMPolarGraphSetStr(graphname, "angleTicksLocation", "Outside")
1785  else
1786  WMPolarGraphSetStr(graphname, "angleTicksLocation", "Off")
1787  endif
1788  if (do_ticks & 2)
1789  WMPolarGraphSetVar(graphname, "doMinorAngleTicks", 1)
1790  else
1791  WMPolarGraphSetVar(graphname, "doMinorAngleTicks", 0)
1792  endif
1793 
1794  DoWindow /T $graphname, graphname
1795 
1796  // cursor info in angles
1797  string graphdf = "root:packages:WMPolarGraphs:" + graphname
1798  setdatafolder graphdf
1799  // current theta, phi coordinates are stored in global variables in the package folder of the graph
1800  variable /g csrA_theta
1801  variable /g csrA_phi
1802  variable /g csrB_theta
1803  variable /g csrB_phi
1804  // the text box is hidden initially. it shows up and hides with the cursor info box.
1805  string tb
1806  tb = "\\{"
1807  tb = tb + "\"A = (%.1f, %.1f)\","
1808  tb = tb + graphdf + ":csrA_theta,"
1809  tb = tb + graphdf + ":csrA_phi"
1810  tb = tb + "}"
1811  TextBox /W=$graphname /A=LT /B=1 /E=2 /F=0 /N=tb_angles /X=1 /Y=1 /V=0 tb
1812  tb = "\\{"
1813  tb = tb + "\"B = (%.1f, %.1f)\","
1814  tb = tb + graphdf + ":csrB_theta,"
1815  tb = tb + graphdf + ":csrB_phi"
1816  tb = tb + "}"
1817  AppendText /W=$graphname /N=tb_angles tb
1818  // updates are triggered by a window hook
1819  SetWindow $graphname, hook(polar_graph_hook)=PearlAnglescanProcess#polar_graph_hook
1820  else
1821  // graph window exists
1822  DoWindow /F $graphname
1823  endif
1824 
1825  setdatafolder savedf
1826  return graphname
1827 };
1828 
1854 static string draw_hemi_axes(string graphname, variable do_grids = defaultValue){
1855  string graphname
1856  variable do_grids
1857 
1858  if (ParamIsDefault(do_grids))
1859  do_grids = 3
1860  endif
1861 
1862  dfref savedf = GetDataFolderDFR()
1863 
1864  string sproj = GetUserData(graphname, "", "projection")
1865  variable projection = str2num("0" + sproj)
1866 
1867  SetDrawLayer /W=$graphname ProgFront
1868 
1869  // polar axis
1870  SetDrawEnv /W=$graphname xcoord=HorizCrossing, ycoord=VertCrossing
1871  SetDrawEnv /W=$graphname linethick= 0.5
1872  SetDrawEnv /W=$graphname dash=2
1873  SetDrawEnv /W=$graphname fillpat=0
1874  SetDrawEnv /W=$graphname fname="default", fsize=7
1875  SetDrawEnv /W=$graphname textxjust=1, textyjust=1
1876  //SetDrawEnv /W=$graphname linefgc=(65535,65535,65535)
1877  SetDrawEnv /W=$graphname save
1878 
1879  if (do_grids & 1)
1880  DrawLine /W=$graphname 0, -2, 0, 2
1881  DrawLine /W=$graphname -2, 0, 2, 0
1882  endif
1883 
1884  variable radi
1885  if (do_grids & 2)
1886  radi = calc_graph_radius(0.5, projection=projection)
1887  DrawOval /W=$graphname -radi, radi, radi, -radi
1888  radi = calc_graph_radius(30, projection=projection)
1889  DrawOval /W=$graphname -radi, radi, radi, -radi
1890  radi = calc_graph_radius(60, projection=projection)
1891  DrawOval /W=$graphname -radi, radi, radi, -radi
1892 
1893  SetDrawEnv /W=$graphname textxjust= 1,textyjust= 2
1894  SetDrawEnv /W=$graphname save
1895  radi = calc_graph_radius(30, projection=projection)
1896  DrawText /W=$graphname radi, -0.1, "30"
1897  radi = calc_graph_radius(60, projection=projection)
1898  DrawText /W=$graphname radi, -0.1, "60"
1899  endif
1900 
1901  setdatafolder savedf
1902 };
1903 
1926 variable draw_diffraction_cone(string graphname, string groupname, variable theta_axis, variable theta_inner, variable phi){
1927  string graphname
1928  string groupname
1929 
1930  variable theta_axis
1931  variable theta_inner
1932  variable phi
1933 
1934  variable r_axis = calc_graph_radius(theta_axis)
1935  variable r_inner = calc_graph_radius(theta_inner)
1936  variable r_outer = calc_graph_radius(2 * theta_axis - theta_inner)
1937 
1938  SetDrawEnv push
1939  SetDrawLayer UserFront
1940  DrawAction getgroup=$groupname, delete
1941  SetDrawEnv gstart, gname=$groupname
1942  variable xc, yc, xr, yr
1943 
1944  // cone periphery
1945  variable r_center = (r_outer + r_inner) / 2
1946  variable r_radius = (r_outer - r_inner) / 2
1947  xc = r_center * cos(phi * pi / 180)
1948  yc = r_center * sin(phi * pi / 180)
1949  xr = r_radius
1950  yr = r_radius
1951  SetDrawEnv xcoord=HorizCrossing, ycoord=VertCrossing
1952  SetDrawEnv dash=11, fillpat=0
1953  DrawOval xc - xr, yc - yr, xc + xr, yc + yr
1954 
1955  // cone axis
1956  xc = r_axis * cos(phi * pi / 180)
1957  yc = r_axis * sin(phi * pi / 180)
1958  r_radius = calc_graph_radius(2)
1959  xr = r_radius
1960  yr = r_radius
1961  SetDrawEnv xcoord=HorizCrossing, ycoord=VertCrossing
1962  SetDrawEnv fillfgc=(0,0,0)
1963  DrawOval xc - xr, yc - yr, xc + xr, yc + yr
1964 
1965  SetDrawEnv gstop
1966  SetDrawEnv pop
1967 };
1968 
1990 string display_scanlines(string nickname, variable alpha_lo, variable alpha_hi, wave m_theta, wave m_tilt, wave m_phi, variable folding = defaultValue, variable projection = defaultValue){
1991  string nickname
1992  variable alpha_lo
1993  variable alpha_hi
1994  wave m_theta
1995  wave m_tilt
1996  wave m_phi
1997  variable folding
1998  variable projection
1999 
2000  if (ParamIsDefault(folding))
2001  folding = 1
2002  endif
2003  if (ParamIsDefault(projection))
2004  projection = 1
2005  endif
2006 
2007  // sort out data folder structure
2008  dfref saveDF = GetDataFolderDFR()
2009  newdatafolder /s/o $nickname
2010  string graphname = "graph_" + nickname
2011 
2012  duplicate /free m_tilt, loc_m_tilt
2013  loc_m_tilt = -m_tilt
2014 
2015  make /n=1 /d /free d_polar, d_azi
2016  variable n_alpha = round(alpha_hi - alpha_lo) + 1
2017  make /n=(n_alpha) /d /free analyser
2018  setscale /i x alpha_lo, alpha_hi, "", analyser
2019  analyser = x
2020 
2021  convert_angles_ttpa2polar(m_theta, loc_m_tilt, m_phi, analyser, d_polar, d_azi)
2022  duplicate /free d_polar, d_radius
2023  d_radius = calc_graph_radius(d_polar, projection=projection)
2024  d_azi += 180// changed 151030 (v1.6)
2025 
2026  graphname = display_polar_graph(graphname)
2027  SetWindow $graphname, userdata(projection)=num2str(projection)
2028 
2029  variable ifold
2030  variable iang
2031  variable nang = numpnts(m_theta)
2032  string s_rad
2033  string s_azi
2034  string s_trace
2035  for (ifold = 0; ifold < folding; ifold += 1)
2036  d_azi = d_azi >= 360 ? d_azi - 360 : d_azi
2037  for (iang = 0; iang < nang; iang += 1)
2038  sprintf s_rad, "rad_%d_%d", ifold, iang
2039  duplicate /o analyser, $s_rad
2040  wave w_rad = $s_rad
2041  w_rad = d_radius[p][iang]
2042 
2043  sprintf s_azi, "azi_%d_%d", ifold, iang
2044  duplicate /o analyser, $s_azi
2045  wave w_azi = $s_azi
2046  w_azi = d_azi[p][iang]
2047 
2048  if (numtype(sum(w_rad)) == 0)
2049  s_trace = WMPolarAppendTrace(graphname, w_rad, w_azi, 360)
2050  ModifyGraph /w=$graphname mode($s_trace)=0, lsize($s_trace)=0.5
2051  endif
2052  endfor
2053  d_azi += 360 / folding
2054  endfor
2055 
2056  draw_hemi_axes(graphname)
2057 
2058  setdatafolder saveDF
2059  return graphname
2060 };
2061 
2078 const variable kProjDist = 0;
2079 const variable kProjStereo = 1;
2080 const variable kProjArea = 2;
2081 const variable kProjGnom = 3;
2082 const variable kProjOrtho = 4;
2083 
2084 static const variable kProjScaleDist = 2;
2085 static const variable kProjScaleStereo = 2;
2086 static const variable kProjScaleArea = 2;
2087 // scaled so that radius(gnom) = radius(stereo) for polar = 88
2088 static const variable kProjScaleGnom = 0.06744519021;
2089 static const variable kProjScaleOrtho = 2;
2090 
2105 threadsafe variable calc_graph_radius(variable polar, variable projection = defaultValue){
2106  variable polar
2107  variable projection
2108 
2109  if (ParamIsDefault(projection))
2110  projection = 1
2111  endif
2112 
2113  variable radius
2114  switch(projection)
2115  case kProjStereo:// stereographic
2116  radius = kProjScaleStereo * tan(polar / 2 * pi / 180)
2117  break
2118  case kProjArea:// equal area
2119  radius = kProjScaleArea * sin(polar / 2 * pi / 180)
2120  break
2121  case kProjGnom:// gnomonic
2122  radius = polar < 90 ? kProjScaleGnom * tan(polar * pi / 180) : inf
2123  break
2124  case kProjOrtho:// orthographic
2125  radius = kProjScaleOrtho * sin(polar * pi / 180)
2126  break
2127  default:// equidistant
2128  radius = kProjScaleDist * polar / 90
2129  endswitch
2130 
2131  return radius
2132 };
2133 
2150 threadsafe variable calc_graph_polar(variable x, variable y, variable projection = defaultValue){
2151  variable x
2152  variable y
2153  variable projection
2154 
2155  if (ParamIsDefault(projection))
2156  projection = 1
2157  endif
2158 
2159  variable radius
2160  variable polar
2161 
2162  radius = sqrt(x^2 + y^2)
2163  switch(projection)
2164  case kProjStereo:// stereographic
2165  polar = 2 * atan(radius / kProjScaleStereo) * 180 / pi
2166  break
2167  case kProjArea:// equal area
2168  polar = 2 * asin(radius / kProjScaleArea) * 180 / pi
2169  break
2170  case kProjGnom:// gnomonic
2171  polar = atan(radius / kProjScaleGnom) * 180 / pi
2172  break
2173  case kProjOrtho:// orthographic
2174  polar = asin(radius / kProjScaleOrtho) * 180 / pi
2175  break
2176  default:// equidistant
2177  polar = 90 * radius / kProjScaleDist
2178  endswitch
2179 
2180  return polar
2181 };
2182 
2203 threadsafe variable calc_graph_azi(variable x, variable y, variable projection = defaultValue, variable zeroAngle = defaultValue){
2204  variable x
2205  variable y
2206  variable projection
2207  variable zeroAngle
2208 
2209  if (ParamIsDefault(projection))
2210  projection = 1
2211  endif
2212  if (ParamIsDefault(zeroAngle))
2213  zeroAngle = 0
2214  endif
2215 
2216  variable azi
2217  if (x > 0)
2218  azi = atan(y / x) * 180 / pi
2219  else
2220  azi = atan(y / x) * 180 / pi + 180
2221  endif
2222 
2223  azi += zeroAngle
2224  if (azi < 0)
2225  azi += 360
2226  endif
2227  if (azi >= 360)
2228  azi -= 360
2229  endif
2230  if (numtype(azi) != 0)
2231  azi = 0
2232  endif
2233 
2234  return azi
2235 };
2236 
2248 static variable update_polar_info(string graphname){
2249  string graphname
2250 
2251  dfref savedf = GetDataFolderDFR()
2252 
2253  string graphdf = "root:packages:WMPolarGraphs:" + graphname
2254  setdatafolder graphdf
2255 
2256  nvar csrA_theta
2257  nvar csrA_phi
2258  nvar csrB_theta
2259  nvar csrB_phi
2260 
2261  string sproj = GetUserData(graphname, "", "projection")
2262  variable projection = str2num("0" + sproj)
2263  nvar zeroAngleWhere
2264 
2265  variable x = hcsr(A, graphname)
2266  variable y = vcsr(A, graphname)
2267  csrA_theta = calc_graph_polar(x, y, projection=projection)
2268  csrA_phi = calc_graph_azi(x, y, projection=projection, zeroAngle=zeroAngleWhere)
2269 
2270  x = hcsr(B, graphname)
2271  y = vcsr(B, graphname)
2272  csrB_theta = calc_graph_polar(x, y, projection=projection)
2273  csrB_phi = calc_graph_azi(x, y, projection=projection, zeroAngle=zeroAngleWhere)
2274 
2275  setdatafolder savedf
2276 };
2277 
2283 static variable polar_graph_hook(WMWinHookStruct* s){
2284  STRUCT WMWinHookStruct &s
2285 
2286  Variable hookResult = 0
2287 
2288  switch(s.eventCode)
2289  case 7:// cursor moved
2290  update_polar_info(s.winname)
2291  break
2292  case 20:// show info
2293  TextBox /W=$s.winname /N=tb_angles /C /V=1
2294  break
2295  case 21:// hide info
2296  TextBox /W=$s.winname /N=tb_angles /C /V=0
2297  break
2298  endswitch
2299 
2300  return hookResult// 0 if nothing done, else 1
2301 };
2302 
2303 variable set_polar_graph_cursor(string nickname, string cursorname, variable polar_angle, variable azim_angle, string graphname = defaultValue){
2304  string nickname
2305  string cursorname
2306  variable polar_angle
2307  variable azim_angle
2308  string graphname
2309 
2310  if (ParamIsDefault(graphname))
2311  if (strlen(nickname) > 0)
2312  graphname = nickname
2313  else
2314  graphname = GetDataFolder(0)
2315  endif
2316  endif
2317 
2318  string s_prefix = ""
2319  string s_int = "values"
2320  dfref df = find_hemi_data(nickname, s_prefix, s_int)
2321 
2322  string s_polar = s_prefix + "pol"
2323  string s_azim = s_prefix + "az"
2324  wave /sdfr=df /z azim = $s_azim
2325  wave /sdfr=df /z polar = $s_polar
2326 
2327  FindLevel /P /Q polar, polar_angle
2328  if (v_flag == 0)
2329  variable polar_level = floor(v_levelx)
2330  FindLevel /P /Q /R=[polar_level] azim, azim_angle
2331  if (v_flag == 0)
2332  variable azim_level = round(v_levelx)
2333  string tracename = "polarY0"
2334  Cursor /W=$graphname /P $cursorname $traceName azim_level
2335  endif
2336  endif
2337 };
2338 
2348 variable hemi_add_anglescan(string nickname, wave values, wave polar, wave azi, wave weights = defaultValue){
2349  string nickname// name prefix of holo waves.
2350  // may be empty.
2351  wave values// intensity values
2352  // the wave can be one- or two-dimensional.
2353  // no specific order required, the function sorts the arrays internally
2354  wave polar// polar coordinates. allowed range 0 <= theta <= 90
2355  // dimensions corresponding to value.
2356  wave azi// azimuthal coordinates. allowed range -360 <= phi < +360
2357  // dimensions corresponding to value.
2358  wave weights// total accumulation time of each point of values. default = 1
2359 
2360  if (ParamIsDefault(weights))
2361  duplicate /free values, weights
2362  weights = 1
2363  endif
2364 
2365  // quick check whether hemi grid is existing
2366  string s_prefix = ""
2367  string s_int = "values"
2368  dfref df = find_hemi_data(nickname, s_prefix, s_int)
2369 
2370  string s_polar = s_prefix + "pol"
2371  string s_azim = s_prefix + "az"
2372  string s_theta = s_prefix + "th"
2373 
2374  wave /sdfr=df /z w_values = $s_int
2375  wave /sdfr=df /z w_azim = $s_azim
2376  wave /sdfr=df /z w_polar = $s_polar
2377  wave /sdfr=df /z w_theta = $s_theta
2378  if (!waveexists(w_values) || !waveexists(w_azim) || !waveexists(w_polar))
2379  abort "Missing hemispherical scan grid. Please call make_hemi_grid() first."
2380  endif
2381 
2382  // make internal copies, one-dimensional, ordered in theta
2383  duplicate /free values, values_copy
2384  duplicate /free polar, polar_copy
2385  duplicate /free azi, azi_copy
2386  duplicate /free weights, weights_copy
2387  variable nn = dimsize(values, 0) * max(dimsize(values, 1), 1)
2388  redimension /n=(nn) values_copy, polar_copy, azi_copy, weights_copy
2389  sort /r polar_copy, polar_copy, azi_copy, values_copy, weights_copy
2390 
2391  variable pol
2392  variable pol_st = abs(w_theta[1] - w_theta[0])
2393  variable pol1, pol2
2394 
2395  duplicate /free azi_copy, azi_slice
2396  duplicate /free values_copy, values_slice
2397  duplicate /free weights_copy, weights_slice
2398  for (pol = 90; pol >= 0; pol -= pol_st)
2399  pol1 = pol - pol_st / 2
2400  pol2 = pol + pol_st / 2
2401  extract /free /indx polar_copy, sel, (pol1 < polar_copy) && (polar_copy <= pol2)
2402  if (numpnts(sel) > 0)
2403  redimension /n=(numpnts(sel)) azi_slice, values_slice, weights_slice
2404  azi_slice = azi_copy[sel]
2405  values_slice = values_copy[sel]
2406  weights_slice = weights_copy[sel]
2407  hemi_add_aziscan(nickname, values_slice, pol, azi_slice, weights=weights_slice)
2408  endif
2409  endfor
2410 };
2411 
2418 variable hemi_add_aziscan(string nickname, wave values, variable polar, wave azi, wave weights = defaultValue){
2419  string nickname// name prefix of holo waves.
2420  // may be empty.
2421  wave values// intensity values of the azimuthal scan at the positions given in the azi parameter
2422  variable polar// polar angle where to add the azi scan
2423  wave azi// angle positions of the azimuthal scan
2424  // acceptable range: >= -360 and < +360
2425  // no specific order required, the function sorts the array internally
2426  wave weights// total accumulation time of each point of values. default = 1
2427 
2428  if (ParamIsDefault(weights))
2429  duplicate /free values, weights
2430  weights = 1
2431  endif
2432 
2433  // hemi grid waves
2434  string s_prefix = ""
2435  string s_int = "values"
2436  dfref df = find_hemi_data(nickname, s_prefix, s_int)
2437 
2438  string s_totals = s_prefix + "tot"
2439  string s_weights = s_prefix + "wt"
2440  string s_polar = s_prefix + "pol"
2441  string s_azim = s_prefix + "az"
2442  string s_index = s_prefix + "index"
2443  string s_theta = s_prefix + "th"
2444  string s_dphi = s_prefix + "dphi"
2445  string s_nphis = s_prefix + "nphis"
2446 
2447  wave /sdfr=df w_polar = $s_polar
2448  wave /sdfr=df w_azim = $s_azim
2449  wave /sdfr=df w_values = $s_int
2450  wave /sdfr=df w_totals = $s_totals
2451  wave /sdfr=df w_weights = $s_weights
2452  wave /sdfr=df w_index = $s_index
2453  wave /sdfr=df w_theta = $s_theta
2454  wave /sdfr=df w_dphi = $s_dphi
2455  wave /sdfr=df w_nphis = $s_nphis
2456 
2457  // destination slice coordinates
2458  //polar = round(polar)
2459  //variable ipol = 90 - polar
2460  variable ipol = BinarySearch(w_theta, polar)
2461  if (ipol < 0)
2462  abort "assertion failed in hemi_add_aziscan(): polar angle not found in grid."
2463  endif
2464 
2465  variable d1, d2
2466  if (ipol >= 1)
2467  d1 = w_index[ipol - 1]
2468  else
2469  d1 = 0
2470  endif
2471  d2 = w_index[ipol] - 1
2472  variable nd = d2 - d1 + 1
2473  variable dphi = w_dphi[ipol]
2474  variable az1, az2
2475 
2476  // source slice coordinates
2477  // order the slice from -dphi/2 to 360-dphi/2
2478  azi = azi < 0 ? azi + 360 : azi
2479  azi = azi >= 360 - dphi/2 ? azi - 360 : azi
2480  duplicate /free values, sel_values
2481  duplicate /free weights, sel_weights
2482 
2483  // loop over destination
2484  variable id
2485  variable v1, v2, w1, w2
2486  for (id = 0; id < nd; id += 1)
2487  az1 = (id - 0.5) * dphi
2488  az2 = (id + 0.5) * dphi
2489  extract /free /indx azi, sel, (az1 <= azi) && (azi < az2)
2490  if (numpnts(sel) > 0)
2491  redimension /n=(numpnts(sel)) sel_values, sel_weights
2492  sel_values = values[sel]
2493  sel_weights = weights[sel]
2494  v1 = w_totals[d1 + id]
2495  w1 = w_weights[d1 + id]
2496  if ((numtype(v1) == 2) || (w1 <= 0))
2497  v1 = 0
2498  w1 = 0
2499  endif
2500  v2 = sum(sel_values)
2501  w2 = sum(sel_weights)
2502  w_totals[d1 + id] = v1 + v2
2503  w_weights[d1 + id] = w1 + w2
2504  endif
2505  endfor
2506  w_values[d1, d1 + nd - 1] = w_totals[p] / w_weights[p]
2507 };
2508 
2524 variable interpolate_hemi_scan(string nickname){
2525  string nickname
2526 
2527  dfref savedf = GetDataFolderDFR()
2528 
2529  string s_prefix = ""
2530  string s_int = "values"
2531  dfref df = find_hemi_data(nickname, s_prefix, s_int)
2532 
2533  string s_polar = s_prefix + "pol"
2534  string s_azim = s_prefix + "az"
2535  string s_ster_x = s_prefix + "ster_x"
2536  string s_ster_y = s_prefix + "ster_y"
2537 
2538  wave /sdfr=df values = $s_int
2539  wave /sdfr=df azim = $s_azim
2540  wave /sdfr=df polar = $s_polar
2541  wave /sdfr=df ster_x = $s_ster_x
2542  wave /sdfr=df ster_y = $s_ster_y
2543 
2544  variable min_ster_x = wavemin(ster_x)
2545  variable max_ster_x = wavemax(ster_x)
2546  variable x0 = min_ster_x
2547  variable xn = 181
2548  variable dx = (max_ster_x - min_ster_x) / (xn - 1)
2549  make /n=(numpnts(ster_x), 3) /free triplet
2550  triplet[][0] = ster_x[p]
2551  triplet[][1] = ster_y[p]
2552  triplet[][2] = values[p]
2553 
2554  variable size = 181
2555  setdatafolder df
2556  make /n=(size, size) /d /o $(s_prefix + "matrix") /wave=matrix
2557  make /n=(size, size) /free mnorm
2558  ImageFromXYZ /as {ster_x, ster_y, values}, matrix, mnorm
2559  matrix /= mnorm
2560  matrixfilter NanZapMedian, matrix
2561  matrixfilter gauss, matrix
2562 
2563  duplicate /free values, ster_finite
2564  ster_finite = (numtype(values) == 0) * (ster_x^2 + ster_y^2)
2565  variable ster_max = wavemax(ster_finite)
2566  matrix = (x^2 + y^2) <= ster_max ? matrix : nan
2567 
2568  setdatafolder savedf
2569 };
2570 
2581 variable quick_pizza_image(wave data, string nickname, variable theta_offset, variable tilt_offset, variable phi_offset, variable npolar = defaultValue, variable nograph = defaultValue, variable folding = defaultValue){
2582  wave data// 2D intensity wave, see requirements above
2583  string nickname// nick name for output data
2584  // in default mode, this will be the name of a child folder containing the output
2585  // in XPDplot mode, this will be a prefix of the generated data in the root folder
2586  variable theta_offset// manipulator theta angle corresponding to normal emission
2587  variable tilt_offset// manipulator tilt angle corresponding to normal emission
2588  variable phi_offset// manipulator phi angle corresponding to phi_result = 0
2589  variable npolar// number of polar angles, determines polar and azimuthal step size
2590  // default = 91 (1 degree steps)
2591  variable nograph// 0 (default) = display a new polar graph
2592  // 1 = don't display a new graph (if a graph is existing from a previous call, it will update)
2593  variable folding// rotational averaging, default = 1
2594 
2595  if (ParamIsDefault(npolar))
2596  npolar = 91
2597  endif
2598  if (ParamIsDefault(nograph))
2599  nograph = 0
2600  endif
2601  if (ParamIsDefault(folding))
2602  folding = 1
2603  endif
2604  string graphname = "graph_" + nickname
2605  string s_prefix = ""
2606 
2607  // sort out data folder structure
2608  dfref saveDF = GetDataFolderDFR()
2609  dfref dataDF = GetWavesDataFolderDFR(data)
2610  setdatafolder dataDF
2611  if (DataFolderExists(":attr"))
2612  setdatafolder :attr
2613  endif
2614  dfref attrDF = GetDataFolderDFR()
2615  setdatafolder dataDF
2616  newdatafolder /s/o $nickname
2617  dfref destDF = GetDataFolderDFR()
2618 
2619  // performance monitoring
2620  variable timerRefNum
2621  variable /g xyz_perf_secs
2622  timerRefNum = startMSTimer
2623 
2624  wave /sdfr=attrDF ManipulatorTheta
2625  wave /sdfr=attrDF ManipulatorTilt
2626  wave /sdfr=attrDF ManipulatorPhi
2627  duplicate /free ManipulatorTheta, m_theta
2628  duplicate /free ManipulatorTilt, m_tilt
2629  duplicate /free ManipulatorPhi, m_phi
2630  m_theta -= theta_offset
2631  m_tilt -= tilt_offset
2632  m_tilt *= -1// checked 140702
2633  m_phi -= phi_offset
2634  //m_phi *= -1 // checked 140702
2635 
2636  make /n=1/d/free d_polar, d_azi
2637  convert_angles_ttpd2polar(m_theta, m_tilt, m_phi, data, d_polar, d_azi)
2638  d_azi += 180// changed 151030 (v1.6)
2639  d_azi = d_azi >= 360 ? d_azi - 360 : d_azi
2640 
2641  duplicate /free data, values
2642  variable nn = dimsize(values, 0) * max(dimsize(values, 1), 1)
2643  redimension /n=(nn) values, d_polar, d_azi
2644  duplicate /o d_polar, ster_rad, ster_x, ster_y
2645 
2646  variable projection = 1
2647  switch(projection)
2648  case 1:// stereographic
2649  ster_rad = 2 * tan(d_polar / 2 * pi / 180)
2650  break
2651  case 2:// azimuthal
2652  ster_rad = 2 * cos((180 - d_polar) / 2 * pi / 180)
2653  break
2654  endswitch
2655  string s_ster_x = s_prefix + "ster_x"
2656  string s_ster_y = s_prefix + "ster_y"
2657 
2658  nn = 401
2659  make /n=(nn, nn) /d /o matrix
2660  make /n=(nn, nn) /free mnorm
2661  setscale /i x -2, +2, matrix, mnorm
2662  setscale /i y -2, +2, matrix, mnorm
2663  matrix = 0
2664  mnorm = 0
2665 
2666  variable ifold
2667  for (ifold = 0; ifold < folding; ifold += 1)
2668  ster_x = ster_rad * cos(d_azi * pi / 180)
2669  ster_y = ster_rad * sin(d_azi * pi / 180)
2670  ImageFromXYZ {ster_x, ster_y, values}, matrix, mnorm
2671  d_azi = d_azi >= 180 ? d_azi + 360 / folding - 180 : d_azi + 360 / folding
2672  endfor
2673 
2674  matrix /= mnorm
2675  matrixfilter /n=5 NanZapMedian matrix
2676  matrixfilter /n=3 gauss matrix
2677 
2678  if (!nograph)
2679  display /k=1
2680  appendimage matrix
2681  modifygraph width={Plan,1,bottom,left}
2682  endif
2683 
2684  if (timerRefNum >= 0)
2685  xyz_perf_secs = stopMSTimer(timerRefNum) / 1e6
2686  endif
2687 
2688  setdatafolder saveDF
2689 };
2690 
2692 variable save_hemi_scan(string nickname, string pathname, string filename){
2693  string nickname
2694  string pathname
2695  string filename
2696 
2697  dfref savedf = getdatafolderdfr()
2698 
2699  // source data
2700  string s_prefix = ""
2701  string s_int = "values"
2702  dfref df = find_hemi_data(nickname, s_prefix, s_int)
2703 
2704  string s_polar = s_prefix + "pol"
2705  string s_azim = s_prefix + "az"
2706  string s_theta = s_prefix + "th"
2707  string s_tot = s_prefix + "tot"
2708  string s_weight = s_prefix + "wt"
2709 
2710  wave /sdfr=df theta1 = $s_theta
2711  wave /sdfr=df polar1 = $s_polar
2712  wave /sdfr=df azim1 = $s_azim
2713  wave /sdfr=df tot1 = $s_tot
2714  wave /sdfr=df weight1 = $s_weight
2715  wave /sdfr=df values1 = $s_int
2716 
2717  save /m="\r\n" /o /p=$pathname /t theta1, polar1, azim1, tot1, weight1, values1 as filename
2718 
2719  setdatafolder saveDF
2720 };
2721 
2725 variable load_hemi_scan(string nickname, string pathname, string filename){
2726  string nickname
2727  string pathname
2728  string filename
2729 
2730  dfref savedf = getdatafolderdfr()
2731 
2732  //loadwave /p=$pathname /t theta1, polar1, azim1, tot1, weight1, values1 as filename
2733  //LoadWave /t/p=pearl_explorer_filepath/q filename
2734  //svar waves = s_wavenames
2735  //if (v_flag > 0)
2736  // string /g pearl_explorer_import = "load_itx_file"
2737  //endif
2738 
2739  setdatafolder saveDF
2740 };
2741 
2774 variable import_tpi_scan(string nickname, wave theta, wave phi, wave intensity, variable folding = defaultValue, variable npolar = defaultValue, variable nograph = defaultValue, variable xpdplot = defaultValue){
2775  string nickname
2776  wave theta
2777  wave phi
2778  wave intensity
2779 
2780  variable folding
2781  variable npolar
2782  variable nograph
2783  variable xpdplot
2784 
2785  if (ParamIsDefault(npolar))
2786  npolar = 91
2787  endif
2788  if (ParamIsDefault(nograph))
2789  nograph = 0
2790  endif
2791  if (ParamIsDefault(folding))
2792  folding = 1
2793  endif
2794  if (ParamIsDefault(xpdplot))
2795  xpdplot = 0
2796  endif
2797 
2798  make_hemi_grid(npolar, nickname, xpdplot=xpdplot)
2799 
2800  variable ifold
2801  duplicate /free phi, fold_phi
2802  for (ifold = 0; ifold < folding; ifold += 1)
2803  hemi_add_anglescan(nickname, intensity, theta, fold_phi)
2804  fold_phi = fold_phi >= 180 ? fold_phi + 360 / folding - fold_phi : fold_phi + 360 / folding
2805  endfor
2806 
2807  if (nograph==0)
2808  display_hemi_scan(nickname)
2809  endif
2810 };
2811 
2823 variable trim_hemi_scan(string nickname, variable theta_max){
2824  string nickname
2825  variable theta_max
2826 
2827  string s_prefix = ""
2828  string s_int = "values"
2829  dfref df = find_hemi_data(nickname, s_prefix, s_int)
2830 
2831  string s_totals = s_prefix + "tot"
2832  string s_weights = s_prefix + "wt"
2833  string s_polar = s_prefix + "pol"
2834 
2835  wave /sdfr=df w_polar = $s_polar
2836  wave /sdfr=df w_values = $s_int
2837  wave /sdfr=df w_totals = $s_totals
2838  wave /sdfr=df w_weights = $s_weights
2839 
2840  w_values = w_polar <= theta_max ? w_totals / w_weights : nan
2841 };
2842 
2862 wave hemi_polar_cut(string nickname, variable azim){
2863  string nickname
2864  variable azim
2865 
2866  dfref savedf = getdatafolderdfr()
2867  string s_prefix = ""
2868  string s_int = "values"
2869  dfref df = find_hemi_data(nickname, s_prefix, s_int)
2870 
2871  string s_totals = s_prefix + "tot"
2872  string s_weights = s_prefix + "wt"
2873  string s_polar = s_prefix + "pol"
2874  string s_azim = s_prefix + "az"
2875  string s_index = s_prefix + "index"
2876  string s_theta = s_prefix + "th"
2877  string s_dphi = s_prefix + "dphi"
2878  string s_nphis = s_prefix + "nphis"
2879  string s_cut
2880  sprintf s_cut, "%s_azi%03u", s_int, round(azim)
2881 
2882  wave /sdfr=df w_polar = $s_polar
2883  wave /sdfr=df w_azim = $s_azim
2884  wave /sdfr=df w_values = $s_int
2885  wave /sdfr=df w_totals = $s_totals
2886  wave /sdfr=df w_weights = $s_weights
2887  wave /sdfr=df w_index = $s_index
2888  wave /sdfr=df w_theta = $s_theta
2889  wave /sdfr=df w_dphi = $s_dphi
2890  wave /sdfr=df w_nphis = $s_nphis
2891 
2892  variable npol = numpnts(w_theta)
2893  variable ipol
2894  variable pol_st = abs(w_theta[1] - w_theta[0])
2895  variable pol
2896  variable pol1, pol2
2897  variable nsel
2898 
2899  setdatafolder df
2900  make /n=(npol) /o $s_cut
2901  wave w_cut = $s_cut
2902  setscale /i x w_theta[0], w_theta[numpnts(w_theta)-1], "deg", w_cut
2903  make /n=1 /free azi_slice
2904  make /n=1 /free values_slice
2905 
2906  for (ipol = 0; ipol < npol; ipol += 1)
2907  pol = w_theta[ipol]
2908  pol1 = pol - pol_st / 2
2909  pol2 = pol + pol_st / 2
2910  extract /free /indx w_polar, sel, (pol1 < w_polar) && (w_polar <= pol2)
2911  nsel = numpnts(sel)
2912  if (nsel > 0)
2913  redimension /n=(nsel+2) azi_slice, values_slice
2914  azi_slice[1, nsel] = w_azim[sel[p-1]]
2915  azi_slice[0] = azi_slice[nsel] - 360
2916  azi_slice[nsel+1] = azi_slice[1] + 360
2917  values_slice[1, nsel] = w_values[sel[p-1]]
2918  values_slice[0] = values_slice[nsel]
2919  values_slice[nsel+1] = values_slice[1]
2920  w_cut[ipol] = interp(azim, azi_slice, values_slice)
2921  else
2922  w_cut[ipol] = nan
2923  endif
2924  endfor
2925 
2926  setdatafolder savedf
2927  return w_cut
2928 };
2929 
2948 wave hemi_azi_cut(string nickname, variable pol){
2949  string nickname
2950  variable pol
2951 
2952  dfref savedf = getdatafolderdfr()
2953  string s_prefix = ""
2954  string s_int = "values"
2955  dfref df = find_hemi_data(nickname, s_prefix, s_int)
2956 
2957  string s_totals = s_prefix + "tot"
2958  string s_weights = s_prefix + "wt"
2959  string s_polar = s_prefix + "pol"
2960  string s_azim = s_prefix + "az"
2961  string s_index = s_prefix + "index"
2962  string s_theta = s_prefix + "th"
2963  string s_dphi = s_prefix + "dphi"
2964  string s_nphis = s_prefix + "nphis"
2965  string s_cut
2966  sprintf s_cut, "%s_pol%03u", s_int, round(pol)
2967 
2968  wave /sdfr=df w_polar = $s_polar
2969  wave /sdfr=df w_azim = $s_azim
2970  wave /sdfr=df w_values = $s_int
2971  wave /sdfr=df w_totals = $s_totals
2972  wave /sdfr=df w_weights = $s_weights
2973  wave /sdfr=df w_index = $s_index
2974  wave /sdfr=df w_theta = $s_theta
2975  wave /sdfr=df w_dphi = $s_dphi
2976  wave /sdfr=df w_nphis = $s_nphis
2977 
2978  variable pol_st = abs(w_theta[1] - w_theta[0])
2979  variable pol1, pol2
2980  variable nsel
2981 
2982  pol1 = pol - pol_st / 2
2983  pol2 = pol + pol_st / 2
2984  extract /free /indx w_polar, sel, (pol1 < w_polar) && (w_polar <= pol2)
2985  nsel = numpnts(sel)
2986  if (nsel > 0)
2987  setdatafolder df
2988  make /n=(nsel) /o $s_cut
2989  wave w_cut = $s_cut
2990  w_cut = w_values[sel]
2991  setscale /i x w_azim[sel[0]], w_azim[sel[nsel-1]], "", w_cut
2992  setdatafolder savedf
2993  return w_cut
2994  else
2995  setdatafolder savedf
2996  return $""
2997  endif
2998  setdatafolder savedf
2999 };
3000 
3001 static variable check_contrast(wave values, variable pcmin, variable pcmax, variable* vmin, variable* vmax){
3002  wave values
3003  variable pcmin
3004  variable pcmax
3005  variable &vmin
3006  variable &vmax
3007 
3008  dfref save_df = GetDataFolderDFR()
3009  dfref dfr = NewFreeDataFolder()
3010  setdatafolder dfr
3011  StatsQuantiles /inan /iw /q /z values
3012  wave index = w_quantilesindex
3013  variable imin = round(numpnts(index) * pcmin / 100)
3014  variable imax = round(numpnts(index) * (100 - pcmax) / 100)
3015  vmin = values[index[imin]]
3016  vmax = values[index[imax]]
3017  KillDataFolder dfr
3018  setdatafolder save_df
3019 };
3020 
3037 variable set_contrast(variable pcmin, variable pcmax, string graphname = defaultValue, string colortable = defaultValue){
3038  variable pcmin
3039  variable pcmax
3040  string graphname
3041  string colortable
3042 
3043  if (ParamIsDefault(graphname))
3044  graphname = ""
3045  endif
3046  if (ParamIsDefault(colortable))
3047  colortable = ""
3048  endif
3049 
3050  dfref save_df = GetDataFolderDFR()
3051 
3052  string objname
3053  string info
3054  string wname
3055  string ctab
3056  variable rev
3057  variable n
3058  variable i
3059  variable vmin
3060  variable vmax
3061 
3062  string traces = TraceNameList(graphname, ";", 1+4)
3063  n = ItemsInList(traces, ";")
3064  for (i = 0; i < n; i += 1)
3065  objname = StringFromList(i, traces, ";")
3066  info = TraceInfo(graphname, objname, 0)
3067  if (strlen(info) > 0)
3068  info = StringByKey("RECREATION", info, ":", ";")
3069  info = StringByKey("zColor(x)", info, "=", ";")
3070  if (strlen(info) > 2)
3071  info = info[1,strlen(info)-2]
3072  wname = StringFromList(0, info, ",")
3073  wave w = $wname
3074  ctab = StringFromList(3, info, ",")
3075  rev = str2num("0" + StringFromList(4, info, ","))
3076  if (strlen(colortable) > 0)
3077  ctab = colortable
3078  endif
3079  check_contrast(w, pcmin, pcmax, vmin, vmax)
3080  ModifyGraph /w=$graphname zColor($objname)={w, vmin, vmax, $ctab, rev}
3081  endif
3082  endif
3083  endfor
3084 
3085  string images = ImageNameList(graphname, ";")
3086  n = ItemsInList(images, ";")
3087  for (i = 0; i < n; i += 1)
3088  objname = StringFromList(i, images, ";")
3089  wave w = ImageNameToWaveRef(graphname, objname)
3090  info = ImageInfo(graphname, objname, 0)
3091  if (strlen(info) > 0)
3092  info = StringByKey("RECREATION", info, ":", ";")
3093  info = StringByKey("ctab", info, "=", ";")
3094  if (strlen(info) > 2)
3095  info = info[1,strlen(info)-2]
3096  ctab = StringFromList(2, info, ",")
3097  rev = str2num("0" + StringFromList(3, info, ","))
3098  if (strlen(colortable) > 0)
3099  ctab = colortable
3100  endif
3101  check_contrast(w, pcmin, pcmax, vmin, vmax)
3102  ModifyImage /w=$graphname $objname ctab={vmin, vmax, $ctab, rev}
3103  endif
3104  endif
3105  endfor
3106 
3107  setdatafolder save_df
3108 };
3109 
wave hemi_polar_cut(string nickname, variable azim)
extract a polar cut from a hemispherical scan.
-
variable trim_hemi_scan(string nickname, variable theta_max)
trim a hemispherical scan at grazing angle
-
variable pizza_service_2(wave data, string nickname, wave m_theta, wave m_tilt, wave m_phi, variable npolar=defaultValue, variable nograph=defaultValue, variable folding=defaultValue, variable xpdplot=defaultValue)
create a pizza plot from a measured (energy-integrated) data strip
-
static const variable kProjScaleOrtho
-
variable polar2cart_wave(wave in, wave out)
-
variable normalize_strip_theta(wave strip, wave theta, variable theta_offset=defaultValue, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
divide the strip by the average polar distribution.
-
variable normalize_strip_2d(wave strip, wave theta, variable theta_offset=defaultValue, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
divide the strip by a two-dimensional normalization function.
-
variable crop_strip(wave strip, variable xlo, variable xhi)
crop a strip at the sides.
-
const variable kProjGnom
-
threadsafe wave ad_profile_y(wave dataset, variable p1, variable p2, string destname, variable noavg=defaultValue)
1D cut through 2D dataset along Y dimension, new destination wave.
-
variable make_hemi_grid(variable npol, string nickname, variable xpdplot=defaultValue)
create a hemispherical, constant solid angle grid
-
variable hemi_add_anglescan(string nickname, wave values, wave polar, wave azi, wave weights=defaultValue)
add an arbitrary angle scan to a hemispherical scan grid.
-
string get_hemi_nickname(wave w)
finds the nick name given any hemi wave
-
variable interpolate_hemi_scan(string nickname)
interpolate a hemispherical scan onto a rectangular grid
-
string get_hemi_prefix(wave w)
finds the prefix given any hemi wave
-
string display_hemi_scan(string nickname, variable projection=defaultValue, variable graphtype=defaultValue, variable do_ticks=defaultValue, variable do_grids=defaultValue, string graphname=defaultValue)
display a plot of a hemispherical angle scan.
-
static variable CalcN_Theta(string HoloMode, variable Theta_in, variable Theta_ran, variable Theta_st)
calculate the number of thetas for a pattern
-
dfr find_hemi_data(string nickname, string *prefix, string *intwave)
finds the folder, prefix and name of holo waves given their nick name
-
variable convert_angles_ttpd2polar(wave theta, wave tilt, wave phi, wave data, wave polar, wave azi)
convert angles from TTPA (theta-tilt-phi-analyser) scheme to polar coordinates.
-
variable clear_hemi_grid(string nickname)
clear a hemispherical scan grid
-
static const variable kProjScaleDist
-
threadsafe variable calc_graph_polar(variable x, variable y, variable projection=defaultValue)
calculate polar angle from Cartesian coordinate
-
static variable check_contrast(wave values, variable pcmin, variable pcmax, variable *vmin, variable *vmax)
-
static variable Calc_The_step(variable th, variable Theta_st, string Holomode)
calculate delta-theta for a given theta
-
const variable kProjArea
-
static variable line_average(wave source, wave dest)
-
threadsafe variable calc_graph_radius(variable polar, variable projection=defaultValue)
calculate the projected polar angle
-
variable pizza_service(wave data, string nickname, variable theta_offset, variable tilt_offset, variable phi_offset, variable npolar=defaultValue, variable nograph=defaultValue, variable folding=defaultValue, variable xpdplot=defaultValue)
create a pizza plot from a measured (energy-integrated) data strip
-
variable rotate_x_wave(wave inout, variable angle)
-
variable cart2polar_wave(wave in, wave out)
-
string display_scanlines(string nickname, variable alpha_lo, variable alpha_hi, wave m_theta, wave m_tilt, wave m_phi, variable folding=defaultValue, variable projection=defaultValue)
display a polar graph with lines indicating the angles covered by an angle scan.
-
wave hemi_azi_cut(string nickname, variable pol)
extract an azimuthal cut from a hemispherical scan
-
variable draw_diffraction_cone(string graphname, string groupname, variable theta_axis, variable theta_inner, variable phi)
draw the circle of a diffraction cone in a stereographic polar graph.
-
variable hemi_add_aziscan(string nickname, wave values, variable polar, wave azi, wave weights=defaultValue)
add an azimuthal scan to a hemispherical scan grid.
-
static const variable kProjScaleGnom
-
variable rotate_y_wave(wave inout, variable angle)
-
variable rotate_hemi_scan(string nickname, variable angle)
azimuthally rotate a hemispherical scan dataset.
-
static const variable kProjScaleStereo
-
processing and holographic mapping of angle scanned XPD data.
-
static string display_polar_graph(string graphname, variable angle_offset=defaultValue, variable do_ticks=defaultValue)
displays an empty polar graph
-
const variable kProjOrtho
-
variable save_hemi_scan(string nickname, string pathname, string filename)
save a hemispherical scan to an Igor text file
-
variable normalize_strip_phi(wave strip, wave theta, wave phi, variable theta_offset=defaultValue, variable theta_range=defaultValue, variable check=defaultValue)
divide the strip by a sine function in phi (wobble correction).
-
variable normalize_strip_thetaphi(wave strip, wave theta, wave phi, variable theta_offset=defaultValue, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
divide the strip by a smooth polar-azimuthal distribution.
-
const variable kProjStereo
-
variable quick_pizza_image(wave data, string nickname, variable theta_offset, variable tilt_offset, variable phi_offset, variable npolar=defaultValue, variable nograph=defaultValue, variable folding=defaultValue)
map angle scan data onto a rectangular grid in stereographic projection
-
static variable polar_graph_hook(WMWinHookStruct *s)
polar graph window hook
-
const variable kProjDist
-
threadsafe variable calc_graph_azi(variable x, variable y, variable projection=defaultValue, variable zeroAngle=defaultValue)
calculate azimuthal angle from Cartesian coordinate
-
variable set_contrast(variable pcmin, variable pcmax, string graphname=defaultValue, string colortable=defaultValue)
set the pseudocolor contrast by percentile.
-
variable strip_delete_frames(wave strip, variable qlo, variable qhi, wave theta, wave tilt, wave phi)
delete a contiguous range of frames from a strip.
-
variable rotate_z_wave(wave inout, variable angle)
-
static variable calc_nth(variable Theta_st, variable Theta_in, variable th, variable Phi_ran, variable Phi_ref, string Holomode)
calculate the number of phis for a given theta
-
static const variable kProjScaleArea
-
variable show_analyser_line(variable theta, variable tilt, variable phi, variable theta_offset, variable tilt_offset, variable phi_offset, variable npolar=defaultValue, variable nograph=defaultValue, variable xpdplot=defaultValue)
calculate and display the line seen by the analyser for a specific emission angle ...
-
variable convert_angles_ttpa2polar(wave theta, wave tilt, wave phi, wave analyser, wave polar, wave azi)
convert angles from TTPA (theta-tilt-phi-analyser) scheme to polar coordinates.
-
static string draw_hemi_axes(string graphname, variable do_grids=defaultValue)
draw polar and azimuthal grids in an existing polar graph.
-
variable duplicate_hemi_scan(string source_nickname, dfref dest_folder, string dest_nickname, variable xpdplot=defaultValue)
duplicate a hemispherical scan dataset.
-
variable set_polar_graph_cursor(string nickname, string cursorname, variable polar_angle, variable azim_angle, string graphname=defaultValue)
-
static variable update_polar_info(string graphname)
update the angles info based on cursors A and B of a given polar graph window
-
variable import_tpi_scan(string nickname, wave theta, wave phi, wave intensity, variable folding=defaultValue, variable npolar=defaultValue, variable nograph=defaultValue, variable xpdplot=defaultValue)
import a hemispherical scan from theta-phi-intensity waves and display it
-
variable load_hemi_scan(string nickname, string pathname, string filename)
load a hemispherical scan from an Igor text file
-
threadsafe wave ad_profile_x(wave dataset, variable q1, variable q2, string destname, variable noavg=defaultValue)
1D cut through 2D dataset along X dimension, new destination wave.
-
static variable calc_phi_step(variable Theta_in, variable th, variable Theta_st, variable Phi_ran, variable Phi_ref, string Holomode)
calculate delta-phi for a given theta
-
variable normalize_strip_x(wave strip, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
divide the strip by the average X distribution.
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-anglescan-tracker_8ipf.html b/doc/html/pearl-anglescan-tracker_8ipf.html index e0dd511..7dde41a 100644 --- a/doc/html/pearl-anglescan-tracker_8ipf.html +++ b/doc/html/pearl-anglescan-tracker_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-anglescan-tracker.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
pearl-anglescan-tracker.ipf File Reference
-
#include "pearl-area-profiles"
-#include "pearl-area-import"
-#include "pearl-scienta-preprocess"
-#include "pearl-anglescan-process"
-#include <New Polar Graphs>
-
+

Go to the source code of this file.

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

static variable AfterCompiledHook ()
 initialize package data once when the procedure is first loaded More...
 
static variable init_package ()
 
static variable save_prefs ()
 save persistent package data to the preferences file. More...
 
static variable load_prefs ()
 load persistent package data from the preferences file. More...
 
static variable IgorQuitHook (string app)
 disconnect EPICS channels before Igor quits. More...
 
variable ast_setup ()
 set up data structures, display graph, and try to connect to analyser. More...
 
variable ast_prepare (variable theta_offset=defaultValue, variable tilt_offset=defaultValue, variable phi_offset=defaultValue)
 prepare for new measurement and clear the data buffer. More...
 
variable ast_set_processing (string reduction_func, string reduction_params)
 set the data processing parameters More...
 
variable ast_add_image (wave image, variable theta, variable tilt, variable phi)
 process and add a detector image to the tracker scan. More...
 
variable ast_export (dfref folder, string nickname, variable xpdplot=defaultValue)
 export tracker data to a separate, independent data set. More...
 
variable ast_import (string nickname)
 import tracker data from an existing angle scan dataset. More...
 
variable ast_update_detector (variable theta, variable tilt, variable phi, variable range)
 update the current position indicator. More...
 
variable ast_close ()
 stop tracker, close graph, release data structures. More...
 
static variable setup_data ()
 
static variable extend_data (variable num_slices)
 extend the data buffer for the next polar scan More...
 
static variable setup_detector ()
 
static variable add_image_data (wave image, variable theta, variable tilt, variable phi)
 reduce a detector image and add the result to the data buffer. More...
 
static variable process_image_data ()
 process the data buffer to generate the tracker dataset. More...
 
static variable update_detector (variable theta, variable tilt, variable phi, variable range)
 update the current position indicator. More...
 
static variable setup_graph ()
 create the graph window. More...
 
static variable update_data_graph ()
 
static variable update_detector_graph ()
 
static variable epics_connect ()
 connect the angle scan tracker to EPICS More...
 
static variable epics_disconnect_chid (string chid_var_name)
 
static variable epics_disconnect ()
 
static variable ast_window_hook (WMWinHookStruct *s)
 window hook More...
 
variable ast_callback_data (variable chan)
 callback function for new analyser data from EPICS. More...
 
variable ast_callback_detector (variable chan)
 callback function for new detector state from EPICS. More...
 
variable ast_callback_manip (variable chan)
 callback function for new manipulator position from EPICS. More...
 
static variable bp_capture (WMButtonAction *ba)
 
static variable toggle_capture ()
 
static variable update_capture ()
 
static variable pmp_data (WMPopupAction *pa)
 
static variable pmp_data_mouseup (WMPopupAction *pa)
 
static variable export_tracker_data ()
 export tracker data (with prompt) More...
 
static variable import_tracker_data ()
 import tracker data (with prompt) More...
 
static variable save_tracker_data ()
 save tracker data to file (with prompt) More...
 
static variable load_tracker_data ()
 import tracker data from file (with prompt) More...
 
static variable pmp_parameters (WMPopupAction *pa)
 
static variable pmp_parameters_mouseup (WMPopupAction *pa)
 
static variable edit_reduction_params ()
 
static variable edit_offsets ()
 
- - - - - - - - - -

-Variables

 version
 
static const string package_path = "root:packages:pearl_anglescan_tracker:"
 data folder path More...
 
static const string prefs_objects = "projection;theta_offset;tilt_offset;phi_offset;reduction_func;reduction_params"
 semicolon-separated list of persistent variable, string, and wave names More...
 
-

Function Documentation

- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable add_image_data (wave image,
variable theta,
variable tilt,
variable phi 
)
-
-static
-
- -

reduce a detector image and add the result to the data buffer.

-
Parameters
- - - - - -
imagedetector image with correct X (energy) and Y (angle) scaling
thetapolar angle of manipulator
tilttilt angle of manipulator
phiazimuthal angle of manipulator
-
-
-

the manipulator angles are corrected by the preset offsets internally.

- -

Definition at line 453 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable AfterCompiledHook ()
-
-static
-
- -

initialize package data once when the procedure is first loaded

- -

Definition at line 73 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable ast_add_image (wave image,
variable theta,
variable tilt,
variable phi 
)
-
- -

process and add a detector image to the tracker scan.

-
Parameters
- - - - - -
imagedetector image with correct X (energy) and Y (angle) scaling
thetapolar angle of manipulator
tilttilt angle of manipulator
phiazimuthal angle of manipulator
-
-
-

the manipulator angles are corrected by the preset offsets internally.

- -

Definition at line 285 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - - -
variable ast_callback_data (variable chan)
-
- -

callback function for new analyser data from EPICS.

- -

Definition at line 851 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - - -
variable ast_callback_detector (variable chan)
-
- -

callback function for new detector state from EPICS.

-

save the manipulator position at the beginning of image acquisition. it is used by ast_callback_data().

- -

Definition at line 956 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - - -
variable ast_callback_manip (variable chan)
-
- -

callback function for new manipulator position from EPICS.

- -

Definition at line 985 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - -
variable ast_close ()
-
- -

stop tracker, close graph, release data structures.

- -

Definition at line 360 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable ast_export (dfref folder,
string nickname,
variable xpdplot = defaultValue 
)
-
- -

export tracker data to a separate, independent data set.

-

the exported data can then be used for further processing. the data is exported to the current data folder, or root if XPDplot compatibility is requested.

-
Parameters
- - - - -
folderdestination folder path
nicknamename prefix for waves
xpdplotxpdplot compatibility, see make_hemi_grid() for details
    -
  • 0 (default)
  • -
  • 1 create additional waves and notebook required by XPDplot
  • -
-
-
-
- -

Definition at line 307 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - - -
variable ast_import (string nickname)
-
- -

import tracker data from an existing angle scan dataset.

-
Parameters
- - -
nicknamename prefix for waves. data must be in current data folder.
-
-
- -

Definition at line 329 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable ast_prepare (variable theta_offset = defaultValue,
variable tilt_offset = defaultValue,
variable phi_offset = defaultValue 
)
-
- -

prepare for new measurement and clear the data buffer.

-

optionally, set new manipulator offsets. the offsets are the manipulator readback coordinates where the sample surface is oriented in normal emission, and the handle of the sample plate points horizontally to the left (9 o'clock).

-
Parameters
- - - - -
theta_offsetset new theta offset. default: no change.
tilt_offsetset new tilt offset. default: no change.
phi_offsetset new phi offset. default: no change.
-
-
- -

Definition at line 211 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable ast_set_processing (string reduction_func,
string reduction_params 
)
-
- -

set the data processing parameters

-

the parameters will be effective for subsequent measurements only. previously acquired data is not affected. the processing parameters are saved with the preferences.

-
Parameters
- - - -
reduction_funcname of custom reduction function, e.g. "int_linbg_reduction". any user-defined function with the same signature as adh5_default_reduction() is allowed.
reduction_paramsparameter string for the reduction function. the format depends on the actual function. for int_linbg_reduction, e.g., "Lcrop=0.1;Hcrop=0.1;Lsize=0.2;Hsize=0.2;Cpos=0.5;Csize=0.4".
-
-
- -

Definition at line 261 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - -
variable ast_setup ()
-
- -

set up data structures, display graph, and try to connect to analyser.

- -

Definition at line 194 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable ast_update_detector (variable theta,
variable tilt,
variable phi,
variable range 
)
-
- -

update the current position indicator.

-
Parameters
- - - - - -
thetapolar angle of manipulator
tilttilt angle of manipulator
phiazimuthal angle of manipulator
rangeangle range (60 or 45)
-
-
-

the manipulator angles are corrected by the preset offsets internally.

- -

Definition at line 349 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable ast_window_hook (WMWinHookStruct * s)
-
-static
-
- -

window hook

-

disconnects from EPICS when the window is closed.

- -

Definition at line 836 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_capture (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1018 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable edit_offsets ()
-
-static
-
- -

Definition at line 1239 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable edit_reduction_params ()
-
-static
-
- -

Definition at line 1223 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable epics_connect ()
-
-static
-
- -

connect the angle scan tracker to EPICS

-

the tracker uses channels of the analyser and the manipulator.

-

if the EPICS XOP is not loaded, the function does nothing. if channels are not available, the function exits with an error code after a timeout of 5 seconds. the Igor run-time error status is reset to suppress the error dialog.

-
Returns
zero if successful, non-zero if an error occurred
-
Todo:
the X03DA channel names are hard-coded.
- -

Definition at line 680 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable epics_disconnect ()
-
-static
-
- -

Definition at line 806 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable epics_disconnect_chid (string chid_var_name)
-
-static
-
- -

Definition at line 792 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable export_tracker_data ()
-
-static
-
- -

export tracker data (with prompt)

- -

Definition at line 1100 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable extend_data (variable num_slices)
-
-static
-
- -

extend the data buffer for the next polar scan

-

call this function if the buffer is full.

-
Parameters
- - -
num_slicesnumber of slices that the measurement contains
-
-
- -

Definition at line 402 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable IgorQuitHook (string app)
-
-static
-
- -

disconnect EPICS channels before Igor quits.

- -

Definition at line 188 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable import_tracker_data ()
-
-static
-
- -

import tracker data (with prompt)

- -

Definition at line 1130 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable init_package ()
-
-static
-
- -

Definition at line 98 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable load_prefs ()
-
-static
-
- -

load persistent package data from the preferences file.

-

the preferences file is an Igor packed experiment file in a special preferences folder.

-

this function is called automatically when the procedure is first compiled, or whenever the user clicks the corresponding button.

- -

Definition at line 163 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable load_tracker_data ()
-
-static
-
- -

import tracker data from file (with prompt)

- -

Definition at line 1170 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_data (WMPopupAction * pa)
-
-static
-
- -

Definition at line 1066 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_data_mouseup (WMPopupAction * pa)
-
-static
-
- -

Definition at line 1080 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_parameters (WMPopupAction * pa)
-
-static
-
- -

Definition at line 1189 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_parameters_mouseup (WMPopupAction * pa)
-
-static
-
- -

Definition at line 1203 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable process_image_data ()
-
-static
-
- -

process the data buffer to generate the tracker dataset.

- -

Definition at line 507 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable save_prefs ()
-
-static
-
- -

save persistent package data to the preferences file.

-

this function is called when the user clicks the corresponding button.

- -

Definition at line 139 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable save_tracker_data ()
-
-static
-
- -

save tracker data to file (with prompt)

- -

Definition at line 1159 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable setup_data ()
-
-static
-
- -

Definition at line 372 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable setup_detector ()
-
-static
-
- -

Definition at line 434 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable setup_graph ()
-
-static
-
- -

create the graph window.

- -

Definition at line 594 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable toggle_capture ()
-
-static
-
- -

Definition at line 1032 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable update_capture ()
-
-static
-
- -

Definition at line 1050 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable update_data_graph ()
-
-static
-
- -

Definition at line 645 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable update_detector (variable theta,
variable tilt,
variable phi,
variable range 
)
-
-static
-
- -

update the current position indicator.

-
Parameters
- - - - - -
thetapolar angle of manipulator
tilttilt angle of manipulator
phiazimuthal angle of manipulator
rangeangle range (60 or 45)
-
-
-

the manipulator angles are corrected by the preset offsets internally.

- -

Definition at line 559 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable update_detector_graph ()
-
-static
-
- -

Definition at line 657 of file pearl-anglescan-tracker.ipf.

- -
-
-

Variable Documentation

- -
-
- - - - - -
- - - - -
const string package_path = "root:packages:pearl_anglescan_tracker:"
-
-static
-
- -

data folder path

- -

Definition at line 68 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string prefs_objects = "projection;theta_offset;tilt_offset;phi_offset;reduction_func;reduction_params"
-
-static
-
- -

semicolon-separated list of persistent variable, string, and wave names

- -

Definition at line 70 of file pearl-anglescan-tracker.ipf.

- -
-
- -
-
- - - - -
version
-
-Initial value:
= 1.6
static const string package_name = "pearl_anglescan_tracker"
static const string package_name
package name is used as data folder name
-
-

Definition at line 5 of file pearl-anglescan-tracker.ipf.

- -
-
diff --git a/doc/html/pearl-anglescan-tracker_8ipf_source.html b/doc/html/pearl-anglescan-tracker_8ipf_source.html index a32cf4c..0887cdb 100644 --- a/doc/html/pearl-anglescan-tracker_8ipf_source.html +++ b/doc/html/pearl-anglescan-tracker_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-anglescan-tracker.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3
2 #pragma version = 1.4
3 #pragma IgorVersion = 6.2
4 #pragma ModuleName = PearlAnglescanTracker
5 #include "pearl-area-profiles", version > 1.04
6 #include "pearl-area-import", version > 1.05
7 #include "pearl-scienta-preprocess", version > 1.00
8 #include "pearl-anglescan-process", version >= 1.6
9 #include <New Polar Graphs>
10 
11 // $Id$
12 //
13 // author: matthias.muntwiler@psi.ch
14 // Copyright (c) 2014-15 Paul Scherrer Institut
15 //
16 // Licensed under the Apache License, Version 2.0 (the "License");
17 // you may not use this file except in compliance with the License.
18 // You may obtain a copy of the License at
19 // http://www.apache.org/licenses/LICENSE-2.0
20 
58 
64 
66 static const string package_name = "pearl_anglescan_tracker";
68 static const string package_path = "root:packages:pearl_anglescan_tracker:";
70 static const string prefs_objects = "projection;theta_offset;tilt_offset;phi_offset;reduction_func;reduction_params";
71 
73 static variable AfterCompiledHook(){
74 
75  dfref savedf = GetDataFolderDFR()
76  variable do_init = 1
77  if (DataFolderExists(package_path))
78  setdatafolder $(package_path)
79  nvar /z init_done
80  if (nvar_exists(init_done))
81  if (init_done)
82  do_init = 0
83  endif
84  endif
85  endif
86 
87  if (do_init)
88  init_package()
89  load_prefs()
90  setdatafolder $(package_path)
91  variable /g init_done = 1
92  endif
93 
94  setdatafolder savedf
95  return 0
96 };
97 
98 static variable init_package(){
99  dfref savedf = getdatafolderdfr()
100  setdatafolder root:
101  newdatafolder /o/s packages
102  newdatafolder /o/s $package_name
103 
104  // configuration (persistent)
105  string /g graphname = "graph_anglescan_tracker"
106  string /g dataname = "tracker"
107  string /g projection = "stereographic"
108 
109  // recently used (persistent)
110  variable /g theta_offset = 0
111  variable /g tilt_offset = 0
112  variable /g phi_offset = 0
113  string /g reduction_func = "int_linbg_reduction"
114  string /g reduction_params = "Lcrop=0.1;Hcrop=0.1;Lsize=0.2;Hsize=0.2;Cpos=0.5;Csize=0.4"
115 
116  // recently used (volatile)
117  string /g export_folderpath = "root:"
118  variable /g export_format = 1
119 
120  // run-time variables (volatile)
121  string /g detector_tracename
122  variable /g capturing = 0
123  variable /g buf_size = 0// number of measurements that fit into the data buffer
124  variable /g buf_count = 0// number of measurements contained in the data buffer
125  variable /g buf_width = 0// number of slices that fit into the data buffer
126 
127  // load icon of sample holder
128  string path = FunctionPath("")
129  path = ParseFilePath(1, path, ":", 1, 0) + "tracker-sample-picture.png"
130  LoadPict /O/Q path, pict_tracker_sample
131 
132  setdatafolder savedf
133 };
134 
139 static variable save_prefs(){
140  dfref saveDF = GetDataFolderDFR()
141 
142  string fullPath = SpecialDirPath("Packages", 0, 0, 0)
143  fullPath += package_name
144  NewPath/O/C/Q tempPackagePrefsPath, fullPath
145  fullPath += ":preferences.pxp"
146 
147  SetDataFolder root:packages
148  SetDataFolder $package_name
149  SaveData /O /Q /J=prefs_objects fullPath
150 
151  KillPath/Z tempPackagePrefsPath
152 
153  SetDataFolder saveDF
154 };
155 
163 static variable load_prefs(){
164  dfref saveDF = GetDataFolderDFR()
165 
166  variable result = -1
167  setdatafolder root:
168  NewDataFolder /O/S packages
169  NewDataFolder /O/S $package_name
170  string fullPath = SpecialDirPath("Packages", 0, 0, 0)
171  fullPath += package_name
172 
173  GetFileFolderInfo /Q /Z fullPath
174  if (V_Flag == 0)// Disk directory exists?
175  fullPath += ":preferences.pxp"
176  GetFileFolderInfo /Q /Z fullPath
177  if (V_Flag == 0)// Preference file exist?
178  LoadData /O /R /Q fullPath
179  result = 0
180  endif
181  endif
182 
183  SetDataFolder saveDF
184  return result
185 };
186 
188 static variable IgorQuitHook(string app){
189  string app
191 };
192 
194 variable ast_setup(){
195  setup_data()
197  setup_graph()
198  epics_connect()
199 };
200 
211 variable ast_prepare(variable theta_offset = defaultValue, variable tilt_offset = defaultValue, variable phi_offset = defaultValue){
212  variable theta_offset
213  variable tilt_offset
214  variable phi_offset
215 
216  dfref savedf = getdatafolderdfr()
217  setdatafolder $(package_path)
218 
219  if (!ParamIsDefault(theta_offset))
220  nvar v_theta_offset = theta_offset
221  v_theta_offset = theta_offset
222  endif
223  if (!ParamIsDefault(tilt_offset))
224  nvar v_tilt_offset = tilt_offset
225  v_tilt_offset = tilt_offset
226  endif
227  if (!ParamIsDefault(phi_offset))
228  nvar v_phi_offset = phi_offset
229  v_phi_offset = phi_offset
230  endif
231 
232  nvar buf_count
233  nvar buf_size
234  nvar buf_width
235  buf_count = 0
236  buf_size = 0
237  buf_width = 0
238 
239  svar dataname
240  clear_hemi_grid(dataname)
241  // work-around: set one point to a real number to make the rest of the trace in the graph transparent
242  wave values = $(dataname + "_i")
243  values[numpnts(values) - 1] = 0
244 
246 
247  setdatafolder saveDF
248 };
249 
261 variable ast_set_processing(string reduction_func, string reduction_params){
262  string reduction_func
263  string reduction_params
264 
265  dfref savedf = getdatafolderdfr()
266  setdatafolder $(package_path)
267 
268  svar red_func = reduction_func
269  svar red_params = reduction_params
270 
271  red_func = reduction_func
272  red_params = reduction_params
273 
274  setdatafolder saveDF
275 };
276 
285 variable ast_add_image(wave image, variable theta, variable tilt, variable phi){
286  wave image
287  variable theta
288  variable tilt
289  variable phi
290 
291  add_image_data(image, theta, tilt, phi)
294 };
295 
307 variable ast_export(dfref folder, string nickname, variable xpdplot = defaultValue){
308  dfref folder
309  string nickname
310  variable xpdplot
311 
312  if (ParamIsDefault(xpdplot))
313  xpdplot = 0
314  endif
315 
316  dfref savedf = getdatafolderdfr()
317  setdatafolder $(package_path)
318 
319  svar dataname
320  duplicate_hemi_scan(dataname, folder, nickname, xpdplot=xpdplot)
321 
322  setdatafolder saveDF
323 };
324 
329 variable ast_import(string nickname){
330  string nickname
331 
332  dfref savedf = getdatafolderdfr()
333 
334  svar /sdfr=$(package_path) dataname
335  duplicate_hemi_scan(nickname, $(package_path), dataname)
336 
337  setdatafolder saveDF
338 };
339 
349 variable ast_update_detector(variable theta, variable tilt, variable phi, variable range){
350  variable theta
351  variable tilt
352  variable phi
353  variable range
354 
355  update_detector(theta, tilt, phi, range)
357 };
358 
360 variable ast_close(){
361  dfref savedf = getdatafolderdfr()
362  setdatafolder $(package_path)
363 
365 
366  svar graphname
367  KillWindow $graphname
368 
369  setdatafolder saveDF
370 };
371 
372 static variable setup_data(){
373  dfref savedf = getdatafolderdfr()
374  setdatafolder $(package_path)
375 
376  nvar buf_size
377  nvar buf_count
378  nvar buf_width
379  buf_size = 0
380  buf_count = 0
381  buf_width = 0
382  make /n=(1,1) /o buf_i
383  make /n=(1) /o buf_th, buf_ph, buf_ti
384 
385  svar dataname
386  variable npolar = 91
387  make_hemi_grid(npolar, dataname)
388 
389  // work-around: set one point to a real number to make the rest of the trace in the graph transparent
390  wave values = $(dataname + "_i")
391  values[numpnts(values) - 1] = 0
392 
393  setdatafolder saveDF
394 };
395 
402 static variable extend_data(variable num_slices){
403  variable num_slices
404 
405  dfref savedf = getdatafolderdfr()
406  setdatafolder $(package_path)
407 
408  nvar buf_size
409  nvar buf_count
410  nvar buf_width
411 
412  variable new_size = buf_size + 91
413  buf_width = num_slices
414 
415  wave buf_i
416  wave buf_th
417  wave buf_ti
418  wave buf_ph
419 
420  redimension /n=(buf_width,new_size) buf_i
421  redimension /n=(new_size) buf_th, buf_ph, buf_ti
422 
423  buf_i[][buf_size, new_size-1] = nan
424  buf_th[buf_size, new_size-1] = nan
425  buf_ph[buf_size, new_size-1] = nan
426  buf_ti[buf_size, new_size-1] = nan
427 
428  buf_size = new_size
429 
430  setdatafolder saveDF
431  return buf_count
432 };
433 
434 static variable setup_detector(){
435  dfref savedf = getdatafolderdfr()
436  setdatafolder $(package_path)
437 
438  make /n=31 /o detector_angle, detector_pol, detector_az, detector_rad
439  setscale /i x -30, 30, "", detector_angle, detector_pol, detector_az, detector_rad
440  detector_angle = x
441 
442  setdatafolder saveDF
443 };
444 
453 static variable add_image_data(wave image, variable theta, variable tilt, variable phi){
454  wave image
455  variable theta
456  variable tilt
457  variable phi
458 
459  dfref savedf = getdatafolderdfr()
460  setdatafolder $(package_path)
461  svar dataname
462  nvar theta_offset
463  nvar tilt_offset
464  nvar phi_offset
465 
466  // extract angle distribution from image using reduction function mechanism from area-import
467  svar red_func_name = reduction_func
468  svar red_params = reduction_params
469  funcref adh5_default_reduction red_func = $red_func_name
470  variable nx = dimsize(image, 0)
471  string loc_params = red_params
472  wave /wave red_results = red_func(image, loc_params)
473  if (numpnts(red_results) < 1)
474  setdatafolder saveDF
475  return 0
476  endif
477 
478  wave profile1 = red_results[0]
479  nx = numpnts(profile1)
480 
481  // write the result to the buffer
482  nvar buf_count
483  nvar buf_size
484  nvar buf_width
485  wave buf_i
486  wave buf_th
487  wave buf_ph
488  wave buf_ti
489 
490  if ((buf_count >= buf_size) || (nx > buf_width))
491  extend_data(nx)
492  setscale /p x dimoffset(profile1,0), dimdelta(profile1,0), waveunits(profile1,0), buf_i
493  endif
494 
495  buf_i[][buf_count] = profile1[p]
496  buf_th[buf_count] = theta - theta_offset
497  buf_ti[buf_count] = -(tilt - tilt_offset)
498  buf_ph[buf_count] = phi - phi_offset
499 
500  buf_count += 1
501 
502  setdatafolder saveDF
503 };
504 
507 static variable process_image_data(){
508  wave image
509  variable theta
510  variable tilt
511  variable phi
512 
513  dfref savedf = getdatafolderdfr()
514  setdatafolder $(package_path)
515  svar dataname
516 
517  nvar buf_count
518  nvar buf_size
519  nvar buf_width
520 
521  wave buf_i
522  wave buf_th
523  wave buf_ph
524  wave buf_ti
525 
526  duplicate /free /R=[0,buf_width-1][0,buf_count-1] buf_i, buf_n
527  duplicate /free /R=[0,buf_count-1] buf_th, w_th
528  duplicate /free /R=[0,buf_count-1] buf_ti, w_ti
529  duplicate /free /R=[0,buf_count-1] buf_ph, w_ph
530 
531  normalize_strip_x(buf_n, smooth_method=4)
532  if (buf_count >= 10)
533  normalize_strip_theta(buf_n, w_th, smooth_method=4)
534  endif
535  if (dimoffset(buf_i,0) < -20)
536  crop_strip(buf_n, -25, 25)
537  else
538  crop_strip(buf_n, -15, 15)
539  endif
540 
541  make /n=1 /free d_polar, d_azi
542  convert_angles_ttpd2polar(w_th, w_ti, w_ph, buf_n, d_polar, d_azi)
543  d_azi += 180// changed 151030 (v1.4)
544  d_azi = d_azi >= 360 ? d_azi - 360 : d_azi
545  hemi_add_anglescan(dataname, buf_n, d_polar, d_azi)
546 
547  setdatafolder saveDF
548 };
549 
559 static variable update_detector(variable theta, variable tilt, variable phi, variable range){
560  variable theta
561  variable tilt
562  variable phi
563  variable range
564 
565  dfref savedf = getdatafolderdfr()
566  setdatafolder $(package_path)
567  nvar theta_offset
568  nvar tilt_offset
569  nvar phi_offset
570 
571  make /n=1 /free m_theta
572  make /n=1 /free m_tilt
573  make /n=1 /free m_phi
574  m_theta = theta - theta_offset
575  m_tilt = tilt - tilt_offset
576  m_tilt *= -1// checked 140702
577  m_phi = phi - phi_offset
578  //m_phi *= -1 // checked 140702
579 
580  wave detector_angle, detector_pol, detector_az, detector_rad
581  setscale /i x -range/2, +range/2, "", detector_angle
582  detector_angle = x
583 
584  convert_angles_ttpa2polar(m_theta, m_tilt, m_phi, detector_angle, detector_pol, detector_az)
585  redimension /n=(numpnts(detector_pol)) detector_rad
586  detector_rad = 2 * tan(detector_pol / 2 * pi / 180)
587  detector_az += 180// changed 151030 (v1.4)
588  detector_az = detector_az >= 360 ? detector_az - 360 : detector_az
589 
590  setdatafolder saveDF
591 };
592 
594 static variable setup_graph(){
595  dfref savedf = getdatafolderdfr()
596  setdatafolder $(package_path)
597 
598  svar dataname
599  svar graphname
600  wave detector_az
601  wave detector_rad
602  wave detector_angle
603  svar tracename = detector_tracename
604 
605  graphname = display_hemi_scan(dataname, graphname=graphname)
606  tracename = WMPolarAppendTrace(graphname, detector_rad, detector_az, 360)
607  ModifyGraph /w=$graphname lstyle($tracename)=0
608  ModifyGraph /w=$graphname lsize($tracename)=1.5
609  ModifyGraph /w=$graphname zColor($tracename)={detector_angle,*,*,RedWhiteBlue,0}
610  ColorScale /w=$graphname /C /N=text1 trace=$tracename
611  ColorScale /w=$graphname /C /N=text1 /F=0 /B=1 /A=LB /X=0.00 /Y=0.00
612  ColorScale /w=$graphname /C /N=text1 width=1.5, heightPct=20, frame=0.00
613  ColorScale /w=$graphname /C /N=text1 lblMargin=0
614  ColorScale /w=$graphname /C /N=text1 nticks=2, tickLen=2.00, tickThick=0.50
615 
616  TextBox /w=$graphname /C /N=tb_manip /F=0 /B=1 /X=0.00 /Y=0.00 /E=2 "\\{\"manip = (%.1f, %.1f, %.1f)\", "
617  AppendText /w=$graphname /N=tb_manip /NOCR "root:packages:pearl_anglescan_tracker:curTheta, "
618  AppendText /w=$graphname /N=tb_manip /NOCR "root:packages:pearl_anglescan_tracker:curTilt, "
619  AppendText /w=$graphname /N=tb_manip /NOCR "root:packages:pearl_anglescan_tracker:curPhi}"
620 
621  // the window hook releases the EPICS variables when the window is killed
622  DoWindow /T $graphname, "Angle Scan Tracker"
623  SetWindow $graphname, hook(ast_hook) = ast_window_hook
624 
625  ControlBar /w=$graphname 21
626  Button b_capture win=$graphname, title="start", pos={0,0}, size={40,21}, proc=PearlAnglescanTracker#bp_capture
627  Button b_capture win=$graphname, fColor=(65535,65535,65535), fSize=10
628  Button b_capture win=$graphname, help={"Start/stop capturing."}
629  PopupMenu pm_params win=$graphname, mode=0, value="load preferences;save preferences;reduction parameters;manipulator offsets", title="parameters"
630  PopupMenu pm_params win=$graphname, pos={70,0}, bodyWidth=80, proc=PearlAnglescanTracker#pmp_parameters
631  PopupMenu pm_params win=$graphname, help={"Load/save/edit data processing parameters"}
632  PopupMenu pm_data win=$graphname, mode=0, value="import;export;load file;save file", title="data"
633  PopupMenu pm_data win=$graphname, pos={120,0}, proc=PearlAnglescanTracker#pmp_data
634  PopupMenu pm_data win=$graphname, help={"Load/save data from/to independent dataset or file"}
635 
636  SetDrawLayer /w=$graphname ProgFront
637  SetDrawEnv /w=$graphname xcoord=rel, ycoord=rel
638  DrawPict /w=$graphname 0, 0, 1, 1, pict_tracker_sample
639 
641 
642  setdatafolder saveDF
643 };
644 
645 static variable update_data_graph(){
646  dfref savedf = getdatafolderdfr()
647  setdatafolder $(package_path)
648 
649  svar dataname
650  svar graphname
651 
652  // nothing to do - trace is updated automatically
653 
654  setdatafolder saveDF
655 };
656 
657 static variable update_detector_graph(){
658  dfref savedf = getdatafolderdfr()
659  setdatafolder $(package_path)
660 
661  svar dataname
662  svar graphname
663 
664  // nothing to do - trace is updated automatically
665 
666  setdatafolder saveDF
667 };
668 
680 static variable epics_connect(){
681  dfref savedf = getdatafolderdfr()
682  setdatafolder $(package_path)
683 
684  // close PVs which may be open from a previous call
686 
687  // create variables and waves
688  make /n=(1)/o arraydata, xscale, yscale
689  make /n=(1,1)/o image
690  variable /g ndimensions
691  variable /g arraysize0, arraysize1
692  variable /g datatype
693  variable /g colormode
694  string /g controls, monitors
695  string /g xunits, yunits
696 
697  // channel ID variables
698  variable /g chidDetectorState = 0
699  variable /g chidArrayData = 0
700  variable /g chidXScale = 0
701  variable /g chidYScale = 0
702  variable /g chidNDimensions = 0
703  variable /g chidArraySize0 = 0
704  variable /g chidArraySize1 = 0
705  variable /g chidDataType = 0
706  variable /g chidColorMode = 0
707  variable /g chidLensMode = 0
708  variable /g chidTheta = 0
709  variable /g chidTilt = 0
710  variable /g chidPhi = 0
711  variable /g curDetectorState = 0
712  variable /g curLensMode = 0
713  variable /g curTheta = 0
714  variable /g curTilt = 0
715  variable /g curPhi = 0
716  variable /g acqTheta = 0
717  variable /g acqTilt = 0
718  variable /g acqPhi = 0
719  variable /g connected = 0
720 
721  string epicsname = "X03DA-SCIENTA:"
722  string imagename = epicsname + "image1:"
723  string camname = epicsname + "cam1:"
724  string manipname = "X03DA-ES2-MA:"
725  variable timeout = 5// seconds
726 
727  #if exists("pvWait")
728  // EPICS.XOP version 0.3.0 or later
729  pvOpen /Q chidDetectorState, camname + "DetectorState_RBV"// 0 = idle
730  pvOpen /Q chidLensMode, camname + "LENS_MODE_RBV"
731  pvOpen /Q chidXScale, camname + "CHANNEL_SCALE_RBV"
732  pvOpen /Q chidYScale, camname + "SLICE_SCALE_RBV"
733  pvOpen /Q chidArrayData, imagename + "ArrayData"
734  pvOpen /Q chidNDimensions, imagename + "NDimensions_RBV"
735  pvOpen /Q chidArraySize0, imagename + "ArraySize0_RBV"
736  pvOpen /Q chidArraySize1, imagename + "ArraySize1_RBV"
737  pvOpen /Q chidDataType, imagename + "DataType_RBV"
738  pvOpen /Q chidColorMode, imagename + "ColorMode_RBV"
739 
740  pvOpen /Q chidTheta, manipname + "THT.RBV"
741  pvOpen /Q chidTilt, manipname + "TLT.RBV"
742  pvOpen /Q chidPhi, manipname + "PHI.RBV"
743 
744  pvWait timeout
745 
746  if (!GetRTError(1))
747  connected = 1
748  endif
749  #elif exists("pvOpen")
750  // EPICS.XOP version < 0.3.0
751  pvOpen /T=(timeout) chidDetectorState, camname + "DetectorState_RBV"// 0 = idle
752  pvOpen /T=(timeout) chidLensMode, camname + "LENS_MODE_RBV"
753  pvOpen /T=(timeout) chidXScale, camname + "CHANNEL_SCALE_RBV"
754  pvOpen /T=(timeout) chidYScale, camname + "SLICE_SCALE_RBV"
755  pvOpen /T=(timeout) chidArrayData, imagename + "ArrayData"
756  pvOpen /T=(timeout) chidNDimensions, imagename + "NDimensions_RBV"
757  pvOpen /T=(timeout) chidArraySize0, imagename + "ArraySize0_RBV"
758  pvOpen /T=(timeout) chidArraySize1, imagename + "ArraySize1_RBV"
759  pvOpen /T=(timeout) chidDataType, imagename + "DataType_RBV"
760  pvOpen /T=(timeout) chidColorMode, imagename + "ColorMode_RBV"
761 
762  pvOpen /T=(timeout) chidTheta, manipname + "THT.RBV"
763  pvOpen /T=(timeout) chidTilt, manipname + "TLT.RBV"
764  pvOpen /T=(timeout) chidPhi, manipname + "PHI.RBV"
765 
766  if (!GetRTError(1))
767  connected = 1
768  endif
769  #endif
770 
771  #if exists("pvMonitor")
772  if (connected)
773  pvMonitor /F=ast_callback_detector chidDetectorState, curDetectorState
774  pvMonitor /F=ast_callback_manip chidTheta, curTheta
775  pvMonitor /F=ast_callback_manip chidTilt, curTilt
776  pvMonitor /F=ast_callback_manip chidPhi, curPhi
777  pvMonitor /F=ast_callback_manip chidLensMode, curLensMode
778  pvMonitor /F=ast_callback_data chidArrayData
779  endif
780  #endif
781 
782  if (connected)
783  print "angle scan tracker: online"
784  else
785  print "angle scan tracker: offline"
786  endif
787 
788  setdatafolder saveDF
789  return !connected
790 };
791 
792 static variable epics_disconnect_chid(string chid_var_name){
793  string chid_var_name
794 
795  #if exists("pvClose")
796  nvar /z chid = $chid_var_name
797  if (nvar_exists(chid))
798  if (chid != 0)
799  pvClose chid
800  endif
801  chid = 0
802  endif
803  #endif
804 };
805 
806 static variable epics_disconnect(){
807  dfref savedf = GetDataFolderDFR()
808  setdatafolder $(package_path)
809 
810  nvar connected
811  if (connected)
812  connected = 0
813  epics_disconnect_chid("chidDetectorState")
814  epics_disconnect_chid("chidArrayData")
815  epics_disconnect_chid("chidXScale")
816  epics_disconnect_chid("chidYScale")
817  epics_disconnect_chid("chidNDimensions")
818  epics_disconnect_chid("chidArraySize0")
819  epics_disconnect_chid("chidArraySize1")
820  epics_disconnect_chid("chidDataType")
821  epics_disconnect_chid("chidColorMode")
822  epics_disconnect_chid("chidLensMode")
823  epics_disconnect_chid("chidTheta")
824  epics_disconnect_chid("chidTilt")
825  epics_disconnect_chid("chidPhi")
826  print "angle scan tracker: offline"
827  endif
828 
829  setdatafolder savedf
830 };
831 
836 static variable ast_window_hook(WMWinHookStruct* s){
837  STRUCT WMWinHookStruct &s
838 
839  Variable hookResult = 0
840 
841  switch(s.eventCode)
842  case 2:// kill
844  break
845  endswitch
846 
847  return hookResult
848 };
849 
851 variable ast_callback_data(variable chan){
852  variable chan
853 
854  nvar capturing = $(package_path + "capturing")
855  if (!capturing)
856  return 0
857  endif
858 
859  dfref savedf = GetDataFolderDFR()
860  setdatafolder $(package_path)
861  #if exists("pvGetWave")
862 
863  // retrieve data
864  nvar chidArrayData
865  nvar chidXScale
866  nvar chidYScale
867  nvar chidNDimensions
868  nvar chidArraySize0
869  nvar chidArraySize1
870  nvar chidDataType
871  nvar chidColorMode
872  nvar chidTheta
873  nvar chidTilt
874  nvar chidPhi
875  nvar acqTheta
876  nvar acqTilt
877  nvar acqPhi
878 
879  wave arraydata
880  wave image
881  wave xscale
882  wave yscale
883  variable ndimensions
884  variable arraysize0
885  variable arraysize1
886  variable datatype
887  variable colormode
888 
889  //printf "array callback: acqtheta = %.1f, acqtilt = %.1f, acqphi = %.1f\r", acqTheta, acqTilt, acqPhi
890 
891  pvGet chidNDimensions, ndimensions
892  pvGet chidArraySize0, arraysize0
893  pvGet chidArraySize1, arraysize1
894  pvGet chidDataType, datatype
895  pvGet chidColorMode, colormode
896 
897  // sanity checks
898  if (ndimensions != 2)
899  return -2
900  endif
901  if (colormode != 0)
902  return -3
903  endif
904 
905  redimension /n=(arraysize0 * arraysize1) arraydata
906  redimension /n=(arraysize0, arraysize1) image
907  redimension /n=(arraysize0) xscale
908  redimension /n=(arraysize1) yscale
909 
910  switch(datatype)
911  case 0:// int8
912  redimension /b arraydata, image
913  break
914  case 1:// uint8
915  redimension /b/u arraydata, image
916  break
917  case 2:// int16
918  redimension /w arraydata, image
919  break
920  case 3:// uint16
921  redimension /w/u arraydata, image
922  break
923  case 4:// int32
924  redimension /i arraydata, image
925  break
926  case 5:// uint32
927  redimension /i/u arraydata, image
928  break
929  case 6:// float32
930  redimension /s arraydata, image
931  break
932  case 7:// float64
933  redimension /d arraydata, image
934  break
935  endswitch
936 
937  pvGetWave chidArrayData, arraydata
938  pvGetWave chidXScale, xscale
939  pvGetWave chidYScale, yscale
940 
941  image = arraydata[p + q * arraysize0]
942  setscale /i x xscale[0], xscale[numpnts(xscale)-1], image
943  setscale /i y yscale[0], yscale[numpnts(yscale)-1], image
944 
945  ast_add_image(image, acqTheta, acqTilt, acqPhi)
946 
947  #endif
948  setdatafolder savedf
949  return 0
950 };
951 
956 variable ast_callback_detector(variable chan){
957  variable chan
958 
959  dfref savedf = GetDataFolderDFR()
960  setdatafolder $(package_path)
961 
962  // retrieve data
963  nvar curDetectorState
964  nvar curTheta
965  nvar curTilt
966  nvar curPhi
967 
968  nvar acqTheta
969  nvar acqTilt
970  nvar acqPhi
971 
972  if (curDetectorState == 1)
973  acqTheta = curTheta
974  acqTilt = curTilt
975  acqPhi = curPhi
976  endif
977 
978  //printf "detector callback: acqtheta = %.1f, acqtilt = %.1f, acqphi = %.1f, detstate = %d\r", acqTheta, acqTilt, acqPhi, curDetectorState
979 
980  setdatafolder savedf
981  return 0
982 };
983 
985 variable ast_callback_manip(variable chan){
986  variable chan
987 
988  dfref savedf = GetDataFolderDFR()
989  setdatafolder $(package_path)
990 
991  // retrieve data
992  nvar lensmode = curLensMode
993  nvar theta = curTheta
994  nvar tilt = curTilt
995  nvar phi = curPhi
996 
997  //printf "manipulator callback: curtheta = %.1f, curtilt = %.1f, curphi = %.1f, lensmode = %d\r", theta, tilt, phi, lensmode
998 
999  variable range
1000  switch(lensmode)
1001  case 1:
1002  range = 45// angular 45
1003  break
1004  case 2:
1005  range = 60// angular 60
1006  break
1007  default:
1008  range = 2// transmission or error
1009  endswitch
1010  ast_update_detector(theta, tilt, phi, range)
1011 
1012  setdatafolder savedf
1013  return 0
1014 };
1015 
1016 // GUI functions
1017 
1018 static variable bp_capture(WMButtonAction* ba){
1019  STRUCT WMButtonAction &ba
1020 
1021  switch( ba.eventCode )
1022  case 2:// mouse up
1023  toggle_capture()
1024  break
1025  case -1:// control being killed
1026  break
1027  endswitch
1028 
1029  return 0
1030 };
1031 
1032 static variable toggle_capture(){
1033  dfref savedf = getdatafolderdfr()
1034  setdatafolder $(package_path)
1035 
1036  nvar capturing
1037  svar graphname
1038 
1039  capturing = !capturing
1040  if (capturing)
1041  ast_prepare()
1042  Button b_capture win=$graphname, title="stop"
1043  else
1044  Button b_capture win=$graphname, title="start"
1045  endif
1046 
1047  setdatafolder saveDF
1048 };
1049 
1050 static variable update_capture(){
1051  dfref savedf = getdatafolderdfr()
1052  setdatafolder $(package_path)
1053 
1054  nvar capturing
1055  svar graphname
1056 
1057  if (capturing)
1058  Button b_capture win=$graphname, title="stop"
1059  else
1060  Button b_capture win=$graphname, title="start"
1061  endif
1062 
1063  setdatafolder saveDF
1064 };
1065 
1066 static variable pmp_data(WMPopupAction* pa){
1067  STRUCT WMPopupAction &pa
1068 
1069  switch( pa.eventCode )
1070  case 2:// mouse up
1071  pmp_data_mouseup(pa)
1072  break
1073  case -1:// control being killed
1074  break
1075  endswitch
1076 
1077  return 0
1078 };
1079 
1080 static variable pmp_data_mouseup(WMPopupAction* pa){
1081  STRUCT WMPopupAction &pa
1082 
1083  switch(pa.popNum)
1084  case 1:
1086  break
1087  case 2:
1089  break
1090  case 3:
1092  break
1093  case 4:
1095  break
1096  endswitch
1097 };
1098 
1100 static variable export_tracker_data(){
1101  dfref savedf = getdatafolderdfr()
1102  setdatafolder $(package_path)
1103 
1104  svar export_folderpath
1105  nvar export_format
1106 
1107  string folderpath = export_folderpath
1108  string nickname = ""
1109  variable format = export_format
1110 
1111  prompt folderpath, "Folder Path"
1112  prompt nickname, "Nick Name"
1113  prompt format, "Format", popup, "PEARL;XPDplot"
1114 
1115  doprompt "Export Parameters", folderpath, nickname, format
1116 
1117  if (v_flag == 0)
1118  export_folderpath = folderpath
1119  export_format = format
1120  // note: if a full or partial path is used, all data folders except for the last in the path must already exist.
1121  newdatafolder /o $folderpath
1122  variable xpdplot = format == 2
1123  ast_export($folderpath, nickname, xpdplot=xpdplot)
1124  endif
1125 
1126  setdatafolder saveDF
1127 };
1128 
1130 static variable import_tracker_data(){
1131  dfref savedf = getdatafolderdfr()
1132  setdatafolder $(package_path)
1133 
1134  svar export_folderpath
1135  string folderpath = export_folderpath
1136  string nickname = ""
1137 
1138  dfref dfBefore = GetDataFolderDFR()
1139  Execute /q/z "CreateBrowser prompt=\"Select wave from dataset\", showWaves=1, showVars=0, showStrs=0"
1140  dfref dfAfter = GetDataFolderDFR()
1141  SetDataFolder dfBefore
1142 
1143  SVAR list = S_BrowserList
1144  NVAR flag = V_Flag
1145 
1146  if ((flag != 0) && (ItemsInList(list) >= 1))
1147  string wname = StringFromList(0, list)
1148  wave w = $wname
1149  string prefix = get_hemi_prefix(w)
1150  dfref df = GetWavesDataFolderDFR(w)
1151  setdatafolder df
1152  ast_import(prefix)
1153  endif
1154 
1155  setdatafolder saveDF
1156 };
1157 
1159 static variable save_tracker_data(){
1160  dfref savedf = getdatafolderdfr()
1161  setdatafolder $(package_path)
1162 
1163  svar dataname
1164  save_hemi_scan(dataname, "", "")
1165 
1166  setdatafolder saveDF
1167 };
1168 
1170 static variable load_tracker_data(){
1171  dfref savedf = getdatafolderdfr()
1172  setdatafolder $(package_path)
1173 
1174  NewDataFolder /O/S load_data
1175  LoadWave /t /q
1176  if (v_flag > 0)
1177  string wname = StringFromList(0, s_wavenames, ";")
1178  wave w = $wname
1179  string prefix = get_hemi_prefix(w)
1180  ast_import(prefix)
1181  endif
1182 
1183  setdatafolder $(package_path)
1184  KillDataFolder /Z load_data
1185 
1186  setdatafolder saveDF
1187 };
1188 
1189 static variable pmp_parameters(WMPopupAction* pa){
1190  STRUCT WMPopupAction &pa
1191 
1192  switch( pa.eventCode )
1193  case 2:// mouse up
1195  break
1196  case -1:// control being killed
1197  break
1198  endswitch
1199 
1200  return 0
1201 };
1202 
1203 static variable pmp_parameters_mouseup(WMPopupAction* pa){
1204  STRUCT WMPopupAction &pa
1205 
1206  switch(pa.popNum)
1207  case 1:
1208  load_prefs()
1209  break
1210  case 2:
1211  save_prefs()
1212  break
1213  case 3:
1215  break
1216  case 4:
1217  edit_offsets()
1218  break
1219  endswitch
1220 
1221 };
1222 
1223 static variable edit_reduction_params(){
1224  dfref savedf = getdatafolderdfr()
1225  setdatafolder $(package_path)
1226 
1227  svar pref_func = reduction_func
1228  svar pref_params = reduction_params
1229 
1230  string loc_func = pref_func
1231  string loc_params = pref_params
1232  if (prompt_func_params(loc_func, loc_params) == 0)
1233  ast_set_processing(loc_func, loc_params)
1234  endif
1235 
1236  setdatafolder saveDF
1237 };
1238 
1239 static variable edit_offsets(){
1240  dfref savedf = getdatafolderdfr()
1241  setdatafolder $(package_path)
1242 
1243  nvar theta_offset
1244  nvar tilt_offset
1245  nvar phi_offset
1246 
1247  variable loc_theta = theta_offset
1248  variable loc_tilt = tilt_offset
1249  variable loc_phi = phi_offset
1250 
1251  prompt loc_theta, "theta offset"
1252  prompt loc_tilt, "tilt offset"
1253  prompt loc_phi, "phi offset"
1254 
1255  doprompt "manipulator offsets", loc_theta, loc_tilt, loc_phi
1256  if (v_flag == 0)
1257  theta_offset = loc_theta
1258  tilt_offset = loc_tilt
1259  phi_offset = loc_phi
1260  endif
1261 
1262  setdatafolder saveDF
1263 };
1264 
variable ast_set_processing(string reduction_func, string reduction_params)
set the data processing parameters
-
variable ast_close()
stop tracker, close graph, release data structures.
-
variable normalize_strip_theta(wave strip, wave theta, variable theta_offset=defaultValue, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
divide the strip by the average polar distribution.
-
static variable epics_connect()
connect the angle scan tracker to EPICS
-
static variable update_detector_graph()
-
static variable bp_capture(WMButtonAction *ba)
-
variable crop_strip(wave strip, variable xlo, variable xhi)
crop a strip at the sides.
-
variable make_hemi_grid(variable npol, string nickname, variable xpdplot=defaultValue)
create a hemispherical, constant solid angle grid
-
variable hemi_add_anglescan(string nickname, wave values, wave polar, wave azi, wave weights=defaultValue)
add an arbitrary angle scan to a hemispherical scan grid.
-
static variable setup_detector()
-
static variable pmp_parameters(WMPopupAction *pa)
-
string get_hemi_prefix(wave w)
finds the prefix given any hemi wave
-
string display_hemi_scan(string nickname, variable projection=defaultValue, variable graphtype=defaultValue, variable do_ticks=defaultValue, variable do_grids=defaultValue, string graphname=defaultValue)
display a plot of a hemispherical angle scan.
-
static variable epics_disconnect()
-
static variable update_data_graph()
-
variable ast_setup()
set up data structures, display graph, and try to connect to analyser.
-
variable convert_angles_ttpd2polar(wave theta, wave tilt, wave phi, wave data, wave polar, wave azi)
convert angles from TTPA (theta-tilt-phi-analyser) scheme to polar coordinates.
-
static const string prefs_objects
semicolon-separated list of persistent variable, string, and wave names
-
static variable setup_graph()
create the graph window.
-
static variable import_tracker_data()
import tracker data (with prompt)
-
variable clear_hemi_grid(string nickname)
clear a hemispherical scan grid
-
static variable extend_data(variable num_slices)
extend the data buffer for the next polar scan
-
static variable pmp_data_mouseup(WMPopupAction *pa)
-
variable ast_prepare(variable theta_offset=defaultValue, variable tilt_offset=defaultValue, variable phi_offset=defaultValue)
prepare for new measurement and clear the data buffer.
-
variable PearlAnglescanTracker(string epicsname, string wbRGB)
Definition: pearl-menu.ipf:187
-
static variable setup_data()
-
static variable epics_disconnect_chid(string chid_var_name)
- -
static variable AfterCompiledHook()
initialize package data once when the procedure is first loaded
-
static variable save_prefs()
save persistent package data to the preferences file.
-
static variable edit_offsets()
-
static variable add_image_data(wave image, variable theta, variable tilt, variable phi)
reduce a detector image and add the result to the data buffer.
-
static const string package_path
data folder path
-
static variable load_tracker_data()
import tracker data from file (with prompt)
-
static variable save_tracker_data()
save tracker data to file (with prompt)
-
static variable update_capture()
-
variable ast_export(dfref folder, string nickname, variable xpdplot=defaultValue)
export tracker data to a separate, independent data set.
-
variable ast_update_detector(variable theta, variable tilt, variable phi, variable range)
update the current position indicator.
-
static variable process_image_data()
process the data buffer to generate the tracker dataset.
-
variable save_hemi_scan(string nickname, string pathname, string filename)
save a hemispherical scan to an Igor text file
-
static variable IgorQuitHook(string app)
disconnect EPICS channels before Igor quits.
-
threadsafe wave adh5_default_reduction(wave source, string *param)
function prototype for adh5_load_reduced_detector
-
variable ast_callback_manip(variable chan)
callback function for new manipulator position from EPICS.
-
variable ast_callback_detector(variable chan)
callback function for new detector state from EPICS.
-
static variable pmp_parameters_mouseup(WMPopupAction *pa)
-
variable prompt_func_params(string func_name, string *func_param)
-
variable convert_angles_ttpa2polar(wave theta, wave tilt, wave phi, wave analyser, wave polar, wave azi)
convert angles from TTPA (theta-tilt-phi-analyser) scheme to polar coordinates.
-
variable ast_add_image(wave image, variable theta, variable tilt, variable phi)
process and add a detector image to the tracker scan.
-
static variable pmp_data(WMPopupAction *pa)
-
variable duplicate_hemi_scan(string source_nickname, dfref dest_folder, string dest_nickname, variable xpdplot=defaultValue)
duplicate a hemispherical scan dataset.
-
static variable init_package()
-
static variable ast_window_hook(WMWinHookStruct *s)
window hook
-
static variable edit_reduction_params()
-
static variable toggle_capture()
-
variable ast_callback_data(variable chan)
callback function for new analyser data from EPICS.
-
variable ast_import(string nickname)
import tracker data from an existing angle scan dataset.
-
static const string package_name
package name is used as data folder name
-
static variable load_prefs()
load persistent package data from the preferences file.
-
variable normalize_strip_x(wave strip, variable smooth_method=defaultValue, variable smooth_factor=defaultValue, variable check=defaultValue)
divide the strip by the average X distribution.
-
static variable update_detector(variable theta, variable tilt, variable phi, variable range)
update the current position indicator.
-
static variable export_tracker_data()
export tracker data (with prompt)
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-area-display_8ipf.html b/doc/html/pearl-area-display_8ipf.html index 97fceb6..8395ef7 100644 --- a/doc/html/pearl-area-display_8ipf.html +++ b/doc/html/pearl-area-display_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-area-display.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
-
pearl-area-display.ipf File Reference
+
pearl-area-display.ipf File Reference
-

visualization tools for 2D and 3D data. -More...

-

Go to the source code of this file.

- - - - - -

-Namespaces

 PearlAreaDisplay
 instant visualization of angle scan and manipulator position.
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

static string graphname_from_dfref (dfref df, string prefix)
 compose a valid and unique graph name from a data folder reference More...
 
string ad_display (wave image)
 open a new graph window with a 2D image. More...
 
string ad_display_histogram (wave image)
 display the histogram of a 2D image. More...
 
string ad_display_profiles (wave image, string filter=defaultValue)
 open a new profiles graph window. More...
 
variable ad_update_profiles (wave image)
 update a profiles graph with new data. More...
 
variable ad_profiles_cursor_mode (wave image, variable mode)
 switch cursors on a profiles graph More...
 
variable ad_profiles_set_cursor (wave image, string cursorname, variable xa, variable ya, variable pscale=defaultValue)
 move a cursor to the specified position in a profiles graph. More...
 
variable ad_profiles_crosshairs (wave image, variable clear=defaultValue)
 draw permanent crosshairs in a profiles graph. More...
 
static wave get_source_image (wave view)
 find the source image wave corresponding to the given view. More...
 
static dfr make_view_folder (wave source)
 create a view data folder. More...
 
static dfr get_view_folder (wave source)
 find the view data folder corresponding to the given source. More...
 
static wave get_view_image (wave source)
 find the view image wave corresponding to the given source. More...
 
static variable bp_reset_cursors (WMButtonAction *ba)
 
static variable svp_smoothing (WMSetVariableAction *sva)
 
static variable pmp_export (WMPopupAction *pa)
 
variable ad_profiles_hook (WMWinHookStruct *s)
 hook function for user events in the profiles window. More...
 
variable ad_calc_cursor_profiles (wave image)
 calculate profiles, statistics, and histogram of a cross-hair delimited region of interest. More...
 
variable ad_calc_profiles (wave image, variable pa, variable qa, variable pb, variable qb)
 calculate profiles, statistics, and histogram of a rectangular region of interest. More...
 
variable ad_export_profile (wave view_image, variable dim, variable trace=defaultValue, variable show=defaultValue, variable overwrite=defaultValue)
 export a profile from a profiles graph to the source data folder. More...
 
static variable set_trace_colors (string graphname)
 
variable ad_calc_histogram (wave image)
 calculate the histogram. More...
 
variable ad_default_image_filter (wave image, string options)
 abstract filter function for image display. More...
 
variable ad_box_filter (wave image, string options)
 boxcar smoothing filter. More...
 
variable ad_transpose_filter (wave image, string options)
 transpose image filter. More...
 
string ad_display_brick (wave data)
 open a new "gizmo" window with three-dimensional data. More...
 
variable ad_brick_slicer (wave data)
 open a slicer panel for 3D data. More...
 
string ad_display_slice (wave data)
 display three-dimensional data by 2D slice. More...
 
static variable update_slice_info ()
 update controls with data scale limits. More...
 
variable ad_gizmo_set_plane (wave brick, variable dim, variable value)
 set the position of a slicing plane of a 3D brick in a Gizmo window. More...
 
variable ad_profiles_set_slice (wave brick, variable dim, variable value)
 set the position of the slicing plane of a 3D brick in a profiles window. More...
 
static variable slp_slice_position (WMSliderAction *sa)
 set slice coordinate (slider procedure). More...
 
static variable svp_slice_position (WMSetVariableAction *sva)
 set slice coordinate (button procedure). More...
 
static variable bp_move_slice (WMButtonAction *ba)
 move slice (button procedure). More...
 
static variable bp_extract_slice (WMButtonAction *ba)
 export a slice (button procedure). More...
 
static variable bp_move_slice_center (wave brick, variable dim, string posvariable)
 move the slice to the center of the dimension (button procedure). More...
 
static variable ad_slicer_move_bg (WMBackgroundStruct *s)
 move a slice by one step (background task). More...
 
variable ad_slicer_init_bg ()
 initialize the slice animation background task. More...
 
variable ad_slicer_start_bg (wave brick, variable dimension, string posvariable, variable delta)
 start the animation. More...
 
variable ad_slicer_stop_bg (string posvariable)
 stop the animation. More...
 
-

Detailed Description

-

visualization tools for 2D and 3D data.

-

these tools were initially developed for monitoring output from EPICS area detector software. they are, however, useful for any kind of intensity versus x,y(,z) data.

-

-2D data

-

TO DO...

-

-3D data

- -

Definition in file pearl-area-display.ipf.

-

Function Documentation

- -
-
- - - - - - - - - - - - - - - - - - -
variable ad_box_filter (wave image,
string options 
)
-
- -

boxcar smoothing filter.

-

filters the image in X and Y directions using Igor's Smooth operation.

-
Parameters
- - - -
imageimage to be filtered: original data and filter result.
optionssmoothing factors in key1=value1;key2=value2;... format.
    -
  • SmoothingX
  • -
  • SmoothingY
  • -
-
-
-
- -

Definition at line 1044 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - -
variable ad_brick_slicer (wave data)
-
- -

open a slicer panel for 3D data.

-

if a panel exists, bring it to the front.

-
Parameters
- - -
datathree-dimensional wave.
-
-
- -

Definition at line 1197 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - -
variable ad_calc_cursor_profiles (wave image)
-
- -

calculate profiles, statistics, and histogram of a cross-hair delimited region of interest.

-
Parameters
- - -
imagewave which contains the image data from the detector.
-
-
-

the function expects further objects as created by ad_display_profiles() in the same data folder as the image wave. the most recent profiles graph of the image must exist, and the cursors A and B must be set on the image.

- -

Definition at line 726 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - -
variable ad_calc_histogram (wave image)
-
- -

calculate the histogram.

-
Parameters
- - -
imagewave which contains the image data from the detector. the function expects further objects as created by ad_display_histogram() in the same data folder as the image wave.
-
-
- -

Definition at line 1007 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable ad_calc_profiles (wave image,
variable pa,
variable qa,
variable pb,
variable qb 
)
-
- -

calculate profiles, statistics, and histogram of a rectangular region of interest.

-

the region of interest a rectangle spanned by the two points A and B. pixels at these coordinates are included.

-
Parameters
- - - - - - -
imagewave which contains the image data.
pafirst point coordinate of A.
qasecond point coordinate of A.
pbfirst point coordinate of B.
qbsecond point coordinate of B.
-
-
-

the function expects further objects as created by ad_display_profiles() in the same data folder as the image wave.

-

this function does not require that the graph exists as long as the data folder is complete.

- -

Definition at line 773 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable ad_default_image_filter (wave image,
string options 
)
-
- -

abstract filter function for image display.

-

this is a function prototype for filtering two-dimensional data for preview. to write your own filter, define a new function which has the same signature.

-
Parameters
- - - -
imageimage to be filtered: original data and filter result.
optionsfilter options in key1=value1;key2=value2;... format.
-
-
-
Returns
the result must be written to the incoming image wave.
- -

Definition at line 1030 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - -
string ad_display (wave image)
-
- -

open a new graph window with a 2D image.

-

this is essentially display; appendimage. the graph is directly linked to the image wave. it is, thus, updated automatically.

-
Parameters
- - -
imagewave which contains the image data.
-
-
-
Returns
(string) name of the graph window
- -

Definition at line 84 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - -
string ad_display_brick (wave data)
-
- -

open a new "gizmo" window with three-dimensional data.

-
Parameters
- - -
datathree-dimensional wave.
-
-
-
Returns
name of the gizmo window.
- -

Definition at line 1082 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - -
string ad_display_histogram (wave image)
-
- -

display the histogram of a 2D image.

-

the function will create additional objects in the same data folder as the image. this objects are displayed in the graph and are updated by calling ad_calc_profiles(). see the code.

-
Parameters
- - -
imagewave which contains the image data from the detector.
-
-
-
Returns
(string) name of the graph window
- -

Definition at line 114 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
string ad_display_profiles (wave image,
string filter = defaultValue 
)
-
- -

open a new profiles graph window.

-

opens an extended graph window with profiles for the specified image. the function copies/creates all necessary data structures in a subfolder of the one which contains the image wave. the data folder name is derived from the image wave name by prefixing with "view_". there can be at most one profiles window of each image wave. the original wave must not be renamed while the graph window is used. to update the graph after modifying the original wave, call ad_update_profiles().

-
Parameters
- - - -
imagewave which contains the image data.
filtername of a filter function which maps the original data to the displayed data. the function must have the same parameters as ad_default_image_filter(). default: boxcar average (ad_box_filter()) using parameters view_filter_smoothing_x and _y.
-
-
-
Returns
name of the graph window
- -

Definition at line 165 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - -
string ad_display_slice (wave data)
-
- -

display three-dimensional data by 2D slice.

-

to select the slice data to display, call ad_profiles_set_slice(), or open a ad_brick_slicer() panel. do not modify the content of the created view_ data folder.

-
Parameters
- - -
datathree-dimensional wave.
-
-
-
Returns
name of the graph window.
- -

Definition at line 1345 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable ad_export_profile (wave view_image,
variable dim,
variable trace = defaultValue,
variable show = defaultValue,
variable overwrite = defaultValue 
)
-
- -

export a profile from a profiles graph to the source data folder.

-

this function does not require that the show exists as long as the view data folder is complete.

-
Parameters
- - - - - - -
view_imagewave which contains the view image (image wave on display in profiles window). the function expects further objects as created by ad_display_profiles() in the same data folder as the view_image wave.
dimdimension index (0 = x, 1 = y).
traceselect profile trace:
    -
  • 0 = cursor A
  • -
  • 1 = cursor B
  • -
  • 2 = average between cursors (default)
  • -
-
showdisplay mode:
    -
  • 0 = do not show (default)
  • -
  • 1 = display in new graph, or append to existing graph
  • -
  • 2 = collate: common graph for all profiles of a dimension. rename graph manually to detach it from future additions.
  • -
-
overwriteoverwrite mode:
    -
  • 0 = create new wave (default). wave name may get a suffix to be unique.
  • -
  • 1 = overwrite existing wave
  • -
-
-
-
- -

Definition at line 875 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable ad_gizmo_set_plane (wave brick,
variable dim,
variable value 
)
-
- -

set the position of a slicing plane of a 3D brick in a Gizmo window.

-
Parameters
- - - - -
brickoriginal data wave.
dimdimension index: 0, 1, or 2.
valuenew coordinate of the slicing plane (axis scaling).
-
-
-
Returns
0 if successful, non-zero otherwise
- -

Definition at line 1422 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable ad_profiles_crosshairs (wave image,
variable clear = defaultValue 
)
-
- -

draw permanent crosshairs in a profiles graph.

-

adds dash-dotted horizontal and vertical crosshairs to a profiles graph. for each active cursor A and/or B, a pair of lines crossing at the cursor position is added. existing crosshairs are moved to the current cursor positions. optionally, existing crosshairs are removed from the graph.

-

in contrast to the cursors, these crosshairs will be exported and printed with the graph. they are drawn using Igor's DrawLine operation. all lines drawn by this function are part of the "crosshairs" draw group.

Parameters
- - - -
imageimage displayed in the graph. this is the original image, not the one in the view data folder.
clear0 (default) = add/update lines. 1 = remove lines.
-
-
- -

Definition at line 481 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable ad_profiles_cursor_mode (wave image,
variable mode 
)
-
- -

switch cursors on a profiles graph

-

the standard cursors allow to select the profiles to display in the profiles panes. additional cursors are shown in the profiles panes.

-

in the background selection mode, additional cursors allow the user to select the limits of the background and peak integration regions. the meaning of the cursors depends on the particular processing function.

-
Parameters
- - - -
modecursor mode.
    -
  • 0 (default) standard profile selection. cursors C-F on profile panes.
  • -
  • 1 background selection. cursors A-F on image.
  • -
-
imageimage displayed in the graph. this is the original image, not the one in the view data folder.
-
-
- -

Definition at line 368 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - -
variable ad_profiles_hook (WMWinHookStruct * s)
-
- -

hook function for user events in the profiles window.

- -

Definition at line 686 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable ad_profiles_set_cursor (wave image,
string cursorname,
variable xa,
variable ya,
variable pscale = defaultValue 
)
-
- -

move a cursor to the specified position in a profiles graph.

-

this function can only set cursors in the image part of the profiles graph.

-
Parameters
- - - - - - -
imageimage displayed in the graph. this is the original image, not the one in the view data folder.
cursornamename of the cursor, e.g. "A" or "B". other cursors are allowed but need to be activated separately.
xax-coordinate to move the cursor to. the position is coerced to the image scale. +/-inf is allowed.
yay-coordinate to move the cursor to. the position is coerced to the image scale. +/-inf is allowed.
pscalescaling of the position argument
    -
  • 0 (default) wave scaling
  • -
  • 1 point scaling
  • -
-
-
-
- -

Definition at line 429 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable ad_profiles_set_slice (wave brick,
variable dim,
variable value 
)
-
- -

set the position of the slicing plane of a 3D brick in a profiles window.

-
Parameters
- - - - -
brickoriginal data wave.
dimdimension index: 0, 1, or 2.
valuenew coordinate of the slicing plane (axis scaling).
-
-
-
Returns
0 if successful, non-zero otherwise
- -

Definition at line 1458 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - -
variable ad_slicer_init_bg ()
-
- -

initialize the slice animation background task.

- -

Definition at line 1717 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable ad_slicer_move_bg (WMBackgroundStruct * s)
-
-static
-
- -

move a slice by one step (background task).

- -

Definition at line 1678 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable ad_slicer_start_bg (wave brick,
variable dimension,
string posvariable,
variable delta 
)
-
- -

start the animation.

-
Parameters
- - - - - -
brick3D data wave
dimensiondimension to animate, 0, 1, or 2.
posvariablefull path to the global position variable.
deltastep increment, should be +/- dimdelta.
-
-
- -

Definition at line 1741 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - -
variable ad_slicer_stop_bg (string posvariable)
-
- -

stop the animation.

-
Parameters
- - -
posvariablefull path to the global position variable.
-
-
- -

Definition at line 1783 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable ad_transpose_filter (wave image,
string options 
)
-
- -

transpose image filter.

-

transposes the image.

-
Parameters
- - - -
imageimage to be transposed: original data and result.
optionsnot used. should be empty.
-
-
- -

Definition at line 1066 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - - - - -
variable ad_update_profiles (wave image)
-
- -

update a profiles graph with new data.

-
Parameters
- - -
imagewave which contains the image data. must be the same (by data folder and name) wave used with ad_display_profiles().
-
-
- -

Definition at line 321 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_extract_slice (WMButtonAction * ba)
-
-static
-
- -

export a slice (button procedure).

-

extract a slice and saves it in a separate wave.

- -

Definition at line 1612 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_move_slice (WMButtonAction * ba)
-
-static
-
- -

move slice (button procedure).

- -

Definition at line 1563 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - -
static variable bp_move_slice_center (wave brick,
variable dim,
string posvariable 
)
-
-static
-
- -

move the slice to the center of the dimension (button procedure).

- -

Definition at line 1666 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_reset_cursors (WMButtonAction * ba)
-
-static
-
- -

Definition at line 618 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static wave get_source_image (wave view)
-
-static
-
- -

find the source image wave corresponding to the given view.

-
Returns
wave reference of the original data wave. the reference may be invalid if the source wave cannot be found.
- -

Definition at line 547 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static dfr get_view_folder (wave source)
-
-static
-
- -

find the view data folder corresponding to the given source.

-

the result data folder reference may be invalid if no view is currently open. use the built-in DataFolderRefStatus function to check for validity.

-
Parameters
- - -
sourcewave which contains the image data. must be the same (by data folder and name) wave used with ad_display_profiles().
-
-
- -

Definition at line 585 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static wave get_view_image (wave source)
-
-static
-
- -

find the view image wave corresponding to the given source.

-
Parameters
- - -
sourcewave which contains the image data. must be the same (by data folder and name) wave used with ad_display_profiles().
-
-
- -

Definition at line 608 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static string graphname_from_dfref (dfref df,
string prefix 
)
-
-static
-
- -

compose a valid and unique graph name from a data folder reference

- -

Definition at line 56 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static dfr make_view_folder (wave source)
-
-static
-
- -

create a view data folder.

- -

Definition at line 561 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pmp_export (WMPopupAction * pa)
-
-static
-
- -

Definition at line 662 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable set_trace_colors (string graphname)
-
-static
-
- -

Definition at line 986 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable slp_slice_position (WMSliderAction * sa)
-
-static
-
- -

set slice coordinate (slider procedure).

- -

Definition at line 1499 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable svp_slice_position (WMSetVariableAction * sva)
-
-static
-
- -

set slice coordinate (button procedure).

- -

Definition at line 1531 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable svp_smoothing (WMSetVariableAction * sva)
-
-static
-
- -

Definition at line 637 of file pearl-area-display.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable update_slice_info ()
-
-static
-
- -

update controls with data scale limits.

-

current folder must be slicer info

- -

Definition at line 1386 of file pearl-area-display.ipf.

- -
-
diff --git a/doc/html/pearl-area-display_8ipf_source.html b/doc/html/pearl-area-display_8ipf_source.html index 84003cf..a7b8472 100644 --- a/doc/html/pearl-area-display_8ipf_source.html +++ b/doc/html/pearl-area-display_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-area-display.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma IgorVersion = 6.2
3 #pragma ModuleName = PearlAreaDisplay
4 #pragma version = 1.04
5 
19 // 3D data is handled by 3 windows. they don't have to be visible all at the same time.
48 
54 
56 static string graphname_from_dfref(dfref df, string prefix){
57  dfref df
58  string prefix
59 
60  string name
61 
62  name = GetDataFolder(1, df)
63  name = ReplaceString("root:", name, "")
64  name = name[0, strlen(name) - 2]
65  name = ReplaceString(" ", name, "")
66  name = CleanupName(prefix + name, 0)
67  if (CheckName(name, 6))
68  name = UniqueName(name, 6, 0)
69  endif
70 
71  return name
72 };
73 
84 string ad_display(wave image){
85  wave image// wave which contains the image data from the detector
86  // returns the name of the graph window
87 
88  dfref savedf = GetDataFolderDFR()
89  dfref imagedf = GetWavesDataFolderDFR(image)
90  setdatafolder imagedf
91 
92  string dfname = ReplaceString("root:", GetDataFolder(1, imagedf), "")
93  string graphtitle = dfname + " View"
94  string /g view_graphname = graphname_from_dfref(imagedf, "view_")
95  svar graphname = view_graphname
96  display /k=1/n=$graphname as graphtitle
97  graphname = s_name
98  appendimage /w=$graphname image
99 
100  setdatafolder savedf
101  return graphname
102 };
103 
114 string ad_display_histogram(wave image){
115  wave image
116 
117  dfref savedf = GetDataFolderDFR()
118  dfref imagedf = GetWavesDataFolderDFR(image)
119  string s_imagedf = GetDataFolder(1, imagedf)
120  setdatafolder imagedf
121 
122  make /n=(1)/o hist// histogram
123 
124  string dfname = ReplaceString("root:", GetDataFolder(1, imagedf), "")
125  string graphtitle = dfname + " Histogram"
126  string /g hist_graphname = graphname_from_dfref(imagedf, "hist_")
127  svar graphname = hist_graphname
128  display /k=1/n=$graphname as graphtitle
129  graphname = s_name
130  appendtograph /w=$graphname hist
131 
132  ModifyGraph /w=$graphname rgb(hist)=(39168,0,0)
133  ModifyGraph /w=$graphname mode=6
134  ModifyGraph /w=$graphname mirror=1
135  ModifyGraph /w=$graphname minor=1
136  ModifyGraph /w=$graphname axThick=0.5
137  ModifyGraph /w=$graphname lblPosMode=1,lblPos=30,lblMargin=0
138  ModifyGraph /w=$graphname btLen=4
139  ModifyGraph /w=$graphname margin(left)=45,margin(bottom)=35,margin(top)=10,margin(right)=10
140  ModifyGraph /w=$graphname gfSize=10
141  Label /w=$graphname bottom "value"
142  Label /w=$graphname left "# pixels"
143 
144  ad_calc_histogram(image)
145 
146  setdatafolder savedf
147  return graphname
148 };
149 
165 string ad_display_profiles(wave image, string filter = defaultValue){
166  wave image
167  string filter
168  variable show_legend = 0// currently not supported
169 
170  if (WaveDims(image) != 2)
171  abort "ad_display_profiles: image wave must be two-dimensional."
172  endif
173  if (ParamIsDefault(filter))
174  filter = "ad_box_filter"
175  endif
176 
177  // data folders and references
178  dfref savedf = GetDataFolderDFR()
179  dfref imagedf = GetWavesDataFolderDFR(image)
180  string s_imagedf = GetDataFolder(1, imagedf)
181  setdatafolder imagedf
182  string s_viewdf = CleanupName("view_" + NameOfWave(image), 0)
183  newdatafolder /o/s $s_viewdf
184  dfref viewdf = GetDataFolderDFR()
185  s_viewdf = GetDataFolder(1, viewdf)
186 
187  // data structures
188  string /g sourcepath = GetWavesDataFolder(image, 2)
189  string viewname = "view_image"
190  duplicate /o image, $viewname /wave=view
191  make /n=(3,3)/o xprofiles// NX x 3 wave with 3 one-dimensional profiles along Y dimension
192  make /n=(3,3)/o yprofiles// NY x 3 wave with 3 one-dimensional profiles along X dimension
193  string /g view_filter
194  string /g view_filter_options
195  view_filter = filter
196  view_filter_options = ""
197  variable /g view_filter_smoothing_x = 1
198  variable /g view_filter_smoothing_y = 1
199  variable /g view_cursor_mode = 0
200  string dfname = ReplaceString("root:", GetDataFolder(1, imagedf), "")
201  string graphtitle = dfname + NameOfWave(image) + " Profiles"
202  string /g prof_graphname = graphname_from_dfref(imagedf, "prof_")
203  svar graphname = prof_graphname
204  variable /g graph_avg// average value in ROI (ROI is defined by the crosshairs A and B)
205  variable /g graph_min// minimum value in ROI
206  variable /g graph_max// maximum value in ROI
207  variable /g graph_sum// sum of all values in ROI
208  variable /g graph_sdev// standard deviation of all values in ROI
209 
210  // graph setup
211  display /k=1 /n=$graphname /w=(100,100,500,400) as graphtitle
212  graphname = s_name
213  AppendToGraph /w=$graphname /L=xprofiles xprofiles[*][0],xprofiles[*][1],xprofiles[*][2]
214  AppendToGraph /w=$graphname /VERT/B=yprofiles yprofiles[*][0],yprofiles[*][1],yprofiles[*][2]
215  AppendImage /w=$graphname view
216  string imgname = StringFromList(0, ImageNameList(graphname, ";"))
217  ModifyImage /w=$graphname $imgname ctab= {*,*,BlueGreenOrange,0}
218  ModifyGraph /w=$graphname rgb(xprofiles)=(39168,0,0),rgb(yprofiles)=(39168,0,0)
219  ModifyGraph /w=$graphname rgb(xprofiles#1)=(0,26112,0),rgb(yprofiles#1)=(0,26112,0)
220  ModifyGraph /w=$graphname rgb(xprofiles#2)=(0,9472,39168),rgb(yprofiles#2)=(0,9472,39168)
221  ModifyGraph /w=$graphname mirror(xprofiles)=2,mirror(bottom)=3,mirror(yprofiles)=2,mirror(left)=3
222  ModifyGraph /w=$graphname nticks=3
223  ModifyGraph /w=$graphname minor=1
224  ModifyGraph /w=$graphname axThick=0.5
225  ModifyGraph /w=$graphname lblPosMode=1,lblPos=30,lblMargin=0
226  ModifyGraph /w=$graphname btLen=4
227  ModifyGraph /w=$graphname freePos(xprofiles)=0
228  ModifyGraph /w=$graphname freePos(yprofiles)=0
229  ModifyGraph /w=$graphname axisEnab(xprofiles)={0.64,1}
230  ModifyGraph /w=$graphname axisEnab(bottom)={0,0.6}
231  ModifyGraph /w=$graphname axisEnab(yprofiles)={0.64,1}
232  ModifyGraph /w=$graphname axisEnab(left)={0,0.6}
233  ModifyGraph /w=$graphname zero(left)=8
234  ModifyGraph /w=$graphname margin(left)=40,margin(bottom)=30,margin(top)=20,margin(right)=40
235  ModifyGraph /w=$graphname gfSize=10
236 
237  // axis labels
238  string labels = note(image)
239  string lab
240  lab = StringByKey("AxisLabelX", labels, "=", "\r")
241  if (!strlen(lab))
242  lab = "X"
243  endif
244  Label /w=$graphname bottom lab + " (\\U)"
245  lab = StringByKey("AxisLabelY", labels, "=", "\r")
246  if (!strlen(lab))
247  lab = "Y"
248  endif
249  Label /w=$graphname left lab + " (\\U)"
250  lab = StringByKey("AxisLabelD", labels, "=", "\r")
251  if (!strlen(lab))
252  lab = "value"
253  endif
254  Label /w=$graphname xprofiles lab + " (\\U)"
255  Label /w=$graphname yprofiles lab + " (\\U)"
256 
257  // legend
258  if (show_legend)
259  Legend /w=$graphname/C/N=text0/J/F=2/D=0.5/T={28}/A=RT/X=0.00/Y=0.00 "\\s(xprofiles)\tprofile A"
260  AppendText /w=$graphname "\\s(xprofiles#1)\tprofile B"
261  AppendText /w=$graphname "\\s(xprofiles#2)\tROI average"
262  AppendText /w=$graphname "min\t\\{" + s_viewdf + "graph_min}"
263  AppendText /w=$graphname "max\t\\{" + s_viewdf + "graph_max}"
264  AppendText /w=$graphname "sum\t\\{" + s_viewdf + "graph_sum}"
265  AppendText /w=$graphname "avg\t\\{" + s_viewdf + "graph_avg}"
266  AppendText /w=$graphname "sdev\t\\{" + s_viewdf + "graph_sdev}"
267  else
268  TextBox /w=$graphname /C/N=text0 /F=0 /B=1 /X=1.00 /Y=1.00
269  lab = StringByKey("Dataset", labels, "=", "\r")
270  if (strlen(lab))
271  AppendText /w=$graphname lab
272  endif
273  AppendText /w=$graphname "sum\t\\{" + s_viewdf + "graph_sum}"
274  AppendText /w=$graphname "avg\t\\{" + s_viewdf + "graph_avg}"
275  AppendText /w=$graphname "sdev\t\\{" + s_viewdf + "graph_sdev}"
276  endif
277 
278  // interactive elements
279  Cursor /w=$graphname /A=1 /P /I /S=2 /H=1 /L=1 A $imgname 0,0
280  Cursor /w=$graphname /A=1 /P /I /S=2 /H=1 /L=1 B $imgname DimSize(view, 0)-1, DimSize(view, 1)-1
281  variable pcurs
282  pcurs = floor(DimSize(xprofiles, 0) / 3)
283  Cursor /w=$graphname /A=0 /P /S=1 /H=0 C xprofiles#2 pcurs
284  pcurs = floor(DimSize(xprofiles, 0) * 2 / 3)
285  Cursor /w=$graphname /A=0 /P /S=1 /H=0 D xprofiles#2 pcurs
286  pcurs = floor(DimSize(yprofiles, 0) / 3)
287  Cursor /w=$graphname /A=0 /P /S=1 /H=0 E yprofiles#2 pcurs
288  pcurs = floor(DimSize(yprofiles, 0) * 2 / 3)
289  Cursor /w=$graphname /A=0 /P /S=1 /H=0 F yprofiles#2 pcurs
290  ShowInfo /w=$graphname /CP=0
291 
292  SetWindow $graphname, hook(ad_profiles_hook)=ad_profiles_hook
293  ControlBar /w=$graphname 21
294  Button b_reset_cursors win=$graphname, title="reset cursors",pos={0,0},size={70,20},proc=PearlAreaDisplay#bp_reset_cursors
295  Button b_reset_cursors win=$graphname, fColor=(65535,65535,65535),fSize=10
296 
297  SetVariable sv_smoothing_x win=$graphname, title="X smoothing",pos={130,2},bodyWidth=40
298  SetVariable sv_smoothing_x win=$graphname, value=view_filter_smoothing_x,limits={1,100,1}
299  SetVariable sv_smoothing_x win=$graphname, proc=PearlAreaDisplay#svp_smoothing
300  SetVariable sv_smooting_y win=$graphname, title="Y smoothing",pos={240,2},bodyWidth=40
301  SetVariable sv_smooting_y win=$graphname, value=view_filter_smoothing_y,limits={1,100,1}
302  SetVariable sv_smooting_y win=$graphname, proc=PearlAreaDisplay#svp_smoothing
303 
304  PopupMenu pm_export win=$graphname, mode=0,title="Export"
305  PopupMenu pm_export win=$graphname, value="X profile;Y profile;X profile (collate);Y profile (collate)"
306  PopupMenu pm_export win=$graphname, pos={308,0},bodyWidth=60,proc=PearlAreaDisplay#pmp_export
307  PopupMenu pm_export win=$graphname, help={"Export profile of selected area and display in graph. Collate mode = display all profiles in same graph."}
308 
309  // data processing
310  ad_update_profiles(image)
311 
312  setdatafolder savedf
313  return graphname
314 };
315 
321 variable ad_update_profiles(wave image){
322  wave image
323 
324  // data folders and references
325  dfref viewdf = get_view_folder(image)
326  if (DataFolderRefStatus(viewdf) == 0)
327  return -1// data folder not found
328  endif
329  dfref savedf = GetDataFolderDFR()
330  setdatafolder viewdf
331 
332  // data structures
333  string viewname = "view_image"
334  duplicate /o image, $viewname /wave=view
335 
336  // data processing
337  svar view_filter
338  svar view_filter_options
339  nvar smoothing_x = view_filter_smoothing_x
340  nvar smoothing_y = view_filter_smoothing_y
341  funcref ad_default_image_filter filterfunc = $view_filter
342  view_filter_options = ReplaceNumberByKey("SmoothingX", view_filter_options, smoothing_x, "=", ";")
343  view_filter_options = ReplaceNumberByKey("SmoothingY", view_filter_options, smoothing_y, "=", ";")
344  filterfunc(view, view_filter_options)
345 
347 
348  setdatafolder savedf
349  return 0
350 };
351 
368 variable ad_profiles_cursor_mode(wave image, variable mode){
369  wave image
370  variable mode
371 
372  dfref savedf = GetDataFolderDFR()
373  wave view_image = get_view_image(image)
374  dfref viewdf = GetWavesDataFolderDFR(view_image)
375  svar /sdfr=viewdf graphname = prof_graphname
376  nvar /sdfr=viewdf cursor_mode = view_cursor_mode
377  wave /sdfr=viewdf xprofiles, yprofiles
378 
379  variable dx = DimSize(view_image, 0)
380  variable dy = DimSize(view_image, 1)
381  switch(mode)
382  case 1:// background selection
383  Cursor /w=$graphname /A=0 /P /I /S=2 /H=1 /L=1 A view_image 0, 0
384  Cursor /w=$graphname /A=0 /P /I /S=2 /H=1 /L=1 B view_image dx-1, dy-1
385  Cursor /w=$graphname /A=0 /P /I /S=2 /H=2 /L=1 C view_image round(0.2 * dx) -1, 0
386  Cursor /w=$graphname /A=0 /P /I /S=2 /H=2 /L=1 D view_image round(0.8 * dx) -1, 0
387  Cursor /w=$graphname /A=0 /P /I /S=2 /H=2 /L=1 E view_image round(0.4 * dx) -1, 0
388  Cursor /w=$graphname /A=0 /P /I /S=2 /H=2 /L=1 F view_image round(0.6 * dx) -1, 0
389 
390  ShowInfo /w=$graphname /CP=0
391  cursor_mode = mode
392  break
393  default:
394  Cursor /w=$graphname /A=1 /P /I /S=2 /H=1 /L=1 A view_image 0,0
395  Cursor /w=$graphname /A=1 /P /I /S=2 /H=1 /L=1 B view_image dx-1, dy-1
396  variable pcurs
397  pcurs = floor(DimSize(xprofiles, 0) / 3)
398  Cursor /w=$graphname /A=0 /P /S=1 /H=0 C xprofiles#2 pcurs
399  pcurs = floor(DimSize(xprofiles, 0) * 2 / 3)
400  Cursor /w=$graphname /A=0 /P /S=1 /H=0 D xprofiles#2 pcurs
401  pcurs = floor(DimSize(yprofiles, 0) / 3)
402  Cursor /w=$graphname /A=0 /P /S=1 /H=0 E yprofiles#2 pcurs
403  pcurs = floor(DimSize(yprofiles, 0) * 2 / 3)
404  Cursor /w=$graphname /A=0 /P /S=1 /H=0 F yprofiles#2 pcurs
405  ShowInfo /w=$graphname /CP=0
406  cursor_mode = 0
407  endswitch
408 
409  setdatafolder savedf
410  return 0
411 };
412 
429 variable ad_profiles_set_cursor(wave image, string cursorname, variable xa, variable ya, variable pscale = defaultValue){
430  wave image
431  string cursorname
432  variable xa, ya
433  variable pscale
434 
435  if (ParamIsDefault(pscale))
436  pscale = 0
437  endif
438 
439  // data folders and references
440  dfref savedf = GetDataFolderDFR()
441  wave view_image = get_view_image(image)
442  dfref viewdf = GetWavesDataFolderDFR(view_image)
443  svar /sdfr=viewdf graphname = prof_graphname
444 
445  variable pa, qa
446  if (pscale)
447  pa = xa
448  qa = ya
449  else
450  pa = round((xa - DimOffset(view_image, 0)) / DimDelta(view_image, 0))
451  qa = round((ya - DimOffset(view_image, 1)) / DimDelta(view_image, 1))
452  endif
453 
454  pa = min(pa, DimSize(view_image, 0) - 1)
455  pa = max(pa, 0)
456  qa = min(qa, DimSize(view_image, 1) - 1)
457  qa = max(qa, 0)
458  Cursor /i /p /w=$graphname $cursorname view_image pa, qa
459 
460  setdatafolder savedf
461  return 0
462 };
463 
474 // the lines can be removed manually using the draw toolbox, or by calling this function with @c clean=1.
481 variable ad_profiles_crosshairs(wave image, variable clear = defaultValue){
482  wave image
483  variable clear
484 
485  if (ParamIsDefault(clear))
486  clear = 0
487  endif
488 
489  // data folders and references
490  wave view_image = get_view_image(image)
491  dfref viewdf = GetWavesDataFolderDFR(view_image)
492  svar /sdfr=viewdf graphname = prof_graphname
493 
494  string cursors = "A;B"
495  string colors = "39168,0,0;0,26112,0"
496  string color
497  variable ncursors
498  variable icursor
499  string cursorname
500  string groupname = "crosshairs"
501  variable xx, yy
502  struct RGBColor rgb
503 
504  if (clear == 0)
505  SetDrawEnv /W=$graphname push
506  DrawAction /w=$graphname getgroup=$groupname, delete, begininsert
507  SetDrawEnv /w=$graphname gstart, gname=$groupname
508 
509  SetDrawEnv /W=$graphname dash=4
510  SetDrawEnv /W=$graphname linethick=0.5
511 
512  ncursors = ItemsInList(cursors, ";")
513  for (icursor=0; icursor < ncursors; icursor += 1)
514  cursorname = StringFromList(icursor, cursors, ";")
515  color = StringFromList(icursor, colors, ";")
516  rgb.red = str2num(StringFromList(0, color, ","))
517  rgb.green = str2num(StringFromList(1, color, ","))
518  rgb.blue = str2num(StringFromList(2, color, ","))
519  if (strlen(CsrInfo($cursorname, graphname)) > 0)
520  xx = hcsr($cursorname, graphname)
521  yy = vcsr($cursorname, graphname)
522  SetDrawEnv /W=$graphname linefgc=(rgb.red, rgb.green, rgb.blue)
523  SetDrawEnv /W=$graphname save
524  SetDrawEnv /W=$graphname xcoord=bottom, ycoord=prel
525  DrawLine /W=$graphname xx, 0, xx, 1
526  SetDrawEnv /W=$graphname xcoord=prel, ycoord=left
527  DrawLine /W=$graphname 0, yy, 1, yy
528  endif
529  endfor
530 
531  SetDrawEnv /w=$graphname gstop
532  DrawAction /w=$graphname endinsert
533  SetDrawEnv /W=$graphname pop
534  SetDrawEnv /W=$graphname save
535  else
536  DrawAction /w=$graphname getgroup=$groupname, delete
537  endif
538 
539  return 0
540 };
541 
547 static wave get_source_image(wave view){
548  wave view// image wave displayed in a profiles window
549 
550  dfref viewdf = GetWavesDataFolderDFR(view)
551  svar /z /sdfr=viewdf sourcepath
552  if (svar_exists(sourcepath))
553  wave /z img = $sourcepath
554  else
555  wave /z img = $""
556  endif
557  return img
558 };
559 
561 static dfr make_view_folder(wave source){
562  wave source// wave which contains the raw data from the detector.
563 
564  // data folders and references
565  dfref savedf = GetDataFolderDFR()
566  dfref imagedf = GetWavesDataFolderDFR(source)
567  string s_imagedf = GetDataFolder(1, imagedf)
568  setdatafolder imagedf
569  string s_viewdf = CleanupName("view_" + NameOfWave(source), 0)
570  newdatafolder /o/s $s_viewdf
571  dfref viewdf = GetDataFolderDFR()
572 
573  setdatafolder savedf
574  return viewdf
575 };
576 
585 static dfr get_view_folder(wave source){
586  wave source
587 
588  // data folders and references
589  dfref savedf = GetDataFolderDFR()
590  dfref imagedf = GetWavesDataFolderDFR(source)
591  dfref viewdf
592  setdatafolder imagedf
593  string s_viewdf = CleanupName("view_" + NameOfWave(source), 0)
594  if (DataFolderExists(s_viewdf))
595  setdatafolder $s_viewdf
596  viewdf = GetDataFolderDFR()
597  endif
598 
599  setdatafolder savedf
600  return viewdf
601 };
602 
608 static wave get_view_image(wave source){
609  wave source
610 
611  dfref viewdf = get_view_folder(source)
612  string viewname = "view_image"
613  wave /sdfr=viewdf view = $viewname
614 
615  return view
616 };
617 
618 static variable bp_reset_cursors(WMButtonAction* ba){
619  STRUCT WMButtonAction &ba
620 
621  switch( ba.eventCode )
622  case 2:// mouse up
623  string imgname = StringFromList(0, ImageNameList(ba.win, ";"))
624  wave /z image = ImageNameToWaveRef(ba.win, imgname)
625  if (waveexists(image))
626  Cursor /i/p A $imgname 0,0
627  Cursor /i/p B $imgname DimSize(image, 0)-1, DimSize(image, 1)-1
628  endif
629  break
630  case -1:// control being killed
631  break
632  endswitch
633 
634  return 0
635 };
636 
637 static variable svp_smoothing(WMSetVariableAction* sva){
638  STRUCT WMSetVariableAction &sva
639 
640  string imglist
641 
642  switch( sva.eventCode )
643  case 1:// mouse up
644  case 2:// Enter key
645  case 3:// Live update
646  imglist = ImageNameList(sva.win, ";")
647  wave /z img = ImageNameToWaveRef(sva.win, StringFromList(0, imglist))
648  if (WaveExists(img))
649  wave source = get_source_image(img)
650  if (WaveExists(source))
651  ad_update_profiles(source)
652  endif
653  endif
654  break
655  case -1:// control being killed
656  break
657  endswitch
658 
659  return 0
660 };
661 
662 static variable pmp_export(WMPopupAction* pa){
663  STRUCT WMPopupAction &pa
664 
665  switch( pa.eventCode )
666  case 2:// mouse up
667  variable popNum = pa.popNum
668 
669  string imgname = StringFromList(0, ImageNameList(pa.win, ";"))
670  wave /z image = ImageNameToWaveRef(pa.win, imgname)
671  if (waveexists(image) && (popNum >= 1) && (popNum <= 2))
672  ad_export_profile(image, popNum - 1, show=1)
673  else if (waveexists(image) && (popNum >= 3) && (popNum <= 4))
674  ad_export_profile(image, popNum - 3, show=2)
675  endif
676 
677  break
678  case -1:// control being killed
679  break
680  endswitch
681 
682  return 0
683 };
684 
686 variable ad_profiles_hook(WMWinHookStruct* s){
687  struct WMWinHookStruct &s
688  variable hookresult = 0
689  string imglist
690  string cmd
691  dfref viewdf
692 
693  switch(s.eventCode)
694  case 2:// delete data folder after window is killed
695  imglist = ImageNameList(s.winName, ";")
696  wave /z img = ImageNameToWaveRef(s.winName, StringFromList(0, imglist))
697  if (WaveExists(img))
698  viewdf = GetWavesDataFolderDFR(img)
699  cmd = "killdatafolder /z " + GetDataFolder(1, viewdf)
700  Execute /P/Q/Z cmd
701  endif
702  break
703  case 7:// update profiles when cursor is moved
704  imglist = ImageNameList(s.winName, ";")
705  wave /z img = ImageNameToWaveRef(s.winName, StringFromList(0, imglist))
706  if (WaveExists(img))
708  hookresult = 1
709  else
710  hookresult = 0
711  endif
712  break
713  endswitch
714 
715  return hookresult
716 };
717 
726 variable ad_calc_cursor_profiles(wave image){
727  wave image
728 
729  dfref savedf = GetDataFolderDFR()
730  dfref imagedf = GetWavesDataFolderDFR(image)
731  setdatafolder imagedf
732 
733  svar graphname = prof_graphname
734 
735  variable pa, qa// point coordinates cursor A
736  if (strlen(CsrInfo(A, graphname)) > 0)
737  pa = pcsr(A, graphname)
738  qa = qcsr(A, graphname)
739  else
740  pa = 0
741  qa = 0
742  endif
743 
744  variable pb, qb// point coordinates cursor B
745  if (strlen(CsrInfo(B, graphname)) > 0)
746  pb = pcsr(B, graphname)
747  qb = qcsr(B, graphname)
748  else
749  pb = DimSize(image, 0) - 1
750  qb = DimSize(image, 1) - 1
751  endif
752 
753  ad_calc_profiles(image, pa, qa, pb, qb)
754  setdatafolder savedf
755 };
756 
773 variable ad_calc_profiles(wave image, variable pa, variable qa, variable pb, variable qb){
774  wave image
775  variable pa, qa
776  variable pb, qb
777 
778  dfref savedf = GetDataFolderDFR()
779  dfref imagedf = GetWavesDataFolderDFR(image)
780  setdatafolder imagedf
781 
782  wave xprofiles
783  wave yprofiles
784  nvar graph_avg
785  nvar graph_min
786  nvar graph_max
787  nvar graph_sum
788  nvar graph_sdev
789 
790  // horizontal profiles at crosshairs
791  redimension /n=(dimsize(image,0), 3) xprofiles
792  setscale /p x dimoffset(image,0), dimdelta(image,0), WaveUnits(image,0), xprofiles
793  setscale d 0, 0, waveunits(image,-1), xprofiles
794  xprofiles[][0] = image[p][qa]
795  xprofiles[][1] = image[p][qb]
796 
797  note /k xprofiles
798  note xprofiles, "SourceWave=" + nameofwave(image)
799  note xprofiles, "SourceDimension=0"
800  note xprofiles, "SourceIndex0=" + num2str(qa)
801  note xprofiles, "SourceIndex1=" + num2str(qb)
802 
803  // average horizontal profile between crosshairs
804  variable qq, q0, q1
805  q0 = min(qa, qb)
806  q1 = max(qa, qb)
807  xprofiles[][2] = 0
808  for (qq = q0; qq <= q1; qq += 1)
809  xprofiles[][2] += image[p][qq]
810  endfor
811  xprofiles[][2] /= q1 - q0 + 1
812 
813  // vertical profiles at crosshairs
814  redimension /n=(dimsize(image,1), 3) yprofiles
815  setscale /p x dimoffset(image,1), dimdelta(image,1), WaveUnits(image,1), yprofiles
816  setscale d 0, 0, waveunits(image,-1), yprofiles
817  yprofiles[][0] = image[pa][p]
818  yprofiles[][1] = image[pb][p]
819 
820  note /k yprofiles
821  note yprofiles, "SourceWave=" + nameofwave(image)
822  note yprofiles, "SourceDimension=1"
823  note yprofiles, "SourceIndex0=" + num2str(pa)
824  note yprofiles, "SourceIndex1=" + num2str(pb)
825 
826  // average vertical profile between crosshairs
827  variable pp, p0, p1
828  p0 = min(pa, pb)
829  p1 = max(pa, pb)
830  yprofiles[][2] = 0
831  for (pp = p0; pp <= p1; pp += 1)
832  yprofiles[][2] += image[pp][p]
833  endfor
834  yprofiles[][2] /= p1 - p0 + 1
835 
836  // statistics between crosshairs
837  Duplicate /r=[p0,p1][q0,q1]/o image, roi_image
838  WaveStats /Q roi_image
839  graph_avg = v_avg
840  graph_min = v_min
841  graph_max = v_max
842  graph_sum = v_avg * v_npnts
843  graph_sdev = v_sdev
844 
845  // histogram
846  wave /z hist
847  if (waveexists(hist))
848  Histogram /B=3 roi_image, hist
849  endif
850 
851  setdatafolder savedf
852 };
853 
875 variable ad_export_profile(wave view_image, variable dim, variable trace = defaultValue, variable show = defaultValue, variable overwrite = defaultValue){
876  wave view_image
877  variable dim
878  variable trace
879  variable show
880  variable overwrite
881 
882  dfref savedf = GetDataFolderDFR()
883 
884  if (ParamIsDefault(trace))
885  trace = 2
886  endif
887  if (ParamIsDefault(show))
888  show = 0
889  endif
890  if (ParamIsDefault(overwrite))
891  overwrite = 0
892  endif
893 
894  // view folder
895  dfref imagedf = GetWavesDataFolderDFR(view_image)
896  string dim_label
897  switch(dim)
898  case 0:
899  wave /sdfr=imagedf profiles=xprofiles
900  dim_label = "x"
901  break
902  case 1:
903  wave /sdfr=imagedf profiles=yprofiles
904  dim_label = "y"
905  break
906  default:
907  return -1// invalid argument
908  endswitch
909  string graphname_string = "export_graph_" + dim_label
910  svar /z /sdfr=imagedf linked_graphname = $graphname_string
911 
912  // source folder
913  wave /z source_image = get_source_image(view_image)
914  if (WaveExists(source_image))
915  dfref sourcedf = GetWavesDataFolderDFR(source_image)
916  setdatafolder sourcedf
917  else
918  return -2// invalid source data folder
919  endif
920 
921  // format dest wave name
922  string profile_note = note(profiles)
923  string name_base
924  string name_dim
925  string name_index
926  string profile_name
927  variable index_width = ceil(log(DimSize(view_image, 1 - dim)))
928  variable index0 = NumberByKey("SourceIndex0", profile_note, "=", "\r")
929  variable index1 = NumberByKey("SourceIndex1", profile_note, "=", "\r")
930  name_dim = "_" + dim_label
931  sprintf name_index, "%0*u_%0*u", index_width, index0, index_width, index1
932  name_base = NameOfWave(source_image)
933  name_base = name_base[0, min(strlen(name_base), 31 - strlen(name_index) - strlen(name_dim) - 1)]
934  profile_name = name_base + name_dim + name_index
935  if ((overwrite == 0) && (CheckName(profile_name, 1)))
936  profile_name = UniqueName(profile_name + "_", 1, 0)
937  endif
938 
939  // create dest wave
940  duplicate /o /r=[][trace] profiles, $profile_name /wave=dest_profile
941  redimension /n=(dimsize(profiles, 0)) dest_profile
942  profile_note = ReplaceStringByKey("SourceWave", profile_note, NameOfWave(source_image), "=", "\r")
943  note /k dest_profile
944  note dest_profile, profile_note
945  print "created", GetWavesDataFolder(dest_profile, 2)
946 
947  if (show)
948  string graphname
949  string graphtitle
950  if (show == 2)
951  // common graph for all profiles of a dimension
952  graphname = "export_profiles_" + dim_label
953  graphtitle = UpperStr(dim_label) + " Profiles"
954  else
955  // one graph per source image
956  if (svar_exists(linked_graphname) && (ItemsInList(WinList(linked_graphname, ";", "WIN:1"), ";") >= 1))
957  graphname = linked_graphname
958  else
959  graphname = GetWavesDataFolder(source_image, 0) + name_dim
960  endif
961  graphtitle = UpperStr(dim_label) + " Profiles: " + GetWavesDataFolder(source_image, 2)
962  endif
963 
964  if ((ItemsInList(WinList(graphname, ";", "WIN:1"), ";") >= 1))
965  appendtograph /w=$graphname dest_profile
966  else
967  setdatafolder imagedf
968  display /k=1 /n=$graphname dest_profile as graphtitle
969  graphname = s_name
970  ModifyGraph /w=$graphname mirror=1,nticks=3,minor=1
971  ModifyGraph /w=$graphname axThick=0.5,btLen=4
972  ModifyGraph /w=$graphname gfSize=10
973  ModifyGraph /w=$graphname grid=2,gridHair=0,gridRGB=(52224,52224,52224)
974  Legend /w=$graphname /C/N=legend0/F=0/B=1/A=LT/X=0.00/Y=0.00
975 
976  if (show != 2)
977  string /g $graphname_string = graphname
978  endif
979  endif
980  endif
981 
982  setdatafolder savedf
983  return 0
984 };
985 
986 static variable set_trace_colors(string graphname){
987  string graphname
988 
989  ModifyGraph /w=$graphname /z rgb[0]=(0, 0, 0)
990  ModifyGraph /w=$graphname /z rgb[1]=(65535, 16385, 16385)
991  ModifyGraph /w=$graphname /z rgb[2]=(2, 39321, 1)
992  ModifyGraph /w=$graphname /z rgb[3]=(0, 0, 65535)
993  ModifyGraph /w=$graphname /z rgb[4]=(39321, 1, 31457)
994  ModifyGraph /w=$graphname /z rgb[5]=(48059, 48059, 48059)
995  ModifyGraph /w=$graphname /z rgb[6]=(65535, 32768, 32768)
996  ModifyGraph /w=$graphname /z rgb[7]=(0, 65535, 0)
997  ModifyGraph /w=$graphname /z rgb[8]=(16385,65535,65535)
998  ModifyGraph /w=$graphname /z rgb[9]=(65535, 32768, 58981)
999 };
1000 
1007 variable ad_calc_histogram(wave image){
1008  wave image
1009 
1010  dfref savedf = GetDataFolderDFR()
1011  dfref imagedf = GetWavesDataFolderDFR(image)
1012  setdatafolder imagedf
1013 
1014  wave hist
1015  Histogram /B=3 image, hist
1016 
1017  setdatafolder savedf
1018 };
1019 
1030 variable ad_default_image_filter(wave image, string options){
1031  wave image
1032  string options
1033 };
1034 
1044 variable ad_box_filter(wave image, string options){
1045  wave image
1046  string options
1047 
1048  variable xsmoothing = NumberByKey("SmoothingX", options, "=", ";")
1049  variable ysmoothing = NumberByKey("SmoothingY", options, "=", ";")
1050 
1051  if ((NumType(xsmoothing) == 0) && (xsmoothing >= 2))
1052  Smooth /B /DIM=0 /E=3 xsmoothing, image
1053  endif
1054  if ((NumType(ysmoothing) == 0) && (ysmoothing >= 2))
1055  Smooth /B /DIM=1 /E=3 ysmoothing, image
1056  endif
1057 };
1058 
1066 variable ad_transpose_filter(wave image, string options){
1067  wave image
1068  string options
1069 
1070  MatrixTranspose image
1071 };
1072 
1073 
1074 // ################### 3D DATA ##################
1075 
1082 string ad_display_brick(wave data){
1083  wave data
1084 
1085  if(exists("NewGizmo") != 4)
1086  abort "Gizmo XOP must be installed."
1087  endif
1088  if (WaveDims(data) != 3)
1089  abort "ad_display_brick: data must be three-dimensional."
1090  endif
1091 
1092  dfref savedf = GetDataFolderDFR()
1093  dfref datadf = GetWavesDataFolderDFR(data)
1094  string s_datadf = GetDataFolder(1, datadf)
1095  dfref viewdf = make_view_folder(data)
1096 
1097  setdatafolder viewdf
1098  string dfname = ReplaceString("root:", s_datadf, "")
1099  string graphtitle = dfname + " Gizmo"
1100  string /g gizmo_graphname = graphname_from_dfref(datadf, "giz_")
1101  svar graphname = gizmo_graphname
1102 
1103  if ((strlen(graphname) > 0) && (wintype(graphname) == 13))
1104  setdatafolder savedf
1105  return graphname// gizmo window exists
1106  endif
1107 
1108  variable nx = dimsize(data, 0)
1109  variable ny = dimsize(data, 1)
1110  variable nz = dimsize(data, 2)
1111 
1112  variable pp
1113  string obj
1114  string cmd
1115 
1116  // igor does not allow calling gizmo functions directly
1117  setdatafolder datadf
1118  sprintf cmd, "NewGizmo /k=1 /n=%s /w=(100,100,500,400) /t=\"%s\"", graphname, graphtitle
1119  execute /q cmd
1120  cmd = "AppendToGizmo /D Axes=BoxAxes, name=axes0"
1121  execute /q cmd
1122 
1123  obj = "surface_xmid"
1124  pp = round(nx / 2 - 1)
1125  sprintf cmd, "AppendToGizmo /D surface=%s, name=%s", nameofwave(data), obj
1126  execute /q cmd
1127  sprintf cmd, "ModifyGizmo modifyObject=%s, property={srcMode, 128}", obj
1128  execute /q cmd
1129  sprintf cmd, "ModifyGizmo ModifyObject=%s, property={plane, %d}", obj, pp
1130  execute /q cmd
1131  sprintf cmd, "ModifyGizmo modifyObject=%s, property={surfaceCtab, BlueGreenOrange}", obj
1132  execute /q cmd
1133  sprintf cmd, "ModifyGizmo ModifyObject=%s, property={SurfaceCTABScaling,128}", obj
1134  execute /q cmd
1135  sprintf cmd, "ModifyGizmo modifyObject=%s, property={surfaceCTABAlpha, 1.0}", obj
1136  execute /q cmd
1137 
1138  obj = "surface_ymid"
1139  pp = round(ny / 2 - 1)
1140  sprintf cmd, "AppendToGizmo /D surface=%s, name=%s", nameofwave(data), obj
1141  execute /q cmd
1142  sprintf cmd, "ModifyGizmo modifyObject=%s, property={srcMode, 64}", obj
1143  execute /q cmd
1144  sprintf cmd, "ModifyGizmo ModifyObject=%s, property={plane, %d}", obj, pp
1145  execute /q cmd
1146  sprintf cmd, "ModifyGizmo modifyObject=%s, property={surfaceCtab, BlueGreenOrange}", obj
1147  execute /q cmd
1148  sprintf cmd, "ModifyGizmo ModifyObject=%s, property={SurfaceCTABScaling,128}", obj
1149  execute /q cmd
1150  sprintf cmd, "ModifyGizmo modifyObject=%s, property={surfaceCTABAlpha, 1.0}", obj
1151  execute /q cmd
1152 
1153  obj = "surface_zmid"
1154  pp = round(nz / 2 - 1)
1155  sprintf cmd, "AppendToGizmo /D surface=%s, name=%s", nameofwave(data), obj
1156  execute /q cmd
1157  sprintf cmd, "ModifyGizmo modifyObject=%s, property={srcMode, 32}", obj
1158  execute /q cmd
1159  sprintf cmd, "ModifyGizmo ModifyObject=%s, property={plane, %d}", obj, pp
1160  execute /q cmd
1161  sprintf cmd, "ModifyGizmo modifyObject=%s, property={surfaceCtab, BlueGreenOrange}", obj
1162  execute /q cmd
1163  sprintf cmd, "ModifyGizmo ModifyObject=%s, property={SurfaceCTABScaling,128}", obj
1164  execute /q cmd
1165  sprintf cmd, "ModifyGizmo modifyObject=%s, property={surfaceCTABAlpha, 1.0}", obj
1166  execute /q cmd
1167 
1168  obj = "axes0"
1169  sprintf cmd, "ModifyGizmo ModifyObject=%s,property={-1,axisScalingMode,1}", obj
1170  execute /q cmd
1171  sprintf cmd, "ModifyGizmo ModifyObject=%s,property={-1,axisColor,0,0,0,1}", obj
1172  execute /q cmd
1173  sprintf cmd, "ModifyGizmo ModifyObject=%s,property={0,ticks,3}", obj
1174  execute /q cmd
1175  sprintf cmd, "ModifyGizmo ModifyObject=%s,property={1,ticks,3}", obj
1176  execute /q cmd
1177  sprintf cmd, "ModifyGizmo ModifyObject=%s,property={2,ticks,3}", obj
1178  execute /q cmd
1179  sprintf cmd, "ModifyGizmo modifyObject=%s property={Clipped,0}", obj
1180  execute /q cmd
1181  sprintf cmd, "ModifyGizmo modifyObject=%s property={-1,fontScaleFactor,2}", obj
1182  execute /q cmd
1183 
1184  sprintf cmd, "ModifyGizmo showAxisCue=1"
1185  execute /q cmd
1186 
1187  setdatafolder savedf
1188  return graphname
1189 };
1190 
1197 variable ad_brick_slicer(wave data){
1198  wave data
1199 
1200  // data folders and references
1201  dfref savedf = GetDataFolderDFR()
1202  dfref datadf = GetWavesDataFolderDFR(data)
1203  string s_datadf = GetDataFolder(1, datadf)
1204  dfref viewdf = make_view_folder(data)
1205 
1206  setdatafolder viewdf
1207  svar /z ex_panel = slicer_panelname
1208  if (svar_exists(ex_panel))
1209  string panels = WinList("SlicerPanel*", ";", "WIN:64")
1210  if (WhichListItem(ex_panel, panels, ";") >= 0)
1211  dowindow /f $(StringFromList(0, panels, ";"))
1212  return 0
1213  endif
1214  endif
1215 
1216  variable /g x_slice_pos
1217  variable /g y_slice_pos
1218  variable /g z_slice_pos
1219  variable /g slab_thickness
1220  string /g brick_path = getwavesdatafolder(data, 2)
1221  variable /g x_autoinc = 0
1222  variable /g y_autoinc = 0
1223  variable /g z_autoinc = 0
1224 
1225  // axis labels
1226  string labels = note(data)
1227  string xlabel = StringByKey("AxisLabelX", labels, "=", "\r")
1228  if (!strlen(xlabel))
1229  xlabel = "X"
1230  endif
1231  string ylabel = StringByKey("AxisLabelY", labels, "=", "\r")
1232  if (!strlen(ylabel))
1233  ylabel = "Y"
1234  endif
1235  string zlabel = StringByKey("AxisLabelZ", labels, "=", "\r")
1236  if (!strlen(zlabel))
1237  zlabel = "Z"
1238  endif
1239  string dlabel = StringByKey("Dataset", labels, "=", "\r")
1240  if (!strlen(dlabel))
1241  dlabel = NameOfWave(data)
1242  endif
1243 
1244  // this section copied from slicer panel
1245  NewPanel /k=1 /W=(500,600,890,940) /N=SlicerPanel as "Brick Slicer"
1246  string /g slicer_panelname = S_name
1247  string panel = s_name
1248 
1249  GroupBox g_xslice win=$panel,pos={8,8},size={376,96},title=xlabel
1250  Slider sl_xslice_position win=$panel,pos={16,32},size={240,56},proc=PearlAreaDisplay#slp_slice_position
1251  Slider sl_xslice_position win=$panel,limits={0,100,1},variable=x_slice_pos,vert= 0
1252  SetVariable sv_xslice_position win=$panel,pos={20,80},size={92,16},proc=PearlAreaDisplay#svp_slice_position,title="X"
1253  SetVariable sv_xslice_position win=$panel,limits={0,100,1},value=x_slice_pos
1254  Button b_xslice_center win=$panel,pos={122,80},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W618"
1255  Button b_xslice_center win=$panel,help={"reset to center position"}
1256  Button b_xslice_extract win=$panel,pos={288,80},size={68,20},proc=PearlAreaDisplay#bp_extract_slice,title="extract slice"
1257  Button b_xslice_extract win=$panel,help={"extract this slice to a separate wave"}
1258  //CheckBox cb_xslab_active win=$panel,pos={288,80},size={80,16},title="Display X Slab"
1259  //CheckBox cb_xslab_active win=$panel,value= 0
1260  TitleBox tb_xslice_animation win=$panel,pos={288,32},size={356,16},title="animation",frame=0
1261  TitleBox tb_xslice_animation win=$panel,anchor= MC
1262  Button b_xslice_back win=$panel,pos={288,48},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W646"
1263  Button b_xslice_back win=$panel,help={"animate backwards"}
1264  Button b_xslice_forward win=$panel,pos={312,48},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W649"
1265  Button b_xslice_forward win=$panel,help={"animate forward"}
1266  Button b_xslice_stop win=$panel,pos={336,48},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W616"
1267  Button b_xslice_stop win=$panel,help={"stop animation"}
1268 
1269  GroupBox g_yslice win=$panel,pos={8,108},size={376,96},title=ylabel
1270  Slider sl_yslice_position win=$panel,pos={16,132},size={240,56},proc=PearlAreaDisplay#slp_slice_position
1271  Slider sl_yslice_position win=$panel,limits={0,100,1},variable=y_slice_pos,vert= 0
1272  SetVariable sv_yslice_position win=$panel,pos={20,180},size={92,16},proc=PearlAreaDisplay#svp_slice_position,title="Y"
1273  SetVariable sv_yslice_position win=$panel,limits={0,100,1},value=y_slice_pos
1274  Button b_yslice_center win=$panel,pos={122,180},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W618"
1275  Button b_yslice_center win=$panel,help={"reset to center position"}
1276  Button b_yslice_extract win=$panel,pos={288,180},size={68,20},proc=PearlAreaDisplay#bp_extract_slice,title="extract slice"
1277  Button b_yslice_extract win=$panel,help={"extract this slice to a separate wave"}
1278  //CheckBox cb_yslab_active win=$panel,pos={288,180},size={80,16},title="Display Y Slab"
1279  //CheckBox cb_yslab_active win=$panel,value= 0
1280  TitleBox tb_yslice_animation win=$panel,pos={288,132},size={356,16},title="animation",frame=0
1281  TitleBox tb_yslice_animation win=$panel,anchor= MC
1282  Button b_yslice_back win=$panel,pos={288,148},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W646"
1283  Button b_yslice_back win=$panel,help={"animate backwards"}
1284  Button b_yslice_forward win=$panel,pos={312,148},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W649"
1285  Button b_yslice_forward win=$panel,help={"animate forward"}
1286  Button b_yslice_stop win=$panel,pos={336,148},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W616"
1287  Button b_yslice_stop win=$panel,help={"stop animation"}
1288 
1289  GroupBox g_zslice win=$panel,pos={8,208},size={376,96},title=zlabel
1290  Slider sl_zslice_position win=$panel,pos={16,232},size={240,56},proc=PearlAreaDisplay#slp_slice_position
1291  Slider sl_zslice_position win=$panel,limits={0,100,1},variable=z_slice_pos,vert= 0
1292  SetVariable sv_zslice_position win=$panel,pos={20,280},size={92,16},proc=PearlAreaDisplay#svp_slice_position,title="Z"
1293  SetVariable sv_zslice_position win=$panel,limits={0,100,1},value=z_slice_pos
1294  Button b_zslice_center win=$panel,pos={122,280},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W618"
1295  Button b_zslice_center win=$panel,help={"reset to center position"}
1296  Button b_zslice_extract win=$panel,pos={288,280},size={68,20},proc=PearlAreaDisplay#bp_extract_slice,title="extract slice"
1297  Button b_zslice_extract win=$panel,help={"extract this slice to a separate wave"}
1298  //CheckBox cb_zslab_active win=$panel,pos={288,280},size={80,16},title="Display Z Slab"
1299  //CheckBox cb_zslab_active win=$panel,value= 0
1300  TitleBox tb_zslice_animation win=$panel,pos={288,232},size={356,16},title="animation",frame=0
1301  TitleBox tb_zslice_animation win=$panel,anchor= MC
1302  Button b_zslice_back win=$panel,pos={288,248},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W646"
1303  Button b_zslice_back win=$panel,help={"animate backwards"}
1304  Button b_zslice_forward win=$panel,pos={312,248},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W649"
1305  Button b_zslice_forward win=$panel,help={"animate forward"}
1306  Button b_zslice_stop win=$panel,pos={336,248},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W616"
1307  Button b_zslice_stop win=$panel,help={"stop animation"}
1308 
1309  TitleBox t_slicerpath win=$panel,pos={8,316},size={128,20},disable=2,title=dlabel
1310  //SetVariable setvar0 win=$panel,pos={240,316},size={120,16},title="slab thickness"
1311  //SetVariable setvar0 win=$panel,limits={1,inf,1},value=slab_thickness
1312 
1313  // update control limits and move slicing planes to the center
1314  setwindow $panel, userdata(control_datafolder) = GetDataFolder(1, viewdf)
1315  setwindow $panel, userdata(brick_path) = brick_path
1317  x_slice_pos = dimoffset(data, 0) + dimsize(data, 0) * dimdelta(data, 0) / 2
1318  y_slice_pos = dimoffset(data, 1) + dimsize(data, 1) * dimdelta(data, 1) / 2
1319  z_slice_pos = dimoffset(data, 2) + dimsize(data, 2) * dimdelta(data, 2) / 2
1320 
1321  svar /z /sdfr=viewdf gizmo_graphname
1322  if (svar_exists(gizmo_graphname) && (strlen(gizmo_graphname) > 0) && (wintype(gizmo_graphname) == 13))
1323  ad_gizmo_set_plane(data, 0, x_slice_pos)
1324  ad_gizmo_set_plane(data, 1, y_slice_pos)
1325  ad_gizmo_set_plane(data, 2, z_slice_pos)
1326  endif
1327  svar /z /sdfr=viewdf slice_graphname
1328  if (svar_exists(slice_graphname) && (strlen(slice_graphname) > 0) && (wintype(slice_graphname) == 1))
1329  ad_profiles_set_slice(data, 2, z_slice_pos)
1330  endif
1331 
1333  setdatafolder savedf
1334 };
1335 
1345 string ad_display_slice(wave data){
1346  wave data
1347 
1348  if (WaveDims(data) != 3)
1349  abort "ad_display_slice: data must be three-dimensional."
1350  endif
1351 
1352  dfref savedf = GetDataFolderDFR()
1353  dfref datadf = GetWavesDataFolderDFR(data)
1354  string s_datadf = GetDataFolder(1, datadf)
1355  dfref viewdf = make_view_folder(data)
1356 
1357  setdatafolder viewdf
1358  string dfname = ReplaceString("root:", s_datadf, "")
1359  dfname = dfname[0, strlen(dfname) - 2]
1360  string graphtitle = dfname + " Slice"
1361 
1362  if (exists("slice_graphname") != 2)
1363  string /g slice_graphname = ""
1364  endif
1365  string /g slice_wavename = CleanupName("slice_" + NameOfWave(data), 0)
1366  svar graphname = slice_graphname
1367  svar slicename = slice_wavename
1368 
1369  make /n=(1,1)/o $slicename
1370  wave slice = $slicename
1371  if ((strlen(graphname) == 0) || (wintype(graphname) != 1))
1372  graphname = ad_display_profiles(slice)
1373  endif
1374  variable z_slice_pos = dimoffset(data, 2) + dimsize(data, 2) * dimdelta(data, 2) / 2
1375  ad_profiles_set_slice(data, 2, z_slice_pos)
1376  ad_profiles_set_cursor(slice, "A", -inf, -inf, pscale=1)
1377  ad_profiles_set_cursor(slice, "B", +inf, +inf, pscale=1)
1378 
1379  setdatafolder savedf
1380  return graphname
1381 };
1382 
1386 static variable update_slice_info(){
1387  dfref savedf = GetDataFolderDFR()
1388 
1389  svar brick_path
1390  //svar slicer_panelname
1391  wave brick = $brick_path
1392 
1393  //dowindow /F $slicer_panelname
1394  variable lo, hi, inc
1395  lo = dimoffset(brick, 0)
1396  inc = dimdelta(brick, 0)
1397  hi = lo + inc * (dimsize(brick, 0) - 1)
1398  Slider sl_xslice_position,limits={lo,hi,inc}
1399  SetVariable sv_xslice_position,limits={lo,hi,inc}
1400  lo = dimoffset(brick, 1)
1401  inc = dimdelta(brick, 1)
1402  hi = lo + inc * (dimsize(brick, 1) - 1)
1403  Slider sl_yslice_position,limits={lo,hi,inc}
1404  SetVariable sv_yslice_position,limits={lo,hi,inc}
1405  lo = dimoffset(brick, 2)
1406  inc = dimdelta(brick, 2)
1407  hi = lo + inc * (dimsize(brick, 2) - 1)
1408  Slider sl_zslice_position,limits={lo,hi,inc}
1409  SetVariable sv_zslice_position,limits={lo,hi,inc}
1410 
1411  setdatafolder savedf
1412 };
1413 
1422 variable ad_gizmo_set_plane(wave brick, variable dim, variable value){
1423  wave brick
1424  variable dim
1425  variable value
1426 
1427  dfref savedf = GetDataFolderDFR()
1428  dfref datadf = GetWavesDataFolderDFR(brick)
1429  dfref viewdf = get_view_folder(brick)
1430  svar /z /sdfr=viewdf graphname=gizmo_graphname
1431 
1432  variable pp = round((value - dimoffset(brick, dim)) / dimdelta(brick, dim))
1433  if ((pp < 0) || (pp >= dimsize(brick, dim)))
1434  return -1// requested value out of range
1435  endif
1436 
1437  if (svar_exists(graphname) && (strlen(graphname) > 0) && (wintype(graphname) == 13))
1438  string axes = "xyz"
1439  string obj = "surface_" + axes[dim] + "mid"
1440  string cmd
1441  sprintf cmd, "ModifyGizmo /N=%s ModifyObject=%s, property={plane, %d}", graphname, obj, pp
1442  execute /q cmd
1443  else
1444  return -2// gizmo window not found
1445  endif
1446 
1447  return 0
1448 };
1449 
1458 variable ad_profiles_set_slice(wave brick, variable dim, variable value){
1459  wave brick
1460  variable dim
1461  variable value
1462 
1463  dfref savedf = GetDataFolderDFR()
1464  dfref datadf = GetWavesDataFolderDFR(brick)
1465  dfref viewdf = get_view_folder(brick)
1466  svar /z /sdfr=viewdf graphname = slice_graphname
1467  svar /z /sdfr=viewdf slicename = slice_wavename
1468 
1469  variable pp = round((value - dimoffset(brick, dim)) / dimdelta(brick, dim))
1470  if ((pp < 0) || (pp >= dimsize(brick, dim)))
1471  return -1// requested value out of range
1472  endif
1473 
1474  if (svar_exists(graphname) && (strlen(graphname) > 0) && (wintype(graphname) == 1))
1475  setdatafolder viewdf
1476  switch(dim)
1477  case 0:// X
1478  wave wdest = ad_extract_slab_x(brick, pp, pp, slicename)
1479  ad_update_profiles(wdest)
1480  break
1481  case 1:// Y
1482  wave wdest = ad_extract_slab_y(brick, pp, pp, slicename)
1483  ad_update_profiles(wdest)
1484  break
1485  case 2:// Z
1486  wave wdest = ad_extract_slab_z(brick, pp, pp, slicename)
1487  ad_update_profiles(wdest)
1488  break
1489  endswitch
1490  else
1491  return -2// graph window not found
1492  endif
1493 
1494  setdatafolder savedf
1495  return 0
1496 };
1497 
1499 static variable slp_slice_position(WMSliderAction* sa){
1500  STRUCT WMSliderAction &sa
1501 
1502  dfref savedf = GetDataFolderDFR()
1503 
1504  switch( sa.eventCode )
1505  case -1:// control being killed
1506  break
1507  default:
1508  if( sa.eventCode & 1 )// value set
1509  string control_datafolder = GetUserData(sa.win, "", "control_datafolder")
1510  setdatafolder control_datafolder
1511  string brick_path = GetUserData(sa.win, "", "brick_path")
1512  string axis = StringFromList(1, sa.ctrlName, "_")
1513  variable dim = char2num(axis[0]) - char2num("x")
1514 
1515  wave /z brick = $brick_path
1516  if (WaveExists(brick))
1517  ad_gizmo_set_plane(brick, dim, sa.curval)
1518  ad_profiles_set_slice(brick, dim, sa.curval)
1519  else
1520  Abort "can't find original wave " + brick_path
1521  endif
1522  endif
1523  break
1524  endswitch
1525 
1526  setdatafolder savedf
1527  return 0
1528 };
1529 
1531 static variable svp_slice_position(WMSetVariableAction* sva){
1532  STRUCT WMSetVariableAction &sva
1533 
1534  dfref savedf = GetDataFolderDFR()
1535 
1536  switch( sva.eventCode )
1537  case 1:// mouse up
1538  case 2:// Enter key
1539  case 3:// Live update
1540  string control_datafolder = GetUserData(sva.win, "", "control_datafolder")
1541  setdatafolder control_datafolder
1542  string brick_path = GetUserData(sva.win, "", "brick_path")
1543  string axis = StringFromList(1, sva.ctrlName, "_")
1544  variable dim = char2num(axis[0]) - char2num("x")
1545 
1546  wave /z brick = $brick_path
1547  if (WaveExists(brick))
1548  ad_gizmo_set_plane(brick, dim, sva.dval)
1549  ad_profiles_set_slice(brick, dim, sva.dval)
1550  else
1551  Abort "can't find original wave " + brick_path
1552  endif
1553  break
1554  case -1:// control being killed
1555  break
1556  endswitch
1557 
1558  setdatafolder savedf
1559  return 0
1560 };
1561 
1563 static variable bp_move_slice(WMButtonAction* ba){
1564  STRUCT WMButtonAction &ba
1565 
1566  dfref savedf = GetDataFolderDFR()
1567 
1568  switch( ba.eventCode )
1569  case 2:// mouse up
1570  string control_datafolder = GetUserData(ba.win, "", "control_datafolder")
1571  setdatafolder control_datafolder
1572  string brick_path = GetUserData(ba.win, "", "brick_path")
1573  string axis = StringFromList(1, ba.ctrlName, "_")
1574  string cmd = StringFromList(2, ba.ctrlName, "_")
1575  variable dim = char2num(axis[0]) - char2num("x")
1576  string posvariable = getdatafolder(1) + axis[0] + "_slice_pos"
1577  nvar pos = $(posvariable)
1578 
1579  wave /z brick = $brick_path
1580  if (WaveExists(brick))
1581  strswitch (cmd)
1582  case "forward":
1583  ad_slicer_start_bg(brick, dim, posvariable, dimdelta(brick, dim))
1584  break
1585  case "back":
1586  ad_slicer_start_bg(brick, dim, posvariable, -dimdelta(brick, dim))
1587  break
1588  case "center":
1589  ad_slicer_stop_bg(posvariable)
1590  bp_move_slice_center(brick, dim, posvariable)
1591  break
1592  case "stop":
1593  ad_slicer_stop_bg(posvariable)
1594  break
1595  endswitch
1596  else
1597  ad_slicer_stop_bg(posvariable)
1598  Abort "can't find original wave " + brick_path
1599  endif
1600  break
1601  case -1:// control being killed
1602  break
1603  endswitch
1604 
1605  setdatafolder savedf
1606  return 0
1607 };
1608 
1612 static variable bp_extract_slice(WMButtonAction* ba){
1613  STRUCT WMButtonAction &ba
1614 
1615  dfref savedf = GetDataFolderDFR()
1616 
1617  switch( ba.eventCode )
1618  case 2:// mouse up
1619  string control_datafolder = GetUserData(ba.win, "", "control_datafolder")
1620  setdatafolder control_datafolder
1621  string brick_path = GetUserData(ba.win, "", "brick_path")
1622  wave brick = $brick_path
1623  dfref brickdf = GetWavesDataFolderDFR(brick)
1624 
1625  string axis = StringFromList(1, ba.ctrlName, "_")
1626  string cmd = StringFromList(2, ba.ctrlName, "_")
1627  variable dim = char2num(axis[0]) - char2num("x")
1628  string posvariable = getdatafolder(1) + axis[0] + "_slice_pos"
1629 
1630  nvar pos = $(posvariable)
1631  variable pp = round((pos - dimoffset(brick, dim)) / dimdelta(brick, dim))
1632  if ((pp < 0) || (pp >= dimsize(brick, dim)))
1633  return -1// requested value out of range
1634  endif
1635 
1636  variable dig = ceil(log(dimsize(brick, dim)))
1637  string slicename
1638  sprintf slicename, "%s_%s%0*u", NameOfWave(brick), axis[0], dig, pp
1639  setdatafolder brickdf
1640  switch(dim)
1641  case 0:// X
1642  wave wdest = ad_extract_slab_x(brick, pp, pp, slicename)
1643  break
1644  case 1:// Y
1645  wave wdest = ad_extract_slab_y(brick, pp, pp, slicename)
1646  break
1647  case 2:// Z
1648  wave wdest = ad_extract_slab_z(brick, pp, pp, slicename)
1649  break
1650  endswitch
1651 
1652  string msg
1653  sprintf msg, "%s=%g", axis[0], pos
1654  note wdest, msg
1655 
1656  break
1657  case -1:// control being killed
1658  break
1659  endswitch
1660 
1661  setdatafolder savedf
1662  return 0
1663 };
1664 
1666 static variable bp_move_slice_center(wave brick, variable dim, string posvariable){
1667  wave brick
1668  variable dim
1669  string posvariable
1670 
1671  nvar pos = $posvariable
1672  pos = dimoffset(brick, dim) + dimdelta(brick, dim) * dimsize(brick, dim) / 2
1673  ad_gizmo_set_plane(brick, dim, pos)
1674  ad_profiles_set_slice(brick, dim, pos)
1675 };
1676 
1678 static variable ad_slicer_move_bg(WMBackgroundStruct* s){
1679  STRUCT WMBackgroundStruct &s
1680 
1681  dfref savedf = GetDataFolderDFR()
1682  setdatafolder root:pearl_area:slicer
1683  wave /t bg_brickpaths
1684  wave /t bg_graphnames
1685  wave /t bg_variablepaths
1686  wave bg_dimensions
1687  wave bg_increments
1688 
1689  variable ii
1690  variable nn = numpnts(bg_brickpaths)
1691  variable dim
1692  variable pp
1693 
1694  for (ii = 0; ii < nn; ii += 1)
1695  wave /z brick = $bg_brickpaths[ii]
1696  nvar /z pos = $bg_variablepaths[ii]
1697  dim = bg_dimensions[0]
1698  pos += bg_increments[ii]
1699  // wrap around at limits
1700  pp = round((pos - dimoffset(brick, dim)) / dimdelta(brick, dim))
1701  if (pp <= -0.5)
1702  pos = dimoffset(brick, dim) + dimdelta(brick, dim) * (dimsize(brick, dim) - 1)
1703  else if (pp >= dimsize(brick, dim) - 0.5)
1704  pos = dimoffset(brick, dim)
1705  endif
1706  if (waveexists(brick))
1707  ad_gizmo_set_plane(brick, dim, pos)
1708  ad_profiles_set_slice(brick, dim, pos)
1709  endif
1710  endfor
1711 
1712  setdatafolder savedf
1713  return 0
1714 };
1715 
1718  dfref savedf = GetDataFolderDFR()
1719  setdatafolder root:
1720  newdatafolder /o/s pearl_area
1721  newdatafolder /o/s slicer
1722 
1723  make /n=0/o/t bg_brickpaths
1724  make /n=0/o/t bg_variablepaths
1725  make /n=0/o/i/u bg_dimensions
1726  make /n=0/o bg_increments
1727 
1728  CtrlNamedBackground ad_slicer, period = 30, proc = PearlAreaDisplay#ad_slicer_move_bg
1729 
1730  setdatafolder savedf
1731  return 0
1732 };
1733 
1741 variable ad_slicer_start_bg(wave brick, variable dimension, string posvariable, variable delta){
1742  wave brick// 3D data wave
1743  variable dimension// dimension to animate, 0, 1, or 2
1744  string posvariable// full path to the global position variable
1745  variable delta// step increment, should be +/- dimdelta
1746 
1747  dfref savedf = GetDataFolderDFR()
1748  setdatafolder root:pearl_area:slicer
1749  wave /t bg_brickpaths
1750  wave /t bg_variablepaths
1751  wave bg_dimensions
1752  wave bg_increments
1753 
1754  // create entry in ad_slicer background task table
1755  variable idx
1756  FindValue /TEXT=posvariable /TXOP=4 /Z bg_variablepaths
1757  if (v_value >= 0)
1758  idx = v_value
1759  else
1760  idx = numpnts(bg_variablepaths)
1761  InsertPoints idx, 1, bg_brickpaths, bg_variablepaths, bg_dimensions, bg_increments
1762  endif
1763 
1764  // set background task
1765  bg_brickpaths[idx] = GetWavesDataFolder(brick, 2)
1766  bg_variablepaths[idx] = posvariable
1767  bg_dimensions[idx] = dimension
1768  bg_increments[idx] = delta
1769 
1770  // start background task
1771  if (numpnts(bg_variablepaths) > 0)
1772  CtrlNamedBackground ad_slicer, start
1773  endif
1774 
1775  setdatafolder savedf
1776  return 0
1777 };
1778 
1783 variable ad_slicer_stop_bg(string posvariable){
1784  string posvariable
1785 
1786  dfref savedf = GetDataFolderDFR()
1787  setdatafolder root:pearl_area:slicer
1788  wave /t bg_brickpaths
1789  wave /t bg_variablepaths
1790  wave bg_dimensions
1791  wave bg_increments
1792 
1793  // find entry in ad_slicer background task table
1794  FindValue /TEXT=posvariable /TXOP=4 /Z bg_variablepaths
1795  if (v_value >= 0)
1796  DeletePoints v_value, 1, bg_brickpaths, bg_variablepaths, bg_dimensions, bg_increments
1797  endif
1798 
1799  // stop background task if task table is empty
1800  if (numpnts(bg_variablepaths) == 0)
1801  CtrlNamedBackground ad_slicer, stop
1802  endif
1803 
1804  setdatafolder savedf
1805  return 0
1806 };
1807 
threadsafe wave ad_extract_slab_x(wave dataset, variable p1, variable p2, string destname, variable noavg=defaultValue)
-
variable ad_profiles_cursor_mode(wave image, variable mode)
switch cursors on a profiles graph
-
static variable ad_slicer_move_bg(WMBackgroundStruct *s)
move a slice by one step (background task).
-
static variable set_trace_colors(string graphname)
-
static variable slp_slice_position(WMSliderAction *sa)
set slice coordinate (slider procedure).
-
variable ad_slicer_start_bg(wave brick, variable dimension, string posvariable, variable delta)
start the animation.
-
variable ad_profiles_crosshairs(wave image, variable clear=defaultValue)
draw permanent crosshairs in a profiles graph.
-
variable ad_update_profiles(wave image)
update a profiles graph with new data.
-
variable ad_slicer_stop_bg(string posvariable)
stop the animation.
-
variable ad_default_image_filter(wave image, string options)
abstract filter function for image display.
-
static variable svp_smoothing(WMSetVariableAction *sva)
-
variable ad_brick_slicer(wave data)
open a slicer panel for 3D data.
-
variable ad_profiles_set_slice(wave brick, variable dim, variable value)
set the position of the slicing plane of a 3D brick in a profiles window.
-
static dfr get_view_folder(wave source)
find the view data folder corresponding to the given source.
-
variable ad_calc_histogram(wave image)
calculate the histogram.
-
static dfr make_view_folder(wave source)
create a view data folder.
-
threadsafe wave ad_extract_slab_z(wave dataset, variable r1, variable r2, string destname, variable noavg=defaultValue)
-
variable ad_calc_profiles(wave image, variable pa, variable qa, variable pb, variable qb)
calculate profiles, statistics, and histogram of a rectangular region of interest.
-
variable ad_profiles_set_cursor(wave image, string cursorname, variable xa, variable ya, variable pscale=defaultValue)
move a cursor to the specified position in a profiles graph.
-
static wave get_view_image(wave source)
find the view image wave corresponding to the given source.
-
instant visualization of angle scan and manipulator position.
-
static variable bp_extract_slice(WMButtonAction *ba)
export a slice (button procedure).
-
static variable pmp_export(WMPopupAction *pa)
-
static wave get_source_image(wave view)
find the source image wave corresponding to the given view.
-
string ad_display_histogram(wave image)
display the histogram of a 2D image.
-
threadsafe wave ad_extract_slab_y(wave dataset, variable q1, variable q2, string destname, variable noavg=defaultValue)
-
string ad_display(wave image)
open a new graph window with a 2D image.
-
static string graphname_from_dfref(dfref df, string prefix)
compose a valid and unique graph name from a data folder reference
-
variable ad_calc_cursor_profiles(wave image)
calculate profiles, statistics, and histogram of a cross-hair delimited region of interest...
-
static variable update_slice_info()
update controls with data scale limits.
-
variable ad_slicer_init_bg()
initialize the slice animation background task.
-
string ad_display_profiles(wave image, string filter=defaultValue)
open a new profiles graph window.
-
static variable svp_slice_position(WMSetVariableAction *sva)
set slice coordinate (button procedure).
-
static variable bp_reset_cursors(WMButtonAction *ba)
-
variable ad_export_profile(wave view_image, variable dim, variable trace=defaultValue, variable show=defaultValue, variable overwrite=defaultValue)
export a profile from a profiles graph to the source data folder.
-
variable ad_gizmo_set_plane(wave brick, variable dim, variable value)
set the position of a slicing plane of a 3D brick in a Gizmo window.
-
variable ad_transpose_filter(wave image, string options)
transpose image filter.
-
string ad_display_slice(wave data)
display three-dimensional data by 2D slice.
-
static variable bp_move_slice_center(wave brick, variable dim, string posvariable)
move the slice to the center of the dimension (button procedure).
-
static variable bp_move_slice(WMButtonAction *ba)
move slice (button procedure).
-
variable ad_box_filter(wave image, string options)
boxcar smoothing filter.
-
string ad_display_brick(wave data)
open a new "gizmo" window with three-dimensional data.
-
variable ad_profiles_hook(WMWinHookStruct *s)
hook function for user events in the profiles window.
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-area-import_8ipf.html b/doc/html/pearl-area-import_8ipf.html index 2388f29..3249abb 100644 --- a/doc/html/pearl-area-import_8ipf.html +++ b/doc/html/pearl-area-import_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-area-import.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
-
pearl-area-import.ipf File Reference
+
pearl-area-import.ipf File Reference
-

HDF5 file import from EPICS area detectors. -More...

-
#include <HDF5 Browser>
-#include "pearl-gui-tools"
-

Go to the source code of this file.

- - - - - -

-Namespaces

 PearlAreaImport
 HDF5 file import from EPICS area detectors.
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

static variable BeforeFileOpenHook (variable refNum, string fileName, string path, string type, string creator, variable kind)
 callback function for drag&drop of HDF5 files into Igor. More...
 
string ad_suggest_foldername (string filename, variable ignoredate=defaultValue, string sourcename=defaultValue, variable unique=defaultValue)
 generate the name of a data folder based on a file name. More...
 
variable ad_load_dialog (string APathName)
 load area detector data files selected in a file dialog window More...
 
string adh5_load_complete (string ANickName, string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue)
 import everything from a HDF5 file created by the Area Detector software. More...
 
string adh5_load_reduced (string ANickName, string APathName, string AFileName, funcref reduction_func, string reduction_param, variable load_data=defaultValue, variable load_attr=defaultValue, variable progress=defaultValue)
 load and reduce a dataset from a HDF5 file created by the Area Detector software. More...
 
string adh5_load_preview (string ANickName, string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue)
 load a single image from a HDF5 file created by the Area Detector software. More...
 
string adh5_load_info (string APathName, string AFileName)
 load descriptive info from a HDF5 file created by the Area Detector software. More...
 
variable adh5_load_detector (variable fileID, string detectorpath)
 load the detector dataset from the open HDF5 file. More...
 
variable adh5_redim (wave data)
 redimension a multi-dimensional area detector array loaded from HDF5. More...
 
static dfr GetAttrDataFolderDFR (wave data)
 find the attributes data folder of an area detector dataset. More...
 
variable adh5_scale (wave data, string source=defaultValue)
 set the dimension scales of an area detector dataset. More...
 
variable adh5_load_detector_slabs (variable fileID, string detectorpath, variable progress=defaultValue)
 load the detector dataset from the open HDF5 file. More...
 
variable adh5_load_detector_image (variable fileID, string detectorpath, variable dim2start, variable dim2count, variable dim3start, variable dim3count)
 load a single image from the detector dataset of the open HDF5 file More...
 
string adh5_list_reduction_funcs ()
 get a list of functions which can be used as reduction functions. More...
 
threadsafe wave adh5_default_reduction (wave source, string *param)
 function prototype for adh5_load_reduced_detector More...
 
threadsafe variable adh5_setup_profile (wave image, wave profile, variable dim)
 set up a one-dimensional wave for a line profile based on a 2D original wave. More...
 
string adh5_test_reduction_func (wave source, funcref reduction_func, string reduction_param, string result_prefix)
 wrapper function for testing reduction functions from the command line. More...
 
threadsafe variable adh5_get_result_waves (wave results, string result_prefix, variable start_index)
 copy waves from wave reference wave into current data folder More...
 
variable adh5_load_reduced_detector (variable fileID, string detectorpath, funcref reduction_func, string reduction_param, variable progress=defaultValue, variable nthreads=defaultValue)
 load a reduced detector dataset from the open HDF5 file. More...
 
static threadsafe variable reduce_slab_worker (funcref reduction_func)
 
static threadsafe wave reduce_slab_image (wave slabdata, wave image, funcref reduction_func, string reduction_param)
 
variable adh5_loadattr_all (variable fileID, string attributespath)
 load an NDAttributes group from an open HDF5 file into the current data folder. More...
 
static variable read_attribute_info (string datawavename, string source, variable *idest)
 sub-function of adh5_loadattr_all. More...
 
variable adh5_scale_scienta (wave data)
 set the energy and angle scales of an area detector dataset from the Scienta analyser. More...
 
variable adh5_scale_scan (wave data)
 scales the extra dimensions of an area detector dataset according to the EPICS scan More...
 
-

Detailed Description

-

HDF5 file import from EPICS area detectors.

-

HDF5 file import from EPICS area detectors such as CCD cameras, 2D electron analysers

-

as of Igor 6.3, Igor can open datasets of up to rank 4. i.e. the extra dimension Y of the file plugin cannot be used. the extra dimensions N and X are supported.

-
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
- - -

Definition in file pearl-area-import.ipf.

-

Function Documentation

- -
-
- - - - - - - - -
variable ad_load_dialog (string APathName)
-
- -

load area detector data files selected in a file dialog window

-
Parameters
- - -
APathNameIgor symbolic path name. if empty, Igor will choose a folder on its own
-
-
- -

Definition at line 166 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string ad_suggest_foldername (string filename,
variable ignoredate = defaultValue,
string sourcename = defaultValue,
variable unique = defaultValue 
)
-
- -

generate the name of a data folder based on a file name.

-

if the file name follows the naming convention source-date-index.extension, the function tries to generate the nick name as source_date_index. otherwise it's just a cleaned up version of the file name.

-

date must be in yyyymmdd or yymmdd format and is clipped to the short yymmdd format. index should be a running numeric index of up to 6 digits, or the time encoded as hhmmss. however, in the current version index can be any string that can be a valid Igor folder name.

-
Parameters
- - - - - -
filenamefile name, including extension. can also include a folder path (which is ignored). the extension is currently ignored, but may be used to select the parent folder in a later version.
ignoredateif non-zero, the nick name will not include the date part. defaults to zero.
sourcenamenick name of the data source. by default, the function tries to detect the source from the file name. this option can be used to override auto-detection. the automatic source names are: sci (scienta by area detector), psh (pshell), sl (optics slit camera by area detector), es (end station camera by area detector), xy (unidentified).
uniqueif non-zero, the resulting name is made a unique data folder name in the current data folder defaults to zero.
-
-
- -

Definition at line 105 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
threadsafe wave adh5_default_reduction (wave source,
string * param 
)
-
- -

function prototype for adh5_load_reduced_detector

-

this is a prototype of custom functions that convert (reduce) a two-dimensional detector image into one or more one-dimensional waves. data processing can be tuned with a set of parameters.

-

reduction functions have a fixed signature (function arguments) so that the file import functions can call them efficiently on a series of detector images. pearl procedures comes with a number of pre-defined reduction functions but you may as well implement your own functions. if you write your own function, you must use the same declaration and arguments as this function except for the function name. you can do many things in a reduction function, e.g. integration over a region of interest, curve fitting, etc.

-

each destination wave is a one-dimensional intensity distribution. the function must redimension each of these waves to one of the image dimensions by calling the adh5_setup_profile() function. this function will also copy the scale information and dimension labels, which is important for the proper scaling of the result.

-

the meaning of the data in the result waves is up to the particular function, e.g. dest1 could hold the mean value and dest2 the one-sigma error, or dest1 could hold the X-profile, and dest2 the Y-profile.

-
Parameters
- - - -
sourcesource wave. two-dimensional intensity distribution (image). the scales are carried over to the result waves.
paramstring with optional parameters, shared between calls. this is a pass-by-reference argument, the function may modify the string.
-
-
-
Returns
a free wave containing references of the result waves. the result waves should as well be free waves. if an error occurred, the reference wave is empty.
- -

Definition at line 1110 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe variable adh5_get_result_waves (wave results,
string result_prefix,
variable start_index 
)
-
- -

copy waves from wave reference wave into current data folder

-

this function copies waves that are referenced in a wave reference wave into the current data folder. the destination waves get new names consisting of a prefix and a numeric index. the index is the array index of the wave in results plus a chosen offset.

-
Parameters
- - - - -
resultsa wave reference wave pointing to result waves from data reduction. the waves can be free or regular waves. results can be a free or regular wave.
result_prefixname prefix of the copied waves.
start_indexstart index (offset) of the copied waves.
-
-
- -

Definition at line 1192 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - -
string adh5_list_reduction_funcs ()
-
- -

get a list of functions which can be used as reduction functions.

-

the function evaluates only the function arguments, it may thus include functions which are not suitable as reduction functions.

- -

Definition at line 1040 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string adh5_load_complete (string ANickName,
string APathName,
string AFileName,
variable load_data = defaultValue,
variable load_attr = defaultValue 
)
-
- -

import everything from a HDF5 file created by the Area Detector software.

-

if the data is from the electron analyser driver and some special attributes are included, the function will set the scales of the image dimensions.

-
Parameters
- - - - - - -
ANickNamedestination folder name (top level under root)
APathNameigor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
AFileNameif empty a dialog box shows up
load_data1 (default): load data; 0: do not load data
load_attr1 (default): load attributes; 0: do not load attributes for proper wave scaling, the attributes must be loaded
-
-
- -

Definition at line 206 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable adh5_load_detector (variable fileID,
string detectorpath 
)
-
- -

load the detector dataset from the open HDF5 file.

-

the function loads the whole dataset at once and redimensions it so that the image dimensions are X and Y

-
Parameters
- - - -
fileIDID of open HDF5 file from HDF5OpenFile
detectorpathpath to detector group in the HDF5 file
-
-
- -

Definition at line 580 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable adh5_load_detector_image (variable fileID,
string detectorpath,
variable dim2start,
variable dim2count,
variable dim3start,
variable dim3count 
)
-
- -

load a single image from the detector dataset of the open HDF5 file

-

the function can average over a region in the extra dimensions.

-
Parameters
- - - - - - - -
fileIDID of open HDF5 file from HDF5OpenFile
detectorpathpath to detector group in the HDF5 file
dim2start2nd dimension coordinate of the first image note that the order of dimensions is reversed in the file 2nd dimension = N dimension in area detector = dimension 0 of the three-dimensional HDF dataset set to 0 if dimension may not be present
dim2countnumber of subsequent images to average set to 1 if dimension may not be present
dim3start3rd dimension coordinate of the first image note that the order of dimensions is reversed in the file 3rd dimension = extra X dimension in area detector = dimension 0 of the four-dimensional HDF dataset set to 0 if dimension may not be present
dim3countnumber of subsequent images to average set to 1 if dimension may not be present
-
-
- -

Definition at line 944 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable adh5_load_detector_slabs (variable fileID,
string detectorpath,
variable progress = defaultValue 
)
-
- -

load the detector dataset from the open HDF5 file.

-

the function loads the dataset image by image using the hyperslab option. this function gives the same result as adh5_load_detector. it is about 5% slower, and it depends on HDF5 Browser code. but it does not choke on large datasets (as long as the final wave fits into memory).

-
Parameters
- - - - -
fileIDID of open HDF5 file from HDF5OpenFile.
detectorpathpath to detector group in the HDF5 file.
progress1 (default): show progress window; 0: do not show progress window.
-
-
-
Returns
0 if successful, non-zero if an error occurred.
- -

Definition at line 779 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
string adh5_load_info (string APathName,
string AFileName 
)
-
- -

load descriptive info from a HDF5 file created by the Area Detector software.

-

the information returned is the array size and active scans

-
Attention
EXPERIMENTAL this function should be merged with adh5_load_preview
-
Parameters
- - - -
APathNameigor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
AFileNameif empty a dialog box shows up
-
-
- -

Definition at line 496 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string adh5_load_preview (string ANickName,
string APathName,
string AFileName,
variable load_data = defaultValue,
variable load_attr = defaultValue 
)
-
- -

load a single image from a HDF5 file created by the Area Detector software.

-

the data wave is loaded into the current data folder. attributes are loaded into the attr subfolder. existing waves in attr are deleted.

-
Warning
EXPERIMENTAL this function uses the root:pearl_area:preview data folder. existing data there may be deleted!
-
Parameters
- - - - - - -
ANickNamedestination wave name. the wave is created in the current data folder.
APathNameigor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
AFileNameif empty a dialog box shows up
load_data1 (default): load data; 0: do not load data
load_attr1 (default): load attributes; 0: do not load attributes note: for correct scaling of the image, the attributes need to be loaded
-
-
- -

Definition at line 386 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string adh5_load_reduced (string ANickName,
string APathName,
string AFileName,
funcref reduction_func,
string reduction_param,
variable load_data = defaultValue,
variable load_attr = defaultValue,
variable progress = defaultValue 
)
-
- -

load and reduce a dataset from a HDF5 file created by the Area Detector software.

-

the resulting dataset is reduced in one image dimension by a user-defined reduction function, e.g. by region-of-interest integration, curve fitting, etc.

-

the function loads the dataset image by image using the hyperslab option and applies a custom reduction function to each image. the results from the reduction function are composed into one result wave. the raw data are discarded.

-

if the data is from the electron analyser driver and some special attributes are included, the function will set the scales of the image dimensions.

-
Parameters
- - - - - - - - - -
ANickNamedestination folder name (top level under root)
APathNameigor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
AFileNameif empty a dialog box shows up
reduction_funccustom reduction function (any user-defined function which has the same parameters as adh5_default_reduction())
reduction_paramparameter string for the reduction function
load_data1 (default): load data; 0: do not load data
load_attr1 (default): load attributes; 0: do not load attributes for proper wave scaling, the attributes must be loaded
progress1 (default): show progress window; 0: do not show progress window
-
-
- -

Definition at line 301 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable adh5_load_reduced_detector (variable fileID,
string detectorpath,
funcref reduction_func,
string reduction_param,
variable progress = defaultValue,
variable nthreads = defaultValue 
)
-
- -

load a reduced detector dataset from the open HDF5 file.

-

the function loads the dataset image by image using the hyperslab option and applies a custom reduction function to each image. the results from the reduction function are composed into one result wave. the raw data are discarded.

-

by default, the reduction function is called in separate threads to reduce the total loading time. (see the global variable adh5_perf_secs which reports the total run time of the function.) the effect varies depending on the balance between file loading (image size) and data processing (complexity of the reduction function). for debugging the reduction function, multi-threading can be disabled.

-
Parameters
- - - - - - - -
fileIDID of open HDF5 file from HDF5OpenFile
detectorpathpath to detector group in the HDF5 file
reduction_funccustom reduction function (any user-defined function which has the same parameters as adh5_default_reduction())
reduction_paramparameter string for the reduction function
progress1 (default): show progress window; 0: do not show progress window
nthreads-1 (default): use as many threads as there are processor cores (in addition to main thread) 0: use main thread only (e.g. for debugging the reduction function) >= 1: use a fixed number of (additional) threads
-
-
- -

Definition at line 1228 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable adh5_loadattr_all (variable fileID,
string attributespath 
)
-
- -

load an NDAttributes group from an open HDF5 file into the current data folder.

-

datasets contained in the group are loaded as waves. if a dataset contains only one data point, it is added to the IN, ID, IV, IU waves, where IN = EPICS channel name, ID = attribute name, IV = value, IU = unit (units are left empty as they are not saved in HDF5). attributes of the NDAttributes group are added to the IN, ID, IV, IU waves, however, IN and IU are left empty as this information is not saved in the HDF5 file.

-
Parameters
- - - -
fileIDID of open HDF5 file from HDF5OpenFile
attributespathpath to NDAttributes group in the HDF5 file
-
-
- -

Definition at line 1552 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - -
variable adh5_redim (wave data)
-
- -

redimension a multi-dimensional area detector array loaded from HDF5.

-

so that the image dimensions are X and Y singleton dimensions are removed (most common cases only)

-

in the redimensioned array, the original dimension type is noted in the dimension label: AD_Dim0 = first image dimension AD_Dim1 = second image dimension AD_DimN = frame sequence AD_DimX = extra dimension X AD_DimY = extra dimension Y (cannot be loaded in Igor)

-
Parameters
- - -
dataarea detector data loaded from HDF5 to be redimensioned
-
-
- -

Definition at line 625 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable adh5_scale (wave data,
string source = defaultValue 
)
-
- -

set the dimension scales of an area detector dataset.

-

the intrinsic dimensions 0 and 1 are scaled according to the data source (currently supported: Prosilica cameras, Scienta electron analyser). the extra dimensions are scaled according to the scan. the latter requires that the positioner names and position values are available.

- -

Definition at line 725 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - -
variable adh5_scale_scan (wave data)
-
- -

scales the extra dimensions of an area detector dataset according to the EPICS scan

-

the scan positioner name and its values must be available

-
Todo:
incomplete
- -

Definition at line 1792 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - -
variable adh5_scale_scienta (wave data)
-
- -

set the energy and angle scales of an area detector dataset from the Scienta analyser.

-

the dimension labels of the energy and angle scales must be set correctly: AD_Dim0 = energy dimension; AD_Dim1 = angle dimension. these dimensions must be the first two dimensions of a multi-dimensional dataset. normally, AD_Dim0 is the X dimension, and AD_Dim1 the Y dimension.

- -

Definition at line 1687 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe variable adh5_setup_profile (wave image,
wave profile,
variable dim 
)
-
- -

set up a one-dimensional wave for a line profile based on a 2D original wave.

-

redimensions the profile wave to the given dimension. copies the scale and dimension label of the given dimension.

- -

Definition at line 1133 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string adh5_test_reduction_func (wave source,
funcref reduction_func,
string reduction_param,
string result_prefix 
)
-
- -

wrapper function for testing reduction functions from the command line.

-

reduction functions cannot be used on the command line because they require a pass-by-reference argument and return free waves. this function expects the reduction parameters in a normal string and copies the results into the current data folder. the prefix of the result names can be specified.

-
Parameters
- - - - - -
sourcesource wave. two-dimensional intensity distribution (image). the scales are carried over to the result waves.
reduction_funcname of the reduction function to apply to the source data.
reduction_paramstring with reduction parameters as required by the specific reduction function.
result_prefixname prefix of result waves. a numeric index is appended to distinguish the results. the index starts at 1. existing waves are overwritten.
-
-
-
Returns
a copy of the reduction_param string, possibly modified by the reduction function.
- -

Definition at line 1166 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable BeforeFileOpenHook (variable refNum,
string fileName,
string path,
string type,
string creator,
variable kind 
)
-
-static
-
- -

callback function for drag&drop of HDF5 files into Igor.

- -

Definition at line 41 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static dfr GetAttrDataFolderDFR (wave data)
-
-static
-
- -

find the attributes data folder of an area detector dataset.

-

since version 1.04 attributes should be stored in a subfolder named attr. earlier versions had the attributes in the same data folder as the actual dataset.

-
Parameters
- - -
datawave containing the main dataset.
-
-
-
Returns
data folder reference of the attributes folder. the reference may be invalid (and default to root) if the folder cannot be found, cf. built-in DataFolderRefStatus function.
- -

Definition at line 706 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - -
static variable read_attribute_info (string datawavename,
string source,
variable * idest 
)
-
-static
-
- -

sub-function of adh5_loadattr_all.

-

reads one attribute from a wave which was loaded from an HDF5 file into the info waves IN, ID, IV, IU. the attribute is read only if the input wave contains exactly one item, i.e. either the measurement is a single image, or the attribute has string type.

-
Parameters
- - - - -
datawavenamename of the attribute wave in the current folder. can be text or numeric.
sourcesource identifier (EPICS name) of the attribute.
idestdestination index in IN, ID, IV, IU where the results are written. the variable is incremented if data was written, otherwise it is left unchanged. make sure IN, ID, IV, IU have at least idest + 1 elements.
-
-
- -

Definition at line 1634 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static threadsafe wave reduce_slab_image (wave slabdata,
wave image,
funcref reduction_func,
string reduction_param 
)
-
-static
-
- -

Definition at line 1519 of file pearl-area-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static threadsafe variable reduce_slab_worker (funcref reduction_func)
-
-static
-
- -

Definition at line 1480 of file pearl-area-import.ipf.

- -
-
diff --git a/doc/html/pearl-area-import_8ipf_source.html b/doc/html/pearl-area-import_8ipf_source.html index 03a82ee..b0eb9d9 100644 --- a/doc/html/pearl-area-import_8ipf_source.html +++ b/doc/html/pearl-area-import_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-area-import.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma IgorVersion = 6.2
3 #pragma ModuleName = PearlAreaImport
4 #include <HDF5 Browser>
5 #include "pearl-gui-tools"
6 
7 // copyright (c) 2013-18 Paul Scherrer Institut
8 //
9 // Licensed under the Apache License, Version 2.0 (the "License");
10 // you may not use this file except in compliance with the License.
11 // You may obtain a copy of the License at
12 // http:///www.apache.org/licenses/LICENSE-2.0
13 
33 
38 
41 static variable BeforeFileOpenHook(variable refNum, string fileName, string path, string type, string creator, variable kind){
42  variable refNum, kind
43  string fileName, path, type, creator
44 
45  variable handledOpen = 0
46 
47  //PathInfo $path
48  //string FilePath = s_path + filename
49  string NickName = CleanupName(ParseFilePath(3, FileName, ":", 0, 0), 0)
50  string FileExt = LowerStr(ParseFilePath(4, FileName, ":", 0, 0))
51  string result = ""
52 
53  // override nickname with custom setting
54  svar /z cnn = gsCustomNickName
55  if (svar_exists(cnn))
56  if (exists("gvNickNameIndex") != 2)
57  variable/g gvNickNameIndex = 1
58  endif
59  nvar nni = gvNickNameIndex
60  NickName = cnn + num2str(nni)
61  nni += 1
62  endif
63 
64  if (stringmatch(FileExt, "h5") == 1)
65  result = adh5_load_complete(NickName, path, FileName)
66  endif
67 
68  string/g s_latest_datafile = result
69  string/g s_latest_nickname = nickname
70 
71  handledOpen = strlen(result) > 0
72  if (handledOpen)
73  close refnum
74  endif
75 
76  return handledOpen// 1 tells Igor not to open the file
77 };
78 
105 string ad_suggest_foldername(string filename, variable ignoredate = defaultValue, string sourcename = defaultValue, variable unique = defaultValue){
106  string filename
107  variable ignoredate
108  string sourcename
109  variable unique
110 
111  if (ParamIsDefault(ignoredate))
112  ignoredate = 0
113  endif
114  if (ParamIsDefault(unique))
115  unique = 0
116  endif
117 
118  string basename = ParseFilePath(3, filename, ":", 0, 0)
119  string extension = ParseFilePath(4, filename, ":", 0, 0)
120  string nickname
121 
122  string autosource
123  if (strsearch(basename, "scienta", 0, 2) >= 0)
124  autosource = "sci"
125  else if (strsearch(basename, "pshell", 0, 2) >= 0)
126  autosource = "psh"
127  else if (strsearch(basename, "OP-SL", 0, 2) >= 0)
128  autosource = "sl"
129  else if (strsearch(basename, "ES-PS", 0, 2) >= 0)
130  autosource = "es"
131  else
132  autosource = "xy"
133  endif
134  if (ParamIsDefault(sourcename))
135  sourcename = autosource
136  endif
137 
138  variable nparts = ItemsInList(basename, "-")
139  if (nparts >= 3)
140  string datepart = StringFromList(1, basename, "-")
141  variable l_datepart = strlen(datepart)
142  if (l_datepart == 8)
143  datepart = datepart[l_datepart-6, l_datepart-1]
144  endif
145  string indexpart = StringFromList(2, basename, "-")
146  if (ignoredate)
147  sprintf nickname, "%s_%s", sourcename, indexpart
148  else
149  sprintf nickname, "%s_%s_%s", sourcename, datepart, indexpart
150  endif
151  else
152  nickname = CleanupName(basename, 0)
153  endif
154 
155  if (unique && CheckName(nickname, 11))
156  nickname = UniqueName(nickname + "_", 11, 0)
157  endif
158 
159  return nickname
160 };
161 
166 variable ad_load_dialog(string APathName){
167  string APathName
168 
169  variable refNum
170  string message = "Select data files"
171  string filepaths
172  string filefilters = "Area Detector HDF5 Files (*.h5):.h5;"
173  filefilters += "All Files:.*;"
174 
175  PathInfo /S $APathName
176  Open /D /R /F=filefilters /M=message /MULT=1 refNum
177  filepaths = S_fileName
178 
179  dfref saveDF = GetDataFolderDFR()
180  setdatafolder root:
181 
182  if (strlen(filepaths) > 0)
183  variable nfiles = ItemsInList(filepaths, "\r")
184  variable ifile
185  for(ifile = 0; ifile < nfiles; ifile += 1)
186  String path = StringFromList(ifile, filepaths, "\r")
187  string nickname = ad_suggest_foldername(path)
188  adh5_load_complete(nickname, "", path)
189  endfor
190  endif
191 
192  setdatafolder saveDF
193 };
194 
206 string adh5_load_complete(string ANickName, string APathName, string AFileName, variable load_data = defaultValue, variable load_attr = defaultValue){
207  string ANickName
208  string APathName
209  string AFileName
210  variable load_data
211  variable load_attr
212 
213  if (ParamIsDefault(load_data))
214  load_data = 1
215  endif
216  if (ParamIsDefault(load_attr))
217  load_attr = 1
218  endif
219 
220  dfref saveDF = GetDataFolderDFR()
221  setdatafolder root:
222  newdatafolder /s/o $("root:" + ANickName)
223 
224  // open file
225  variable fileID
226  string instrumentpath = "/entry/instrument/"
227  string detectorpath = instrumentpath + "detector/"
228  string attributespath = instrumentpath + "NDAttributes/"
229  string datasetname
230  string datawavename
231 
232  // performance monitoring
233  variable timerRefNum
234  variable /g adh5_perf_secs
235  timerRefNum = startMSTimer
236 
237  // avoid compilation error if HDF5 XOP has not been loaded
238  #if Exists("HDF5OpenFile")
239  HDF5OpenFile /P=$APathName/R fileID as AFileName
240  if (v_flag == 0)
241  AFileName = s_path + s_filename
242  print "loading " + s_filename + "\r"
243 
244  if (load_data)
245  adh5_load_detector_slabs(fileID, detectorpath)
246  endif
247  if (load_attr)
248  newdatafolder /o/s attr
249  adh5_loadattr_all(fileID, attributespath)
250  setdatafolder ::
251  endif
252 
253  wave /z data
254  if (waveexists(data))
255  //adh5_redim(data) // not to be used with adh5_load_detector_slabs
256  adh5_scale(data)
257  endif
258 
259  HDF5CloseFile fileID
260  else
261  AFileName = ""
262  endif
263  #else
264  Abort "HDF5 XOP not loaded."
265  #endif
266 
267  if (timerRefNum >= 0)
268  adh5_perf_secs = stopMSTimer(timerRefNum) / 1e6
269  endif
270 
271  setdatafolder saveDF
272  return AFileName
273 };
274 
301 string adh5_load_reduced(string ANickName, string APathName, string AFileName, funcref reduction_func, string reduction_param, variable load_data = defaultValue, variable load_attr = defaultValue, variable progress = defaultValue){
302  string ANickName
303  string APathName
304  string AFileName
305 
306  funcref adh5_default_reduction reduction_func
307  string reduction_param
308 
309  variable load_data
310  variable load_attr
311  variable progress
312 
313  if (ParamIsDefault(load_data))
314  load_data = 1
315  endif
316  if (ParamIsDefault(load_attr))
317  load_attr = 1
318  endif
319  if (ParamIsDefault(progress))
320  progress = 1
321  endif
322 
323  dfref saveDF = GetDataFolderDFR()
324  setdatafolder root:
325  newdatafolder /s/o $("root:" + ANickName)
326 
327  // open file
328  variable fileID
329  string instrumentpath = "/entry/instrument/"
330  string detectorpath = instrumentpath + "detector/"
331  string attributespath = instrumentpath + "NDAttributes/"
332  string datasetname
333  string datawavename
334 
335  // performance monitoring
336  variable timerRefNum
337  variable /g adh5_perf_secs
338  timerRefNum = startMSTimer
339 
340  // avoid compilation error if HDF5 XOP has not been loaded
341  #if Exists("HDF5OpenFile")
342  HDF5OpenFile /P=$APathName/R fileID as AFileName
343  if (v_flag == 0)
344  AFileName = s_path + s_filename
345  print "loading " + s_filename + "\r"
346 
347  if (load_attr)
348  newdatafolder /o/s attr
349  adh5_loadattr_all(fileID, attributespath)
350  setdatafolder ::
351  endif
352  if (load_data)
353  adh5_load_reduced_detector(fileID, detectorpath, reduction_func, reduction_param, progress=progress)
354  endif
355 
356  HDF5CloseFile fileID
357  else
358  AFileName = ""
359  endif
360  #else
361  Abort "HDF5 XOP not loaded."
362  #endif
363 
364  if (timerRefNum >= 0)
365  adh5_perf_secs = stopMSTimer(timerRefNum) / 1e6
366  endif
367 
368  setdatafolder saveDF
369  return AFileName
370 };
371 
386 string adh5_load_preview(string ANickName, string APathName, string AFileName, variable load_data = defaultValue, variable load_attr = defaultValue){
387  string ANickName
388  string APathName
389  string AFileName
390  variable load_data
391  variable load_attr
392 
393  if (ParamIsDefault(load_data))
394  load_data = 1
395  endif
396  if (ParamIsDefault(load_attr))
397  load_attr = 1
398  endif
399 
400  dfref saveDF = GetDataFolderDFR()
401  setdatafolder root:
402  newdatafolder /o/s pearl_area
403  newdatafolder /o/s preview
404 
405  // open file
406  variable fileID
407  string instrumentpath = "/entry/instrument/"
408  string detectorpath = instrumentpath + "detector/"
409  string attributespath = instrumentpath + "NDAttributes/"
410  string datasetname
411  string datawavename
412 
413  // performance monitoring
414  variable timerRefNum
415  variable /g adh5_perf_secs
416  timerRefNum = startMSTimer
417 
418  // avoid compilation error if HDF5 XOP has not been loaded
419  #if Exists("HDF5OpenFile")
420  HDF5OpenFile /P=$APathName/R/Z fileID as AFileName
421  if (v_flag == 0)
422  AFileName = s_path + s_filename
423 
424  // detector data
425  datasetname = detectorpath + "data"
426  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
427  InitHDF5DataInfo(di)
428  variable err = HDF5DatasetInfo(fileID, datasetname, 0, di)
429  if (err != 0)
430  print "error accessing detector/data"
431  return ""
432  endif
433  if (di.ndims < 2)
434  print "error: rank of dataset < 2"
435  return ""
436  endif
437 
438  variable dim2start = 0, dim2count = 1, dim3start = 0, dim3count = 1
439  if (di.ndims >= 3)
440  dim2start = floor(di.dims[di.ndims - 3] / 2)
441  dim2count = 1
442  endif
443  if (di.ndims >= 4)
444  dim3start = floor(di.dims[di.ndims - 4] / 2)
445  dim3count = 1
446  endif
447 
448  if (load_data)
449  adh5_load_detector_image(fileID, detectorpath, dim2start, dim2count, dim3start, dim3count)
450  wave /z data
451  string destpath = GetDataFolder(1, saveDF) + ANickName
452  if (waveexists(data))
453  duplicate /o data, $destpath
454  wave /z data = $destpath
455  endif
456  endif
457 
458  if (load_attr)
459  setdatafolder saveDF
460  newdatafolder /o/s attr
461  killwaves /a/z
462  adh5_loadattr_all(fileID, attributespath)
463  setdatafolder ::
464  if (waveexists(data))
465  adh5_scale(data)
466  endif
467  endif
468 
469  HDF5CloseFile fileID
470  else
471  print "error opening file " + AFileName
472  AFileName = ""
473  endif
474  #else
475  Abort "HDF5 XOP not loaded."
476  #endif
477 
478  if (timerRefNum >= 0)
479  adh5_perf_secs = stopMSTimer(timerRefNum) / 1e6
480  endif
481 
482  setdatafolder saveDF
483  return AFileName
484 };
485 
496 string adh5_load_info(string APathName, string AFileName){
497  string APathName
498  string AFileName
499 
500  dfref saveDF = GetDataFolderDFR()
501 
502  // open file
503  variable fileID
504  string instrumentpath = "/entry/instrument/"
505  string detectorpath = instrumentpath + "detector/"
506  string attributespath = instrumentpath + "NDAttributes/"
507  string datasetname
508  string datawavename
509 
510  string s_info = ""
511  string s
512 
513  variable idim
514 
515  // avoid compilation error if HDF5 XOP has not been loaded
516  #if Exists("HDF5OpenFile")
517  HDF5OpenFile /P=$APathName/R/Z fileID as AFileName
518  if (v_flag == 0)
519  AFileName = s_path + s_filename
520 
521  // detector data
522  datasetname = detectorpath + "data"
523  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
524  InitHDF5DataInfo(di)
525  variable err = HDF5DatasetInfo(fileID, datasetname, 0, di)
526  if (err != 0)
527  print "error accessing detector/data"
528  return ""
529  endif
530 
531  for (idim = 0; idim < di.ndims; idim += 1)
532  sprintf s, "dim %u: %u points", idim, di.dims[idim]
533  if (strlen(s_info) > 0)
534  s_info = s_info + "\r" + s
535  else
536  s_info = s
537  endif
538  endfor
539 
540  dfref df = NewFreeDataFolder()
541  setdatafolder df
542  adh5_loadattr_all(fileID, attributespath)
543 
544  for (idim = 1; idim < 5; idim += 1)
545  sprintf s, "Scan%uActive", idim
546  wave /z w = $s
547  if (waveexists(w) && (numpnts(w) > 0) && (w[0] > 0))
548  sprintf s, "Scan%uPositioner1", idim
549  wave /t wt = $s
550  sprintf s, "scan %u: %s", idim, wt[0]
551  if (strlen(s_info) > 0)
552  s_info = s_info + "\r" + s
553  else
554  s_info = s
555  endif
556  endif
557  endfor
558 
559  HDF5CloseFile fileID
560  else
561  print "error opening file " + AFileName
562  AFileName = ""
563  endif
564  #else
565  Abort "HDF5 XOP not loaded."
566  #endif
567 
568  setdatafolder saveDF
569  return s_info
570 };
571 
580 variable adh5_load_detector(variable fileID, string detectorpath){
581  variable fileID
582  string detectorpath
583 
584  // avoid compilation error if HDF5 XOP has not been loaded
585  #if Exists("HDF5LoadData")
586  string datasetname
587  string datawavename
588 
589  // detector data
590  datasetname = detectorpath + "data"
591  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
592  InitHDF5DataInfo(di)
593  variable err = HDF5DatasetInfo(fileID, datasetname, 0, di)
594  if (err != 0)
595  print "error accessing detector/data"
596  return -1
597  endif
598  if (di.ndims < 2)
599  print "error: rank of dataset < 2"
600  return -2
601  endif
602 
603  HDF5LoadData /O /Q /Z fileID, datasetname
604  wave data
605 
606  #else
607  Abort "HDF5 XOP not loaded."
608  #endif
609 };
610 
625 variable adh5_redim(wave data){
626  wave data
627 
628  duplicate /free data, tempdata
629  variable nd = wavedims(tempdata)
630  variable nx = dimsize(tempdata, nd - 1)
631  variable ny = dimsize(tempdata, nd - 2)
632  variable nz = dimsize(tempdata, nd - 3)
633  variable nt = dimsize(tempdata, nd - 4)
634 
635  switch (nd)
636  case 2:
637  if (nx <= 1)
638  redimension /n=(ny) data
639  setdimlabel 0, -1, AD_Dim1, data
640  data = tempdata[p][0]
641  else if (ny <= 1)
642  redimension /n=(nx) data
643  setdimlabel 0, -1, AD_Dim0, data
644  data = tempdata[0][p]
645  else
646  redimension /n=(nx,ny) data
647  setdimlabel 0, -1, AD_Dim0, data
648  setdimlabel 1, -1, AD_Dim1, data
649  data = tempdata[q][p]
650  endif
651  break
652  case 3:
653  if (nx <= 1)
654  redimension /n=(ny,nz) data
655  setdimlabel 0, -1, AD_Dim1, data
656  setdimlabel 1, -1, AD_DimN, data
657  multithread data = tempdata[q][p][0]
658  else if (ny <= 1)
659  redimension /n=(nx,nz) data
660  setdimlabel 0, -1, AD_Dim0, data
661  setdimlabel 1, -1, AD_DimN, data
662  multithread data = tempdata[q][0][p]
663  else if (nz <= 1)
664  redimension /n=(nx,ny) data
665  setdimlabel 0, -1, AD_Dim0, data
666  setdimlabel 1, -1, AD_Dim1, data
667  multithread data = tempdata[0][q][p]
668  else
669  redimension /n=(nx,ny,nz) data
670  setdimlabel 0, -1, AD_Dim0, data
671  setdimlabel 1, -1, AD_Dim1, data
672  setdimlabel 2, -1, AD_DimN, data
673  multithread data = tempdata[r][q][p]
674  endif
675  break
676  case 4:
677  if (nz <= 1)
678  // singleton "frame number" dimension
679  redimension /n=(nx,ny,nt) data
680  setdimlabel 0, -1, AD_Dim0, data
681  setdimlabel 1, -1, AD_Dim1, data
682  setdimlabel 2, -1, AD_DimX, data
683  multithread data = tempdata[r][0][q][p]
684  else
685  redimension /n=(nx,ny,nz,nt) data
686  setdimlabel 0, -1, AD_Dim0, data
687  setdimlabel 1, -1, AD_Dim1, data
688  setdimlabel 2, -1, AD_DimN, data
689  setdimlabel 3, -1, AD_DimX, data
690  multithread data = tempdata[s][r][q][p]
691  endif
692  break
693  endswitch
694 };
695 
706 static dfr GetAttrDataFolderDFR(wave data){
707  wave data
708 
709  dfref dataDF = GetWavesDataFolderDFR(data)
710  dfref attrDF = dataDF:attr
711  if (DataFolderRefStatus(attrDF) == 0)
712  attrDF = dataDF
713  endif
714 
715  return attrDF
716 };
717 
725 variable adh5_scale(wave data, string source = defaultValue){
726  wave data
727  string source
728 
729  dfref saveDF = GetDataFolderDFR()
730  dfref dataDF = GetWavesDataFolderDFR(data)
731  dfref attrDF = GetAttrDataFolderDFR(data)
732 
733  if (ParamIsDefault(source))
734  // is the source a Scienta analyser?
735  wave /SDFR=attrDF /Z AcquisitionMode
736  wave /SDFR=attrDF /T /Z Manufacturer
737  source = "unknown"
738  if (waveexists(Manufacturer) && (numpnts(Manufacturer) >= 1))
739  strswitch(Manufacturer[0])
740  case "VG Scienta":
741  source = "scienta"
742  break
743  case "Prosilica":
744  source = "prosilica"
745  break
746  endswitch
747  else if (waveexists(AcquisitionMode) && (numpnts(AcquisitionMode) >= 1))
748  if (stringmatch(note(AcquisitionMode), "*SCIENTA*"))
749  source = "scienta"
750  endif
751  endif
752  endif
753 
754  strswitch(source)
755  case "prosilica":
756  // pixel scale - nothing to do
757  break
758  case "scienta":
759  adh5_scale_scienta(data)
760  break
761  endswitch
762 
763  setdatafolder saveDF
764 };
765 
779 variable adh5_load_detector_slabs(variable fileID, string detectorpath, variable progress = defaultValue){
780  variable fileID
781  string detectorpath
782  variable progress
783 
784  if (ParamIsDefault(progress))
785  progress = 1
786  endif
787  variable result = 0
788 
789  // avoid compilation error if HDF5 XOP has not been loaded
790  #if Exists("HDF5LoadData")
791  string datasetname
792  string datawavename
793 
794  // detector data
795  datasetname = detectorpath + "data"
796  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
797  InitHDF5DataInfo(di)
798  variable err = HDF5DatasetInfo(fileID, datasetname, 0, di)
799  if (err != 0)
800  print "error accessing detector/data"
801  return -1
802  endif
803  if (di.ndims < 2)
804  print "error: rank of dataset < 2"
805  return -2
806  endif
807 
808  // nx and nz are the image dimensions
809  variable idx, idy, idz, idt, izt
810  idx = di.ndims - 1
811  idy = di.ndims - 2
812  idz = -1
813  idt = -1
814 
815  variable nx, ny, nz, nt, nzt
816  nx = di.dims[idx]
817  ny = di.dims[idy]
818  nz = 1
819  nt = 1
820 
821  make /n=(nx,ny,nz,nt) /o data
822  string dim_labels = "AD_Dim0;AD_Dim1;AD_DimN;AD_DimX;AD_DimY"
823  string dim_label
824  dim_label = StringFromList(0, dim_labels, ";")
825  setdimlabel 0, -1, $dim_label, data
826  dim_labels = RemoveFromList(dim_label, dim_labels, ";")
827  dim_label = StringFromList(0, dim_labels, ";")
828  setdimlabel 1, -1, $dim_label, data
829  dim_labels = RemoveFromList(dim_label, dim_labels, ";")
830 
831  // find additional dimensions, ignore singletons
832  variable id
833  for (id = idy - 1; (id >= 0) && (nz == 1); id -= 1)
834  if (di.dims[id] > 1)
835  idz = id
836  nz = di.dims[id]
837  dim_label = StringFromList(0, dim_labels, ";")
838  setdimlabel 2, -1, $dim_label, data
839  endif
840  dim_labels = RemoveListItem(0, dim_labels, ";")
841  endfor
842  for (id = idz - 1; (id >= 0) && (nt == 1); id -= 1)
843  if (di.dims[id] > 1)
844  idt = id
845  nt = di.dims[id]
846  dim_label = StringFromList(0, dim_labels, ";")
847  setdimlabel 3, -1, $dim_label, data
848  endif
849  dim_labels = RemoveListItem(0, dim_labels, ";")
850  endfor
851  redimension /n=(nx,ny,nz,nt) data
852 
853  // default values if dimensions are not present in dataset
854  if (idz < 0)
855  idz = idx + 1
856  idt = idz + 1
857  else if (idt < 0)
858  idt = idx + 1
859  endif
860 
861  nzt = nz * nt
862  izt = 0
863  if (progress)
864  display_progress_panel("HDF5 Import", "Loading data...", nzt)
865  endif
866 
867  // load data image by image
868  HDF5MakeHyperslabWave(GetDataFolder(1) + "slab", max(di.ndims, 4))
869  wave slab
870  slab[][%Start] = 0
871  slab[][%Stride] = 1
872  slab[][%Count] = 1
873  slab[][%Block] = 1
874  slab[idx][%Block] = nx
875  slab[idy][%Block] = ny
876 
877  variable iz, it
878  for (iz = 0; iz < nz; iz += 1)
879  for (it = 0; it < nt; it += 1)
880  slab[idz][%Start] = iz
881  slab[idt][%Start] = it
882  HDF5LoadData /O /Q /Z /SLAB=slab /N=slabdata fileID, datasetname
883  wave slabdata// 2D, 3D, or 4D with singletons
884  switch (WaveDims(slabdata))
885  case 2:
886  data[][][iz][it] = slabdata[q][p]
887  break
888  case 3:
889  data[][][iz][it] = slabdata[0][q][p]
890  break
891  case 4:
892  data[][][iz][it] = slabdata[0][0][q][p]
893  break
894  endswitch
895  // progress window
896  izt += 1
897  if (progress)
898  if (update_progress_panel(izt))
899  result = -4// user abort
900  break
901  endif
902  endif
903  endfor
904  if (result < 0)
905  break
906  endif
907  endfor
908 
909  if (nz == 1)
910  redimension /n=(nx,ny) data
911  else if (nt == 1)
912  redimension /n=(nx,ny,nz) data
913  endif
914 
915  if (progress)
917  endif
918  #else
919  Abort "HDF5 XOP not loaded."
920  #endif
921 
922  return result
923 };
924 
944 variable adh5_load_detector_image(variable fileID, string detectorpath, variable dim2start, variable dim2count, variable dim3start, variable dim3count){
945  variable fileID
946  string detectorpath
947  variable dim2start
948  variable dim2count
949  variable dim3start
950  variable dim3count
951 
952  // avoid compilation error if HDF5 XOP has not been loaded
953  #if Exists("HDF5LoadData")
954  string datasetname
955  string datawavename
956 
957  // detector data
958  datasetname = detectorpath + "data"
959  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
960  InitHDF5DataInfo(di)
961  variable err = HDF5DatasetInfo(fileID, datasetname, 0, di)
962  if (err != 0)
963  print "error accessing detector/data"
964  return -1
965  endif
966  if (di.ndims < 1)
967  print "error: rank of dataset < 1"
968  return -2
969  endif
970 
971  // nx and nz are the image dimensions
972  variable idx, idy, idz, idt
973  idx = di.ndims - 1
974  idy = di.ndims >= 2 ? di.ndims - 2 : 1
975  idz = di.ndims >= 3 ? di.ndims - 3 : 2
976  idt = di.ndims >= 4 ? di.ndims - 4 : 3
977 
978  variable nx, ny
979  nx = di.dims[idx]
980  ny = di.ndims >= 2 ? di.dims[idy] : 1
981 
982  variable dim2end = dim2start + dim2count - 1
983  variable dim3end = dim3start + dim3count - 1
984 
985  // the slab wave is at least 4-dimensional
986  // it will also load lower-dimensional datasets
987  HDF5MakeHyperslabWave(GetDataFolder(1) + "slab", max(di.ndims, 4))
988  wave slab
989  slab[][%Start] = 0
990  slab[][%Stride] = 1
991  slab[][%Count] = 1
992  slab[][%Block] = 1
993  slab[idx][%Block] = nx
994  slab[idy][%Block] = ny
995 
996  make /n=(nx,ny)/o/d data
997  data = 0
998  variable iz, it
999  variable navg = 0
1000  for (iz = dim2start; iz <= dim2end; iz += 1)
1001  for (it = dim3start; it <= dim3end; it += 1)
1002  slab[idz][%Start] = iz
1003  slab[idt][%Start] = it
1004  HDF5LoadData /O /Q /Z /SLAB=slab /N=slabdata fileID, datasetname
1005  wave slabdata// 2D, 3D, or 4D with singletons
1006  switch (WaveDims(slabdata))
1007  case 1:
1008  data += slabdata[p]
1009  navg += 1
1010  break
1011  case 2:
1012  data += slabdata[q][p]
1013  navg += 1
1014  break
1015  case 3:
1016  data += slabdata[0][q][p]
1017  navg += 1
1018  break
1019  case 4:
1020  data += slabdata[0][0][q][p]
1021  navg += 1
1022  break
1023  endswitch
1024  endfor
1025  endfor
1026  data /= navg
1027  setdimlabel 0, -1, AD_Dim0, data
1028  setdimlabel 1, -1, AD_Dim1, data
1029 
1030  #else
1031  Abort "HDF5 XOP not loaded."
1032  #endif
1033 };
1034 
1041  string all_funcs = FunctionList("*", ";", "KIND:6,NPARAMS:2,VALTYPE:8")
1042  string result = ""
1043 
1044  variable ii
1045  variable nn = ItemsInList(all_funcs, ";")
1046 
1047  string funcname
1048  string info
1049  variable nparams
1050  variable accept
1051 
1052  for (ii = 0; ii < nn; ii += 1)
1053  funcname = StringFromList(ii, all_funcs, ";")
1054  info = FunctionInfo(funcname)
1055  accept = (NumberByKey("RETURNTYPE", info, ":", ";") == 0x4000)
1056  accept = accept && (cmpstr(StringByKey("THREADSAFE", info, ":", ";"), "yes") == 0)
1057  accept = accept && (NumberByKey("N_PARAMS", info, ":", ";") == 2)
1058  accept = accept && (NumberByKey("N_OPT_PARAMS", info, ":", ";") == 0)
1059  if (accept)
1060  // one numeric wave and one pass-by-reference string
1061  accept = accept && (NumberByKey("PARAM_0_TYPE", info, ":", ";") == 0x4002)
1062  accept = accept && (NumberByKey("PARAM_1_TYPE", info, ":", ";") == 0x3000)
1063  endif
1064  if (accept)
1065  result = AddListItem(funcname, result, ";")
1066  endif
1067  endfor
1068 
1069  result = SortList(result, ";", 4)
1070  return result
1071 };
1072 
1110 threadsafe wave adh5_default_reduction(wave source, string* param){
1111  wave source
1112  string &param
1113 
1114  // demo code
1115  // integrate along the dimensions
1116  make /n=0 /free dest1, dest2
1117  adh5_setup_profile(source, dest1, 0)
1118  ad_profile_x_w(source, 0, -1, dest1)
1119  adh5_setup_profile(source, dest2, 1)
1120  ad_profile_y_w(source, 0, -1, dest2)
1121 
1122  make /n=2 /free /wave results
1123  results[0] = dest1
1124  results[1] = dest2
1125  return results
1126 };
1127 
1133 threadsafe variable adh5_setup_profile(wave image, wave profile, variable dim){
1134  wave image// prototype
1135  wave profile// destination wave
1136  variable dim// which dimension to keep: 0 = X, 1 = Y
1137 
1138  redimension /n=(dimsize(image, dim)) profile
1139  setscale /p x dimoffset(image, dim), dimdelta(image, dim), waveunits(image, dim), profile
1140  setscale d 0, 0, waveunits(image, -1), profile
1141  setdimlabel 0, -1, $getdimlabel(image, dim, -1), profile
1142 };
1143 
1166 string adh5_test_reduction_func(wave source, funcref reduction_func, string reduction_param, string result_prefix){
1167  wave source
1168  funcref adh5_default_reduction reduction_func
1169  string reduction_param
1170  string result_prefix
1171 
1172  wave /wave results = reduction_func(source, reduction_param)
1173  adh5_get_result_waves(results, result_prefix, 1)
1174 
1175  return reduction_param
1176 };
1177 
1192 threadsafe variable adh5_get_result_waves(wave results, string result_prefix, variable start_index){
1193  wave /wave results
1194  string result_prefix
1195  variable start_index
1196 
1197  variable nw = numpnts(results)
1198  variable iw
1199  string sw
1200  for (iw = 0; iw < nw; iw += 1)
1201  sw = result_prefix + num2str(iw + start_index)
1202  duplicate /o results[iw], $sw
1203  endfor
1204 };
1205 
1228 variable adh5_load_reduced_detector(variable fileID, string detectorpath, funcref reduction_func, string reduction_param, variable progress = defaultValue, variable nthreads = defaultValue){
1229  variable fileID
1230  string detectorpath
1231  funcref adh5_default_reduction reduction_func
1232  string reduction_param
1233  variable progress
1234  variable nthreads
1235 
1236  if (ParamIsDefault(progress))
1237  progress = 1
1238  endif
1239  if (ParamIsDefault(nthreads))
1240  nthreads = -1
1241  endif
1242  variable result = 0
1243 
1244  // avoid compilation error if HDF5 XOP has not been loaded
1245  #if Exists("HDF5LoadData")
1246  string datasetname
1247  string datawavename
1248 
1249  // detector data
1250  datasetname = detectorpath + "data"
1251  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
1252  InitHDF5DataInfo(di)
1253  variable err = HDF5DatasetInfo(fileID, datasetname, 0, di)
1254  if (err != 0)
1255  print "error accessing detector/data"
1256  return -1
1257  endif
1258  if (di.ndims < 2)
1259  print "error: rank of dataset < 2"
1260  return -2
1261  endif
1262 
1263  // nx and nz are the image dimensions
1264  variable idx, idy, idz, idt
1265  idx = di.ndims - 1
1266  idy = di.ndims - 2
1267  idz = -1
1268  idt = -1
1269 
1270  variable nx, ny, nz, nt
1271  nx = di.dims[idx]
1272  ny = di.dims[idy]
1273  nz = 1
1274  nt = 1
1275 
1276  // find additional dimensions, ignore singletons
1277  variable id
1278  for (id = idy - 1; (id >= 0) && (nz == 1); id -= 1)
1279  if (di.dims[id] > 1)
1280  idz = id
1281  nz = di.dims[id]
1282  endif
1283  endfor
1284  for (id = idz - 1; (id >= 0) && (nt == 1); id -= 1)
1285  if (di.dims[id] > 1)
1286  idt = id
1287  nt = di.dims[id]
1288  endif
1289  endfor
1290  // default values if dimensions are not present in dataset
1291  if (idz < 0)
1292  idz = idx + 1
1293  idt = idz + 1
1294  else if (idt < 0)
1295  idt = idx + 1
1296  endif
1297  variable nzt = nz * nt
1298  variable izt
1299 
1300  // load data image by image
1301  HDF5MakeHyperslabWave(GetDataFolder(1) + "slab", max(di.ndims, 4))
1302  wave slab
1303  slab[][%Start] = 0
1304  slab[][%Stride] = 1
1305  slab[][%Count] = 1
1306  slab[][%Block] = 1
1307  slab[idx][%Block] = nx
1308  slab[idy][%Block] = ny
1309 
1310  // set up multi threading
1311  if (nthreads < 0)
1312  nthreads = ThreadProcessorCount
1313  endif
1314  if (nthreads > 0)
1315  variable threadGroupID = ThreadGroupCreate(nthreads)
1316  variable ithread
1317  for (ithread = 0; ithread < nthreads; ithread += 1)
1318  ThreadStart threadGroupID, ithread, reduce_slab_worker(reduction_func)
1319  endfor
1320  else
1321  make /n=(nzt) /df /free processing_folders
1322  endif
1323 
1324  if (progress)
1325  display_progress_panel("HDF5 Import", "Loading data (step 1 of 2)...", nzt)
1326  endif
1327 
1328  make /n=(nx,ny)/d image_template
1329  setdimlabel 0, -1, AD_Dim0, image_template
1330  setdimlabel 1, -1, AD_Dim1, image_template
1331  adh5_scale(image_template)
1332 
1333  variable iz, it
1334  string dfname
1335  variable iw, nw
1336  string sw
1337  make /n=0 /free /wave result_waves
1338 
1339  izt = 0
1340  for (iz = 0; iz < nz; iz += 1)
1341  for (it = 0; it < nt; it += 1)
1342  // load hyperslab
1343  slab[idz][%Start] = iz
1344  slab[idt][%Start] = it
1345  dfname = "processing_" + num2str(izt)
1346  newdatafolder /s $dfname
1347  HDF5LoadData /O /Q /Z /SLAB=slab /N=slabdata fileID, datasetname
1348 
1349  // send to processing queue
1350  duplicate image_template, image
1351  variable /g r_index = iz
1352  variable /g s_index = it
1353  string /g func_param = reduction_param
1354 
1355  if (nthreads > 0)
1356  WaveClear image
1357  ThreadGroupPutDF threadGroupID, :
1358  else
1359  processing_folders[izt] = GetDataFolderDFR()
1360  wave slabdata
1361  wave /wave reduced_waves = reduce_slab_image(slabdata, image, reduction_func, func_param)
1362  variable /g func_result = numpnts(reduced_waves)
1363  adh5_get_result_waves(reduced_waves, "redw_", 0)
1364  WaveClear slabdata, image, reduced_waves
1365  setdatafolder ::
1366  endif
1367 
1368  izt += 1
1369  // progress window
1370  if (progress)
1371  if (update_progress_panel(izt))
1372  result = -4// user abort
1373  break
1374  endif
1375  endif
1376  endfor
1377  endfor
1378 
1379  killwaves /z slab, image_template
1380  if (progress)
1381  update_progress_panel(0, message="Processing data (step 2 of 2)...")
1382  endif
1383 
1384  dfref dfr
1385  for (izt = 0; (izt < nzt) && (result == 0); izt += 1)
1386  if (nthreads > 0)
1387  do
1388  dfr = ThreadGroupGetDFR(threadGroupID, 1000)
1389  if (DatafolderRefStatus(dfr) != 0)
1390  break
1391  endif
1392  if (progress)
1393  if (update_progress_panel(izt))
1394  result = -4// user abort
1395  break
1396  endif
1397  endif
1398  while (1)
1399  else
1400  dfr = processing_folders[izt]
1401  if (progress)
1402  if (update_progress_panel(izt))
1403  result = -4// user abort
1404  break
1405  endif
1406  endif
1407  endif
1408 
1409  if (result != 0)
1410  break
1411  endif
1412 
1413  nvar rr = dfr:r_index
1414  nvar ss = dfr:s_index
1415  nvar func_result = dfr:func_result
1416 
1417  if (func_result < 1)
1418  result = -3// dimension reduction error
1419  break
1420  endif
1421 
1422  if (numpnts(result_waves) == 0)
1423  redimension /n=(func_result) result_waves
1424  for (iw = 0; iw < func_result; iw += 1)
1425  sw = "redw_" + num2str(iw)
1426  wave profile = dfr:$sw
1427  sw = "ReducedData" + num2str(iw+1)
1428  make /n=(dimsize(profile, 0), nz, nt) /d /o $sw
1429  wave data = $sw
1430  setdimlabel 0, -1, $getdimlabel(profile, 0, -1), data
1431  setscale /p x dimoffset(profile, 0), dimdelta(profile, 0), waveunits(profile, 0), data
1432  setscale d 0, 0, waveunits(profile, -1), data
1433  result_waves[iw] = data
1434  endfor
1435  endif
1436  for (iw = 0; iw < func_result; iw += 1)
1437  sw = "redw_" + num2str(iw)
1438  wave profile = dfr:$sw
1439  wave data = result_waves[iw]
1440  data[][rr][ss] = profile[p]
1441  endfor
1442  endfor
1443 
1444  if (nthreads > 0)
1445  variable tstatus = ThreadGroupRelease(threadGroupID)
1446  if (tstatus == -2)
1447  result = -5// thread did not terminate properly
1448  endif
1449  else
1450  for (izt = 0; izt < nzt; izt += 1)
1451  KillDataFolder /Z processing_folders[izt]
1452  endfor
1453  endif
1454 
1455  if (result == 0)
1456  nw = numpnts(result_waves)
1457  for (iw = 0; iw < nw; iw += 1)
1458  wave data = result_waves[iw]
1459  if (nz == 1)
1460  redimension /n=(dimsize(data, 0)) data
1461  else if (nt == 1)
1462  redimension /n=(dimsize(data, 0),nz) data
1463  setdimlabel 1, -1, AD_DimN, data
1464  else
1465  setdimlabel 1, -1, AD_DimN, data
1466  setdimlabel 2, -1, AD_DimX, data
1467  endif
1468  endfor
1469  endif
1470  if (progress)
1472  endif
1473 
1474  #else
1475  Abort "HDF5 XOP not loaded."
1476  #endif
1477  return result
1478 };
1479 
1480 threadsafe static variable reduce_slab_worker(funcref reduction_func){
1481  funcref adh5_default_reduction reduction_func
1482  do
1483  // wait for job from main thread
1484  do
1485  dfref dfr = ThreadGroupGetDFR(0, 1000)
1486  if (DataFolderRefStatus(dfr) == 0)
1487  if (GetRTError(2))
1488  return 0// no more jobs
1489  endif
1490  else
1491  break
1492  endif
1493  while (1)
1494 
1495  // get input data
1496  wave slabdata = dfr:slabdata
1497  wave image = dfr:image
1498  svar func_param = dfr:func_param
1499  nvar rr = dfr:r_index
1500  nvar ss = dfr:s_index
1501 
1502  // do the work
1503  newdatafolder /s outDF
1504  variable /g r_index = rr
1505  variable /g s_index = ss
1506  wave /wave reduced_waves = reduce_slab_image(slabdata, image, reduction_func, func_param)
1507  variable /g func_result = numpnts(reduced_waves)
1508 
1509  // send output to queue and clean up
1510  adh5_get_result_waves(reduced_waves, "redw_", 0)
1511  WaveClear slabdata, image, reduced_waves
1512  ThreadGroupPutDF 0, :
1513  KillDataFolder dfr
1514  while (1)
1515 
1516  return 0
1517 };
1518 
1519 threadsafe static wave reduce_slab_image(wave slabdata, wave image, funcref reduction_func, string reduction_param){
1520  wave slabdata
1521  wave image
1522  funcref adh5_default_reduction reduction_func
1523  string reduction_param
1524 
1525  switch (WaveDims(slabdata))
1526  case 2:
1527  image = slabdata[q][p]
1528  break
1529  case 3:
1530  image = slabdata[0][q][p]
1531  break
1532  case 4:
1533  image = slabdata[0][0][q][p]
1534  break
1535  endswitch
1536 
1537  return reduction_func(image, reduction_param)
1538 };
1539 
1552 variable adh5_loadattr_all(variable fileID, string attributespath){
1553  variable fileID
1554  string attributespath
1555 
1556  string datasetname
1557  string datawavename
1558 
1559  // avoid compilation error if HDF5 XOP has not been loaded
1560  #if Exists("HDF5LoadData")
1561 
1562  // datasets in NDAttributes group
1563  HDF5ListGroup /F /TYPE=2 fileID, attributespath
1564  string h5datasets = S_HDF5ListGroup
1565  HDF5ListAttributes /TYPE=1 /Z fileID, attributespath
1566  string h5attributes = S_HDF5ListAttributes
1567 
1568  variable nds = ItemsInList(h5datasets, ";")
1569  variable na = ItemsInList(h5attributes, ";")
1570  variable ids
1571  variable idest = 0
1572  variable n_attr
1573  string s_attr
1574  string s_source
1575 
1576  make /n=(nds+na) /t /o IN, ID, IV, IU
1577 
1578  for (ids = 0; ids < nds; ids += 1)
1579  datasetname = StringFromList(ids, h5datasets, ";")
1580  HDF5LoadData /O/Q fileID, datasetname
1581  if (v_flag == 0)
1582  datawavename = StringFromList(0, s_wavenames)
1583  else
1584  datawavename = ""
1585  endif
1586  HDF5LoadData /A="source"/O/Q/TYPE=2 fileID, datasetname
1587  if (v_flag == 0)
1588  wave /t source
1589  s_source = source[0]
1590  else
1591  s_source = ""
1592  endif
1593  read_attribute_info(datawavename, s_source, idest)
1594  endfor
1595 
1596  // attributes of NDAttributes group
1597  if (v_flag == 0)
1598  nds = ItemsInList(h5attributes, ";")
1599  else
1600  nds = 0
1601  endif
1602  for (ids = 0; ids < nds; ids += 1)
1603  datasetname = StringFromList(ids, h5attributes, ";")
1604  HDF5LoadData /A=datasetname/O/Q/TYPE=1 fileID, attributespath
1605  if (v_flag == 0)
1606  datawavename = StringFromList(0, s_wavenames)
1607  read_attribute_info(datawavename, "", idest)// we don't get the source of these attributes
1608  endif
1609  endfor
1610 
1611  redimension /n=(idest) IN, ID, IV, IU
1612  sort {IN, ID}, IN, ID, IV, IU
1613 
1614  killwaves /z source
1615  #else
1616  Abort "HDF5 XOP not loaded."
1617  #endif
1618 
1619 };
1620 
1634 static variable read_attribute_info(string datawavename, string source, variable* idest){
1635  string datawavename// name of the attribute wave in the current folder.
1636  // can be text or numeric.
1637  string source
1638  // source identifier (EPICS name) of the attribute.
1639  variable &idest
1640  // destination index in IN, ID, IV, IU where the results are written.
1641  // the variable is incremented if data was written, otherwise it is left unchanged.
1642  // make sure IN, ID, IV, IU have at least idest + 1 elements.
1643 
1644  wave /t IN
1645  wave /t ID
1646  wave /t IV
1647  wave /t IU
1648 
1649  variable n_attr
1650  string s_attr
1651 
1652  if (exists(datawavename) == 1)
1653  if (strlen(source) > 0)
1654  Note $datawavename, "PV=" + source
1655  endif
1656  switch(WaveType($datawavename, 1))
1657  case 1:// numeric
1658  wave w_attr = $datawavename
1659  n_attr = numpnts(w_attr)
1660  sprintf s_attr, "%.12g", w_attr[0]
1661  break
1662  case 2:// text
1663  wave /t wt_attr = $datawavename
1664  n_attr = numpnts(wt_attr)
1665  s_attr = wt_attr[0]
1666  break
1667  default:// unknown
1668  n_attr = 0
1669  endswitch
1670  if (n_attr == 1)
1671  IN[idest] = source
1672  ID[idest] = datawavename
1673  IV[idest] = s_attr
1674  IU[idest] = ""// we don't get the units
1675  idest += 1
1676  endif
1677  endif
1678 };
1679 
1687 variable adh5_scale_scienta(wave data){
1688  wave data
1689 
1690  dfref saveDF = GetDataFolderDFR()
1691 
1692  dfref dataDF = GetWavesDataFolderDFR(data)
1693  dfref attrDF = GetAttrDataFolderDFR(data)
1694 
1695  wave /SDFR=attrDF LensMode
1696  wave /SDFR=attrDF /Z ChannelBegin, ChannelEnd
1697  wave /SDFR=attrDF /Z SliceBegin, SliceEnd
1698 
1699  variable EDim, ADim
1700  variable ELow, EHigh, ALow, AHigh
1701  string EUnit, AUnit
1702 
1703  // which dimension is angle and which one is energy?
1704  strswitch(GetDimLabel(data, 0, -1))
1705  case "AD_Dim0":
1706  EDim = 0
1707  break
1708  case "AD_Dim1":
1709  EDim = 1
1710  break
1711  default:
1712  EDim = -1
1713  endswitch
1714  strswitch(GetDimLabel(data, 1, -1))
1715  case "AD_Dim0":
1716  ADim = 0
1717  break
1718  case "AD_Dim1":
1719  ADim = 1
1720  break
1721  default:
1722  ADim = -1
1723  endswitch
1724 
1725  // defaults (point scaling)
1726  if (EDim >= 0)
1727  ELow = dimoffset(data, EDim)
1728  EHigh = dimoffset(data, EDim) + dimdelta(data, EDim) * (dimsize(data, EDim) - 1)
1729  EUnit = "eV"
1730  endif
1731  if (ADim >= 0)
1732  ALow = dimoffset(data, ADim)
1733  AHigh = dimoffset(data, ADim) + dimdelta(data, ADim) * (dimsize(data, ADim) - 1)
1734  AUnit = "arb."
1735  endif
1736 
1737  // lens mode can give more detail
1738  if (waveexists(LensMode) && (numpnts(LensMode) >= 1))
1739  switch(LensMode[0])
1740  case 1:// Angular45
1741  ALow = -45/2
1742  AHigh = +45/2
1743  AUnit = ""
1744  break
1745  case 2:// Angular60
1746  ALow = -60/2
1747  AHigh = +60/2
1748  AUnit = ""
1749  break
1750  endswitch
1751  endif
1752 
1753  // best option if scales are explicit in separate waves
1754  if (waveexists(ChannelBegin) && waveexists(ChannelEnd) && (numpnts(ChannelBegin) >= 1) && (numpnts(ChannelEnd) >= 1))
1755  ELow = ChannelBegin[0]
1756  EHigh = ChannelEnd[0]
1757  endif
1758  if (waveexists(SliceBegin) && waveexists(SliceEnd) && (numpnts(SliceBegin) >= 1) && (numpnts(SliceEnd) >= 1))
1759  ALow = SliceBegin[0]
1760  AHigh = SliceEnd[0]
1761  endif
1762 
1763  // apply new scales
1764  switch(EDim)
1765  case 0:
1766  setscale /i x ELow, EHigh, EUnit, data
1767  break
1768  case 1:
1769  setscale /i y ELow, EHigh, EUnit, data
1770  break
1771  endswitch
1772  switch(ADim)
1773  case 0:
1774  setscale /i x ALow, AHigh, AUnit, data
1775  break
1776  case 1:
1777  setscale /i y ALow, AHigh, AUnit, data
1778  break
1779  endswitch
1780 
1781  setscale d 0, 0, "arb.", data
1782 
1783  setdatafolder saveDF
1784 };
1785 
1792 variable adh5_scale_scan(wave data){
1793  wave data
1794 
1795  dfref saveDF = GetDataFolderDFR()
1796 
1797  dfref dataDF = GetWavesDataFolderDFR(data)
1798  wave /SDFR=dataDF AcquisitionMode, DetectorMode, EnergyMode
1799 
1800  wave /SDFR=dataDF /z Scan1Active, Scan2Active
1801  wave /SDFR=dataDF /t /z Scan1Positioner1, Scan1Readback1
1802  wave /SDFR=dataDF /t /z Scan1Positioner2, Scan1Readback2
1803  wave /SDFR=dataDF /t /z Scan2Positioner1, Scan2Readback1
1804  wave /SDFR=dataDF /t /z Scan2Positioner2, Scan2Readback2
1805 
1806  // TODO : search the data folder for positioner waves,
1807  // i.e. waves with the PV name corresponding to Scan1Positioner1 in their wave note.
1808  wave /z zscale
1809 
1810  strswitch(GetDimLabel(data, 0, -1))
1811  case "AD_DimN":
1812  setscale /i x zscale[0], zscale[numpnts(zscale)-1], "", data
1813  break
1814  endswitch
1815  strswitch(GetDimLabel(data, 1, -1))
1816  case "AD_DimN":
1817  setscale /i y zscale[0], zscale[numpnts(zscale)-1], "", data
1818  break
1819  endswitch
1820  strswitch(GetDimLabel(data, 2, -1))
1821  case "AD_DimN":
1822  setscale /i z zscale[0], zscale[numpnts(zscale)-1], "", data
1823  break
1824  endswitch
1825 
1826  setdatafolder saveDF
1827 };
1828 
string adh5_load_preview(string ANickName, string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue)
load a single image from a HDF5 file created by the Area Detector software.
-
variable kill_progress_panel()
-
variable display_progress_panel(string title, string message, variable progress_max)
-
string adh5_load_info(string APathName, string AFileName)
load descriptive info from a HDF5 file created by the Area Detector software.
-
variable ad_load_dialog(string APathName)
load area detector data files selected in a file dialog window
-
threadsafe wave ad_profile_x_w(wave dataset, variable q1, variable q2, wave destwave, variable noavg=defaultValue)
1D cut through 2D dataset along X dimension, existing destination wave.
-
static variable read_attribute_info(string datawavename, string source, variable *idest)
sub-function of adh5_loadattr_all.
-
static dfr GetAttrDataFolderDFR(wave data)
find the attributes data folder of an area detector dataset.
-
threadsafe variable adh5_setup_profile(wave image, wave profile, variable dim)
set up a one-dimensional wave for a line profile based on a 2D original wave.
-
threadsafe variable adh5_get_result_waves(wave results, string result_prefix, variable start_index)
copy waves from wave reference wave into current data folder
-
variable adh5_scale_scienta(wave data)
set the energy and angle scales of an area detector dataset from the Scienta analyser.
-
string adh5_test_reduction_func(wave source, funcref reduction_func, string reduction_param, string result_prefix)
wrapper function for testing reduction functions from the command line.
-
variable adh5_loadattr_all(variable fileID, string attributespath)
load an NDAttributes group from an open HDF5 file into the current data folder.
-
variable adh5_scale_scan(wave data)
scales the extra dimensions of an area detector dataset according to the EPICS scan ...
-
string ad_suggest_foldername(string filename, variable ignoredate=defaultValue, string sourcename=defaultValue, variable unique=defaultValue)
generate the name of a data folder based on a file name.
-
threadsafe wave ad_profile_y_w(wave dataset, variable p1, variable p2, wave destwave, variable noavg=defaultValue)
1D cut through 2D dataset along X dimension, existing destination wave.
-
string adh5_load_complete(string ANickName, string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue)
import everything from a HDF5 file created by the Area Detector software.
-
variable adh5_load_reduced_detector(variable fileID, string detectorpath, funcref reduction_func, string reduction_param, variable progress=defaultValue, variable nthreads=defaultValue)
load a reduced detector dataset from the open HDF5 file.
-
string adh5_load_reduced(string ANickName, string APathName, string AFileName, funcref reduction_func, string reduction_param, variable load_data=defaultValue, variable load_attr=defaultValue, variable progress=defaultValue)
load and reduce a dataset from a HDF5 file created by the Area Detector software. ...
-
variable adh5_redim(wave data)
redimension a multi-dimensional area detector array loaded from HDF5.
-
threadsafe wave adh5_default_reduction(wave source, string *param)
function prototype for adh5_load_reduced_detector
-
variable adh5_load_detector_slabs(variable fileID, string detectorpath, variable progress=defaultValue)
load the detector dataset from the open HDF5 file.
-
variable adh5_scale(wave data, string source=defaultValue)
set the dimension scales of an area detector dataset.
-
variable update_progress_panel(variable progress, string message=defaultValue, variable progress_max=defaultValue)
-
variable adh5_load_detector(variable fileID, string detectorpath)
load the detector dataset from the open HDF5 file.
-
static threadsafe wave reduce_slab_image(wave slabdata, wave image, funcref reduction_func, string reduction_param)
-
static variable BeforeFileOpenHook(variable refNum, string fileName, string path, string type, string creator, variable kind)
callback function for drag&drop of HDF5 files into Igor.
-
string adh5_list_reduction_funcs()
get a list of functions which can be used as reduction functions.
-
variable adh5_load_detector_image(variable fileID, string detectorpath, variable dim2start, variable dim2count, variable dim3start, variable dim3count)
load a single image from the detector dataset of the open HDF5 file
-
static threadsafe variable reduce_slab_worker(funcref reduction_func)
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-area-profiles_8ipf.html b/doc/html/pearl-area-profiles_8ipf.html index 3a1682e..eb8f1bb 100644 --- a/doc/html/pearl-area-profiles_8ipf.html +++ b/doc/html/pearl-area-profiles_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-area-profiles.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
-
pearl-area-profiles.ipf File Reference
+
pearl-area-profiles.ipf File Reference
-

profile extraction for multi-dimensional datasets acquired from area detectors. -More...

-

Go to the source code of this file.

- - - - - -

-Namespaces

 PearlAreaProfiles
 profile extraction for multi-dimensional datasets acquired from area detectors.
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

threadsafe wave ad_extract_rod (wave dataset, variable x1, variable x2, variable y1, variable y2, variable z1, variable z2, string destname, variable noavg=defaultValue, variable sdev=defaultValue, variable pscale=defaultValue)
 1D cut through 3D dataset, integrate in normal dimensions More...
 
threadsafe wave ad_extract_rod_x (wave dataset, variable q1, variable q2, variable r1, variable r2, string destname, variable noavg=defaultValue, variable sdev=defaultValue)
 1D cut through 3D dataset along X dimension. More...
 
threadsafe wave ad_extract_rod_y (wave dataset, variable p1, variable p2, variable r1, variable r2, string destname, variable noavg=defaultValue, variable sdev=defaultValue)
 1D cut through 3D dataset along Y dimension. More...
 
threadsafe wave ad_extract_rod_z (wave dataset, variable p1, variable p2, variable q1, variable q2, string destname, variable noavg=defaultValue, variable sdev=defaultValue)
 1D cut through 3D dataset along Z dimension. More...
 
threadsafe wave ad_extract_slab (wave dataset, variable x1, variable x2, variable y1, variable y2, variable z1, variable z2, string destname, variable noavg=defaultValue, variable pscale=defaultValue)
 2D cut through 3D dataset, integrate in normal dimension More...
 
threadsafe wave ad_extract_slab_x (wave dataset, variable p1, variable p2, string destname, variable noavg=defaultValue)
 
threadsafe wave ad_extract_slab_y (wave dataset, variable q1, variable q2, string destname, variable noavg=defaultValue)
 
threadsafe wave ad_extract_slab_z (wave dataset, variable r1, variable r2, string destname, variable noavg=defaultValue)
 
threadsafe wave ad_profile_x (wave dataset, variable q1, variable q2, string destname, variable noavg=defaultValue)
 1D cut through 2D dataset along X dimension, new destination wave. More...
 
threadsafe wave ad_profile_x_w (wave dataset, variable q1, variable q2, wave destwave, variable noavg=defaultValue)
 1D cut through 2D dataset along X dimension, existing destination wave. More...
 
threadsafe wave ad_profile_y (wave dataset, variable p1, variable p2, string destname, variable noavg=defaultValue)
 1D cut through 2D dataset along Y dimension, new destination wave. More...
 
threadsafe wave ad_profile_y_w (wave dataset, variable p1, variable p2, wave destwave, variable noavg=defaultValue)
 1D cut through 2D dataset along X dimension, existing destination wave. More...
 
threadsafe variable calc_y_profile_mins (wave image)
 
variable ad_collect_multiscan_y (wave dataset, wave positions, wave destwave, variable noavg=defaultValue)
 collect profiles from a multi-scan. More...
 
-

Detailed Description

-

profile extraction for multi-dimensional datasets acquired from area detectors.

-
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
- - -

Definition in file pearl-area-profiles.ipf.

-

Function Documentation

- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable ad_collect_multiscan_y (wave dataset,
wave positions,
wave destwave,
variable noavg = defaultValue 
)
-
- -

collect profiles from a multi-scan.

-
Warning
experimental: name and interface of this function may change.
- -

Definition at line 621 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_extract_rod (wave dataset,
variable x1,
variable x2,
variable y1,
variable y2,
variable z1,
variable z2,
string destname,
variable noavg = defaultValue,
variable sdev = defaultValue,
variable pscale = defaultValue 
)
-
- -

1D cut through 3D dataset, integrate in normal dimensions

-
Parameters
- - - - - - - -
dataset
x1,x2,y1,y2,z1,z2coordinates of integration region by default, the coordinates use wave scaling coordinates of rod dimensions (to be preserved) must be nan coordinate pairs don't have to be ordered, i.e. both x1 <= x2 and x1 >= x2 are allowed.
destnamename of destination wave. to be created in current data folder. if empty, the function returns a free wave
noavgnon-zero = calculate the sum, default = 0 as of version 1.05, this option should rather be called "calc_sum" or similar. it is noavg for compatibility with older code.
sdevnon-zero = calculate the standard deviation, default = 0 by default, the function calculates the average of the integration region set either the noavg or sdev option to select the sum or the standard deviation, respectively. if both options are set, noavg (sum) takes precedence.
pscalescaling of the slab coordinates x1, x2, ..., z2: zero or default = wave scaling, non-zero = point scaling
-
-
-
Remarks
    -
  • version 1.02: the specification of the destination coordinates has changed
  • -
  • version 1.04: the function returns an empty wave reference if an error occurred
  • -
-
- -

Definition at line 54 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_extract_rod_x (wave dataset,
variable q1,
variable q2,
variable r1,
variable r2,
string destname,
variable noavg = defaultValue,
variable sdev = defaultValue 
)
-
- -

1D cut through 3D dataset along X dimension.

-

see ad_extract_rod() for descriptions of common parameters.

- -

Definition at line 106 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_extract_rod_y (wave dataset,
variable p1,
variable p2,
variable r1,
variable r2,
string destname,
variable noavg = defaultValue,
variable sdev = defaultValue 
)
-
- -

1D cut through 3D dataset along Y dimension.

-

see ad_extract_rod() for descriptions of common parameters.

- -

Definition at line 168 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_extract_rod_z (wave dataset,
variable p1,
variable p2,
variable q1,
variable q2,
string destname,
variable noavg = defaultValue,
variable sdev = defaultValue 
)
-
- -

1D cut through 3D dataset along Z dimension.

-

see ad_extract_rod() for descriptions of common parameters.

- -

Definition at line 231 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_extract_slab (wave dataset,
variable x1,
variable x2,
variable y1,
variable y2,
variable z1,
variable z2,
string destname,
variable noavg = defaultValue,
variable pscale = defaultValue 
)
-
- -

2D cut through 3D dataset, integrate in normal dimension

-
Parameters
- - - - - - -
dataset
x1,x2,y1,y2,z1,z2coordinates of integration region. by default, the coordinates use wave scaling. coordinates of slab dimensions (to be preserved) must be nan. coordinate pairs don't have to be ordered, i.e. both x1 <= x2 and x1 >= x2 are allowed. coordinates can be out of range (-inf and +inf allowed) to select the whole range.
destnamename of destination wave. to be created in current data folder. if empty, the function returns a free wave.
noavgzero or default = average, non-zero = sum.
pscalescaling of the slab coordinates x1, x2, ..., z2: zero or default = wave scaling, non-zero = point scaling.
-
-
-
Remarks
    -
  • version 1.02: the specification of the destination coordinates has changed
  • -
  • version 1.04: the function returns an empty wave reference if an error occurred
  • -
-
- -

Definition at line 313 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_extract_slab_x (wave dataset,
variable p1,
variable p2,
string destname,
variable noavg = defaultValue 
)
-
- -

Definition at line 358 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_extract_slab_y (wave dataset,
variable q1,
variable q2,
string destname,
variable noavg = defaultValue 
)
-
- -

Definition at line 398 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_extract_slab_z (wave dataset,
variable r1,
variable r2,
string destname,
variable noavg = defaultValue 
)
-
- -

Definition at line 438 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_profile_x (wave dataset,
variable q1,
variable q2,
string destname,
variable noavg = defaultValue 
)
-
- -

1D cut through 2D dataset along X dimension, new destination wave.

- -

Definition at line 480 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_profile_x_w (wave dataset,
variable q1,
variable q2,
wave destwave,
variable noavg = defaultValue 
)
-
- -

1D cut through 2D dataset along X dimension, existing destination wave.

- -

Definition at line 504 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_profile_y (wave dataset,
variable p1,
variable p2,
string destname,
variable noavg = defaultValue 
)
-
- -

1D cut through 2D dataset along Y dimension, new destination wave.

- -

Definition at line 542 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe wave ad_profile_y_w (wave dataset,
variable p1,
variable p2,
wave destwave,
variable noavg = defaultValue 
)
-
- -

1D cut through 2D dataset along X dimension, existing destination wave.

- -

Definition at line 567 of file pearl-area-profiles.ipf.

- -
-
- -
-
- - - - - - - - -
threadsafe variable calc_y_profile_mins (wave image)
-
- -

Definition at line 603 of file pearl-area-profiles.ipf.

- -
-
diff --git a/doc/html/pearl-area-profiles_8ipf_source.html b/doc/html/pearl-area-profiles_8ipf_source.html index 2f797aa..645c662 100644 --- a/doc/html/pearl-area-profiles_8ipf_source.html +++ b/doc/html/pearl-area-profiles_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-area-profiles.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma IgorVersion = 6.1
3 #pragma ModuleName = PearlAreaProfiles
4 #pragma version = 1.05
5 
19 
25 
54 threadsafe wave ad_extract_rod(wave dataset, variable x1, variable x2, variable y1, variable y2, variable z1, variable z2, string destname, variable noavg = defaultValue, variable sdev = defaultValue, variable pscale = defaultValue){
55  wave dataset
56  variable x1, x2, y1, y2, z1, z2
57  string destname
58  variable noavg
59  variable sdev
60  variable pscale
61 
62  if (wavedims(dataset) != 3)
63  return $""
64  endif
65  if (ParamIsDefault(noavg))
66  noavg = 0
67  endif
68  if (ParamIsDefault(sdev))
69  sdev = 0
70  endif
71  if (ParamIsDefault(pscale))
72  pscale = 0
73  endif
74 
75  variable p1, p2, q1, q2, r1, r2
76  if (pscale)
77  p1 = x1
78  p2 = x2
79  q1 = y1
80  q2 = y2
81  r1 = z1
82  r2 = z2
83  else
84  p1 = round((x1 - DimOffset(dataset, 0)) / DimDelta(dataset, 0))
85  p2 = round((x2 - DimOffset(dataset, 0)) / DimDelta(dataset, 0))
86  q1 = round((y1 - DimOffset(dataset, 1)) / DimDelta(dataset, 1))
87  q2 = round((y2 - DimOffset(dataset, 1)) / DimDelta(dataset, 1))
88  r1 = round((z1 - DimOffset(dataset, 2)) / DimDelta(dataset, 2))
89  r2 = round((z2 - DimOffset(dataset, 2)) / DimDelta(dataset, 2))
90  endif
91 
92  if ((numtype(p1) == 2) || (numtype(p2) == 2))
93  return ad_extract_rod_x(dataset, min(q1, q2), max(q1, q2), min(r1, r2), max(r1, r2), destname, noavg=noavg, sdev=sdev)
94  else if ((numtype(q1) == 2) || (numtype(q2) == 2))
95  return ad_extract_rod_y(dataset, min(p1, p2), max(p1, p2), min(r1, r2), max(r1, r2), destname, noavg=noavg, sdev=sdev)
96  else if ((numtype(r1) == 2) || (numtype(r2) == 2))
97  return ad_extract_rod_z(dataset, min(p1, p2), max(p1, p2), min(q1, q2), max(q1, q2), destname, noavg=noavg, sdev=sdev)
98  else
99  return $""
100  endif
101 };
102 
106 threadsafe wave ad_extract_rod_x(wave dataset, variable q1, variable q2, variable r1, variable r2, string destname, variable noavg = defaultValue, variable sdev = defaultValue){
107  wave dataset
108  variable q1, q2, r1, r2
109  // -inf < q1 < q2 < +inf, -inf < r1 < r2 < +inf
110  string destname
111  variable noavg
112  variable sdev
113 
114  if (ParamIsDefault(noavg))
115  noavg = 0
116  endif
117  if (ParamIsDefault(sdev))
118  sdev = 0
119  endif
120  variable avg = !noavg && !sdev
121 
122  q1 = max(q1, 0)
123  q2 = min(q2, dimsize(dataset, 1) - 1)
124  r1 = max(r1, 0)
125  r2 = min(r2, dimsize(dataset, 2) - 1)
126 
127  if (strlen(destname) > 0)
128  duplicate /r=[][q1,q1][r1,r1]/o dataset, $destname
129  wave w_dest = $destname
130  else
131  duplicate /r=[][q1,q1][r1,r1] /free dataset, w_dest
132  endif
133  redimension /n=(dimsize(w_dest, 0)) w_dest
134  setscale /p x dimoffset(dataset, 0), dimdelta(dataset, 0), waveunits(dataset, 0), w_dest
135 
136  w_dest = 0
137  variable qq, rr
138  variable nn = 0
139  for (qq = q1; qq <= q2; qq += 1)
140  for (rr = r1; rr <= r2; rr += 1)
141  w_dest += dataset[p][qq][rr]
142  nn += 1
143  endfor
144  endfor
145 
146  if (sdev)
147  duplicate /free w_dest, w_squares
148  w_squares = 0
149  for (qq = q1; qq <= q2; qq += 1)
150  for (rr = r1; rr <= r2; rr += 1)
151  w_squares += dataset[p][qq][rr]^2
152  endfor
153  endfor
154  endif
155 
156  if (avg)
157  w_dest /= nn
158  else if (sdev)
159  w_dest = sqrt( (w_squares - w_dest^2 / nn) / (nn - 1) )
160  endif
161 
162  return w_dest
163 };
164 
168 threadsafe wave ad_extract_rod_y(wave dataset, variable p1, variable p2, variable r1, variable r2, string destname, variable noavg = defaultValue, variable sdev = defaultValue){
169  wave dataset
170  variable p1, p2, r1, r2
171  // 0 <= p1 < p2 < dimsize(0), 0 <= r1 < r2 < dimsize(2)
172  string destname
173  variable noavg
174  variable sdev
175 
176  if (ParamIsDefault(noavg))
177  noavg = 0
178  endif
179  if (ParamIsDefault(sdev))
180  sdev = 0
181  endif
182  variable avg = !noavg && !sdev
183 
184  p1 = max(p1, 0)
185  p2 = min(p2, dimsize(dataset, 0) - 1)
186  r1 = max(r1, 0)
187  r2 = min(r2, dimsize(dataset, 2) - 1)
188 
189  if (strlen(destname) > 0)
190  duplicate /r=[p1,p1][][r1,r1]/o dataset, $destname
191  wave w_dest = $destname
192  else
193  duplicate /r=[p1,p1][][r1,r1] /free dataset, w_dest
194  endif
195  redimension /n=(dimsize(w_dest, 1)) w_dest
196  setscale /p x dimoffset(dataset, 1), dimdelta(dataset, 1), waveunits(dataset, 1), w_dest
197 
198  w_dest = 0
199  variable pp, rr
200  variable nn = 0
201  for (pp = p1; pp <= p2; pp += 1)
202  for (rr = r1; rr <= r2; rr += 1)
203  w_dest += dataset[pp][p][rr]
204  nn += 1
205  endfor
206  endfor
207 
208  if (sdev)
209  duplicate /free w_dest, w_squares
210  w_squares = 0
211  for (pp = p1; pp <= p2; pp += 1)
212  for (rr = r1; rr <= r2; rr += 1)
213  w_squares += dataset[pp][p][rr]^2
214  nn += 1
215  endfor
216  endfor
217  endif
218 
219  if (avg)
220  w_dest /= nn
221  else if (sdev)
222  w_dest = sqrt( (w_squares - w_dest^2 / nn) / (nn - 1) )
223  endif
224 
225  return w_dest
226 };
227 
231 threadsafe wave ad_extract_rod_z(wave dataset, variable p1, variable p2, variable q1, variable q2, string destname, variable noavg = defaultValue, variable sdev = defaultValue){
232  wave dataset
233  variable p1, p2, q1, q2
234  // 0 <= p1 < p2 < dimsize(0), 0 <= q1 < q2 < dimsize(1)
235  string destname
236  variable noavg
237  variable sdev
238 
239  if (ParamIsDefault(noavg))
240  noavg = 0
241  endif
242  if (ParamIsDefault(sdev))
243  sdev = 0
244  endif
245  variable avg = !noavg && !sdev
246 
247  p1 = max(p1, 0)
248  p2 = min(p2, dimsize(dataset, 0) - 1)
249  q1 = max(q1, 0)
250  q2 = min(q2, dimsize(dataset, 1) - 1)
251 
252  if (strlen(destname) > 0)
253  duplicate /r=[p1,p1][q1,q1][]/o dataset, $destname
254  wave w_dest = $destname
255  else
256  duplicate /r=[p1,p1][q1,q1][] /free dataset, w_dest
257  endif
258  redimension /n=(dimsize(w_dest, 2)) w_dest
259  setscale /p x dimoffset(dataset, 2), dimdelta(dataset, 2), waveunits(dataset, 2), w_dest
260 
261  w_dest = 0
262  variable pp, qq
263  variable nn = 0
264  for (pp = p1; pp <= p2; pp += 1)
265  for (qq = q1; qq <= q2; qq += 1)
266  w_dest += dataset[pp][qq][p]
267  nn += 1
268  endfor
269  endfor
270 
271  if (sdev)
272  duplicate /free w_dest, w_squares
273  w_squares = 0
274  for (pp = p1; pp <= p2; pp += 1)
275  for (qq = q1; qq <= q2; qq += 1)
276  w_squares += dataset[pp][qq][p]^2
277  nn += 1
278  endfor
279  endfor
280  endif
281 
282  if (avg)
283  w_dest /= nn
284  else if (sdev)
285  w_dest = sqrt( (w_squares - w_dest^2 / nn) / (nn - 1) )
286  endif
287 
288  return w_dest
289 };
290 
313 threadsafe wave ad_extract_slab(wave dataset, variable x1, variable x2, variable y1, variable y2, variable z1, variable z2, string destname, variable noavg = defaultValue, variable pscale = defaultValue){
314  wave dataset
315  variable x1, x2, y1, y2, z1, z2
316  string destname
317  variable noavg
318  variable pscale
319 
320  if (wavedims(dataset) != 3)
321  return $""
322  endif
323  if (ParamIsDefault(noavg))
324  noavg = 0
325  endif
326  if (ParamIsDefault(pscale))
327  pscale = 0
328  endif
329 
330  variable p1, p2, q1, q2, r1, r2
331  if (pscale)
332  p1 = x1
333  p2 = x2
334  q1 = y1
335  q2 = y2
336  r1 = z1
337  r2 = z2
338  else
339  p1 = round((x1 - DimOffset(dataset, 0)) / DimDelta(dataset, 0))
340  p2 = round((x2 - DimOffset(dataset, 0)) / DimDelta(dataset, 0))
341  q1 = round((y1 - DimOffset(dataset, 1)) / DimDelta(dataset, 1))
342  q2 = round((y2 - DimOffset(dataset, 1)) / DimDelta(dataset, 1))
343  r1 = round((z1 - DimOffset(dataset, 2)) / DimDelta(dataset, 2))
344  r2 = round((z2 - DimOffset(dataset, 2)) / DimDelta(dataset, 2))
345  endif
346 
347  if ((numtype(p1) < 2) && (numtype(p2) < 2))
348  return ad_extract_slab_x(dataset, min(p1, p2), max(p1, p2), destname, noavg=noavg)
349  else if ((numtype(q1) < 2) && (numtype(q2) < 2))
350  return ad_extract_slab_y(dataset, min(q1, q2), max(q1, q2), destname, noavg=noavg)
351  else if ((numtype(r1) < 2) && (numtype(r2) < 2))
352  return ad_extract_slab_z(dataset, min(r1, r2), max(r1, r2), destname, noavg=noavg)
353  else
354  return $""
355  endif
356 };
357 
358 threadsafe wave ad_extract_slab_x(wave dataset, variable p1, variable p2, string destname, variable noavg = defaultValue){
359  wave dataset
360  variable p1, p2
361  // x coordinate range (point scaling) to be integrated
362  // -inf <= p1 < p2 <= +inf
363  string destname// name of destination wave. to be created in current data folder. overrides existing.
364  // if empty, the function returns a free wave
365  variable noavg// zero or default = average, non-zero = sum
366 
367  if (ParamIsDefault(noavg))
368  noavg = 0
369  endif
370  p1 = max(p1, 0)
371  p2 = min(p2, dimsize(dataset, 0) - 1)
372 
373  if (strlen(destname) > 0)
374  duplicate /r=[p1,p1][][]/o dataset, $destname
375  wave w_dest = $destname
376  else
377  duplicate /r=[p1,p1][][] /free dataset, w_dest
378  endif
379  redimension /n=(dimsize(w_dest, 1), dimsize(w_dest, 2)) w_dest
380  setscale /p x dimoffset(dataset, 1), dimdelta(dataset, 1), waveunits(dataset, 1), w_dest
381  setscale /p y dimoffset(dataset, 2), dimdelta(dataset, 2), waveunits(dataset, 2), w_dest
382 
383  w_dest = 0
384  variable pp
385  variable nn = 0
386  for (pp = p1; pp <= p2; pp += 1)
387  w_dest += dataset[pp][p][q]
388  nn += 1
389  endfor
390 
391  if (noavg == 0)
392  w_dest /= nn
393  endif
394 
395  return w_dest
396 };
397 
398 threadsafe wave ad_extract_slab_y(wave dataset, variable q1, variable q2, string destname, variable noavg = defaultValue){
399  wave dataset
400  variable q1, q2
401  // y coordinate range (point scaling) to be integrated
402  // -inf <= q1 < q2 <= +inf
403  string destname// name of destination wave. to be created in current data folder. overrides existing.
404  // if empty, the function returns a free wave
405  variable noavg// zero or default = average, non-zero = sum
406 
407  if (ParamIsDefault(noavg))
408  noavg = 0
409  endif
410  q1 = max(q1, 0)
411  q2 = min(q2, dimsize(dataset, 1) - 1)
412 
413  if (strlen(destname) > 0)
414  duplicate /r=[][q1,q1][]/o dataset, $destname
415  wave w_dest = $destname
416  else
417  duplicate /r=[][q1,q1][] /free dataset, w_dest
418  endif
419  redimension /n=(dimsize(w_dest, 0), dimsize(w_dest, 2)) w_dest
420  setscale /p x dimoffset(dataset, 0), dimdelta(dataset, 0), waveunits(dataset, 0), w_dest
421  setscale /p y dimoffset(dataset, 2), dimdelta(dataset, 2), waveunits(dataset, 2), w_dest
422 
423  w_dest = 0
424  variable qq
425  variable nn = 0
426  for (qq = q1; qq <= q2; qq += 1)
427  w_dest += dataset[p][qq][q]
428  nn += 1
429  endfor
430 
431  if (noavg == 0)
432  w_dest /= nn
433  endif
434 
435  return w_dest
436 };
437 
438 threadsafe wave ad_extract_slab_z(wave dataset, variable r1, variable r2, string destname, variable noavg = defaultValue){
439  wave dataset
440  variable r1, r2
441  // z coordinate range (point scaling) to be integrated
442  // -inf <= r1 < r2 <= +inf
443  string destname// name of destination wave. to be created in current data folder. overrides existing.
444  // if empty, the function returns a free wave
445  variable noavg// zero or default = average, non-zero = sum
446 
447  if (ParamIsDefault(noavg))
448  noavg = 0
449  endif
450  r1 = max(r1, 0)
451  r2 = min(r2, dimsize(dataset, 2) - 1)
452 
453  if (strlen(destname) > 0)
454  duplicate /r=[][][r1,r1]/o dataset, $destname
455  wave w_dest = $destname
456  else
457  duplicate /r=[][][r1,r1] /free dataset, w_dest
458  endif
459  redimension /n=(dimsize(w_dest, 0), dimsize(w_dest, 1)) w_dest
460  setscale /p x dimoffset(dataset, 0), dimdelta(dataset, 0), waveunits(dataset, 0), w_dest
461  setscale /p y dimoffset(dataset, 1), dimdelta(dataset, 1), waveunits(dataset, 1), w_dest
462 
463  w_dest = 0
464  variable rr
465  variable nn = 0
466  for (rr = r1; rr <= r2; rr += 1)
467  w_dest += dataset[p][q][rr]
468  nn += 1
469  endfor
470 
471  if (noavg == 0)
472  w_dest /= nn
473  endif
474 
475  return w_dest
476 };
477 
480 threadsafe wave ad_profile_x(wave dataset, variable q1, variable q2, string destname, variable noavg = defaultValue){
481  wave dataset
482  variable q1, q2// -inf <= q1 < q2 <= +inf
483  // deprecated: q2 = -1 stands for dimsize(0) - 1
484  string destname// name of destination wave. to be created in current data folder. overrides existing.
485  // if empty, the function returns a free wave
486  variable noavg// zero or default = average, non-zero = sum
487 
488  if (ParamIsDefault(noavg))
489  noavg = 0
490  endif
491 
492  if (strlen(destname) > 0)
493  duplicate /r=[0,0][] /o dataset, $destname
494  wave w_dest = $destname
495  else
496  duplicate /r=[0,0][] /free dataset, w_dest
497  endif
498 
499  return ad_profile_x_w(dataset, q1, q2, w_dest, noavg=noavg)
500 };
501 
504 threadsafe wave ad_profile_x_w(wave dataset, variable q1, variable q2, wave destwave, variable noavg = defaultValue){
505  wave dataset
506  variable q1, q2// -inf <= q1 < q2 <= +inf
507  // deprecated: q2 = -1 stands for dimsize(0) - 1
508  wave destwave// existing destination wave
509  variable noavg// zero or default = average, non-zero = sum
510 
511  if (ParamIsDefault(noavg))
512  noavg = 0
513  endif
514 
515  redimension /n=(dimsize(dataset, 0)) destwave
516  setscale /p x dimoffset(dataset, 0), dimdelta(dataset, 0), waveunits(dataset, 0), destwave
517  setscale d 0, 0, waveunits(dataset, -1), destwave
518 
519  q1 = max(q1, 0)
520  if (q2 < 0)
521  q2 = inf
522  endif
523  q2 = min(q2, dimsize(dataset, 1) - 1)
524 
525  destwave = 0
526  variable qq
527  variable nn = 0
528  for (qq = q1; qq <= q2; qq += 1)
529  destwave += dataset[p][qq]
530  nn += 1
531  endfor
532 
533  if (noavg == 0)
534  destwave /= nn
535  endif
536 
537  return destwave
538 };
539 
542 threadsafe wave ad_profile_y(wave dataset, variable p1, variable p2, string destname, variable noavg = defaultValue){
543  wave dataset
544  variable p1, p2// -inf <= p1 < p2 < inf
545  // deprecated: p2 = -1 stands for dimsize(0) - 1
546  string destname// name of destination wave. to be created in current data folder. overrides existing.
547  // if empty, the function returns a free wave
548  variable noavg// zero or default = average, non-zero = sum
549 
550  if (ParamIsDefault(noavg))
551  noavg = 0
552  endif
553 
554  if (strlen(destname) > 0)
555  duplicate /r=[][0,0] /o dataset, $destname
556  wave w_dest = $destname
557  else
558  duplicate /r=[][0,0] /free dataset, w_dest
559  endif
560  MatrixTranspose w_dest
561 
562  return ad_profile_y_w(dataset, p1, p2, w_dest, noavg=noavg)
563 };
564 
567 threadsafe wave ad_profile_y_w(wave dataset, variable p1, variable p2, wave destwave, variable noavg = defaultValue){
568  wave dataset
569  variable p1, p2// -inf <= p1 < p2 < inf
570  // deprecated: p2 = -1 stands for dimsize(0) - 1
571  wave destwave// existing destination wave
572  variable noavg// zero or default = average, non-zero = sum
573 
574  if (ParamIsDefault(noavg))
575  noavg = 0
576  endif
577 
578  redimension /n=(dimsize(dataset, 1)) destwave
579  setscale /p x dimoffset(dataset, 1), dimdelta(dataset, 1), waveunits(dataset, 1), destwave
580  setscale d 0, 0, waveunits(dataset, -1), destwave
581 
582  p1 = max(p1, 0)
583  if (p2 < 0)
584  p2 = inf
585  endif
586  p2 = min(p2, dimsize(dataset, 0) - 1)
587 
588  destwave = 0
589  variable pp
590  variable nn = 0
591  for (pp = p1; pp <= p2; pp += 1)
592  destwave += dataset[pp][p]
593  nn += 1
594  endfor
595 
596  if (noavg == 0)
597  destwave /= nn
598  endif
599 
600  return destwave
601 };
602 
603 threadsafe variable calc_y_profile_mins(wave image){
604  // experimental
605  wave image
606 
607  wave yminlocs = ad_profile_x(image, 0, 0, "ymins", noavg=1)
608  variable nx = dimsize(image, 0)
609  variable ix
610  for (ix = 0; ix < nx; ix += 1)
611  wave profile = ad_profile_y(image, ix, ix, "", noavg=1)
612  wavestats /q/m=1 profile
613  yminlocs[ix] = v_minloc
614  endfor
615 };
616 
621 variable ad_collect_multiscan_y(wave dataset, wave positions, wave destwave, variable noavg = defaultValue){
622  wave dataset
623  wave positions
624  wave destwave
625  variable noavg
626 
627  variable tol = (wavemax(positions) - wavemin(positions)) / numpnts(positions) / 100
628 
629  duplicate /free positions, positions_sorted
630  sort positions_sorted, positions_sorted
631  duplicate /free positions_sorted, positions_diff
632  differentiate /p /meth=2 positions_sorted /d=positions_diff
633  positions_diff[0] = 1
634  extract /free positions_sorted, positions_unique, positions_diff > tol
635  variable n_unique = numpnts(positions_unique)
636  redimension /n=(dimsize(dataset, 0), n_unique) destwave
637 
638  variable i
639  variable nx, ny
640  for (i = 0; i < n_unique; i += 1)
641  extract /free dataset, data_extract, abs(positions[q] - positions_unique[i]) < tol
642  nx = dimsize(dataset, 0)
643  ny = dimsize(data_extract, 0) / nx
644  redimension /n=(nx, ny) data_extract
645  wave profile = ad_profile_x(data_extract, -inf, inf, "", noavg=noavg)
646  destwave[][i] = profile[p]
647  endfor
648 };
649 
threadsafe wave ad_extract_slab_x(wave dataset, variable p1, variable p2, string destname, variable noavg=defaultValue)
-
threadsafe wave ad_extract_rod_x(wave dataset, variable q1, variable q2, variable r1, variable r2, string destname, variable noavg=defaultValue, variable sdev=defaultValue)
1D cut through 3D dataset along X dimension.
-
threadsafe wave ad_profile_y(wave dataset, variable p1, variable p2, string destname, variable noavg=defaultValue)
1D cut through 2D dataset along Y dimension, new destination wave.
-
threadsafe wave ad_profile_x_w(wave dataset, variable q1, variable q2, wave destwave, variable noavg=defaultValue)
1D cut through 2D dataset along X dimension, existing destination wave.
-
threadsafe wave ad_extract_slab_z(wave dataset, variable r1, variable r2, string destname, variable noavg=defaultValue)
-
variable ad_collect_multiscan_y(wave dataset, wave positions, wave destwave, variable noavg=defaultValue)
collect profiles from a multi-scan.
-
threadsafe wave ad_extract_slab_y(wave dataset, variable q1, variable q2, string destname, variable noavg=defaultValue)
-
threadsafe wave ad_extract_rod_z(wave dataset, variable p1, variable p2, variable q1, variable q2, string destname, variable noavg=defaultValue, variable sdev=defaultValue)
1D cut through 3D dataset along Z dimension.
-
threadsafe wave ad_profile_y_w(wave dataset, variable p1, variable p2, wave destwave, variable noavg=defaultValue)
1D cut through 2D dataset along X dimension, existing destination wave.
-
threadsafe wave ad_extract_rod_y(wave dataset, variable p1, variable p2, variable r1, variable r2, string destname, variable noavg=defaultValue, variable sdev=defaultValue)
1D cut through 3D dataset along Y dimension.
-
threadsafe variable calc_y_profile_mins(wave image)
-
threadsafe wave ad_profile_x(wave dataset, variable q1, variable q2, string destname, variable noavg=defaultValue)
1D cut through 2D dataset along X dimension, new destination wave.
-
threadsafe wave ad_extract_rod(wave dataset, variable x1, variable x2, variable y1, variable y2, variable z1, variable z2, string destname, variable noavg=defaultValue, variable sdev=defaultValue, variable pscale=defaultValue)
1D cut through 3D dataset, integrate in normal dimensions
-
threadsafe wave ad_extract_slab(wave dataset, variable x1, variable x2, variable y1, variable y2, variable z1, variable z2, string destname, variable noavg=defaultValue, variable pscale=defaultValue)
2D cut through 3D dataset, integrate in normal dimension
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-arpes_8ipf.html b/doc/html/pearl-arpes_8ipf.html index f39baf2..c3f9d74 100644 --- a/doc/html/pearl-arpes_8ipf.html +++ b/doc/html/pearl-arpes_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-arpes.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
pearl-arpes.ipf File Reference
-

data acquisition and analysis package for ARPES at PEARL. -More...

-
#include "pearl-area-display"
-#include "pearl-area-profiles"
-#include "pearl-area-import"
-#include "pearl-pshell-import"
-#include "pearl-data-explorer"
-#include "pearl-anglescan-process"
-#include "pearl-anglescan-panel"
-#include "pearl-anglescan-tracker"
-#include "pearl-scienta-preprocess"
-#include "pearl-elog"
-

Go to the source code of this file.

- - - - - -

-Namespaces

 PearlArpes
 data acquisition and analysis package for ARPES at PEARL.
 
- - - - - - -

-Functions

static variable AfterCompiledHook ()
 initializes package data once when the procedure is first loaded More...
 
variable UnloadPearlArpesPackage ()
 
-

Detailed Description

-

data acquisition and analysis package for ARPES at PEARL.

-

this procedure defines the PEARL ARPES package the main purpose of this file is to load the necessary dependent procedures (see the include statements at the top)

-
Precondition
    -
  • HDF5 XOP must be loaded.
  • -
  • on-line data acquisition functionality requires the EPICS XOP to be loaded
  • -
-
-
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
- - -

Definition in file pearl-arpes.ipf.

-

Function Documentation

- -
-
- - - - - -
- - - - - - - -
static variable AfterCompiledHook ()
-
-static
-
- -

initializes package data once when the procedure is first loaded

- -

Definition at line 83 of file pearl-arpes.ipf.

- -
-
- -
-
- - - - - - - -
variable UnloadPearlArpesPackage ()
-
- -

Definition at line 90 of file pearl-arpes.ipf.

- -
-
diff --git a/doc/html/pearl-arpes_8ipf_source.html b/doc/html/pearl-arpes_8ipf_source.html index dad2924..75f08c7 100644 --- a/doc/html/pearl-arpes_8ipf_source.html +++ b/doc/html/pearl-arpes_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-arpes.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma IgorVersion = 6.1
3 #pragma ModuleName = PearlArpes
4 #pragma version = 1.05
5 #include "pearl-area-display"// 2D and 3D data visualization
6 #include "pearl-area-profiles"// data processing for multi-dimensional datasets
7 #include "pearl-area-import"// import data files generated by area detector software
8 #include "pearl-pshell-import"
9 #include "pearl-data-explorer"// preview and import panel for PEARL data
10 #include "pearl-anglescan-process"// angle scan (XPD) processing functions
11 #include "pearl-anglescan-panel"// panel interface to angle scan processing
12 #include "pearl-anglescan-tracker"// live preview of hemispherical angle scan
13 #include "pearl-scienta-preprocess"// pre-processing functions for Scienta detector images
14 #include "pearl-elog"
15 #if exists("pvOpen")
16 #include "pearl-area-live"// live view of area detector
17 #include "pearl-epics"// EPICS access under Igor
18 #include "pearl-arpes-scans"// run ARPES scans under Igor
19 #endif
20 
21 // $Id$
22 //
23 // author: matthias.muntwiler@psi.ch
24 // Copyright (c) 2012-15 Paul Scherrer Institut
25 //
26 // Licensed under the Apache License, Version 2.0 (the "License");
27 // you may not use this file except in compliance with the License.
28 // You may obtain a copy of the License at
29 // http://www.apache.org/licenses/LICENSE-2.0
30 
49 
55 
81 
83 static variable AfterCompiledHook(){
84 
85  dfref savefolder = GetDataFolderDFR()
86 
87  return 0
88 };
89 
91  execute /p/q/z "DELETEINCLUDE \"pearl-arpes\""
92  execute /p/q/z "COMPILEPROCEDURES "
93 };
94 
variable UnloadPearlArpesPackage()
Definition: pearl-arpes.ipf:90
-
static variable AfterCompiledHook()
initializes package data once when the procedure is first loaded
Definition: pearl-arpes.ipf:83
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-data-explorer_8ipf.html b/doc/html/pearl-data-explorer_8ipf.html index 9cb5a06..d554693 100644 --- a/doc/html/pearl-data-explorer_8ipf.html +++ b/doc/html/pearl-data-explorer_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-data-explorer.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
-
pearl-data-explorer.ipf File Reference
+
pearl-data-explorer.ipf File Reference
-

preview and import panel for PEARL data -More...

-
#include "pearl-area-import"
-#include "pearl-area-profiles"
-#include "pearl-area-display"
-#include "pearl-pshell-import"
-

Go to the source code of this file.

- - - - - -

-Namespaces

 PearlDataExplorer
 preview and import panel for PEARL data
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

variable pearl_data_explorer ()
 
static variable init_package ()
 initialize the global variables of the data explorer. More...
 
static variable save_prefs ()
 
static variable load_prefs ()
 
static variable pearl_file_type (string filename)
 check whether a file can be imported by this module. More...
 
static variable update_filelist ()
 read a list of PEARL files from the file system More...
 
static variable update_datasets ()
 
static variable preview_file (string filename)
 
static wave preview_pshell_file (string filename)
 load the preview of a PShell HDF5 file. More...
 
static wave preview_hdf_file (string filename)
 load the preview of a PEARL HDF5 file. More...
 
static wave preview_itx_file (string filename)
 
static wave preview_mtrx_file (string filename)
 load the preview of a Matrix STM file. More...
 
static variable extract_preview_image (wave data, wave preview)
 
static variable preview_dataset (string datasetname)
 
static variable preview_datafolder ()
 
static variable preview_setscale_x (wave data, wave preview)
 
static variable preview_attributes (dfref attr_folder, dfref dest_folder=defaultValue, wave attr_filter=defaultValue, variable include_datawaves=defaultValue, variable include_infowaves=defaultValue)
 
static variable display_dataset (string datasetname)
 
variable test_attributes_notebook ()
 
static variable attributes_notebook (wave attr_names, wave attr_values, string title)
 
static variable notebook_add_attributes (string notebook_name, wave attr_filter, wave attr_names, wave attr_values)
 
static string show_preview_graph (wave data, wave xdata=defaultValue)
 
static string display_preview_trace (wave xtrace, wave ytrace)
 
static variable load_selected_files (string options=defaultValue)
 
static variable load_file (string filename, string options=defaultValue)
 
static variable prompt_hdf_options (string *options)
 
variable prompt_default_process (string *param)
 prototype for prompting for processing function parameters. More...
 
variable prompt_func_params (string func_name, string *func_param)
 
static dfr load_pshell_file (string filename, string options=defaultValue)
 
static dfr load_hdf_file (string filename, string options=defaultValue)
 
static dfr load_itx_file (string filename, string options=defaultValue)
 
static dfr load_mtrx_file (string filename, string options=defaultValue)
 load a matrix (STM) data file More...
 
string itx_suggest_foldername (string filename, variable ignoredate=defaultValue, string sourcename=defaultValue, variable unique=defaultValue)
 
void PearlDataExplorer ()
 
static variable bp_load_prefs (WMButtonAction *ba)
 
static variable bp_save_prefs (WMButtonAction *ba)
 
static variable bp_browse_filepath (WMButtonAction *ba)
 
static variable bp_update_filelist (WMButtonAction *ba)
 
static variable bp_load_files (WMButtonAction *ba)
 
static variable bp_load_files_opt (WMButtonAction *ba)
 
static variable bp_file_next (WMButtonAction *ba)
 
static variable bp_file_prev (WMButtonAction *ba)
 
static variable lbp_filelist (WMListboxAction *lba)
 
static variable bp_update_datasets (WMButtonAction *ba)
 
static variable bp_dataset_folder (WMButtonAction *ba)
 
static variable bp_dataset_display (WMButtonAction *ba)
 
static variable bp_dataset_next (WMButtonAction *ba)
 
static variable bp_dataset_prev (WMButtonAction *ba)
 
static variable lbp_datasets (WMListboxAction *lba)
 
static variable bp_attr_notebook (WMButtonAction *ba)
 
- - - - - - - - - - - - - -

-Variables

static const string package_name = "pearl_explorer"
 
static const string package_path = "root:packages:pearl_explorer:"
 
static const string ks_filematch_adh5 = "*.h5"
 
static const string ks_filematch_pshell = "psh*.h5"
 
static const string ks_filematch_itx = "*.itx"
 
static const string ks_filematch_mtrx = "*_mtrx"
 
-

Detailed Description

-

preview and import panel for PEARL data

-

preview and import panel for PEARL data:

- -

Definition in file pearl-data-explorer.ipf.

-

Function Documentation

- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - -
static variable attributes_notebook (wave attr_names,
wave attr_values,
string title 
)
-
-static
-
- -

Definition at line 805 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_attr_notebook (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1733 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_browse_filepath (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1419 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_dataset_display (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1624 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_dataset_folder (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1598 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_dataset_next (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1644 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_dataset_prev (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1671 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_file_next (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1485 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_file_prev (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1517 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_load_files (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1457 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_load_files_opt (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1471 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_load_prefs (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1391 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_save_prefs (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1405 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_update_datasets (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1584 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_update_filelist (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1443 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable display_dataset (string datasetname)
-
-static
-
- -

Definition at line 765 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static string display_preview_trace (wave xtrace,
wave ytrace 
)
-
-static
-
- -

Definition at line 922 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static variable extract_preview_image (wave data,
wave preview 
)
-
-static
-
- -

Definition at line 478 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable init_package ()
-
-static
-
- -

initialize the global variables of the data explorer.

-

initializes the global variables and data folder for this procedure file must be called once before the panel is created warning: this function overwrites previous values

- -

Definition at line 55 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string itx_suggest_foldername (string filename,
variable ignoredate = defaultValue,
string sourcename = defaultValue,
variable unique = defaultValue 
)
-
- -

Definition at line 1241 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable lbp_datasets (WMListboxAction * lba)
-
-static
-
- -

Definition at line 1698 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable lbp_filelist (WMListboxAction * lba)
-
-static
-
- -

Definition at line 1549 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static variable load_file (string filename,
string options = defaultValue 
)
-
-static
-
- -

Definition at line 979 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static dfr load_hdf_file (string filename,
string options = defaultValue 
)
-
-static
-
- -

Definition at line 1125 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static dfr load_itx_file (string filename,
string options = defaultValue 
)
-
-static
-
- -

Definition at line 1175 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static dfr load_mtrx_file (string filename,
string options = defaultValue 
)
-
-static
-
- -

load a matrix (STM) data file

- -

Definition at line 1218 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable load_prefs ()
-
-static
-
- -

Definition at line 116 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static dfr load_pshell_file (string filename,
string options = defaultValue 
)
-
-static
-
- -

Definition at line 1073 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable load_selected_files (string options = defaultValue)
-
-static
-
- -

Definition at line 955 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable notebook_add_attributes (string notebook_name,
wave attr_filter,
wave attr_names,
wave attr_values 
)
-
-static
-
- -

Definition at line 844 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - - - -
variable pearl_data_explorer ()
-
- -

Definition at line 44 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable pearl_file_type (string filename)
-
-static
-
- -

check whether a file can be imported by this module.

-

the file type is determined by the extension of the file name.

-
Returns
file type
    -
  • 0 not a recognized file type
  • -
  • 1 PShell file (HDF5, name starts with psh_)
  • -
  • 2 area detector HDF5 file
  • -
  • 3 Igor text (itx) file
  • -
  • 4 Matrix STM file (*_mtrx)
  • -
-
- -

Definition at line 161 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - - - -
void PearlDataExplorer ()
-
- -

Definition at line 1300 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable preview_attributes (dfref attr_folder,
dfref dest_folder = defaultValue,
wave attr_filter = defaultValue,
variable include_datawaves = defaultValue,
variable include_infowaves = defaultValue 
)
-
-static
-
- -

Definition at line 631 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable preview_datafolder ()
-
-static
-
- -

Definition at line 560 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable preview_dataset (string datasetname)
-
-static
-
- -

Definition at line 517 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable preview_file (string filename)
-
-static
-
- -

Definition at line 255 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static wave preview_hdf_file (string filename)
-
-static
-
- -

load the preview of a PEARL HDF5 file.

-

the preview is an arbitrary detector image extracted from the file, see adh5_load_preview(). the preview is loaded to the preview_image wave in the pear_explorer data folder.

-

the s_file_info string is updated with information about the scan dimensions.

-
Parameters
- - -
filenamename of a file in the directory specified by the pearl_explorer_filepath path object.
-
-
-
Returns
wave reference of the preview image
- -

Definition at line 363 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static wave preview_itx_file (string filename)
-
-static
-
- -

Definition at line 395 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static wave preview_mtrx_file (string filename)
-
-static
-
- -

load the preview of a Matrix STM file.

-

the preview is loaded to the preview_image wave in the pearl_explorer data folder.

-

the s_file_info string is updated with information about the scan dimensions.

-

this function requires the MatrixFileReader.xop and pearl-matrix-import.ipf to be loaded. otherwise it will return an empty wave reference.

-
Parameters
- - -
filenamename of a file in the directory specified by the pearl_explorer_filepath path object.
-
-
-
Returns
wave reference of the preview image. empty wave reference if the function failed.
- -

Definition at line 435 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static wave preview_pshell_file (string filename)
-
-static
-
- -

load the preview of a PShell HDF5 file.

-

the preview is an arbitrary detector image extracted from the file, see adh5_load_preview(). the preview is loaded to the preview_image wave in the pear_explorer data folder.

-

the s_file_info string is updated with information about the scan dimensions.

-
Parameters
- - -
filenamename of a file in the directory specified by the pearl_explorer_filepath path object.
-
-
-
Returns
wave reference of the preview image
- -

Definition at line 307 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static variable preview_setscale_x (wave data,
wave preview 
)
-
-static
-
- -

Definition at line 601 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - - - - -
variable prompt_default_process (string * param)
-
- -

prototype for prompting for processing function parameters.

-

the function should prompt the user for function parameters, and update the param argument if the user clicked OK. returns 0 if the user clicked OK, 1 if the user cancelled.

-

prompt functions must have the same name as the corresponding reduction function with the prefix "prompt_". be aware of the limited length of function names in Igor.

-

this function is a prototype. it does nothing but returns OK.

- -

Definition at line 1053 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable prompt_func_params (string func_name,
string * func_param 
)
-
- -

Definition at line 1059 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable prompt_hdf_options (string * options)
-
-static
-
- -

Definition at line 1014 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable save_prefs ()
-
-static
-
- -

Definition at line 96 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static string show_preview_graph (wave data,
wave xdata = defaultValue 
)
-
-static
-
- -

Definition at line 871 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - - - -
variable test_attributes_notebook ()
-
- -

Definition at line 798 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable update_datasets ()
-
-static
-
- -

Definition at line 212 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable update_filelist ()
-
-static
-
- -

read a list of PEARL files from the file system

-

wtFiles and wSelectedFiles in the package data folder are updated. only files for which pearl_file_type() returns non-zero are listed.

- -

Definition at line 184 of file pearl-data-explorer.ipf.

- -
-
-

Variable Documentation

- -
-
- - - - - -
- - - - -
const string ks_filematch_adh5 = "*.h5"
-
-static
-
- -

Definition at line 39 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string ks_filematch_itx = "*.itx"
-
-static
-
- -

Definition at line 41 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string ks_filematch_mtrx = "*_mtrx"
-
-static
-
- -

Definition at line 42 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string ks_filematch_pshell = "psh*.h5"
-
-static
-
- -

Definition at line 40 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string package_name = "pearl_explorer"
-
-static
-
- -

Definition at line 36 of file pearl-data-explorer.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string package_path = "root:packages:pearl_explorer:"
-
-static
-
- -

Definition at line 37 of file pearl-data-explorer.ipf.

- -
-
diff --git a/doc/html/pearl-data-explorer_8ipf_source.html b/doc/html/pearl-data-explorer_8ipf_source.html index e420c12..9ca149c 100644 --- a/doc/html/pearl-data-explorer_8ipf_source.html +++ b/doc/html/pearl-data-explorer_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-data-explorer.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma IgorVersion = 6.1
3 #pragma ModuleName = PearlDataExplorer
4 #pragma version = 1.50
5 #include "pearl-area-import"
6 #include "pearl-area-profiles"
7 #include "pearl-area-display"
8 #include "pearl-pshell-import"
9 #if exists("MFR_OpenResultFile")
10 #include "pearl-matrix-import"
11 #endif
12 
13 // copyright (c) 2013-16 Paul Scherrer Institut
14 //
15 // Licensed under the Apache License, Version 2.0 (the "License");
16 // you may not use this file except in compliance with the License.
17 // You may obtain a copy of the License at
18 // http:///www.apache.org/licenses/LICENSE-2.0
19 
30 
35 
36 static const string package_name = "pearl_explorer";
37 static const string package_path = "root:packages:pearl_explorer:";
38 
39 static const string ks_filematch_adh5 = "*.h5";
40 static const string ks_filematch_pshell = "psh*.h5";
41 static const string ks_filematch_itx = "*.itx";
42 static const string ks_filematch_mtrx = "*_mtrx";
43 
45  init_package()
46  load_prefs()
47  execute /q/z "PearlDataExplorer()"
48 };
49 
55 static variable init_package(){
56 
57  dfref savefolder = GetDataFolderDFR()
58  SetDataFolder root:
59  newdatafolder /o/s packages
60  newdatafolder /o/s $package_name
61  if (exists("v_InitPanelDone") == 2)
62  SetDataFolder savefolder
63  return 0
64  endif
65 
66  make /o/n=0/t wtFiles
67  make /o/n=0/i wSelectedFiles,wSelectedDatasets
68  make /o/n=0/t wtDatasets
69  make /o/n=0/t wtPositioners,wtDetectors
70  make /o/n=0/i wSelectedPositioners,wSelectedDetectors
71 
72  make /o/n=(1,1) preview_image// preview 2D data
73  make /o/n=0 preview_trace// preview 1D data
74  make /o/n=0/t attr_names, attr_values, attr_filter, attr_filter_summary
75 
76  // persistent strings and variables. persistent = saved in preferences
77  string /g s_filepath = ""// directory path to be listed
78  string /g s_hdf_options = ""// recently used HDF5 load options
79  string /g s_reduction_params = ""// recently used reduction parameters
80  string /g s_preview_pvs = ""// semicolon-separated list of EPICS PVs to display in preview.
81  // the list items can contain wildcards for StringMatch
82  s_preview_pvs = "*OP:CURRENT*;*Stats*Total*;*CADC*"
83 
84  // non-persistent strings and variables
85  string /g s_preview_file = ""// file or folder name of the current preview
86  string /g s_preview_source = ""// data source, e.g. EPICS channel name, of the current preview
87  string /g s_profiles_graph = ""// window name of the current preview if the data is two-dimensional
88  string /g s_preview_trace_graph = ""// window name of the current preview if the data is one-dimensional
89  string /g s_file_info = ""// description of selected file
90 
91  variable/g v_InitPanelDone = 1
92 
93  SetDataFolder savefolder
94 };
95 
96 static variable save_prefs(){
97  // saves persistent package data to the preferences file
98  // the data saved in the file are: data file path, attributes filter
99  dfref saveDF = GetDataFolderDFR()
100 
101  string fullPath = SpecialDirPath("Packages", 0, 0, 0)
102  fullPath += package_name
103  NewPath/O/C/Q tempPackagePrefsPath, fullPath
104  fullPath += ":preferences.pxp"
105 
106  SetDataFolder root:packages
107  SetDataFolder $package_name
108  string objects = "attr_filter;attr_filter_summary;s_filepath;s_hdf_options;s_reduction_params;s_preview_pvs"
109  SaveData /O /Q /J=objects fullPath
110 
111  KillPath/Z tempPackagePrefsPath
112 
113  SetDataFolder saveDF
114 };
115 
116 static variable load_prefs(){
117  // loads persistent package data from the preferences file
118  // the preferences file is an Igor packed experiment file in a special preferences folder
119  dfref saveDF = GetDataFolderDFR()
120 
121  variable result = -1
122  setdatafolder root:
123  NewDataFolder /O/S packages
124  NewDataFolder /O/S $package_name
125  dfref packageDF = GetDataFolderDFR()
126  string fullPath = SpecialDirPath("Packages", 0, 0, 0)
127  fullPath += package_name
128 
129  GetFileFolderInfo /Q /Z fullPath
130  if (V_Flag == 0)// Disk directory exists?
131  fullPath += ":preferences.pxp"
132  GetFileFolderInfo /Q /Z fullPath
133  if (V_Flag == 0)// Preference file exist?
134  LoadData /O /R /Q fullPath
135  result = 0
136  endif
137  endif
138 
139  if (result == 0)
140  svar /sdfr=packageDF filepath = s_filepath
141  NewPath /O/Z pearl_explorer_filepath, filepath
144  endif
145 
146  SetDataFolder saveDF
147  return result
148 };
149 
161 static variable pearl_file_type(string filename){
162  string filename
163 
164  if (StringMatch(filename, ks_filematch_pshell))
165  return 1
166  else if (StringMatch(filename, ks_filematch_adh5))
167  return 2
168  else if (StringMatch(filename, ks_filematch_itx))
169  return 3
170 #if exists("MFR_OpenResultFile")
171  else if (StringMatch(filename, ks_filematch_mtrx))
172  return 4
173 #endif
174  else
175  return 0
176  endif
177 };
178 
184 static variable update_filelist(){
185  dfref saveDF = GetDataFolderDFR()
186 
187  string all_files
188  wave /t wtFiles = $(package_path + "wtFiles")
189  wave wSelectedFiles = $(package_path + "wSelectedFiles")
190  variable nn
191 
192  PathInfo pearl_explorer_filepath
193  if (v_flag == 1)
194  all_files = IndexedFile(pearl_explorer_filepath, -1, "????")
195  nn = ItemsInList(all_files)
196  else
197  all_files = ""
198  nn = 0
199  endif
200 
201  make /n=(nn) /t /free wtAllFiles
202  wtAllFiles = StringFromList(p, all_files)
203  Extract /o /t wtAllFiles, wtFiles, pearl_file_type(wtAllFiles[p])
204  Sort /A /R wtFiles, wtFiles
205 
206  redimension /n=(numpnts(wtFiles)) wSelectedFiles
207  wSelectedFiles = 0
208 
209  setdatafolder saveDF
210 };
211 
212 static variable update_datasets(){
213  // updates the list of imported datasets.
214  // a dataset means any top-level data folder
215  // which includes a string variable named pearl_explorer_import.
216  dfref saveDF = GetDataFolderDFR()
217 
218  setdatafolder root:
219  dfref rootdf = GetDataFolderDFR()
220  setdatafolder $package_path
221  dfref privatedf = GetDataFolderDFR()
222 
223  wave /t wtDatasets
224  wave wSelectedDatasets
225  variable maxdf = CountObjectsDFR(rootdf, 4)
226  redimension /n=(maxdf) wtDatasets
227 
228  variable idf = 0
229  variable ndf = 0
230  string sdf
231 
232  do
233  sdf = GetIndexedObjNameDFR(rootdf, 4, idf)
234  if (strlen(sdf) >= 1)
235  setdatafolder rootdf
236  setdatafolder $sdf
237  svar /z importer = pearl_explorer_import
238  if (svar_exists(importer))
239  wtDatasets[ndf] = sdf
240  ndf += 1
241  endif
242  else
243  break
244  endif
245  idf += 1
246  while(1)
247 
248  redimension /n=(ndf) wtDatasets, wSelectedDatasets
249  wSelectedDatasets = 0
250  sort wtDatasets, wtDatasets
251 
252  setdatafolder saveDF
253 };
254 
255 static variable preview_file(string filename){
256  string filename
257 
258  dfref saveDF = GetDataFolderDFR()
259 
260  variable ft = pearl_file_type(filename)
261  switch(ft)
262  case 1:
263  wave /z image = preview_pshell_file(filename)
264  break
265  case 2:
266  wave /z image = preview_hdf_file(filename)
267  break
268  case 3:
269  wave /z image = preview_itx_file(filename)
270  break
271  case 4:
272  wave /z image = preview_mtrx_file(filename)
273  break
274  default:
275  wave /z image = $""
276  endswitch
277 
278  if (WaveExists(image))
279  string graphname = show_preview_graph(image)
280  // preset ELOG panel - if available
281  if (exists("PearlElog#set_panel_attributes") == 6)
282  string cmd
283  sprintf cmd, "PearlElog#set_panel_attributes(\"\", \"File=%s\")", ParseFilePath(0, filename, ":", 1, 0)
284  execute /Q/Z cmd
285  if (strlen(graphname) > 0)
286  sprintf cmd, "PearlElog#set_panel_graphs(\"\", \"%s\")", graphname
287  execute /Q/Z cmd
288  endif
289  endif
290  endif
291 
292  setdatafolder saveDF
293  return 0
294 };
295 
307 static wave preview_pshell_file(string filename){
308  string filename
309 
310  dfref saveDF = GetDataFolderDFR()
311 
312  setdatafolder $package_path
313  dfref previewDF = GetDataFolderDFR()
314  svar s_preview_file
315  svar s_preview_source
316  svar /z s_file_info
317  if (! svar_exists(s_file_info))
318  string /g s_file_info
319  endif
320 
321  dfref tempDF = NewFreeDataFolder()
322  setdatafolder tempDF
323  string dataname
324  dataname = psh5_load_preview("pearl_explorer_filepath", filename)
325 
326  s_preview_file = filename
327  s_preview_source = ""
328 
329  wave /z data = $dataname
330  if (waveexists(data))
331  duplicate /o data, previewDF:preview_image
332  else
333  print "no data found in file " + filename
334  endif
335 
336  if (strlen(s_preview_file) > 0)
337  s_file_info = psh5_load_info("pearl_explorer_filepath", filename)
338  else
339  s_file_info = ""
340  endif
341 
342  dfref attrDF = tempDF:attr
343  if (DataFolderRefStatus(attrDF))
344  preview_attributes(attrDF)
345  endif
346 
347  setdatafolder saveDF
348  wave /z /sdfr=previewDF preview_image
349  return preview_image
350 };
351 
363 static wave preview_hdf_file(string filename){
364  string filename
365 
366  dfref saveDF = GetDataFolderDFR()
367  setdatafolder $package_path
368  svar s_preview_file
369  svar s_preview_source
370  adh5_load_preview("preview_image", "pearl_explorer_filepath", filename)
371  s_preview_file = filename
372  s_preview_source = ""
373  wave /z preview_image
374 
375  svar /z s_file_info
376  if (! svar_exists(s_file_info))
377  string /g s_file_info
378  endif
379  if (strlen(s_preview_file) > 0)
380  s_file_info = adh5_load_info("pearl_explorer_filepath", filename)
381  else
382  s_file_info = ""
383  endif
384 
385  if (DataFolderExists("attr"))
386  setdatafolder attr
387  preview_attributes(GetDataFolderDFR())
388  setdatafolder ::
389  endif
390 
391  setdatafolder saveDF
392  return preview_image
393 };
394 
395 static wave preview_itx_file(string filename){
396  string filename
397 
398  dfref saveDF = GetDataFolderDFR()
399  setdatafolder $package_path
400  svar s_preview_file
401  svar s_preview_source
402  wave preview_image
403 
404  // note: some versions of PEARL data files save data to a new data folder,
405  // and leave the newly created folder as the current folder.
406  // the free data folder is used by those files which don't create their own data folder.
407  // this is the new recommended behaviour
408  dfref dataDF = newfreedatafolder()
409  setdatafolder dataDF
410  LoadWave /t/p=pearl_explorer_filepath/q filename
411  s_preview_file = s_filename
412  s_preview_source = ""
413 
415  preview_attributes(dataDF, include_datawaves=0)
416 
417  setdatafolder saveDF
418  return preview_image
419 };
420 
435 static wave preview_mtrx_file(string filename){
436  string filename
437 
438 #if exists("MFR_OpenResultFile")
439  dfref saveDF = GetDataFolderDFR()
440  setdatafolder $package_path
441  variable /g V_MatrixFileReaderOverwrite = 1
442  variable /g V_MatrixFileReaderFolder = 0
443  variable /g V_MatrixFileReaderDouble = 0
444  svar s_preview_file
445  svar s_preview_source
446  string datanames
447  string dataname
448  datanames = mtrx_load_preview("preview", "pearl_explorer_filepath", filename)
449  if (strlen(datanames) > 0)
450  s_preview_file = filename
451 
452  dataname = StringFromList(0, datanames)
453  wave data = $dataname
454  duplicate /o $dataname, preview_image
455  s_preview_source = StringByKey("Dataset", note(data), "=", "\r")
456 
457  svar /z s_file_info
458  if (svar_exists(s_file_info))
459  s_file_info = ""
460  endif
461 
462  variable i
463  variable n = ItemsInList(datanames)
464  string s
465  for (i = 0; i < n; i += 1)
466  s = StringFromList(i, datanames)
467  killwaves /z $s
468  endfor
469  endif
470  wave /z preview_image
471  setdatafolder saveDF
472 #else
473  wave /z preview_image = $""
474 #endif
475  return preview_image
476 };
477 
478 static variable extract_preview_image(wave data, wave preview){
479  // extracts a preview image from a wave of arbitrary dimension
480  wave data
481  wave preview
482 
483  variable z1, z2
484 
485  // extract image
486  switch (WaveDims(data))
487  case 1:
488  redimension /n=(numpnts(data)) preview
489  preview = data[p]
490  break
491  case 2:
492  redimension /n=(dimsize(data, 0), dimsize(data, 1)) preview
493  preview = data
494  break
495  case 3:
496  redimension /n=(dimsize(data, 0), dimsize(data, 1)) preview
497  z1 = floor(DimSize(data, 2) / 2)
498  z2 = z1
499  wave slab = ad_extract_slab(data, nan, nan, nan, nan, z1, z2, "", pscale=1)
500  preview = slab
501  break
502  case 4:
503  // not implemented
504  endswitch
505 
506  switch (WaveDims(data))
507  case 4:
508  case 3:
509  case 2:
510  setscale /p y dimoffset(data, 1), dimdelta(data, 1), waveunits(data, 1), preview
511  case 1:
512  setscale /p x dimoffset(data, 0), dimdelta(data, 0), waveunits(data, 0), preview
513  setscale d 0, 0, waveunits(data, -1), preview
514  endswitch
515 };
516 
517 static variable preview_dataset(string datasetname){
518  string datasetname// name of a data folder under root
519 
520  dfref saveDF = GetDataFolderDFR()
521 
522  if (!DataFolderExists("root:" + datasetname))
523  return -1
524  endif
525  setdatafolder root:
526  setdatafolder $datasetname
527  dfref datadf = GetDataFolderDFR()
528  wave /z data
529 
530  setdatafolder $package_path
531  svar s_preview_file
532  svar s_preview_source
533  wave preview_image
534  if (WaveExists(data))
535  s_preview_file = datasetname
536  s_preview_source = ""
537  extract_preview_image(data, preview_image)
538  show_preview_graph(preview_image)
539  else
540  preview_image = nan
541  s_preview_file = datasetname
542  setdatafolder datadf
544  show_preview_graph(preview_image)
545  endif
546 
547  // attributes
548  setdatafolder datadf
549  if (DataFolderExists("attr"))
550  setdatafolder attr
551  preview_attributes(GetDataFolderDFR())
552  else
553  preview_attributes(GetDataFolderDFR(), include_datawaves=0)
554  endif
555 
556  setdatafolder saveDF
557  return 0
558 };
559 
560 static variable preview_datafolder(){
561  // preview data in the current data folder
562  dfref saveDF = GetDataFolderDFR()
563 
564  setdatafolder $package_path
565  svar s_preview_file
566  svar s_preview_source
567  svar s_preview_pvs
568  wave preview_image
569 
570  setdatafolder saveDF
571 
572  // select a wave to display
573  // consider only double-precision waves, i.e. ignore text and other special waves
574  // filter by matching PV name to s_preview_pvs
575  string d_names = WaveList("*", ";", "DP:1")
576  variable nw = ItemsInList(d_names, ";")
577  variable npv = ItemsInList(s_preview_pvs, ";")
578  variable iw, ipv
579  string wname, wnote, pv_name, pv_match
580  for (iw = 0; iw < nw; iw += 1)
581  wname = StringFromList(iw, d_names, ";")
582  wnote = note($wname)
583  pv_name = StringByKey("PV", wnote, "=", "\r")
584  // find matching data wave by PV name
585  for (ipv = 0; ipv < npv; ipv += 1)
586  pv_match = StringFromList(ipv, s_preview_pvs)
587  if (StringMatch(pv_name, pv_match))
588  wave data = $wname
589  s_preview_source = pv_name
590  extract_preview_image(data, preview_image)
591  preview_setscale_x(data, preview_image)
592  npv = 0
593  nw = 0
594  endif
595  endfor
596  endfor
597 
598  setdatafolder saveDF
599 };
600 
601 static variable preview_setscale_x(wave data, wave preview){
602  // sets the approximate x scale of OTF data.
603  // requires an Axis1 tag with name of x wave in the wave note.
604  // if any of these conditions is true, the function does not change the scaling:
605  // 1) Axis1 tag or referenced wave is missing.
606  // 2) preview wave is not set to point scaling.
607  // 3) x wave is not monotonic (90% of the steps in the same direction).
608  wave data
609  wave preview
610 
611  if ((DimOffset(preview, 0) == 0) && (DimDelta(preview, 0) == 1))
612  string xname = StringByKey("Axis1", note(data), "=", "\r")
613  wave /z xwave = $xname
614  if (WaveExists(xwave))
615  // check for monotonicity
616  variable monotonic = 0
617  duplicate /free xwave, xdiff
618  differentiate /p xwave /D=xdiff
619  duplicate /free xdiff, xflag
620  xflag = xdiff > 0
621  monotonic = sum(xflag) > numpnts(xwave) * 0.9
622  xflag = xdiff < 0
623  monotonic = monotonic || (sum(xflag) > numpnts(xwave) * 0.9)
624  if (monotonic)
625  setscale /i x xwave[0], xwave[numpnts(xwave)-1], waveunits(xwave, -1), preview
626  endif
627  endif
628  endif
629 };
630 
631 static variable preview_attributes(dfref attr_folder, dfref dest_folder = defaultValue, wave attr_filter = defaultValue, variable include_datawaves = defaultValue, variable include_infowaves = defaultValue){
632  // copies the first elements of attributes in the specified folder to the preview waves
633  // by default, all existing attributes are copied
634  // if a text wave attr_filter exists in the pear_explorer folder, only the attributes referenced therein are copied
635  // to set up a filter, duplicate the attr_names wave of a template dataset, and remove unwanted items
636  dfref attr_folder// data folder which contains the attribute waves
637  dfref dest_folder// destination folder. the output is written to the attr_names and attr_values waves
638  // default = package folder
639  wave /t attr_filter// list of attributes allowed in the output
640  // default = use attr_filter of package folder
641  variable include_datawaves// 1 (default) = include data waves (any numeric wave which has a PV=name note)
642  // 0 = don't include attributes from data waves
643  variable include_infowaves// 1 (default) = include attributes from info waves (IN, ID, IV, IU)
644  // 0 = don't include attributes from info waves
645 
646  dfref saveDF = GetDataFolderDFR()
647  setdatafolder $package_path
648 
649  if (ParamIsDefault(dest_folder))
650  dest_folder = GetDataFolderDFR()// package folder
651  endif
652  if (ParamIsDefault(attr_filter))
653  wave /t /z attr_filter
654  endif
655  if (ParamIsDefault(include_datawaves))
656  include_datawaves = 1
657  endif
658  if (ParamIsDefault(include_infowaves))
659  include_infowaves = 1
660  endif
661 
662  setdatafolder dest_folder
663  wave /t /z attr_names, attr_values
664  if (!WaveExists(attr_names) || !WaveExists(attr_values))
665  make /n=(1) /o /t attr_names, attr_values
666  endif
667  attr_names = ""
668  attr_values = ""
669 
670  setdatafolder attr_folder
671  wave /t /z IN
672  wave /t /z ID
673  wave /t /z IV
674  wave /t /z IU
675 
676  // compile list of attributes
677  variable nattr// destination attributes
678  variable iattr
679  variable ninfo// info wave elements
680  variable iinfo
681  variable nw// attribute waves
682  variable iw
683  string sw
684  string ss
685 
686  if (WaveExists(IN) && include_infowaves)
687  ninfo = numpnts(IN)
688  else
689  ninfo = 0
690  endif
691  if (include_datawaves)
692  string waves = WaveList("*", ";", "")
693  string exceptions = "ID;IN;IU;IV"
694  waves = RemoveFromList(exceptions, waves)
695  nw = ItemsInList(waves, ";")
696  else
697  nw = 0
698  endif
699 
700  if (WaveExists(attr_filter) && (numpnts(attr_filter) >= 1))
701  nattr = numpnts(attr_filter)
702  redimension /n=(nattr) attr_names
703  attr_names = attr_filter
704  else
705  if(ninfo > 0)
706  redimension /n=(ninfo) attr_names
707  attr_names = SelectString(strlen(ID[p]) >= 0, IN[p], ID[p])// use ID unless empty
708  endif
709 
710  nattr = ninfo + nw
711  iattr = ninfo
712  redimension /n=(nattr) attr_names
713  for (iw = 0; iw < nw; iw +=1 )
714  sw = StringFromList(iw, waves, ";")
715  ss = StringByKey("PV", note($sw), "=", "\r")
716  FindValue /text=sw attr_names
717  if ((v_value < 0) && (strlen(ss) >= 0))
718  attr_names[iattr] = sw
719  iattr += 1
720  endif
721  endfor
722  nattr = iattr
723  endif
724  redimension /n=(nattr) attr_names, attr_values
725  sort attr_names, attr_names
726 
727  // look up attribute values
728  for (iattr = 0; iattr < nattr; iattr += 1)
729  sw = attr_names[iattr]
730  // try info waves
731  if (ninfo > 0)
732  FindValue /text=sw ID
733  if (v_value >= 0)
734  attr_values[iattr] = IV[v_value]
735  endif
736  FindValue /text=sw IN
737  if (v_value >= 0)
738  attr_values[iattr] = IV[v_value]
739  endif
740  endif
741 
742  // override from attribute wave if existent
743  if (nw > 0)
744  switch (WaveType($sw, 1))
745  case 1:// numeric
746  wave /z w = $sw
747  if (WaveExists(w) && (numpnts(w) >= 1))
748  sprintf ss, "%g", w[0]
749  attr_values[iattr] = ss
750  endif
751  break
752  case 2:// text
753  wave /t/z wt = $sw
754  if (WaveExists(wt) && (numpnts(wt) >= 1))
755  attr_values[iattr] = wt[0]
756  endif
757  break
758  endswitch
759  endif
760  endfor
761 
762  setdatafolder saveDF
763 };
764 
765 static variable display_dataset(string datasetname){
766  // displays the graph of a loaded dataset in its own window
767  string datasetname// name of a data folder under root
768 
769  dfref saveDF = GetDataFolderDFR()
770 
771  if (!DataFolderExists("root:" + datasetname))
772  return -1
773  endif
774  setdatafolder root:
775  setdatafolder $datasetname
776  dfref datadf = GetDataFolderDFR()
777  wave /z data
778  if (!WaveExists(data))
779  wave /z data = data1
780  endif
781 
782  if (WaveExists(data))
783  switch(WaveDims(data))
784  case 2:
785  ad_display_profiles(data)
786  break
787  case 3:
788  ad_display_slice(data)
789  ad_brick_slicer(data)
790  break
791  endswitch
792  endif
793 
794  setdatafolder saveDF
795  return 0
796 };
797 
799  dfref df = GetDataFolderDFR()
800  wave /t /sdfr=df attr_names
801  wave /t /sdfr=df attr_values
802  attributes_notebook(attr_names, attr_values, GetDataFolder(0))
803 };
804 
805 static variable attributes_notebook(wave attr_names, wave attr_values, string title){
806  wave /t attr_names
807  wave /t attr_values
808  string title
809 
810  dfref saveDF = GetDataFolderDFR()
811  setdatafolder $package_path
812  wave /t/z attr_filter, attr_filter_summary
813 
814  string name = CleanupName("nb_" + title[0,28], 0)
815  if (WinType(name) == 5)
816  Notebook $name selection={startOfFile, endOfFile}
817  Notebook $name text=""
818  else
819  NewNotebook /F=1 /K=1 /N=$name as title
820  GetWindow $name wsize
821  v_right = v_left + 260
822  v_bottom = v_top + 360
823  MoveWindow /W=$name v_left, v_top, v_right, v_bottom
824  Notebook $name tabs={2*72}
825  endif
826 
827  // summary
828  if (WaveExists(attr_filter_summary) && (numpnts(attr_filter_summary) >= 1))
829  notebook $name fStyle=1, text="Summary\r\r"
830  notebook $name fStyle=0
831  notebook_add_attributes(name, attr_filter_summary, attr_names, attr_values)
832  notebook $name text="\r"
833  endif
834 
835  // all attributes
836  notebook $name fStyle=1, text="All Attributes\r\r"
837  notebook $name fStyle=0
838  notebook_add_attributes(name, $"", attr_names, attr_values)
839  notebook $name selection={startOfFile,startOfFile}, findText={"",1}
840 
841  setdatafolder saveDF
842 };
843 
844 static variable notebook_add_attributes(string notebook_name, wave attr_filter, wave attr_names, wave attr_values){
845  string notebook_name
846  wave /t /z attr_filter
847  wave /t attr_names
848  wave /t attr_values
849 
850  variable nw = numpnts(attr_names)
851  variable iw
852  string sw
853  string ss
854 
855  variable do_filter = WaveExists(attr_filter)
856 
857  for (iw = 0; iw < nw; iw += 1)
858  if (do_filter)
859  sw = attr_names[iw]
860  FindValue /text=sw attr_filter
861  else
862  v_value = 0
863  endif
864  if (v_value >= 0)
865  sprintf ss, "%s\t%s\r", attr_names[iw], attr_values[iw]
866  notebook $notebook_name text=ss
867  endif
868  endfor
869 };
870 
871 static string show_preview_graph(wave data, wave xdata = defaultValue){
872  // displays a preview of one- or two-dimensional data
873  wave data// data to be displayed. must either one-dimensional or two-dimensional
874  wave xdata// positions on x axis
875 
876  dfref saveDF = GetDataFolderDFR()
877  setdatafolder $package_path
878 
879  svar s_profiles_graph
880  svar s_preview_file
881  svar s_preview_source
882  svar s_preview_trace_graph
883 
884  if ((strlen(s_profiles_graph) > 0) && (WinType(s_profiles_graph) == 1))
885  KillWindow $s_profiles_graph
886  endif
887  if ((strlen(s_preview_trace_graph) > 0) && (WinType(s_preview_trace_graph) == 1))
888  KillWindow $s_preview_trace_graph
889  endif
890 
891  string graphname
892  if (wavedims(data) == 2)
893  s_profiles_graph = ad_display_profiles(data)
894  ModifyGraph /w=$s_profiles_graph /z wbRGB=(48640,56832,60160)
895  graphname = s_profiles_graph
896  else if (wavedims(data) == 1)
897  duplicate /o data, preview_trace
898  if (!ParamIsDefault(xdata))
899  duplicate /o xdata, preview_trace_x
900  else
901  duplicate /o data, preview_trace_x
902  preview_trace_x = x
903  setscale d 0, 0, WaveUnits(data, 0), preview_trace_x
904  endif
905  s_preview_trace_graph = display_preview_trace(preview_trace_x, preview_trace)
906  ModifyGraph /w=$s_preview_trace_graph wbRGB=(48640,56832,60160)
907  graphname = s_preview_trace_graph
908  else
909  return ""
910  endif
911 
912  string title = "Preview " + s_preview_file
913  if (strlen(s_preview_source) > 0)
914  title = title + " (" + s_preview_source[0,31] + ")"
915  endif
916  dowindow /f/t $graphname, title
917 
918  setdatafolder saveDF
919  return graphname
920 };
921 
922 static string display_preview_trace(wave xtrace, wave ytrace){
923  wave xtrace
924  wave ytrace
925 
926  display /n=pearl_explorer_1d /k=1 ytrace vs xtrace as "Preview"
927  string graphname = s_name
928  ModifyGraph /w=$graphname rgb[0]=(0,0,0)
929  ModifyGraph /w=$graphname grid=2
930  ModifyGraph /w=$graphname mirror=1
931  ModifyGraph /w=$graphname minor=1
932  ModifyGraph /w=$graphname axThick=0.5
933  ModifyGraph /w=$graphname gridRGB=(52224,52224,52224)
934  ModifyGraph /w=$graphname gridHair=0
935  ModifyGraph /w=$graphname tick=0
936  ModifyGraph /w=$graphname btLen=4
937 
938  // axis labels
939  string labels = note(ytrace)
940  string lab
941  lab = StringByKey("AxisLabelX", labels, "=", "\r")
942  if (!strlen(lab))
943  lab = "X"
944  endif
945  Label /w=$graphname bottom lab + " (\\U)"
946  lab = StringByKey("AxisLabelD", labels, "=", "\r")
947  if (!strlen(lab))
948  lab = "value"
949  endif
950  Label /w=$graphname left lab + " (\\U)"
951 
952  return s_name
953 };
954 
955 static variable load_selected_files(string options = defaultValue){
956  string options
957 
958  dfref saveDF = GetDataFolderDFR()
959  setdatafolder $package_path
960 
961  wave wSelectedFiles
962  wave/t wtFiles
963  variable nn = numpnts(wSelectedFiles)
964  variable ii
965  for (ii = 0; ii < nn; ii += 1)
966  if (wSelectedFiles[ii])
967  if (ParamIsDefault(options))
968  load_file(wtFiles[ii])
969  else
970  load_file(wtFiles[ii], options=options)
971  endif
972  endif
973  endfor
974 
976  setdatafolder saveDF
977 };
978 
979 static variable load_file(string filename, string options = defaultValue){
980  string filename
981  string options
982 
983  dfref saveDF = GetDataFolderDFR()
984 
985  variable ft = pearl_file_type(filename)
986  switch(ft)
987  case 1:
988  if (ParamIsDefault(options))
989  load_pshell_file(filename)
990  else
991  load_pshell_file(filename, options=options)
992  endif
993  break
994  case 2:
995  if (ParamIsDefault(options))
996  load_hdf_file(filename)
997  else
998  load_hdf_file(filename, options=options)
999  endif
1000  break
1001  case 3:
1002  load_itx_file(filename)
1003  break
1004  case 4:
1005  load_mtrx_file(filename)
1006  break
1007  default:
1008  break
1009  endswitch
1010 
1011  setdatafolder saveDF
1012 };
1013 
1014 static variable prompt_hdf_options(string* options){
1015  string &options
1016 
1017  string mode = StringByKey("mode", options, ":", ";")
1018  string reduction_func = StringByKey("reduction_func", options, ":", ";")
1019 
1020  string modes = "load_reduced"
1021  string reduction_functions = adh5_list_reduction_funcs()
1022 
1023  if (strlen(mode) == 0)
1024  mode = StringFromList(0, modes, ";")
1025  endif
1026  if (strlen(reduction_func) == 0)
1027  reduction_func = StringFromList(0, reduction_functions, ";")
1028  endif
1029 
1030  prompt mode, "Mode", popup, modes
1031  prompt reduction_func, "Reduction Function", popup, reduction_functions
1032  doprompt "HDF5 Loading Options", mode, reduction_func
1033 
1034  if (v_flag == 0)
1035  options = ReplaceStringByKey("mode", options, mode, ":", ";")
1036  options = ReplaceStringByKey("reduction_func", options, reduction_func, ":", ";")
1037  endif
1038  return v_flag// 0 = OK, 1 = cancel
1039 };
1040 
1053 variable prompt_default_process(string* param){
1054  string &param
1055 
1056  return 0
1057 };
1058 
1059 variable prompt_func_params(string func_name, string* func_param){
1060  string func_name
1061  string &func_param
1062 
1063  string prompt_name = "prompt_" + func_name
1064  if (exists(prompt_name) == 6)
1065  funcref prompt_default_process prompt_func = $prompt_name
1066  return prompt_func(func_param)
1067  else
1068  // ignore missing prompt function
1069  return 0
1070  endif
1071 };
1072 
1073 static dfr load_pshell_file(string filename, string options = defaultValue){
1074  string filename
1075  string options
1076 
1077  dfref saveDF = GetDataFolderDFR()
1078  string nickname = ad_suggest_foldername(filename)
1079  string loaded_filename = ""
1080 
1081  if (ParamIsDefault(options))
1082  loaded_filename = psh5_load_complete(nickname, "pearl_explorer_filepath", filename)
1083  else
1084  if (strlen(options) == 0)
1085  svar pref_options = $(package_path + "s_hdf_options")
1086  options = pref_options
1087  if (prompt_hdf_options(options) == 0)
1088  // OK
1089  pref_options = options
1090  else
1091  // cancel
1092  options = ""
1093  endif
1094  endif
1095 
1096  string mode = StringByKey("mode", options, ":", ";")
1097 
1098  strswitch(mode)
1099  case "load_reduced":
1100  string reduction_func = StringByKey("reduction_func", options, ":", ";")
1101  svar pref_params = $(package_path + "s_reduction_params")
1102  string reduction_params = pref_params
1103  if (prompt_func_params(reduction_func, reduction_params) == 0)
1104  pref_params = reduction_params
1105  print reduction_func, reduction_params
1106  psh5_load_reduced(nickname, "pearl_explorer_filepath", filename, $reduction_func, reduction_params)
1107  svar s_filepath
1108  loaded_filename = s_filepath
1109  endif
1110  break
1111  endswitch
1112  endif
1113 
1114  dfref dataDF
1115  if (strlen(loaded_filename) > 0)
1116  setdatafolder $("root:" + nickname)
1117  dataDF = GetDataFolderDFR()
1118  string /g pearl_explorer_import = "load_pshell_file"
1119  endif
1120 
1121  setdatafolder saveDF
1122  return dataDF
1123 };
1124 
1125 static dfr load_hdf_file(string filename, string options = defaultValue){
1126  string filename
1127  string options
1128 
1129  dfref saveDF = GetDataFolderDFR()
1130  string nickname = ad_suggest_foldername(filename)
1131  string loaded_filename = ""
1132 
1133  if (ParamIsDefault(options))
1134  loaded_filename = adh5_load_complete(nickname, "pearl_explorer_filepath", filename)
1135  else
1136  if (strlen(options) == 0)
1137  svar pref_options = $(package_path + "s_hdf_options")
1138  options = pref_options
1139  if (prompt_hdf_options(options) == 0)
1140  // OK
1141  pref_options = options
1142  else
1143  // cancel
1144  options = ""
1145  endif
1146  endif
1147 
1148  string mode = StringByKey("mode", options, ":", ";")
1149 
1150  strswitch(mode)
1151  case "load_reduced":
1152  string reduction_func = StringByKey("reduction_func", options, ":", ";")
1153  svar pref_params = $(package_path + "s_reduction_params")
1154  string reduction_params = pref_params
1155  if (prompt_func_params(reduction_func, reduction_params) == 0)
1156  pref_params = reduction_params
1157  print reduction_func, reduction_params
1158  loaded_filename = adh5_load_reduced(nickname, "pearl_explorer_filepath", filename, $reduction_func, reduction_params)
1159  endif
1160  break
1161  endswitch
1162  endif
1163 
1164  dfref dataDF
1165  if (strlen(loaded_filename) > 0)
1166  setdatafolder $("root:" + nickname)
1167  dataDF = GetDataFolderDFR()
1168  string /g pearl_explorer_import = "load_hdf_file"
1169  endif
1170 
1171  setdatafolder saveDF
1172  return dataDF
1173 };
1174 
1175 static dfr load_itx_file(string filename, string options = defaultValue){
1176  string filename
1177  string options
1178 
1179  dfref saveDF = GetDataFolderDFR()
1180  string nickname = itx_suggest_foldername(filename)
1181 
1182  if (ParamIsDefault(options))
1183  options = ""
1184  endif
1185 
1186  setdatafolder root:
1187  newdatafolder /s/o $("root:" + nickname)
1188  dfref dataDF = GetDataFolderDFR()
1189 
1190  // note: some versions of PEARL data files save data to a new data folder,
1191  // and leave the newly created folder as the current folder.
1192  // the free data folder is used by those files which don't create their own data folder.
1193  // this is the new recommended behaviour
1194 
1195  LoadWave /t/p=pearl_explorer_filepath/q filename
1196  svar waves = s_wavenames
1197  dfref actDF = GetDataFolderDFR()
1198  if (v_flag > 0)
1199  string /g pearl_explorer_import = "load_itx_file"
1200  endif
1201 
1202  if (!DataFolderRefsEqual(actDF, dataDF))
1203  // the file created its own data folder.
1204  // let's kill the pre-allocated folder
1205  setdatafolder dataDF
1206  if (ItemsInList(WaveList("*", ";", ""), ";") == 0)
1207  killdatafolder /z dataDF
1208  endif
1209  endif
1210 
1211  setdatafolder saveDF
1212  return actDF
1213 };
1214 
1218 static dfr load_mtrx_file(string filename, string options = defaultValue){
1219  string filename
1220  string options
1221 
1222  dfref saveDF = GetDataFolderDFR()
1223  dfref dataDF = $""
1224 
1225 #if exists("MFR_OpenResultFile")
1226  setdatafolder root:
1227  string datasets = ""
1228  datasets = mtrx_load_file("pearl_explorer_filepath", filename)
1229  if (strlen(datasets) > 0)
1230  string /g pearl_explorer_import = "load_mtrx_file"
1231  string s1 = StringFromList(0, datasets)
1232  wave w1 = $s1
1233  dataDF = GetWavesDataFolderDFR(w1)
1234  endif
1235 #endif
1236 
1237  setdatafolder saveDF
1238  return dataDF
1239 };
1240 
1241 string itx_suggest_foldername(string filename, variable ignoredate = defaultValue, string sourcename = defaultValue, variable unique = defaultValue){
1242  // suggests the name of a data folder based on a file name
1243  // if the file name follows the naming convention source-date-index.extension,
1244  // the function tries to generate the nick name as source_date_index.
1245  // otherwise it's just a cleaned up version of the file name.
1246  string filename// file name, including extension. can also include a folder path (which is ignored)
1247  // the extension is currently ignored, but may be used later to select the parent folder
1248  variable ignoredate// if non-zero, the nick name will not include the date part
1249  // defaults to zero
1250  string sourcename// nick name of the data source
1251  // the function tries to detect the source from the file name
1252  // this option can be used to override auto-detection
1253  // allowed values: sscan, otf
1254  variable unique// if non-zero, the resulting name is made a unique data folder name in the current data folder
1255  // defaults to zero
1256 
1257  if (ParamIsDefault(ignoredate))
1258  ignoredate = 0
1259  endif
1260  if (ParamIsDefault(unique))
1261  unique = 0
1262  endif
1263 
1264  string basename = ParseFilePath(3, filename, ":", 0, 0)
1265  string extension = ParseFilePath(4, filename, ":", 0, 0)
1266  string nickname
1267 
1268  string autosource
1269  if (strsearch(basename, "X03DA_PC", 0, 2) >= 0)
1270  autosource = "sscan"
1271  basename = ReplaceString("_", basename, "-")
1272  ignoredate = 1
1273  else if (strsearch(basename, "otf", 0, 2) >= 0)
1274  autosource = "otf"
1275  endif
1276  if (ParamIsDefault(sourcename))
1277  sourcename = autosource
1278  endif
1279 
1280  variable nparts = ItemsInList(basename, "-")
1281  if (nparts >= 3)
1282  string datepart = StringFromList(nparts - 2, basename, "-")
1283  string indexpart = StringFromList(nparts - 1, basename, "-")
1284  if (ignoredate)
1285  sprintf nickname, "%s_%s", sourcename, indexpart
1286  else
1287  sprintf nickname, "%s_%s_%s", sourcename, datepart, indexpart
1288  endif
1289  else
1290  nickname = CleanupName(basename, 0)
1291  endif
1292 
1293  if (unique && CheckName(nickname, 11))
1294  nickname = UniqueName(nickname + "_", 11, 0)
1295  endif
1296 
1297  return nickname
1298 };
1299 
1301  PauseUpdate; Silent 1// building window...
1302  NewPanel /K=1 /W=(800,0,1530,444) as "PEARL Data Explorer"
1303  ModifyPanel cbRGB=(48640,56832,60160)
1304 
1305  GroupBox gb_filepath,pos={8,4},size={224,52},title="file system folder"
1306  TitleBox tb_filepath,pos={20,24},size={174,20},frame=2
1307  TitleBox tb_filepath,variable=root:packages:pearl_explorer:s_filepath,fixedSize=1
1308  Button b_browse_filepath,pos={200,24},size={20,20},proc=PearlDataExplorer#bp_browse_filepath,title="..."
1309  Button b_browse_filepath,fColor=(65280,48896,32768)
1310 
1311  GroupBox gb_prefs,pos={240,4},size={58,52},title="prefs",help={"explorer package preferences"}
1312  Button b_save_prefs,pos={252,20},size={32,17},proc=PearlDataExplorer#bp_save_prefs,title="save"
1313  Button b_save_prefs,help={"save preferences of the data explorer package (data file path, attributes filter)"}
1314  Button b_save_prefs,fColor=(65280,48896,32768)
1315  Button b_load_prefs,pos={252,36},size={32,17},proc=PearlDataExplorer#bp_load_prefs,title="load"
1316  Button b_load_prefs,help={"load preferences of the data explorer package"}
1317  Button b_load_prefs,fColor=(65280,48896,32768)
1318 
1319  GroupBox gb_filelist,pos={8,64},size={224,372},title="data files"
1320  ListBox lb_files,pos={20,84},size={200,212},proc=PearlDataExplorer#lbp_filelist
1321  ListBox lb_files,listWave=root:packages:pearl_explorer:wtFiles
1322  ListBox lb_files,selWave=root:packages:pearl_explorer:wSelectedFiles,row= 11,mode= 4
1323  TitleBox tb_file_info,pos={20,300},size={198,78},frame=2,fixedSize=1
1324  TitleBox tb_file_info,variable= root:packages:pearl_explorer:s_file_info
1325 
1326  Button b_update_filelist,pos={20,386},size={60,20},proc=PearlDataExplorer#bp_update_filelist,title="update list"
1327  Button b_update_filelist,fColor=(65280,48896,32768)
1328  CheckBox cb_file_preview,pos={84,390},size={60,20},title="preview"
1329  CheckBox cb_file_preview,help={"enable/disable automatic preview window when selecting a data file"}
1330  CheckBox cb_file_preview,value=1
1331  Button b_file_prev,pos={176,386},size={20,20},proc=PearlDataExplorer#bp_file_prev,title="\\W646"
1332  Button b_file_prev,help={"previous file"}
1333  Button b_file_prev,fColor=(65280,48896,32768)
1334  Button b_file_next,pos={200,386},size={20,20},proc=PearlDataExplorer#bp_file_next,title="\\W649"
1335  Button b_file_next,help={"next file"}
1336  Button b_file_next,fColor=(65280,48896,32768)
1337 
1338  Button b_load_files,pos={20,410},size={76,20},proc=PearlDataExplorer#bp_load_files,title="load complete"
1339  Button b_load_files,help={"load the complete contents from the selected files"}
1340  Button b_load_files,fColor=(65280,48896,32768)
1341  Button b_load_files_opt,pos={100,410},size={76,20},proc=PearlDataExplorer#bp_load_files_opt,title="load reduced"
1342  Button b_load_files_opt,help={"load data from the selected files with options (reduced dimensions)"}
1343  Button b_load_files_opt,fColor=(65280,48896,32768)
1344 
1345  // datasets group
1346  GroupBox gb_datasets,pos={240,64},size={224,372},title="datasets"
1347  ListBox lb_datasets,pos={252,84},size={200,300},proc=PearlDataExplorer#lbp_datasets,help={"list of loaded datasets"}
1348  ListBox lb_datasets,listWave=root:packages:pearl_explorer:wtDatasets
1349  ListBox lb_datasets,selWave=root:packages:pearl_explorer:wSelectedDatasets,mode= 1
1350  ListBox lb_datasets,selRow= -1
1351 
1352  Button b_update_datasets,pos={252,386},size={60,20},proc=PearlDataExplorer#bp_update_datasets,title="update list"
1353  Button b_update_datasets,help={"update the list of datasets"}
1354  Button b_update_datasets,fColor=(65280,48896,32768)
1355  CheckBox cb_dataset_preview,pos={316,390},size={60,20},title="preview"
1356  CheckBox cb_dataset_preview,help={"enable/disable automatic preview window when selecting a dataset"}
1357  CheckBox cb_dataset_preview,value=0
1358  Button b_dataset_prev,pos={408,386},size={20,20},proc=PearlDataExplorer#bp_dataset_prev,title="\\W646"
1359  Button b_dataset_prev,help={"goto previous dataset"}
1360  Button b_dataset_prev,fColor=(65280,48896,32768)
1361  Button b_dataset_next,pos={432,386},size={20,20},proc=PearlDataExplorer#bp_dataset_next,title="\\W649"
1362  Button b_dataset_next,help={"goto next dataset"}
1363  Button b_dataset_next,fColor=(65280,48896,32768)
1364 
1365  Button b_dataset_folder,pos={252,410},size={50,20},proc=PearlDataExplorer#bp_dataset_folder,title="goto DF"
1366  Button b_dataset_folder,help={"set the current data folder of the selected dataset"}
1367  Button b_dataset_folder,fColor=(65280,48896,32768)
1368  Button b_dataset_display,pos={306,410},size={50,20},proc=PearlDataExplorer#bp_dataset_display,title="display"
1369  Button b_dataset_display,help={"display the selected dataset in its own window"}
1370  Button b_dataset_display,fColor=(65280,48896,32768)
1371 
1372  GroupBox gb_preview,pos={472,4},size={250,52},title="preview"
1373  TitleBox tb_preview_file,pos={484,24},size={226,20},frame=2
1374  TitleBox tb_preview_file,variable=root:packages:pearl_explorer:s_preview_file,fixedSize=1
1375 
1376  GroupBox gb_attributes,pos={472,64},size={250,372},title="attributes"
1377  Button b_attr_notebook,pos={484,386},size={60,20},proc=PearlDataExplorer#bp_attr_notebook,title="notebook"
1378  Button b_attr_notebook,help={"show attribute list in a notebook"}
1379  Button b_attr_notebook,fColor=(65280,48896,32768)
1380 
1381  String fldrSav0= GetDataFolder(1)
1382  SetDataFolder root:packages:pearl_explorer:
1383  Edit/W=(484,84,710,384)/HOST=# attr_names,attr_values
1384  ModifyTable format(Point)=1,width(Point)=0,width(attr_names)=103,width(attr_values)=103
1385  ModifyTable statsArea=85
1386  SetDataFolder fldrSav0
1387  RenameWindow #,T0
1388  SetActiveSubwindow ##
1389 };
1390 
1391 static variable bp_load_prefs(WMButtonAction* ba){
1392  STRUCT WMButtonAction &ba
1393 
1394  switch( ba.eventCode )
1395  case 2:// mouse up
1396  load_prefs()
1397  break
1398  case -1:// control being killed
1399  break
1400  endswitch
1401 
1402  return 0
1403 };
1404 
1405 static variable bp_save_prefs(WMButtonAction* ba){
1406  STRUCT WMButtonAction &ba
1407 
1408  switch( ba.eventCode )
1409  case 2:// mouse up
1410  save_prefs()
1411  break
1412  case -1:// control being killed
1413  break
1414  endswitch
1415 
1416  return 0
1417 };
1418 
1419 static variable bp_browse_filepath(WMButtonAction* ba){
1420  STRUCT WMButtonAction &ba
1421 
1422  dfref saveDF = GetDataFolderDFR()
1423 
1424  switch( ba.eventCode )
1425  case 2:// mouse up
1426  PathInfo /S pearl_explorer_filepath
1427  NewPath /M="select data file folder" /O/Z pearl_explorer_filepath
1428  if (v_flag == 0)
1429  PathInfo /S pearl_explorer_filepath
1430  svar filepath = $(package_path + "s_filepath")
1431  filepath = s_path
1432  update_filelist()
1433  endif
1434  break
1435  case -1:// control being killed
1436  break
1437  endswitch
1438 
1439  setdatafolder saveDF
1440  return 0
1441 };
1442 
1443 static variable bp_update_filelist(WMButtonAction* ba){
1444  STRUCT WMButtonAction &ba
1445 
1446  switch( ba.eventCode )
1447  case 2:// mouse up
1448  update_filelist()
1449  break
1450  case -1:// control being killed
1451  break
1452  endswitch
1453 
1454  return 0
1455 };
1456 
1457 static variable bp_load_files(WMButtonAction* ba){
1458  STRUCT WMButtonAction &ba
1459 
1460  switch( ba.eventCode )
1461  case 2:// mouse up
1463  break
1464  case -1:// control being killed
1465  break
1466  endswitch
1467 
1468  return 0
1469 };
1470 
1471 static variable bp_load_files_opt(WMButtonAction* ba){
1472  STRUCT WMButtonAction &ba
1473 
1474  switch( ba.eventCode )
1475  case 2:// mouse up
1476  load_selected_files(options="")
1477  break
1478  case -1:// control being killed
1479  break
1480  endswitch
1481 
1482  return 0
1483 };
1484 
1485 static variable bp_file_next(WMButtonAction* ba){
1486  STRUCT WMButtonAction &ba
1487 
1488  dfref saveDF = GetDataFolderDFR()
1489 
1490  switch( ba.eventCode )
1491  case 2:// mouse up
1492  setdatafolder $package_path
1493  wave /t wtFiles
1494  wave wSelectedFiles
1495  FindValue /i=1 wSelectedFiles
1496  v_value += 1
1497  if (v_value >= numpnts(wtFiles))
1498  v_value = min(numpnts(wtFiles) - 1, 0)
1499  endif
1500  wSelectedFiles = p == v_value
1501  if (v_value >= 0)
1502  variable ifile = v_value
1503  ControlInfo /W=PearlDataExplorer cb_file_preview
1504  if (v_value)
1505  preview_file(wtFiles[ifile])
1506  endif
1507  endif
1508  break
1509  case -1:// control being killed
1510  break
1511  endswitch
1512 
1513  setdatafolder saveDF
1514  return 0
1515 };
1516 
1517 static variable bp_file_prev(WMButtonAction* ba){
1518  STRUCT WMButtonAction &ba
1519 
1520  dfref saveDF = GetDataFolderDFR()
1521 
1522  switch( ba.eventCode )
1523  case 2:// mouse up
1524  setdatafolder $package_path
1525  wave /t wtFiles
1526  wave wSelectedFiles
1527  FindValue /i=1 wSelectedFiles
1528  v_value -= 1
1529  if (v_value < 0)
1530  v_value = numpnts(wtFiles) - 1
1531  endif
1532  wSelectedFiles = p == v_value
1533  if (v_value >= 0)
1534  variable ifile = v_value
1535  ControlInfo /W=PearlDataExplorer cb_file_preview
1536  if (v_value)
1537  preview_file(wtFiles[ifile])
1538  endif
1539  endif
1540  break
1541  case -1:// control being killed
1542  break
1543  endswitch
1544 
1545  setdatafolder saveDF
1546  return 0
1547 };
1548 
1549 static variable lbp_filelist(WMListboxAction* lba){
1550  STRUCT WMListboxAction &lba
1551 
1552  Variable row = lba.row
1553  Variable col = lba.col
1554  WAVE/T/Z listWave = lba.listWave
1555  WAVE/Z selWave = lba.selWave
1556 
1557  switch( lba.eventCode )
1558  case -1:// control being killed
1559  break
1560  case 1:// mouse down
1561  if (selWave[row])
1562  ControlInfo /W=PearlDataExplorer cb_file_preview
1563  if (v_value)
1564  preview_file(listWave[row])
1565  endif
1566  endif
1567  break
1568  case 3:// double click
1569  break
1570  case 4:// cell selection
1571  case 5:// cell selection plus shift key
1572  break
1573  case 6:// begin edit
1574  break
1575  case 7:// finish edit
1576  break
1577  case 13:// checkbox clicked (Igor 6.2 or later)
1578  break
1579  endswitch
1580 
1581  return 0
1582 };
1583 
1584 static variable bp_update_datasets(WMButtonAction* ba){
1585  STRUCT WMButtonAction &ba
1586 
1587  switch( ba.eventCode )
1588  case 2:// mouse up
1589  update_datasets()
1590  break
1591  case -1:// control being killed
1592  break
1593  endswitch
1594 
1595  return 0
1596 };
1597 
1598 static variable bp_dataset_folder(WMButtonAction* ba){
1599  STRUCT WMButtonAction &ba
1600 
1601  switch( ba.eventCode )
1602  case 2:// mouse up
1603  ControlInfo /W=PearlDataExplorer lb_datasets
1604  if (v_value >= 0)
1605  setdatafolder $package_path
1606  wave /t wtDatasets
1607  string dataset = wtDatasets[v_value]
1608  string cmd
1609  sprintf cmd, "setdatafolder root:%s", PossiblyQuoteName(dataset)
1610  execute /q /z cmd
1611  cmd = "setdatafolder :scan1"
1612  execute /q /z cmd
1613  sprintf cmd, "setdatafolder %s", GetDataFolder(1)
1614  print cmd
1615  endif
1616  break
1617  case -1:// control being killed
1618  break
1619  endswitch
1620 
1621  return 0
1622 };
1623 
1624 static variable bp_dataset_display(WMButtonAction* ba){
1625  STRUCT WMButtonAction &ba
1626 
1627  switch( ba.eventCode )
1628  case 2:// mouse up
1629  ControlInfo /W=PearlDataExplorer lb_datasets
1630  if (v_value >= 0)
1631  setdatafolder $package_path
1632  wave /t wtDatasets
1633  string dataset = wtDatasets[v_value]
1634  display_dataset(dataset)
1635  endif
1636  break
1637  case -1:// control being killed
1638  break
1639  endswitch
1640 
1641  return 0
1642 };
1643 
1644 static variable bp_dataset_next(WMButtonAction* ba){
1645  STRUCT WMButtonAction &ba
1646 
1647  switch( ba.eventCode )
1648  case 2:// mouse up
1649  ControlInfo /W=PearlDataExplorer lb_datasets
1650  wave /t wtDatasets = $(s_datafolder + s_value)
1651  v_value += 1
1652  if (v_value >= numpnts(wtDatasets))
1653  v_value = min(0, numpnts(wtDatasets) - 1)
1654  endif
1655  ListBox lb_datasets win=PearlDataExplorer, selRow=v_value
1656  if (v_value >= 0)
1657  variable ids = v_value
1658  ControlInfo /W=PearlDataExplorer cb_dataset_preview
1659  if (v_value)
1660  preview_dataset(wtDatasets[ids])
1661  endif
1662  endif
1663  break
1664  case -1:// control being killed
1665  break
1666  endswitch
1667 
1668  return 0
1669 };
1670 
1671 static variable bp_dataset_prev(WMButtonAction* ba){
1672  STRUCT WMButtonAction &ba
1673 
1674  switch( ba.eventCode )
1675  case 2:// mouse up
1676  ControlInfo /W=PearlDataExplorer lb_datasets
1677  wave /t wtDatasets = $(s_datafolder + s_value)
1678  v_value -= 1
1679  if (v_value < 0)
1680  v_value = max(-1, numpnts(wtDatasets) - 1)
1681  endif
1682  ListBox lb_datasets win=PearlDataExplorer, selRow=v_value
1683  if (v_value >= 0)
1684  variable ids = v_value
1685  ControlInfo /W=PearlDataExplorer cb_dataset_preview
1686  if (v_value)
1687  preview_dataset(wtDatasets[ids])
1688  endif
1689  endif
1690  break
1691  case -1:// control being killed
1692  break
1693  endswitch
1694 
1695  return 0
1696 };
1697 
1698 static variable lbp_datasets(WMListboxAction* lba){
1699  STRUCT WMListboxAction &lba
1700 
1701  Variable row = lba.row
1702  Variable col = lba.col
1703  WAVE/T/Z listWave = lba.listWave
1704  WAVE/Z selWave = lba.selWave
1705 
1706  switch( lba.eventCode )
1707  case -1:// control being killed
1708  break
1709  case 1:// mouse down
1710  if (row >= 0)
1711  ControlInfo /W=PearlDataExplorer cb_dataset_preview
1712  if (v_value)
1713  preview_dataset(listWave[row])
1714  endif
1715  endif
1716  break
1717  case 3:// double click
1718  break
1719  case 4:// cell selection
1720  case 5:// cell selection plus shift key
1721  break
1722  case 6:// begin edit
1723  break
1724  case 7:// finish edit
1725  break
1726  case 13:// checkbox clicked (Igor 6.2 or later)
1727  break
1728  endswitch
1729 
1730  return 0
1731 };
1732 
1733 static variable bp_attr_notebook(WMButtonAction* ba){
1734  STRUCT WMButtonAction &ba
1735 
1736  dfref saveDF = GetDataFolderDFR()
1737 
1738  switch( ba.eventCode )
1739  case 2:// mouse up
1740  setdatafolder $package_path
1741  svar s_preview_file
1742  wave /t /z attr_names
1743  wave /t /z attr_values
1744  if (WaveExists(attr_names))
1745  attributes_notebook(attr_names, attr_values, s_preview_file)
1746  endif
1747  break
1748  case -1:// control being killed
1749  break
1750  endswitch
1751 
1752  setdatafolder saveDF
1753  return 0
1754 };
1755 
static dfr load_mtrx_file(string filename, string options=defaultValue)
load a matrix (STM) data file
-
static const string package_path
-
string adh5_load_preview(string ANickName, string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue)
load a single image from a HDF5 file created by the Area Detector software.
-
static variable update_datasets()
-
string psh5_load_reduced(string ANickName, string APathName, string AFileName, funcref reduction_func, string reduction_param, variable progress=defaultValue, variable nthreads=defaultValue)
load and reduce the ScientaImage dataset of the first scan of a PShell data file. ...
-
static variable bp_browse_filepath(WMButtonAction *ba)
-
static variable preview_file(string filename)
-
variable prompt_default_process(string *param)
prototype for prompting for processing function parameters.
-
string adh5_load_info(string APathName, string AFileName)
load descriptive info from a HDF5 file created by the Area Detector software.
-
static variable bp_dataset_prev(WMButtonAction *ba)
-
static string display_preview_trace(wave xtrace, wave ytrace)
-
static variable bp_file_prev(WMButtonAction *ba)
-
variable ad_brick_slicer(wave data)
open a slicer panel for 3D data.
-
static variable lbp_datasets(WMListboxAction *lba)
-
void PearlDataExplorer()
-
static variable bp_load_files_opt(WMButtonAction *ba)
-
static variable load_selected_files(string options=defaultValue)
-
static variable bp_load_files(WMButtonAction *ba)
-
static variable preview_datafolder()
-
static variable bp_file_next(WMButtonAction *ba)
-
static variable lbp_filelist(WMListboxAction *lba)
-
static variable prompt_hdf_options(string *options)
-
static variable bp_update_datasets(WMButtonAction *ba)
-
static const string ks_filematch_pshell
-
static const string ks_filematch_adh5
-
static wave preview_mtrx_file(string filename)
load the preview of a Matrix STM file.
-
static variable init_package()
initialize the global variables of the data explorer.
-
static wave preview_pshell_file(string filename)
load the preview of a PShell HDF5 file.
-
static variable bp_dataset_folder(WMButtonAction *ba)
-
static variable preview_dataset(string datasetname)
-
static const string package_name
-
static variable update_filelist()
read a list of PEARL files from the file system
-
static dfr load_itx_file(string filename, string options=defaultValue)
-
string psh5_load_preview(string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue, string pref_scans=defaultValue, string pref_datasets=defaultValue)
load a preview image from a PShell data file.
-
static variable bp_attr_notebook(WMButtonAction *ba)
-
static variable load_file(string filename, string options=defaultValue)
-
preview and import panel for PEARL data
-
static variable bp_load_prefs(WMButtonAction *ba)
-
static variable preview_setscale_x(wave data, wave preview)
-
static variable bp_save_prefs(WMButtonAction *ba)
-
static dfr load_hdf_file(string filename, string options=defaultValue)
-
string ad_suggest_foldername(string filename, variable ignoredate=defaultValue, string sourcename=defaultValue, variable unique=defaultValue)
generate the name of a data folder based on a file name.
-
static wave preview_hdf_file(string filename)
load the preview of a PEARL HDF5 file.
-
static variable pearl_file_type(string filename)
check whether a file can be imported by this module.
-
static variable bp_dataset_display(WMButtonAction *ba)
-
static const string ks_filematch_itx
-
string adh5_load_complete(string ANickName, string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue)
import everything from a HDF5 file created by the Area Detector software.
-
static variable bp_dataset_next(WMButtonAction *ba)
-
static variable extract_preview_image(wave data, wave preview)
-
string psh5_load_info(string APathName, string AFileName)
load descriptive info from a PShell data file.
-
string adh5_load_reduced(string ANickName, string APathName, string AFileName, funcref reduction_func, string reduction_param, variable load_data=defaultValue, variable load_attr=defaultValue, variable progress=defaultValue)
load and reduce a dataset from a HDF5 file created by the Area Detector software. ...
-
string ad_display_profiles(wave image, string filter=defaultValue)
open a new profiles graph window.
-
static variable bp_update_filelist(WMButtonAction *ba)
-
variable pearl_data_explorer()
-
string itx_suggest_foldername(string filename, variable ignoredate=defaultValue, string sourcename=defaultValue, variable unique=defaultValue)
-
string psh5_load_complete(string ANickName, string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue)
load everything from a PShell data file.
-
static variable load_prefs()
-
variable prompt_func_params(string func_name, string *func_param)
-
static wave preview_itx_file(string filename)
-
static variable display_dataset(string datasetname)
-
static dfr load_pshell_file(string filename, string options=defaultValue)
-
static variable save_prefs()
-
variable test_attributes_notebook()
-
static string show_preview_graph(wave data, wave xdata=defaultValue)
-
string mtrx_load_preview(string destName, string pathName, string fileName, string traces=defaultValue)
load a preview image from a Matrix data file.
-
string ad_display_slice(wave data)
display three-dimensional data by 2D slice.
-
static const string ks_filematch_mtrx
-
static variable attributes_notebook(wave attr_names, wave attr_values, string title)
-
string mtrx_load_file(string pathName, string fileName, string traces=defaultValue)
load all data from a Matrix data file.
-
static variable preview_attributes(dfref attr_folder, dfref dest_folder=defaultValue, wave attr_filter=defaultValue, variable include_datawaves=defaultValue, variable include_infowaves=defaultValue)
-
string adh5_list_reduction_funcs()
get a list of functions which can be used as reduction functions.
-
static variable notebook_add_attributes(string notebook_name, wave attr_filter, wave attr_names, wave attr_values)
-
threadsafe wave ad_extract_slab(wave dataset, variable x1, variable x2, variable y1, variable y2, variable z1, variable z2, string destname, variable noavg=defaultValue, variable pscale=defaultValue)
2D cut through 3D dataset, integrate in normal dimension
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-elog_8ipf.html b/doc/html/pearl-elog_8ipf.html index 13c357e..013d305 100644 --- a/doc/html/pearl-elog_8ipf.html +++ b/doc/html/pearl-elog_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-elog.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
-
pearl-elog.ipf File Reference
+
pearl-elog.ipf File Reference
-

interface for writing ELOG entries with Igor graphs as attachment. -More...

-

Go to the source code of this file.

- - - - - -

-Namespaces

 PearlElog
 interface for writing ELOG entries with Igor graphs as attachment.
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

variable pearl_elog (string logbook)
 main function to initialize ELOG and to open an ELOG panel. More...
 
static variable IgorBeforeNewHook (string igorApplicationNameStr)
 save preferences and recent values before Igor opens a new experiment. More...
 
static variable IgorQuitHook (string igorApplicationNameStr)
 save preferences and recent values before Igor quits. More...
 
static variable AfterFileOpenHook (variable refNum, string file, string pathName, string type, string creator, variable kind)
 initialize the package and reload preferences after an experiment is loaded. More...
 
static dfr get_elog_df (string name, variable category)
 get the package, logbook, or template datafolder. More...
 
static variable init_package (variable clean=defaultValue)
 initialize the package data folder. More...
 
variable elog_init_pearl_templates ()
 setup PEARL template logbooks. More...
 
static variable init_volatile_vars ()
 initialize volatile variables. More...
 
variable elog_create_logbook (string name, string template=defaultValue)
 create a new logbook. More...
 
variable elog_config (string elog_path=defaultValue, string hostname=defaultValue, variable port=defaultValue, string subdir=defaultValue)
 set global module configuration parameters More...
 
variable elog_login (string logbook, string username, string password)
 set username and password for login to a logbook More...
 
variable elog_logout (string logbook)
 clear username and password of a logbook or all logbooks. More...
 
static variable save_prefs ()
 save persistent package data to the preferences file. More...
 
static variable load_prefs ()
 load persistent package data from the preferences file. More...
 
static string list_logbooks (variable templates=defaultValue)
 get a list of configured logbooks or templates. More...
 
variable elog_validate_attributes (string logbook, string attributes)
 validate attributes More...
 
variable elog_create_entry (string logbook, string attributes, string message, variable encoding=defaultValue, string graphs=defaultValue, variable replyto=defaultValue)
 create a new entry in ELOG More...
 
variable elog_add_attachment (string logbook, variable id, string graphs)
 add one or more graphs to an existing ELOG entry More...
 
static string prepare_command_line (string logbook)
 format the ELOG command and essential address arguments. More...
 
static string format_url (string logbook)
 format the URL for display to the user More...
 
static string prepare_graph_attachments (string graphs)
 prepare screenshots of graph windows for attachments More...
 
static string get_timestamp (string sep)
 
static string create_message_file (string message)
 save the message to a temporary text file More...
 
static string create_graph_file (string graphname, variable fileindex)
 save a graph to a temporary graphics file More...
 
static string create_cmd_file (string cmd)
 write the command line to a file. More...
 
static string get_log_path ()
 
static variable cleanup_temp_files ()
 delete temporary files created by the ELOG module. More...
 
static variable parse_result ()
 parse the result file from an elog invokation. More...
 
string elog_prompt_logbook ()
 prompt to open or create a logbook More...
 
variable elog_prompt_login (string logbook)
 prompt the user for login to a logbook More...
 
string PearlElogPanel (string logbook)
 open a new panel for submitting data to ELOG. More...
 
static variable elog_panel_hook (WMWinHookStruct *s)
 
static variable update_attach_items (string logbook)
 update the list of attachments More...
 
static variable move_attach_item (string logbook, variable item, variable distance)
 move an attachment item in the list of attachments More...
 
static variable bp_attach_updown (WMButtonAction *ba)
 button procedure for the attachment up and down buttons More...
 
static variable bp_submit (WMButtonAction *ba)
 button procedure for the Submit and Reply buttons More...
 
static variable bp_attach_top (WMButtonAction *ba)
 select top graph window for attachment More...
 
static variable bp_attach_allnone (WMButtonAction *ba)
 select/deselect all graph windows for attachment More...
 
static variable bp_attach (WMButtonAction *ba)
 
static variable bp_save_graphs (WMButtonAction *ba)
 
static variable bp_clear (WMButtonAction *ba)
 
static variable bp_login (WMButtonAction *ba)
 
static variable bp_logout (WMButtonAction *ba)
 
static string get_default_panel_name ()
 
static string get_panel_attributes (string windowname)
 get a list of attributes from the fields of the ELOG panel. More...
 
static string set_panel_attributes (string windowname, string attributes, variable clear=defaultValue)
 set the fields of the ELOG panel More...
 
static string get_panel_message (string windowname)
 get the message field of the ELOG panel More...
 
static string set_panel_message (string windowname, string message)
 set the message field of the ELOG panel More...
 
static string get_panel_graphs (string windowname)
 get the names of the graphs selected for attachment More...
 
static string set_panel_graphs (string windowname, string graphs)
 update selection of graphs for attachment More...
 
- - - - - - - - - - - - - - - - - - - - - - - -

-Variables

static const string package_name = "pearl_elog"
 
static const string package_path = "root:packages:pearl_elog:"
 
static const variable kdfRoot = 0
 
static const variable kdfVolatile = 1
 
static const variable kdfPersistent = 2
 
static const variable kdfTemplates = 3
 
static const string elog_success_msg = "Message successfully transmitted"
 
static const string elog_parse_id = "ID=%u"
 
static const variable kAttachColSel = 0
 
static const variable kAttachColTitle = 1
 
static const variable kAttachColName = 2
 
-

Detailed Description

-

interface for writing ELOG entries with Igor graphs as attachment.

-

the functions in this module support the following ELOG features:

-

usage:

    -
  1. the administrator of the ELOG server creates logbook templates according to the configuration of the logbooks. the templates are written in Igor code.
  2. -
  3. the user opens logbooks via the Open ELOG panel menu item. before first use, select a template and enter a name for the logbook. the new logbook is written to the preference file, and can afterwards be opened directly.
  4. -
  5. if the server requires a user name and password, click the login button.
  6. -
  7. edit the message, attributes and attachments as necessary, and submit to ELOG.
  8. -
  9. log out before saving the experiment to clear the password.
  10. -
-
Attention
the user name and password are stored in the global data tree of an experiment. it is not possible to handle passwords safely in Igor. they can be read by anyone having access to an open Igor experiment or a saved experiment file (unless the password is reset before saving). therefore:
    -
  • use a password for the ELOG server which is different from your other passwords.
  • -
  • clear the password (logout button in the panel) before saving an experiment.
  • -
-
-

elog command line

*  elog -h <hostname> [-p port] [-d subdir]
-*                               Location where elogd is running
-*      -l logbook               Name of logbook
-*      -s                       Use SSL for communication
-*      [-v]                     For verbose output
-*      [-w password]            Write password defined on server
-*      [-u username password]   User name and password
-*      [-f <attachment>]        Up to 50 attachments
-*      -a <attribute>=<value>   Up to 50 attributes
-*      [-r <id>]                Reply to existing message
-*      [-q]                     Quote original text on reply
-*      [-e <id>]                Edit existing message
-*      [-x]                     Suppress email notification
-*      [-n 0|1|2]               Encoding: 0:ELcode,1:plain,2:HTML
-*      -m <textfile>] | <text>
-* 
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
- - -

Definition in file pearl-elog.ipf.

-

Function Documentation

- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable AfterFileOpenHook (variable refNum,
string file,
string pathName,
string type,
string creator,
variable kind 
)
-
-static
-
- -

initialize the package and reload preferences after an experiment is loaded.

- -

Definition at line 143 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_attach (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1634 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_attach_allnone (WMButtonAction * ba)
-
-static
-
- -

select/deselect all graph windows for attachment

- -

Definition at line 1613 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_attach_top (WMButtonAction * ba)
-
-static
-
- -

select top graph window for attachment

- -

Definition at line 1597 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_attach_updown (WMButtonAction * ba)
-
-static
-
- -

button procedure for the attachment up and down buttons

- -

Definition at line 1518 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_clear (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1695 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_login (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1711 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_logout (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1729 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_save_graphs (WMButtonAction * ba)
-
-static
-
- -

Definition at line 1667 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable bp_submit (WMButtonAction * ba)
-
-static
-
- -

button procedure for the Submit and Reply buttons

- -

Definition at line 1550 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable cleanup_temp_files ()
-
-static
-
- -

delete temporary files created by the ELOG module.

-

this deletes all temporary graph files that are referenced by the volatile temp_graph_files list. temp_graph_files is a semicolon-delimited string. items are added by create_graph_file().

-

this function should be called before a new experiment is loaded or igor quits.

- -

Definition at line 1115 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static string create_cmd_file (string cmd)
-
-static
-
- -

write the command line to a file.

-

the command script changes the working directory to the Temporary directory. it also deletes a previous elog.log file.

-
Note
somewhere the command line (even inside command files) is limited to 1024 bytes. for this reason all files should now be in the Temporary directory assigned by igor.
- -

Definition at line 1059 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static string create_graph_file (string graphname,
variable fileindex 
)
-
-static
-
- -

save a graph to a temporary graphics file

-

the file is saved to the Temporary directory returned by igor's SpecialDirPath function. the file name contains a time stamp and the specified file index to make it unique. the function returns the name of the file (excluding path!)

-

the full path is added to the temp_graph_files global list. a hook function will delete the files listed there when igor quits.

-
Parameters
- - - -
graphnameobject name of the graph to save.
fileindexincrememtal index of the file within one submission. the file name is made unique by a time stamp and this file index. submissions within the same second must have a unique file index.
-
-
-
Returns
(string) name of the created file. empty string if unsuccessful.
-
Version
1.41 the return value has changed from full path to file name only due to the limited length of the command line (1024 bytes).
- -

Definition at line 1023 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static string create_message_file (string message)
-
-static
-
- -

save the message to a temporary text file

-

the file is saved to the Temporary directory returned by igor's SpecialDirPath function under the file name "elog_temp_message.txt". the function returns the name of the file (excluding path!)

-
Note
percent characters (%) cannot be passed to elog. they are removed silently from the message.
-
Parameters
- - -
messagetext message to save to the file.
-
-
-
Returns
(string) name of the created file. empty string if unsuccessful.
-
Version
1.41 the return value has changed from full path to file name only due to the limited length of the command line (1024 bytes).
- -

Definition at line 982 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable elog_add_attachment (string logbook,
variable id,
string graphs 
)
-
- -

add one or more graphs to an existing ELOG entry

-
Parameters
- - - - -
logbookname of the target logbook
ididentification number of the existing entry
graphsnames of graph windows to be added as attachments, semicolon separated
-
-
-
Warning
this will delete all existing attachments of the entry!
- -

Definition at line 792 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable elog_config (string elog_path = defaultValue,
string hostname = defaultValue,
variable port = defaultValue,
string subdir = defaultValue 
)
-
- -

set global module configuration parameters

- -

Definition at line 473 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable elog_create_entry (string logbook,
string attributes,
string message,
variable encoding = defaultValue,
string graphs = defaultValue,
variable replyto = defaultValue 
)
-
- -

create a new entry in ELOG

-

this is the main function to create a new entry in a logbook.

-
Parameters
- - - - - - - -
logbookname of the target logbook.
attributeskey=value list of attributes, semicolon separated.
messagefree text part of the entry.
encodingencoding of message, 0:ELcode, 1:plain (default), 2:HTML.
graphsnames of graph windows to be added as attachments, semicolon separated.
replytoexisting message ID (> 1) to follow up on. 0 or default: start new thread.
-
-
-
Returns
ID number of the new entry (> 0), or error code (< 0).
    -
  • -1: failed to save temporary message file.
  • -
  • -2: invalid/missing command line.
  • -
  • -3: invalid/missing attributes.
  • -
  • -4: elog returned error
  • -
-
- -

Definition at line 685 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable elog_create_logbook (string name,
string template = defaultValue 
)
-
- -

create a new logbook.

-

create a new empty logbook or duplicate from a template.

-
Parameters
- - - -
namename of the new logbook. if the logbook exists, the existing logbook folder is killed and replaced by a new one. this may fail if a window is still open.
templatename of the template. if empty string, a new empty logbook is created.
-
-
- -

Definition at line 414 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - -
variable elog_init_pearl_templates ()
-
- -

setup PEARL template logbooks.

-

template logbooks for PEARL.

-
Remarks
this function is specific to the setup at PEARL.
- -

Definition at line 262 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable elog_login (string logbook,
string username,
string password 
)
-
- -

set username and password for login to a logbook

-

the username and password are stored (in plain text) in global strings under the selected logbook folder. this is necessary for sending data to the ELOG server.

-

call elog_logout() to clear the password variables and to avoid unintended use of your credentials.

-
Warning
igor does not have a built-in mechanism to protect passwords. user names and passwords are stored in plain text in the data folder tree. as such they are saved to experiment files and preferences.
-
Parameters
- - -
logbookname of the target logbook.
-
-
- -

Definition at line 513 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - - -
variable elog_logout (string logbook)
-
- -

clear username and password of a logbook or all logbooks.

-

the username and password are stored (in plain text) in global strings under the selected logbook folder. this function resets the username and password strings.

-
Parameters
- - -
logbookname of the target logbook. if empty, the passwords of all logbooks are cleared.
-
-
- -

Definition at line 533 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable elog_panel_hook (WMWinHookStruct * s)
-
-static
-
- -

Definition at line 1394 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - -
string elog_prompt_logbook ()
-
- -

prompt to open or create a logbook

- -

Definition at line 1184 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - - -
variable elog_prompt_login (string logbook)
-
- -

prompt the user for login to a logbook

- -

Definition at line 1214 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable elog_validate_attributes (string logbook,
string attributes 
)
-
- -

validate attributes

-
Returns
0 if all required attributes are present and enumerated items are correct. non-zero if a violation is detected.
-
Todo:
function currently not implemented, always returns 0
- -

Definition at line 653 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static string format_url (string logbook)
-
-static
-
- -

format the URL for display to the user

-
Parameters
- - -
logbookname of the target logbook
-
-
- -

Definition at line 902 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static string get_default_panel_name ()
-
-static
-
- -

Definition at line 1746 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static dfr get_elog_df (string name,
variable category 
)
-
-static
-
- -

get the package, logbook, or template datafolder.

-
Parameters
- - - -
namename of logbook or template, or empty string for respective parent folder.
categoryparameter category:
    -
  • kdfRoot package root
  • -
  • kdfVolatile volatile
  • -
  • kdfPersistent persistent
  • -
  • kdfTemplates template
  • -
-
-
-
-
Returns
data folder reference
- -

Definition at line 170 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static string get_log_path ()
-
-static
-
- -

Definition at line 1095 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static string get_panel_attributes (string windowname)
-
-static
-
- -

get a list of attributes from the fields of the ELOG panel.

-
Parameters
- - -
windownamewindow name of the ELOG panel if empty, use default name "PearlElogPanel"
-
-
-
Returns
list of attributes to in the format "key1=value1;key2=value2".
- -

Definition at line 1759 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static string get_panel_graphs (string windowname)
-
-static
-
- -

get the names of the graphs selected for attachment

-
Parameters
- - -
windownamepanel window name
-
-
-
Returns
a semicolon-separated list, or the empty string if the selection is not valid.
- -

Definition at line 1914 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static string get_panel_message (string windowname)
-
-static
-
- -

get the message field of the ELOG panel

-
Parameters
- - -
windownamewindow name of the ELOG panel if empty, use default name "PearlElogPanel"
-
-
-
Returns
message text
- -

Definition at line 1868 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static string get_timestamp (string sep)
-
-static
-
- -

Definition at line 958 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable IgorBeforeNewHook (string igorApplicationNameStr)
-
-static
-
- -

save preferences and recent values before Igor opens a new experiment.

- -

Definition at line 127 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable IgorQuitHook (string igorApplicationNameStr)
-
-static
-
- -

save preferences and recent values before Igor quits.

- -

Definition at line 135 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable init_package (variable clean = defaultValue)
-
-static
-
- -

initialize the package data folder.

-

the data folder is initialized with a default, local configuration without any logbooks. the server configuration should be set in the preferences.

-
Parameters
- - -
cleandecides what to do if the package configuration exists.
    -
  • 0 (default) keep existing configuration.
  • -
  • 1 overwrite existing configuration.
  • -
-
-
-
- -

Definition at line 217 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable init_volatile_vars ()
-
-static
-
- -

initialize volatile variables.

-

create and initialize all volatile variables for the configured notebooks. values of existing variables are not changed.

-

this function must be called after new logbooks have been configured, specifically by elog_create_logbook() and load_prefs().

- -

Definition at line 340 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static string list_logbooks (variable templates = defaultValue)
-
-static
-
- -

get a list of configured logbooks or templates.

-

this is list of data folder names under persistent:logbooks (or persistent:templates). the function does not check whether the folders contain valid data.

-
Parameters
- - -
templatesselect whether logbooks (0, default) or templates (1) are returned.
-
-
-
Returns
semicolon-separated list of logbooks
- -

Definition at line 618 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable load_prefs ()
-
-static
-
- -

load persistent package data from the preferences file.

-

the preferences file is an Igor packed experiment file in a special preferences folder

- -

Definition at line 584 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - -
static variable move_attach_item (string logbook,
variable item,
variable distance 
)
-
-static
-
- -

move an attachment item in the list of attachments

- -

Definition at line 1494 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable parse_result ()
-
-static
-
- -

parse the result file from an elog invokation.

-
Returns
the ID of the generated message, or a value <= 0 if an error occurred.
- -

Definition at line 1141 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - - -
variable pearl_elog (string logbook)
-
- -

main function to initialize ELOG and to open an ELOG panel.

-

this function takes care of all necessary initialization, configuration, and preferences. if a panel exists, it will be moved to the front.

-
Parameters
- - -
logbookname of the logbook if empty, the user is prompted to select or create a logbook by elog_prompt_logbook().
-
-
- -

Definition at line 97 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - - - - -
string PearlElogPanel (string logbook)
-
- -

open a new panel for submitting data to ELOG.

-

this function creates only the panel but not the necessary data folders. call init_package() and load_prefs() once before creating panels.

-
Parameters
- - -
logbookname of the target logbook
-
-
- -

Definition at line 1241 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static string prepare_command_line (string logbook)
-
-static
-
- -

format the ELOG command and essential address arguments.

-

the following arguments are included (from global variables) if applicable: host name, port, SSL, sub-dir, username, password the result string does not include leading or trailing space

-
Parameters
- - -
logbookname of the target logbook
-
-
- -

Definition at line 853 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static string prepare_graph_attachments (string graphs)
-
-static
-
- -

prepare screenshots of graph windows for attachments

-

prepares the attachment files from Igor graph windows and returns the arguments to the elog command to attach the files. file names are returned without path. the result string does not include leading or trailing space.

-
Parameters
- - -
graphsnames of graph windows to be added as attachments, semicolon separated
-
-
- -

Definition at line 939 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable save_prefs ()
-
-static
-
- -

save persistent package data to the preferences file.

-

saves everything under the persistent folder of the package.

- -

Definition at line 564 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - -
static string set_panel_attributes (string windowname,
string attributes,
variable clear = defaultValue 
)
-
-static
-
- -

set the fields of the ELOG panel

-
Parameters
- - - - -
windownamewindow name of the ELOG panel if empty, use default name "PearlElogPanel"
attributeslist of attributes to set (format "key1=value1;key2=value2")
clearwhat to do if a key is missing in attributes?
    -
  • 0 (default) leave the field unchanged
  • -
  • 1 clear the field
  • -
-
-
-
- -

Definition at line 1806 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static string set_panel_graphs (string windowname,
string graphs 
)
-
-static
-
- -

update selection of graphs for attachment

-
Parameters
- - - -
windownamepanel window name. looks for default panel if empty.
graphssemicolon-separated list of names of graph windows to select for attachment.
-
-
- -

Definition at line 1954 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static string set_panel_message (string windowname,
string message 
)
-
-static
-
- -

set the message field of the ELOG panel

-
Parameters
- - - -
windownamewindow name of the ELOG panel if empty, use default name "PearlElogPanel"
messagemessage text that can be passed to the Notebook operation.
-
-
-
Returns
original message (unchanged)
- -

Definition at line 1894 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable update_attach_items (string logbook)
-
-static
-
- -

update the list of attachments

- -

Definition at line 1433 of file pearl-elog.ipf.

- -
-
-

Variable Documentation

- -
-
- - - - - -
- - - - -
const string elog_parse_id = "ID=%u"
-
-static
-
- -

Definition at line 1134 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string elog_success_msg = "Message successfully transmitted"
-
-static
-
- -

Definition at line 1133 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kAttachColName = 2
-
-static
-
- -

Definition at line 1430 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kAttachColSel = 0
-
-static
-
- -

Definition at line 1428 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kAttachColTitle = 1
-
-static
-
- -

Definition at line 1429 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kdfPersistent = 2
-
-static
-
- -

Definition at line 155 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kdfRoot = 0
-
-static
-
- -

Definition at line 153 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kdfTemplates = 3
-
-static
-
- -

Definition at line 156 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const variable kdfVolatile = 1
-
-static
-
- -

Definition at line 154 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string package_name = "pearl_elog"
-
-static
-
- -

Definition at line 85 of file pearl-elog.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string package_path = "root:packages:pearl_elog:"
-
-static
-
- -

Definition at line 86 of file pearl-elog.ipf.

- -
-
diff --git a/doc/html/pearl-elog_8ipf_source.html b/doc/html/pearl-elog_8ipf_source.html index d9b8fb7..abdfffb 100644 --- a/doc/html/pearl-elog_8ipf_source.html +++ b/doc/html/pearl-elog_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-elog.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma version = 1.41
3 #pragma IgorVersion = 6.2
4 #pragma ModuleName = PearlElog
5 
6 // author: matthias.muntwiler@psi.ch
7 // Copyright (c) 2013-17 Paul Scherrer Institut
8 
9 // Licensed under the Apache License, Version 2.0 (the "License");
10 // you may not use this file except in compliance with the License.
11 // You may obtain a copy of the License at
12 // http://www.apache.org/licenses/LICENSE-2.0
13 
79 
84 
85 static const string package_name = "pearl_elog";
86 static const string package_path = "root:packages:pearl_elog:";
87 
97 variable pearl_elog(string logbook){
98  string logbook
99 
100  if (init_package() == 0)
101  load_prefs()
102  string templates = list_logbooks(templates=1)
103  if (ItemsInList(templates) < 1)
105  endif
106  endif
107 
108  if (strlen(logbook) == 0)
109  logbook = elog_prompt_logbook()
110  endif
111 
112  string win_name = logbook + "ElogPanel"
113  if (strlen(logbook) > 0)
114  if (strlen(WinList(win_name, ";", "")) > 0)
115  DoWindow /F $win_name
116  else
117  win_name = PearlElogPanel(logbook)
118  STRUCT WMWinHookStruct s
119  s.eventCode = 0
120  s.winName = win_name
121  elog_panel_hook(s)
122  endif
123  endif
124 };
125 
127 static variable IgorBeforeNewHook(string igorApplicationNameStr){
128  string igorApplicationNameStr
129  save_prefs()
131  return 0
132 };
133 
135 static variable IgorQuitHook(string igorApplicationNameStr){
136  string igorApplicationNameStr
137  save_prefs()
139  return 0
140 };
141 
143 static variable AfterFileOpenHook(variable refNum, string file, string pathName, string type, string creator, variable kind){
144  Variable refNum,kind
145  String file,pathName,type,creator
146  if( (kind >= 1) && (kind <= 2))
147  init_package(clean=1)
148  load_prefs()
149  endif
150  return 0
151 };
152 
153 static const variable kdfRoot = 0;
154 static const variable kdfVolatile = 1;
155 static const variable kdfPersistent = 2;
156 static const variable kdfTemplates = 3;
157 
170 static dfr get_elog_df(string name, variable category){
171  string name
172  variable category
173 
174  dfref df_package = $package_path
175  dfref df_persistent = df_package:persistent
176  dfref df_volatile = df_package:volatile
177 
178  switch(category)
179  case kdfRoot:
180  dfref df_parent = df_package
181  break
182  case kdfPersistent:
183  dfref df_parent = df_persistent
184  break
185  case kdfTemplates:
186  dfref df_parent = df_persistent:templates
187  break
188  case kdfVolatile:
189  dfref df_parent = df_volatile
190  break
191  default:
192  Abort "get_elog_df: undefined data folder category."
193  endswitch
194 
195  if ((strlen(name) > 0) && (category >= 1))
196  if (category == kdfTemplates)
197  dfref df_logbooks = df_parent
198  else
199  dfref df_logbooks = df_parent:logbooks
200  endif
201  dfref df_logbook = df_logbooks:$name
202  return df_logbook
203  else
204  return df_parent
205  endif
206 };
207 
217 static variable init_package(variable clean = defaultValue){
218  variable clean
219 
220  if (ParamIsDefault(clean))
221  clean = 0
222  endif
223 
224  dfref savedf = getdatafolderdfr()
225  dfref df_root = get_elog_df("", kdfRoot)
226  if ((clean == 0) && (DataFolderRefStatus(df_root) == 1))
227  return 1
228  endif
229 
230  setdatafolder root:
231  newdatafolder /o/s packages
232  newdatafolder /o/s $package_name
233  dfref df_package_root = getdatafolderdfr()
234  newdatafolder /o/s volatile
235  dfref df_volatile = getdatafolderdfr()
236  newdatafolder /o logbooks
237  setdatafolder df_package_root
238  newdatafolder /o/s persistent
239  dfref df_persistent = getdatafolderdfr()
240  newdatafolder /o logbooks
241  newdatafolder /o templates
242 
243  // common configuration
244  setdatafolder df_persistent
245  string /g elog_path = "c:\\program files (x86)\\ELOG\\elog.exe"
246  string /g hostname = "localhost"
247  variable /g port = 0// 0 = unspecified (default)
248  variable /g ssl = 0// 0 = plain text (incl. passwords), 1 = secure connection
249  string /g subdir = ""
250  variable /g loglevel = 4
251 
252  setdatafolder savedf
253  return 0
254 };
255 
263  dfref savedf = getdatafolderdfr()
264 
265  dfref df_root = get_elog_df("", kdfRoot)
266  dfref df_persistent = get_elog_df("", kdfPersistent)
267  dfref df_templates = get_elog_df("", kdfTemplates)
268 
269  // Experiments template
270  setdatafolder df_templates
271  newdatafolder /o/s Experiments
272 
273  // attributes (persistent)
274  // available attributes
275  string /g attributes = "author;project;sample;source;task;technique;file;valid;"
276  // controls corresponding to attributes
277  // prefix determines the control type: sv_ = setvariable (string), pm_ = popup menu, cb = check box
278  string /g controls = "sv_author;sv_project;sv_sample;pm_source;pm_task;pm_technique;sv_file;cb_valid;"
279  // attributes with fixed options, value item declares the options string
280  string /g options = "source=sources;task=tasks;technique=techniques"
281  // attributes which must be defined
282  string /g required_attributes = "author;project;sample;source;task;technique;valid"
283 
284  // option lists
285  string /g sources = "Manual Entry;PShell;Scienta Data;SScan Data;Prosilica Data;OTF Data;Beamline Status;LEED Data;QMS Data;Matrix Data;Igor Pro;Other"
286  string /g tasks = "Measurement;Optimization;Analysis;Sample Preparation;Sample Storage;Comment;Development;Maintenance;Test;Other"
287  string /g techniques = "XPS;UPS;XPD;XAS;XMCD;PhD;ARUPS;STM;STS;LEED;AES;QMS;MBE;Sputter/Anneal;Test;Other"
288 
289  // Calculations template
290  setdatafolder df_templates
291  newdatafolder /o/s Calculations
292 
293  // attributes (persistent)
294  // available attributes
295  string /g attributes = "author;project;sample;program;revision;machine;job;experiment;source path;result path;valid"
296  // controls corresponding to attributes
297  // prefix determines the control type: sv_ = setvariable (string), pm_ = popup menu, cb = check box
298  string /g controls = "sv_author;sv_project;sv_sample;pm_program;sv_revision;pm_machine;sv_job;sv_experiment;sv_sourcepath;sv_resultpath;cb_valid"
299  // attributes with fixed options, value item declares the options string
300  string /g options = "program=programs;machine=machines"
301  // attributes which must be defined
302  string /g required_attributes = "author;project;sample"
303 
304  // option lists
305  string /g programs = "PMSCO;EDAC;MSC;SSC;MUFPOT;DMSUP;Other"
306  string /g machines = "PC;VM;Ra;Merlin;llcx;Other"
307 
308  // System template
309  setdatafolder df_templates
310  newdatafolder /o/s System
311 
312  // attributes (persistent)
313  // available attributes
314  string /g attributes = "author;type;system;source;file"
315  // controls corresponding to attributes
316  // prefix determines the control type: sv_ = setvariable (string), pm_ = popup menu, cb = check box
317  string /g controls = "sv_author;pm_type;pm_system;pm_source;sv_file"
318  // attributes with fixed options, value item declares the options string
319  string /g options = "type=types;system=systems;source=sources"
320  // attributes which must be defined
321  string /g required_attributes = "author;type;system"
322 
323  // option lists
324  string /g types = "Installation;Repair;Maintenance;Test;Commissioning;Bakeout;Incident;Cool-down;Warm-up;Storage;Other"
325  string /g systems = "Vacuum;Control System;BL;XA;XP;SA;SP;T;LL;Monochromator;Carving;Scienta;STM;PC-Scienta;PC-Matrix;PC-Console;PC-Console-Win;PC-XP;EPS;LAC;Desiccator"
326  string /g sources = "Manual Entry;PShell;Scienta Data;SScan Data;Prosilica Data;OTF Data;Beamline Status;LEED Data;QMS Data;Matrix Data;Igor Pro;Other"
327 
328  setdatafolder savedf
329  return 0
330 };
331 
340 static variable init_volatile_vars(){
341  dfref savedf = GetDataFolderDFR()
342 
343  dfref df_volatile_root = get_elog_df("", kdfVolatile)
344  dfref df_volatile_parent = df_volatile_root:logbooks
345 
346  string logbooks = list_logbooks()
347  string logbook
348  variable nlb = ItemsInList(logbooks)
349  variable ilb
350 
351  SetDataFolder df_volatile_root
352  if (exists("temp_graph_files") != 2)
353  string /g temp_graph_files = ""
354  endif
355 
356  for (ilb = 0; ilb < nlb; ilb += 1)
357  logbook = StringFromList(ilb, logbooks)
358 
359  SetDataFolder df_volatile_parent
360  if (DataFolderExists(logbook))
361  SetDataFolder $logbook
362  else
363  NewDataFolder /o/s $logbook
364  endif
365 
366  if (exists("username") != 2)
367  string /g username = ""
368  endif
369  if (exists("password") != 2)
370  string /g password = ""
371  endif
372  if (exists("msg_id") != 2)
373  variable /g msg_id = 0
374  endif
375  if (exists("att_list") != 1)
376  make /n=(0,3) /t /o attach_list
377  make /n=(0,3) /i /o attach_sel
378  endif
379  if (exists("url") != 2)
380  string /g url = ""
381  endif
382  endfor
383 
384  SetDataFolder savedf
385  return 0
386 };
387 
401 
414 variable elog_create_logbook(string name, string template = defaultValue){
415  string name
416  string template
417 
418  if (ParamIsDefault(template))
419  template = ""
420  endif
421 
422  dfref savedf = getdatafolderdfr()
423  dfref df_root = get_elog_df("", kdfRoot)
424  dfref df_persistent_root = get_elog_df("", kdfPersistent)
425  dfref df_persistent_parent = df_persistent_root:logbooks
426  dfref df_volatile_root = get_elog_df("", kdfVolatile)
427  dfref df_volatile_parent = df_volatile_root:logbooks
428 
429  setdatafolder df_persistent_parent
430  if (CheckName(name, 11) != 0)
431  setdatafolder savedf
432  Abort "invalid logbook name"
433  return -1
434  endif
435 
436  if (strlen(template) > 0)
437  dfref df_template = get_elog_df(template, kdfTemplates)
438  dfref df_existing = get_elog_df(name, kdfPersistent)
439  if (DataFolderRefStatus(df_existing))
440  KillDataFolder /Z df_existing
441  endif
442  DuplicateDataFolder df_template, df_persistent_parent:$name
443  else
444  NewDataFolder /o/s df_persistent_parent:$name
445 
446  // ELOG logbook name
447  string /g logbook = name
448  // attributes (persistent)
449  // available attributes
450  string /g attributes = ""
451  // controls corresponding to attributes
452  // prefix determines the control type: sv_ = setvariable (string), pm_ = popup menu, cb = check box
453  string /g controls = ""
454  // attributes with fixed options, value item declares the options string
455  string /g options = ""
456  // attributes which must be defined
457  string /g required_attributes = ""
458  endif
459 
460  // usage data (persistent)
461  setdatafolder get_elog_df(name, kdfPersistent)
462  string /g recent = ""
463  string /g recent_message = ""
464 
466 
467  setdatafolder savedf
468  return 0
469 };
470 
473 variable elog_config(string elog_path = defaultValue, string hostname = defaultValue, variable port = defaultValue, string subdir = defaultValue){
474  string elog_path
475  string hostname
476  variable port
477  string subdir
478 
479  dfref df = get_elog_df("", kdfPersistent)
480 
481  if (!ParamIsDefault(elog_path))
482  svar /sdfr=df g_elog_path = elog_path
483  g_elog_path = elog_path
484  endif
485  if (!ParamIsDefault(hostname))
486  svar /sdfr=df g_hostname = hostname
487  g_hostname = hostname
488  endif
489  if (!ParamIsDefault(port))
490  nvar /sdfr=df g_port = port
491  g_port = port
492  endif
493  if (!ParamIsDefault(subdir))
494  svar /sdfr=df g_subdir = subdir
495  g_subdir = subdir
496  endif
497 };
498 
513 variable elog_login(string logbook, string username, string password){
514  string logbook
515  string username
516  string password
517 
518  dfref df = get_elog_df(logbook, kdfVolatile)
519  svar /sdfr=df g_username=username
520  svar /sdfr=df g_password=password
521  g_username = username
522  g_password = password
523 };
524 
533 variable elog_logout(string logbook){
534  string logbook
535 
536  dfref df = get_elog_df(logbook, kdfVolatile)
537  if (strlen(logbook) > 0)
538  svar /z /sdfr=df g_username=username
539  svar /z /sdfr=df g_password=password
540  if (svar_exists(g_username))
541  g_username = ""
542  endif
543  if (svar_exists(g_password))
544  g_password = ""
545  endif
546  else
547  dfref df2 = df:logbooks
548  variable nlb = CountObjectsDFR(df2, 4)
549  variable ilb
550  string slb
551  for (ilb = 0; ilb < nlb; ilb += 1)
552  slb = GetIndexedObjNameDFR(df2, 4, ilb)
553  if (strlen(slb) > 0)
554  elog_logout(slb)
555  endif
556  endfor
557  endif
558 };
559 
564 static variable save_prefs(){
565  dfref saveDF = GetDataFolderDFR()
566 
567  dfref df = get_elog_df("", kdfPersistent)
568  if (DataFolderRefStatus(df) == 1)
569  string fullPath = SpecialDirPath("Packages", 0, 0, 0)
570  fullPath += package_name
571  NewPath/O/C/Q tempPackagePrefsPath, fullPath
572  fullPath += ":preferences.pxp"
573  SetDataFolder df
574  SaveData /O /Q /R fullPath
575  KillPath/Z tempPackagePrefsPath
576  endif
577 
578  SetDataFolder saveDF
579 };
580 
584 static variable load_prefs(){
585  dfref saveDF = GetDataFolderDFR()
586 
587  variable result = -1
588  init_package()
589  setdatafolder get_elog_df("", kdfPersistent)
590 
591  string fullPath = SpecialDirPath("Packages", 0, 0, 0)
592  fullPath += package_name
593 
594  GetFileFolderInfo /Q /Z fullPath
595  if (V_Flag == 0)// Disk directory exists?
596  fullPath += ":preferences.pxp"
597  GetFileFolderInfo /Q /Z fullPath
598  if (V_Flag == 0)// Preference file exist?
599  LoadData /O /R /Q fullPath
601  result = 0
602  endif
603  endif
604 
605  SetDataFolder saveDF
606  return result
607 };
608 
618 static string list_logbooks(variable templates = defaultValue){
619  variable templates
620 
621  if (ParamIsDefault(templates))
622  templates = 0
623  endif
624 
625  dfref df_persistent = get_elog_df("", kdfPersistent)
626  if (templates)
627  dfref df_logbooks = df_persistent:templates
628  else
629  dfref df_logbooks = df_persistent:logbooks
630  endif
631  string logbooks = ""
632 
633  variable nlb = CountObjectsDFR(df_logbooks, 4)
634  variable ilb
635  string slb
636  for (ilb = 0; ilb < nlb; ilb += 1)
637  slb = GetIndexedObjNameDFR(df_logbooks, 4, ilb)
638  if (strlen(slb) > 0)
639  logbooks = AddListItem(slb, logbooks)
640  endif
641  endfor
642 
643  return SortList(logbooks, ";", 16)
644 };
645 
653 variable elog_validate_attributes(string logbook, string attributes){
654 
655  string logbook// name of the logbook (as in igor folder name)
656  string attributes// key=value list of attributes, semicolon separated
657 
658  variable result = 0
659  return result
660 };
661 
685 variable elog_create_entry(string logbook, string attributes, string message, variable encoding = defaultValue, string graphs = defaultValue, variable replyto = defaultValue){
686  string logbook
687  string attributes
688  string message
689  variable encoding
690  string graphs
691  variable replyto
692 
693  if (ParamIsDefault(encoding))
694  encoding = 1
695  endif
696  if (ParamIsDefault(graphs))
697  graphs = ""
698  endif
699  if (ParamIsDefault(replyto))
700  replyto = 0
701  endif
702 
703  dfref savedf = getdatafolderdfr()
704  dfref df_general = get_elog_df("", kdfPersistent)
705  dfref df_volatile = get_elog_df(logbook, kdfVolatile)
706 
707  variable result = 0
708  nvar /sdfr=df_volatile msg_id
709  nvar /sdfr=df_general loglevel
710 
711  if (elog_validate_attributes(logbook,attributes) != 0)
712  if (loglevel >= 2)
713  print "ELOG: failed to validate attributes."
714  endif
715  result = -3
716  endif
717 
718  string cmd = prepare_command_line(logbook)
719  if (strlen(cmd) == 0)
720  if (loglevel >= 2)
721  print "ELOG: failed to prepare command line."
722  endif
723  result = -2
724  endif
725 
726  if (replyto >= 1)
727  cmd += " -r " + num2str(replyto)
728  endif
729  cmd += " -n " + num2str(encoding)
730 
731  variable nattr = ItemsInList(attributes, ";")
732  variable iattr
733  string sattr
734  for (iattr = 0; (iattr < nattr) && (result == 0); iattr += 1)
735  sattr = StringFromList(iattr, attributes, ";")
736  if (strlen(StringFromList(1, sattr, "=")) > 0)
737  sattr = ReplaceString("%", sattr, "")
738  cmd += " -a \"" + sattr + "\""
739  endif
740  endfor
741 
742  if (result == 0)
743  string cmd_graphs = prepare_graph_attachments(graphs)
744  cmd += " " + cmd_graphs
745  endif
746 
747  if ((result == 0) && (strlen(message) > 0))
748  string messagefile = create_message_file(message)
749  if (strlen(messagefile) > 0)
750  cmd += " -m \"" + messagefile + "\""
751  cmd += " > elog.log"
752  if (loglevel >= 5)
753  print cmd
754  endif
755  string cmd_file_path = create_cmd_file(cmd)
756  if (strlen(cmd_file_path) > 0)
757  ExecuteScriptText cmd_file_path
758  variable id = parse_result()
759  if (id > 0)
760  msg_id = id
761  if (loglevel >= 4)
762  print "ELOG: sent message " + num2str(id)
763  endif
764  else
765  if (loglevel >= 2)
766  print "ELOG: sending message failed."
767  endif
768  result = -4
769  endif
770  else
771  result = -2
772  endif
773  else
774  if (loglevel >= 2)
775  print "ELOG: failed to create temporary message file."
776  endif
777  result = -1
778  endif
779  endif
780 
781  setdatafolder savedf
782  return result
783 };
784 
792 variable elog_add_attachment(string logbook, variable id, string graphs){
793  string logbook
794  variable id// existing entry ID
795  string graphs// names of graph windows to be added as attachments, semicolon separated
796 
797  dfref savedf = getdatafolderdfr()
798  dfref df_general = get_elog_df("", kdfPersistent)
799  dfref df_volatile = get_elog_df(logbook, kdfVolatile)
800 
801  variable result = 0
802  nvar /sdfr=df_volatile msg_id
803  nvar /sdfr=df_general loglevel
804 
805  string cmd = prepare_command_line(logbook)
806  if (strlen(cmd) == 0)
807  result = -2// error: invalid/missing command line
808  endif
809 
810  cmd += " -e " + num2str(id)
811 
812  if (result == 0)
813  string cmd_graphs = prepare_graph_attachments(graphs)
814  if (strlen(cmd_graphs) == 0)
815  result = -3// error: invalid/missing graphs
816  endif
817  endif
818 
819  if (result == 0)
820  cmd += " " + cmd_graphs
821  cmd += " > elog.log"
822  string cmd_file_path = create_cmd_file(cmd)
823  if (strlen(cmd_file_path) > 0)
824  ExecuteScriptText cmd_file_path
825  id = parse_result()
826  if (id > 0)
827  msg_id = id
828  if (loglevel >= 4)
829  print "ELOG: attached graphs to message " + num2str(id)
830  endif
831  else
832  if (loglevel >= 2)
833  print "ELOG: failed to attach graphs."
834  endif
835  result = -4// error: elog returned error
836  endif
837  else
838  result = -2// error: invalid command line
839  endif
840  endif
841 
842  setdatafolder savedf
843  return result
844 };
845 
853 static string prepare_command_line(string logbook){
854  string logbook
855 
856  dfref df_general = get_elog_df("", kdfPersistent)
857  dfref df_persistent = get_elog_df(logbook, kdfPersistent)
858  dfref df_volatile = get_elog_df(logbook, kdfVolatile)
859 
860  svar /sdfr=df_general elog_path
861  svar /sdfr=df_general hostname
862  nvar /sdfr=df_general port
863  nvar /sdfr=df_general ssl
864  svar /sdfr=df_general subdir
865  nvar /sdfr=df_general loglevel
866  svar /sdfr=df_volatile username
867  svar /sdfr=df_volatile password
868 
869  string cmd
870  cmd = "\"" + elog_path + "\""
871  if (loglevel >= 5)
872  cmd += " -v"
873  endif
874  cmd += " -h " + hostname
875  if ((nvar_exists(port)) && (port > 0))
876  cmd += " -p " + num2str(port)
877  endif
878  if ((svar_exists(subdir)) && (strlen(subdir) > 0))
879  cmd += " -d " + subdir
880  endif
881  cmd += " -l \"" + logbook + "\""
882  if ((nvar_exists(ssl)) && (ssl != 0))
883  cmd += " -s"
884  endif
885  //cmd += " -w " + password
886  if (svar_exists(username) && svar_exists(password) && (strlen(username) > 0) && (strlen(password) > 0))
887  cmd += " -u " + username + " " + password
888  endif
889 
890  if (loglevel >= 5)
891  print cmd
892  endif
893 
894  return cmd
895 };
896 
902 static string format_url(string logbook){
903  string logbook
904 
905  dfref df_general = get_elog_df("", kdfPersistent)
906 
907  svar /sdfr=df_general hostname
908  nvar /sdfr=df_general port
909  nvar /sdfr=df_general ssl
910  svar /sdfr=df_general subdir
911 
912  string cmd = ""
913  if ((nvar_exists(ssl)) && (ssl != 0))
914  cmd += "https://"
915  else
916  cmd += "http://"
917  endif
918  cmd += hostname
919  if ((nvar_exists(port)) && (port > 0))
920  cmd += ":" + num2str(port)
921  endif
922  if ((svar_exists(subdir)) && (strlen(subdir) > 0))
923  cmd += "/" + subdir
924  endif
925  cmd += "/" + logbook
926 
927  return cmd
928 };
929 
939 static string prepare_graph_attachments(string graphs){
940  string graphs// names of graph windows to be added as attachments, semicolon separated
941 
942  string cmd = ""
943  variable ngraphs = ItemsInList(graphs, ";")
944  variable igraph
945  string sgraph
946  string graph_path
947  for (igraph = 0; igraph < ngraphs; igraph += 1)
948  sgraph = StringFromList(igraph, graphs, ";")
949  graph_path = create_graph_file(sgraph, igraph)
950  if (strlen(graph_path) > 0)
951  cmd += " -f \"" + graph_path + "\""
952  endif
953  endfor
954 
955  return cmd
956 };
957 
958 static string get_timestamp(string sep){
959  string sep
960  Variable now = DateTime
961  string dat = ReplaceString("-", Secs2Date(DateTime, -2), "")
962  string tim = ReplaceString(":", Secs2Time(DateTime, 3), "")
963  return dat + sep + tim
964 };
965 
982 static string create_message_file(string message){
983  string message
984 
985  message = ReplaceString("%", message, "")
986  string path = SpecialDirPath("Temporary", 0, 1, 0)
987  variable len = strlen(path)
988  string filename
989 
990  if (numtype(len) == 0)
991  filename = "elog_temp_message.txt"
992  path += filename
993  variable f1
994  Open f1 as path
995  fprintf f1, message
996  Close f1
997  else
998  filename = ""
999  endif
1000 
1001  return filename
1002 };
1003 
1023 static string create_graph_file(string graphname, variable fileindex){
1024  string graphname
1025  variable fileindex
1026 
1027  dfref df_volatile_root = get_elog_df("", kdfVolatile)
1028  svar /sdfr=df_volatile_root temp_graph_files
1029 
1030  string path = SpecialDirPath("Temporary", 0, 1, 0)
1031  string ts = get_timestamp("_")
1032  variable len = strlen(path)
1033  string filename
1034 
1035  if (numtype(len) == 0)
1036  filename = "elog_" + ts + "_" + num2str(fileindex) + ".png"
1037  path += filename
1038  SavePICT /B=72 /E=-5 /M /O /W=(0,0,8,6) /WIN=$graphname /Z as path
1039  if (v_flag == 0)
1040  temp_graph_files = AddListItem(path, temp_graph_files, ";", inf)
1041  else
1042  filename = ""
1043  endif
1044  else
1045  filename = ""
1046  endif
1047 
1048  return filename
1049 };
1050 
1059 static string create_cmd_file(string cmd){
1060  string cmd
1061 
1062  dfref df_general = get_elog_df("", kdfPersistent)
1063  nvar /sdfr=df_general loglevel
1064 
1065  if (strlen(cmd) >= 1024)
1066  if (loglevel >= 2)
1067  print "ELOG: command line too long (add fewer attachments)."
1068  endif
1069  return ""
1070  endif
1071 
1072  string work_path = SpecialDirPath("Temporary", 0, 1, 0)
1073  variable len = strlen(work_path)
1074  if (numtype(len) == 0)
1075  string cmdx
1076  string cmd_path = work_path + "elog_temp_cmd.bat"
1077 
1078  variable f1
1079  Open f1 as cmd_path
1080  cmdx = "c:\r\n"
1081  fprintf f1, cmdx
1082  cmdx = "cd \"" + work_path + "\"\r\n"
1083  fprintf f1, cmdx
1084  cmdx = "del elog.log"
1085  fprintf f1, cmdx + "\r\n"
1086  fprintf f1, cmd
1087  Close f1
1088  else
1089  cmd_path = ""
1090  endif
1091 
1092  return cmd_path
1093 };
1094 
1095 static string get_log_path(){
1096  string path = SpecialDirPath("Temporary", 0, 1, 0)
1097  variable len = strlen(path)
1098  if (numtype(len) == 0)
1099  path += "elog.log"
1100  else
1101  path = ""
1102  endif
1103 
1104  return path
1105 };
1106 
1115 static variable cleanup_temp_files(){
1116  dfref df_volatile_root = get_elog_df("", kdfVolatile)
1117  if (DataFolderRefStatus(df_volatile_root))
1118  svar /sdfr=df_volatile_root /z temp_graph_files
1119  if (SVAR_Exists(temp_graph_files))
1120  variable nfi = ItemsInList(temp_graph_files)
1121  variable ifi
1122  string sfi
1123  for (ifi = 0; ifi < nfi; ifi += 1)
1124  sfi = StringFromList(ifi, temp_graph_files)
1125  DeleteFile /Z sfi
1126  endfor
1127  temp_graph_files = ""
1128  endif
1129  endif
1130  return 0
1131 };
1132 
1133 static const string elog_success_msg = "Message successfully transmitted";
1134 static const string elog_parse_id = "ID=%u";
1135 
1141 static variable parse_result(){
1142  dfref df_general = get_elog_df("", kdfPersistent)
1143  nvar /sdfr=df_general loglevel
1144 
1145  string path = get_log_path()
1146  string line = ""
1147  string output = ""
1148  variable success = 0
1149  variable id = -1
1150  string part1 = ""
1151  string part2 = ""
1152 
1153  variable len = strlen(path)
1154  if (numtype(len) == 0)
1155  variable f1
1156  Open /R/Z f1 as path
1157  if (v_flag == 0)
1158  do
1159  FReadLine f1, line
1160  if (strlen(line) > 0)
1161  part1 = StringFromList(0, line, ",")
1162  part2 = ReplaceString(" ", StringFromList(1, line, ","), "")
1163  success = cmpstr(part1, elog_success_msg) == 0
1164  if (success)
1165  sscanf part2, elog_parse_id, id
1166  endif
1167  else
1168  break
1169  endif
1170  output += line
1171  while(!success)
1172  Close f1
1173  endif
1174  endif
1175  if (loglevel >= 5)
1176  print output
1177  endif
1178 
1179  return id
1180 };
1181 
1185  string logbooks = list_logbooks(templates=0)
1186  logbooks = AddListItem("(new)", logbooks)
1187  string templates = list_logbooks(templates=1)
1188  templates = AddListItem("(none)", templates)
1189 
1190  string logbook = StringFromList(0, logbooks)
1191  string template = StringFromList(0, logbooks)
1192  string name = ""
1193  string username = ""
1194  string password = ""
1195 
1196  prompt logbook, "logbook", popup logbooks
1197  prompt template, "template", popup templates
1198  prompt name, "new logbook name"
1199 
1200  doprompt "select logbook", logbook, template, name
1201  if (!v_flag)
1202  if (cmpstr(logbook, "(new)") == 0)
1203  elog_create_logbook(name, template=template)
1204  logbook = name
1205  endif
1206  else
1207  logbook = ""
1208  endif
1209  return logbook
1210 };
1211 
1214 variable elog_prompt_login(string logbook){
1215  string logbook
1216 
1217  string logbooks = list_logbooks(templates=0)
1218 
1219  string username = ""
1220  string password = ""
1221 
1222  prompt logbook, "logbook", popup logbooks
1223  prompt username, "user name"
1224  prompt password, "password (blank to log out)"
1225 
1226  doprompt "log in to logbook", logbook, username, password
1227  if (!v_flag)
1228  elog_login(logbook, username, password)
1229  endif
1230 
1231  return v_flag
1232 };
1233 
1241 string PearlElogPanel(string logbook){
1242  string logbook
1243 
1244  dfref savedf = getdatafolderdfr()
1245  dfref df_general = get_elog_df("", kdfPersistent)
1246  dfref df_persistent = get_elog_df(logbook, kdfPersistent)
1247  dfref df_volatile = get_elog_df(logbook, kdfVolatile)
1248 
1249  string win_name = logbook + "ElogPanel"
1250  string win_title = "ELOG " + logbook
1251 
1252  NewPanel /K=1 /N=$win_name /W=(600,200,1200,700) as win_title
1253  win_name = s_name
1254  ModifyPanel /w=$win_name cbRGB=(52224,52224,65280)
1255 
1256  svar /sdfr=df_persistent attributes
1257  svar /sdfr=df_persistent controls
1258  svar /sdfr=df_persistent options
1259  wave /t /sdfr=df_volatile attach_list
1260  wave /sdfr=df_volatile attach_sel
1261  svar /sdfr=df_volatile url
1262 
1263  variable iattr
1264  variable nattr = ItemsInList(attributes, ";")
1265  string s_attr
1266  string s_control
1267  string s_option
1268  string persistent_path = GetDataFolder(1, df_persistent)
1269  string volatile_path = GetDataFolder(1, df_volatile)
1270  string options_path
1271  string variable_path
1272  variable ypos = 2
1273  variable height = 0
1274 
1275  for (iattr = 0; iattr < nattr; iattr += 1)
1276  s_attr = StringFromList(iattr, attributes, ";")
1277  s_control = StringFromList(iattr, controls, ";")
1278  strswitch(s_control[0,1])
1279  case "sv":
1280  SetVariable $s_control, win=$win_name, pos={0,ypos}, size={300,16}, bodyWidth=230
1281  SetVariable $s_control, win=$win_name, title=s_attr, value= _STR:""
1282  SetVariable $s_control, win=$win_name, userdata(attribute)=s_attr
1283  ypos += 18
1284  break
1285  case "pm":
1286  options_path = persistent_path + StringByKey(s_attr, options, "=", ";")
1287  PopupMenu $s_control, win=$win_name, pos={0,ypos}, size={300,21}, bodyWidth=230
1288  PopupMenu $s_control, win=$win_name, title=s_attr
1289  PopupMenu $s_control, win=$win_name, mode=1, popvalue="Test", value= #options_path
1290  PopupMenu $s_control, win=$win_name, userdata(attribute)=s_attr
1291  ypos += 23
1292  break
1293  case "cb":
1294  CheckBox $s_control, win=$win_name, pos={70,ypos}, size={300,14}
1295  CheckBox $s_control, win=$win_name, title=s_attr, value= 1
1296  CheckBox $s_control, win=$win_name, userdata(attribute)=s_attr
1297  ypos += 17
1298  break
1299  endswitch
1300  endfor
1301 
1302  TitleBox t_attach, win=$win_name, pos={308,5}, size={70,14}, title="Attachments", frame=0
1303  height = ypos - 21 - 4
1304  ListBox lb_attach, win=$win_name, pos={308,21}, size={264,height}
1305  ListBox lb_attach, win=$win_name, listWave=attach_list
1306  ListBox lb_attach, win=$win_name, mode=1, selWave=attach_sel, selRow=-1
1307  ListBox lb_attach, win=$win_name, widths={20,160,80}
1308  ListBox lb_attach, win=$win_name, help={"Choose graphs to attach to the message."}
1309 
1310  Button b_attach_top, win=$win_name, pos={420,2}, size={40,18}, title="top"
1311  Button b_attach_top, win=$win_name, fcolor=(56576,60928,47872)
1312  Button b_attach_top, win=$win_name, proc=PearlElog#bp_attach_top
1313  Button b_attach_top, win=$win_name, help={"Select top graph for attachment."}
1314  Button b_attach_all, win=$win_name, pos={460,2}, size={40,18}, title="all"
1315  Button b_attach_all, win=$win_name, fcolor=(56576,60928,47872)
1316  Button b_attach_all, win=$win_name, proc=PearlElog#bp_attach_allnone
1317  Button b_attach_all, win=$win_name, help={"Select all graphs for attachment."}
1318  Button b_attach_none, win=$win_name, pos={500,2}, size={40,18}, title="none"
1319  Button b_attach_none, win=$win_name, fcolor=(56576,60928,47872)
1320  Button b_attach_none, win=$win_name, proc=PearlElog#bp_attach_allnone
1321  Button b_attach_none, win=$win_name, help={"Deselect all attachments."}
1322  Button b_save_graphs, win=$win_name, pos={540,2}, size={40,18}, title="save"
1323  Button b_save_graphs, win=$win_name, fcolor=(56576,60928,47872)
1324  Button b_save_graphs, win=$win_name, proc=PearlElog#bp_save_graphs
1325  Button b_save_graphs, win=$win_name, help={"Save selected graphs as PNG bitmap files."}
1326  Button b_attach_up, win=$win_name, pos={576,20}, size={20,20}, title="\\W517"
1327  Button b_attach_up, win=$win_name, fcolor=(56576,60928,47872)
1328  Button b_attach_up, win=$win_name, proc=PearlElog#bp_attach_updown
1329  Button b_attach_up, win=$win_name, help={"Move selected graph up."}
1330  Button b_attach_dw, win=$win_name, pos={576,40}, size={20,20}, title="\\W523"
1331  Button b_attach_dw, win=$win_name, fcolor=(56576,60928,47872)
1332  Button b_attach_dw, win=$win_name, proc=PearlElog#bp_attach_updown
1333  Button b_attach_dw, win=$win_name, help={"Move selected graph down."}
1334 
1335  ypos += 246-160
1336  Button b_submit,win=$win_name, pos={70,ypos},size={46,20},proc=PearlElog#bp_submit,title="Submit"
1337  Button b_submit,win=$win_name, help={"Submit form data to ELOG (new entry)."}
1338  Button b_submit,win=$win_name, fcolor=(56576,60928,47872)
1339  Button b_clear,win=$win_name, pos={120,ypos},size={46,20},proc=PearlElog#bp_clear,title="Clear"
1340  Button b_clear,win=$win_name, help={"Clear the form fields"}
1341  Button b_clear,win=$win_name, fcolor=(56576,60928,47872)
1342 
1343  ypos += 272-246
1344  variable_path = volatile_path + "msg_id"
1345  SetVariable sv_id,win=$win_name, pos={51,ypos},size={119,16},bodyWidth=77
1346  SetVariable sv_id,win=$win_name, title="ID",value=$variable_path
1347  SetVariable sv_id,win=$win_name, help={"ID of last submitted message, or message to attach or reply to."}
1348 
1349  TitleBox t_host, win=$win_name, pos={170,ypos+4}, size={112.00,14.00}, frame=0
1350  TitleBox t_host, win=$win_name, variable=url
1351 
1352  ypos += 270-272
1353  Button b_attach,win=$win_name, pos={170,ypos},size={48,20},proc=PearlElog#bp_attach,title="Attach"
1354  Button b_attach,win=$win_name, help={"Attach the selected graph to an existing ELOG entry (correct ID required)."}
1355  Button b_attach,win=$win_name, fcolor=(56576,60928,47872)
1356  Button b_reply,win=$win_name, pos={220,ypos},size={48,20},proc=PearlElog#bp_submit,title="Reply"
1357  Button b_reply,win=$win_name, help={"Submit form data to ELOG as a reply to an existing message (correct ID required)."}
1358  Button b_reply,win=$win_name, fcolor=(56576,60928,47872)
1359  Button b_login,win=$win_name, pos={550,ypos},size={46,20},proc=PearlElog#bp_login,title="Login"
1360  Button b_login,win=$win_name, help={"Enter user name and password."}
1361  Button b_login,win=$win_name, fcolor=(56576,60928,47872)
1362  Button b_logout,win=$win_name, pos={550,ypos},size={46,20},proc=PearlElog#bp_logout,title="Logout"
1363  Button b_logout,win=$win_name, help={"Clear user name and password."}
1364  Button b_logout,win=$win_name, fcolor=(56576,60928,47872), disable=3
1365 
1366  SetWindow $win_name, hook(elogPanelHook)=PearlElog#elog_panel_hook
1367  SetWindow $win_name, userdata(logbook)=logbook
1368 
1369  ypos += 160-270
1370  TitleBox t_message,win=$win_name, pos={10,ypos},size={58,16},fixedSize=1,frame=0,anchor=RT,title="Message"
1371  DefineGuide UGH0={FT,ypos},UGV0={FL,70},UGH1={FB,-52},UGV1={FR,-2}
1372  NewNotebook /F=0 /N=Message /OPTS=3 /W=(115,404,345,341)/FG=(UGV0,UGH0,UGV1,UGH1) /HOST=#
1373  Notebook kwTopWin, defaultTab=20, statusWidth=0, autoSave=0
1374  Notebook kwTopWin fSize=10, fStyle=0, textRGB=(0,0,0)
1375  RenameWindow #,Message
1376  string nb_name = win_name + "#Message"
1377  SetActiveSubwindow ##
1378 
1379  // restore recently used attributes and message
1380  svar /z /sdfr=df_persistent recent
1381  if (svar_exists(recent) && (strlen(recent) > 0))
1382  set_panel_attributes(win_name, recent)
1383  endif
1384  svar /z /sdfr=df_persistent recent_message
1385  if (svar_exists(recent_message) && (strlen(recent_message) > 0))
1386  set_panel_message(win_name, recent_message)
1387  endif
1388  Notebook $nb_name selection={startOfFile,startOfFile}, findText={"",1}
1389 
1390  setdatafolder savedf
1391  return win_name
1392 };
1393 
1394 static variable elog_panel_hook(WMWinHookStruct* s){
1395  STRUCT WMWinHookStruct &s
1396 
1397  Variable hookResult = 0
1398 
1399  switch(s.eventCode)
1400  case 0:// activate
1401  string logbook = GetUserData(s.winName, "", "logbook")
1402  if (strlen(logbook) > 0)
1403  dfref df_volatile = get_elog_df(logbook, kdfVolatile)
1404  svar /sdfr=df_volatile url
1405  url = format_url(logbook)
1406  update_attach_items(logbook)
1407  endif
1408  break
1409  case 6:// resize
1410  // move bottom-aligned controls when the window is resized
1411  variable b_top = s.winRect.bottom + 4
1412  Button b_submit,pos={70,b_top}
1413  Button b_clear,pos={120,b_top}
1414  TitleBox t_host, pos={170,b_top+4}
1415  b_top += 24
1416  Button b_attach,pos={170,b_top}
1417  Button b_reply,pos={220,b_top}
1418  Button b_login, pos={550,b_top}
1419  Button b_logout, pos={550,b_top}
1420  b_top += 2
1421  SetVariable sv_id,pos={51,b_top}
1422  break
1423  endswitch
1424 
1425  return hookResult// 0 if nothing done, else 1
1426 };
1427 
1428 static const variable kAttachColSel = 0;
1429 static const variable kAttachColTitle = 1;
1430 static const variable kAttachColName = 2;
1431 
1433 static variable update_attach_items(string logbook){
1434  string logbook
1435 
1436  dfref savedf = getdatafolderdfr()
1437  dfref df_volatile = get_elog_df(logbook, kdfVolatile)
1438  wave /t /sdfr=df_volatile attach_list
1439  wave /sdfr=df_volatile attach_sel
1440 
1441  if (!waveexists(attach_list))
1442  return -1
1443  endif
1444  string names = WinList("*", ";", "WIN:1;VISIBLE:1")
1445  names = SortList(names, ";", 16)
1446 
1447  // remove closed graphs
1448  variable i
1449  variable k
1450  variable n = DimSize(attach_list, 0)
1451  string s
1452  for (i = n-1; i >= 0; i -= 1)
1453  s = attach_list[i][kAttachColName]
1454  if (WhichListItem(s, names) < 0)
1455  DeletePoints /M=0 i, 1, attach_list, attach_sel
1456  endif
1457  endfor
1458 
1459  // add new graphs
1460  n = ItemsInList(names)
1461  for (i = 0; i < n; i += 1)
1462  s = StringFromList(i, names)
1463  FindValue /text=s /txop=4 /z attach_list
1464  if (v_value < 0)
1465  k = DimSize(attach_list, 0)
1466  Redimension /n=(k+1,3) attach_list, attach_sel
1467  //InsertPoints /M=0 k, 1, attach_list, attach_sel
1468  attach_list[k][kAttachColSel] = ""
1469  attach_list[k][kAttachColTitle] = ""
1470  attach_list[k][kAttachColName] = s
1471  attach_sel[k][kAttachColSel] = 32
1472  attach_sel[k][kAttachColTitle] = 0
1473  attach_sel[k][kAttachColName] = 0
1474  endif
1475  endfor
1476 
1477  // update titles
1478  n = DimSize(attach_list, 0)
1479  for (i = n-1; i >= 0; i -= 1)
1480  s = attach_list[i][kAttachColName]
1481  getwindow /z $s, wtitle
1482  if (v_flag == 0)
1483  attach_list[i][kAttachColTitle] = s_value
1484  else
1485  attach_list[i][kAttachColTitle] = s
1486  endif
1487  endfor
1488 
1489  setdatafolder savedf
1490  return 0
1491 };
1492 
1494 static variable move_attach_item(string logbook, variable item, variable distance){
1495  string logbook
1496  variable item
1497  variable distance
1498 
1499  dfref savedf = getdatafolderdfr()
1500  dfref df_volatile = get_elog_df(logbook, kdfVolatile)
1501  wave /t /sdfr=df_volatile attach_list
1502  wave /sdfr=df_volatile attach_sel
1503  variable n = DimSize(attach_list, 0)
1504  variable dest = item + distance
1505 
1506  if ((item >= 0) && (item < n) && (dest >= 0) && (dest < n))
1507  string name = attach_list[item][kAttachColName]
1508  variable sel = attach_sel[item][kAttachColSel]
1509  DeletePoints /M=0 item, 1, attach_list, attach_sel
1510  InsertPoints /M=0 dest, 1, attach_list, attach_sel
1511  attach_list[dest][kAttachColName] = name
1512  update_attach_items(logbook)
1513  attach_sel[dest][kAttachColSel] = sel
1514  endif
1515 };
1516 
1518 static variable bp_attach_updown(WMButtonAction* ba){
1519  STRUCT WMButtonAction &ba
1520 
1521  switch( ba.eventCode )
1522  case 2:// mouse up
1523  string logbook = GetUserData(ba.win, "", "logbook")
1524  ControlInfo /w=$ba.win lb_attach
1525  variable row = v_value
1526  dfref df = $s_datafolder
1527  wave /t /sdfr=df attach_list = $s_value
1528  if (cmpstr(ba.ctrlName, "b_attach_up") == 0)
1529  // up button
1530  if (row >= 1)
1531  move_attach_item(logbook, row, -1)
1532  ListBox lb_attach, win=$ba.win, selRow=(row-1)
1533  endif
1534  else
1535  // down button
1536  if (row < DimSize(attach_list, 0) - 1)
1537  move_attach_item(logbook, row, +1)
1538  ListBox lb_attach, win=$ba.win, selRow=(row+1)
1539  endif
1540  endif
1541  break
1542  case -1:// control being killed
1543  break
1544  endswitch
1545 
1546  return 0
1547 };
1548 
1550 static variable bp_submit(WMButtonAction* ba){
1551  STRUCT WMButtonAction &ba
1552 
1553  switch( ba.eventCode )
1554  case 2:// mouse up
1555  string logbook = GetUserData(ba.win, "", "logbook")
1556  string attributes
1557  string message
1558  string graphs
1559  attributes = get_panel_attributes(ba.win)
1560  message = get_panel_message(ba.win)
1561  graphs = get_panel_graphs(ba.win)
1562 
1563  variable id
1564  if (cmpstr(ba.ctrlName, "b_reply") == 0)
1565  // Reply button
1566  ControlInfo /w=$ba.win sv_id
1567  id = v_value
1568  else
1569  // Submit button
1570  id = 0
1571  endif
1572 
1573  if ((elog_validate_attributes(logbook, attributes) == 0) && (strlen(message) > 0))
1574  variable result
1575  result = elog_create_entry(logbook, attributes, message, graphs=graphs, replyto=id)
1576  if (result == 0)
1577  dfref df = get_elog_df(logbook, kdfPersistent)
1578  svar /sdfr=df recent
1579  recent = attributes
1580  svar /sdfr=df recent_message
1581  recent_message = message
1582  else
1583  abort "Submission failed. Error code " + num2str(result) + "."
1584  endif
1585  else
1586  abort "Submission failed due to missing/invalid attribute."
1587  endif
1588  break
1589  case -1:// control being killed
1590  break
1591  endswitch
1592 
1593  return 0
1594 };
1595 
1597 static variable bp_attach_top(WMButtonAction* ba){
1598  STRUCT WMButtonAction &ba
1599 
1600  switch( ba.eventCode )
1601  case 2:// mouse up
1602  string graphs = WinName(0, 1, 1)
1603  set_panel_graphs(ba.win, graphs)
1604  break
1605  case -1:// control being killed
1606  break
1607  endswitch
1608 
1609  return 0
1610 };
1611 
1613 static variable bp_attach_allnone(WMButtonAction* ba){
1614  STRUCT WMButtonAction &ba
1615 
1616  switch( ba.eventCode )
1617  case 2:// mouse up
1618  string logbook = GetUserData(ba.win, "", "logbook")
1619  dfref df_volatile = get_elog_df(logbook, kdfVolatile)
1620  wave /sdfr=df_volatile attach_sel
1621  if (cmpstr(ba.ctrlName, "b_attach_all") == 0)
1622  attach_sel[][kAttachColSel] = attach_sel[p][kAttachColSel] | 16
1623  else
1624  attach_sel[][kAttachColSel] = attach_sel[p][kAttachColSel] & ~16
1625  endif
1626  break
1627  case -1:// control being killed
1628  break
1629  endswitch
1630 
1631  return 0
1632 };
1633 
1634 static variable bp_attach(WMButtonAction* ba){
1635  STRUCT WMButtonAction &ba
1636 
1637  switch( ba.eventCode )
1638  case 2:// mouse up
1639  string logbook = GetUserData(ba.win, "", "logbook")
1640  string graphs
1641  graphs = get_panel_graphs(ba.win)
1642 
1643  variable id
1644  ControlInfo /w=$ba.win sv_id
1645  id = v_value
1646 
1647  // TODO : is there a way around this restriction?
1648  DoAlert /T="ELOG" 1, "This operation will replace all existing attachments. Do you want to continue?"
1649 
1650  if ((id > 0) && (v_flag == 1))
1651  variable result
1652  result = elog_add_attachment(logbook, id, graphs)
1653  if (result != 0)
1654  abort "Submission failed. Error code " + num2str(result) + "."
1655  endif
1656  else
1657  abort "Submission failed due to missing/invalid attribute."
1658  endif
1659  break
1660  case -1:// control being killed
1661  break
1662  endswitch
1663 
1664  return 0
1665 };
1666 
1667 static variable bp_save_graphs(WMButtonAction* ba){
1668  STRUCT WMButtonAction &ba
1669 
1670  switch( ba.eventCode )
1671  case 2:// mouse up
1672  string logbook = GetUserData(ba.win, "", "logbook")
1673  string graphs = get_panel_graphs(ba.win)
1674  variable ngraphs = ItemsInList(graphs, ";")
1675 
1676  variable igraph
1677  string sgraph
1678  string graph_path
1679  for (igraph = 0; igraph < ngraphs; igraph += 1)
1680  sgraph = StringFromList(igraph, graphs, ";")
1681  graph_path = create_graph_file(sgraph, igraph)
1682  if (strlen(graph_path) > 0)
1683  print graph_path
1684  endif
1685  endfor
1686 
1687  break
1688  case -1:// control being killed
1689  break
1690  endswitch
1691 
1692  return 0
1693 };
1694 
1695 static variable bp_clear(WMButtonAction* ba){
1696  STRUCT WMButtonAction &ba
1697 
1698  switch( ba.eventCode )
1699  case 2:// mouse up
1700  set_panel_attributes(ba.win, "", clear=1)
1701  set_panel_message(ba.win, "")
1702  set_panel_graphs(ba.win, "")
1703  break
1704  case -1:// control being killed
1705  break
1706  endswitch
1707 
1708  return 0
1709 };
1710 
1711 static variable bp_login(WMButtonAction* ba){
1712  STRUCT WMButtonAction &ba
1713 
1714  switch( ba.eventCode )
1715  case 2:// mouse up
1716  string logbook = GetUserData(ba.win, "", "logbook")
1717  if (elog_prompt_login(logbook) == 0)
1718  Button b_login, win=$ba.win, disable=3
1719  Button b_logout, win=$ba.win, disable=0
1720  endif
1721  break
1722  case -1:// control being killed
1723  break
1724  endswitch
1725 
1726  return 0
1727 };
1728 
1729 static variable bp_logout(WMButtonAction* ba){
1730  STRUCT WMButtonAction &ba
1731 
1732  switch( ba.eventCode )
1733  case 2:// mouse up
1734  string logbook = GetUserData(ba.win, "", "logbook")
1735  elog_logout(logbook)
1736  Button b_login, win=$ba.win, disable=0
1737  Button b_logout, win=$ba.win, disable=3
1738  break
1739  case -1:// control being killed
1740  break
1741  endswitch
1742 
1743  return 0
1744 };
1745 
1746 static string get_default_panel_name(){
1747  string windowname
1748  windowname = StringFromList(0, WinList("*ElogPanel*", ";", "WIN:64"), ";")
1749  return windowname
1750 };
1751 
1759 static string get_panel_attributes(string windowname){
1760  string windowname
1761 
1762  if (strlen(windowname) == 0)
1763  windowname = get_default_panel_name()
1764  endif
1765  if (strlen(windowname) == 0)
1766  return ""
1767  endif
1768 
1769  string controls = ControlNameList(windowname, ";")
1770  string attributes = ""
1771  string control
1772  string attribute
1773  variable ico
1774  variable nco = ItemsInList(controls, ";")
1775  for (ico = 0; ico < nco; ico += 1)
1776  control = StringFromList(ico, controls, ";")
1777  attribute = GetUserData(windowname, control, "attribute")
1778  if (strlen(attribute) > 0)
1779  ControlInfo /w=$windowname $control
1780  switch(v_flag)
1781  case 2:// checkbox
1782  attributes = ReplaceNumberByKey(attribute, attributes, v_value, "=", ";")
1783  break
1784  case 3:// popupmenu
1785  case 5:// setvariable
1786  attributes = ReplaceStringByKey(attribute, attributes, s_value, "=", ";")
1787  break
1788  endswitch
1789  endif
1790  endfor
1791 
1792  return attributes
1793 };
1794 
1806 static string set_panel_attributes(string windowname, string attributes, variable clear = defaultValue){
1807  string windowname
1808  string attributes
1809  variable clear
1810 
1811  if (strlen(windowname) == 0)
1812  windowname = get_default_panel_name()
1813  endif
1814  if (strlen(windowname) == 0)
1815  return ""
1816  endif
1817  if (ParamIsDefault(clear))
1818  clear = 0
1819  endif
1820 
1821  string path
1822 
1823  string controls = ControlNameList(windowname, ";")
1824  string control
1825  string attribute
1826  string value
1827  variable numval
1828  variable ico
1829  variable nco = ItemsInList(controls, ";")
1830  for (ico = 0; ico < nco; ico += 1)
1831  control = StringFromList(ico, controls, ";")
1832  attribute = GetUserData(windowname, control, "attribute")
1833  if (strlen(attribute))
1834  value = StringByKey(attribute, attributes, "=", ";")
1835  if (strlen(value) || clear)
1836  ControlInfo /w=$windowname $control
1837  switch(v_flag)
1838  case 2:// checkbox
1839  numval = NumberByKey(attribute, attributes, "=", ";")
1840  if ((numtype(numval) != 0) && clear)
1841  numval = 0
1842  endif
1843  if (numtype(numval) == 0)
1844  CheckBox $control, value=numval, win=$windowname
1845  endif
1846  break
1847  case 3:// popupmenu
1848  PopupMenu $control, popvalue=value, win=$windowname
1849  break
1850  case 5:// setvariable
1851  SetVariable /z $control, value= _STR:value, win=$windowname
1852  break
1853  endswitch
1854  endif
1855  endif
1856  endfor
1857 
1858  return attributes
1859 };
1860 
1868 static string get_panel_message(string windowname){
1869  string windowname
1870 
1871  if (strlen(windowname) == 0)
1872  windowname = get_default_panel_name()
1873  endif
1874  if (strlen(windowname) == 0)
1875  return ""
1876  endif
1877 
1878  string nb = windowname + "#Message"
1879  notebook $nb selection={startOfFile, endOfFile}
1880  getselection notebook, $nb, 2
1881 
1882  return s_selection
1883 };
1884 
1894 static string set_panel_message(string windowname, string message){
1895  string windowname
1896  string message
1897 
1898  if (strlen(windowname) == 0)
1899  windowname = get_default_panel_name()
1900  endif
1901 
1902  string nb = windowname + "#Message"
1903  notebook $nb selection={startOfFile, endOfFile},text=message
1904 
1905  return message
1906 };
1907 
1914 static string get_panel_graphs(string windowname){
1915  string windowname// panel window name
1916 
1917  dfref savedf = getdatafolderdfr()
1918  if (strlen(windowname) == 0)
1919  windowname = get_default_panel_name()
1920  endif
1921  if (strlen(windowname) == 0)
1922  return ""
1923  endif
1924 
1925  string logbook = GetUserData(windowname, "", "logbook")
1926  dfref df_volatile = get_elog_df(logbook, kdfVolatile)
1927  wave /t /sdfr=df_volatile attach_list
1928  wave /sdfr=df_volatile attach_sel
1929  string graphs = ""
1930  string windows = ""
1931  string graphname
1932 
1933  variable n = DimSize(attach_sel, 0)
1934  variable i
1935  for (i = 0; i < n; i += 1)
1936  if (attach_sel[i][kAttachColSel] & 16)
1937  graphname = attach_list[i][kAttachColName]
1938  windows = WinList(graphname, ";", "WIN:1")
1939  if (ItemsInList(windows) == 1)
1940  graphs = AddListItem(graphname, graphs, ";", inf)
1941  endif
1942  endif
1943  endfor
1944 
1945  return graphs
1946 };
1947 
1954 static string set_panel_graphs(string windowname, string graphs){
1955  string windowname
1956  string graphs
1957 
1958  if (strlen(windowname) == 0)
1959  windowname = get_default_panel_name()
1960  endif
1961  if (strlen(windowname) == 0)
1962  return ""
1963  endif
1964 
1965  string logbook = GetUserData(windowname, "", "logbook")
1966  update_attach_items(logbook)
1967  dfref df_volatile = get_elog_df(logbook, kdfVolatile)
1968  wave /t /sdfr=df_volatile attach_list
1969  wave /sdfr=df_volatile attach_sel
1970 
1971  variable n = DimSize(attach_sel, 0)
1972  variable i
1973  string graphname
1974  for (i = 0; i < n; i += 1)
1975  graphname = attach_list[i][kAttachColName]
1976  if (WhichListItem(graphname, graphs)>= 0)
1977  attach_sel[i][kAttachColSel] = 48
1978  else
1979  attach_sel[i][kAttachColSel] = 32
1980  endif
1981  endfor
1982 };
1983 
variable elog_create_entry(string logbook, string attributes, string message, variable encoding=defaultValue, string graphs=defaultValue, variable replyto=defaultValue)
create a new entry in ELOG
Definition: pearl-elog.ipf:685
-
static variable AfterFileOpenHook(variable refNum, string file, string pathName, string type, string creator, variable kind)
initialize the package and reload preferences after an experiment is loaded.
Definition: pearl-elog.ipf:143
-
variable elog_add_attachment(string logbook, variable id, string graphs)
add one or more graphs to an existing ELOG entry
Definition: pearl-elog.ipf:792
-
static const string package_path
Definition: pearl-elog.ipf:86
-
static string get_panel_graphs(string windowname)
get the names of the graphs selected for attachment
-
static variable bp_attach_updown(WMButtonAction *ba)
button procedure for the attachment up and down buttons
-
static string create_message_file(string message)
save the message to a temporary text file
Definition: pearl-elog.ipf:982
-
static variable parse_result()
parse the result file from an elog invokation.
-
variable elog_create_logbook(string name, string template=defaultValue)
create a new logbook.
Definition: pearl-elog.ipf:414
-
static string set_panel_attributes(string windowname, string attributes, variable clear=defaultValue)
set the fields of the ELOG panel
-
static variable bp_logout(WMButtonAction *ba)
-
static string get_default_panel_name()
-
static variable elog_panel_hook(WMWinHookStruct *s)
-
variable elog_config(string elog_path=defaultValue, string hostname=defaultValue, variable port=defaultValue, string subdir=defaultValue)
set global module configuration parameters
Definition: pearl-elog.ipf:473
-
interface for writing ELOG entries with Igor graphs as attachment.
-
static variable IgorBeforeNewHook(string igorApplicationNameStr)
save preferences and recent values before Igor opens a new experiment.
Definition: pearl-elog.ipf:127
-
static string set_panel_graphs(string windowname, string graphs)
update selection of graphs for attachment
-
variable elog_init_pearl_templates()
setup PEARL template logbooks.
Definition: pearl-elog.ipf:262
-
static string create_graph_file(string graphname, variable fileindex)
save a graph to a temporary graphics file
-
static const variable kAttachColName
-
static variable bp_clear(WMButtonAction *ba)
-
variable elog_login(string logbook, string username, string password)
set username and password for login to a logbook
Definition: pearl-elog.ipf:513
-
static variable bp_attach_top(WMButtonAction *ba)
select top graph window for attachment
-
static const variable kAttachColSel
-
string PearlElogPanel(string logbook)
open a new panel for submitting data to ELOG.
-
variable elog_validate_attributes(string logbook, string attributes)
validate attributes
Definition: pearl-elog.ipf:653
-
static string prepare_graph_attachments(string graphs)
prepare screenshots of graph windows for attachments
Definition: pearl-elog.ipf:939
-
static string list_logbooks(variable templates=defaultValue)
get a list of configured logbooks or templates.
Definition: pearl-elog.ipf:618
-
static variable bp_attach(WMButtonAction *ba)
-
static variable move_attach_item(string logbook, variable item, variable distance)
move an attachment item in the list of attachments
-
static dfr get_elog_df(string name, variable category)
get the package, logbook, or template datafolder.
Definition: pearl-elog.ipf:170
-
string elog_prompt_logbook()
prompt to open or create a logbook
-
static variable bp_save_graphs(WMButtonAction *ba)
-
static variable update_attach_items(string logbook)
update the list of attachments
-
static variable bp_login(WMButtonAction *ba)
-
static const variable kdfVolatile
Definition: pearl-elog.ipf:154
-
static const variable kdfTemplates
Definition: pearl-elog.ipf:156
-
static string prepare_command_line(string logbook)
format the ELOG command and essential address arguments.
Definition: pearl-elog.ipf:853
-
static variable cleanup_temp_files()
delete temporary files created by the ELOG module.
-
static string get_log_path()
-
static const variable kAttachColTitle
-
static const string elog_parse_id
-
static string get_panel_message(string windowname)
get the message field of the ELOG panel
-
static string create_cmd_file(string cmd)
write the command line to a file.
-
static variable init_volatile_vars()
initialize volatile variables.
Definition: pearl-elog.ipf:340
-
static variable load_prefs()
load persistent package data from the preferences file.
Definition: pearl-elog.ipf:584
-
static const variable kdfPersistent
Definition: pearl-elog.ipf:155
-
static variable init_package(variable clean=defaultValue)
initialize the package data folder.
Definition: pearl-elog.ipf:217
-
static variable save_prefs()
save persistent package data to the preferences file.
Definition: pearl-elog.ipf:564
-
static const variable kdfRoot
Definition: pearl-elog.ipf:153
-
variable elog_prompt_login(string logbook)
prompt the user for login to a logbook
-
static string set_panel_message(string windowname, string message)
set the message field of the ELOG panel
-
static variable IgorQuitHook(string igorApplicationNameStr)
save preferences and recent values before Igor quits.
Definition: pearl-elog.ipf:135
-
static variable bp_submit(WMButtonAction *ba)
button procedure for the Submit and Reply buttons
-
static variable bp_attach_allnone(WMButtonAction *ba)
select/deselect all graph windows for attachment
-
static string get_panel_attributes(string windowname)
get a list of attributes from the fields of the ELOG panel.
-
static const string elog_success_msg
-
static string get_timestamp(string sep)
Definition: pearl-elog.ipf:958
-
variable elog_logout(string logbook)
clear username and password of a logbook or all logbooks.
Definition: pearl-elog.ipf:533
-
variable pearl_elog(string logbook)
main function to initialize ELOG and to open an ELOG panel.
Definition: pearl-elog.ipf:97
-
static string format_url(string logbook)
format the URL for display to the user
Definition: pearl-elog.ipf:902
-
static const string package_name
Definition: pearl-elog.ipf:85
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-fitfuncs_8ipf.html b/doc/html/pearl-fitfuncs_8ipf.html index 813faec..59983a7 100644 --- a/doc/html/pearl-fitfuncs_8ipf.html +++ b/doc/html/pearl-fitfuncs_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-fitfuncs.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
-
pearl-fitfuncs.ipf File Reference
+
pearl-fitfuncs.ipf File Reference
-

various fit functions for photoelectron spectroscopy. -More...

-
#include "mm-physconst"
-

Go to the source code of this file.

- - - - -

-Data Structures

struct  DoniachSunjicStruct
 
- - - - -

-Namespaces

 PearlFitFuncs
 various fit functions for photoelectron spectroscopy.
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

threadsafe variable MultiGaussLinBG (wave w, variable x)
 multiple gaussian peaks on a linear background fit function. More...
 
threadsafe variable MultiGaussLinBG_AO (wave pw, wave yw, wave xw)
 multiple gaussian peaks on a linear background fit function (all at once). More...
 
variable MultiVoigtLinBG (wave w, variable x)
 multiple voigt peaks on a linear background fit function. More...
 
threadsafe variable DoniachSunjic (variable x, variable amp, variable pos, variable sing, variable fwhm)
 Doniach-Sunjic line shape. More...
 
variable MultiDoniachSunjicLinBG (wave w, variable x)
 multiple doniach-sunjic peaks on a linear background fit function. More...
 
threadsafe variable ds1_bg (wave w, variable x)
 
threadsafe variable ds2_bg (wave w, variable x)
 
variable ds4_bg (wave w, variable x)
 
variable ds6_bg (wave w, variable x)
 
threadsafe variable DoniachSunjicBroadS (DoniachSunjicStruct *s)
 
variable DoniachSunjicBroad (wave pw, wave yw, wave xw)
 
variable Calc_DoniachSunjicBroad (wave pw, wave yw)
 
variable Fit_DoniachSunjicBroad (wave pw, wave yw, wave xw, wave ww)
 
variable Au4f (wave w, variable x)
 
variable Au4f_2p2 (wave w, variable x)
 
variable ShowComponents_Au4f_2p2 (wave coef_wave, wave fit_wave)
 
variable Au4f_2p3 (wave w, variable x)
 
variable ShowComponents_Au4f_2p3 (wave coef_wave, wave fit_wave)
 
variable FermiGaussConv (wave pw, wave yw, wave xw)
 convolution of Fermi-Dirac distribution and a Gaussian. More...
 
-

Detailed Description

-

various fit functions for photoelectron spectroscopy.

-

this procedure contains various functions for curve fitting.

-
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
- - -

Definition in file pearl-fitfuncs.ipf.

-

Function Documentation

- -
-
- - - - - - - - - - - - - - - - - - -
variable Au4f (wave w,
variable x 
)
-
- -

Definition at line 564 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable Au4f_2p2 (wave w,
variable x 
)
-
- -

Definition at line 609 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable Au4f_2p3 (wave w,
variable x 
)
-
- -

Definition at line 694 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable Calc_DoniachSunjicBroad (wave pw,
wave yw 
)
-
- -

Definition at line 507 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe variable DoniachSunjic (variable x,
variable amp,
variable pos,
variable sing,
variable fwhm 
)
-
- -

Doniach-Sunjic line shape.

-

[S. Doniach, M. Sunjic, J. Phys. C 3 (1970) 285]

-
Parameters
- - - - - - -
xindependent variable
ampamplitude
posposition
singsingularity index (0 <= sing < 1)
fwhmfull width at half maximum
-
-
- -

Definition at line 140 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable DoniachSunjicBroad (wave pw,
wave yw,
wave xw 
)
-
- -

Definition at line 446 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - -
threadsafe variable DoniachSunjicBroadS (DoniachSunjicStructs)
-
- -

Definition at line 357 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
threadsafe variable ds1_bg (wave w,
variable x 
)
-
- -

Definition at line 183 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
threadsafe variable ds2_bg (wave w,
variable x 
)
-
- -

Definition at line 206 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable ds4_bg (wave w,
variable x 
)
-
- -

Definition at line 234 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable ds6_bg (wave w,
variable x 
)
-
- -

Definition at line 275 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable FermiGaussConv (wave pw,
wave yw,
wave xw 
)
-
- -

convolution of Fermi-Dirac distribution and a Gaussian.

-
    -
  • pw[0] = constant background
  • -
  • pw[1] = linear background
  • -
  • pw[2] = amplitude
  • -
  • pw[3] = Fermi level in eV
  • -
  • pw[4] = temperature in K
  • -
  • pw[5] = gaussian width = FWHM / 1.66511
  • -
- -

Definition at line 817 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable Fit_DoniachSunjicBroad (wave pw,
wave yw,
wave xw,
wave ww 
)
-
- -

Definition at line 528 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable MultiDoniachSunjicLinBG (wave w,
variable x 
)
-
- -

multiple doniach-sunjic peaks on a linear background fit function.

-
Parameters
- - - -
wshape parameters. the length of the wave defines the number of peaks.
    -
  • w[0] = constant coefficient of background
  • -
  • w[1] = linear coefficient of background
  • -
  • w[2 + (i-1) * 4] = amplitude of peak i
  • -
  • w[3 + (i-1) * 4] = position of peak i
  • -
  • w[4 + (i-1) * 4] = width (fwhm) of peak i
  • -
  • w[5 + (i-1) * 4] = singularity index (0...1) of peak i
  • -
-
xindependent variable
-
-
- -

Definition at line 167 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
threadsafe variable MultiGaussLinBG (wave w,
variable x 
)
-
- -

multiple gaussian peaks on a linear background fit function.

-
Note
FWHM = width * 2 * sqrt(ln(2)) = width * 1.665
-
Parameters
- - - -
wshape parameters. the length of the wave defines the number of peaks.
    -
  • w[0] = constant coefficient of background
  • -
  • w[1] = linear coefficient of background
  • -
  • w[2 + (i-1) * 3] = amplitude of peak i
  • -
  • w[3 + (i-1) * 3] = position of peak i
  • -
  • w[4 + (i-1) * 3] = width of peak i (see note)
  • -
-
xindependent variable
-
-
- -

Definition at line 44 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
threadsafe variable MultiGaussLinBG_AO (wave pw,
wave yw,
wave xw 
)
-
- -

multiple gaussian peaks on a linear background fit function (all at once).

-

this is the all-at-once version of MultiGaussLinBG. it runs about 15% faster compared to the point-by-point function (measured on a 200 point spectrum with 3 peaks).

-
Note
FWHM = width * 2 * sqrt(ln(2)) = width * 1.665
-
Parameters
- - - - -
pwshape parameters. the length of the wave defines the number of peaks.
    -
  • pw[0] = constant coefficient of background
  • -
  • pw[1] = linear coefficient of background
  • -
  • pw[2 + (i-1) * 3] = amplitude of peak i
  • -
  • pw[3 + (i-1) * 3] = position of peak i
  • -
  • pw[4 + (i-1) * 3] = width of peak i (see note)
  • -
-
ywy (dependent) values.
xwx (independent) independent values.
-
-
- -

Definition at line 79 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable MultiVoigtLinBG (wave w,
variable x 
)
-
- -

multiple voigt peaks on a linear background fit function.

-
Parameters
- - - -
wshape parameters. the length of the wave defines the number of peaks.
    -
  • w[0] = constant coefficient of background
  • -
  • w[1] = linear coefficient of background
  • -
  • w[2 + (i-1) * 4] = amplitude of peak i
  • -
  • w[3 + (i-1) * 4] = position of peak i
  • -
  • w[4 + (i-1) * 4] = width of peak i
  • -
  • w[5 + (i-1) * 4] = shape of peak i
  • -
-
xindependent variable
-
-
- -

Definition at line 110 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable ShowComponents_Au4f_2p2 (wave coef_wave,
wave fit_wave 
)
-
- -

Definition at line 663 of file pearl-fitfuncs.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable ShowComponents_Au4f_2p3 (wave coef_wave,
wave fit_wave 
)
-
- -

Definition at line 762 of file pearl-fitfuncs.ipf.

- -
-
diff --git a/doc/html/pearl-fitfuncs_8ipf_source.html b/doc/html/pearl-fitfuncs_8ipf_source.html index 5df518f..6a2a4dd 100644 --- a/doc/html/pearl-fitfuncs_8ipf_source.html +++ b/doc/html/pearl-fitfuncs_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-fitfuncs.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma IgorVersion = 6.2
3 #pragma ModuleName = PearlFitFuncs
4 #pragma version = 1.02
5 #include "mm-physconst"
6 
20 
25 
26 
27 //------------------------------------------------------------------------------
28 // Gaussian shapes
29 //------------------------------------------------------------------------------
30 
44 threadsafe variable MultiGaussLinBG(wave w, variable x){
45  wave w
46  variable x
47 
48  variable np = numpnts(w)
49  variable ip
50 
51  variable v = w[0] + x * w[1]
52  for (ip = 2; ip < np; ip += 3)
53  v += w[ip] * exp( -( (x - w[ip+1]) / w[ip+2] )^2 )
54  endfor
55 
56  return v
57 };
58 
79 threadsafe variable MultiGaussLinBG_AO(wave pw, wave yw, wave xw){
80  wave pw
81  wave yw
82  wave xw
83 
84  variable np = numpnts(pw)
85  variable ip
86 
87  yw = pw[0] + xw[p] * pw[1]
88  for (ip = 2; ip < np; ip += 3)
89  yw += pw[ip] * exp( -( (xw[p] - pw[ip+1]) / pw[ip+2] )^2 )
90  endfor
91 };
92 
93 //------------------------------------------------------------------------------
94 // Voigt shapes
95 //------------------------------------------------------------------------------
96 
110 variable MultiVoigtLinBG(wave w, variable x){
111  wave w
112  variable x
113 
114  variable np = numpnts(w)
115  variable ip
116 
117  variable v = w[0] + x * w[1]
118  for (ip = 2; ip < np; ip += 4)
119  v += w[ip] * VoigtFunc((x - w[ip+1]) / w[ip+2], w[ip+3])
120  endfor
121 
122  return v
123 };
124 
125 
126 //------------------------------------------------------------------------------
127 // Doniach-Sunjic shapes
128 //------------------------------------------------------------------------------
129 
140 threadsafe variable DoniachSunjic(variable x, variable amp, variable pos, variable sing, variable fwhm){
141  variable x
142  variable amp
143  variable pos
144  variable sing
145  variable fwhm
146 
147  variable nom, denom
148  nom = cos(pi * sing / 2 + (1 - sing) * atan((x - pos) / fwhm * 2))
149  denom = ((x - pos)^2 + fwhm^2 / 4)^((1 - sing) / 2)
150 
151  return amp * nom / denom * fwhm / 2
152 };
153 
167 variable MultiDoniachSunjicLinBG(wave w, variable x){
168  wave w
169  variable x
170 
171  variable np = numpnts(w)
172  variable ip
173 
174  variable v = w[0] + x * w[1]
175  for (ip = 2; ip < np; ip += 4)
176  v += DoniachSunjic(x, w[ip], w[ip+1], w[ip+3], w[ip+2])
177  endfor
178 
179  return v
180 };
181 
182 
183 threadsafe variable ds1_bg(wave w, variable x){
184  // Doniach-Sunjic fit function
185  // 0 <= sing < 1
186  wave w// coefficients - see below
187  variable x// independent variable
188 
189  //CurveFitDialog/ These comments were created by the Curve Fitting dialog. Altering them will
190  //CurveFitDialog/ make the function less convenient to work with in the Curve Fitting dialog.
191  //CurveFitDialog/ Equation:
192  //CurveFitDialog/ f(x) = DoniachSunjic(x, amp, pos, sing, fwhm) + bg
193  //CurveFitDialog/ End of Equation
194  //CurveFitDialog/ Independent Variables 1
195  //CurveFitDialog/ x
196  //CurveFitDialog/ Coefficients 5
197  //CurveFitDialog/ w[0] = bg
198  //CurveFitDialog/ w[1] = amp
199  //CurveFitDialog/ w[2] = pos
200  //CurveFitDialog/ w[3] = sing
201  //CurveFitDialog/ w[4] = FWHM
202 
203  return DoniachSunjic(x, w[1], w[2], w[3], w[4]) + w[0]
204 };
205 
206 threadsafe variable ds2_bg(wave w, variable x){
207  Wave w
208  Variable x
209 
210  //CurveFitDialog/ These comments were created by the Curve Fitting dialog. Altering them will
211  //CurveFitDialog/ make the function less convenient to work with in the Curve Fitting dialog.
212  //CurveFitDialog/ Equation:
213  //CurveFitDialog/ f(x) = w_0+( w_1*cos(pi*w_3/2+(1-w_3)*atan((x-w_2)/w_4)))/(((x-w_2)^2+w_4^2)^((1-w_3)/2)) +(w_5*cos(pi*w_7/2+(1-w_7)*atan((x-(w_6))/w_8)))/(((x-w_6)^2+w_8^2)^((1-w_7)/2))
214  //CurveFitDialog/ End of Equation
215  //CurveFitDialog/ Independent Variables 1
216  //CurveFitDialog/ x
217  //CurveFitDialog/ Coefficients 9
218  //CurveFitDialog/ w[0] = bg
219  //CurveFitDialog/ w[1] = amp1
220  //CurveFitDialog/ w[2] = pos1
221  //CurveFitDialog/ w[3] = sing1
222  //CurveFitDialog/ w[4] = wid1
223  //CurveFitDialog/ w[5] = amp2
224  //CurveFitDialog/ w[6] = pos2
225  //CurveFitDialog/ w[7] = sing2
226  //CurveFitDialog/ w[8] = wid2
227 
228  variable ds1 = DoniachSunjic(x, w[1], w[2], w[3], w[4])
229  variable ds2 = DoniachSunjic(x, w[5], w[6], w[7], w[8])
230 
231  return w[0] + ds1 + ds2
232 };
233 
234 variable ds4_bg(wave w, variable x){
235  Wave w
236  Variable x
237 
238  //CurveFitDialog/ These comments were created by the Curve Fitting dialog. Altering them will
239  //CurveFitDialog/ make the function less convenient to work with in the Curve Fitting dialog.
240  //CurveFitDialog/ Equation:
241  //CurveFitDialog/ f(x) = w_0+( w_1*cos(pi*w_3/2+(1-w_3)*atan((x-w_2)/w_4)))/(((x-w_2)^2+w_4^2)^((1-w_3)/2)) +(w_5*cos(pi*w_7/2+(1-w_7)*atan((x-(w_6))/w_8)))/(((x-w_6)^2+w_8^2)^((1-w_7)/2)) +( w_9*cos(pi*w_11/2+(1-w_11)*atan((x-w_10)/w_12)))/(((x-w_10)^2+w_12^2)^((1-w_11)/2)) +( w_13*cos(pi*w_15/2+(1-w_15)*atan((x-w_14)/w_16)))/(((x-w_14)^2+w_16^2)^((1-w_15)/2))
242  //CurveFitDialog/ End of Equation
243  //CurveFitDialog/ Independent Variables 1
244  //CurveFitDialog/ x
245  //CurveFitDialog/ Coefficients 17
246  //CurveFitDialog/ w[0] = w_0
247  //CurveFitDialog/ w[1] = w_11
248  //CurveFitDialog/ w[2] = w_12
249  //CurveFitDialog/ w[3] = w_13
250  //CurveFitDialog/ w[4] = w_14
251  //CurveFitDialog/ w[5] = w_21
252  //CurveFitDialog/ w[6] = w_22
253  //CurveFitDialog/ w[7] = w_23
254  //CurveFitDialog/ w[8] = w_24
255  //CurveFitDialog/ w[9] = w_31
256  //CurveFitDialog/ w[10] = w_32
257  //CurveFitDialog/ w[11] = w_33
258  //CurveFitDialog/ w[12] = w_34
259  //CurveFitDialog/ w[13] = w_41
260  //CurveFitDialog/ w[14] = w_42
261  //CurveFitDialog/ w[15] = w_43
262  //CurveFitDialog/ w[16] = w_44
263  Variable ds1, ds2, ds3, ds4
264  ds1=( w[1]*cos(pi*w[3]/2+(1-w[3])*atan((x-w[2])/w[4])))/(((x-w[2])^2+w[4]^2)^((1-w[3])/2))
265  ds2=( w[5]*cos(pi*w[7]/2+(1-w[7])*atan((x-w[6])/w[8])))/(((x-w[6])^2+w[8]^2)^((1-w[7])/2))
266  ds3=( w[9]*cos(pi*w[11]/2+(1-w[11])*atan((x-w[10])/w[12])))/(((x-w[10])^2+w[12]^2)^((1-w[11])/2))
267  ds4=( w[13]*cos(pi*w[15]/2+(1-w[15])*atan((x-w[14])/w[16])))/(((x-w[14])^2+w[16]^2)^((1-w[15])/2))
268 
269 
270  return w[0]+ds1+ds2+ds3+ds4
271 
272 
273 };
274 
275 variable ds6_bg(wave w, variable x){
276  Wave w
277  Variable x
278 
279  //CurveFitDialog/ These comments were created by the Curve Fitting dialog. Altering them will
280  //CurveFitDialog/ make the function less convenient to work with in the Curve Fitting dialog.
281  //CurveFitDialog/ Equation:
282  //CurveFitDialog/
283  //CurveFitDialog/ Variable g, ds1, ds2, ds3, ds4, ds5, ds6
284  //CurveFitDialog/ ds1=( w_11*cos(pi*w_13/2+(1-w_13)*atan((x-w_12)/w_14)))/(((x-w_12)^2+w_14^2)^((1-w_13)/2))
285  //CurveFitDialog/ ds2=( w_21*cos(pi*w_23/2+(1-w_23)*atan((x-w_22)/w_24)))/(((x-w_22)^2+w_24^2)^((1-w_23)/2))
286  //CurveFitDialog/ ds3=( w_31*cos(pi*w_33/2+(1-w_33)*atan((x-w_32)/w_34)))/(((x-w_32)^2+w_34^2)^((1-w_33)/2))
287  //CurveFitDialog/ ds4=( w_41*cos(pi*w_43/2+(1-w_43)*atan((x-w_42)/w_44)))/(((x-w_42)^2+w_44^2)^((1-w_43)/2))
288  //CurveFitDialog/ ds5=( w_51*cos(pi*w_53/2+(1-w_53)*atan((x-w_52)/w_54)))/(((x-w_52)^2+w_54^2)^((1-w_53)/2))
289  //CurveFitDialog/ ds6=( w_61*cos(pi*w_63/2+(1-w_63)*atan((x-w_62)/w_64)))/(((x-w_62)^2+w_64^2)^((1-w_63)/2))
290  //CurveFitDialog/
291  //CurveFitDialog/ f(x) =w_0+ds1+ds2+ds3+ds4+ds5+ds6
292  //CurveFitDialog/
293  //CurveFitDialog/ End of Equation
294  //CurveFitDialog/ Independent Variables 1
295  //CurveFitDialog/ x
296  //CurveFitDialog/ Coefficients 25
297  //CurveFitDialog/ w[0] = w_0
298  //CurveFitDialog/ w[1] = w_11
299  //CurveFitDialog/ w[2] = w_12
300  //CurveFitDialog/ w[3] = w_13
301  //CurveFitDialog/ w[4] = w_14
302  //CurveFitDialog/ w[5] = w_21
303  //CurveFitDialog/ w[6] = w_22
304  //CurveFitDialog/ w[7] = w_23
305  //CurveFitDialog/ w[8] = w_24
306  //CurveFitDialog/ w[9] = w_31
307  //CurveFitDialog/ w[10] = w_32
308  //CurveFitDialog/ w[11] = w_33
309  //CurveFitDialog/ w[12] = w_34
310  //CurveFitDialog/ w[13] = w_41
311  //CurveFitDialog/ w[14] = w_42
312  //CurveFitDialog/ w[15] = w_43
313  //CurveFitDialog/ w[16] = w_44
314  //CurveFitDialog/ w[17] = w_51
315  //CurveFitDialog/ w[18] = w_52
316  //CurveFitDialog/ w[19] = w_53
317  //CurveFitDialog/ w[20] = w_54
318  //CurveFitDialog/ w[21] = w_61
319  //CurveFitDialog/ w[22] = w_62
320  //CurveFitDialog/ w[23] = w_63
321  //CurveFitDialog/ w[24] = w_64
322 
323 
324  Variable ds1, ds2, ds3, ds4, ds5, ds6
325  ds1=( w[1]*cos(pi*w[3]/2+(1-w[3])*atan((x-w[2])/w[4])))/(((x-w[2])^2+w[4]^2)^((1-w[3])/2))
326  ds2=( w[5]*cos(pi*w[7]/2+(1-w[7])*atan((x-w[6])/w[8])))/(((x-w[6])^2+w[8]^2)^((1-w[7])/2))
327  ds3=( w[9]*cos(pi*w[11]/2+(1-w[11])*atan((x-w[10])/w[12])))/(((x-w[10])^2+w[12]^2)^((1-w[11])/2))
328  ds4=( w[13]*cos(pi*w[15]/2+(1-w[15])*atan((x-w[14])/w[16])))/(((x-w[14])^2+w[16]^2)^((1-w[15])/2))
329  ds5=( w[17]*cos(pi*w[19]/2+(1-w[19])*atan((x-w[18])/w[20])))/(((x-w[18])^2+w[20]^2)^((1-w[19])/2))
330  ds6=( w[21]*cos(pi*w[23]/2+(1-w[23])*atan((x-w[22])/w[24])))/(((x-w[22])^2+w[24]^2)^((1-w[23])/2))
331 
332  return w[0]+ds1+ds2+ds3+ds4+ds5+ds6
333 
334 };
335 
337  // data structure for DoniachSunjicBroadS structural function fit
338 
339  // waves populated by the FuncFit operation
340  wave pw;
341  wave yw;
342  wave xw;
343 
344  // convolution parameters to be set upon creation of the structure
345  variable precision;
346  variable oversampling;
347 
348  // auxiliary fields used internally by DoniachSunjicBroadS
349  // do not touch these
350  wave xdw;
351  wave model;
354 };
355 
356 //------------------------------------------------------------------------------
357 threadsafe variable DoniachSunjicBroadS(DoniachSunjicStruct* s){
358 //------------------------------------------------------------------------------
359  // Two-peak (bulk + surface) Doniach-Sunjic line shape with Gaussian broadening (convolution).
360  // Hold parameter 5 at 0 to fit just one peak.
361 
362  // Structural fit function for efficient fitting in procedures.
363  // Calculating the convolution requires auxiliary waves and additional, non-fitting parameters.
364  // To eliminate the time-consuming overhead of creating and killing the auxiliary waves,
365  // these waves are held in the fitting structure.
366 
367  // Caution: The function on its own is thread-safe.
368  // However, since FuncFit uses the same structure in all threads, the fitting cannot run in parallel.
369  // Set /NTHR=1.
370 
371  // See also Fit_DoniachSunjicBroad (example), DoniachSunjicBroad (conventional fit function)
372  Struct DoniachSunjicStruct &s
373 
374  // pw[0] = bulk amplitude
375  // pw[1] = bulk position
376  // pw[2] = Lorentzian FWHM
377  // pw[3] = Donjach-Sunjic singularity index (0..1)
378  // pw[4] = surface shift
379  // pw[5] = surface/bulk ratio
380  // pw[6] = Gaussian FWHM
381  // pw[7] = constant background
382  // pw[8] = linear background
383 
384  wave xw = s.xw
385  wave yw = s.yw
386  wave pw = s.pw
387 
388  variable precision = s.precision
389  variable oversampling = s.oversampling
390 
391  if (WaveExists(s.xdw))
392  wave xdw = s.xdw
393  wave model = s.model
394  wave broadening = s.broadening
395  wave convolution = s.convolution
396  else
397  make /n=0 /free xdw, model, broadening, convolution
398  redimension /d xdw, model, broadening, convolution
399  wave fs.xdw = xdw
400  wave fs.model = model
401  wave fs.broadening = broadening
402  wave fs.convolution = convolution
403  endif
404 
405  // calculate wave spacing based on minimum spacing of desired x points
406  differentiate /p xw /d=xdw
407  xdw = abs(xdw)
408  variable xd = wavemin(xdw) / oversampling
409 
410  // calculate broadening wave size based on width and precision variable
411  variable x0b = pw[6] * precision
412  variable nb = 2 * floor(x0b / xd) + 1
413 
414  // calculate model size based on desired range for yw
415  variable x0m = max(abs(wavemax(xw) - pw[1]), abs(wavemin(xw) - pw[1])) + x0b
416  variable nm = 2 * floor(x0m / xd) + 1
417  nb = min(nb, nm * 10)// limit wave size to avoid runtime errors for unphysically large parameter
418 
419  // create and calculate initial waves, normalize exponential
420  redimension /n=(nb) broadening
421  redimension /n=(nm) model
422  setscale/i x -x0b, x0b, "", broadening
423  setscale/i x -x0m, x0m, "", model
424 
425  broadening = exp( - (x / pw[6])^2 * 4 * ln(2))
426  variable nrm = area(broadening)
427  broadening /= nrm
428  model = DoniachSunjic(x, 1, 0, pw[3], pw[2])// bulk
429  model += DoniachSunjic(x, pw[5], pw[4], pw[3], pw[2])// surface
430 
431  // calculate the convolution
432  Convolve /a broadening, model
433  variable scale = pw[0] / wavemax(model)
434  model *= scale
435 
436  // prepare output
437  nm = numpnts(model)
438  x0m = xd * (nm - 1) / 2
439  setscale/i x -x0m, x0m, "", model
440 
441  yw = model(xw[p] - pw[1]) + pw[7] + pw[8] * xw[p]
442  yw = numtype(yw) ? 0 : yw
443 };
444 
445 //------------------------------------------------------------------------------
446 variable DoniachSunjicBroad(wave pw, wave yw, wave xw){
447 //------------------------------------------------------------------------------
448  // Two-peak (bulk + surface) Doniach-Sunjic line shape with Gaussian broadening (convolution).
449  // Hold parameter 5 at 0 to fit just one peak.
450  // Conventional fit function for use with the curve-fitting dialog.
451  // Compared to DoniachSunjicBroadS this function incurs extra overhead
452  // because auxiliary waves are created and killed between function calls.
453  // See also DoniachSunjicBroadS (optimized structural fit function)
454  Wave pw
455  Wave yw
456  Wave xw
457 
458  // pw[0] = bulk amplitude
459  // pw[1] = bulk position
460  // pw[2] = Lorentzian FWHM
461  // pw[3] = Donjach-Sunjic singularity index (0..1)
462  // pw[4] = surface shift
463  // pw[5] = surface/bulk ratio
464  // pw[6] = Gaussian FWHM
465  // pw[7] = constant background
466  // pw[8] = linear background
467 
468  // set up data structure
469  struct DoniachSunjicStruct fs
470  fs.precision = 5
471  fs.oversampling = 4
472 
473  wave fs.pw = pw
474  wave fs.xw = xw
475  wave fs.yw = yw
476 
477  // create temporary calculation waves in a global folder
478  dfref df = root:packages:pearl_fitfuncs:doniach_sunjic
479  if (DataFolderRefStatus(df) == 0)
480  newdatafolder root:packages:pearl_fitfuncs:doniach_sunjic
481  dfref df = root:packages:pearl_fitfuncs:doniach_sunjic
482  endif
483 
484  wave /z /sdfr=df fs.xdw = xdw
485  wave /z /sdfr=df fs.model = model
486  wave /z /sdfr=df fs.broadening = broadening
487  wave /z /sdfr=df fs.convolution = convolution
488 
489  if (WaveExists(fs.xdw) == 0)
490  dfref savedf = GetDataFolderDFR()
491  setdatafolder df
492  make /n=0 /d xdw, model, broadening, convolution
493  wave fs.xdw = xdw
494  wave fs.model = model
495  wave fs.broadening = broadening
496  wave fs.convolution = convolution
497  setdatafolder savedf
498  endif
499 
500  // calculate
502 
503  yw = fs.yw
504 };
505 
506 //------------------------------------------------------------------------------
507 variable Calc_DoniachSunjicBroad(wave pw, wave yw){
508 //------------------------------------------------------------------------------
509  // Calculate the DoniachSunjicBroadS line shape
510  Wave pw// coefficient wave
511  Wave yw// output wave, correct x-scaling required on input
512 
513  struct DoniachSunjicStruct fs
514  fs.precision = 5
515  fs.oversampling = 4
516 
517  duplicate /free pw, fs.pw
518  duplicate /free yw, fs.xw
519  fs.xw = x
520  duplicate /free yw, fs.yw
521 
523 
524  yw = fs.yw
525 };
526 
527 //------------------------------------------------------------------------------
528 variable Fit_DoniachSunjicBroad(wave pw, wave yw, wave xw, wave ww){
529 //------------------------------------------------------------------------------
530  // Fit the DoniachSunjicBroadS line shape.
531  // The function applies constraints which assume that the energy scale is in eV.
532  // Returns chi^2.
533  wave pw// coefficient wave- pre-load it with initial guess
534  wave yw
535  wave /z xw
536  wave /z ww// weights (standard deviation)
537 
538  struct DoniachSunjicStruct fs
539  fs.precision = 5
540  fs.oversampling = 4
541 
542  duplicate /free pw, fs.pw
543  if (WaveExists(xw))
544  duplicate /free xw, fs.xw
545  else
546  duplicate /free yw, fs.xw
547  fs.xw = x
548  endif
549  duplicate /free yw, fs.yw
550 
551  variable v_chisq = nan
552  variable V_FitMaxIters = 100
553  make /n=1 /t /free constraints = {"K0 >= 0", "K2 > 0", "K2 < 10", "K3 >= 0", "K3 < 1", "K4 >= -10", "K4 <= 10", "K5 >= 0", "K5 <= 1", "K6 >= 0", "K6 < 10"}
554  // note: only single thread allowed
555  FuncFit /NTHR=1 DoniachSunjicBroadS, pw, yw /X=xw /D /STRC=fs /C=constraints /NWOK /I=1 /W=ww
556 
557  return v_chisq
558 };
559 
560 //------------------------------------------------------------------------------
561 // peak-specific fit functions
562 //------------------------------------------------------------------------------
563 
564 variable Au4f(wave w, variable x){
565  // fit function for a nitrogen 1s-pi* absorption spectrum
566  // modelled as multiple Voigt shapes on a constant background
567  // similar to the Igor VoigtFit function
568  // but with a constant gaussian width (instrumental broadening) for all peaks
569  // gaussian and lorentzian widths are specified as FWHM
570  wave w// parameters
571  // w[0] constant background
572  // w[1] linear background
573  // w[2] global gaussian FWHM
574  // w[3 + 0 + (n-1) * 3] peak n area
575  // w[3 + 1 + (n-1) * 3] peak n position
576  // w[3 + 2 + (n-1) * 3] peak n lorentzian FWHM
577  // length of wave defines number of peaks
578 
579  // for compatibility with older code the linear background term can be omitted.
580  // if the number of parameters divides by 3, the linear background term is added,
581  // otherwise only the constant background.
582  variable x
583 
584  variable np = 15
585  variable ip, ip0
586 
587  variable bg = w[0]
588  variable v = bg
589  if (mod(np, 3) == 0)
590  v += w[1] * x
591  ip0 = 3
592  else
593  ip0 = 2
594  endif
595 
596  variable vc1, vc2, vc3, vc4
597  vc2 = 2 * sqrt(ln(2)) / w[ip0-1]
598  for (ip = ip0; ip < np; ip += 3)
599  vc1 = w[ip] / sqrt(pi) * vc2
600  vc3 = w[ip+1]
601  vc4 = vc2 * w[ip+2] / 2
602  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
603  endfor
604 
605  return v
606 
607 };
608 
609 variable Au4f_2p2(wave w, variable x){
610  // Au 4f 5/2 and 7/2 2-component Voigt fit with a common gaussian width
611  // gaussian and lorentzian widths are specified as FWHM
612  wave w// parameters
613  // w[0] constant background
614  // w[1] linear background
615  // w[2] global gaussian FWHM
616  // w[3] 5/2 bulk area
617  // w[4] 5/2 bulk position
618  // w[5] 5/2 lorentzian FWHM
619  // w[6] 7/2 bulk area
620  // w[7] 7/2 bulk position
621  // w[8] 7/2 lorentzian FWHM
622  // w[9] surface/bulk area ratio
623  // w[10] surface core level shift
624  variable x
625 
626  variable bg = w[0] + w[1] * x
627  variable v = bg
628 
629  variable vc1// amplitude
630  variable vc2// width
631  variable vc3// position
632  variable vc4// shape
633  vc2 = 2 * sqrt(ln(2)) / w[2]
634 
635  // 5/2 bulk
636  vc1 = w[3] / sqrt(pi) * vc2
637  vc3 = w[4]
638  vc4 = vc2 * w[5] / 2
639  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
640 
641  // 5/2 surface
642  vc1 = w[3] / sqrt(pi) * vc2 * w[9]
643  vc3 = w[4] + w[10]
644  vc4 = vc2 * w[5] / 2
645  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
646 
647  // 7/2 bulk
648  vc1 = w[6] / sqrt(pi) * vc2
649  vc3 = w[7]
650  vc4 = vc2 * w[8] / 2
651  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
652 
653  // 7/2 surface
654  vc1 = w[6] / sqrt(pi) * vc2 * w[9]
655  vc3 = w[7] + w[10]
656  vc4 = vc2 * w[8] / 2
657  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
658 
659  return v
660 
661 };
662 
663 variable ShowComponents_Au4f_2p2(wave coef_wave, wave fit_wave){
664  wave coef_wave
665  wave fit_wave
666 
667  duplicate /free coef_wave, coef1, coef2
668  coef1[9] = 0
669  coef2[3] *= coef_wave[9]
670  coef2[4] += coef_wave[10]
671  coef2[6] *= coef_wave[9]
672  coef2[7] += coef_wave[10]
673  coef2[9] = 0
674 
675  string s_fit_wave = NameOfWave(fit_wave)
676  string s_fit_p1 = s_fit_wave + "_p1"
677  string s_fit_p2 = s_fit_wave + "_p2"
678  duplicate /o fit_wave, $(s_fit_p1) /wave=fit_p1
679  duplicate /o fit_wave, $(s_fit_p2) /wave=fit_p2
680 
681  fit_p1 = Au4f_2p2(coef1, x)
682  fit_p2 = Au4f_2p2(coef2, x)
683 
684  string traces = TraceNameList("", ";", 1)
685  if ((WhichListItem(s_fit_wave, traces, ";") >= 0) && (WhichListItem(s_fit_p1, traces, ";") < 0))
686  appendtograph fit_p1, fit_p2
687  ModifyGraph lstyle($s_fit_p1)=2
688  ModifyGraph lstyle($s_fit_p2)=2
689  ModifyGraph rgb($s_fit_p1)=(0,0,65280)
690  ModifyGraph rgb($s_fit_p2)=(0,0,65280)
691  endif
692 };
693 
694 variable Au4f_2p3(wave w, variable x){
695  // Au 4f 5/2 and 7/2 3-component Voigt fit with a common gaussian width
696  // gaussian and lorentzian widths are specified as FWHM
697  wave w// parameters
698  // w[0] constant background
699  // w[1] linear background
700  // w[2] global gaussian FWHM
701  // w[3] 5/2 bulk area
702  // w[4] 5/2 bulk position
703  // w[5] 5/2 lorentzian FWHM
704  // w[6] 7/2 bulk area
705  // w[7] 7/2 bulk position
706  // w[8] 7/2 lorentzian FWHM
707  // w[9] surface/bulk area ratio
708  // w[10] surface core level shift
709  // w[11] 2nd layer/bulk area ratio
710  // w[12] 2nd layer core level shift
711  variable x
712 
713  variable bg = w[0] + w[1] * x
714  variable v = bg
715 
716  variable vc1// amplitude
717  variable vc2// width
718  variable vc3// position
719  variable vc4// shape
720  vc2 = 2 * sqrt(ln(2)) / w[2]
721 
722  // 5/2 bulk
723  vc1 = w[3] / sqrt(pi) * vc2
724  vc3 = w[4]
725  vc4 = vc2 * w[5] / 2
726  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
727 
728  // 5/2 surface
729  vc1 = w[3] / sqrt(pi) * vc2 * w[9]
730  vc3 = w[4] + w[10]
731  vc4 = vc2 * w[5] / 2
732  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
733 
734  // 5/2 2nd layer
735  vc1 = w[3] / sqrt(pi) * vc2 * w[11]
736  vc3 = w[4] + w[12]
737  vc4 = vc2 * w[5] / 2
738  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
739 
740  // 7/2 bulk
741  vc1 = w[6] / sqrt(pi) * vc2
742  vc3 = w[7]
743  vc4 = vc2 * w[8] / 2
744  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
745 
746  // 7/2 surface
747  vc1 = w[6] / sqrt(pi) * vc2 * w[9]
748  vc3 = w[7] + w[10]
749  vc4 = vc2 * w[8] / 2
750  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
751 
752  // 7/2 2nd layer
753  vc1 = w[6] / sqrt(pi) * vc2 * w[11]
754  vc3 = w[7] + w[12]
755  vc4 = vc2 * w[8] / 2
756  v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
757 
758  return v
759 
760 };
761 
762 variable ShowComponents_Au4f_2p3(wave coef_wave, wave fit_wave){
763  wave coef_wave
764  wave fit_wave
765 
766  duplicate /free coef_wave, coef1, coef2, coef3
767  coef1[9] = 0
768  coef1[11] = 0
769 
770  coef2[3] *= coef_wave[9]
771  coef2[4] += coef_wave[10]
772  coef2[6] *= coef_wave[9]
773  coef2[7] += coef_wave[10]
774  coef2[9] = 0
775  coef2[11] = 0
776 
777  coef3[3] *= coef_wave[11]
778  coef3[4] += coef_wave[12]
779  coef3[6] *= coef_wave[11]
780  coef3[7] += coef_wave[12]
781  coef3[9] = 0
782  coef3[11] = 0
783 
784  string s_fit_wave = NameOfWave(fit_wave)
785  string s_fit_p1 = s_fit_wave + "_p1"
786  string s_fit_p2 = s_fit_wave + "_p2"
787  string s_fit_p3 = s_fit_wave + "_p3"
788  duplicate /o fit_wave, $(s_fit_p1) /wave=fit_p1
789  duplicate /o fit_wave, $(s_fit_p2) /wave=fit_p2
790  duplicate /o fit_wave, $(s_fit_p3) /wave=fit_p3
791 
792  fit_p1 = Au4f_2p2(coef1, x)
793  fit_p2 = Au4f_2p2(coef2, x)
794  fit_p3 = Au4f_2p2(coef3, x)
795 
796  string traces = TraceNameList("", ";", 1)
797  if ((WhichListItem(s_fit_wave, traces, ";") >= 0) && (WhichListItem(s_fit_p1, traces, ";") < 0))
798  appendtograph fit_p1, fit_p2, fit_p3
799  ModifyGraph lstyle($s_fit_p1)=2
800  ModifyGraph lstyle($s_fit_p2)=2
801  ModifyGraph lstyle($s_fit_p3)=2
802  ModifyGraph rgb($s_fit_p1)=(0,0,65280)
803  ModifyGraph rgb($s_fit_p2)=(0,0,65280)
804  ModifyGraph rgb($s_fit_p3)=(0,0,65280)
805  endif
806 };
807 
817 variable FermiGaussConv(wave pw, wave yw, wave xw){
818  WAVE pw, yw, xw
819 
820  // half width of temporary gaussian wave is pw[5] multiplied by this factor (may be fractional)
821  variable precision_g = 5
822  variable oversampling = 4
823 
824  // calculate wave spacing based on minimum spacing of desired x points
825  duplicate /free xw, xdw
826  differentiate /p xw /d=xdw
827  xdw = abs(xdw)
828  variable xd = wavemin(xdw) / oversampling
829 
830  // calculate gausswave size based on pw[5] and precision variable
831  variable x0g = abs(pw[5]) * precision_g
832  variable ng = 2 * floor(x0g / xd) + 1
833 
834  // calculate fermiwave size based on desired range for yw
835  variable emax = wavemax(xw)
836  variable emin = wavemin(xw)
837  variable x0f = max(abs(emax - pw[3]), abs(emin - pw[3])) + x0g
838  variable ne = 2 * floor(x0f / xd) + 1
839 
840  // create and calculate initial waves, normalize exponential
841  make /d /n=(ng) /free gausswave
842  make /d /n=(ne) /free fermiwave
843  setscale/i x -x0g, x0g, "", gausswave
844  setscale/i x -x0f, x0f, "", fermiwave
845 
846  gausswave = exp( - (x / pw[5] )^2 )
847  fermiwave = 1 / (exp( x / (kBoltzmann * pw[4])) + 1.0 )
848 
849  // calculate the convolution
850  duplicate /free fermiwave, resultwave
851  Convolve /a gausswave, resultwave
852  variable rmax = wavemax(resultwave)
853  resultwave /= rmax
854 
855  // prepare output
856  ng = numpnts(resultwave)
857  x0g = xd * (ng - 1) / 2
858  setscale/i x -x0g, x0g, "", resultwave
859 
860  yw = pw[2] * resultwave(xw[p] - pw[3]) + pw[0] + pw[1] * xw[p]
861 };
862 
threadsafe variable MultiGaussLinBG(wave w, variable x)
multiple gaussian peaks on a linear background fit function.
-
variable DoniachSunjicBroad(wave pw, wave yw, wave xw)
-
threadsafe variable MultiGaussLinBG_AO(wave pw, wave yw, wave xw)
multiple gaussian peaks on a linear background fit function (all at once).
- -
variable ds4_bg(wave w, variable x)
- -
variable FermiGaussConv(wave pw, wave yw, wave xw)
convolution of Fermi-Dirac distribution and a Gaussian.
-
threadsafe variable DoniachSunjicBroadS(DoniachSunjicStruct *s)
- -
threadsafe variable DoniachSunjic(variable x, variable amp, variable pos, variable sing, variable fwhm)
Doniach-Sunjic line shape.
-
variable Au4f(wave w, variable x)
-
variable Au4f_2p3(wave w, variable x)
-
variable Au4f_2p2(wave w, variable x)
-
variable ShowComponents_Au4f_2p2(wave coef_wave, wave fit_wave)
-
variable Calc_DoniachSunjicBroad(wave pw, wave yw)
-
variable ShowComponents_Au4f_2p3(wave coef_wave, wave fit_wave)
-
variable Fit_DoniachSunjicBroad(wave pw, wave yw, wave xw, wave ww)
- - - -
threadsafe variable ds2_bg(wave w, variable x)
- - -
variable ds6_bg(wave w, variable x)
- -
variable MultiDoniachSunjicLinBG(wave w, variable x)
multiple doniach-sunjic peaks on a linear background fit function.
-
threadsafe variable ds1_bg(wave w, variable x)
- -
variable MultiVoigtLinBG(wave w, variable x)
multiple voigt peaks on a linear background fit function.
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-gui-tools_8ipf.html b/doc/html/pearl-gui-tools_8ipf.html index aa5a64d..97ccab7 100644 --- a/doc/html/pearl-gui-tools_8ipf.html +++ b/doc/html/pearl-gui-tools_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-gui-tools.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
pearl-gui-tools.ipf File Reference

Go to the source code of this file.

- - - - - - - - -

-Functions

variable display_progress_panel (string title, string message, variable progress_max)
 
variable update_progress_panel (variable progress, string message=defaultValue, variable progress_max=defaultValue)
 
variable kill_progress_panel ()
 
-

Function Documentation

- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable display_progress_panel (string title,
string message,
variable progress_max 
)
-
- -

Definition at line 18 of file pearl-gui-tools.ipf.

- -
-
- -
-
- - - - - - - -
variable kill_progress_panel ()
-
- -

Definition at line 50 of file pearl-gui-tools.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable update_progress_panel (variable progress,
string message = defaultValue,
variable progress_max = defaultValue 
)
-
- -

Definition at line 32 of file pearl-gui-tools.ipf.

- -
-
diff --git a/doc/html/pearl-gui-tools_8ipf_source.html b/doc/html/pearl-gui-tools_8ipf_source.html index efda9ac..e563545 100644 --- a/doc/html/pearl-gui-tools_8ipf_source.html +++ b/doc/html/pearl-gui-tools_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-gui-tools.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma IgorVersion = 6.1
3 #pragma ModuleName = PearlGuiTools
4 #pragma version = 1.01
5 
6 // Miscellaneous GUI tools
7 // * progress bar
8 
9 // created: matthias.muntwiler@psi.ch, 2013-11-14
10 // Copyright (c) 2013 Paul Scherrer Institut
11 // $Id$
12 
13 // Licensed under the Apache License, Version 2.0 (the "License");
14 // you may not use this file except in compliance with the License.
15 // You may obtain a copy of the License at
16 // http://www.apache.org/licenses/LICENSE-2.0
17 
18 variable display_progress_panel(string title, string message, variable progress_max){
19  string title
20  string message
21  variable progress_max
22 
23  NewPanel /K=1 /N=ProgressPanel /W=(200,200,402,260) as title
24  TitleBox t_message,pos={2,2},size={189,13},title=message
25  TitleBox t_message,frame=0
26  ValDisplay vd_progress,pos={2,20},size={198,13}
27  ValDisplay vd_progress,limits={0,progress_max,0},barmisc={0,0},mode= 3,value= _NUM:0
28  Button b_abort,pos={74,38},size={50,20},title="Abort"
29  DoUpdate /W=ProgressPanel /E=1
30 };
31 
32 variable update_progress_panel(variable progress, string message = defaultValue, variable progress_max = defaultValue){
33  // returns true if the user clicked the Abort button
34  variable progress
35  string message
36  variable progress_max
37 
38  if (!ParamIsDefault(message))
39  TitleBox t_message,title=message,win=ProgressPanel
40  endif
41  if (ParamIsDefault(progress_max))
42  ValDisplay vd_progress,value=_NUM:progress,win=ProgressPanel
43  else
44  ValDisplay vd_progress,limits={0,progress_max,0},value=_NUM:progress,win=ProgressPanel
45  endif
46  DoUpdate /W=ProgressPanel
47  return (v_flag == 2)
48 };
49 
51  KillWindow ProgressPanel
52 };
53 
variable kill_progress_panel()
-
variable display_progress_panel(string title, string message, variable progress_max)
-
variable update_progress_panel(variable progress, string message=defaultValue, variable progress_max=defaultValue)
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-matrix-import_8ipf.html b/doc/html/pearl-matrix-import_8ipf.html index 35dc795..088d2c1 100644 --- a/doc/html/pearl-matrix-import_8ipf.html +++ b/doc/html/pearl-matrix-import_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-matrix-import.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
pearl-matrix-import.ipf File Reference
-

data file import for omicron matrix (STM) files -More...

-

Go to the source code of this file.

- - - - - -

-Data Structures

struct  errorCode
 from matrixfilereader help More...
 
- - - - -

-Namespaces

 PearlMatrixImport
 data file import for omicron matrix (STM) files
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

static variable init_package ()
 initialize the package data folder. More...
 
static variable check_package_folder ()
 check that the package data folder exists More...
 
static variable AfterFileOpenHook (variable refNum, string file, string pathName, string type, string creator, variable kind)
 initialize the package and reload preferences after an experiment is loaded. More...
 
static variable BeforeFileOpenHook (variable refNum, string fileName, string path, string type, string creator, variable kind)
 open a matrix file that was dropped into Igor. More...
 
string matrix_format_elog_message (wave metadata)
 generate elog message from bricklet metadata More...
 
variable matrix_preview_2d (wave data, wave metadata)
 
static wave preview_matrix_file (string filename)
 load the preview of a Matrix data file More...
 
static variable initStruct (errorCode *errorCode)
 from matrixfilereader help More...
 
variable mtrx_load_all ()
 load all data from a Matrix data file. More...
 
variable mtrx_parse_filename (string fileName, string *resultFile, variable *runCycle, variable *scanCycle, string *channel)
 parse matrix file names More...
 
string mtrx_split_filename (string fileName, string *prefix, string *datepart, string *timepart)
 split a matrix filename and return the first three parts More...
 
dfr mtrx_create_folder (string fileName, dfref df_base=defaultValue)
 create or look up a data folder based on a matrix file name. More...
 
dfr mtrx_get_cycle_folder (dfref df_base=defaultValue, variable runCycle=defaultValue, variable scanCycle=defaultValue)
 create a data folder for bricklet data. More...
 
variable mtrx_file_brickletID (string resultFile, variable runCycle, variable scanCycle, string channel)
 find out bricklet ID of a file More...
 
variable mtrx_open_file (string pathName, string fileNameOrPath)
 open a matrix result or data file More...
 
string mtrx_load_preview (string destName, string pathName, string fileName, string traces=defaultValue)
 load a preview image from a Matrix data file. More...
 
string mtrx_load_file (string pathName, string fileName, string traces=defaultValue)
 load all data from a Matrix data file. More...
 
variable mtrx_scale_dataset (wave data)
 
string mtrx_load_info (string APathName, string AFileName)
 load descriptive info from a Matrix data file. More...
 
variable subtract_line_bg (wave img)
 remove linear background line-by-line More...
 
- - - - - - - -

-Variables

static const string package_name = "pearl_matrix_import"
 
static const string package_path = "root:packages:pearl_matrix_import:"
 
static const string ks_filematch_mtrx = "*_mtrx"
 
-

Detailed Description

-

data file import for omicron matrix (STM) files

-

the matrix file import requires the matrix file reader XOP by thomas braun (http://www.igorexchange.com/project/matrixFileReader) which in turn requires an installation of vernissage by omicron nanotechnology.

-
Warning
EXPERIMENTAL the matrix import module and its interface may change radically in future revisions!
-
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
- - -

Definition in file pearl-matrix-import.ipf.

-

Function Documentation

- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable AfterFileOpenHook (variable refNum,
string file,
string pathName,
string type,
string creator,
variable kind 
)
-
-static
-
- -

initialize the package and reload preferences after an experiment is loaded.

- -

Definition at line 85 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static variable BeforeFileOpenHook (variable refNum,
string fileName,
string path,
string type,
string creator,
variable kind 
)
-
-static
-
- -

open a matrix file that was dropped into Igor.

-

preliminary implementation. this should rather load the entire file and display a preview. graph windows should be reused by subsequent loads. also decide on a data saving location.

- -

Definition at line 102 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable check_package_folder ()
-
-static
-
- -

check that the package data folder exists

-

initialize the package if the folder does not exist.

- -

Definition at line 72 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - -
static variable init_package ()
-
-static
-
- -

initialize the package data folder.

- -

Definition at line 45 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static variable initStruct (errorCodeerrorCode)
-
-static
-
- -

from matrixfilereader help

- -

Definition at line 212 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - -
string matrix_format_elog_message (wave metadata)
-
- -

generate elog message from bricklet metadata

-
Parameters
- - -
metadatatwo-column text wave
-
-
- -

Definition at line 120 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable matrix_preview_2d (wave data,
wave metadata 
)
-
- -

Definition at line 145 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
dfr mtrx_create_folder (string fileName,
dfref df_base = defaultValue 
)
-
- -

create or look up a data folder based on a matrix file name.

-

the name of the folder is mtrx_date_time, where date and time are parsed from the file name. for this to work, the file name must consist of at least three parts that are separated by dash or underscore. the second (third) part contains the date (time). date and time are copied as strings.

-

if the data folder exists, a reference to the existing folder is returned.

-
Parameters
- - - -
fileNamename of the result or data file.
df_base(optional) base data folder. default: current folder.
-
-
-
Returns
reference of the newly created or existing data folder.
- -

Definition at line 360 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable mtrx_file_brickletID (string resultFile,
variable runCycle,
variable scanCycle,
string channel 
)
-
- -

find out bricklet ID of a file

-
Warning
EXPERIMENTAL the code of this function is inefficient. the function may be removed in a later version.
-
Parameters
- - - - - -
resultFilebase name of result file without chain link number and extension. as returned by mtrx_parse_filename.
runCyclerequested run cycle. 0 = first available.
scanCyclerequested scan cycle. 0 = first available.
channelchannel name. for example: "I", "Z", "Aux(V)", etc. empty string: first available.
-
-
-
Returns
bricklet ID, or -1 if an error occurred.
- -

Definition at line 461 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
dfr mtrx_get_cycle_folder (dfref df_base = defaultValue,
variable runCycle = defaultValue,
variable scanCycle = defaultValue 
)
-
- -

create a data folder for bricklet data.

-

the name of the folder is, for example "r23s2" where the first (second) number is the run (scan) cycle. run cycle and scan cycle numbers are taken from the open matrix file unless overridden by optional arguments.

-

if the data folder exists, a reference to the existing folder is returned. if one of the run or scan cycle numbers is lower than 1, the base folder is returned.

-
Parameters
- - - - -
df_base(optional) base data folder. default: current folder.
runCycle(optional) run cycle number. must be >= 1. default: from last mtrx_open_file call.
scanCycle(optional) scan cycle number. must be >= 1. default: from last mtrx_open_file call.
-
-
-
Returns
reference of the newly created or existing data folder.
- -

Definition at line 405 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - -
variable mtrx_load_all ()
-
- -

load all data from a Matrix data file.

- -

Definition at line 231 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
string mtrx_load_file (string pathName,
string fileName,
string traces = defaultValue 
)
-
- -

load all data from a Matrix data file.

-

the data wave is loaded into a sub-subfolder the current data folder. the relative path has the format ":mtrx_{date}_{time}:r{run_cycle}s{scan_cycle}", where the parameters {date}, {time}, {run_cycle} and {scan_cycle} are copied from the file name. the file name must be formatted according to the specifications set out below.

-
Parameters
- - - - -
pathNameigor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
fileNameif empty a dialog box shows up the file name must adhere to the format "{prefix}-{date}-{time}-{anything}--{run_cycle}_{scan_cycle}.{extension}". the first three seperators can alternatively be underscores. it may be necessary to change the configuration of the Matrix application.
traces(currently not used) semicolon-separated list of preferred traces. the items of the list are match strings for the Igor StringMatch function. only matching traces are loaded from the file. default: "*Up;*Down;*ReUp;*ReDown;"
-
-
-
Returns
semicolon-separated list of loaded waves including partial path from current data folder.
- -

Definition at line 767 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
string mtrx_load_info (string APathName,
string AFileName 
)
-
- -

load descriptive info from a Matrix data file.

-

the info string lists the following information for each scan contained in the file:

    -
  • path of the scan group inside the file.
  • -
  • number of scan positions.
  • -
  • dataset names of scan positioners.
  • -
  • dataset names of detectors.
  • -
-
Parameters
- - - -
APathNameigor symbolic path name. can be empty if the path is specified in AFileName or a dialog box should be displayed
AFileNameif empty a dialog box shows up
-
-
-
Returns
newline terminated string.
- -

Definition at line 863 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string mtrx_load_preview (string destName,
string pathName,
string fileName,
string traces = defaultValue 
)
-
- -

load a preview image from a Matrix data file.

-

the data wave is loaded into the current data folder.

-
Parameters
- - - - - -
destNamedestination wave name. the wave is created in the current data folder.
pathNameigor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
fileNameif empty a dialog box shows up the file name must adhere to the format "{prefix}-{date}-{time}-{anything}--{run_cycle}_{scan_cycle}.{extension}". the first three seperators can alternatively be underscores. it may be necessary to change the configuration of the Matrix application.
traces(currently not used) semicolon-separated list of preferred traces. the items of the list are match strings for the Igor StringMatch function. only the first matching trace is loaded from the file. default: "*Up;*Down;*ReUp;*ReDown;"
-
-
-
Returns
semicolon-separated list of loaded waves including partial path from current data folder.
- -

Definition at line 682 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable mtrx_open_file (string pathName,
string fileNameOrPath 
)
-
- -

open a matrix result or data file

-

this function opens a matrix result file (.mtrx) or data file (.*_mtrx).

-

if a data file is selected, the function locates the corresponding result file, opens it, and looks up the bricklet ID of the data file. if a result file is selected, the function opens it but does not look up bricklet IDs.

-

the result file remains open and can be accessed using the mtrx_ functions or MFR_ operations. once a result file is open, you can easily access any bricklets linked to it, i.e., any run cycle, scan cycle, and channel.

-

the function stores information about the opened file in a global package data folder. if the same result file is opened again later, the information is reused and the file not read again. this may cause problems if the file has been modified in the meantime, or if the cached data become corrupt for some reason. the function detects if a data file is not linked in the open result file, and updates the cache. in other situations it may be necessary to force a reload.

-
Todo:
fix possible cache issues, add an option to override the cache.
-
Parameters
- - - -
pathNameigor path name or empty string.
fileNamefile name, with or without path, or empty string.
-
-
-
Returns
file type
    -
  • 0 result file (logbook)
  • -
  • 1 result data file (bricklet)
  • -
  • -1 error, no data loaded
  • -
  • -2 matrixfilereader.xop not installed
  • -
-
- -

Definition at line 545 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable mtrx_parse_filename (string fileName,
string * resultFile,
variable * runCycle,
variable * scanCycle,
string * channel 
)
-
- -

parse matrix file names

-

parse matrix file names for result name, run cycle, scan cycle, and channel.

-
Parameters
- - - - - - -
fileNamematrix result or data file name (without path).
resultFile(out) base name of the result file. append "_%04u.mtrx" to get the actual result file. we do not know the chain link number at this stage.
runCycle(out) run cycle number. necessary to look up the bricklet ID.
scanCycle(out) scan cycle number. necessary to look up the bricklet ID.
channel(out) channel name.
-
-
-
Returns
file type
    -
  • 0 result file (logbook)
  • -
  • 1 result data file (bricklet)
  • -
-result file names look like: default_2015Apr20-124353_STM-STM_AtomManipulation_0001.mtrx, default_2015Apr20-124353_STM-STM_AtomManipulation_0002.mtrx, etc. the function returns the first part up to the experiment name ("AtomManipulation" in the examples). all other return values set to defaults and must not be regarded.
-

result data files look like: default_2015Apr20-124353_STM-STM_AtomManipulation–136_1.Aux1(V)_mtrx, default_2015Apr20-124353_STM-STM_AtomManipulation–136_1.I(V)_mtrx, default_2015Apr20-124353_STM-STM_AtomManipulation–14_1.I_mtrx, default_2015Apr20-124353_STM-STM_AtomManipulation–14_1.Z_mtrx, etc. the function returns all results as described in the parameter list.

- -

Definition at line 294 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - -
variable mtrx_scale_dataset (wave data)
-
- -

Definition at line 829 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string mtrx_split_filename (string fileName,
string * prefix,
string * datepart,
string * timepart 
)
-
- -

split a matrix filename and return the first three parts

-

we assume that the second (third) part contains the date (time). the parts are separated by dash or underscore.

- -

Definition at line 332 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static wave preview_matrix_file (string filename)
-
-static
-
- -

load the preview of a Matrix data file

-

the preview is loaded to the preview_image wave in the pearl_explorer data folder.

-

the s_file_info string is updated with information about the scan dimensions.

-
Parameters
- - -
filenamename of a file in the directory specified by the pearl_explorer_filepath path object.
-
-
-
Returns
wave reference of the preview image
- -

Definition at line 170 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - - - - -
variable subtract_line_bg (wave img)
-
- -

remove linear background line-by-line

- -

Definition at line 886 of file pearl-matrix-import.ipf.

- -
-
-

Variable Documentation

- -
-
- - - - - -
- - - - -
const string ks_filematch_mtrx = "*_mtrx"
-
-static
-
- -

Definition at line 40 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string package_name = "pearl_matrix_import"
-
-static
-
- -

Definition at line 37 of file pearl-matrix-import.ipf.

- -
-
- -
-
- - - - - -
- - - - -
const string package_path = "root:packages:pearl_matrix_import:"
-
-static
-
- -

Definition at line 38 of file pearl-matrix-import.ipf.

- -
-
diff --git a/doc/html/pearl-matrix-import_8ipf_source.html b/doc/html/pearl-matrix-import_8ipf_source.html index 86f42c9..9cbdae0 100644 --- a/doc/html/pearl-matrix-import_8ipf_source.html +++ b/doc/html/pearl-matrix-import_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-matrix-import.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3
2 #pragma version = 1.00
3 #pragma IgorVersion = 6.36
4 #pragma ModuleName = PearlMatrixImport
5 
6 // author: matthias.muntwiler@psi.ch
7 // Copyright (c) 2016 Paul Scherrer Institut
8 
9 // Licensed under the Apache License, Version 2.0 (the "License");
10 // you may not use this file except in compliance with the License.
11 // You may obtain a copy of the License at
12 // http://www.apache.org/licenses/LICENSE-2.0
13 
31 
36 
37 static const string package_name = "pearl_matrix_import";
38 static const string package_path = "root:packages:pearl_matrix_import:";
39 
40 static const string ks_filematch_mtrx = "*_mtrx";
41 
45 static variable init_package(){
46 
47  dfref savedf = getdatafolderdfr()
48 
49  setdatafolder root:
50  newdatafolder /o/s packages
51  newdatafolder /o/s $package_name
52 
53  variable /g loglevel = 3
54  string /g dataFilePath = ""
55  string /g resultFilePath = ""
56  variable /g runCycle = 0
57  variable /g scanCycle = 0
58  string /g channelName = ""
59  variable /g brickletID = 0
60  variable /g V_MatrixFileReaderOverwrite = 1
61  variable /g V_MatrixFileReaderFolder = 0
62  variable /g V_MatrixFileReaderDouble = 0
63 
64  setdatafolder savedf
65  return 0
66 };
67 
72 static variable check_package_folder(){
73  dfref df_pack = $(package_path)
74  if (DataFolderRefStatus(df_pack))
75  svar /sdfr=df_pack /z resultFilePath
76  if (!svar_exists(resultFilePath))
77  init_package()
78  endif
79  else
80  init_package()
81  endif
82 };
83 
85 static variable AfterFileOpenHook(variable refNum, string file, string pathName, string type, string creator, variable kind){
86  Variable refNum,kind
87  String file,pathName,type,creator
88  if( (kind >= 1) && (kind <= 2))
89  init_package()
90  //load_prefs()
91  endif
92  return 0
93 };
94 
102 static variable BeforeFileOpenHook(variable refNum, string fileName, string path, string type, string creator, variable kind){
103  Variable refNum,kind
104  String fileName,path,type,creator
105 
106  Variable handledOpen = 0
107  if (StringMatch(fileName, ks_filematch_mtrx))
108  setdatafolder root:
109  newdatafolder /o /s matrix
110  mtrx_load_preview("matrix", path, fileName)
111  handledOpen = 1
112  endif
113  return handledOpen
114 };
115 
120 string matrix_format_elog_message(wave metadata){
121  wave /t metadata
122 
123  string key
124  string value
125  variable nkeys = dimsize(metadata, 0)
126  variable ikey
127  string message_keys
128  message_keys = "resultFileName;sampleName;channelName;"
129  message_keys += "XYScanner.Points.value;XYScanner.Raster_Time.value;XYScanner.Raster_Time.unit;XYScanner.Width.value;XYScanner.Width.unit;XYScanner.Height.value;XYScanner.Height.unit;"
130  message_keys += "GapVoltageControl.Voltage.value;GapVoltageControl.Voltage.unit;"
131  message_keys += "Regulator.Loop_Gain_1_I.value;Regulator.Loop_Gain_1_I.unit;Regulator.Setpoint_1.value;Regulator.Setpoint_1.unit;"
132  message_keys += "Spectroscopy.Device_1_Start.value;Spectroscopy.Device_1_Start.unit;Spectroscopy.Spectroscopy_Mode.value;"
133  string message
134 
135  message_keys = ""
136  for (ikey = 0; ikey < nkeys; ikey += 1)
137  key = metadata[ikey][0]
138  value = metadata[ikey][1]
139  if (WhichListItem(key, message_keys) >= 0)
140  message += key + " = " + value + "\r"
141  endif
142  endfor
143 };
144 
145 variable matrix_preview_2d(wave data, wave metadata){
146  wave data
147  wave /t metadata
148 
149  Display
150  AppendImage data
151  ModifyImage data ctab= {*,*,Mud,0}
152  ModifyGraph margin(left)=30,margin(bottom)=30,margin(top)=5,margin(right)=5,height={Plan,1,left,bottom}
153  ModifyGraph mirror=2
154  ModifyGraph nticks=3
155  ModifyGraph axThick=0.5
156  ModifyGraph btLen=4
157 
158 };
159 
170 static wave preview_matrix_file(string filename){
171  string filename
172 
173  dfref saveDF = GetDataFolderDFR()
174  setdatafolder $package_path
175  svar s_preview_file
176  svar s_preview_source
177  mtrx_load_preview("preview_image", "pearl_explorer_filepath", filename)
178  s_preview_file = filename
179  s_preview_source = ""
180  wave /z preview_image
181 
182  svar /z s_file_info
183  if (! svar_exists(s_file_info))
184  string /g s_file_info
185  endif
186  if (strlen(s_preview_file) > 0)
187  s_file_info = mtrx_load_info("pearl_explorer_filepath", filename)
188  else
189  s_file_info = ""
190  endif
191 
192  setdatafolder saveDF
193  return preview_image
194 };
195 
197 struct errorCode{;
198  int32 SUCCESS;
208  int32 WAVE_EXIST;
209 };
210 
212 static variable initStruct(errorCode* errorCode){
213  Struct errorCode &errorCode
214 
215  errorCode.SUCCESS =0
216  errorCode.UNKNOWN_ERROR=10001
217  errorCode.ALREADY_FILE_OPEN=10002
218  errorCode.EMPTY_RESULTFILE=10004
219  errorCode.FILE_NOT_READABLE=10008
220  errorCode.NO_NEW_BRICKLETS=10016
221  errorCode.WRONG_PARAMETER=10032
222  errorCode.INTERNAL_ERROR_CONVERTING_DATA=10064
223  errorCode.NO_FILE_OPEN=10128
224  errorCode.INVALID_RANGE=10256
225  errorCode.WAVE_EXIST=10512
226 
227 };
228 
231 variable mtrx_load_all(){
232 
233  struct errorCode errorCode
234  initStruct(errorCode)
235 
236 #if exists("MFR_OpenResultFile")
237  MFR_OpenResultFile
238  if(V_flag != errorCode.SUCCESS)
239  MFR_GetXOPErrorMessage
240  return -1
241  endif
242 
243  MFR_GetBrickletData
244  if(V_flag != errorCode.SUCCESS)
245  MFR_GetXOPErrorMessage
246  return -1
247  endif
248 
249  MFR_GetBrickletMetaData
250  if(V_flag != errorCode.SUCCESS)
251  MFR_GetXOPErrorMessage
252  return -1
253  endif
254 
255  return 0
256 #else
257  return -1
258 #endif
259 };
260 
294 variable mtrx_parse_filename(string fileName, string* resultFile, variable* runCycle, variable* scanCycle, string* channel){
295  string fileName
296  string &resultFile
297  variable &runCycle
298  variable &scanCycle
299  string &channel
300 
301  variable fileType = 0
302  resultFile = ""
303  channel = ""
304  runCycle = 0
305  scanCycle = 0
306 
307  string regexp = ""
308  string index1 = ""
309  string index2 = ""
310  string extension = ""
311 
312  if (StringMatch(fileName, "*.mtrx"))
313  regexp = "(.+)_([[:digit:]]+)\.(.+)"
314  SplitString /E=regexp fileName, resultFile, index1, extension
315  fileType = 0
316  else
317  regexp = "(.+)--([[:digit:]]+)_([[:digit:]]+)\.((.+)_mtrx)"
318  SplitString /E=regexp fileName, resultFile, index1, index2, extension, channel
319  fileType = 1
320  runCycle = str2num(index1)
321  scanCycle = str2num(index2)
322  endif
323 
324  return fileType
325 };
326 
332 string mtrx_split_filename(string fileName, string* prefix, string* datepart, string* timepart){
333  string fileName
334  string &prefix
335  string &datepart
336  string &timepart
337 
338  string regexp
339  regexp = "([[:alpha:][:digit:]]+)[-_]([[:alpha:][:digit:]]+)[-_]([[:alpha:][:digit:]]+)[-_].+"
340  SplitString /E=regexp fileName, prefix, datepart, timepart
341  return datepart
342 };
343 
360 dfr mtrx_create_folder(string fileName, dfref df_base = defaultValue){
361  string fileName
362  dfref df_base
363 
364  if (ParamIsDefault(df_base))
365  df_base = GetDataFolderDFR()
366  endif
367 
368  string prefix
369  string datepart
370  string timepart
371  string folderName
372 
373  mtrx_split_filename(fileName, prefix, datepart, timepart)
374  folderName = "mtrx_" + datepart + "_" + timepart
375  folderName = CleanupName(folderName, 0)
376 
377  dfref df_save = GetDataFolderDFR()
378  setdatafolder root:
379  newdatafolder /o /s $foldername
380  dfref df = GetDataFolderDFR()
381 
382  setdatafolder df_save
383  return df
384 };
385 
405 dfr mtrx_get_cycle_folder(dfref df_base = defaultValue, variable runCycle = defaultValue, variable scanCycle = defaultValue){
406  dfref df_base
407  variable runCycle
408  variable scanCycle
409 
410  dfref df_save = GetDataFolderDFR()
411  dfref df_pack = $(package_path)
412  if (ParamIsDefault(df_base))
413  df_base = GetDataFolderDFR()
414  endif
415  if (ParamIsDefault(runCycle))
416  nvar /sdfr=df_pack defRunCycle = runCycle
417  runCycle = defRunCycle
418  endif
419  if (ParamIsDefault(scanCycle))
420  nvar /sdfr=df_pack defScanCycle = scanCycle
421  scanCycle = defScanCycle
422  endif
423 
424  string dfname
425  if ((runCycle >= 1) && (scanCycle >= 1))
426  sprintf dfname, "r%us%u", runCycle, scanCycle
427  setdatafolder df_base
428  dfref df = $dfname
429  if (DataFolderRefStatus(df) == 0)
430  newdatafolder $dfname
431  dfref df = $dfname
432  endif
433  else
434  dfref df = df_base
435  endif
436 
437  setdatafolder df_save
438  return df
439 };
440 
461 variable mtrx_file_brickletID(string resultFile, variable runCycle, variable scanCycle, string channel){
462  string resultFile
463  variable runCycle
464  variable scanCycle
465  string channel
466 
467  dfref df_overview = NewFreeDataFolder()
468  variable link = 1
469  variable id = -1
470  variable idx = 0
471 
472  string resultFileName
473 #if exists("MFR_OpenResultFile")
474  struct errorCode errorCode
475  initStruct(errorCode)
476  do
477  sprintf resultFileName, "%s_%04u.mtrx", resultFile, link
478  MFR_OpenResultFile /K resultFileName
479  if(V_flag != errorCode.SUCCESS)
480  return -1
481  endif
482  MFR_CreateOverviewTable /DEST=df_overview
483  // dimension labels are: brickletID, scanCycleCount, runCycleCount, sequenceID, dimension, channelName
484  wave /t /sdfr=df_overview overviewTable
485  make /n=(dimsize(overviewTable, 0)) /i /u /free runcycles, scancycles, ids, match
486  make /n=(dimsize(overviewTable, 0)) /t /free channels
487  ids = str2num(overviewtable[p][%brickletID])
488  if (runcycle > 0)
489  runcycles = str2num(overviewtable[p][%runCycleCount])
490  else
491  runcycles = runcycle
492  endif
493  if (scancycle > 0)
494  scancycles = str2num(overviewtable[p][%scanCycleCount])
495  else
496  scancycles = scancycle
497  endif
498  if (strlen(channel) > 0)
499  channels = overviewTable[p][%channelName]
500  else
501  channels = channel
502  endif
503  Extract /FREE ids, match_ids, (scancycles == scanCycle) && (runcycles == runCycle) && (cmpstr(channels, channel) == 0)
504  if (numpnts(match_ids) > 0)
505  id = match_ids[0]
506  else
507  link += 1
508  endif
509  while (id < 0)
510 #endif
511  return id
512 };
513 
545 variable mtrx_open_file(string pathName, string fileNameOrPath){
546  string pathName
547  string fileNameOrPath
548 
549  check_package_folder()
550  dfref df_save = GetDataFolderDFR()
551  dfref df_pack = $(package_path)
552  svar /sdfr=df_pack dataFilePath
553  svar /sdfr=df_pack resultFilePath
554  nvar /sdfr=df_pack runCycle
555  nvar /sdfr=df_pack scanCycle
556  svar /sdfr=df_pack channelName
557  nvar /sdfr=df_pack brickletID
558 
559  string loc_resultFileName
560  string loc_resultFilePath
561  variable loc_runCycle
562  variable loc_scanCycle
563  string loc_channelName
564 
565  // make sure we have a valid and complete file path
566  GetFileFolderInfo /P=$pathName /Q /Z=2 fileNameOrPath
567  string filePath
568  if ((v_flag == 0) && (v_isFile))
569  filePath = s_path
570  else
571  return -1
572  endif
573 
574  // get base file name
575  string fileName
576  string fileDir
577  string baseFileName
578  variable fileType
579  fileName = ParseFilePath(0, filePath, ":", 1, 0)
580  fileDir = ParseFilePath(1, filePath, ":", 1, 0)
581  fileType = mtrx_parse_filename(fileName, baseFileName, loc_runCycle, loc_scanCycle, loc_channelName)
582 
583  variable link = 1
584  variable id = -1
585  variable result = -1
586  variable using_cache = 0
587 
588  struct errorCode errorCode
589  initStruct(errorCode)
590  do
591  sprintf loc_resultFileName, "%s_%04u.mtrx", baseFileName, link
592  loc_resultFilePath = fileDir + loc_resultFileName
593 #if exists("MFR_OpenResultFile")
594  if ((strlen(resultFilePath) == 0) || (cmpstr(loc_resultFilePath, resultFilePath) != 0))
595  MFR_OpenResultFile /K loc_resultFilePath
596  if(V_flag != errorCode.SUCCESS)
597  MFR_GetXOPErrorMessage
598  result = -1
599  break
600  endif
601  resultFilePath = loc_resultFilePath
602  if (fileType == 1)
603  dataFilePath = filePath
604  else
605  dataFilePath = ""
606  endif
607  runCycle = 0
608  scanCycle = 0
609  channelName = ""
610  brickletID = 0
611  MFR_CreateOverviewTable /DEST=df_pack
612  if(V_flag != errorCode.SUCCESS)
613  MFR_GetXOPErrorMessage
614  result = -1
615  break
616  endif
617  using_cache = 0
618  else
619  using_cache = 1
620  endif
621 #else
622  print "matrixfilereader.xop not installed"
623  result = -2
624  break
625 #endif
626  // dimension labels are: brickletID, scanCycleCount, runCycleCount, sequenceID, dimension, channelName
627  wave /t /sdfr=df_pack overviewTable
628  make /n=(dimsize(overviewTable, 0)) /i /u /o df_pack:runCycles, df_pack:scanCycles, df_pack:ids
629  make /n=(dimsize(overviewTable, 0)) /t /o df_pack:channels
630  wave /sdfr=df_pack ids, runCycles, scanCycles
631  wave /t /sdfr=df_pack channels
632  ids = str2num(overviewtable[p][%brickletID])
633  runCycles = str2num(overviewtable[p][%runCycleCount])
634  scanCycles = str2num(overviewtable[p][%scanCycleCount])
635  channels = overviewTable[p][%channelName]
636  result = fileType
637 
638  // if a data file is opened, make sure we found the right result file
639  if ((loc_runCycle > 0) && (loc_scanCycle > 0))
640  Extract /FREE ids, match_ids, (runCycles == loc_runCycle) && (scanCycles == loc_scanCycle) && (cmpstr(channels, loc_channelName) == 0)
641  if (numpnts(match_ids) > 0)
642  id = match_ids[0]
643  runCycle = loc_runCycle
644  scanCycle = loc_scanCycle
645  channelName = loc_channelName
646  brickletID = id
647  break
648  else if (using_cache)
649  resultFilePath = ""
650  else
651  link += 1
652  endif
653  else
654  break
655  endif
656  while (id < 0)
657 
658  return result
659 };
660 
682 string mtrx_load_preview(string destName, string pathName, string fileName, string traces = defaultValue){
683  string destName
684  string pathName
685  string fileName
686  string traces
687 
688  if (ParamIsDefault(traces))
689  traces = "*Up;*Down;*ReUp;*ReDown;"
690  endif
691 
692  dfref df_save = GetDataFolderDFR()
693 
694  string datanames = ""
695  string datapaths = ""
696  variable filestatus = mtrx_open_file(pathName, fileName)
697  if (filestatus != 1)
698  return ""
699  endif
700 
701  dfref df_pack = $(package_path)
702  svar /sdfr=df_pack dataFilePath
703  svar /sdfr=df_pack resultFilePath
704  nvar /sdfr=df_pack runCycle
705  nvar /sdfr=df_pack scanCycle
706  svar /sdfr=df_pack channelName
707  nvar /sdfr=df_pack brickletID
708 
709 #if exists("MFR_OpenResultFile")
710  dfref df_data = df_save
711  variable /g df_data:V_MatrixFileReaderOverwrite = 1
712  variable /g df_data:V_MatrixFileReaderFolder = 0
713  variable /g df_data:V_MatrixFileReaderDouble = 0
714  struct errorCode errorCode
715  initStruct(errorCode)
716  MFR_GetBrickletData /N=destName /R=(brickletID) /S=2 /DEST=df_data
717  if(V_flag == errorCode.SUCCESS)
718  datanames = S_waveNames
719  variable i
720  variable n = ItemsInList(datanames)
721  string s
722  s = StringFromList(0, datanames)
723  wave data = $s
724  mtrx_scale_dataset(data)
725  if (WaveDims(data) == 2)
726  subtract_line_bg(data)
727  endif
728  datapaths = AddListItem(GetWavesDataFolder(data, 4), datapaths, ";", inf)
729  for (i = 1; i < n; i += 1)
730  s = StringFromList(i, datanames)
731  killwaves /z $s
732  endfor
733  else
734  MFR_GetXOPErrorMessage
735  endif
736  //MFR_GetBrickletMetaData /N=ANickName /R=(brickletID) // /DEST=dfref
737 #else
738  print "matrixfilereader.xop not installed"
739 #endif
740 
741  setdatafolder df_save
742  return datapaths
743 };
744 
767 string mtrx_load_file(string pathName, string fileName, string traces = defaultValue){
768  string pathName
769  string fileName
770  string traces
771 
772  if (ParamIsDefault(traces))
773  traces = "*Up;*Down;*ReUp;*ReDown;"
774  endif
775 
776  dfref df_save = GetDataFolderDFR()
777 
778  string datanames = ""
779  string datapaths = ""
780  variable filestatus = mtrx_open_file(pathName, fileName)
781  if (filestatus != 1)
782  return ""
783  endif
784 
785  dfref df_pack = $(package_path)
786  svar /sdfr=df_pack dataFilePath
787  svar /sdfr=df_pack resultFilePath
788  nvar /sdfr=df_pack runCycle
789  nvar /sdfr=df_pack scanCycle
790  svar /sdfr=df_pack channelName
791  nvar /sdfr=df_pack brickletID
792 
793 #if exists("MFR_OpenResultFile")
794  string resultFileName = ParseFilePath(0, resultFilePath, ":", 1, 0)
795  dfref df_result = mtrx_create_folder(resultFileName, df_base=df_save)
796  dfref df_data = mtrx_get_cycle_folder(df_base = df_result)
797  variable /g df_data:V_MatrixFileReaderOverwrite = 1
798  variable /g df_data:V_MatrixFileReaderFolder = 0
799  variable /g df_data:V_MatrixFileReaderDouble = 0
800 
801  struct errorCode errorCode
802  initStruct(errorCode)
803  string name
804  name = CleanupName(channelName, 0)
805  MFR_GetBrickletData /N=name /R=(brickletID) /DEST=df_data
806  if(V_flag == errorCode.SUCCESS)
807  datanames = S_waveNames
808  variable i
809  variable n = ItemsInList(datanames)
810  string s
811  for (i = 0; i < n; i += 1)
812  s = StringFromList(i, datanames)
813  wave /sdfr=df_data data = $s
814  mtrx_scale_dataset(data)
815  datapaths = AddListItem(GetWavesDataFolder(data, 4), datapaths, ";", inf)
816  endfor
817  else
818  MFR_GetXOPErrorMessage
819  endif
820  //MFR_GetBrickletMetaData /N=ANickName /R=(brickletID) // /DEST=dfref
821 #else
822  print "matrixfilereader.xop not installed"
823 #endif
824 
825  setdatafolder df_save
826  return datapaths
827 };
828 
829 variable mtrx_scale_dataset(wave data){
830  wave data
831 
832  dfref df_pack = $(package_path)
833  nvar /sdfr=df_pack runCycle
834  nvar /sdfr=df_pack scanCycle
835  svar /sdfr=df_pack channelName
836  nvar /sdfr=df_pack brickletID
837 
838  string scanDir = StringFromList(2, NameOfWave(data), "_")
839  if (WaveDims(data) == 2)
840  Note data, "AxisLabelX=X"
841  Note data, "AxisLabelY=Y"
842  endif
843  Note data, "AxisLabelD=" + channelName
844  string title
845  sprintf title, "%u-%u %s %s", runCycle, scanCycle, channelName, scanDir
846  Note data, "Dataset=" + title
847 };
848 
863 string mtrx_load_info(string APathName, string AFileName){
864  string APathName
865  string AFileName
866 
867  dfref saveDF = GetDataFolderDFR()
868  dfref fileDF = NewFreeDataFolder()
869  setdatafolder fileDF
870 
871  variable fileID
872  string filepath
873  string scanpaths
874  variable nscans
875  variable iscan
876  string scanpath
877  string info = ""
878 
879 
880  setdatafolder saveDF
881  return info
882 };
883 
886 variable subtract_line_bg(wave img){
887  wave img
888 
889  variable nx = dimsize(img, 0)
890  variable ny = dimsize(img, 1)
891  variable iy
892  make /n=(nx) /free line, fit
893  for (iy = 0; iy < ny; iy += 1)
894  line = img[p][iy]
895  if (numtype(sum(line)) == 0)
896  CurveFit /N /Q /NTHR=0 line line /D=fit
897  img[][iy] = line[p] - fit[p]
898  endif
899  endfor
900 };
901 
static const string package_path
-
dfr mtrx_create_folder(string fileName, dfref df_base=defaultValue)
create or look up a data folder based on a matrix file name.
-
variable mtrx_file_brickletID(string resultFile, variable runCycle, variable scanCycle, string channel)
find out bricklet ID of a file
-
static variable initStruct(errorCode *errorCode)
from matrixfilereader help
- -
string mtrx_split_filename(string fileName, string *prefix, string *datepart, string *timepart)
split a matrix filename and return the first three parts
- -
variable matrix_preview_2d(wave data, wave metadata)
-
static wave preview_matrix_file(string filename)
load the preview of a Matrix data file
-
int32 INTERNAL_ERROR_CONVERTING_DATA
-
string mtrx_load_info(string APathName, string AFileName)
load descriptive info from a Matrix data file.
-
string matrix_format_elog_message(wave metadata)
generate elog message from bricklet metadata
-
from matrixfilereader help
-
variable mtrx_load_all()
load all data from a Matrix data file.
- -
static const string ks_filematch_mtrx
- - - -
static variable AfterFileOpenHook(variable refNum, string file, string pathName, string type, string creator, variable kind)
initialize the package and reload preferences after an experiment is loaded.
- -
dfr mtrx_get_cycle_folder(dfref df_base=defaultValue, variable runCycle=defaultValue, variable scanCycle=defaultValue)
create a data folder for bricklet data.
- -
static variable init_package()
initialize the package data folder.
-
variable mtrx_parse_filename(string fileName, string *resultFile, variable *runCycle, variable *scanCycle, string *channel)
parse matrix file names
-
string mtrx_load_preview(string destName, string pathName, string fileName, string traces=defaultValue)
load a preview image from a Matrix data file.
-
static variable BeforeFileOpenHook(variable refNum, string fileName, string path, string type, string creator, variable kind)
open a matrix file that was dropped into Igor.
-
static const string package_name
- - -
static variable check_package_folder()
check that the package data folder exists
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-menu_8ipf.html b/doc/html/pearl-menu_8ipf.html index 899436c..a223bb3 100644 --- a/doc/html/pearl-menu_8ipf.html +++ b/doc/html/pearl-menu_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-menu.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
pearl-menu.ipf File Reference

Go to the source code of this file.

- - - - - - - - - - - - - - - - - - - - -

-Functions

string PearlMenuEnableFunc (string funcname)
 
variable LoadPearlOptics ()
 
variable LoadPearlArpes ()
 
variable LoadPearlPreparation ()
 
variable Display2dProfiles ()
 
variable Display3dSlicer ()
 
variable DisplayGizmoSlicer ()
 
variable PearlLiveDisplay (string epicsname, string nickname, string wbRGB)
 
variable PearlAnglescanTracker (string epicsname, string wbRGB)
 
-

Function Documentation

- -
-
- - - - - - - -
variable Display2dProfiles ()
-
- -

Definition at line 113 of file pearl-menu.ipf.

- -
-
- -
-
- - - - - - - -
variable Display3dSlicer ()
-
- -

Definition at line 130 of file pearl-menu.ipf.

- -
-
- -
-
- - - - - - - -
variable DisplayGizmoSlicer ()
-
- -

Definition at line 149 of file pearl-menu.ipf.

- -
-
- -
-
- - - - - - - -
variable LoadPearlArpes ()
-
- -

Definition at line 101 of file pearl-menu.ipf.

- -
-
- -
-
- - - - - - - -
variable LoadPearlOptics ()
-
- -

Definition at line 94 of file pearl-menu.ipf.

- -
-
- -
-
- - - - - - - -
variable LoadPearlPreparation ()
-
- -

Definition at line 107 of file pearl-menu.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable PearlAnglescanTracker (string epicsname,
string wbRGB 
)
-
- -

Definition at line 187 of file pearl-menu.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable PearlLiveDisplay (string epicsname,
string nickname,
string wbRGB 
)
-
- -

Definition at line 168 of file pearl-menu.ipf.

- -
-
- -
-
- - - - - - - - -
string PearlMenuEnableFunc (string funcname)
-
- -

Definition at line 82 of file pearl-menu.ipf.

- -
-
diff --git a/doc/html/pearl-menu_8ipf_source.html b/doc/html/pearl-menu_8ipf_source.html index 1b9fa76..f74f3f9 100644 --- a/doc/html/pearl-menu_8ipf_source.html +++ b/doc/html/pearl-menu_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-menu.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=1// Use modern global access method.
2 #pragma ModuleName = PearlMenu
3 #pragma version = 1.02
4 
5 // main menu for PEARL data acquisition and analysis packages
6 
7 // $Id$
8 // author: matthias.muntwiler@psi.ch
9 // Copyright (c) 2013-14 Paul Scherrer Institut
10 
11 // Licensed under the Apache License, Version 2.0 (the "License");
12 // you may not use this file except in compliance with the License.
13 // You may obtain a copy of the License at
14 // http://www.apache.org/licenses/LICENSE-2.0
15 
16 
17 
18 
19 
20 
21 
22 
23 
24 
25 
26 
27 
28 
29 
30 
31 
32 
33 
34 
35 
36 
37 
38 
39 
40 
41 
42 
43 
44 
45 
46 
47 
48 
49 
50 
51 
52 
53 
54 
55 
56 
57 
58 
59 
60 
61 
62 
63 
64 
65 
66 
67 
68 
69 
70 
71 
72 
73 
74 
75 
76 
77 
78 
79 
80 
81 
82 string PearlMenuEnableFunc(string funcname){
83  // checks whether a function name exists
84  // and conditionally returns a prefix which disables the menu item
85  // if the function does not exist
86  string funcname
87  if (exists(funcname) >= 3)
88  return ""
89  else
90  return "("
91  endif
92 };
93 
94 variable LoadPearlOptics(){
95  execute /p/q/z "INSERTINCLUDE \"pearl-optics\""
96  execute /p/q/z "COMPILEPROCEDURES "
97  execute /p/q/z "PearlOpticsPanel#po_InitPanel()"
98  execute /p/q/z "BuildMenu \"PEARL\""
99 };
100 
101 variable LoadPearlArpes(){
102  execute /p/q/z "INSERTINCLUDE \"pearl-arpes\""
103  execute /p/q/z "COMPILEPROCEDURES "
104  execute /p/q/z "BuildMenu \"PEARL\""
105 };
106 
108  execute /p/q/z "INSERTINCLUDE \"pearl-preparation\""
109  execute /p/q/z "COMPILEPROCEDURES "
110  execute /p/q/z "BuildMenu \"PEARL\""
111 };
112 
113 variable Display2dProfiles(){
114  dfref dfBefore = GetDataFolderDFR()
115  Execute /q/z "CreateBrowser prompt=\"Select 2D wave\", showWaves=1, showVars=0, showStrs=0"
116  dfref dfAfter = GetDataFolderDFR()
117  SetDataFolder dfBefore
118 
119  SVAR list = S_BrowserList
120  NVAR flag = V_Flag
121 
122  if ((flag != 0) && (ItemsInList(list) >= 1))
123  string brickname = StringFromList(0, list)
124  string cmd
125  sprintf cmd, "ad_display_profiles(%s)", brickname
126  execute /q/z cmd
127  endif
128 };
129 
130 variable Display3dSlicer(){
131  dfref dfBefore = GetDataFolderDFR()
132  Execute /q/z "CreateBrowser prompt=\"Select 3D wave\", showWaves=1, showVars=0, showStrs=0"
133  dfref dfAfter = GetDataFolderDFR()
134  SetDataFolder dfBefore
135 
136  SVAR list = S_BrowserList
137  NVAR flag = V_Flag
138 
139  if ((flag != 0) && (ItemsInList(list) >= 1))
140  string brickname = StringFromList(0, list)
141  string cmd
142  sprintf cmd, "ad_display_slice(%s)", brickname
143  execute /q/z cmd
144  sprintf cmd, "ad_brick_slicer(%s)", brickname
145  execute /q/z cmd
146  endif
147 };
148 
150  dfref dfBefore = GetDataFolderDFR()
151  Execute /q/z "CreateBrowser prompt=\"Select 3D wave\", showWaves=1, showVars=0, showStrs=0"
152  dfref dfAfter = GetDataFolderDFR()
153  SetDataFolder dfBefore
154 
155  SVAR list = S_BrowserList
156  NVAR flag = V_Flag
157 
158  if ((flag != 0) && (ItemsInList(list) >= 1))
159  string brickname = StringFromList(0, list)
160  string cmd
161  sprintf cmd, "ad_display_brick(%s)", brickname
162  execute /q/z cmd
163  sprintf cmd, "ad_brick_slicer(%s)", brickname
164  execute /q/z cmd
165  endif
166 };
167 
168 variable PearlLiveDisplay(string epicsname, string nickname, string wbRGB){
169  string epicsname// base name of the detector, e.g. X03DA-SCIENTA:
170  // image1: and cam1: are appended by the function
171  // see ad_connect
172  string nickname// nick name under which this detector is referred to in Igor
173  // must be a valid data folder name
174  // see ad_connect
175  string wbRGB// window background color, e.g. "(32768,49152,55296)"
176  string cmd
177  sprintf cmd, "ad_connect(\"%s\", \"%s\")", epicsname, nickname
178  execute /q/z cmd
179  sprintf cmd, "ad_display_profiles(root:pearl_epics:%s:image)", nickname
180  execute /q/z cmd
181  sprintf cmd, "ModifyGraph wbRGB=%s", wbRGB
182  execute /q/z cmd
183  sprintf cmd, "add_roi_controls()"
184  execute /q/z cmd
185 };
186 
187 variable PearlAnglescanTracker(string epicsname, string wbRGB){
188  string epicsname// base name of the detector, e.g. X03DA-SCIENTA:
189  // image1: and cam1: are appended by the function
190  // see ast_setup
191  string wbRGB// window background color, e.g. "(32768,49152,55296)"
192  string cmd
193  sprintf cmd, "ast_setup()"
194  execute /q/z cmd
195  sprintf cmd, "ModifyGraph wbRGB=%s", wbRGB
196  execute /q/z cmd
197 };
198 
variable PearlLiveDisplay(string epicsname, string nickname, string wbRGB)
Definition: pearl-menu.ipf:168
-
variable DisplayGizmoSlicer()
Definition: pearl-menu.ipf:149
-
variable LoadPearlPreparation()
Definition: pearl-menu.ipf:107
-
variable PearlAnglescanTracker(string epicsname, string wbRGB)
Definition: pearl-menu.ipf:187
-
variable LoadPearlArpes()
Definition: pearl-menu.ipf:101
-
variable LoadPearlOptics()
Definition: pearl-menu.ipf:94
-
variable Display3dSlicer()
Definition: pearl-menu.ipf:130
-
string PearlMenuEnableFunc(string funcname)
Definition: pearl-menu.ipf:82
-
variable Display2dProfiles()
Definition: pearl-menu.ipf:113
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-otf-import_8ipf.html b/doc/html/pearl-otf-import_8ipf.html index 8d7551f..adb6cd1 100644 --- a/doc/html/pearl-otf-import_8ipf.html +++ b/doc/html/pearl-otf-import_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-otf-import.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
pearl-otf-import.ipf File Reference

Go to the source code of this file.

- - - - - - - - - - - - - - - - - - - - - - -

-Functions

variable otf_load_itx_all (string pathname)
 
variable otf_load_itx_match (string pathname, string matchstr)
 
variable otf_load_itx (string pathname, string filename)
 
variable otf_gather_iterator (dfref df, string *sdata)
 
variable otf_gather_batch (string ywavematch, string xwavematch, string destfolder)
 
variable gather_batch (string foldermatch, string ywavematch, string xwavematch, string destfolder)
 
variable otf_rename_folders_iterator (dfref df, string *sdata)
 
variable otf_rename_folders (string pattern, variable unique_index=defaultValue, string new_suffix=defaultValue, string match_str=defaultValue)
 
variable otf_interp (variable e1, variable e2, variable npts, variable smo)
 
variable otf_smo_int (wave win, wave wout, wave wpe, variable smo)
 
-

Function Documentation

- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable gather_batch (string foldermatch,
string ywavematch,
string xwavematch,
string destfolder 
)
-
- -

Definition at line 162 of file pearl-otf-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable otf_gather_batch (string ywavematch,
string xwavematch,
string destfolder 
)
-
- -

Definition at line 152 of file pearl-otf-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable otf_gather_iterator (dfref df,
string * sdata 
)
-
- -

Definition at line 106 of file pearl-otf-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable otf_interp (variable e1,
variable e2,
variable npts,
variable smo 
)
-
- -

Definition at line 271 of file pearl-otf-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable otf_load_itx (string pathname,
string filename 
)
-
- -

Definition at line 76 of file pearl-otf-import.ipf.

- -
-
- -
-
- - - - - - - - -
variable otf_load_itx_all (string pathname)
-
- -

Definition at line 31 of file pearl-otf-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable otf_load_itx_match (string pathname,
string matchstr 
)
-
- -

Definition at line 53 of file pearl-otf-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable otf_rename_folders (string pattern,
variable unique_index = defaultValue,
string new_suffix = defaultValue,
string match_str = defaultValue 
)
-
- -

Definition at line 231 of file pearl-otf-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable otf_rename_folders_iterator (dfref df,
string * sdata 
)
-
- -

Definition at line 185 of file pearl-otf-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable otf_smo_int (wave win,
wave wout,
wave wpe,
variable smo 
)
-
- -

Definition at line 304 of file pearl-otf-import.ipf.

- -
-
diff --git a/doc/html/pearl-otf-import_8ipf_source.html b/doc/html/pearl-otf-import_8ipf_source.html index 63be600..0f01427 100644 --- a/doc/html/pearl-otf-import_8ipf_source.html +++ b/doc/html/pearl-otf-import_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-otf-import.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=1// Use modern global access method.
2 #pragma IgorVersion = 6.1
3 #pragma ModuleName = PearlOtfImport
4 #pragma version = 1.01
5 
6 // procedures for importing on-the-fly (OTF) scans
7 // OTF scans are saved as ITX files
8 // matthias muntwiler, 2013-02-22
9 // $Id$
10 
11 // introduction
12 // the latest version of the PEARL OTF server saves data in igor text (ITX)
13 // the files contain code which saves all data from one file into one data folder with a unique name
14 // multiple files can be selected in the explorer and loaded by a double click
15 
16 // description
17 // OTF data folder names have the format otf_date_time_suffix, where only suffix is user-defined
18 // thus, raw data folder names are unique
19 // data folder names can be converted to a shorter format
20 // an OTF data folder contains a wave for each measured quantity (detector)
21 // and the IN, ID, IV, and IU waves for additional beamline parameters
22 // detector waves must have a wave note containing the following key=value pairs:
23 // PV=name of EPICS process variable
24 // PhysicalType=physical type of the quantity in the same way as used by pearl-optics-import
25 // Axis1=wave name of principal X axis
26 
27 // convergence
28 // while the file formats may be different, data files generated by the OTF and EPICS scan tools
29 // shall ultimately produce the same data structures in an Igor experiment
30 
31 variable otf_load_itx_all(string pathname){
32  // loads all OTF files from a given path
33  // this function is for older files (before 2013-03-01) which do not specify a destination data folder
34  // newer files can be loaded by double click from the explorer
35  // without the danger of overwriting data from other files
36  string pathname
37  string filename
38 
39  if (strlen(pathname) <= 0)
40  newpath /o/q otf_load_itx
41  pathname = "otf_load_itx"
42  endif
43  string filelist = IndexedFile($pathname, -1, ".itx")
44  filelist = ListMatch(filelist, "otf*.itx", ";")
45  variable nfile = ItemsInList(filelist, ";")
46  variable ifile
47  for (ifile = 0; ifile < nfile; ifile += 1)
48  filename = StringFromList(ifile, filelist, ";")
49  otf_load_itx(pathname, filename)
50  endfor
51 };
52 
53 variable otf_load_itx_match(string pathname, string matchstr){
54  // loads all OTF files from a given path whose names match a given string
55  // this function is for older files (before 2013-03-01) which do not specify a destination data folder
56  // newer files can be loaded by double click from the explorer
57  // without the danger of overwriting data from other files
58  string pathname
59  string matchstr
60  string filename
61 
62  if (strlen(pathname) <= 0)
63  newpath /o/q otf_load_itx
64  pathname = "otf_load_itx"
65  endif
66  string filelist = IndexedFile($pathname, -1, ".itx")
67  filelist = ListMatch(filelist, matchstr, ";")
68  variable nfile = ItemsInList(filelist, ";")
69  variable ifile
70  for (ifile = 0; ifile < nfile; ifile += 1)
71  filename = StringFromList(ifile, filelist, ";")
72  otf_load_itx(pathname, filename)
73  endfor
74 };
75 
76 variable otf_load_itx(string pathname, string filename){
77  // loads a specific OTF file
78  // this function is for older files (before 2013-03-01) which do not specify a destination data folder
79  // newer files can be loaded by double click from the explorer
80  // without the danger of overwriting data from other files
81  string pathname
82  string filename
83 
84  dfref savedf = GetDataFolderDFR()
85  setdatafolder root:
86 
87  newdatafolder /s/o otf_load_itx_temp
88  if (strlen(pathname) > 0)
89  LoadWave /O/P=$pathname/Q/T filename
90  else
91  LoadWave /O/Q/T filename
92  endif
93  if (v_flag)
94  string foldername
95  foldername = ParseFilePath(3, s_filename, "/", 0, 0)
96  foldername = foldername[0,16]
97  foldername = CleanupName(foldername, 0)
98  //foldername = UniqueName(foldername, 11, 0)
99  renamedatafolder root:otf_load_itx_temp, $foldername
100  printf "loaded otf data from file %s into folder %s\r", s_filename, foldername
101  endif
102 
103  setdatafolder savedf
104 };
105 
106 variable otf_gather_iterator(dfref df, string* sdata){
107  // data folder iterator used by otf_gather_batch
108  dfref df
109  string &sdata// key=value list of parameters
110  // xwavematch
111  // ywavematch
112  // destfolder
113 
114  string src_name
115  string dst_name
116  string src_folder
117  string dst_folder
118  string df_id
119  string prefix, sdate, stime
120 
121  setdatafolder df
122  src_folder = GetDataFolder(0, df)
123  sscanf src_folder, "%[^_]_%[0-9]_%[0-9]", prefix, sdate, stime
124  df_id = ""
125  if (strlen(sdate) > 0)
126  df_id += "_" + sdate
127  endif
128  if (strlen(stime) > 0)
129  df_id += "_" + stime
130  endif
131  dst_folder = StringByKey("destfolder", sdata)
132 
133  src_name = StringByKey("xwavematch", sdata)
134  src_name = WaveList(src_name, "", "")
135  if (ItemsInList(src_name) >= 1)
136  src_name = StringFromList(0, src_name)
137  dst_name = dst_folder + src_name + df_id
138  //print src_name, dst_name
139  duplicate $src_name, $dst_name
140  endif
141 
142  src_name = StringByKey("ywavematch", sdata)
143  src_name = WaveList(src_name, "", "")
144  if (ItemsInList(src_name) >= 1)
145  src_name = StringFromList(0, src_name)
146  dst_name = dst_folder + src_name + df_id
147  //print src_name, dst_name
148  duplicate $src_name, $dst_name
149  endif
150 };
151 
152 variable otf_gather_batch(string ywavematch, string xwavematch, string destfolder){
153  // gathers (copies) OTF datasets in one data folder
154  // can be used for example for the Igor batch curve fitting tool
155  string ywavematch// match string identifies the y wave to be copied
156  string xwavematch// match string identifies the x wave to be copied
157  string destfolder// name of the destination data folder. folder does not have to exist.
158 
159  return gather_batch("otf*", ywavematch, xwavematch, destfolder)
160 };
161 
162 variable gather_batch(string foldermatch, string ywavematch, string xwavematch, string destfolder){
163  // gathers (copies) OTF datasets in one data folder
164  // can be used for example for the Igor batch curve fitting tool
165  string foldermatch// match string to select data folders, e.g. "otf*"
166  string ywavematch// match string identifies the y wave to be copied
167  string xwavematch// match string identifies the x wave to be copied
168  string destfolder// name of the destination data folder. folder does not have to exist.
169 
170  dfref savedf = GetDataFolderDFR()
171  newdatafolder /o/s $destfolder
172  destfolder = GetDataFolder(1)
173 
174  string iteratordata = ""
175  iteratordata = ReplaceStringByKey("xwavematch", iteratordata, xwavematch)
176  iteratordata = ReplaceStringByKey("ywavematch", iteratordata, ywavematch)
177  iteratordata = ReplaceStringByKey("destfolder", iteratordata, destfolder)
178 
179  setdatafolder savedf
180  iteratordata = IterateDataFolders(foldermatch, otf_gather_iterator, iteratordata)
181 
182  setdatafolder savedf
183 };
184 
185 variable otf_rename_folders_iterator(dfref df, string* sdata){
186  // data folder iterator used by otf_rename_folders
187  dfref df
188  string &sdata// key=value list of parameters
189 
190  string pattern = StringByKey("pattern", sdata)
191  variable unique_index = NumberByKey("unique_index", sdata)
192  string new_suffix = StringByKey("new_suffix", sdata)
193 
194  string src_folder
195  string dst_folder
196  string sprefix, sdate, stime, ssuffix
197 
198  setdatafolder df
199  src_folder = GetDataFolder(0, df)
200  sprefix = "otf"
201  sscanf src_folder, "otf_%[0-9]_%[0-9]%s", sdate, stime, ssuffix
202  // return early if folder name does not match the expected pattern
203  if ((strlen(sdate) == 0) || (strlen(stime) == 0))
204  return 1
205  endif
206 
207  dst_folder = sprefix
208  if (cmpstr(pattern[0], "0") != 0)
209  dst_folder += "_" + sdate
210  endif
211  if (cmpstr(pattern[1], "0") != 0)
212  dst_folder += "_" + stime
213  endif
214  if (cmpstr(pattern[2], "0") != 0)
215  if (strlen(new_suffix) > 0)
216  ssuffix = "_" + new_suffix
217  endif
218  dst_folder += ssuffix
219  endif
220 
221  if ((unique_index > 0) || (CheckName(dst_folder, 11) != 0))
222  dst_folder = UniqueName(dst_folder + "_", 11, unique_index)
223  endif
224 
225  setdatafolder ::
226  print src_folder + " -> " + dst_folder
227  RenameDataFolder $src_folder, $dst_folder
228  return 0
229 };
230 
231 variable otf_rename_folders(string pattern, variable unique_index = defaultValue, string new_suffix = defaultValue, string match_str = defaultValue){
232  // renames OTF data folders by omitting parts of the file name
233  string pattern// string of zeros and ones indicates which name parts to keep
234  // pos 1: date
235  // pos 2: time
236  // pos 3: custom suffix
237  variable unique_index// if you remove date and time,
238  // this start index will be used to make names unique
239  // if non-zero, new names will be forced to include a unique index
240  // if zero (default), new names will get a unique index only in case of a conflict
241  // optional, defaults to 0
242  string new_suffix
243  // replace old suffix by this one
244  // if empty (default), the old suffix will be kept
245  // optional, defaults to empty string
246  string match_str// match folder name to rename
247  // optional, defaults to "otf*" (matches all OTF folders)
248 
249  dfref savedf = GetDataFolderDFR()
250 
251  if (ParamIsDefault(unique_index))
252  unique_index = 0
253  endif
254  if (ParamIsDefault(new_suffix))
255  new_suffix = ""
256  endif
257  if (ParamIsDefault(match_str))
258  match_str = "otf*"
259  endif
260 
261  string iteratordata = ""
262  iteratordata = ReplaceStringByKey("pattern", iteratordata, pattern)
263  iteratordata = ReplaceNumberByKey("unique_index", iteratordata, unique_index)
264  iteratordata = ReplaceStringByKey("new_suffix", iteratordata, new_suffix)
265 
266  iteratordata = IterateDataFolders(match_str, otf_rename_folders_iterator, iteratordata)
267 
268  setdatafolder savedf
269 };
270 
271 variable otf_interp(variable e1, variable e2, variable npts, variable smo){
272  variable e1
273  variable e2
274  variable npts
275  variable smo
276 
277  wave ch1 = current_ch1
278  wave ch2 = current_ch2
279  wave pe = photonenergy
280  wave cff
281  wave rc = ringcurrent
282 
283  duplicate /o ch1, current_ch1_int
284  wave ch1i = current_ch1_int
285  duplicate /o ch2, current_ch2_int
286  wave ch2i = current_ch2_int
287  duplicate /o pe, photonenergy_int
288  wave pei = photonenergy_int
289  duplicate /o cff, cff_int
290  wave cffi = cff_int
291  duplicate /o rc, ringcurrent_int
292  wave rci = ringcurrent_int
293 
294  redimension /n=(npts) ch1i, ch2i, pei, cffi, rci
295  setscale /i x e1, e2, "eV", ch1i, ch2i, pei, cffi, rci
296 
297  otf_smo_int(ch1, ch1i, pe, smo)
298  otf_smo_int(ch2, ch2i, pe, smo)
299  otf_smo_int(pe, pei, pe, smo)
300  otf_smo_int(cff, cffi, pe, smo)
301  otf_smo_int(rc, rci, pe, smo)
302 };
303 
304 variable otf_smo_int(wave win, wave wout, wave wpe, variable smo){
305  wave win
306  wave wout
307  wave wpe
308  variable smo
309 
310  //duplicate /o win, wtmp
311  duplicate /free win, wtmp
312  smooth /b /e=3 smo, wtmp
313  wout = interp(x, wpe, wtmp)
314 };
315 
variable otf_gather_iterator(dfref df, string *sdata)
-
string IterateDataFolders(string matchStr, funcref iterator, string sdata, string progress_title=defaultValue)
Definition: pearl-tools.ipf:79
-
variable otf_load_itx(string pathname, string filename)
-
variable otf_interp(variable e1, variable e2, variable npts, variable smo)
-
variable gather_batch(string foldermatch, string ywavematch, string xwavematch, string destfolder)
-
variable otf_load_itx_match(string pathname, string matchstr)
-
variable otf_gather_batch(string ywavematch, string xwavematch, string destfolder)
-
variable otf_rename_folders(string pattern, variable unique_index=defaultValue, string new_suffix=defaultValue, string match_str=defaultValue)
-
variable otf_rename_folders_iterator(dfref df, string *sdata)
-
variable otf_load_itx_all(string pathname)
-
variable otf_smo_int(wave win, wave wout, wave wpe, variable smo)
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-pmsco-import_8ipf.html b/doc/html/pearl-pmsco-import_8ipf.html new file mode 100644 index 0000000..02e7315 --- /dev/null +++ b/doc/html/pearl-pmsco-import_8ipf.html @@ -0,0 +1,102 @@ + + + + + + + +PEARL Procedures: pearl-pmsco-import.ipf File Reference + + + + + + + + + + + + + + +
+
+ + + + + + +
+
PEARL Procedures +  rev-distro-2.0.2-0-g3235d52 +
+
Igor procedures for the analysis of PEARL data
+
+
+ + + + + + + +
+
+ +
+
+
+ +
+ +
+
+ + +
+ +
+ +
+
+
pearl-pmsco-import.ipf File Reference
+
+
+ +

Go to the source code of this file.

+
+
+ + + + diff --git a/doc/html/pearl-pmsco-import_8ipf_source.html b/doc/html/pearl-pmsco-import_8ipf_source.html new file mode 100644 index 0000000..02d5e48 --- /dev/null +++ b/doc/html/pearl-pmsco-import_8ipf_source.html @@ -0,0 +1,100 @@ + + + + + + + +PEARL Procedures: pearl-pmsco-import.ipf Source File + + + + + + + + + + + + + + +
+
+ + + + + + +
+
PEARL Procedures +  rev-distro-2.0.2-0-g3235d52 +
+
Igor procedures for the analysis of PEARL data
+
+
+ + + + + + + +
+
+ +
+
+
+ +
+ +
+
+ + +
+ +
+ +
+
+
pearl-pmsco-import.ipf
+
+
+Go to the documentation of this file.
+
+ + + + diff --git a/doc/html/pearl-polar-coordinates_8ipf.html b/doc/html/pearl-polar-coordinates_8ipf.html index d1b97e8..4e36ca8 100644 --- a/doc/html/pearl-polar-coordinates_8ipf.html +++ b/doc/html/pearl-polar-coordinates_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-polar-coordinates.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
pearl-polar-coordinates.ipf File Reference

Go to the source code of this file.

- - - - - - - - - - - - -

-Functions

variable cart2polar (variable xx, variable yy, variable zz, variable *radius, variable *theta, variable *phi)
 
variable cart2polar_wave (wave in, wave out)
 
variable polar2cart (variable radius, variable theta, variable phi, variable *xx, variable *yy, variable *zz)
 
variable polar2cart_wave (wave in, wave out)
 
variable polar_distance (variable polar1, variable azim1, variable polar2, variable azim2)
 
-

Function Documentation

- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable cart2polar (variable xx,
variable yy,
variable zz,
variable * radius,
variable * theta,
variable * phi 
)
-
- -

Definition at line 10 of file pearl-polar-coordinates.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable cart2polar_wave (wave in,
wave out 
)
-
- -

Definition at line 36 of file pearl-polar-coordinates.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable polar2cart (variable radius,
variable theta,
variable phi,
variable * xx,
variable * yy,
variable * zz 
)
-
- -

Definition at line 48 of file pearl-polar-coordinates.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable polar2cart_wave (wave in,
wave out 
)
-
- -

Definition at line 58 of file pearl-polar-coordinates.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable polar_distance (variable polar1,
variable azim1,
variable polar2,
variable azim2 
)
-
- -

Definition at line 69 of file pearl-polar-coordinates.ipf.

- -
-
diff --git a/doc/html/pearl-polar-coordinates_8ipf_source.html b/doc/html/pearl-polar-coordinates_8ipf_source.html index 12d91aa..3ae81f7 100644 --- a/doc/html/pearl-polar-coordinates_8ipf_source.html +++ b/doc/html/pearl-polar-coordinates_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-polar-coordinates.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3
2 #pragma version = 1.1
3 #pragma IgorVersion = 6.1
4 #pragma ModuleName = PearlPolarCoordinates
5 
6 // author: matthias.muntwiler@psi.ch
7 // Copyright (c) 2011-13 Paul Scherrer Institut
8 // $Id$
9 
10 variable cart2polar(variable xx, variable yy, variable zz, variable* radius, variable* theta, variable* phi){
11  // converts a 3-vector from Cartesian to polar coordinates
12  variable xx, yy, zz
13  variable &radius, &theta, &phi// angles in degrees
14 
15  radius = sqrt(xx^2 + yy^2 + zz^2)
16 
17  if (radius > 0)
18  theta = acos(zz / radius) * 180 / pi
19  else
20  theta = 0
21  endif
22 
23  if (xx > 0)
24  phi = atan(yy / xx) * 180 / pi
25  else if (xx < 0)
26  phi = atan(yy / xx) * 180 / pi + 180
27  else
28  if (yy > 0)
29  phi = 90
30  else
31  phi = 270
32  endif
33  endif
34 };
35 
36 variable cart2polar_wave(wave in, wave out){
37  // converts a wave of 3-vectors from Cartesian to polar coordinates
38  wave in// wave with dimensions (3, N), N >= 1, (x, y, z)
39  wave out// wave same dimensions as in, (radius, theta, phi)
40  // angles in degrees
41 
42  out[0][] = sqrt(in[0][q]^2 + in[1][q]^2 + in[2][q]^2)
43  out[1][] = acos(in[2][q] / out[0][q]) * 180 / pi
44  out[2][] = atan(in[1][q] / in[0][q]) * 180 / pi + 180 * (in[0][q] < 0)
45  out[2][] = numtype(out[2][q]) == 0 ? out[2][q] : 90 + 180 * (in[1][q] < 0)
46 };
47 
48 variable polar2cart(variable radius, variable theta, variable phi, variable* xx, variable* yy, variable* zz){
49  // converts a 3-vector from Cartesian to polar coordinates
50  variable radius, theta, phi// angles in degrees
51  variable &xx, &yy, &zz
52 
53  xx = radius * sin(theta * pi / 180) * cos(phi * pi / 180)
54  yy = radius * sin(theta * pi / 180) * sin(phi * pi / 180)
55  zz = radius * cos(theta * pi / 180)
56 };
57 
58 variable polar2cart_wave(wave in, wave out){
59  // converts a wave of 3-vectors from polar to Cartesian coordinates
60  wave in// wave with dimensions (3, N), N >= 1, (radius, theta, phi)
61  // angles in degrees
62  wave out// wave same dimensions as in, (x, y, z)
63 
64  out[0][] = in[0][q] * sin(in[1][q] * pi / 180) * cos(in[2][q] * pi / 180)
65  out[1][] = in[0][q] * sin(in[1][q] * pi / 180) * sin(in[2][q] * pi / 180)
66  out[2][] = in[0][q] * cos(in[1][q] * pi / 180)
67 };
68 
69 variable polar_distance(variable polar1, variable azim1, variable polar2, variable azim2){
70  // returns the angle between two spherical coordinates
71  variable polar1, azim1
72  // angles in degrees
73  variable polar2, azim2
74  // angles in degrees
75 
76  variable xx1, yy1, zz1
77  variable xx2, yy2, zz2
78 
79  polar2cart(1, polar1, azim1, xx1, yy1, zz1)
80  polar2cart(1, polar2, azim2, xx2, yy2, zz2)
81 
82  variable vv
83  vv = (xx1 * xx2 + yy1 * yy2 + zz1 * zz2) / sqrt(xx1^2 + yy1^2 + zz1^2) / sqrt(xx2^2 + yy2^2 + zz2^2)
84  return acos(vv) * 180 / pi
85 };
86 
variable polar2cart_wave(wave in, wave out)
-
variable cart2polar(variable xx, variable yy, variable zz, variable *radius, variable *theta, variable *phi)
-
variable cart2polar_wave(wave in, wave out)
-
variable polar_distance(variable polar1, variable azim1, variable polar2, variable azim2)
-
variable polar2cart(variable radius, variable theta, variable phi, variable *xx, variable *yy, variable *zz)
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-pshell-import_8ipf.html b/doc/html/pearl-pshell-import_8ipf.html index f7b598a..678ca87 100644 --- a/doc/html/pearl-pshell-import_8ipf.html +++ b/doc/html/pearl-pshell-import_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-pshell-import.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
-
pearl-pshell-import.ipf File Reference
+
pearl-pshell-import.ipf File Reference
-

import data from PShell -More...

-
#include <HDF5 Browser>
-#include "pearl-gui-tools"
-#include "pearl-area-import"
-

Go to the source code of this file.

- - - - - -

-Namespaces

 PearlPShellImport
 import data from PShell
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

variable psh5_open_file (string ANickName, string APathName, string AFileName)
 open a HDF5 file created by the PShell data acquisition program and prepare the data folder. More...
 
variable psh5_close_file (variable fileID)
 close a HDF5 file opened by psh5_open_file. More...
 
string psh5_load_complete (string ANickName, string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue)
 load everything from a PShell data file. More...
 
string psh5_load_preview (string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue, string pref_scans=defaultValue, string pref_datasets=defaultValue)
 load a preview image from a PShell data file. More...
 
string psh5_load_scan_complete (variable fileID, string scanpath, variable load_data=defaultValue, variable load_attr=defaultValue)
 load all data of a selected scan from a PShell data file. More...
 
string psh5_list_scans (variable fileID)
 list scan groups of a PShell data file. More...
 
string psh5_list_scan_datasets (variable fileID, string scanpath, variable include_regions=defaultValue)
 list datasets of a PShell scan group. More...
 
string psh5_list_scan_regions (variable fileID, string scanpath)
 list regions of a PShell scan group. More...
 
string psh5_load_scan_data (variable fileID, string scanpath)
 load all datasets of a PShell scan group. More...
 
string psh5_load_scan_attrs (variable fileID, string scanpath, variable attr_sets=defaultValue)
 load attributes of a PShell scan group. More...
 
string psh5_load_scan_meta (variable fileID, string scanpath)
 load metadata of a PShell scan group. More...
 
string psh5_load_dataset (variable fileID, string scanpath, string datasetname, variable set_scale=defaultValue)
 load a dataset from an open PShell HDF5 file. More...
 
static string select_dataset (string file_datasets, string pref_datasets)
 select the preferred dataset from a list of available datasets. More...
 
string psh5_load_scan_preview (variable fileID, string scanpath, variable set_scale=defaultValue, string pref_datasets=defaultValue)
 load a preview dataset from an open PShell HDF5 file. More...
 
string psh5_load_scan_section (variable fileID, string scanpath, variable dim, variable set_scale=defaultValue, string pref_datasets=defaultValue)
 load a longitudinal section of a scan from an open PShell HDF5 file. More...
 
variable psh5_load_dataset_meta (variable fileID, string datapath, string datasetname, wave datawave)
 load metadata of a PShell dataset. More...
 
string psh5_load_dataset_slabs (variable fileID, string datapath, string datasetname, variable progress=defaultValue)
 load a dataset slab-wise from the open PShell HDF5 file. More...
 
string psh5_load_dataset_slab (variable fileID, string datapath, string datasetname, variable dim2start, variable dim2count, variable dim3start, variable dim3count)
 load a single image from the open PShell data file. More...
 
variable ps_set_dimlabels (wave data)
 set dimension labels according to the axis type More...
 
variable ps_set_dimlabels2 (wave data, string name)
 set dimension labels according to the axis type More...
 
static dfr find_scan_folder (dfref dataDF)
 find the scan folder More...
 
static dfr find_attr_folder (dfref dataDF)
 find the attributes data folder More...
 
variable ps_scale_datasets ()
 set the dimension scales of loaded PShell Scienta datasets according to attributes. More...
 
variable ps_scale_dataset (wave data)
 set the dimension scales of a loaded PShell Scienta dataset according to attributes. More...
 
static wave find_scale_wave (string name, dfref dataDF, dfref scanDF, dfref attrDF)
 
variable ps_detect_scale (wave ax, wave lo, wave hi, wave un)
 detect the dimension scales from attributes. More...
 
variable ps_scale_dataset_2 (wave data, wave ax, wave lo, wave hi, wave un)
 set the dimension scales of a dataset. More...
 
string psh5_load_reduced (string ANickName, string APathName, string AFileName, funcref reduction_func, string reduction_param, variable progress=defaultValue, variable nthreads=defaultValue)
 load and reduce the ScientaImage dataset of the first scan of a PShell data file. More...
 
string psh5_load_dataset_reduced (variable fileID, string scanpath, string datasetname, funcref reduction_func, string reduction_param, variable progress=defaultValue, variable nthreads=defaultValue)
 load a reduced dataset from the open PShell HDF5 file. More...
 
static threadsafe variable reduce_slab_worker (funcref reduction_func)
 
static threadsafe wave reduce_slab_image (wave slabdata, wave image, funcref reduction_func, string reduction_param)
 
string psh5_load_info (string APathName, string AFileName)
 load descriptive info from a PShell data file. More...
 
string psh5_load_scan_info (variable fileID, string scanpath)
 load descriptive info from a PShell scan. More...
 
static string twave2list (wave wt, string sep)
 convert text wave to list. More...
 
static string wave2list (wave w, string format, string sep)
 convert numeric wave to list. More...
 
- - - - - - - - - - - - - - - - - - - - - - - - - -

-Variables

const string kEnergyDimLabel = "energy"
 Dimension label for the energy dispersive dimension of multi-dimensional datasets. More...
 
const string kAngleDimLabel = "angle"
 Dimension label for the angle dispersive dimension of multi-dimensional datasets. More...
 
const string kScanDimLabel = "scan"
 Dimension label for the scan dimension of multi-dimensional datasets. More...
 
const string kDataDimLabel = "data"
 Dimension label for the data dimension. More...
 
const string kPreviewDatasets = "ScientaImage;ScientaSpectrum;ImageAngleDistribution;ImageEnergyDistribution;Counts;SampleCurrent;"
 List of preferred datasets to load for preview. More...
 
const string kScientaScalingDatasets = "LensMode;ScientaChannelBegin;ScientaChannelEnd;ScientaSliceBegin;ScientaSliceEnd;"
 List of datasets that must be loaded to determine the axis scaling of a Scienta image. More...
 
const string kTransposedDatasets = "ScientaImage;"
 List of datasets that should be transposed upon loading. More...
 
const variable kDetectorSensitivity = 4
 multiply scienta detector intensity by this value to get actual counts. More...
 
-

Detailed Description

-

import data from PShell

-

HDF5 file import from the PShell data acquisition program. the main import functions are:

- -

the following helper functions are also needed:

- -
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
- - -

Definition in file pearl-pshell-import.ipf.

-

Function Documentation

- -
-
- - - - - -
- - - - - - - - -
static dfr find_attr_folder (dfref dataDF)
-
-static
-
- -

find the attributes data folder

-

this is the :attr folder.

- -

Definition at line 1458 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static wave find_scale_wave (string name,
dfref dataDF,
dfref scanDF,
dfref attrDF 
)
-
-static
-
- -

Definition at line 1546 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static dfr find_scan_folder (dfref dataDF)
-
-static
-
- -

find the scan folder

-

the scan folder is the one that contains the :attr folder the data and scan folders may refer to the same folder.

- -

Definition at line 1441 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable ps_detect_scale (wave ax,
wave lo,
wave hi,
wave un 
)
-
- -

detect the dimension scales from attributes.

-

the function checks the data , scan and attributes folders for scan parameters. the results are written to the provided waves. the function is normally called by ps_scale_datasets() but can also be used independently.

-

the current datafolder must be the data or the scan folder. the data folder contains the waves that are to be scaled. the scan folder contains the scan positions and the :attr folder.

-

the provided waves are redimensioned by the function, and dimension labels are set. the scale parameters can then be extracted by keyword, e.g.,

    -
  • lo[%energy] analyser energy dimension.
  • -
  • lo[%angle] analyser angle dimension.
  • -
  • lo[%scan] scan dimension.
  • -
  • lo[%data] data dimension.
  • -
-

the function tries to read the following waves, in the data, scan, and attributes folders, where the first folder in the list takes precedence. it may fall back to more or less reasonable default values if no data is not found.

    -
  • LensMode
  • -
  • ScientaChannelBegin
  • -
  • ScientaChannelEnd
  • -
  • ScientaSliceBegin
  • -
  • ScientaSliceEnd
  • -
  • ScanWritables
  • -
  • wave referenced by ScanWritables[0]
  • -
-
Parameters
- - - - - -
axtext wave to receive the axis labels.
lowave to receive the lower limits.
hiwave to receive the upper limits.
untext wave to receive the unit labels.
-
-
-
Returns
the function results are written to the lo, hi, un, and ax waves.
-
Version
this function supports regions from version 1.03. check that you're in the correct data folder!
- -

Definition at line 1603 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - -
variable ps_scale_dataset (wave data)
-
- -

set the dimension scales of a loaded PShell Scienta dataset according to attributes.

-

the current datafolder must contain the :attr folder. the data wave can be in the current folder or a sub-folder.

-

the dimension labels of the dataset waves must have been set correctly, e.g. by ps_set_dimlabels(). this is implicitly done by the high-level load functions.

-

the function is useful if a single dataset is loaded and scaled. if multiple datasets are loaded, ps_scale_datasets() is slightly more efficient.

-
Parameters
- - -
datadata wave to be scaled. dimension labels (index -1) must be set correctly, cf. ps_set_dimlabels().
-
-
-
Version
this function supports regions from version 1.03.
- -

Definition at line 1532 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable ps_scale_dataset_2 (wave data,
wave ax,
wave lo,
wave hi,
wave un 
)
-
- -

set the dimension scales of a dataset.

-

the function is normally called by ps_scale_datasets() but can also be used independently. the limits and units must be given as function arguments with proper dimension labels.

-

the provided limit and unit waves must have dimension labels matching the -1 index dimension labels of the data wave, such as set by the ps_detect_scale() function. the scale parameters are extracted by keyword, e.g.,

    -
  • lo[%energy] analyser energy dimension.
  • -
  • lo[%angle] analyser angle dimension.
  • -
  • lo[%scan] scan dimension.
  • -
  • lo[%data] data dimension.
  • -
-

if the data dimension labels and units are at their defaults ("value" and "arb.", respectively), the function tries to read them from the existing wave note ("AxisLabelD" and "AxisUnitD"), or based on the wave name if the name is one of the known measurement variables: "ScientaImage", "ImageAngleDistribution", "ScientaAngleDistribution", "ScientaSpectrum", "ImageEnergyDistribution", "ScientaEnergyDistribution", "SampleCurrent", "RefCurrent", "AuxCurrent", "MachineCurrent".

-
Parameters
- - - - - - -
datadata wave to be scaled. dimension labels (index -1) must be set to match the limit waves.
axaxis labels. the axis labels are written to the wave note in the format AxisLabel%s=%s where X, Y, Z, D is substituted for the first place holder and the label for the second one.
lolower limits. the lower limits are applied using the SetScale operation.
hiupper limits. the upper limits are applied using the SetScale operation.
ununit labels. the unit labels are applied using the SetScale operation.
-
-
-
Version
this function supports regions from version 1.03.
- -

Definition at line 1763 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - -
variable ps_scale_datasets ()
-
- -

set the dimension scales of loaded PShell Scienta datasets according to attributes.

-

datasets listed in the ScanReadables waves are scaled according to the attribute waves in the data, scan, and attributes folders, whichever is found first.

-

the current datafolder must contain the ScanReadables wave and the :attr folder. the ScanReadables text wave contains names of the waves to scale. wave names can include a relative path to a sub-folder. the path separator is "/".

-

the dimension labels of the dataset waves must have been set correctly, e.g. by ps_set_dimlabels(). this is implicitly done by the high-level load functions.

-
Version
this function supports regions from version 1.03. check that you're in the correct data folder!
- -

Definition at line 1486 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - -
variable ps_set_dimlabels (wave data)
-
- -

set dimension labels according to the axis type

-

this function asserts a particular ordering of dimensions types based on the name of the wave for ScientaImage, ScientaSpectrum, ImageAngleDistribution, ImageEnergyDistribution. all other waves must be one-dimensional, and the dimension must be the scan dimension.

-

dimension labels are required by scaling functions.

-
Parameters
- - -
datadata wave as loaded from PShell file
-
-
-
Returns
    -
  • 0 all labels set successfully.
  • -
  • 1 unidentified data source.
  • -
  • 2 wave does not contain data.
  • -
-
- -

Definition at line 1365 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable ps_set_dimlabels2 (wave data,
string name 
)
-
- -

set dimension labels according to the axis type

-

same as ps_set_dimlabels() except that the dimension labels are set according to a separate name argument instead of the wave name.

-
Parameters
- - - -
datadata wave as loaded from PShell file.
nameoriginal name of the dataset in the PShell file.
-
-
-
Returns
    -
  • 0 all labels set successfully.
  • -
  • 1 unidentified data source.
  • -
  • 2 wave does not contain data.
  • -
-
- -

Definition at line 1384 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - -
variable psh5_close_file (variable fileID)
-
- -

close a HDF5 file opened by psh5_open_file.

-

this function just closes the HDF5 file. no change is made to the loaded data.

-
Parameters
- - -
fileIDID of open HDF5 file from psh5_open_file().
-
-
- -

Definition at line 139 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_list_scan_datasets (variable fileID,
string scanpath,
variable include_regions = defaultValue 
)
-
- -

list datasets of a PShell scan group.

-

the function returns a list of all datasets of the selected scan. this does not include datasets from the attributes sub-group.

-
Note
in a future version, an option may be introduced to filter datasets by function (Readable and/or Writable).
-
Parameters
- - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to the scan group in the HDF5 file, e.g. "/scan 1".
-
-
-
Returns
semicolon-separated list of dataset paths.
-
Version
since version 1.03 this function returns paths relative to scanpath.
- -

Definition at line 439 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
string psh5_list_scan_regions (variable fileID,
string scanpath 
)
-
- -

list regions of a PShell scan group.

-

the function returns a list of all region groups of the selected scan.

-
Parameters
- - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to the scan group in the HDF5 file, e.g. "/scan 1".
-
-
-
Returns
semicolon-separated list of datagroup paths.
- -

Definition at line 480 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - -
string psh5_list_scans (variable fileID)
-
- -

list scan groups of a PShell data file.

-

the function returns a list of all top-level groups whose name starts with "scan".

-
Parameters
- - -
fileIDID of open HDF5 file from psh5_open_file().
-
-
-
Returns
semicolon-separated list of group paths.
- -

Definition at line 404 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_complete (string ANickName,
string APathName,
string AFileName,
variable load_data = defaultValue,
variable load_attr = defaultValue 
)
-
- -

load everything from a PShell data file.

-
Parameters
- - - - - - -
ANickNamedestination folder name (top level under root)
APathNameigor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
AFileNameif empty a dialog box shows up
load_dataselect whether datasets (positioners and detectors) are loaded.
    -
  • 1 (default) load data.
  • -
  • 0 do not load data.
  • -
-
load_attrselect whether attributes (auxiliary device readbacks) are loaded. for proper wave scaling, the attributes must be loaded.
    -
  • 1 (default) load attributes.
  • -
  • 0 do not load attributes.
  • -
-
-
-
-
Returns
complete path of the loaded file if successful. empty string otherwise.
-
-global string s_filepath in new data folder contains the full file path on disk.
-
-global string s_scanpaths in new data folder contains a list of scan groups inside the file.
- -

Definition at line 169 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_dataset (variable fileID,
string scanpath,
string datasetname,
variable set_scale = defaultValue 
)
-
- -

load a dataset from an open PShell HDF5 file.

-

if the dataset has a maximum of two dimensions, the function loads it at once. if it has more than two dimension, the function calls psh5_load_dataset_slabs() to load the data slab by slab.

- -

the dataset is loaded into the current data folder unless datasetname contains a region specifier. in the latter case, the dataset is loaded into sub-folder with the name of the region. the function returns from the original data folder.

-
Parameters
- - - - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to the scan group in the HDF5 file, e.g. "/scan 1".
datasetnamename of the dataset. the name of the loaded wave is a cleaned up version of the dataset name. the name can include the region name as a relative path, e.g. "region1/ScientaSpectrum". in this case, the dataset is loaded into a sub-folder named "region1".
set_scaleby default, the function tries to set the wave scaling if the attributes have been loaded. if multiple datasets are loaded from a file, it is more efficient to set the scaling of all loaded datasets at the end by calling ps_scale_datasets().
    -
  • 1 (default) set the wave scaling.
  • -
  • 0 do not set the wave scaling.
  • -
-
-
-
-
Returns
name of loaded wave if successful. empty string otherwise.
-
Version
this function supports regions as of version 1.03.
- -

Definition at line 688 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
variable psh5_load_dataset_meta (variable fileID,
string datapath,
string datasetname,
wave datawave 
)
-
- -

load metadata of a PShell dataset.

-

"metadata" are the HDF5 attributes attached to the scan dataset.

-

data is added to the wave note.

-
Parameters
- - - - - -
fileIDID of open HDF5 file from psh5_open_file().
datapathpath to the containing group in the HDF5 file. path separator is the slash "/".
datasetnamename of the dataset. may include relative path.
datawavemetadata is added to the wave note of this wave.
-
-
-
Returns
0 if successful, non-zero if an error occurred.
- -

Definition at line 1073 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_dataset_reduced (variable fileID,
string scanpath,
string datasetname,
funcref reduction_func,
string reduction_param,
variable progress = defaultValue,
variable nthreads = defaultValue 
)
-
- -

load a reduced dataset from the open PShell HDF5 file.

-

the function loads the dataset image by image using the hyperslab option and applies a custom reduction function to each image. the results from the reduction function are written to the ReducedData1, ReducedData2, etc. waves. the raw data are discarded.

-

by default, the reduction function is called in separate threads to reduce the total loading time. (see the global variable psh5_perf_secs which reports the total run time of the function.) the effect varies depending on the balance between file loading (image size) and data processing (complexity of the reduction function). for debugging the reduction function, multi-threading can be disabled.

-

if the reduction function requires the image waves to be scaled properly, the attributes must have been loaded by psh5_load_scan_attrs() before. in this case, the scales of the result waves are also set by the function. otherwise, the results can also be scaled by ps_scale_dataset() later.

-
Parameters
- - - - - - - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to scan group in the HDF5 file.
datasetnamename of the dataset. this must currently be "ScientaImage", other data is not supported. the name of the loaded wave is a cleaned up version of the dataset name. the name can include the region name as a relative path, e.g. "region1/ScientaImage". in this case, the dataset is loaded into a sub-folder named "region1".
reduction_funccustom data reduction function. this can be any user-defined function which has the same parameters as adh5_default_reduction. some reduction functions are predefined in the PearlScientaPreprocess module.
reduction_paramparameter string for the reduction function.
progressprogress window.
    -
  • 1 (default) show progress window
  • -
  • 0 do not show progress window
  • -
-
nthreads
    -
  • -1 (default) use as many threads as there are processor cores (in addition to main thread).
  • -
  • 0 use main thread only (for debugging and profiling).
  • -
  • >= 1 use a fixed number of (additional) threads.
  • -
-
-
-
-
Returns
semicolon-separated list of the loaded dataset ReducedData1, ReducedData2, etc. if successful. auxiliary waves, scan positions, attributes are loaded but not listed in the string. empty string if an error occurred. error messages are printed to the history.
-
Version
this function supports regions as of version 1.03.
- -

Definition at line 2022 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_dataset_slab (variable fileID,
string datapath,
string datasetname,
variable dim2start,
variable dim2count,
variable dim3start,
variable dim3count 
)
-
- -

load a single image from the open PShell data file.

-

the function can average over a region in the extra dimensions.

-
Parameters
- - - - - - - - -
fileIDID of open HDF5 file from psh5_open_file().
datapathpath to the containing group in the HDF5 file. path separator is the slash "/".
datasetname of the dataset. also defines the name of the loaded wave.
dim2start2nd dimension coordinate of the first image set to 0 if dimension may not be present
dim2countnumber of subsequent images to average set to 1 if dimension may not be present
dim3start3rd dimension coordinate of the first image set to 0 if dimension may not be present
dim3countnumber of subsequent images to average set to 1 if dimension may not be present
-
-
-
Returns
name of loaded wave if successful. empty string otherwise.
- -

Definition at line 1266 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_dataset_slabs (variable fileID,
string datapath,
string datasetname,
variable progress = defaultValue 
)
-
- -

load a dataset slab-wise from the open PShell HDF5 file.

-

the function loads the dataset image by image using the hyperslab option.

-
Parameters
- - - - - -
fileIDID of open HDF5 file from psh5_open_file().
datapathpath to the containing group in the HDF5 file. path separator is the slash "/".
datasetname of the dataset. also defines the name of the loaded wave.
progressselect whether a progress window is displayed during the process.
    -
  • 1 (default) show progress window.
  • -
  • 0 do not show progress window.
  • -
-
-
-
-
Returns
name of loaded wave if successful. empty string otherwise.
- -

Definition at line 1130 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
string psh5_load_info (string APathName,
string AFileName 
)
-
- -

load descriptive info from a PShell data file.

-

the info string lists the following information for each scan contained in the file:

    -
  • path of the scan group inside the file.
  • -
  • number of scan positions.
  • -
  • dataset names of scan positioners.
  • -
  • dataset names of detectors.
  • -
-
Parameters
- - - -
APathNameigor symbolic path name. can be empty if the path is specified in AFileName or a dialog box should be displayed
AFileNameif empty a dialog box shows up
-
-
-
Returns
newline terminated string.
- -

Definition at line 2349 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_preview (string APathName,
string AFileName,
variable load_data = defaultValue,
variable load_attr = defaultValue,
string pref_scans = defaultValue,
string pref_datasets = defaultValue 
)
-
- -

load a preview image from a PShell data file.

-

the data wave is loaded into the current data folder. attributes are loaded into the attr subfolder. existing waves in attr are deleted.

-
Parameters
- - - - - - - -
APathNameigor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
AFileNameif empty a dialog box shows up
load_data1 (default): load data; 0: do not load data
load_attr1 (default): load attributes; 0: do not load attributes note: for correct scaling of the image, the attributes need to be loaded
pref_scanssemicolon-separated list of preferred scans. the items of the list are match strings for the Igor StringMatch function. the first matching scan (i.e. top-level HDF5 group with a matching name) is loaded from the file. if no match is found, the first scan is loaded.
pref_datasetssemicolon-separated list of preferred datasets. the items of the list are match strings for the Igor StringMatch function. the first matching dataset is loaded from the file. if no match is found, the first dataset listed in the file is loaded.
-
-
-
Returns
name of loaded preview wave.
- -

Definition at line 250 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_reduced (string ANickName,
string APathName,
string AFileName,
funcref reduction_func,
string reduction_param,
variable progress = defaultValue,
variable nthreads = defaultValue 
)
-
- -

load and reduce the ScientaImage dataset of the first scan of a PShell data file.

-

the resulting dataset is reduced in one image dimension by a user-defined reduction function, e.g. by region-of-interest integration, curve fitting, etc. cf. adh5_default_reduction for further details.

-

the function loads the dataset image by image using the hyperslab option and applies a custom reduction function to each image. the results from the reduction function are composed into one result wave. the raw data are discarded.

-

if the data is from the electron analyser driver and some special attributes are included, the function will set the scales of the image dimensions.

-

by default, the reduction function is called in separate threads to reduce the total loading time. (see the global variable psh5_perf_secs which reports the total run time of the function.) the effect varies depending on the balance between file loading (image size) and data processing (complexity of the reduction function). for debugging the reduction function, multi-threading can be disabled.

-
Parameters
- - - - - - - - -
ANickNamedestination folder name (top level under root).
APathNameigor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed.
AFileNameif empty a dialog box shows up.
reduction_funccustom data reduction function. this can be any user-defined function which has the same parameters as adh5_default_reduction. some reduction functions are predefined in the PearlScientaPreprocess module.
reduction_paramparameter string for the reduction function.
progressprogress window.
    -
  • 1 (default) show progress window
  • -
  • 0 do not show progress window
  • -
-
nthreads
    -
  • -1 (default) use as many threads as there are processor cores (in addition to main thread).
  • -
  • 0 use main thread only (for debugging and profiling).
  • -
  • >= 1 use a fixed number of (additional) threads.
  • -
-
-
-
-
Returns
semicolon-separated list of the loaded dataset ReducedData1, ReducedData2, etc. if successful. auxiliary waves, scan positions, attributes are loaded but not listed in the string. empty string if an error occurred. error messages are printed to the history.
-
-global string s_filepath in new data folder contains the full file path on disk.
-
-global string s_scanpaths in new data folder contains a list of scan groups inside the file.
- -

Definition at line 1893 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_scan_attrs (variable fileID,
string scanpath,
variable attr_sets = defaultValue 
)
-
- -

load attributes of a PShell scan group.

-

"attributes" are the auxiliary data inside the attrs group. do not confuse with HDF5 attributes! HDF5 attributes are loaded by the psh5_load_scan_meta() function.

-

data is loaded into the current data folder. this should normally be the :attr folder inside the respective scan folder.

-
Parameters
- - - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to the scan group in the HDF5 file, e.g. "/scan 1".
attr_setsspecify the attribute sets to be loaded. this value can be an arithmetic OR of the following constants. by default, all attributes are loaded.
    -
  • 1 all datasets that are present in the file.
  • -
  • 2 datasets relevant for wave scaling of Scienta data.
  • -
-
-
-
-
Returns
semicolon-separated list of the loaded waves.
- -

Definition at line 553 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_scan_complete (variable fileID,
string scanpath,
variable load_data = defaultValue,
variable load_attr = defaultValue 
)
-
- -

load all data of a selected scan from a PShell data file.

-

data is loaded into the current data folder. attribute datasets are loaded into sub-folder attr. region datasets are loaded into region sub-folders. existing data, if present, is overwritten.

-
Parameters
- - - - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to the scan group in the HDF5 file, e.g. "/scan 1".
load_dataselect whether datasets (positioners and detectors) are loaded.
    -
  • 1 (default) load data.
  • -
  • 0 do not load data.
  • -
-
load_attrselect whether attributes (auxiliary device readbacks) are loaded. for proper wave scaling, the attributes must be loaded.
    -
  • 1 (default) load attributes.
  • -
  • 0 do not load attributes.
  • -
-
-
-
-
Returns
semicolon-separated list of the loaded data waves (excluding attributes).
- -

Definition at line 360 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
string psh5_load_scan_data (variable fileID,
string scanpath 
)
-
- -

load all datasets of a PShell scan group.

-

data is loaded into the current data folder. region datasets are loaded into the respective region sub-folders.

-

this function does not scale the datasets. call ps_scale_datasets() separately.

-
Parameters
- - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to the scan group in the HDF5 file, e.g. "/scan 1".
-
-
-
Returns
semicolon-separated list of the loaded waves.
- -

Definition at line 513 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
string psh5_load_scan_info (variable fileID,
string scanpath 
)
-
- -

load descriptive info from a PShell scan.

-

the info string contains up to three lines which are made up of the following information:

    -
  • number of scan positions.
  • -
  • dataset names of scan positioners.
  • -
  • dataset names of detectors (without region names).
  • -
  • region names
  • -
-
Parameters
- - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to scan group in the HDF5 file.
-
-
-
Returns
newline terminated string.
- -

Definition at line 2396 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
string psh5_load_scan_meta (variable fileID,
string scanpath 
)
-
- -

load metadata of a PShell scan group.

-

metadata are the HDF5 attributes attached to the scan group. the following attributes are loaded. the respective wave names under Igor are given in parentheses.

-
    -
  • Dimensions (ScanDimensions)
  • -
  • Writables (ScanWritables)
  • -
  • Readables (ScanReadables)
  • -
  • Steps (ScanSteps)
  • -
-

if they are missing in the file, ScanDimensions and ScanReadables are set to default values assuming the file contains a single spectrum.

-

data is loaded into the current data folder.

-
Parameters
- - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to the scan group in the HDF5 file, e.g. "/scan 1".
-
-
-
Returns
semicolon-separated list of the loaded waves.
- -

Definition at line 621 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_scan_preview (variable fileID,
string scanpath,
variable set_scale = defaultValue,
string pref_datasets = defaultValue 
)
-
- -

load a preview dataset from an open PShell HDF5 file.

-

if the dataset has a maximum of two dimensions, the function loads it at once. if it has more than two dimension, the function selects and loads one two-dimensional slab.

-
Parameters
- - - - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to the scan group in the HDF5 file, e.g. "/scan 1".
set_scaleby default, the function tries to set the wave scaling if the attributes have been loaded. if multiple datasets are loaded from a file, it is more efficient to set the scaling of all loaded datasets at the end by calling ps_scale_datasets().
    -
  • 1 (default) set the wave scaling.
  • -
  • 0 do not set the wave scaling.
  • -
-
pref_datasetssemicolon-separated list of preferred datasets. the items of the list are match strings for the Igor StringMatch function. the first matching dataset is loaded from the file. if no match is found, the first dataset listed in the file is loaded. if empty, a hard-coded default preference list is used.
-
-
-
Returns
name of loaded wave if successful. empty string otherwise.
- -

Definition at line 822 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string psh5_load_scan_section (variable fileID,
string scanpath,
variable dim,
variable set_scale = defaultValue,
string pref_datasets = defaultValue 
)
-
- -

load a longitudinal section of a scan from an open PShell HDF5 file.

-

the dataset must have three dimensions.

-
Parameters
- - - - - - -
fileIDID of open HDF5 file from psh5_open_file().
scanpathpath to the scan group in the HDF5 file, e.g. "/scan 1".
dimreserved, must be 0.
set_scaleby default, the function tries to set the wave scaling if the attributes have been loaded. if multiple datasets are loaded from a file, it is more efficient to set the scaling of all loaded datasets at the end by calling ps_scale_datasets().
    -
  • 1 (default) set the wave scaling.
  • -
  • 0 do not set the wave scaling.
  • -
-
pref_datasetssemicolon-separated list of preferred datasets. the items of the list are match strings for the Igor StringMatch function. the first matching dataset is loaded from the file. if no match is found, the first dataset listed in the file is loaded. if empty, a hard-coded default preference list is used.
-
-
-
Returns
name of loaded wave if successful. empty string otherwise.
-
Warning
EXPERIMENTAL: this function is under development.
- -

Definition at line 935 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable psh5_open_file (string ANickName,
string APathName,
string AFileName 
)
-
- -

open a HDF5 file created by the PShell data acquisition program and prepare the data folder.

-

the function opens a specified or interactively selected HDF5 file, creates a data folder $ANickName under root, and changes to the new data folder.

-

the file must be closed by psh5_close_file() after use.

-
Parameters
- - - - -
ANickNamedestination folder name (top level under root).
APathNameigor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
AFileNameif empty a dialog box shows up
-
-
-
Returns
ID of open HDF5 file from HDF5OpenFile. zero if an error occurred.
-
-global string s_filepath in new data folder contains the full file path on disk.
-
-global string s_scanpaths in new data folder contains a list of scan groups inside the file.
- -

Definition at line 109 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static threadsafe wave reduce_slab_image (wave slabdata,
wave image,
funcref reduction_func,
string reduction_param 
)
-
-static
-
- -

Definition at line 2323 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - -
static threadsafe variable reduce_slab_worker (funcref reduction_func)
-
-static
-
- -

Definition at line 2284 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static string select_dataset (string file_datasets,
string pref_datasets 
)
-
-static
-
- -

select the preferred dataset from a list of available datasets.

-
Parameters
- - - -
file_datasetssemicolon-separated list of datasets that are available in the file. the items may include a path separated by slashes "/". only the last component of the path is checked.
pref_datasetssemicolon-separated list of preferred datasets. the items of the list are match strings for the Igor StringMatch function. the first matching dataset is loaded from the file. if no match is found, the first file dataset is selected.
-
-
-
Returns
selected dataset.
- -

Definition at line 760 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - -
static string twave2list (wave wt,
string sep 
)
-
-static
-
- -

convert text wave to list.

- -

Definition at line 2455 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - - -
- - - - - - - - - - - - - - - - - - - - - - - - -
static string wave2list (wave w,
string format,
string sep 
)
-
-static
-
- -

convert numeric wave to list.

- -

Definition at line 2472 of file pearl-pshell-import.ipf.

- -
-
-

Variable Documentation

- -
-
- - - - -
const string kAngleDimLabel = "angle"
-
- -

Dimension label for the angle dispersive dimension of multi-dimensional datasets.

- -

Definition at line 67 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - -
const string kDataDimLabel = "data"
-
- -

Dimension label for the data dimension.

-

This label may be used to store the parameters for the setscale d operation.

- -

Definition at line 74 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - -
const variable kDetectorSensitivity = 4
-
- -

multiply scienta detector intensity by this value to get actual counts.

- -

Definition at line 86 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - -
const string kEnergyDimLabel = "energy"
-
- -

Dimension label for the energy dispersive dimension of multi-dimensional datasets.

- -

Definition at line 64 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - -
const string kPreviewDatasets = "ScientaImage;ScientaSpectrum;ImageAngleDistribution;ImageEnergyDistribution;Counts;SampleCurrent;"
-
- -

List of preferred datasets to load for preview.

- -

Definition at line 77 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - -
const string kScanDimLabel = "scan"
-
- -

Dimension label for the scan dimension of multi-dimensional datasets.

- -

Definition at line 70 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - -
const string kScientaScalingDatasets = "LensMode;ScientaChannelBegin;ScientaChannelEnd;ScientaSliceBegin;ScientaSliceEnd;"
-
- -

List of datasets that must be loaded to determine the axis scaling of a Scienta image.

- -

Definition at line 80 of file pearl-pshell-import.ipf.

- -
-
- -
-
- - - - -
const string kTransposedDatasets = "ScientaImage;"
-
- -

List of datasets that should be transposed upon loading.

- -

Definition at line 83 of file pearl-pshell-import.ipf.

- -
-
diff --git a/doc/html/pearl-pshell-import_8ipf_source.html b/doc/html/pearl-pshell-import_8ipf_source.html index 30d445d..d54d080 100644 --- a/doc/html/pearl-pshell-import_8ipf_source.html +++ b/doc/html/pearl-pshell-import_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-pshell-import.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma IgorVersion = 6.36
3 #pragma ModuleName = PearlPShellImport
4 #include <HDF5 Browser>
5 #include "pearl-gui-tools"
6 #include "pearl-area-import"
7 
8 // copyright (c) 2013-18 Paul Scherrer Institut
9 //
10 // Licensed under the Apache License, Version 2.0 (the "License");
11 // you may not use this file except in compliance with the License.
12 // You may obtain a copy of the License at
13 // http:///www.apache.org/licenses/LICENSE-2.0
14 
57 
62 
64 const string kEnergyDimLabel = "energy";
65 
67 const string kAngleDimLabel = "angle";
68 
70 const string kScanDimLabel = "scan";
71 
74 const string kDataDimLabel = "data";
75 
77 const string kPreviewDatasets = "ScientaImage;ScientaSpectrum;ImageAngleDistribution;ImageEnergyDistribution;Counts;SampleCurrent;";
78 
80 const string kScientaScalingDatasets = "LensMode;ScientaChannelBegin;ScientaChannelEnd;ScientaSliceBegin;ScientaSliceEnd;";
81 
83 const string kTransposedDatasets = "ScientaImage;";
84 
86 const variable kDetectorSensitivity = 4;
87 
109 variable psh5_open_file(string ANickName, string APathName, string AFileName){
110  string ANickName
111  string APathName
112  string AFileName
113 
114  setdatafolder root:
115  newdatafolder /s /o $("root:" + ANickName)
116  dfref fileDF = GetDataFolderDFR()
117 
118  variable fileID
119  HDF5OpenFile /P=$APathName /R fileID as AFileName
120  if (v_flag == 0)
121  string /g s_filepath
122  string /g s_scanpaths
123  s_filepath = s_path + s_filename
124  s_scanpaths = psh5_list_scans(fileID)
125  else
126  fileID = 0
127  endif
128 
129  return fileID
130 };
131 
139 variable psh5_close_file(variable fileID){
140  variable fileID
141 
142  HDF5CloseFile fileID
143 };
144 
169 string psh5_load_complete(string ANickName, string APathName, string AFileName, variable load_data = defaultValue, variable load_attr = defaultValue){
170  string ANickName
171  string APathName
172  string AFileName
173  variable load_data
174  variable load_attr
175 
176  if (ParamIsDefault(load_data))
177  load_data = 1
178  endif
179  if (ParamIsDefault(load_attr))
180  load_attr = 1
181  endif
182 
183  dfref saveDF = GetDataFolderDFR()
184 
185  // performance monitoring
186  variable timerRefNum
187  variable /g psh5_perf_secs
188  timerRefNum = startMSTimer
189 
190  variable fileID = psh5_open_file(ANickName, APathName, AFileName)
191  if (fileID)
192  dfref fileDF = GetDataFolderDFR()
193  svar s_filepath
194  svar s_scanpaths
195  AFileName = s_filepath
196  print "loading " + s_filepath + "\r"
197 
198  variable ig
199  variable ng = ItemsInList(s_scanpaths, ";")
200  string sg
201  string folder
202 
203  for (ig = 0; ig < ng; ig += 1)
204  sg = StringFromList(ig, s_scanpaths, ";")
205  folder = ReplaceString("/", sg, "")
206  folder = ReplaceString(" ", folder, "")
207  folder = CleanupName(folder, 0)
208  setdatafolder fileDF
209  newdatafolder /s /o $folder
210  psh5_load_scan_complete(fileID, sg, load_data=load_data, load_attr=load_attr)
211  endfor
212 
213  psh5_close_file(fileID)
214  else
215  AFileName = ""
216  endif
217 
218  psh5_perf_secs = stopMSTimer(timerRefNum) / 1e6
219 
220  setdatafolder saveDF
221  return AFileName
222 };
223 
250 string psh5_load_preview(string APathName, string AFileName, variable load_data = defaultValue, variable load_attr = defaultValue, string pref_scans = defaultValue, string pref_datasets = defaultValue){
251  string APathName
252  string AFileName
253  variable load_data
254  variable load_attr
255  string pref_scans
256  string pref_datasets
257 
258  if (ParamIsDefault(load_data))
259  load_data = 1
260  endif
261  if (ParamIsDefault(load_attr))
262  load_attr = 1
263  endif
264  if (ParamIsDefault(pref_scans))
265  pref_scans = "*scan1*;"
266  endif
267  if (ParamIsDefault(pref_datasets))
268  pref_datasets = ""
269  endif
270 
271  dfref saveDF = GetDataFolderDFR()
272 
273  variable fileID
274  string scanpaths = ""
275  string dataname = ""
276 
277  // performance monitoring
278  variable timerRefNum
279  variable /g adh5_perf_secs
280  timerRefNum = startMSTimer
281 
282  HDF5OpenFile /P=$APathName /R /Z fileID as AFileName
283  if (v_flag == 0)
284  AFileName = s_path + s_filename
285  dfref fileDF = GetDataFolderDFR()
286 
287  scanpaths = psh5_list_scans(fileID)
288  variable ng = ItemsInList(scanpaths)
289  variable ig
290  string sg
291  variable np = ItemsInList(pref_scans)
292  variable ip
293  string sp
294  variable found = 0
295  if (ng > 0)
296  for (ip = 0; ip < np; ip += 1)
297  for (ig = 0; ig < ng; ig += 1)
298  sg = StringFromList(ig, scanpaths)
299  sp = StringFromList(ip, pref_scans)
300  if (StringMatch(sg, sp))
301  found = 1
302  break
303  endif
304  endfor
305  if (found)
306  break
307  endif
308  endfor
309  if (!found)
310  ig = 0
311  endif
312  sg = StringFromList(ig, scanpaths)
313 
314  if (load_attr)
315  setdatafolder fileDF
316  newdatafolder /o/s attr
317  killwaves /a/z
318  psh5_load_scan_attrs(fileID, sg)
319  endif
320 
321  setdatafolder fileDF
322  dataname = psh5_load_scan_preview(fileID, sg, set_scale=load_attr, pref_datasets=pref_datasets)
323  else
324  print "no scans found in file " + AFileName
325  endif
326 
327  HDF5CloseFile fileID
328  endif
329 
330  if (timerRefNum >= 0)
331  adh5_perf_secs = stopMSTimer(timerRefNum) / 1e6
332  endif
333 
334  setdatafolder saveDF
335  return dataname
336 };
337 
360 string psh5_load_scan_complete(variable fileID, string scanpath, variable load_data = defaultValue, variable load_attr = defaultValue){
361  variable fileID
362  string scanpath
363  variable load_data
364  variable load_attr
365 
366  if (ParamIsDefault(load_data))
367  load_data = 1
368  endif
369  if (ParamIsDefault(load_attr))
370  load_attr = 1
371  endif
372 
373  dfref saveDF = GetDataFolderDFR()
374 
375  dfref dataDF = GetDataFolderDFR()
376  string wavenames
377  string attrnames
378  psh5_load_scan_meta(fileID, scanpath)
379  if (load_attr)
380  newdatafolder /s /o attr
381  attrnames = psh5_load_scan_attrs(fileID, scanpath)
382  endif
383  if (load_data)
384  setdatafolder dataDF
385  wavenames = psh5_load_scan_data(fileID, scanpath)
386  endif
387  if (load_data && load_attr)
388  setdatafolder dataDF
390  endif
391 
392  setdatafolder saveDF
393  return wavenames
394 };
395 
404 string psh5_list_scans(variable fileID){
405  variable fileID
406 
407  HDF5ListGroup /F /TYPE=1 fileID, "/"
408 
409  variable ig
410  variable ng = ItemsInList(S_HDF5ListGroup, ";")
411  string sg
412  string scans = ""
413 
414  for (ig = 0; ig < ng; ig += 1)
415  sg = StringFromList(ig, S_HDF5ListGroup, ";")
416  if (cmpstr(sg[1,4], "scan") == 0)
417  scans = AddListItem(sg, scans, ";", inf)
418  endif
419  endfor
420 
421  return scans
422 };
423 
439 string psh5_list_scan_datasets(variable fileID, string scanpath, variable include_regions = defaultValue){
440  variable fileID
441  string scanpath
442  variable include_regions
443 
444  if (ParamIsDefault(include_regions))
445  include_regions = 0
446  endif
447  string result
448 
449  HDF5ListGroup /TYPE=2 /Z fileID, scanpath
450  result = S_HDF5ListGroup
451 
452  if (include_regions)
453  HDF5ListGroup /R /TYPE=2 /Z fileID, scanpath
454  variable n = ItemsInList(S_HDF5ListGroup)
455  variable i
456  string ds
457  string region_datasets
458  for (i = 0; i < n; i += 1)
459  ds = StringFromList(i, S_HDF5ListGroup)
460  if (StringMatch(ds, "region*/*"))
461  //region_datasets = psh5_list_scan_datasets(fileID, ReplaceString("//", scanpath + "/" + region, "/"), include_regions=0)
462  result = AddListItem(ds, result, ";", inf)
463  endif
464  endfor
465  endif
466 
467  return result
468 };
469 
480 string psh5_list_scan_regions(variable fileID, string scanpath){
481  variable fileID
482  string scanpath
483 
484  HDF5ListGroup /TYPE=1 /Z fileID, scanpath
485  variable n = ItemsInList(S_HDF5ListGroup)
486  variable i
487  string result = ""
488  string s
489  for (i = 0; i < n; i += 1)
490  s = StringFromList(i, S_HDF5ListGroup)
491  if (StringMatch(s, "region*"))
492  result = AddListItem(s, result, ";", inf)
493  endif
494  endfor
495 
496  return result
497 };
498 
513 string psh5_load_scan_data(variable fileID, string scanpath){
514  variable fileID
515  string scanpath
516 
517  string datasets = psh5_list_scan_datasets(fileID, scanpath, include_regions=1)
518  variable nds = ItemsInList(datasets)
519  variable ids
520  string sds
521  string sw
522  string wavenames = ""
523  for (ids = 0; ids < nds; ids += 1)
524  sds = StringFromList(ids, datasets)
525  sw = psh5_load_dataset(fileID, scanpath, sds, set_scale=0)
526  wavenames = AddListItem(sw, wavenames, ";", inf)
527  endfor
528 
529  return wavenames
530 };
531 
553 string psh5_load_scan_attrs(variable fileID, string scanpath, variable attr_sets = defaultValue){
554  variable fileID
555  string scanpath
556  variable attr_sets
557 
558  if (ParamIsDefault(attr_sets))
559  attr_sets = 1
560  endif
561 
562  string attr_path = ReplaceString("//", scanpath + "/attrs", "/")
563  string attr_list = ""
564  if (attr_sets & 1)
565  HDF5ListGroup /TYPE=2 /Z fileID, attr_path
566  if (!v_flag)
567  attr_list = S_HDF5ListGroup
568  endif
569  endif
570 
571  variable ids
572  variable nds
573  string sds
574 
575  if (attr_sets & 2)
576  nds = ItemsInList(kScientaScalingDatasets, ";")
577  for (ids = 0; ids < nds; ids += 1)
578  sds = StringFromList(ids, kScientaScalingDatasets)
579  if (WhichListItem(sds, attr_list) < 0)
580  attr_list = AddListItem(sds, attr_list, ";", inf)
581  endif
582  endfor
583  endif
584 
585  nds = ItemsInList(attr_list, ";")
586  string wavenames = ""
587  for (ids = 0; ids < nds; ids += 1)
588  sds = StringFromList(ids, attr_list, ";")
589  HDF5LoadData /O /Q /Z fileID, attr_path + "/" + sds
590  if (!v_flag)
591  wavenames = AddListItem(s_wavenames, wavenames, ";", inf)
592  endif
593  endfor
594  wavenames = ReplaceString(";;", wavenames, ";")
595 
596  return wavenames
597 };
598 
621 string psh5_load_scan_meta(variable fileID, string scanpath){
622  variable fileID
623  string scanpath
624  string wavenames = ""
625 
626  HDF5LoadData /O /Q /Z /A="Dimensions" /N=ScanDimensions /TYPE=1 fileID, scanpath
627  if (!v_flag)
628  wavenames = AddListItem(s_wavenames, wavenames, ";", inf)
629  else
630  make /n=1 /o ScanDimensions
631  ScanDimensions = 0
632  wavenames = AddListItem("ScanDimensions", wavenames, ";", inf)
633  endif
634  HDF5LoadData /O /Q /Z /A="Readables" /N=ScanReadables /TYPE=1 fileID, scanpath
635  if (!v_flag)
636  wavenames = AddListItem(s_wavenames, wavenames, ";", inf)
637  else
638  make /n=1 /o /t ScanReadables
639  ScanReadables[0] = "ScientaSpectrum"
640  wavenames = AddListItem("ScanReadables", wavenames, ";", inf)
641  endif
642  HDF5LoadData /O /Q /Z /A="Writables" /N=ScanWritables /TYPE=1 fileID, scanpath
643  if (!v_flag)
644  wavenames = AddListItem(s_wavenames, wavenames, ";", inf)
645  endif
646  HDF5LoadData /O /Q /Z /A="Steps" /N=ScanSteps /TYPE=1 fileID, scanpath
647  if (!v_flag)
648  wavenames = AddListItem(s_wavenames, wavenames, ";", inf)
649  endif
650  wavenames = ReplaceString(";;", wavenames, ";")
651 
652  return wavenames
653 };
654 
688 string psh5_load_dataset(variable fileID, string scanpath, string datasetname, variable set_scale = defaultValue){
689  variable fileID
690  string scanpath
691  string datasetname
692  variable set_scale
693 
694  if (ParamIsDefault(set_scale))
695  set_scale = 1
696  endif
697 
698  dfref base_df = GetDataFolderDFR()
699 
700  string datasetpath
701  datasetpath = scanpath + "/" + datasetname
702  datasetpath = ReplaceString("//", datasetpath, "/")
703 
704  string regionname
705  string regionpath
706  if (ItemsInList(datasetname, "/") >= 2)
707  regionname = StringFromList(0, datasetname, "/")
708  regionpath = ReplaceString("//", scanpath + "/" + regionname, "/")
709  datasetname = RemoveListItem(0, datasetname, "/")
710  NewDataFolder /o/s $regionname
711  else
712  regionname = ""
713  regionpath = scanpath
714  endif
715 
716  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
717  InitHDF5DataInfo(di)
718  variable err = HDF5DatasetInfo(fileID, datasetpath, 0, di)
719  if (err != 0)
720  print "error accessing detector/data"
721  return ""
722  endif
723 
724  string dataname
725  if (di.ndims < 2)
726  HDF5LoadData /O /Q /Z fileID, datasetpath
727  dataname = StringFromList(0, S_waveNames)
728  else
729  dataname = psh5_load_dataset_slabs(fileID, regionpath, datasetname)
730  endif
731 
732  wave /z data = $dataname
733  if (waveexists(data))
734  psh5_load_dataset_meta(fileID, regionpath, datasetname, data)
735  ps_set_dimlabels(data)
736  if (set_scale)
737  ps_scale_dataset(data)
738  endif
739  else
740  dataname = ""
741  endif
742 
743  setdatafolder base_df
744  return dataname
745 };
746 
760 static string select_dataset(string file_datasets, string pref_datasets){
761  string file_datasets
762  string pref_datasets
763 
764  variable index
765  variable nds = ItemsInList(file_datasets)
766  variable ids
767  string sds = ""
768  string mds = ""
769  variable np = ItemsInList(pref_datasets)
770  variable ip
771  string sp
772  variable found = 0
773  if (nds > 0)
774  for (ip = 0; ip < np; ip += 1)
775  for (ids = 0; ids < nds; ids += 1)
776  sds = StringFromList(ids, file_datasets)
777  index = ItemsInList(sds, "/") - 1
778  mds = StringFromList(index, sds, "/")
779  sp = StringFromList(ip, pref_datasets)
780  if (StringMatch(mds, sp))
781  found = 1
782  break
783  endif
784  endfor
785  if (found)
786  break
787  endif
788  endfor
789  if (!found)
790  ids = 0
791  sds = StringFromList(ids, file_datasets)
792  endif
793  endif
794 
795  return sds
796 };
797 
822 string psh5_load_scan_preview(variable fileID, string scanpath, variable set_scale = defaultValue, string pref_datasets = defaultValue){
823  variable fileID
824  string scanpath
825  variable set_scale
826  string pref_datasets
827 
828  if (ParamIsDefault(set_scale))
829  set_scale = 1
830  endif
831  if (ParamIsDefault(pref_datasets) || (strlen(pref_datasets) == 0))
832  pref_datasets = kPreviewDatasets
833  endif
834 
835  dfref saveDF = GetDataFolderDFR()
836  dfref dataDF = saveDF
837 
838  string datasets = psh5_list_scan_datasets(fileID, scanpath, include_regions=1)
839  string datasetname = select_dataset(datasets, pref_datasets)
840  string datasetpath
841  datasetpath = scanpath + "/" + datasetname
842  datasetpath = ReplaceString("//", datasetpath, "/")
843 
844  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
845  InitHDF5DataInfo(di)
846  variable err = HDF5DatasetInfo(fileID, datasetpath, 0, di)
847  if (err != 0)
848  print "error accessing detector/data"
849  return ""
850  endif
851 
852  string dataname
853  if (di.ndims < 2)
854  HDF5LoadData /O /Q /Z fileID, datasetpath
855  dataname = StringFromList(0, S_waveNames)
856  wave /z data = $dataname
857  if (waveexists(data))
858  ps_set_dimlabels(data)
859  endif
860  else
861  variable dim2start = 0
862  variable dim2count = 1
863  variable dim3start = 0
864  variable dim3count = 1
865  if (di.ndims >= 3)
866  dim2start = floor(di.dims[2] / 2)
867  dim2count = 1
868  endif
869  if (di.ndims >= 4)
870  dim3start = floor(di.dims[3] / 2)
871  dim3count = 1
872  endif
873 
874  dataname = psh5_load_dataset_slab(fileID, scanpath, datasetname, dim2start, dim2count, dim3start, dim3count)
875  endif
876 
877  wave /z data = $dataname
878  if (waveexists(data))
879  if (set_scale)
880  setdatafolder dataDF
881  string positioners
882  string positioner
883  string positionerpath
884  positioners = psh5_load_scan_meta(fileID, scanpath)
885  wave /t /z ScanWritables
886  if (waveexists(ScanWritables) && (numpnts(ScanWritables) >= 1))
887  positioner = ScanWritables[0]
888  if (strlen(positioner) > 0)
889  positionerpath = scanpath + "/" + positioner
890  positionerpath = ReplaceString("//", positionerpath, "/")
891  HDF5LoadData /O /Q /Z fileID, positionerpath
892  endif
893  endif
894 
895  setdatafolder dataDF
896  newdatafolder /o/s attr
897  psh5_load_scan_attrs(fileID, scanpath, attr_sets=2)
898  setdatafolder dataDF
899  ps_scale_dataset(data)
900  endif
901  else
902  dataname = ""
903  endif
904 
905  return dataname
906 };
907 
935 string psh5_load_scan_section(variable fileID, string scanpath, variable dim, variable set_scale = defaultValue, string pref_datasets = defaultValue){
936  variable fileID
937  string scanpath
938  variable dim
939  variable set_scale
940  string pref_datasets
941 
942  // select first dimension (future argument)
943  // 0 = first dimension is x axis (energy of scienta image)
944  dim = 0
945 
946  if (ParamIsDefault(set_scale))
947  set_scale = 1
948  endif
949  if (ParamIsDefault(pref_datasets) || (strlen(pref_datasets) == 0))
950  pref_datasets = kPreviewDatasets
951  endif
952 
953  dfref saveDF = GetDataFolderDFR()
954  dfref dataDF = saveDF
955 
956  string datasets = psh5_list_scan_datasets(fileID, scanpath)
957  string datasetname = select_dataset(datasets, pref_datasets)
958  string datasetpath
959  datasetpath = scanpath + "/" + datasetname
960  datasetpath = ReplaceString("//", datasetpath, "/")
961  string dataname = StringFromList(ItemsInList(datasetpath, "/") - 1, datasetpath, "/")
962  string destname = dataname[0,29] + num2str(dim)
963 
964  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
965  InitHDF5DataInfo(di)
966  variable err = HDF5DatasetInfo(fileID, datasetpath, 0, di)
967  if (err != 0)
968  print "error accessing detector/data"
969  return ""
970  else if (di.ndims != 3)
971  print "error: rank of dataset != 3"
972  return ""
973  endif
974 
975  variable idx, idy, idz, idt
976  variable transpose = WhichListItem(dataname, kTransposedDatasets) >= 0
977  if (transpose)
978  idx = 1
979  idy = 0
980  else
981  idx = 0
982  idy = 1
983  endif
984  idz = 2
985  idt = 3
986 
987  variable nx, ny, nz
988  nx = di.dims[idx]
989  ny = di.dims[idy]
990  nz = di.dims[idz]
991 
992  HDF5MakeHyperslabWave("slab", max(di.ndims, 4))
993  wave slab
994  slab[][%Start] = 0
995  slab[][%Stride] = 1
996  slab[][%Count] = 1
997  slab[][%Block] = 1
998 
999  if (dim == 0)
1000  slab[idy][%Start] = floor(ny / 2)
1001  slab[idx][%Block] = nx
1002  make /n=(nx,nz) /o $destname
1003  else
1004  slab[idx][%Start] = floor(nx / 2)
1005  slab[idy][%Block] = ny
1006  make /n=(ny,nz) /o $destname
1007  endif
1008  slab[idz][%Block] = nz
1009  wave data = $destname
1010  data = 0
1011 
1012  HDF5LoadData /O /Q /Z /SLAB=slab /N=slabdata fileID, datasetpath
1013  if (!v_flag)
1014  wave slabdata
1015  if (transpose)
1016  data += slabdata[0][p][q][0]
1017  else
1018  data += slabdata[p][0][q][0]
1019  endif
1020  endif
1021  killwaves /z slab, slabdata
1022 
1023  if (set_scale)
1024  make /n=(1,1,1) /free dummy
1025  ps_set_dimlabels2(dummy, dataname)
1026  setdimlabel 0, -1, $GetDimLabel(dummy, dim, -1), data
1027  setdimlabel 1, -1, $kScanDimLabel, data
1028 
1029  setdatafolder dataDF
1030  string positioners
1031  string positioner
1032  string positionerpath
1033  positioners = psh5_load_scan_meta(fileID, scanpath)
1034  wave /t /z ScanWritables
1035  if (waveexists(ScanWritables) && (numpnts(ScanWritables) >= 1))
1036  positioner = ScanWritables[0]
1037  if (strlen(positioner) > 0)
1038  positionerpath = scanpath + "/" + positioner
1039  positionerpath = ReplaceString("//", positionerpath, "/")
1040  HDF5LoadData /O /Q /Z fileID, positionerpath
1041  endif
1042  endif
1043 
1044  setdatafolder dataDF
1045  newdatafolder /o/s attr
1046  killwaves /a/z
1047  psh5_load_scan_attrs(fileID, scanpath, attr_sets=2)
1048  setdatafolder dataDF
1049  ps_scale_dataset(data)
1050  endif
1051 
1052  return destname
1053 };
1054 
1073 variable psh5_load_dataset_meta(variable fileID, string datapath, string datasetname, wave datawave){
1074  variable fileID
1075  string datapath
1076  string datasetname
1077  wave datawave
1078 
1079  dfref saveDF = GetDataFolderDFR()
1080  SetDataFolder NewFreeDataFolder()
1081 
1082  string datasetpath = datapath + "/" + datasetname
1083  datasetpath = ReplaceString("//", datasetpath, "/")
1084  string wnote
1085 
1086  HDF5LoadData /O /Q /Z /A="Writable Dimension" /N=WriteDim fileID, datasetpath
1087  if (!v_flag)
1088  wave WriteDim
1089  // scan dimension starts at 1
1090  sprintf wnote, "ScanDimension=%u", WriteDim[0]
1091  Note datawave, wnote
1092  endif
1093 
1094  HDF5LoadData /O /Q /Z /A="Writable Index" /N=WriteIndex fileID, datasetpath
1095  if (!v_flag)
1096  wave WriteIndex
1097  sprintf wnote, "WriteableIndex=%u", WriteIndex[0]
1098  Note datawave, wnote
1099  endif
1100 
1101  HDF5LoadData /O /Q /Z /A="Readable Index" /N=ReadIndex fileID, datasetpath
1102  if (!v_flag)
1103  wave ReadIndex
1104  sprintf wnote, "ReadableIndex=%u", ReadIndex[0]
1105  Note datawave, wnote
1106  endif
1107 
1108  setdatafolder saveDF
1109  return 0
1110 };
1111 
1130 string psh5_load_dataset_slabs(variable fileID, string datapath, string datasetname, variable progress = defaultValue){
1131  variable fileID
1132  string datapath
1133  string datasetname
1134  variable progress
1135 
1136  if (ParamIsDefault(progress))
1137  progress = 1
1138  endif
1139 
1140  variable result = 0
1141  string datasetpath
1142  string datawavename
1143  datasetpath = datapath + "/" + datasetname
1144  datasetpath = ReplaceString("//", datasetpath, "/")
1145  datawavename = StringFromList(ItemsInList(datasetpath, "/") - 1, datasetpath, "/")
1146 
1147  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
1148  InitHDF5DataInfo(di)
1149  variable err = HDF5DatasetInfo(fileID, datasetpath, 0, di)
1150  if (err != 0)
1151  print "error accessing detector/data"
1152  return ""
1153  endif
1154  if (di.ndims < 2)
1155  print "error: rank of dataset < 2"
1156  return ""
1157  else if (di.ndims < 3)
1158  progress = 0
1159  endif
1160 
1161  variable idx, idy, idz, idt, izt
1162  variable transpose = WhichListItem(datawavename, kTransposedDatasets) >= 0
1163  if (transpose)
1164  idx = 1
1165  idy = 0
1166  else
1167  idx = 0
1168  idy = 1
1169  endif
1170  idz = 2
1171  idt = 3
1172 
1173  variable nx, ny, nz, nt, nzt
1174  nx = di.dims[idx]
1175  ny = di.dims[idy]
1176  nz = di.dims[idz]
1177  nt = di.dims[idt]
1178  make /n=(nx,ny,nz,nt) /o $datawavename
1179  wave data = $datawavename
1180 
1181  nz = max(nz, 1)
1182  nt = max(nt, 1)
1183  nzt = nz * nt
1184  izt = 0
1185  if (progress)
1186  display_progress_panel("HDF5 Import", "Loading data...", nzt)
1187  endif
1188 
1189  // load data image by image
1190  HDF5MakeHyperslabWave("slab", max(di.ndims, 4))
1191  wave slab
1192  slab[][%Start] = 0
1193  slab[][%Stride] = 1
1194  slab[][%Count] = 1
1195  slab[][%Block] = 1
1196  slab[idx][%Block] = nx
1197  slab[idy][%Block] = ny
1198 
1199  variable iz, it
1200  for (iz = 0; iz < nz; iz += 1)
1201  for (it = 0; it < nt; it += 1)
1202  slab[idz][%Start] = iz
1203  slab[idt][%Start] = it
1204  HDF5LoadData /O /Q /Z /SLAB=slab /N=slabdata fileID, datasetpath
1205  wave slabdata// 2D, 3D, or 4D with singletons
1206  if (transpose)
1207  data[][][iz][it] = slabdata[q][p][0][0]
1208  else
1209  data[][][iz][it] = slabdata[p][q][0][0]
1210  endif
1211 
1212  // progress window
1213  izt += 1
1214  if (progress)
1215  if (update_progress_panel(izt))
1216  result = -4// user abort
1217  break
1218  endif
1219  endif
1220  endfor
1221  if (result < 0)
1222  break
1223  endif
1224  endfor
1225 
1226  if (progress)
1228  endif
1229 
1230  killwaves /z slab, slabdata
1231  if (!result)
1232  ps_set_dimlabels(data)
1233  return datawavename
1234  else
1235  killwaves /z data
1236  return ""
1237  endif
1238 };
1239 
1266 string psh5_load_dataset_slab(variable fileID, string datapath, string datasetname, variable dim2start, variable dim2count, variable dim3start, variable dim3count){
1267  variable fileID
1268  string datapath
1269  string datasetname
1270  variable dim2start
1271  variable dim2count
1272  variable dim3start
1273  variable dim3count
1274 
1275  string datasetpath
1276  string datawavename
1277  datasetpath = datapath + "/" + datasetname
1278  datasetpath = ReplaceString("//", datasetpath, "/")
1279  datawavename = StringFromList(ItemsInList(datasetpath, "/") - 1, datasetpath, "/")
1280 
1281  STRUCT HDF5DataInfo di
1282  InitHDF5DataInfo(di)
1283  variable err = HDF5DatasetInfo(fileID, datasetpath, 0, di)
1284  if (err != 0)
1285  print "error accessing detector/data"
1286  return ""
1287  endif
1288  if (di.ndims < 2)
1289  print "error: rank of dataset < 2"
1290  return ""
1291  endif
1292 
1293  variable idx, idy, idz, idt
1294  variable transpose = WhichListItem(datawavename, kTransposedDatasets) >= 0
1295  if (transpose)
1296  idx = 1
1297  idy = 0
1298  else
1299  idx = 0
1300  idy = 1
1301  endif
1302  idz = 2
1303  idt = 3
1304 
1305  variable nx, ny
1306  nx = di.dims[idx]
1307  ny = di.dims[idy]
1308  make /n=(nx,ny) /o $datawavename
1309  wave data = $datawavename
1310  data = 0
1311 
1312  HDF5MakeHyperslabWave("slab", max(di.ndims, 4))
1313  wave slab
1314  slab[][%Start] = 0
1315  slab[][%Stride] = 1
1316  slab[][%Count] = 1
1317  slab[][%Block] = 1
1318  slab[idx][%Block] = nx
1319  slab[idy][%Block] = ny
1320 
1321  variable iz, it
1322  variable navg = 0
1323  variable dim2end = dim2start + dim2count - 1
1324  variable dim3end = dim3start + dim3count - 1
1325  for (iz = dim2start; iz <= dim2end; iz += 1)
1326  for (it = dim3start; it <= dim3end; it += 1)
1327  slab[idz][%Start] = iz
1328  slab[idt][%Start] = it
1329  HDF5LoadData /O /Q /Z /SLAB=slab /N=slabdata fileID, datasetpath
1330  if (!v_flag)
1331  wave slabdata
1332  if (transpose)
1333  data += slabdata[q][p][0][0]
1334  else
1335  data += slabdata[p][q][0][0]
1336  endif
1337  navg += 1
1338  endif
1339  endfor
1340  endfor
1341  if (navg)
1342  data /= navg
1343  endif
1344 
1345  killwaves /z slab, slabdata
1346  ps_set_dimlabels(data)
1347  return datawavename
1348 };
1349 
1365 variable ps_set_dimlabels(wave data){
1366  wave data
1367 
1368  ps_set_dimlabels2(data, NameOfWave(data))
1369 };
1370 
1384 variable ps_set_dimlabels2(wave data, string name){
1385  wave data
1386  string name
1387 
1388  variable dummy
1389  try
1390  // intrinsic dimensions
1391  strswitch(name)
1392  case "ScientaImage":
1393  setdimlabel 0, -1, $kEnergyDimLabel, data
1394  setdimlabel 1, -1, $kAngleDimLabel, data
1395  if (WaveDims(data) >= 3)
1396  setdimlabel 2, -1, $kScanDimLabel, data
1397  endif
1398  AbortOnRTE
1399  break
1400  case "ImageAngleDistribution":
1401  case "ScientaAngleDistribution":
1402  if (WaveDims(data) >= 2)
1403  setdimlabel 0, -1, $kScanDimLabel, data
1404  setdimlabel 1, -1, $kAngleDimLabel, data
1405  else
1406  setdimlabel 0, -1, $kAngleDimLabel, data
1407  endif
1408  AbortOnRTE
1409  break
1410  case "ScientaSpectrum":
1411  case "ImageEnergyDistribution":
1412  case "ScientaEnergyDistribution":
1413  if (WaveDims(data) >= 2)
1414  setdimlabel 0, -1, $kScanDimLabel, data
1415  setdimlabel 1, -1, $kEnergyDimLabel, data
1416  else
1417  setdimlabel 0, -1, $kEnergyDimLabel, data
1418  endif
1419  AbortOnRTE
1420  break
1421  default:
1422  if (WaveDims(data) == 1)
1423  setdimlabel 0, -1, $kScanDimLabel, data
1424  AbortOnRTE
1425  else
1426  return 1
1427  endif
1428  endswitch
1429  catch
1430  dummy = GetRTError(1)
1431  return 2
1432  endtry
1433  return 0
1434 };
1435 
1441 static dfr find_scan_folder(dfref dataDF){
1442  dfref dataDF
1443 
1444  dfref attrDF = dataDF:attr
1445  if (!DataFolderRefStatus(attrDF))
1446  string df = GetDataFolder(1, dataDF) + ":"
1447  dfref scanDF = $df
1448  else
1449  dfref scanDF = dataDF
1450  endif
1451  return scanDF
1452 };
1453 
1458 static dfr find_attr_folder(dfref dataDF){
1459  dfref dataDF
1460 
1461  dfref attrDF = dataDF:attr
1462  if (!DataFolderRefStatus(attrDF))
1463  string df = GetDataFolder(1, dataDF) + ":"
1464  dfref scanDF = $df
1465  dfref attrDF = scanDF:attr
1466  endif
1467  return attrDF
1468 };
1469 
1487  dfref scanDF = GetDataFolderDFR()
1488  dfref attrDF = find_attr_folder(scanDF)
1489 
1490  make /n=3 /free lo, hi
1491  make /n=3 /t /free ax, un
1492  wave /t /z /SDFR=scanDF ScanReadables
1493  if (WaveExists(ScanReadables))
1494  variable isr
1495  variable nsr = numpnts(ScanReadables)
1496  string ssr
1497  string sdf
1498  for (isr = 0; isr < nsr; isr += 1)
1499  setdatafolder scanDF
1500  ssr = ScanReadables[isr]
1501  if (ItemsInList(ssr, "/") >= 2)
1502  sdf = StringFromList(0, ssr, "/")
1503  ssr = RemoveListItem(0, ssr, "/")
1504  setdatafolder $sdf
1505  endif
1506  wave /z wsr=$ssr
1507  if (WaveExists(wsr))
1508  ps_detect_scale(ax, lo, hi, un)
1509  ps_scale_dataset_2(wsr, ax, lo, hi, un)
1510  endif
1511  endfor
1512  endif
1513  setdatafolder scanDF
1514 };
1515 
1532 variable ps_scale_dataset(wave data){
1533  wave data
1534 
1535  dfref saveDF = GetDataFolderDFR()
1536  dfref dataDF = GetWavesDataFolderDFR(data)
1537 
1538  setdatafolder dataDF
1539  make /n=3 /free lo, hi
1540  make /n=3 /t /free ax, un
1541  ps_detect_scale(ax, lo, hi, un)
1542  ps_scale_dataset_2(data, ax, lo, hi, un)
1543  setdatafolder saveDF
1544 };
1545 
1546 static wave find_scale_wave(string name, dfref dataDF, dfref scanDF, dfref attrDF){
1547  string name
1548  dfref dataDF
1549  dfref scanDF
1550  dfref attrDF
1551 
1552  wave /SDFR=dataDF /Z w = $name
1553  if (!WaveExists(w))
1554  wave /SDFR=scanDF /Z w = $name
1555  if (!WaveExists(w))
1556  wave /SDFR=attrDF /Z w = $name
1557  endif
1558  endif
1559  return w
1560 };
1561 
1603 variable ps_detect_scale(wave ax, wave lo, wave hi, wave un){
1604  wave /t ax
1605  wave lo
1606  wave hi
1607  wave /t un
1608 
1609  dfref dataDF = GetDataFolderDFR()
1610  dfref scanDF = find_scan_folder(dataDF)
1611  dfref attrDF = find_attr_folder(dataDF)
1612 
1613  redimension /n=4 lo, hi, un, ax
1614  setdimlabel 0, 0, $kEnergyDimLabel, lo, hi, un, ax
1615  setdimlabel 0, 1, $kAngleDimLabel, lo, hi, un, ax
1616  setdimlabel 0, 2, $kScanDimLabel, lo, hi, un, ax
1617  setdimlabel 0, 3, $kDataDimLabel, lo, hi, un, ax
1618 
1619  // default values
1620  lo[%$kEnergyDimLabel] = 0
1621  hi[%$kEnergyDimLabel] = 1
1622  un[%$kEnergyDimLabel] = "eV"
1623  ax[%$kEnergyDimLabel] = "Ekin"
1624 
1625  lo[%$kAngleDimLabel] = -1
1626  hi[%$kAngleDimLabel] = 1
1627  un[%$kAngleDimLabel] = "arb."
1628  un[%$kAngleDimLabel] = "slice"
1629 
1630  lo[%$kScanDimLabel] = 0
1631  hi[%$kScanDimLabel] = 1
1632  un[%$kScanDimLabel] = "arb."
1633  ax[%$kScanDimLabel] = "scan"
1634 
1635  lo[%$kDataDimLabel] = 0
1636  hi[%$kDataDimLabel] = 0
1637  un[%$kDataDimLabel] = "arb."
1638  ax[%$kDataDimLabel] = "value"
1639 
1640  wave /SDFR=attrDF /T /Z LensMode
1641  wave /Z ChannelBegin = find_scale_wave("ScientaChannelBegin", dataDF, scanDF, attrDF)
1642  wave /Z ChannelEnd = find_scale_wave("ScientaChannelEnd", dataDF, scanDF, attrDF)
1643  wave /Z SliceBegin = find_scale_wave("ScientaSliceBegin", dataDF, scanDF, attrDF)
1644  wave /Z SliceEnd = find_scale_wave("ScientaSliceEnd", dataDF, scanDF, attrDF)
1645 
1646  // lens mode can give more detail
1647  if (waveexists(LensMode) && (numpnts(LensMode) >= 1))
1648  strswitch(LensMode[0])
1649  case "Angular45":
1650  lo[%$kAngleDimLabel] = -45/2
1651  hi[%$kAngleDimLabel] = +45/2
1652  un[%$kAngleDimLabel] = ""
1653  ax[%$kAngleDimLabel] = "angle"
1654  break
1655  case "Angular60":
1656  lo[%$kAngleDimLabel] = -60/2
1657  hi[%$kAngleDimLabel] = +60/2
1658  un[%$kAngleDimLabel] = ""
1659  ax[%$kAngleDimLabel] = "angle"
1660  break
1661  case "Transmission":
1662  un[%$kAngleDimLabel] = "arb."
1663  ax[%$kAngleDimLabel] = "offset"
1664  break
1665  endswitch
1666  endif
1667 
1668  // best option if scales are explicit in separate waves
1669  if (waveexists(ChannelBegin) && waveexists(ChannelEnd) && (numpnts(ChannelBegin) >= 1) && (numpnts(ChannelEnd) >= 1))
1670  lo[%$kEnergyDimLabel] = ChannelBegin[0]
1671  hi[%$kEnergyDimLabel] = ChannelEnd[0]
1672  endif
1673  if (waveexists(SliceBegin) && waveexists(SliceEnd) && (numpnts(SliceBegin) >= 1) && (numpnts(SliceEnd) >= 1))
1674  lo[%$kAngleDimLabel] = SliceBegin[0]
1675  hi[%$kAngleDimLabel] = SliceEnd[0]
1676  endif
1677 
1678  wave /z /t /SDFR=scanDF ScanWritables
1679  if (WaveExists(ScanWritables))
1680  wave /z /SDFR=scanDF scanner = $ScanWritables[0]
1681  if (!WaveExists(scanner))
1682  wave /z /SDFR=attrDF scanner = $ScanWritables[0]
1683  endif
1684  if (WaveExists(scanner) && (numpnts(scanner) >= 1))
1685  lo[%$kScanDimLabel] = scanner[0]
1686  hi[%$kScanDimLabel] = scanner[numpnts(scanner)-1]
1687  ax[%$kScanDimLabel] = NameOfWave(scanner)
1688  strswitch(NameOfWave(scanner))
1689  case "Eph":
1690  ax[%$kScanDimLabel] = "photon energy"
1691  un[%$kScanDimLabel] = "eV"
1692  break
1693  case "ManipulatorX":
1694  case "ManipulatorY":
1695  case "ManipulatorZ":
1696  case "FocusYTrans":
1697  case "FocusZTrans":
1698  case "RefocusYTrans":
1699  case "RefocusZTrans":
1700  case "ExitSlitY":
1701  un[%$kScanDimLabel] = "mm"
1702  break
1703  case "ExitSlit":
1704  un[%$kScanDimLabel] = "m"
1705  break
1706  case "ManipulatorTheta":
1707  case "ManipulatorTilt":
1708  case "ManipulatorPhi":
1709  un[%$kScanDimLabel] = ""
1710  break
1711  case "FocusXRot":
1712  case "FocusYRot":
1713  case "FocusZRot":
1714  case "RefocusXRot":
1715  case "RefocusYRot":
1716  case "RefocusZRot":
1717  un[%$kScanDimLabel] = "mrad"
1718  break
1719  endswitch
1720  endif
1721  endif
1722 };
1723 
1763 variable ps_scale_dataset_2(wave data, wave ax, wave lo, wave hi, wave un){
1764  wave data
1765  wave /t ax
1766  wave lo
1767  wave hi
1768  wave /t un
1769 
1770  string snote = note(data)
1771  string sdim
1772  sdim = GetDimLabel(data, 0, -1)
1773  if (strlen(sdim))
1774  setscale /i x lo[%$sdim], hi[%$sdim], un[%$sdim], data
1775  snote = ReplaceStringByKey("AxisLabelX", snote, ax[%$sdim], "=", "\r")
1776  endif
1777 
1778  sdim = GetDimLabel(data, 1, -1)
1779  if (strlen(sdim))
1780  setscale /i y lo[%$sdim], hi[%$sdim], un[%$sdim], data
1781  snote = ReplaceStringByKey("AxisLabelY", snote, ax[%$sdim], "=", "\r")
1782  endif
1783 
1784  sdim = GetDimLabel(data, 2, -1)
1785  if (strlen(sdim))
1786  setscale /i z lo[%$sdim], hi[%$sdim], un[%$sdim], data
1787  snote = ReplaceStringByKey("AxisLabelZ", snote, ax[%$sdim], "=", "\r")
1788  endif
1789 
1790  string data_unit = un[%$kDataDimLabel]
1791  string data_label = ax[%$kDataDimLabel]
1792  string s
1793  variable def = (cmpstr(data_unit, "arb.") == 0) && (cmpstr(data_label, "value") == 0)
1794 
1795  if (def)
1796  s = StringByKey("AxisLabelD", snote, "=", "\r")
1797  if (strlen(s) > 0)
1798  data_label = s
1799  def = 0
1800  endif
1801  s = StringByKey("AxisUnitD", snote, "=", "\r")
1802  if (strlen(s) > 0)
1803  data_unit = s
1804  def = 0
1805  endif
1806  endif
1807 
1808  if (def)
1809  strswitch(NameOfWave(data))
1810  case "ScientaImage":
1811  case "ImageAngleDistribution":
1812  case "ScientaAngleDistribution":
1813  case "ScientaSpectrum":
1814  case "ImageEnergyDistribution":
1815  case "ScientaEnergyDistribution":
1816  data *= kDetectorSensitivity
1817  data_unit = "counts"
1818  data_label = "intensity"
1819  def = 0
1820  break
1821  case "SampleCurrent":
1822  case "RefCurrent":
1823  case "AuxCurrent":
1824  data_unit = "A"
1825  data_label = "current"
1826  def = 0
1827  break
1828  case "MachineCurrent":
1829  data_unit = "mA"
1830  data_label = "current"
1831  def = 0
1832  break
1833  endswitch
1834  endif
1835 
1836  setscale d 0, 0, data_unit, data
1837  snote = ReplaceStringByKey("AxisLabelD", snote, data_label, "=", "\r")
1838  snote = ReplaceStringByKey("AxisUnitD", snote, data_unit, "=", "\r")
1839  snote = ReplaceStringByKey("Dataset", snote, NameOfWave(data), "=", "\r")
1840  note /k data, snote
1841 };
1842 
1893 string psh5_load_reduced(string ANickName, string APathName, string AFileName, funcref reduction_func, string reduction_param, variable progress = defaultValue, variable nthreads = defaultValue){
1894  string ANickName
1895  string APathName
1896  string AFileName
1897  funcref adh5_default_reduction reduction_func
1898  string reduction_param
1899  variable progress
1900  variable nthreads
1901 
1902  if (ParamIsDefault(progress))
1903  progress = 1
1904  endif
1905  if (ParamIsDefault(nthreads))
1906  nthreads = -1
1907  endif
1908 
1909  dfref saveDF = GetDataFolderDFR()
1910 
1911  // performance monitoring
1912  variable timerRefNum
1913  variable /g psh5_perf_secs
1914  timerRefNum = startMSTimer
1915 
1916  variable fileID = psh5_open_file(ANickName, APathName, AFileName)
1917  string wavenames = ""
1918  if (fileID)
1919  dfref fileDF = GetDataFolderDFR()
1920  svar s_filepath
1921  svar s_scanpaths
1922  AFileName = s_filepath
1923  print "loading " + s_filepath + "\r"
1924 
1925  variable ig = 0
1926  variable ng = ItemsInList(s_scanpaths)
1927  string scanpath
1928  string folder
1929  string positioners
1930  string positioner
1931  string positionerpath
1932 
1933  scanpath = StringFromList(ig, s_scanpaths)
1934  folder = ReplaceString("/", scanpath, "")
1935  folder = ReplaceString(" ", folder, "")
1936  folder = CleanupName(folder, 0)
1937  setdatafolder fileDF
1938  newdatafolder /s /o $folder
1939  dfref dataDF = GetDataFolderDFR()
1940  positioners = psh5_load_scan_meta(fileID, scanpath)
1941  newdatafolder /s /o attr
1942  killwaves /a/z
1943  psh5_load_scan_attrs(fileID, scanpath)
1944  setdatafolder dataDF
1945  wave /t /z ScanWritables
1946  if (waveexists(ScanWritables) && (numpnts(ScanWritables) >= 1))
1947  positioner = ScanWritables[0]
1948  if (strlen(positioner) > 0)
1949  positionerpath = scanpath + "/" + positioner
1950  positionerpath = ReplaceString("//", positionerpath, "/")
1951  HDF5LoadData /O /Q /Z fileID, positionerpath
1952  endif
1953  endif
1954 
1955  setdatafolder dataDF
1956  string datasets = psh5_list_scan_datasets(fileID, scanpath, include_regions=1)
1957  string dataset = select_dataset(datasets, "ScientaImage")
1958  wavenames = psh5_load_dataset_reduced(fileID, scanpath, dataset, reduction_func, reduction_param, progress=progress, nthreads=nthreads)
1959 
1960  psh5_close_file(fileID)
1961  endif
1962 
1963  if (timerRefNum >= 0)
1964  psh5_perf_secs = stopMSTimer(timerRefNum) / 1e6
1965  endif
1966 
1967  setdatafolder saveDF
1968  return wavenames
1969 };
1970 
1971 
2022 string psh5_load_dataset_reduced(variable fileID, string scanpath, string datasetname, funcref reduction_func, string reduction_param, variable progress = defaultValue, variable nthreads = defaultValue){
2023  variable fileID
2024  string scanpath
2025  string datasetname
2026  funcref adh5_default_reduction reduction_func
2027  string reduction_param
2028  variable progress
2029  variable nthreads
2030 
2031  if (ParamIsDefault(progress))
2032  progress = 1
2033  endif
2034  if (ParamIsDefault(nthreads))
2035  nthreads = -1
2036  endif
2037 
2038  dfref base_df = GetDataFolderDFR()
2039  variable result = 0
2040  string datasetpath
2041  string datawavename
2042  string wavenames = ""
2043 
2044  datasetpath = scanpath + "/" + datasetname
2045  datasetpath = ReplaceString("//", datasetpath, "/")
2046  datawavename = StringFromList(ItemsInList(datasetpath, "/") - 1, datasetpath, "/")
2047 
2048  string regionname
2049  string regionpath
2050  if (ItemsInList(datasetname, "/") >= 2)
2051  regionname = StringFromList(0, datasetname, "/")
2052  regionpath = ReplaceString("//", scanpath + "/" + regionname, "/")
2053  datasetname = RemoveListItem(0, datasetname, "/")
2054  NewDataFolder /o/s $regionname
2055  else
2056  regionname = ""
2057  regionpath = scanpath
2058  endif
2059 
2060  STRUCT HDF5DataInfo di// Defined in HDF5 Browser.ipf.
2061  InitHDF5DataInfo(di)
2062  variable err = HDF5DatasetInfo(fileID, datasetpath, 0, di)
2063  if (err != 0)
2064  print "error accessing detector/data"
2065  result = -1
2066  return wavenames
2067  endif
2068  if (di.ndims < 2)
2069  print "error: rank of dataset < 2"
2070  result = -2
2071  return wavenames
2072  else if (di.ndims < 3)
2073  progress = 0
2074  endif
2075 
2076  variable idx, idy, idz, idt
2077  variable transpose = WhichListItem(datawavename, kTransposedDatasets) >= 0
2078  if (transpose)
2079  idx = 1
2080  idy = 0
2081  else
2082  idx = 0
2083  idy = 1
2084  endif
2085  idz = 2
2086  idt = 3
2087 
2088  variable nx, ny, nz, nt, nzt
2089  nx = di.dims[idx]
2090  ny = di.dims[idy]
2091  nz = di.dims[idz]
2092  nt = di.dims[idt]
2093  // adjust singleton dimensions
2094  nz = max(nz, 1)
2095  nt = max(nt, 1)
2096  nzt = nz * nt
2097 
2098  // load data image by image
2099  HDF5MakeHyperslabWave("slab", max(di.ndims, 4))
2100  wave slab
2101  slab[][%Start] = 0
2102  slab[][%Stride] = 1
2103  slab[][%Count] = 1
2104  slab[][%Block] = 1
2105  slab[idx][%Block] = nx
2106  slab[idy][%Block] = ny
2107 
2108  // set up multi threading
2109  if (nthreads < 0)
2110  nthreads = ThreadProcessorCount
2111  endif
2112  if (nthreads > 0)
2113  variable threadGroupID = ThreadGroupCreate(nthreads)
2114  variable ithread
2115  for (ithread = 0; ithread < nthreads; ithread += 1)
2116  ThreadStart threadGroupID, ithread, reduce_slab_worker(reduction_func)
2117  endfor
2118  else
2119  make /n=(nzt) /df /free processing_folders
2120  endif
2121 
2122  if (progress)
2123  display_progress_panel("HDF5 Import", "Loading data (step 1 of 2)...", nzt)
2124  endif
2125 
2126  // create a template wave with the correct scales and labels
2127  make /n=(nx,ny) /d /o $datawavename
2128  wave template = $datawavename
2129  ps_set_dimlabels2(template, datawavename)
2130  ps_scale_dataset(template)
2131 
2132  variable iz, it, izt
2133  string dfname
2134  variable iw, nw
2135  string sw
2136  make /n=0 /free /wave result_waves
2137 
2138  izt = 0
2139  for (iz = 0; iz < nz; iz += 1)
2140  for (it = 0; it < nt; it += 1)
2141  // load hyperslab
2142  slab[idz][%Start] = iz
2143  slab[idt][%Start] = it
2144  dfname = "processing_" + num2str(izt)
2145  newdatafolder /s $dfname
2146  HDF5LoadData /O /Q /Z /SLAB=slab /N=slabdata fileID, datasetpath
2147 
2148  // send to processing queue
2149  duplicate template, image
2150  variable /g r_index = iz
2151  variable /g s_index = it
2152  string /g func_param = reduction_param
2153 
2154  if (nthreads > 0)
2155  WaveClear image
2156  ThreadGroupPutDF threadGroupID, :
2157  else
2158  processing_folders[izt] = GetDataFolderDFR()
2159  make /n=1/d profile1, profile2
2160  wave slabdata
2161  wave /wave reduced_waves = reduce_slab_image(slabdata, image, reduction_func, func_param)
2162  variable /g func_result = numpnts(reduced_waves)
2163  adh5_get_result_waves(reduced_waves, "redw_", 0)
2164  WaveClear slabdata, image, reduced_waves
2165  setdatafolder ::
2166  endif
2167 
2168  izt += 1
2169  // progress window
2170  if (progress)
2171  if (update_progress_panel(izt))
2172  print "user abort"
2173  result = -4
2174  break
2175  endif
2176  endif
2177  endfor
2178  endfor
2179 
2180  killwaves /z slab, slabdata, template
2181  if (progress)
2182  update_progress_panel(0, message="Processing data (step 2 of 2)...")
2183  endif
2184 
2185  dfref dfr
2186  for (izt = 0; (izt < nzt) && (result == 0); izt += 1)
2187  if (nthreads > 0)
2188  do
2189  if (progress)
2190  if (update_progress_panel(izt))
2191  print "user abort"
2192  result = -4
2193  break
2194  endif
2195  endif
2196  dfr = ThreadGroupGetDFR(threadGroupID, 1000)
2197  if (DatafolderRefStatus(dfr) != 0)
2198  break
2199  endif
2200  while (1)
2201  else
2202  if (progress)
2203  if (update_progress_panel(izt))
2204  print "user abort"
2205  result = -4
2206  break
2207  endif
2208  endif
2209  dfr = processing_folders[izt]
2210  endif
2211 
2212  if (result != 0)
2213  break
2214  endif
2215 
2216  nvar rr = dfr:r_index
2217  nvar ss = dfr:s_index
2218  nvar func_result = dfr:func_result
2219 
2220  if (func_result < 1)
2221  print "error during data reduction."
2222  result = -3
2223  break
2224  endif
2225 
2226  if (numpnts(result_waves) == 0)
2227  redimension /n=(func_result) result_waves
2228  for (iw = 0; iw < func_result; iw += 1)
2229  sw = "redw_" + num2str(iw)
2230  wave profile = dfr:$sw
2231  sw = "ReducedData" + num2str(iw+1)
2232  make /n=(dimsize(profile, 0), nz, nt) /d /o $sw
2233  wave data = $sw
2234  setdimlabel 0, -1, $getdimlabel(profile, 0, -1), data
2235  setdimlabel 1, -1, $kScanDimLabel, data
2236  note data, note(profile)
2237  ps_scale_dataset(data)
2238  setscale /p x dimoffset(profile, 0), dimdelta(profile, 0), waveunits(profile, 0), data
2239  setscale d 0, 0, waveunits(profile, -1), data
2240  result_waves[iw] = data
2241  endfor
2242  endif
2243  for (iw = 0; iw < func_result; iw += 1)
2244  sw = "redw_" + num2str(iw)
2245  wave profile = dfr:$sw
2246  wave data = result_waves[iw]
2247  data[][rr][ss] = profile[p]
2248  endfor
2249  endfor
2250 
2251  if (nthreads > 0)
2252  variable tstatus = ThreadGroupRelease(threadGroupID)
2253  if (tstatus == -2)
2254  print "error: thread did not terminate properly."
2255  result = -5
2256  endif
2257  else
2258  for (izt = 0; izt < nzt; izt += 1)
2259  KillDataFolder /Z processing_folders[izt]
2260  endfor
2261  endif
2262 
2263  if (result == 0)
2264  nw = numpnts(result_waves)
2265  wavenames = ""
2266  for (iw = 0; iw < nw; iw += 1)
2267  wave data = result_waves[iw]
2268  if (nz == 1)
2269  redimension /n=(-1, 0, 0) data
2270  else if (nt == 1)
2271  redimension /n=(-1, nz, 0) data
2272  endif
2273  wavenames += nameofwave(data) + ";"
2274  endfor
2275  endif
2276  if (progress)
2278  endif
2279 
2280  setdatafolder base_df
2281  return wavenames
2282 };
2283 
2284 threadsafe static variable reduce_slab_worker(funcref reduction_func){
2285  funcref adh5_default_reduction reduction_func
2286  do
2287  // wait for job from main thread
2288  do
2289  dfref dfr = ThreadGroupGetDFR(0, 1000)
2290  if (DataFolderRefStatus(dfr) == 0)
2291  if (GetRTError(2))
2292  return 0// no more jobs
2293  endif
2294  else
2295  break
2296  endif
2297  while (1)
2298 
2299  // get input data
2300  wave slabdata = dfr:slabdata
2301  wave image = dfr:image
2302  svar func_param = dfr:func_param
2303  nvar rr = dfr:r_index
2304  nvar ss = dfr:s_index
2305 
2306  // do the work
2307  newdatafolder /s outDF
2308  variable /g r_index = rr
2309  variable /g s_index = ss
2310  wave /wave reduced_waves = reduce_slab_image(slabdata, image, reduction_func, func_param)
2311  variable /g func_result = numpnts(reduced_waves)
2312 
2313  // send output to queue and clean up
2314  adh5_get_result_waves(reduced_waves, "redw_", 0)
2315  WaveClear slabdata, image, reduced_waves
2316  ThreadGroupPutDF 0, :
2317  KillDataFolder dfr
2318  while (1)
2319 
2320  return 0
2321 };
2322 
2323 threadsafe static wave reduce_slab_image(wave slabdata, wave image, funcref reduction_func, string reduction_param){
2324  wave slabdata
2325  wave image
2326  funcref adh5_default_reduction reduction_func
2327  string reduction_param
2328 
2329  // the multiplication by detector sensitivity assumes that we are loading a ScientaImage.
2330  image = slabdata[q][p][0][0] * kDetectorSensitivity
2331 
2332  return reduction_func(image, reduction_param)
2333 };
2334 
2349 string psh5_load_info(string APathName, string AFileName){
2350  string APathName
2351  string AFileName
2352 
2353  dfref saveDF = GetDataFolderDFR()
2354  dfref fileDF = NewFreeDataFolder()
2355  setdatafolder fileDF
2356 
2357  variable fileID
2358  string filepath
2359  string scanpaths
2360  variable nscans
2361  variable iscan
2362  string scanpath
2363  string info = ""
2364 
2365  HDF5OpenFile /P=$APathName /R fileID as AFileName
2366  if (v_flag == 0)
2367  filepath = s_path + s_filename
2368  scanpaths = psh5_list_scans(fileID)
2369  nscans = ItemsInList(scanpaths)
2370  for (iscan = 0; iscan < nscans; iscan += 1)
2371  scanpath = StringFromList(iscan, scanpaths)
2372  info = info + scanpath + "\r"
2373  info = info + psh5_load_scan_info(fileID, scanpath)
2374  endfor
2375  HDF5CloseFile fileID
2376  endif
2377 
2378  setdatafolder saveDF
2379  return info
2380 };
2381 
2396 string psh5_load_scan_info(variable fileID, string scanpath){
2397  variable fileID
2398  string scanpath
2399 
2400  string info = ""
2401  string positions = ""
2402  string positioners = ""
2403  string readables = ""
2404  string detectors = ""
2405  string regions = ""
2406 
2407  psh5_load_scan_meta(fileID, scanpath)
2408 
2409  wave /z ScanDimensions
2410  wave /t /z ScanWritables
2411  wave /t /z ScanReadables
2412  wave /z ScanSteps
2413 
2414  if (WaveExists(ScanSteps) && (numpnts(ScanSteps) >= 1))
2415  ScanSteps += 1
2416  positions = "positions = (" + wave2list(ScanSteps, "%u", ",") + ")"
2417  info = AddListItem(positions, info, "\r", inf)
2418  endif
2419  if (WaveExists(ScanWritables) && (numpnts(ScanWritables) >= 1))
2420  positioners = "positioners = " + twave2list(ScanWritables, ",")
2421  info = AddListItem(positioners, info, "\r", inf)
2422  endif
2423 
2424  variable i, m, n
2425  string s
2426  if (WaveExists(ScanReadables) && (numpnts(ScanReadables) >= 1))
2427  readables = twave2list(ScanReadables, ",")
2428  n = ItemsInList(readables, ",")
2429  for (i = 0; i < n; i += 1)
2430  s = StringFromList(i, readables, ",")
2431  m = ItemsInList(s, "/")
2432  if (m > 1)
2433  s = StringFromList(m - 1, s, "/")
2434  endif
2435  if (WhichListItem(s, detectors, ",") < 0)
2436  detectors = AddListItem(s, detectors, ",", inf)
2437  endif
2438  endfor
2439  detectors = "detectors = " + detectors
2440  info = AddListItem(detectors, info, "\r", inf)
2441  endif
2442 
2443  regions = psh5_list_scan_regions(fileID, scanpath)
2444  if (strlen(regions) > 0)
2445  regions = "regions = " + regions
2446  info = AddListItem(regions, info, "\r", inf)
2447  endif
2448 
2449  return info
2450 };
2451 
2455 static string twave2list(wave wt, string sep){
2456  wave /t wt
2457  string sep
2458 
2459  string list = ""
2460  variable n = numpnts(wt)
2461  variable i
2462  for (i = 0; i < n; i += 1)
2463  list = AddListItem(wt[i], list, sep, inf)
2464  endfor
2465 
2466  return list
2467 };
2468 
2472 static string wave2list(wave w, string format, string sep){
2473  wave w
2474  string format
2475  string sep
2476 
2477  string list = ""
2478  variable n = numpnts(w)
2479  variable i
2480  string s
2481  for (i = 0; i < n; i += 1)
2482  sprintf s, format, w[i]
2483  list = AddListItem(s, list, sep, inf)
2484  endfor
2485 
2486  return list
2487 };
2488 
string psh5_list_scan_regions(variable fileID, string scanpath)
list regions of a PShell scan group.
-
const string kEnergyDimLabel
Dimension label for the energy dispersive dimension of multi-dimensional datasets.
-
string psh5_load_dataset_reduced(variable fileID, string scanpath, string datasetname, funcref reduction_func, string reduction_param, variable progress=defaultValue, variable nthreads=defaultValue)
load a reduced dataset from the open PShell HDF5 file.
-
variable kill_progress_panel()
-
string psh5_load_reduced(string ANickName, string APathName, string AFileName, funcref reduction_func, string reduction_param, variable progress=defaultValue, variable nthreads=defaultValue)
load and reduce the ScientaImage dataset of the first scan of a PShell data file. ...
-
variable display_progress_panel(string title, string message, variable progress_max)
-
string psh5_load_scan_preview(variable fileID, string scanpath, variable set_scale=defaultValue, string pref_datasets=defaultValue)
load a preview dataset from an open PShell HDF5 file.
-
string psh5_load_scan_attrs(variable fileID, string scanpath, variable attr_sets=defaultValue)
load attributes of a PShell scan group.
-
const string kTransposedDatasets
List of datasets that should be transposed upon loading.
-
string psh5_load_scan_complete(variable fileID, string scanpath, variable load_data=defaultValue, variable load_attr=defaultValue)
load all data of a selected scan from a PShell data file.
-
static threadsafe variable reduce_slab_worker(funcref reduction_func)
-
variable ps_set_dimlabels2(wave data, string name)
set dimension labels according to the axis type
-
const string kScanDimLabel
Dimension label for the scan dimension of multi-dimensional datasets.
-
string psh5_load_dataset(variable fileID, string scanpath, string datasetname, variable set_scale=defaultValue)
load a dataset from an open PShell HDF5 file.
-
variable ps_set_dimlabels(wave data)
set dimension labels according to the axis type
-
threadsafe variable adh5_get_result_waves(wave results, string result_prefix, variable start_index)
copy waves from wave reference wave into current data folder
-
static dfr find_scan_folder(dfref dataDF)
find the scan folder
-
const string kAngleDimLabel
Dimension label for the angle dispersive dimension of multi-dimensional datasets. ...
-
static string twave2list(wave wt, string sep)
convert text wave to list.
-
variable ps_scale_dataset_2(wave data, wave ax, wave lo, wave hi, wave un)
set the dimension scales of a dataset.
-
static threadsafe wave reduce_slab_image(wave slabdata, wave image, funcref reduction_func, string reduction_param)
-
static string wave2list(wave w, string format, string sep)
convert numeric wave to list.
-
static string select_dataset(string file_datasets, string pref_datasets)
select the preferred dataset from a list of available datasets.
-
const string kDataDimLabel
Dimension label for the data dimension.
-
string psh5_load_preview(string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue, string pref_scans=defaultValue, string pref_datasets=defaultValue)
load a preview image from a PShell data file.
-
variable psh5_open_file(string ANickName, string APathName, string AFileName)
open a HDF5 file created by the PShell data acquisition program and prepare the data folder...
-
string psh5_load_dataset_slabs(variable fileID, string datapath, string datasetname, variable progress=defaultValue)
load a dataset slab-wise from the open PShell HDF5 file.
-
variable ps_scale_datasets()
set the dimension scales of loaded PShell Scienta datasets according to attributes.
-
string psh5_load_scan_meta(variable fileID, string scanpath)
load metadata of a PShell scan group.
-
const string kScientaScalingDatasets
List of datasets that must be loaded to determine the axis scaling of a Scienta image.
-
string psh5_load_scan_section(variable fileID, string scanpath, variable dim, variable set_scale=defaultValue, string pref_datasets=defaultValue)
load a longitudinal section of a scan from an open PShell HDF5 file.
-
string psh5_list_scan_datasets(variable fileID, string scanpath, variable include_regions=defaultValue)
list datasets of a PShell scan group.
-
string psh5_load_info(string APathName, string AFileName)
load descriptive info from a PShell data file.
-
string psh5_load_dataset_slab(variable fileID, string datapath, string datasetname, variable dim2start, variable dim2count, variable dim3start, variable dim3count)
load a single image from the open PShell data file.
-
threadsafe wave adh5_default_reduction(wave source, string *param)
function prototype for adh5_load_reduced_detector
-
string psh5_load_scan_data(variable fileID, string scanpath)
load all datasets of a PShell scan group.
-
const variable kDetectorSensitivity
multiply scienta detector intensity by this value to get actual counts.
-
string psh5_load_complete(string ANickName, string APathName, string AFileName, variable load_data=defaultValue, variable load_attr=defaultValue)
load everything from a PShell data file.
-
static dfr find_attr_folder(dfref dataDF)
find the attributes data folder
-
static wave find_scale_wave(string name, dfref dataDF, dfref scanDF, dfref attrDF)
-
variable update_progress_panel(variable progress, string message=defaultValue, variable progress_max=defaultValue)
-
string psh5_list_scans(variable fileID)
list scan groups of a PShell data file.
-
variable psh5_close_file(variable fileID)
close a HDF5 file opened by psh5_open_file.
-
variable ps_detect_scale(wave ax, wave lo, wave hi, wave un)
detect the dimension scales from attributes.
-
variable psh5_load_dataset_meta(variable fileID, string datapath, string datasetname, wave datawave)
load metadata of a PShell dataset.
-
const string kPreviewDatasets
List of preferred datasets to load for preview.
-
variable ps_scale_dataset(wave data)
set the dimension scales of a loaded PShell Scienta dataset according to attributes.
-
string psh5_load_scan_info(variable fileID, string scanpath)
load descriptive info from a PShell scan.
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-scienta-preprocess_8ipf.html b/doc/html/pearl-scienta-preprocess_8ipf.html index b010a9c..71d809d 100644 --- a/doc/html/pearl-scienta-preprocess_8ipf.html +++ b/doc/html/pearl-scienta-preprocess_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-scienta-preprocess.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
-
pearl-scienta-preprocess.ipf File Reference
+
pearl-scienta-preprocess.ipf File Reference
-

preprocessing functions for Scienta detector images. -More...

-
#include "pearl-fitfuncs"
-

Go to the source code of this file.

- - - - - -

-Namespaces

 PearlScientaPreprocess
 preprocessing functions for Scienta detector images.
 
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

-Functions

variable prompt_int_linbg_reduction (string *param)
 prompt the user for integrate on linear background reduction parameters. More...
 
string capture_int_linbg_cursors ()
 this function is for testing only, until we implement a proper interface More...
 
string csr_int_linbg_reduction (string win)
 set reduction parameters from cursors in a graph. More...
 
threadsafe wave int_linbg_reduction (wave source, string *param)
 linear-background subtracted integration reduction function. More...
 
variable prompt_int_quadbg_reduction (string *param)
 
threadsafe wave int_quadbg_reduction (wave source, string *param)
 integrate peak area minus a quadratic background More...
 
variable prompt_redim_linbg_reduction (string *param)
 parameter dialog for the redim_linbg_reduction() function More...
 
threadsafe wave redim_linbg_reduction (wave source, string *param)
 linear background reduction function for incorrectly dimensioned scienta image More...
 
variable test_gauss4_reduction (wave image)
 apply the gauss4_reduction function to a single image More...
 
variable prompt_gauss4_reduction (string *param)
 prompt for the gauss4_reduction parameters More...
 
threadsafe wave gauss4_reduction (wave source, string *param)
 fit horizontal cuts of an image with up to four gaussian peaks on a linear background More...
 
-

Detailed Description

-

preprocessing functions for Scienta detector images.

-

this procedure contains functions for data reduction and instrument-specific normalization.

-
Author
matthias muntwiler, matth.nosp@m.ias..nosp@m.muntw.nosp@m.iler.nosp@m.@psi..nosp@m.ch
- - -

Definition in file pearl-scienta-preprocess.ipf.

-

Function Documentation

- -
-
- - - - - - - -
string capture_int_linbg_cursors ()
-
- -

this function is for testing only, until we implement a proper interface

- -

Definition at line 67 of file pearl-scienta-preprocess.ipf.

- -
-
- -
-
- - - - - - - - -
string csr_int_linbg_reduction (string win)
-
- -

set reduction parameters from cursors in a graph.

-

PRELIMINARY - function arguments may change

-

sets reduction parameters from cursors in a graph. an even number of cursors (2 or more) must be set on the image. cursor names and order do not matter, except that the alphabetically first cursor which is attached to an image selects the image. the cursors mark the following positions, from innermost to outermost pair: 1) low and high limits of peak region. 2) peak-side boundary of lower and upper background region. 3) lower and upper cropping region.

- -

Definition at line 89 of file pearl-scienta-preprocess.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
threadsafe wave gauss4_reduction (wave source,
string * param 
)
-
- -

fit horizontal cuts of an image with up to four gaussian peaks on a linear background

-

the function fits each horizontal profile (EDC) with four gaussian peaks on a linear background. the position and width of the peaks is kept fixed according to input parameters. the peak amplitude is constrained to positive value.

-

the width parameter is defined as in Igor's gauss curve fit function (standard deviation divided by the square root of two). the return value in dest1 is the integrated peak of one of the peaks. dest2 returns the corresponding error estimate.

-
Parameters
- - - -
sourcesource wave. two-dimensional distribution of counts. for correct weighting and error estimation it is important that the source wave contains actual counts (Poisson statistics).
param(in, out) semicolon-separated key=value list of processing parameters. this is a pass-by-reference argument. the following parameters are required. position, width and limit parameters are on the x (energy) scale.
    -
  • rngl low limit of fit interval
  • -
  • rngh high limit of fit interval
  • -
  • pos1 position of peak 1
  • -
  • wid1 width of peak 1
  • -
  • pos2 position of peak 2
  • -
  • wid2 width of peak 2
  • -
  • pos3 position of peak 3
  • -
  • wid3 width of peak 3
  • -
  • pos4 position of peak 4
  • -
  • wid4 width of peak 4
  • -
  • npeaks number of peaks to fit: 1...4 the others are held at amplitude 0.
  • -
  • ybox box size of averaging in y direction, must be 1 or 3. other values lead to corrupt data.
  • -
-
-
-
-
Returns
free wave containing references of the result waves. the number of waves is two times the number of peaks that are fit. the first npeaks waves contain the peak integrals, the second npeaks waves the corresponding error estimates.
- -

Definition at line 672 of file pearl-scienta-preprocess.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
threadsafe wave int_linbg_reduction (wave source,
string * param 
)
-
- -

linear-background subtracted integration reduction function.

-

data reduction function for adh5_load_reduced_detector. cf. adh5_default_reduction for an explanation of reduction functions.

-

this function calculates the average pixel value of each angular slice in one center and two background intervals. a background value is calculated at the center position by linear interpolation from the two background values. returns the center minus linear background in dest1. returns the Poisson one-sigma error in dest2.

-

typical values (peak centered on detector, FWHM ~ 20 % of image) Lcrop=0.11;Hcrop=0.11;Lsize=0.2;Hsize=0.2;Cpos=0.5;Csize=0.2

-
Parameters
- - - -
sourcescienta detector image, energy axis along X, angle axis along Y. two-dimensional intensity distribution (image). the scales are carried over to the result waves.
paramparameters in a key1=value1;key2=value2;... list. all region parameters are relative to the image size (0...1).
    -
  • Lcrop = size of the lower cropping region
  • -
  • Hcrop = size of the upper cropping region
  • -
  • Lsize = size of the lower background integration region
  • -
  • Hsize = size of the upper background integration region
  • -
  • Cpos = center position of the of the peak integration region
  • -
  • Csize = size of the peak integration region
  • -
-
-
-
-
Returns
free wave containing references of the two result waves. the first wave is the integral minus linear background. the second wave is the Poisson one-sigma error.
- -

Definition at line 214 of file pearl-scienta-preprocess.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
threadsafe wave int_quadbg_reduction (wave source,
string * param 
)
-
- -

integrate peak area minus a quadratic background

-

data reduction function for adh5_load_reduced_detector. cf. adh5_default_reduction for an explanation of reduction functions.

-

this function calculates the average pixel value of each angular slice in one center and two background intervals. a background value is calculated at the center position by linear interpolation from the two background values. returns the center minus linear background in dest1. returns the Poisson one-sigma error in dest2.

-

typical values (peak centered on detector, FWHM ~ 20 % of image) Lcrop=0.11;Hcrop=0.11;Lsize=0.2;Hsize=0.2;Cpos=0.5;Csize=0.2

-
Parameters
- - - -
sourcescienta detector image, energy axis along X, angle axis along Y. two-dimensional intensity distribution (image). the scales are carried over to the result waves.
paramparameters in a key1=value1;key2=value2;... list. all region parameters are relative to the image size (0...1).
    -
  • Lcrop = size of the lower cropping region
  • -
  • Hcrop = size of the upper cropping region
  • -
  • Lsize = size of the lower background integration region
  • -
  • Hsize = size of the upper background integration region
  • -
  • Cpos = center position of the of the peak integration region
  • -
  • Csize = size of the peak integration region
  • -
-
-
-
-
Returns
free wave containing references of the two result waves. the first wave is the integral minus linear background. the second wave is the Poisson one-sigma error.
- -

Definition at line 367 of file pearl-scienta-preprocess.ipf.

- -
-
- -
-
- - - - - - - - -
variable prompt_gauss4_reduction (string * param)
-
- -

prompt for the gauss4_reduction parameters

- -

Definition at line 580 of file pearl-scienta-preprocess.ipf.

- -
-
- -
-
- - - - - - - - -
variable prompt_int_linbg_reduction (string * param)
-
- -

prompt the user for integrate on linear background reduction parameters.

- -

Definition at line 35 of file pearl-scienta-preprocess.ipf.

- -
-
- -
-
- - - - - - - - -
variable prompt_int_quadbg_reduction (string * param)
-
- -

Definition at line 305 of file pearl-scienta-preprocess.ipf.

- -
-
- -
-
- - - - - - - - -
variable prompt_redim_linbg_reduction (string * param)
-
- -

parameter dialog for the redim_linbg_reduction() function

-
Parameters
- - -
paramparameter string in a key1=value1;key2=value2;... list. the parameter string is passed by reference. see redim_linbg_reduction() for a description of parameters.
-
-
-
Returns
zero if the user clicked OK, non-zero if the user clicked Cancel.
- -

Definition at line 463 of file pearl-scienta-preprocess.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
threadsafe wave redim_linbg_reduction (wave source,
string * param 
)
-
- -

linear background reduction function for incorrectly dimensioned scienta image

-

if the energy step size does not divide the energy range to an integer number, the scienta image is exported with the wrong array size. this can be fixed by redimensioning the array.

-

the current implementation works in the case where dimension 0 needs to be incremented. the function may be generalized to dimension 1 and/or decrementing by additional parameters. it is not known yet whether a generalization is needed or whether it can cover all cases.

-

background subtraction and peak integration is the same as by the int_linbg_reduction() function.

-
Parameters
- - - -
sourcesource wave Scienta detector image, energy axis along X, angle axis along Y
paramparameter string in a key1=value1;key2=value2;... list. the parameter string is passed by reference.
-
-
-

all region parameters are relative to the image size (0...1).

    -
  • Lcrop size of the lower cropping region
  • -
  • Hcrop size of the upper cropping region
  • -
  • Lsize size of the lower background integration region
  • -
  • Hsize size of the upper background integration region
  • -
  • Cpos center position of the of the peak integration region
  • -
  • Csize size of the peak integration region
  • -
-

typical values (peak centered on detector, FWHM ~ 20 % of image) Lcrop=0.11;Hcrop=0.11;Lsize=0.2;Hsize=0.2;Cpos=0.5;Csize=0.2

-
Returns
free wave containing references of the two result waves. the first wave is the integral minus linear background. the second wave is the Poisson one-sigma error.
- -

Definition at line 526 of file pearl-scienta-preprocess.ipf.

- -
-
- -
-
- - - - - - - - -
variable test_gauss4_reduction (wave image)
-
- -

apply the gauss4_reduction function to a single image

-

useful for testing or manual processing. to debug, (temporarily) remove the threadsafe attribute from the gauss2_reduction function.

- -

Definition at line 546 of file pearl-scienta-preprocess.ipf.

- -
-
diff --git a/doc/html/pearl-scienta-preprocess_8ipf_source.html b/doc/html/pearl-scienta-preprocess_8ipf_source.html index 97d02da..a76ea3a 100644 --- a/doc/html/pearl-scienta-preprocess_8ipf_source.html +++ b/doc/html/pearl-scienta-preprocess_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-scienta-preprocess.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma IgorVersion = 6.1
3 #pragma ModuleName = PearlScientaPreprocess
4 #include "pearl-fitfuncs"
5 
6 // Copyright (c) 2013-18 Paul Scherrer Institut
7 //
8 // Licensed under the Apache License, Version 2.0 (the "License");
9 // you may not use this file except in compliance with the License.
10 // You may obtain a copy of the License at
11 // http://www.apache.org/licenses/LICENSE-2.0
12 
27 
32 
35 variable prompt_int_linbg_reduction(string* param){
36  string &param
37 
38  variable Lcrop = NumberByKey("Lcrop", param, "=", ";")
39  variable Lsize = NumberByKey("Lsize", param, "=", ";")
40  variable Hcrop = NumberByKey("Hcrop", param, "=", ";")
41  variable Hsize = NumberByKey("Hsize", param, "=", ";")
42  variable Cpos = NumberByKey("Cpos", param, "=", ";")
43  variable Csize = NumberByKey("Csize", param, "=", ";")
44 
45  prompt Lcrop, "Lower cropping region"
46  prompt Hcrop, "Upper cropping region"
47  prompt Lsize, "Lower background region"
48  prompt Hsize, "Upper background region"
49  prompt Cpos, "Center position"
50  prompt Csize, "Center integration region"
51 
52  doprompt "int_linbg_reduction Parameters", lcrop, hcrop, lsize, hsize, cpos, csize
53  if (v_flag == 0)
54  param = ReplaceNumberByKey("Lcrop", param, Lcrop, "=", ";")
55  param = ReplaceNumberByKey("Lsize", param, Lsize, "=", ";")
56  param = ReplaceNumberByKey("Hcrop", param, Hcrop, "=", ";")
57  param = ReplaceNumberByKey("Hsize", param, Hsize, "=", ";")
58  param = ReplaceNumberByKey("Cpos", param, Cpos, "=", ";")
59  param = ReplaceNumberByKey("Csize", param, Csize, "=", ";")
60  endif
61 
62  return v_flag
63 };
64 
68  string param = csr_int_linbg_reduction("")
69  svar /z global_params = root:packages:pearl_explorer:s_reduction_params
70  if (svar_exists(global_params))
71  global_params = param
72  endif
73  return param
74 };
75 
89 string csr_int_linbg_reduction(string win){
90  string win
91 
92  // read all cursor positions
93  variable ic
94  string sc
95  variable nc = 10
96  make /n=(nc) /free positions
97  variable np = 0
98  wave /z image = $""
99  string imagename = ""
100  string tracename = ""
101  string info
102 
103  for (ic = 0; ic < nc; ic += 1)
104  sc = num2char(char2num("A") + ic)
105  wave /z wc = CsrWaveRef($sc, win)
106  info = CsrInfo($sc, win)
107  tracename = StringByKey("TNAME", info, ":", ";")
108  if (waveexists(wc) && (wavedims(wc) == 2))
109  if (!waveexists(image))
110  wave image = wc
111  imagename = tracename
112  endif
113  if (cmpstr(tracename, imagename) == 0)
114  positions[np] = pcsr($sc, win)
115  np += 1
116  endif
117  endif
118  endfor
119 
120  np = floor(np / 2) * 2// ignore odd cursor
121  redimension /n=(np) positions
122  sort positions, positions
123  // shift upper positions by one so that the rightmost pixel becomes 1.0
124  positions = p >= np / 2 ? positions + 1 : positions
125  positions = positions / dimsize(image, 0)
126 
127  // map innermost cursor pair to peak center and size
128  variable ip2 = np / 2
129  variable ip1 = ip2 - 1
130  variable Cpos = (positions[ip1] + positions[ip2]) / 2
131  variable Csize = positions[ip2] - positions[ip1]
132  if (ip1 >= 0)
133  Cpos = (positions[ip1] + positions[ip2]) / 2
134  Csize = positions[ip2] - positions[ip1]
135  else
136  // default: a small region in the center
137  Cpos = 0.5
138  Csize = 0.2
139  endif
140 
141  // background region
142  ip1 -= 1
143  ip2 += 1
144  variable Lsize
145  variable Hsize
146  if (ip1 >= 0)
147  Lsize = positions[ip1]
148  Hsize = 1 - positions[ip2]
149  else
150  // default: everything outside the peak region
151  Lsize = Cpos - Csize / 2
152  Hsize = 1 - (Cpos + Csize / 2)
153  endif
154 
155  // crop region
156  ip1 -= 1
157  ip2 += 1
158  variable Lcrop
159  variable Hcrop
160  if (ip1 >= 0)
161  Lcrop = positions[ip1]
162  Hcrop = 1 - positions[ip2]
163  else
164  // default: dead corners of the EW4000 at PEARL
165  Lcrop = 0.11
166  Hcrop = 0.11
167  endif
168  Lsize = max(Lsize - Lcrop, 0)
169  Hsize = max(Hsize - Hcrop, 0)
170 
171  string param = ""
172  param = ReplaceNumberByKey("Lcrop", param, Lcrop, "=", ";")
173  param = ReplaceNumberByKey("Lsize", param, Lsize, "=", ";")
174  param = ReplaceNumberByKey("Hcrop", param, Hcrop, "=", ";")
175  param = ReplaceNumberByKey("Hsize", param, Hsize, "=", ";")
176  param = ReplaceNumberByKey("Cpos", param, Cpos, "=", ";")
177  param = ReplaceNumberByKey("Csize", param, Csize, "=", ";")
178 
179  return param
180 };
181 
214 threadsafe wave int_linbg_reduction(wave source, string* param){
215  wave source
216  string &param
217 
218  variable nx = dimsize(source, 0)
219  variable ny = dimsize(source, 1)
220 
221  // read parameters
222  variable lcrop = NumberByKey("Lcrop", param, "=", ";")
223  variable lsize = NumberByKey("Lsize", param, "=", ";")
224  variable hcrop = NumberByKey("Hcrop", param, "=", ";")
225  variable hsize = NumberByKey("Hsize", param, "=", ";")
226  variable cpos = NumberByKey("Cpos", param, "=", ";")
227  variable csize = NumberByKey("Csize", param, "=", ";")
228 
229  make /wave /free /n=2 result_waves
230  make /free /n=0 dest1, dest2
231  result_waves[0] = dest1
232  result_waves[1] = dest2
233  adh5_setup_profile(source, dest1, 1)
234  adh5_setup_profile(source, dest2, 1)
235 
236  // validate parameters
237  // background parameters are optional, center parameter is required.
238  if (numtype(lcrop) != 0)
239  lcrop = 0
240  endif
241  if (numtype(lsize) != 0)
242  lsize = 0
243  endif
244  if (numtype(hcrop) != 0)
245  hcrop = 0
246  endif
247  if (numtype(hsize) != 0)
248  hsize = 0
249  endif
250  if (numtype(Cpos) != 0)
251  redimension /n=0 result_waves
252  return result_waves// Cpos parameter missing
253  endif
254  if (numtype(Csize) != 0)
255  redimension /n=0 result_waves
256  return result_waves// Csize parameter missing
257  endif
258 
259  variable lpos = lcrop + lsize / 2
260  variable hpos = 1 - (hcrop + hsize / 2)
261 
262  variable p0
263  variable p1
264 
265  duplicate /free dest1, lbg, hbg
266  if (lsize > 0)
267  p0 = round(lcrop * nx)
268  p1 = round((lcrop + lsize) * nx)
269  ad_profile_y_w(source, p0, p1, lbg)
270  else
271  lbg = 0
272  endif
273  if (hsize > 0)
274  p0 = round((1 - hcrop - hsize) * nx)
275  p1 = round((1 - hcrop) * nx)
276  ad_profile_y_w(source, p0, p1, hbg)
277  else
278  hbg = 0
279  endif
280  if (csize > 0)
281  p0 = round((cpos - csize/2) * nx)
282  p1 = round((cpos + csize/2) * nx)
283  ad_profile_y_w(source, p0, p1, dest1)
284  else
285  dest1 = 0
286  endif
287 
288  variable scale = (cpos - lpos) / (hpos - lpos)
289  dest2 = dest1
290  dest1 -= scale * (hbg - lbg) + lbg
291  dest2 = sqrt(dest2 + scale^2 * (hbg + lbg))
292 
293  string s_note1
294  string s_note2
295  sprintf s_note1, "AxisLabelD=peak integral"
296  sprintf s_note2, "KineticEnergy=%.3f", cpos * nx * dimdelta(source, 0) + dimoffset(source, 0)
297  Note dest1, s_note1
298  Note dest1, s_note2
299  Note dest2, s_note1
300  Note dest2, s_note2
301 
302  return result_waves
303 };
304 
305 variable prompt_int_quadbg_reduction(string* param){
306  string &param
307 
308  variable Lcrop = NumberByKey("Lcrop", param, "=", ";")
309  variable Lsize = NumberByKey("Lsize", param, "=", ";")
310  variable Hcrop = NumberByKey("Hcrop", param, "=", ";")
311  variable Hsize = NumberByKey("Hsize", param, "=", ";")
312  variable Cpos = NumberByKey("Cpos", param, "=", ";")
313  variable Csize = NumberByKey("Csize", param, "=", ";")
314 
315  prompt Lcrop, "Lower cropping region"
316  prompt Hcrop, "Upper cropping region"
317  prompt Lsize, "Lower background region"
318  prompt Hsize, "Upper background region"
319  prompt Cpos, "Center position"
320  prompt Csize, "Center integration region"
321 
322  doprompt "int_quadbg_reduction Parameters", lcrop, hcrop, lsize, hsize, cpos, csize
323  if (v_flag == 0)
324  param = ReplaceNumberByKey("Lcrop", param, Lcrop, "=", ";")
325  param = ReplaceNumberByKey("Lsize", param, Lsize, "=", ";")
326  param = ReplaceNumberByKey("Hcrop", param, Hcrop, "=", ";")
327  param = ReplaceNumberByKey("Hsize", param, Hsize, "=", ";")
328  param = ReplaceNumberByKey("Cpos", param, Cpos, "=", ";")
329  param = ReplaceNumberByKey("Csize", param, Csize, "=", ";")
330  endif
331 
332  return v_flag
333 };
334 
367 threadsafe wave int_quadbg_reduction(wave source, string* param){
368  wave source
369  string &param
370 
371  variable nx = dimsize(source, 0)
372  variable ny = dimsize(source, 1)
373 
374  // read parameters
375  variable lcrop = NumberByKey("Lcrop", param, "=", ";")
376  variable lsize = NumberByKey("Lsize", param, "=", ";")
377  variable hcrop = NumberByKey("Hcrop", param, "=", ";")
378  variable hsize = NumberByKey("Hsize", param, "=", ";")
379  variable cpos = NumberByKey("Cpos", param, "=", ";")
380  variable csize = NumberByKey("Csize", param, "=", ";")
381 
382  make /wave /free /n=2 result_waves
383  make /free /n=0 dest1, dest2
384  result_waves[0] = dest1
385  result_waves[1] = dest2
386  adh5_setup_profile(source, dest1, 1)
387  adh5_setup_profile(source, dest2, 1)
388 
389  // validate parameters
390  // background parameters are optional, center parameter is required.
391  if (numtype(lcrop) != 0)
392  lcrop = 0
393  endif
394  if (numtype(lsize) != 0)
395  lsize = 0
396  endif
397  if (numtype(hcrop) != 0)
398  hcrop = 0
399  endif
400  if (numtype(hsize) != 0)
401  hsize = 0
402  endif
403  if (numtype(Cpos) != 0)
404  redimension /n=0 result_waves
405  return result_waves// Cpos parameter missing
406  endif
407  if (numtype(Csize) != 0)
408  redimension /n=0 result_waves
409  return result_waves// Csize parameter missing
410  endif
411 
412  // crop boundaries
413  variable pcl = round(lcrop * nx)
414  variable pch = round((1 - hcrop) * nx)
415  // fit boundaries
416  variable pfl = round((lcrop + lsize) * nx)
417  variable pfh = round((1 - hcrop - hsize) * nx)
418  // integration boundaries
419  variable pil = round((cpos - csize/2) * nx)
420  variable pih = round((cpos + csize/2) * nx)
421 
422  // prepare intermediate data buffer
423  make /n=(nx) /d /free profile, mask, fit
424  setscale /p x dimoffset(source,0), dimdelta(source,0), waveunits(source,0), profile, mask, fit
425  mask = ((p >= pcl) && (p < pfl)) || ((p >= pfh) && (p < pch))
426 
427  variable qq
428  variable sp, sf
429  variable xil = x2pnt(profile, pil)
430  variable xih = x2pnt(profile, pih)
431 
432  make /n=3 /free /d w_coef
433  for (qq = 0; qq < ny; qq += 1)
434  profile = source[p][qq]
435  curvefit /Q /NTHR=1 /W=2 poly 3, kwCWave=w_coef, profile /M=mask
436  fit = poly(w_coef, x)
437  sp = sum(profile, xil, xih)
438  sf = sum(fit, xil, xih)
439  dest1[qq] = sp - sf
440  dest2[qq] = sqrt(sp)
441  endfor
442 
443  string s_note1
444  string s_note2
445  sprintf s_note1, "AxisLabelD=peak integral"
446  sprintf s_note2, "KineticEnergy=%.3f", cpos * nx * dimdelta(source, 0) + dimoffset(source, 0)
447  Note dest1, s_note1
448  Note dest1, s_note2
449  Note dest2, s_note1
450  Note dest2, s_note2
451 
452  return result_waves
453 };
454 
463 variable prompt_redim_linbg_reduction(string* param){
464  string &param
465 
466  variable Lcrop = NumberByKey("Lcrop", param, "=", ";")
467  variable Lsize = NumberByKey("Lsize", param, "=", ";")
468  variable Hcrop = NumberByKey("Hcrop", param, "=", ";")
469  variable Hsize = NumberByKey("Hsize", param, "=", ";")
470  variable Cpos = NumberByKey("Cpos", param, "=", ";")
471  variable Csize = NumberByKey("Csize", param, "=", ";")
472 
473  prompt Lcrop, "Lower cropping region"
474  prompt Hcrop, "Upper cropping region"
475  prompt Lsize, "Lower background region"
476  prompt Hsize, "Upper background region"
477  prompt Cpos, "Center position"
478  prompt Csize, "Center integration region"
479 
480  doprompt "redim_linbg_reduction Parameters", lcrop, hcrop, lsize, hsize, cpos, csize
481  if (v_flag == 0)
482  param = ReplaceNumberByKey("Lcrop", param, Lcrop, "=", ";")
483  param = ReplaceNumberByKey("Lsize", param, Lsize, "=", ";")
484  param = ReplaceNumberByKey("Hcrop", param, Hcrop, "=", ";")
485  param = ReplaceNumberByKey("Hsize", param, Hsize, "=", ";")
486  param = ReplaceNumberByKey("Cpos", param, Cpos, "=", ";")
487  param = ReplaceNumberByKey("Csize", param, Csize, "=", ";")
488  endif
489 
490  return v_flag
491 };
492 
526 threadsafe wave redim_linbg_reduction(wave source, string* param){
527  wave source
528  string &param
529 
530  variable nx = dimsize(source, 0)
531  variable ny = dimsize(source, 1)
532 
533  duplicate /free source, source_redim
534  redimension /n=(nx * ny) source_redim
535  nx += 1
536  redimension /n=(nx, ny) source_redim
537 
538  return int_linbg_reduction(source_redim, param)
539 };
540 
546 variable test_gauss4_reduction(wave image){
547  wave image
548 
549  string param = ""
550 
551  param = ReplaceNumberByKey("rngl", param, -inf, "=", ";")
552  param = ReplaceNumberByKey("rngh", param, inf, "=", ";")
553  param = ReplaceNumberByKey("npeaks", param, 4, "=", ";")
554  param = ReplaceNumberByKey("ybox", param, 1, "=", ";")
555  param = ReplaceNumberByKey("pos1", param, 11, "=", ";")
556  param = ReplaceNumberByKey("wid1", param, 0.1, "=", ";")
557  param = ReplaceNumberByKey("pos2", param, 12, "=", ";")
558  param = ReplaceNumberByKey("wid2", param, 0.2, "=", ";")
559  param = ReplaceNumberByKey("pos3", param, 13, "=", ";")
560  param = ReplaceNumberByKey("wid3", param, 0.3, "=", ";")
561  param = ReplaceNumberByKey("pos4", param, 14, "=", ";")
562  param = ReplaceNumberByKey("wid4", param, 0.4, "=", ";")
563 
564  wave /wave results = gauss4_reduction(image, param)
565 
566  variable npk = numpnts(results) / 2
567  variable ipk
568  string sw
569  for (ipk = 0; ipk < npk; ipk += 1)
570  sw = "test_int_" + num2str(ipk + 1)
571  duplicate /o results[ipk], $sw
572  sw = "test_sig_" + num2str(ipk + 1)
573  duplicate /o results[ipk + npk], $sw
574  endfor
575 };
576 
580 variable prompt_gauss4_reduction(string* param){
581  string &param
582 
583  variable rngl = NumberByKey("rngl", param, "=", ";")
584  variable rngh = NumberByKey("rngh", param, "=", ";")
585  variable pos1 = NumberByKey("pos1", param, "=", ";")
586  variable wid1 = NumberByKey("wid1", param, "=", ";")
587  variable pos2 = NumberByKey("pos2", param, "=", ";")
588  variable wid2 = NumberByKey("wid2", param, "=", ";")
589  variable pos3 = NumberByKey("pos3", param, "=", ";")
590  variable wid3 = NumberByKey("wid3", param, "=", ";")
591  variable pos4 = NumberByKey("pos4", param, "=", ";")
592  variable wid4 = NumberByKey("wid4", param, "=", ";")
593  variable npeaks = NumberByKey("npeaks", param, "=", ";")
594  variable ybox = NumberByKey("ybox", param, "=", ";")
595 
596  prompt rngl, "range low"
597  prompt rngh, "range high"
598  prompt pos1, "position 1"
599  prompt wid1, "width 1"
600  prompt pos2, "position 2"
601  prompt wid2, "width 2"
602  prompt pos3, "position 3"
603  prompt wid3, "width 3"
604  prompt pos4, "position 4"
605  prompt wid4, "width 4"
606  prompt npeaks, "number of peaks"
607  prompt ybox, "ybox (1 or 3)"
608 
609  doprompt "gauss4_reduction reduction parameters (1/2)", rngl, rngh, npeaks, ybox
610  if (v_flag == 0)
611  param = ReplaceNumberByKey("rngl", param, rngl, "=", ";")
612  param = ReplaceNumberByKey("rngh", param, rngh, "=", ";")
613  param = ReplaceNumberByKey("npeaks", param, npeaks, "=", ";")
614  param = ReplaceNumberByKey("ybox", param, ybox, "=", ";")
615 
616  doprompt "gauss4_reduction reduction parameters (2/2)", pos1, wid1, pos2, wid2, pos3, wid3, pos4, wid4
617  if (v_flag == 0)
618  param = ReplaceNumberByKey("pos1", param, pos1, "=", ";")
619  param = ReplaceNumberByKey("wid1", param, wid1, "=", ";")
620  param = ReplaceNumberByKey("pos2", param, pos2, "=", ";")
621  param = ReplaceNumberByKey("wid2", param, wid2, "=", ";")
622  param = ReplaceNumberByKey("pos3", param, pos3, "=", ";")
623  param = ReplaceNumberByKey("wid3", param, wid3, "=", ";")
624  param = ReplaceNumberByKey("pos4", param, pos4, "=", ";")
625  param = ReplaceNumberByKey("wid4", param, wid4, "=", ";")
626  endif
627  endif
628 
629  return v_flag
630 };
631 
672 threadsafe wave gauss4_reduction(wave source, string* param){
673  wave source
674  string &param
675 
676  variable nx = dimsize(source, 0)
677  variable ny = dimsize(source, 1)
678 
679  // read parameters
680  variable rngl = NumberByKey("rngl", param, "=", ";")
681  variable rngh = NumberByKey("rngh", param, "=", ";")
682  variable pos1 = NumberByKey("pos1", param, "=", ";")
683  variable wid1 = NumberByKey("wid1", param, "=", ";")
684  variable pos2 = NumberByKey("pos2", param, "=", ";")
685  variable wid2 = NumberByKey("wid2", param, "=", ";")
686  variable pos3 = NumberByKey("pos3", param, "=", ";")
687  variable wid3 = NumberByKey("wid3", param, "=", ";")
688  variable pos4 = NumberByKey("pos4", param, "=", ";")
689  variable wid4 = NumberByKey("wid4", param, "=", ";")
690  variable npeaks = NumberByKey("npeaks", param, "=", ";")
691  variable ybox = NumberByKey("ybox", param, "=", ";")
692 
693  // prepare curve fit
694  variable ipk
695  make /free xprof
696  adh5_setup_profile(source, xprof, 0)
697  duplicate /free xprof, xprof_sig
698  variable pl = max(x2pnt(xprof, rngl), 0)
699  variable ph = min(x2pnt(xprof, rngh), numpnts(xprof) - 1)
700 
701  make /free /n=(npeaks) peak_coef
702  peak_coef = p * 3 + 2
703  variable n_coef = npeaks * 3 + 2
704  make /free /d /n=14 w_coef, W_sigma
705  w_coef[0] = {0, 0, 1, pos1, wid1, 1, pos2, wid2, 1, pos3, wid3, 1, pos4, wid4}
706  redimension /n=(n_coef) w_coef, w_sigma
707 
708  // text constraints cannot be used in threadsafe functions.
709  // the following matrix-vector forumlation is equivalent to:
710  // make /free /T /N=6 constraints
711  // constraints[0] = {"K2 >= 0", "K5 >= 0", "K8 >= 0", "K11 >= 0", "K1 <= 0", "K0 => 0"}
712  make /free /n=(npeaks + 2, numpnts(w_coef)) cmat
713  make /free /n=(npeaks + 2) cvec
714  cmat = 0
715  cmat[0][0] = -1
716  cmat[1][1] = 1
717  cvec = 0
718 
719  string hold = "00"
720  for (ipk=0; ipk < npeaks; ipk += 1)
721  hold += "011"
722  cmat[2 + ipk][2 + ipk*3] = -1
723  endfor
724 
725  // prepare output
726  make /free /n=(npeaks * 2) /wave result_waves
727  string s_note
728  for (ipk = 0; ipk < npeaks; ipk += 1)
729  make /free /n=0 pk_int
730  adh5_setup_profile(source, pk_int, 1)
731  pk_int = nan
732  sprintf s_note, "AxisLabelD=peak %u integral", ipk+1
733  Note pk_int, s_note
734  sprintf s_note, "KineticEnergy=%.3f", w_coef[3 + ipk * 3]
735  Note pk_int, s_note
736  result_waves[ipk] = pk_int
737 
738  make /free /n=0 pk_sig
739  adh5_setup_profile(source, pk_sig, 1)
740  pk_sig = nan
741  sprintf s_note, "AxisLabelD=peak %u sigma", ipk+1
742  Note pk_sig, s_note
743  sprintf s_note, "KineticEnergy=%.3f", w_coef[3 + ipk * 3]
744  Note pk_sig, s_note
745  result_waves[ipk + npeaks] = pk_sig
746 
747  waveclear pk_int, pk_sig
748  endfor
749 
750  // loop over angle scale
751  variable p0 = 0
752  variable p1 = dimsize(source, 1) - 1
753  variable pp
754  variable wmin
755  variable wmax
756  if (ybox > 1)
757  p0 += ceil((ybox - 1) / 2)
758  p1 -= ceil((ybox - 1) / 2)
759  endif
760  variable V_FitNumIters
761 
762  for (pp = p0; pp <= p1; pp += 1)
763  // box average
764  xprof = source[p][pp]
765  if (ybox > 1)
766  xprof += source[p][pp-1] + source[p][pp+1]
767  endif
768  xprof_sig = max(sqrt(xprof), 1)
769  xprof /= ybox
770  xprof_sig /= ybox
771 
772  // generate guess
773  wmin = wavemin(xprof)
774  wmax = wavemax(xprof)
775  w_coef[0] = wmin
776  w_coef[1] = 0
777 
778  for (ipk=0; ipk < npeaks; ipk += 1)
779  w_coef[2 + ipk*3] = wmax - wmin
780  endfor
781  FuncFit /H=hold /Q /NTHR=1 /N /W=2 MultiGaussLinBG_AO w_coef xprof[pl,ph] /C={cmat, cvec} /I=1 /W=xprof_sig[pl,ph]
782  wave w_sigma
783 
784  // retrieve results, leave them at nan if the fit did not converge
785  if (V_FitNumIters < 40)
786  for (ipk = 0; ipk < npeaks; ipk += 1)
787  wave val = result_waves[ipk]
788  wave sig = result_waves[ipk + npeaks]
789  val[pp] = max(w_coef[peak_coef[ipk]], 0)
790  sig[pp] = max(w_sigma[peak_coef[ipk]], 0)
791  endfor
792  endif
793  endfor
794 
795  // calculate integral
796  for (ipk = 0; ipk < npeaks; ipk += 1)
797  wave val = result_waves[ipk]
798  wave sig = result_waves[ipk + npeaks]
799  val *= w_coef[peak_coef[ipk] + 2] * sqrt(pi)
800  sig *= w_coef[peak_coef[ipk] + 2] * sqrt(pi)
801  endfor
802 
803  return result_waves
804 };
805 
806 
838 string find_gauss4_reduction_params(wave spectrum, wave peakpos){
839  wave spectrum
840  wave peakpos
841  string param = ""
842 
843  variable wmin = wavemin(spectrum)
844  variable wmax = wavemax(spectrum)
845 
846  // read parameters
847  variable rngl = dimoffset(spectrum, 0)
848  variable rngh = dimoffset(spectrum, 0) + dimdelta(spectrum, 0) * (dimsize(spectrum, 0) - 1)
849  make /n=4 /free positions, widths
850  variable npeaks = numpnts(peakpos)
851  variable ybox = 1
852  positions = 0
853  positions[0, npeaks-1] = peakpos[p]
854  widths = 0.2
855 
856  variable n_coef = npeaks * 3 + 2
857  make /free /d /n=(n_coef) w_coef
858  w_coef = 0
859  w_coef[0] = wmin
860  w_coef[1] = 0
861 
862  make /free /n=(2+npeaks, numpnts(w_coef)) cmat
863  make /free /n=(2+npeaks) cvec
864  cmat = 0
865  cmat[0][0] = -1
866  cmat[1][1] = 1
867  cvec = 0
868 
869  variable ip
870  for (ip=0; ip < npeaks; ip += 1)
871  cmat[2 + ip][2 + ip*3] = -1
872  w_coef[2 + ip*3] = wmax - wmin
873  w_coef[3 + ip*3] = peakpos[ip]
874  w_coef[4 + ip*3] = widths[ip]
875  endfor
876 
877  variable V_FitNumIters
878  FuncFit /Q /NTHR=1 /N MultiGaussLinBG w_coef spectrum /C={cmat, cvec}
879 
880  for (ip=0; ip < npeaks; ip += 1)
881  positions[ip] = w_coef[3 + ip * 3]
882  widths[ip ] = abs(w_coef[4 + ip * 3])
883  endfor
884  for (ip=npeaks; ip < 4; ip += 1)
885  positions[ip] = 0
886  widths[ip] = 0.2
887  endfor
888 
889  param = ReplaceNumberByKey("rngl", param, rngl, "=", ";")
890  param = ReplaceNumberByKey("rngh", param, rngh, "=", ";")
891  param = ReplaceNumberByKey("npeaks", param, npeaks, "=", ";")
892  param = ReplaceNumberByKey("ybox", param, ybox, "=", ";")
893  param = ReplaceNumberByKey("pos1", param, positions[0], "=", ";")
894  param = ReplaceNumberByKey("wid1", param, widths[0], "=", ";")
895  param = ReplaceNumberByKey("pos2", param, positions[1], "=", ";")
896  param = ReplaceNumberByKey("wid2", param, widths[1], "=", ";")
897  param = ReplaceNumberByKey("pos3", param, positions[2], "=", ";")
898  param = ReplaceNumberByKey("wid3", param, widths[2], "=", ";")
899  param = ReplaceNumberByKey("pos4", param, positions[3], "=", ";")
900  param = ReplaceNumberByKey("wid4", param, widths[3], "=", ";")
901 
902  return param
903 };
904 
912 variable test_shockley_anglefit(wave image, variable branch){
913  wave image
914  variable branch
915 
916  string param = ""
917  param = ReplaceStringByKey("branch", param, num2str(branch), "=", ";")
918 
919  string s_branch
920  if (branch >= 0)
921  s_branch = "p"
922  else
923  s_branch = "n"
924  endif
925  string pkpos_name = "saf_pkpos_" + s_branch
926  string pkwid_name = "saf_pkwid_" + s_branch
927 
928  wave /wave results = shockley_anglefit(image, param)
929  duplicate results[0], $pkpos_name
930  duplicate results[1], $pkwid_name
931 };
932 
933 variable prompt_Shockley_anglefit(string* param){
934  string &param
935 
936  variable branch = NumberByKey("branch", param, "=", ";")
937 
938  prompt branch, "Branch (-1 or +1)"
939 
940  doprompt "Shockley_anglefit_reduction Parameters", branch
941  if (v_flag == 0)
942  param = ReplaceNumberByKey("branch", param, branch, "=", ";")
943  endif
944 
945  return v_flag
946 };
947 
970 threadsafe wave Shockley_anglefit(wave source, string* param){
971  wave source
972  string &param
973 
974  variable nx = dimsize(source, 0)
975  variable ny = dimsize(source, 1)
976 
977  // read parameters
978  variable branch = NumberByKey("branch", param, "=", ";")
979 
980  // validate parameters
981  if (numtype(branch) != 0)
982  branch = +1
983  endif
984 
985  // prepare output
986  make /wave /free /n=2 result_waves
987  make /free /n=0 dest1, dest2
988  result_waves[0] = dest1
989  result_waves[1] = dest2
990  adh5_setup_profile(source, dest1, 0)
991  adh5_setup_profile(source, dest2, 0)
992  dest1 = nan
993  dest2 = nan
994 
995  // select angle range
996  // hard-coded for a particular measurement series
997  variable y0
998  variable y1
999  if (branch < 0)
1000  y0 = -5
1001  y1 = 0
1002  else
1003  y0 = 0
1004  y1 = 5
1005  endif
1006 
1007  // select energy range
1008  // start at the point of highest intensity and go up 0.45 eV
1009  variable p0
1010  variable p1
1011  variable q0
1012  variable q1
1013  duplicate /free dest1, center
1014  q0 = round((y0 - dimoffset(source, 1)) / dimdelta(source, 1))
1015  q1 = round((y1 - dimoffset(source, 1)) / dimdelta(source, 1))
1016  ad_profile_x_w(source, q0, q1, center)
1017  wavestats /q/m=1 center
1018  p0 = round((v_maxloc - dimoffset(source, 0)) / dimdelta(source, 0))
1019  p1 = round((v_maxloc + 0.4 - dimoffset(source, 0)) / dimdelta(source, 0))
1020 
1021  // prepare intermediate data buffer
1022  make /n=(ny)/d/free profile
1023  setscale /p x dimoffset(source,1), dimdelta(source,1), waveunits(source,1), profile
1024 
1025  variable pp
1026  for (pp = p0; pp <= p1; pp += 1)
1027  profile = source[pp][p]
1028  curvefit /Q /NTHR=1 /W=2 gauss profile(y0,y1)
1029  wave w_coef
1030  dest1[pp] = w_coef[2]
1031  dest2[pp] = w_coef[3]
1032  endfor
1033 
1034  return result_waves
1035 };
1036 
1037 variable scienta_norm(wave w, variable x){
1038  wave w
1039  variable x
1040 
1041  return w[0] * (x^2 - w[1]^2)
1042 };
1043 
1044 wave fit_scienta_ang_transm(wave data, wave params){
1045  wave data// measured angular distribution (1D)
1046  wave /z params
1047 
1048  if (!waveexists(params))
1049  make /n=12 /o params
1050  endif
1051  redimension /n=12/d params
1052 
1053  variable h = wavemax(data) - wavemin(data)
1054  params[0] = h / 2
1055  params[1] = 0
1056  params[2] = 7
1057  params[3] = h / 4
1058  params[4] = -23
1059  params[5] = 4
1060  params[6] = h / 4
1061  params[7] = +23
1062  params[8] = 4
1063  params[9] = h / 2
1064  params[10] = 0
1065  params[11] = -0.001
1066  FuncFit /NTHR=0 /q scienta_ang_transm params data
1067 
1068  return params
1069 };
1070 
1071 threadsafe variable scienta_ang_transm(wave w, variable x){
1072  // parameterized angular transmission function of the analyser
1073  wave w// coefficients
1074  // w[0] = amplitude gauss 1
1075  // w[1] = position gauss 1
1076  // w[2] = width gauss 1
1077  // w[3] = amplitude gauss 2
1078  // w[4] = position gauss 2
1079  // w[5] = width gauss 2
1080  // w[6] = amplitude gauss 3
1081  // w[7] = position gauss 3
1082  // w[8] = width gauss 3
1083  // w[9] = constant background
1084  // w[10] = linear background
1085  // w[11] = quadratic background
1086  variable x
1087 
1088  make /free /n=4 /d w_int
1089  w_int[0] = 0
1090  w_int[1,] = w[p - 1]
1091  variable pk1 = gauss1d(w_int, x)
1092  w_int[1,] = w[p + 2]
1093  variable pk2 = gauss1d(w_int, x)
1094  w_int[1,] = w[p + 5]
1095  variable pk3 = gauss1d(w_int, x)
1096  w_int[0,2] = w[9 + p]
1097  w_int[3] = 0
1098  variable bg = poly(w_int, x)
1099 
1100  return bg + pk1 + pk2 + pk3
1101 };
1102 
1103 wave fit_scienta_poly_bg(wave data, wave params, variable bgterms){
1104  wave data// measured distribution (2D)
1105  wave /z params// wave, will be redimensioned for the correct size
1106  variable bgterms// number of terms in the polynomial background: 2, 3, or 4
1107 
1108  if (!waveexists(params))
1109  make /n=15 /o params
1110  endif
1111  redimension /n=15 /d params
1112 
1113  variable wmax = wavemax(data)
1114  variable wmin = wavemin(data)
1115  params[0] = 0
1116  params[1] = 7
1117  params[2] = 1 / 2
1118  params[3] = -23
1119  params[4] = 4
1120  params[5] = 1 / 2
1121  params[6] = +23
1122  params[7] = 4
1123  params[8] = 1
1124  params[9] = 0
1125  params[10] = -0.001
1126  params[11] = wmin
1127  params[12] = (wmax - wmin) / dimdelta(data,1) / dimsize(data,1)
1128  params[13] = 0
1129  params[14] = 0
1130 
1131  string h = "0000000000000"
1132  if (bgterms < 3)
1133  h = h + "1"
1134  else
1135  h = h + "0"
1136  endif
1137  if (bgterms < 4)
1138  h = h + "1"
1139  else
1140  h = h + "0"
1141  endif
1142  FuncFitMD /NTHR=1 /q /h=h scienta_poly_bg params data
1143 
1144  return params
1145 };
1146 
1147 variable scienta_poly_bg(wave w, variable e, variable a){
1148  // polynomial background with
1149  // parameterized angular transmission function of the analyser
1150  wave w// coefficients
1151  // angular transmission, varies with a
1152  // amplitude of gauss 1 = 1 constant
1153  // other peak amplitudes and linear terms are relative to gauss 1
1154  // w[0] = position gauss 1
1155  // w[1] = width gauss 1
1156  // w[2] = amplitude gauss 2, relative to gauss 1
1157  // w[3] = position gauss 2
1158  // w[4] = width gauss 2
1159  // w[5] = amplitude gauss 3, relative to gauss 1
1160  // w[6] = position gauss 3
1161  // w[7] = width gauss 3
1162  // w[8] = constant term
1163  // w[9] = linear term
1164  // w[10] = quadratic term
1165  // spectral background, varies with e
1166  // w[11] = constant term
1167  // w[12] = linear term
1168  // w[13] = quadratic term
1169  // w[14] = cubic term
1170  variable a// detection angle
1171  variable e// electron energy
1172 
1173  make /free /n=4 /d w_int
1174  variable p0 = 0
1175 
1176  w_int[0] = 0
1177  w_int[1] = 1
1178  w_int[2,] = w[p0 + p - 2]
1179  variable pk1 = gauss1d(w_int, a)
1180  p0 += 2
1181 
1182  w_int[1,] = w[p0 + p - 1]
1183  variable pk2 = gauss1d(w_int, a)
1184  p0 += 3
1185 
1186  w_int[1,] = w[p0 + p - 1]
1187  variable pk3 = gauss1d(w_int, a)
1188  p0 += 3
1189 
1190  w_int[0,2] = w[p0 + p]
1191  w_int[3] = 0
1192  variable base = poly(w_int, a)
1193  p0 += 3
1194 
1195  w_int[0,3] = w[p0 + p]
1196  variable bg = poly(w_int, e)
1197 
1198  return bg * (base + pk1 + pk2 + pk3)
1199 };
1200 
threadsafe variable MultiGaussLinBG(wave w, variable x)
multiple gaussian peaks on a linear background fit function.
-
threadsafe variable MultiGaussLinBG_AO(wave pw, wave yw, wave xw)
multiple gaussian peaks on a linear background fit function (all at once).
-
variable prompt_gauss4_reduction(string *param)
prompt for the gauss4_reduction parameters
-
threadsafe wave redim_linbg_reduction(wave source, string *param)
linear background reduction function for incorrectly dimensioned scienta image
-
variable test_gauss4_reduction(wave image)
apply the gauss4_reduction function to a single image
-
threadsafe wave ad_profile_x_w(wave dataset, variable q1, variable q2, wave destwave, variable noavg=defaultValue)
1D cut through 2D dataset along X dimension, existing destination wave.
-
threadsafe variable adh5_setup_profile(wave image, wave profile, variable dim)
set up a one-dimensional wave for a line profile based on a 2D original wave.
-
variable prompt_int_quadbg_reduction(string *param)
-
threadsafe wave int_linbg_reduction(wave source, string *param)
linear-background subtracted integration reduction function.
-
threadsafe wave gauss4_reduction(wave source, string *param)
fit horizontal cuts of an image with up to four gaussian peaks on a linear background ...
-
variable prompt_redim_linbg_reduction(string *param)
parameter dialog for the redim_linbg_reduction() function
-
threadsafe wave ad_profile_y_w(wave dataset, variable p1, variable p2, wave destwave, variable noavg=defaultValue)
1D cut through 2D dataset along X dimension, existing destination wave.
-
threadsafe wave int_quadbg_reduction(wave source, string *param)
integrate peak area minus a quadratic background
-
variable prompt_int_linbg_reduction(string *param)
prompt the user for integrate on linear background reduction parameters.
-
string csr_int_linbg_reduction(string win)
set reduction parameters from cursors in a graph.
-
string capture_int_linbg_cursors()
this function is for testing only, until we implement a proper interface
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-tools_8ipf.html b/doc/html/pearl-tools_8ipf.html index b1ae11b..58eccdb 100644 --- a/doc/html/pearl-tools_8ipf.html +++ b/doc/html/pearl-tools_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-tools.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
pearl-tools.ipf File Reference
-
#include "pearl-gui-tools"
-
+

Go to the source code of this file.

- - - - - - - - - - - - - - -

-Functions

variable DefaultWaveIterator (wave w, string *sdata)
 
variable AppendToGraphIterator (wave w, string *sdata)
 
variable SumWavesIterator (wave w, string *sdata)
 
string IterateWaves (string matchStr, funcref iterator, string sdata)
 
variable DefaultFolderIterator (dfref df, string *sdata)
 
string IterateDataFolders (string matchStr, funcref iterator, string sdata, string progress_title=defaultValue)
 
-

Function Documentation

- -
-
- - - - - - - - - - - - - - - - - - -
variable AppendToGraphIterator (wave w,
string * sdata 
)
-
- -

Definition at line 26 of file pearl-tools.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable DefaultFolderIterator (dfref df,
string * sdata 
)
-
- -

Definition at line 65 of file pearl-tools.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable DefaultWaveIterator (wave w,
string * sdata 
)
-
- -

Definition at line 18 of file pearl-tools.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
string IterateDataFolders (string matchStr,
funcref iterator,
string sdata,
string progress_title = defaultValue 
)
-
- -

Definition at line 79 of file pearl-tools.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
string IterateWaves (string matchStr,
funcref iterator,
string sdata 
)
-
- -

Definition at line 45 of file pearl-tools.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable SumWavesIterator (wave w,
string * sdata 
)
-
- -

Definition at line 34 of file pearl-tools.ipf.

- -
-
diff --git a/doc/html/pearl-tools_8ipf_source.html b/doc/html/pearl-tools_8ipf_source.html index 6307608..4a55367 100644 --- a/doc/html/pearl-tools_8ipf_source.html +++ b/doc/html/pearl-tools_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-tools.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3// Use modern global access method and strict wave access.
2 #pragma version = 1.00
3 #pragma IgorVersion = 6.2
4 #pragma ModuleName = PearlTools
5 #include "pearl-gui-tools"
6 
7 // general programming tools for Igor
8 
9 // $Id$
10 // author: matthias.muntwiler@psi.ch
11 // Copyright (c) 2009-14 Paul Scherrer Institut
12 
13 // Licensed under the Apache License, Version 2.0 (the "License");
14 // you may not use this file except in compliance with the License.
15 // You may obtain a copy of the License at
16 // http://www.apache.org/licenses/LICENSE-2.0
17 
18 variable DefaultWaveIterator(wave w, string* sdata){
19 // function prototype for IterateWaves
20  wave w// wave which the iterator is supposed to work on
21  string &sdata// string with additional data, shared between calls
22  // this is a pass-by-reference argument,
23  // the function may modify the string
24 };
25 
26 variable AppendToGraphIterator(wave w, string* sdata){
27 // append iterated waves to the current graph
28  wave w// wave to be displayed
29  string &sdata// not used
30 
31  appendtograph w
32 };
33 
34 variable SumWavesIterator(wave w, string* sdata){
35 // sum waves into one result wave
36  wave w// wave which the iterator is supposed to work on
37  string &sdata// name of the result wave, can include absolute path
38  // the wave must exist and compatible with the summands
39  // the caller is responsible for initialization of the wave
40 
41  wave result = $sdata
42  result += w
43 };
44 
45 string IterateWaves(string matchStr, funcref iterator, string sdata){
46 // iterate over all waves matching a specified pattern (see built-in WaveList function),
47 // passing each wave to a user-defined iterator function
48  string matchStr// matchStr as for WaveList
49  funcref DefaultWaveIterator iterator// iterator function
50  // use the DefaultWaveIterator function as a template
51  string sdata// data string passed to iterator function
52  // the iterator may modify the string
53  // the function returns the string at the end
54 
55  string wlist = WaveList(matchStr, ";", "")
56  variable n = ItemsInList(wlist, ";")
57  variable i
58  for (i = 0; i < n; i += 1)
59  wave w = $(StringFromList(i, wlist, ";"))
60  iterator(w, sdata)
61  endfor
62  return sdata
63 };
64 
65 variable DefaultFolderIterator(dfref df, string* sdata){
66 // function prototype for IterateWaves
67  dfref df// data folder reference which the iterator is supposed to work on
68  string &sdata// string with additional data, shared between calls
69  // this is a pass-by-reference argument,
70  // the function may modify the string
71 
72  // switch to requested data folder
73  setdatafolder df
74  // for testing
75  print getdatafolder(1)
76  // no need to switch back to original folder
77 };
78 
79 string IterateDataFolders(string matchStr, funcref iterator, string sdata, string progress_title = defaultValue){
80 // iterate over all data folders matching a specified pattern in the current data folder,
81 // passing each folder to a user-defined iterator function
82  string matchStr// matchStr as for the built-in stringmatch function
83  funcref DefaultFolderIterator iterator// iterator function
84  // use the DefaultFolderIterator function as a template
85  string sdata// data string passed to iterator function
86  // the iterator may modify the string
87  // the function returns the string at the end
88  string progress_title// title of the progress window (optional)
89  // if not specified or empty, the progress window will not be shown.
90  // if the progress window is show, the user can abort the iteration.
91  // the function result does not indicate whether the iteration was completed or aborted.
92  // the iterator and caller must take care of leaving the data in a consistent state.
93 
94  if (ParamIsDefault(progress_title))
95  progress_title = ""
96  endif
97  variable show_progress = strlen(progress_title) > 0
98 
99  dfref origdf = GetDataFolderDFR()
100  dfref curdf
101  variable index = 0
102  variable abort_req = 0
103  string objName
104 
105  variable ndf = CountObjectsDFR(origdf, 4)
106  if (show_progress)
107  display_progress_panel(progress_title, "", ndf)
108  endif
109 
110  do
111  objName = GetIndexedObjNameDFR(origdf, 4, index)
112  if (strlen(objName) == 0)
113  break
114  endif
115  if (stringmatch(objname, matchstr))
116  if (show_progress)
117  abort_req = update_progress_panel(index, message=objName)
118  if (abort_req)
119  break
120  endif
121  endif
122  setdatafolder origdf
123  curdf = $(":" + objname)
124  iterator(curdf, sdata)
125  endif
126  index += 1
127  while(1)
128 
129  if (show_progress)
131  endif
132 
133  setdatafolder origdf
134  return sdata
135 };
136 
variable kill_progress_panel()
-
string IterateDataFolders(string matchStr, funcref iterator, string sdata, string progress_title=defaultValue)
Definition: pearl-tools.ipf:79
-
variable display_progress_panel(string title, string message, variable progress_max)
-
variable AppendToGraphIterator(wave w, string *sdata)
Definition: pearl-tools.ipf:26
-
string IterateWaves(string matchStr, funcref iterator, string sdata)
Definition: pearl-tools.ipf:45
-
variable DefaultWaveIterator(wave w, string *sdata)
Definition: pearl-tools.ipf:18
-
variable update_progress_panel(variable progress, string message=defaultValue, variable progress_max=defaultValue)
-
variable SumWavesIterator(wave w, string *sdata)
Definition: pearl-tools.ipf:34
-
variable DefaultFolderIterator(dfref df, string *sdata)
Definition: pearl-tools.ipf:65
-
+Go to the documentation of this file.
diff --git a/doc/html/pearl-vector-operations_8ipf.html b/doc/html/pearl-vector-operations_8ipf.html index 5e41ff5..41ec36c 100644 --- a/doc/html/pearl-vector-operations_8ipf.html +++ b/doc/html/pearl-vector-operations_8ipf.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-vector-operations.ipf File Reference @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-
pearl-vector-operations.ipf File Reference

Go to the source code of this file.

- - - - - - - - - - - - - - - - - - - - -

-Functions

variable rotate2d_x (variable xx, variable yy, variable angle)
 
variable rotate2d_y (variable xx, variable yy, variable angle)
 
wave create_rotation_matrix_free ()
 
wave set_rotation_x (wave matrix, variable angle)
 
wave set_rotation_y (wave matrix, variable angle)
 
wave set_rotation_z (wave matrix, variable angle)
 
variable rotate_x_wave (wave inout, variable angle)
 
variable rotate_y_wave (wave inout, variable angle)
 
variable rotate_z_wave (wave inout, variable angle)
 
-

Function Documentation

- -
-
- - - - - - - -
wave create_rotation_matrix_free ()
-
- -

Definition at line 26 of file pearl-vector-operations.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable rotate2d_x (variable xx,
variable yy,
variable angle 
)
-
- -

Definition at line 10 of file pearl-vector-operations.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - -
variable rotate2d_y (variable xx,
variable yy,
variable angle 
)
-
- -

Definition at line 18 of file pearl-vector-operations.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable rotate_x_wave (wave inout,
variable angle 
)
-
- -

Definition at line 83 of file pearl-vector-operations.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable rotate_y_wave (wave inout,
variable angle 
)
-
- -

Definition at line 101 of file pearl-vector-operations.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
variable rotate_z_wave (wave inout,
variable angle 
)
-
- -

Definition at line 119 of file pearl-vector-operations.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
wave set_rotation_x (wave matrix,
variable angle 
)
-
- -

Definition at line 35 of file pearl-vector-operations.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
wave set_rotation_y (wave matrix,
variable angle 
)
-
- -

Definition at line 51 of file pearl-vector-operations.ipf.

- -
-
- -
-
- - - - - - - - - - - - - - - - - - -
wave set_rotation_z (wave matrix,
variable angle 
)
-
- -

Definition at line 67 of file pearl-vector-operations.ipf.

- -
-
diff --git a/doc/html/pearl-vector-operations_8ipf_source.html b/doc/html/pearl-vector-operations_8ipf_source.html index 390c2ae..92f922f 100644 --- a/doc/html/pearl-vector-operations_8ipf_source.html +++ b/doc/html/pearl-vector-operations_8ipf_source.html @@ -3,7 +3,8 @@ - + + PEARL Procedures: pearl-vector-operations.ipf Source File @@ -14,14 +15,10 @@ - @@ -32,7 +29,7 @@
PEARL Procedures -  rev-distro-2.0.0-0-gfda49c3-dirty +  rev-distro-2.0.2-0-g3235d52
Igor procedures for the analysis of PEARL data
@@ -41,41 +38,19 @@ - + - - + + + +
-Go to the documentation of this file.
1 #pragma rtGlobals=3
2 #pragma version = 2.0
3 #pragma IgorVersion = 6.1
4 #pragma ModuleName = PearlVectorOperations
5 
6 // author: matthias.muntwiler@psi.ch
7 // Copyright (c) 2011-13 Paul Scherrer Institut
8 // $Id$
9 
10 variable rotate2d_x(variable xx, variable yy, variable angle){
11  // rotates a 2D cartesian vector and returns its x component
12  variable xx, yy
13  variable angle// rotation angle in degrees
14 
15  return xx * cos(angle * pi / 180) - yy * sin(angle * pi / 180)
16 };
17 
18 variable rotate2d_y(variable xx, variable yy, variable angle){
19  // rotates a 2D cartesian vector and returns its y component
20  variable xx, yy
21  variable angle// rotation angle in degrees
22 
23  return xx * sin(angle * pi / 180) + yy * cos(angle * pi / 180)
24 };
25 
27  // creates a matrix which represents a 3-vector rotation
28  // the matrix is initialized as identity
29 
30  make /n=(3,3)/free matrix
31  matrix = p == q// identity
32  return matrix
33 };
34 
35 wave set_rotation_x(wave matrix, variable angle){
36  // calculates a matrix representing a 3-vector rotation around the x axis
37  wave matrix// rotation matrix
38  variable angle// rotation angle in degrees
39 
40  variable si = sin(angle * pi / 180)
41  variable co = cos(angle * pi / 180)
42 
43  matrix[1][1] = co
44  matrix[2][2] = co
45  matrix[2][1] = si
46  matrix[1][2] = -si
47 
48  return matrix
49 };
50 
51 wave set_rotation_y(wave matrix, variable angle){
52  // calculates a matrix representing a 3-vector rotation around the y axis
53  wave matrix// rotation matrix
54  variable angle// rotation angle in degrees
55 
56  variable si = sin(angle * pi / 180)
57  variable co = cos(angle * pi / 180)
58 
59  matrix[0][0] = co
60  matrix[2][2] = co
61  matrix[0][2] = si
62  matrix[2][0] = -si
63 
64  return matrix
65 };
66 
67 wave set_rotation_z(wave matrix, variable angle){
68  // calculates a matrix representing a 3-vector rotation around the z axis
69  wave matrix// rotation matrix
70  variable angle// rotation angle in degrees
71 
72  variable si = sin(angle * pi / 180)
73  variable co = cos(angle * pi / 180)
74 
75  matrix[0][0] = co
76  matrix[1][1] = co
77  matrix[1][0] = si
78  matrix[0][1] = -si
79 
80  return matrix
81 };
82 
83 variable rotate_x_wave(wave inout, variable angle){
84  // rotates a wave of 3-vectors about the x axis
85  wave inout// wave with dimensions (3, N), N >= 1, (x, y, z)
86  // result will be in same wave
87  variable angle// rotation angle in degrees
88 
89  wave m_rotation_x = create_rotation_matrix_free()
90  make /n=3/d/free w_temp_rotate_x
91  variable ivec, nvec
92  nvec = max(DimSize(inout, 1), 1)
93  for (ivec = 0; ivec < nvec; ivec += 1)
94  set_rotation_x(m_rotation_x, angle)
95  w_temp_rotate_x = inout[p][ivec]
96  matrixop /free w_temp_rotate_x_result = m_rotation_x x w_temp_rotate_x
97  inout[][ivec] = w_temp_rotate_x_result[p]
98  endfor
99 };
100 
101 variable rotate_y_wave(wave inout, variable angle){
102  // rotates a wave of 3-vectors about the y axis
103  wave inout// wave with dimensions (3, N), N >= 1, (x, y, z)
104  // result will be in same wave
105  variable angle// rotation angle in degrees
106 
107  wave m_rotation_y = create_rotation_matrix_free()
108  make /n=3/d/free w_temp_rotate_y
109  variable ivec, nvec
110  nvec = max(DimSize(inout, 1), 1)
111  for (ivec = 0; ivec < nvec; ivec += 1)
112  set_rotation_y(m_rotation_y, angle)
113  w_temp_rotate_y = inout[p][ivec]
114  matrixop /free w_temp_rotate_y_result = m_rotation_y x w_temp_rotate_y
115  inout[][ivec] = w_temp_rotate_y_result[p]
116  endfor
117 };
118 
119 variable rotate_z_wave(wave inout, variable angle){
120  // rotates a wave of 3-vectors about the z axis
121  wave inout// wave with dimensions (3, N), N >= 1, (x, y, z)
122  // result will be in same wave
123  variable angle// rotation angle in degrees
124 
125  wave m_rotation_z = create_rotation_matrix_free()
126  make /n=3/d/free w_temp_rotate_z
127  variable ivec, nvec
128  nvec = max(DimSize(inout, 1), 1)
129  for (ivec = 0; ivec < nvec; ivec += 1)
130  set_rotation_z(m_rotation_z, angle)
131  w_temp_rotate_z = inout[p][ivec]
132  matrixop /free w_temp_rotate_z_result = m_rotation_z x w_temp_rotate_z
133  inout[][ivec] = w_temp_rotate_z_result[p]
134  endfor
135 };
136 
wave set_rotation_x(wave matrix, variable angle)
-
variable rotate_x_wave(wave inout, variable angle)
-
variable rotate2d_x(variable xx, variable yy, variable angle)
-
wave set_rotation_z(wave matrix, variable angle)
-
variable rotate_y_wave(wave inout, variable angle)
-
variable rotate2d_y(variable xx, variable yy, variable angle)
-
variable rotate_z_wave(wave inout, variable angle)
-
wave create_rotation_matrix_free()
-
wave set_rotation_y(wave matrix, variable angle)
-
+Go to the documentation of this file.
diff --git a/doc/html/resize.js b/doc/html/resize.js index 2b86c36..56e4a02 100644 --- a/doc/html/resize.js +++ b/doc/html/resize.js @@ -1,73 +1,104 @@ -var cookie_namespace = 'doxygen'; -var sidenav,navtree,content,header; - -function readCookie(cookie) -{ - var myCookie = cookie_namespace+"_"+cookie+"="; - if (document.cookie) - { - var index = document.cookie.indexOf(myCookie); - if (index != -1) - { - var valStart = index + myCookie.length; - var valEnd = document.cookie.indexOf(";", valStart); - if (valEnd == -1) - { - valEnd = document.cookie.length; - } - var val = document.cookie.substring(valStart, valEnd); - return val; - } - } - return 0; -} - -function writeCookie(cookie, val, expiration) -{ - if (val==undefined) return; - if (expiration == null) - { - var date = new Date(); - date.setTime(date.getTime()+(10*365*24*60*60*1000)); // default expiration is one week - expiration = date.toGMTString(); - } - document.cookie = cookie_namespace + "_" + cookie + "=" + val + "; expires=" + expiration+"; path=/"; -} - -function resizeWidth() -{ - var windowWidth = $(window).width() + "px"; - var sidenavWidth = $(sidenav).outerWidth(); - content.css({marginLeft:parseInt(sidenavWidth)+"px"}); - writeCookie('width',sidenavWidth, null); -} - -function restoreWidth(navWidth) -{ - var windowWidth = $(window).width() + "px"; - content.css({marginLeft:parseInt(navWidth)+6+"px"}); - sidenav.css({width:navWidth + "px"}); -} - -function resizeHeight() -{ - var headerHeight = header.outerHeight(); - var footerHeight = footer.outerHeight(); - var windowHeight = $(window).height() - headerHeight - footerHeight; - content.css({height:windowHeight + "px"}); - navtree.css({height:windowHeight + "px"}); - sidenav.css({height:windowHeight + "px"}); -} - function initResizable() { + var cookie_namespace = 'doxygen'; + var sidenav,navtree,content,header,collapsed,collapsedWidth=0,barWidth=6,desktop_vp=768,titleHeight; + + function readCookie(cookie) + { + var myCookie = cookie_namespace+"_"+cookie+"="; + if (document.cookie) { + var index = document.cookie.indexOf(myCookie); + if (index != -1) { + var valStart = index + myCookie.length; + var valEnd = document.cookie.indexOf(";", valStart); + if (valEnd == -1) { + valEnd = document.cookie.length; + } + var val = document.cookie.substring(valStart, valEnd); + return val; + } + } + return 0; + } + + function writeCookie(cookie, val, expiration) + { + if (val==undefined) return; + if (expiration == null) { + var date = new Date(); + date.setTime(date.getTime()+(10*365*24*60*60*1000)); // default expiration is one week + expiration = date.toGMTString(); + } + document.cookie = cookie_namespace + "_" + cookie + "=" + val + "; expires=" + expiration+"; path=/"; + } + + function resizeWidth() + { + var windowWidth = $(window).width() + "px"; + var sidenavWidth = $(sidenav).outerWidth(); + content.css({marginLeft:parseInt(sidenavWidth)+"px"}); + writeCookie('width',sidenavWidth-barWidth, null); + } + + function restoreWidth(navWidth) + { + var windowWidth = $(window).width() + "px"; + content.css({marginLeft:parseInt(navWidth)+barWidth+"px"}); + sidenav.css({width:navWidth + "px"}); + } + + function resizeHeight() + { + var headerHeight = header.outerHeight(); + var footerHeight = footer.outerHeight(); + var windowHeight = $(window).height() - headerHeight - footerHeight; + content.css({height:windowHeight + "px"}); + navtree.css({height:windowHeight + "px"}); + sidenav.css({height:windowHeight + "px"}); + var width=$(window).width(); + if (width!=collapsedWidth) { + if (width=desktop_vp) { + if (!collapsed) { + collapseExpand(); + } + } else if (width>desktop_vp && collapsedWidth0) { + restoreWidth(0); + collapsed=true; + } + else { + var width = readCookie('width'); + if (width>200 && width<$(window).width()) { restoreWidth(width); } else { restoreWidth(200); } + collapsed=false; + } + } + header = $("#top"); sidenav = $("#side-nav"); content = $("#doc-content"); navtree = $("#nav-tree"); footer = $("#nav-path"); $(".side-nav-resizable").resizable({resize: function(e, ui) { resizeWidth(); } }); + $(sidenav).resizable({ minWidth: 0 }); $(window).resize(function() { resizeHeight(); }); + var device = navigator.userAgent.toLowerCase(); + var touch_device = device.match(/(iphone|ipod|ipad|android)/); + if (touch_device) { /* wider split bar for touch only devices */ + $(sidenav).css({ paddingRight:'20px' }); + $('.ui-resizable-e').css({ width:'20px' }); + $('#nav-sync').css({ right:'34px' }); + barWidth=20; + } var width = readCookie('width'); if (width) { restoreWidth(width); } else { resizeWidth(); } resizeHeight(); @@ -76,22 +107,8 @@ function initResizable() if (i>=0) window.location.hash=url.substr(i); var _preventDefault = function(evt) { evt.preventDefault(); }; $("#splitbar").bind("dragstart", _preventDefault).bind("selectstart", _preventDefault); - $(document).bind('touchmove',function(e){ - var device = navigator.userAgent.toLowerCase(); - var ios = device.match(/(iphone|ipod|ipad)/); - if (ios) { - try { - var target = e.target; - while (target) { - if ($(target).css('-webkit-overflow-scrolling')=='touch') return; - target = target.parentNode; - } - e.preventDefault(); - } catch(err) { - e.preventDefault(); - } - } - }); + $(".ui-resizable-handle").dblclick(collapseExpand); + $(window).load(resizeHeight); } diff --git a/doc/html/search/all_0.html b/doc/html/search/all_0.html index d54e0bd..f25360b 100644 --- a/doc/html/search/all_0.html +++ b/doc/html/search/all_0.html @@ -1,7 +1,7 @@ - + diff --git a/doc/html/search/all_0.js b/doc/html/search/all_0.js index fd42ac4..fd59060 100644 --- a/doc/html/search/all_0.js +++ b/doc/html/search/all_0.js @@ -1,96 +1,5 @@ var searchData= [ - ['ad_5fbox_5ffilter',['ad_box_filter',['../pearl-area-display_8ipf.html#a27f0957d61f3c2d30a4854911b460c36',1,'pearl-area-display.ipf']]], - ['ad_5fbrick_5fslicer',['ad_brick_slicer',['../pearl-area-display_8ipf.html#ae3b4756cdc12a4a4b15a770ba0069823',1,'pearl-area-display.ipf']]], - ['ad_5fcalc_5fcursor_5fprofiles',['ad_calc_cursor_profiles',['../pearl-area-display_8ipf.html#a72b57037abd27f65986034c0b4cc191e',1,'pearl-area-display.ipf']]], - ['ad_5fcalc_5fhistogram',['ad_calc_histogram',['../pearl-area-display_8ipf.html#a48b08ab53729d9d0477deaceedef2769',1,'pearl-area-display.ipf']]], - ['ad_5fcalc_5fprofiles',['ad_calc_profiles',['../pearl-area-display_8ipf.html#a48044f9ee518d47770e33ee9f381f204',1,'pearl-area-display.ipf']]], - ['ad_5fcollect_5fmultiscan_5fy',['ad_collect_multiscan_y',['../pearl-area-profiles_8ipf.html#a3cadf0b28d1fd84e9922610c20868283',1,'pearl-area-profiles.ipf']]], - ['ad_5fdefault_5fimage_5ffilter',['ad_default_image_filter',['../pearl-area-display_8ipf.html#a6418a1b2d18b82cb71c0fecbd513a934',1,'pearl-area-display.ipf']]], - ['ad_5fdisplay',['ad_display',['../pearl-area-display_8ipf.html#ae2b11295d2715e9af019513923c64570',1,'pearl-area-display.ipf']]], - ['ad_5fdisplay_5fbrick',['ad_display_brick',['../pearl-area-display_8ipf.html#a65b07e355df20cfb692dfb32f472b478',1,'pearl-area-display.ipf']]], - ['ad_5fdisplay_5fhistogram',['ad_display_histogram',['../pearl-area-display_8ipf.html#a8cc3ea3bea4e851e4144140a2da42a03',1,'pearl-area-display.ipf']]], - ['ad_5fdisplay_5fprofiles',['ad_display_profiles',['../pearl-area-display_8ipf.html#a8fad5aebaca72887d5898b4c421bcdae',1,'pearl-area-display.ipf']]], - ['ad_5fdisplay_5fslice',['ad_display_slice',['../pearl-area-display_8ipf.html#af8d5e003fcff1f750685ed6f94717730',1,'pearl-area-display.ipf']]], - ['ad_5fexport_5fprofile',['ad_export_profile',['../pearl-area-display_8ipf.html#ad3e190d1ec1b82ebef00c9f9ac44b50a',1,'pearl-area-display.ipf']]], - ['ad_5fextract_5frod',['ad_extract_rod',['../pearl-area-profiles_8ipf.html#a8de5d4f1bcca91df5bbff568ab7b582d',1,'pearl-area-profiles.ipf']]], - ['ad_5fextract_5frod_5fx',['ad_extract_rod_x',['../pearl-area-profiles_8ipf.html#a83700e2faf844e2480c89b6ca4c66a79',1,'pearl-area-profiles.ipf']]], - ['ad_5fextract_5frod_5fy',['ad_extract_rod_y',['../pearl-area-profiles_8ipf.html#a363af257a04d51fff2a8d5b282f65f21',1,'pearl-area-profiles.ipf']]], - ['ad_5fextract_5frod_5fz',['ad_extract_rod_z',['../pearl-area-profiles_8ipf.html#a3483707fbdbfdbaec069591a5d3b07a6',1,'pearl-area-profiles.ipf']]], - ['ad_5fextract_5fslab',['ad_extract_slab',['../pearl-area-profiles_8ipf.html#a65bb359c057a9d900c486e186c9974df',1,'pearl-area-profiles.ipf']]], - ['ad_5fextract_5fslab_5fx',['ad_extract_slab_x',['../pearl-area-profiles_8ipf.html#af612340d1d132cacda9de7bb77c2e0aa',1,'pearl-area-profiles.ipf']]], - ['ad_5fextract_5fslab_5fy',['ad_extract_slab_y',['../pearl-area-profiles_8ipf.html#a2eb6a0bcced893e827cfa4e1236e8460',1,'pearl-area-profiles.ipf']]], - ['ad_5fextract_5fslab_5fz',['ad_extract_slab_z',['../pearl-area-profiles_8ipf.html#a71f02613c4a4d21c014493e906dbe922',1,'pearl-area-profiles.ipf']]], - ['ad_5fgizmo_5fset_5fplane',['ad_gizmo_set_plane',['../pearl-area-display_8ipf.html#aee051acfe6a3c8214118b78dfe4854fd',1,'pearl-area-display.ipf']]], - ['ad_5fload_5fdialog',['ad_load_dialog',['../pearl-area-import_8ipf.html#aedff2e67d2e1bac907f2eaf24a6e5c3c',1,'pearl-area-import.ipf']]], - ['ad_5fprofile_5fx',['ad_profile_x',['../pearl-area-profiles_8ipf.html#ab1a65cf82f6933db3dd7b564582e8ed1',1,'pearl-area-profiles.ipf']]], - ['ad_5fprofile_5fx_5fw',['ad_profile_x_w',['../pearl-area-profiles_8ipf.html#aa40fd5049f993e72fd52a66a6cdde7cc',1,'pearl-area-profiles.ipf']]], - ['ad_5fprofile_5fy',['ad_profile_y',['../pearl-area-profiles_8ipf.html#abb1eed32a982037ebab00f5c3ea95e62',1,'pearl-area-profiles.ipf']]], - ['ad_5fprofile_5fy_5fw',['ad_profile_y_w',['../pearl-area-profiles_8ipf.html#a8b09e13162fa47cc076e1e661e80b002',1,'pearl-area-profiles.ipf']]], - ['ad_5fprofiles_5fcrosshairs',['ad_profiles_crosshairs',['../pearl-area-display_8ipf.html#a6d20a8c6bf5ed143d375dee71fb3a6d5',1,'pearl-area-display.ipf']]], - ['ad_5fprofiles_5fcursor_5fmode',['ad_profiles_cursor_mode',['../pearl-area-display_8ipf.html#a5657fc4dcd395aef637c19e8df57a418',1,'pearl-area-display.ipf']]], - ['ad_5fprofiles_5fhook',['ad_profiles_hook',['../pearl-area-display_8ipf.html#a89a5e3e29a0cd09951dcdf13aa28d941',1,'pearl-area-display.ipf']]], - ['ad_5fprofiles_5fset_5fcursor',['ad_profiles_set_cursor',['../pearl-area-display_8ipf.html#ad2a84495ddac89bc8f4203fca56babfd',1,'pearl-area-display.ipf']]], - ['ad_5fprofiles_5fset_5fslice',['ad_profiles_set_slice',['../pearl-area-display_8ipf.html#abaf229d75d9d579a559295795a6bc2e1',1,'pearl-area-display.ipf']]], - ['ad_5fslicer_5finit_5fbg',['ad_slicer_init_bg',['../pearl-area-display_8ipf.html#a7334815c60e2c11e2754c07489a62f4b',1,'pearl-area-display.ipf']]], - ['ad_5fslicer_5fmove_5fbg',['ad_slicer_move_bg',['../pearl-area-display_8ipf.html#a4af98ec7af48a653c6fac716ea8fa505',1,'pearl-area-display.ipf']]], - ['ad_5fslicer_5fstart_5fbg',['ad_slicer_start_bg',['../pearl-area-display_8ipf.html#ad79b37ab4fcf2cbdad6874813d93d4b1',1,'pearl-area-display.ipf']]], - ['ad_5fslicer_5fstop_5fbg',['ad_slicer_stop_bg',['../pearl-area-display_8ipf.html#a77a71985e716a300e0b61c233cd93f40',1,'pearl-area-display.ipf']]], - ['ad_5fsuggest_5ffoldername',['ad_suggest_foldername',['../pearl-area-import_8ipf.html#ad28dbbba73e553f7b5dcf8baf1c86786',1,'pearl-area-import.ipf']]], - ['ad_5ftranspose_5ffilter',['ad_transpose_filter',['../pearl-area-display_8ipf.html#a8411f0cfec3515f1ae4f0140efc14318',1,'pearl-area-display.ipf']]], - ['ad_5fupdate_5fprofiles',['ad_update_profiles',['../pearl-area-display_8ipf.html#afa2546f9cb03dfa8bf0cc9966f0b7a45',1,'pearl-area-display.ipf']]], - ['add_5fimage_5fdata',['add_image_data',['../pearl-anglescan-tracker_8ipf.html#a35a5cd8a21b48be8d726c69eb5fca134',1,'pearl-anglescan-tracker.ipf']]], - ['adh5_5fdefault_5freduction',['adh5_default_reduction',['../pearl-area-import_8ipf.html#ade69cb0f82e0c9cf6082d5fcc29f742f',1,'pearl-area-import.ipf']]], - ['adh5_5fget_5fresult_5fwaves',['adh5_get_result_waves',['../pearl-area-import_8ipf.html#a27a72a3901a5342ca9dea02e3219631c',1,'pearl-area-import.ipf']]], - ['adh5_5flist_5freduction_5ffuncs',['adh5_list_reduction_funcs',['../pearl-area-import_8ipf.html#aa5e29dc1a380311d00a5f85be867e47b',1,'pearl-area-import.ipf']]], - ['adh5_5fload_5fcomplete',['adh5_load_complete',['../pearl-area-import_8ipf.html#ab1040bf272c69dc69777b2f91df41fab',1,'pearl-area-import.ipf']]], - ['adh5_5fload_5fdetector',['adh5_load_detector',['../pearl-area-import_8ipf.html#a84dc7f466b42dde5d96c49827b2122cf',1,'pearl-area-import.ipf']]], - ['adh5_5fload_5fdetector_5fimage',['adh5_load_detector_image',['../pearl-area-import_8ipf.html#a931a7bfaaf75d308a0ce3c74ffc751bc',1,'pearl-area-import.ipf']]], - ['adh5_5fload_5fdetector_5fslabs',['adh5_load_detector_slabs',['../pearl-area-import_8ipf.html#a4a9741d1c19b10bb98b73bd5163a497b',1,'pearl-area-import.ipf']]], - ['adh5_5fload_5finfo',['adh5_load_info',['../pearl-area-import_8ipf.html#ac76d5ba94a3d7c864437420d80c77064',1,'pearl-area-import.ipf']]], - ['adh5_5fload_5fpreview',['adh5_load_preview',['../pearl-area-import_8ipf.html#a98f29671bdce6a5981e8865de8b9d483',1,'pearl-area-import.ipf']]], - ['adh5_5fload_5freduced',['adh5_load_reduced',['../pearl-area-import_8ipf.html#a98f9339cd2fae80d0d92451df88395aa',1,'pearl-area-import.ipf']]], - ['adh5_5fload_5freduced_5fdetector',['adh5_load_reduced_detector',['../pearl-area-import_8ipf.html#a3f2ac36f961941e46e80a775de8300e5',1,'pearl-area-import.ipf']]], - ['adh5_5floadattr_5fall',['adh5_loadattr_all',['../pearl-area-import_8ipf.html#acde16dc7a393250b17165344f865f7b5',1,'pearl-area-import.ipf']]], - ['adh5_5fredim',['adh5_redim',['../pearl-area-import_8ipf.html#acfa6d2675e63f4f686289ef853b262a9',1,'pearl-area-import.ipf']]], - ['adh5_5fscale',['adh5_scale',['../pearl-area-import_8ipf.html#a774751d1857ea6946a942448dc913128',1,'pearl-area-import.ipf']]], - ['adh5_5fscale_5fscan',['adh5_scale_scan',['../pearl-area-import_8ipf.html#a1fdcc02340375afe8d8cd7537c6e9cfb',1,'pearl-area-import.ipf']]], - ['adh5_5fscale_5fscienta',['adh5_scale_scienta',['../pearl-area-import_8ipf.html#a227e4db1c51a910dcf86d355473fe74e',1,'pearl-area-import.ipf']]], - ['adh5_5fsetup_5fprofile',['adh5_setup_profile',['../pearl-area-import_8ipf.html#a9439de3b676e686eeca4e6b2588c01a6',1,'pearl-area-import.ipf']]], - ['adh5_5ftest_5freduction_5ffunc',['adh5_test_reduction_func',['../pearl-area-import_8ipf.html#a98804ce23a5c2c314ac243baa0824424',1,'pearl-area-import.ipf']]], - ['aftercompiledhook',['AfterCompiledHook',['../pearl-anglescan-panel_8ipf.html#a8e4eacc6efacf2c65615c1ea72d722ed',1,'AfterCompiledHook(): pearl-anglescan-panel.ipf'],['../pearl-anglescan-tracker_8ipf.html#a8e4eacc6efacf2c65615c1ea72d722ed',1,'AfterCompiledHook(): pearl-anglescan-tracker.ipf'],['../pearl-arpes_8ipf.html#a8e4eacc6efacf2c65615c1ea72d722ed',1,'AfterCompiledHook(): pearl-arpes.ipf']]], - ['afterfileopenhook',['AfterFileOpenHook',['../pearl-elog_8ipf.html#a3f524f5190341d2accc8cb8c3ed2ceb5',1,'AfterFileOpenHook(variable refNum, string file, string pathName, string type, string creator, variable kind): pearl-elog.ipf'],['../pearl-matrix-import_8ipf.html#a3f524f5190341d2accc8cb8c3ed2ceb5',1,'AfterFileOpenHook(variable refNum, string file, string pathName, string type, string creator, variable kind): pearl-matrix-import.ipf']]], - ['already_5ffile_5fopen',['ALREADY_FILE_OPEN',['../structerror_code.html#a19dc49bdfb4bd9601f17f907da158026',1,'errorCode']]], - ['analyse_5fcurved_5fedge',['analyse_curved_edge',['../fermi-edge-analysis_8ipf.html#a1c4a805435a1d43c2b6dfb6deb633894',1,'fermi-edge-analysis.ipf']]], - ['analyser_5fenergy_5fresolution',['analyser_energy_resolution',['../fermi-edge-analysis_8ipf.html#ad23de34bb698589e2576ce2836b89d55',1,'fermi-edge-analysis.ipf']]], - ['appendtographiterator',['AppendToGraphIterator',['../pearl-tools_8ipf.html#a90c62bdfc186e2482ccb18113a591d5e',1,'pearl-tools.ipf']]], - ['arpes_20package',['ARPES package',['../group___arpes_package.html',1,'']]], - ['arrange_5fcontrols',['arrange_controls',['../pearl-anglescan-panel_8ipf.html#a65dbeab54647d7c27a139035d69c812f',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fcalculate_5foutput',['asp_calculate_output',['../pearl-anglescan-panel_8ipf.html#af21424ce00e4bac1ac990d2bb83d46dc',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fclose_5fgraphs',['asp_close_graphs',['../pearl-anglescan-panel_8ipf.html#aac9d4d0388cbe8e6aa8f47b1c5276d83',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fdisplay_5fdist_5fcheck',['asp_display_dist_check',['../pearl-anglescan-panel_8ipf.html#a59886414c7dc2486c5a17f078896c705',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fdisplay_5foutput',['asp_display_output',['../pearl-anglescan-panel_8ipf.html#acf9ce1db5521da3d96ef6ca89a5d255f',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fdisplay_5fpreviews',['asp_display_previews',['../pearl-anglescan-panel_8ipf.html#a66b3eef1fd0be13dfef0a66781f55062',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fduplicate_5foutput',['asp_duplicate_output',['../pearl-anglescan-panel_8ipf.html#a67dc53b9eb9447d3a92965d6f0c742e5',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fimport_5fraw',['asp_import_raw',['../pearl-anglescan-panel_8ipf.html#a21aab19fbcde395df6e1ea8654b3af9a',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fsave_5foutput_5fetpi',['asp_save_output_etpi',['../pearl-anglescan-panel_8ipf.html#abb4d53822bc34bda0e38332c7777ebac',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fsave_5foutput_5fitx',['asp_save_output_itx',['../pearl-anglescan-panel_8ipf.html#a0e0f10d125f1cdacffa3bff9b0854aa9',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fshow_5fpanel',['asp_show_panel',['../pearl-anglescan-panel_8ipf.html#a452f09c3057638056ac2b5a15ac660b2',1,'pearl-anglescan-panel.ipf']]], - ['asp_5fupdate_5fgraph',['asp_update_graph',['../pearl-anglescan-panel_8ipf.html#a93dc5a029ae9831066e6ad133522ee88',1,'pearl-anglescan-panel.ipf']]], - ['ast_5fadd_5fimage',['ast_add_image',['../pearl-anglescan-tracker_8ipf.html#a43d85b93bb42a67b8e8afb9afc8d8eae',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fcallback_5fdata',['ast_callback_data',['../pearl-anglescan-tracker_8ipf.html#a4cf5ad2fdf771ffc157a3924a03f5a46',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fcallback_5fdetector',['ast_callback_detector',['../pearl-anglescan-tracker_8ipf.html#ac953a75b45d65adf37ce5560bf441876',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fcallback_5fmanip',['ast_callback_manip',['../pearl-anglescan-tracker_8ipf.html#a9b4acc299c5e698695baf0b4817ff7eb',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fclose',['ast_close',['../pearl-anglescan-tracker_8ipf.html#a8a74ddd33e286105a45a89105de72621',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fexport',['ast_export',['../pearl-anglescan-tracker_8ipf.html#ac9c92805f39c7a5c68d4c017d14ee178',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fimport',['ast_import',['../pearl-anglescan-tracker_8ipf.html#ae4ece97352b85ced47e954c025e3b69b',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fprepare',['ast_prepare',['../pearl-anglescan-tracker_8ipf.html#a766f90a9dad70d9deb4272ba480ee84a',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fset_5fprocessing',['ast_set_processing',['../pearl-anglescan-tracker_8ipf.html#a02271bf812a3e3f87c958f4c58e9f71b',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fsetup',['ast_setup',['../pearl-anglescan-tracker_8ipf.html#a5fb1f1abddb56b129f053605035d3281',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fupdate_5fdetector',['ast_update_detector',['../pearl-anglescan-tracker_8ipf.html#a150243e26e8adf8b354b8afde064136d',1,'pearl-anglescan-tracker.ipf']]], - ['ast_5fwindow_5fhook',['ast_window_hook',['../pearl-anglescan-tracker_8ipf.html#a33e84ae8e13f405d466b28e83f608cb9',1,'pearl-anglescan-tracker.ipf']]], - ['attributes_5fnotebook',['attributes_notebook',['../pearl-data-explorer_8ipf.html#ad6cfb2c00d5112add84542a25eb68b19',1,'pearl-data-explorer.ipf']]], - ['au4f',['Au4f',['../pearl-fitfuncs_8ipf.html#a13a5ee22049d9a3379cd6e55654e70a3',1,'pearl-fitfuncs.ipf']]], - ['au4f_5f2p2',['Au4f_2p2',['../pearl-fitfuncs_8ipf.html#a24cd6a0c96ef8c720e371bb31ac0a479',1,'pearl-fitfuncs.ipf']]], - ['au4f_5f2p3',['Au4f_2p3',['../pearl-fitfuncs_8ipf.html#a709f7c4585b1d850ea8aae1885ac18cb',1,'pearl-fitfuncs.ipf']]] + ['anglescan_2dprocessing_2edox',['anglescan-processing.dox',['../anglescan-processing_8dox.html',1,'']]], + ['angle_2dscan_20processing',['Angle-scan processing',['../pag_anglescan_processing.html',1,'']]] ]; diff --git a/doc/html/search/all_1.html b/doc/html/search/all_1.html index 8cc6a1d..b13f0f7 100644 --- a/doc/html/search/all_1.html +++ b/doc/html/search/all_1.html @@ -1,7 +1,7 @@ - + diff --git a/doc/html/search/all_1.js b/doc/html/search/all_1.js index b456c8d..e89aa0a 100644 --- a/doc/html/search/all_1.js +++ b/doc/html/search/all_1.js @@ -1,49 +1,4 @@ var searchData= [ - ['beforefileopenhook',['BeforeFileOpenHook',['../pearl-area-import_8ipf.html#ae2cfa1ac6651cfc3fb0dfce03494995b',1,'BeforeFileOpenHook(variable refNum, string fileName, string path, string type, string creator, variable kind): pearl-area-import.ipf'],['../pearl-matrix-import_8ipf.html#ae2cfa1ac6651cfc3fb0dfce03494995b',1,'BeforeFileOpenHook(variable refNum, string fileName, string path, string type, string creator, variable kind): pearl-matrix-import.ipf']]], - ['bp_5fattach',['bp_attach',['../pearl-elog_8ipf.html#acbba78d869a543edf7c2b80d7a8d2344',1,'pearl-elog.ipf']]], - ['bp_5fattach_5fallnone',['bp_attach_allnone',['../pearl-elog_8ipf.html#a4040736819edadf4b26982bcfdb9c7b9',1,'pearl-elog.ipf']]], - ['bp_5fattach_5ftop',['bp_attach_top',['../pearl-elog_8ipf.html#a91b5f51982d23a36d1760b8874b5736a',1,'pearl-elog.ipf']]], - ['bp_5fattach_5fupdown',['bp_attach_updown',['../pearl-elog_8ipf.html#aa1dfae6d78a367d50ee8fc1ffe9cb69b',1,'pearl-elog.ipf']]], - ['bp_5fattr_5fnotebook',['bp_attr_notebook',['../pearl-data-explorer_8ipf.html#a4ef196f752bb5780ed4f4a588f9ebc81',1,'pearl-data-explorer.ipf']]], - ['bp_5fbrowse_5ffilepath',['bp_browse_filepath',['../pearl-data-explorer_8ipf.html#a02a64144b7ed2c1bc230e265c55e81a1',1,'pearl-data-explorer.ipf']]], - ['bp_5fcapture',['bp_capture',['../pearl-anglescan-tracker_8ipf.html#afaec8443094530fd1e723251e04c5dc9',1,'pearl-anglescan-tracker.ipf']]], - ['bp_5fclear',['bp_clear',['../pearl-elog_8ipf.html#ab39637298c93b7aefd67febf3a4e7672',1,'pearl-elog.ipf']]], - ['bp_5fcrop_5falpha_5fpreview',['bp_crop_alpha_preview',['../pearl-anglescan-panel_8ipf.html#ae73ae76ff6e2344143d4dee7cc26b4b5',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fdataset_5fdisplay',['bp_dataset_display',['../pearl-data-explorer_8ipf.html#a5660c6f5f78d880b0805bad4eefed1d5',1,'pearl-data-explorer.ipf']]], - ['bp_5fdataset_5ffolder',['bp_dataset_folder',['../pearl-data-explorer_8ipf.html#a6b642da731bde1029e0fa2ff69d5fb06',1,'pearl-data-explorer.ipf']]], - ['bp_5fdataset_5fnext',['bp_dataset_next',['../pearl-data-explorer_8ipf.html#a3bbb332e319ef7ec5f0fe2d16afaf005',1,'pearl-data-explorer.ipf']]], - ['bp_5fdataset_5fprev',['bp_dataset_prev',['../pearl-data-explorer_8ipf.html#add62ff5193206c9f207952bcd72dac88',1,'pearl-data-explorer.ipf']]], - ['bp_5fextract_5fslice',['bp_extract_slice',['../pearl-area-display_8ipf.html#a31461b664ec651a39442e9a46ffd88c9',1,'pearl-area-display.ipf']]], - ['bp_5ffile_5fnext',['bp_file_next',['../pearl-data-explorer_8ipf.html#a9cefcdc49b2169e99c743b0a683ed3a6',1,'pearl-data-explorer.ipf']]], - ['bp_5ffile_5fprev',['bp_file_prev',['../pearl-data-explorer_8ipf.html#a6aa44ff12b8530adbaaaf7405b1a68ba',1,'pearl-data-explorer.ipf']]], - ['bp_5fgraph_5fpng',['bp_graph_png',['../pearl-anglescan-panel_8ipf.html#a9be861636d98d7891e6d106deac2f90b',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fgraph_5fupdate',['bp_graph_update',['../pearl-anglescan-panel_8ipf.html#a940f2115fb5b47e19516168d15346472',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fload_5ffiles',['bp_load_files',['../pearl-data-explorer_8ipf.html#a742902dfaf2246f10b70f52805c6df1f',1,'pearl-data-explorer.ipf']]], - ['bp_5fload_5ffiles_5fopt',['bp_load_files_opt',['../pearl-data-explorer_8ipf.html#ad61aa85dcf24dbf7e093dac3d0bf6f19',1,'pearl-data-explorer.ipf']]], - ['bp_5fload_5fprefs',['bp_load_prefs',['../pearl-data-explorer_8ipf.html#a1868754e64cb1448e564c0936e78574d',1,'pearl-data-explorer.ipf']]], - ['bp_5flogin',['bp_login',['../pearl-elog_8ipf.html#a14f8376a0485aa654ccf3d2f30ab4d01',1,'pearl-elog.ipf']]], - ['bp_5flogout',['bp_logout',['../pearl-elog_8ipf.html#ad4472ea917691c41ad0b4ea6f36010a5',1,'pearl-elog.ipf']]], - ['bp_5fmove_5fslice',['bp_move_slice',['../pearl-area-display_8ipf.html#ab8c9979c6f3ab95f983c2a525a69c035',1,'pearl-area-display.ipf']]], - ['bp_5fmove_5fslice_5fcenter',['bp_move_slice_center',['../pearl-area-display_8ipf.html#abe702d40071e3c5e662eb8d47dd6d885',1,'pearl-area-display.ipf']]], - ['bp_5fnorm_5falpha_5fcheck',['bp_norm_alpha_check',['../pearl-anglescan-panel_8ipf.html#a630dfc775d45843c71c279bbb01d05a6',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fnorm_5falpha_5fpreview',['bp_norm_alpha_preview',['../pearl-anglescan-panel_8ipf.html#aaaf3facc118f90a8f1b32948446899b3',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fnorm_5fphi_5fcheck',['bp_norm_phi_check',['../pearl-anglescan-panel_8ipf.html#ae42eb7f46e5c1a1b5d334ebb5e94d2d3',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fnorm_5fphi_5fpreview',['bp_norm_phi_preview',['../pearl-anglescan-panel_8ipf.html#a740c8a80ab2fc0550a05cf3b032821d0',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fnorm_5ftheta_5fcheck',['bp_norm_theta_check',['../pearl-anglescan-panel_8ipf.html#a0931ce925d2dae6a1bb7e4a65a8a2be7',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fnorm_5ftheta_5fpreview',['bp_norm_theta_preview',['../pearl-anglescan-panel_8ipf.html#af57abb0a7d41b800d33bb748f9fc5c38',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fnorm_5fthetaphi_5fcheck',['bp_norm_thetaphi_check',['../pearl-anglescan-panel_8ipf.html#a89caab501e8f15262d6e4f2fa5b4a1bd',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fnorm_5fthetaphi_5fpreview',['bp_norm_thetaphi_preview',['../pearl-anglescan-panel_8ipf.html#aaa3478a3b0f26b12a12196cfaa87a8ae',1,'pearl-anglescan-panel.ipf']]], - ['bp_5foutput_5fcalc',['bp_output_calc',['../pearl-anglescan-panel_8ipf.html#adefddc5f384948c9dab3ee65b4a0668a',1,'pearl-anglescan-panel.ipf']]], - ['bp_5foutput_5fduplicate',['bp_output_duplicate',['../pearl-anglescan-panel_8ipf.html#ae838bde232c45d81f88303e91b16326b',1,'pearl-anglescan-panel.ipf']]], - ['bp_5foutput_5fetpi',['bp_output_etpi',['../pearl-anglescan-panel_8ipf.html#a16d2f6a58fedc370d7901126bb814bbb',1,'pearl-anglescan-panel.ipf']]], - ['bp_5foutput_5fitx',['bp_output_itx',['../pearl-anglescan-panel_8ipf.html#a0bdc14f90bdc40045200ac23229b225d',1,'pearl-anglescan-panel.ipf']]], - ['bp_5freset_5fcursors',['bp_reset_cursors',['../pearl-area-display_8ipf.html#a24b17f99fafd8043ed3e4502000da316',1,'pearl-area-display.ipf']]], - ['bp_5fsave_5fgraphs',['bp_save_graphs',['../pearl-elog_8ipf.html#a8251cea45c8d1f1993a4051a6d0760c4',1,'pearl-elog.ipf']]], - ['bp_5fsave_5fprefs',['bp_save_prefs',['../pearl-data-explorer_8ipf.html#ad8a01428a137278a31d4f1f4f9c634c5',1,'pearl-data-explorer.ipf']]], - ['bp_5fsource_5fselect',['bp_source_select',['../pearl-anglescan-panel_8ipf.html#a1e50019bc895a0787cb3f07d776e9463',1,'pearl-anglescan-panel.ipf']]], - ['bp_5fsubmit',['bp_submit',['../pearl-elog_8ipf.html#adeff6678e57313cb218824f06d32b5ec',1,'pearl-elog.ipf']]], - ['bp_5fupdate_5fdatasets',['bp_update_datasets',['../pearl-data-explorer_8ipf.html#af9f8769ca2989f152f23d976d1467a48',1,'pearl-data-explorer.ipf']]], - ['bp_5fupdate_5ffilelist',['bp_update_filelist',['../pearl-data-explorer_8ipf.html#a45be265789a5260e3daa05eca0ec309e',1,'pearl-data-explorer.ipf']]], - ['broadening',['broadening',['../struct_doniach_sunjic_struct.html#ac9b18c8b44b43c2ee438f37f8d002a66',1,'DoniachSunjicStruct']]] + ['fermi_2dedge_2danalysis_2eipf',['fermi-edge-analysis.ipf',['../fermi-edge-analysis_8ipf.html',1,'']]] ]; diff --git a/doc/html/search/all_2.html b/doc/html/search/all_2.html index d15ac65..9543c57 100644 --- a/doc/html/search/all_2.html +++ b/doc/html/search/all_2.html @@ -1,7 +1,7 @@ - + diff --git a/doc/html/search/all_2.js b/doc/html/search/all_2.js index ba72aff..7cf7879 100644 --- a/doc/html/search/all_2.js +++ b/doc/html/search/all_2.js @@ -1,32 +1,4 @@ var searchData= [ - ['calc_5fdoniachsunjicbroad',['Calc_DoniachSunjicBroad',['../pearl-fitfuncs_8ipf.html#aff8e8b103c32c8e723b57ce7ad5ef0f5',1,'pearl-fitfuncs.ipf']]], - ['calc_5fgraph_5fazi',['calc_graph_azi',['../pearl-anglescan-process_8ipf.html#a4fc744e24e3e9c5efb17f14ab622bcae',1,'pearl-anglescan-process.ipf']]], - ['calc_5fgraph_5fpolar',['calc_graph_polar',['../pearl-anglescan-process_8ipf.html#ae2b036a06ffac8d2bb292a65401f8a9a',1,'pearl-anglescan-process.ipf']]], - ['calc_5fgraph_5fradius',['calc_graph_radius',['../pearl-anglescan-process_8ipf.html#a75219b38ea58012abcffc848d536faa4',1,'pearl-anglescan-process.ipf']]], - ['calc_5fnth',['calc_nth',['../pearl-anglescan-process_8ipf.html#a9624070f3e938378631432430d47a389',1,'pearl-anglescan-process.ipf']]], - ['calc_5fphi_5fstep',['calc_phi_step',['../pearl-anglescan-process_8ipf.html#a999a9cd7d00d3e1ec8e768228a664ad1',1,'pearl-anglescan-process.ipf']]], - ['calc_5fthe_5fstep',['Calc_The_step',['../pearl-anglescan-process_8ipf.html#a1fb6aa7870dfbf0ed92660b7aae579e0',1,'pearl-anglescan-process.ipf']]], - ['calc_5fy_5fprofile_5fmins',['calc_y_profile_mins',['../pearl-area-profiles_8ipf.html#ab58b7c0a88743ecbcb0fc8296577a792',1,'pearl-area-profiles.ipf']]], - ['calcn_5ftheta',['CalcN_Theta',['../pearl-anglescan-process_8ipf.html#ac0def1ded61f9cd758df0c99f4ff9470',1,'pearl-anglescan-process.ipf']]], - ['capture_5fint_5flinbg_5fcursors',['capture_int_linbg_cursors',['../pearl-scienta-preprocess_8ipf.html#ae6877c51ad15c2ba8a69c65356cb34b8',1,'pearl-scienta-preprocess.ipf']]], - ['cart2polar',['cart2polar',['../pearl-polar-coordinates_8ipf.html#aca0a5aaa4854d83ef667c53007312fb8',1,'pearl-polar-coordinates.ipf']]], - ['cart2polar_5fwave',['cart2polar_wave',['../pearl-polar-coordinates_8ipf.html#adfc1f0b3cddf672b0ccdb6a22b97ba9e',1,'pearl-polar-coordinates.ipf']]], - ['check_5fcontrast',['check_contrast',['../pearl-anglescan-process_8ipf.html#a2e1ed05781f9eb4be5e77695ef049962',1,'pearl-anglescan-process.ipf']]], - ['check_5fnorm_5falpha',['check_norm_alpha',['../pearl-anglescan-panel_8ipf.html#af5435ccaabba78f855b244929dc09ed0',1,'pearl-anglescan-panel.ipf']]], - ['check_5fnorm_5fphi',['check_norm_phi',['../pearl-anglescan-panel_8ipf.html#a91d5343cc96730de12b535cb0bef9df2',1,'pearl-anglescan-panel.ipf']]], - ['check_5fnorm_5ftheta',['check_norm_theta',['../pearl-anglescan-panel_8ipf.html#addddc12e5b622a3d00756d724e5d05a9',1,'pearl-anglescan-panel.ipf']]], - ['check_5fnorm_5fthetaphi',['check_norm_thetaphi',['../pearl-anglescan-panel_8ipf.html#a4708e7385790d1a9f2d58c4d64a60653',1,'pearl-anglescan-panel.ipf']]], - ['check_5fpackage_5ffolder',['check_package_folder',['../pearl-matrix-import_8ipf.html#ac7790f06151821678a65ab0065a5323e',1,'pearl-matrix-import.ipf']]], - ['cleanup_5ftemp_5ffiles',['cleanup_temp_files',['../pearl-elog_8ipf.html#ad7640d06f004ecd4a8980ea29d24dcbe',1,'pearl-elog.ipf']]], - ['clear_5fhemi_5fgrid',['clear_hemi_grid',['../pearl-anglescan-process_8ipf.html#a3ec6935a5903d0974c93a2072d743013',1,'pearl-anglescan-process.ipf']]], - ['convert_5fangles_5fttpa2polar',['convert_angles_ttpa2polar',['../pearl-anglescan-process_8ipf.html#a3cc7eddf5c6b0658260cfb32dd2c026d',1,'pearl-anglescan-process.ipf']]], - ['convert_5fangles_5fttpd2polar',['convert_angles_ttpd2polar',['../pearl-anglescan-process_8ipf.html#a2b38c6c9b6e60593ba69d3773b6bc779',1,'pearl-anglescan-process.ipf']]], - ['convolution',['convolution',['../struct_doniach_sunjic_struct.html#a7f05f7827435fea3c986a8d538496955',1,'DoniachSunjicStruct']]], - ['create_5fcmd_5ffile',['create_cmd_file',['../pearl-elog_8ipf.html#ac8b61eefed231018cc36d47e95bd8c22',1,'pearl-elog.ipf']]], - ['create_5fgraph_5ffile',['create_graph_file',['../pearl-elog_8ipf.html#a2417d079483f773f8231c5f2caba6cf0',1,'pearl-elog.ipf']]], - ['create_5fmessage_5ffile',['create_message_file',['../pearl-elog_8ipf.html#af652f6f257be1ee749fe788d1b03f75f',1,'pearl-elog.ipf']]], - ['create_5frotation_5fmatrix_5ffree',['create_rotation_matrix_free',['../pearl-vector-operations_8ipf.html#a72c3200a7344c708ea76e20cc2c19c43',1,'pearl-vector-operations.ipf']]], - ['crop_5fstrip',['crop_strip',['../pearl-anglescan-process_8ipf.html#ab65d25af7476ed18f7bf7359614a912b',1,'pearl-anglescan-process.ipf']]], - ['csr_5fint_5flinbg_5freduction',['csr_int_linbg_reduction',['../pearl-scienta-preprocess_8ipf.html#a95fbd22f52f61d2bff0625b7b8e159d1',1,'pearl-scienta-preprocess.ipf']]] + ['introduction',['Introduction',['../index.html',1,'']]] ]; diff --git a/doc/html/search/all_3.html b/doc/html/search/all_3.html index 9f526c6..03405c0 100644 --- a/doc/html/search/all_3.html +++ b/doc/html/search/all_3.html @@ -1,7 +1,7 @@ - + diff --git a/doc/html/search/all_3.js b/doc/html/search/all_3.js index 17c28b6..a490ea9 100644 --- a/doc/html/search/all_3.js +++ b/doc/html/search/all_3.js @@ -1,31 +1,4 @@ var searchData= [ - ['defaultfolderiterator',['DefaultFolderIterator',['../pearl-tools_8ipf.html#a3fb8c06030dc41a599380150807caeb0',1,'pearl-tools.ipf']]], - ['defaultwaveiterator',['DefaultWaveIterator',['../pearl-tools_8ipf.html#a6bdd1c0b269f1d7d99843ce0cb218cc7',1,'pearl-tools.ipf']]], - ['display2dprofiles',['Display2dProfiles',['../pearl-menu_8ipf.html#aad7d768680c6d8a9b8a7025c7e1ec75d',1,'pearl-menu.ipf']]], - ['display3dslicer',['Display3dSlicer',['../pearl-menu_8ipf.html#ac73a94f760455f19294a9f917b43f145',1,'pearl-menu.ipf']]], - ['display_5fdataset',['display_dataset',['../pearl-data-explorer_8ipf.html#ae79a57a41c734ce8836f427b81011b5d',1,'pearl-data-explorer.ipf']]], - ['display_5fhemi_5fscan',['display_hemi_scan',['../pearl-anglescan-process_8ipf.html#ae57302acfc822c4817f2b7eef55efea2',1,'pearl-anglescan-process.ipf']]], - ['display_5fpolar_5fgraph',['display_polar_graph',['../pearl-anglescan-process_8ipf.html#a46fd99d35a43601c39af6096d4e4f770',1,'pearl-anglescan-process.ipf']]], - ['display_5fpreview_5ftrace',['display_preview_trace',['../pearl-data-explorer_8ipf.html#a001074020ad32b290d390a450a389c69',1,'pearl-data-explorer.ipf']]], - ['display_5fprogress_5fpanel',['display_progress_panel',['../pearl-gui-tools_8ipf.html#aaf29d090c81e00cf44af295193b24c5a',1,'pearl-gui-tools.ipf']]], - ['display_5fscanlines',['display_scanlines',['../pearl-anglescan-process_8ipf.html#a1f4f74a8ae557c56e1e3aacd0b45f3f1',1,'pearl-anglescan-process.ipf']]], - ['displaygizmoslicer',['DisplayGizmoSlicer',['../pearl-menu_8ipf.html#aab34952c2f3b36f9ee8619eb901ff581',1,'pearl-menu.ipf']]], - ['do_5fcrop_5falpha',['do_crop_alpha',['../pearl-anglescan-panel_8ipf.html#a893478e43be64b0c404b7573d2e89cc2',1,'pearl-anglescan-panel.ipf']]], - ['do_5finit_5fprocess',['do_init_process',['../pearl-anglescan-panel_8ipf.html#a1836e607851ba4d5a4048f4cfb8121a7',1,'pearl-anglescan-panel.ipf']]], - ['do_5fnorm_5falpha',['do_norm_alpha',['../pearl-anglescan-panel_8ipf.html#a8f7266ac2840155dede704fda66fe6b0',1,'pearl-anglescan-panel.ipf']]], - ['do_5fnorm_5fphi',['do_norm_phi',['../pearl-anglescan-panel_8ipf.html#a790519191391ac03c75eb7b57ea0749e',1,'pearl-anglescan-panel.ipf']]], - ['do_5fnorm_5ftheta',['do_norm_theta',['../pearl-anglescan-panel_8ipf.html#a7b288598e3faa37e414b1443982c1a3e',1,'pearl-anglescan-panel.ipf']]], - ['do_5fnorm_5fthetaphi',['do_norm_thetaphi',['../pearl-anglescan-panel_8ipf.html#af6509fc7584b0bcbdc8561df2bc12a58',1,'pearl-anglescan-panel.ipf']]], - ['doniachsunjic',['DoniachSunjic',['../pearl-fitfuncs_8ipf.html#aaa48428994f8720a12e7237ef43e86ea',1,'pearl-fitfuncs.ipf']]], - ['doniachsunjicbroad',['DoniachSunjicBroad',['../pearl-fitfuncs_8ipf.html#ae2d138beb7cb39e8042487893095b461',1,'pearl-fitfuncs.ipf']]], - ['doniachsunjicbroads',['DoniachSunjicBroadS',['../pearl-fitfuncs_8ipf.html#a9d110819fa3cd2173f3103724e394fdf',1,'pearl-fitfuncs.ipf']]], - ['doniachsunjicstruct',['DoniachSunjicStruct',['../struct_doniach_sunjic_struct.html',1,'']]], - ['draw_5fdiffraction_5fcone',['draw_diffraction_cone',['../pearl-anglescan-process_8ipf.html#afedad38a418cee5d1fb9e08aae2160a0',1,'pearl-anglescan-process.ipf']]], - ['draw_5fhemi_5faxes',['draw_hemi_axes',['../pearl-anglescan-process_8ipf.html#af00d9061e410ad033a9fd1f0ca561e0d',1,'pearl-anglescan-process.ipf']]], - ['ds1_5fbg',['ds1_bg',['../pearl-fitfuncs_8ipf.html#af62cb65b7444ff60e956a45bd5d0ec27',1,'pearl-fitfuncs.ipf']]], - ['ds2_5fbg',['ds2_bg',['../pearl-fitfuncs_8ipf.html#a1e729418252bf0d05ea6ec5cbd65b834',1,'pearl-fitfuncs.ipf']]], - ['ds4_5fbg',['ds4_bg',['../pearl-fitfuncs_8ipf.html#ab32134566b2573672ac674565deebd36',1,'pearl-fitfuncs.ipf']]], - ['ds6_5fbg',['ds6_bg',['../pearl-fitfuncs_8ipf.html#a5a2a03026b88f3dd99214ab1b26e6f80',1,'pearl-fitfuncs.ipf']]], - ['duplicate_5fhemi_5fscan',['duplicate_hemi_scan',['../pearl-anglescan-process_8ipf.html#aa5b1e2ab1dd43a73b7157406b803887e',1,'pearl-anglescan-process.ipf']]] + ['mainpage_2edox',['mainpage.dox',['../mainpage_8dox.html',1,'']]] ]; diff --git a/doc/html/search/all_4.html b/doc/html/search/all_4.html index 7b814aa..8e1f4b9 100644 --- a/doc/html/search/all_4.html +++ b/doc/html/search/all_4.html @@ -1,7 +1,7 @@ - + diff --git a/doc/html/search/all_4.js b/doc/html/search/all_4.js index 931ed3c..d1de4b2 100644 --- a/doc/html/search/all_4.js +++ b/doc/html/search/all_4.js @@ -1,26 +1,23 @@ var searchData= [ - ['edit_5foffsets',['edit_offsets',['../pearl-anglescan-tracker_8ipf.html#a37aaf2f08c3910bed554a10dd82616ec',1,'pearl-anglescan-tracker.ipf']]], - ['edit_5freduction_5fparams',['edit_reduction_params',['../pearl-anglescan-tracker_8ipf.html#a3844e7fd93b4f54aa52f084687c2106c',1,'pearl-anglescan-tracker.ipf']]], - ['elog_5fadd_5fattachment',['elog_add_attachment',['../pearl-elog_8ipf.html#ac2f76abed8cfaa7ac02a46c0b89004f0',1,'pearl-elog.ipf']]], - ['elog_5fconfig',['elog_config',['../pearl-elog_8ipf.html#a424460442afd5f6f853e68cd665ed785',1,'pearl-elog.ipf']]], - ['elog_5fcreate_5fentry',['elog_create_entry',['../pearl-elog_8ipf.html#a05301d497e4796e5fb5adde3728ba971',1,'pearl-elog.ipf']]], - ['elog_5fcreate_5flogbook',['elog_create_logbook',['../pearl-elog_8ipf.html#ab6d97edbf33e8ec039b34ff756e7ab93',1,'pearl-elog.ipf']]], - ['elog_5finit_5fpearl_5ftemplates',['elog_init_pearl_templates',['../pearl-elog_8ipf.html#aaca820a0149ce6a0e843ca72b9c9e7ab',1,'pearl-elog.ipf']]], - ['elog_5flogin',['elog_login',['../pearl-elog_8ipf.html#a3eac4012891c2813e401aee2c1134763',1,'pearl-elog.ipf']]], - ['elog_5flogout',['elog_logout',['../pearl-elog_8ipf.html#a96e4cbbdb0fd8c58d87b502dc1883664',1,'pearl-elog.ipf']]], - ['elog_5fpanel_5fhook',['elog_panel_hook',['../pearl-elog_8ipf.html#af8b1ea711208bcc2cd1647abe04131dc',1,'pearl-elog.ipf']]], - ['elog_5fparse_5fid',['elog_parse_id',['../pearl-elog_8ipf.html#a6a9923c6465c91b1f9d1d97b090f424b',1,'pearl-elog.ipf']]], - ['elog_5fprompt_5flogbook',['elog_prompt_logbook',['../pearl-elog_8ipf.html#acedf0c8ae34e9ebadd6fa0d9d1353aa4',1,'pearl-elog.ipf']]], - ['elog_5fprompt_5flogin',['elog_prompt_login',['../pearl-elog_8ipf.html#afbace5ffc3167b42b09657ce6cc854ca',1,'pearl-elog.ipf']]], - ['elog_5fsuccess_5fmsg',['elog_success_msg',['../pearl-elog_8ipf.html#a63aa38b624b66fe502505040c25bc0c3',1,'pearl-elog.ipf']]], - ['elog_5fvalidate_5fattributes',['elog_validate_attributes',['../pearl-elog_8ipf.html#ab2558ef5cd5e5dfba410bd58ed258b64',1,'pearl-elog.ipf']]], - ['empty_5fresultfile',['EMPTY_RESULTFILE',['../structerror_code.html#ab7f29ef2ba8497c55f2bc55c4b9fc186',1,'errorCode']]], - ['epics_5fconnect',['epics_connect',['../pearl-anglescan-tracker_8ipf.html#a306b168cab2f9c4146cee87009e69f6d',1,'pearl-anglescan-tracker.ipf']]], - ['epics_5fdisconnect',['epics_disconnect',['../pearl-anglescan-tracker_8ipf.html#a4619cb98a75adb3c39ea3a62e524b793',1,'pearl-anglescan-tracker.ipf']]], - ['epics_5fdisconnect_5fchid',['epics_disconnect_chid',['../pearl-anglescan-tracker_8ipf.html#acfe94a64ff3e8c4cb32e34ffb9cae594',1,'pearl-anglescan-tracker.ipf']]], - ['errorcode',['errorCode',['../structerror_code.html',1,'']]], - ['export_5ftracker_5fdata',['export_tracker_data',['../pearl-anglescan-tracker_8ipf.html#a09e95dbf1582fcf2e6f71baddb147f86',1,'pearl-anglescan-tracker.ipf']]], - ['extend_5fdata',['extend_data',['../pearl-anglescan-tracker_8ipf.html#a4bde8b2fc39c61c0d5a6879f1d0ae115',1,'pearl-anglescan-tracker.ipf']]], - ['extract_5fpreview_5fimage',['extract_preview_image',['../pearl-data-explorer_8ipf.html#a0adc1b370fd3bf230b61b094b3c0accb',1,'pearl-data-explorer.ipf']]] + ['pearl_2danglescan_2dpanel_2eipf',['pearl-anglescan-panel.ipf',['../pearl-anglescan-panel_8ipf.html',1,'']]], + ['pearl_2danglescan_2dprocess_2eipf',['pearl-anglescan-process.ipf',['../pearl-anglescan-process_8ipf.html',1,'']]], + ['pearl_2danglescan_2dtracker_2eipf',['pearl-anglescan-tracker.ipf',['../pearl-anglescan-tracker_8ipf.html',1,'']]], + ['pearl_2darea_2ddisplay_2eipf',['pearl-area-display.ipf',['../pearl-area-display_8ipf.html',1,'']]], + ['pearl_2darea_2dimport_2eipf',['pearl-area-import.ipf',['../pearl-area-import_8ipf.html',1,'']]], + ['pearl_2darea_2dprofiles_2eipf',['pearl-area-profiles.ipf',['../pearl-area-profiles_8ipf.html',1,'']]], + ['pearl_2darpes_2eipf',['pearl-arpes.ipf',['../pearl-arpes_8ipf.html',1,'']]], + ['pearl_2ddata_2dexplorer_2eipf',['pearl-data-explorer.ipf',['../pearl-data-explorer_8ipf.html',1,'']]], + ['pearl_2delog_2eipf',['pearl-elog.ipf',['../pearl-elog_8ipf.html',1,'']]], + ['pearl_2dfitfuncs_2eipf',['pearl-fitfuncs.ipf',['../pearl-fitfuncs_8ipf.html',1,'']]], + ['pearl_2dgui_2dtools_2eipf',['pearl-gui-tools.ipf',['../pearl-gui-tools_8ipf.html',1,'']]], + ['pearl_2dmatrix_2dimport_2eipf',['pearl-matrix-import.ipf',['../pearl-matrix-import_8ipf.html',1,'']]], + ['pearl_2dmenu_2eipf',['pearl-menu.ipf',['../pearl-menu_8ipf.html',1,'']]], + ['pearl_2dotf_2dimport_2eipf',['pearl-otf-import.ipf',['../pearl-otf-import_8ipf.html',1,'']]], + ['pearl_2dpmsco_2dimport_2eipf',['pearl-pmsco-import.ipf',['../pearl-pmsco-import_8ipf.html',1,'']]], + ['pearl_2dpolar_2dcoordinates_2eipf',['pearl-polar-coordinates.ipf',['../pearl-polar-coordinates_8ipf.html',1,'']]], + ['pearl_2dpshell_2dimport_2eipf',['pearl-pshell-import.ipf',['../pearl-pshell-import_8ipf.html',1,'']]], + ['pearl_2dscienta_2dpreprocess_2eipf',['pearl-scienta-preprocess.ipf',['../pearl-scienta-preprocess_8ipf.html',1,'']]], + ['pearl_2dtools_2eipf',['pearl-tools.ipf',['../pearl-tools_8ipf.html',1,'']]], + ['pearl_2dvector_2doperations_2eipf',['pearl-vector-operations.ipf',['../pearl-vector-operations_8ipf.html',1,'']]] ]; diff --git a/doc/html/search/files_0.html b/doc/html/search/files_0.html index 0b637cf..4f272b8 100644 --- a/doc/html/search/files_0.html +++ b/doc/html/search/files_0.html @@ -1,7 +1,7 @@ - + diff --git a/doc/html/search/files_0.js b/doc/html/search/files_0.js index e89aa0a..e032ed1 100644 --- a/doc/html/search/files_0.js +++ b/doc/html/search/files_0.js @@ -1,4 +1,4 @@ var searchData= [ - ['fermi_2dedge_2danalysis_2eipf',['fermi-edge-analysis.ipf',['../fermi-edge-analysis_8ipf.html',1,'']]] + ['anglescan_2dprocessing_2edox',['anglescan-processing.dox',['../anglescan-processing_8dox.html',1,'']]] ]; diff --git a/doc/html/search/files_1.html b/doc/html/search/files_1.html index 1094e74..dcce422 100644 --- a/doc/html/search/files_1.html +++ b/doc/html/search/files_1.html @@ -1,7 +1,7 @@ - + diff --git a/doc/html/search/files_1.js b/doc/html/search/files_1.js index a490ea9..e89aa0a 100644 --- a/doc/html/search/files_1.js +++ b/doc/html/search/files_1.js @@ -1,4 +1,4 @@ var searchData= [ - ['mainpage_2edox',['mainpage.dox',['../mainpage_8dox.html',1,'']]] + ['fermi_2dedge_2danalysis_2eipf',['fermi-edge-analysis.ipf',['../fermi-edge-analysis_8ipf.html',1,'']]] ]; diff --git a/doc/html/search/files_2.html b/doc/html/search/files_2.html index a08dbd3..d5c6c3b 100644 --- a/doc/html/search/files_2.html +++ b/doc/html/search/files_2.html @@ -1,7 +1,7 @@ - + diff --git a/doc/html/search/files_2.js b/doc/html/search/files_2.js index 39a3ee0..a490ea9 100644 --- a/doc/html/search/files_2.js +++ b/doc/html/search/files_2.js @@ -1,22 +1,4 @@ var searchData= [ - ['pearl_2danglescan_2dpanel_2eipf',['pearl-anglescan-panel.ipf',['../pearl-anglescan-panel_8ipf.html',1,'']]], - ['pearl_2danglescan_2dprocess_2eipf',['pearl-anglescan-process.ipf',['../pearl-anglescan-process_8ipf.html',1,'']]], - ['pearl_2danglescan_2dtracker_2eipf',['pearl-anglescan-tracker.ipf',['../pearl-anglescan-tracker_8ipf.html',1,'']]], - ['pearl_2darea_2ddisplay_2eipf',['pearl-area-display.ipf',['../pearl-area-display_8ipf.html',1,'']]], - ['pearl_2darea_2dimport_2eipf',['pearl-area-import.ipf',['../pearl-area-import_8ipf.html',1,'']]], - ['pearl_2darea_2dprofiles_2eipf',['pearl-area-profiles.ipf',['../pearl-area-profiles_8ipf.html',1,'']]], - ['pearl_2darpes_2eipf',['pearl-arpes.ipf',['../pearl-arpes_8ipf.html',1,'']]], - ['pearl_2ddata_2dexplorer_2eipf',['pearl-data-explorer.ipf',['../pearl-data-explorer_8ipf.html',1,'']]], - ['pearl_2delog_2eipf',['pearl-elog.ipf',['../pearl-elog_8ipf.html',1,'']]], - ['pearl_2dfitfuncs_2eipf',['pearl-fitfuncs.ipf',['../pearl-fitfuncs_8ipf.html',1,'']]], - ['pearl_2dgui_2dtools_2eipf',['pearl-gui-tools.ipf',['../pearl-gui-tools_8ipf.html',1,'']]], - ['pearl_2dmatrix_2dimport_2eipf',['pearl-matrix-import.ipf',['../pearl-matrix-import_8ipf.html',1,'']]], - ['pearl_2dmenu_2eipf',['pearl-menu.ipf',['../pearl-menu_8ipf.html',1,'']]], - ['pearl_2dotf_2dimport_2eipf',['pearl-otf-import.ipf',['../pearl-otf-import_8ipf.html',1,'']]], - ['pearl_2dpolar_2dcoordinates_2eipf',['pearl-polar-coordinates.ipf',['../pearl-polar-coordinates_8ipf.html',1,'']]], - ['pearl_2dpshell_2dimport_2eipf',['pearl-pshell-import.ipf',['../pearl-pshell-import_8ipf.html',1,'']]], - ['pearl_2dscienta_2dpreprocess_2eipf',['pearl-scienta-preprocess.ipf',['../pearl-scienta-preprocess_8ipf.html',1,'']]], - ['pearl_2dtools_2eipf',['pearl-tools.ipf',['../pearl-tools_8ipf.html',1,'']]], - ['pearl_2dvector_2doperations_2eipf',['pearl-vector-operations.ipf',['../pearl-vector-operations_8ipf.html',1,'']]] + ['mainpage_2edox',['mainpage.dox',['../mainpage_8dox.html',1,'']]] ]; diff --git a/doc/html/search/files_3.html b/doc/html/search/files_3.html new file mode 100644 index 0000000..d5a9528 --- /dev/null +++ b/doc/html/search/files_3.html @@ -0,0 +1,26 @@ + + + + + + + + + +
+
Loading...
+
+ +
Searching...
+
No Matches
+ +
+ + diff --git a/doc/html/search/files_3.js b/doc/html/search/files_3.js new file mode 100644 index 0000000..d1de4b2 --- /dev/null +++ b/doc/html/search/files_3.js @@ -0,0 +1,23 @@ +var searchData= +[ + ['pearl_2danglescan_2dpanel_2eipf',['pearl-anglescan-panel.ipf',['../pearl-anglescan-panel_8ipf.html',1,'']]], + ['pearl_2danglescan_2dprocess_2eipf',['pearl-anglescan-process.ipf',['../pearl-anglescan-process_8ipf.html',1,'']]], + ['pearl_2danglescan_2dtracker_2eipf',['pearl-anglescan-tracker.ipf',['../pearl-anglescan-tracker_8ipf.html',1,'']]], + ['pearl_2darea_2ddisplay_2eipf',['pearl-area-display.ipf',['../pearl-area-display_8ipf.html',1,'']]], + ['pearl_2darea_2dimport_2eipf',['pearl-area-import.ipf',['../pearl-area-import_8ipf.html',1,'']]], + ['pearl_2darea_2dprofiles_2eipf',['pearl-area-profiles.ipf',['../pearl-area-profiles_8ipf.html',1,'']]], + ['pearl_2darpes_2eipf',['pearl-arpes.ipf',['../pearl-arpes_8ipf.html',1,'']]], + ['pearl_2ddata_2dexplorer_2eipf',['pearl-data-explorer.ipf',['../pearl-data-explorer_8ipf.html',1,'']]], + ['pearl_2delog_2eipf',['pearl-elog.ipf',['../pearl-elog_8ipf.html',1,'']]], + ['pearl_2dfitfuncs_2eipf',['pearl-fitfuncs.ipf',['../pearl-fitfuncs_8ipf.html',1,'']]], + ['pearl_2dgui_2dtools_2eipf',['pearl-gui-tools.ipf',['../pearl-gui-tools_8ipf.html',1,'']]], + ['pearl_2dmatrix_2dimport_2eipf',['pearl-matrix-import.ipf',['../pearl-matrix-import_8ipf.html',1,'']]], + ['pearl_2dmenu_2eipf',['pearl-menu.ipf',['../pearl-menu_8ipf.html',1,'']]], + ['pearl_2dotf_2dimport_2eipf',['pearl-otf-import.ipf',['../pearl-otf-import_8ipf.html',1,'']]], + ['pearl_2dpmsco_2dimport_2eipf',['pearl-pmsco-import.ipf',['../pearl-pmsco-import_8ipf.html',1,'']]], + ['pearl_2dpolar_2dcoordinates_2eipf',['pearl-polar-coordinates.ipf',['../pearl-polar-coordinates_8ipf.html',1,'']]], + ['pearl_2dpshell_2dimport_2eipf',['pearl-pshell-import.ipf',['../pearl-pshell-import_8ipf.html',1,'']]], + ['pearl_2dscienta_2dpreprocess_2eipf',['pearl-scienta-preprocess.ipf',['../pearl-scienta-preprocess_8ipf.html',1,'']]], + ['pearl_2dtools_2eipf',['pearl-tools.ipf',['../pearl-tools_8ipf.html',1,'']]], + ['pearl_2dvector_2doperations_2eipf',['pearl-vector-operations.ipf',['../pearl-vector-operations_8ipf.html',1,'']]] +]; diff --git a/doc/html/search/pages_0.html b/doc/html/search/pages_0.html index 0db7267..4955b9e 100644 --- a/doc/html/search/pages_0.html +++ b/doc/html/search/pages_0.html @@ -1,7 +1,7 @@ - + diff --git a/doc/html/search/pages_0.js b/doc/html/search/pages_0.js index 7cf7879..f1b4aa4 100644 --- a/doc/html/search/pages_0.js +++ b/doc/html/search/pages_0.js @@ -1,4 +1,4 @@ var searchData= [ - ['introduction',['Introduction',['../index.html',1,'']]] + ['angle_2dscan_20processing',['Angle-scan processing',['../pag_anglescan_processing.html',1,'']]] ]; diff --git a/doc/html/search/pages_1.html b/doc/html/search/pages_1.html index 2c67a8e..aedb14e 100644 --- a/doc/html/search/pages_1.html +++ b/doc/html/search/pages_1.html @@ -1,7 +1,7 @@ - + diff --git a/doc/html/search/pages_1.js b/doc/html/search/pages_1.js index 1d460e2..7cf7879 100644 --- a/doc/html/search/pages_1.js +++ b/doc/html/search/pages_1.js @@ -1,4 +1,4 @@ var searchData= [ - ['projections',['Projections',['../PageProjections.html',1,'']]] + ['introduction',['Introduction',['../index.html',1,'']]] ]; diff --git a/doc/html/search/search.css b/doc/html/search/search.css index 4d7612f..3cf9df9 100644 --- a/doc/html/search/search.css +++ b/doc/html/search/search.css @@ -6,14 +6,12 @@ #MSearchBox { white-space : nowrap; - position: absolute; float: none; - display: inline; margin-top: 8px; right: 0px; width: 170px; + height: 24px; z-index: 102; - background-color: white; } #MSearchBox .left @@ -48,12 +46,13 @@ height:19px; background:url('search_m.png') repeat-x; border:none; - width:111px; + width:115px; margin-left:20px; padding-left:4px; color: #909090; outline: none; font: 9pt Arial, Verdana, sans-serif; + -webkit-border-radius: 0px; } #FSearchBox #MSearchField { @@ -64,7 +63,7 @@ display:block; position:absolute; right:10px; - top:0px; + top:8px; width:20px; height:19px; background:url('search_r.png') no-repeat; @@ -102,7 +101,7 @@ left: 0; top: 0; border: 1px solid #90A5CE; background-color: #F9FAFC; - z-index: 1; + z-index: 10001; padding-top: 4px; padding-bottom: 4px; -moz-border-radius: 4px; @@ -165,6 +164,7 @@ iframe#MSearchResults { left: 0; top: 0; border: 1px solid #000; background-color: #EEF1F7; + z-index:10000; } /* ----------------------------------- */ diff --git a/doc/html/search/searchdata.js b/doc/html/search/searchdata.js index fc44d62..b248120 100644 --- a/doc/html/search/searchdata.js +++ b/doc/html/search/searchdata.js @@ -1,36 +1,21 @@ var indexSectionsWithContent = { - 0: "abcdefghiklmnopqrstuvwxy", - 1: "de", - 2: "p", - 3: "fmp", - 4: "abcdefghiklmnopqrstuw", - 5: "abcefhikmnopsuvwxy", - 6: "a", - 7: "ipt" + 0: "afimp", + 1: "afmp", + 2: "ai" }; var indexSectionNames = { 0: "all", - 1: "classes", - 2: "namespaces", - 3: "files", - 4: "functions", - 5: "variables", - 6: "groups", - 7: "pages" + 1: "files", + 2: "pages" }; var indexSectionLabels = { 0: "All", - 1: "Data Structures", - 2: "Namespaces", - 3: "Files", - 4: "Functions", - 5: "Variables", - 6: "Modules", - 7: "Pages" + 1: "Files", + 2: "Pages" }; diff --git a/doc/html/tabs.css b/doc/html/tabs.css index 9cf578f..bbde11e 100644 --- a/doc/html/tabs.css +++ b/doc/html/tabs.css @@ -1,60 +1 @@ -.tabs, .tabs2, .tabs3 { - background-image: url('tab_b.png'); - width: 100%; - z-index: 101; - font-size: 13px; - font-family: 'Lucida Grande',Geneva,Helvetica,Arial,sans-serif; -} - -.tabs2 { - font-size: 10px; -} -.tabs3 { - font-size: 9px; -} - -.tablist { - margin: 0; - padding: 0; - display: table; -} - -.tablist li { - float: left; - display: table-cell; - background-image: url('tab_b.png'); - line-height: 36px; - list-style: none; -} - -.tablist a { - display: block; - padding: 0 20px; - font-weight: bold; - background-image:url('tab_s.png'); - background-repeat:no-repeat; - background-position:right; - color: #283A5D; - text-shadow: 0px 1px 1px rgba(255, 255, 255, 0.9); - text-decoration: none; - outline: none; -} - -.tabs3 .tablist a { - padding: 0 10px; -} - -.tablist a:hover { - background-image: url('tab_h.png'); - background-repeat:repeat-x; - color: #fff; - text-shadow: 0px 1px 1px rgba(0, 0, 0, 1.0); - text-decoration: none; -} - -.tablist li.current a { - background-image: url('tab_a.png'); - background-repeat:repeat-x; - color: #fff; - text-shadow: 0px 1px 1px rgba(0, 0, 0, 1.0); -} +.sm{position:relative;z-index:9999}.sm,.sm ul,.sm li{display:block;list-style:none;margin:0;padding:0;line-height:normal;direction:ltr;text-align:left;-webkit-tap-highlight-color:transparent}.sm-rtl,.sm-rtl ul,.sm-rtl li{direction:rtl;text-align:right}.sm>li>h1,.sm>li>h2,.sm>li>h3,.sm>li>h4,.sm>li>h5,.sm>li>h6{margin:0;padding:0}.sm ul{display:none}.sm li,.sm a{position:relative}.sm a{display:block}.sm a.disabled{cursor:not-allowed}.sm:after{content:"\00a0";display:block;height:0;font:0px/0 serif;clear:both;visibility:hidden;overflow:hidden}.sm,.sm *,.sm *:before,.sm *:after{-moz-box-sizing:border-box;-webkit-box-sizing:border-box;box-sizing:border-box}.sm-dox{background-image:url("tab_b.png")}.sm-dox a,.sm-dox a:focus,.sm-dox a:hover,.sm-dox a:active{padding:0px 12px;padding-right:43px;font-family:"Lucida Grande","Geneva","Helvetica",Arial,sans-serif;font-size:13px;font-weight:bold;line-height:36px;text-decoration:none;text-shadow:0px 1px 1px rgba(255,255,255,0.9);color:#283A5D;outline:none}.sm-dox a:hover{background-image:url("tab_a.png");background-repeat:repeat-x;color:#fff;text-shadow:0px 1px 1px #000}.sm-dox a.current{color:#D23600}.sm-dox a.disabled{color:#bbb}.sm-dox a span.sub-arrow{position:absolute;top:50%;margin-top:-14px;left:auto;right:3px;width:28px;height:28px;overflow:hidden;font:bold 12px/28px monospace !important;text-align:center;text-shadow:none;background:rgba(255,255,255,0.5);border-radius:5px}.sm-dox a.highlighted span.sub-arrow:before{display:block;content:'-'}.sm-dox>li:first-child>a,.sm-dox>li:first-child>:not(ul) a{border-radius:5px 5px 0 0}.sm-dox>li:last-child>a,.sm-dox>li:last-child>*:not(ul) a,.sm-dox>li:last-child>ul,.sm-dox>li:last-child>ul>li:last-child>a,.sm-dox>li:last-child>ul>li:last-child>*:not(ul) a,.sm-dox>li:last-child>ul>li:last-child>ul,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul{border-radius:0 0 5px 5px}.sm-dox>li:last-child>a.highlighted,.sm-dox>li:last-child>*:not(ul) a.highlighted,.sm-dox>li:last-child>ul>li:last-child>a.highlighted,.sm-dox>li:last-child>ul>li:last-child>*:not(ul) a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>a.highlighted,.sm-dox>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>ul>li:last-child>*:not(ul) a.highlighted{border-radius:0}.sm-dox ul{background:rgba(162,162,162,0.1)}.sm-dox ul a,.sm-dox ul a:focus,.sm-dox ul a:hover,.sm-dox ul a:active{font-size:12px;border-left:8px solid transparent;line-height:36px;text-shadow:none;background-color:white;background-image:none}.sm-dox ul a:hover{background-image:url("tab_a.png");background-repeat:repeat-x;color:#fff;text-shadow:0px 1px 1px #000}.sm-dox ul ul a,.sm-dox ul ul a:hover,.sm-dox ul ul a:focus,.sm-dox ul ul a:active{border-left:16px solid transparent}.sm-dox ul ul ul a,.sm-dox ul ul ul a:hover,.sm-dox ul ul ul a:focus,.sm-dox ul ul ul a:active{border-left:24px solid transparent}.sm-dox ul ul ul ul a,.sm-dox ul ul ul ul a:hover,.sm-dox ul ul ul ul a:focus,.sm-dox ul ul ul ul a:active{border-left:32px solid transparent}.sm-dox ul ul ul ul ul a,.sm-dox ul ul ul ul ul a:hover,.sm-dox ul ul ul ul ul a:focus,.sm-dox ul ul ul ul ul a:active{border-left:40px solid transparent}@media (min-width: 768px){.sm-dox ul{position:absolute;width:12em}.sm-dox li{float:left}.sm-dox.sm-rtl li{float:right}.sm-dox ul li,.sm-dox.sm-rtl ul li,.sm-dox.sm-vertical li{float:none}.sm-dox a{white-space:nowrap}.sm-dox ul a,.sm-dox.sm-vertical a{white-space:normal}.sm-dox .sm-nowrap>li>a,.sm-dox .sm-nowrap>li>:not(ul) a{white-space:nowrap}.sm-dox{padding:0 10px;background-image:url("tab_b.png");line-height:36px}.sm-dox a span.sub-arrow{top:50%;margin-top:-2px;right:12px;width:0;height:0;border-width:4px;border-style:solid dashed dashed dashed;border-color:#283A5D transparent transparent transparent;background:transparent;border-radius:0}.sm-dox a,.sm-dox a:focus,.sm-dox a:active,.sm-dox a:hover,.sm-dox a.highlighted{padding:0px 12px;background-image:url("tab_s.png");background-repeat:no-repeat;background-position:right;border-radius:0 !important}.sm-dox a:hover{background-image:url("tab_a.png");background-repeat:repeat-x;color:#fff;text-shadow:0px 1px 1px #000}.sm-dox a:hover span.sub-arrow{border-color:#fff transparent transparent transparent}.sm-dox a.has-submenu{padding-right:24px}.sm-dox li{border-top:0}.sm-dox>li>ul:before,.sm-dox>li>ul:after{content:'';position:absolute;top:-18px;left:30px;width:0;height:0;overflow:hidden;border-width:9px;border-style:dashed dashed solid dashed;border-color:transparent transparent #bbb transparent}.sm-dox>li>ul:after{top:-16px;left:31px;border-width:8px;border-color:transparent transparent #fff transparent}.sm-dox ul{border:1px solid #bbb;padding:5px 0;background:#fff;border-radius:5px !important;box-shadow:0 5px 9px rgba(0,0,0,0.2)}.sm-dox ul a span.sub-arrow{right:8px;top:50%;margin-top:-5px;border-width:5px;border-color:transparent transparent transparent #555;border-style:dashed dashed dashed solid}.sm-dox ul a,.sm-dox ul a:hover,.sm-dox ul a:focus,.sm-dox ul a:active,.sm-dox ul a.highlighted{color:#555;background-image:none;border:0 !important;color:#555;background-image:none}.sm-dox ul a:hover{background-image:url("tab_a.png");background-repeat:repeat-x;color:#fff;text-shadow:0px 1px 1px #000}.sm-dox ul a:hover span.sub-arrow{border-color:transparent transparent transparent #fff}.sm-dox span.scroll-up,.sm-dox span.scroll-down{position:absolute;display:none;visibility:hidden;overflow:hidden;background:#fff;height:36px}.sm-dox span.scroll-up:hover,.sm-dox span.scroll-down:hover{background:#eee}.sm-dox span.scroll-up:hover span.scroll-up-arrow,.sm-dox span.scroll-up:hover span.scroll-down-arrow{border-color:transparent transparent #D23600 transparent}.sm-dox span.scroll-down:hover span.scroll-down-arrow{border-color:#D23600 transparent transparent transparent}.sm-dox span.scroll-up-arrow,.sm-dox span.scroll-down-arrow{position:absolute;top:0;left:50%;margin-left:-6px;width:0;height:0;overflow:hidden;border-width:6px;border-style:dashed dashed solid dashed;border-color:transparent transparent #555 transparent}.sm-dox span.scroll-down-arrow{top:8px;border-style:solid dashed dashed dashed;border-color:#555 transparent transparent transparent}.sm-dox.sm-rtl a.has-submenu{padding-right:12px;padding-left:24px}.sm-dox.sm-rtl a span.sub-arrow{right:auto;left:12px}.sm-dox.sm-rtl.sm-vertical a.has-submenu{padding:10px 20px}.sm-dox.sm-rtl.sm-vertical a span.sub-arrow{right:auto;left:8px;border-style:dashed solid dashed dashed;border-color:transparent #555 transparent transparent}.sm-dox.sm-rtl>li>ul:before{left:auto;right:30px}.sm-dox.sm-rtl>li>ul:after{left:auto;right:31px}.sm-dox.sm-rtl ul a.has-submenu{padding:10px 20px !important}.sm-dox.sm-rtl ul a span.sub-arrow{right:auto;left:8px;border-style:dashed solid dashed dashed;border-color:transparent #555 transparent transparent}.sm-dox.sm-vertical{padding:10px 0;border-radius:5px}.sm-dox.sm-vertical a{padding:10px 20px}.sm-dox.sm-vertical a:hover,.sm-dox.sm-vertical a:focus,.sm-dox.sm-vertical a:active,.sm-dox.sm-vertical a.highlighted{background:#fff}.sm-dox.sm-vertical a.disabled{background-image:url("tab_b.png")}.sm-dox.sm-vertical a span.sub-arrow{right:8px;top:50%;margin-top:-5px;border-width:5px;border-style:dashed dashed dashed solid;border-color:transparent transparent transparent #555}.sm-dox.sm-vertical>li>ul:before,.sm-dox.sm-vertical>li>ul:after{display:none}.sm-dox.sm-vertical ul a{padding:10px 20px}.sm-dox.sm-vertical ul a:hover,.sm-dox.sm-vertical ul a:focus,.sm-dox.sm-vertical ul a:active,.sm-dox.sm-vertical ul a.highlighted{background:#eee}.sm-dox.sm-vertical ul a.disabled{background:#fff}} diff --git a/doc/latex/refman.pdf b/doc/latex/refman.pdf index abbce3b..2c6c953 100644 Binary files a/doc/latex/refman.pdf and b/doc/latex/refman.pdf differ