如何为bokeh网格图设置默认/激活工具?

How do I set default / active tools for a bokeh gridplot?(如何为bokeh网格图设置默认/激活工具?)
本文介绍了如何为bokeh网格图设置默认/激活工具?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如果要定义波克图的活动(默认)工具,可以通过传递"active_Drag"、"active_specect"、...记录的图形实例的参数here。 我还没有成功地为网格图设置标准活动工具,在该网格图中,所有单个绘图共享一个工具栏。这是我的代码的相关部分:
    tools = [
            PanTool(),
            BoxZoomTool(),
            WheelZoomTool(),
            UndoTool(),
            RedoTool(),
            ResetTool(),
            SaveTool(),
            HoverTool(tooltips=[
                ("Value", "$y")
                ])
            ]

    x_axes_range = Range1d(self.data.index[0], self.data.index[-1])

    for plot_type, plot_settings in pcfg.plot_types[self.name].items():

        plots.append(figure(x_axis_type="datetime", title=plot_type, plot_height = 400, x_range = x_axes_range, 
                            tools = tools, active_drag = None, active_inspect = None, active_scroll = None, active_tap = None))
    ...

    plots[plot_counter].line(self.data.index, self.data[parameter], color=parameter_settings[1], legend=parameter_settings[0])

...

gp = gridplot(plots, ncols = 1, sizing_mode = "scale_width")

script, div = components(gp)
因此,在我显示它的网站上,"BoxZoomTool()"被选为活动工具,虽然我在图的初始化中将活动工具设置为无,但可用的工具是我传递给figure()inits的那些工具。

我确实看到了"TOOLBAR_OPTION"here,但我不知道如何使用该参数更改活动工具。

推荐答案

更新2020年6月4日

嗯,似乎有人创建了GitHub Issue和changes were already merged。让我们看看这在下一个Bokeh版本中是否有效


旧答案

研究

我相信您只能像这样使用toolbar_options更改徽标:

toolbar_options=dict(logo='gray')

我希望将来有更多的选择。

我已经检查了如何实现您想要的(我也需要这样做),似乎网格图使用了一个特殊的工具栏将所有绘图工具栏连接在一起:ProxyToolbar

# Make the grid
tools = []
rows = []

for row in children:
    row_tools = []
    row_children = []
    for item in row:
        if merge_tools:
            if item is not None:
                for plot in item.select(dict(type=Plot)):
                    row_tools = row_tools + plot.toolbar.tools
                    plot.toolbar_location = None
        if item is None:
            width, height = 0, 0
            for neighbor in row:
                if isinstance(neighbor, Plot):
                    width = neighbor.plot_width
                    height = neighbor.plot_height
                    break
            item = Spacer(width=width, height=height)
        if isinstance(item, LayoutDOM):
            item.sizing_mode = sizing_mode
            if isinstance(item, Plot):
                if plot_width:
                    item.plot_width = plot_width
                if plot_height:
                    item.plot_height = plot_height
            row_children.append(item)
        else:
            raise ValueError("Only LayoutDOM items can be inserted into Grid")
    tools = tools + row_tools
    rows.append(Row(children=row_children, sizing_mode=sizing_mode))

grid = Column(children=rows, sizing_mode=sizing_mode)

if not merge_tools:
    return grid

if toolbar_location:
    proxy = ProxyToolbar(tools=tools, **toolbar_options)
    toolbar = ToolbarBox(toolbar=proxy, toolbar_location=toolbar_location)

这些工具收集在一个列表中,以将它们分配给特殊工具栏。我没有看到在任何地方收集默认活动元素。

替代解决方案

所以您可以手动创建一个工具栏和网格图,您可以在其中为Toolbar类设置您想要的属性。检查我构建的这个示例:

from bokeh.models import Button, ColumnDataSource, Range1d, Toolbar, ToolbarBox
from bokeh.models.tools import HoverTool, WheelZoomTool, PanTool, CrosshairTool
from bokeh.layouts import layout
from bokeh.plotting import curdoc, figure

x_range = Range1d(start=0, end=10)
y_range = Range1d(start=0, end=10)

# ------------------- PLOT 1 --------------------------- #

plot_1 = figure(
    title='First figure',
    width=400,
    height=400,
    x_range=x_range,
    y_range=y_range,
    toolbar_location=None,
    x_axis_label='x axis',
    y_axis_label='y axis',
)

x = [1, 2, 3, 4]
y = [4, 3, 2, 1]

source = ColumnDataSource(data=dict(x=x, y=y))

plot_1.circle(
    x='x',
    y='y',
    source=source,
    radius=0.5,
    fill_alpha=0.6,
    fill_color='green',
    line_color='black',
)

# ------------------- PLOT 2 --------------------------- #

plot_2 = figure(
    name='plot_2',
    title='Second figure',
    width=400,
    height=400,
    x_range=x_range,
    y_range=y_range,
    toolbar_location=None,
    x_axis_label='x axis',
    y_axis_label='y axis',
)

plot_2.circle(
    x='x',
    y='y',
    source=source,
    radius=0.5,
    fill_alpha=0.6,
    fill_color='red',
    line_color='black',
)

# ---------------- ADD TOOLS TO THE PLOT --------------------- #

wheel_zoom = WheelZoomTool()
pan_tool = PanTool()
hover = HoverTool()
crosshair = CrosshairTool()
tools = (wheel_zoom, pan_tool, hover, crosshair)

toolbar = Toolbar(
    tools=[wheel_zoom, pan_tool, hover, crosshair],
    active_inspect=[crosshair],
    # active_drag =                         # here you can assign the defaults
    # active_scroll =                       # wheel_zoom sometimes is not working if it is set here
    # active_tap 
)

toolbar_box = ToolbarBox(
    toolbar=toolbar,
    toolbar_location='left'
)

plot_1.add_tools(*tools)
plot_2.add_tools(*tools)

# ----------------- PLOT LAYOUT -------------------------- #

layout_1 = layout(
    children=[
        [toolbar_box, plot_1, plot_2],
    ],
    sizing_mode='fixed',
)

curdoc().add_root(layout_1)

注意:我正在进行一些测试,有时测试不能很好地工作。这些工具被标记为默认工具,但随机不起作用,恐怕与Java脚本和异步任务有关。所以也许我们应该等等。

第二个替代解决方案

我想我找到了一个总是有效的解决方案。这是一种变通办法。在我的示例中,我使用了两个绘图,但只显示了第一个绘图的工具栏。无论如何,您都需要为这两个绘图设置默认工具栏值。

from bokeh.models import Button, ColumnDataSource, Range1d, Toolbar, ToolbarBox
from bokeh.models.tools import HoverTool, WheelZoomTool, PanTool, CrosshairTool, LassoSelectTool
from bokeh.layouts import layout
from bokeh.plotting import curdoc, figure

x_range = Range1d(start=0, end=10)
y_range = Range1d(start=0, end=10)

# ------------------- PLOT 1 --------------------------- #

plot_1 = figure(
    title='First figure',
    width=400,
    height=400,
    x_range=x_range,
    y_range=y_range,
    toolbar_location='left',        # show only the toolbar of the first plot
    tools='',
    x_axis_label='x axis',
    y_axis_label='y axis',
)

x = [1, 2, 3, 4]
y = [4, 3, 2, 1]

source = ColumnDataSource(data=dict(x=x, y=y))

plot_1.circle(
    x='x',
    y='y',
    source=source,
    radius=0.5,
    fill_alpha=0.6,
    fill_color='green',
    line_color='black',
)

# ------------------- PLOT 2 --------------------------- #

plot_2 = figure(
    name='plot_2',
    title='Second figure',
    width=400,
    height=400,
    x_range=x_range,
    y_range=y_range,
    toolbar_location=None,
    tools='',
    x_axis_label='x axis',
    y_axis_label='y axis',
)

plot_2.circle(
    x='x',
    y='y',
    source=source,
    radius=0.5,
    fill_alpha=0.6,
    fill_color='red',
    line_color='black',
)

# ---------------- ADD TOOLS TO THE PLOT --------------------- #

wheel_zoom = WheelZoomTool()
lasso_select = LassoSelectTool()
pan_tool = PanTool()
hover = HoverTool()
crosshair = CrosshairTool()
tools = (wheel_zoom, lasso_select, pan_tool, hover, crosshair)

plot_1.add_tools(*tools)
plot_2.add_tools(*tools)

plot_1.toolbar.active_inspect=[crosshair]     # defaults added to the first plot
plot_1.toolbar.active_scroll=wheel_zoom
plot_1.toolbar.active_tap=None
plot_1.toolbar.active_drag=lasso_select

plot_2.toolbar.active_inspect=[crosshair]     # defaults added to the second plot
plot_2.toolbar.active_scroll=wheel_zoom
plot_2.toolbar.active_tap=None
plot_2.toolbar.active_drag=lasso_select

# ----------------- PLOT LAYOUT -------------------------- #

layout_1 = layout(
    children=[
        [plot_1, plot_2],
    ],
    sizing_mode='fixed',
)

curdoc().add_root(layout_1)

开发人员反馈

事实上,Bryan(bokeh开发人员)在聊天中告诉了我

我实际上要回答的是,默认的工具激活和栅格图从来没有被一起考虑过,也不受支持,尽管如果您找到了适合您的特定用例的方法,这可能是最好的选择。正如您所说的,通常情况下,用户不应该直接使用工具栏,他们非常挑剔,原因有很多。

这篇关于如何为bokeh网格图设置默认/激活工具?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持编程学习网!

本站部分内容来源互联网,如果有图片或者内容侵犯您的权益请联系我们删除!

相关文档推荐

Leetcode 234: Palindrome LinkedList(Leetcode 234:回文链接列表)
How do I read an Excel file directly from Dropbox#39;s API using pandas.read_excel()?(如何使用PANDAS.READ_EXCEL()直接从Dropbox的API读取Excel文件?)
subprocess.Popen tries to write to nonexistent pipe(子进程。打开尝试写入不存在的管道)
I want to realize Popen-code from Windows to Linux:(我想实现从Windows到Linux的POpen-code:)
Reading stdout from a subprocess in real time(实时读取子进程中的标准输出)
How to call type safely on a random file in Python?(如何在Python中安全地调用随机文件上的类型?)