Combine plots and tables with linked selection and data source selection by widget

I’m trying to get a linked selection from two plots to also update in a table from a multi-dimensional data set. I’m also using drop down selection to choose the plot x-variables.

I can either get the table to reflect what’s selected, or to show the new variable, but not both, eg:

import numpy as np
import pandas as pd
import panel as pn
import holoviews as hv
import hvplot.pandas

from bokeh.sampledata.autompg import autompg
autompgi = autompg.interactive()

select_column1  = pn.widgets.Select(name='Data set 1', options=list(autompg.columns))
select_column2  = pn.widgets.Select(name='Data set 2', options=list(autompg.columns),value='displ')

ls = hv.link_selections.instance()

@pn.depends(select_column1,select_column2)
def plots(col1,col2):    
    return ls(autompg.hvplot.scatter(x=col1,y='cyl',tools=['box_select', 'lasso_select'],width=500)\
              +autompg.hvplot.scatter(x=col2,y='cyl',tools=['box_select', 'lasso_select'],width=500))

@pn.depends(select_column1,select_column2)
def table_sel(col1,col2):
    
    ## Can select different data sources in columns for the scatter plots and table, but can't restrict
    ## table to linked selection.
    # table = ls.filter(autompg[[col1,col2,'cyl']]).hvplot.table()     
        
    ## Can select different data sources in columns for the scatter plots and restrict the table to
    ## linked selection. But table doesn't change when choosing new data source.
    table = autompgi[[col1,col2,'cyl']].pipe(ls.filter, selection_expr=ls.param.selection_expr)
    return table
    
pn.Column(
    pn.Row(select_column1,select_column2),
    plots,
    table_sel
)

Is there a way to do this?

Thanks for the report, which I can reproduce.

For the second case, it looks to me like a bug in Panel or hvPlot, because updating the panel based on the widget works fine for a plain Pandas dataframe:

import panel as pn
from bokeh.sampledata.autompg import autompg
pn.extension()

s = pn.widgets.Select(options=list(autompg.columns))
def t(col1): return autompg[[col1,'cyl']]
    
pn.Column(s, pn.bind(t, col1=s))

But fails to update the table when it’s an hvPlot .interactive object:

import panel as pn, hvplot.pandas
from bokeh.sampledata.autompg import autompg
pn.extension()

s = pn.widgets.Select(options=list(autompg.columns))
autompg = autompg.interactive()
def t(col1): return autompg[[col1,'cyl']]
    
pn.Column(s, pn.bind(t, col1=s))

It does look like the callback is being executed in both cases (if I put e.g. if col1!='mpg': 1/0 in the callback and watch the JS console), but the web page doesn’t get updated to the new table. I don’t see any other messages on the JS console. Seems like a bug to report on Panel, to me!

For the first case, if I watch the JS console, there are various messages printed that suggest that the linked selections filtering is getting confused by applying a filter to data that has different columns defined than it expects. I can’t immediately tell if that’s a bug (i.e., whether link_selections should silently proceed if some columns are missing) or if it’s a misuse of link_selections and there’s a different way to make it work.

1 Like