Как проверить, прокрутил ли пользователь (или перешел) до определенного элемента (на основе идентификатора) в Angular7? - PullRequest
1 голос
/ 21 апреля 2019

Как проверить, прокрутил ли пользователь (или перешел) до определенного элемента (на основе идентификатора) в браузере, чтобы я мог проверить условие и назначить имя класса динамически в угловых 7?

Ответы [ 2 ]

1 голос
/ 21 апреля 2019

По сути, вы можете прослушивать событие прокрутки окна с Angular, используя HostListener с событием window:scroll, например:

@HostListener('window:scroll', ['$event'])
onWindowScroll() {
  // handle scrolling event here
}

Доступен Пример StackBlitz для объяснения ниже

ScrolledTo директива

Что бы я сделал для максимальной гибкости в этом случае, - это создать директиву для применения к любому элементу HTML, который предоставил бы два состояния:

  • достигается : true, когда позиция прокрутки достигает вершины элемента, к которому применяется директива
  • пройдено : true когда позиция прокрутки прошла высоту элемента, к которой применяется директива
import { Directive, ElementRef, HostListener } from '@angular/core';

@Directive({
  selector: '[scrolledTo]',
  exportAs: 'scrolledTo', // allows directive to be targeted by a template reference variable
})
export class ScrolledToDirective {
  reached = false;
  passed = false;

  constructor(public el: ElementRef) { }

  @HostListener('window:scroll', ['$event'])
  onWindowScroll() {
    const elementPosition = this.el.nativeElement.offsetTop;
    const elementHeight = this.el.nativeElement.clientHeight;
    const scrollPosition = window.pageYOffset;

    // set `true` when scrolling has reached current element
    this.reached = scrollPosition >= elementPosition;

    // set `true` when scrolling has passed current element height
    this.passed = scrollPosition >= (elementPosition + elementHeight);
  }
}

Назначение классов CSS

Используя переменную ссылки на шаблон , вы сможете получить эти состояния, определяющие директиву export #myTemplateRef="scrolledTo", в своем HTML-коде и применять классы CSS по своему усмотрению в соответствии с возвращаемыми значениями.

<div scrolledTo #scrolledToElement="scrolledTo">
  <!-- whatever HTML content -->
</div>

<div
  [class.reached]="scrolledToElement.reached"
  [class.passed]="scrolledToElement.passed">
  <!-- whatever HTML content -->
</div>

Таким образом, вы можете назначать классы другим HTML-элементам или самому элементу spied ... практически так, как вы хотите, в зависимости от ваших потребностей!

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

0 голосов
/ 22 апреля 2019

Использовать "IntersectionObserver" - https://developer.mozilla.org/en-US/docs/Web/API/Intersection_Observer_API

Создайте директиву, как указано ниже в примере, и примените к элементу, который вы хотите отслеживать. Когда элемент станет видимым, будет запущен объект пересечения!

Ниже приведен угловой пример загрузки содержимого div (изображения) только тогда, когда границы div видны.

https://stackblitz.com/edit/angular-intersection-observor

<span class="card" *ngFor="let card of data" (deferLoad)="card.visible = true">
    <img src={{card.url}} *ngIf="card.visible"/>
</span>


import { Directive, Output, EventEmitter, ElementRef, AfterViewInit } from '@angular/core';
@Directive({
  selector:"[deferLoad]"
})
export class DeferLoadDirective implements AfterViewInit {
  private _intersectionObserver: IntersectionObserver;

  @Output() deferLoad: EventEmitter<any> = new EventEmitter();

  constructor(
    private _element: ElementRef
  ) {};

  ngAfterViewInit() {
    this._intersectionObserver = new IntersectionObserver(entries => {
      this.checkIntersection(entries);
    });
    this._intersectionObserver.observe(this._element.nativeElement as Element);
  }

  checkIntersection(entries: IntersectionObserverEntry[]) {
    entries.forEach((entry) => {
      if ((<any>entry).isIntersecting && entry.target === this._element.nativeElement) {
        this.deferLoad.emit();
        this._intersectionObserver.unobserve(this._element.nativeElement as Element);
        this._intersectionObserver.disconnect();
      }
    });
  }

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