JQuery слайд нервный - PullRequest
       106

JQuery слайд нервный

62 голосов
/ 26 августа 2009

Я пытался вставлять и выводить DIV с помощью функции переключения jQuery, но результат всегда скачок в начале и / или конце анимации. Вот код js, который я использую:

$(document).ready(function(){
    $('#link1').click(
        function() {
            $('#note_1').parent().slideToggle(5000);
        }
);

И HTML:

<div class="notice">
    <p>Here's some text. And more text. <span id="link1">Test1</span></p>
    <div class="wrapper">
        <div id="note_1">
            <p>Some content</p>
            <p>More blalba</p>
        </div>
    </div>
</div>

Вы также можете увидеть полный пример здесь: jQuery Slide test

Я обычно использую Mootools и могу без проблем создавать этот слайд. Но я начинаю новый проект в Django, и большинство приложений в Django используют jQuery. Итак, для этого и после прочтения jQuery против Mootools я решил, что это будет хорошим поводом начать использовать jQuery. Поэтому моей первой потребностью было сделать слайд с этим DIV. И это не сработало должным образом.

Я провел дополнительный поиск и обнаружил, что это старая ошибка в jQuery с полями и отступами, примененными к DIV. Решение состоит в том, чтобы обернуть DIV в другой DIV. В моем случае это не помогло.

Продолжая поиск, я обнаружил этот пост Анимация слайд-слайда повторно посещена . Это исправляет скачок на одном конце, но не на другом ( Test2 in jQuery Slide test ).

На переполнении стека я нашел это jQuery IE анимация отрывистого слайда . В комментариях я увидел, что проблема с тегом P внутри DIV. Если я заменю P-теги на DIV-теги, которые решают проблему, но это не является правильным решением.

Наконец я нашел это Странное поведение jQuery, слайд . Прочитав его, я понял, что проблема, решаемая переключением с тега P на DIV, заключалась в полях P (отсутствует в DIV) и коллапсе полей между элементами. Поэтому, если я переключу поля на отступы, это решит проблему. Но я теряю рушащееся поведение полей, которое я хочу.

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

Я пропустил более простое решение?

Как подсказывает krdluzni, я пытался написать как собственный скрипт с помощью метода animate. Вот мой код:

var $div = $('#note_2').parent();
var height = $div.height();

$('#link2').click(
    function () {
        if ( $div.height() > 0 ) {
            $div.animate({ height: 0 }, { duration: 5000 }).css('overflow', 'hidden');
        } else {
            $div.animate({ height : height }, { duration: 5000 });
        }

        return false;
});

Но это тоже не работает, потому что jQuery всегда устанавливает переполнение на видимое в конце анимации. Таким образом, DIV снова появляется в конце анимации, но накладывается на остальную часть контента.

Я пробовал также с UI.Slide (и Scale and Size). Это работает, но содержимое под DIV не перемещается с анимацией. Это только прыжок в конце / начале анимации, чтобы заполнить пробел. Я не хочу этого

UPDATE:

Одной из частей решения является динамическая установка высоты контейнера DIV перед чем-либо. Это решить одним прыжком. Но не единственная причина разрушения маржи. Вот код:

var parent_div = $("#note_1").parent();
parent_div.css("height", parent_div.height()+"px");
parent_div.hide();

ВТОРОЕ ОБНОВЛЕНИЕ:

Вы можете увидеть ошибку на собственном сайте jQuery на этой странице (пример B): Обучающие программы: живые примеры jQuery

ТРЕТЬЕ ОБНОВЛЕНИЕ:

Пробовал с jQuery 1.4, больше никаких шансов: - (

Ответы [ 28 ]

42 голосов
/ 22 декабря 2011

Я обнаружил, что последовательно работает установка невидимой границы в 1 пиксель:

border: 1px solid transparent;

Нет необходимости фиксировать ширину, высоту или что-либо еще, и анимация не прыгает Ура!

33 голосов
/ 15 января 2010

Решение состоит в том, что скользящий div должен иметь ширину, заданную в пикселях. Не используйте ни auto, ни%. И у тебя будет отличный результат! Проблема заключается во встроенных элементах, которые находятся в скользящем элементе div.

но если они имеют ширину в пикселях, высота будет одинаковой. Попытайся.

21 голосов
/ 27 июля 2012

Я столкнулся с этой проблемой сегодня. Однако я заметил, что отключение всех CSS решило проблему. Также я знал, что раньше он работал нормально, поэтому, должно быть, последние изменения вызвали проблему.

Оказалось, что я использовал переходы в CSS для облегчения всплытия и выхода из него .

Как только эти переходы были удалены из элементов, которые я добавлял, все было хорошо.

Так что, если у вас та же проблема, просто добавьте эти строки к элементам, которые вы добавляете:

-webkit-transition: none;
-moz-transition: none;
-o-transition: none;
-ms-transition: none;
transition: none;

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

14 голосов
/ 26 августа 2009

Попробуйте удалить все поля CSS из всех элементов. Обычно отрывистая анимация происходит из-за того, что рамки анимации не учитываются.

4 голосов
/ 13 ноября 2015

Дрожание происходит, когда родительский div ".wrapper" в вашем случае имеет отступ.

Заполнение идет на дочернем div, а не на родительском. jQuery - анимация высоты, а не заполнение.

Пример:

  <div class="notice">
     <p>Here's some text. And more text. <span id="link1">Test1</span></p>
     <div class="wrapper" style="padding: 0">
        <div id="note_1" style="padding: 20px">
           <p>Some content</p>
           <p>More blalba</p>
        </div>
     </div>
   </div>

Надеюсь, это поможет.

3 голосов
/ 07 сентября 2012

Я считаю, что animate () - это самый надежный способ анимировать что-либо в jQuery (по крайней мере, через браузер).

Это динамически оборачивает содержимое в div, а затем анимирует высоту этой оболочки div, используя высоту его внутреннего содержимого.

http://jsfiddle.net/BmWjy/13/

$('a').click(function(event) {
        event.preventDefault();
        xToggleHeight($(this).next());
});

//For each collapsible element.
$('.collapsible').each(function() {
        //Wrap a div around and set to hidden.
        $(this).wrap('<div style="height:0;overflow:hidden;visibility:hidden;"/>');
});

function xToggleHeight(el){
        //Get the height of the content including any margins.
        var contentHeight = el.children('.collapsible').outerHeight(true);
        //If the element is currently expanded.
        if(el.hasClass("expanded")){
                //Collapse
                el.removeClass("expanded")
                        .stop().animate({height:0},5000,
                        function(){
                                //on collapse complete
                                //Set to hidden so content is invisible.
                                $(this).css({'overflow':'hidden', 'visibility':'hidden'});
                        }
                );
        }else{
                //Expand
                el.addClass("expanded").css({'overflow':'', 'visibility':'visible'})
                        .stop().animate({height: contentHeight},5000,
                        function(){
                                //on expanded complete
                                //Set height to auto incase browser/content is resized afterwards.
                                $(this).css('height','');
                        }
                );
        }
}
2 голосов
/ 30 декабря 2016

Для меня удаление минимальной высоты из моего контейнера решило проблему.

2 голосов
/ 20 октября 2013

Очевидно, что существует множество разных решений этой проблемы - и в зависимости от вашего макета разные решения имеют разные результаты.

Вот что у меня было (урезано)

<div>
   <p>Text</p>
</div>
<div class="hidden">
   <p></p>
</div>

Когда я буду использовать jQuery для отображения <div class="hidden">, поле элемента <p> будет свернуто с полем элемента <p> над ним.

Я думал, что это было странно, поскольку они были в разных <divs>.

Мое решение состояло в том, чтобы убрать поле в нижней части <p>. Наличие поля на одной стороне предотвращает сужение поля снизу первого <p> с верхом второго <p>.

Этот обходной путь решил мою проблему, возможно, может быть применен к другим, но может не работать для всех.

2 голосов
/ 01 февраля 2011

Я заметил, если у вас есть <br /> после вашего контейнера <div>, анимация также будет нервной. Удаление этой проблемы решило мою проблему.

2 голосов
/ 26 августа 2009

Вы можете написать собственную анимацию, используя метод animate. Это даст вам абсолютный контроль над всеми деталями.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...