Issue I353 [80,prog,change,resolved] Change in behavior of adjustable variable assignments in Lua affecting current v.s. default values. Suggested by davidm-20070118 to improve ion trap example. As of 8.0.2, the behavior of when assignments to adjustable variables in Lua affect current v.s. default values was changed slightly to be more reasonable. A quick executive summary is given first followed by the full excruciating details. Summary... This change is somewhat subtle and has no effect on most programs that simply define adjustable variables and use them in segments, but some programs that do more complicated things with adjustable variables can be affected (e.g. the "trap" example that redefines some adjustable variables from one Lua file in another Lua file), particularly when the user adjusts these variables from the Variables tab in View. Under the old behavior, adjustments made to these variables in the Variables tab in View could get ignored (i.e. the program, in overriding these variables, also overrides the user). Under the new behavior, the user adjustments are not ignored. Namely, under the new behavior, assignments to an adjustable variable from Lua programs ALWAYS affect the current value and not the default value. Moreover, following program loading (and before the Fly'm), the current values are used to define the default values. Discussion... Each SIMION adjustable variable has both a "current value" and a "default value". The default value is defined in the program. It typically doesn't change, but it will be reset if changed in the user program source code that is then reloaded, as occurs on (re)loading the workbench and also starting a new Fly'm. The current value is initially set to the default value. The user or the program can change the current value at run-time. The current value is reset to the default value if you click "Reset Values" on the Variables tab. SIMION also saves and restores the current value before and after a Fly'm so that the current value after a Fly'm is the current value before a Fly'm. In SIMION 8.0.0-8.0.1, the statement adjustable x = 3 when executed sets the default value for the adjustable variable x to 3. It leaves the current value unchanged except when the default value changes, in which case the current value is reset to the default value. In contrast, the following seemingly similar code has a different behavior: adjustable x x = 3 The first line does not change the current/default values but the second line updates the current value. Note that only "adjustable" assignment statements (which act as declarations) touch the default value. Typical usage is this: simion.workbench_program() adjustable x = 3 -- define default value function segment.other_actions() print(x) x = x + 1 -- update current value temporarily in Fly'm. end When the program is loaded, the default value becomes 3. The current value is normally unchanged at that time, but it will reset to the default value if the default value changes (as might occur if you change the value in the second line of the program and then reload the program such as by reloading the workbench or starting a new Fly'm). Later, when the other_actions segment runs during the Fly'm, the current value of x is updated. Changes to the current value remain in effect until the Fly'm finishes, in which case the current value of x is reset to its current value before the Fly'm. The change in behavior in 8.0.2 is as follows. The statement adjustable x = 3 and the statements adjustable x x = 3 now have the same effect (more consistent). They both temporarily set the current value to 3 and leave the default value untouched. However, when the program finishes loading, SIMION now sets the default value for the adjustable variable to its current value. SIMION then resets its current value to the current value prior to loading except if the default value was changed. CONCEPTUALLY YOU CAN THINK OF IT THIS WAY: DURING PROGRAM LOADING, THE PROGRAM -IN EFFECT- DEFINES THE DEFAULT VALUE, WHILE AT PROGRAM RUNNING THE PROGRAM MAY ONLY UPDATE (TEMPORARILY) AND ACCESS THE CURRENT VALUE. *Under the changed behavior, the end result of the typical usage given above is the same*, but the implementation is slightly differently. During program loading, the current value temporarily changes to 3. At the end of program loading, the default value is set to the then current value (3) and the current value is reset to the current value prior to loading (unless the default has changed). During the Fly'm, the current value is incremented. At the end of the Fly'm the current value is reset to the current value prior to the Fly'm. The end results differs, however, under the new behavior for some more atypical cases such as in the trap example where adjustable variables are initially defined in one file (e.g. util.lua) and overriden by redefinitions in another file (e.g. inject.lua). -- util.lua file adjustable _mean_free_path = 4.0 -- inject.lua file adjustable _mean_free_path = 1.0 Under the old behavior, when this is loaded, the default value changes to 4 and then to 1, which is ok. However, if the user changes the current value in the Adjustable tab to, say, 8.0, then the current value specified by the user will always get reset to the default value on program reloading. The first adjustable definition in util.lua temporarily resets the default value to 4.0 when it was previously most likely the 1.0 defined later. SIMION sees that the default value has changed, so it **resets the current value to 4** (not wanted). In inject.lua, this happens again and the current value is reset to 1.0. So, the current value always becomes 1.0 regardless what the user entered in the Variables tab. Under the new behavior, after loading, the default value becomes 1.0, and the current value is reset to current value prior to loading (unless the default value changed). This is the desired behavior. Consider this more atypical case: simion.workbench_program() adjustable x = 2 x = 3 function segment.other_actions() ... end Here, the second and third lines are both executed during program loading (not Fly'm). Under the old behavior, after loading the default value becomes 2 and the current value permanently becomes 3. Under the new behavior, the default value becomes 3 and the current value remains unchanged (unless the default value changes). Consider this other more atypical case: simion.workbench_program() function segment.other_actions() adjustable linear_damping = 10 print(linear_damping) end Here, the third line is executed during the Fly'm. Under the old behavior, during the Fly'm the default value becomes 10. If the default value changes, the current value is changed to 10 until the end of the Fly'm, in which case it is reset to the value prior to the Fly'm. This behavior is probably not so useful. Under the new behavior, the current value changes to 10. If just this is done function segment.other_actions() adjustable linear_damping print(linear_damping) end Then under both the old and new behavior the default and current values are unchanged. Consider this: simion.workbench_program() adjustable x = 3 adjustable y = x Initially, the default and current values of x and y are both 3. Now, say the user adjusts x to 4 and reloads the program by starting a new Fly'm. Under the old behavior, the second line has no effect, but the third line sets the default value of y to 4. Under the new behavior, default and current values of both variables remain unchanged by the reloading. Changed in 8.0.2.