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

时间:2016-10-21 21:16:08

标签: python graph bokeh

我有<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/> <xsl:strip-space elements="*"/> <xsl:template match="/Zoo"> <xsl:copy> <xsl:apply-templates select="Habitat/BigCat | Habitat/SmallCat"/> <xsl:apply-templates/> </xsl:copy> </xsl:template> <xsl:template match="BigCat| SmallCat"> <Habitat HabitatID="sub_habitat.{position()}.{../@HabitatID}"> <xsl:copy-of select="../*[not(self::BigCat or self::SmallCat or self::BodyTemp)]"/> <xsl:copy-of select="."/> </Habitat> </xsl:template> <xsl:template match="Habitat"> <xsl:copy> <xsl:copy-of select="@* | BodyTemp"/> <xsl:apply-templates select="BigCat | SmallCat" mode="child"/> </xsl:copy> </xsl:template> <xsl:template match="BigCat| SmallCat" mode="child"> <Child> <HabitatID> <xsl:text>sub_habitat.</xsl:text> <xsl:value-of select="position()"/> <xsl:text>.</xsl:text> <xsl:value-of select="../@HabitatID"/> </HabitatID> </Child> </xsl:template> </xsl:stylesheet> 绑定到<?xml version="1.0" encoding="UTF-8"?> <Zoo> <Habitat HabitatID="sub_habitat.1.habitat.cage.1"> <Type>Cats</Type> <Food>Birds</Food> <BigCat AnimalID="Tiger.1"> <Type>Bengal</Type> </BigCat> </Habitat> <Habitat HabitatID="sub_habitat.2.habitat.cage.1"> <Type>Cats</Type> <Food>Birds</Food> <SmallCat AnimalID="bobcat.1"> <Type>Bobcat</Type> </SmallCat> </Habitat> <Habitat HabitatID="habitat.cage.1"> <BodyTemp>endothermic</BodyTemp> <Child> <HabitatID>sub_habitat.1.habitat.cage.1</HabitatID> </Child> <Child> <HabitatID>sub_habitat.2.habitat.cage.1</HabitatID> </Child> </Habitat> </Zoo> ,根据一些小部件选择进行更新。如果我从vbar开始,我的初始数据看起来很棒。但是,当我更新图表时,ColumnDataSource会更新以适应更新的数据并导致条形的相对宽度发生变化。

理想情况下,宽度应始终与显示的条数成比例。我试着查看line_width=5x_range上的各种属性,看看我是否可以获得范围并尝试自己计算宽度,但我还没有找到任何有用的东西。一直环顾四周,没有文件。有什么想法吗?

1 个答案:

答案 0 :(得分:4)

我终于在@bigreddot的帮助下想出了这个。事实证明我使用了错误的财产。我没有使用line_width,而是使用width。由于我的x_rangedatetime范围,而datetimes以毫秒表示,因此我需要足够大的宽度才能正确显示。这需要在放大时设置比例宽度,因为宽度代表x_axis上的特定时段。

由于我的功能是更改freq我对列进行分组并更新ColumnDataSource.data的功能,因此我只需要在更新时重新计算width。< / p>

这是工作代码:

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)

和我的更新功能:

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)