Open in CoCalc
@interact def f(a=True, b=False, auto_update=False): print a, b
Interact: please open in CoCalc
interact??
File: /projects/sage/sage-7.3/local/lib/python2.7/site-packages/smc_sagews/sage_salvus.py Source: class Interact(object): """ Use interact to create interactive worksheet cells with sliders, text boxes, radio buttons, check boxes, color selectors, and more. Put ``@interact`` on the line before a function definition in a cell by itself, and choose appropriate defaults for the variable names to determine the types of controls (see tables below). You may also put ``@interact(layout=...)`` to control the layout of controls. Within the function, you may explicitly set the value of the control corresponding to a variable foo to bar by typing interact.foo = bar. Type "interact.controls.[tab]" to get access to all of the controls. INPUT: - ``f`` -- function - ``width`` -- number, or string such as '80%', '300px', '20em'. - ``style`` -- CSS style string, which allows you to change the border, background color, etc., of the interact. - ``update_args`` -- (default: None); list of strings, so that only changing the corresponding controls causes the function to be re-evaluated; changing other controls will not cause an update. - ``auto_update`` -- (default: True); if False, a button labeled 'Update' will appear which you can click on to re-evalute. - ``layout`` -- (default: one control per row) a list [row0, row1, ...] of lists of tuples row0 = [(var_name, width, label), ...], where the var_name's are strings, the widths must add up to at most 12, and the label is optional. This will layout all of the controls and output using Twitter Bootstraps "Fluid layout", with spans corresponding to the widths. Use var_name='' to specify where the output goes, if you don't want it to last. You may specify entries for controls that you will create later using interact.var_name = foo. NOTES: The flicker and layout options above are only in SALVUS. For backwards compatibility with the Sage notebook, if layout is a dictionary (with keys 'top', 'bottom', 'left', 'right'), then the appropriate layout will be rendered as it used to be in the Sage notebook. OUTPUT: - creates an interactive control. AUTOMATIC CONTROL RULES ----------------------- There are also some defaults that allow you to make controls automatically without having to explicitly specify them. E.g., you can make ``x`` a continuous slider of values between ``u`` and ``v`` by just writing ``x=(u,v)`` in the argument list. - ``u`` - blank input_box - ``u=elt`` - input_box with ``default=element``, unless other rule below - ``u=(umin,umax)`` - continuous slider (really `100` steps) - ``u=(umin,umax,du)`` - slider with step size ``du`` - ``u=list`` - buttons if ``len(list)`` at most `5`; otherwise, drop down - ``u=generator`` - a slider (up to `10000` steps) - ``u=bool`` - a checkbox - ``u=Color('blue')`` - a color selector; returns ``Color`` object - ``u=matrix`` - an ``input_grid`` with ``to_value`` set to ``matrix.parent()`` and default values given by the matrix - ``u=(default, v)`` - ``v`` anything as above, with given ``default`` value - ``u=(label, v)`` - ``v`` anything as above, with given ``label`` (a string) EXAMPLES: The layout option:: @interact(layout={'top': [['a', 'b']], 'left': [['c']], 'bottom': [['d']], 'right':[['e']]}) def _(a=x^2, b=(0..20), c=100, d=x+1, e=sin(2)): print(a+b+c+d+e) We illustrate some features that are only in Salvus, not in the Sage cell server or Sage notebook. You can set the value of a control called foo to 100 using interact.foo=100. For example:: @interact def f(n=20, twice=None): interact.twice = int(n)*2 In this example, we create and delete multiple controls depending on properties of the input:: @interact def f(n=20, **kwds): print(kwds) n = Integer(n) if n % 2 == 1: del interact.half else: interact.half = input_box(n/2, readonly=True) if n.is_prime(): interact.is_prime = input_box('True', readonly=True) else: del interact.is_prime You can access the value of a control associated to a variable foo that you create using interact.foo, and check whether there is a control associated to a given variable name using hasattr:: @interact def f(): if not hasattr(interact, 'foo'): interact.foo = 'hello' else: print(interact.foo) An indecisive interact:: @interact def f(n=selector(['yes', 'no'])): for i in range(5): interact.n = i%2 sleep(.2) We use the style option to make a holiday interact:: @interact(width=25, style="background-color:lightgreen; border:5px dashed red;") def f(x=button('Merry ...',width=20)): pass We make a little box that can be dragged around, resized, and is updated via a computation (in this case, counting primes):: @interact(width=30, style="background-color:lightorange; position:absolute; z-index:1000; box-shadow : 8px 8px 4px #888;") def f(prime=text_control(label="Counting primes: ")): salvus.javascript("cell.element.closest('.salvus-cell-output-interact').draggable().resizable()") p = 2 c = 1 while True: interact.prime = '%s, %.2f'%(p, float(c)/p) p = next_prime(p) c += 1 sleep(.25) """ def __call__(self, f=None, layout=None, width=None, style=None, update_args=None, auto_update=True, flicker=False, output=True): if f is None: return _interact_layout(layout, width, style, update_args, auto_update, flicker) else: return salvus.interact(f, layout=layout, width=width, style=style, update_args=update_args, auto_update=auto_update, flicker=flicker, output=output) def __setattr__(self, arg, value): I = interact_exec_stack[-1] if arg in I._controls and not isinstance(value, control): # setting value of existing control v = I._controls[arg].convert_to_client(value) desc = {'var':arg, 'default':v} I._last_vals[arg] = value else: # create a new control new_control = interact_control(arg, value) I._controls[arg] = new_control desc = new_control.jsonable() desc['id'] = I._uuid salvus.javascript("worksheet.set_interact_var(obj)", obj=desc) def __delattr__(self, arg): try: del interact_exec_stack[-1]._controls[arg] except KeyError: pass desc['id'] = I._uuid salvus.javascript("worksheet.del_interact_var(obj)", obj=jsonable(arg)) def __getattr__(self, arg): try: return interact_exec_stack[-1]._last_vals[arg] except Exception as err: raise AttributeError("no interact control corresponding to input variable '%s'"%arg) def changed(self): """ Return the variables that changed since last evaluation of the interact function body. [SALVUS only] For example:: @interact def f(n=True, m=False, xyz=[1,2,3]): print n, m, xyz, interact.changed() """ return interact_exec_stack[-1].changed