2013-05-09 3 views
1

Я использую модифицированную версию этого D3 tutorial bar chart.d3.js: Обратный вызов перехода не вызывается для ввода()

Что важно для меня, так это то, что анимация не должна складываться при выходе из окна браузера, а затем запускать все из них, когда окно снова находится в фокусе, заставляя браузер зависать, так как в соответствии с this suggestion, я пытаюсь использовать a setTimeout вместо setInterval, который должен вызываться, когда анимация закончилась.

У меня проблемы с обратными вызовами, и я не понимаю, почему работает обратный вызов transition(), но не enter().

После настроить масштаб графика &, вот как моя инициализация функция выглядит следующим образом:

function redrawTimer() { 
    data.shift(); 
    data.push(next()); 
    redraw(function(){ 
    console.log('callback'); 
    setTimeout(redrawTimer, 1500); 
    }); 
} 

setTimeout(redrawTimer, 1500); 

function redraw(callback) { 

    var rect = chart.selectAll("rect") 
     .data(data, function(d) { return d.time; }); 

    rect.enter().insert("rect") 
     .attr("x", function(d, i) { return x(i + 1) - .5; }) 
     .attr("y", function(d) { return h - y(d.value) - .5; }) 
     .attr("width", w) 
     .attr("height", function(d) { return y(d.value); }) 
     .attr("fill", "white") 
     .attr("fill-opacity", 0.2) 
    .transition() 
     .duration(1000) 
     .attr("x", function(d, i) { return x(i) - .5; }) 
     .each('end', callback); // Doesn't work at all 

    rect.transition() 
     .duration(1000) 
     .attr("x", function(d, i) { return x(i) - .5; }); 
     //.each('end', callback); // Works but for each of the 50 elements 

    rect.exit().transition() 
     .duration(1000) 
     .attr("x", function(d, i) { return x(i - 1) - .5; }) 
     //.each('end', callback) // This only works after the first transition so using it to trigger the next data point is useless 
     .remove(); 
} 

См this jsFiddle для возились с кодом :)

Это может быть, что я не вполне понимаю, как transition() работает по-разному на enter() или exit() или только на селектор.

Можете ли вы меня просветить?

Если вы можете сделать обратную связь, но не решите мою проблему, указанную выше (анимация при выходе из браузера), пожалуйста, помогите мне в этом, так как я отвечу ваши комментарии/ответ.

Edit:

мне удалось избавиться от нароста очереди анимации путем тестирования, для которых элемент перехода закончился, и только взять последний:

rect.transition() 
     .duration(1000) 
     .attr("x", function(d, i) { return x(i) - .5; }) 
     .each('end', function(d, i){ 
     if(i == 49) 
      callback(); 
     }); 

ответ

6

Элементы могут иметь только один активный переход за раз. rect.enter().transtition() сразу же перезаписывается rect.transition() (rect - это выбор обновления, который также содержит элементы ввода!). Поэтому rect.enter().transition().each('end', callback) никогда не вызывается.

Для получения дополнительной информации см. API documentation on transitions или Mike's tutorial.

+0

Это имело бы смысл, но меня озадачило то, что 'attr (" x ", function ..)" после ''() запускается, как ожидалось, 50 раз, если я ставлю 'console.log' внутри функции. Но не конец обратного вызова. Кроме того, ваш ответ будет означать, что код учебника неисправен. – Cristian

+1

'rect.enter(). Attr (" x ", ...)' не то же самое, что 'rect.enter(). Transition(). Attr (" x ", ...)'. Но, как ни странно, каждый вызов '.attr (" x ", ...)' запускается. Я предполагаю, что 'rect.enter(). Transition()' запускается и впоследствии отменяется с помощью 'rect.transition()'. Поэтому каждый '.attr (« x », ...)' вызывается, но '.each (« end », ...)' в выборе ввода не будет. Чтобы избежать путаницы, просто удалите переход ввода. Этот код отлично работает без него. Если вы хотите иметь _different_ переходы для ввода и обновления, укажите переход обновления _before_ переходы ввода. – herrstucki

+0

Кто-то должен обновить этот учебник, тогда это очень вводит в заблуждение, написав переход дважды http://mbostock.github.io/d3/tutorial/bar-2.html – Cristian

Смежные вопросы