例如,在html <table>
中,<tr>
可能包含<th>
和<td>
。如何将数据绑定到行选择,该行选择甚至会创建<th>
列,奇数为<td>
?
答案 0 :(得分:3)
所以,这似乎也不完美,但总是有html()方法。
var d = [['a','b','c','d']];
var r = d3.select('#myTable').selectAll('tr')
.data(d);
r.enter().append('tr').html(function(d) {
var i, s = '';
for (i = 0; i < d.length; i += 1) {
s += (i%2===0) ? '<th>' : '<td>';
s += d[i];
s += (i%2===0) ? '</th>' : '</td>';
}
return s;
});
答案 1 :(得分:2)
据我所知,你是正确的 - 在标准的D3习语中没有办法做到这一点。据推测,只要selection.append()
可以执行某项功能,就可以实现这一目标:
选择。的追加强>(名称)
追加具有指定名称的新元素...必须将名称指定为常量,但将来我们可能允许附加现有元素或函数来动态生成名称。
希望这样的函数可以采用标准(data, index)
参数,并解决这个问题。否则,目前,我无法通过单个.enter()
选择创建不同的元素 - .enter()
仅支持.append
,.insert
,和.select
,其中任何一个都不能使用函数参数。
您可以通过将数据复制到元组并双重附加到.enter()
选项来获得您想要的一些内容,如下所示:http://jsfiddle.net/xuJ6w/4/
// munge data
var tuples = data.map(function(row) {
var newRow = [],
x;
// create array of objects
for (x=0; x<row.length; x+=2) {
newRow.push({
label: row[x],
value: row[x+1]
})
}
return newRow;
});
var rows = d3.select('table').selectAll('tr')
.data(tuples);
rows.enter().append('tr');
var cellPairs = rows.selectAll('.cell')
.data(function(d) { return d; });
var entry = cellPairs.enter();
entry.append('th')
.attr('class', 'cell')
.text(function(d) {
return d.label;
});
entry.insert('td', 'th + th')
.attr('class', 'cell')
.text(function(d) {
return d.value;
});
但正如您所看到的,在调用更新时:
cellPairs
.style('background', '#CCC');
仅更新最后添加的节点,因此数据尚未完全绑定。
答案 2 :(得分:1)
我能想到的最好的方法是通过根据数据索引应用类来使<td>
看起来像<th>
:
var d = ['a','b','c','d','e','f','g'];
var tr = d3.select("#myTableRow").selectAll("td")
.data(d).enter().append("td")
.text(function(d) { return d; })
.classed("thLike", function(d,i) { return i%2===0; });
CSS:
.thLike {
font-weight: bold;
}
答案 3 :(得分:0)
https://github.com/mbostock/d3/wiki/Selections#wiki-data
选择器也可以相交(“.this.that”用于逻辑AND)或 联合(“.this,.that”用于逻辑OR)。
所以,这样的事情对你有用。我没有测试过(如果这个选择不起作用,你可以在每个TD / TH单元格中添加相同的类,并用TR .myClass
选择):
var cells = tableRow.selectAll("TD, TH").data(data);
cells.enter().each(d, i) {
var cell = d3.select(this);
cell.append(i%2 ? "TD" : "TH");
})