admin管理员组文章数量:1023848
My DOM structure looks like this, when I rendered my visualization with D3.js and enter, update, exit pattern:
g
rect
...
g
rect
...
g
rect
...
I am working with multiple elements and nested selections in my groups, but for simplicity I will demonstrate this with the rects. The DOM gets done by:
group = d3.select('.svg-content')
.selectAll('g')
.data(items, function (item) { return item.Id; });
groupEnter = group.enter()
.append('svg:g')
.attr('class','group-content');
// enter
groupEnter.append('svg:rect')
.style('fill', '#000')
.attr('x', function (item) { return item.x })
.attr('y', function (item) { return item.y; })
.attr('width', function (item) { return item.width; })
.attr('height', function (item) { return item.height; });
// update
group.select('rect')
.attr('x', function (item) { return item.x })
.attr('width', function (item) { return item.width; });
// remove
group.exit().remove();
This works!
Now I want to achieve the following:
g
g
rect
...
g
g
rect
...
g
g
rect
...
I want to encapsule the rect in another group element.
group = d3.select('.svg-content')
.selectAll('g')
.data(items, function (item) { return item.Id; });
groupEnter = group.enter()
.append('svg:g')
.attr('class','group-content');
// enter
groupEnter
.append('svg:g') // NEW
.attr('class','rect-content') // NEW
.append('svg:rect')
.style('fill', '#000')
.attr('x', function (item) { return item.x })
.attr('y', function (item) { return item.y; })
.attr('width', function (item) { return item.width; })
.attr('height', function (item) { return item.height; });
// update
group
.select('.rect-content') // NEW
.select('rect')
.attr('x', function (item) { return item.x })
.attr('width', function (item) { return item.width; });
// remove
group.exit().remove(); // NOTE: without this, it works!
What is wrong with this code? Without the remove block it works, but I need this to handle new/removed items. How to make it right?
My DOM structure looks like this, when I rendered my visualization with D3.js and enter, update, exit pattern:
g
rect
...
g
rect
...
g
rect
...
I am working with multiple elements and nested selections in my groups, but for simplicity I will demonstrate this with the rects. The DOM gets done by:
group = d3.select('.svg-content')
.selectAll('g')
.data(items, function (item) { return item.Id; });
groupEnter = group.enter()
.append('svg:g')
.attr('class','group-content');
// enter
groupEnter.append('svg:rect')
.style('fill', '#000')
.attr('x', function (item) { return item.x })
.attr('y', function (item) { return item.y; })
.attr('width', function (item) { return item.width; })
.attr('height', function (item) { return item.height; });
// update
group.select('rect')
.attr('x', function (item) { return item.x })
.attr('width', function (item) { return item.width; });
// remove
group.exit().remove();
This works!
Now I want to achieve the following:
g
g
rect
...
g
g
rect
...
g
g
rect
...
I want to encapsule the rect in another group element.
group = d3.select('.svg-content')
.selectAll('g')
.data(items, function (item) { return item.Id; });
groupEnter = group.enter()
.append('svg:g')
.attr('class','group-content');
// enter
groupEnter
.append('svg:g') // NEW
.attr('class','rect-content') // NEW
.append('svg:rect')
.style('fill', '#000')
.attr('x', function (item) { return item.x })
.attr('y', function (item) { return item.y; })
.attr('width', function (item) { return item.width; })
.attr('height', function (item) { return item.height; });
// update
group
.select('.rect-content') // NEW
.select('rect')
.attr('x', function (item) { return item.x })
.attr('width', function (item) { return item.width; });
// remove
group.exit().remove(); // NOTE: without this, it works!
What is wrong with this code? Without the remove block it works, but I need this to handle new/removed items. How to make it right?
Share Improve this question edited Dec 16, 2014 at 8:49 Robin Wieruch asked Dec 16, 2014 at 8:44 Robin WieruchRobin Wieruch 15.9k11 gold badges88 silver badges111 bronze badges 2- Looks fine at first glance. Could you elaborate on how it's not working please? – Lars Kotthoff Commented Dec 16, 2014 at 9:25
- It will remove all rects. I think the process cannot connect the new g element with the data and thinks it should be removed. – Robin Wieruch Commented Dec 16, 2014 at 9:41
1 Answer
Reset to default 15The problem is that you're selecting plain g
elements to bind the data to (.selectAll('g').data(...)
). This works fine when there's only one level of those elements, but as .selectAll()
works recursively, it will select many more elements than you would think when you have the nested structure.
That is, the selection contains many more elements, which "consume" the bound data. So the data doesn't end up being matched to the correct elements.
To fix, simply make the selector more specific:
group = d3.select('.svg-content')
.selectAll('g.group-content')
.data(...);
Complete demo here.
My DOM structure looks like this, when I rendered my visualization with D3.js and enter, update, exit pattern:
g
rect
...
g
rect
...
g
rect
...
I am working with multiple elements and nested selections in my groups, but for simplicity I will demonstrate this with the rects. The DOM gets done by:
group = d3.select('.svg-content')
.selectAll('g')
.data(items, function (item) { return item.Id; });
groupEnter = group.enter()
.append('svg:g')
.attr('class','group-content');
// enter
groupEnter.append('svg:rect')
.style('fill', '#000')
.attr('x', function (item) { return item.x })
.attr('y', function (item) { return item.y; })
.attr('width', function (item) { return item.width; })
.attr('height', function (item) { return item.height; });
// update
group.select('rect')
.attr('x', function (item) { return item.x })
.attr('width', function (item) { return item.width; });
// remove
group.exit().remove();
This works!
Now I want to achieve the following:
g
g
rect
...
g
g
rect
...
g
g
rect
...
I want to encapsule the rect in another group element.
group = d3.select('.svg-content')
.selectAll('g')
.data(items, function (item) { return item.Id; });
groupEnter = group.enter()
.append('svg:g')
.attr('class','group-content');
// enter
groupEnter
.append('svg:g') // NEW
.attr('class','rect-content') // NEW
.append('svg:rect')
.style('fill', '#000')
.attr('x', function (item) { return item.x })
.attr('y', function (item) { return item.y; })
.attr('width', function (item) { return item.width; })
.attr('height', function (item) { return item.height; });
// update
group
.select('.rect-content') // NEW
.select('rect')
.attr('x', function (item) { return item.x })
.attr('width', function (item) { return item.width; });
// remove
group.exit().remove(); // NOTE: without this, it works!
What is wrong with this code? Without the remove block it works, but I need this to handle new/removed items. How to make it right?
My DOM structure looks like this, when I rendered my visualization with D3.js and enter, update, exit pattern:
g
rect
...
g
rect
...
g
rect
...
I am working with multiple elements and nested selections in my groups, but for simplicity I will demonstrate this with the rects. The DOM gets done by:
group = d3.select('.svg-content')
.selectAll('g')
.data(items, function (item) { return item.Id; });
groupEnter = group.enter()
.append('svg:g')
.attr('class','group-content');
// enter
groupEnter.append('svg:rect')
.style('fill', '#000')
.attr('x', function (item) { return item.x })
.attr('y', function (item) { return item.y; })
.attr('width', function (item) { return item.width; })
.attr('height', function (item) { return item.height; });
// update
group.select('rect')
.attr('x', function (item) { return item.x })
.attr('width', function (item) { return item.width; });
// remove
group.exit().remove();
This works!
Now I want to achieve the following:
g
g
rect
...
g
g
rect
...
g
g
rect
...
I want to encapsule the rect in another group element.
group = d3.select('.svg-content')
.selectAll('g')
.data(items, function (item) { return item.Id; });
groupEnter = group.enter()
.append('svg:g')
.attr('class','group-content');
// enter
groupEnter
.append('svg:g') // NEW
.attr('class','rect-content') // NEW
.append('svg:rect')
.style('fill', '#000')
.attr('x', function (item) { return item.x })
.attr('y', function (item) { return item.y; })
.attr('width', function (item) { return item.width; })
.attr('height', function (item) { return item.height; });
// update
group
.select('.rect-content') // NEW
.select('rect')
.attr('x', function (item) { return item.x })
.attr('width', function (item) { return item.width; });
// remove
group.exit().remove(); // NOTE: without this, it works!
What is wrong with this code? Without the remove block it works, but I need this to handle new/removed items. How to make it right?
Share Improve this question edited Dec 16, 2014 at 8:49 Robin Wieruch asked Dec 16, 2014 at 8:44 Robin WieruchRobin Wieruch 15.9k11 gold badges88 silver badges111 bronze badges 2- Looks fine at first glance. Could you elaborate on how it's not working please? – Lars Kotthoff Commented Dec 16, 2014 at 9:25
- It will remove all rects. I think the process cannot connect the new g element with the data and thinks it should be removed. – Robin Wieruch Commented Dec 16, 2014 at 9:41
1 Answer
Reset to default 15The problem is that you're selecting plain g
elements to bind the data to (.selectAll('g').data(...)
). This works fine when there's only one level of those elements, but as .selectAll()
works recursively, it will select many more elements than you would think when you have the nested structure.
That is, the selection contains many more elements, which "consume" the bound data. So the data doesn't end up being matched to the correct elements.
To fix, simply make the selector more specific:
group = d3.select('.svg-content')
.selectAll('g.group-content')
.data(...);
Complete demo here.
本文标签: javascriptd3js enter()updateexit() with group element in betweenStack Overflow
版权声明:本文标题:javascript - d3.js: enter(), update, exit() with group element in between - Stack Overflow 内容由热心网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://it.en369.cn/questions/1740847960a1785012.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论