I have a plot with interactive controls. I'd like to give the user the option between having the plot automatically update (when the plot's parameters are changed with the slider) and having the update happen only when an 'update' button is pushed. I've been spinning my wheels on this for a long time. Any and all help is appreciated.
1 Answers
Edit
Can you think of another way to accomplish the same thing [...]? It would be nice to have a solution that didn't involve duplicating each slider.
-nibudd
DynamicModule[{a = 1, tempA = 1, auto = True}
,
ifAuto = Dynamic[
If[auto, Identity, Setting]@#,
TrackedSymbols :> {auto}
] &;
Column[{
ifAuto @ Dynamic @ Plot[Sin[a x], {x, 0, 1}],
Slider[Dynamic[a], {1, 10}],
Checkbox[Dynamic[auto]],
Button["Update", auto = True; FinishDynamic[]; auto = False;,
Method -> "Queued", Enabled -> Dynamic@Not@auto]
}]
]
ifAutofunction is meant to be used onDynamicparts of GUI that you want to be affected by this behaviour.ifAuto'sDynamicoutput is triggered only when variableautochangesIf
auto === Truethen it acts as it wasn't there. E.gDynamic[Plot[...]...]is shown and the FrontEnd will take care about its updates according to what was set there.If[fromifautois only run whenautochanges so it does not affect the performance, neat. Read more in tutorial/AdvancedDynamicFunctionality/Nesting DynamicIf
auto === FalsethenSetting @ Dynamic @ Plot[...is shown, effectively strippingDynamicsand leavingPlot[...which won't be updated bya'schanges (because of the very outerTrackedSymbols:>{auto}.
Initial approach
The idea is to switch controllers between main a variable and a temporary one tempA's.
The Checkbox toggles that. It also makes both variables synchronized so that the transistion is "smooth".
DynamicModule[{a = 1, tempA = 1, auto = True},
Column[{
Dynamic @ Plot[Sin[a x], {x, 0, 1}],
PaneSelector[
{
True -> Slider[Dynamic[a], {1, 10}],
False -> Slider[Dynamic[tempA], {1, 10}]
},
Dynamic@auto
],
Checkbox[Dynamic[auto, If[auto = #, a = tempA, tempA = a] &]],
Button["Update", a = tempA, Enabled -> Dynamic@Not@auto]
}
]
]
Instead of PaneSelector you can use
`Slider[Dynamic[tempA, (tempA = #; If[auto, a = tempA]) &], {1, 10}]`
but spamming If whenever you move a Slider is not neat.
-
This is exactly the kind of thing I was trying to achieve. Now to understand what you've done here - thank you! – nibudd Jul 20 '16 at 21:52
-
If you'll indulge me, I have some questions about how this works:
What is the
Ifpure function taking as its argument, the value ofCheckbox?What is the meaning of
auto = #in the first argument ofIf? Is#being evaluated to determine which expression to execute (a = tempAortempA = a) and then assigning that value toauto?
2b. If so, why is that necessary? Isn't auto already tied to the Checkbox?
- What is the meaning of
@here? I can't find any documentation on this kind of usage (Dynamic @ Plot[...,Dynamic @ auto, orDynamic @ Not @ auto)
-
1@nibudd 1. take a look at docs for
Dynamic, the second argument ofDynamiccan be a function which does whatever you want with the state of the controller.#is a slot which will be filled with that state, so True or False. 2.auto = #has 2 roles, assignsCheckboxstate toautoand returns this value so we can synchronizeawithtempA(whenaortempAis active the other isn't though we don't want it's old value to pop up after switching). Hope that was clear. About@, take a look at What the @#%^&*?! – Kuba Jul 21 '16 at 16:22 -
I did read the documentation on
Dynamic, but since I'm relatively new to Mathematica, I did not find it terribly helpful. I appreciate you clearing up my confusion. Can you think of another way to accomplish the same thing by using the TrackedSymbols attribute of Plot? I've been trying to do this with something likeTrackedSymbols :> Dynamic[list, If[manualUpdate = #, list = {update}, list = {a, b}] &]' whereupdateis tied to my update button, anda, b` are tied to two different sliders. It would be nice to have a solution that didn't involve duplicating each slider. – nibudd Jul 21 '16 at 16:52 -
1
-
So
SettingcausesTrackedSymbolx:>{auto}to be applied toDynamic@Plot[...butIdentitydoes not? Why is that? – nibudd Jul 22 '16 at 18:23 -
@nibudd I don't understand, I said what
Settingdoes and documentation also says so, it stripsDynamicinner toSetting. That is all. – Kuba Jul 25 '16 at 13:52

ContinuousActionif you have not done so already. It is not an answer to your question but it can provide a reasonable in-between in some cases. – Mr.Wizard Jul 20 '16 at 21:25ControlActiveis good to know. – Kuba Jul 20 '16 at 21:26