86 lines
2.3 KiB
JavaScript
86 lines
2.3 KiB
JavaScript
import { create } from '~/lib/utils/intersection_observer';
|
|
|
|
describe('IntersectionObserver Utility', () => {
|
|
beforeAll(() => {
|
|
global.IntersectionObserver = class MockIntersectionObserver {
|
|
constructor(callback) {
|
|
this.callback = callback;
|
|
|
|
this.entries = [];
|
|
}
|
|
|
|
addEntry(entry) {
|
|
this.entries.push(entry);
|
|
}
|
|
|
|
trigger() {
|
|
this.callback(this.entries);
|
|
}
|
|
};
|
|
});
|
|
describe('create', () => {
|
|
describe('memoization', () => {
|
|
const options = { rootMargin: '1px 1px 1px 1px' };
|
|
let expectedOutput;
|
|
|
|
beforeEach(() => {
|
|
create.cache.clear();
|
|
expectedOutput = create(options);
|
|
});
|
|
|
|
it('returns the same Observer for the same options input', () => {
|
|
expect(expectedOutput.id).toBe(create(options).id);
|
|
});
|
|
|
|
it('creates a new Observer for unique input options', () => {
|
|
expect(expectedOutput.id).not.toBe(create({ rootMargin: '1px 2px 3px 4px' }));
|
|
});
|
|
|
|
it('creates a new Observer for the same input options in different object references', () => {
|
|
expect(expectedOutput.id).not.toBe(create({ rootMargin: '1px 1px 1px 1px' }));
|
|
});
|
|
});
|
|
});
|
|
|
|
describe('Observer behavior', () => {
|
|
let observer = null;
|
|
let id = null;
|
|
|
|
beforeEach(() => {
|
|
create.cache.clear();
|
|
({ observer, id } = create());
|
|
});
|
|
|
|
it.each`
|
|
isIntersecting | event
|
|
${false} | ${'IntersectionDisappear'}
|
|
${true} | ${'IntersectionAppear'}
|
|
`(
|
|
'should emit the correct event on the entry target based on the computed Intersection',
|
|
async ({ isIntersecting, event }) => {
|
|
const target = document.createElement('div');
|
|
observer.addEntry({ target, isIntersecting });
|
|
|
|
target.addEventListener(event, (e) => {
|
|
expect(e.detail.observer).toBe(id);
|
|
});
|
|
|
|
observer.trigger();
|
|
},
|
|
);
|
|
|
|
it('should always emit an Update event with the entry and the observer', () => {
|
|
const target = document.createElement('div');
|
|
const entry = { target };
|
|
|
|
observer.addEntry(entry);
|
|
|
|
target.addEventListener('IntersectionUpdate', (e) => {
|
|
expect(e.detail.observer).toBe(id);
|
|
expect(e.detail.entry).toStrictEqual(entry);
|
|
});
|
|
|
|
observer.trigger();
|
|
});
|
|
});
|
|
});
|