我正在研究d3中的散点图。 我的数据组织如下:
对于每个类别,都有一个勾选框,允许用户隐藏/显示相关的观察结果。我这样做是通过过滤数据然后将“display”属性更改为“none”/“display”。 (第285-365行)
//BUTTONS
var filterNord = d3.select("#filterNord");
var filterNordTopTen = d3.select("#filterNordTopTen");
var filterNordBottomTen = d3.select("#filterNordBottomTen");
var filterCentro = d3.select("#filterCentro");
var filterCentroTopTen = d3.select("#filterCentroTopTen");
var filterCentroBottomTen = d3.select("#filterCentroBottomTen");
var filterSud = d3.select("#filterSud");
var filterSudTopTen = d3.select("#filterSudTopTen");
var filterSudBottomTen = d3.select("#filterSudBottomTen");
//--Generic functions
function filterParent (parent, childTop, childBottom, family) {
parent
.on("click", function () {
if (parent.classed("on")==true) {
//hide data
chart.selectAll("circle")
.filter(function (d) {return d.gruppo == family;})
.attr("display", "none")
//change class
parent.attr("class", "off")
//change children
childTop.property("checked", false);
childTop.attr("class", "off");
childBottom.property("checked", false);
childBottom.attr("class", "off");
} else {
//show data
chart.selectAll("circle")
.filter(function (d) {return d.gruppo == family;})
.attr("display", "display")
//change class
parent.attr("class", "on")
//change children
childTop.property("checked", true);
childTop.attr("class", "on");
childBottom.property("checked", true);
childBottom.attr("class", "on");
}
;})
}
function filterChild (child, parent, sibiling, family, rank) {
child
.on("click", function () {
if (child.classed("on")==true) {
//hide data
chart.selectAll("circle")
.filter(function (d) {return d.topTen == rank && d.gruppo == family;})
.attr("display", "none")
//change class
child
.attr("class", "off")
//change parent if necessary
if (sibiling.classed("on") == false) {
parent.property("checked", false).attr("class", "off");}
} else {
//show data
chart.selectAll("circle")
.filter(function (d) {return d.topTen == rank && d.gruppo == family;})
.attr("display", "display")
//change class
child
.attr("class", "on")
//change parent if necessary
if (parent.classed("on")==false) {
parent.property("checked", true).attr("class", "on")}
}
;})
}
filterParent (filterNord, filterNordTopTen, filterNordBottomTen, "N");
filterChild (filterNordTopTen, filterNord, filterNordBottomTen, "N", "1");
filterChild (filterNordBottomTen, filterNord, filterNordTopTen, "N", "0");
filterParent (filterCentro, filterCentroTopTen, filterCentroBottomTen, "C");
filterChild (filterCentroTopTen, filterCentro, filterCentroBottomTen, "C", "1");
filterChild (filterCentroBottomTen, filterCentro, filterCentroTopTen, "C", "0");
filterParent (filterSud, filterSudTopTen, filterSudBottomTen, "S");
filterChild (filterSudTopTen, filterSud, filterSudBottomTen, "S", "1");
filterChild (filterSudBottomTen, filterSud, filterSudTopTen, "S", "0");
当隐藏值时,我希望图表只能缩放其余的点。我知道我应该通过.exit()选择然后更改.remove()来更改数据集。之后我可以相应地改变比例。我尝试过两种方式,但都不起作用。
//Update data to points that do not belong to the category I need to hide (i.e. N)
dataset = dataset.filter(function (d) {return d.gruppo!="N";})
//Remove data in the exit selection
d3.selectAll("circle").data(dataset).remove();
//Update data only to the category I want to show again
dataset = dataset.filter(function (d) {return d.gruppo=="N";})
//Call the draw function
draw();
但这会产生问题(例如,错误的数据被删除;当我将鼠标悬停在它们上方时,圆圈会改变颜色,我觉得很奇怪)。我认为问题是过滤功能(由于!=运算符);所以我尝试使用不同的过滤器,例如:
//Update data to points that belong to the categories I wish to keep (i.e. C and S)
dataset = dataset.filter(function (d) {return d.gruppo!=="C" && d.gruppo!=="S";})
//Remove data in the exit selection
d3.selectAll("circle").data(dataset).remove();
//Update data only to the category I want to show again
dataset = dataset.filter(function (d) {return d.gruppo=="N";})
//Call the draw function
draw();
这适用于第一次隐藏/显示迭代但随后它不再起作用。
我已经阅读了很多关于.exit()和.enter()的文章,但要么我没有得到一些关于它们如何工作的基本观点,要么我实施它们是错误的。