dc.js rowChart按最大键过滤

时间:2017-12-08 11:13:45

标签: dc.js crossfilter

我有一个仪表板,我随着时间的推移显示了Headcount。一个是显示人数随时间变化的行图,另一个是由HCLevel1分割的rowChart - 只是允许用户过滤。

我希望rowChart在日期过滤器中显示最新时段的Heads(而不是显示完整时段的完整总和,这将是错误的)。

我可以通过将两个字段组合成一个维度来实现这一点,但问题是当我使用rowChart按业务过滤时,我只在折线图中看到一个月 - 而我想要查看已过滤的整个期间。我无法弄清楚如何使用假组来完成此操作,因为rowChart的维度/键是HCLevel1。

我的数据格式如下:

var data =  = [
{
  "HCLevel1": "Commercial",
  "HCLevel2": "Portfolio TH",
  "Period": 201407,
  "Heads": 720
},

我已尝试使用此自定义缩减(从另一个SO问题中获取),但它无法正常工作(减去值,不正确的值等)。

function reduceAddAvgPeriods(p, v) {
    if (v.Period in p.periodsArray) {
        p.periodsArray[v.Period] += v.Heads;
    } else {
        p.periodsArray[v.Period] = 0;
        p.periodCount++;
    }
    p.heads += v.Heads;
    return p;
}

目前,我的jsfiddle示例是为维度组合了两个字段,但正如您所看到的,我无法使用rowChart过滤以显示折线图上的完整句点。

我可以使用reductio给出平均值,但我想为最近过滤的日期提供实际的Heads值。

https://jsfiddle.net/kevinelphick/4ybekqey/3/

我希望这是可能的,任何帮助都会非常感谢,谢谢!

1 个答案:

答案 0 :(得分:1)

几天前我瞥了一眼,但我花了一点时间才弄明白。棘手!

我们可以通过考虑以下两个事实来限制设计:

  1. 我们希望按“级别”过滤行图。那只是

    var dimLevel = cf.dimension(function (d) { return d.HCLevel1 || ''; });
    
  2. A group does not observe its own dimension's filters.因此,我们可能希望使用#1中的维度来生成行图的数据(组)。

  3. 考虑到这两个限制,也许我们可以按级别进行维度和分组,但是在组的区间内,跟踪导致该区间的周期?

    这是stacked charts经常使用的常见模式:

    var levelPeriodGroup = dimLevel.group().reduce(
        function(p, v) {
            p[v.Period] = (p[v.Period] || 0) + v.Heads;
            return p;
        },
        function(p, v) {
            p[v.Period] -= v.Heads;
            return p;
        },
        function() {
            return {};
        }
    );
    

    在这里,我们只是'剥离'顶层堆栈,丢弃任何零:

    function last_period(group, maxPeriod) {
        return {
            all: function() {
                var max = maxPeriod();
                return group.all().map(function(kv) {
                    return {key: kv.key, value: kv.value[max]};
                }).filter(function(kv) {
                    return kv.value > 0;
                });
            }
        };
    }
    

    为了使last_period保持一般,maxPeriod现在是一个函数,我们将这样定义:

    function max_period() {
        return dimPeriod.top(1)[0].Period;
    }
    

    将所有内容整合在一起并提供给行图:

    rowChart
        .group(last_period(levelPeriodGroup, max_period))
        .dimension(dimLevel)
        .elasticX(true);
    

    由于期间不再是图表标签的一部分,我们可以把它放在标题中:

    <h4>Last Period: <span id="last-period"></span></h4>
    

    并在绘制行图时更新它:

    rowChart.on('pretransition', function(chart) {
        d3.select('#last-period').text(max_period());
    });