Compare commits
7 Commits
rev-distro
...
rev-distro
Author | SHA1 | Date | |
---|---|---|---|
9a65d26984 | |||
c8a69460bc | |||
600061f684 | |||
0dc6ca820b | |||
a87975d1e6 | |||
86cf328961 | |||
2479582c08 |
17
README.md
17
README.md
@ -11,16 +11,20 @@ PEARL Procedures should be installed according to the regular Igor Pro guideline
|
|||||||
|
|
||||||
- Make a `pearl-procs` directory in your private or shared `User Procedures` folder, and copy the PEARL Procedures distribution there.
|
- Make a `pearl-procs` directory in your private or shared `User Procedures` folder, and copy the PEARL Procedures distribution there.
|
||||||
- Create shortcuts of the `pearl-arpes.ipf` and `pearl-menu.ipf` files, and move them to the `Igor Procedures` folder next to your `User Procedures` folder.
|
- Create shortcuts of the `pearl-arpes.ipf` and `pearl-menu.ipf` files, and move them to the `Igor Procedures` folder next to your `User Procedures` folder.
|
||||||
- Find the `HDF5.XOP` extension in the `Igor Pro Folder` under `More Extensions/File Loaders`, create a shortcut, and move the shortcut to the `Igor Extensions` folder next to your `User Procedures` folder.
|
- Find the `HDF5.XOP` (`HDF5-64.xop` for Igor 7 64-bit) extension in the `Igor Pro Folder` under `More Extensions/File Loaders` (`More Extensions (64-bit)/File Loaders`), create a shortcut, and move the shortcut to the `Igor Extensions` folder next to your `User Procedures` folder.
|
||||||
- Find the `HDF5 Help.ihf` next to `HDF5.XOP`, create a shortcut, and move the shortcut to the `Igor Help Files` folder next to your `User Procedures` folder.
|
- Find the `HDF5 Help.ihf` next to `HDF5.XOP`, create a shortcut, and move the shortcut to the `Igor Help Files` folder next to your `User Procedures` folder.
|
||||||
|
|
||||||
|
PEARL Procedures has been tested under Igor Pro version 6.37 (32-bit). Older versions prior to 6.36 are not be compatible. Please update to the latest Igor Pro 6 version before reporting any problems.
|
||||||
|
|
||||||
|
PEARL Procedures compiles under Igor 7.00. Some features, in particular 3D graphics, may not work properly.
|
||||||
|
|
||||||
|
|
||||||
License
|
License
|
||||||
=======
|
=======
|
||||||
|
|
||||||
The source code of PEARL Procedures is available under the [Apache License, Version 2.0](http://www.apache.org/licenses/LICENSE-2.0) at <https://git.psi.ch/pearl-public/igor-procs>.
|
The source code of PEARL Procedures is available under the [Apache License, Version 2.0](http://www.apache.org/licenses/LICENSE-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.
|
Please read and respect the respective license agreements.
|
||||||
|
Please share your extensions of the code with the original author.
|
||||||
|
|
||||||
Author
|
Author
|
||||||
------
|
------
|
||||||
@ -32,3 +36,12 @@ Copyright
|
|||||||
|
|
||||||
Copyright 2009-2016 by [Paul Scherrer Institut](http://www.psi.ch)
|
Copyright 2009-2016 by [Paul Scherrer Institut](http://www.psi.ch)
|
||||||
|
|
||||||
|
|
||||||
|
Release Notes
|
||||||
|
=============
|
||||||
|
|
||||||
|
## rev-distro-1.1.1
|
||||||
|
|
||||||
|
- If you have upgraded PEARL Procedures from pre-1.1.1 and Igor breaks in pearl-elog.ipf while opening an experiment, please delete the ELOG preferences file `pearl-elog/preferences.pxp`. (Check the Igor Help to find the package preferences folder on your system.)
|
||||||
|
|
||||||
|
|
||||||
|
@ -6,14 +6,14 @@
|
|||||||
#include "pearl-polar-coordinates"
|
#include "pearl-polar-coordinates"
|
||||||
#include <New Polar Graphs>
|
#include <New Polar Graphs>
|
||||||
|
|
||||||
// $Id$
|
// copyright (c) 2013-16 Paul Scherrer Institut
|
||||||
//
|
|
||||||
// copyright (c) 2013-15 Paul Scherrer Institut
|
|
||||||
//
|
//
|
||||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
// you may not use this file except in compliance with the License.
|
// you may not use this file except in compliance with the License.
|
||||||
// You may obtain a copy of the License at
|
// You may obtain a copy of the License at
|
||||||
// http:///www.apache.org/licenses/LICENSE-2.0
|
// http:///www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Please acknowledge the use of this code.
|
||||||
|
|
||||||
/// @file
|
/// @file
|
||||||
/// @brief processing and holographic mapping of angle scanned XPD data.
|
/// @brief processing and holographic mapping of angle scanned XPD data.
|
||||||
@ -64,7 +64,7 @@
|
|||||||
///
|
///
|
||||||
/// @author matthias muntwiler, matthias.muntwiler@psi.ch
|
/// @author matthias muntwiler, matthias.muntwiler@psi.ch
|
||||||
///
|
///
|
||||||
/// @copyright 2013-15 Paul Scherrer Institut @n
|
/// @copyright 2013-16 Paul Scherrer Institut @n
|
||||||
/// Licensed under the Apache License, Version 2.0 (the "License"); @n
|
/// Licensed under the Apache License, Version 2.0 (the "License"); @n
|
||||||
/// you may not use this file except in compliance with the License. @n
|
/// you may not use this file except in compliance with the License. @n
|
||||||
/// You may obtain a copy of the License at
|
/// You may obtain a copy of the License at
|
||||||
@ -79,15 +79,38 @@
|
|||||||
///
|
///
|
||||||
/// PearlAnglescanProcess is declared in @ref pearl-anglescan-process.ipf.
|
/// PearlAnglescanProcess is declared in @ref pearl-anglescan-process.ipf.
|
||||||
|
|
||||||
/// @warning experimental
|
|
||||||
function strip_remove_frames(strip, yscale, ylo, yhi)
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param[in,out] strip 2D data, X-axis = analyser angle, Y-axis = arbitrary manipulator scan.
|
||||||
|
/// the result is written to the original wave.
|
||||||
|
///
|
||||||
|
/// @param[in,out] theta 1D data, manipulator scan.
|
||||||
|
/// the result is written to the original wave.
|
||||||
|
///
|
||||||
|
/// @param[in,out] tilt 1D data, manipulator scan.
|
||||||
|
/// the result is written to the original wave.
|
||||||
|
///
|
||||||
|
/// @param[in,out] phi 1D data, manipulator scan.
|
||||||
|
/// the result is written to the original wave.
|
||||||
|
///
|
||||||
|
/// @param[in] qlo point index of first frame to delete.
|
||||||
|
///
|
||||||
|
/// @param[in] qhi point index of last frame to delete.
|
||||||
|
/// qhi must be greater or equal than qlo.
|
||||||
|
///
|
||||||
|
function strip_delete_frames(strip, qlo, qhi, theta, tilt, phi)
|
||||||
wave strip // 2D data, X-axis = analyser angle, Y-axis = arbitrary manipulator scan
|
wave strip // 2D data, X-axis = analyser angle, Y-axis = arbitrary manipulator scan
|
||||||
wave /z yscale // Y scaling, e.g. ManipulatorPhi
|
variable qlo
|
||||||
// if unassigned, point scaling is assumed
|
variable qhi
|
||||||
variable ylo
|
wave theta
|
||||||
variable yhi
|
wave tilt
|
||||||
|
wave phi
|
||||||
|
|
||||||
if (ylo > yhi)
|
if (qlo > qhi)
|
||||||
return -1
|
return -1
|
||||||
endif
|
endif
|
||||||
|
|
||||||
@ -95,8 +118,8 @@ function strip_remove_frames(strip, yscale, ylo, yhi)
|
|||||||
variable snx = dimsize(strip, 0)
|
variable snx = dimsize(strip, 0)
|
||||||
variable sny = dimsize(strip, 1)
|
variable sny = dimsize(strip, 1)
|
||||||
variable sq1lo = 0
|
variable sq1lo = 0
|
||||||
variable sq1hi = max(round((ylo - dimoffset(strip, 1)) / dimdelta(strip, 1)), 0)
|
variable sq1hi = max(qlo-1, 0)
|
||||||
variable sq2lo = min(round((ylo - dimoffset(strip, 1)) / dimdelta(strip, 1)), sny - 1)
|
variable sq2lo = min(qhi+1, sny - 1)
|
||||||
variable sq2hi = dimsize(strip, 1) - 1
|
variable sq2hi = dimsize(strip, 1) - 1
|
||||||
|
|
||||||
// dest indices
|
// dest indices
|
||||||
@ -111,10 +134,24 @@ function strip_remove_frames(strip, yscale, ylo, yhi)
|
|||||||
|
|
||||||
duplicate /free strip, strip_copy
|
duplicate /free strip, strip_copy
|
||||||
redimension /n=(dnx,dny) strip
|
redimension /n=(dnx,dny) strip
|
||||||
|
|
||||||
strip[][dq1lo,dq1hi] = strip_copy[p][q + q1ofs]
|
strip[][dq1lo,dq1hi] = strip_copy[p][q + q1ofs]
|
||||||
strip[][dq2lo,dq2hi] = strip_copy[p][q + q2ofs]
|
strip[][dq2lo,dq2hi] = strip_copy[p][q + q2ofs]
|
||||||
|
|
||||||
|
duplicate /free theta, theta_copy
|
||||||
|
redimension /n=(dny) theta
|
||||||
|
theta[dq1lo,dq1hi] = theta_copy[p + q1ofs]
|
||||||
|
theta[dq2lo,dq2hi] = theta_copy[p + q2ofs]
|
||||||
|
|
||||||
|
duplicate /free tilt, tilt_copy
|
||||||
|
redimension /n=(dny) tilt
|
||||||
|
tilt[dq1lo,dq1hi] = tilt_copy[p + q1ofs]
|
||||||
|
tilt[dq2lo,dq2hi] = tilt_copy[p + q2ofs]
|
||||||
|
|
||||||
|
duplicate /free phi, phi_copy
|
||||||
|
redimension /n=(dny) phi
|
||||||
|
phi[dq1lo,dq1hi] = phi_copy[p + q1ofs]
|
||||||
|
phi[dq2lo,dq2hi] = phi_copy[p + q2ofs]
|
||||||
|
|
||||||
return 0
|
return 0
|
||||||
end
|
end
|
||||||
|
|
||||||
@ -144,6 +181,7 @@ end
|
|||||||
/// @return if check waves are enabled, the following waves are created (overwritten if existing):
|
/// @return if check waves are enabled, the following waves are created (overwritten if existing):
|
||||||
/// @arg check_dist average X distribution
|
/// @arg check_dist average X distribution
|
||||||
/// @arg check_smoo smoothed distribution used to normalize the strip
|
/// @arg check_smoo smoothed distribution used to normalize the strip
|
||||||
|
///
|
||||||
function normalize_strip_x(strip, [smooth_method, smooth_factor, check])
|
function normalize_strip_x(strip, [smooth_method, smooth_factor, check])
|
||||||
wave strip
|
wave strip
|
||||||
variable smooth_method
|
variable smooth_method
|
||||||
@ -233,6 +271,7 @@ end
|
|||||||
/// @return if check waves are enabled, the following waves are created (overwritten if existing):
|
/// @return if check waves are enabled, the following waves are created (overwritten if existing):
|
||||||
/// @arg check_dist average theta distribution
|
/// @arg check_dist average theta distribution
|
||||||
/// @arg check_smoo smoothed distribution used to normalize the strip
|
/// @arg check_smoo smoothed distribution used to normalize the strip
|
||||||
|
///
|
||||||
function normalize_strip_theta(strip, theta, [theta_offset, smooth_method, smooth_factor, check])
|
function normalize_strip_theta(strip, theta, [theta_offset, smooth_method, smooth_factor, check])
|
||||||
wave strip
|
wave strip
|
||||||
wave theta
|
wave theta
|
||||||
@ -300,6 +339,70 @@ function normalize_strip_theta(strip, theta, [theta_offset, smooth_method, smoot
|
|||||||
endif
|
endif
|
||||||
end
|
end
|
||||||
|
|
||||||
|
/// divide the strip by a two-dimensional normalization function.
|
||||||
|
///
|
||||||
|
/// @warning experimental. this function is under development.
|
||||||
|
///
|
||||||
|
/// @param check enable output of intermediate results
|
||||||
|
/// @arg 0 (default) don't create additional waves
|
||||||
|
/// @arg 1 create check waves in the current folder
|
||||||
|
/// @arg 2 calculate check waves only, do not modify strip
|
||||||
|
///
|
||||||
|
/// @return if check waves are enabled, the following waves are created (overwritten if existing):
|
||||||
|
/// @arg check_dist average theta distribution
|
||||||
|
/// @arg check_smoo smoothed distribution used to normalize the strip
|
||||||
|
///
|
||||||
|
function normalize_strip_2d(strip, theta, [theta_offset, smooth_method, smooth_factor, check])
|
||||||
|
wave strip
|
||||||
|
wave theta
|
||||||
|
variable theta_offset
|
||||||
|
variable smooth_method
|
||||||
|
variable smooth_factor
|
||||||
|
variable check
|
||||||
|
|
||||||
|
if (ParamIsDefault(check))
|
||||||
|
check = 0
|
||||||
|
endif
|
||||||
|
if (ParamIsDefault(theta_offset))
|
||||||
|
theta_offset = 0
|
||||||
|
endif
|
||||||
|
if (ParamIsDefault(smooth_method))
|
||||||
|
smooth_method = 4
|
||||||
|
endif
|
||||||
|
if (ParamIsDefault(smooth_factor))
|
||||||
|
smooth_factor = 0.5
|
||||||
|
endif
|
||||||
|
|
||||||
|
variable nx = dimsize(strip, 0)
|
||||||
|
variable ny = dimsize(strip, 1)
|
||||||
|
|
||||||
|
duplicate /free strip, dist, alpha_int, theta_int
|
||||||
|
theta_int = theta[q] - theta_offset
|
||||||
|
alpha_int = dimoffset(strip, 0) + p * dimdelta(strip, 0)
|
||||||
|
redimension /n=(nx * ny) dist, alpha_int, theta_int
|
||||||
|
|
||||||
|
switch(smooth_method)
|
||||||
|
case 4:
|
||||||
|
loess /dest=dist_smoo /smth=(smooth_factor) srcWave=dist, factors={alpha_int, theta_int}
|
||||||
|
redimension /n=(nx, ny) dist_smoo
|
||||||
|
break
|
||||||
|
default:
|
||||||
|
Abort "undefined smooth method"
|
||||||
|
break
|
||||||
|
endswitch
|
||||||
|
|
||||||
|
// divide
|
||||||
|
if (check != 2)
|
||||||
|
strip /= dist_smoo
|
||||||
|
endif
|
||||||
|
|
||||||
|
// check
|
||||||
|
if (check)
|
||||||
|
//duplicate /o dist, check_dist
|
||||||
|
duplicate /o dist_smoo, check_smoo
|
||||||
|
endif
|
||||||
|
end
|
||||||
|
|
||||||
/// crop a strip at the sides.
|
/// crop a strip at the sides.
|
||||||
///
|
///
|
||||||
/// the strip is cropped in place, data outside the region of interest is lost.
|
/// the strip is cropped in place, data outside the region of interest is lost.
|
||||||
@ -705,9 +808,9 @@ function convert_angles_ttpa2polar(theta, tilt, phi, analyser, polar, azi)
|
|||||||
// this is simply a polar-cartesian mapping, independent of the manipulator
|
// this is simply a polar-cartesian mapping, independent of the manipulator
|
||||||
// phi=0 is in the polar rotation plane
|
// phi=0 is in the polar rotation plane
|
||||||
make /n=(3,na) /d /free w_orig_polar, w_orig_cart, w_rot_cart, w_rot_polar
|
make /n=(3,na) /d /free w_orig_polar, w_orig_cart, w_rot_cart, w_rot_polar
|
||||||
w_orig_polar[0] = radius
|
w_orig_polar[0][] = radius
|
||||||
w_orig_polar[1] = analyser[q]
|
w_orig_polar[1][] = analyser[q]
|
||||||
w_orig_polar[2] = 0
|
w_orig_polar[2][] = 0
|
||||||
polar2cart_wave(w_orig_polar, w_orig_cart)
|
polar2cart_wave(w_orig_polar, w_orig_cart)
|
||||||
// if the angle-dispersive axis was horizontal, we'd need to rotate the detector
|
// if the angle-dispersive axis was horizontal, we'd need to rotate the detector
|
||||||
//rotate_z_wave(w_orig_cart, 90)
|
//rotate_z_wave(w_orig_cart, 90)
|
||||||
@ -1802,21 +1905,46 @@ function /s display_scanlines(nickname, alpha_lo, alpha_hi, m_theta, m_tilt, m_p
|
|||||||
return graphname
|
return graphname
|
||||||
end
|
end
|
||||||
|
|
||||||
static constant kProjScaleLinear = 2
|
/// @page PageProjections Projections
|
||||||
|
///
|
||||||
|
/// the functions of the anglescan package support the following map projections.
|
||||||
|
/// for a description of the different projections, see, for example,
|
||||||
|
/// https://en.wikipedia.org/wiki/Map_projection
|
||||||
|
///
|
||||||
|
/// | Selector | Projection | Function | Properties |
|
||||||
|
/// | :----: | :----: | :----: | :---- |
|
||||||
|
/// | kProjDist = 0 | azimuthal equidistant | r = c * theta | radius is proportional to polar angle. |
|
||||||
|
/// | kProjStereo = 1 | stereographic | r = c * tan theta/2 | circles on sphere map to circles. |
|
||||||
|
/// | kProjArea = 2 | azimuthal equal-area | r = c * sin theta/2 | preserves area measure. |
|
||||||
|
/// | kProjGnom = 3 | gnomonic | r = c * tan theta | great circles map to straight lines. |
|
||||||
|
/// | kProjOrtho = 4 | orthographic | r = c * sin theta | k-space mapping in ARPES and LEED. |
|
||||||
|
///
|
||||||
|
/// the projections in this package are defined for 0 <= theta < 90.
|
||||||
|
///
|
||||||
|
constant kProjDist = 0
|
||||||
|
constant kProjStereo = 1
|
||||||
|
constant kProjArea = 2
|
||||||
|
constant kProjGnom = 3
|
||||||
|
constant kProjOrtho = 4
|
||||||
|
|
||||||
|
static constant kProjScaleDist = 2
|
||||||
static constant kProjScaleStereo = 2
|
static constant kProjScaleStereo = 2
|
||||||
static constant kProjScaleAzim = 2
|
static constant kProjScaleArea = 2
|
||||||
// scaled so that radius(gnom) = radius(stereo) for polar = 88
|
// scaled so that radius(gnom) = radius(stereo) for polar = 88
|
||||||
static constant kProjScaleGnomonic = 0.06744519021
|
static constant kProjScaleGnom = 0.06744519021
|
||||||
|
static constant kProjScaleOrtho = 2
|
||||||
|
|
||||||
/// calculate the projected polar angle
|
/// calculate the projected polar angle
|
||||||
///
|
///
|
||||||
/// @param polar polar angle in degrees
|
/// @param polar polar angle in degrees
|
||||||
///
|
///
|
||||||
/// @param projection mapping function from polar to cartesian coordinates
|
/// @param projection mapping function from polar to cartesian coordinates.
|
||||||
/// @arg 0 linear
|
/// see @ref PageProjections for details.
|
||||||
/// @arg 1 stereographic (default)
|
/// @arg kProjDist = 0 azimuthal equidistant
|
||||||
/// @arg 2 azimuthal
|
/// @arg kProjStereo = 1 stereographic (default)
|
||||||
/// @arg 3 gnomonic (0 <= polar < 90)
|
/// @arg kProjArea = 2 azimuthal equal-area
|
||||||
|
/// @arg kProjGnom = 3 gnomonic (0 <= polar < 90)
|
||||||
|
/// @arg kProjOrtho = 4 orthographic
|
||||||
///
|
///
|
||||||
/// @return projected radius.
|
/// @return projected radius.
|
||||||
/// the radius is scaled such that grazing emission maps to 2.
|
/// the radius is scaled such that grazing emission maps to 2.
|
||||||
@ -1830,17 +1958,20 @@ threadsafe function calc_graph_radius(polar, [projection])
|
|||||||
|
|
||||||
variable radius
|
variable radius
|
||||||
switch(projection)
|
switch(projection)
|
||||||
case 1: // stereographic
|
case kProjStereo: // stereographic
|
||||||
radius = kProjScaleStereo * tan(polar / 2 * pi / 180)
|
radius = kProjScaleStereo * tan(polar / 2 * pi / 180)
|
||||||
break
|
break
|
||||||
case 2: // azimuthal
|
case kProjArea: // equal area
|
||||||
radius = kProjScaleAzim * cos((180 - polar) / 2 * pi / 180)
|
radius = kProjScaleArea * sin(polar / 2 * pi / 180)
|
||||||
break
|
break
|
||||||
case 3: // gnomonic
|
case kProjGnom: // gnomonic
|
||||||
radius = polar < 90 ? kProjScaleGnomonic * tan(polar * pi / 180) : inf
|
radius = polar < 90 ? kProjScaleGnom * tan(polar * pi / 180) : inf
|
||||||
break
|
break
|
||||||
default: // linear
|
case kProjOrtho: // orthographic
|
||||||
radius = kProjScaleLinear * polar / 90
|
radius = kProjScaleOrtho * sin(polar * pi / 180)
|
||||||
|
break
|
||||||
|
default: // equidistant
|
||||||
|
radius = kProjScaleDist * polar / 90
|
||||||
endswitch
|
endswitch
|
||||||
|
|
||||||
return radius
|
return radius
|
||||||
@ -1852,10 +1983,13 @@ end
|
|||||||
///
|
///
|
||||||
/// @param x, y projected Cartesian coordinate
|
/// @param x, y projected Cartesian coordinate
|
||||||
///
|
///
|
||||||
/// @param projection mapping function from polar to cartesian coordinates
|
/// @param projection mapping function from polar to cartesian coordinates.
|
||||||
/// @arg 0 linear
|
/// see @ref PageProjections for details.
|
||||||
/// @arg 1 stereographic (default)
|
/// @arg kProjDist = 0 azimuthal equidistant
|
||||||
/// @arg 2 azimuthal
|
/// @arg kProjStereo = 1 stereographic (default)
|
||||||
|
/// @arg kProjArea = 2 azimuthal equal-area
|
||||||
|
/// @arg kProjGnom = 3 gnomonic (0 <= polar < 90)
|
||||||
|
/// @arg kProjOrtho = 4 orthographic
|
||||||
///
|
///
|
||||||
/// @returns polar angle in degrees
|
/// @returns polar angle in degrees
|
||||||
///
|
///
|
||||||
@ -1873,17 +2007,20 @@ threadsafe function calc_graph_polar(x, y, [projection])
|
|||||||
|
|
||||||
radius = sqrt(x^2 + y^2)
|
radius = sqrt(x^2 + y^2)
|
||||||
switch(projection)
|
switch(projection)
|
||||||
case 1: // stereographic
|
case kProjStereo: // stereographic
|
||||||
polar = 2 * atan(radius / kProjScaleStereo) * 180 / pi
|
polar = 2 * atan(radius / kProjScaleStereo) * 180 / pi
|
||||||
break
|
break
|
||||||
case 2: // azimuthal
|
case kProjArea: // equal area
|
||||||
polar = 180 - 2 * acos(radius / kProjScaleAzim) * 180 / pi
|
polar = 2 * asin(radius / kProjScaleArea) * 180 / pi
|
||||||
break
|
break
|
||||||
case 3: // gnomonic
|
case kProjGnom: // gnomonic
|
||||||
polar = atan(radius / kProjScaleGnomonic) * 180 / pi
|
polar = atan(radius / kProjScaleGnom) * 180 / pi
|
||||||
break
|
break
|
||||||
default: // linear
|
case kProjOrtho: // orthographic
|
||||||
polar = 90 * radius / kProjScaleLinear
|
polar = asin(radius / kProjScaleOrtho) * 180 / pi
|
||||||
|
break
|
||||||
|
default: // equidistant
|
||||||
|
polar = 90 * radius / kProjScaleDist
|
||||||
endswitch
|
endswitch
|
||||||
|
|
||||||
return polar
|
return polar
|
||||||
@ -1894,10 +2031,13 @@ end
|
|||||||
/// @param x, y projected Cartesian coordinate
|
/// @param x, y projected Cartesian coordinate
|
||||||
///
|
///
|
||||||
/// @param projection mapping function from polar to cartesian coordinates.
|
/// @param projection mapping function from polar to cartesian coordinates.
|
||||||
/// projections 0-2 have no effect on the azimuthal coordinate.
|
/// all supported projections are azimuthal, they have no effect on the azimuthal coordinate.
|
||||||
/// @arg 0 linear
|
/// see @ref PageProjections for details.
|
||||||
/// @arg 1 stereographic (default)
|
/// @arg kProjDist = 0 azimuthal equidistant
|
||||||
/// @arg 2 azimuthal
|
/// @arg kProjStereo = 1 stereographic (default)
|
||||||
|
/// @arg kProjArea = 2 azimuthal equal-area
|
||||||
|
/// @arg kProjGnom = 3 gnomonic (0 <= polar < 90)
|
||||||
|
/// @arg kProjOrtho = 4 orthographic
|
||||||
///
|
///
|
||||||
/// @param zeroAngle zeroAngleWhere parameter of polar graphs
|
/// @param zeroAngle zeroAngleWhere parameter of polar graphs
|
||||||
/// @arg 0 (default) zero is at the 3 o'clock position
|
/// @arg 0 (default) zero is at the 3 o'clock position
|
||||||
@ -2483,4 +2623,158 @@ function import_tpi_scan(nickname, theta, phi, intensity, [folding, npolar, nogr
|
|||||||
endfor
|
endfor
|
||||||
|
|
||||||
display_hemi_scan(nickname)
|
display_hemi_scan(nickname)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param nickname name of the scan dataset.
|
||||||
|
/// can be empty if no prefix is used.
|
||||||
|
/// the dataset must be in the current datafolder.
|
||||||
|
///
|
||||||
|
/// @param azim azimuthal angle in degrees
|
||||||
|
///
|
||||||
|
/// @return 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.
|
||||||
|
///
|
||||||
|
function /wave hemi_polar_cut(nickname, azim)
|
||||||
|
string nickname
|
||||||
|
variable azim
|
||||||
|
|
||||||
|
if (strlen(nickname))
|
||||||
|
string s_prefix = nickname + "_"
|
||||||
|
string s_int = s_prefix + "i"
|
||||||
|
else
|
||||||
|
s_prefix = ""
|
||||||
|
s_int = "values"
|
||||||
|
endif
|
||||||
|
string s_totals = s_prefix + "tot"
|
||||||
|
string s_weights = s_prefix + "wt"
|
||||||
|
string s_polar = s_prefix + "pol"
|
||||||
|
string s_azim = s_prefix + "az"
|
||||||
|
string s_index = s_prefix + "index"
|
||||||
|
string s_theta = s_prefix + "th"
|
||||||
|
string s_dphi = s_prefix + "dphi"
|
||||||
|
string s_nphis = s_prefix + "nphis"
|
||||||
|
string s_cut
|
||||||
|
sprintf s_cut, "%s_azi%03u", s_int, round(azim)
|
||||||
|
|
||||||
|
wave w_polar = $s_polar
|
||||||
|
wave w_azim = $s_azim
|
||||||
|
wave w_values = $s_int
|
||||||
|
wave w_totals = $s_totals
|
||||||
|
wave w_weights = $s_weights
|
||||||
|
wave w_index = $s_index
|
||||||
|
wave w_theta = $s_theta
|
||||||
|
wave w_dphi = $s_dphi
|
||||||
|
wave w_nphis = $s_nphis
|
||||||
|
|
||||||
|
variable npol = numpnts(w_theta)
|
||||||
|
variable ipol
|
||||||
|
variable pol_st = abs(w_theta[1] - w_theta[0])
|
||||||
|
variable pol
|
||||||
|
variable pol1, pol2
|
||||||
|
variable nsel
|
||||||
|
make /n=(npol) /o $s_cut
|
||||||
|
wave w_cut = $s_cut
|
||||||
|
setscale /i x w_theta[0], w_theta[numpnts(w_theta)-1], "deg", w_cut
|
||||||
|
make /n=1 /free azi_slice
|
||||||
|
make /n=1 /free values_slice
|
||||||
|
|
||||||
|
for (ipol = 0; ipol < npol; ipol += 1)
|
||||||
|
pol = w_theta[ipol]
|
||||||
|
pol1 = pol - pol_st / 2
|
||||||
|
pol2 = pol + pol_st / 2
|
||||||
|
extract /free /indx w_polar, sel, (pol1 < w_polar) && (w_polar <= pol2)
|
||||||
|
nsel = numpnts(sel)
|
||||||
|
if (nsel > 0)
|
||||||
|
redimension /n=(nsel+2) azi_slice, values_slice
|
||||||
|
azi_slice[1, nsel] = w_azim[sel[p-1]]
|
||||||
|
azi_slice[0] = azi_slice[nsel] - 360
|
||||||
|
azi_slice[nsel+1] = azi_slice[1] + 360
|
||||||
|
values_slice[1, nsel] = w_values[sel[p-1]]
|
||||||
|
values_slice[0] = values_slice[nsel]
|
||||||
|
values_slice[nsel+1] = values_slice[1]
|
||||||
|
w_cut[ipol] = interp(azim, azi_slice, values_slice)
|
||||||
|
else
|
||||||
|
w_cut[ipol] = nan
|
||||||
|
endif
|
||||||
|
endfor
|
||||||
|
return w_cut
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param nickname name of the scan dataset.
|
||||||
|
/// can be empty if no prefix is used.
|
||||||
|
/// the dataset must be in the current datafolder.
|
||||||
|
///
|
||||||
|
/// @param pol polar angle in degrees
|
||||||
|
///
|
||||||
|
/// @return 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.
|
||||||
|
///
|
||||||
|
function /wave hemi_azi_cut(nickname, pol)
|
||||||
|
string nickname
|
||||||
|
variable pol
|
||||||
|
|
||||||
|
if (strlen(nickname))
|
||||||
|
string s_prefix = nickname + "_"
|
||||||
|
string s_int = s_prefix + "i"
|
||||||
|
else
|
||||||
|
s_prefix = ""
|
||||||
|
s_int = "values"
|
||||||
|
endif
|
||||||
|
string s_totals = s_prefix + "tot"
|
||||||
|
string s_weights = s_prefix + "wt"
|
||||||
|
string s_polar = s_prefix + "pol"
|
||||||
|
string s_azim = s_prefix + "az"
|
||||||
|
string s_index = s_prefix + "index"
|
||||||
|
string s_theta = s_prefix + "th"
|
||||||
|
string s_dphi = s_prefix + "dphi"
|
||||||
|
string s_nphis = s_prefix + "nphis"
|
||||||
|
string s_cut
|
||||||
|
sprintf s_cut, "%s_pol%03u", s_int, round(pol)
|
||||||
|
|
||||||
|
wave w_polar = $s_polar
|
||||||
|
wave w_azim = $s_azim
|
||||||
|
wave w_values = $s_int
|
||||||
|
wave w_totals = $s_totals
|
||||||
|
wave w_weights = $s_weights
|
||||||
|
wave w_index = $s_index
|
||||||
|
wave w_theta = $s_theta
|
||||||
|
wave w_dphi = $s_dphi
|
||||||
|
wave w_nphis = $s_nphis
|
||||||
|
|
||||||
|
variable pol_st = abs(w_theta[1] - w_theta[0])
|
||||||
|
variable pol1, pol2
|
||||||
|
variable nsel
|
||||||
|
|
||||||
|
pol1 = pol - pol_st / 2
|
||||||
|
pol2 = pol + pol_st / 2
|
||||||
|
extract /free /indx w_polar, sel, (pol1 < w_polar) && (w_polar <= pol2)
|
||||||
|
nsel = numpnts(sel)
|
||||||
|
if (nsel > 0)
|
||||||
|
make /n=(nsel) /o $s_cut
|
||||||
|
wave w_cut = $s_cut
|
||||||
|
w_cut = w_values[sel]
|
||||||
|
setscale /i x w_azim[sel[0]], w_azim[sel[nsel-1]], "deg", w_cut
|
||||||
|
return w_cut
|
||||||
|
else
|
||||||
|
return $""
|
||||||
|
endif
|
||||||
|
end
|
||||||
|
@ -52,6 +52,25 @@
|
|||||||
/// PearlAreaDisplay is declared in @ref pearl-area-display.ipf.
|
/// PearlAreaDisplay is declared in @ref pearl-area-display.ipf.
|
||||||
///
|
///
|
||||||
|
|
||||||
|
/// compose a valid and unique graph name from a data folder reference
|
||||||
|
static function /s graphname_from_dfref(df, prefix)
|
||||||
|
dfref df
|
||||||
|
string prefix
|
||||||
|
|
||||||
|
string name
|
||||||
|
|
||||||
|
name = GetDataFolder(1, df)
|
||||||
|
name = ReplaceString("root:", name, "")
|
||||||
|
name = name[0, strlen(name) - 2]
|
||||||
|
name = ReplaceString(" ", name, "")
|
||||||
|
name = CleanupName(prefix + name, 0)
|
||||||
|
if (CheckName(name, 6))
|
||||||
|
name = UniqueName(name, 6, 0)
|
||||||
|
endif
|
||||||
|
|
||||||
|
return name
|
||||||
|
end
|
||||||
|
|
||||||
/// open a new graph window with a 2D image.
|
/// open a new graph window with a 2D image.
|
||||||
///
|
///
|
||||||
/// this is essentially <code>display; appendimage</code>.
|
/// this is essentially <code>display; appendimage</code>.
|
||||||
@ -72,7 +91,7 @@ function /s ad_display(image)
|
|||||||
|
|
||||||
string dfname = ReplaceString("root:", GetDataFolder(1, imagedf), "")
|
string dfname = ReplaceString("root:", GetDataFolder(1, imagedf), "")
|
||||||
string graphtitle = dfname + " View"
|
string graphtitle = dfname + " View"
|
||||||
string /g view_graphname = CleanupName("view_" + dfname, 0)
|
string /g view_graphname = graphname_from_dfref(imagedf, "view_")
|
||||||
svar graphname = view_graphname
|
svar graphname = view_graphname
|
||||||
display /k=1/n=$graphname as graphtitle
|
display /k=1/n=$graphname as graphtitle
|
||||||
graphname = s_name
|
graphname = s_name
|
||||||
@ -104,7 +123,7 @@ function /s ad_display_histogram(image)
|
|||||||
|
|
||||||
string dfname = ReplaceString("root:", GetDataFolder(1, imagedf), "")
|
string dfname = ReplaceString("root:", GetDataFolder(1, imagedf), "")
|
||||||
string graphtitle = dfname + " Histogram"
|
string graphtitle = dfname + " Histogram"
|
||||||
string /g hist_graphname = CleanupName("hist_" + dfname, 0)
|
string /g hist_graphname = graphname_from_dfref(imagedf, "hist_")
|
||||||
svar graphname = hist_graphname
|
svar graphname = hist_graphname
|
||||||
display /k=1/n=$graphname as graphtitle
|
display /k=1/n=$graphname as graphtitle
|
||||||
graphname = s_name
|
graphname = s_name
|
||||||
@ -171,16 +190,15 @@ function /s ad_display_profiles(image, [filter])
|
|||||||
duplicate /o image, $viewname /wave=view
|
duplicate /o image, $viewname /wave=view
|
||||||
make /n=(3,3)/o xprofiles // NX x 3 wave with 3 one-dimensional profiles along Y dimension
|
make /n=(3,3)/o xprofiles // NX x 3 wave with 3 one-dimensional profiles along Y dimension
|
||||||
make /n=(3,3)/o yprofiles // NY x 3 wave with 3 one-dimensional profiles along X dimension
|
make /n=(3,3)/o yprofiles // NY x 3 wave with 3 one-dimensional profiles along X dimension
|
||||||
make /n=(1)/o hist // histogram
|
|
||||||
string /g view_filter
|
string /g view_filter
|
||||||
string /g view_filter_options
|
string /g view_filter_options
|
||||||
view_filter = filter
|
view_filter = filter
|
||||||
view_filter_options = ""
|
view_filter_options = ""
|
||||||
variable /g view_filter_smoothing_x = 1
|
variable /g view_filter_smoothing_x = 1
|
||||||
variable /g view_filter_smoothing_y = 1
|
variable /g view_filter_smoothing_y = 1
|
||||||
string dfname = GetDataFolder(0, imagedf)
|
string dfname = ReplaceString("root:", GetDataFolder(1, imagedf), "")
|
||||||
string graphtitle = dfname + ":" + NameOfWave(image) + " Profiles"
|
string graphtitle = dfname + NameOfWave(image) + " Profiles"
|
||||||
string /g prof_graphname = CleanupName("prof_" + dfname, 0)
|
string /g prof_graphname = graphname_from_dfref(imagedf, "prof_")
|
||||||
svar graphname = prof_graphname
|
svar graphname = prof_graphname
|
||||||
variable /g graph_avg // average value in ROI (ROI is defined by the crosshairs A and B)
|
variable /g graph_avg // average value in ROI (ROI is defined by the crosshairs A and B)
|
||||||
variable /g graph_min // minimum value in ROI
|
variable /g graph_min // minimum value in ROI
|
||||||
@ -193,16 +211,13 @@ function /s ad_display_profiles(image, [filter])
|
|||||||
graphname = s_name
|
graphname = s_name
|
||||||
AppendToGraph /w=$graphname /L=xprofiles xprofiles[*][0],xprofiles[*][1],xprofiles[*][2]
|
AppendToGraph /w=$graphname /L=xprofiles xprofiles[*][0],xprofiles[*][1],xprofiles[*][2]
|
||||||
AppendToGraph /w=$graphname /VERT/B=yprofiles yprofiles[*][0],yprofiles[*][1],yprofiles[*][2]
|
AppendToGraph /w=$graphname /VERT/B=yprofiles yprofiles[*][0],yprofiles[*][1],yprofiles[*][2]
|
||||||
AppendToGraph /w=$graphname /R=hist/B=yprofiles hist
|
|
||||||
AppendImage /w=$graphname view
|
AppendImage /w=$graphname view
|
||||||
string imgname = StringFromList(0, ImageNameList(graphname, ";"))
|
string imgname = StringFromList(0, ImageNameList(graphname, ";"))
|
||||||
ModifyImage /w=$graphname $imgname ctab= {*,*,BlueGreenOrange,0}
|
ModifyImage /w=$graphname $imgname ctab= {*,*,BlueGreenOrange,0}
|
||||||
ModifyGraph /w=$graphname rgb(xprofiles)=(39168,0,0),rgb(yprofiles)=(39168,0,0)
|
ModifyGraph /w=$graphname rgb(xprofiles)=(39168,0,0),rgb(yprofiles)=(39168,0,0)
|
||||||
ModifyGraph /w=$graphname rgb(xprofiles#1)=(0,26112,0),rgb(yprofiles#1)=(0,26112,0)
|
ModifyGraph /w=$graphname rgb(xprofiles#1)=(0,26112,0),rgb(yprofiles#1)=(0,26112,0)
|
||||||
ModifyGraph /w=$graphname rgb(xprofiles#2)=(0,9472,39168),rgb(yprofiles#2)=(0,9472,39168)
|
ModifyGraph /w=$graphname rgb(xprofiles#2)=(0,9472,39168),rgb(yprofiles#2)=(0,9472,39168)
|
||||||
ModifyGraph /w=$graphname rgb(hist)=(43520,43520,43520)
|
ModifyGraph /w=$graphname mirror(xprofiles)=2,mirror(bottom)=3,mirror(yprofiles)=2,mirror(left)=3
|
||||||
ModifyGraph /w=$graphname mode(hist)=5,hbFill(hist)=2
|
|
||||||
ModifyGraph /w=$graphname mirror(xprofiles)=0,mirror(bottom)=3,mirror(yprofiles)=3,mirror(left)=3
|
|
||||||
ModifyGraph /w=$graphname nticks=3
|
ModifyGraph /w=$graphname nticks=3
|
||||||
ModifyGraph /w=$graphname minor=1
|
ModifyGraph /w=$graphname minor=1
|
||||||
ModifyGraph /w=$graphname axThick=0.5
|
ModifyGraph /w=$graphname axThick=0.5
|
||||||
@ -210,21 +225,33 @@ function /s ad_display_profiles(image, [filter])
|
|||||||
ModifyGraph /w=$graphname btLen=4
|
ModifyGraph /w=$graphname btLen=4
|
||||||
ModifyGraph /w=$graphname freePos(xprofiles)=0
|
ModifyGraph /w=$graphname freePos(xprofiles)=0
|
||||||
ModifyGraph /w=$graphname freePos(yprofiles)=0
|
ModifyGraph /w=$graphname freePos(yprofiles)=0
|
||||||
ModifyGraph /w=$graphname freePos(hist)=0
|
|
||||||
ModifyGraph /w=$graphname axisEnab(xprofiles)={0.64,1}
|
ModifyGraph /w=$graphname axisEnab(xprofiles)={0.64,1}
|
||||||
ModifyGraph /w=$graphname axisEnab(hist)={0.64,1}
|
|
||||||
ModifyGraph /w=$graphname axisEnab(bottom)={0,0.6}
|
ModifyGraph /w=$graphname axisEnab(bottom)={0,0.6}
|
||||||
ModifyGraph /w=$graphname axisEnab(yprofiles)={0.64,1}
|
ModifyGraph /w=$graphname axisEnab(yprofiles)={0.64,1}
|
||||||
ModifyGraph /w=$graphname axisEnab(left)={0,0.6}
|
ModifyGraph /w=$graphname axisEnab(left)={0,0.6}
|
||||||
ModifyGraph /w=$graphname zero(left)=8
|
ModifyGraph /w=$graphname zero(left)=8
|
||||||
ModifyGraph /w=$graphname margin(left)=40,margin(bottom)=30,margin(top)=20,margin(right)=40
|
ModifyGraph /w=$graphname margin(left)=40,margin(bottom)=30,margin(top)=20,margin(right)=40
|
||||||
ModifyGraph /w=$graphname gfSize=10
|
ModifyGraph /w=$graphname gfSize=10
|
||||||
Label /w=$graphname xprofiles "value (\\U)"
|
|
||||||
Label /w=$graphname bottom "X (\\U)"
|
// axis labels
|
||||||
Label /w=$graphname yprofiles "value (\\U)"
|
string labels = note(image)
|
||||||
Label /w=$graphname left "Y (\\U)"
|
string lab
|
||||||
Label /w=$graphname hist "\\Epixels"
|
lab = StringByKey("AxisLabelX", labels, "=", "\r")
|
||||||
SetAxis /w=$graphname /A /E=1 hist
|
if (!strlen(lab))
|
||||||
|
lab = "X"
|
||||||
|
endif
|
||||||
|
Label /w=$graphname bottom lab + " (\\U)"
|
||||||
|
lab = StringByKey("AxisLabelY", labels, "=", "\r")
|
||||||
|
if (!strlen(lab))
|
||||||
|
lab = "Y"
|
||||||
|
endif
|
||||||
|
Label /w=$graphname left lab + " (\\U)"
|
||||||
|
lab = StringByKey("AxisLabelD", labels, "=", "\r")
|
||||||
|
if (!strlen(lab))
|
||||||
|
lab = "value"
|
||||||
|
endif
|
||||||
|
Label /w=$graphname xprofiles lab + " (\\U)"
|
||||||
|
Label /w=$graphname yprofiles lab + " (\\U)"
|
||||||
|
|
||||||
// legend
|
// legend
|
||||||
if (show_legend)
|
if (show_legend)
|
||||||
@ -233,13 +260,18 @@ function /s ad_display_profiles(image, [filter])
|
|||||||
AppendText /w=$graphname "\\s(xprofiles#2)\tROI average"
|
AppendText /w=$graphname "\\s(xprofiles#2)\tROI average"
|
||||||
AppendText /w=$graphname "min\t\\{" + s_viewdf + "graph_min}"
|
AppendText /w=$graphname "min\t\\{" + s_viewdf + "graph_min}"
|
||||||
AppendText /w=$graphname "max\t\\{" + s_viewdf + "graph_max}"
|
AppendText /w=$graphname "max\t\\{" + s_viewdf + "graph_max}"
|
||||||
AppendText /w=$graphname "avg\t\\{" + s_viewdf + "graph_avg}"
|
|
||||||
AppendText /w=$graphname "sum\t\\{" + s_viewdf + "graph_sum}"
|
AppendText /w=$graphname "sum\t\\{" + s_viewdf + "graph_sum}"
|
||||||
|
AppendText /w=$graphname "avg\t\\{" + s_viewdf + "graph_avg}"
|
||||||
AppendText /w=$graphname "sdev\t\\{" + s_viewdf + "graph_sdev}"
|
AppendText /w=$graphname "sdev\t\\{" + s_viewdf + "graph_sdev}"
|
||||||
else
|
else
|
||||||
TextBox /w=$graphname /C/N=text_sum/F=0/B=1/X=1.00/Y=1.00 "sum \\{" + s_viewdf + "graph_sum}"
|
TextBox /w=$graphname /C/N=text0 /F=0 /B=1 /X=1.00 /Y=1.00
|
||||||
TextBox /w=$graphname /C/N=text_avg/F=0/B=1/X=1.00/Y=6.00 "avg \\{" + s_viewdf + "graph_avg}"
|
lab = StringByKey("Dataset", labels, "=", "\r")
|
||||||
TextBox /w=$graphname /C/N=text_sdev/F=0/B=1/X=1.00/Y=11.00 "sdev \\{" + s_viewdf + "graph_sdev}"
|
if (strlen(lab))
|
||||||
|
AppendText /w=$graphname lab
|
||||||
|
endif
|
||||||
|
AppendText /w=$graphname "sum\t\\{" + s_viewdf + "graph_sum}"
|
||||||
|
AppendText /w=$graphname "avg\t\\{" + s_viewdf + "graph_avg}"
|
||||||
|
AppendText /w=$graphname "sdev\t\\{" + s_viewdf + "graph_sdev}"
|
||||||
endif
|
endif
|
||||||
|
|
||||||
// interactive elements
|
// interactive elements
|
||||||
@ -991,7 +1023,7 @@ function /s ad_display_brick(data)
|
|||||||
setdatafolder viewdf
|
setdatafolder viewdf
|
||||||
string dfname = ReplaceString("root:", s_datadf, "")
|
string dfname = ReplaceString("root:", s_datadf, "")
|
||||||
string graphtitle = dfname + " Gizmo"
|
string graphtitle = dfname + " Gizmo"
|
||||||
string /g gizmo_graphname = CleanupName("giz_" + dfname, 0)
|
string /g gizmo_graphname = graphname_from_dfref(datadf, "giz_")
|
||||||
svar graphname = gizmo_graphname
|
svar graphname = gizmo_graphname
|
||||||
|
|
||||||
if ((strlen(graphname) > 0) && (wintype(graphname) == 13))
|
if ((strlen(graphname) > 0) && (wintype(graphname) == 13))
|
||||||
@ -1115,13 +1147,32 @@ function ad_brick_slicer(data)
|
|||||||
variable /g x_autoinc = 0
|
variable /g x_autoinc = 0
|
||||||
variable /g y_autoinc = 0
|
variable /g y_autoinc = 0
|
||||||
variable /g z_autoinc = 0
|
variable /g z_autoinc = 0
|
||||||
|
|
||||||
|
// axis labels
|
||||||
|
string labels = note(data)
|
||||||
|
string xlabel = StringByKey("AxisLabelX", labels, "=", "\r")
|
||||||
|
if (!strlen(xlabel))
|
||||||
|
xlabel = "X"
|
||||||
|
endif
|
||||||
|
string ylabel = StringByKey("AxisLabelY", labels, "=", "\r")
|
||||||
|
if (!strlen(ylabel))
|
||||||
|
ylabel = "Y"
|
||||||
|
endif
|
||||||
|
string zlabel = StringByKey("AxisLabelZ", labels, "=", "\r")
|
||||||
|
if (!strlen(zlabel))
|
||||||
|
zlabel = "Z"
|
||||||
|
endif
|
||||||
|
string dlabel = StringByKey("Dataset", labels, "=", "\r")
|
||||||
|
if (!strlen(dlabel))
|
||||||
|
dlabel = NameOfWave(data)
|
||||||
|
endif
|
||||||
|
|
||||||
// this section copied from slicer panel
|
// this section copied from slicer panel
|
||||||
NewPanel /k=1 /W=(500,600,890,940) /N=SlicerPanel as "Brick Slicer"
|
NewPanel /k=1 /W=(500,600,890,940) /N=SlicerPanel as "Brick Slicer"
|
||||||
string /g slicer_panelname = S_name
|
string /g slicer_panelname = S_name
|
||||||
string panel = s_name
|
string panel = s_name
|
||||||
|
|
||||||
GroupBox g_xslice win=$panel,pos={8,8},size={376,96},title="X Slice"
|
GroupBox g_xslice win=$panel,pos={8,8},size={376,96},title=xlabel
|
||||||
Slider sl_xslice_position win=$panel,pos={16,32},size={240,56},proc=PearlAreaDisplay#slp_slice_position
|
Slider sl_xslice_position win=$panel,pos={16,32},size={240,56},proc=PearlAreaDisplay#slp_slice_position
|
||||||
Slider sl_xslice_position win=$panel,limits={0,100,1},variable=x_slice_pos,vert= 0
|
Slider sl_xslice_position win=$panel,limits={0,100,1},variable=x_slice_pos,vert= 0
|
||||||
SetVariable sv_xslice_position win=$panel,pos={20,80},size={92,16},proc=PearlAreaDisplay#svp_slice_position,title="X"
|
SetVariable sv_xslice_position win=$panel,pos={20,80},size={92,16},proc=PearlAreaDisplay#svp_slice_position,title="X"
|
||||||
@ -1141,7 +1192,7 @@ function ad_brick_slicer(data)
|
|||||||
Button b_xslice_stop win=$panel,pos={336,48},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W616"
|
Button b_xslice_stop win=$panel,pos={336,48},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W616"
|
||||||
Button b_xslice_stop win=$panel,help={"stop animation"}
|
Button b_xslice_stop win=$panel,help={"stop animation"}
|
||||||
|
|
||||||
GroupBox g_yslice win=$panel,pos={8,108},size={376,96},title="Y Slice"
|
GroupBox g_yslice win=$panel,pos={8,108},size={376,96},title=ylabel
|
||||||
Slider sl_yslice_position win=$panel,pos={16,132},size={240,56},proc=PearlAreaDisplay#slp_slice_position
|
Slider sl_yslice_position win=$panel,pos={16,132},size={240,56},proc=PearlAreaDisplay#slp_slice_position
|
||||||
Slider sl_yslice_position win=$panel,limits={0,100,1},variable=y_slice_pos,vert= 0
|
Slider sl_yslice_position win=$panel,limits={0,100,1},variable=y_slice_pos,vert= 0
|
||||||
SetVariable sv_yslice_position win=$panel,pos={20,180},size={92,16},proc=PearlAreaDisplay#svp_slice_position,title="Y"
|
SetVariable sv_yslice_position win=$panel,pos={20,180},size={92,16},proc=PearlAreaDisplay#svp_slice_position,title="Y"
|
||||||
@ -1161,7 +1212,7 @@ function ad_brick_slicer(data)
|
|||||||
Button b_yslice_stop win=$panel,pos={336,148},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W616"
|
Button b_yslice_stop win=$panel,pos={336,148},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W616"
|
||||||
Button b_yslice_stop win=$panel,help={"stop animation"}
|
Button b_yslice_stop win=$panel,help={"stop animation"}
|
||||||
|
|
||||||
GroupBox g_zslice win=$panel,pos={8,208},size={376,96},title="Z Slice"
|
GroupBox g_zslice win=$panel,pos={8,208},size={376,96},title=zlabel
|
||||||
Slider sl_zslice_position win=$panel,pos={16,232},size={240,56},proc=PearlAreaDisplay#slp_slice_position
|
Slider sl_zslice_position win=$panel,pos={16,232},size={240,56},proc=PearlAreaDisplay#slp_slice_position
|
||||||
Slider sl_zslice_position win=$panel,limits={0,100,1},variable=z_slice_pos,vert= 0
|
Slider sl_zslice_position win=$panel,limits={0,100,1},variable=z_slice_pos,vert= 0
|
||||||
SetVariable sv_zslice_position win=$panel,pos={20,280},size={92,16},proc=PearlAreaDisplay#svp_slice_position,title="Z"
|
SetVariable sv_zslice_position win=$panel,pos={20,280},size={92,16},proc=PearlAreaDisplay#svp_slice_position,title="Z"
|
||||||
@ -1181,7 +1232,7 @@ function ad_brick_slicer(data)
|
|||||||
Button b_zslice_stop win=$panel,pos={336,248},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W616"
|
Button b_zslice_stop win=$panel,pos={336,248},size={20,20},proc=PearlAreaDisplay#bp_move_slice,title="\\W616"
|
||||||
Button b_zslice_stop win=$panel,help={"stop animation"}
|
Button b_zslice_stop win=$panel,help={"stop animation"}
|
||||||
|
|
||||||
TitleBox t_slicerpath win=$panel,pos={8,316},size={128,20},disable=2,title=GetDataFolder(1,viewdf)
|
TitleBox t_slicerpath win=$panel,pos={8,316},size={128,20},disable=2,title=dlabel
|
||||||
//SetVariable setvar0 win=$panel,pos={240,316},size={120,16},title="slab thickness"
|
//SetVariable setvar0 win=$panel,pos={240,316},size={120,16},title="slab thickness"
|
||||||
//SetVariable setvar0 win=$panel,limits={1,inf,1},value=slab_thickness
|
//SetVariable setvar0 win=$panel,limits={1,inf,1},value=slab_thickness
|
||||||
|
|
||||||
|
@ -613,3 +613,36 @@ threadsafe function calc_y_profile_mins(image)
|
|||||||
yminlocs[ix] = v_minloc
|
yminlocs[ix] = v_minloc
|
||||||
endfor
|
endfor
|
||||||
end
|
end
|
||||||
|
|
||||||
|
/// collect profiles from a multi-scan.
|
||||||
|
///
|
||||||
|
/// @warning experimental: name and interface of this function may change.
|
||||||
|
///
|
||||||
|
function ad_collect_multiscan_y(dataset, positions, destwave, [noavg])
|
||||||
|
wave dataset
|
||||||
|
wave positions
|
||||||
|
wave destwave
|
||||||
|
variable noavg
|
||||||
|
|
||||||
|
variable tol = (wavemax(positions) - wavemin(positions)) / numpnts(positions) / 100
|
||||||
|
|
||||||
|
duplicate /free positions, positions_sorted
|
||||||
|
sort positions_sorted, positions_sorted
|
||||||
|
duplicate /free positions_sorted, positions_diff
|
||||||
|
differentiate /p /meth=2 positions_sorted /d=positions_diff
|
||||||
|
positions_diff[0] = 1
|
||||||
|
extract /free positions_sorted, positions_unique, positions_diff > tol
|
||||||
|
variable n_unique = numpnts(positions_unique)
|
||||||
|
redimension /n=(dimsize(dataset, 0), n_unique) destwave
|
||||||
|
|
||||||
|
variable i
|
||||||
|
variable nx, ny
|
||||||
|
for (i = 0; i < n_unique; i += 1)
|
||||||
|
extract /free dataset, data_extract, abs(positions[q] - positions_unique[i]) < tol
|
||||||
|
nx = dimsize(dataset, 0)
|
||||||
|
ny = dimsize(data_extract, 0) / nx
|
||||||
|
redimension /n=(nx, ny) data_extract
|
||||||
|
wave profile = ad_profile_x(data_extract, -inf, inf, "", noavg=noavg)
|
||||||
|
destwave[][i] = profile[p]
|
||||||
|
endfor
|
||||||
|
end
|
||||||
|
@ -1,11 +1,14 @@
|
|||||||
#pragma rtGlobals=3 // Use modern global access method and strict wave access.
|
#pragma rtGlobals=3 // Use modern global access method and strict wave access.
|
||||||
#pragma IgorVersion = 6.1
|
#pragma IgorVersion = 6.1
|
||||||
#pragma ModuleName = PearlDataExplorer
|
#pragma ModuleName = PearlDataExplorer
|
||||||
#pragma version = 1.43
|
#pragma version = 1.50
|
||||||
#include "pearl-area-import"
|
#include "pearl-area-import"
|
||||||
#include "pearl-area-profiles"
|
#include "pearl-area-profiles"
|
||||||
#include "pearl-area-display"
|
#include "pearl-area-display"
|
||||||
#include "pearl-pshell-import"
|
#include "pearl-pshell-import"
|
||||||
|
#if exists("MFR_OpenResultFile")
|
||||||
|
#include "pearl-matrix-import"
|
||||||
|
#endif
|
||||||
|
|
||||||
// copyright (c) 2013-16 Paul Scherrer Institut
|
// copyright (c) 2013-16 Paul Scherrer Institut
|
||||||
//
|
//
|
||||||
@ -20,7 +23,10 @@
|
|||||||
///
|
///
|
||||||
///
|
///
|
||||||
/// preview and import panel for PEARL data:
|
/// preview and import panel for PEARL data:
|
||||||
/// scienta analyser, prosilica cameras, s-scans, otf-scans
|
/// @arg area detector (HDF5) files from scienta analyser and prosilica cameras (if HDF5.xop is installed).
|
||||||
|
/// @arg igor text files from s-scans and otf-scans.
|
||||||
|
/// @arg pshell (HDF5) data files (if HDF5.xop is installed).
|
||||||
|
/// @arg matrix STM files (if MatrixFileReader.xop is installed).
|
||||||
|
|
||||||
/// @namespace PearlDataExplorer
|
/// @namespace PearlDataExplorer
|
||||||
/// @brief preview and import panel for PEARL data
|
/// @brief preview and import panel for PEARL data
|
||||||
@ -33,6 +39,7 @@ static strconstant package_path = "root:packages:pearl_explorer:"
|
|||||||
static strconstant ks_filematch_adh5 = "*.h5"
|
static strconstant ks_filematch_adh5 = "*.h5"
|
||||||
static strconstant ks_filematch_pshell = "psh*.h5"
|
static strconstant ks_filematch_pshell = "psh*.h5"
|
||||||
static strconstant ks_filematch_itx = "*.itx"
|
static strconstant ks_filematch_itx = "*.itx"
|
||||||
|
static strconstant ks_filematch_mtrx = "*_mtrx"
|
||||||
|
|
||||||
function pearl_data_explorer()
|
function pearl_data_explorer()
|
||||||
init_package()
|
init_package()
|
||||||
@ -140,31 +147,64 @@ static function load_prefs()
|
|||||||
return result
|
return result
|
||||||
end
|
end
|
||||||
|
|
||||||
|
/// check whether a file can be imported by this module.
|
||||||
|
///
|
||||||
|
/// the file type is determined by the extension of the file name.
|
||||||
|
///
|
||||||
|
/// @return file type
|
||||||
|
/// @arg 0 not a recognized file type
|
||||||
|
/// @arg 1 PShell file (HDF5, name starts with psh_)
|
||||||
|
/// @arg 2 area detector HDF5 file
|
||||||
|
/// @arg 3 Igor text (itx) file
|
||||||
|
/// @arg 4 Matrix STM file (*_mtrx)
|
||||||
|
///
|
||||||
|
static function pearl_file_type(filename)
|
||||||
|
string filename
|
||||||
|
|
||||||
|
if (StringMatch(filename, ks_filematch_pshell))
|
||||||
|
return 1
|
||||||
|
elseif (StringMatch(filename, ks_filematch_adh5))
|
||||||
|
return 2
|
||||||
|
elseif (StringMatch(filename, ks_filematch_itx))
|
||||||
|
return 3
|
||||||
|
#if exists("MFR_OpenResultFile")
|
||||||
|
elseif (StringMatch(filename, ks_filematch_mtrx))
|
||||||
|
return 4
|
||||||
|
#endif
|
||||||
|
else
|
||||||
|
return 0
|
||||||
|
endif
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
static function update_filelist()
|
static function update_filelist()
|
||||||
dfref saveDF = GetDataFolderDFR()
|
dfref saveDF = GetDataFolderDFR()
|
||||||
|
|
||||||
string hdf_files, itx_files, all_files
|
string all_files
|
||||||
wave /t wtFiles = $(package_path + "wtFiles")
|
wave /t wtFiles = $(package_path + "wtFiles")
|
||||||
wave wSelectedFiles = $(package_path + "wSelectedFiles")
|
wave wSelectedFiles = $(package_path + "wSelectedFiles")
|
||||||
variable nn
|
variable nn
|
||||||
|
|
||||||
PathInfo pearl_explorer_filepath
|
PathInfo pearl_explorer_filepath
|
||||||
if (v_flag == 1)
|
if (v_flag == 1)
|
||||||
hdf_files = IndexedFile(pearl_explorer_filepath, -1, ".h5")
|
all_files = IndexedFile(pearl_explorer_filepath, -1, "????")
|
||||||
itx_files = IndexedFile(pearl_explorer_filepath, -1, ".itx")
|
|
||||||
all_files = hdf_files + itx_files
|
|
||||||
all_files = SortList(hdf_files + itx_files, ";", 4)
|
|
||||||
nn = ItemsInList(all_files)
|
nn = ItemsInList(all_files)
|
||||||
else
|
else
|
||||||
all_files = ""
|
all_files = ""
|
||||||
nn = 0
|
nn = 0
|
||||||
endif
|
endif
|
||||||
|
|
||||||
redimension /n=(nn) wtFiles, wSelectedFiles
|
make /n=(nn) /t /free wtAllFiles
|
||||||
if (nn > 0)
|
wtAllFiles = StringFromList(p, all_files)
|
||||||
wtFiles = StringFromList(p, all_files)
|
Extract /o /t wtAllFiles, wtFiles, pearl_file_type(wtAllFiles[p])
|
||||||
wSelectedFiles = 0
|
Sort /A /R wtFiles, wtFiles
|
||||||
endif
|
|
||||||
|
redimension /n=(numpnts(wtFiles)) wSelectedFiles
|
||||||
|
wSelectedFiles = 0
|
||||||
|
|
||||||
setdatafolder saveDF
|
setdatafolder saveDF
|
||||||
end
|
end
|
||||||
@ -216,14 +256,24 @@ static function preview_file(filename)
|
|||||||
string filename
|
string filename
|
||||||
|
|
||||||
dfref saveDF = GetDataFolderDFR()
|
dfref saveDF = GetDataFolderDFR()
|
||||||
|
|
||||||
if (StringMatch(filename, ks_filematch_pshell))
|
variable ft = pearl_file_type(filename)
|
||||||
wave /z image = preview_pshell_file(filename)
|
switch(ft)
|
||||||
elseif (StringMatch(filename, ks_filematch_adh5))
|
case 1:
|
||||||
wave /z image = preview_hdf_file(filename)
|
wave /z image = preview_pshell_file(filename)
|
||||||
elseif (StringMatch(filename, ks_filematch_itx))
|
break
|
||||||
wave /z image = preview_itx_file(filename)
|
case 2:
|
||||||
endif
|
wave /z image = preview_hdf_file(filename)
|
||||||
|
break
|
||||||
|
case 3:
|
||||||
|
wave /z image = preview_itx_file(filename)
|
||||||
|
break
|
||||||
|
case 4:
|
||||||
|
wave /z image = preview_mtrx_file(filename)
|
||||||
|
break
|
||||||
|
default:
|
||||||
|
wave /z image = $""
|
||||||
|
endswitch
|
||||||
|
|
||||||
if (WaveExists(image))
|
if (WaveExists(image))
|
||||||
string graphname = show_preview_graph(image)
|
string graphname = show_preview_graph(image)
|
||||||
@ -240,9 +290,10 @@ static function preview_file(filename)
|
|||||||
endif
|
endif
|
||||||
|
|
||||||
setdatafolder saveDF
|
setdatafolder saveDF
|
||||||
|
return 0
|
||||||
end
|
end
|
||||||
|
|
||||||
/// load the preview of a PShell HDF5 file (not implemented).
|
/// 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 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 preview is loaded to the preview_image wave in the pear_explorer data folder.
|
||||||
@ -354,6 +405,63 @@ static function /wave preview_itx_file(filename)
|
|||||||
return preview_image
|
return preview_image
|
||||||
end
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param filename name of a file in the directory specified by the pearl_explorer_filepath path object.
|
||||||
|
///
|
||||||
|
/// @return wave reference of the preview image.
|
||||||
|
/// empty wave reference if the function failed.
|
||||||
|
///
|
||||||
|
static function /wave preview_mtrx_file(filename)
|
||||||
|
string filename
|
||||||
|
|
||||||
|
#if exists("MFR_OpenResultFile")
|
||||||
|
dfref saveDF = GetDataFolderDFR()
|
||||||
|
setdatafolder $package_path
|
||||||
|
variable /g V_MatrixFileReaderOverwrite = 1
|
||||||
|
variable /g V_MatrixFileReaderFolder = 0
|
||||||
|
variable /g V_MatrixFileReaderDouble = 0
|
||||||
|
svar s_preview_file
|
||||||
|
svar s_preview_source
|
||||||
|
string datanames
|
||||||
|
string dataname
|
||||||
|
datanames = mtrx_load_preview("preview", "pearl_explorer_filepath", filename)
|
||||||
|
if (strlen(datanames) > 0)
|
||||||
|
s_preview_file = filename
|
||||||
|
|
||||||
|
dataname = StringFromList(0, datanames)
|
||||||
|
wave data = $dataname
|
||||||
|
duplicate /o $dataname, preview_image
|
||||||
|
s_preview_source = StringByKey("Dataset", note(data), "=", "\r")
|
||||||
|
|
||||||
|
svar /z s_file_info
|
||||||
|
if (svar_exists(s_file_info))
|
||||||
|
s_file_info = ""
|
||||||
|
endif
|
||||||
|
|
||||||
|
variable i
|
||||||
|
variable n = ItemsInList(datanames)
|
||||||
|
string s
|
||||||
|
for (i = 0; i < n; i += 1)
|
||||||
|
s = StringFromList(i, datanames)
|
||||||
|
killwaves /z $s
|
||||||
|
endfor
|
||||||
|
endif
|
||||||
|
wave /z preview_image
|
||||||
|
setdatafolder saveDF
|
||||||
|
#else
|
||||||
|
wave /z preview_image = $""
|
||||||
|
#endif
|
||||||
|
return preview_image
|
||||||
|
end
|
||||||
|
|
||||||
static function extract_preview_image(data, preview)
|
static function extract_preview_image(data, preview)
|
||||||
// extracts a preview image from a wave of arbitrary dimension
|
// extracts a preview image from a wave of arbitrary dimension
|
||||||
wave data
|
wave data
|
||||||
@ -759,18 +867,21 @@ static function /s show_preview_graph(data, [xdata])
|
|||||||
svar s_profiles_graph
|
svar s_profiles_graph
|
||||||
svar s_preview_file
|
svar s_preview_file
|
||||||
svar s_preview_source
|
svar s_preview_source
|
||||||
|
svar s_preview_trace_graph
|
||||||
|
|
||||||
|
if ((strlen(s_profiles_graph) > 0) && (WinType(s_profiles_graph) == 1))
|
||||||
|
KillWindow $s_profiles_graph
|
||||||
|
endif
|
||||||
|
if ((strlen(s_preview_trace_graph) > 0) && (WinType(s_preview_trace_graph) == 1))
|
||||||
|
KillWindow $s_preview_trace_graph
|
||||||
|
endif
|
||||||
|
|
||||||
string graphname
|
string graphname
|
||||||
if (wavedims(data) == 2)
|
if (wavedims(data) == 2)
|
||||||
if ((strlen(s_profiles_graph) > 0) && (WinType(s_profiles_graph) == 1))
|
s_profiles_graph = ad_display_profiles(data)
|
||||||
ad_update_profiles(data)
|
ModifyGraph /w=$s_profiles_graph /z wbRGB=(48640,56832,60160)
|
||||||
else
|
|
||||||
s_profiles_graph = ad_display_profiles(data)
|
|
||||||
ModifyGraph /w=$s_profiles_graph /z wbRGB=(48640,56832,60160)
|
|
||||||
endif
|
|
||||||
graphname = s_profiles_graph
|
graphname = s_profiles_graph
|
||||||
elseif (wavedims(data) == 1)
|
elseif (wavedims(data) == 1)
|
||||||
svar s_preview_trace_graph
|
|
||||||
duplicate /o data, preview_trace
|
duplicate /o data, preview_trace
|
||||||
if (!ParamIsDefault(xdata))
|
if (!ParamIsDefault(xdata))
|
||||||
duplicate /o xdata, preview_trace_x
|
duplicate /o xdata, preview_trace_x
|
||||||
@ -779,20 +890,8 @@ static function /s show_preview_graph(data, [xdata])
|
|||||||
preview_trace_x = x
|
preview_trace_x = x
|
||||||
setscale d 0, 0, WaveUnits(data, 0), preview_trace_x
|
setscale d 0, 0, WaveUnits(data, 0), preview_trace_x
|
||||||
endif
|
endif
|
||||||
if ((strlen(s_preview_trace_graph) == 0) || (WinType(s_preview_trace_graph) != 1))
|
s_preview_trace_graph = display_preview_trace(preview_trace_x, preview_trace)
|
||||||
display /n=pearl_explorer_1d /k=1 preview_trace vs preview_trace_x as "Preview"
|
ModifyGraph /w=$s_preview_trace_graph wbRGB=(48640,56832,60160)
|
||||||
s_preview_trace_graph = s_name
|
|
||||||
ModifyGraph /w=$s_preview_trace_graph wbRGB=(48640,56832,60160)
|
|
||||||
ModifyGraph /w=$s_preview_trace_graph rgb[0]=(0,0,0)
|
|
||||||
ModifyGraph /w=$s_preview_trace_graph grid=2
|
|
||||||
ModifyGraph /w=$s_preview_trace_graph mirror=1
|
|
||||||
ModifyGraph /w=$s_preview_trace_graph minor=1
|
|
||||||
ModifyGraph /w=$s_preview_trace_graph axThick=0.5
|
|
||||||
ModifyGraph /w=$s_preview_trace_graph gridRGB=(52224,52224,52224)
|
|
||||||
ModifyGraph /w=$s_preview_trace_graph gridHair=0
|
|
||||||
ModifyGraph /w=$s_preview_trace_graph tick=0
|
|
||||||
ModifyGraph /w=$s_preview_trace_graph btLen=4
|
|
||||||
endif
|
|
||||||
graphname = s_preview_trace_graph
|
graphname = s_preview_trace_graph
|
||||||
else
|
else
|
||||||
return ""
|
return ""
|
||||||
@ -808,6 +907,39 @@ static function /s show_preview_graph(data, [xdata])
|
|||||||
return graphname
|
return graphname
|
||||||
end
|
end
|
||||||
|
|
||||||
|
static function /s display_preview_trace(xtrace, ytrace)
|
||||||
|
wave xtrace
|
||||||
|
wave ytrace
|
||||||
|
|
||||||
|
display /n=pearl_explorer_1d /k=1 ytrace vs xtrace as "Preview"
|
||||||
|
string graphname = s_name
|
||||||
|
ModifyGraph /w=$graphname rgb[0]=(0,0,0)
|
||||||
|
ModifyGraph /w=$graphname grid=2
|
||||||
|
ModifyGraph /w=$graphname mirror=1
|
||||||
|
ModifyGraph /w=$graphname minor=1
|
||||||
|
ModifyGraph /w=$graphname axThick=0.5
|
||||||
|
ModifyGraph /w=$graphname gridRGB=(52224,52224,52224)
|
||||||
|
ModifyGraph /w=$graphname gridHair=0
|
||||||
|
ModifyGraph /w=$graphname tick=0
|
||||||
|
ModifyGraph /w=$graphname btLen=4
|
||||||
|
|
||||||
|
// axis labels
|
||||||
|
string labels = note(ytrace)
|
||||||
|
string lab
|
||||||
|
lab = StringByKey("AxisLabelX", labels, "=", "\r")
|
||||||
|
if (!strlen(lab))
|
||||||
|
lab = "X"
|
||||||
|
endif
|
||||||
|
Label /w=$graphname bottom lab + " (\\U)"
|
||||||
|
lab = StringByKey("AxisLabelD", labels, "=", "\r")
|
||||||
|
if (!strlen(lab))
|
||||||
|
lab = "value"
|
||||||
|
endif
|
||||||
|
Label /w=$graphname left lab + " (\\U)"
|
||||||
|
|
||||||
|
return s_name
|
||||||
|
end
|
||||||
|
|
||||||
static function load_selected_files([options])
|
static function load_selected_files([options])
|
||||||
string options
|
string options
|
||||||
|
|
||||||
@ -838,22 +970,32 @@ static function load_file(filename, [options])
|
|||||||
|
|
||||||
dfref saveDF = GetDataFolderDFR()
|
dfref saveDF = GetDataFolderDFR()
|
||||||
|
|
||||||
if (StringMatch(filename, ks_filematch_pshell))
|
variable ft = pearl_file_type(filename)
|
||||||
if (ParamIsDefault(options))
|
switch(ft)
|
||||||
load_pshell_file(filename)
|
case 1:
|
||||||
else
|
if (ParamIsDefault(options))
|
||||||
load_pshell_file(filename, options=options)
|
load_pshell_file(filename)
|
||||||
endif
|
else
|
||||||
elseif (StringMatch(filename, ks_filematch_adh5))
|
load_pshell_file(filename, options=options)
|
||||||
if (ParamIsDefault(options))
|
endif
|
||||||
load_hdf_file(filename)
|
break
|
||||||
else
|
case 2:
|
||||||
load_hdf_file(filename, options=options)
|
if (ParamIsDefault(options))
|
||||||
endif
|
load_hdf_file(filename)
|
||||||
elseif (StringMatch(filename, ks_filematch_itx))
|
else
|
||||||
load_itx_file(filename)
|
load_hdf_file(filename, options=options)
|
||||||
endif
|
endif
|
||||||
|
break
|
||||||
|
case 3:
|
||||||
|
load_itx_file(filename)
|
||||||
|
break
|
||||||
|
case 4:
|
||||||
|
load_mtrx_file(filename)
|
||||||
|
break
|
||||||
|
default:
|
||||||
|
break
|
||||||
|
endswitch
|
||||||
|
|
||||||
setdatafolder saveDF
|
setdatafolder saveDF
|
||||||
end
|
end
|
||||||
|
|
||||||
@ -1056,6 +1198,32 @@ static function /df load_itx_file(filename, [options])
|
|||||||
return actDF
|
return actDF
|
||||||
end
|
end
|
||||||
|
|
||||||
|
/// load a matrix (STM) data file
|
||||||
|
///
|
||||||
|
///
|
||||||
|
static function /df load_mtrx_file(filename, [options])
|
||||||
|
string filename
|
||||||
|
string options
|
||||||
|
|
||||||
|
dfref saveDF = GetDataFolderDFR()
|
||||||
|
dfref dataDF = $""
|
||||||
|
|
||||||
|
#if exists("MFR_OpenResultFile")
|
||||||
|
setdatafolder root:
|
||||||
|
string datasets = ""
|
||||||
|
datasets = mtrx_load_file("pearl_explorer_filepath", filename)
|
||||||
|
if (strlen(datasets) > 0)
|
||||||
|
string /g pearl_explorer_import = "load_mtrx_file"
|
||||||
|
string s1 = StringFromList(0, datasets)
|
||||||
|
wave w1 = $s1
|
||||||
|
dataDF = GetWavesDataFolderDFR(w1)
|
||||||
|
endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
setdatafolder saveDF
|
||||||
|
return dataDF
|
||||||
|
end
|
||||||
|
|
||||||
function /s itx_suggest_foldername(filename, [ignoredate,sourcename,unique])
|
function /s itx_suggest_foldername(filename, [ignoredate,sourcename,unique])
|
||||||
// suggests the name of a data folder based on a file name
|
// suggests the name of a data folder based on a file name
|
||||||
// if the file name follows the naming convention source-date-index.extension,
|
// if the file name follows the naming convention source-date-index.extension,
|
||||||
@ -1426,6 +1594,9 @@ static function bp_dataset_folder(ba) : ButtonControl
|
|||||||
string cmd
|
string cmd
|
||||||
sprintf cmd, "setdatafolder root:%s", PossiblyQuoteName(dataset)
|
sprintf cmd, "setdatafolder root:%s", PossiblyQuoteName(dataset)
|
||||||
execute /q /z cmd
|
execute /q /z cmd
|
||||||
|
cmd = "setdatafolder :scan1"
|
||||||
|
execute /q /z cmd
|
||||||
|
sprintf cmd, "setdatafolder %s", GetDataFolder(1)
|
||||||
print cmd
|
print cmd
|
||||||
endif
|
endif
|
||||||
break
|
break
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
#pragma rtGlobals=3 // Use modern global access method and strict wave access.
|
#pragma rtGlobals=3 // Use modern global access method and strict wave access.
|
||||||
#pragma version = 1.31
|
#pragma version = 1.40
|
||||||
#pragma IgorVersion = 6.2
|
#pragma IgorVersion = 6.2
|
||||||
#pragma ModuleName = PearlElog
|
#pragma ModuleName = PearlElog
|
||||||
|
|
||||||
@ -16,13 +16,38 @@
|
|||||||
/// @ingroup ArpesPackage
|
/// @ingroup ArpesPackage
|
||||||
///
|
///
|
||||||
///
|
///
|
||||||
/// the functions in this module support the following work flows:
|
/// the functions in this module support the following ELOG features:
|
||||||
/// 1. send a preview of a selected measurement to ELOG.
|
/// - submit new entries and replies to existing entries.
|
||||||
/// 2. send any Igor graph to ELOG. (CLI and GUI)
|
/// - text field, list box, and check box attributes.
|
||||||
/// 3. direct access to all ELOG parameters. (CLI only)
|
/// - attach any Igor graph to ELOG.
|
||||||
|
/// - configurable logbook templates for logbooks that share the same configuration.
|
||||||
|
/// - common server configurations available on the ELOG command line
|
||||||
|
/// (hostname, port, SSL, username, password, sub-directory).
|
||||||
|
/// - not specific to the configuration at PEARL.
|
||||||
|
/// PEARL code is concentrated in the elog_init_pearl_templates() function.
|
||||||
|
/// - the configuration of the ELOG server and logbooks
|
||||||
|
/// as well as the most recently used attributes are persisted in the preference file.
|
||||||
///
|
///
|
||||||
/// the configuration of the ELOG server and logbooks (except user name and password)
|
/// usage:
|
||||||
/// as well as the most recently used attributes are persisted in the preference file.
|
/// 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. 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.
|
||||||
|
/// 3. if the server requires a user name and password,
|
||||||
|
/// click the login button.
|
||||||
|
/// 4. edit the message, attributes and attachments as necessary, and submit to ELOG.
|
||||||
|
/// 5. log out before saving the experiment to clear the password.
|
||||||
|
///
|
||||||
|
/// @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 command line
|
||||||
///@verbatim
|
///@verbatim
|
||||||
@ -43,12 +68,6 @@
|
|||||||
/// -m <textfile>] | <text>
|
/// -m <textfile>] | <text>
|
||||||
///@endverbatim
|
///@endverbatim
|
||||||
///
|
///
|
||||||
/// user name and password are used if configured in the package data folder.
|
|
||||||
/// there is currently no separate user interface.
|
|
||||||
///
|
|
||||||
/// @attention some functions in this module refer specifically to the ELOG configuration at PEARL.
|
|
||||||
///
|
|
||||||
/// @todo ask for logbook, username and password before opening the panel.
|
|
||||||
///
|
///
|
||||||
/// @author matthias muntwiler, matthias.muntwiler@psi.ch
|
/// @author matthias muntwiler, matthias.muntwiler@psi.ch
|
||||||
///
|
///
|
||||||
@ -82,7 +101,7 @@ function pearl_elog(logbook)
|
|||||||
load_prefs()
|
load_prefs()
|
||||||
string templates = list_logbooks(templates=1)
|
string templates = list_logbooks(templates=1)
|
||||||
if (ItemsInList(templates) < 1)
|
if (ItemsInList(templates) < 1)
|
||||||
init_pearl_templates()
|
elog_init_pearl_templates()
|
||||||
endif
|
endif
|
||||||
endif
|
endif
|
||||||
|
|
||||||
@ -95,7 +114,11 @@ function pearl_elog(logbook)
|
|||||||
if (strlen(WinList(win_name, ";", "")) > 0)
|
if (strlen(WinList(win_name, ";", "")) > 0)
|
||||||
DoWindow /F $win_name
|
DoWindow /F $win_name
|
||||||
else
|
else
|
||||||
PearlElogPanel(logbook)
|
win_name = PearlElogPanel(logbook)
|
||||||
|
STRUCT WMWinHookStruct s
|
||||||
|
s.eventCode = 0
|
||||||
|
s.winName = win_name
|
||||||
|
elog_panel_hook(s)
|
||||||
endif
|
endif
|
||||||
endif
|
endif
|
||||||
end
|
end
|
||||||
@ -104,6 +127,7 @@ end
|
|||||||
static function IgorBeforeNewHook(igorApplicationNameStr)
|
static function IgorBeforeNewHook(igorApplicationNameStr)
|
||||||
string igorApplicationNameStr
|
string igorApplicationNameStr
|
||||||
save_prefs()
|
save_prefs()
|
||||||
|
cleanup_temp_files()
|
||||||
return 0
|
return 0
|
||||||
end
|
end
|
||||||
|
|
||||||
@ -111,6 +135,7 @@ end
|
|||||||
static function IgorQuitHook(igorApplicationNameStr)
|
static function IgorQuitHook(igorApplicationNameStr)
|
||||||
string igorApplicationNameStr
|
string igorApplicationNameStr
|
||||||
save_prefs()
|
save_prefs()
|
||||||
|
cleanup_temp_files()
|
||||||
return 0
|
return 0
|
||||||
end
|
end
|
||||||
|
|
||||||
@ -234,7 +259,7 @@ end
|
|||||||
///
|
///
|
||||||
/// @remark this function is specific to the setup at PEARL.
|
/// @remark this function is specific to the setup at PEARL.
|
||||||
///
|
///
|
||||||
static function init_pearl_templates()
|
function elog_init_pearl_templates()
|
||||||
dfref savedf = getdatafolderdfr()
|
dfref savedf = getdatafolderdfr()
|
||||||
|
|
||||||
dfref df_root = get_elog_df("", kdfRoot)
|
dfref df_root = get_elog_df("", kdfRoot)
|
||||||
@ -247,10 +272,10 @@ static function init_pearl_templates()
|
|||||||
|
|
||||||
// attributes (persistent)
|
// attributes (persistent)
|
||||||
// available attributes
|
// available attributes
|
||||||
string /g attributes = "author;project;sample;source;task;technique;valid;file"
|
string /g attributes = "author;project;sample;source;task;technique;file;valid;"
|
||||||
// controls corresponding to attributes
|
// controls corresponding to attributes
|
||||||
// prefix determines the control type: sv_ = setvariable (string), pm_ = popup menu, cb = check box
|
// prefix determines the control type: sv_ = setvariable (string), pm_ = popup menu, cb = check box
|
||||||
string /g controls = "sv_author;sv_project;sv_sample;pm_source;pm_task;pm_technique;cb_valid;sv_file"
|
string /g controls = "sv_author;sv_project;sv_sample;pm_source;pm_task;pm_technique;sv_file;cb_valid;"
|
||||||
// attributes with fixed options, value item declares the options string
|
// attributes with fixed options, value item declares the options string
|
||||||
string /g options = "source=sources;task=tasks;technique=techniques"
|
string /g options = "source=sources;task=tasks;technique=techniques"
|
||||||
// attributes which must be defined
|
// attributes which must be defined
|
||||||
@ -258,8 +283,8 @@ static function init_pearl_templates()
|
|||||||
|
|
||||||
// option lists
|
// option lists
|
||||||
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"
|
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"
|
||||||
string /g tasks = "Measurement;Sample Preparation;Sample Storage;Optimization;Analysis;Development;Maintenance;Test;Comment;Other"
|
string /g tasks = "Measurement;Optimization;Analysis;Sample Preparation;Sample Storage;Comment;Development;Maintenance;Test;Other"
|
||||||
string /g techniques = "XPS;UPS;XPD;XAS;XMCD;PhD;ARUPS;LEED;AES;STM;STS;QMS;MBE;Test;Other"
|
string /g techniques = "XPS;UPS;XPD;XAS;XMCD;PhD;ARUPS;STM;STS;LEED;AES;QMS;MBE;Sputter/Anneal;Test;Other"
|
||||||
|
|
||||||
// Calculations template
|
// Calculations template
|
||||||
setdatafolder df_templates
|
setdatafolder df_templates
|
||||||
@ -267,18 +292,38 @@ static function init_pearl_templates()
|
|||||||
|
|
||||||
// attributes (persistent)
|
// attributes (persistent)
|
||||||
// available attributes
|
// available attributes
|
||||||
string /g attributes = "author;project;sample;program;revision;machine;job;source path;result path;valid"
|
string /g attributes = "author;project;sample;program;revision;machine;job;experiment;source path;result path;valid"
|
||||||
// controls corresponding to attributes
|
// controls corresponding to attributes
|
||||||
// prefix determines the control type: sv_ = setvariable (string), pm_ = popup menu, cb = check box
|
// prefix determines the control type: sv_ = setvariable (string), pm_ = popup menu, cb = check box
|
||||||
string /g controls = "sv_author;sv_project;sv_sample;pm_program;sv_revision;pm_machine;sv_job;sv_sourcepath;sv_resultpath;cb_valid"
|
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"
|
||||||
// attributes with fixed options, value item declares the options string
|
// attributes with fixed options, value item declares the options string
|
||||||
string /g options = "program=programs;machine=machines"
|
string /g options = "program=programs;machine=machines"
|
||||||
// attributes which must be defined
|
// attributes which must be defined
|
||||||
string /g required_attributes = "author;project;sample"
|
string /g required_attributes = "author;project;sample"
|
||||||
|
|
||||||
// option lists
|
// option lists
|
||||||
string /g programs = "DMSUP;EDAC;MSC;MUFPOT;SSC"
|
string /g programs = "PMSCO;EDAC;MSC;SSC;MUFPOT;DMSUP;Other"
|
||||||
string /g machines = "llcx;Merlin;PC"
|
string /g machines = "PC;VM;Ra;Merlin;llcx;Other"
|
||||||
|
|
||||||
|
// System template
|
||||||
|
setdatafolder df_templates
|
||||||
|
newdatafolder /o/s System
|
||||||
|
|
||||||
|
// attributes (persistent)
|
||||||
|
// available attributes
|
||||||
|
string /g attributes = "author;type;system;source;file"
|
||||||
|
// controls corresponding to attributes
|
||||||
|
// prefix determines the control type: sv_ = setvariable (string), pm_ = popup menu, cb = check box
|
||||||
|
string /g controls = "sv_author;pm_type;pm_system;pm_source;sv_file"
|
||||||
|
// attributes with fixed options, value item declares the options string
|
||||||
|
string /g options = "type=types;system=systems;source=sources"
|
||||||
|
// attributes which must be defined
|
||||||
|
string /g required_attributes = "author;type;system"
|
||||||
|
|
||||||
|
// option lists
|
||||||
|
string /g types = "Installation;Repair;Maintenance;Test;Commissioning;Bakeout;Incident;Cool-down;Warm-up;Storage;Other"
|
||||||
|
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"
|
||||||
|
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"
|
||||||
|
|
||||||
setdatafolder savedf
|
setdatafolder savedf
|
||||||
return 0
|
return 0
|
||||||
@ -303,6 +348,11 @@ static function init_volatile_vars()
|
|||||||
variable nlb = ItemsInList(logbooks)
|
variable nlb = ItemsInList(logbooks)
|
||||||
variable ilb
|
variable ilb
|
||||||
|
|
||||||
|
SetDataFolder df_volatile_root
|
||||||
|
if (exists("temp_graph_files") != 2)
|
||||||
|
string /g temp_graph_files = ""
|
||||||
|
endif
|
||||||
|
|
||||||
for (ilb = 0; ilb < nlb; ilb += 1)
|
for (ilb = 0; ilb < nlb; ilb += 1)
|
||||||
logbook = StringFromList(ilb, logbooks)
|
logbook = StringFromList(ilb, logbooks)
|
||||||
|
|
||||||
@ -322,6 +372,13 @@ static function init_volatile_vars()
|
|||||||
if (exists("msg_id") != 2)
|
if (exists("msg_id") != 2)
|
||||||
variable /g msg_id = 0
|
variable /g msg_id = 0
|
||||||
endif
|
endif
|
||||||
|
if (exists("att_list") != 1)
|
||||||
|
make /n=(0,3) /t /o attach_list
|
||||||
|
make /n=(0,3) /i /o attach_sel
|
||||||
|
endif
|
||||||
|
if (exists("url") != 2)
|
||||||
|
string /g url = ""
|
||||||
|
endif
|
||||||
endfor
|
endfor
|
||||||
|
|
||||||
SetDataFolder savedf
|
SetDataFolder savedf
|
||||||
@ -347,6 +404,9 @@ end
|
|||||||
/// create a new empty logbook or duplicate from a template.
|
/// create a new empty logbook or duplicate from a template.
|
||||||
///
|
///
|
||||||
/// @param name name of the new logbook.
|
/// @param name name 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.
|
||||||
///
|
///
|
||||||
/// @param template name of the template.
|
/// @param template name of the template.
|
||||||
/// if empty string, a new empty logbook is created.
|
/// if empty string, a new empty logbook is created.
|
||||||
@ -368,6 +428,10 @@ function elog_create_logbook(name, [template])
|
|||||||
|
|
||||||
if (strlen(template) > 0)
|
if (strlen(template) > 0)
|
||||||
dfref df_template = get_elog_df(template, kdfTemplates)
|
dfref df_template = get_elog_df(template, kdfTemplates)
|
||||||
|
dfref df_existing = get_elog_df(name, kdfPersistent)
|
||||||
|
if (DataFolderRefStatus(df_existing))
|
||||||
|
KillDataFolder /Z df_existing
|
||||||
|
endif
|
||||||
DuplicateDataFolder df_template, df_persistent_parent:$name
|
DuplicateDataFolder df_template, df_persistent_parent:$name
|
||||||
else
|
else
|
||||||
NewDataFolder /o/s df_persistent_parent:$name
|
NewDataFolder /o/s df_persistent_parent:$name
|
||||||
@ -695,7 +759,6 @@ function elog_create_entry(logbook, attributes, message, [encoding, graphs, repl
|
|||||||
endif
|
endif
|
||||||
result = -4
|
result = -4
|
||||||
endif
|
endif
|
||||||
cleanup_temp_files()
|
|
||||||
else
|
else
|
||||||
if (loglevel >= 2)
|
if (loglevel >= 2)
|
||||||
print "ELOG: failed to create temporary message file."
|
print "ELOG: failed to create temporary message file."
|
||||||
@ -759,7 +822,6 @@ function elog_add_attachment(logbook, id, graphs)
|
|||||||
endif
|
endif
|
||||||
result = -4 // error: elog returned error
|
result = -4 // error: elog returned error
|
||||||
endif
|
endif
|
||||||
cleanup_temp_files()
|
|
||||||
endif
|
endif
|
||||||
|
|
||||||
setdatafolder savedf
|
setdatafolder savedf
|
||||||
@ -817,6 +879,39 @@ static function /s prepare_command_line(logbook)
|
|||||||
return cmd
|
return cmd
|
||||||
end
|
end
|
||||||
|
|
||||||
|
/// format the URL for display to the user
|
||||||
|
///
|
||||||
|
///
|
||||||
|
/// @param logbook name of the target logbook
|
||||||
|
///
|
||||||
|
static function /s format_url(logbook)
|
||||||
|
string logbook
|
||||||
|
|
||||||
|
dfref df_general = get_elog_df("", kdfPersistent)
|
||||||
|
|
||||||
|
svar /sdfr=df_general hostname
|
||||||
|
nvar /sdfr=df_general port
|
||||||
|
nvar /sdfr=df_general ssl
|
||||||
|
svar /sdfr=df_general subdir
|
||||||
|
|
||||||
|
string cmd = ""
|
||||||
|
if ((nvar_exists(ssl)) && (ssl != 0))
|
||||||
|
cmd += "https://"
|
||||||
|
else
|
||||||
|
cmd += "http://"
|
||||||
|
endif
|
||||||
|
cmd += hostname
|
||||||
|
if ((nvar_exists(port)) && (port > 0))
|
||||||
|
cmd += ":" + num2str(port)
|
||||||
|
endif
|
||||||
|
if ((svar_exists(subdir)) && (strlen(subdir) > 0))
|
||||||
|
cmd += "/" + subdir
|
||||||
|
endif
|
||||||
|
cmd += "/" + logbook
|
||||||
|
|
||||||
|
return cmd
|
||||||
|
end
|
||||||
|
|
||||||
/// prepare screenshots of graph windows for attachments
|
/// prepare screenshots of graph windows for attachments
|
||||||
///
|
///
|
||||||
/// prepares the attachment files from Igor graph windows
|
/// prepares the attachment files from Igor graph windows
|
||||||
@ -875,13 +970,18 @@ static function /s create_graph_file(graphname, fileindex)
|
|||||||
string graphname
|
string graphname
|
||||||
variable fileindex
|
variable fileindex
|
||||||
|
|
||||||
|
dfref df_volatile_root = get_elog_df("", kdfVolatile)
|
||||||
|
svar /sdfr=df_volatile_root temp_graph_files
|
||||||
|
|
||||||
string path = SpecialDirPath("Temporary", 0, 1, 0)
|
string path = SpecialDirPath("Temporary", 0, 1, 0)
|
||||||
string ts = get_timestamp("_")
|
string ts = get_timestamp("_")
|
||||||
variable len = strlen(path)
|
variable len = strlen(path)
|
||||||
if (numtype(len) == 0)
|
if (numtype(len) == 0)
|
||||||
path += "elog_" + ts + "_" + num2str(fileindex) + ".png"
|
path += "elog_" + ts + "_" + num2str(fileindex) + ".png"
|
||||||
SavePICT /B=72 /E=-5 /M /O /W=(0,0,8,6) /WIN=$graphname /Z as path
|
SavePICT /B=72 /E=-5 /M /O /W=(0,0,8,6) /WIN=$graphname /Z as path
|
||||||
if (v_flag != 0)
|
if (v_flag == 0)
|
||||||
|
temp_graph_files = AddListItem(path, temp_graph_files, ";", inf)
|
||||||
|
else
|
||||||
path = ""
|
path = ""
|
||||||
endif
|
endif
|
||||||
else
|
else
|
||||||
@ -921,12 +1021,30 @@ static function /s get_log_path()
|
|||||||
return path
|
return path
|
||||||
end
|
end
|
||||||
|
|
||||||
static function /s cleanup_temp_files()
|
/// delete temporary files created by the ELOG module.
|
||||||
string path = SpecialDirPath("Temporary", 0, 1, 0)
|
///
|
||||||
string cmd
|
/// this deletes all temporary graph files that are referenced by the volatile temp_graph_files list.
|
||||||
sprintf cmd, "del \"%s\elog*.*\"", path
|
/// temp_graph_files is a semicolon-delimited string.
|
||||||
//ExecuteScriptText cmd
|
/// items are added by create_graph_file().
|
||||||
return path
|
///
|
||||||
|
/// this function should be called before a new experiment is loaded or igor quits.
|
||||||
|
///
|
||||||
|
static function cleanup_temp_files()
|
||||||
|
dfref df_volatile_root = get_elog_df("", kdfVolatile)
|
||||||
|
if (DataFolderRefStatus(df_volatile_root))
|
||||||
|
svar /sdfr=df_volatile_root /z temp_graph_files
|
||||||
|
if (SVAR_Exists(temp_graph_files))
|
||||||
|
variable nfi = ItemsInList(temp_graph_files)
|
||||||
|
variable ifi
|
||||||
|
string sfi
|
||||||
|
for (ifi = 0; ifi < nfi; ifi += 1)
|
||||||
|
sfi = StringFromList(ifi, temp_graph_files)
|
||||||
|
DeleteFile /Z sfi
|
||||||
|
endfor
|
||||||
|
temp_graph_files = ""
|
||||||
|
endif
|
||||||
|
endif
|
||||||
|
return 0
|
||||||
end
|
end
|
||||||
|
|
||||||
static strconstant elog_success_msg = "Message successfully transmitted"
|
static strconstant elog_success_msg = "Message successfully transmitted"
|
||||||
@ -1048,14 +1166,17 @@ function /s PearlElogPanel(logbook)
|
|||||||
string win_name = logbook + "ElogPanel"
|
string win_name = logbook + "ElogPanel"
|
||||||
string win_title = "ELOG " + logbook
|
string win_title = "ELOG " + logbook
|
||||||
|
|
||||||
NewPanel /K=1 /N=$win_name /W=(600,200,926,494) as win_title
|
NewPanel /K=1 /N=$win_name /W=(600,200,1200,700) as win_title
|
||||||
win_name = s_name
|
win_name = s_name
|
||||||
ModifyPanel /w=$win_name cbRGB=(52224,52224,65280)
|
ModifyPanel /w=$win_name cbRGB=(52224,52224,65280)
|
||||||
|
|
||||||
svar /sdfr=df_persistent attributes
|
svar /sdfr=df_persistent attributes
|
||||||
svar /sdfr=df_persistent controls
|
svar /sdfr=df_persistent controls
|
||||||
svar /sdfr=df_persistent options
|
svar /sdfr=df_persistent options
|
||||||
|
wave /t /sdfr=df_volatile attach_list
|
||||||
|
wave /sdfr=df_volatile attach_sel
|
||||||
|
svar /sdfr=df_volatile url
|
||||||
|
|
||||||
variable iattr
|
variable iattr
|
||||||
variable nattr = ItemsInList(attributes, ";")
|
variable nattr = ItemsInList(attributes, ";")
|
||||||
string s_attr
|
string s_attr
|
||||||
@ -1066,35 +1187,28 @@ function /s PearlElogPanel(logbook)
|
|||||||
string options_path
|
string options_path
|
||||||
string variable_path
|
string variable_path
|
||||||
variable ypos = 2
|
variable ypos = 2
|
||||||
|
variable height = 0
|
||||||
|
|
||||||
Button b_login,win=$win_name, pos={264,ypos},size={46,20},proc=PearlElog#bp_login,title="Login"
|
|
||||||
Button b_login,win=$win_name, help={"Enter user name and password."}
|
|
||||||
Button b_login,win=$win_name, fcolor=(56576,60928,47872)
|
|
||||||
|
|
||||||
Button b_logout,win=$win_name, pos={264,ypos},size={46,20},proc=PearlElog#bp_logout,title="Logout"
|
|
||||||
Button b_logout,win=$win_name, help={"Clear user name and password."}
|
|
||||||
Button b_logout,win=$win_name, fcolor=(56576,60928,47872), disable=3
|
|
||||||
|
|
||||||
for (iattr = 0; iattr < nattr; iattr += 1)
|
for (iattr = 0; iattr < nattr; iattr += 1)
|
||||||
s_attr = StringFromList(iattr, attributes, ";")
|
s_attr = StringFromList(iattr, attributes, ";")
|
||||||
s_control = StringFromList(iattr, controls, ";")
|
s_control = StringFromList(iattr, controls, ";")
|
||||||
strswitch(s_control[0,1])
|
strswitch(s_control[0,1])
|
||||||
case "sv":
|
case "sv":
|
||||||
SetVariable $s_control, win=$win_name, pos={0,ypos}, size={260,16}, bodyWidth=200
|
SetVariable $s_control, win=$win_name, pos={0,ypos}, size={300,16}, bodyWidth=230
|
||||||
SetVariable $s_control, win=$win_name, title=s_attr, value= _STR:""
|
SetVariable $s_control, win=$win_name, title=s_attr, value= _STR:""
|
||||||
SetVariable $s_control, win=$win_name, userdata(attribute)=s_attr
|
SetVariable $s_control, win=$win_name, userdata(attribute)=s_attr
|
||||||
ypos += 18
|
ypos += 18
|
||||||
break
|
break
|
||||||
case "pm":
|
case "pm":
|
||||||
options_path = persistent_path + StringByKey(s_attr, options, "=", ";")
|
options_path = persistent_path + StringByKey(s_attr, options, "=", ";")
|
||||||
PopupMenu $s_control, win=$win_name, pos={0,ypos}, size={260,21}, bodyWidth=200
|
PopupMenu $s_control, win=$win_name, pos={0,ypos}, size={300,21}, bodyWidth=230
|
||||||
PopupMenu $s_control, win=$win_name, title=s_attr
|
PopupMenu $s_control, win=$win_name, title=s_attr
|
||||||
PopupMenu $s_control, win=$win_name, mode=1, popvalue="Test", value= #options_path
|
PopupMenu $s_control, win=$win_name, mode=1, popvalue="Test", value= #options_path
|
||||||
PopupMenu $s_control, win=$win_name, userdata(attribute)=s_attr
|
PopupMenu $s_control, win=$win_name, userdata(attribute)=s_attr
|
||||||
ypos += 23
|
ypos += 23
|
||||||
break
|
break
|
||||||
case "cb":
|
case "cb":
|
||||||
CheckBox $s_control, win=$win_name, pos={60,ypos}, size={260,14}
|
CheckBox $s_control, win=$win_name, pos={70,ypos}, size={300,14}
|
||||||
CheckBox $s_control, win=$win_name, title=s_attr, value= 1
|
CheckBox $s_control, win=$win_name, title=s_attr, value= 1
|
||||||
CheckBox $s_control, win=$win_name, userdata(attribute)=s_attr
|
CheckBox $s_control, win=$win_name, userdata(attribute)=s_attr
|
||||||
ypos += 17
|
ypos += 17
|
||||||
@ -1102,48 +1216,81 @@ function /s PearlElogPanel(logbook)
|
|||||||
endswitch
|
endswitch
|
||||||
endfor
|
endfor
|
||||||
|
|
||||||
PopupMenu pm_attach,win=$win_name, pos={0,ypos},size={260,21},bodyWidth=200,title="Attachment"
|
TitleBox t_attach, win=$win_name, pos={308,5}, size={70,14}, title="Attachments", frame=0
|
||||||
PopupMenu pm_attach,win=$win_name, mode=1,popvalue="(none)",value=PearlElog#pm_list_attach_items()
|
height = ypos - 21 - 4
|
||||||
PopupMenu pm_attach,win=$win_name, help={"Choose any visible Igor graph for attachment."}
|
ListBox lb_attach, win=$win_name, pos={308,21}, size={264,height}
|
||||||
Button b_select_attach_top,win=$win_name, pos={264,ypos},size={60,20},proc=PearlElog#bp_select_attach_top,title="Top Graph"
|
ListBox lb_attach, win=$win_name, listWave=attach_list
|
||||||
Button b_select_attach_top,win=$win_name, help={"Select top graph window."}
|
ListBox lb_attach, win=$win_name, mode=1, selWave=attach_sel, selRow=-1
|
||||||
Button b_select_attach_top,win=$win_name, fcolor=(56576,60928,47872)
|
ListBox lb_attach, win=$win_name, widths={20,160,80}
|
||||||
|
ListBox lb_attach, win=$win_name, help={"Choose graphs to attach to the message."}
|
||||||
|
|
||||||
|
Button b_attach_top, win=$win_name, pos={420,2}, size={40,18}, title="top"
|
||||||
|
Button b_attach_top, win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
Button b_attach_top, win=$win_name, proc=PearlElog#bp_attach_top
|
||||||
|
Button b_attach_top, win=$win_name, help={"Select top graph for attachment."}
|
||||||
|
Button b_attach_all, win=$win_name, pos={460,2}, size={40,18}, title="all"
|
||||||
|
Button b_attach_all, win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
Button b_attach_all, win=$win_name, proc=PearlElog#bp_attach_allnone
|
||||||
|
Button b_attach_all, win=$win_name, help={"Select all graphs for attachment."}
|
||||||
|
Button b_attach_none, win=$win_name, pos={500,2}, size={40,18}, title="none"
|
||||||
|
Button b_attach_none, win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
Button b_attach_none, win=$win_name, proc=PearlElog#bp_attach_allnone
|
||||||
|
Button b_attach_none, win=$win_name, help={"Deselect all attachments."}
|
||||||
|
Button b_save_graphs, win=$win_name, pos={540,2}, size={40,18}, title="save"
|
||||||
|
Button b_save_graphs, win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
Button b_save_graphs, win=$win_name, proc=PearlElog#bp_save_graphs
|
||||||
|
Button b_save_graphs, win=$win_name, help={"Save selected graphs as PNG bitmap files."}
|
||||||
|
Button b_attach_up, win=$win_name, pos={576,20}, size={20,20}, title="\\W517"
|
||||||
|
Button b_attach_up, win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
Button b_attach_up, win=$win_name, proc=PearlElog#bp_attach_updown
|
||||||
|
Button b_attach_up, win=$win_name, help={"Move selected graph up."}
|
||||||
|
Button b_attach_dw, win=$win_name, pos={576,40}, size={20,20}, title="\\W523"
|
||||||
|
Button b_attach_dw, win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
Button b_attach_dw, win=$win_name, proc=PearlElog#bp_attach_updown
|
||||||
|
Button b_attach_dw, win=$win_name, help={"Move selected graph down."}
|
||||||
|
|
||||||
ypos += 246-160
|
ypos += 246-160
|
||||||
Button b_submit,win=$win_name, pos={60,ypos},size={46,20},proc=PearlElog#bp_submit,title="Submit"
|
Button b_submit,win=$win_name, pos={70,ypos},size={46,20},proc=PearlElog#bp_submit,title="Submit"
|
||||||
Button b_submit,win=$win_name, help={"Submit form data to ELOG (new entry)."}
|
Button b_submit,win=$win_name, help={"Submit form data to ELOG (new entry)."}
|
||||||
Button b_submit,win=$win_name, fcolor=(56576,60928,47872)
|
Button b_submit,win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
Button b_clear,win=$win_name, pos={120,ypos},size={46,20},proc=PearlElog#bp_clear,title="Clear"
|
||||||
Button b_clear,win=$win_name, pos={110,ypos},size={46,20},proc=PearlElog#bp_clear,title="Clear"
|
|
||||||
Button b_clear,win=$win_name, help={"Clear the form fields"}
|
Button b_clear,win=$win_name, help={"Clear the form fields"}
|
||||||
Button b_clear,win=$win_name, fcolor=(56576,60928,47872)
|
Button b_clear,win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
|
||||||
ypos += 272-246
|
ypos += 272-246
|
||||||
variable_path = volatile_path + "msg_id"
|
variable_path = volatile_path + "msg_id"
|
||||||
SetVariable sv_id,win=$win_name, pos={46,ypos},size={109,16},bodyWidth=94
|
SetVariable sv_id,win=$win_name, pos={51,ypos},size={119,16},bodyWidth=77
|
||||||
SetVariable sv_id,win=$win_name, title="ID",value=$variable_path
|
SetVariable sv_id,win=$win_name, title="ID",value=$variable_path
|
||||||
SetVariable sv_id,win=$win_name, help={"ID of last submitted message, or message to attach or reply to."}
|
SetVariable sv_id,win=$win_name, help={"ID of last submitted message, or message to attach or reply to."}
|
||||||
|
|
||||||
|
TitleBox t_host, win=$win_name, pos={170,ypos+4}, size={112.00,14.00}, frame=0
|
||||||
|
TitleBox t_host, win=$win_name, variable=url
|
||||||
|
|
||||||
ypos += 270-272
|
ypos += 270-272
|
||||||
Button b_attach,win=$win_name, pos={160,ypos},size={48,20},proc=PearlElog#bp_attach,title="Attach"
|
Button b_attach,win=$win_name, pos={170,ypos},size={48,20},proc=PearlElog#bp_attach,title="Attach"
|
||||||
Button b_attach,win=$win_name, help={"Attach the selected graph to an existing ELOG entry (correct ID required)."}
|
Button b_attach,win=$win_name, help={"Attach the selected graph to an existing ELOG entry (correct ID required)."}
|
||||||
Button b_attach,win=$win_name, fcolor=(56576,60928,47872)
|
Button b_attach,win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
Button b_reply,win=$win_name, pos={220,ypos},size={48,20},proc=PearlElog#bp_submit,title="Reply"
|
||||||
Button b_reply,win=$win_name, pos={210,ypos},size={48,20},proc=PearlElog#bp_submit,title="Reply"
|
|
||||||
Button b_reply,win=$win_name, help={"Submit form data to ELOG as a reply to an existing message (correct ID required)."}
|
Button b_reply,win=$win_name, help={"Submit form data to ELOG as a reply to an existing message (correct ID required)."}
|
||||||
Button b_reply,win=$win_name, fcolor=(56576,60928,47872)
|
Button b_reply,win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
Button b_login,win=$win_name, pos={550,ypos},size={46,20},proc=PearlElog#bp_login,title="Login"
|
||||||
ypos += 184-270
|
Button b_login,win=$win_name, help={"Enter user name and password."}
|
||||||
TitleBox t_message,win=$win_name, pos={0,ypos},size={58,16},fixedSize=1,frame=0,anchor=RT,title="Message"
|
Button b_login,win=$win_name, fcolor=(56576,60928,47872)
|
||||||
|
Button b_logout,win=$win_name, pos={550,ypos},size={46,20},proc=PearlElog#bp_logout,title="Logout"
|
||||||
|
Button b_logout,win=$win_name, help={"Clear user name and password."}
|
||||||
|
Button b_logout,win=$win_name, fcolor=(56576,60928,47872), disable=3
|
||||||
|
|
||||||
SetWindow $win_name, hook(elogPanelHook)=PearlElog#elog_panel_hook
|
SetWindow $win_name, hook(elogPanelHook)=PearlElog#elog_panel_hook
|
||||||
SetWindow $win_name, userdata(logbook)=logbook
|
SetWindow $win_name, userdata(logbook)=logbook
|
||||||
|
|
||||||
DefineGuide UGH0={FT,ypos},UGV0={FL,60},UGH1={FB,-52},UGV1={FR,-2}
|
ypos += 160-270
|
||||||
|
TitleBox t_message,win=$win_name, pos={10,ypos},size={58,16},fixedSize=1,frame=0,anchor=RT,title="Message"
|
||||||
|
DefineGuide UGH0={FT,ypos},UGV0={FL,70},UGH1={FB,-52},UGV1={FR,-2}
|
||||||
NewNotebook /F=0 /N=Message /OPTS=3 /W=(115,404,345,341)/FG=(UGV0,UGH0,UGV1,UGH1) /HOST=#
|
NewNotebook /F=0 /N=Message /OPTS=3 /W=(115,404,345,341)/FG=(UGV0,UGH0,UGV1,UGH1) /HOST=#
|
||||||
Notebook kwTopWin, defaultTab=20, statusWidth=0, autoSave=0
|
Notebook kwTopWin, defaultTab=20, statusWidth=0, autoSave=0
|
||||||
Notebook kwTopWin font="Arial", fSize=10, fStyle=0, textRGB=(0,0,0)
|
Notebook kwTopWin fSize=10, fStyle=0, textRGB=(0,0,0)
|
||||||
RenameWindow #,Message
|
RenameWindow #,Message
|
||||||
|
string nb_name = win_name + "#Message"
|
||||||
SetActiveSubwindow ##
|
SetActiveSubwindow ##
|
||||||
|
|
||||||
// restore recently used attributes and message
|
// restore recently used attributes and message
|
||||||
@ -1155,6 +1302,7 @@ function /s PearlElogPanel(logbook)
|
|||||||
if (svar_exists(recent_message) && (strlen(recent_message) > 0))
|
if (svar_exists(recent_message) && (strlen(recent_message) > 0))
|
||||||
set_panel_message(win_name, recent_message)
|
set_panel_message(win_name, recent_message)
|
||||||
endif
|
endif
|
||||||
|
Notebook $nb_name selection={startOfFile,startOfFile}, findText={"",1}
|
||||||
|
|
||||||
setdatafolder savedf
|
setdatafolder savedf
|
||||||
return win_name
|
return win_name
|
||||||
@ -1166,49 +1314,152 @@ static function elog_panel_hook(s)
|
|||||||
Variable hookResult = 0
|
Variable hookResult = 0
|
||||||
|
|
||||||
switch(s.eventCode)
|
switch(s.eventCode)
|
||||||
|
case 0: // activate
|
||||||
|
string logbook = GetUserData(s.winName, "", "logbook")
|
||||||
|
if (strlen(logbook) > 0)
|
||||||
|
dfref df_volatile = get_elog_df(logbook, kdfVolatile)
|
||||||
|
svar /sdfr=df_volatile url
|
||||||
|
url = format_url(logbook)
|
||||||
|
update_attach_items(logbook)
|
||||||
|
endif
|
||||||
|
break
|
||||||
case 6: // resize
|
case 6: // resize
|
||||||
// move bottom-aligned controls when the window is resized
|
// move bottom-aligned controls when the window is resized
|
||||||
variable b_top = s.winRect.bottom + 4
|
variable b_top = s.winRect.bottom + 4
|
||||||
Button b_submit,pos={60,b_top}
|
Button b_submit,pos={70,b_top}
|
||||||
Button b_clear,pos={110,b_top}
|
Button b_clear,pos={120,b_top}
|
||||||
|
TitleBox t_host, pos={170,b_top+4}
|
||||||
b_top += 24
|
b_top += 24
|
||||||
Button b_attach,pos={160,b_top}
|
Button b_attach,pos={170,b_top}
|
||||||
Button b_reply,pos={210,b_top}
|
Button b_reply,pos={220,b_top}
|
||||||
|
Button b_login, pos={550,b_top}
|
||||||
|
Button b_logout, pos={550,b_top}
|
||||||
b_top += 2
|
b_top += 2
|
||||||
SetVariable sv_id,pos={46,b_top}
|
SetVariable sv_id,pos={51,b_top}
|
||||||
break
|
break
|
||||||
endswitch
|
endswitch
|
||||||
|
|
||||||
return hookResult // 0 if nothing done, else 1
|
return hookResult // 0 if nothing done, else 1
|
||||||
end
|
end
|
||||||
|
|
||||||
/// get a list of graph windows for a popup menu.
|
static constant kAttachColSel = 0
|
||||||
static function /s pm_list_attach_items()
|
static constant kAttachColTitle = 1
|
||||||
|
static constant kAttachColName = 2
|
||||||
|
|
||||||
// get graph names
|
/// update the list of attachments
|
||||||
|
static function update_attach_items(logbook)
|
||||||
|
string logbook
|
||||||
|
|
||||||
|
dfref savedf = getdatafolderdfr()
|
||||||
|
dfref df_volatile = get_elog_df(logbook, kdfVolatile)
|
||||||
|
wave /t /sdfr=df_volatile attach_list
|
||||||
|
wave /sdfr=df_volatile attach_sel
|
||||||
|
|
||||||
|
if (!waveexists(attach_list))
|
||||||
|
return -1
|
||||||
|
endif
|
||||||
string names = WinList("*", ";", "WIN:1;VISIBLE:1")
|
string names = WinList("*", ";", "WIN:1;VISIBLE:1")
|
||||||
names = SortList(names, ";", 16)
|
names = SortList(names, ";", 16)
|
||||||
|
|
||||||
// get corresponding graph titles
|
// remove closed graphs
|
||||||
variable nnames = ItemsInList(names, ";")
|
variable i
|
||||||
variable iname
|
variable k
|
||||||
string name
|
variable n = DimSize(attach_list, 0)
|
||||||
string item
|
string s
|
||||||
string items = ""
|
for (i = n-1; i >= 0; i -= 1)
|
||||||
|
s = attach_list[i][kAttachColName]
|
||||||
// format each entry like "name: title"
|
if (WhichListItem(s, names) < 0)
|
||||||
for (iname = 0; iname < nnames; iname += 1)
|
DeletePoints /M=0 i, 1, attach_list, attach_sel
|
||||||
name = StringFromList(iname, names, ";")
|
|
||||||
getwindow /z $name, wtitle
|
|
||||||
if (v_flag == 0)
|
|
||||||
item = ReplaceString(";", s_value, ", ") // title
|
|
||||||
item = item + " (" + name + ")"
|
|
||||||
items = AddListItem(item, items, ";", inf)
|
|
||||||
endif
|
endif
|
||||||
endfor
|
endfor
|
||||||
|
|
||||||
items = AddListItem("(none)", items, ";")
|
// add new graphs
|
||||||
return items
|
n = ItemsInList(names)
|
||||||
|
for (i = 0; i < n; i += 1)
|
||||||
|
s = StringFromList(i, names)
|
||||||
|
FindValue /text=s /txop=4 /z attach_list
|
||||||
|
if (v_value < 0)
|
||||||
|
k = DimSize(attach_list, 0)
|
||||||
|
InsertPoints /M=0 k, 1, attach_list, attach_sel
|
||||||
|
attach_list[i][kAttachColSel] = ""
|
||||||
|
attach_list[i][kAttachColTitle] = ""
|
||||||
|
attach_list[k][kAttachColName] = s
|
||||||
|
attach_sel[i][kAttachColSel] = 32
|
||||||
|
attach_sel[i][kAttachColTitle] = 0
|
||||||
|
attach_sel[i][kAttachColName] = 0
|
||||||
|
endif
|
||||||
|
endfor
|
||||||
|
|
||||||
|
// update titles
|
||||||
|
n = DimSize(attach_list, 0)
|
||||||
|
for (i = n-1; i >= 0; i -= 1)
|
||||||
|
s = attach_list[i][kAttachColName]
|
||||||
|
getwindow /z $s, wtitle
|
||||||
|
if (v_flag == 0)
|
||||||
|
attach_list[i][kAttachColTitle] = s_value
|
||||||
|
else
|
||||||
|
attach_list[i][kAttachColTitle] = s
|
||||||
|
endif
|
||||||
|
endfor
|
||||||
|
|
||||||
|
setdatafolder savedf
|
||||||
|
return 0
|
||||||
|
end
|
||||||
|
|
||||||
|
/// move an attachment item in the list of attachments
|
||||||
|
static function move_attach_item(logbook, item, distance)
|
||||||
|
string logbook
|
||||||
|
variable item
|
||||||
|
variable distance
|
||||||
|
|
||||||
|
dfref savedf = getdatafolderdfr()
|
||||||
|
dfref df_volatile = get_elog_df(logbook, kdfVolatile)
|
||||||
|
wave /t /sdfr=df_volatile attach_list
|
||||||
|
wave /sdfr=df_volatile attach_sel
|
||||||
|
variable n = DimSize(attach_list, 0)
|
||||||
|
variable dest = item + distance
|
||||||
|
|
||||||
|
if ((item >= 0) && (item < n) && (dest >= 0) && (dest < n))
|
||||||
|
string name = attach_list[item][kAttachColName]
|
||||||
|
variable sel = attach_sel[item][kAttachColSel]
|
||||||
|
DeletePoints /M=0 item, 1, attach_list, attach_sel
|
||||||
|
InsertPoints /M=0 dest, 1, attach_list, attach_sel
|
||||||
|
attach_list[dest][kAttachColName] = name
|
||||||
|
update_attach_items(logbook)
|
||||||
|
attach_sel[dest][kAttachColSel] = sel
|
||||||
|
endif
|
||||||
|
end
|
||||||
|
|
||||||
|
/// button procedure for the attachment up and down buttons
|
||||||
|
static function bp_attach_updown(ba) : ButtonControl
|
||||||
|
STRUCT WMButtonAction &ba
|
||||||
|
|
||||||
|
switch( ba.eventCode )
|
||||||
|
case 2: // mouse up
|
||||||
|
string logbook = GetUserData(ba.win, "", "logbook")
|
||||||
|
ControlInfo /w=$ba.win lb_attach
|
||||||
|
variable row = v_value
|
||||||
|
dfref df = $s_datafolder
|
||||||
|
wave /t /sdfr=df attach_list = $s_value
|
||||||
|
if (cmpstr(ba.ctrlName, "b_attach_up") == 0)
|
||||||
|
// up button
|
||||||
|
if (row >= 1)
|
||||||
|
move_attach_item(logbook, row, -1)
|
||||||
|
ListBox lb_attach, win=$ba.win, selRow=(row-1)
|
||||||
|
endif
|
||||||
|
else
|
||||||
|
// down button
|
||||||
|
if (row < DimSize(attach_list, 0) - 1)
|
||||||
|
move_attach_item(logbook, row, +1)
|
||||||
|
ListBox lb_attach, win=$ba.win, selRow=(row+1)
|
||||||
|
endif
|
||||||
|
endif
|
||||||
|
break
|
||||||
|
case -1: // control being killed
|
||||||
|
break
|
||||||
|
endswitch
|
||||||
|
|
||||||
|
return 0
|
||||||
end
|
end
|
||||||
|
|
||||||
/// button procedure for the Submit and Reply buttons
|
/// button procedure for the Submit and Reply buttons
|
||||||
@ -1259,7 +1510,7 @@ static function bp_submit(ba) : ButtonControl
|
|||||||
end
|
end
|
||||||
|
|
||||||
/// select top graph window for attachment
|
/// select top graph window for attachment
|
||||||
static function bp_select_attach_top(ba) : ButtonControl
|
static function bp_attach_top(ba) : ButtonControl
|
||||||
STRUCT WMButtonAction &ba
|
STRUCT WMButtonAction &ba
|
||||||
|
|
||||||
switch( ba.eventCode )
|
switch( ba.eventCode )
|
||||||
@ -1274,6 +1525,28 @@ static function bp_select_attach_top(ba) : ButtonControl
|
|||||||
return 0
|
return 0
|
||||||
end
|
end
|
||||||
|
|
||||||
|
/// select/deselect all graph windows for attachment
|
||||||
|
static function bp_attach_allnone(ba) : ButtonControl
|
||||||
|
STRUCT WMButtonAction &ba
|
||||||
|
|
||||||
|
switch( ba.eventCode )
|
||||||
|
case 2: // mouse up
|
||||||
|
string logbook = GetUserData(ba.win, "", "logbook")
|
||||||
|
dfref df_volatile = get_elog_df(logbook, kdfVolatile)
|
||||||
|
wave /sdfr=df_volatile attach_sel
|
||||||
|
if (cmpstr(ba.ctrlName, "b_attach_all") == 0)
|
||||||
|
attach_sel[][kAttachColSel] = attach_sel[p][kAttachColSel] | 16
|
||||||
|
else
|
||||||
|
attach_sel[][kAttachColSel] = attach_sel[p][kAttachColSel] & ~16
|
||||||
|
endif
|
||||||
|
break
|
||||||
|
case -1: // control being killed
|
||||||
|
break
|
||||||
|
endswitch
|
||||||
|
|
||||||
|
return 0
|
||||||
|
end
|
||||||
|
|
||||||
static function bp_attach(ba) : ButtonControl
|
static function bp_attach(ba) : ButtonControl
|
||||||
STRUCT WMButtonAction &ba
|
STRUCT WMButtonAction &ba
|
||||||
|
|
||||||
@ -1307,6 +1580,34 @@ static function bp_attach(ba) : ButtonControl
|
|||||||
return 0
|
return 0
|
||||||
end
|
end
|
||||||
|
|
||||||
|
static function bp_save_graphs(ba) : ButtonControl
|
||||||
|
STRUCT WMButtonAction &ba
|
||||||
|
|
||||||
|
switch( ba.eventCode )
|
||||||
|
case 2: // mouse up
|
||||||
|
string logbook = GetUserData(ba.win, "", "logbook")
|
||||||
|
string graphs = get_panel_graphs(ba.win)
|
||||||
|
variable ngraphs = ItemsInList(graphs, ";")
|
||||||
|
|
||||||
|
variable igraph
|
||||||
|
string sgraph
|
||||||
|
string graph_path
|
||||||
|
for (igraph = 0; igraph < ngraphs; igraph += 1)
|
||||||
|
sgraph = StringFromList(igraph, graphs, ";")
|
||||||
|
graph_path = create_graph_file(sgraph, igraph)
|
||||||
|
if (strlen(graph_path) > 0)
|
||||||
|
print graph_path
|
||||||
|
endif
|
||||||
|
endfor
|
||||||
|
|
||||||
|
break
|
||||||
|
case -1: // control being killed
|
||||||
|
break
|
||||||
|
endswitch
|
||||||
|
|
||||||
|
return 0
|
||||||
|
end
|
||||||
|
|
||||||
static function bp_clear(ba) : ButtonControl
|
static function bp_clear(ba) : ButtonControl
|
||||||
STRUCT WMButtonAction &ba
|
STRUCT WMButtonAction &ba
|
||||||
|
|
||||||
@ -1522,15 +1823,14 @@ end
|
|||||||
|
|
||||||
/// get the names of the graphs selected for attachment
|
/// get the names of the graphs selected for attachment
|
||||||
///
|
///
|
||||||
|
/// @param windowname panel window name
|
||||||
/// @returns a semicolon-separated list,
|
/// @returns a semicolon-separated list,
|
||||||
/// or the empty string if the selection is not valid.
|
/// or the empty string if the selection is not valid.
|
||||||
///
|
///
|
||||||
/// in the current version, the function returns at most one graph.
|
|
||||||
/// in future versions, the function may return more than one graph.
|
|
||||||
///
|
|
||||||
static function /s get_panel_graphs(windowname)
|
static function /s get_panel_graphs(windowname)
|
||||||
string windowname // panel window name
|
string windowname // panel window name
|
||||||
|
|
||||||
|
dfref savedf = getdatafolderdfr()
|
||||||
if (strlen(windowname) == 0)
|
if (strlen(windowname) == 0)
|
||||||
windowname = get_default_panel_name()
|
windowname = get_default_panel_name()
|
||||||
endif
|
endif
|
||||||
@ -1538,24 +1838,38 @@ static function /s get_panel_graphs(windowname)
|
|||||||
return ""
|
return ""
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ControlInfo /W=$windowname pm_attach
|
string logbook = GetUserData(windowname, "", "logbook")
|
||||||
|
dfref df_volatile = get_elog_df(logbook, kdfVolatile)
|
||||||
// menu item has the form: "title (name)"
|
wave /t /sdfr=df_volatile attach_list
|
||||||
string graphname = ReplaceString(")", StringFromList(ItemsInList(s_value, "(") - 1, s_value, "("), "")
|
wave /sdfr=df_volatile attach_sel
|
||||||
string graphs = ""
|
string graphs = ""
|
||||||
string windows = WinList(graphname, ";", "WIN:1")
|
string windows = ""
|
||||||
if (ItemsInList(windows) == 1)
|
string graphname
|
||||||
graphs = graphname
|
|
||||||
else
|
variable n = DimSize(attach_sel, 0)
|
||||||
graphs = ""
|
variable i
|
||||||
endif
|
for (i = 0; i < n; i += 1)
|
||||||
|
if (attach_sel[i][kAttachColSel] & 16)
|
||||||
|
graphname = attach_list[i][kAttachColName]
|
||||||
|
windows = WinList(graphname, ";", "WIN:1")
|
||||||
|
if (ItemsInList(windows) == 1)
|
||||||
|
graphs = AddListItem(graphname, graphs, ";", inf)
|
||||||
|
endif
|
||||||
|
endif
|
||||||
|
endfor
|
||||||
|
|
||||||
return graphs
|
return graphs
|
||||||
end
|
end
|
||||||
|
|
||||||
|
/// update selection of graphs for attachment
|
||||||
|
///
|
||||||
|
/// @param windowname panel window name. looks for default panel if empty.
|
||||||
|
///
|
||||||
|
/// @param graphs semicolon-separated list of names of graph windows to select for attachment.
|
||||||
|
///
|
||||||
static function /s set_panel_graphs(windowname, graphs)
|
static function /s set_panel_graphs(windowname, graphs)
|
||||||
string windowname // panel window name. looks for default panel if empty.
|
string windowname
|
||||||
string graphs // name of graph window to select for attachment.
|
string graphs
|
||||||
|
|
||||||
if (strlen(windowname) == 0)
|
if (strlen(windowname) == 0)
|
||||||
windowname = get_default_panel_name()
|
windowname = get_default_panel_name()
|
||||||
@ -1564,23 +1878,21 @@ static function /s set_panel_graphs(windowname, graphs)
|
|||||||
return ""
|
return ""
|
||||||
endif
|
endif
|
||||||
|
|
||||||
// the panel supports only one graph
|
string logbook = GetUserData(windowname, "", "logbook")
|
||||||
string graph = StringFromList(0, graphs, ";")
|
update_attach_items(logbook)
|
||||||
|
dfref df_volatile = get_elog_df(logbook, kdfVolatile)
|
||||||
string items = pm_list_attach_items()
|
wave /t /sdfr=df_volatile attach_list
|
||||||
string item
|
wave /sdfr=df_volatile attach_sel
|
||||||
string itemname
|
|
||||||
variable nitems = ItemsInList(items, ";")
|
variable n = DimSize(attach_sel, 0)
|
||||||
variable iitem
|
variable i
|
||||||
for (iitem = 0; iitem < nitems; iitem += 1)
|
string graphname
|
||||||
item = StringFromList(iitem, items, ";")
|
for (i = 0; i < n; i += 1)
|
||||||
itemname = ReplaceString(")", StringFromList(ItemsInList(item, "(") - 1, item, "("), "")
|
graphname = attach_list[i][kAttachColName]
|
||||||
if (cmpstr(graph, itemname) == 0)
|
if (WhichListItem(graphname, graphs)>= 0)
|
||||||
iitem += 1
|
attach_sel[i][kAttachColSel] = 48
|
||||||
PopupMenu pm_attach mode=iitem, win=$windowname
|
else
|
||||||
break
|
attach_sel[i][kAttachColSel] = 32
|
||||||
endif
|
endif
|
||||||
endfor
|
endfor
|
||||||
|
|
||||||
return graph
|
|
||||||
end
|
end
|
@ -454,7 +454,7 @@ function Au4f(w, x): fitfunc
|
|||||||
vc1 = w[ip] / sqrt(pi) * vc2
|
vc1 = w[ip] / sqrt(pi) * vc2
|
||||||
vc3 = w[ip+1]
|
vc3 = w[ip+1]
|
||||||
vc4 = vc2 * w[ip+2] / 2
|
vc4 = vc2 * w[ip+2] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
endfor
|
endfor
|
||||||
|
|
||||||
return v
|
return v
|
||||||
@ -491,25 +491,25 @@ function Au4f_2p2(w, x): fitfunc
|
|||||||
vc1 = w[3] / sqrt(pi) * vc2
|
vc1 = w[3] / sqrt(pi) * vc2
|
||||||
vc3 = w[4]
|
vc3 = w[4]
|
||||||
vc4 = vc2 * w[5] / 2
|
vc4 = vc2 * w[5] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
|
|
||||||
// 5/2 surface
|
// 5/2 surface
|
||||||
vc1 = w[3] / sqrt(pi) * vc2 * w[9]
|
vc1 = w[3] / sqrt(pi) * vc2 * w[9]
|
||||||
vc3 = w[4] + w[10]
|
vc3 = w[4] + w[10]
|
||||||
vc4 = vc2 * w[5] / 2
|
vc4 = vc2 * w[5] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
|
|
||||||
// 7/2 bulk
|
// 7/2 bulk
|
||||||
vc1 = w[6] / sqrt(pi) * vc2
|
vc1 = w[6] / sqrt(pi) * vc2
|
||||||
vc3 = w[7]
|
vc3 = w[7]
|
||||||
vc4 = vc2 * w[8] / 2
|
vc4 = vc2 * w[8] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
|
|
||||||
// 7/2 surface
|
// 7/2 surface
|
||||||
vc1 = w[6] / sqrt(pi) * vc2 * w[9]
|
vc1 = w[6] / sqrt(pi) * vc2 * w[9]
|
||||||
vc3 = w[7] + w[10]
|
vc3 = w[7] + w[10]
|
||||||
vc4 = vc2 * w[8] / 2
|
vc4 = vc2 * w[8] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
|
|
||||||
return v
|
return v
|
||||||
|
|
||||||
@ -578,37 +578,37 @@ function Au4f_2p3(w, x): fitfunc
|
|||||||
vc1 = w[3] / sqrt(pi) * vc2
|
vc1 = w[3] / sqrt(pi) * vc2
|
||||||
vc3 = w[4]
|
vc3 = w[4]
|
||||||
vc4 = vc2 * w[5] / 2
|
vc4 = vc2 * w[5] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
|
|
||||||
// 5/2 surface
|
// 5/2 surface
|
||||||
vc1 = w[3] / sqrt(pi) * vc2 * w[9]
|
vc1 = w[3] / sqrt(pi) * vc2 * w[9]
|
||||||
vc3 = w[4] + w[10]
|
vc3 = w[4] + w[10]
|
||||||
vc4 = vc2 * w[5] / 2
|
vc4 = vc2 * w[5] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
|
|
||||||
// 5/2 2nd layer
|
// 5/2 2nd layer
|
||||||
vc1 = w[3] / sqrt(pi) * vc2 * w[11]
|
vc1 = w[3] / sqrt(pi) * vc2 * w[11]
|
||||||
vc3 = w[4] + w[12]
|
vc3 = w[4] + w[12]
|
||||||
vc4 = vc2 * w[5] / 2
|
vc4 = vc2 * w[5] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
|
|
||||||
// 7/2 bulk
|
// 7/2 bulk
|
||||||
vc1 = w[6] / sqrt(pi) * vc2
|
vc1 = w[6] / sqrt(pi) * vc2
|
||||||
vc3 = w[7]
|
vc3 = w[7]
|
||||||
vc4 = vc2 * w[8] / 2
|
vc4 = vc2 * w[8] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
|
|
||||||
// 7/2 surface
|
// 7/2 surface
|
||||||
vc1 = w[6] / sqrt(pi) * vc2 * w[9]
|
vc1 = w[6] / sqrt(pi) * vc2 * w[9]
|
||||||
vc3 = w[7] + w[10]
|
vc3 = w[7] + w[10]
|
||||||
vc4 = vc2 * w[8] / 2
|
vc4 = vc2 * w[8] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
|
|
||||||
// 7/2 2nd layer
|
// 7/2 2nd layer
|
||||||
vc1 = w[6] / sqrt(pi) * vc2 * w[11]
|
vc1 = w[6] / sqrt(pi) * vc2 * w[11]
|
||||||
vc3 = w[7] + w[12]
|
vc3 = w[7] + w[12]
|
||||||
vc4 = vc2 * w[8] / 2
|
vc4 = vc2 * w[8] / 2
|
||||||
v += vc1 * Voigt(vc2 * (x - vc3), vc4)
|
v += vc1 * VoigtFunc(vc2 * (x - vc3), vc4)
|
||||||
|
|
||||||
return v
|
return v
|
||||||
|
|
||||||
|
900
pearl/pearl-matrix-import.ipf
Normal file
900
pearl/pearl-matrix-import.ipf
Normal file
@ -0,0 +1,900 @@
|
|||||||
|
#pragma rtGlobals=3
|
||||||
|
#pragma version = 1.00
|
||||||
|
#pragma IgorVersion = 6.36
|
||||||
|
#pragma ModuleName = PearlMatrixImport
|
||||||
|
|
||||||
|
// author: matthias.muntwiler@psi.ch
|
||||||
|
// Copyright (c) 2016 Paul Scherrer Institut
|
||||||
|
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
|
/// @file
|
||||||
|
/// @brief 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, matthias.muntwiler@psi.ch
|
||||||
|
///
|
||||||
|
/// @copyright 2016 Paul Scherrer Institut @n
|
||||||
|
/// Licensed under the Apache License, Version 2.0 (the "License"); @n
|
||||||
|
/// you may not use this file except in compliance with the License. @n
|
||||||
|
/// You may obtain a copy of the License at
|
||||||
|
/// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
|
/// @namespace PearlMatrixImport
|
||||||
|
/// @brief data file import for omicron matrix (STM) files
|
||||||
|
///
|
||||||
|
/// PearlMatrixImport is declared in @ref pearl-matrix-import.ipf.
|
||||||
|
|
||||||
|
static strconstant package_name = "pearl_matrix_import"
|
||||||
|
static strconstant package_path = "root:packages:pearl_matrix_import:"
|
||||||
|
|
||||||
|
static strconstant ks_filematch_mtrx = "*_mtrx"
|
||||||
|
|
||||||
|
/// initialize the package data folder.
|
||||||
|
///
|
||||||
|
///
|
||||||
|
static function init_package()
|
||||||
|
|
||||||
|
dfref savedf = getdatafolderdfr()
|
||||||
|
|
||||||
|
setdatafolder root:
|
||||||
|
newdatafolder /o/s packages
|
||||||
|
newdatafolder /o/s $package_name
|
||||||
|
|
||||||
|
variable /g loglevel = 3
|
||||||
|
string /g dataFilePath = ""
|
||||||
|
string /g resultFilePath = ""
|
||||||
|
variable /g runCycle = 0
|
||||||
|
variable /g scanCycle = 0
|
||||||
|
string /g channelName = ""
|
||||||
|
variable /g brickletID = 0
|
||||||
|
variable /g V_MatrixFileReaderOverwrite = 1
|
||||||
|
variable /g V_MatrixFileReaderFolder = 0
|
||||||
|
variable /g V_MatrixFileReaderDouble = 0
|
||||||
|
|
||||||
|
setdatafolder savedf
|
||||||
|
return 0
|
||||||
|
end
|
||||||
|
|
||||||
|
/// check that the package data folder exists
|
||||||
|
///
|
||||||
|
/// initialize the package if the folder does not exist.
|
||||||
|
///
|
||||||
|
static function check_package_folder()
|
||||||
|
dfref df_pack = $(package_path)
|
||||||
|
if (DataFolderRefStatus(df_pack))
|
||||||
|
svar /sdfr=df_pack /z resultFilePath
|
||||||
|
if (!svar_exists(resultFilePath))
|
||||||
|
init_package()
|
||||||
|
endif
|
||||||
|
else
|
||||||
|
init_package()
|
||||||
|
endif
|
||||||
|
end
|
||||||
|
|
||||||
|
/// initialize the package and reload preferences after an experiment is loaded.
|
||||||
|
static function AfterFileOpenHook(refNum,file,pathName,type,creator,kind)
|
||||||
|
Variable refNum,kind
|
||||||
|
String file,pathName,type,creator
|
||||||
|
if( (kind >= 1) && (kind <= 2))
|
||||||
|
init_package()
|
||||||
|
//load_prefs()
|
||||||
|
endif
|
||||||
|
return 0
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
static function BeforeFileOpenHook(refNum,fileName,path,type,creator,kind)
|
||||||
|
Variable refNum,kind
|
||||||
|
String fileName,path,type,creator
|
||||||
|
|
||||||
|
Variable handledOpen = 0
|
||||||
|
if (StringMatch(fileName, ks_filematch_mtrx))
|
||||||
|
setdatafolder root:
|
||||||
|
newdatafolder /o /s matrix
|
||||||
|
mtrx_load_preview("matrix", path, fileName)
|
||||||
|
handledOpen = 1
|
||||||
|
endif
|
||||||
|
return handledOpen
|
||||||
|
End
|
||||||
|
|
||||||
|
/// generate elog message from bricklet metadata
|
||||||
|
///
|
||||||
|
/// @param metadata two-column text wave
|
||||||
|
///
|
||||||
|
function /s matrix_format_elog_message(metadata)
|
||||||
|
wave /t metadata
|
||||||
|
|
||||||
|
string key
|
||||||
|
string value
|
||||||
|
variable nkeys = dimsize(metadata, 0)
|
||||||
|
variable ikey
|
||||||
|
string message_keys
|
||||||
|
message_keys = "resultFileName;sampleName;channelName;"
|
||||||
|
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;"
|
||||||
|
message_keys += "GapVoltageControl.Voltage.value;GapVoltageControl.Voltage.unit;"
|
||||||
|
message_keys += "Regulator.Loop_Gain_1_I.value;Regulator.Loop_Gain_1_I.unit;Regulator.Setpoint_1.value;Regulator.Setpoint_1.unit;"
|
||||||
|
message_keys += "Spectroscopy.Device_1_Start.value;Spectroscopy.Device_1_Start.unit;Spectroscopy.Spectroscopy_Mode.value;"
|
||||||
|
string message
|
||||||
|
|
||||||
|
message_keys = ""
|
||||||
|
for (ikey = 0; ikey < nkeys; ikey += 1)
|
||||||
|
key = metadata[ikey][0]
|
||||||
|
value = metadata[ikey][1]
|
||||||
|
if (WhichListItem(key, message_keys) >= 0)
|
||||||
|
message += key + " = " + value + "\r"
|
||||||
|
endif
|
||||||
|
endfor
|
||||||
|
end
|
||||||
|
|
||||||
|
function matrix_preview_2d(data, metadata)
|
||||||
|
wave data
|
||||||
|
wave /t metadata
|
||||||
|
|
||||||
|
Display
|
||||||
|
AppendImage data
|
||||||
|
ModifyImage data ctab= {*,*,Mud,0}
|
||||||
|
ModifyGraph margin(left)=30,margin(bottom)=30,margin(top)=5,margin(right)=5,height={Plan,1,left,bottom}
|
||||||
|
ModifyGraph mirror=2
|
||||||
|
ModifyGraph nticks=3
|
||||||
|
ModifyGraph axThick=0.5
|
||||||
|
ModifyGraph btLen=4
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param filename name of a file in the directory specified by the pearl_explorer_filepath path object.
|
||||||
|
///
|
||||||
|
/// @return wave reference of the preview image
|
||||||
|
///
|
||||||
|
static function /wave preview_matrix_file(filename)
|
||||||
|
string filename
|
||||||
|
|
||||||
|
dfref saveDF = GetDataFolderDFR()
|
||||||
|
setdatafolder $package_path
|
||||||
|
svar s_preview_file
|
||||||
|
svar s_preview_source
|
||||||
|
mtrx_load_preview("preview_image", "pearl_explorer_filepath", filename)
|
||||||
|
s_preview_file = filename
|
||||||
|
s_preview_source = ""
|
||||||
|
wave /z preview_image
|
||||||
|
|
||||||
|
svar /z s_file_info
|
||||||
|
if (! svar_exists(s_file_info))
|
||||||
|
string /g s_file_info
|
||||||
|
endif
|
||||||
|
if (strlen(s_preview_file) > 0)
|
||||||
|
s_file_info = mtrx_load_info("pearl_explorer_filepath", filename)
|
||||||
|
else
|
||||||
|
s_file_info = ""
|
||||||
|
endif
|
||||||
|
|
||||||
|
setdatafolder saveDF
|
||||||
|
return preview_image
|
||||||
|
end
|
||||||
|
|
||||||
|
/// from matrixfilereader help
|
||||||
|
Structure errorCode
|
||||||
|
int32 SUCCESS
|
||||||
|
int32 UNKNOWN_ERROR
|
||||||
|
int32 ALREADY_FILE_OPEN
|
||||||
|
int32 EMPTY_RESULTFILE
|
||||||
|
int32 FILE_NOT_READABLE
|
||||||
|
int32 NO_NEW_BRICKLETS
|
||||||
|
int32 WRONG_PARAMETER
|
||||||
|
int32 INTERNAL_ERROR_CONVERTING_DATA
|
||||||
|
int32 NO_FILE_OPEN
|
||||||
|
int32 INVALID_RANGE
|
||||||
|
int32 WAVE_EXIST
|
||||||
|
EndStructure
|
||||||
|
|
||||||
|
/// from matrixfilereader help
|
||||||
|
static Function initStruct(errorCode)
|
||||||
|
Struct errorCode &errorCode
|
||||||
|
|
||||||
|
errorCode.SUCCESS =0
|
||||||
|
errorCode.UNKNOWN_ERROR=10001
|
||||||
|
errorCode.ALREADY_FILE_OPEN=10002
|
||||||
|
errorCode.EMPTY_RESULTFILE=10004
|
||||||
|
errorCode.FILE_NOT_READABLE=10008
|
||||||
|
errorCode.NO_NEW_BRICKLETS=10016
|
||||||
|
errorCode.WRONG_PARAMETER=10032
|
||||||
|
errorCode.INTERNAL_ERROR_CONVERTING_DATA=10064
|
||||||
|
errorCode.NO_FILE_OPEN=10128
|
||||||
|
errorCode.INVALID_RANGE=10256
|
||||||
|
errorCode.WAVE_EXIST=10512
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
/// load all data from a Matrix data file.
|
||||||
|
///
|
||||||
|
function mtrx_load_all()
|
||||||
|
|
||||||
|
struct errorCode errorCode
|
||||||
|
initStruct(errorCode)
|
||||||
|
|
||||||
|
#if exists("MFR_OpenResultFile")
|
||||||
|
MFR_OpenResultFile
|
||||||
|
if(V_flag != errorCode.SUCCESS)
|
||||||
|
MFR_GetXOPErrorMessage
|
||||||
|
return -1
|
||||||
|
endif
|
||||||
|
|
||||||
|
MFR_GetBrickletData
|
||||||
|
if(V_flag != errorCode.SUCCESS)
|
||||||
|
MFR_GetXOPErrorMessage
|
||||||
|
return -1
|
||||||
|
endif
|
||||||
|
|
||||||
|
MFR_GetBrickletMetaData
|
||||||
|
if(V_flag != errorCode.SUCCESS)
|
||||||
|
MFR_GetXOPErrorMessage
|
||||||
|
return -1
|
||||||
|
endif
|
||||||
|
|
||||||
|
return 0
|
||||||
|
#else
|
||||||
|
return -1
|
||||||
|
#endif
|
||||||
|
end
|
||||||
|
|
||||||
|
/// parse matrix file names
|
||||||
|
///
|
||||||
|
/// parse matrix file names for result name, run cycle, scan cycle, and channel.
|
||||||
|
///
|
||||||
|
/// @param fileName matrix result or data file name (without path).
|
||||||
|
///
|
||||||
|
/// @param 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.
|
||||||
|
///
|
||||||
|
/// @param runCycle (out) run cycle number. necessary to look up the bricklet ID.
|
||||||
|
///
|
||||||
|
/// @param scanCycle (out) scan cycle number. necessary to look up the bricklet ID.
|
||||||
|
///
|
||||||
|
/// @param channel (out) channel name.
|
||||||
|
///
|
||||||
|
/// @return file type
|
||||||
|
/// @arg 0 result file (logbook)
|
||||||
|
/// @arg 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.
|
||||||
|
///
|
||||||
|
function mtrx_parse_filename(fileName, resultFile, runCycle, scanCycle, channel)
|
||||||
|
string fileName
|
||||||
|
string &resultFile
|
||||||
|
variable &runCycle
|
||||||
|
variable &scanCycle
|
||||||
|
string &channel
|
||||||
|
|
||||||
|
variable fileType = 0
|
||||||
|
resultFile = ""
|
||||||
|
channel = ""
|
||||||
|
runCycle = 0
|
||||||
|
scanCycle = 0
|
||||||
|
|
||||||
|
string regexp = ""
|
||||||
|
string index1 = ""
|
||||||
|
string index2 = ""
|
||||||
|
string extension = ""
|
||||||
|
|
||||||
|
if (StringMatch(fileName, "*.mtrx"))
|
||||||
|
regexp = "(.+)_([[:digit:]]+)\.(.+)"
|
||||||
|
SplitString /E=regexp fileName, resultFile, index1, extension
|
||||||
|
fileType = 0
|
||||||
|
else
|
||||||
|
regexp = "(.+)--([[:digit:]]+)_([[:digit:]]+)\.((.+)_mtrx)"
|
||||||
|
SplitString /E=regexp fileName, resultFile, index1, index2, extension, channel
|
||||||
|
fileType = 1
|
||||||
|
runCycle = str2num(index1)
|
||||||
|
scanCycle = str2num(index2)
|
||||||
|
endif
|
||||||
|
|
||||||
|
return fileType
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
function /s mtrx_split_filename(fileName, prefix, datepart, timepart)
|
||||||
|
string fileName
|
||||||
|
string &prefix
|
||||||
|
string &datepart
|
||||||
|
string &timepart
|
||||||
|
|
||||||
|
string regexp
|
||||||
|
regexp = "([[:alpha:][:digit:]]+)[-_]([[:alpha:][:digit:]]+)[-_]([[:alpha:][:digit:]]+)[-_].+"
|
||||||
|
SplitString /E=regexp fileName, prefix, datepart, timepart
|
||||||
|
return datepart
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param fileName name of the result or data file.
|
||||||
|
///
|
||||||
|
/// @param df_base (optional) base data folder.
|
||||||
|
/// default: current folder.
|
||||||
|
///
|
||||||
|
/// @return reference of the newly created or existing data folder.
|
||||||
|
///
|
||||||
|
function /df mtrx_create_folder(fileName, [df_base])
|
||||||
|
string fileName
|
||||||
|
dfref df_base
|
||||||
|
|
||||||
|
if (ParamIsDefault(df_base))
|
||||||
|
df_base = GetDataFolderDFR()
|
||||||
|
endif
|
||||||
|
|
||||||
|
string prefix
|
||||||
|
string datepart
|
||||||
|
string timepart
|
||||||
|
string folderName
|
||||||
|
|
||||||
|
mtrx_split_filename(fileName, prefix, datepart, timepart)
|
||||||
|
folderName = "mtrx_" + datepart + "_" + timepart
|
||||||
|
folderName = CleanupName(folderName, 0)
|
||||||
|
|
||||||
|
dfref df_save = GetDataFolderDFR()
|
||||||
|
setdatafolder root:
|
||||||
|
newdatafolder /o /s $foldername
|
||||||
|
dfref df = GetDataFolderDFR()
|
||||||
|
|
||||||
|
setdatafolder df_save
|
||||||
|
return df
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param df_base (optional) base data folder.
|
||||||
|
/// default: current folder.
|
||||||
|
///
|
||||||
|
/// @param runCycle (optional) run cycle number. must be >= 1.
|
||||||
|
/// default: from last mtrx_open_file call.
|
||||||
|
///
|
||||||
|
/// @param scanCycle (optional) scan cycle number. must be >= 1.
|
||||||
|
/// default: from last mtrx_open_file call.
|
||||||
|
///
|
||||||
|
/// @return reference of the newly created or existing data folder.
|
||||||
|
///
|
||||||
|
function /df mtrx_get_cycle_folder([df_base, runCycle, scanCycle])
|
||||||
|
dfref df_base
|
||||||
|
variable runCycle
|
||||||
|
variable scanCycle
|
||||||
|
|
||||||
|
dfref df_save = GetDataFolderDFR()
|
||||||
|
dfref df_pack = $(package_path)
|
||||||
|
if (ParamIsDefault(df_base))
|
||||||
|
df_base = GetDataFolderDFR()
|
||||||
|
endif
|
||||||
|
if (ParamIsDefault(runCycle))
|
||||||
|
nvar /sdfr=df_pack defRunCycle = runCycle
|
||||||
|
runCycle = defRunCycle
|
||||||
|
endif
|
||||||
|
if (ParamIsDefault(scanCycle))
|
||||||
|
nvar /sdfr=df_pack defScanCycle = scanCycle
|
||||||
|
scanCycle = defScanCycle
|
||||||
|
endif
|
||||||
|
|
||||||
|
string dfname
|
||||||
|
if ((runCycle >= 1) && (scanCycle >= 1))
|
||||||
|
sprintf dfname, "r%us%u", runCycle, scanCycle
|
||||||
|
setdatafolder df_base
|
||||||
|
dfref df = $dfname
|
||||||
|
if (DataFolderRefStatus(df) == 0)
|
||||||
|
newdatafolder $dfname
|
||||||
|
dfref df = $dfname
|
||||||
|
endif
|
||||||
|
else
|
||||||
|
dfref df = df_base
|
||||||
|
endif
|
||||||
|
|
||||||
|
setdatafolder df_save
|
||||||
|
return df
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param resultFile base name of result file without chain link number and extension.
|
||||||
|
/// as returned by mtrx_parse_filename.
|
||||||
|
///
|
||||||
|
/// @param runCycle requested run cycle.
|
||||||
|
/// 0 = first available.
|
||||||
|
///
|
||||||
|
/// @param scanCycle requested scan cycle.
|
||||||
|
/// 0 = first available.
|
||||||
|
///
|
||||||
|
/// @param channel channel name. for example: "I", "Z", "Aux(V)", etc.
|
||||||
|
/// empty string: first available.
|
||||||
|
///
|
||||||
|
/// @return bricklet ID, or -1 if an error occurred.
|
||||||
|
///
|
||||||
|
function mtrx_file_brickletID(resultFile, runCycle, scanCycle, channel)
|
||||||
|
string resultFile
|
||||||
|
variable runCycle
|
||||||
|
variable scanCycle
|
||||||
|
string channel
|
||||||
|
|
||||||
|
dfref df_overview = NewFreeDataFolder()
|
||||||
|
variable link = 1
|
||||||
|
variable id = -1
|
||||||
|
variable idx = 0
|
||||||
|
|
||||||
|
string resultFileName
|
||||||
|
#if exists("MFR_OpenResultFile")
|
||||||
|
struct errorCode errorCode
|
||||||
|
initStruct(errorCode)
|
||||||
|
do
|
||||||
|
sprintf resultFileName, "%s_%04u.mtrx", resultFile, link
|
||||||
|
MFR_OpenResultFile /K resultFileName
|
||||||
|
if(V_flag != errorCode.SUCCESS)
|
||||||
|
return -1
|
||||||
|
endif
|
||||||
|
MFR_CreateOverviewTable /DEST=df_overview
|
||||||
|
// dimension labels are: brickletID, scanCycleCount, runCycleCount, sequenceID, dimension, channelName
|
||||||
|
wave /t /sdfr=df_overview overviewTable
|
||||||
|
make /n=(dimsize(overviewTable, 0)) /i /u /free runcycles, scancycles, ids, match
|
||||||
|
make /n=(dimsize(overviewTable, 0)) /t /free channels
|
||||||
|
ids = str2num(overviewtable[p][%brickletID])
|
||||||
|
if (runcycle > 0)
|
||||||
|
runcycles = str2num(overviewtable[p][%runCycleCount])
|
||||||
|
else
|
||||||
|
runcycles = runcycle
|
||||||
|
endif
|
||||||
|
if (scancycle > 0)
|
||||||
|
scancycles = str2num(overviewtable[p][%scanCycleCount])
|
||||||
|
else
|
||||||
|
scancycles = scancycle
|
||||||
|
endif
|
||||||
|
if (strlen(channel) > 0)
|
||||||
|
channels = overviewTable[p][%channelName]
|
||||||
|
else
|
||||||
|
channels = channel
|
||||||
|
endif
|
||||||
|
Extract /FREE ids, match_ids, (scancycles == scanCycle) && (runcycles == runCycle) && (cmpstr(channels, channel) == 0)
|
||||||
|
if (numpnts(match_ids) > 0)
|
||||||
|
id = match_ids[0]
|
||||||
|
else
|
||||||
|
link += 1
|
||||||
|
endif
|
||||||
|
while (id < 0)
|
||||||
|
#endif
|
||||||
|
return id
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param pathName igor path name or empty string.
|
||||||
|
///
|
||||||
|
/// @param fileName file name, with or without path, or empty string.
|
||||||
|
///
|
||||||
|
/// @return file type
|
||||||
|
/// @arg 0 result file (logbook)
|
||||||
|
/// @arg 1 result data file (bricklet)
|
||||||
|
/// @arg -1 error, no data loaded
|
||||||
|
/// @arg -2 matrixfilereader.xop not installed
|
||||||
|
///
|
||||||
|
function mtrx_open_file(pathName, fileNameOrPath)
|
||||||
|
string pathName
|
||||||
|
string fileNameOrPath
|
||||||
|
|
||||||
|
check_package_folder()
|
||||||
|
dfref df_save = GetDataFolderDFR()
|
||||||
|
dfref df_pack = $(package_path)
|
||||||
|
svar /sdfr=df_pack dataFilePath
|
||||||
|
svar /sdfr=df_pack resultFilePath
|
||||||
|
nvar /sdfr=df_pack runCycle
|
||||||
|
nvar /sdfr=df_pack scanCycle
|
||||||
|
svar /sdfr=df_pack channelName
|
||||||
|
nvar /sdfr=df_pack brickletID
|
||||||
|
|
||||||
|
string loc_resultFileName
|
||||||
|
string loc_resultFilePath
|
||||||
|
variable loc_runCycle
|
||||||
|
variable loc_scanCycle
|
||||||
|
string loc_channelName
|
||||||
|
|
||||||
|
// make sure we have a valid and complete file path
|
||||||
|
GetFileFolderInfo /P=$pathName /Q /Z=2 fileNameOrPath
|
||||||
|
string filePath
|
||||||
|
if ((v_flag == 0) && (v_isFile))
|
||||||
|
filePath = s_path
|
||||||
|
else
|
||||||
|
return -1
|
||||||
|
endif
|
||||||
|
|
||||||
|
// get base file name
|
||||||
|
string fileName
|
||||||
|
string fileDir
|
||||||
|
string baseFileName
|
||||||
|
variable fileType
|
||||||
|
fileName = ParseFilePath(0, filePath, ":", 1, 0)
|
||||||
|
fileDir = ParseFilePath(1, filePath, ":", 1, 0)
|
||||||
|
fileType = mtrx_parse_filename(fileName, baseFileName, loc_runCycle, loc_scanCycle, loc_channelName)
|
||||||
|
|
||||||
|
variable link = 1
|
||||||
|
variable id = -1
|
||||||
|
variable result = -1
|
||||||
|
variable using_cache = 0
|
||||||
|
|
||||||
|
struct errorCode errorCode
|
||||||
|
initStruct(errorCode)
|
||||||
|
do
|
||||||
|
sprintf loc_resultFileName, "%s_%04u.mtrx", baseFileName, link
|
||||||
|
loc_resultFilePath = fileDir + loc_resultFileName
|
||||||
|
#if exists("MFR_OpenResultFile")
|
||||||
|
if ((strlen(resultFilePath) == 0) || (cmpstr(loc_resultFilePath, resultFilePath) != 0))
|
||||||
|
MFR_OpenResultFile /K loc_resultFilePath
|
||||||
|
if(V_flag != errorCode.SUCCESS)
|
||||||
|
MFR_GetXOPErrorMessage
|
||||||
|
result = -1
|
||||||
|
break
|
||||||
|
endif
|
||||||
|
resultFilePath = loc_resultFilePath
|
||||||
|
if (fileType == 1)
|
||||||
|
dataFilePath = filePath
|
||||||
|
else
|
||||||
|
dataFilePath = ""
|
||||||
|
endif
|
||||||
|
runCycle = 0
|
||||||
|
scanCycle = 0
|
||||||
|
channelName = ""
|
||||||
|
brickletID = 0
|
||||||
|
MFR_CreateOverviewTable /DEST=df_pack
|
||||||
|
if(V_flag != errorCode.SUCCESS)
|
||||||
|
MFR_GetXOPErrorMessage
|
||||||
|
result = -1
|
||||||
|
break
|
||||||
|
endif
|
||||||
|
using_cache = 0
|
||||||
|
else
|
||||||
|
using_cache = 1
|
||||||
|
endif
|
||||||
|
#else
|
||||||
|
print "matrixfilereader.xop not installed"
|
||||||
|
result = -2
|
||||||
|
break
|
||||||
|
#endif
|
||||||
|
// dimension labels are: brickletID, scanCycleCount, runCycleCount, sequenceID, dimension, channelName
|
||||||
|
wave /t /sdfr=df_pack overviewTable
|
||||||
|
make /n=(dimsize(overviewTable, 0)) /i /u /o df_pack:runCycles, df_pack:scanCycles, df_pack:ids
|
||||||
|
make /n=(dimsize(overviewTable, 0)) /t /o df_pack:channels
|
||||||
|
wave /sdfr=df_pack ids, runCycles, scanCycles
|
||||||
|
wave /t /sdfr=df_pack channels
|
||||||
|
ids = str2num(overviewtable[p][%brickletID])
|
||||||
|
runCycles = str2num(overviewtable[p][%runCycleCount])
|
||||||
|
scanCycles = str2num(overviewtable[p][%scanCycleCount])
|
||||||
|
channels = overviewTable[p][%channelName]
|
||||||
|
result = fileType
|
||||||
|
|
||||||
|
// if a data file is opened, make sure we found the right result file
|
||||||
|
if ((loc_runCycle > 0) && (loc_scanCycle > 0))
|
||||||
|
Extract /FREE ids, match_ids, (runCycles == loc_runCycle) && (scanCycles == loc_scanCycle) && (cmpstr(channels, loc_channelName) == 0)
|
||||||
|
if (numpnts(match_ids) > 0)
|
||||||
|
id = match_ids[0]
|
||||||
|
runCycle = loc_runCycle
|
||||||
|
scanCycle = loc_scanCycle
|
||||||
|
channelName = loc_channelName
|
||||||
|
brickletID = id
|
||||||
|
break
|
||||||
|
elseif (using_cache)
|
||||||
|
resultFilePath = ""
|
||||||
|
else
|
||||||
|
link += 1
|
||||||
|
endif
|
||||||
|
else
|
||||||
|
break
|
||||||
|
endif
|
||||||
|
while (id < 0)
|
||||||
|
|
||||||
|
return result
|
||||||
|
end
|
||||||
|
|
||||||
|
/// load a preview image from a Matrix data file.
|
||||||
|
///
|
||||||
|
/// the data wave is loaded into the current data folder.
|
||||||
|
///
|
||||||
|
/// @param destName destination wave name. the wave is created in the current data folder.
|
||||||
|
///
|
||||||
|
/// @param pathName igor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
|
||||||
|
///
|
||||||
|
/// @param fileName if 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.
|
||||||
|
///
|
||||||
|
/// @param 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;"
|
||||||
|
///
|
||||||
|
/// @return semicolon-separated list of loaded waves including partial path from current data folder.
|
||||||
|
///
|
||||||
|
function /s mtrx_load_preview(destName, pathName, fileName, [traces])
|
||||||
|
string destName
|
||||||
|
string pathName
|
||||||
|
string fileName
|
||||||
|
string traces
|
||||||
|
|
||||||
|
if (ParamIsDefault(traces))
|
||||||
|
traces = "*Up;*Down;*ReUp;*ReDown;"
|
||||||
|
endif
|
||||||
|
|
||||||
|
dfref df_save = GetDataFolderDFR()
|
||||||
|
|
||||||
|
string datanames = ""
|
||||||
|
string datapaths = ""
|
||||||
|
variable filestatus = mtrx_open_file(pathName, fileName)
|
||||||
|
if (filestatus != 1)
|
||||||
|
return ""
|
||||||
|
endif
|
||||||
|
|
||||||
|
dfref df_pack = $(package_path)
|
||||||
|
svar /sdfr=df_pack dataFilePath
|
||||||
|
svar /sdfr=df_pack resultFilePath
|
||||||
|
nvar /sdfr=df_pack runCycle
|
||||||
|
nvar /sdfr=df_pack scanCycle
|
||||||
|
svar /sdfr=df_pack channelName
|
||||||
|
nvar /sdfr=df_pack brickletID
|
||||||
|
|
||||||
|
#if exists("MFR_OpenResultFile")
|
||||||
|
dfref df_data = df_save
|
||||||
|
variable /g df_data:V_MatrixFileReaderOverwrite = 1
|
||||||
|
variable /g df_data:V_MatrixFileReaderFolder = 0
|
||||||
|
variable /g df_data:V_MatrixFileReaderDouble = 0
|
||||||
|
struct errorCode errorCode
|
||||||
|
initStruct(errorCode)
|
||||||
|
MFR_GetBrickletData /N=destName /R=(brickletID) /S=2 /DEST=df_data
|
||||||
|
if(V_flag == errorCode.SUCCESS)
|
||||||
|
datanames = S_waveNames
|
||||||
|
variable i
|
||||||
|
variable n = ItemsInList(datanames)
|
||||||
|
string s
|
||||||
|
s = StringFromList(0, datanames)
|
||||||
|
wave data = $s
|
||||||
|
mtrx_scale_dataset(data)
|
||||||
|
if (WaveDims(data) == 2)
|
||||||
|
subtract_line_bg(data)
|
||||||
|
endif
|
||||||
|
datapaths = AddListItem(GetWavesDataFolder(data, 4), datapaths, ";", inf)
|
||||||
|
for (i = 1; i < n; i += 1)
|
||||||
|
s = StringFromList(i, datanames)
|
||||||
|
killwaves /z $s
|
||||||
|
endfor
|
||||||
|
else
|
||||||
|
MFR_GetXOPErrorMessage
|
||||||
|
endif
|
||||||
|
//MFR_GetBrickletMetaData /N=ANickName /R=(brickletID) // /DEST=dfref
|
||||||
|
#else
|
||||||
|
print "matrixfilereader.xop not installed"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
setdatafolder df_save
|
||||||
|
return datapaths
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param pathName igor symbolic path name. can be empty if the path is specified in FileName or a dialog box should be displayed
|
||||||
|
///
|
||||||
|
/// @param fileName if 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.
|
||||||
|
///
|
||||||
|
/// @param 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;"
|
||||||
|
///
|
||||||
|
/// @return semicolon-separated list of loaded waves including partial path from current data folder.
|
||||||
|
///
|
||||||
|
function /s mtrx_load_file(pathName, fileName, [traces])
|
||||||
|
string pathName
|
||||||
|
string fileName
|
||||||
|
string traces
|
||||||
|
|
||||||
|
if (ParamIsDefault(traces))
|
||||||
|
traces = "*Up;*Down;*ReUp;*ReDown;"
|
||||||
|
endif
|
||||||
|
|
||||||
|
dfref df_save = GetDataFolderDFR()
|
||||||
|
|
||||||
|
string datanames = ""
|
||||||
|
string datapaths = ""
|
||||||
|
variable filestatus = mtrx_open_file(pathName, fileName)
|
||||||
|
if (filestatus != 1)
|
||||||
|
return ""
|
||||||
|
endif
|
||||||
|
|
||||||
|
dfref df_pack = $(package_path)
|
||||||
|
svar /sdfr=df_pack dataFilePath
|
||||||
|
svar /sdfr=df_pack resultFilePath
|
||||||
|
nvar /sdfr=df_pack runCycle
|
||||||
|
nvar /sdfr=df_pack scanCycle
|
||||||
|
svar /sdfr=df_pack channelName
|
||||||
|
nvar /sdfr=df_pack brickletID
|
||||||
|
|
||||||
|
#if exists("MFR_OpenResultFile")
|
||||||
|
string resultFileName = ParseFilePath(0, resultFilePath, ":", 1, 0)
|
||||||
|
dfref df_result = mtrx_create_folder(resultFileName, df_base=df_save)
|
||||||
|
dfref df_data = mtrx_get_cycle_folder(df_base = df_result)
|
||||||
|
variable /g df_data:V_MatrixFileReaderOverwrite = 1
|
||||||
|
variable /g df_data:V_MatrixFileReaderFolder = 0
|
||||||
|
variable /g df_data:V_MatrixFileReaderDouble = 0
|
||||||
|
|
||||||
|
struct errorCode errorCode
|
||||||
|
initStruct(errorCode)
|
||||||
|
string name
|
||||||
|
name = CleanupName(channelName, 0)
|
||||||
|
MFR_GetBrickletData /N=name /R=(brickletID) /DEST=df_data
|
||||||
|
if(V_flag == errorCode.SUCCESS)
|
||||||
|
datanames = S_waveNames
|
||||||
|
variable i
|
||||||
|
variable n = ItemsInList(datanames)
|
||||||
|
string s
|
||||||
|
for (i = 0; i < n; i += 1)
|
||||||
|
s = StringFromList(i, datanames)
|
||||||
|
wave /sdfr=df_data data = $s
|
||||||
|
mtrx_scale_dataset(data)
|
||||||
|
datapaths = AddListItem(GetWavesDataFolder(data, 4), datapaths, ";", inf)
|
||||||
|
endfor
|
||||||
|
else
|
||||||
|
MFR_GetXOPErrorMessage
|
||||||
|
endif
|
||||||
|
//MFR_GetBrickletMetaData /N=ANickName /R=(brickletID) // /DEST=dfref
|
||||||
|
#else
|
||||||
|
print "matrixfilereader.xop not installed"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
setdatafolder df_save
|
||||||
|
return datapaths
|
||||||
|
end
|
||||||
|
|
||||||
|
function mtrx_scale_dataset(data)
|
||||||
|
wave data
|
||||||
|
|
||||||
|
dfref df_pack = $(package_path)
|
||||||
|
nvar /sdfr=df_pack runCycle
|
||||||
|
nvar /sdfr=df_pack scanCycle
|
||||||
|
svar /sdfr=df_pack channelName
|
||||||
|
nvar /sdfr=df_pack brickletID
|
||||||
|
|
||||||
|
string scanDir = StringFromList(2, NameOfWave(data), "_")
|
||||||
|
if (WaveDims(data) == 2)
|
||||||
|
Note data, "AxisLabelX=X"
|
||||||
|
Note data, "AxisLabelY=Y"
|
||||||
|
endif
|
||||||
|
Note data, "AxisLabelD=" + channelName
|
||||||
|
string title
|
||||||
|
sprintf title, "%u-%u %s %s", runCycle, scanCycle, channelName, scanDir
|
||||||
|
Note data, "Dataset=" + title
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param APathName igor symbolic path name. can be empty if the path is specified in AFileName or a dialog box should be displayed
|
||||||
|
///
|
||||||
|
/// @param AFileName if empty a dialog box shows up
|
||||||
|
///
|
||||||
|
/// @return newline terminated string.
|
||||||
|
///
|
||||||
|
function /s mtrx_load_info(APathName, AFileName)
|
||||||
|
string APathName
|
||||||
|
string AFileName
|
||||||
|
|
||||||
|
dfref saveDF = GetDataFolderDFR()
|
||||||
|
dfref fileDF = NewFreeDataFolder()
|
||||||
|
setdatafolder fileDF
|
||||||
|
|
||||||
|
variable fileID
|
||||||
|
string filepath
|
||||||
|
string scanpaths
|
||||||
|
variable nscans
|
||||||
|
variable iscan
|
||||||
|
string scanpath
|
||||||
|
string info = ""
|
||||||
|
|
||||||
|
|
||||||
|
setdatafolder saveDF
|
||||||
|
return info
|
||||||
|
end
|
||||||
|
|
||||||
|
/// remove linear background line-by-line
|
||||||
|
///
|
||||||
|
function subtract_line_bg(img)
|
||||||
|
wave img
|
||||||
|
|
||||||
|
variable nx = dimsize(img, 0)
|
||||||
|
variable ny = dimsize(img, 1)
|
||||||
|
variable iy
|
||||||
|
make /n=(nx) /free line, fit
|
||||||
|
for (iy = 0; iy < ny; iy += 1)
|
||||||
|
line = img[p][iy]
|
||||||
|
if (numtype(sum(line)) == 0)
|
||||||
|
CurveFit /N /Q /NTHR=0 line line /D=fit
|
||||||
|
img[][iy] = line[p] - fit[p]
|
||||||
|
endif
|
||||||
|
endfor
|
||||||
|
end
|
File diff suppressed because it is too large
Load Diff
@ -703,3 +703,99 @@ function scienta_poly_bg(w, e, a): fitfunc
|
|||||||
|
|
||||||
return bg * (base + pk1 + pk2 + pk3)
|
return bg * (base + pk1 + pk2 + pk3)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
/// parameter dialog for the redim_linbg_reduction() function
|
||||||
|
///
|
||||||
|
/// @param param parameter string in a key1=value1;key2=value2;... list.
|
||||||
|
/// the parameter string is passed by reference.
|
||||||
|
/// see redim_linbg_reduction() for a description of parameters.
|
||||||
|
///
|
||||||
|
/// @return zero if the user clicked OK, non-zero if the user clicked Cancel.
|
||||||
|
///
|
||||||
|
function prompt_redim_linbg_reduction(param)
|
||||||
|
string ¶m
|
||||||
|
|
||||||
|
variable Lcrop = NumberByKey("Lcrop", param, "=", ";")
|
||||||
|
variable Lsize = NumberByKey("Lsize", param, "=", ";")
|
||||||
|
variable Hcrop = NumberByKey("Hcrop", param, "=", ";")
|
||||||
|
variable Hsize = NumberByKey("Hsize", param, "=", ";")
|
||||||
|
variable Cpos = NumberByKey("Cpos", param, "=", ";")
|
||||||
|
variable Csize = NumberByKey("Csize", param, "=", ";")
|
||||||
|
|
||||||
|
prompt Lcrop, "Lower cropping region"
|
||||||
|
prompt Hcrop, "Upper cropping region"
|
||||||
|
prompt Lsize, "Lower background region"
|
||||||
|
prompt Hsize, "Upper background region"
|
||||||
|
prompt Cpos, "Center position"
|
||||||
|
prompt Csize, "Center integration region"
|
||||||
|
|
||||||
|
doprompt "redim_linbg_reduction Parameters", lcrop, hcrop, lsize, hsize, cpos, csize
|
||||||
|
if (v_flag == 0)
|
||||||
|
param = ReplaceNumberByKey("Lcrop", param, Lcrop, "=", ";")
|
||||||
|
param = ReplaceNumberByKey("Lsize", param, Lsize, "=", ";")
|
||||||
|
param = ReplaceNumberByKey("Hcrop", param, Hcrop, "=", ";")
|
||||||
|
param = ReplaceNumberByKey("Hsize", param, Hsize, "=", ";")
|
||||||
|
param = ReplaceNumberByKey("Cpos", param, Cpos, "=", ";")
|
||||||
|
param = ReplaceNumberByKey("Csize", param, Csize, "=", ";")
|
||||||
|
endif
|
||||||
|
|
||||||
|
return v_flag
|
||||||
|
end
|
||||||
|
|
||||||
|
/// 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.
|
||||||
|
///
|
||||||
|
/// @param source source wave
|
||||||
|
/// Scienta detector image, energy axis along X, angle axis along Y
|
||||||
|
///
|
||||||
|
/// @param dest1 destination wave 1
|
||||||
|
///
|
||||||
|
/// @param dest2 destination wave 2
|
||||||
|
/// each wave is a one-dimensional intensity distribution
|
||||||
|
/// the function may redimension these waves to one of the image dimensions
|
||||||
|
/// (it must be clear to the user which dimension this is).
|
||||||
|
/// the meaning of dest1 and dest2 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.
|
||||||
|
///
|
||||||
|
/// @param param parameter 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).
|
||||||
|
/// @arg Lcrop size of the lower cropping region
|
||||||
|
/// @arg Hcrop size of the upper cropping region
|
||||||
|
/// @arg Lsize size of the lower background integration region
|
||||||
|
/// @arg Hsize size of the upper background integration region
|
||||||
|
/// @arg Cpos center position of the of the peak integration region
|
||||||
|
/// @arg 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
|
||||||
|
///
|
||||||
|
/// @return zero if successful, non-zero if an error occurs.
|
||||||
|
///
|
||||||
|
threadsafe function redim_linbg_reduction(source, dest1, dest2, param)
|
||||||
|
wave source
|
||||||
|
wave dest1, dest2
|
||||||
|
string ¶m
|
||||||
|
|
||||||
|
variable nx = dimsize(source, 0)
|
||||||
|
variable ny = dimsize(source, 1)
|
||||||
|
|
||||||
|
duplicate /free source, source_redim
|
||||||
|
redimension /n=(nx * ny) source_redim
|
||||||
|
nx += 1
|
||||||
|
redimension /n=(nx, ny) source_redim
|
||||||
|
|
||||||
|
return int_linbg_reduction(source_redim, dest1, dest2, param)
|
||||||
|
end
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user