10.09.2018, 16:39
|
Новичок на форуме
|
|
Регистрация: 10.09.2018
Сообщений: 4
|
|
Как задать порядок выполнения событий (анимаций)
Доброго времени суток!
Столкнулся с такой проблемой. Делаю скрипт к html-шаблону. Есть фрагмент в коде <div id="target" ...>. Необходимо сделать плавный скроллинг к нему по клику на ссылку <a href="#target">.
Проблема в том, что на этом клике висит ещё одно событие, которое скрывает некоторые элементы со страницы. Из-за этого положение координат целевого элемента смещается.
Каким образом добавить мой скрипт в очередь выполнения функций(событий), чтобы получить координаты для скроллинга после того как ранее установленные скрипты закончат скрытие элементов?
<!DOCTYPE HTML>
<html lang="ru-RU">
<head><title></title><meta charset="UTF-8"></head>
<body>
<script type="text/javascript" src="https://code.jquery.com/jquery-3.3.1.js"></script>
<script type="text/javascript" src="https://code.jquery.com/ui/1.12.1/jquery-ui.js"></script>
<script type="text/javascript">
/* Этот фрагмент нельзя менять */
$(function(){
$('a[href^="#"]').click( function() {
$('#hideme').hide(1000);
});
});
/* Далее всё что угодно */
$(function(){
$('a[href^="#"]').click( function() {
var sc = $(this).attr("href");
var dn = $(sc).offset().top;
// sc - в переменную заносим информацию о том, к какому блоку надо перейти
// dn - определяем положение блока на странице
alert('Положение блока на странице по вертикали '+dn+' (Ошибочное)');
$('html, body').animate({scrollTop: dn}, 1000);
// 1000 скорость перехода в миллисекундах
$('a').remove();
});
});
</script>
<a href="#target">Перейти к фрагменту</a>
<div id="hideme" style="display:block;width: 100%; height: 500px; background: green;"></div>
<div id="other" style="display:block;width: 100%; height: 1200px; background: yellow;"></div>
<div id="target" style="display:block;width: 100%; height: 300px; background: red;"></div>
<div id="other" style="display:block;width: 100%; height: 700px; background: blue;"></div>
<div id="other" style="display:block;width: 100%; height: 700px; background: magenta;"></div>
</body>
</html>
|
|
10.09.2018, 16:43
|
Профессор
|
|
Регистрация: 14.01.2015
Сообщений: 12,989
|
|
RedPython,
опишите в одном обработчике, поставив в очередь анимации или hide(1000, function() { анимация прокрутки})
|
|
10.09.2018, 16:56
|
Новичок на форуме
|
|
Регистрация: 10.09.2018
Сообщений: 4
|
|
laimas, при этом варианте прийдётся править фрагмент в большой js-библиотеке, которую писал сторонний разработчик.
Из костылей можно использовать setTimeout, но на реальной странице выглядит мягко говоря коряво...
$(function(){
$('a[href^="#"]').click( function() {
var sc = $(this).attr("href");
setTimeout(function ()
{
var dn = $(sc).offset().top;
// sc - в переменную заносим информацию о том, к какому блоку надо перейти
// dn - определяем положение блока на странице
$('html, body').animate({scrollTop: dn}, 1000);
// 1000 скорость перехода в миллисекундах
}, 1000);
$('a').remove();
});
});
|
|
10.09.2018, 17:06
|
Профессор
|
|
Регистрация: 14.01.2015
Сообщений: 12,989
|
|
RedPython,
а чего там править, вы же нашли эти два фрагмента, сложно перенести один в другой?
|
|
10.09.2018, 17:17
|
|
Профессор
|
|
Регистрация: 27.05.2010
Сообщений: 33,126
|
|
плавный переход к блоку
RedPython,
<!DOCTYPE HTML>
<html lang="ru-RU">
<head><title></title><meta charset="UTF-8"></head>
<body>
<script type="text/javascript" src="https://code.jquery.com/jquery-3.3.1.js"></script>
<script type="text/javascript" src="https://code.jquery.com/ui/1.12.1/jquery-ui.js"></script>
<script type="text/javascript">
/* Этот фрагмент нельзя менять */
$(function(){
$('a[href^="#"]').click( function(event) {
event.preventDefault();
var id = this.hash;
$(this).remove();
$('#hideme').slideUp(1000, function() {
var dn = $(id).offset().top;
$('html, body').animate({scrollTop: dn}, 1000);
});
});
});
</script>
<a href="#target">Перейти к фрагменту</a>
<div id="hideme" style="display:block;width: 100%; height: 500px; background: green;"></div>
<div id="other" style="display:block;width: 100%; height: 1200px; background: yellow;"></div>
<div id="target" style="display:block;width: 100%; height: 300px; background: red;"></div>
<div id="other" style="display:block;width: 100%; height: 700px; background: blue;"></div>
<div id="other" style="display:block;width: 100%; height: 700px; background: magenta;"></div>
</body>
</html>
Последний раз редактировалось рони, 10.09.2018 в 17:20.
|
|
10.09.2018, 17:19
|
|
Тлен
|
|
Регистрация: 02.01.2010
Сообщений: 6,590
|
|
"Нельзя менять" - это крайне нездоровая хрень.
Из костылей можно сделать так:
/* Далее всё что угодно */
$(function(){
$('a[href^="#"]')
.off('click') // отменяем поставленные ранее кем-то обработчики
.click(function(){ // ставим заново общий
var sc = $(this).attr("href");
$('#hideme').hide(1000, function(){
var dn = $(sc).offset().top;
// sc - в переменную заносим информацию о том, к какому блоку надо перейти
// dn - определяем положение блока на странице
alert('Положение блока на странице по вертикали '+dn+' (Ошибочное)');
$('html, body').animate({scrollTop: dn}, 1000);
// 1000 скорость перехода в миллисекундах
$('a').remove(); // удаляем все ссылки на страницые, это точно нужно?
});
});
});
Второй вариант - поменять метод hide jquery добавив какую-нить отсебятину, например:
$.fn.hide = function(hide){
return function(speed, callback) {
this.trigger('hide');
return hide.apply(this, arguments);
}
}($.fn.hide);
и соответственно на on('hide') повесить всё нужное.
__________________
29375, 35
|
|
10.09.2018, 19:19
|
Новичок на форуме
|
|
Регистрация: 10.09.2018
Сообщений: 4
|
|
Сообщение от laimas
|
RedPython,
а чего там править, вы же нашли эти два фрагмента, сложно перенести один в другой?
|
Потому, что это шаблон построен на функционале аккордион (спойлер) из bootstrap + всякие "плюшки"... был сделан примерный код, чтобы не перебирать все 100500 скриптов с html-вёрсткой
|
|
10.09.2018, 19:44
|
|
Профессор
|
|
Регистрация: 27.05.2010
Сообщений: 33,126
|
|
Сообщение от RedPython
|
(спойлер) из bootstrap
|
http://bootstrap-doc.ru/v4/component...pse.php#events
... возможно так
$(function(){
var id;
$('#hideme').on('hidden.bs.collapse', function() {
var dn = $(id).offset().top;
id && $('html, body').animate({scrollTop: dn}, 1000);
});
$('a[href^="#"]').click( function(event) {
var id = this.hash;
});
});
|
|
10.09.2018, 19:46
|
Новичок на форуме
|
|
Регистрация: 10.09.2018
Сообщений: 4
|
|
Сообщение от Aetae
|
"Нельзя менять" - это крайне нездоровая хрень.
|
Всё нормально там. Из костылей можно setTimeout использовать, но из-за необходимости допиливания ещё нескольких функций, этот велосипед быстро развалится.
Там на самом деле большая лента из секций, которая представляют собой спойлеры. Разные скрипты, которые обрабатывают в каждой раскрытой секции чекбоксы и прочие меню. После заполнения пользователем секции отрабатывают скрипты, которые проводят валидацию и перенаправляют в нужную секцию (с точки зрения приложения). Вдобавок ко всему ещё внутри секции попадает контент из ajax. Поэтому знать размер секции нельзя знать наверняка.
Дело в том, что из-за того что секции раскрываются то там то здесь (ну на самом деле только предыдущая или следующая). То пользователя сильно напрягает, почему он вдруг застрял с заполнением анкеты.
Код в теме, чисто демонстрационный. Главный вопрос в том, как управлять очередью выполнения анимации событий.
За лазанье в код фреймворков по ушам надают. Так как регламент работ запрещает менять стандартную логику библиотек. Потому, что это приведёт к запаркам у других разработчиков.
Последний раз редактировалось RedPython, 10.09.2018 в 19:50.
|
|
|
|