dashboard 仪表盘

此组件需要商业版 Vaadin Dashboard 扩展组件。

dashboard 组件以小部件网格的形式显示内容。网格会根据可用宽度更改列数。一个小部件可以跨越多列和多行,还可以按用户可折叠的分区进行分组。在可编辑模式下,用户可以自行移动、调整大小和移除小部件。

XML 元素

dashboard

Java 类

JmixDashboard

基本用法

在视图 XML 中声明 dashb 命名空间:

<view xmlns="http://jmix.io/schema/flowui/view"
      xmlns:dashb="http://jmix.io/schema/vaadin-dashboard/ui"
      title="msg://dashboardBasicsView.title">

当使用顶部操作面板中的 Add Component 操作添加组件时,Studio 会自动添加该命名空间。请参见 组件面板。

最简单的仪表盘包含一个 dashboard 元素和其中的几个 dashboardWidget 元素:

<dashb:dashboard id="dashboard" width="100%">
    <dashb:dashboardWidget id="revenueWidget" title="msg://revenueWidget.title">
        <dashb:content>
            <h3 id="revenueValue" text="1,204,500"/>
        </dashb:content>
    </dashb:dashboardWidget>

    <dashb:dashboardWidget id="ordersWidget" title="msg://ordersWidget.title">
        <dashb:content>
            <h3 id="ordersValue" text="3,182"/>
        </dashb:content>
    </dashb:dashboardWidget>
</dashb:dashboard>

小部件

小部件(widget)由 dashboardWidget 元素声明。需要一个 id,并在内部的 content 元素中包含一个组件。title 属性设置小部件标题中显示的文本,并支持消息键值:

<dashb:dashboardWidget id="revenueWidget" title="msg://revenueWidget.title">
    <dashb:content>
        <vbox id="revenueBox" padding="false">
            <h3 id="revenueValue" text="1,204,500"/>
            <span id="revenueCaption" text="msg://revenueWidget.caption"/>
        </vbox>
    </dashb:content>
</dashb:dashboardWidget>

content 元素中可以放入视图中的任何组件。如需在一个小部件中显示多个组件,则可以将多个组件放在一个布局容器中,如上所示。

小部件 Header

除了标题之外,小部件还可以有 headerContent 元素。其组件显示在小部件的 header 栏。可用于放置刷新按钮、过滤器或状态徽章:

<dashb:dashboardWidget id="ordersWidget" title="msg://ordersWidget.title">
    <dashb:content>
        <h3 id="ordersValue" text="3,182"/>
    </dashb:content>
    <dashb:headerContent>
        <button id="refreshOrdersBtn" icon="REFRESH" themeNames="tertiary-inline"/>
    </dashb:headerContent>
</dashb:dashboardWidget>

content 和 headerContent 都必须仅包含一个元素。如果设置多个元素,会在视图打开时抛出开发异常。

小部件尺寸

默认情况下,一个小部件占用网格的一个单元格。使用 colspan 和 rowspan 属性可以跨越多行和多列:

<dashb:dashboardWidget id="salesWidget" title="msg://salesWidget.title"
                       colspan="2" rowspan="2">
    <dashb:content>
        <vbox id="salesBox" width="100%" height="100%">
            <span id="salesValue" text="msg://salesWidget.caption"/>
        </vbox>
    </dashb:content>
</dashb:dashboardWidget>

小部件占用的列数不会超过网格的列数。在窄屏幕上,宽的小部件会收缩到可用的列数。

以编程方式创建小部件

可以在运行时创建和添加小部件。使用 UiComponents 工厂创建小部件及其内容:

@Autowired
private UiComponents uiComponents;

private DashboardWidget createWidget(String title, String value) {
    DashboardWidget widget = uiComponents.create(DashboardWidget.class);
    widget.setTitle(title);

    H3 valueLabel = uiComponents.create(H3.class);
    valueLabel.setText(value);
    widget.setContent(valueLabel); // a widget holds one component; use a layout for several

    return widget;
}

@Subscribe
public void onInit(final InitEvent event) {
    dashboard.add(createWidget("Revenue", "1,204,500"),
            createWidget("Orders", "3,182"));
}

还可以设置新小部件的位置,以及逐个移除或全部移除所有小部件:

DashboardWidget widget = createWidget("Visitors", "18,420");
dashboard.addWidgetAtIndex(0, widget);
dashboard.removeAll();

分区

小部件可以使用 dashboardSection 元素进行分组,同一个组的小部件使用共同的标题。用户可以折叠分区,隐藏其所有小部件:

<dashb:dashboard id="dashboard" width="100%">
    <dashb:dashboardWidget id="totalsWidget" title="msg://totalsWidget.title">
        <dashb:content>
            <h3 id="totalsValue" text="1,204,500"/>
        </dashb:content>
    </dashb:dashboardWidget>

    <dashb:dashboardSection id="regionsSection" title="msg://regionsSection.title">
        <dashb:dashboardWidget id="northWidget" title="msg://northWidget.title">
            <dashb:content>
                <h3 id="northValue" text="612,100"/>
            </dashb:content>
        </dashb:dashboardWidget>
        <dashb:dashboardWidget id="southWidget" title="msg://southWidget.title">
            <dashb:content>
                <h3 id="southValue" text="592,400"/>
            </dashb:content>
        </dashb:dashboardWidget>
    </dashb:dashboardSection>
</dashb:dashboard>

与小部件一样,分区需要一个 id。一个分区只能包含 dashboardWidget 元素,并且不能将分区放入另一个分区中。直接在 dashboard 元素中声明的小部件和分区内的小部件可以以任意顺序混合。

以编程方式创建分区

要创建分区,请使用 addSection() 方法,然后向其中添加小部件,例如使用 以编程方式创建小部件 中的 createWidget() 方法。移除分区时,其小部件也会被移除:

DashboardSection regionsSection = dashboard.addSection("Regions");
regionsSection.add(createWidget("North", "612,100"),
        createWidget("South", "592,400"));

响应式网格

仪表盘根据自身的宽度和列宽限制计算列数。列的宽度不会小于 minimumColumnWidth 值。当仪表盘变窄时,列数会减少。maximumColumnCount 属性设置宽屏幕上的最大列数:

<dashb:dashboard id="dashboard"
                 width="100%"
                 maximumColumnCount="4"
                 minimumColumnWidth="18em"
                 maximumColumnWidth="32em"
                 minimumRowHeight="12em"
                 gap="1em"
                 padding="1em"
                 denseLayout="true"
                 themeNames="shaded-background elevated-widgets">

denseLayout 属性设置网格间隙的填充方式。如果为 true,较小的小部件会向上移动,填充较大部件留下的空白空间,此时不会保持部件声明的顺序。

所有这些属性都有 setter,因此可以在运行时 Java 中设置:

dashboard.setMaximumColumnCount(3);
dashboard.setMinimumColumnWidth("18em");
dashboard.setMaximumColumnWidth("32em");
dashboard.setMinimumRowHeight("10em");
dashboard.setGap("1em");
dashboard.setPadding("1em");
dashboard.setDenseLayout(true);

可编辑模式

默认情况下,用户看到的小部件与声明时完全一致。如果将 editable 属性设置为 true,用户可以移动、调整大小和移除小部件,以及更改分区的顺序:

<dashb:dashboard id="dashboard" width="100%" editable="true">

在此模式下,每个小部件都会显示一个拖动手柄、一个调整大小手柄和一个移除按钮。这些操作也可以通过键盘执行。用户选择获得焦点的部件进行编辑,然后使用方向键移动或调整其大小。

可以在运行时切换可编辑模式,例如通过一个自定义的按钮实现:

@ViewComponent
private JmixDashboard dashboard;

@Subscribe("customizeBtn")
public void onCustomizeBtnClick(final ClickEvent<JmixButton> event) {
    dashboard.setEditable(!dashboard.isEditable());
}

用户每次更改时,仪表盘都会发送一个事件。请参见 事件和处理器。

部件布局持久化

仪表盘不会自动持久化用户的更改。如需保留自定义布局,请定义一个数据模型,存储每个小部件的固定标识符和布局属性,例如顺序、分区、列跨度和行跨度。在用户完成编辑时保存当前小部件配置,并在视图打开时根据存储的配置重新创建小部件。如果每个用户可以有不同布局,请将存储的配置还需要与用户关联。

一个简单实现的示例,请参见 Vaadin 文档中的 小部件的持久化和加载。

编辑控件本地化

编辑模式控件的提示和可访问名称来在 Jmix 消息包定义,因此会与应用程序的其余部分共同翻译。如需更改默认文本,请在项目的主消息包中定义以下键值:

dashboard.i18n.selectSection=Select section for editing
dashboard.i18n.selectWidget=Select widget for editing

dashboard.i18n.remove=Remove
dashboard.i18n.resize=Resize
dashboard.i18n.resizeApply=Apply
dashboard.i18n.resizeShrinkWidth=Shrink width
dashboard.i18n.resizeGrowWidth=Grow width
dashboard.i18n.resizeShrinkHeight=Shrink height
dashboard.i18n.resizeGrowHeight=Grow height

dashboard.i18n.move=Move
dashboard.i18n.moveApply=Apply
dashboard.i18n.moveForward=Move Forward
dashboard.i18n.moveBackward=Move Backward

有关覆盖扩展组件中定义的消息的详细信息,请参见 消息包。

主题样式

使用 themeNames 属性设置组件主题。

样式 描述

shaded-background

为仪表盘添加阴影背景,使小部件更加突出。

elevated-widgets

显示带有阴影的小部件。

flat-widgets

显示无边框和阴影的小部件。

还可以通过 classNames 属性为仪表盘、分区和小部件添加自定义 CSS 类名。

XML 属性

下面是 dashboard 的特殊属性:

名称 描述 默认值

denseLayout

如果为 true,较小的小部件会向上移动以填充较大部件留下的间隙,并且不保持部件声明的顺序。请参见 响应式网格。

false

editable

如果为 true,用户可以移动、调整大小和移除小部件,以及更改分区的顺序。请参见 可编辑模式。

false

gap

小部件之间的间距,以 CSS 长度表示,例如 1em。

—

maximumColumnCount

最大列数,无论仪表盘的宽度如何。如果未设置,列数取决于 minimumColumnWidth。

—

maximumColumnWidth

列的最大宽度,以 CSS 长度表示。

—

minimumColumnWidth

列的最小宽度,以 CSS 长度表示。列的宽度不会小于该值。如果空间不够,会减少一行内的列数。请参见 响应式网格。

—

minimumRowHeight

行的最小高度,以 CSS 长度表示。如果内容需要更多空间,行会变高。

—

padding

仪表盘边框与其小部件之间的内边距,以 CSS 长度表示。

—

rootHeadingLevel

生成的标记中根级项目标题的标题级别。仅影响可访问性。

2

下面是 dashboard 支持的其他通用属性:

事件和处理器

通用处理器 对所有组件的配置方式相同。 下面是 dashboard 的特殊事件和处理器:

在 Jmix Studio 生成处理器桩代码时,可以使用 Jmix UI 组件面板的 Handlers 标签页或者视图类顶部面板的 Generate Handler 添加,也可以通过 Code → Generate 菜单(Alt+Insert / Cmd+N)生成。

名称 描述

DashboardItemMovedEvent

当小部件或分区移动到新位置时发送。getItem() 方法返回被移动的条目,getSection() 返回分区。

DashboardItemMoveModeChangedEvent

当某项开始或结束键盘移动模式时发送。

DashboardItemRemovedEvent

当用户移除小部件或分区时发送。

itemRemoveHandler

拦截用户发起的小部件或分区移除事件。在收到的事件上调用 removeItem() 则完成移除,例如在用户确认之后。

DashboardItemResizedEvent

当小部件调整大小时发送。

DashboardItemResizeModeChangedEvent

当某项开始或结束键盘调整大小模式时发送。

DashboardItemSelectedChangedEvent

当项被选中或取消选中以进行键盘编辑时发送。

下面是 dashboard 支持的其他通用事件:

XML 内部元素

一个 dashboard 可以包含 dashboardWidget 和 dashboardSection 作为内部元素。