What is the correct syntax for using a radio button to set values to be used elsewhere? (restated)

Here is my question, restated – I want to be able to choose the values for a complicated function from a set of alternatives values that I have gathered. The function requires several input values, and I want to be able to choose one or the other of the sets. Example:

forest = Range[30];
energy = Reverse[Range[30]];
RadioButtonBar[Dynamic[choice], {1 -> “Forest”, 2 -> “Energy”} ]
series = Dynamic[Switch[choice, 1, forest, 2, energy]]
title = Dynamic[Switch[choice, 1, “Tree Growth”, 2, “Energy Use”]]
ListPlot[series, PlotLabel -> title]

In the notebook, I load a variety of data items (two different time series, series names, start dates, scaling values, …) for eight or nine things. I want to be able to just click a button (or some other control), and then evaluate the function (or several functions) that make use of the selected data.

If you test the code above, you will find that the value of “series” isn’t a list of values but instead something with the head Dynamic, that can’t be used for calculation, plotting, etc.

=================

  

 

Try and wrap Dynamic around the entire Switch. – And better copy the code in here, so people can copy and paste it in their notebook for testing.
– Mockup Dungeon
Oct 24 ’14 at 16:23

  

 

@MockupDungeon That fixed it! That’s not very intuitive, at least to me, but that’s the way you do it. Repost as an answer and I’ll mark it as an answer. Thanks.
– George Wolfe
Oct 24 ’14 at 16:30

=================

2 Answers
2

=================

The problem is, that the Head of series is now Dynamic. With a simple Part you get rid of this:

ListPlot[series[[1]], PlotLabel -> title]

Besides, why not using Manipulate? Your problem seem perfectly suited for this:

Manipulate[
forest = Range[30];
energy = Reverse[Range[30]];

Switch[choice
, 1, series = forest; title = “Tree Growth”
, 2, series = energy; title = “Energy Use”
];

ListPlot[series, PlotLabel -> title]

, {{choice, 1, “Choice”}, {1 -> “Forest”, 2 -> “Energy”}}
]

  

 

Edited to suggest Manipulate instead.
– Mockup Dungeon
Oct 25 ’14 at 1:59

  

 

I have a set of analytics I might or might not want to try after choosing a data set. I don’t need for everything to change at once.
– George Wolfe
Oct 25 ’14 at 2:15

Generally, Dynamic is used in two ways:

Re-evaluating expressions when they would change, and displaying the result. The syntax is Dynamic[expr]. Dynamic[expr] cannot be used to represent the value of expr in different context and calculate with it. It is only used to display it.
Allowing controls to change values of variables. Typical syntax: someControl[Dynamic[x], …].

Your first piece of code with RadioButtonBar falls into the second category and is correct.

The second, with Switch, falls into the first category, and it is incorrect. Switch can’t use Dynamic[x] as a value. It is the entire Switch that needs to be re-evaluated when x changes, so all of it needs to be wrapped in Dynamic, but x must not. If you use this Switch construct in other code, once again the full code needs to be wrapped in Dynamic, and Dynamic must be removed from around Switch (unless the result of Switch is only used for display).

The key is: do you need to only display the result? Then wrap it with Dynamic. If you need to do calculations with the result then the full calculation needs to be wrapped by Dynamic.

In fact Dynamic is directly tied to a displayed region on screen and will only re-evaluate if this region is visible, but not otherwise. You can try this by e.g. evaluating Dynamic[Print[x]; x], scrolling the corresponding region off-screen (by about a full window height), then changing the value of x. The contents of the dynamic won’t be re-evaluated in this case.

  

 

Now I get it. Makes sense. Thanks. My dilemma – do I choose the answer or the explanation.
– George Wolfe
Oct 24 ’14 at 16:33

  

 

@Szabolics This language should be in help for Dynamic, but I don’t remember seeing it.
– George Wolfe
Oct 24 ’14 at 16:44

  

 

@Szabolics I encountered a problem. I want to chose one of four text strings and of four pairs of lists of values. Everything comes back with the head “Dynamic”. I can disply the text string and lists of values, but if I try to get a subset of one of the list of values (values[[1;;10]]) I get an error message saying I can’t take positions 1 through 10 in the values, which are displayed in red.
– George Wolfe
Oct 24 ’14 at 17:18

  

 

@GeorgeWolfe I don’t completely understand the question, but I’ll come back to this in a few hours. If you do values = Dynamic[Switch[…]] then it’s the same problem I described. It’s not possible to use Dynamic-wrapped stuff for computation, only for display. A better way would be values := Switch[…] (not the :=), then Dynamic[ values[[1;;10]] ]
– Szabolcs
Oct 24 ’14 at 19:10

  

 

@Szabolics I restated my question. I think it is understandable now.
– George Wolfe
Oct 25 ’14 at 1:33