@thisissoon/angular-scrollspy
Version:
A simple lightweight library for Angular which automatically updates links to indicate the currently active section in the viewport
107 lines • 8.4 kB
JavaScript
/**
* @fileoverview added by tsickle
* @suppress {checkTypes,extraRequire,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
*/
import { Injectable } from '@angular/core';
/**
* Service that stores a list of `Spy`'s and the state
* of their nav items `inViewport` and `active` state
*
*/
export class ScrollSpyService {
constructor() {
/**
* List of `Spy`'s
*
* \@memberof ScrollSpyService
*/
this.spys = [];
/**
* Stores requests to add items to spy when spy hasn't been created
* yet. Once spy has been added then request will be made again.
*
* \@memberof ScrollSpyService
*/
this.buffer = [];
}
/**
* Add spy to list of `spys`
*
* \@memberof ScrollSpyService
* @param {?} id
* @param {?} items
* @return {?}
*/
addSpy(id, items) {
this.spys.push({ id, items });
/** @type {?} */
const buffer = this.buffer.filter(i => i.spyId === id);
this.buffer = this.buffer.filter(i => i.spyId !== id);
buffer.forEach(i => this.setSpySectionStatus(i.sectionId, i.spyId, i.inViewport));
}
/**
* Remove spy from list of `spys`
*
* \@memberof ScrollSpyService
* @param {?} id
* @return {?}
*/
removeSpy(id) {
/** @type {?} */
const i = this.spys.findIndex(s => s.id === id);
this.spys.splice(i, 1);
}
/**
* Set the `inViewport` status for a spy item then sets the active
* to true for the first item in the list that has `inViewport`
* set to true
*
* \@memberof ScrollSpyService
* @param {?} sectionId
* @param {?} spyId
* @param {?} inViewport
* @return {?}
*/
setSpySectionStatus(sectionId, spyId, inViewport) {
/** @type {?} */
const spy = this.spys.find(s => s.id === spyId);
if (!spy) {
this.buffer.push({ sectionId, spyId, inViewport });
return;
}
/** @type {?} */
const item = spy.items.find(i => i.section === sectionId);
if (!item) {
return;
}
item.inViewport = inViewport;
/** @type {?} */
const firstInViewport = spy.items.filter(i => i.inViewport)[0];
spy.items.forEach(i => (i.active = false));
if (firstInViewport) {
firstInViewport.active = true;
firstInViewport.detectChanges();
}
}
}
ScrollSpyService.decorators = [
{ type: Injectable }
];
if (false) {
/**
* List of `Spy`'s
*
* \@memberof ScrollSpyService
* @type {?}
*/
ScrollSpyService.prototype.spys;
/**
* Stores requests to add items to spy when spy hasn't been created
* yet. Once spy has been added then request will be made again.
*
* \@memberof ScrollSpyService
* @type {?}
*/
ScrollSpyService.prototype.buffer;
}
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic2Nyb2xsLXNweS5zZXJ2aWNlLmpzIiwic291cmNlUm9vdCI6Im5nOi8vQHRoaXNpc3Nvb24vYW5ndWxhci1zY3JvbGxzcHkvIiwic291cmNlcyI6WyJhcHAvc2Nyb2xsLXNweS9zY3JvbGwtc3B5LXNlcnZpY2Uvc2Nyb2xsLXNweS5zZXJ2aWNlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7QUFBQSxPQUFPLEVBQUUsVUFBVSxFQUFhLE1BQU0sZUFBZSxDQUFDOzs7Ozs7QUFXdEQsTUFBTSxPQUFPLGdCQUFnQjtJQUQ3Qjs7Ozs7O1FBT1MsU0FBSSxHQUFVLEVBQUUsQ0FBQzs7Ozs7OztRQU9qQixXQUFNLEdBQVUsRUFBRSxDQUFDO0lBc0Q1QixDQUFDOzs7Ozs7Ozs7SUFoRFEsTUFBTSxDQUFDLEVBQVUsRUFBRSxLQUF3QztRQUNoRSxJQUFJLENBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxFQUFFLEVBQUUsRUFBRSxLQUFLLEVBQUUsQ0FBQyxDQUFDOztjQUN4QixNQUFNLEdBQUcsSUFBSSxDQUFDLE1BQU0sQ0FBQyxNQUFNLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsS0FBSyxLQUFLLEVBQUUsQ0FBQztRQUN0RCxJQUFJLENBQUMsTUFBTSxHQUFHLElBQUksQ0FBQyxNQUFNLENBQUMsTUFBTSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEtBQUssS0FBSyxFQUFFLENBQUMsQ0FBQztRQUN0RCxNQUFNLENBQUMsT0FBTyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQ2pCLElBQUksQ0FBQyxtQkFBbUIsQ0FBQyxDQUFDLENBQUMsU0FBUyxFQUFFLENBQUMsQ0FBQyxLQUFLLEVBQUUsQ0FBQyxDQUFDLFVBQVUsQ0FBQyxDQUM3RCxDQUFDO0lBQ0osQ0FBQzs7Ozs7Ozs7SUFNTSxTQUFTLENBQUMsRUFBVTs7Y0FDbkIsQ0FBQyxHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsU0FBUyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsS0FBSyxFQUFFLENBQUM7UUFDL0MsSUFBSSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDO0lBQ3pCLENBQUM7Ozs7Ozs7Ozs7OztJQVFNLG1CQUFtQixDQUN4QixTQUFpQixFQUNqQixLQUFhLEVBQ2IsVUFBbUI7O2NBRWIsR0FBRyxHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsS0FBSyxLQUFLLENBQUM7UUFDL0MsSUFBSSxDQUFDLEdBQUcsRUFBRTtZQUNSLElBQUksQ0FBQyxNQUFNLENBQUMsSUFBSSxDQUFDLEVBQUUsU0FBUyxFQUFFLEtBQUssRUFBRSxVQUFVLEVBQUUsQ0FBQyxDQUFDO1lBQ25ELE9BQU87U0FDUjs7Y0FDSyxJQUFJLEdBQUcsR0FBRyxDQUFDLEtBQUssQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsT0FBTyxLQUFLLFNBQVMsQ0FBQztRQUN6RCxJQUFJLENBQUMsSUFBSSxFQUFFO1lBQ1QsT0FBTztTQUNSO1FBRUQsSUFBSSxDQUFDLFVBQVUsR0FBRyxVQUFVLENBQUM7O2NBQ3ZCLGVBQWUsR0FBRyxHQUFHLENBQUMsS0FBSyxDQUFDLE1BQU0sQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxVQUFVLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDOUQsR0FBRyxDQUFDLEtBQUssQ0FBQyxPQUFPLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxNQUFNLEdBQUcsS0FBSyxDQUFDLENBQUMsQ0FBQztRQUUzQyxJQUFJLGVBQWUsRUFBRTtZQUNuQixlQUFlLENBQUMsTUFBTSxHQUFHLElBQUksQ0FBQztZQUM5QixlQUFlLENBQUMsYUFBYSxFQUFFLENBQUM7U0FDakM7SUFDSCxDQUFDOzs7WUFuRUYsVUFBVTs7Ozs7Ozs7O0lBT1QsZ0NBQXdCOzs7Ozs7OztJQU94QixrQ0FBMEIiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBJbmplY3RhYmxlLCBRdWVyeUxpc3QgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcblxuaW1wb3J0IHsgU2Nyb2xsU3B5SXRlbURpcmVjdGl2ZSB9IGZyb20gJy4uL3Njcm9sbC1zcHktaXRlbS9zY3JvbGwtc3B5LWl0ZW0uZGlyZWN0aXZlJztcbmltcG9ydCB7IFNweSB9IGZyb20gJy4uL3NoYXJlZC9zcHkubW9kZWwnO1xuXG4vKipcbiAqIFNlcnZpY2UgdGhhdCBzdG9yZXMgYSBsaXN0IG9mIGBTcHlgJ3MgYW5kIHRoZSBzdGF0ZVxuICogb2YgdGhlaXIgbmF2IGl0ZW1zIGBpblZpZXdwb3J0YCBhbmQgYGFjdGl2ZWAgc3RhdGVcbiAqXG4gKi9cbkBJbmplY3RhYmxlKClcbmV4cG9ydCBjbGFzcyBTY3JvbGxTcHlTZXJ2aWNlIHtcbiAgLyoqXG4gICAqIExpc3Qgb2YgYFNweWAnc1xuICAgKlxuICAgKiBAbWVtYmVyb2YgU2Nyb2xsU3B5U2VydmljZVxuICAgKi9cbiAgcHVibGljIHNweXM6IFNweVtdID0gW107XG4gIC8qKlxuICAgKiBTdG9yZXMgcmVxdWVzdHMgdG8gYWRkIGl0ZW1zIHRvIHNweSB3aGVuIHNweSBoYXNuJ3QgYmVlbiBjcmVhdGVkXG4gICAqIHlldC4gT25jZSBzcHkgaGFzIGJlZW4gYWRkZWQgdGhlbiByZXF1ZXN0IHdpbGwgYmUgbWFkZSBhZ2Fpbi5cbiAgICpcbiAgICogQG1lbWJlcm9mIFNjcm9sbFNweVNlcnZpY2VcbiAgICovXG4gIHB1YmxpYyBidWZmZXI6IGFueVtdID0gW107XG4gIC8qKlxuICAgKiBBZGQgc3B5IHRvIGxpc3Qgb2YgYHNweXNgXG4gICAqXG4gICAqIEBtZW1iZXJvZiBTY3JvbGxTcHlTZXJ2aWNlXG4gICAqL1xuICBwdWJsaWMgYWRkU3B5KGlkOiBzdHJpbmcsIGl0ZW1zOiBRdWVyeUxpc3Q8U2Nyb2xsU3B5SXRlbURpcmVjdGl2ZT4pOiB2b2lkIHtcbiAgICB0aGlzLnNweXMucHVzaCh7IGlkLCBpdGVtcyB9KTtcbiAgICBjb25zdCBidWZmZXIgPSB0aGlzLmJ1ZmZlci5maWx0ZXIoaSA9PiBpLnNweUlkID09PSBpZCk7XG4gICAgdGhpcy5idWZmZXIgPSB0aGlzLmJ1ZmZlci5maWx0ZXIoaSA9PiBpLnNweUlkICE9PSBpZCk7XG4gICAgYnVmZmVyLmZvckVhY2goaSA9PlxuICAgICAgdGhpcy5zZXRTcHlTZWN0aW9uU3RhdHVzKGkuc2VjdGlvbklkLCBpLnNweUlkLCBpLmluVmlld3BvcnQpLFxuICAgICk7XG4gIH1cbiAgLyoqXG4gICAqIFJlbW92ZSBzcHkgZnJvbSBsaXN0IG9mIGBzcHlzYFxuICAgKlxuICAgKiBAbWVtYmVyb2YgU2Nyb2xsU3B5U2VydmljZVxuICAgKi9cbiAgcHVibGljIHJlbW92ZVNweShpZDogc3RyaW5nKTogdm9pZCB7XG4gICAgY29uc3QgaSA9IHRoaXMuc3B5cy5maW5kSW5kZXgocyA9PiBzLmlkID09PSBpZCk7XG4gICAgdGhpcy5zcHlzLnNwbGljZShpLCAxKTtcbiAgfVxuICAvKipcbiAgICogU2V0IHRoZSBgaW5WaWV3cG9ydGAgc3RhdHVzIGZvciBhIHNweSBpdGVtIHRoZW4gc2V0cyB0aGUgYWN0aXZlXG4gICAqIHRvIHRydWUgZm9yIHRoZSBmaXJzdCBpdGVtIGluIHRoZSBsaXN0IHRoYXQgaGFzIGBpblZpZXdwb3J0YFxuICAgKiBzZXQgdG8gdHJ1ZVxuICAgKlxuICAgKiBAbWVtYmVyb2YgU2Nyb2xsU3B5U2VydmljZVxuICAgKi9cbiAgcHVibGljIHNldFNweVNlY3Rpb25TdGF0dXMoXG4gICAgc2VjdGlvbklkOiBzdHJpbmcsXG4gICAgc3B5SWQ6IHN0cmluZyxcbiAgICBpblZpZXdwb3J0OiBib29sZWFuLFxuICApOiB2b2lkIHtcbiAgICBjb25zdCBzcHkgPSB0aGlzLnNweXMuZmluZChzID0+IHMuaWQgPT09IHNweUlkKTtcbiAgICBpZiAoIXNweSkge1xuICAgICAgdGhpcy5idWZmZXIucHVzaCh7IHNlY3Rpb25JZCwgc3B5SWQsIGluVmlld3BvcnQgfSk7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGNvbnN0IGl0ZW0gPSBzcHkuaXRlbXMuZmluZChpID0+IGkuc2VjdGlvbiA9PT0gc2VjdGlvbklkKTtcbiAgICBpZiAoIWl0ZW0pIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBpdGVtLmluVmlld3BvcnQgPSBpblZpZXdwb3J0O1xuICAgIGNvbnN0IGZpcnN0SW5WaWV3cG9ydCA9IHNweS5pdGVtcy5maWx0ZXIoaSA9PiBpLmluVmlld3BvcnQpWzBdO1xuICAgIHNweS5pdGVtcy5mb3JFYWNoKGkgPT4gKGkuYWN0aXZlID0gZmFsc2UpKTtcblxuICAgIGlmIChmaXJzdEluVmlld3BvcnQpIHtcbiAgICAgIGZpcnN0SW5WaWV3cG9ydC5hY3RpdmUgPSB0cnVlO1xuICAgICAgZmlyc3RJblZpZXdwb3J0LmRldGVjdENoYW5nZXMoKTtcbiAgICB9XG4gIH1cbn1cbiJdfQ==