SetVariable: linking limits to the scaling of an image
kpantzas
I've been working on a user interface for a family of procedures that I commonly use to analyze transmission electron microscopy (TEM) images.
Part of that interface includes a Line Profile Tool that is more TEM image oriented - a somewhat simplified and extended version of Wavemetrics' Image Line Profile tool.
One of the reasons I wanted to create my own line profile tool is that the the built-in Line Profile interface does not handle scaled images, i.e. the width of the profile is always in pixels. In my interface the
limits
option for the SetVariable
that sets the width is set to not exceed to not exceed the scaled size of the image (DimDelta(imWave,0)*DimSize(imWave,0)
), and to increment by half the scaling increment (0.5*DimDelta(imWave,0)
). Here, imWave
refers to the wave that holds the image.It occurred to me that if I rescale the image, I may not automatically update the limits of the
SetVariable
field. Am I correct?If that is the case, how can I ensure that the limits of the
SetVariable
field are linked to the scaling of the image that is being displayed?I posted the full code as a project here: http://www.igorexchange.com/project/SimpLiFi
The part that is concerned is here:
SetVariable profWidthVar, pos={236,8}, size={90,15}, proc=QHAADFSetProfWidthProc
SetVariable profWidthVar, title="Width"
SetVariable profWidthVar, help={"Width over which to average profile"}
SetVariable profWidthVar, limits={0,sqrt(2)*DimDelta(imWave,0)*DimSize(imWave,0),DimDelta(imWave,0)}, value=root:Packages:QHAADF:LineProfile:swidth
SetVariable profWidthVar, title="Width"
SetVariable profWidthVar, help={"Width over which to average profile"}
SetVariable profWidthVar, limits={0,sqrt(2)*DimDelta(imWave,0)*DimSize(imWave,0),DimDelta(imWave,0)}, value=root:Packages:QHAADF:LineProfile:swidth
April 11, 2017 at 10:18 am - Permalink
April 11, 2017 at 10:50 am - Permalink
April 11, 2017 at 11:01 am - Permalink
SetScale
operation on the wave that contains the image data, and not to resize the window that displays the image.April 11, 2017 at 11:07 am - Permalink
John Weeks
WaveMetrics, Inc.
support@wavemetrics.com
April 11, 2017 at 11:36 am - Permalink
You should be able to use SetFormula to get this to work.
For example:
WAVE wave0
print "recalculate called"
End
Function test()
Variable/G root:dummy1
Make/N=(100, 200) root:imageWave = enoise(10)
SetFormula root:dummy1, "recalculate(root:imageWave)"
SetScale x, 0, 10, root:imageWave
End
Execute test() and notice that you get the print out indicating that recalculate was called. If you execute the SetScale command again, recalculate is called again. You would make the changes to the SetVariable control in the recalculate() function.
Note that you're setting yourself up for potential debugging nightmares by using dependencies like this.
April 11, 2017 at 11:44 am - Permalink
Create a Function that does only two things ... It reads the current scale of imWave and sets global variables (gimScale and gimDelta) with that value.
Define the limits of the setvariable by the global variables.
NVAR root:Packages:MyTEMPackage:gimDelta
setvariable myimScale, limits={gimScale,0,gimDelta}
Create a window hook function. Attach it as a hook to the image graph and to the panel. The hook function will get an "activate" event. Have the activate event call the above function and then go to sleep.
Every time you activate the window or the panel, the globals will update, and thus the set variable limits will be updated.
I _think_ that this should work. I _think_ that I used this trick in the past. I _think_ that you cannot just blindly update the setvariable limits in the hook function because the call itself will (re)activate the hook function, leading to an infinite time loop.
--
J. J. Weimer
Chemistry / Chemical & Materials Engineering, UAH
April 11, 2017 at 04:51 pm - Permalink
I ended up using jjweimer's suggestion, and created this function
NVAR gimDelta = root:Packages:QHAADF:LineProfile:gimDelta
NVAR gimScale = root:Packages:QHAADF:LineProfile:gimScale
WAVE imWave = $WMGetImageWave(WMTopImageGraph())
gimDelta = DimDelta(imWave,0)
gimScale = DimDelta(imWave,0)*DimSize(imWave,0)
SetVariable profWidthVar, win=QHAADFLineProfileGraph, limits={0,sqrt(2)*gimScale,0.5*gimDelta}
End
that I call from the hook functions I've placed on both the window that displays the image and the window that displays the line profile.
April 12, 2017 at 05:02 am - Permalink
* You might want to put a return 0 at the end of your function call. This is a bit of "good coding practice".
* I am not certain that you really need to recall the setvariable within the function. I _think_ that you can set up the setvariable one time in your panel creation using the globals. Then, you can change the globals somewhere else and the limits will be adjusted.
* If you do end up continuing to change the setvariable within the function call itself, you do not need global variables at all. The only reason to use the globals is to avoid that you need to re-invoke the setvariable call each time the hook function is called. I suspect you may otherwise be running the case where, you activate the graph, that calls the hook, that calls the setvariable, that activates the panel, that calls the hook, that calls the setvariable, that activates the panel, that calls the hook ...
So a few changes and tests might be in line before you call it entirely fail safe.
--
J. J. Weimer
Chemistry / Chemical & Materials Engineering, UAH
April 12, 2017 at 05:19 am - Permalink
Several replies ago, you mentioned that the scaling is changed by a SetScale operation. Is there a reason not to call your function (QHAADFUpdForImScale) that updates the SetVar immediately after SetScale?
April 12, 2017 at 05:20 am - Permalink
I was guessing the reason was to avoid problems in those cases when someone manually types the setscale change on the command line?????
But otherwise, I would have to wonder as well.
--
J. J. Weimer
Chemistry / Chemical & Materials Engineering, UAH
April 12, 2017 at 05:22 am - Permalink