def test_callback_property_executes(self, bokeh_model_page): button = Button(css_classes=['foo']) button.callback = CustomJS(code=RECORD("clicked", "true")) page = bokeh_model_page(button) button = page.driver.find_element_by_css_selector('.foo .bk-btn') button.click() results = page.results assert results == {'clicked': True} assert page.has_no_console_errors()
def upload_button(): ''' Handles file selection via JavaScript. :returns: bokeh.models.Button ''' file_source.on_change('data', callback_file_upload) button = Button(label="Choose file..", width=500) button.callback = CustomJS(args=dict(file_source=file_source), code=""" function read_file(filename) { var reader = new FileReader(); reader.onload = load_handler; reader.onerror = error_handler; // readAsDataURL represents the file's data as a base64 encoded string reader.readAsDataURL(filename); } function load_handler(event) { var b64string = event.target.result; file_source.data = {'file_contents' : [b64string], 'file_name':[input.files[0].name]}; file_source.trigger("change"); } function error_handler(evt) { if(evt.target.error.name == "NotReadableError") { alert("Can't read file!"); } } var input = document.createElement('input'); input.setAttribute('type', 'file'); input.onchange = function(){ if (window.FileReader) { read_file(input.files[0]); } else { alert('FileReader is not supported in this browser'); } } input.click(); """) return button
def show_hide_button(in_lab, checkbox_name, checkbox_code, iterable, width=100): ''' Button to trigger specific checkboxes in a checkboxgroup if they contain the string 'in_lab' Input: - name : string of character contained in labels of checkboxes to be checked - checkbox_name : the variable name of your checkbox group - checkbox_code : the callback code of your checkbox group ( thus the code of the checkbox group should NOT use cb_obj ) - iterable : list of (key,value) tuples for the arguments of the button callback, the checkbox group must be one of them Output: - button that check/uncheck checkboxes with 'in_lab' in their label ''' button = Button( label='Hide %s' % in_lab, width=width, button_type='danger', name=in_lab) # button to check/uncheck all boxes with 'prof' button_success_code = """new_active = %s.active.slice(); for (i=0;i<%s.labels.length;i++) {if (%s.labels[i].includes('%s') && !(new_active.includes(i))) {new_active.push(i)}};new_active.sort();%s.active = new_active.slice();""" % ( checkbox_name, checkbox_name, checkbox_name, in_lab, checkbox_name) + checkbox_code button_danger_code = """new_active = %s.active.slice(); for (i=0;i<%s.labels.length;i++) {if (%s.labels[i].includes('%s') && %s.active.includes(i)) {new_active.splice(new_active.indexOf(i),1)}};%s.active = new_active.slice();""" % ( checkbox_name, checkbox_name, checkbox_name, in_lab, checkbox_name, checkbox_name) + checkbox_code button_code = """if (cb_obj.button_type.includes("danger")){""" \ + button_danger_code\ + """cb_obj.button_type = "success";cb_obj.label = "Show %s";} else {""" % in_lab \ + button_success_code \ + """cb_obj.button_type = "danger";cb_obj.label = "Hide %s";}""" % in_lab button.callback = CustomJS(args={key: value for key, value in iterable}, code=button_code) return button
def test_data_table_selected_highlighting(output_file_url, selenium, screenshot): # Create a DataTable and Button that sets a selection data = dict(x = list(range(10))) source = ColumnDataSource(data=data) columns = [TableColumn(field="x", title="X")] data_table = DataTable(source=source, columns=columns) button = Button(label="Click") button.callback = CustomJS(args=dict(source=source), code=""" source['selected']['1d'].indices = [1, 2] source.change.emit(); """) # Save the table and start the test save(column(data_table, button)) selenium.get(output_file_url) assert has_no_console_errors(selenium) # Click the button to select the rows button = selenium.find_element_by_class_name('bk-bs-btn') button.click() screenshot.assert_is_valid()
extractVelocityZC = Button(label="Extract Velocity", button_type="success") extractVelocityZC.on_click(CalculateVelocity) periodFractions = CheckboxButtonGroup(labels=[ "1/4 Period", "1/2 Period", "3/4 Period", "1 Period", "4/3 Period", "3/2 Period" ], active=[0, 0, 0, 1, 0, 0], name="Period Fractions", width=150) downloadVelocityTraceZC = Button(label="Download Velocity Trace", button_type="success") downloadVelocityTraceZC.callback = CustomJS( args=dict(vel_source=ds_zeroCrossing_velocity, base_source=ds_splinefit_peaks), code=open(join(dirname(__file__), "download.js")).read()) def FitVelocity(attr, old, new): # Perform a spline fit to the velocity data x = ds_zeroCrossing_velocity.data['x'][1:] y = ds_zeroCrossing_velocity.data['velocity'] gSmooth = sp.ndimage.filters.gaussian_filter1d(y, velSmoothSlider.value) ds_zeroCrossing_velocity.data = dict( x=[ds_analysis.data['x'][breakoutPt]] + x, velocity=y, smoothed=[0.0] + list(gSmooth)) #ipdb.set_trace()
length_plot.segment( x0='bh_tsne_x', y0=0, x1='bh_tsne_x', y1='length', line_width=1, line_cap='round', line_color=factor_cmap( 'cluster', factors=list(df.cluster.unique()), palette=crcolor, ), source=source, name='length', ) length_plot.add_layout(Title(text="Length vs. Contig", align="center"), "left") length_plot.xgrid.grid_line_color = None length_plot.yaxis.formatter = PrintfTickFormatter(format="%f bp") length_plot.yaxis.major_label_orientation = np.pi / 4 button = Button(label="Save selected contigs to list", button_type="success") button.callback = CustomJS(args=dict(source=contigsList), code=open( join(dirname(__file__), "download_contigs_list.js")).read()) cluster_layout = layout( children=[column(row(cluster_plot, gc_plot), row(length_plot, button))]) show(cluster_layout)
def cluster_gui(doc): global s2, s1, old_indices old_indices = [] output_file("tile.html") tile_provider = get_provider(CARTODBPOSITRON) x = [] y = [] name = [] global fig03 fig03 = figure( plot_width=400, plot_height=400, tools=["box_zoom", "wheel_zoom", "reset", "save"], title="Waveforms from current selection", ) for i, st in enumerate(stations): xm, ym = merc(st.lat, st.lon) x.append(xm) y.append(ym) name.append(st.nsl_string()) # create first subplot plot_width = 400 plot_height = 400 d = num.ones_like(x) s1 = ColumnDataSource(data=dict(x=x, y=y, ind=d, name=name)) # range bounds supplied in web mercator coordinates fig01 = figure( x_axis_type="mercator", y_axis_type="mercator", plot_width=plot_width, plot_height=plot_height, tools=[ "lasso_select", "box_select", "reset", "save", "box_zoom", "wheel_zoom" ], title="Select", ) fig01.add_tile(tile_provider) fig01.scatter("x", "y", source=s1, alpha=0.6, size=8) # create second subplot s2 = ColumnDataSource(data=dict(x=[], y=[], ind=[], name=[])) color_mapper = LinearColorMapper(palette='Magma256', low=1, high=100) fig02 = figure( x_axis_type="mercator", y_axis_type="mercator", plot_width=plot_width, plot_height=plot_height, x_range=(num.min(x), num.max(x)), y_range=(num.min(y), num.max(y)), tools=["box_zoom", "wheel_zoom", "reset", "save"], title="Stations selected for Array", ) fig02.add_tile(tile_provider) fig02.scatter("x", "y", source=s2, alpha=1, color={ 'field': 'ind', 'transform': color_mapper }, size=8) x_event, y_event = merc(event.lat, event.lon) fig01.scatter(x_event, y_event, size=8, color="red") fig02.scatter(x_event, y_event, size=8, color="red") columns = [ TableColumn(field="x", title="X axis"), TableColumn(field="y", title="Y axis"), TableColumn(field="ind", title="indices"), TableColumn(field="name", title="name"), ] table = DataTable( source=s2, columns=columns, width=400, height=600, sortable=True, selectable=True, editable=True, ) source_count = 0 callback_slider = CustomJS(code=""" source_count = slider.value; """) global slider slider = Slider(start=1, end=100, value=1, step=1, title="Array number") slider.js_on_change('value', callback_slider) s1.selected.js_on_change( "indices", CustomJS(args=dict(s1=s1, s2=s2, s3=slider, table=table), code=""" var inds = cb_obj.indices; var d1 = s1.data; var d2 = s2.data; const A = s3.value; for (var i = 0; i < inds.length; i++) { d2['x'].push(d1['x'][inds[i]]) d2['y'].push(d1['y'][inds[i]]) d2['name'].push(d1['name'][inds[i]]) d2['ind'].push(A) } s2.change.emit(); table.change.emit(); s2.data = s2.data; var inds = source_data.selected.indices; var data = source_data.data; var out = "name, x, y, ind\\n"; for (i = 0; i < inds.length; i++) { out += data['name'][inds[i]] + "," + data['x'][inds[i]] + "," + data['y'][inds[i]] + "," + data['ind'][inds[i]] + "\\n"; } var file = new Blob([out], {type: 'text/plain'}); """), ), savebutton = Button(label="Save", button_type="success") savebutton.callback = CustomJS( args=dict(source_data=s1), code=""" var inds = source_data.selected.indices; var data = source_data.data; var out = "name, x, y, ind\\n"; for (i = 0; i < inds.length; i++) { out += data['name'][inds[i]] + "," + data['x'][inds[i]] + "," + data['y'][inds[i]] + "," + data['ind'][inds[i]] + "\\n"; } var file = new Blob([out], {type: 'text/plain'}); var elem = window.document.createElement('a'); elem.href = window.URL.createObjectURL(file); elem.download = 'arrays.txt'; document.body.appendChild(elem); elem.click(); document.body.removeChild(elem); """, ) tooltips = [ ("X:", "@x"), ("Y:", "@y"), ("Array:", "@ind"), ("Station:", "@name"), ] fig01.add_tools(HoverTool(tooltips=tooltips)) fig02.add_tools(HoverTool(tooltips=tooltips)) fig03.add_tools(HoverTool(tooltips=tooltips)) endbutton = Button(label="End and proceed", button_type="success") endbutton.on_click(button_callback) clearbutton = Button(label="Clear all", button_type="success") clearbutton.on_click(clearbuttonlast_callback) clearbuttonlast = Button(label="Clear last selection", button_type="success") clearbuttonlast.on_click(clearbuttonlast_callback) clearbuttonone = Button(label="Remove one from list", button_type="success") clearbuttonone.on_click(clearbuttonone_callback) b = Button(label="Reset all plots") b.js_on_click( CustomJS(code="""\ document.querySelectorAll('.bk-tool-icon-reset[title="Reset"]').forEach(d => d.click()) """)) #layout = grid([fig01, fig02, table, fig03, slider, clearbuttonlast, clearbutton, savebutton, endbutton], ncols=3, nrows=4) global text_input text_input = TextInput(value="1", title="Array number:") buttons = column(clearbuttonlast, clearbuttonone, clearbutton, savebutton, endbutton) inputs = column(text_input, slider) layout_grid = layout([fig01, fig02, buttons], [fig03, inputs, table]) #curdoc().add_root(layout) cluster_result = [] doc.add_root(layout_grid) #global session #session = push_session(curdoc()) #curdoc().add_periodic_callback(update, 100) #session.show(layout) doc.add_periodic_callback(update, 900) curdoc().title = "Array selection"
def show_hide_button_list(keyword_dict, checkbox_code, iterable, width=100, separator='-'): """ Return a number of button that check / uncheck boxes in a CheckBoxGroup based on a keyword list and the CheckBoxGroup labels - keyword_dict: an OrderedDict of groups of keywords, each group has keyword of a specific length {key1:['abc','def','ghi',...],key2:['ab','cd',...],...} - checkbox_code: callback code of the CheckBoxGroup - iterable: list of (key,value) tuples for the arguments of the CheckBoxGroup callback, must include the CheckBoxGroup itself as ('checkbox',CheckBoxGroup) - width: width of the buttons Output: - buttons that check/uncheck checkboxes in a CheckBoxGroup if they include a certain keyword in their label - button to uncheck all the checkboxes and switch all buttons to "show" - button to check all the checkboxes and switch all buttons to "hide" """ # create a button for each keyword in keyword_dict button_list = [] for keyword in list(flatten(keyword_dict)): button_list.append( Button(label='Hide ' + keyword, name=keyword, button_type='danger', width=width)) clear_button = Button(label='Clear all', width=width) # button to uncheck all checkboxes check_button = Button(label='Check all', width=width) # button to check all checkboxes # adds the buttons to the iterable list for the callback arguments new_iterable = iterable + [('button_' + button.name, button) for button in button_list] # a string of the form '[button_a,button_b,...]' for the callback codes button_str = str(['button_' + button.name for button in button_list]).replace("'", "") button_key_code = "" # code that goes over each keyword group and button status to reconstruct the label of checkboxes to be checked / unchecked show_full_code = "show_full = [];" # the array of labels with associated checkboxes that need to be checked show_full = [] it = 0 loopid = ['i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't'] for key in keyword_dict: # loop to generate the code based on the number of keyword groups button_key_code += ''' show_%s = []; for (i=0;i<show_name.length;i++){ if(show_name[i].length==%s){show_%s.push(show_name[i])}; }; ''' % (key, str(len(keyword_dict[key][0])), key) show_full_code += "for(%s=0;%s<show_%s.length;%s++){" % ( loopid[it], loopid[it], key, loopid[it]) show_full.append('show_%s[%s]' % (key, loopid[it])) it += 1 show_full_code += "show_full.push(" + ( "+'" + separator + "'+").join(show_full) + ")" + "};" * it button_key_code += show_full_code # initial code for the buttons button_switch_code = """ if (cb_obj.button_type.includes("danger")){ cb_obj.button_type = "success"; cb_obj.label = "Show "+cb_obj.name; } else { cb_obj.button_type = "danger"; cb_obj.label = "Hide "+cb_obj.name; } button_list = """ + button_str + """; """ # initial code for the "clear all" button clear_switch_code = """ button_list = """ + button_str + """; for (i=0;i<button_list.length;i++){ button_list[i].button_type = "success" button_list[i].label = "Show "+button_list[i].name } """ # initial code for the "check all" button check_switch_code = """ button_list = """ + button_str + """; for (i=0;i<button_list.length;i++){ button_list[i].button_type = "danger" button_list[i].label = "Hide "+button_list[i].name } """ button_code = button_switch_code + """ show_name = []; for(i=0;i<button_list.length;i++) { if(button_list[i].button_type.includes("danger")) {show_name.push(button_list[i].name)}; }; """ + button_key_code + """ new_active = []; for (i=0;i<show_full.length;i++){ for(j=0;j<checkbox.labels.length;j++){ if (checkbox.labels[j].includes(show_full[i])) {new_active.push(j);}; }; }; new_active.sort(); checkbox.active = new_active.slice(); """ + checkbox_code for button in button_list: button.callback = CustomJS( args={key: value for key, value in new_iterable}, code=button_code) clear_button_code = button_code.replace(button_switch_code, clear_switch_code) clear_button.callback = CustomJS( args={key: value for key, value in new_iterable}, code=clear_button_code) check_button_code = button_code.replace(button_switch_code, check_switch_code) check_button.callback = CustomJS( args={key: value for key, value in new_iterable}, code=check_button_code) return [clear_button, check_button] + button_list
# inspiration for this code: # credit: https://stackoverflow.com/users/8412027/joris # via: https://stackoverflow.com/questions/31824124/is-there-a-way-to-save-bokeh-data-table-content # note: savebutton line `var out = "x, y\\n";` defines the header of the exported file, # headers are helpful to have for downstream processing (e.g. in pandas or another python script). savebutton = Button(label="Save", button_type="success") savebutton.callback = CustomJS( args=dict(source_data=s1), code=""" var inds = source_data.selected.indices; var data = source_data.data; var out = "x, y\\n"; for (i = 0; i < inds.length; i++) { out += data['x'][inds[i]] + "," + data['y'][inds[i]] + "\\n"; } var file = new Blob([out], {type: 'text/plain'}); var elem = window.document.createElement('a'); elem.href = window.URL.createObjectURL(file); elem.download = 'selected-data.txt'; document.body.appendChild(elem); elem.click(); document.body.removeChild(elem); """, ) # add Hover tool # define what is displayed in the tooltip tooltips = [ ("X:", "@x"), ("Y:", "@y"), ("static text", "static text"),
def doc_maker(): ''' make the whole document ''' global spt_data, custom_path curdoc().clear() # removes everything in the current document # dropdown to select a spectrum select_spectrum = Select(title="Select a spectrum:", value='', options=[''] + sorted(os.listdir(spec_path)), name="select_spectrum", width=200) # textinput to give the full path to the location of spectra path_input = TextInput(title='Spectra folder', width=200, name="path_input") path_input.on_change('value', update_spec_path) # button to load the spectrum selected in the 'select_spectrum' dropdown load_button = Button(label='Load spectrum', width=200, css_classes=["custom_button"]) load_button.on_click(load_spectrum) if spt_data == {}: curdoc().add_root(widgetbox(path_input, select_spectrum, load_button)) if custom_path: path_input.value = custom_path else: path_input.value = spec_path return spectrum = spt_data['cur_spec'] header = spt_data[spectrum]['header'] species = np.array([spt_data[spectrum]['columns'][var] for var in header]) SZA = str(spt_data[spectrum]['sza']) zobs = str(spt_data[spectrum]['zobs']) freq = species[0] # the frequency list tm = species[1] # measured transmittance list tc = species[2] # calculated transmittance list cont = species[3] # continuum not_gas = 4 # number of column that are not retrieved species residuals = spt_data[spectrum]['resid'] # 100*(calculated - measured) sigma_rms = spt_data[spectrum]['rms_resid'] # sqrt(mean(residuals**2)) # spectrum figure fig = figure(name="spec_fig", title=spectrum + '; SZA=' + SZA + '; zobs=' + zobs + 'km; %resid=100*(Measured-Calculated); RMSresid=' + ('%.4f' % sigma_rms) + '%', plot_width=1000, plot_height=400, tools=TOOLS, y_range=Range1d(-0.04, 1.04), outline_line_alpha=0, active_inspect="crosshair", active_drag="box_zoom") # residual figure fig_resid = figure(name="resid_fig", plot_width=1000, plot_height=150, x_range=fig.x_range, tools=TOOLS, y_range=Range1d(-3, 3), outline_line_alpha=0, active_inspect="crosshair", active_drag="box_zoom") # axes labels fig_resid.xaxis.axis_label = u'Wavenumber (cm\u207B\u00B9)' fig_resid.yaxis.axis_label = '% Residuals' fig.yaxis.axis_label = 'Transmittance' #fig.xaxis.axis_label = u'Wavenumber (cm\u207B\u00B9)' for elem in [fig, fig_resid]: elem.yaxis.axis_label_text_font_size = "14pt" elem.yaxis.major_label_text_font_size = "13pt" elem.xaxis.axis_label_text_font_size = "14pt" elem.xaxis.major_label_text_font_size = "13pt" N_plots = list( range(len(species) - 2) ) # a range list from 0 to the number of plots, used by the checkbox group # group of checkboxes that will be used to toggle line and HoverTool visibility checkbox = CheckboxGroup(labels=header[3:] + ['Measured', 'Calculated'], active=N_plots, width=200) # plotting species lines plots = [] for j in range(len(species) - not_gas): try: plots.append( fig.line(x=freq, y=species[j + not_gas], color=colors[header[j + not_gas]], line_width=2, name=header[j + not_gas])) except KeyError: print( 'KeyError:', header[j + not_gas], 'is not specified in the "colors" dictionary, you need to add it with an associated color' ) sys.exit() # each line has a associated hovertool with a callback that looks at the checkboxes status for the tool visibility. fig.add_tools( HoverTool(mode='vline', line_policy='prev', renderers=[plots[j]], names=[header[j + not_gas]], tooltips=OrderedDict([('name', header[j + not_gas]), ('index', '$index'), ('(x;y)', '(@x{0.00} ; @y{0.000})') ]))) # adding the measured spectrum plots.append(fig.line(x=freq, y=tm, color='black', line_width=2, name='Tm')) fig.add_tools( HoverTool(mode='vline', line_policy='prev', renderers=[plots[j + 1]], names=['Tm'], tooltips=OrderedDict([('name', 'Measured'), ('index', '$index'), ('(x;y)', '(@x{0.00} ; @y{0.000})')]))) # adding the calculated spectrum plots.append( fig.line(x=freq, y=tc, color='chartreuse', line_width=2, name='Tc')) #fig.add_tools( HoverTool(mode='vline',line_policy='prev',renderers=[plots[j+2]],names=['Tc'],tooltips=OrderedDict( [('name','Calculated'),('index','$index'),('(x;y)','(@x{0.00} ; @y{0.000})')] )) ) # adding the continuum #plots.append(fig.line(x=freq,y=cont,color='#FF3399',line_dash='dashed',line_width=2,name='Cont')) #fig.add_tools( HoverTool(mode='vline',line_policy='prev',renderers=[plots[j+1]],names=['Cont'],tooltips=OrderedDict( [('name','Continuum'),('index','$index'),('(x;y)','(@x{0.00} ; @y{0.000})')] )) ) # legend outside of the figure fig_legend = Legend(items=[(header[j + not_gas], [plots[j]]) for j in range(len(species) - not_gas)] + [('Measured', [plots[-2]]), ('Calculated', [plots[-1]])], location=(0, 0), border_line_alpha=0) fig.add_layout(fig_legend, 'right') fig.legend.click_policy = "hide" fig.legend.inactive_fill_alpha = 0.6 # now the residual figure fig_resid.line(x=freq, y=residuals, color='black', name='residuals') fig_resid.line(x=freq, y=np.zeros(len(freq)), color='red') fig_resid.add_tools( HoverTool(mode='vline', line_policy='prev', names=['residuals'], tooltips={ 'index': '$index', '(x;y)': '($x{0.00} ; $y{0.000})' })) # set up a dummy legend for the residual figure so that it aligns with the spectrum figure dummy = fig_resid.line(x=freq, y=[0 for i in range(len(freq))], color='white', visible=False, alpha=0) fig_resid_legend = Legend(items=[(' ', [dummy])], location=(0, 0), border_line_alpha=0) fig_resid.add_layout(fig_resid_legend, 'right') # checkbox group callback checkbox_iterable = [('p' + str(i), plots[i]) for i in N_plots] + [('checkbox', checkbox)] checkbox_code = ''.join([ 'p' + str(i) + '.visible = checkbox.active.includes(' + str(i) + ');' for i in N_plots ]) checkbox.callback = CustomJS( args={key: value for key, value in checkbox_iterable}, code=checkbox_code) # button to uncheck all checkboxes clear_button = Button(label='Hide all lines', width=200) clear_button_code = """checkbox.active=[];""" + checkbox_code clear_button.callback = CustomJS( args={key: value for key, value in checkbox_iterable}, code=clear_button_code) # button to check all checkboxes check_button = Button(label='Show all lines', width=200) check_button_code = """checkbox.active=""" + str( N_plots) + """;""" + checkbox_code check_button.callback = CustomJS( args={key: value for key, value in checkbox_iterable}, code=check_button_code) # extension for the saved file name based on the path to spectra ext = custom_path.split(os.sep)[-2] # title div div = Div( text='<p align="center"><font size=4><b>{}</b></font></p>'.format(ext), width=fig.plot_width - 100) add_vlinked_crosshairs(fig, fig_resid) sub_grid = gridplot([[fig], [fig_resid], [div]], toolbar_location="left") # button to activate/deactivate hover tools hover_button = Button(label='Enable hover tools', button_type='success', width=200) hover_list = [i for i in sub_grid.select({"type": HoverTool})] # in 'comp' mode, each plot has a different hover tool, I hide them and this button will click them all at once. hover_button_code = """ if(cb_obj.button_type.includes("success")){ cb_obj.button_type = 'warning'; cb_obj.label = 'Disable hover tools' } else { cb_obj.button_type = 'success'; cb_obj.label= 'Enable hover tools'; } """ + ''.join([ "hover{}.active = !hover{}.active;".format(i, i) for i in range(len(hover_list)) ]) hover_button.callback = CustomJS( args={'hover{}'.format(i): elem for i, elem in enumerate(hover_list)}, code=hover_button_code) # put all the widgets in a box group = widgetbox(clear_button, check_button, hover_button, width=200, name="group") # the final grid for static plots grid = gridplot([[sub_grid, group]], toolbar_location=None) # save a standalone html document in spectra_app/save with open(os.path.join(save_path, '{}_{}.html'.format(spectrum, ext)), 'w') as outfile: outfile.write(file_html(grid, CDN, spectrum[:12] + spectrum[-3:])) group = widgetbox(clear_button, check_button, hover_button, path_input, select_spectrum, load_button, width=200) app_grid = gridplot([[sub_grid, group]], toolbar_location=None) # add that grid to the document curdoc().add_root(app_grid) if custom_path: path_input.value = custom_path else: path_input.value = spec_path
def blockminer_tab(page_width): # source for top N table topN_src = ColumnDataSource( data=dict(percentage=[], address=[], block_count=[])) class This_tab(Mytab): def __init__(self, table, cols, dedup_cols): Mytab.__init__(self, table, cols, dedup_cols) self.table = table self.df2 = None self.key_tab = 'blockminer' self.n = 20 # ------- DIVS setup begin self.page_width = page_width txt = """<hr/> <div style="text-align:center;width:{}px;height:{}px; position:relative;background:black;margin-bottom:200px"> <h1 style="color:#fff;margin-bottom:300px">{}</h1> </div>""".format(self.page_width, 50, 'Welcome') self.notification_div = { 'top': Div(text=txt, width=self.page_width, height=20), 'bottom': Div(text=txt, width=self.page_width, height=10), } self.section_divider = '-----------------------------------' self.section_headers = {} # ----- UPDATED DIVS END # ---------------------- DIVS ---------------------------- def section_header_div(self, text, html_header='h2', width=600, margin_top=150, margin_bottom=-150): text = """<div style="margin-top:{}px;margin-bottom:-{}px;"><{} style="color:#4221cc;">{}</{}></div>""" \ .format(margin_top, margin_bottom, html_header, text, html_header) return Div(text=text, width=width, height=15) def load_this_data(self, start_date, end_date): end_date = datetime.combine(end_date, datetime.min.time()) start_date = datetime.combine(start_date, datetime.min.time()) logger.warning('load_data start date:%s', start_date) logger.warning('load_data end date:%s', end_date) # load only mined blocks and remove the double entry supplemental_where = "AND update_type = 'mined_block' AND amount >= 0" self.df_load(start_date, end_date, supplemental_where=supplemental_where, cols=['address', 'amount', 'block_time']) logger.warning('after load:%s', self.df.head(30)) return self.prep_dataset(start_date, end_date) def prep_dataset(self, start_date, end_date): try: logger.warning("prep dataset start date:%s", start_date) self.df1 = self.df1[['address', 'block_time']] self.df1['address'] = self.df1['address']\ .map(self.poolname_verbose_trun) self.df1 = self.df1.groupby(['address' ]).agg({'block_time': 'count'}) self.df1 = self.df1.reset_index() self.df1 = self.df1.rename( columns={'block_time': 'block_count'}) self.df1['percentage'] = 100*self.df1['block_count']\ /self.df1['block_count'].sum() self.df1['percentage'] = self.df1['percentage'].map( lambda x: round(x, 1)) self.df1 = self.df1.reset_index() logger.warning("topN column:%s", self.df1.columns.tolist()) #logger.warning('END prep dataset DF1:%s', self.df1.head()) return self.df1.hvplot.bar( 'address', 'block_count', rot=90, height=600, width=self.page_width, title='# of blocks mined by miner address', hover_cols=['percentage']) except Exception: logger.error('prep dataset:', exc_info=True) def view_topN(self): logger.warning("top n called:%s", self.n) # change n from string to int try: #table_n = df1.hvplot.table(columns=['address','percentage'], #title=title, width=400) logger.warning('top N:%s', self.n) df2 = self.df1.nlargest(self.n, 'percentage') df2 = df2.compute() logger.warning('in view top n :%s', df2.head(10)) new_data = dict(percentage=df2.percentage.tolist(), address=df2.address.tolist(), block_count=df2.block_count.tolist()) topN_src.stream(new_data, rollover=self.n) columns = [ TableColumn(field="address", title="Address"), TableColumn(field="percentage", title="percentage"), TableColumn(field="block_count", title="# of blocks") ] table_n = DataTable(source=topN_src, columns=columns, width=300, height=600) gc.collect() return table_n except Exception: logger.error('view_topN:', exc_info=True) def set_n(self, n): if isinstance(n, int): pass else: try: self.n = int(n) except Exception: logger.error('set_n', exc_info=True) # #################################################### # UTILITY DIVS def results_div(self, text, width=600, height=300): div = Div(text=text, width=width, height=height) return div def title_div(self, text, width=700): text = '<h2 style="color:green;">{}</h2>'.format(text) return Div(text=text, width=width, height=20) def notification_updater_2(self, text): self.notification_div.text = '<h3 style="color:red">{}</h3>'.format( text) def spacing_div(self, width=20, height=100): return Div(text='', width=width, height=height) def spacing_paragraph(self, width=20, height=100): return Paragraph(text='', width=width, height=height) def update(attrname, old, new): this_tab.notification_updater( "Calculations underway. Please be patient") stream_start_date.event(start_date=datepicker_start.value) stream_end_date.event(end_date=datepicker_end.value) this_tab.set_n(topN_select.value) this_tab.view_topN() this_tab.notification_updater("ready") # update based on selected top n def update_topN(): this_tab.notification_updater("Calculations in progress! Please wait.") logger.warning('topN selected value:%s', topN_select.value) this_tab.set_n(topN_select.value) this_tab.view_topN() this_tab.notification_updater("ready") try: # create class and get date range cols = ['address', 'block_timestamp', 'block_time'] this_tab = This_tab('account_ext_warehouse', cols, []) #STATIC DATES first_date_range = "2018-04-23 00:00:00" first_date_range = datetime.strptime(first_date_range, "%Y-%m-%d %H:%M:%S") last_date_range = datetime.now().date() last_date = last_date_range first_date = datetime_to_date(last_date - timedelta(days=60)) # STREAMS Setup # date comes out stream in milliseconds stream_start_date = streams.Stream.define('Start_date', start_date=first_date)() stream_end_date = streams.Stream.define('End_date', end_date=last_date)() # create a text widget for top N topN_select = Select(title='Top N', value=str(this_tab.n), options=menu) datepicker_start = DatePicker(title="Start", min_date=first_date_range, max_date=last_date_range, value=first_date) datepicker_end = DatePicker(title="End", min_date=first_date_range, max_date=last_date_range, value=last_date) # ALL MINERS. # --------------------- ALL MINERS ---------------------------------- hv_bar_plot = hv.DynamicMap( this_tab.load_this_data, streams=[stream_start_date, stream_end_date], datashade=True) renderer = hv.renderer('bokeh') bar_plot = renderer.get_plot(hv_bar_plot) # --------------------- TOP N MINERS ----------------------------------- # set up data source for the ton N miners table this_tab.view_topN() columns = [ TableColumn(field="address", title="Address"), TableColumn(field="percentage", title="percentage"), TableColumn(field="block_count", title="# of blocks") ] topN_table = DataTable(source=topN_src, columns=columns, width=400, height=600) # add callbacks datepicker_start.on_change('value', update) datepicker_end.on_change('value', update) topN_select.on_change("value", lambda attr, old, new: update_topN()) download_button = Button(label='Save Table to CSV', button_type="success") download_button.callback = CustomJS( args=dict(source=topN_src), code=open( join(dirname(__file__), "../../../static/js/topN_download.js")).read()) # put the controls in a single element controls = WidgetBox(datepicker_start, datepicker_end, download_button, topN_select) # create the dashboards grid = gridplot([[this_tab.notification_div['top']], [Spacer(width=20, height=70)], [ topN_table, controls, ], [bar_plot.state]]) # Make a tab with the layout tab = Panel(child=grid, title='miners: blocks') return tab except Exception: logger.error("Blockminer", exc_info=True) return tab_error_flag('miners: blocks')
}, code=code)) ### define widgets and layouts ### widgets = [] alert_div = Div(text="", name='alert_div') widgets.append(alert_div) load_button = Button(label='Load Data') load_button.callback = CustomJS(args=dict(tableInfo=table_info), code=""" // disable this button so we won't create the linker again cb_obj.disabled = true; // create a linker object and put it into window, so it can be used in other callbacks // window.shared defined in main.js const linker = new Linker(tableInfo); window.shared['linker'] = linker; """) widgets.append(load_button) title_mol_fam = Div(text='<h3>Molecular Family</h3>') title_spectra = Div(text='<h3>Spectra</h3>') title_bgc = Div(text='<h3>Biosynthetic Gene Cluster</h3>') title_gcf = Div(text='<h3>Gene Cluster Family</h3>') info_mf_spectra = Div(text=""" <h3>MF - Spectra Links</h3> <ul> <li>(1, 1), (1, 2), (1, 3)</li>
source_code = """ var inds = cb_obj.selected['1d'].indices; checkbox.active = inds; checkbox.change.emit() """ checkbox_code = """ source.selected['1d'].indices = cb_obj.active; """ button_code = """ console.log('checkbox',checkbox.active); console.log('source',source.selected['1d'].indices); """ source.callback = CustomJS(args=dict(checkbox=checkbox), code=source_code) checkbox.callback = CustomJS(args=dict(table=data_table, source=source), code=checkbox_code) button.callback = CustomJS(args=dict(table=data_table, checkbox=checkbox, source=source), code=button_code) show(widgetbox(data_table, checkbox, button))
def select_points_scatter(data, X='X', Y='Y', hue='hue', factor_type='categorical', group='group', alpha=.6, plot_width=400, plot_height=400, palette=Spectral6, vmin=0, vmax=3): '''source: dataframe with required columns for x and y positions as well as group name and color for each group.''' #initialize coloring if factor_type == 'categorical': color = factor_cmap(hue, palette=palette, factors=list(data[hue].unique())) elif factor_type == 'continuous': color_mapper = LinearColorMapper(palette=palette, low=vmin, high=vmax) color = {'field': hue, 'transform': color_mapper} else: raise ValueError( 'factor_type must be \'continuous\' or \'categorical\'') #initialize main plot s1 = ColumnDataSource(data=data) p1 = figure(plot_width=400, plot_height=400, tools="pan,wheel_zoom,lasso_select,reset", title="Select Here") p1.circle(X, Y, source=s1, alpha=alpha, color=color) #### initialize selected plot s2 = ColumnDataSource(data={X: [], Y: [], group: [], hue: []}) p2 = figure(plot_width=400, plot_height=400, tools="", title="Watch Here", x_range=p1.x_range, y_range=p1.y_range) p2.circle(X, Y, source=s2, alpha=alpha, color=color) #initialize table to show selected points columns = [ TableColumn(field=X, title="X axis"), TableColumn(field=Y, title="Y axis"), TableColumn(field=group, title=group) ] table = DataTable(source=s2, columns=columns, width=155, height=plot_height - 20) #define callback when points are selected s1.selected.js_on_change( 'indices', CustomJS(args=dict( s1=s1, s2=s2, table=table, X=X, Y=Y, hue=hue, group=group, ), code=""" var inds = cb_obj.indices; var d1 = s1.data; var d2 = s2.data; d2[X] = [] d2[Y] = [] d2[hue] = [] d2[group] = [] for (var i = 0; i < inds.length; i++) { d2[X].push(d1[X][inds[i]]) d2[Y].push(d1[Y][inds[i]]) d2[hue].push(d1[hue][inds[i]]) d2[group].push(d1[group][inds[i]]) } s2.change.emit(); table.change.emit(); """)) savebutton = Button(label="Save", button_type="success", width=155) javaScript = """ function table_to_csv(source) { const columns = Object.keys(source.data) const nrows = source.get_length() const lines = [columns.join(',')] for (let i = 0; i < nrows; i++) { let row = []; for (let j = 0; j < columns.length; j++) { const column = columns[j] row.push(source.data[column][i].toString()) } lines.push(row.join(',')) } return lines.join('\\n').concat('\\n') } const filename = 'data_result.csv' filetext = table_to_csv(source) const blob = new Blob([filetext], { type: 'text/csv;charset=utf-8;' }) //addresses IE if (navigator.msSaveBlob) { navigator.msSaveBlob(blob, filename) } else { const link = document.createElement('a') link.href = URL.createObjectURL(blob) link.download = filename link.target = '_blank' link.style.visibility = 'hidden' link.dispatchEvent(new MouseEvent('click')) } """ savebutton.callback = CustomJS(args=dict(source=s2, index_col=group), code=javaScript) layout = row(p1, p2, column(table, savebutton)) show(layout)
range=(0, end), step=end // 100, title="Rows") slider_rows.on_change('range', update) end = dataframe['time'].max() slider_time = RangeSlider(start=0, end=end, range=(0, end), step=end // 100, title="Time") slider_time.on_change('range', update) button_download = Button(label="Download", button_type='success') button_download.callback = CustomJS(args=dict(source=source), code=open( os.path.join(os.path.dirname(__file__), "download.js")).read()) widgets = [ select_concurrency, checkbox_database, multiselect_query_id, slider_rows, slider_time, button_download ] # Layout curdoc().title = "Big Data Benchmarking" curdoc().add_root( column(row(widgetbox(widgets), widgetbox(data_table)), row(bar_concurrency_by_database), row([item for item in plots['scatter_plot']]), row([item for item in plots['bar_database_by_query_category']]), row([item for item in plots['bar_database_by_table_size']]),
from bokeh.layouts import column, row from bokeh.models import Button, CustomJS, PasswordInput, PreText, TextInput from bokeh.plotting import output_file, show USER = "******" PASSWD = "Bok3h" text = PreText(text="LOGIN TO KNOW\nTHE SECRET:") user = TextInput(placeholder="username", title="(UserName: "******")") pwd = PasswordInput(placeholder="password", title="(Password: "******")") btn = Button(label="GO!", width=150) secret = PreText() # Secret information displayed if correct password entered ## Verify if the password typed is bokeh using a JS script verify_pwd = CustomJS(args=dict(user=user, pwd=pwd, secret=secret), code=""" secret.text = 'Wrong Password.'; if (user.value == %r && pwd.value == %r) { secret.text = 'Right Password. The Secret is 42.'; } """ % (USER, PASSWD)) #user.callback = verify_pwd # Check password pressing enter. pwd.callback = verify_pwd # Check password pressing enter. btn.callback = verify_pwd # Check password clicking on the Button. output_file("using_password_input.html", title="Password Field") page = row(column(text, user, pwd, btn), secret) show(page)
step=1, title="X-range") fundamental_xrange.on_change('value', bt.change_xrange) checkbox_button_group = CheckboxButtonGroup( labels=["Auto-Save to Table", "FreezeInset"], active=[]) checkbox_button_group.on_change('active', bt.startstop_autoupdate) # This button allows to lock in the current data detect_button = Button(label='Manual Detect and add to Table') detect_button.on_change('clicks', bt.detect_base_freq_bokeh) save_button = Button(label='Save Current Table') #save_button.on_change('clicks',bt.save_table) save_button.callback = CustomJS(args=dict(source=bt.sources['savednotes']), code=open( join(dirname(__file__), "download.js")).read()) #%% # make the grid & add the plots widgets = widgetbox(length_slider, concertpitch_slider, fundamental_xrange, detect_button, save_button, checkbox_button_group, width=400) #curdoc().add_root(row([ # column(bt.p_fft,bt.p_fft_f1,widgets), # column(bt.p_signal,bt.p_fft_f2), # column(bt.p_saved)]
'xr': chart.x_range, 'translate': dict([(x[1], x[0]) for x in DISEASE_DROPDOWN]) } js_history = CustomJS(args=request, code=read_js('history_push.js')) js_toggle_split = CustomJS(args={'pick': picker}, code=read_js('toggle_split.js')) # Events for selector in [disease_selector, smooth_selector]: selector.on_change('value', update_plot) selector.js_on_change('value', js_history) picker.js_on_change('active', js_toggle_split) picker.js_on_change('active', js_history) picker.active = chart_type chart.x_range.callback = js_history download_button.callback = CustomJS(args=dict( source=source_split, save_path='epidemic_co_il_{}.csv'.format( disease_selector.value.lower().replace(' ', '_'))), code=read_js('save_data.js')) # Document for element in [controls, chart_range, chart, chart_split, bars]: element.sizing_mode = "stretch_both" curdoc().add_root(element) curdoc().title = "Epidemic" curdoc().template_variables.update(p=picker.active) if 'disease' in args.keys(): curdoc().title = "Epidemic - {}".format(disease) update_plot(None, None, None)
def photometry_plot(obj_id, user, width=600, height=300): """Create scatter plot of photometry for object. Parameters ---------- obj_id : str ID of Obj to be plotted. Returns ------- (str, str) Returns (docs_json, render_items) json for the desired plot. """ data = pd.read_sql( DBSession().query( Photometry, Telescope.nickname.label("telescope"), Instrument.name.label("instrument"), ).join(Instrument, Instrument.id == Photometry.instrument_id).join( Telescope, Telescope.id == Instrument.telescope_id).filter( Photometry.obj_id == obj_id).filter( Photometry.groups.any( Group.id.in_([g.id for g in user.accessible_groups ]))).statement, DBSession().bind, ) if data.empty: return None, None, None data['color'] = [get_color(f) for f in data['filter']] data['label'] = [ f'{i} {f}-band' for i, f in zip(data['instrument'], data['filter']) ] data['zp'] = PHOT_ZP data['magsys'] = 'ab' data['alpha'] = 1.0 data['lim_mag'] = -2.5 * np.log10( data['fluxerr'] * DETECT_THRESH) + data['zp'] # Passing a dictionary to a bokeh datasource causes the frontend to die, # deleting the dictionary column fixes that del data['original_user_data'] # keep track of things that are only upper limits data['hasflux'] = ~data['flux'].isna() # calculate the magnitudes - a photometry point is considered "significant" # or "detected" (and thus can be represented by a magnitude) if its snr # is above DETECT_THRESH obsind = data['hasflux'] & (data['flux'].fillna(0.0) / data['fluxerr'] >= DETECT_THRESH) data.loc[~obsind, 'mag'] = None data.loc[obsind, 'mag'] = -2.5 * np.log10(data[obsind]['flux']) + PHOT_ZP # calculate the magnitude errors using standard error propagation formulae # https://en.wikipedia.org/wiki/Propagation_of_uncertainty#Example_formulae data.loc[~obsind, 'magerr'] = None coeff = 2.5 / np.log(10) magerrs = np.abs(coeff * data[obsind]['fluxerr'] / data[obsind]['flux']) data.loc[obsind, 'magerr'] = magerrs data['obs'] = obsind data['stacked'] = False split = data.groupby('label', sort=False) finite = np.isfinite(data['flux']) fdata = data[finite] lower = np.min(fdata['flux']) * 0.95 upper = np.max(fdata['flux']) * 1.05 plot = figure( plot_width=width, plot_height=height, active_drag='box_zoom', tools='box_zoom,wheel_zoom,pan,reset,save', y_range=(lower, upper), ) imhover = HoverTool(tooltips=tooltip_format) plot.add_tools(imhover) model_dict = {} for i, (label, sdf) in enumerate(split): # for the flux plot, we only show things that have a flux value df = sdf[sdf['hasflux']] key = f'obs{i}' model_dict[key] = plot.scatter( x='mjd', y='flux', color='color', marker='circle', fill_color='color', alpha='alpha', source=ColumnDataSource(df), ) imhover.renderers.append(model_dict[key]) key = f'bin{i}' model_dict[key] = plot.scatter( x='mjd', y='flux', color='color', marker='circle', fill_color='color', source=ColumnDataSource(data=dict( mjd=[], flux=[], fluxerr=[], filter=[], color=[], lim_mag=[], mag=[], magerr=[], stacked=[], instrument=[], )), ) imhover.renderers.append(model_dict[key]) key = 'obserr' + str(i) y_err_x = [] y_err_y = [] for d, ro in df.iterrows(): px = ro['mjd'] py = ro['flux'] err = ro['fluxerr'] y_err_x.append((px, px)) y_err_y.append((py - err, py + err)) model_dict[key] = plot.multi_line( xs='xs', ys='ys', color='color', alpha='alpha', source=ColumnDataSource(data=dict(xs=y_err_x, ys=y_err_y, color=df['color'], alpha=[1.0] * len(df))), ) key = f'binerr{i}' model_dict[key] = plot.multi_line( xs='xs', ys='ys', color='color', source=ColumnDataSource(data=dict(xs=[], ys=[], color=[])), ) plot.xaxis.axis_label = 'MJD' plot.yaxis.axis_label = 'Flux (μJy)' plot.toolbar.logo = None toggle = CheckboxWithLegendGroup( labels=list(data.label.unique()), active=list(range(len(data.label.unique()))), colors=list(data.color.unique()), ) # TODO replace `eval` with Namespaces # https://github.com/bokeh/bokeh/pull/6340 toggle.callback = CustomJS( args={ 'toggle': toggle, **model_dict }, code=open( os.path.join(os.path.dirname(__file__), '../static/js/plotjs', 'togglef.js')).read(), ) slider = Slider(start=0.0, end=15.0, value=0.0, step=1.0, title='Binsize (days)') callback = CustomJS( args={ 'slider': slider, 'toggle': toggle, **model_dict }, code=open( os.path.join(os.path.dirname(__file__), '../static/js/plotjs', 'stackf.js')).read().replace('default_zp', str(PHOT_ZP)).replace( 'detect_thresh', str(DETECT_THRESH)), ) slider.js_on_change('value', callback) # Mark the first and last detections detection_dates = data[data['hasflux']]['mjd'] if len(detection_dates) > 0: first = round(detection_dates.min(), 6) last = round(detection_dates.max(), 6) first_color = "#34b4eb" last_color = "#8992f5" midpoint = (upper + lower) / 2 line_top = 5 * upper - 4 * midpoint line_bottom = 5 * lower - 4 * midpoint y = np.linspace(line_bottom, line_top, num=5000) first_r = plot.line( x=np.full(5000, first), y=y, line_alpha=0.5, line_color=first_color, line_width=2, ) plot.add_tools( HoverTool( tooltips=[("First detection", f'{first}')], renderers=[first_r], )) last_r = plot.line( x=np.full(5000, last), y=y, line_alpha=0.5, line_color=last_color, line_width=2, ) plot.add_tools( HoverTool( tooltips=[("Last detection", f'{last}')], renderers=[last_r], )) layout = row(plot, toggle) layout = column(slider, layout) p1 = Panel(child=layout, title='Flux') # now make the mag light curve ymax = (np.nanmax(( np.nanmax(data.loc[obsind, 'mag']) if any(obsind) else np.nan, np.nanmax(data.loc[~obsind, 'lim_mag']) if any(~obsind) else np.nan, )) + 0.1) ymin = (np.nanmin(( np.nanmin(data.loc[obsind, 'mag']) if any(obsind) else np.nan, np.nanmin(data.loc[~obsind, 'lim_mag']) if any(~obsind) else np.nan, )) - 0.1) xmin = data['mjd'].min() - 2 xmax = data['mjd'].max() + 2 plot = figure( plot_width=width, plot_height=height + 100, active_drag='box_zoom', tools='box_zoom,wheel_zoom,pan,reset,save', y_range=(ymax, ymin), x_range=(xmin, xmax), toolbar_location='above', toolbar_sticky=False, x_axis_location='above', ) # Mark the first and last detections again detection_dates = data[obsind]['mjd'] if len(detection_dates) > 0: first = round(detection_dates.min(), 6) last = round(detection_dates.max(), 6) midpoint = (ymax + ymin) / 2 line_top = 5 * ymax - 4 * midpoint line_bottom = 5 * ymin - 4 * midpoint y = np.linspace(line_bottom, line_top, num=5000) first_r = plot.line( x=np.full(5000, first), y=y, line_alpha=0.5, line_color=first_color, line_width=2, ) plot.add_tools( HoverTool( tooltips=[("First detection", f'{first}')], renderers=[first_r], )) last_r = plot.line( x=np.full(5000, last), y=y, line_alpha=0.5, line_color=last_color, line_width=2, ) plot.add_tools( HoverTool( tooltips=[("Last detection", f'{last}')], renderers=[last_r], point_policy='follow_mouse', )) imhover = HoverTool(tooltips=tooltip_format) plot.add_tools(imhover) model_dict = {} for i, (label, df) in enumerate(split): key = f'obs{i}' model_dict[key] = plot.scatter( x='mjd', y='mag', color='color', marker='circle', fill_color='color', alpha='alpha', source=ColumnDataSource(df[df['obs']]), ) imhover.renderers.append(model_dict[key]) unobs_source = df[~df['obs']].copy() unobs_source.loc[:, 'alpha'] = 0.8 key = f'unobs{i}' model_dict[key] = plot.scatter( x='mjd', y='lim_mag', color='color', marker='inverted_triangle', fill_color='white', line_color='color', alpha='alpha', source=ColumnDataSource(unobs_source), ) imhover.renderers.append(model_dict[key]) key = f'bin{i}' model_dict[key] = plot.scatter( x='mjd', y='mag', color='color', marker='circle', fill_color='color', source=ColumnDataSource(data=dict( mjd=[], flux=[], fluxerr=[], filter=[], color=[], lim_mag=[], mag=[], magerr=[], instrument=[], stacked=[], )), ) imhover.renderers.append(model_dict[key]) key = 'obserr' + str(i) y_err_x = [] y_err_y = [] for d, ro in df[df['obs']].iterrows(): px = ro['mjd'] py = ro['mag'] err = ro['magerr'] y_err_x.append((px, px)) y_err_y.append((py - err, py + err)) model_dict[key] = plot.multi_line( xs='xs', ys='ys', color='color', alpha='alpha', source=ColumnDataSource(data=dict( xs=y_err_x, ys=y_err_y, color=df[df['obs']]['color'], alpha=[1.0] * len(df[df['obs']]), )), ) key = f'binerr{i}' model_dict[key] = plot.multi_line( xs='xs', ys='ys', color='color', source=ColumnDataSource(data=dict(xs=[], ys=[], color=[])), ) key = f'unobsbin{i}' model_dict[key] = plot.scatter( x='mjd', y='lim_mag', color='color', marker='inverted_triangle', fill_color='white', line_color='color', alpha=0.8, source=ColumnDataSource(data=dict( mjd=[], flux=[], fluxerr=[], filter=[], color=[], lim_mag=[], mag=[], magerr=[], instrument=[], stacked=[], )), ) imhover.renderers.append(model_dict[key]) key = f'all{i}' model_dict[key] = ColumnDataSource(df) key = f'bold{i}' model_dict[key] = ColumnDataSource(df[[ 'mjd', 'flux', 'fluxerr', 'mag', 'magerr', 'filter', 'zp', 'magsys', 'lim_mag', 'stacked', ]]) plot.xaxis.axis_label = 'MJD' plot.yaxis.axis_label = 'AB mag' plot.toolbar.logo = None obj = DBSession().query(Obj).get(obj_id) if obj.dm is not None: plot.extra_y_ranges = { "Absolute Mag": Range1d(start=ymax - obj.dm, end=ymin - obj.dm) } plot.add_layout( LinearAxis(y_range_name="Absolute Mag", axis_label="m - DM"), 'right') now = Time.now().mjd plot.extra_x_ranges = { "Days Ago": Range1d(start=now - xmin, end=now - xmax) } plot.add_layout(LinearAxis(x_range_name="Days Ago", axis_label="Days Ago"), 'below') toggle = CheckboxWithLegendGroup( labels=list(data.label.unique()), active=list(range(len(data.label.unique()))), colors=list(data.color.unique()), ) # TODO replace `eval` with Namespaces # https://github.com/bokeh/bokeh/pull/6340 toggle.callback = CustomJS( args={ 'toggle': toggle, **model_dict }, code=open( os.path.join(os.path.dirname(__file__), '../static/js/plotjs', 'togglem.js')).read(), ) slider = Slider(start=0.0, end=15.0, value=0.0, step=1.0, title='Binsize (days)') button = Button(label="Export Bold Light Curve to CSV") button.callback = CustomJS( args={ 'slider': slider, 'toggle': toggle, **model_dict }, code=open( os.path.join(os.path.dirname(__file__), '../static/js/plotjs', "download.js")).read().replace('objname', obj_id).replace( 'default_zp', str(PHOT_ZP)), ) toplay = row(slider, button) callback = CustomJS( args={ 'slider': slider, 'toggle': toggle, **model_dict }, code=open( os.path.join(os.path.dirname(__file__), '../static/js/plotjs', 'stackm.js')).read().replace('default_zp', str(PHOT_ZP)).replace( 'detect_thresh', str(DETECT_THRESH)), ) slider.js_on_change('value', callback) layout = row(plot, toggle) layout = column(toplay, layout) p2 = Panel(child=layout, title='Mag') tabs = Tabs(tabs=[p2, p1]) return _plot_to_json(tabs)
def create_ui(self, data): self.logger.info("number of data items %d", len(data)) # Create data source and data table # path, score, software_id, featcnt, featfreq, app name, app path, decision, status, comment, active in play, still voilating decision_editor = SelectEditor(options=[ "Unprocessed", "GPL Violation", "LGPL Violation", "Open Source App", "False Positive", "False Negative (LGPL)", "False Negative (GPL)" ]) status_editor = SelectEditor(options=[ "Unprocessed", "Emailed", "Confirmed", "Denied", "Authorized" ]) if self.app_info: columns = [ TableColumn(field="myindex", title="Id"), TableColumn(field="path", title="File Path"), TableColumn(field="score", title="Score"), TableColumn(field="normscore", title="NormScore", formatter=NumberFormatter(format="0.00")), TableColumn(field="partial", title="PartialMatch"), TableColumn(field="repo_id", title="Repo ID"), TableColumn(field="software_name", title="OSS"), TableColumn(field="version", title="Version"), TableColumn( field="featcnt", title="FeatCount", ), TableColumn( field="featfreq", title="FeatFreq", ), TableColumn(field="package_name", title="Package"), TableColumn(field="app_path", title="App Path"), TableColumn(field="app_count", title="App Count"), TableColumn(field="decision", title="Decision", editor=decision_editor), TableColumn(field="status", title="Status", editor=status_editor), TableColumn(field="comment", title="Comment"), # I am not sure whether we should add these two fields here. # TableColumn(field="active", title="Active in Play"), # TableColumn(field="still_violating", title="Still Violating"), ] else: template_str = '<a href="' + self.REPO_URL + '/<%= value %>"><%= value %></a>' columns = [ TableColumn( field="myindex", title="Id", ), TableColumn(field="name", title="Name"), TableColumn(field="score", title="Score", formatter=NumberFormatter(format="0.00")), TableColumn(field="normscore", title="NormScore", formatter=NumberFormatter(format="0.00")), TableColumn(field="partial", title="PartialMatch"), TableColumn(field="repo_id", title="RepoID"), TableColumn( field="software_name", title="OSS", formatter=HTMLTemplateFormatter(template=template_str)), TableColumn(field="featcnt", title="FeatCount", formatter=NumberFormatter(format="0,000,000")), TableColumn(field="featfreq", title="FeatFreq", formatter=NumberFormatter(format="0,000,000")), TableColumn(field="version", title="Version"), TableColumn(field="decision", title="Decision", editor=decision_editor), TableColumn(field="status", title="Status", editor=status_editor), TableColumn(field="comment", title="Comment"), TableColumn(field="path", title="Path"), ] # source is the displayed table, and can be modified by user # original_source is the original data, it is the base, and can only be modified by the program self.source = ColumnDataSource(self._data) self.original_source = ColumnDataSource(self._data) self.data_table = DataTable(source=self.source, columns=columns, width=2000, height=2000, editable=True, sortable=True) # Disable sortable for now! # selector or filters # reference link for callback: https://gist.github.com/dennisobrien/450d7da20daaba6d39d0 min_matching_score_slider = Slider(start=0, end=2, value=0.3, step=.01, title="Minimum Matching Score") max_matching_score_slider = Slider(start=0, end=2, value=0.7, step=.01, title="Maximum Matching Score") featfreq_slider = Slider(start=0, end=10000, value=0, step=1, title="Minimum Matching Num of Features") featcnt_slider = Slider(start=0, end=10000, value=50, step=1, title="Minimum Feature Count is OSS") kind_select = Select(value="All", options=["All", "Java", "Native"]) file_select = Select(value="Name", options=["Name", "MD5", "Path"]) search_input = TextInput(value=None, title="Enter library to search", callback=None) search_button = Button(label="Search", button_type="success") download_callback_code = """ var data = source.get('data'); var filetext = 'Id,File Name,Matching Score,Normalized Matching Score,Repo ID,Software Name,Feature Count,Feature Freq.,Version,Decision,Status,Comment,File Path\\n'; var order = ['myindex', 'name', 'score', 'normscore', 'repo_id', 'software_name', 'featcnt', 'featfreq', 'version', 'decision', 'status', 'comment', 'path']; for (var i = 0; i < data['path'].length; ++i) { var currRow = []; for (var item in order) { key = order[item] currRow.push(data[key][i]); } var joined = currRow.join().concat('\\n'); filetext = filetext.concat(joined); } var filename = 'violations.csv'; var blob = new Blob([filetext], { type: 'text/csv;charset=utf-8;' }); //addresses IE if (navigator.msSaveBlob) { //navigator.msSaveBlob(blob, filename); } else { var link = document.createElement("a"); link = document.createElement('a'); link.href = URL.createObjectURL(blob); link.download = filename; link.target = "_blank"; link.style.visibility = 'hidden'; link.dispatchEvent(new MouseEvent('click')); } """ # enable downloading of results as a csv file download_button = Button(label="Download", button_type="success") download_button.callback = CustomJS(args=dict(source=self.source), code=download_callback_code) # enable comparison of selected rows compare_button = Button(label="Compare", button_type="success") compare_button.on_click(self.compare_callback) # update on change #controls = [min_matching_score_slider, max_matching_score_slider, featfreq_slider, \ # featcnt_slider, kind_select, file_select, button] #for item in controls: # item.on_change('value', lambda attr, old, new: self.update_source(item)) combined_callback_code = """ var data = source.get('data'); var original_data = original_source.get('data'); var min_score = min_matching_score_slider.get('value'); var max_score = max_matching_score_slider.get('value'); var search_input = search_input.get('value'); var min_featfreq = featfreq_slider.get('value'); var min_featcnt = featcnt_slider.get('value'); var kind = kind_select.get('value'); console.log("min score: " + min_score + ", max score: " + max_score + ", min_featfreq: " + min_featfreq + ", min_featcnt" + min_featcnt + ", kind" + kind); var java_suffix = ".dex"; var native_suffix = ".so"; console.log("searchinput: " + search_input); var re; if (search_input) { re = new RegExp(search_input); } else { re = new RegExp(".*"); } for (var key in original_data) { data[key] = []; for (var i = 0; i < original_data['path'].length; ++i) { if ((original_data['normscore'][i] >= min_score) && (original_data['normscore'][i] <= max_score) && (original_data['featfreq'][i] >= min_featfreq) && (original_data['featcnt'][i] >= min_featcnt)) { // filter by java if (kind == "Java" && original_data['path'][i].indexOf(java_suffix, original_data['path'][i].length - java_suffix.length) === -1) continue; // filter by native if (kind == "Native" && original_data['path'][i].indexOf(native_suffix, original_data['path'][i].length - native_suffix.length) === -1) continue; // filter by search regex if (!re.test(original_data['name'][i])) { console.log("mismatch: " + original_data['name'][i]); continue; } // this row is the expected kind data[key].push(original_data[key][i]); } } } source.trigger('change'); target.trigger('change'); """ generic_callback = CustomJS(args=dict( source=self.source, original_source=self.original_source, search_input=search_input, max_matching_score_slider=max_matching_score_slider, min_matching_score_slider=min_matching_score_slider, featfreq_slider=featfreq_slider, featcnt_slider=featcnt_slider, kind_select=kind_select, target=self.data_table), code=combined_callback_code) min_matching_score_slider.callback = generic_callback max_matching_score_slider.callback = generic_callback featfreq_slider.callback = generic_callback featcnt_slider.callback = generic_callback search_button.callback = generic_callback kind_select.callback = generic_callback # install callback when a row gets selected self.source.on_change('selected', self.selected_callback) ########################################################### # Main ########################################################### controls = [min_matching_score_slider, max_matching_score_slider, featfreq_slider, \ featcnt_slider, kind_select, file_select, search_input, search_button, \ download_button, compare_button] plots_box = widgetbox(*controls, width=800, sizing_mode="fixed") layout = column(plots_box, self.data_table, sizing_mode="fixed") return layout
def plot_t_sne(read_counting_table, tsne_result, url_link, output_file_): read_counting_table["t-SNE-component_1"] = [pos[0] for pos in tsne_result] read_counting_table["t-SNE-component_2"] = [pos[1] for pos in tsne_result] read_counting_table["Attributes_split"] = \ read_counting_table["Attributes"].apply(lambda attr: dict( [key_value_pair.split("=") for key_value_pair in attr.split(";")])) hower_data = dict( x=read_counting_table["t-SNE-component_1"], y=read_counting_table["t-SNE-component_2"], feature=read_counting_table["Feature"], cluster_label=read_counting_table["Cluster_label"], gene=read_counting_table["Gene"], attribute=read_counting_table["Attributes"]) source = ColumnDataSource(hower_data) hover = HoverTool(tooltips=[ ("Gene", "@gene"), ("Feature", "@feature"), ("Cluster label", "@cluster_label")]) plot = figure(plot_width=900, plot_height=900, tools=[hover, BoxZoomTool(), ResetTool(), PanTool(), WheelZoomTool(), "lasso_select", "tap"], output_backend="webgl", lod_threshold=100, title="Grad-Seq t-SNE RNA-Seq") plot.toolbar.logo = None plot.circle("x", "y", source=source, size=7, alpha=3, line_color="grey", color="grey") plot.yaxis.axis_label_text_font_size = "15pt" plot.xaxis.axis_label_text_font_size = "15pt" plot.title.text_font_size = '15pt' url = url_link taptool = plot.select(type=TapTool) taptool.callback = OpenURL(url=url) taptool = plot.select(type=TapTool) taptool.callback = OpenURL(url=url) plot.xaxis.axis_label = "Dimension 1" plot.yaxis.axis_label = "Dimension 2" source2 = ColumnDataSource(data=dict(x=[], y=[])) plot2 = figure(plot_width=300, plot_height=300, tools="", title="Zoom", output_backend="webgl", lod_threshold=100) plot2.toolbar.logo = None plot2.circle('x', 'y', source=source2, alpha=0.6) columns = [ TableColumn(field="gene", title="Genes"), TableColumn(field="feature", title="Feature"), TableColumn(field="attribute", title="Attributes") ] data_table = DataTable(source=source, columns=columns, width=450, height=800, fit_columns=True) savebutton = Button(label="Save", button_type="success") source.selected.js_on_change('indices', CustomJS(args=dict(s1=source, s2=source2), code=""" var inds = cb_obj.indices; var d1 = s1.data; var d2 = s2.data; d2['x'] = [] d2['y'] = [] for (var i = 0; i < inds.length; i++) { d2['x'].push(d1['x'][inds[i]]) d2['y'].push(d1['y'][inds[i]]) } s2.change.emit(); """) ) savebutton.callback = CustomJS(args=dict(source_data=source), code=""" var inds = source_data.selected['1d'].indices; var data = source_data.data; console.log("inds", inds); console.log("data", data); var out = "Features\\tGene\\tAttributes + \\n"; for (i = 0; i < inds.length; i++) { out += data['feature'][inds[i]] + "\\t" + data['gene'][inds[i]] + "\\t" + data['attribute'][inds[i]] + "\\n"; } var file = new Blob([out], {type: 'text/plain'}); var elem = window.document.createElement('a'); elem.href = window.URL.createObjectURL(file); elem.download = 'selected-data.csv'; document.body.appendChild(elem); elem.click(); document.body.removeChild(elem); """) output_file(output_file_ + ".html", title="Grad-seq t-SNE") layout = row(plot, data_table, column(plot2, savebutton)) show(layout)
# create a plot and style its properties fig = figure(width=plot_width, height=plot_height, x_axis_type="datetime", toolbar_location='above', tools="pan,box_zoom,xwheel_zoom,reset,save"); fig.quad(top='price_max', bottom='price_min', left='time_left', right='time_right', source=plot_data, color=Blues3[1]) fig.line(x='time_mid', y='price_mean', source=plot_data, color=Blues3[0]); # add widgets title=Div(text="<h1>Stock Price</h1>") description=Paragraph(text='Type in a symbol or select one from Dow 30 \ and Nasdaq 100, and its price on 5/6/2010 will be plotted shortly. Due to its \ high frequency, the series plotted is downsampled, with the shaded area denoting \ the min/max prices at every time point. Details can be revealed by zoom in with \ tools above the plot.') symbol_box=TextInput(value='', title='Type Symbol', width=100) market_select = Select(value='', title='Select ', width=100, options=['', 'Dow 30', 'Nasdaq 100']) symbol_select = Select(value='', title='Symbol ', width=100, options=[]) button = Button(label="GO", button_type='success', width=100) progress_bar=PreText() # add callbacks and interactions button.callback=CustomJS(code=dims_jscode, args=dict(plot=fig, dims=dims)) button.on_click(button_click) fig.x_range.on_change('start', update_plot) #fig.x_range.on_change('end', update_plot) fig.x_range.callback = CustomJS(code=dims_jscode, args=dict(plot=fig, dims=dims)) market_select.on_change('value', update_symbol_select) symbol_select.on_change('value', update_symbol_box) # put the button and plot in a layout and add to the document doc=curdoc() doc.add_root(column([widgetbox([title, description]), row([widgetbox(symbol_box), market_select,symbol_select]), button, progress_bar, fig], sizing_mode='scale_width'))
upload.callback = CustomJS( args=dict(file_source=file_source), code=""" function read_file(filename) { var reader = new FileReader(); reader.onload = load_handler; reader.onerror = error_handler; // readAsDataURL represents the file's data as a base64 encoded string reader.readAsDataURL(filename); } function load_handler(event) { var b64string = event.target.result; file_source.data = {'file_contents' : [b64string], 'file_name':[input.files[0].name]}; file_source.trigger("change"); } function error_handler(evt) { if(evt.target.error.name == "NotReadableError") { alert("Can't read file!"); } } var input = document.createElement('input'); input.setAttribute('type', 'file'); input.setAttribute('accept', 'image/*'); input.onchange = function(){ if (window.FileReader) { read_file(input.files[0]); } else { alert('FileReader is not supported in this browser'); } } input.click(); """, )
for i in N_plots] + [('l' + str(i), l[i]) for i in N_plots] + [('checkbox', checkbox)] checkbox_code = ''.join([ 'p' + str(i) + '.visible = checkbox.active.includes(' + str(i) + ');' + 'l' + str(i) + '.visible = checkbox.active.includes(' + str(i) + ');' for i in N_plots ]) checkbox.callback = CustomJS(args={key: value for key, value in iterable}, code=checkbox_code) # Create "Clear All" button and its callback clear_button = Button(label='Clear All') clear_button_code = "checkbox.active=[];" + checkbox_code clear_button.callback = CustomJS(args={key: value for key, value in iterable}, code=clear_button_code) # Create "Select All" button and its callback check_button = Button(label='Select All') checkbox_code2 = ''.join([ 'p' + str(i) + '.visible = checkbox.active.includes(' + str(i) + ');' for i in N_plots ]) checkbox_code3 = ''.join(['l' + str(i) + '.visible = False;' for i in N_plots]) check_button_code = "checkbox.active=" + str( list(N_plots)) + ";" + checkbox_code2 + checkbox_code3 check_button.callback = CustomJS(args={key: value for key, value in iterable}, code=check_button_code)
def color_plot_bokeh(source, TOOLS, uniformity_method): """ NAME: color_plot PURPOSE: Given result of dot product and cluster, plot all possible 2 dimensional projection scatter plot with color corresponding to dot product values. Save all the graph in the corresponding folder. INPUT: source = dictionary-like data struction in Bokeh to update selected values in real-time TOOLS = list of tools used in bokeh plots uniformity method = dot product/projection, projection refers to fractional length OUTPUT: None HISTORY: 2018-07-30 - Written - Michael Poon """ # Go through all combinations of axis projection and plot them counter = 0 all_proj = [None] * 16 for i in range(6): for j in range(i + 1, 6): color_plot_ij_bokeh(source, TOOLS, i, j, all_proj, counter, uniformity_method) counter += 1 # Create frequency histogram if uniformity_method == 'projection': all_proj[15] = figure(tools=TOOLS, plot_width=350, plot_height=300) hist, edges = np.histogram(result, bins='auto', density=True, range=(0, 1)) all_proj[15].quad(top=hist, bottom=0, left=edges[:-1], right=edges[1:]) all_proj[15].xaxis.axis_label = 'Fractional Length of Projection' all_proj[15].yaxis.axis_label = 'Frequency' t = Title() t.text = 'Fractional Length Frequency Histogram' all_proj[15].title = t elif uniformity_method == 'dot product': all_proj[15] = figure(tools=TOOLS, plot_width=350, plot_height=300) hist, edges = np.histogram(result, bins='auto', density=True, range=(0, 1)) all_proj[15].quad(top=hist, bottom=0, left=edges[:-1], right=edges[1:]) all_proj[15].xaxis.axis_label = 'Maximum Absolute Dot Product' all_proj[15].yaxis.axis_label = 'Frequency' t = Title() t.text = 'Dot Product Frequency Histogram' all_proj[15].title = t # Adding titles and adjusting graph spacing t1 = Title() t1.text = 'Position Space Projections' all_proj[0].title = t1 t2 = Title() t2.text = 'Velocity Space Projections' all_proj[12].title = t2 t3 = Title() t3.text = 'Position-Velocity Space Projections' all_proj[6].title = t3 t4 = Title() if uniformity_method == "dot product": t4.text = "Maximum Dot Product" else: t4.text = "Fractional Length of Proj." all_proj[2].title = t4 all_proj[2].title.text_font_size = "14pt" # add button to show average dot product/projection if uniformity_method == "dot product": button = Button(label='Dot Product Method', button_type='warning', width=350) else: button = Button(label='Projection Method', button_type='warning', width=350) button.callback = CustomJS(args=dict(source=source), code=""" var inds = source.selected['1d'].indices; var data = source.data; var selected_dp = 0.; var total_dp = 0.; if (inds.length != 0) { for (i = 0; i < inds.length; i++) { selected_dp += data['result'][inds[i]]; } window.alert(inds.length + " of " + data['result'].length + " points chosen. Average Result = " + (selected_dp/inds.length).toFixed(2)); } else { for (i = 0; i < data['result'].length; i++) { total_dp += data['result'][i]; } window.alert("No points chosen. Average Result (of all points) = " + (total_dp/data['result'].length).toFixed(2)); } """) show( gridplot([[all_proj[0], button, all_proj[2], all_proj[6], all_proj[9]], [ all_proj[1], all_proj[5], all_proj[3], all_proj[7], all_proj[10] ], [all_proj[12], None, all_proj[4], all_proj[8], all_proj[11]], [all_proj[13], all_proj[14], all_proj[15], None, None]])) # Show twice to compare when selecting regions show( gridplot([[all_proj[0], button, all_proj[2], all_proj[6], all_proj[9]], [ all_proj[1], all_proj[5], all_proj[3], all_proj[7], all_proj[10] ], [all_proj[12], None, all_proj[4], all_proj[8], all_proj[11]], [all_proj[13], all_proj[14], all_proj[15], None, None]]))
import os from bokeh.io import curdoc from bokeh.models import ColumnDataSource, Button, CustomJS from bokeh.layouts import widgetbox app_path = os.path.dirname(__file__) datajs = os.path.join(app_path, 'templates', 'data.js') content = "var DATA = {'a':[5,4,3],'b':{'c':[10,12,14]}};" "" outfile = open(datajs, 'w') outfile.writelines(content) outfile.close() button = Button(label='test', width=200) button.callback = CustomJS(code="custom();") curdoc().add_root(widgetbox(button))
size_column = Select(title='Size', value='constant', options=['constant'] + columns) size_column.on_change('value', update_columns) slider = Slider(start=years[0], end=years[-1], value=years[0], step=1, title="Year") slider.on_change('value', update_year) region_column = CheckboxGroup(labels=regions[:],active = range(len(regions))) region_column.on_change('active',update_columns) reset_button = Button(label = 'Reset') reset_button.on_click(reset) download_button = Button(label = 'Download', button_type="success") download_button.callback = CustomJS(args=dict(source=download_CDS), code=open(join(dirname(__file__), "download.js")).read()) #Create initial plot p, plot_source, stats = make_plot() #Create description boxes stats_box = Div(text = update_stats_box(stats)) desc_box = Div(text = update_desc_box()) #Create logo images logo = load_image('static/Datakinda-Banner.png',1224,119) #Create url - "about this tool" div = Div(text=""" """ + \ """<a href="https://docs.google.com/document/d/1Z2MZDObaYwlFy86DSqBlsCAKspy9_DfxBybbKTU180A/edit"><u><i>About this tool</i></u></a>""",width = 800, height = 10)
'p' + str(i) + '.visible = checkbox.active.includes(' + str(i / 2) + ');p' + str(i + 1) + '.visible = checkbox.active.includes(' + str(i / 2) + ');pcor' + str(i / 2) + '.visible = checkbox.active.includes(' + str(i / 2) + ');' for i in range(0, len(N_plots), 2) ]) checkbox.callback = CustomJS( args={key: value for key, value in checkbox_iterable}, code=checkbox_code) # button to uncheck all checkboxes clear_button = Button(label='Clear all', width=120) clear_button_code = """checkbox.active=[];""" + checkbox_code clear_button.callback = CustomJS( args={key: value for key, value in checkbox_iterable}, code=clear_button_code) # button to check all checkboxes check_button = Button(label='Check all', width=120) check_button_code = """checkbox.active=""" + str( N_plots) + """;""" + checkbox_code check_button.callback = CustomJS( args={key: value for key, value in checkbox_iterable}, code=check_button_code) download_button = Button(label='Save Table to CSV', width=200) download_button.callback = CustomJS(args=dict(dt=data_table), code=""" var tab = dt.get('source').get('data');
def photometry_plot(obj_id, width=600, height=300): """Create scatter plot of photometry for object. Parameters ---------- obj_id : str ID of Obj to be plotted. Returns ------- (str, str) Returns (docs_json, render_items) json for the desired plot. """ data = pd.read_sql( DBSession().query( Photometry, Telescope.nickname.label('telescope'), Instrument.name.label('instrument')).join(Instrument).join( Telescope).filter(Photometry.obj_id == obj_id).statement, DBSession().bind) if data.empty: return None, None, None data['color'] = [get_color(f) for f in data['filter']] data['label'] = [ f'{i} {f}-band' for i, f in zip(data['instrument'], data['filter']) ] data['zp'] = PHOT_ZP data['magsys'] = 'ab' data['alpha'] = 1. data['lim_mag'] = -2.5 * np.log10( data['fluxerr'] * DETECT_THRESH) + data['zp'] # Passing a dictionary to a bokeh datasource causes the frontend to die, # deleting the dictionary column fixes that del data['original_user_data'] # keep track of things that are only upper limits data['hasflux'] = ~data['flux'].isna() # calculate the magnitudes - a photometry point is considered "significant" # or "detected" (and thus can be represented by a magnitude) if its snr # is above DETECT_THRESH obsind = data['hasflux'] & (data['flux'].fillna(0.) / data['fluxerr'] >= DETECT_THRESH) data.loc[~obsind, 'mag'] = None data.loc[obsind, 'mag'] = -2.5 * np.log10(data[obsind]['flux']) + PHOT_ZP # calculate the magnitude errors using standard error propagation formulae # https://en.wikipedia.org/wiki/Propagation_of_uncertainty#Example_formulae data.loc[~obsind, 'magerr'] = None coeff = 2.5 / np.log(10) magerrs = np.abs(coeff * data[obsind]['fluxerr'] / data[obsind]['flux']) data.loc[obsind, 'magerr'] = magerrs data['obs'] = obsind data['stacked'] = False split = data.groupby('label', sort=False) # show middle 98% of data finite = np.isfinite(data['flux']) fdata = data[finite] lower = np.percentile(fdata['flux'], 1.) upper = np.percentile(fdata['flux'], 99.) lower -= np.abs(lower) * 0.1 upper += np.abs(upper) * 0.1 plot = figure(plot_width=width, plot_height=height, active_drag='box_zoom', tools='box_zoom,wheel_zoom,pan,reset,save', y_range=(lower, upper)) imhover = HoverTool(tooltips=tooltip_format) plot.add_tools(imhover) model_dict = {} for i, (label, sdf) in enumerate(split): # for the flux plot, we only show things that have a flux value df = sdf[sdf['hasflux']] key = f'obs{i}' model_dict[key] = plot.scatter( x='mjd', y='flux', color='color', marker='circle', fill_color='color', alpha='alpha', source=ColumnDataSource(df), ) imhover.renderers.append(model_dict[key]) key = f'bin{i}' model_dict[key] = plot.scatter( x='mjd', y='flux', color='color', marker='circle', fill_color='color', source=ColumnDataSource(data=dict(mjd=[], flux=[], fluxerr=[], filter=[], color=[], lim_mag=[], mag=[], magerr=[], stacked=[], instrument=[]))) imhover.renderers.append(model_dict[key]) key = 'obserr' + str(i) y_err_x = [] y_err_y = [] for d, ro in df.iterrows(): px = ro['mjd'] py = ro['flux'] err = ro['fluxerr'] y_err_x.append((px, px)) y_err_y.append((py - err, py + err)) model_dict[key] = plot.multi_line( xs='xs', ys='ys', color='color', alpha='alpha', source=ColumnDataSource(data=dict(xs=y_err_x, ys=y_err_y, color=df['color'], alpha=[1.] * len(df)))) key = f'binerr{i}' model_dict[key] = plot.multi_line( xs='xs', ys='ys', color='color', source=ColumnDataSource(data=dict(xs=[], ys=[], color=[]))) plot.xaxis.axis_label = 'MJD' plot.yaxis.axis_label = 'Flux (μJy)' plot.toolbar.logo = None toggle = CheckboxWithLegendGroup(labels=list(data.label.unique()), active=list( range(len(data.label.unique()))), colors=list(data.color.unique())) # TODO replace `eval` with Namespaces # https://github.com/bokeh/bokeh/pull/6340 toggle.callback = CustomJS(args={ 'toggle': toggle, **model_dict }, code=open( os.path.join(os.path.dirname(__file__), '../static/js/plotjs', 'togglef.js')).read()) slider = Slider(start=0., end=15., value=0., step=1., title='binsize (days)') callback = CustomJS( args={ 'slider': slider, 'toggle': toggle, **model_dict }, code=open( os.path.join(os.path.dirname(__file__), '../static/js/plotjs', 'stackf.js')).read().replace('default_zp', str(PHOT_ZP)).replace( 'detect_thresh', str(DETECT_THRESH))) slider.js_on_change('value', callback) layout = row(plot, toggle) layout = column(slider, layout) p1 = Panel(child=layout, title='Flux') # now make the mag light curve ymax = 1.1 * data['lim_mag'] ymin = 0.9 * data['lim_mag'] if len(data['obs']) > 0: ymax[data['obs']] = (data['mag'] + data['magerr']) * 1.1 ymin[data['obs']] = (data['mag'] - data['magerr']) * 0.9 plot = figure(plot_width=width, plot_height=height, active_drag='box_zoom', tools='box_zoom,wheel_zoom,pan,reset,save', y_range=(np.nanmax(ymax), np.nanmin(ymin)), toolbar_location='above') imhover = HoverTool(tooltips=tooltip_format) plot.add_tools(imhover) model_dict = {} for i, (label, df) in enumerate(split): key = f'obs{i}' model_dict[key] = plot.scatter(x='mjd', y='mag', color='color', marker='circle', fill_color='color', alpha='alpha', source=ColumnDataSource(df[df['obs']])) imhover.renderers.append(model_dict[key]) unobs_source = df[~df['obs']].copy() unobs_source.loc[:, 'alpha'] = 0.8 key = f'unobs{i}' model_dict[key] = plot.scatter(x='mjd', y='lim_mag', color='color', marker='inverted_triangle', fill_color='white', line_color='color', alpha='alpha', source=ColumnDataSource(unobs_source)) imhover.renderers.append(model_dict[key]) key = f'bin{i}' model_dict[key] = plot.scatter( x='mjd', y='mag', color='color', marker='circle', fill_color='color', source=ColumnDataSource(data=dict(mjd=[], flux=[], fluxerr=[], filter=[], color=[], lim_mag=[], mag=[], magerr=[], instrument=[], stacked=[]))) imhover.renderers.append(model_dict[key]) key = 'obserr' + str(i) y_err_x = [] y_err_y = [] for d, ro in df[df['obs']].iterrows(): px = ro['mjd'] py = ro['mag'] err = ro['magerr'] y_err_x.append((px, px)) y_err_y.append((py - err, py + err)) model_dict[key] = plot.multi_line( xs='xs', ys='ys', color='color', alpha='alpha', source=ColumnDataSource(data=dict(xs=y_err_x, ys=y_err_y, color=df[df['obs']]['color'], alpha=[1.] * len(df[df['obs']])))) key = f'binerr{i}' model_dict[key] = plot.multi_line( xs='xs', ys='ys', color='color', source=ColumnDataSource(data=dict(xs=[], ys=[], color=[]))) key = f'unobsbin{i}' model_dict[key] = plot.scatter( x='mjd', y='lim_mag', color='color', marker='inverted_triangle', fill_color='white', line_color='color', alpha=0.8, source=ColumnDataSource(data=dict(mjd=[], flux=[], fluxerr=[], filter=[], color=[], lim_mag=[], mag=[], magerr=[], instrument=[], stacked=[]))) imhover.renderers.append(model_dict[key]) key = f'all{i}' model_dict[key] = ColumnDataSource(df) key = f'bold{i}' model_dict[key] = ColumnDataSource(df[[ 'mjd', 'flux', 'fluxerr', 'mag', 'magerr', 'filter', 'zp', 'magsys', 'lim_mag', 'stacked' ]]) plot.xaxis.axis_label = 'MJD' plot.yaxis.axis_label = 'AB mag' plot.toolbar.logo = None toggle = CheckboxWithLegendGroup(labels=list(data.label.unique()), active=list( range(len(data.label.unique()))), colors=list(data.color.unique())) # TODO replace `eval` with Namespaces # https://github.com/bokeh/bokeh/pull/6340 toggle.callback = CustomJS(args={ 'toggle': toggle, **model_dict }, code=open( os.path.join(os.path.dirname(__file__), '../static/js/plotjs', 'togglem.js')).read()) slider = Slider(start=0., end=15., value=0., step=1., title='Binsize (days)') button = Button(label="Export Bold Light Curve to CSV") button.callback = CustomJS(args={ 'slider': slider, 'toggle': toggle, **model_dict }, code=open( os.path.join(os.path.dirname(__file__), '../static/js/plotjs', "download.js")).read().replace( 'objname', obj_id).replace( 'default_zp', str(PHOT_ZP))) toplay = row(slider, button) callback = CustomJS( args={ 'slider': slider, 'toggle': toggle, **model_dict }, code=open( os.path.join(os.path.dirname(__file__), '../static/js/plotjs', 'stackm.js')).read().replace('default_zp', str(PHOT_ZP)).replace( 'detect_thresh', str(DETECT_THRESH))) slider.js_on_change('value', callback) layout = row(plot, toggle) layout = column(toplay, layout) p2 = Panel(child=layout, title='Mag') tabs = Tabs(tabs=[p2, p1]) return _plot_to_json(tabs)
def comps_tab(comps): df = comps df['Close Date'] = pd.to_datetime(df['Close Date']) df = df.drop(columns=['index']) df['Size'] = 24 df['Color'] = "#31AADE" df['xs'] = 'Close Date' df['ys'] = 'Finished Lot Value' SIZES = list(range(12, 36, 3)) COLORS = Spectral6 N_SIZES = len(SIZES) N_COLORS = len(COLORS) MARKERSOURCE = list(df['Site Condition'].unique()) MARKERS = ['hex', 'circle_x', 'triangle', 'square'] source = ColumnDataSource(df) columns = sorted(df.columns) discrete = [x for x in columns if df[x].dtype == object] continuous = [x for x in columns if x not in discrete] x_axis_select = Select(title='X-Axis', value='Close Date', options=columns) y_axis_select = Select(title='Y-Axis', value='Finished Lot Value', options=columns) size = Select(title='Size', value='None', options=['None'] + continuous) color = Select(title='Color', value='None', options=['None'] + continuous) kw = dict() x_title = x_axis_select.value.title() y_title = y_axis_select.value.title() df['xs'] = df[x_axis_select.value].values df['ys'] = df[y_axis_select.value].values x_title = x_axis_select.value.title() y_title = y_axis_select.value.title() kw = dict() if x_axis_select.value in discrete: kw['x_range'] = sorted(set(df['xs'])) if y_axis_select.value in discrete: kw['y_range'] = sorted(set(df['ys'])) kw['title'] = "%s vs %s" % (x_title, y_title) if x_axis_select.value in discrete: p.xaxis.major_label_orientation = pd.np.pi / 4 df['Size'] = 24 if size.value != 'None': if len(set(df[size.value])) > N_SIZES: groups = pd.qcut(df[size.value].values, N_SIZES, duplicates='drop') else: groups = pd.Categorical(df[size.value]) df['Size'] = [SIZES[xx] for xx in groups.codes] df['Color'] = "#31AADE" if color.value != 'None': if len(set(df[color.value])) > N_COLORS: groups = pd.qcut(df[color.value].values, N_COLORS, duplicates='drop') else: groups = pd.Categorical(df[color.value]) df['Color'] = [COLORS[xx] for xx in groups.codes] p = figure(plot_height=500, plot_width=800, tools='pan,box_zoom,hover,reset', **kw) p.xaxis.axis_label = x_title p.yaxis.axis_label = y_title map_options = GMapOptions(lat=df.Lat.mean(), lng=df.Long.mean(), map_type="roadmap", zoom=8) pmap = gmap(Google_API, map_options, plot_width=360, plot_height=400, title="CMA Map", toolbar_location="above") pmap.circle(x="Long", y="Lat", size=15, fill_color='Color', fill_alpha=0.25, line_color='black', line_width=.08, source=source) callback = CustomJS(code=""" var tooltips = document.getElementsByClassName("bk-tooltip"); for (var i = 0, len = tooltips.length; i < len; i ++) { tooltips[i].style.top = "10px"; // unset what bokeh.js sets tooltips[i].style.left = "800px"; tooltips[i].style.bottom = ""; tooltips[i].style.right = ""; } """) p.scatter(x='xs', y='ys', color='Color', size='Size', line_color="white", alpha=0.6, marker=factor_mark('Site Condition', MARKERS, MARKERSOURCE), hover_color='white', hover_alpha=0.5, source=source) hover = HoverTool(tooltips=[(x_title, '@xs'), (y_title, '@ys'), ('Name', '@Neighborhood'), ('FLV', '@{Finished Lot Value}{$0,0}'), ('Community Count', '@{Community Count}'), ('Market_Tier', '@{Market Tier}'), ('Close Date', '@DateString'), ('Lot Count', '@{Lot Count}'), ('Site_Condition', '@{Site Condition}'), ('Seller', '@Seller'), ('Entitlements', '@Entitlements'), ('Market', '@Market')], callback=callback) def select_df(): # filter df here based on widget inputs selected = df # (df['Square Footage (1)'] <= float(sf_slider.value[1])) return selected def update(): df = select_df() df['xs'] = df[x_axis_select.value].values df['ys'] = df[y_axis_select.value].values x_title = x_axis_select.value.title() y_title = y_axis_select.value.title() kw = dict() if x_axis_select.value in discrete: kw['x_range'] = sorted(set(df['xs'])) if y_axis_select.value in discrete: kw['y_range'] = sorted(set(df['ys'])) kw['title'] = "%s vs %s" % (x_title, y_title) if x_axis_select.value in discrete: p.xaxis.major_label_orientation = pd.np.pi / 4 df['Size'] = 24 if size.value != 'None': if len(set(df[size.value])) > N_SIZES: groups = pd.qcut(df[size.value].values, N_SIZES, duplicates='drop') else: groups = pd.Categorical(df[size.value]) df['Size'] = [SIZES[xx] for xx in groups.codes] df['Color'] = "#31AADE" if color.value != 'None': if len(set(df[color.value])) > N_COLORS: groups = pd.qcut(df[color.value].values, N_COLORS, duplicates='drop') else: groups = pd.Categorical(df[color.value]) df['Color'] = [COLORS[xx] for xx in groups.codes] source = df return source controls = [x_axis_select, y_axis_select, size, color] for control in controls: control.on_change('value', lambda attr, old, new: update()) button = Button(label="Download", button_type="success") button.callback = df.to_csv( os.path.abspath( os.path.join(os.path.dirname(__file__), '..', 'data', 'Downloads', 'sales_comps_' + str(date) + '.csv'))) table = DataTable(source=source, editable=True, height=600, width=1400, fit_columns=True, scroll_to_selection=True) widgets = column([*controls, button], width=180, height=250) widgets.sizing_mode = "fixed" # Make a tab with the layout p.add_tools(hover) l = layout([[column([widgets]), p, pmap], table], sizing_mode='fixed') # l = layout(table) update() tab = Panel(child=l, title='Comps') return tab
def volcano_plot(data_sans): index = data_sans['access'] x = data_sans['logfc'] y = data_sans['pvalue'] pos = data_sans['pos'] source = ColumnDataSource( data=dict(x=x, y=y, accession=index, position=pos)) color_mapper = CategoricalColorMapper(factors=["up", "normal", "down"], palette=['yellow', 'green', 'blue']) # dictionnary for the hoover tool hover = HoverTool(tooltips=[("accession", "@accession"), ("x", "@x"), ("y", "@y")]) yrange = [min(y) - 0.1, max(y) + 0.1] xrange = [min(x) - 1, max(x) + 0.1] # setting the tools TOOLS = ",pan,wheel_zoom,box_zoom,reset,box_select,lasso_select,previewsave" # create a new plot with a title and axis labels p = figure(y_range=yrange, x_range=xrange, x_axis_label='log(fc)', y_axis_label='-log(pvalue)', tools=TOOLS, plot_width=800, plot_height=800) p.add_tools(hover) # title modification p.title.text = "pvalue versus fold-change" p.title.align = "center" p.title.text_color = "blue" p.title.text_font_size = "25px" #p.title.background_fill_color = "#aaaaee" #setting the widgets slider h_slider = Slider(start=yrange[0], end=yrange[1], value=1, step=.1, title="variation of log(pvalue)") v_slider_right = Slider(start=0, end=xrange[1], value=0.5, step=.01, title="right fold change") v_slider_left = Slider(start=xrange[0], end=0, value=-0.5, step=.01, title="left log fold change") # Horizontal line hline = Span(location=h_slider.value, dimension='width', line_color='green', line_width=2) # Vertical line vline1 = Span(location=v_slider_right.value, dimension='height', line_color='blue', line_width=2) vline2 = Span(location=v_slider_left.value, dimension='height', line_color='black', line_width=2) #setting the widgets slider h_slider = Slider(start=yrange[0], end=yrange[1], value=1, step=.1, title="variation of log(pvalue)") v_slider_right = Slider(start=0, end=xrange[1], value=0.5, step=.01, title="right fold change") v_slider_left = Slider(start=xrange[0], end=0, value=-0.5, step=.01, title="left log fold change") p.renderers.extend([vline1, vline2, hline]) # add a circle points p.circle('x', 'y', source=source, color=dict(field='position', transform=color_mapper), legend='position') #setting the code to obain a real time ajustement of value and color #on th plot code = """ var data = source.data; var low = v_slider_left.value; var up = v_slider_right.value var back_value = h_slider.value; x = data['x'] y = data['y'] pos = data['position'] span.location = slider.value for (i = 0; i < x.length; i++) { if( (x[i] < low) && (y[i] > back_value)) { pos[i] = 'down' } else if ((x[i] > up) && (y[i] > back_value)){ pos[i] = 'up' } else { pos[i] = 'normal' } } console.log(source.data) source.change.emit() """ # callback of the sliders h_slider.callback = CustomJS(args=dict(source=source, span=hline, slider=h_slider, v_slider_left=v_slider_left, h_slider=h_slider, v_slider_right=v_slider_right), code=code) v_slider_right.callback = CustomJS(args=dict( source=source, span=vline1, slider=v_slider_right, v_slider_left=v_slider_left, h_slider=h_slider, v_slider_right=v_slider_right), code=code) v_slider_left.callback = CustomJS(args=dict(source=source, span=vline2, slider=v_slider_left, v_slider_left=v_slider_left, h_slider=h_slider, v_slider_right=v_slider_right), code=code) # creating du tableau des résulats de la selection datacolumn columns = [ TableColumn(field="accession", title="numero d'accession"), TableColumn(field="x", title="log(fc)"), TableColumn(field="y", title="-log(pvalue)"), TableColumn(field="position", title="position"), ] data_table = DataTable(source=source, columns=columns, width=400, height=280) # creating of the download button button = Button(label="Download", button_type="success") button.callback = CustomJS(args=dict(source=source), code=open( join(dirname(__file__), "static/js/download.js")).read()) layout = row( p, widgetbox(v_slider_left, v_slider_right, h_slider, data_table, button)) return layout