{
 "metadata": {
  "celltoolbar": "Slideshow",
  "name": "",
  "signature": "sha256:f6c1dd624d35ab0c768f77dffdae914baf4d88a3c244047c00ffca8b9c96e81e"
 },
 "nbformat": 3,
 "nbformat_minor": 0,
 "worksheets": [
  {
   "cells": [
    {
     "cell_type": "markdown",
     "metadata": {},
     "source": [
      "[Index](Index.ipynb) - [Next](Widget List.ipynb)"
     ]
    },
    {
     "cell_type": "heading",
     "level": 1,
     "metadata": {},
     "source": [
      "Simple Widget Introduction"
     ]
    },
    {
     "cell_type": "heading",
     "level": 2,
     "metadata": {},
     "source": [
      "What are widgets?"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "Widgets are elements that exists in both the front-end and the back-end.\n",
      "\n",
      "** Insert Frontend-Backend Picture **"
     ]
    },
    {
     "cell_type": "heading",
     "level": 2,
     "metadata": {},
     "source": [
      "What can they be used for?"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "You can use widgets to build **interactive GUIs** for your notebooks.  \n",
      "You can also use widgets to **synchronize stateful and stateless information** between Python and JavaScript."
     ]
    },
    {
     "cell_type": "heading",
     "level": 2,
     "metadata": {},
     "source": [
      "Using widgets  "
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "To use the widget framework, you need to **import `IPython.html.widgets`**."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "from IPython.html.widgets import *"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [],
     "prompt_number": 1
    },
    {
     "cell_type": "heading",
     "level": 3,
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "repr"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {},
     "source": [
      "Widgets have their own display `repr` which allows them to be displayed using IPython's display framework.  Constructing and returning an `IntSliderWidget` automatically displays the widget (as seen below).  Widgets are **displayed inside the `widget area`**, which sits between the code cell and output.  **You can hide all of the widgets** in the `widget area` by clicking the grey *x* in the margin."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "IntSliderWidget()"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [],
     "prompt_number": 2
    },
    {
     "cell_type": "heading",
     "level": 3,
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "display()"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {},
     "source": [
      "You can also explicitly display the widget using `display(...)`."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "from IPython.display import display\n",
      "w = IntSliderWidget()\n",
      "display(w)"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [],
     "prompt_number": 3
    },
    {
     "cell_type": "heading",
     "level": 3,
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "Multiple display() calls"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {},
     "source": [
      "If you display the same widget twice, the displayed instances in the front-end **will remain in sync** with each other."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "display(w)"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [],
     "prompt_number": 4
    },
    {
     "cell_type": "heading",
     "level": 2,
     "metadata": {},
     "source": [
      "Why does displaying the same widget twice work?"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "Widgets are **represented in the back-end by a single object**.  Each time a widget is displayed, **a new representation** of that same object is created in the front-end.  These representations are called **views**.\n",
      "\n",
      "** Insert Backend-Frontend Views Figure **"
     ]
    },
    {
     "cell_type": "heading",
     "level": 3,
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "Closing widgets"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {},
     "source": [
      "You can close a widget by calling its `close()` method."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "w.close()"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [],
     "prompt_number": 5
    },
    {
     "cell_type": "heading",
     "level": 2,
     "metadata": {},
     "source": [
      "Widget properties"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "All of the IPython widgets **share a similar naming scheme**.  To read the value of a widget, you can query its `value` property."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "w.value"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [
      {
       "metadata": {},
       "output_type": "pyout",
       "prompt_number": 6,
       "text": [
        "0"
       ]
      }
     ],
     "prompt_number": 6
    },
    {
     "cell_type": "markdown",
     "metadata": {},
     "source": [
      "Similarly, to set a widget's value, you can set its `value` property."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "w.value = 100"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [],
     "prompt_number": 7
    },
    {
     "cell_type": "heading",
     "level": 3,
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "Keys"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {},
     "source": [
      "In addition to `value`, most widgets share `keys`, `description`, `disabled`, and `visible`.  To see the entire list of synchronized, stateful properties, of any specific widget, you can **query the `keys` property**."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "w.keys"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [
      {
       "metadata": {},
       "output_type": "pyout",
       "prompt_number": 8,
       "text": [
        "['_view_name',\n",
        " 'orientation',\n",
        " 'msg_throttle',\n",
        " 'min',\n",
        " 'max',\n",
        " '_css',\n",
        " 'value',\n",
        " 'readout',\n",
        " 'disabled',\n",
        " 'visible',\n",
        " 'step',\n",
        " 'description']"
       ]
      }
     ],
     "prompt_number": 8
    },
    {
     "cell_type": "heading",
     "level": 3,
     "metadata": {},
     "source": [
      "Shorthand for setting the initial values of widget properties"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "While creating a widget, you can set some or all of the initial values of that widget by **defining them as keyword arguments in the widget's constructor** (as seen below)."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "TextWidget(value='Hello World!', disabled=True)"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [],
     "prompt_number": 9
    },
    {
     "cell_type": "heading",
     "level": 2,
     "metadata": {},
     "source": [
      "Linking two similar widgets"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "If you need to display the same value two different ways, you'll have to use two different widgets.  Instead of **attempting to manually synchronize the values** of the two widgets, you can use the `traitlet` `link` function **to link two properties together**.  Below, the values of three widgets are linked together."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "from IPython.utils.traitlets import link\n",
      "a = FloatTextWidget()\n",
      "b = FloatSliderWidget()\n",
      "c = FloatProgressWidget()\n",
      "display(a,b,c)\n",
      "\n",
      "\n",
      "mylink = link((a, 'value'), (b, 'value'), (c, 'value'))"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [],
     "prompt_number": 10
    },
    {
     "cell_type": "heading",
     "level": 3,
     "metadata": {},
     "source": [
      "Unlinking widgets"
     ]
    },
    {
     "cell_type": "markdown",
     "metadata": {
      "slideshow": {
       "slide_type": "slide"
      }
     },
     "source": [
      "Unlinking the widgets is simple.  All you have to do is call `.unlink` on the link object."
     ]
    },
    {
     "cell_type": "code",
     "collapsed": false,
     "input": [
      "mylink.unlink()"
     ],
     "language": "python",
     "metadata": {},
     "outputs": [],
     "prompt_number": 11
    },
    {
     "cell_type": "markdown",
     "metadata": {},
     "source": [
      "[Index](Index.ipynb) - [Next](Widget List.ipynb)"
     ]
    }
   ],
   "metadata": {}
  }
 ]
}