enter我正在尝试使用 d3v5 在单个连接的函数中附加多个元素。
使用时将多个元素附加到单个组的正确方法是什么selection.join()?
我尝试创建的 DOM 结构如下所示:
<svg id="chart">
<g class="data-group">
<rect class="data-rect" x="5" y="5" width="10" height="10" style="fill: red;"></rect>
<text class="data-text" x="15" y="20">data1</text>
</g>
<g class="data-group">
<rect class="data-rect" x="25" y="25" width="10" height="10" style="fill: green;"></rect>
<text class="data-text" x="35" y="40">data2</text>
</g>
<g class="data-group">
<rect class="data-rect" x="50" y="50" width="10" height="10" style="fill: gray;"></rect>
<text class="data-text" x="60" y="65">data3</text>
</g>
</svg>
Run Code Online (Sandbox Code Playgroud)
我可以通过循环数据 小提琴轻松手动生成此结构
for(var i = 0; i < data.length; i++){
let o = data[i];
let g = d3.select('#chart')
.append('g')
.datum(o)
.attr('class', 'data-group');
g.append('rect')
.attr('class', 'data-rect')
.attr('x',5)
.attr('y', d => d.id * offset)
.attr('width', 10)
.attr('height', 10)
.style('fill', d => d.color);
g.append('text')
.attr('class', 'data-text')
.attr('x', 15)
.attr('y', d => d.id * offset + 9)
.text(d => d.text);
}
Run Code Online (Sandbox Code Playgroud)
我想使用selection.join()这样我就可以干净地利用输入、更新和退出。
我可以接近这个结构,但是,我无法附加该text元素,因为它将附加到rect而不是g(并且你不能将文本附加到矩形!)
小提琴
d3.select('#chart')
.selectAll('.data-group')
.data(data, d => d.id)
.join((enter) => {
return enter
.append('g')
.attr('class', 'data-group')
.append('rect')
.attr('class', 'data-rect')
.attr('x',d => d.id * offset)
.attr('y', 5)
.attr('width', 10)
.attr('height', 10)
.style('fill', d => d.color);
})
Run Code Online (Sandbox Code Playgroud)
附加多个元素然后返回enter也不起作用,它会引发异常
小提琴
请参阅BallPointBen对我原来问题的评论。
可以通过执行以下操作将多个元素附加到连接中:
d3.select('#chart')
.selectAll('.data-group')
.data(data, d => d.id)
.join((enter) => {
let g = enter;
g.append('g')
.attr('class', 'data-group')
g.append('rect')
.attr('class', 'data-rect')
.attr('x',d => d.id * offset)
.attr('y', 5)
.attr('width', 10)
.attr('height', 10)
.style('fill', d => d.color);
g.append('text')
.attr('class', 'data-text');
return g;
})
Run Code Online (Sandbox Code Playgroud)