wns*_*mth 21 animation transition d3.js
我正在使用流行的d3库的V3,并且基本上希望有三个转换,然后是彼此:第一个转换应该应用于退出选择,第二个应用于更新选择,第三个转换应用于输入选择.它们应该以这样的方式链接:当其中一个选择为空时,跳过其相应的转换.即,如果没有退出选择,则应立即开始更新选择.到目前为止,我已经提出了这个代码(使用该delay函数).
// DATA JOIN
var items = d3.select('#data').selectAll('.item');
items = items.data(data, function(d){
return d.twitter_screenname;
});
// EXIT
items.exit().transition().duration(TRANSITION_DURATION).style('opacity', 0).remove();
// UPDATE
// Divs bewegen
items.transition().duration(TRANSITION_DURATION).delay(TRANSITION_DURATION * 1)
.style('left', function(d, i) {
return positions[i].left + "px";
}).style('top', function(d, i) {
return positions[i].top + "px";
});
// ENTER
// Divs hinzufügen
var div = items.enter().append('div')
.attr('class', 'item')
.style('left', function(d, i) {
return positions[i].left + "px";
}).style('top', function(d, i) {
return positions[i].top + "px";
});
div.style('opacity', 0)
.transition().duration(TRANSITION_DURATION).delay(TRANSITION_DURATION * 2)
.style('opacity', 1);
Run Code Online (Sandbox Code Playgroud)
首先,它不允许"跳过"过渡,其次我认为有一种更好的方式delay.我看过http://bl.ocks.org/mbostock/3903818,但我真的不明白发生了什么.
此外,不知何故只是写作items.exit().transition().duration(TRANSITION_DURATION).remove()不起作用items,可能是因为它们不是SVG元素而是divs.
mbo*_*ock 33
当然.这有两种方式.
首先,您可以使用显式延迟,然后使用selection.empty计算跳过空转换.(这只是对你已经做过的一点修改.)
var div = d3.select("body").selectAll("div")
.data(["enter", "update"], function(d) { return d || this.textContent; });
// 2. update
div.transition()
.duration(duration)
.delay(!div.exit().empty() * duration)
.style("background", "orange");
// 3. enter
div.enter().append("div")
.text(function(d) { return d; })
.style("opacity", 0)
.transition()
.duration(duration)
.delay((!div.exit().empty() + !div.enter().empty()) * duration)
.style("background", "green")
.style("opacity", 1);
// 1. exit
div.exit()
.style("background", "red")
.transition()
.duration(duration)
.style("opacity", 0)
.remove();
Run Code Online (Sandbox Code Playgroud)
http://bl.ocks.org/mbostock/5779682
这里有一个棘手的问题是,在创建输入元素的转换之前,必须在更新元素上创建转换; 这是因为enter.append将输入元素合并到更新选择中,并且您希望将它们分开; 有关详细信息,请参阅仅更新转换示例.
或者,您可以使用transition.transition进行链转换,并使用transition.each将这些链式转换应用于现有选择.在transition.each的上下文中,selection.transition继承现有的转换而不是创建新的转换.
var div = d3.select("body").selectAll("div")
.data(["enter", "update"], function(d) { return d || this.textContent; });
// 1. exit
var exitTransition = d3.transition().duration(750).each(function() {
div.exit()
.style("background", "red")
.transition()
.style("opacity", 0)
.remove();
});
// 2. update
var updateTransition = exitTransition.transition().each(function() {
div.transition()
.style("background", "orange");
});
// 3. enter
var enterTransition = updateTransition.transition().each(function() {
div.enter().append("div")
.text(function(d) { return d; })
.style("opacity", 0)
.transition()
.style("background", "green")
.style("opacity", 1);
});
Run Code Online (Sandbox Code Playgroud)
http://bl.ocks.org/mbostock/5779690
我认为后者更具惯用性,尽管使用transition.each将转换应用于选择(而不是使用默认参数派生转换)并不是一个众所周知的特征.