Angular — Не удается использовать «scrollPositionRestoration»

#angular

#angular

Вопрос:

В настоящее время я использую Angular 6.1.5. Когда веб-сайт перенаправляется на другую страницу, я бы хотел, чтобы страница прокручивалась обратно к началу. Я пытался использовать { scrollPositionRestoration: 'top' } , но это не работает.

Вот мой код в app.routing.ts.

 export const routing = RouterModule.forRoot(appRoutes, { scrollPositionRestoration: 'top' });
  

Есть ли альтернатива этому? Я попытался изменить «top» на «enabled», но это также не работает. Я также попробовал window.scrollTo(0,0); и поместил его в ngOnInit() , но это тоже не работает.

Ответ №1:

В моем случае не сработало, потому что у меня это было в моем CSS.

 @media (prefers-reduced-motion: no-preference) {
  :root {
    scroll-behavior: smooth;
  }
}
  

Я изменил на

 scroll-behavior: auto;
  

И затем он начинает работать

Комментарии:

1. Отличная работа. поведение прокрутки: автоматическое; также будет работать в firefox.

2. Это отлично работает в safari. Спасибо 🙂

Ответ №2:

Обновите параметры в своем коде, чтобы также предоставить ему scrollOffset .

 export const routing = RouterModule.forRoot(appRoutes, { scrollOffset: [0, 0], scrollPositionRestoration: 'top' });
  

Другим вариантом было бы сделать это более «вручную». Вот StackBlitz, демонстрирующий этот подход. В принципе, в компоненте ввода для приложения (или в компоненте ввода для области вашего приложения с формами) вы могли бы подписаться на события маршрутизатора и на NavigationEnd вы можете использовать window.scrollTo

 import { Component } from '@angular/core';
import { Router, Event, NavigationEnd } from '@angular/router';
import { filter } from 'rxjs/operators';

@Component({
  selector: 'my-app',
  template: '<router-outlet></router-outlet>'
})
export class AppComponent  {
  constructor(
    router: Router
  ) {
    router.events
          .pipe(filter((routerEvent: Event) => routerEvent instanceof NavigationEnd))
          .subscribe(() => window.scrollTo(0, 0));
  }
}
  

Комментарии:

1. привет, это не сработало. страницы не будут прокручиваться обратно наверх. пробовал scrollPositionRestoration: также включено

2. @mhfour Вам нужно будет предоставить более подробную информацию о том, что вы делаете тогда. Вот StackBlitz , демонстрирующий, что вышеупомянутое действительно работает.

3. @peinarydevelopment я также слышал от многих других, которые заявляли, что все еще существуют проблемы с scrollPositionRestoration. у меня в основном есть страницы с очень длинными формами. когда пользователь нажимает «Сохранить» в нижней части формы, он / она должен быть перенаправлен в верхнюю часть следующей формы

4. @mhfour Я обновил свой ответ альтернативным подходом. К сожалению, ваш вопрос и комментарии на самом деле не помогают привести вас к решению. Я продемонстрировал, что scrollPositionRestoration это может работать, а вы не предоставили никаких подробностей о том, когда / где это не работает. Надеюсь, альтернативный подход решит вашу проблему.

Ответ №3:

Поскольку вы используете router-outlet, возможно, что элемент components имеет размер 0x0.
Путем добавления правила CSS в app-root к блоку отображения, заставило scrollPositionRestoration работать:

 app-root {
   display: block;
}

export const routing = RouterModule.forRoot(appRoutes, { scrollOffset: [0, 0], scrollPositionRestoration: 'top' });
  

Это должно сработать.

Ответ №4:

Единственное решение, которое работает для меня на Angular 10.2.x, — это использование setTimeout в течение 190 мс и не меньше! Если я установлю таймер ниже 190 мс, прокрутка не будет работать!

Когда я устанавливаю таймер на 300 мс, я вижу, как после маршрутизации страница сначала прокручивается до позиции, которая мне не нужна, а затем страница прокручивается до 0, как и должно быть. Я все еще не понимаю, какой процесс в Angular делает ненужной прокрутку после перехода на страницу.

Я пробовал разные предлагаемые решения. Например, такие, как изменение значения свойства scrollPositionRestoration и выполнение принудительной прокрутки в перехватчике AfterViewInit, и изменение глобальной высоты тега body и использование (activate) на выходе маршрутизатора и многие другие, но помогло только это. Скорее всего, это какая-то ошибка в маршрутизаторе Angular 10.2.x

 constructor(
  private router: Router,
) {
  router.events.subscribe(event => {
  if (event instanceof NavigationEnd) {
    setTimeout(() => {
      document.documentElement.scrollTop = 0; // || window.scrollTo(0, 0);
    }, 190);
  }
}