##// END OF EJS Templates
support for unicode identifiers...
support for unicode identifiers This rewrites some of the regular expressions that are used to match Python identifiers, so that they are unicode compatible. In Python 3, identifiers can contain unicode characters as long as the first character is not numeric. Examples for the changes: • inputtransformer: ``` In [1]: π = 3.14 In [2]: π.is_integer? Object `is_integer` not found. ``` ---------- • namespace: ``` π.is_integ*? ``` or ``` In [1]: %psearch π.is_integ Python identifiers can only contain ascii characters. ``` ---------- • prefilter: ``` %autocall 1 φ = float get_ipython().prefilter("φ 3") # should be 'φ(3)', but returns 'φ 3' ``` ---------- • completerlib: If there is a file e.g. named `π.py` in the current directory, then ``` import IPython IPython.core.completerlib.module_list('.') # should contain module 'π' ```

File last commit:

r23943:84bcdc34
r25595:d9c0e690
Show More
Updating Displays.ipynb
337 lines | 6.8 KiB | text/plain | TextLexer

Updatable Displays

Note: This feature requires notebook >= 5.0 or JupyterLab, and

IPython 6 implements a new API as part of the Jupyter Protocol version 5.1 for easily updating displays.

When you display something, you can now pass a display_id argument to attach an id to that output.

Any future display with the same ID will also update other displays that had the same ID.

display with a display_id will return a DisplayHandle object, which gives you easy access to update the output:

In [1]:
from IPython.display import display, update_display
In [2]:
handle = display('x', display_id='update-me')
handle
'z'
Out[2]:
<DisplayHandle display_id=update-me>

When we call handle.display('y'), we get a new display of 'y', but in addition to that, we updated the previous display.

In [3]:
handle.display('y')
'z'

We can also just update the existing displays, without creating a new display:

In [4]:
handle.update('z')

You don't have to generate display_ids yourself, if you specify display_id=True, then a unique ID will be assigned:

In [5]:
handle = display("hello", display_id=True)
handle
'hello'
Out[5]:
<DisplayHandle display_id=118a56127f42348f8893440da7181c57>

Calling handle.display(obj) is the same as calling display(obj, handle.display_id), so you don't need to use the handle objects if you don't want to:

In [6]:
display('x', display_id='here');
'z'
In [7]:
display('y', display_id='here');
'z'

And just like display, there is now update_display, which is what DisplayHandle.update calls:

In [8]:
update_display('z', display_id='here')

More detailed example

One of the motivating use cases for this is simple progress bars.

Here is an example ProgressBar using these APIs:

In [9]:
from IPython.display import ProgressBar

bar = ProgressBar(10)
bar.display()

And the ProgressBar has .display and .update methods:

In [10]:
import time

bar.display()

for i in range(11):
    bar.progress = i
    bar.update()
    time.sleep(0.25)

The ProgressBar also has an update built into iteration:

In [11]:
for i in ProgressBar(10):
    time.sleep(0.25)

We would encourage any updatable-display objects that track their own display_ids to follow-suit with .display() and .update() or .update_display() methods.