gpt4 book ai didi

javascript - D3 图表无法更新 -- 选择的进入和退出属性均为空

转载 作者:行者123 更新时间:2023-11-30 09:43:48 25 4
gpt4 key购买 nike

我正在尝试使用 .json 文件制作散点图。它将让用户选择要显示 json 文件中的哪组数据。所以我尝试使用更新模式。

下面的代码将进行第一次绘图,但是每次调用 selectGroup() 时(代码在 html 文件中),没有任何更新。 console.log(selection) 每次都会返回一个新数组,但该选择的进入和退出属性始终为空。有人可以帮我看一下吗?多谢!

var margin = {
top: 30,
right: 40,
bottom: 30,
left: 40
}
var width = 640 - margin.right - margin.left,
height = 360 - margin.top - margin.bottom;
var dataGroup;
var groupNumDefault = "I";
var maxX, maxY;
var svg, xAxis, xScale, yAxis, yScale;



//select and read data by group
function init() {
d3.json("data.json", function (d) {
maxX = d3.max(d, function (d) {
return d.x;
});
maxY = d3.max(d, function (d) {
return d.y;
});
console.log(maxY);

svg = d3.select("svg")
.attr("id", "scatter_plot")
.attr("width", 960)
.attr("height", 500)
.append("g")
.attr("id", "drawing_area")
.attr("transform", "translate(" + margin.left + "," + margin.top + ")");

//x-axis
xScale = d3.scale.linear().range([0, width]).domain([0, maxX]);
xAxis = d3.svg.axis()
.scale(xScale).orient("bottom").ticks(6);

//y-axis
yScale = d3.scale.linear().range([0, height]).domain([maxY, 0]);
yAxis = d3.svg.axis().scale(yScale).orient("left").ticks(6);

svg.append("g")
.attr("class", "x_axis")
.attr("transform", "translate(0," + (height) + ")")
.call(xAxis);

svg.append("g")
.attr("class", "y_axis")
.call(yAxis);

});

selectGroup(groupNumDefault);
}

//update data
function selectGroup(groupNum) {
d3.json("/data.json", function (d) {
dataGroup = d.filter(function (el) {
return el.group == groupNum;
});
console.log(dataGroup);
drawChart(dataGroup);

});
}


//drawing function
function drawChart(data) {
var selection = d3.select("svg").selectAll("circle")
.data(data);
console.log(selection);

selection.enter()
.append("circle")
.attr("class", "dots")
.attr("cx", function (d) {
console.log("updating!");
return xScale(d.x);
})
.attr("cy", function (d) {
return yScale(d.y);
})
.attr("r", function (d) {
return 10;
})
.attr("fill", "red");

selection.exit().remove();
}

init();

最佳答案

这里的问题有两个方面:


首先,您的 data() 调用中缺少关键函数,这意味着默认情况下数据是按索引(数据数组中的位置)匹配的,这意味着如果旧版本则没有进入和退出选择发送到 data() 的当前数据集具有相同的大小。相反,当 d3 按索引匹配时,大多数(可能是全部)数据将被放入更新选择中(旧数据集中的第一个数据 = 新数据集中的第一个数据,旧数据集中的第二个数据 = 第二个数据)在新数据集中等)

var selection = d3.select("svg").selectAll("circle")
.data(data);

参见:https://bl.ocks.org/mbostock/3808221

基本上,您需要将数据调用调整为类似这样的内容(如果您的数据具有 .id 属性或任何其他可以唯一标识每个数据的属性)

var selection = d3.select("svg").selectAll("circle")
.data(data, function(d) { return d.id; });

这将根据数据的实际内容而不仅仅是其索引生成 Enter() 和 exit() (和更新)选择。


其次,并不是第二轮的所有内容都保证在进入或退出选择中。某些数据可能只是现有数据的更新,而不是这些选择中的任何一个(在您的情况下,它可能每次都是全新的)。然而,考虑到上面描述的情况,几乎可以保证您的大部分数据都会在更新选择中,其中一些是错误的。要显示更新,您需要像这样更改代码(我假设这里是 d3 v3,显然 v4 略有不同)

selection.enter()
.append("circle")
.attr("class", "dots")
.attr("r", function (d) {
return 10;
})
.attr("fill", "red");

// this new bit is the update selection (which includes the just added enter selection
// now, the syntax is different in v4)
selection // v3 version
// .merge(selection) // v4 version (remove semi-colon off preceding enter statement)
.attr("cx", function (d) {
console.log("updating!");
return xScale(d.x);
})
.attr("cy", function (d) {
return yScale(d.y);
})

selection.exit().remove();

这两个更改应该可以看到您的可视化工作,当然,除非问题是简单的问题,例如第二次出现一组空数据,这也可以解释事情:-)

关于javascript - D3 图表无法更新 -- 选择的进入和退出属性均为空,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39863247/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com