【发布时间】:2021-02-21 18:47:22
【问题描述】:
我有一个使用 D3 正确构建的堆积条形图。 原始数据如下所示:
var originalData = {
header: ["label", "count", "missing"],
rows: [
{label: "A", count: 0, missing: 0},
{label: "B", count: 24, missing: 59},
{label: "C", count: 6, missing: 77},
{label: "D", count: 7, missing: 76},
{label: "E", count: 2, missing: 81},
{label: "F", count: 7, missing: 76},
{label: "G", count: 0, missing: 83}
]
};
因此,每个条形图都是一堆条形图,分别代表 count 和 missing 数量。
这个originalData 被传递给d3.stack 函数以生成用于绘制矩形的堆叠条形对象。
var barChartObject = d3.stack().keys(originalData.header.slice(1) )
.value( (d,key) => d[key] )
(originalData.rows);
生成的对象是这样的:
[
[[0,0],[0,24],[0,6],[0,7],[0,2],[0,7],[0,0]]
[[0,0],[24,83],[6,83],[7,83],[2,83],[7,83],[0,83]]
]
注意:每个“对”实际上是一个对象,其中包含用于构建对的原始数据,这些数据在 .data 字段中可用。
绘制矩形的代码如下所示:
onBarClick = (event, data) => {
...
}
var barGroupTag = this.svg.selectAll()
.data(barChartObject)
.enter()
.append("g")
barGroupTag.selectAll("rect")
.data(d => d)
.enter()
.append("rect")
...
.on("mouseover", this.onMouseOverBar)
.on("mouseout", this.onMouseOutBar)
.on('click', this.onBarClick);
然后使用<g>标签手动包装矩形以允许自定义属性存储。
barGroupTag.selectAll("rect")
.each( function () {
var rectNode = this;
d3.select(rectNode.parentNode)
.insert("g")
.append( () => rectNode);
}
);
问题是我需要访问与每个柱关联的原始数据,但不幸的是,在回调中,第二个参数返回整个堆栈而不是单个对。所以我无法弄清楚被点击的这个数组的元素是什么。我检查了传递给回调的第三个参数,但事实并非如此。例如,如果我单击 [0,24] 元素(第二个堆栈的底部栏),在回调中我得到 event 作为 PointerEvent 对象,而 data 是对象数组:
[[0,0],[0,24],[0,6],[0,7],[0,2],[0,7],[0,0]]
我可以使用.data 字段来访问原始数据,例如data[index].data.label 或data[index].data.count,但问题是我不知道索引的值。
这很奇怪,因为如果我使用 .attr 向矩形添加一个属性,则会收到单个对象(d 值)而不是整个数组,因此我可以执行以下操作:
.attr("xxx", d => {return d.data.count > 0 ? "aaa" : "bbb" } )
那么为什么传递给回调的值是整个 bar 数组,而不是与单击 bar 关联的单个元素?如何获取与点击栏关联的原始数据?
【问题讨论】:
-
您使用的是 d3 v6,对吗?当我转到this example 并将
.on("click", console.log)添加到条形图时,我看到正在记录各个值。在左下栏的情况下,我看到[0, 5038433]。 -
是的,版本是
6.2.0,d3-collection是版本1.0.7。我在 Observable 上的另一个样本上注意到了同样的行为。样品工作正常,但不是我的。关于您链接的示例,我发现d3.stack函数的使用方式有所不同。此外,使用d3.stack的输出时,选择也略有不同。我会尝试做出一些改变。 -
我忘了提到
<rect>节点是用<g>标记手动包装的(请参阅更新的代码)。这就是问题所在。此操作正在更改与rect关联的数据。删除该代码后,onclick 回调报告了正确的对值。 -
很好,现在解决了吗?
-
如果这解决了您的问题,我建议您写一个自我回答,或者最好完全删除该帖子,因为对我们其他人来说没有什么可取的。
标签: javascript d3.js bar-chart