0

I am developing in Javascript to render a table using a DataTables (Table plug-in for jQuery). I am also using Bootstrap Multiselect (https://github.com/davidstutz/bootstrap-multiselect) to filter the table. I would like to re-render my BokehJS plot everytime the table is re-drawn. I have hooked up the correct calls but I am also calling Bokeh.Plotting.show to re-render the graph. This forces me to remove the last created div to avoid multiple graphs plotted. I am new to the JS side of Bokeh and wanted to understand if there is a cleaner method to update the plot in JS?

    var eventFired = function ( type ) {
    //var n = $('#demo_info')[0];
    //n.innerHTML += '<div>'+type+' event - '+new Date().getTime()+'</div>';
    //n.scrollTop = n.scrollHeight;   

    var plt = Bokeh.Plotting;

    // set up some data
    var M = 25;
    var xx = [];
    var yy = [];
    var colors = [];
    var radii = [];
    for (var y = 0; y <= M; y += 4) {
        for (var x = 0; x <= M; x += 4) {
            xx.push(x * (Math.random() +0.5));
            yy.push(y * (Math.random() +0.5));
            colors.push(plt.color(50+8*x, 30+8*y, 150));
            radii.push(Math.random() * 0.4 + 1.7)
        }
    }

    // create a data source
    var source = new Bokeh.ColumnDataSource({
        data: { x: xx, y: yy, radius: radii, colors: colors }
    });

    // make the plot and add some tools
    var tools = "pan,crosshair,wheel_zoom,box_zoom,reset,save";
    var p = plt.figure({ title: type+' event - '+new Date().getTime(),
                        height: 300,
                        width: 300,
                        tools: tools });

    // call the circle glyph method to add some circle glyphs
    var circles = p.circle({ field: "x" }, { field: "y" }, {
        source: source,
        radius: radii,
        fill_color: colors,
        fill_alpha: 0.6,
        line_color: null
    });

    //remove old plot on update conditions
    $('.bk-root').remove();

    // Show the plot, appending it to the end of the current
    // section of the document we are in.

    Bokeh.Plotting.show(p, document.getElementById('myplot'));
    //To Do: add in transition to improve the UI appearance
}

And here is the the datatable setting up the call back to the BokehJS script.

</script>
      $('#table').DataTable({
    responsive: {
        details: {
            display: $.fn.dataTable.Responsive.display.modal( {
                header: function ( row ) {
                    var data = row.data();
                    return 'Details for '+data[0]+' '+data[1];
                }
            } ),
            renderer: $.fn.dataTable.Responsive.renderer.tableAll( {
                tableClass: 'table'
            } )
        }
    },
    paginate: false,
    info: false,
    paging: true,
    autoWidth: true,
    dom: '<"dt-buttons">Bf<"clear">lirtp',
    "buttons": [ 'copy', 'csv', 'excel' ],
  }).on( 'draw.dt',   function () { eventFired( 'Draw' ); } );

Lastly, is there a good method to update the plot via a transition effect to improve the appearance of the re-plotting?

1 Answer 1

1

I eventually figured out all of the components in the process in a modified use case compared to the one shown above. In my present approach I needed to utilize my source data and emit a 'change' trigger.

source.data.factors = [my new factor list]
source.trigger('change');

The new factor list based on the jQuery datatable can be obtained as followed.

$('mytable').DataTable().columns(0, {search: 'applied'}).data()[0]

Also in my use case I am working with a categorical axis. In my specific use case, my factors will dynamically change upon redraw of the graph. This can be achieved using the plot's attributes.

p.attributes.x_range.factors = [ my new factor list from my updated source data]

There is also no need to remove the old plot, and the added plus is the redraw is very fast for my simple plots.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.