Как предотвратить этот странный jQuery.animate() lag?
См. демонстрацию: jsFiddle
- У меня есть простая форма, которая переключается при нажатии 'show'/'cancel'
- Все работает отлично, но , если вы нажмете "отменить" вскоре после того, как будет раскрыта форма, есть хорошая 2-3-секундная отставание до начала анимации.
- Это не происходит, если вы подождали несколько секунд, прежде чем нажать "отменить".
- Задержка происходит во всех проверенных браузерах (например, ff, chrome).
1. Что может вызвать это отставание и как его можно предотвратить?
2. Есть ли лучший способ кодирования этой последовательности анимаций, который может предотвратить любые задержки?
HTML
<div id="newResFormWrap">
<form id="newResForm" action="" method="post" name="newRes">
<div id="newResFormCont">
<h3>title</h3>
<p>form!</p>
<div class="button" id="cancelNewRes">Cancel</div>
</div>
</form>
</div>
<div class="button" id="addRes">show</div>
JQuery
$("#newResForm").css({opacity: 0});
$("#addRes").click(function () {
toggleNewRes()
});
$("#cancelNewRes").click(function () {
toggleNewRes()
});
//toggleNewRes
function toggleNewRes() {
if ($("#newResFormWrap").css('display') == "none") {//if hidden
$("#addRes").animate({ opacity: 0 }, 'fast', function() {
$("#newResFormWrap").toggle('fast', function (){
$("#newResForm").animate({ opacity: 100 },2000);
});
});
} else { //if visible
$("#newResForm").animate({ opacity: 0 }, 100,function() {
$("#newResFormWrap").toggle('fast', function (){
$("#addRes").animate({ opacity: 100 });
});
});
}
}
Ответы
Ответ 1
Обязательно очистите очередь при запуске новой анимации с помощью stop()
:
$("#newResForm").stop().animate({ opacity: 0 }, 100,function() {
$("#newResFormWrap").toggle('fast', function (){
$("#addRes").animate({ opacity: 100 });
// ...
Что вызывает отставание, так это то, что ваша длинная 2-секундная анимация $("#newResForm").animate({ opacity: 100 },2000)
еще не закончена. JQuery помещает анимацию по умолчанию в очередь, ожидая завершения ее до начала следующего. Вы очищаете очередь с помощью stop()
, что особенно полезно, если у вас есть две противоречивые анимации (например, открытая и закрытая анимация или анимация мыши/мыши). На самом деле вам может показаться хорошей практикой начать все ваши цепочки анимации с помощью stop()
, если вы не знаете, что хотите, чтобы они стояли в очереди с предыдущими анимациями, которые могли произойти в другом месте.
Перейдя в более сложные темы, вы можете даже назвать разные очереди, чтобы, например, анимация зависания и анимация разворачивания/сглаживания обрабатывались отдельно для целей stop()
. Для получения дополнительной информации см. Опцию queue
(если задана строка) в http://api.jquery.com/animate/.
Ответ 2
Добавьте .stop()
перед вашими вызовами анимации:
function toggleNewRes() {
if ($("#newResFormWrap").css('display') == "none") {//if hidden
$("#addRes").stop().animate({ opacity: 0 }, 'fast', function() {
/...
});
} else { //if visible
$("#newResForm").stop().animate({ opacity: 0 }, 100,function() {
/...
});
}
}
Ответ 3
Попробуйте использовать stop()
:
Вот jsfiddle.
if ($("#newResFormWrap").is(':visible')) {//this way is eaiser to check
$("#addRes").stop(true,false).animate({ opacity: 0 }, 'fast', function() {
$("#newResFormWrap").toggle('fast', function (){
$("#newResForm").animate({ opacity: 100 },2000);
});
});
}
Ответ 4
Пара вещей. Сначала проверьте JSFiddle, чтобы увидеть его в действии.
Проблема заключается в том, что ваше затухание в анимации занимает 2 секунды. Поэтому, когда вы закрываете его в течение 2 секунд, вы получаете задержку.
Я перекомпилировал ваши тайминги, чтобы гарантировать, что нет задержки. Посмотрите, понравитесь ли вы им и не стесняйтесь изменять их по своему усмотрению.
if ($("#newResFormWrap").css('display') == "none") {//if hidden
$("#addRes").animate({ opacity: 0 }, 'fast', function() {
$("#newResFormWrap").toggle(0, function (){
$("#newResForm").animate({ opacity: 100 },400);
});
});
} else { //if visible
console.log('click');
$("#newResForm").animate({ opacity: 0 }, 0, function() {
console.log('animated');
$("#newResFormWrap").toggle(0)
});
$("#addRes").animate({ opacity: 100 }, 'fast');
}