-
-
Notifications
You must be signed in to change notification settings - Fork 2.7k
first pass at plotly-ipython graph widget #171
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
with open(js_widget_file) as f: | ||
js_widget_code = f.read() | ||
|
||
display(Javascript(js_widget_code)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
not sure what the best way to inject JS code into ipython is. we should only have to do this once - maybe require.js
can help us here?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Or maybe do it on import?
So far so good from my end. 👍 One thing that caught my eyes though: could patterns like from IPython.html.widgets import IntSliderWidget
from plotly.widgets import Graph
import plotly.plotly as py
from IPython.display import display
# ....
slider = IntSliderWidget(min=0,max=20,step=0.1)
slider.on_trait_change(make_cagraph = Graph(py.plot([{}], filename='taylor series widget', auto_open=False))llback(slider, graph), 'value')
display(slider)
display(graph) be abstracted a little bit more ? Maybe have something like: from plotly.widgets import Graph, Slider
graph = Graph(py.plot([{}], filename='taylor series widget', auto_open=False))
slider = Slider(min=0, max=20, step=0.1)
slider.on_trait_change(make_callback(slder, graph), 'value')
slider.display()
graph.display() would make things easier for users that never played around with IPython widgets before. |
Alright, digging in :) Where/how does the restyle/relayout call get sent to plotly? Is this what's happening? (1) User calls |
Can we (should we) change Say, using So, instead of restyle and relayout, users can do things like:
Under the hood, we can still call relayout and restyle, but we might want to consider some convenience functions. |
@theengineear re #171 (comment) - on (3) yeah, the JS code communicates to the embedded Plotly iframe through the postMessage protocol and listens to messages sent from the events in the iframe on the |
@theengineear re #171 (comment), we'll want to keep the |
we could have something more gnarly like a This sort of feels like moving towards @BRONSOLO 's
Yikes! |
@chriddyp , is there a way to add a completely new trace to a graph? I naively tried to restyle a blank graph, but realized that that's not workable. Along these lines, we could also offer to just serve up a blank iframe for people to build on. Thoughts? |
@theengineear there isn't right now, which is pretty annoying! |
This is something that needs to be built into the js, yeah? Same as the remove-trace? |
yeah exactly |
@chriddyp , i added in the framework for add/delete/move traces (it's not working yet because that PR isn't pulled into master on streambed) the syntax may also change, i opened up a discussion about how we format |
Also, this doesn't work for me and I'm confused why :( import random
import plotly.plotly as py
from plotly.graph_objs import *
from plotly.widgets import Graph
plotly_url = py.plot([Scatter()], filename='blank', auto_open=False)
graph = Graph(plotly_url)
def click_handler(*args, **kwargs):
graph.restyle({'y': [[random.random() for _ in range(10)]]}, traces=[0])
graph.on_click(click_handler)
graph Also, also, it's not clear in the docs, but can you remove a click handler once you assign it? or do they overwrite themselves? |
Have you taken a peek as the dev-tools console for this stuff, btw? full of errors and warnings. This is just a warning, but we could probably clean it up by sending a string instead of an object? Is that reasonable? Not sure what to do about this one... it just happens a bunch of times and then eventually stops complaining an works: |
Another thing, I opened the dev tools initially to try and debug why pointing python at my local streambed wasn't working, which I haven't figured out--i thought i'd just ask :) Is 'https://plot.ly' hardcoded for us in python, or in frontend js? |
k, found where the 'https://plot.ly' was hiding in graphWidget.js I'm going to pass that into graphWidget.js now, but I'm also going to need a reference from graph_widget.py. for now that means i need to import plotly.py (ew)... This is exactly why we should really create a new |
@chriddyp , the above commit should fix communication with local plotly instances. This will seriously improve development when changes need to be made to plotly frontent js code and the python-api widget code. NOTE (this is a little annoying... the iframe js code is cached so every time you do make a change, you need to clear your cache) took me a second to realize that earlier and thought I'd mention it here. |
All of our messages seem to be being sent twice! Not sure where that’s coming from. This is a temporary fix that synced with the new frontend postMessage hopefully we can revert this.
See #177 for the updates to this widgets branch. |
Conflicts: plotly/widgets/graph_widget.py
Widgets update syntax
Re: #171 (comment) For graphJson, I'm thinking of somehow allowing an 'attributes' object that would just return the specified keys. For now, we can filter this in postMessage so that postMessage requests are stable, but eventually it will be better to make graphJson more flexible, but that might be a bigger refactor than i can do today. Therefore: // message for getting the *full* figure
{
'task': 'getAttributes',
}
// message for getting certain attributes
{
'task': 'getAttributes',
'attributes': ['data[0].opacity', 'layout.title']
}
// message for getting defaults if user didn't specify
{
'task': 'getAttributes',
'useDefaults': True
}
// message for getting data only (no layout)
{
'task': 'getAttributes',
'attributes': ['data']
}
// message for getting layout only (no data)
{
'task': 'getAttributes',
'attributes': ['layout']
} Something like this seem okay? There's already a postMessage |
|
to put it on record, we're going to go with the opposite logic, |
first pass at plotly-ipython graph widget
boom! On Thu, Jan 22, 2015 at 5:34 PM, chriddyp [email protected] wrote:
|
usage: http://nbviewer.ipython.org/gist/chriddyp/98a3d27a33ecc044a393
animation example - taylor series of sine (values update as you pan around) http://nbviewer.ipython.org/gist/chriddyp/9600fa8314e70ce89f06

cc @theengineear , @etpinard , @msund , @jackparmer
pretty clean, pretty fun!
getFigure
postMessage spec, maybe implementation?