Автопрокрутка до последнего элемента массива: решение на JS
Быстрый ответ
Мгновенно переместите видимую область страницы к определённому элементу с помощью метода scrollIntoView
:
document.querySelector('.target').scrollIntoView();
Добавьте опцию для плавного перемещения:
document.querySelector('.target').scrollIntoView({ behavior: 'smooth' });
Применение в React: непосредственное перемещение
В мире React для обращения к DOM-элементам встречается применение refs. Вообще это напоминает процесс вызова предмета в магическом мире Гарри Поттера, только для элементов HTML:
const elementRef = useRef(null);
Правда, в отличие от волшебного мира, нам всё же приходится привязывать данный ref к целевому элементу:
<div ref={elementRef}>Вот и цель</div>
Теперь мы в состоянии прокрутить страницу к нужному элементу:
elementRef.current?.scrollIntoView({ behavior: 'smooth', block: 'start' });
Не забывайте использовать оператор ?.
для проверки наличия значения в ref
. Это поможет избежать ошибки undefined
.
Визуализация
Вообразим, словно веб-страница — это небесное пространство:
🌥️
🏔️ 🎯 <- Элемент (Цель вашего пути!)
🌳🌳🌳
Начинаем прокрутку с использованием scrollIntoView
:
element.scrollIntoView({ behavior: 'smooth' });
Продолжаем движение:
🌥️ ✈️
🏔️ 🎯 <- Ещё чуть-чуть...
🌳🌳🌳
И вот настал момент для идеального приземления:
🌥️
🏔️ ✈️ -> 🎯 <- Приземляемся!
🌳🌳🌳
Достаточно прозрачно, не так ли?
Детальное рассмотрение прокрутки
Может быть, вы думаете: "Нужна прокрутка, а не обрисовка вселенной Marvel". Но на самом деле мы упростили задачу и сосредоточились на ней, превратив всё в самостоятельную функцию:
const executeScroll = () => elementRef.current?.scrollIntoView(
{ behavior: 'smooth' }
);
Не забывайте, что использование ReactDOM.findDOMNode
нежелательно, это не самый лучший подход.
Чтобы включить плавную прокрутку, добавьте в CSS:
html {
scroll-behavior: smooth;
}
Для динамических списков, например, чат-ботов, которые работают неуклонно круглым суткам:
const messagesEndRef = useRef([]);
{messages.map((message, index) => (
<div key={index} ref={el => messagesEndRef.current[index] = el}>{message}</div>
))}
Прокрутка до последнего сообщения выполняется так:
if (isNewMessage) {
messagesEndRef.current[messages.length – 1]?.scrollIntoView({ behavior: 'smooth' });
}
Мастерство управления прокруткой
Динамические переходы
При необходимости переключаться между различными элементами, добавьте немного логики для выбора целевого элемента для метода scrollIntoView
.
Прокрутка по запросу
Реализуйте прокрутку по запросу. Например, прокрутка может быть запущена только при наступлении определённого события или выполнении действия пользователем.
Скрытая сложность
Сокройте механизм прокрутки позади абстракции — воспользуйтесь функциями или кастомными хуками. Так вы сосредоточите внимание на основном, при этом подробности реализации останутся не бросающимися в глаза.
Полезные ресурсы
- Метод Element: scrollIntoView() – Веб API | MDN — исчерпывающее руководство по
scrollIntoView
. - Плавная прокрутка | CSS-Tricks – CSS-Tricks — советы по созданию плавной прокрутки с применением jQuery.
- Метод Window scrollTo() — как выполнить прокрутку: советы от W3Schools.
- Плавная прокрутка до конкретного div при клике – Javascript — Stack Overflow — пример реализации плавной прокрутки.
- Can I use... Таблицы поддержки для HTML5, CSS3 и т. д. — здесь вы можете проверить совместимость своего CSS-кода.
- Как реализовать плавную прокрутку на чистом JavaScript — SitePoint — создание плавной прокрутки вручную.
- API наблюдателя за пересечениями – Веб API | MDN — законное наблюдение за элементами, описанное в официальной документации.