简体   繁体   English

基于Bokeh中的x_range自动设置vbar line_width

[英]Auto set vbar line_width based on x_range in Bokeh

I have a vbar tied to a ColumnDataSource which gets updated based on some widget selections. 我有一个与ColumnDataSource绑定的vbar ,它根据一些小部件选择进行更新。 If I start with line_width=5 it looks great with my initial data. 如果我从line_width=5开始,我的初始数据看起来很棒。 However, when I update the graph, the x_range gets updated to fit the updated data and causes the relative width of the bars to change. 但是,当我更新图形时, x_range会更新以适应更新的数据并导致条形的相对宽度发生变化。

Ideally, the width should always be proportional to the number of bars displayed. 理想情况下,宽度应始终与显示的条数成比例。 I tried looking at the various properties on the x_range and xaxis to see if I could get the range and try to calculate the width myself but I haven't found anything that helps. 我试着查看x_rangexaxis上的各种属性,看看我是否可以获得范围并尝试自己计算宽度,但我没有找到任何xaxis东西。 Been looking around and the documentation and nothing. 一直环顾四周,没有文件。 Any thoughts? 有什么想法吗?

I finally figured this out with help from @bigreddot. 我终于在@bigreddot的帮助下想出了这个。 It turns out that I was using the wrong property. 事实证明我使用了错误的财产。 Instead of using line_width I needed to use width . 而不是使用line_width我需要使用width Since my x_range is a datetime range, and datetimes are expressed in milliseconds, I needed a large enough width to display correctly. 由于我的x_rangedatetime范围,并且datetimes以毫秒表示,因此我需要足够大的宽度才能正确显示。 This takes care of setting a proportional width when zooming in, since the width represents a specific period on the x_axis . 这需要在放大时设置比例宽度,因为宽度表示x_axis上的特定时间段。

Since I have a function to change the freq of how I group my columns and update my ColumnDataSource.data , I just need to re-calculate the width when I update it. 由于我有一个函数来更改我的列分组和更新我的ColumnDataSource.datafreq ,我只需要在更新它时重新计算width

Here's the working code: 这是工作代码:

def get_data(freq='MS'):
    return pd.DataFrame(srs.groupby(pd.Grouper(freq=freq)).mean())

source = ColumnDataSource(data=ColumnDataSource.from_df(get_data()))

def get_width():
    mindate = min(source.data['date'])
    maxdate = max(source.data['date'])
    return 0.8 * (maxdate-mindate).total_seconds()*1000 / len(source.data['date'])

f = figure(plot_width=550, plot_height=400, x_axis_type="datetime")
f.x_range.set(bounds='auto')
r = f.vbar(source=source, top='volume', x='date', width=get_width())
bar_glyph = f.renderers[-1].glyph

handle = show(f, notebook_handle=True)

and my update function: 和我的更新功能:

def update_data(freq={'Quarter': 'QS', 'Month': 'MS', 'Week': 'W'}):
    source.data = ColumnDataSource.from_df(get_data(freq))
    r.glyph.width = get_width()
    push_notebook()

i = interact(update_data)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM