embla-carousel
Advanced tools
Comparing version 8.0.0-rc11 to 8.0.0-rc12
@@ -17,7 +17,7 @@ import { EmblaCarouselType } from './EmblaCarousel'; | ||
export type DragHandlerType = { | ||
init: (emblaApi: EmblaCarouselType, watchDrag: DragHandlerOptionType) => void; | ||
init: (emblaApi: EmblaCarouselType) => void; | ||
destroy: () => void; | ||
pointerDown: () => boolean; | ||
}; | ||
export declare function DragHandler(axis: AxisType, direction: DirectionType, rootNode: HTMLElement, ownerDocument: Document, ownerWindow: WindowType, target: Vector1DType, dragTracker: DragTrackerType, location: Vector1DType, animation: AnimationType, scrollTo: ScrollToType, scrollBody: ScrollBodyType, scrollTarget: ScrollTargetType, index: CounterType, eventHandler: EventHandlerType, percentOfView: PercentOfViewType, dragFree: boolean, dragThreshold: number, skipSnaps: boolean, baseFriction: number): DragHandlerType; | ||
export declare function DragHandler(axis: AxisType, direction: DirectionType, rootNode: HTMLElement, ownerDocument: Document, ownerWindow: WindowType, target: Vector1DType, dragTracker: DragTrackerType, location: Vector1DType, animation: AnimationType, scrollTo: ScrollToType, scrollBody: ScrollBodyType, scrollTarget: ScrollTargetType, index: CounterType, eventHandler: EventHandlerType, percentOfView: PercentOfViewType, dragFree: boolean, dragThreshold: number, skipSnaps: boolean, baseFriction: number, watchDrag: DragHandlerOptionType): DragHandlerType; | ||
export {}; |
@@ -26,4 +26,4 @@ import { EngineType } from './Engine'; | ||
slideNodes: () => HTMLElement[]; | ||
slidesInView: (target?: boolean) => number[]; | ||
slidesNotInView: (target?: boolean) => number[]; | ||
slidesInView: () => number[]; | ||
slidesNotInView: () => number[]; | ||
}; | ||
@@ -30,0 +30,0 @@ declare function EmblaCarousel(root: HTMLElement, userOptions?: EmblaOptionsType, userPlugins?: EmblaPluginType[]): EmblaCarouselType; |
@@ -15,4 +15,6 @@ import { AxisType } from './Axis'; | ||
import { ScrollProgressType } from './ScrollProgress'; | ||
import { SlideRegistryType } from './SlideRegistry'; | ||
import { ScrollTargetType } from './ScrollTarget'; | ||
import { ScrollToType } from './ScrollTo'; | ||
import { SlideFocusType } from './SlideFocus'; | ||
import { SlideLooperType } from './SlideLooper'; | ||
@@ -55,4 +57,7 @@ import { SlidesHandlerType } from './SlidesHandler'; | ||
scrollTarget: ScrollTargetType; | ||
scrollSnapList: number[]; | ||
scrollSnaps: number[]; | ||
slideIndexes: number[]; | ||
slideFocus: SlideFocusType; | ||
slideRegistry: SlideRegistryType['slideRegistry']; | ||
containerRect: DOMRect; | ||
@@ -59,0 +64,0 @@ slideRects: DOMRect[]; |
import { EmblaCarouselType } from './EmblaCarousel'; | ||
type CallbackType = (emblaApi: EmblaCarouselType, evt: EmblaEventType) => void; | ||
export type EmblaEventType = 'init' | 'pointerDown' | 'pointerUp' | 'slidesChanged' | 'scroll' | 'select' | 'settle' | 'destroy' | 'reInit' | 'resize'; | ||
export type EmblaEventType = 'init' | 'pointerDown' | 'pointerUp' | 'slidesChanged' | 'slidesInView' | 'scroll' | 'select' | 'settle' | 'destroy' | 'reInit' | 'resize'; | ||
export type EventHandlerType = { | ||
@@ -5,0 +5,0 @@ init: (emblaApi: EmblaCarouselType) => void; |
@@ -9,2 +9,3 @@ import { AlignmentOptionType } from './Alignment'; | ||
import { SlidesHandlerOptionType } from './SlidesHandler'; | ||
import { SlidesInViewOptionsType } from './SlidesInView'; | ||
export type LooseOptionsType = { | ||
@@ -29,3 +30,3 @@ [key: string]: unknown; | ||
dragThreshold: number; | ||
inViewThreshold: number; | ||
inViewThreshold: SlidesInViewOptionsType; | ||
loop: boolean; | ||
@@ -32,0 +33,0 @@ skipSnaps: boolean; |
@@ -5,5 +5,5 @@ import { EmblaCarouselType } from './EmblaCarousel'; | ||
export type PluginsHandlerType = { | ||
init: (plugins: EmblaPluginType[], embla: EmblaCarouselType) => EmblaPluginsType; | ||
init: (emblaApi: EmblaCarouselType, plugins: EmblaPluginType[]) => EmblaPluginsType; | ||
destroy: () => void; | ||
}; | ||
export declare function PluginsHandler(optionsHandler: OptionsHandlerType): PluginsHandlerType; |
@@ -8,6 +8,6 @@ import { AxisType } from './Axis'; | ||
export type ResizeHandlerType = { | ||
init: (emblaApi: EmblaCarouselType, watchResize: ResizeHandlerOptionType) => void; | ||
init: (emblaApi: EmblaCarouselType) => void; | ||
destroy: () => void; | ||
}; | ||
export declare function ResizeHandler(container: HTMLElement, eventHandler: EventHandlerType, ownerWindow: WindowType, slides: HTMLElement[], axis: AxisType): ResizeHandlerType; | ||
export declare function ResizeHandler(container: HTMLElement, eventHandler: EventHandlerType, ownerWindow: WindowType, slides: HTMLElement[], axis: AxisType, watchResize: ResizeHandlerOptionType): ResizeHandlerType; | ||
export {}; |
@@ -0,5 +1,7 @@ | ||
import { LimitType } from './Limit'; | ||
export type ScrollContainOptionType = false | 'trimSnaps' | 'keepSnaps'; | ||
export type ScrollContainType = { | ||
snapsContained: number[]; | ||
scrollContainLimit: LimitType; | ||
}; | ||
export declare function ScrollContain(viewSize: number, contentSize: number, snapsAligned: number[], containScroll: ScrollContainOptionType): ScrollContainType; |
@@ -8,2 +8,2 @@ import { AlignmentType } from './Alignment'; | ||
}; | ||
export declare function ScrollSnaps(axis: AxisType, alignment: AlignmentType, containerRect: DOMRect, slideRects: DOMRect[], slideSizesWithGaps: number[], slidesToScroll: SlidesToScrollType, containScroll: boolean): ScrollSnapsType; | ||
export declare function ScrollSnaps(axis: AxisType, alignment: AlignmentType, containerRect: DOMRect, slideRects: DOMRect[], slidesToScroll: SlidesToScrollType): ScrollSnapsType; |
import { AxisType } from './Axis'; | ||
import { SlidesInViewType } from './SlidesInView'; | ||
import { Vector1DType } from './Vector1d'; | ||
@@ -18,3 +17,3 @@ import { TranslateType } from './Translate'; | ||
}; | ||
export declare function SlideLooper(axis: AxisType, direction: DirectionType, viewSize: number, contentSize: number, slideSizesWithGaps: number[], scrollSnaps: number[], slidesInView: SlidesInViewType, offsetLocation: Vector1DType, slides: HTMLElement[]): SlideLooperType; | ||
export declare function SlideLooper(axis: AxisType, direction: DirectionType, viewSize: number, contentSize: number, slideSizes: number[], slideSizesWithGaps: number[], snaps: number[], scrollSnaps: number[], offsetLocation: Vector1DType, slides: HTMLElement[]): SlideLooperType; | ||
export {}; |
@@ -6,6 +6,6 @@ import { EmblaCarouselType } from './EmblaCarousel'; | ||
export type SlidesHandlerType = { | ||
init: (emblaApi: EmblaCarouselType, watchSlides: SlidesHandlerOptionType) => void; | ||
init: (emblaApi: EmblaCarouselType) => void; | ||
destroy: () => void; | ||
}; | ||
export declare function SlidesHandler(container: HTMLElement, eventHandler: EventHandlerType): SlidesHandlerType; | ||
export declare function SlidesHandler(container: HTMLElement, eventHandler: EventHandlerType, watchSlides: SlidesHandlerOptionType): SlidesHandlerType; | ||
export {}; |
@@ -1,11 +0,8 @@ | ||
import { LimitType } from './Limit'; | ||
export type SlideBoundType = { | ||
start: number; | ||
end: number; | ||
index: number; | ||
}; | ||
import { EventHandlerType } from './EventHandler'; | ||
export type SlidesInViewOptionsType = IntersectionObserverInit['threshold']; | ||
export type SlidesInViewType = { | ||
check: (location: number, bounds?: SlideBoundType[]) => number[]; | ||
findSlideBounds: (offsets?: number[], threshold?: number) => SlideBoundType[]; | ||
init: () => void; | ||
destroy: () => void; | ||
get: (inView?: boolean) => number[]; | ||
}; | ||
export declare function SlidesInView(viewSize: number, contentSize: number, slideSizes: number[], snaps: number[], limit: LimitType, loop: boolean, inViewThreshold: number): SlidesInViewType; | ||
export declare function SlidesInView(container: HTMLElement, slides: HTMLElement[], eventHandler: EventHandlerType, threshold: SlidesInViewOptionsType): SlidesInViewType; |
@@ -6,3 +6,5 @@ import { AxisType } from './Axis'; | ||
slideSizesWithGaps: number[]; | ||
startGap: number; | ||
endGap: number; | ||
}; | ||
export declare function SlideSizes(axis: AxisType, containerRect: DOMRect, slideRects: DOMRect[], slides: HTMLElement[], readEdgeGap: boolean, ownerWindow: WindowType): SlideSizesType; |
@@ -0,1 +1,3 @@ | ||
import { AxisType } from './Axis'; | ||
import { DirectionType } from './Direction'; | ||
export type SlidesToScrollOptionType = 'auto' | number; | ||
@@ -5,2 +7,2 @@ export type SlidesToScrollType = { | ||
}; | ||
export declare function SlidesToScroll(viewSize: number, slideSizesWithGaps: number[], slidesToScroll: SlidesToScrollOptionType): SlidesToScrollType; | ||
export declare function SlidesToScroll(axis: AxisType, direction: DirectionType, viewSize: number, slidesToScroll: SlidesToScrollOptionType, loop: boolean, containerRect: DOMRect, slideRects: DOMRect[], startGap: number, endGap: number): SlidesToScrollType; |
@@ -14,4 +14,5 @@ import { PointerEventType } from './DragTracker'; | ||
export declare function arrayLastIndex<Type>(array: Type[]): number; | ||
export declare function arrayFromNumber(n: number, startAt?: number): number[]; | ||
export declare function objectKeys<Type extends object>(object: Type): string[]; | ||
export declare function objectsMergeDeep(objectA: Record<string, unknown>, objectB: Record<string, unknown>): Record<string, unknown>; | ||
export declare function isMouseEvent(evt: PointerEventType, ownerWindow: WindowType): evt is MouseEvent; |
@@ -39,2 +39,5 @@ 'use strict'; | ||
} | ||
function arrayFromNumber(n, startAt = 0) { | ||
return Array.from(Array(n), (_, i) => startAt + i); | ||
} | ||
function objectKeys(object) { | ||
@@ -209,3 +212,3 @@ return Object.keys(object); | ||
function DragHandler(axis, direction, rootNode, ownerDocument, ownerWindow, target, dragTracker, location, animation, scrollTo, scrollBody, scrollTarget, index, eventHandler, percentOfView, dragFree, dragThreshold, skipSnaps, baseFriction) { | ||
function DragHandler(axis, direction, rootNode, ownerDocument, ownerWindow, target, dragTracker, location, animation, scrollTo, scrollBody, scrollTarget, index, eventHandler, percentOfView, dragFree, dragThreshold, skipSnaps, baseFriction, watchDrag) { | ||
const { | ||
@@ -237,3 +240,3 @@ cross: crossAxis | ||
let isMouse = false; | ||
function init(emblaApi, watchDrag) { | ||
function init(emblaApi) { | ||
if (!watchDrag) return; | ||
@@ -388,3 +391,3 @@ function downIfAllowed(evt) { | ||
function ResizeHandler(container, eventHandler, ownerWindow, slides, axis) { | ||
function ResizeHandler(container, eventHandler, ownerWindow, slides, axis, watchResize) { | ||
let resizeObserver; | ||
@@ -397,3 +400,3 @@ let containerSize; | ||
} | ||
function init(emblaApi, watchResize) { | ||
function init(emblaApi) { | ||
if (!watchResize) return; | ||
@@ -539,6 +542,7 @@ containerSize = readSize(container); | ||
function ScrollContain(viewSize, contentSize, snapsAligned, containScroll) { | ||
const scrollBounds = Limit(-contentSize + viewSize, snapsAligned[0]); | ||
const scrollBounds = Limit(-contentSize + viewSize, 0); | ||
const snapsBounded = measureBounded(); | ||
const scrollContainLimit = findScrollContainLimit(); | ||
const snapsContained = measureContained(); | ||
function findDuplicates() { | ||
function findScrollContainLimit() { | ||
const startSnap = snapsBounded[0]; | ||
@@ -559,7 +563,8 @@ const endSnap = arrayLast(snapsBounded); | ||
max | ||
} = findDuplicates(); | ||
} = scrollContainLimit; | ||
return snapsBounded.slice(min, max); | ||
} | ||
const self = { | ||
snapsContained | ||
snapsContained, | ||
scrollContainLimit | ||
}; | ||
@@ -606,7 +611,7 @@ return self; | ||
max, | ||
length: scrollLength | ||
length | ||
} = limit; | ||
function get(n) { | ||
const currentLocation = n - max; | ||
return currentLocation / -scrollLength; | ||
return length ? currentLocation / -length : 0; | ||
} | ||
@@ -619,3 +624,3 @@ const self = { | ||
function ScrollSnaps(axis, alignment, containerRect, slideRects, slideSizesWithGaps, slidesToScroll, containScroll) { | ||
function ScrollSnaps(axis, alignment, containerRect, slideRects, slidesToScroll) { | ||
const { | ||
@@ -638,11 +643,3 @@ startEdge, | ||
function measureAligned() { | ||
const containedStartSnap = 0; | ||
const containedEndSnap = arrayLast(snaps) - arrayLast(slideSizesWithGaps); | ||
return groupSlides(snaps).map(g => g[0]).map((snap, index, groupedSnaps) => { | ||
const isFirst = !index; | ||
const isLast = index === arrayLastIndex(groupedSnaps); | ||
if (containScroll && isFirst) return containedStartSnap; | ||
if (containScroll && isLast) return containedEndSnap; | ||
return snap + alignments[index]; | ||
}); | ||
return groupSlides(snaps).map(g => g[0]).map((snap, index) => snap + alignments[index]); | ||
} | ||
@@ -656,2 +653,34 @@ const self = { | ||
function SlideRegistry(viewSize, contentSize, containSnaps, scrollContainLimit, slidesToScroll, slideIndexes) { | ||
const { | ||
groupSlides | ||
} = slidesToScroll; | ||
const { | ||
min, | ||
max | ||
} = scrollContainLimit; | ||
const slideRegistry = createSlideRegistry(); | ||
function createSlideRegistry() { | ||
const groupedSlideIndexes = groupSlides(slideIndexes); | ||
if (!containSnaps || contentSize <= viewSize) return groupedSlideIndexes; | ||
return groupedSlideIndexes.slice(min, max).map((group, index, groups) => { | ||
const indexIsFirst = !index; | ||
const indexIsLast = !indexIsFirst && index === arrayLastIndex(groups); | ||
if (indexIsFirst) { | ||
const range = arrayLast(groups[0]) + 1; | ||
return arrayFromNumber(range); | ||
} | ||
if (indexIsLast) { | ||
const range = arrayLastIndex(slideIndexes) - arrayLast(groups)[0] + 1; | ||
return arrayFromNumber(range, arrayLast(groups)[0]); | ||
} | ||
return group; | ||
}); | ||
} | ||
const self = { | ||
slideRegistry | ||
}; | ||
return self; | ||
} | ||
function ScrollTarget(loop, scrollSnaps, contentSize, limit, targetVector) { | ||
@@ -685,3 +714,4 @@ const { | ||
const matchingTargets = targets.filter(t => mathSign(t) === direction); | ||
return minDistance(matchingTargets); | ||
if (matchingTargets.length) return minDistance(matchingTargets); | ||
return arrayLast(targets) - contentSize; | ||
} | ||
@@ -758,2 +788,34 @@ function byIndex(index, direction) { | ||
function SlideFocus(root, slides, slideRegistry, scrollTo, scrollBody, eventStore) { | ||
let lastTabPressTime = 0; | ||
function init() { | ||
eventStore.add(document, 'keydown', registerTabPress, false); | ||
slides.forEach(addSlideFocusEvent); | ||
} | ||
function registerTabPress(event) { | ||
if (event.code === 'Tab') lastTabPressTime = new Date().getTime(); | ||
} | ||
function addSlideFocusEvent(slide) { | ||
const focus = () => { | ||
const nowTime = new Date().getTime(); | ||
const diffTime = nowTime - lastTabPressTime; | ||
if (diffTime > 10) return; | ||
root.scrollLeft = 0; | ||
const index = slides.indexOf(slide); | ||
const group = slideRegistry.findIndex(group => group.includes(index)); | ||
if (!isNumber(group)) return; | ||
scrollBody.useDuration(0); | ||
scrollTo.index(group, 0); | ||
}; | ||
eventStore.add(slide, 'focus', focus, { | ||
passive: true, | ||
capture: true | ||
}); | ||
} | ||
const self = { | ||
init | ||
}; | ||
return self; | ||
} | ||
function Vector1D(initialValue) { | ||
@@ -815,3 +877,4 @@ let value = initialValue; | ||
function SlideLooper(axis, direction, viewSize, contentSize, slideSizesWithGaps, scrollSnaps, slidesInView, offsetLocation, slides) { | ||
function SlideLooper(axis, direction, viewSize, contentSize, slideSizes, slideSizesWithGaps, snaps, scrollSnaps, offsetLocation, slides) { | ||
const roundingSafety = 0.5; | ||
const ascItems = arrayKeys(slideSizesWithGaps); | ||
@@ -831,11 +894,15 @@ const descItems = arrayKeys(slideSizesWithGaps).reverse(); | ||
} | ||
function findLoopPoints(indexes, edge) { | ||
const isStartEdge = edge === 'start'; | ||
const offset = isStartEdge ? -contentSize : contentSize; | ||
const slideBounds = slidesInView.findSlideBounds([offset]); | ||
function findSlideBounds(offset) { | ||
return snaps.map((snap, index) => ({ | ||
start: snap - slideSizes[index] + roundingSafety + offset, | ||
end: snap + viewSize - roundingSafety + offset | ||
})); | ||
} | ||
function findLoopPoints(indexes, offset, isEndEdge) { | ||
const slideBounds = findSlideBounds(offset); | ||
return indexes.map(index => { | ||
const initial = isStartEdge ? 0 : -contentSize; | ||
const altered = isStartEdge ? contentSize : 0; | ||
const bounds = slideBounds.filter(b => b.index === index)[0]; | ||
const loopPoint = bounds[isStartEdge ? 'end' : 'start']; | ||
const initial = isEndEdge ? 0 : -contentSize; | ||
const altered = isEndEdge ? contentSize : 0; | ||
const boundEdge = isEndEdge ? 'end' : 'start'; | ||
const loopPoint = slideBounds[index][boundEdge]; | ||
return { | ||
@@ -852,3 +919,3 @@ index, | ||
const indexes = slidesInGap(descItems, gap); | ||
return findLoopPoints(indexes, 'end'); | ||
return findLoopPoints(indexes, contentSize, false); | ||
} | ||
@@ -858,3 +925,3 @@ function endPoints() { | ||
const indexes = slidesInGap(ascItems, gap); | ||
return findLoopPoints(indexes, 'start'); | ||
return findLoopPoints(indexes, -contentSize, true); | ||
} | ||
@@ -894,6 +961,6 @@ function canLoop() { | ||
function SlidesHandler(container, eventHandler) { | ||
function SlidesHandler(container, eventHandler, watchSlides) { | ||
let mutationObserver; | ||
let destroyed = false; | ||
function init(emblaApi, watchSlides) { | ||
function init(emblaApi) { | ||
if (!watchSlides) return; | ||
@@ -930,46 +997,52 @@ function defaultCallback(mutations) { | ||
function SlidesInView(viewSize, contentSize, slideSizes, snaps, limit, loop, inViewThreshold) { | ||
const { | ||
removeOffset, | ||
constrain | ||
} = limit; | ||
const roundingSafety = 0.5; | ||
const cachedOffsets = loop ? [0, contentSize, -contentSize] : [0]; | ||
const cachedBounds = findSlideBounds(cachedOffsets, inViewThreshold); | ||
function findSlideThresholds(threshold) { | ||
const slideThreshold = threshold || 0; | ||
return slideSizes.map(slideSize => { | ||
const thresholdLimit = Limit(roundingSafety, slideSize - roundingSafety); | ||
return thresholdLimit.constrain(slideSize * slideThreshold); | ||
function SlidesInView(container, slides, eventHandler, threshold) { | ||
const intersectionEntryMap = {}; | ||
let inViewCache = null; | ||
let notInViewCache = null; | ||
let intersectionObserver; | ||
let destroyed = false; | ||
function init() { | ||
intersectionObserver = new IntersectionObserver(entries => { | ||
if (destroyed) return; | ||
entries.forEach(entry => { | ||
const index = slides.indexOf(entry.target); | ||
intersectionEntryMap[index] = entry; | ||
}); | ||
inViewCache = null; | ||
notInViewCache = null; | ||
eventHandler.emit('slidesInView'); | ||
}, { | ||
root: container.parentElement, | ||
threshold | ||
}); | ||
slides.forEach(slide => intersectionObserver.observe(slide)); | ||
} | ||
function findSlideBounds(offsets, threshold) { | ||
const slideOffsets = offsets || cachedOffsets; | ||
const slideThresholds = findSlideThresholds(threshold); | ||
return slideOffsets.reduce((list, offset) => { | ||
const bounds = snaps.map((snap, index) => ({ | ||
start: snap - slideSizes[index] + slideThresholds[index] + offset, | ||
end: snap + viewSize - slideThresholds[index] + offset, | ||
index | ||
})); | ||
return list.concat(bounds); | ||
}, []); | ||
function destroy() { | ||
if (intersectionObserver) intersectionObserver.disconnect(); | ||
destroyed = true; | ||
} | ||
function check(location, bounds) { | ||
const limitedLocation = loop ? removeOffset(location) : constrain(location); | ||
const slideBounds = bounds || cachedBounds; | ||
return slideBounds.reduce((list, slideBound) => { | ||
function createInViewList(inView) { | ||
return objectKeys(intersectionEntryMap).reduce((list, slideIndex) => { | ||
const index = parseInt(slideIndex); | ||
const { | ||
index, | ||
start, | ||
end | ||
} = slideBound; | ||
const inList = list.includes(index); | ||
const inView = start < limitedLocation && end > limitedLocation; | ||
return !inList && inView ? list.concat([index]) : list; | ||
isIntersecting | ||
} = intersectionEntryMap[index]; | ||
const inViewMatch = inView && isIntersecting; | ||
const notInViewMatch = !inView && !isIntersecting; | ||
if (inViewMatch || notInViewMatch) list.push(index); | ||
return list; | ||
}, []); | ||
} | ||
function get(inView = true) { | ||
if (inView && inViewCache) return inViewCache; | ||
if (!inView && notInViewCache) return notInViewCache; | ||
const slideIndexes = createInViewList(inView); | ||
if (inView) inViewCache = slideIndexes; | ||
if (!inView) notInViewCache = slideIndexes; | ||
return slideIndexes; | ||
} | ||
const self = { | ||
check, | ||
findSlideBounds | ||
init, | ||
destroy, | ||
get | ||
}; | ||
@@ -1011,3 +1084,5 @@ return self; | ||
slideSizes, | ||
slideSizesWithGaps | ||
slideSizesWithGaps, | ||
startGap, | ||
endGap | ||
}; | ||
@@ -1017,3 +1092,7 @@ return self; | ||
function SlidesToScroll(viewSize, slideSizesWithGaps, slidesToScroll) { | ||
function SlidesToScroll(axis, direction, viewSize, slidesToScroll, loop, containerRect, slideRects, startGap, endGap) { | ||
const { | ||
startEdge, | ||
endEdge | ||
} = axis; | ||
const groupByNumber = isNumber(slidesToScroll); | ||
@@ -1024,7 +1103,19 @@ function byNumber(array, groupSize) { | ||
function bySize(array) { | ||
return arrayKeys(array).reduce((groupSizes, i) => { | ||
const chunk = slideSizesWithGaps.slice(arrayLast(groupSizes), i + 1); | ||
const chunkSize = chunk.reduce((a, s) => a + s, 0); | ||
return !i || chunkSize > viewSize ? groupSizes.concat(i) : groupSizes; | ||
}, []).map((start, i, groupSizes) => array.slice(start, groupSizes[i + 1])); | ||
if (!array.length) return []; | ||
return arrayKeys(array).reduce((groups, rectB) => { | ||
const rectA = arrayLast(groups) || 0; | ||
const isFirst = rectA === 0; | ||
const isLast = rectB === arrayLastIndex(array); | ||
const edgeA = containerRect[startEdge] - slideRects[rectA][startEdge]; | ||
const edgeB = containerRect[startEdge] - slideRects[rectB][endEdge]; | ||
const gapA = !loop && isFirst ? direction.apply(startGap) : 0; | ||
const gapB = !loop && isLast ? direction.apply(endGap) : 0; | ||
const chunkSize = mathAbs(edgeB - gapB - (edgeA + gapA)); | ||
if (chunkSize > viewSize) groups.push(rectB); | ||
if (isLast) groups.push(array.length); | ||
return groups; | ||
}, []).map((currentSize, index, groups) => { | ||
const previousSize = Math.max(groups[index - 1] || 0); | ||
return array.slice(previousSize, currentSize); | ||
}); | ||
} | ||
@@ -1047,3 +1138,2 @@ function groupSlides(array) { | ||
startIndex, | ||
inViewThreshold, | ||
loop, | ||
@@ -1053,5 +1143,9 @@ duration, | ||
dragThreshold, | ||
inViewThreshold, | ||
slidesToScroll: groupSlides, | ||
skipSnaps, | ||
containScroll | ||
containScroll, | ||
watchResize, | ||
watchSlides, | ||
watchDrag | ||
} = options; | ||
@@ -1070,12 +1164,15 @@ // Measurements | ||
slideSizes, | ||
slideSizesWithGaps | ||
slideSizesWithGaps, | ||
startGap, | ||
endGap | ||
} = SlideSizes(axis, containerRect, slideRects, slides, readEdgeGap, ownerWindow); | ||
const slidesToScroll = SlidesToScroll(viewSize, slideSizesWithGaps, groupSlides); | ||
const slidesToScroll = SlidesToScroll(axis, direction, viewSize, groupSlides, loop, containerRect, slideRects, startGap, endGap); | ||
const { | ||
snaps, | ||
snapsAligned | ||
} = ScrollSnaps(axis, alignment, containerRect, slideRects, slideSizesWithGaps, slidesToScroll, containSnaps); | ||
} = ScrollSnaps(axis, alignment, containerRect, slideRects, slidesToScroll); | ||
const contentSize = -arrayLast(snaps) + arrayLast(slideSizesWithGaps); | ||
const { | ||
snapsContained | ||
snapsContained, | ||
scrollContainLimit | ||
} = ScrollContain(viewSize, contentSize, snapsAligned, containScroll); | ||
@@ -1144,3 +1241,9 @@ const scrollSnaps = containSnaps ? snapsContained : snapsAligned; | ||
const scrollTo = ScrollTo(animation, index, indexPrevious, scrollTarget, scrollBody, target, eventHandler); | ||
const slidesInView = SlidesInView(viewSize, contentSize, slideSizes, snaps, limit, loop, inViewThreshold); | ||
const scrollProgress = ScrollProgress(limit); | ||
const eventStore = EventStore(); | ||
const slidesInView = SlidesInView(container, slides, eventHandler, inViewThreshold); | ||
const { | ||
slideRegistry | ||
} = SlideRegistry(viewSize, contentSize, containSnaps, scrollContainLimit, slidesToScroll, slideIndexes); | ||
const slideFocus = SlideFocus(root, slides, slideRegistry, scrollTo, scrollBody, eventStore); | ||
// Engine | ||
@@ -1156,4 +1259,4 @@ const engine = { | ||
direction, | ||
dragHandler: DragHandler(axis, direction, root, ownerDocument, ownerWindow, target, DragTracker(axis, ownerWindow), location, animation, scrollTo, scrollBody, scrollTarget, index, eventHandler, percentOfView, dragFree, dragThreshold, skipSnaps, friction), | ||
eventStore: EventStore(), | ||
dragHandler: DragHandler(axis, direction, root, ownerDocument, ownerWindow, target, DragTracker(axis, ownerWindow), location, animation, scrollTo, scrollBody, scrollTarget, index, eventHandler, percentOfView, dragFree, dragThreshold, skipSnaps, friction, watchDrag), | ||
eventStore, | ||
percentOfView, | ||
@@ -1166,14 +1269,17 @@ index, | ||
options, | ||
resizeHandler: ResizeHandler(container, eventHandler, ownerWindow, slides, axis), | ||
resizeHandler: ResizeHandler(container, eventHandler, ownerWindow, slides, axis, watchResize), | ||
scrollBody, | ||
scrollBounds: ScrollBounds(limit, location, target, scrollBody, percentOfView), | ||
scrollLooper: ScrollLooper(contentSize, limit, offsetLocation, [location, offsetLocation, target]), | ||
scrollProgress: ScrollProgress(limit), | ||
scrollProgress, | ||
scrollSnapList: scrollSnaps.map(scrollProgress.get), | ||
scrollSnaps, | ||
scrollTarget, | ||
scrollTo, | ||
slideLooper: SlideLooper(axis, direction, viewSize, contentSize, slideSizesWithGaps, scrollSnaps, slidesInView, offsetLocation, slides), | ||
slidesHandler: SlidesHandler(container, eventHandler), | ||
slideLooper: SlideLooper(axis, direction, viewSize, contentSize, slideSizes, slideSizesWithGaps, snaps, scrollSnaps, offsetLocation, slides), | ||
slideFocus, | ||
slidesHandler: SlidesHandler(container, eventHandler, watchSlides), | ||
slidesInView, | ||
slideIndexes, | ||
slideRegistry, | ||
slidesToScroll, | ||
@@ -1273,6 +1379,6 @@ target, | ||
slidesToScroll: 1, | ||
inViewThreshold: 0, | ||
breakpoints: {}, | ||
dragFree: false, | ||
dragThreshold: 10, | ||
inViewThreshold: 0, | ||
loop: false, | ||
@@ -1310,3 +1416,3 @@ skipSnaps: false, | ||
let activePlugins = []; | ||
function init(plugins, emblaApi) { | ||
function init(emblaApi, plugins) { | ||
activePlugins = plugins.filter(({ | ||
@@ -1395,5 +1501,7 @@ options | ||
engine.translate.to(engine.location.get()); | ||
engine.slidesInView.init(); | ||
engine.slideFocus.init(); | ||
engine.eventHandler.init(self); | ||
engine.resizeHandler.init(self, options.watchResize); | ||
engine.slidesHandler.init(self, options.watchSlides); | ||
engine.resizeHandler.init(self); | ||
engine.slidesHandler.init(self); | ||
documentVisibleHandler.add(ownerDocument, 'visibilitychange', () => { | ||
@@ -1403,6 +1511,4 @@ if (ownerDocument.hidden) animations.reset(); | ||
if (engine.options.loop) engine.slideLooper.loop(); | ||
if (container.offsetParent && slides.length) { | ||
engine.dragHandler.init(self, options.watchDrag); | ||
} | ||
pluginApis = pluginsHandler.init(pluginList, self); | ||
if (container.offsetParent && slides.length) engine.dragHandler.init(self); | ||
pluginApis = pluginsHandler.init(self, pluginList); | ||
} | ||
@@ -1436,11 +1542,2 @@ function reActivate(withOptions, withPlugins) { | ||
} | ||
function slidesInView(target) { | ||
const location = engine[target ? 'target' : 'location'].get(); | ||
const type = options.loop ? 'removeOffset' : 'constrain'; | ||
return engine.slidesInView.check(engine.limit[type](location)); | ||
} | ||
function slidesNotInView(target) { | ||
const inView = slidesInView(target); | ||
return engine.slideIndexes.filter(index => !inView.includes(index)); | ||
} | ||
function scrollTo(index, jump, direction) { | ||
@@ -1468,3 +1565,3 @@ if (!options.active || destroyed) return; | ||
function scrollSnapList() { | ||
return engine.scrollSnaps.map(engine.scrollProgress.get); | ||
return engine.scrollSnapList; | ||
} | ||
@@ -1480,2 +1577,8 @@ function scrollProgress() { | ||
} | ||
function slidesInView() { | ||
return engine.slidesInView.get(); | ||
} | ||
function slidesNotInView() { | ||
return engine.slidesInView.get(false); | ||
} | ||
function plugins() { | ||
@@ -1482,0 +1585,0 @@ return pluginApis; |
@@ -37,2 +37,5 @@ function isNumber(subject) { | ||
} | ||
function arrayFromNumber(n, startAt = 0) { | ||
return Array.from(Array(n), (_, i) => startAt + i); | ||
} | ||
function objectKeys(object) { | ||
@@ -207,3 +210,3 @@ return Object.keys(object); | ||
function DragHandler(axis, direction, rootNode, ownerDocument, ownerWindow, target, dragTracker, location, animation, scrollTo, scrollBody, scrollTarget, index, eventHandler, percentOfView, dragFree, dragThreshold, skipSnaps, baseFriction) { | ||
function DragHandler(axis, direction, rootNode, ownerDocument, ownerWindow, target, dragTracker, location, animation, scrollTo, scrollBody, scrollTarget, index, eventHandler, percentOfView, dragFree, dragThreshold, skipSnaps, baseFriction, watchDrag) { | ||
const { | ||
@@ -235,3 +238,3 @@ cross: crossAxis | ||
let isMouse = false; | ||
function init(emblaApi, watchDrag) { | ||
function init(emblaApi) { | ||
if (!watchDrag) return; | ||
@@ -386,3 +389,3 @@ function downIfAllowed(evt) { | ||
function ResizeHandler(container, eventHandler, ownerWindow, slides, axis) { | ||
function ResizeHandler(container, eventHandler, ownerWindow, slides, axis, watchResize) { | ||
let resizeObserver; | ||
@@ -395,3 +398,3 @@ let containerSize; | ||
} | ||
function init(emblaApi, watchResize) { | ||
function init(emblaApi) { | ||
if (!watchResize) return; | ||
@@ -537,6 +540,7 @@ containerSize = readSize(container); | ||
function ScrollContain(viewSize, contentSize, snapsAligned, containScroll) { | ||
const scrollBounds = Limit(-contentSize + viewSize, snapsAligned[0]); | ||
const scrollBounds = Limit(-contentSize + viewSize, 0); | ||
const snapsBounded = measureBounded(); | ||
const scrollContainLimit = findScrollContainLimit(); | ||
const snapsContained = measureContained(); | ||
function findDuplicates() { | ||
function findScrollContainLimit() { | ||
const startSnap = snapsBounded[0]; | ||
@@ -557,7 +561,8 @@ const endSnap = arrayLast(snapsBounded); | ||
max | ||
} = findDuplicates(); | ||
} = scrollContainLimit; | ||
return snapsBounded.slice(min, max); | ||
} | ||
const self = { | ||
snapsContained | ||
snapsContained, | ||
scrollContainLimit | ||
}; | ||
@@ -604,7 +609,7 @@ return self; | ||
max, | ||
length: scrollLength | ||
length | ||
} = limit; | ||
function get(n) { | ||
const currentLocation = n - max; | ||
return currentLocation / -scrollLength; | ||
return length ? currentLocation / -length : 0; | ||
} | ||
@@ -617,3 +622,3 @@ const self = { | ||
function ScrollSnaps(axis, alignment, containerRect, slideRects, slideSizesWithGaps, slidesToScroll, containScroll) { | ||
function ScrollSnaps(axis, alignment, containerRect, slideRects, slidesToScroll) { | ||
const { | ||
@@ -636,11 +641,3 @@ startEdge, | ||
function measureAligned() { | ||
const containedStartSnap = 0; | ||
const containedEndSnap = arrayLast(snaps) - arrayLast(slideSizesWithGaps); | ||
return groupSlides(snaps).map(g => g[0]).map((snap, index, groupedSnaps) => { | ||
const isFirst = !index; | ||
const isLast = index === arrayLastIndex(groupedSnaps); | ||
if (containScroll && isFirst) return containedStartSnap; | ||
if (containScroll && isLast) return containedEndSnap; | ||
return snap + alignments[index]; | ||
}); | ||
return groupSlides(snaps).map(g => g[0]).map((snap, index) => snap + alignments[index]); | ||
} | ||
@@ -654,2 +651,34 @@ const self = { | ||
function SlideRegistry(viewSize, contentSize, containSnaps, scrollContainLimit, slidesToScroll, slideIndexes) { | ||
const { | ||
groupSlides | ||
} = slidesToScroll; | ||
const { | ||
min, | ||
max | ||
} = scrollContainLimit; | ||
const slideRegistry = createSlideRegistry(); | ||
function createSlideRegistry() { | ||
const groupedSlideIndexes = groupSlides(slideIndexes); | ||
if (!containSnaps || contentSize <= viewSize) return groupedSlideIndexes; | ||
return groupedSlideIndexes.slice(min, max).map((group, index, groups) => { | ||
const indexIsFirst = !index; | ||
const indexIsLast = !indexIsFirst && index === arrayLastIndex(groups); | ||
if (indexIsFirst) { | ||
const range = arrayLast(groups[0]) + 1; | ||
return arrayFromNumber(range); | ||
} | ||
if (indexIsLast) { | ||
const range = arrayLastIndex(slideIndexes) - arrayLast(groups)[0] + 1; | ||
return arrayFromNumber(range, arrayLast(groups)[0]); | ||
} | ||
return group; | ||
}); | ||
} | ||
const self = { | ||
slideRegistry | ||
}; | ||
return self; | ||
} | ||
function ScrollTarget(loop, scrollSnaps, contentSize, limit, targetVector) { | ||
@@ -683,3 +712,4 @@ const { | ||
const matchingTargets = targets.filter(t => mathSign(t) === direction); | ||
return minDistance(matchingTargets); | ||
if (matchingTargets.length) return minDistance(matchingTargets); | ||
return arrayLast(targets) - contentSize; | ||
} | ||
@@ -756,2 +786,34 @@ function byIndex(index, direction) { | ||
function SlideFocus(root, slides, slideRegistry, scrollTo, scrollBody, eventStore) { | ||
let lastTabPressTime = 0; | ||
function init() { | ||
eventStore.add(document, 'keydown', registerTabPress, false); | ||
slides.forEach(addSlideFocusEvent); | ||
} | ||
function registerTabPress(event) { | ||
if (event.code === 'Tab') lastTabPressTime = new Date().getTime(); | ||
} | ||
function addSlideFocusEvent(slide) { | ||
const focus = () => { | ||
const nowTime = new Date().getTime(); | ||
const diffTime = nowTime - lastTabPressTime; | ||
if (diffTime > 10) return; | ||
root.scrollLeft = 0; | ||
const index = slides.indexOf(slide); | ||
const group = slideRegistry.findIndex(group => group.includes(index)); | ||
if (!isNumber(group)) return; | ||
scrollBody.useDuration(0); | ||
scrollTo.index(group, 0); | ||
}; | ||
eventStore.add(slide, 'focus', focus, { | ||
passive: true, | ||
capture: true | ||
}); | ||
} | ||
const self = { | ||
init | ||
}; | ||
return self; | ||
} | ||
function Vector1D(initialValue) { | ||
@@ -813,3 +875,4 @@ let value = initialValue; | ||
function SlideLooper(axis, direction, viewSize, contentSize, slideSizesWithGaps, scrollSnaps, slidesInView, offsetLocation, slides) { | ||
function SlideLooper(axis, direction, viewSize, contentSize, slideSizes, slideSizesWithGaps, snaps, scrollSnaps, offsetLocation, slides) { | ||
const roundingSafety = 0.5; | ||
const ascItems = arrayKeys(slideSizesWithGaps); | ||
@@ -829,11 +892,15 @@ const descItems = arrayKeys(slideSizesWithGaps).reverse(); | ||
} | ||
function findLoopPoints(indexes, edge) { | ||
const isStartEdge = edge === 'start'; | ||
const offset = isStartEdge ? -contentSize : contentSize; | ||
const slideBounds = slidesInView.findSlideBounds([offset]); | ||
function findSlideBounds(offset) { | ||
return snaps.map((snap, index) => ({ | ||
start: snap - slideSizes[index] + roundingSafety + offset, | ||
end: snap + viewSize - roundingSafety + offset | ||
})); | ||
} | ||
function findLoopPoints(indexes, offset, isEndEdge) { | ||
const slideBounds = findSlideBounds(offset); | ||
return indexes.map(index => { | ||
const initial = isStartEdge ? 0 : -contentSize; | ||
const altered = isStartEdge ? contentSize : 0; | ||
const bounds = slideBounds.filter(b => b.index === index)[0]; | ||
const loopPoint = bounds[isStartEdge ? 'end' : 'start']; | ||
const initial = isEndEdge ? 0 : -contentSize; | ||
const altered = isEndEdge ? contentSize : 0; | ||
const boundEdge = isEndEdge ? 'end' : 'start'; | ||
const loopPoint = slideBounds[index][boundEdge]; | ||
return { | ||
@@ -850,3 +917,3 @@ index, | ||
const indexes = slidesInGap(descItems, gap); | ||
return findLoopPoints(indexes, 'end'); | ||
return findLoopPoints(indexes, contentSize, false); | ||
} | ||
@@ -856,3 +923,3 @@ function endPoints() { | ||
const indexes = slidesInGap(ascItems, gap); | ||
return findLoopPoints(indexes, 'start'); | ||
return findLoopPoints(indexes, -contentSize, true); | ||
} | ||
@@ -892,6 +959,6 @@ function canLoop() { | ||
function SlidesHandler(container, eventHandler) { | ||
function SlidesHandler(container, eventHandler, watchSlides) { | ||
let mutationObserver; | ||
let destroyed = false; | ||
function init(emblaApi, watchSlides) { | ||
function init(emblaApi) { | ||
if (!watchSlides) return; | ||
@@ -928,46 +995,52 @@ function defaultCallback(mutations) { | ||
function SlidesInView(viewSize, contentSize, slideSizes, snaps, limit, loop, inViewThreshold) { | ||
const { | ||
removeOffset, | ||
constrain | ||
} = limit; | ||
const roundingSafety = 0.5; | ||
const cachedOffsets = loop ? [0, contentSize, -contentSize] : [0]; | ||
const cachedBounds = findSlideBounds(cachedOffsets, inViewThreshold); | ||
function findSlideThresholds(threshold) { | ||
const slideThreshold = threshold || 0; | ||
return slideSizes.map(slideSize => { | ||
const thresholdLimit = Limit(roundingSafety, slideSize - roundingSafety); | ||
return thresholdLimit.constrain(slideSize * slideThreshold); | ||
function SlidesInView(container, slides, eventHandler, threshold) { | ||
const intersectionEntryMap = {}; | ||
let inViewCache = null; | ||
let notInViewCache = null; | ||
let intersectionObserver; | ||
let destroyed = false; | ||
function init() { | ||
intersectionObserver = new IntersectionObserver(entries => { | ||
if (destroyed) return; | ||
entries.forEach(entry => { | ||
const index = slides.indexOf(entry.target); | ||
intersectionEntryMap[index] = entry; | ||
}); | ||
inViewCache = null; | ||
notInViewCache = null; | ||
eventHandler.emit('slidesInView'); | ||
}, { | ||
root: container.parentElement, | ||
threshold | ||
}); | ||
slides.forEach(slide => intersectionObserver.observe(slide)); | ||
} | ||
function findSlideBounds(offsets, threshold) { | ||
const slideOffsets = offsets || cachedOffsets; | ||
const slideThresholds = findSlideThresholds(threshold); | ||
return slideOffsets.reduce((list, offset) => { | ||
const bounds = snaps.map((snap, index) => ({ | ||
start: snap - slideSizes[index] + slideThresholds[index] + offset, | ||
end: snap + viewSize - slideThresholds[index] + offset, | ||
index | ||
})); | ||
return list.concat(bounds); | ||
}, []); | ||
function destroy() { | ||
if (intersectionObserver) intersectionObserver.disconnect(); | ||
destroyed = true; | ||
} | ||
function check(location, bounds) { | ||
const limitedLocation = loop ? removeOffset(location) : constrain(location); | ||
const slideBounds = bounds || cachedBounds; | ||
return slideBounds.reduce((list, slideBound) => { | ||
function createInViewList(inView) { | ||
return objectKeys(intersectionEntryMap).reduce((list, slideIndex) => { | ||
const index = parseInt(slideIndex); | ||
const { | ||
index, | ||
start, | ||
end | ||
} = slideBound; | ||
const inList = list.includes(index); | ||
const inView = start < limitedLocation && end > limitedLocation; | ||
return !inList && inView ? list.concat([index]) : list; | ||
isIntersecting | ||
} = intersectionEntryMap[index]; | ||
const inViewMatch = inView && isIntersecting; | ||
const notInViewMatch = !inView && !isIntersecting; | ||
if (inViewMatch || notInViewMatch) list.push(index); | ||
return list; | ||
}, []); | ||
} | ||
function get(inView = true) { | ||
if (inView && inViewCache) return inViewCache; | ||
if (!inView && notInViewCache) return notInViewCache; | ||
const slideIndexes = createInViewList(inView); | ||
if (inView) inViewCache = slideIndexes; | ||
if (!inView) notInViewCache = slideIndexes; | ||
return slideIndexes; | ||
} | ||
const self = { | ||
check, | ||
findSlideBounds | ||
init, | ||
destroy, | ||
get | ||
}; | ||
@@ -1009,3 +1082,5 @@ return self; | ||
slideSizes, | ||
slideSizesWithGaps | ||
slideSizesWithGaps, | ||
startGap, | ||
endGap | ||
}; | ||
@@ -1015,3 +1090,7 @@ return self; | ||
function SlidesToScroll(viewSize, slideSizesWithGaps, slidesToScroll) { | ||
function SlidesToScroll(axis, direction, viewSize, slidesToScroll, loop, containerRect, slideRects, startGap, endGap) { | ||
const { | ||
startEdge, | ||
endEdge | ||
} = axis; | ||
const groupByNumber = isNumber(slidesToScroll); | ||
@@ -1022,7 +1101,19 @@ function byNumber(array, groupSize) { | ||
function bySize(array) { | ||
return arrayKeys(array).reduce((groupSizes, i) => { | ||
const chunk = slideSizesWithGaps.slice(arrayLast(groupSizes), i + 1); | ||
const chunkSize = chunk.reduce((a, s) => a + s, 0); | ||
return !i || chunkSize > viewSize ? groupSizes.concat(i) : groupSizes; | ||
}, []).map((start, i, groupSizes) => array.slice(start, groupSizes[i + 1])); | ||
if (!array.length) return []; | ||
return arrayKeys(array).reduce((groups, rectB) => { | ||
const rectA = arrayLast(groups) || 0; | ||
const isFirst = rectA === 0; | ||
const isLast = rectB === arrayLastIndex(array); | ||
const edgeA = containerRect[startEdge] - slideRects[rectA][startEdge]; | ||
const edgeB = containerRect[startEdge] - slideRects[rectB][endEdge]; | ||
const gapA = !loop && isFirst ? direction.apply(startGap) : 0; | ||
const gapB = !loop && isLast ? direction.apply(endGap) : 0; | ||
const chunkSize = mathAbs(edgeB - gapB - (edgeA + gapA)); | ||
if (chunkSize > viewSize) groups.push(rectB); | ||
if (isLast) groups.push(array.length); | ||
return groups; | ||
}, []).map((currentSize, index, groups) => { | ||
const previousSize = Math.max(groups[index - 1] || 0); | ||
return array.slice(previousSize, currentSize); | ||
}); | ||
} | ||
@@ -1045,3 +1136,2 @@ function groupSlides(array) { | ||
startIndex, | ||
inViewThreshold, | ||
loop, | ||
@@ -1051,5 +1141,9 @@ duration, | ||
dragThreshold, | ||
inViewThreshold, | ||
slidesToScroll: groupSlides, | ||
skipSnaps, | ||
containScroll | ||
containScroll, | ||
watchResize, | ||
watchSlides, | ||
watchDrag | ||
} = options; | ||
@@ -1068,12 +1162,15 @@ // Measurements | ||
slideSizes, | ||
slideSizesWithGaps | ||
slideSizesWithGaps, | ||
startGap, | ||
endGap | ||
} = SlideSizes(axis, containerRect, slideRects, slides, readEdgeGap, ownerWindow); | ||
const slidesToScroll = SlidesToScroll(viewSize, slideSizesWithGaps, groupSlides); | ||
const slidesToScroll = SlidesToScroll(axis, direction, viewSize, groupSlides, loop, containerRect, slideRects, startGap, endGap); | ||
const { | ||
snaps, | ||
snapsAligned | ||
} = ScrollSnaps(axis, alignment, containerRect, slideRects, slideSizesWithGaps, slidesToScroll, containSnaps); | ||
} = ScrollSnaps(axis, alignment, containerRect, slideRects, slidesToScroll); | ||
const contentSize = -arrayLast(snaps) + arrayLast(slideSizesWithGaps); | ||
const { | ||
snapsContained | ||
snapsContained, | ||
scrollContainLimit | ||
} = ScrollContain(viewSize, contentSize, snapsAligned, containScroll); | ||
@@ -1142,3 +1239,9 @@ const scrollSnaps = containSnaps ? snapsContained : snapsAligned; | ||
const scrollTo = ScrollTo(animation, index, indexPrevious, scrollTarget, scrollBody, target, eventHandler); | ||
const slidesInView = SlidesInView(viewSize, contentSize, slideSizes, snaps, limit, loop, inViewThreshold); | ||
const scrollProgress = ScrollProgress(limit); | ||
const eventStore = EventStore(); | ||
const slidesInView = SlidesInView(container, slides, eventHandler, inViewThreshold); | ||
const { | ||
slideRegistry | ||
} = SlideRegistry(viewSize, contentSize, containSnaps, scrollContainLimit, slidesToScroll, slideIndexes); | ||
const slideFocus = SlideFocus(root, slides, slideRegistry, scrollTo, scrollBody, eventStore); | ||
// Engine | ||
@@ -1154,4 +1257,4 @@ const engine = { | ||
direction, | ||
dragHandler: DragHandler(axis, direction, root, ownerDocument, ownerWindow, target, DragTracker(axis, ownerWindow), location, animation, scrollTo, scrollBody, scrollTarget, index, eventHandler, percentOfView, dragFree, dragThreshold, skipSnaps, friction), | ||
eventStore: EventStore(), | ||
dragHandler: DragHandler(axis, direction, root, ownerDocument, ownerWindow, target, DragTracker(axis, ownerWindow), location, animation, scrollTo, scrollBody, scrollTarget, index, eventHandler, percentOfView, dragFree, dragThreshold, skipSnaps, friction, watchDrag), | ||
eventStore, | ||
percentOfView, | ||
@@ -1164,14 +1267,17 @@ index, | ||
options, | ||
resizeHandler: ResizeHandler(container, eventHandler, ownerWindow, slides, axis), | ||
resizeHandler: ResizeHandler(container, eventHandler, ownerWindow, slides, axis, watchResize), | ||
scrollBody, | ||
scrollBounds: ScrollBounds(limit, location, target, scrollBody, percentOfView), | ||
scrollLooper: ScrollLooper(contentSize, limit, offsetLocation, [location, offsetLocation, target]), | ||
scrollProgress: ScrollProgress(limit), | ||
scrollProgress, | ||
scrollSnapList: scrollSnaps.map(scrollProgress.get), | ||
scrollSnaps, | ||
scrollTarget, | ||
scrollTo, | ||
slideLooper: SlideLooper(axis, direction, viewSize, contentSize, slideSizesWithGaps, scrollSnaps, slidesInView, offsetLocation, slides), | ||
slidesHandler: SlidesHandler(container, eventHandler), | ||
slideLooper: SlideLooper(axis, direction, viewSize, contentSize, slideSizes, slideSizesWithGaps, snaps, scrollSnaps, offsetLocation, slides), | ||
slideFocus, | ||
slidesHandler: SlidesHandler(container, eventHandler, watchSlides), | ||
slidesInView, | ||
slideIndexes, | ||
slideRegistry, | ||
slidesToScroll, | ||
@@ -1271,6 +1377,6 @@ target, | ||
slidesToScroll: 1, | ||
inViewThreshold: 0, | ||
breakpoints: {}, | ||
dragFree: false, | ||
dragThreshold: 10, | ||
inViewThreshold: 0, | ||
loop: false, | ||
@@ -1308,3 +1414,3 @@ skipSnaps: false, | ||
let activePlugins = []; | ||
function init(plugins, emblaApi) { | ||
function init(emblaApi, plugins) { | ||
activePlugins = plugins.filter(({ | ||
@@ -1393,5 +1499,7 @@ options | ||
engine.translate.to(engine.location.get()); | ||
engine.slidesInView.init(); | ||
engine.slideFocus.init(); | ||
engine.eventHandler.init(self); | ||
engine.resizeHandler.init(self, options.watchResize); | ||
engine.slidesHandler.init(self, options.watchSlides); | ||
engine.resizeHandler.init(self); | ||
engine.slidesHandler.init(self); | ||
documentVisibleHandler.add(ownerDocument, 'visibilitychange', () => { | ||
@@ -1401,6 +1509,4 @@ if (ownerDocument.hidden) animations.reset(); | ||
if (engine.options.loop) engine.slideLooper.loop(); | ||
if (container.offsetParent && slides.length) { | ||
engine.dragHandler.init(self, options.watchDrag); | ||
} | ||
pluginApis = pluginsHandler.init(pluginList, self); | ||
if (container.offsetParent && slides.length) engine.dragHandler.init(self); | ||
pluginApis = pluginsHandler.init(self, pluginList); | ||
} | ||
@@ -1434,11 +1540,2 @@ function reActivate(withOptions, withPlugins) { | ||
} | ||
function slidesInView(target) { | ||
const location = engine[target ? 'target' : 'location'].get(); | ||
const type = options.loop ? 'removeOffset' : 'constrain'; | ||
return engine.slidesInView.check(engine.limit[type](location)); | ||
} | ||
function slidesNotInView(target) { | ||
const inView = slidesInView(target); | ||
return engine.slideIndexes.filter(index => !inView.includes(index)); | ||
} | ||
function scrollTo(index, jump, direction) { | ||
@@ -1466,3 +1563,3 @@ if (!options.active || destroyed) return; | ||
function scrollSnapList() { | ||
return engine.scrollSnaps.map(engine.scrollProgress.get); | ||
return engine.scrollSnapList; | ||
} | ||
@@ -1478,2 +1575,8 @@ function scrollProgress() { | ||
} | ||
function slidesInView() { | ||
return engine.slidesInView.get(); | ||
} | ||
function slidesNotInView() { | ||
return engine.slidesInView.get(false); | ||
} | ||
function plugins() { | ||
@@ -1480,0 +1583,0 @@ return pluginApis; |
@@ -1,1 +0,1 @@ | ||
!function(n,t){"object"==typeof exports&&"undefined"!=typeof module?module.exports=t():"function"==typeof define&&define.amd?define(t):(n="undefined"!=typeof globalThis?globalThis:n||self).EmblaCarousel=t()}(this,(function(){"use strict";function n(n){return"number"==typeof n}function t(n){return"string"==typeof n}function e(n){return"boolean"==typeof n}function r(n){return"[object Object]"===Object.prototype.toString.call(n)}function o(n){return Math.abs(n)}function i(n){return Math.sign(n)}function c(n,t){return o(n-t)}function u(n){return d(n).map(Number)}function s(n){return n[a(n)]}function a(n){return Math.max(0,n.length-1)}function d(n){return Object.keys(n)}function l(n,t){return[n,t].reduce(((n,t)=>(d(t).forEach((e=>{const o=n[e],i=t[e],c=r(o)&&r(i);n[e]=c?l(o,i):i})),n)),{})}function f(n,t){return void 0!==t.MouseEvent&&n instanceof t.MouseEvent}function p(t,e){const r={start:function(){return 0},center:function(n){return o(n)/2},end:o};function o(n){return e-n}return{measure:function(o){return n(t)?e*Number(t):r[t](o)}}}function m(n,t){const e=o(n-t);function r(t){return t<n}function i(n){return n>t}function c(n){return r(n)||i(n)}return{length:e,max:t,min:n,constrain:function(e){return c(e)?r(e)?n:t:e},reachedAny:c,reachedMax:i,reachedMin:r,removeOffset:function(n){return e?n-e*Math.ceil((n-t)/e):n}}}function g(n,t,e){const{constrain:r}=m(0,n),i=n+1;let c=u(t);function u(n){return e?o((i+n)%i):r(n)}function s(){return c}function a(){return g(n,s(),e)}const d={get:s,set:function(n){return c=u(n),d},add:function(n){return a().set(s()+n)},clone:a};return d}function h(){let n=[];const t={add:function(e,r,o,i={passive:!0}){return e.addEventListener(r,o,i),n.push((()=>e.removeEventListener(r,o,i))),t},clear:function(){n=n.filter((n=>n()))}};return t}function x(n,t,r,u,s,a,d,l,p,g,x,y,v,b,S,w,E,D,M){const{cross:A}=n,L=["INPUT","SELECT","TEXTAREA"],O={passive:!1},I=h(),P=h(),T=m(50,225).constrain(S.measure(20)),F={mouse:300,touch:400},z={mouse:500,touch:600},B=w?43:25;let k=!1,H=0,R=0,N=!1,C=!1,V=!1,j=!1;function q(n){const e=d.readPoint(n),r=d.readPoint(n,A),o=c(e,H),i=c(r,R);if(!C&&!j){if(!n.cancelable)return U(n);if(C=o>i,!C)return U(n)}const u=d.pointerMove(n);o>E&&(V=!0),x.useFriction(.3).useDuration(1),p.start(),a.add(t.apply(u)),n.preventDefault()}function U(n){const e=y.byDistance(0,!1).index!==v.get(),r=d.pointerUp(n)*(w?z:F)[j?"mouse":"touch"],u=function(n,t){const e=v.add(-1*i(n)),r=y.byDistance(n,!w).distance;return w||o(n)<T?r:D&&t?.5*r:y.byIndex(e.get(),0).distance}(t.apply(r),e),s=function(n,t){if(0===n||0===t)return 0;if(o(n)<=o(t))return 0;const e=c(o(n),o(t));return o(e/n)}(r,u),a=B-10*s,l=M+s/50;C=!1,N=!1,P.clear(),x.useDuration(a).useFriction(l),g.distance(u,!w),j=!1,b.emit("pointerUp")}function W(n){V&&(n.stopPropagation(),n.preventDefault())}return{init:function(n,t){if(!t)return;function o(o){(e(t)||t(n,o))&&function(n){const t=f(n,s);if(j=t,t&&0!==n.button)return;if(function(n){const t=n.nodeName||"";return L.includes(t)}(n.target))return;V=w&&t&&!n.buttons&&k,k=c(a.get(),l.get())>=2,N=!0,d.pointerDown(n),x.useFriction(0).useDuration(0),a.set(l),function(){const n=j?u:r;P.add(n,"touchmove",q,O).add(n,"touchend",U).add(n,"mousemove",q,O).add(n,"mouseup",U)}(),H=d.readPoint(n),R=d.readPoint(n,A),b.emit("pointerDown")}(o)}const i=r;I.add(i,"dragstart",(n=>n.preventDefault()),O).add(i,"touchmove",(()=>{}),O).add(i,"touchend",(()=>{})).add(i,"touchstart",o).add(i,"mousedown",o).add(i,"touchcancel",U).add(i,"contextmenu",U).add(i,"click",W,!0)},pointerDown:function(){return N},destroy:function(){I.clear(),P.clear()}}}function y(n,t){let e,r;function i(n){return n.timeStamp}function c(e,r){const o="client"+("x"===(r||n.scroll)?"X":"Y");return(f(e,t)?e:e.touches[0])[o]}return{pointerDown:function(n){return e=n,r=n,c(n)},pointerMove:function(n){const t=c(n)-c(r),o=i(n)-i(e)>170;return r=n,o&&(e=n),t},pointerUp:function(n){if(!e||!r)return 0;const t=c(r)-c(e),u=i(n)-i(e),s=i(n)-i(r)>170,a=t/u;return u&&!s&&o(a)>.1?a:0},readPoint:c}}function v(n,t,r,o,i){let c,u,s=[],a=!1;function d(n){return i.measureSize(n.getBoundingClientRect())}return{init:function(i,l){if(!l)return;u=d(n),s=o.map(d),c=new ResizeObserver((c=>{a||(e(l)||l(i,c))&&function(e){for(const c of e){const e=c.target===n,a=o.indexOf(c.target);if((e?u:s[a])!==d(e?n:o[a])){r.requestAnimationFrame((()=>{i.reInit(),t.emit("resize")}));break}}}(c)})),[n].concat(o).forEach((n=>c.observe(n)))},destroy:function(){c&&c.disconnect(),a=!0}}}function b(n,t,e,r,i){const c=i.measure(10),u=i.measure(50),s=m(.1,.99);let a=!1;return{constrain:function(i){if(a||!n.reachedAny(e.get())||!n.reachedAny(t.get()))return;const d=n.reachedMin(t.get())?"min":"max",l=o(n[d]-t.get()),f=e.get()-t.get(),p=s.constrain(l/u);e.subtract(f*p),!i&&o(f)<c&&(e.set(n.constrain(e.get())),r.useDuration(25).useBaseFriction())},toggleActive:function(n){a=!n}}}function S(n,t,e,r){const o=m(-t+n,e[0]),i=e.map(o.constrain).map((n=>parseFloat(n.toFixed(3))));return{snapsContained:function(){if(t<=n)return[o.max];if("keepSnaps"===r)return i;const{min:e,max:c}=function(){const n=i[0],t=s(i),e=i.lastIndexOf(n),r=i.indexOf(t)+1;return m(e,r)}();return i.slice(e,c)}()}}function w(n,t,e,r){const o=t.min+.1,i=t.max+.1,{reachedMin:c,reachedMax:u}=m(o,i);return{loop:function(t){if(!function(n){return 1===n?u(e.get()):-1===n&&c(e.get())}(t))return;const o=n*(-1*t);r.forEach((n=>n.add(o)))}}}function E(n){const{max:t,length:e}=n;return{get:function(n){return(n-t)/-e}}}function D(n,t,e,r,c){const{reachedAny:u,removeOffset:s,constrain:a}=r;function d(n){return n.concat().sort(((n,t)=>o(n)-o(t)))[0]}function l(t,r){const o=[t,t+e,t-e];if(!n)return o[0];if(!r)return d(o);return d(o.filter((n=>i(n)===r)))}return{byDistance:function(e,r){const i=c.get()+e,{index:d,distance:f}=function(e){const r=n?s(e):a(e),i=t.map((n=>n-r)).map((n=>l(n,0))).map(((n,t)=>({diff:n,index:t}))).sort(((n,t)=>o(n.diff)-o(t.diff))),{index:c}=i[0];return{index:c,distance:r}}(i),p=!n&&u(i);return!r||p?{index:d,distance:e}:{index:d,distance:e+l(t[d]-f,0)}},byIndex:function(n,e){return{index:n,distance:l(t[n]-c.get(),e)}},shortcut:l}}function M(t){let e=t;function r(t){return n(t)?t:t.get()}return{get:function(){return e},set:function(n){e=r(n)},add:function(n){e+=r(n)},subtract:function(n){e-=r(n)}}}function A(n,t,e){const r="x"===n.scroll?function(n){return`translate3d(${n}px,0px,0px)`}:function(n){return`translate3d(0px,${n}px,0px)`},o=e.style;let i=!1;return{clear:function(){i||(o.transform="",e.getAttribute("style")||e.removeAttribute("style"))},to:function(n){i||(o.transform=r(t.apply(n)))},toggleActive:function(n){i=!n}}}function L(n,t,e,r,o,i,c,s,a){const d=u(o),l=u(o).reverse(),f=function(){const n=i[0]-1;return g(m(l,n),"end")}().concat(function(){const n=e-i[0]-1;return g(m(d,n),"start")}());function p(n,t){return n.reduce(((n,t)=>n-o[t]),t)}function m(n,t){return n.reduce(((n,e)=>p(n,t)>0?n.concat([e]):n),[])}function g(e,o){const i="start"===o,u=i?-r:r,d=c.findSlideBounds([u]);return e.map((e=>{const o=i?0:-r,c=i?r:0,u=d.filter((n=>n.index===e))[0][i?"end":"start"];return{index:e,slideLocation:M(-1),translate:A(n,t,a[e]),target:()=>s.get()>u?o:c}}))}return{canLoop:function(){return f.every((({index:n})=>p(d.filter((t=>t!==n)),e)<=.1))},clear:function(){f.forEach((n=>n.translate.clear()))},loop:function(){f.forEach((n=>{const{target:t,translate:e,slideLocation:r}=n,o=t();o!==r.get()&&(e.to(o),r.set(o))}))},loopPoints:f}}function O(n,t){let r,o=!1;return{init:function(i,c){c&&(r=new MutationObserver((n=>{o||(e(c)||c(i,n))&&function(n){for(const e of n)if("childList"===e.type){i.reInit(),t.emit("slidesChanged");break}}(n)})),r.observe(n,{childList:!0}))},destroy:function(){r&&r.disconnect(),o=!0}}}function I(n,t,e,r,o,i,c){const{removeOffset:u,constrain:s}=o,a=i?[0,t,-t]:[0],d=l(a,c);function l(t,o){const i=t||a,c=function(n){const t=n||0;return e.map((n=>m(.5,n-.5).constrain(n*t)))}(o);return i.reduce(((t,o)=>{const i=r.map(((t,r)=>({start:t-e[r]+c[r]+o,end:t+n-c[r]+o,index:r})));return t.concat(i)}),[])}return{check:function(n,t){const e=i?u(n):s(n);return(t||d).reduce(((n,t)=>{const{index:r,start:o,end:i}=t;return!n.includes(r)&&(o<e&&i>e)?n.concat([r]):n}),[])},findSlideBounds:l}}function P(t,e,r){const o=n(r);return{groupSlides:function(n){return o?function(n,t){return u(n).filter((n=>n%t==0)).map((e=>n.slice(e,e+t)))}(n,r):function(n){return u(n).reduce(((n,r)=>{const o=e.slice(s(n),r+1).reduce(((n,t)=>n+t),0);return!r||o>t?n.concat(r):n}),[]).map(((t,e,r)=>n.slice(t,r[e+1])))}(n)}}}function T(n,t,e,r,c,d,l,f){const{align:T,axis:F,direction:z,startIndex:B,inViewThreshold:k,loop:H,duration:R,dragFree:N,dragThreshold:C,slidesToScroll:V,skipSnaps:j,containScroll:q}=d,U=t.getBoundingClientRect(),W=e.map((n=>n.getBoundingClientRect())),$=function(n){const t="rtl"===n?-1:1;return{apply:function(n){return n*t}}}(z),G=function(n,t){const e="y"===n?"y":"x";return{scroll:e,cross:"y"===n?"x":"y",startEdge:"y"===e?"top":"rtl"===t?"right":"left",endEdge:"y"===e?"bottom":"rtl"===t?"left":"right",measureSize:function(n){const{width:t,height:r}=n;return"x"===e?t:r}}}(F,z),Q=G.measureSize(U),X=function(n){return{measure:function(t){return n*(t/100)}}}(Q),Y=p(T,Q),J=!H&&!!q,K=H||!!q,{slideSizes:Z,slideSizesWithGaps:_}=function(n,t,e,r,i,c){const{measureSize:u,startEdge:d,endEdge:l}=n,f=e[0]&&i,p=function(){if(!f)return 0;const n=e[0];return o(t[d]-n[d])}(),m=function(){if(!f)return 0;const n=c.getComputedStyle(s(r));return parseFloat(n.getPropertyValue(`margin-${l}`))}(),g=e.map(u),h=e.map(((n,t,e)=>{const r=!t,o=t===a(e);return r?g[t]+p:o?g[t]+m:e[t+1][d]-n[d]})).map(o);return{slideSizes:g,slideSizesWithGaps:h}}(G,U,W,e,K,c),nn=P(Q,_,V),{snaps:tn,snapsAligned:en}=function(n,t,e,r,i,c,u){const{startEdge:d,endEdge:l}=n,{groupSlides:f}=c,p=f(r).map((n=>s(n)[l]-n[0][d])).map(o).map(t.measure),m=r.map((n=>e[d]-n[d])).map((n=>-o(n))),g=function(){const n=s(m)-s(i);return f(m).map((n=>n[0])).map(((t,e,r)=>{const o=!e,i=e===a(r);return u&&o?0:u&&i?n:t+p[e]}))}();return{snaps:m,snapsAligned:g}}(G,Y,U,W,_,nn,J),rn=-s(tn)+s(_),{snapsContained:on}=S(Q,rn,en,q),cn=J?on:en,{limit:un}=function(n,t,e){const r=t[0];return{limit:m(e?r-n:s(t),r)}}(rn,cn,H),sn=g(a(cn),B,H),an=sn.clone(),dn=u(e),ln={start:()=>f.start(bn),stop:()=>f.stop(bn),update:()=>(({dragHandler:n,scrollBody:t,scrollBounds:e,eventHandler:r,animation:o,options:{loop:i}})=>{const c=n.pointerDown();i||e.constrain(c);const u=t.seek().settled();u&&!c&&(o.stop(),r.emit("settle")),u||r.emit("scroll")})(bn),render:n=>(({scrollBody:n,translate:t,location:e,offsetLocation:r,scrollLooper:o,slideLooper:i,options:{loop:c}},u)=>{const s=n.velocity();r.set(e.get()-s+s*u),c&&(o.loop(n.direction()),i.loop()),t.to(r.get())})(bn,n)},fn=cn[sn.get()],pn=M(fn),mn=M(fn),gn=M(fn),hn=function(n,t,e,r){let c=!0,u=0,s=0,a=e,d=r,l=n.get(),f=0;function p(n){return a=n,g}function m(n){return d=n,g}const g={direction:function(){return s},duration:function(){return a},velocity:function(){return u},seek:function(){const e=t.get()-n.get();let r=0;return a?(u+=e/a,u*=d,l+=u,n.add(u),r=l-f):(u=0,n.set(t),r=e),s=i(r),f=l,c=o(e)<.001,g},settled:function(){return c},useBaseFriction:function(){return m(r)},useBaseDuration:function(){return p(e)},useFriction:m,useDuration:p};return g}(pn,gn,R,.68),xn=D(H,cn,rn,un,gn),yn=function(n,t,e,r,o,i,c){function u(r){const u=r.distance,s=r.index!==t.get();i.add(u),u&&(o.duration()?n.start():(n.update(),n.render(1),n.update())),s&&(e.set(t.get()),t.set(r.index),c.emit("select"))}return{distance:function(n,t){u(r.byDistance(n,t))},index:function(n,e){const o=t.clone().set(n);u(r.byIndex(o.get(),e))}}}(ln,sn,an,xn,hn,gn,l),vn=I(Q,rn,Z,tn,un,H,k),bn={ownerDocument:r,ownerWindow:c,eventHandler:l,containerRect:U,slideRects:W,animation:ln,axis:G,direction:$,dragHandler:x(G,$,n,r,c,gn,y(G,c),pn,ln,yn,hn,xn,sn,l,X,N,C,j,.68),eventStore:h(),percentOfView:X,index:sn,indexPrevious:an,limit:un,location:pn,offsetLocation:mn,options:d,resizeHandler:v(t,l,c,e,G),scrollBody:hn,scrollBounds:b(un,pn,gn,hn,X),scrollLooper:w(rn,un,mn,[pn,mn,gn]),scrollProgress:E(un),scrollSnaps:cn,scrollTarget:xn,scrollTo:yn,slideLooper:L(G,$,Q,rn,_,cn,vn,mn,e),slidesHandler:O(t,l),slidesInView:vn,slideIndexes:dn,slidesToScroll:nn,target:gn,translate:A(G,$,t)};return bn}const F={align:"center",axis:"x",container:null,slides:null,containScroll:"trimSnaps",direction:"ltr",slidesToScroll:1,breakpoints:{},dragFree:!1,dragThreshold:10,inViewThreshold:0,loop:!1,skipSnaps:!1,duration:25,startIndex:0,active:!0,watchDrag:!0,watchResize:!0,watchSlides:!0};function z(n){function t(n,t){return l(n,t||{})}const e={mergeOptions:t,optionsAtMedia:function(e){const r=e.breakpoints||{},o=d(r).filter((t=>n.matchMedia(t).matches)).map((n=>r[n])).reduce(((n,e)=>t(n,e)),{});return t(e,o)},optionsMediaQueries:function(t){return t.map((n=>d(n.breakpoints||{}))).reduce(((n,t)=>n.concat(t)),[]).map(n.matchMedia)}};return e}function B(n,e,r){const i=n.ownerDocument,c=i.defaultView,u=z(c),s=function(n){let t=[];return{init:function(e,r){return t=e.filter((({options:t})=>!1!==n.optionsAtMedia(t).active)),t.forEach((t=>t.init(r,n))),e.reduce(((n,t)=>Object.assign(n,{[t.name]:t})),{})},destroy:function(){t=t.filter((n=>n.destroy()))}}}(u),a=h(),d=h(),l=function(){const n={};let t;function e(t){return n[t]||[]}const r={init:function(n){t=n},emit:function(n){return e(n).forEach((e=>e(t,n))),r},off:function(t,o){return n[t]=e(t).filter((n=>n!==o)),r},on:function(t,o){return n[t]=e(t).concat([o]),r}};return r}(),{animationRealms:f}=B,{mergeOptions:p,optionsAtMedia:m,optionsMediaQueries:g}=u,{on:x,off:y,emit:v}=l,b=k;let S,w,E,D,M=!1,A=p(F,B.globalOptions),L=p(A),O=[];function I(t,e){const r=T(n,E,D,i,c,t,l,e);if(t.loop&&!r.slideLooper.canLoop()){return I(Object.assign({},t,{loop:!1}),e)}return r}function P(e,r){if(M)return;const u=f.find((n=>n.window===c)),l=u||function(n){const t=1e3/60;let e=[],r=null,i=0,c=0;function u(s){r||(r=s);const a=s-r;for(r=s,i+=a;i>=t;)e.forEach((({animation:n})=>n.update())),i-=t;const d=o(i/t);e.forEach((({animation:n})=>n.render(d))),c&&n.requestAnimationFrame(u)}return{start:function(t){e.includes(t)||e.push(t),c||(c=n.requestAnimationFrame(u))},stop:function(t){e=e.filter((n=>n!==t)),e.length||(n.cancelAnimationFrame(c),r=null,i=0,c=0)},reset:function(){r=null,i=0},window:n}}(c);u||f.push(l),A=p(A,e),L=m(A),O=r||O,function(){const{container:e,slides:r}=L,o=t(e)?n.querySelector(e):e;E=o||n.children[0];const i=t(r)?E.querySelectorAll(r):r;D=[].slice.call(i||E.children)}(),S=I(L,l),g([A,...O.map((({options:n})=>n))]).forEach((n=>a.add(n,"change",k))),L.active&&(S.translate.to(S.location.get()),S.eventHandler.init(V),S.resizeHandler.init(V,L.watchResize),S.slidesHandler.init(V,L.watchSlides),d.add(i,"visibilitychange",(()=>{i.hidden&&l.reset()})),S.options.loop&&S.slideLooper.loop(),E.offsetParent&&D.length&&S.dragHandler.init(V,L.watchDrag),w=s.init(O,V))}function k(n,t){const e=C();H(),P(p({startIndex:e},n),t),l.emit("reInit")}function H(){S.dragHandler.destroy(),S.animation.stop(),S.eventStore.clear(),S.translate.clear(),S.slideLooper.clear(),S.resizeHandler.destroy(),S.slidesHandler.destroy(),s.destroy(),a.clear(),d.clear()}function R(n){const t=S[n?"target":"location"].get(),e=L.loop?"removeOffset":"constrain";return S.slidesInView.check(S.limit[e](t))}function N(n,t,e){L.active&&!M&&(S.scrollBody.useBaseFriction().useDuration(t?0:L.duration),S.scrollTo.index(n,e||0))}function C(){return S.index.get()}const V={canScrollNext:function(){return S.index.add(1).get()!==C()},canScrollPrev:function(){return S.index.add(-1).get()!==C()},containerNode:function(){return E},internalEngine:function(){return S},destroy:function(){M||(M=!0,a.clear(),H(),l.emit("destroy"))},off:y,on:x,emit:v,plugins:function(){return w},previousScrollSnap:function(){return S.indexPrevious.get()},reInit:b,rootNode:function(){return n},scrollNext:function(n){N(S.index.add(1).get(),!0===n,-1)},scrollPrev:function(n){N(S.index.add(-1).get(),!0===n,1)},scrollProgress:function(){return S.scrollProgress.get(S.location.get())},scrollSnapList:function(){return S.scrollSnaps.map(S.scrollProgress.get)},scrollTo:N,selectedScrollSnap:C,slideNodes:function(){return D},slidesInView:R,slidesNotInView:function(n){const t=R(n);return S.slideIndexes.filter((n=>!t.includes(n)))}};return P(e,r),setTimeout((()=>l.emit("init")),0),V}return B.animationRealms=[],B.globalOptions=void 0,B})); | ||
!function(n,t){"object"==typeof exports&&"undefined"!=typeof module?module.exports=t():"function"==typeof define&&define.amd?define(t):(n="undefined"!=typeof globalThis?globalThis:n||self).EmblaCarousel=t()}(this,(function(){"use strict";function n(n){return"number"==typeof n}function t(n){return"string"==typeof n}function e(n){return"boolean"==typeof n}function r(n){return"[object Object]"===Object.prototype.toString.call(n)}function o(n){return Math.abs(n)}function i(n){return Math.sign(n)}function c(n,t){return o(n-t)}function u(n){return d(n).map(Number)}function s(n){return n[a(n)]}function a(n){return Math.max(0,n.length-1)}function l(n,t=0){return Array.from(Array(n),((n,e)=>t+e))}function d(n){return Object.keys(n)}function f(n,t){return[n,t].reduce(((n,t)=>(d(t).forEach((e=>{const o=n[e],i=t[e],c=r(o)&&r(i);n[e]=c?f(o,i):i})),n)),{})}function p(n,t){return void 0!==t.MouseEvent&&n instanceof t.MouseEvent}function m(t,e){const r={start:function(){return 0},center:function(n){return o(n)/2},end:o};function o(n){return e-n}return{measure:function(o){return n(t)?e*Number(t):r[t](o)}}}function g(n,t){const e=o(n-t);function r(t){return t<n}function i(n){return n>t}function c(n){return r(n)||i(n)}return{length:e,max:t,min:n,constrain:function(e){return c(e)?r(e)?n:t:e},reachedAny:c,reachedMax:i,reachedMin:r,removeOffset:function(n){return e?n-e*Math.ceil((n-t)/e):n}}}function h(n,t,e){const{constrain:r}=g(0,n),i=n+1;let c=u(t);function u(n){return e?o((i+n)%i):r(n)}function s(){return c}function a(){return h(n,s(),e)}const l={get:s,set:function(n){return c=u(n),l},add:function(n){return a().set(s()+n)},clone:a};return l}function x(){let n=[];const t={add:function(e,r,o,i={passive:!0}){return e.addEventListener(r,o,i),n.push((()=>e.removeEventListener(r,o,i))),t},clear:function(){n=n.filter((n=>n()))}};return t}function y(n,t,r,u,s,a,l,d,f,m,h,y,v,b,S,w,E,D,I,L){const{cross:A}=n,M=["INPUT","SELECT","TEXTAREA"],T={passive:!1},O=x(),F=x(),P=g(50,225).constrain(S.measure(20)),z={mouse:300,touch:400},R={mouse:500,touch:600},k=w?43:25;let B=!1,H=0,V=0,C=!1,N=!1,j=!1,G=!1;function q(n){const e=l.readPoint(n),r=l.readPoint(n,A),o=c(e,H),i=c(r,V);if(!N&&!G){if(!n.cancelable)return U(n);if(N=o>i,!N)return U(n)}const u=l.pointerMove(n);o>E&&(j=!0),h.useFriction(.3).useDuration(1),f.start(),a.add(t.apply(u)),n.preventDefault()}function U(n){const e=y.byDistance(0,!1).index!==v.get(),r=l.pointerUp(n)*(w?R:z)[G?"mouse":"touch"],u=function(n,t){const e=v.add(-1*i(n)),r=y.byDistance(n,!w).distance;return w||o(n)<P?r:D&&t?.5*r:y.byIndex(e.get(),0).distance}(t.apply(r),e),s=function(n,t){if(0===n||0===t)return 0;if(o(n)<=o(t))return 0;const e=c(o(n),o(t));return o(e/n)}(r,u),a=k-10*s,d=I+s/50;N=!1,C=!1,F.clear(),h.useDuration(a).useFriction(d),m.distance(u,!w),G=!1,b.emit("pointerUp")}function W(n){j&&(n.stopPropagation(),n.preventDefault())}return{init:function(n){if(!L)return;function t(t){(e(L)||L(n,t))&&function(n){const t=p(n,s);if(G=t,t&&0!==n.button)return;if(function(n){const t=n.nodeName||"";return M.includes(t)}(n.target))return;j=w&&t&&!n.buttons&&B,B=c(a.get(),d.get())>=2,C=!0,l.pointerDown(n),h.useFriction(0).useDuration(0),a.set(d),function(){const n=G?u:r;F.add(n,"touchmove",q,T).add(n,"touchend",U).add(n,"mousemove",q,T).add(n,"mouseup",U)}(),H=l.readPoint(n),V=l.readPoint(n,A),b.emit("pointerDown")}(t)}const o=r;O.add(o,"dragstart",(n=>n.preventDefault()),T).add(o,"touchmove",(()=>{}),T).add(o,"touchend",(()=>{})).add(o,"touchstart",t).add(o,"mousedown",t).add(o,"touchcancel",U).add(o,"contextmenu",U).add(o,"click",W,!0)},pointerDown:function(){return C},destroy:function(){O.clear(),F.clear()}}}function v(n,t){let e,r;function i(n){return n.timeStamp}function c(e,r){const o="client"+("x"===(r||n.scroll)?"X":"Y");return(p(e,t)?e:e.touches[0])[o]}return{pointerDown:function(n){return e=n,r=n,c(n)},pointerMove:function(n){const t=c(n)-c(r),o=i(n)-i(e)>170;return r=n,o&&(e=n),t},pointerUp:function(n){if(!e||!r)return 0;const t=c(r)-c(e),u=i(n)-i(e),s=i(n)-i(r)>170,a=t/u;return u&&!s&&o(a)>.1?a:0},readPoint:c}}function b(n,t,r,o,i,c){let u,s,a=[],l=!1;function d(n){return i.measureSize(n.getBoundingClientRect())}return{init:function(i){if(!c)return;s=d(n),a=o.map(d),u=new ResizeObserver((u=>{l||(e(c)||c(i,u))&&function(e){for(const c of e){const e=c.target===n,u=o.indexOf(c.target);if((e?s:a[u])!==d(e?n:o[u])){r.requestAnimationFrame((()=>{i.reInit(),t.emit("resize")}));break}}}(u)})),[n].concat(o).forEach((n=>u.observe(n)))},destroy:function(){u&&u.disconnect(),l=!0}}}function S(n,t,e,r,i){const c=i.measure(10),u=i.measure(50),s=g(.1,.99);let a=!1;return{constrain:function(i){if(a||!n.reachedAny(e.get())||!n.reachedAny(t.get()))return;const l=n.reachedMin(t.get())?"min":"max",d=o(n[l]-t.get()),f=e.get()-t.get(),p=s.constrain(d/u);e.subtract(f*p),!i&&o(f)<c&&(e.set(n.constrain(e.get())),r.useDuration(25).useBaseFriction())},toggleActive:function(n){a=!n}}}function w(n,t,e,r){const o=t.min+.1,i=t.max+.1,{reachedMin:c,reachedMax:u}=g(o,i);return{loop:function(t){if(!function(n){return 1===n?u(e.get()):-1===n&&c(e.get())}(t))return;const o=n*(-1*t);r.forEach((n=>n.add(o)))}}}function E(n,t,e,r,c){const{reachedAny:u,removeOffset:a,constrain:l}=r;function d(n){return n.concat().sort(((n,t)=>o(n)-o(t)))[0]}function f(t,r){const o=[t,t+e,t-e];if(!n)return o[0];if(!r)return d(o);const c=o.filter((n=>i(n)===r));return c.length?d(c):s(o)-e}return{byDistance:function(e,r){const i=c.get()+e,{index:s,distance:d}=function(e){const r=n?a(e):l(e),i=t.map((n=>n-r)).map((n=>f(n,0))).map(((n,t)=>({diff:n,index:t}))).sort(((n,t)=>o(n.diff)-o(t.diff))),{index:c}=i[0];return{index:c,distance:r}}(i),p=!n&&u(i);return!r||p?{index:s,distance:e}:{index:s,distance:e+f(t[s]-d,0)}},byIndex:function(n,e){return{index:n,distance:f(t[n]-c.get(),e)}},shortcut:f}}function D(t){let e=t;function r(t){return n(t)?t:t.get()}return{get:function(){return e},set:function(n){e=r(n)},add:function(n){e+=r(n)},subtract:function(n){e-=r(n)}}}function I(n,t,e){const r="x"===n.scroll?function(n){return`translate3d(${n}px,0px,0px)`}:function(n){return`translate3d(0px,${n}px,0px)`},o=e.style;let i=!1;return{clear:function(){i||(o.transform="",e.getAttribute("style")||e.removeAttribute("style"))},to:function(n){i||(o.transform=r(t.apply(n)))},toggleActive:function(n){i=!n}}}function L(n,t,e,r,o,i,c,s,a,l){const d=u(i),f=u(i).reverse(),p=function(){const n=s[0]-1;return h(g(f,n),r,!1)}().concat(function(){const n=e-s[0]-1;return h(g(d,n),-r,!0)}());function m(n,t){return n.reduce(((n,t)=>n-i[t]),t)}function g(n,t){return n.reduce(((n,e)=>m(n,t)>0?n.concat([e]):n),[])}function h(i,u,s){const d=function(n){return c.map(((t,r)=>({start:t-o[r]+.5+n,end:t+e-.5+n})))}(u);return i.map((e=>{const o=s?0:-r,i=s?r:0,c=s?"end":"start",u=d[e][c];return{index:e,slideLocation:D(-1),translate:I(n,t,l[e]),target:()=>a.get()>u?o:i}}))}return{canLoop:function(){return p.every((({index:n})=>m(d.filter((t=>t!==n)),e)<=.1))},clear:function(){p.forEach((n=>n.translate.clear()))},loop:function(){p.forEach((n=>{const{target:t,translate:e,slideLocation:r}=n,o=t();o!==r.get()&&(e.to(o),r.set(o))}))},loopPoints:p}}function A(n,t,r){let o,i=!1;return{init:function(c){r&&(o=new MutationObserver((n=>{i||(e(r)||r(c,n))&&function(n){for(const e of n)if("childList"===e.type){c.reInit(),t.emit("slidesChanged");break}}(n)})),o.observe(n,{childList:!0}))},destroy:function(){o&&o.disconnect(),i=!0}}}function M(n,t,e,r){const o={};let i,c=null,u=null,s=!1;return{init:function(){i=new IntersectionObserver((n=>{s||(n.forEach((n=>{const e=t.indexOf(n.target);o[e]=n})),c=null,u=null,e.emit("slidesInView"))}),{root:n.parentElement,threshold:r}),t.forEach((n=>i.observe(n)))},destroy:function(){i&&i.disconnect(),s=!0},get:function(n=!0){if(n&&c)return c;if(!n&&u)return u;const t=function(n){return d(o).reduce(((t,e)=>{const r=parseInt(e),{isIntersecting:i}=o[r];return(n&&i||!n&&!i)&&t.push(r),t}),[])}(n);return n&&(c=t),n||(u=t),t}}}function T(t,e,r,i,c,l,d,f,p){const{startEdge:m,endEdge:g}=t,h=n(i);return{groupSlides:function(n){return h?function(n,t){return u(n).filter((n=>n%t==0)).map((e=>n.slice(e,e+t)))}(n,i):function(n){return n.length?u(n).reduce(((t,i)=>{const u=s(t)||0,h=0===u,x=i===a(n),y=l[m]-d[u][m],v=l[m]-d[i][g],b=!c&&h?e.apply(f):0;return o(v-(!c&&x?e.apply(p):0)-(y+b))>r&&t.push(i),x&&t.push(n.length),t}),[]).map(((t,e,r)=>{const o=Math.max(r[e-1]||0);return n.slice(o,t)})):[]}(n)}}}function O(t,e,r,c,d,f,p,O){const{align:F,axis:P,direction:z,startIndex:R,loop:k,duration:B,dragFree:H,dragThreshold:V,inViewThreshold:C,slidesToScroll:N,skipSnaps:j,containScroll:G,watchResize:q,watchSlides:U,watchDrag:W}=f,$=e.getBoundingClientRect(),Q=r.map((n=>n.getBoundingClientRect())),X=function(n){const t="rtl"===n?-1:1;return{apply:function(n){return n*t}}}(z),Y=function(n,t){const e="y"===n?"y":"x";return{scroll:e,cross:"y"===n?"x":"y",startEdge:"y"===e?"top":"rtl"===t?"right":"left",endEdge:"y"===e?"bottom":"rtl"===t?"left":"right",measureSize:function(n){const{width:t,height:r}=n;return"x"===e?t:r}}}(P,z),J=Y.measureSize($),K=function(n){return{measure:function(t){return n*(t/100)}}}(J),Z=m(F,J),_=!k&&!!G,nn=k||!!G,{slideSizes:tn,slideSizesWithGaps:en,startGap:rn,endGap:on}=function(n,t,e,r,i,c){const{measureSize:u,startEdge:l,endEdge:d}=n,f=e[0]&&i,p=function(){if(!f)return 0;const n=e[0];return o(t[l]-n[l])}(),m=function(){if(!f)return 0;const n=c.getComputedStyle(s(r));return parseFloat(n.getPropertyValue(`margin-${d}`))}(),g=e.map(u),h=e.map(((n,t,e)=>{const r=!t,o=t===a(e);return r?g[t]+p:o?g[t]+m:e[t+1][l]-n[l]})).map(o);return{slideSizes:g,slideSizesWithGaps:h,startGap:p,endGap:m}}(Y,$,Q,r,nn,d),cn=T(Y,X,J,N,k,$,Q,rn,on),{snaps:un,snapsAligned:sn}=function(n,t,e,r,i){const{startEdge:c,endEdge:u}=n,{groupSlides:a}=i,l=a(r).map((n=>s(n)[u]-n[0][c])).map(o).map(t.measure),d=r.map((n=>e[c]-n[c])).map((n=>-o(n))),f=a(d).map((n=>n[0])).map(((n,t)=>n+l[t]));return{snaps:d,snapsAligned:f}}(Y,Z,$,Q,cn),an=-s(un)+s(en),{snapsContained:ln,scrollContainLimit:dn}=function(n,t,e,r){const o=g(-t+n,0),i=e.map(o.constrain).map((n=>parseFloat(n.toFixed(3)))),c=function(){const n=i[0],t=s(i);return g(i.lastIndexOf(n),i.indexOf(t)+1)}();return{snapsContained:function(){if(t<=n)return[o.max];if("keepSnaps"===r)return i;const{min:e,max:u}=c;return i.slice(e,u)}(),scrollContainLimit:c}}(J,an,sn,G),fn=_?ln:sn,{limit:pn}=function(n,t,e){const r=t[0];return{limit:g(e?r-n:s(t),r)}}(an,fn,k),mn=h(a(fn),R,k),gn=mn.clone(),hn=u(r),xn={start:()=>O.start(On),stop:()=>O.stop(On),update:()=>(({dragHandler:n,scrollBody:t,scrollBounds:e,eventHandler:r,animation:o,options:{loop:i}})=>{const c=n.pointerDown();i||e.constrain(c);const u=t.seek().settled();u&&!c&&(o.stop(),r.emit("settle")),u||r.emit("scroll")})(On),render:n=>(({scrollBody:n,translate:t,location:e,offsetLocation:r,scrollLooper:o,slideLooper:i,options:{loop:c}},u)=>{const s=n.velocity();r.set(e.get()-s+s*u),c&&(o.loop(n.direction()),i.loop()),t.to(r.get())})(On,n)},yn=fn[mn.get()],vn=D(yn),bn=D(yn),Sn=D(yn),wn=function(n,t,e,r){let c=!0,u=0,s=0,a=e,l=r,d=n.get(),f=0;function p(n){return a=n,g}function m(n){return l=n,g}const g={direction:function(){return s},duration:function(){return a},velocity:function(){return u},seek:function(){const e=t.get()-n.get();let r=0;return a?(u+=e/a,u*=l,d+=u,n.add(u),r=d-f):(u=0,n.set(t),r=e),s=i(r),f=d,c=o(e)<.001,g},settled:function(){return c},useBaseFriction:function(){return m(r)},useBaseDuration:function(){return p(e)},useFriction:m,useDuration:p};return g}(vn,Sn,B,.68),En=E(k,fn,an,pn,Sn),Dn=function(n,t,e,r,o,i,c){function u(r){const u=r.distance,s=r.index!==t.get();i.add(u),u&&(o.duration()?n.start():(n.update(),n.render(1),n.update())),s&&(e.set(t.get()),t.set(r.index),c.emit("select"))}return{distance:function(n,t){u(r.byDistance(n,t))},index:function(n,e){const o=t.clone().set(n);u(r.byIndex(o.get(),e))}}}(xn,mn,gn,En,wn,Sn,p),In=function(n){const{max:t,length:e}=n;return{get:function(n){return e?(n-t)/-e:0}}}(pn),Ln=x(),An=M(e,r,p,C),{slideRegistry:Mn}=function(n,t,e,r,o,i){const{groupSlides:c}=o,{min:u,max:d}=r;return{slideRegistry:function(){const r=c(i);return!e||t<=n?r:r.slice(u,d).map(((n,t,e)=>{const r=!t,o=!r&&t===a(e);return r?l(s(e[0])+1):o?l(a(i)-s(e)[0]+1,s(e)[0]):n}))}()}}(J,an,_,dn,cn,hn),Tn=function(t,e,r,o,i,c){let u=0;function s(n){"Tab"===n.code&&(u=(new Date).getTime())}function a(s){c.add(s,"focus",(()=>{if((new Date).getTime()-u>10)return;t.scrollLeft=0;const c=e.indexOf(s),a=r.findIndex((n=>n.includes(c)));n(a)&&(i.useDuration(0),o.index(a,0))}),{passive:!0,capture:!0})}return{init:function(){c.add(document,"keydown",s,!1),e.forEach(a)}}}(t,r,Mn,Dn,wn,Ln),On={ownerDocument:c,ownerWindow:d,eventHandler:p,containerRect:$,slideRects:Q,animation:xn,axis:Y,direction:X,dragHandler:y(Y,X,t,c,d,Sn,v(Y,d),vn,xn,Dn,wn,En,mn,p,K,H,V,j,.68,W),eventStore:Ln,percentOfView:K,index:mn,indexPrevious:gn,limit:pn,location:vn,offsetLocation:bn,options:f,resizeHandler:b(e,p,d,r,Y,q),scrollBody:wn,scrollBounds:S(pn,vn,Sn,wn,K),scrollLooper:w(an,pn,bn,[vn,bn,Sn]),scrollProgress:In,scrollSnapList:fn.map(In.get),scrollSnaps:fn,scrollTarget:En,scrollTo:Dn,slideLooper:L(Y,X,J,an,tn,en,un,fn,bn,r),slideFocus:Tn,slidesHandler:A(e,p,U),slidesInView:An,slideIndexes:hn,slideRegistry:Mn,slidesToScroll:cn,target:Sn,translate:I(Y,X,e)};return On}const F={align:"center",axis:"x",container:null,slides:null,containScroll:"trimSnaps",direction:"ltr",slidesToScroll:1,inViewThreshold:0,breakpoints:{},dragFree:!1,dragThreshold:10,loop:!1,skipSnaps:!1,duration:25,startIndex:0,active:!0,watchDrag:!0,watchResize:!0,watchSlides:!0};function P(n){function t(n,t){return f(n,t||{})}const e={mergeOptions:t,optionsAtMedia:function(e){const r=e.breakpoints||{},o=d(r).filter((t=>n.matchMedia(t).matches)).map((n=>r[n])).reduce(((n,e)=>t(n,e)),{});return t(e,o)},optionsMediaQueries:function(t){return t.map((n=>d(n.breakpoints||{}))).reduce(((n,t)=>n.concat(t)),[]).map(n.matchMedia)}};return e}function z(n,e,r){const i=n.ownerDocument,c=i.defaultView,u=P(c),s=function(n){let t=[];return{init:function(e,r){return t=r.filter((({options:t})=>!1!==n.optionsAtMedia(t).active)),t.forEach((t=>t.init(e,n))),r.reduce(((n,t)=>Object.assign(n,{[t.name]:t})),{})},destroy:function(){t=t.filter((n=>n.destroy()))}}}(u),a=x(),l=x(),d=function(){const n={};let t;function e(t){return n[t]||[]}const r={init:function(n){t=n},emit:function(n){return e(n).forEach((e=>e(t,n))),r},off:function(t,o){return n[t]=e(t).filter((n=>n!==o)),r},on:function(t,o){return n[t]=e(t).concat([o]),r}};return r}(),{animationRealms:f}=z,{mergeOptions:p,optionsAtMedia:m,optionsMediaQueries:g}=u,{on:h,off:y,emit:v}=d,b=k;let S,w,E,D,I=!1,L=p(F,z.globalOptions),A=p(L),M=[];function T(t,e){const r=O(n,E,D,i,c,t,d,e);if(t.loop&&!r.slideLooper.canLoop()){return T(Object.assign({},t,{loop:!1}),e)}return r}function R(e,r){if(I)return;const u=f.find((n=>n.window===c)),d=u||function(n){const t=1e3/60;let e=[],r=null,i=0,c=0;function u(s){r||(r=s);const a=s-r;for(r=s,i+=a;i>=t;)e.forEach((({animation:n})=>n.update())),i-=t;const l=o(i/t);e.forEach((({animation:n})=>n.render(l))),c&&n.requestAnimationFrame(u)}return{start:function(t){e.includes(t)||e.push(t),c||(c=n.requestAnimationFrame(u))},stop:function(t){e=e.filter((n=>n!==t)),e.length||(n.cancelAnimationFrame(c),r=null,i=0,c=0)},reset:function(){r=null,i=0},window:n}}(c);u||f.push(d),L=p(L,e),A=m(L),M=r||M,function(){const{container:e,slides:r}=A,o=t(e)?n.querySelector(e):e;E=o||n.children[0];const i=t(r)?E.querySelectorAll(r):r;D=[].slice.call(i||E.children)}(),S=T(A,d),g([L,...M.map((({options:n})=>n))]).forEach((n=>a.add(n,"change",k))),A.active&&(S.translate.to(S.location.get()),S.slidesInView.init(),S.slideFocus.init(),S.eventHandler.init(C),S.resizeHandler.init(C),S.slidesHandler.init(C),l.add(i,"visibilitychange",(()=>{i.hidden&&d.reset()})),S.options.loop&&S.slideLooper.loop(),E.offsetParent&&D.length&&S.dragHandler.init(C),w=s.init(C,M))}function k(n,t){const e=V();B(),R(p({startIndex:e},n),t),d.emit("reInit")}function B(){S.dragHandler.destroy(),S.animation.stop(),S.eventStore.clear(),S.translate.clear(),S.slideLooper.clear(),S.resizeHandler.destroy(),S.slidesHandler.destroy(),s.destroy(),a.clear(),l.clear()}function H(n,t,e){A.active&&!I&&(S.scrollBody.useBaseFriction().useDuration(t?0:A.duration),S.scrollTo.index(n,e||0))}function V(){return S.index.get()}const C={canScrollNext:function(){return S.index.add(1).get()!==V()},canScrollPrev:function(){return S.index.add(-1).get()!==V()},containerNode:function(){return E},internalEngine:function(){return S},destroy:function(){I||(I=!0,a.clear(),B(),d.emit("destroy"))},off:y,on:h,emit:v,plugins:function(){return w},previousScrollSnap:function(){return S.indexPrevious.get()},reInit:b,rootNode:function(){return n},scrollNext:function(n){H(S.index.add(1).get(),!0===n,-1)},scrollPrev:function(n){H(S.index.add(-1).get(),!0===n,1)},scrollProgress:function(){return S.scrollProgress.get(S.location.get())},scrollSnapList:function(){return S.scrollSnapList},scrollTo:H,selectedScrollSnap:V,slideNodes:function(){return D},slidesInView:function(){return S.slidesInView.get()},slidesNotInView:function(){return S.slidesInView.get(!1)}};return R(e,r),setTimeout((()=>d.emit("init")),0),C}return z.animationRealms=[],z.globalOptions=void 0,z})); |
{ | ||
"name": "embla-carousel", | ||
"version": "8.0.0-rc11", | ||
"version": "8.0.0-rc12", | ||
"author": "David Jerleke", | ||
@@ -5,0 +5,0 @@ "description": "A lightweight carousel library with fluid motion and great swipe precision", |
@@ -9,7 +9,7 @@ <br /> | ||
<p align="center"> | ||
<a href="https://opensource.org/licenses/MIT"><img src="https://img.shields.io/npm/l/embla-carousel?color=%238ab4f8"></a> | ||
<a href="https://www.npmjs.com/package/embla-carousel"><img src="https://img.shields.io/npm/v/embla-carousel.svg?color=%23c1a8e2"></a> | ||
<a href="https://github.com/davidjerleke/embla-carousel/actions?query=workflow%3A%22Continuous+Integration%22"><img src="https://img.shields.io/github/actions/workflow/status/davidjerleke/embla-carousel/cd.yml?color=%238ab4f8"></a> | ||
<a href="https://prettier.io"><img src="https://img.shields.io/badge/code_style-prettier-ff69b4.svg?style=flat&color=%23c1a8e2"></a> | ||
<a href="https://bundlephobia.com/result?p=embla-carousel@latest"><img src="https://img.shields.io/bundlephobia/minzip/embla-carousel?color=%238ab4f8&label=gzip%20size"> | ||
<a href="https://opensource.org/licenses/MIT"><img src="https://img.shields.io/npm/l/embla-carousel?color=%238ab4f8&style=flat-square"></a> | ||
<a href="https://www.npmjs.com/package/embla-carousel"><img src="https://img.shields.io/npm/v/embla-carousel.svg?color=%23c1a8e2&style=flat-square"></a> | ||
<a href="https://github.com/davidjerleke/embla-carousel/actions?query=workflow%3A%22Continuous+Integration%22"><img src="https://img.shields.io/github/actions/workflow/status/davidjerleke/embla-carousel/cd.yml?color=%238ab4f8&style=flat-square"></a> | ||
<a href="https://prettier.io"><img src="https://img.shields.io/badge/code_style-prettier-ff69b4.svg?color=%23c1a8e2&style=flat-square"></a> | ||
<a href="https://bundlephobia.com/result?p=embla-carousel@latest"><img src="https://img.shields.io/bundlephobia/minzip/embla-carousel?color=%238ab4f8&style=flat-square&label=gzip%20size"> | ||
</a> | ||
@@ -23,3 +23,3 @@ </p> | ||
<p align="center"> | ||
<a href="https://www.embla-carousel.com/">Embla Carousel</a> is a bare bones carousel library with great fluid motion and awesome swipe precision. It's library agnostic, dependency free and 100% open source. Build awesome carousels by extending Embla Carousel with your own CSS and JavaScript. | ||
<strong>Embla Carousel</strong> is a bare bones carousel library with great fluid motion and awesome swipe precision. It's library agnostic, dependency free and 100% open source. | ||
</p> | ||
@@ -31,3 +31,3 @@ | ||
<strong> | ||
<code> <a href="https://www.embla-carousel.com/get-started/#choose-installation-type">Installation</a> </code> | ||
<code> <a href="https://www.embla-carousel.com/examples/predefined/">Examples</a> </code> | ||
</strong> | ||
@@ -38,3 +38,3 @@ </p> | ||
<strong> | ||
<code> <a href="https://www.embla-carousel.com/api/">API Reference</a> </code> | ||
<code> <a href="https://www.embla-carousel.com/examples/generator/">Generator</a> </code> | ||
</strong> | ||
@@ -45,3 +45,3 @@ </p> | ||
<strong> | ||
<code> <a href="https://www.embla-carousel.com/examples/static/">Examples</a> </code> | ||
<code> <a href="https://www.embla-carousel.com/get-started/#choose-installation-type">Installation</a> </code> | ||
</strong> | ||
@@ -55,19 +55,24 @@ </p> | ||
<strong> | ||
<h2 align="center">Platforms</h2> | ||
<h2 align="center">Ready for</h2> | ||
</strong> | ||
<p align="center"> | ||
<a href="https://www.embla-carousel.com/">Embla Carousel</a> is ready to use with the following tools/libraries. | ||
</p> | ||
<p align="center"> | ||
<a href="https://www.embla-carousel.com/get-started/module/"> | ||
<img src="https://www.embla-carousel.com/javascript-logo.svg" width="45" height="45" /> | ||
<img src="https://www.embla-carousel.com/javascript-logo.svg" width="40" height="40" /> | ||
</a> | ||
| ||
<a href="https://www.embla-carousel.com/get-started/module/"> | ||
<img src="https://www.embla-carousel.com/typescript-logo.svg" width="45" height="45" /> | ||
<img src="https://www.embla-carousel.com/typescript-logo.svg" width="40" height="40" /> | ||
</a> | ||
| ||
<a href="https://www.embla-carousel.com/get-started/react/"> | ||
<img src="https://www.embla-carousel.com/react-logo.svg" width="45" height="45" /> | ||
<img src="https://www.embla-carousel.com/react-logo.svg" width="40" height="40" /> | ||
</a> | ||
| ||
<a href="https://www.embla-carousel.com/get-started/vue/"> | ||
<img src="https://www.embla-carousel.com/vue-logo.svg" width="40" height="40" /> | ||
| ||
<a href="https://www.embla-carousel.com/get-started/svelte/"> | ||
<img src="https://www.embla-carousel.com/svelte-logo.svg" width="40" height="40" /> | ||
</a> | ||
</p> | ||
@@ -86,19 +91,25 @@ </div> | ||
<p align="center"> | ||
<a href="https://github.com/nikrowell"><img src="https://avatars2.githubusercontent.com/u/260039?s=120&v=4" title="nikrowell" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/michaelrambeau"><img src="https://avatars0.githubusercontent.com/u/5546996?s=120&v=4" title="michaelrambeau" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/ehellman"><img src="https://avatars3.githubusercontent.com/u/586152?s=120&v=4" title="ehellman" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/afilp"><img src="https://avatars0.githubusercontent.com/u/7850073?s=120&v=4" title="afilp" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/mrksmts"><img src="https://avatars1.githubusercontent.com/u/437794?s=120&v=4" title="mrksmts" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/SLMNBJ"><img src="https://avatars2.githubusercontent.com/u/30017004?s=120&v=4" title="SLMNBJ" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/readeral"><img src="https://avatars0.githubusercontent.com/u/15904136?s=120&v=4" title="readeral" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/romellem"><img src="https://avatars2.githubusercontent.com/u/8504000?s=120&v=4" title="romellem" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/niubsta"><img src="https://avatars0.githubusercontent.com/u/270320?s=120&v=4" title="niubsta" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/allen-garvey"><img src="https://avatars1.githubusercontent.com/u/9314727?s=120s&v=4" title="allen-garvey" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/sedlukha"><img src="https://avatars3.githubusercontent.com/u/14075940?s=120&v=4" title="sedlukha" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/wopian"><img src="https://avatars3.githubusercontent.com/u/3440094?s=120&v=4" title="wopian" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/msallent"><img src="https://avatars3.githubusercontent.com/u/8879212?s=120&v=4" title="msallent" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/omarkhatibco"><img src="https://avatars1.githubusercontent.com/u/9054278?s=120&v=4" title="omarkhatibco" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/ppromerojr"><img src="https://avatars1.githubusercontent.com/u/15343254?s=120&v=4" title="ppromerojr" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/openscript"><img src="https://avatars3.githubusercontent.com/u/1105080?s=120&v=4" title="openscript" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/nikrowell"><img src="https://avatars2.githubusercontent.com/u/260039?s=120&v=4" title="nikrowell" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/michaelrambeau"><img src="https://avatars0.githubusercontent.com/u/5546996?s=120&v=4" title="michaelrambeau" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/ehellman"><img src="https://avatars3.githubusercontent.com/u/586152?s=120&v=4" title="ehellman" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/afilp"><img src="https://avatars0.githubusercontent.com/u/7850073?s=120&v=4" title="afilp" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/mrksmts"><img src="https://avatars1.githubusercontent.com/u/437794?s=120&v=4" title="mrksmts" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/SLMNBJ"><img src="https://avatars2.githubusercontent.com/u/30017004?s=120&v=4" title="SLMNBJ" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/readeral"><img src="https://avatars0.githubusercontent.com/u/15904136?s=120&v=4" title="readeral" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/romellem"><img src="https://avatars2.githubusercontent.com/u/8504000?s=120&v=4" title="romellem" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/niubsta"><img src="https://avatars0.githubusercontent.com/u/270320?s=120&v=4" title="niubsta" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/allen-garvey"><img src="https://avatars1.githubusercontent.com/u/9314727?s=120s&v=4" title="allen-garvey" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/sedlukha"><img src="https://avatars3.githubusercontent.com/u/14075940?s=120&v=4" title="sedlukha" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/wopian"><img src="https://avatars3.githubusercontent.com/u/3440094?s=120&v=4" title="wopian" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/msallent"><img src="https://avatars3.githubusercontent.com/u/8879212?s=120&v=4" title="msallent" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/omarkhatibco"><img src="https://avatars1.githubusercontent.com/u/9054278?s=120&v=4" title="omarkhatibco" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/ppromerojr"><img src="https://avatars1.githubusercontent.com/u/15343254?s=120&v=4" title="ppromerojr" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/openscript"><img src="https://avatars3.githubusercontent.com/u/1105080?s=120&v=4" title="openscript" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/pipisasa"><img src="https://avatars.githubusercontent.com/u/54534600?s=120&v=4" title="pipisasa" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/silllli"><img src="https://avatars.githubusercontent.com/u/9334305?s=120&v=4" title="silllli" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/JoshuaCrewe"><img src="https://avatars.githubusercontent.com/u/12238901?s=120&v=4" title="JoshuaCrewe" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/th-km"><img src="https://avatars.githubusercontent.com/u/35410212?s=120&v=4" title="th-km" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/rojadesign"><img src="https://avatars.githubusercontent.com/u/35687281?s=120&v=4" title="th-km"" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/SaizFerri"><img src="https://avatars.githubusercontent.com/u/19834971?s=120&v=4" title="SaizFerri" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/horseeyephil"><img src="https://avatars.githubusercontent.com/u/32337092?s=120&v=4" title="horseeyephil" width="50" height="50" style="max-width:100%;"></a> | ||
</p> | ||
@@ -117,4 +128,4 @@ </div> | ||
<p align="center"> | ||
<a href="https://github.com/gunnarx2"><img src="https://avatars2.githubusercontent.com/u/10469652?s=120&v=4" title="gunnarx2" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/xiel"><img src="https://avatars0.githubusercontent.com/u/615522?s=120&v=4" title="xiel" width="60" height="60" style="max-width:100%;"></a> | ||
<a href="https://github.com/gunnarx2"><img src="https://avatars2.githubusercontent.com/u/10469652?s=120&v=4" title="gunnarx2" width="50" height="50" style="max-width:100%;"></a> | ||
<a href="https://github.com/xiel"><img src="https://avatars0.githubusercontent.com/u/615522?s=120&v=4" title="xiel" width="50" height="50" style="max-width:100%;"></a> | ||
</p> | ||
@@ -121,0 +132,0 @@ </div> |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
145769
45
3661
148