简介: 我正在尝试扩展 d3 - 树布局。
我正在尝试通过 ajax/setTimeout 在切换事件上添加新节点。
我做了什么: 我成功同步添加新节点: https://jsfiddle.net/xfj875vc/1/
我只更改了代码的两部分:
更改 1(添加了向没有子节点的节点添加新子节点的方法):
函数 addNewNode(d, 项目) {
d._children = d._children || [];
d._children = d._children.concat(item);
}
更改 2(单击切换时调用 addNewNode,我仅为没有子节点的节点添加新节点):
var nodeEnter = node.enter().append("svg:g")
.attr("class", "node")
.attr("transform", function(d) { return "translate(" + source.y0 + "," + source.x0 + ")"; })
.on("click", function(d) {
// change start
var newItem;
if (!d._children || d._children.length === 0) {
newItem = [
{
"name": "i am new",
"children": [
{ "name": "i am new child 1"},
{ "name": "i am new child 2"}
]
}
];
addNewNode(d, newItem);
}
// change end
toggle(d); update(d);
});
2个问题:
- 当添加带有子节点的节点时,它会显示它并展开所有内容,子节点应该最小化。
- 如果我尝试将代码包装在 setTimeout 中,它会添加子项。但是,过渡和动画无法正常工作,d3 还展开了嵌套子项,您可以在这里看到它:
https://jsfiddle.net/xfj875vc/3/ (尝试点击更多一次)
谢谢
最佳答案
首先是你的方法
function addNewNode(d, item) {
d._children = d._children || [];
d._children = d._children.concat(item);
}
我们必须明白,
d._children 在折叠时具有值
,并且因此 d.children 将是未定义的
。 当节点扩展时反之亦然。因此我不确定您在上面的代码中想要做什么。其次,这将放置一个 d._children.concat(item);数组内的数组。这不是预期的,因此我对下面的 for 循环执行相同的操作。
应该是:
function addNewNode(d, item) {
item.forEach(function(i){
if(d._children)
d._children.push(i)//will add child to the closed node
else
d.children.push(i)//will add child to expanded node.
})
}
接下来,我将在数据中保留一个标志,以指示它不需要通过点击时的 ajax 加载。
{
"name": "flare",
"loaded" : true, //so this node flare will not be loaded on click via ajax
"children": [
{
"name": "analytics",
"loaded" : true,//so this node analytics will not be loaded on click via ajax
"children": [...
最后,在我的点击函数中,只有当该标志未定义时,我才会加载。
.on("click", function(d) {
if (d.loaded === undefined) {\\do ajax
setTimeout(function() {
var newItem;
newItem = [{
"name": "i am new",
"children": [{
"name": "i am new child 1"
}, {
"name": "i am new child 2"
}]
}];
addNewNode(d, newItem);
d.loaded = true;//mark it as loaded so it doesn't load next time
console.log("called", d)
toggle(d);
update(d);
}, 1000)
} else {//already loaded so dont do ajax
toggle(d);
update(d);
}
});
工作代码here
如果您希望折叠加载的节点。
您创建一个新节点,如下所示:
newItem = [{
"name": "i am new",
"children": [{
"name": "i am new child 1"
}, {
"name": "i am new child 2"
}]
}];
而不是这样做
newItem = [{
"name": "i am new",
"_children": [{ //note its changed to _children to show collapsed
"name": "i am new child 1"
}, {
"name": "i am new child 2"
}]
}];
工作代码here
希望这有帮助!
关于javascript - 将节点动态添加到 D3 树布局请求(切换时),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34543373/