如何通过过滤计算 Vaadin 8 网格页脚中的总计

2024-04-21

我知道我必须使用grid.getDataProvider()得到ListDataProvider(假设我发送了List to grid.setItems())。在其他计算页脚总数中我这样做:

Collection myItems = ((ListDataProvider)grid.getDataProvider()).getItems();
for(MyItem myItem : myItems)
   total += myItem.getValue();
footer.getCell(footerCell).setText(format(total));

但是,如果我添加页脚,则会失败,因为它会计算网格中的所有项目。例如,如果我添加:

((ListDataProvider)grid.getDataProvider()).addFilter(myFilter);

顶部的代码失败,因为页脚不是过滤后的总计,而是完整的网格总计。

话虽如此有人建议我使用 https://vaadin.com/forum/#!/thread/16837508:

grid.getDataCommunicator().fetchItemsWithRange(...);

然而,这是一个受保护的方法。假设我创建自己的子类,我什至不明白该方法是如何工作的。

但即便如此,这似乎也过于复杂,而且应该很简单,特别是如果能够在网格中添加过滤的话。

因此,我的大问题是,如果我过滤网格,如何计算 Vaadin 8 网格中的页脚总数?


要重新计算总数,您可以使用数据提供者监听器 https://vaadin.com/download/release/8.1/8.1.5/docs/api/com/vaadin/data/provider/DataProviderListener.html当过滤器改变时触发。在其实现中你可以fetch https://vaadin.com/download/release/8.1/8.1.5/docs/api/com/vaadin/data/provider/DataProvider.html#fetch-com.vaadin.data.provider.Query-的物品来自数据提供者 https://vaadin.com/download/release/8.1/8.1.5/docs/api/com/vaadin/data/provider/DataProvider.html with a Query https://vaadin.com/download/release/8.1/8.1.5/docs/api/com/vaadin/data/provider/Query.html,因为 fetch 方法还会考虑您定义的过滤器。

下面的例子主要是基于Vaadin 网格采样器 https://demo.vaadin.com/sampler/#ui/grids-and-trees/grid/features这个想法是显示每月报价及其总计的列表。该过滤器将允许您查看从某个月份开始的数据(这很愚蠢,但它可以让您开始):

import com.vaadin.data.provider.ListDataProvider;
import com.vaadin.data.provider.Query;
import com.vaadin.ui.ComboBox;
import com.vaadin.ui.Grid;
import com.vaadin.ui.VerticalLayout;
import com.vaadin.ui.components.grid.FooterRow;
import com.vaadin.ui.components.grid.HeaderRow;
import com.vaadin.ui.themes.ValoTheme;

import java.util.List;
import java.util.Random;
import java.util.stream.Collectors;
import java.util.stream.IntStream;

public class FilteredGrid extends VerticalLayout {
    public FilteredGrid() {
        // list data provider with some random data
        Random random = new Random();
        List<Quote> quotes = IntStream.range(1, 11).mapToObj(month -> new Quote(month, random.nextInt(10))).collect(Collectors.toList());
        ListDataProvider<Quote> provider = new ListDataProvider<>(quotes);

        // month number filter combo
        ComboBox<Integer> monthFilterCombo = new ComboBox<>("Starting with", IntStream.range(1, 10).boxed().collect(Collectors.toList()));
        monthFilterCombo.setEmptySelectionCaption("All");
        monthFilterCombo.addStyleName(ValoTheme.COMBOBOX_SMALL);
        monthFilterCombo.addValueChangeListener(event -> {
            if (event.getValue() == null) {
                provider.clearFilters();
            } else {
                provider.setFilter(quote -> quote.getMonth() > event.getValue());
            }
        });

        // grid setup
        Grid<Quote> grid = new Grid<>(Quote.class);
        grid.setDataProvider(provider);

        // header and footer
        HeaderRow header = grid.appendHeaderRow();
        header.getCell("month").setComponent(monthFilterCombo);
        FooterRow footer = grid.prependFooterRow();
        footer.getCell("month").setHtml("<b>Total:</b>");
        provider.addDataProviderListener(event -> footer.getCell("value").setHtml(calculateTotal(provider)));

        // add grid to UI
        setSizeFull();
        grid.setSizeFull();
        addComponent(grid);

        // trigger initial calculation
        provider.refreshAll();
    }

    // calculate the total of the filtered data
    private String calculateTotal(ListDataProvider<Quote> provider) {
        return "<b>" + String.valueOf(provider.fetch(new Query<>()).mapToInt(Quote::getValue).sum()) + "</b>";
    }

    // basic bean for easy binding
    public class Quote {
        private int month;
        private int value;

        public Quote(int month, int value) {
            this.month = month;
            this.value = value;
        }

        public int getMonth() {
            return month;
        }

        public void setMonth(int month) {
            this.month = month;
        }

        public int getValue() {
            return value;
        }

        public void setValue(int value) {
            this.value = value;
        }
    }
}

Result:

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何通过过滤计算 Vaadin 8 网格页脚中的总计 的相关文章

随机推荐