(D3) Data Driven Documents — Transition Repetition

谁都会走 提交于 2019-12-25 16:58:38

问题


I've looked for over 3 hours now trying to find a way to chain transitions indefinitely...

My only solution is wrapping the code in a function, then repeatedly calling the function with setInterval or waiting for the transition 'end' event

Example one liner:

d3.selectAll('circle').data([1,2,3]).enter().append('circle').attr('cy':function(d){return d * 100},'cx':function(){Math.random() * window.innerWidth},'r':'10px')

//sets initial locations for circles that are created to match data array

.transition().attr('cy':function(){Math.random() * window.innerHeight},'cx':function(){Math.random() * window.innerWidth}})
.transition().attr('cy':function(){Math.random() * window.innerHeight},'cx':function(){Math.random() * window.innerWidth}})
.transition().attr('cy':function(){Math.random() * window.innerHeight},'cx':function(){Math.random() * window.innerWidth}})
.transition().attr('cy':function(){Math.random() * window.innerHeight},'cx':function(){Math.random() * window.innerWidth}})
.transition().attr('cy':function(){Math.random() * window.innerHeight},'cx':function(){Math.random() * window.innerWidth}})

//I'm looking for something that can repeat the transition without using setInterval)

回答1:


One way or another, I think you're going to have to wrap your transition settings in a function, so that you can call it recursively. However, @Jon S. is right, you can use the transition's "end" event instead of a separate timer.

The complication is that the callback function in transition.each("end", callback) is (as the method name suggests) called for each element in the array. A simple check can make sure the recursion only happens once, for the first element, and doesn't branch indefinitely.

Here's an example: http://fiddle.jshell.net/UD9ng/1/

Key code:

var moving = false;

function move(selection) {

    moving = true;
    selection.transition().duration(5000).ease("sin-in-out")
        .attr("cx", function(){return Math.random()*width;})
        .attr("cy", function(){return Math.random()*height;})
        //.call(move); //stack overflow error!
        .each("end", function(d,i){ 
            if (!i) circles.call(move); //only run for i==0
        });

}

As you can see from the comments, I tried using the transition's .call() method (which invokes a function once for the entire transition object), but there is no way currently to delay that call until the end of the transition, so repeated sub-transition calls were being added to a queue until the console spit out an error with a huge stack trace behind it. The weird thing was, it didn't look like anything was wrong, since all the queued-up transitions were still moving smoothly -- but they would have run out of transitions eventually.

The each/end approach -- with the recursive function called on the original selection -- replaces the finished transition instead of chaining to it, so it can continue indefinitely without consuming increasing resources.



来源:https://stackoverflow.com/questions/21211560/d3-data-driven-documents-transition-repetition

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!