Could we have Plotly FigureWidget support?

Hi @givemecoffee,

Iā€™ve been thinkering too with the idea of a plotly scatterplot where you can select some points and return their indices to filter data for the next plot. I donā€™t have a definitive, ā€œgenericā€ solution for this, but if youā€™re building only for your specific needs it should be possible to use Components to control Plotly.js plots directly.


As an introduction, plotly.py is a Python client which generates a JSON spec that plotly.js consumes to render a plot. Actually streamlit.plotly_graph dumps the JSON spec from the Figure and passes it to react-plotly for rendering :slight_smile: . You could easily replicate this using Streamlit components to train yourself !

Then thereā€™s FigureWidget which is another Python class that renders Plotly graphs but in the ipywidgets model. At first glance, when rendering FigureWidget, a plotly.js graph is mounted and communication between the plotly.js plot and Python FigureWidget is done through ipywidgetsā€™ event model.
Thereā€™s no ā€œdump Python class in a JSON format to pass it to plotly.js for renderingā€. FigureWidget is tightly coupled to Ƭpywidgets event model so that when you do widget_object.data[0].on_selection(fn_to_cut_down_df) it sends a custom event to plotly.js through ipywidgets, then the JS plot updates itself with this info.
You could try and extract all the callbacks events from FigureWidget to try and pass them to react-plotly with Streamlit Components but ā€¦ Iā€™m not sure, it looks time-consuming and demanding at first glance :confused: but that may be my ignorance of how ipywidgets work.


For now the faster but very specific approaches would be :

  1. You can build a single specific Plotly.js component with a lasso selection event inside, have Python send a dataframe through Components to your lasso interactive plot and return indices out from the selection, as you suggest actually, and then use those indices to filter data for the next plot.
  2. You could build one single component which contains all your plotly.js plots and any cross interactivity in JS, so you encapsulate everything in a single Component with multiple plots.

I donā€™t have an answer for integrating ipywidgets in Streamlit Components, because I donā€™t know much how we can capture their event system. We have opened a discussion on this here Ipywidgets (WIP) if you have info on this. If anyone has a better idea Iā€™m interested too :slight_smile:

Fanilo

2 Likes