A custom variable is only used within the context of a trajectory (e.g., for a calculation), so its name and value are simply stored in the namespace. A device node variable not only has its name-value pair stored in the namespace, but the device node corresponding to the variable name also gets set to the variable’s value.
As a simple example, we have a custom variable in a trajectory that holds an offset value and another that holds a list of motor positions. The device node variable in this trajectory is sampleAngle.softPosition and it makes use of the two custom variables:
As the trajectory goes through the loop, it takes the position list values, adds the offset to them, and then moves sampleAngle.softPosition to the resulting value. The dryrun table below demonstrates how the output of this would look:
NOTE: If the device node belongs to an add-removable device and the device has not been added, then the trajectory’s variable defaults to being a custom variable.
Variable evaluation also has a syntax to it. The trajectory processor will evaluate variables in the order they are added to the trajectory. If a variable depends on the declaration of some other variable, then it must be declared beforehand. This rule will apply to all elements in the trajectory’s init and vary scopes. Top level reserved variables could be added in any order. They will be processed before loops are processed.
NOTE: Trajectory syntax does not distinguish between custom variables and device names. However, visually the users can choose to write custom variables all UPPERCASE and all device names lowercase. This notation will allow the users to immediately see if some variable is used incorrectly. Additionally, the dryrun summary will show all custom variables. Users will be able to detect whether the name is misspelled or whether it’s a sample environment device that has not been added to the instrument.
After dry running a trajectory, all the custom variables should be listed at the end. This is the preferred way of identifying variables. Since custom variables will not be marked with a special character, the trajectory will not be able to issue a warning if the device name is misspelled – it will be automatically be interpreted as a custom variable.
will be converted to sample.mode, sample.aperture, and sample.sampleThickness; full node IDs that can be moved within the device model.
NOTE: Using dotted notation in an expression for an object that has not yet been defined will result in error.
For example, start.sample.name will have a String value (identifying the sample) which was set before the trajectory started running.
Trajectories do not retrieve “live” values directly from the device model as it’s running. In other words, a trajectory cannot access the live value of a node as the node changes during the trajectory’s execution – what is available to the trajectory is a snapshot of the node states as they were right before the trajectory started running. The state can be accessed via the start prefix followed by full node ID (for example: start.lakeshore340.primaryNode). Here are two common scenarios in which static node values are used:
Within the init block, add the file rule:
filePrefix = start.sample.name + sample.name
When run, the trajectory should produce a similar output to the one in the dryrun table below:
The trajectory is moving the sampleAngle.softPosition node from 1 to 3 degrees twice and in each of these loops the sample.name node is renamed. As seen side-by-side in the resulting filePrefix, manipulating sample.name does not affect start.sample.name – the latter is a static entity, retaining its starting value throughout the trajectory, while the former is subject to change.
The start keyword is also useful when accessing a motor’s position snapshot value for use as the center position in a range scan. To illustrate this with another example, please create the following loop in a trajectory:
This loop will step through five points, moving detectorAngle.softPosition by 1 degree between each point. Although it’s difficult to see, the value provided for “center” is start.detectorAngle.softPosition. As such, the center value will be the detector angle motor’s position at the start of the trajectory’s run. If we move detectorAngle.softPosition to 4.19 degrees before running the trajectory, then we should get a similar output to the one in the dryrun table below:
4.19 degrees ends up being the third (or center) value of five that detectorAngle.softPosition moves through. Note, that it is detectorAngle.softPosition that changes throughout the range scan trajectory, not start.detectorAngle.softPosition.
The NICE team can configure specific nodes to be volatile, at the request of the instrument scientist. All volatile nodes will update their values, from hardware, before the trajectory’s static variable is initialized. Volatile nodes are NOT updated during a trajectory’s execution.