Change number of legend items in javascript

I posted this to SO, but getting no responses, decided maybe here was a better venue:

Basically I have a page I want to switch between data sets in the browser without communicating with the server (my users will be switching back and forth a lot). I have a bokeh chart that starts out with 7 line series in a chart. A select widget changes the data and shows only 4 series via a customjs callback

for i in range(7):
    if i < 4:
        js_code += """data['y%d']=data.%s;""" % (i,newseriesnames[i])
    js_code += """line%d.visible = %s;""" % (i,'true' if i < 4 else 'false')
js_code += 'source.change.emit();'
callback = CustomJS(args = args,code=js_code)
select.js_on_change('value',callback)

``

where line0 through line6 are the lines in the plot linked to data objects data[‘y0’] through data[‘y6’] and select is a bokeh selector widget. This works great in the bokeh chart itself, but it doesn’t update the legend. The legend is always the same as when it is first rendered. It retains the 7 elements, even when they are hidden in the chart.

Some things that don’t seem to work:

  1. Setting legend.items[4].renderers[0].visible=false
  2. Setting legend.items[4].visible=false
  3. Calling legend.change.emit(), legend.items[4].change.emit(), and legend.items[4].renderers[0].change.emit()
  4. Overwriting the legend with a different one made using bokeh’s python Legend() method
    A workaround is, in python create a new legend for every possible set of line charts
for group_name in group_names:
    legend_items[group_name] = make_legend(group_name)
    plot.add_layout(legend_items[group_name], 'right')
for g in legend_items:
    legend_items[g].visible = False
legend_items[group_names[0]].visible = True

``

and then in the callback turn off all but the one you want to show

for f in group_names:
    js_code += """legend_items['%s'].visible = false;""" % f
js_code += 'legend_items[f].visible = true;'

``

This works but seems inelegant. How would someone tackle this?

This is still an open issue:

  https://github.com/bokeh/bokeh/issues/589

Bryan

···

On Sep 16, 2018, at 13:52, [email protected] wrote:

I posted this to SO, but getting no responses, decided maybe here was a better venue:

https://stackoverflow.com/questions/52122984/bokeh-hiding-legend-items-in-javascript-callback

Basically I have a page I want to switch between data sets in the browser without communicating with the server (my users will be switching back and forth a lot). I have a bokeh chart that starts out with 7 line series in a chart. A select widget changes the data and shows only 4 series via a customjs callback

for i in range(7):
    if i < 4:
        js_code += """data['y%d']=data.%s;""" % (i,newseriesnames[i])
    js_code += """line%d.visible = %s;""" % (i,'true' if i < 4 else 'false')
js_code += 'source.change.emit();'
callback = CustomJS(args = args,code=js_code)
select.js_on_change('value',callback)

where line0 through line6 are the lines in the plot linked to data objects data['y0'] through data['y6'] and select is a bokeh selector widget. This works great in the bokeh chart itself, but it doesn't update the legend. The legend is always the same as when it is first rendered. It retains the 7 elements, even when they are hidden in the chart.

Some things that don't seem to work:
  • Setting legend.items[4].renderers[0].visible=false
  • Setting legend.items[4].visible=false
  • Calling legend.change.emit(), legend.items[4].change.emit(), and legend.items[4].renderers[0].change.emit()
  • Overwriting the legend with a different one made using bokeh's python Legend() method
A workaround is, in python create a new legend for every possible set of line charts

for group_name in group_names:
    legend_items[group_name] = make_legend(group_name)
    plot.add_layout(legend_items[group_name], 'right')
for g in legend_items:
    legend_items[g].visible = False
legend_items[group_names[0]].visible = True

and then in the callback turn off all but the one you want to show

for f in group_names:
    js_code += """legend_items['%s'].visible = false;""" % f
js_code += 'legend_items[f].visible = true;'

This works but seems inelegant. How would someone tackle this?

--
You received this message because you are subscribed to the Google Groups "Bokeh Discussion - Public" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [email protected].
To post to this group, send email to [email protected].
To view this discussion on the web visit https://groups.google.com/a/continuum.io/d/msgid/bokeh/f65e8f27-baf3-4ebb-9337-f3751cd3b740%40continuum.io.
For more options, visit https://groups.google.com/a/continuum.io/d/optout.