domet 1.0.1 → 1.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,19 +1,28 @@
1
- import { useCallback, useEffect, useLayoutEffect, useMemo, useRef, useState, } from "react";
1
+ Object.defineProperty(exports, '__esModule', { value: true });
2
+
3
+ var react = require('react');
4
+
2
5
  const DEFAULT_VISIBILITY_THRESHOLD = 0.6;
3
6
  const DEFAULT_HYSTERESIS_MARGIN = 150;
4
7
  const SCROLL_IDLE_MS = 100;
5
- const useIsomorphicLayoutEffect = typeof window !== "undefined" ? useLayoutEffect : useEffect;
6
- export function useDomet(sectionIds, containerRef = null, options = {}) {
7
- const { offset = 0, offsetRatio = 0.08, debounceMs = 10, visibilityThreshold = DEFAULT_VISIBILITY_THRESHOLD, hysteresisMargin = DEFAULT_HYSTERESIS_MARGIN, behavior = "auto", onActiveChange, onSectionEnter, onSectionLeave, onScrollStart, onScrollEnd, } = options;
8
- const _sectionIdsKey = JSON.stringify(sectionIds);
9
- const stableSectionIds = useMemo(() => sectionIds, [sectionIds]);
10
- const sectionIndexMap = useMemo(() => {
8
+ const useIsomorphicLayoutEffect = typeof window !== "undefined" ? react.useLayoutEffect : react.useEffect;
9
+ function useDomet(sectionIds, containerRef = null, options = {}) {
10
+ const { offset = 0, offsetRatio = 0.08, debounceMs = 10, visibilityThreshold = DEFAULT_VISIBILITY_THRESHOLD, hysteresisMargin = DEFAULT_HYSTERESIS_MARGIN, behavior = "auto", onActiveChange, onSectionEnter, onSectionLeave, onScrollStart, onScrollEnd } = options;
11
+ JSON.stringify(sectionIds);
12
+ const stableSectionIds = react.useMemo(()=>sectionIds, [
13
+ sectionIds
14
+ ]);
15
+ const sectionIndexMap = react.useMemo(()=>{
11
16
  const map = new Map();
12
- stableSectionIds.forEach((id, i) => map.set(id, i));
17
+ for(let i = 0; i < stableSectionIds.length; i++){
18
+ map.set(stableSectionIds[i], i);
19
+ }
13
20
  return map;
14
- }, [stableSectionIds]);
15
- const [activeId, setActiveId] = useState(stableSectionIds[0] || null);
16
- const [scroll, setScroll] = useState({
21
+ }, [
22
+ stableSectionIds
23
+ ]);
24
+ const [activeId, setActiveId] = react.useState(stableSectionIds[0] || null);
25
+ const [scroll, setScroll] = react.useState({
17
26
  y: 0,
18
27
  progress: 0,
19
28
  direction: null,
@@ -21,74 +30,79 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
21
30
  isScrolling: false,
22
31
  maxScroll: 0,
23
32
  viewportHeight: 0,
24
- offset: 0,
33
+ offset: 0
25
34
  });
26
- const [sections, setSections] = useState({});
27
- const [containerElement, setContainerElement] = useState(null);
28
- const refs = useRef({});
29
- const refCallbacks = useRef({});
30
- const activeIdRef = useRef(stableSectionIds[0] || null);
31
- const lastScrollY = useRef(0);
32
- const lastScrollTime = useRef(Date.now());
33
- const rafId = useRef(null);
34
- const isThrottled = useRef(false);
35
- const throttleTimeoutId = useRef(null);
36
- const hasPendingScroll = useRef(false);
37
- const isProgrammaticScrolling = useRef(false);
38
- const programmaticScrollTimeoutId = useRef(null);
39
- const isScrollingRef = useRef(false);
40
- const scrollIdleTimeoutRef = useRef(null);
41
- const prevSectionsInViewport = useRef(new Set());
42
- const recalculateRef = useRef(() => { });
43
- const scrollCleanupRef = useRef(null);
44
- const callbackRefs = useRef({
35
+ const [sections, setSections] = react.useState({});
36
+ const [containerElement, setContainerElement] = react.useState(null);
37
+ const refs = react.useRef({});
38
+ const refCallbacks = react.useRef({});
39
+ const activeIdRef = react.useRef(stableSectionIds[0] || null);
40
+ const lastScrollY = react.useRef(0);
41
+ const lastScrollTime = react.useRef(Date.now());
42
+ const rafId = react.useRef(null);
43
+ const isThrottled = react.useRef(false);
44
+ const throttleTimeoutId = react.useRef(null);
45
+ const hasPendingScroll = react.useRef(false);
46
+ const isProgrammaticScrolling = react.useRef(false);
47
+ const programmaticScrollTimeoutId = react.useRef(null);
48
+ const isScrollingRef = react.useRef(false);
49
+ const scrollIdleTimeoutRef = react.useRef(null);
50
+ const prevSectionsInViewport = react.useRef(new Set());
51
+ const recalculateRef = react.useRef(()=>{});
52
+ const scrollCleanupRef = react.useRef(null);
53
+ const callbackRefs = react.useRef({
45
54
  onActiveChange,
46
55
  onSectionEnter,
47
56
  onSectionLeave,
48
57
  onScrollStart,
49
- onScrollEnd,
58
+ onScrollEnd
50
59
  });
51
60
  callbackRefs.current = {
52
61
  onActiveChange,
53
62
  onSectionEnter,
54
63
  onSectionLeave,
55
64
  onScrollStart,
56
- onScrollEnd,
65
+ onScrollEnd
57
66
  };
58
- const getEffectiveOffset = useCallback(() => {
67
+ const getEffectiveOffset = react.useCallback(()=>{
59
68
  return offset;
60
- }, [offset]);
61
- const getScrollBehavior = useCallback(() => {
69
+ }, [
70
+ offset
71
+ ]);
72
+ const getScrollBehavior = react.useCallback(()=>{
62
73
  if (behavior === "auto") {
63
- if (typeof window === "undefined")
64
- return "instant";
74
+ if (typeof window === "undefined") return "instant";
65
75
  const prefersReducedMotion = window.matchMedia("(prefers-reduced-motion: reduce)").matches;
66
76
  return prefersReducedMotion ? "instant" : "smooth";
67
77
  }
68
78
  return behavior;
69
- }, [behavior]);
70
- useIsomorphicLayoutEffect(() => {
71
- const nextContainer = containerRef?.current ?? null;
79
+ }, [
80
+ behavior
81
+ ]);
82
+ useIsomorphicLayoutEffect(()=>{
83
+ var _ref;
84
+ const nextContainer = (_ref = containerRef == null ? void 0 : containerRef.current) != null ? _ref : null;
72
85
  if (nextContainer !== containerElement) {
73
86
  setContainerElement(nextContainer);
74
87
  }
75
- }, [containerRef, containerElement]);
76
- const registerRef = useCallback((id) => {
88
+ }, [
89
+ containerRef,
90
+ containerElement
91
+ ]);
92
+ const registerRef = react.useCallback((id)=>{
77
93
  const existing = refCallbacks.current[id];
78
- if (existing)
79
- return existing;
80
- const callback = (el) => {
94
+ if (existing) return existing;
95
+ const callback = (el)=>{
81
96
  if (el) {
82
97
  refs.current[id] = el;
83
- }
84
- else {
98
+ } else {
85
99
  delete refs.current[id];
86
100
  }
87
101
  };
88
102
  refCallbacks.current[id] = callback;
89
103
  return callback;
90
104
  }, []);
91
- const scrollToSection = useCallback((id) => {
105
+ const scrollToSection = react.useCallback((id)=>{
92
106
  if (!stableSectionIds.includes(id)) {
93
107
  if (process.env.NODE_ENV !== "production") {
94
108
  console.warn(`[domet] scrollToSection: id "${id}" not in sectionIds`);
@@ -96,12 +110,11 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
96
110
  return;
97
111
  }
98
112
  const element = refs.current[id];
99
- if (!element)
100
- return;
113
+ if (!element) return;
101
114
  if (programmaticScrollTimeoutId.current) {
102
115
  clearTimeout(programmaticScrollTimeoutId.current);
103
116
  }
104
- scrollCleanupRef.current?.();
117
+ scrollCleanupRef.current == null ? void 0 : scrollCleanupRef.current.call(scrollCleanupRef);
105
118
  isProgrammaticScrolling.current = true;
106
119
  activeIdRef.current = id;
107
120
  setActiveId(id);
@@ -109,19 +122,19 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
109
122
  const elementRect = element.getBoundingClientRect();
110
123
  const effectiveOffset = getEffectiveOffset() + 10;
111
124
  const scrollTarget = container || window;
112
- const unlockScroll = () => {
125
+ const unlockScroll = ()=>{
113
126
  isProgrammaticScrolling.current = false;
114
127
  if (programmaticScrollTimeoutId.current) {
115
128
  clearTimeout(programmaticScrollTimeoutId.current);
116
129
  programmaticScrollTimeoutId.current = null;
117
130
  }
118
- requestAnimationFrame(() => {
131
+ requestAnimationFrame(()=>{
119
132
  recalculateRef.current();
120
133
  });
121
134
  };
122
135
  let debounceTimer = null;
123
136
  let isUnlocked = false;
124
- const cleanup = () => {
137
+ const cleanup = ()=>{
125
138
  if (debounceTimer) {
126
139
  clearTimeout(debounceTimer);
127
140
  debounceTimer = null;
@@ -132,31 +145,30 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
132
145
  }
133
146
  scrollCleanupRef.current = null;
134
147
  };
135
- const doUnlock = () => {
136
- if (isUnlocked)
137
- return;
148
+ const doUnlock = ()=>{
149
+ if (isUnlocked) return;
138
150
  isUnlocked = true;
139
151
  cleanup();
140
152
  unlockScroll();
141
153
  };
142
- const resetDebounce = () => {
154
+ const resetDebounce = ()=>{
143
155
  if (debounceTimer) {
144
156
  clearTimeout(debounceTimer);
145
157
  }
146
158
  debounceTimer = setTimeout(doUnlock, SCROLL_IDLE_MS);
147
159
  };
148
- const handleScrollActivity = () => {
160
+ const handleScrollActivity = ()=>{
149
161
  resetDebounce();
150
162
  };
151
- const handleScrollEnd = () => {
163
+ const handleScrollEnd = ()=>{
152
164
  doUnlock();
153
165
  };
154
166
  scrollTarget.addEventListener("scroll", handleScrollActivity, {
155
- passive: true,
167
+ passive: true
156
168
  });
157
169
  if ("onscrollend" in scrollTarget) {
158
170
  scrollTarget.addEventListener("scrollend", handleScrollEnd, {
159
- once: true,
171
+ once: true
160
172
  });
161
173
  }
162
174
  scrollCleanupRef.current = cleanup;
@@ -166,121 +178,117 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
166
178
  const relativeTop = elementRect.top - containerRect.top + container.scrollTop;
167
179
  container.scrollTo({
168
180
  top: relativeTop - effectiveOffset,
169
- behavior: scrollBehavior,
181
+ behavior: scrollBehavior
170
182
  });
171
- }
172
- else {
183
+ } else {
173
184
  const absoluteTop = elementRect.top + window.scrollY;
174
185
  window.scrollTo({
175
186
  top: absoluteTop - effectiveOffset,
176
- behavior: scrollBehavior,
187
+ behavior: scrollBehavior
177
188
  });
178
189
  }
179
190
  if (scrollBehavior === "instant") {
180
191
  doUnlock();
181
- }
182
- else {
192
+ } else {
183
193
  resetDebounce();
184
194
  }
185
- }, [stableSectionIds, containerElement, getEffectiveOffset, getScrollBehavior]);
186
- const sectionProps = useCallback((id) => ({
187
- id,
188
- ref: registerRef(id),
189
- "data-domet": id,
190
- }), [registerRef]);
191
- const navProps = useCallback((id) => ({
192
- onClick: () => scrollToSection(id),
193
- "aria-current": activeId === id ? "page" : undefined,
194
- "data-active": activeId === id,
195
- }), [activeId, scrollToSection]);
196
- useEffect(() => {
195
+ }, [
196
+ stableSectionIds,
197
+ containerElement,
198
+ getEffectiveOffset,
199
+ getScrollBehavior
200
+ ]);
201
+ const sectionProps = react.useCallback((id)=>({
202
+ id,
203
+ ref: registerRef(id),
204
+ "data-domet": id
205
+ }), [
206
+ registerRef
207
+ ]);
208
+ const navProps = react.useCallback((id)=>({
209
+ onClick: ()=>scrollToSection(id),
210
+ "aria-current": activeId === id ? "page" : undefined,
211
+ "data-active": activeId === id
212
+ }), [
213
+ activeId,
214
+ scrollToSection
215
+ ]);
216
+ react.useEffect(()=>{
217
+ var _stableSectionIds_;
197
218
  const idsSet = new Set(stableSectionIds);
198
- for (const id of Object.keys(refs.current)) {
219
+ for (const id of Object.keys(refs.current)){
199
220
  if (!idsSet.has(id)) {
200
221
  delete refs.current[id];
201
222
  }
202
223
  }
203
- for (const id of Object.keys(refCallbacks.current)) {
224
+ for (const id of Object.keys(refCallbacks.current)){
204
225
  if (!idsSet.has(id)) {
205
226
  delete refCallbacks.current[id];
206
227
  }
207
228
  }
208
229
  const currentActive = activeIdRef.current;
209
- const nextActive = currentActive && idsSet.has(currentActive)
210
- ? currentActive
211
- : (stableSectionIds[0] ?? null);
230
+ const nextActive = currentActive && idsSet.has(currentActive) ? currentActive : (_stableSectionIds_ = stableSectionIds[0]) != null ? _stableSectionIds_ : null;
212
231
  if (nextActive !== currentActive) {
213
232
  activeIdRef.current = nextActive;
214
233
  }
215
- setActiveId((prev) => (prev !== nextActive ? nextActive : prev));
216
- }, [stableSectionIds]);
217
- const getSectionBounds = useCallback(() => {
234
+ setActiveId((prev)=>prev !== nextActive ? nextActive : prev);
235
+ }, [
236
+ stableSectionIds
237
+ ]);
238
+ const getSectionBounds = react.useCallback(()=>{
218
239
  const container = containerElement;
219
240
  const scrollTop = container ? container.scrollTop : window.scrollY;
220
241
  const containerTop = container ? container.getBoundingClientRect().top : 0;
221
- return stableSectionIds
222
- .map((id) => {
242
+ return stableSectionIds.map((id)=>{
223
243
  const el = refs.current[id];
224
- if (!el)
225
- return null;
244
+ if (!el) return null;
226
245
  const rect = el.getBoundingClientRect();
227
- const relativeTop = container
228
- ? rect.top - containerTop + scrollTop
229
- : rect.top + window.scrollY;
246
+ const relativeTop = container ? rect.top - containerTop + scrollTop : rect.top + window.scrollY;
230
247
  return {
231
248
  id,
232
249
  top: relativeTop,
233
250
  bottom: relativeTop + rect.height,
234
- height: rect.height,
251
+ height: rect.height
235
252
  };
236
- })
237
- .filter((bounds) => bounds !== null);
238
- }, [stableSectionIds, containerElement]);
239
- const calculateActiveSection = useCallback(() => {
240
- if (isProgrammaticScrolling.current)
241
- return;
253
+ }).filter((bounds)=>bounds !== null);
254
+ }, [
255
+ stableSectionIds,
256
+ containerElement
257
+ ]);
258
+ const calculateActiveSection = react.useCallback(()=>{
259
+ if (isProgrammaticScrolling.current) return;
242
260
  const container = containerElement;
243
261
  const currentActiveId = activeIdRef.current;
244
262
  const now = Date.now();
245
263
  const scrollY = container ? container.scrollTop : window.scrollY;
246
- const viewportHeight = container
247
- ? container.clientHeight
248
- : window.innerHeight;
249
- const scrollHeight = container
250
- ? container.scrollHeight
251
- : document.documentElement.scrollHeight;
264
+ const viewportHeight = container ? container.clientHeight : window.innerHeight;
265
+ const scrollHeight = container ? container.scrollHeight : document.documentElement.scrollHeight;
252
266
  const maxScroll = Math.max(0, scrollHeight - viewportHeight);
253
267
  const scrollProgress = maxScroll > 0 ? scrollY / maxScroll : 0;
254
- const scrollDirection = scrollY === lastScrollY.current
255
- ? null
256
- : scrollY > lastScrollY.current
257
- ? "down"
258
- : "up";
268
+ const scrollDirection = scrollY === lastScrollY.current ? null : scrollY > lastScrollY.current ? "down" : "up";
259
269
  const deltaTime = now - lastScrollTime.current;
260
270
  const deltaY = scrollY - lastScrollY.current;
261
271
  const velocity = deltaTime > 0 ? Math.abs(deltaY) / deltaTime : 0;
262
272
  lastScrollY.current = scrollY;
263
273
  lastScrollTime.current = now;
264
274
  const sectionBounds = getSectionBounds();
265
- if (sectionBounds.length === 0)
266
- return;
275
+ if (sectionBounds.length === 0) return;
267
276
  const baseOffset = getEffectiveOffset();
268
277
  const effectiveOffset = Math.max(baseOffset, viewportHeight * offsetRatio);
269
278
  const triggerLine = scrollY + effectiveOffset;
270
279
  const viewportTop = scrollY;
271
280
  const viewportBottom = scrollY + viewportHeight;
272
- const scores = sectionBounds.map((section) => {
281
+ const scores = sectionBounds.map((section)=>{
282
+ var _sectionIndexMap_get;
273
283
  const visibleTop = Math.max(section.top, viewportTop);
274
284
  const visibleBottom = Math.min(section.bottom, viewportBottom);
275
285
  const visibleHeight = Math.max(0, visibleBottom - visibleTop);
276
286
  const visibilityRatio = section.height > 0 ? visibleHeight / section.height : 0;
277
287
  const visibleInViewportRatio = viewportHeight > 0 ? visibleHeight / viewportHeight : 0;
278
288
  const isInViewport = section.bottom > viewportTop && section.top < viewportBottom;
279
- const sectionProgress = (() => {
280
- if (section.height === 0)
281
- return 0;
289
+ const sectionProgress = (()=>{
290
+ if (section.height === 0) return 0;
282
291
  const entryPoint = viewportBottom;
283
- const _exitPoint = viewportTop;
284
292
  const totalTravel = viewportHeight + section.height;
285
293
  const traveled = entryPoint - section.top;
286
294
  return Math.max(0, Math.min(1, traveled / totalTravel));
@@ -288,15 +296,11 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
288
296
  let score = 0;
289
297
  if (visibilityRatio >= visibilityThreshold) {
290
298
  score += 1000 + visibilityRatio * 500;
291
- }
292
- else if (isInViewport) {
299
+ } else if (isInViewport) {
293
300
  score += visibleInViewportRatio * 800;
294
301
  }
295
- const sectionIndex = sectionIndexMap.get(section.id) ?? 0;
296
- if (scrollDirection &&
297
- isInViewport &&
298
- section.top <= triggerLine &&
299
- section.bottom > triggerLine) {
302
+ const sectionIndex = (_sectionIndexMap_get = sectionIndexMap.get(section.id)) != null ? _sectionIndexMap_get : 0;
303
+ if (scrollDirection && isInViewport && section.top <= triggerLine && section.bottom > triggerLine) {
300
304
  score += 200;
301
305
  }
302
306
  score -= sectionIndex * 0.1;
@@ -306,47 +310,43 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
306
310
  visibilityRatio,
307
311
  isInViewport,
308
312
  bounds: section,
309
- progress: sectionProgress,
313
+ progress: sectionProgress
310
314
  };
311
315
  });
312
- const isAtBottom = scrollY + viewportHeight >= scrollHeight - 5;
313
- const isAtTop = scrollY <= 5;
316
+ const hasScroll = maxScroll > 10;
317
+ const isAtBottom = hasScroll && scrollY + viewportHeight >= scrollHeight - 5;
318
+ const isAtTop = hasScroll && scrollY <= 5;
314
319
  let newActiveId = null;
315
320
  if (isAtBottom && stableSectionIds.length > 0) {
316
321
  newActiveId = stableSectionIds[stableSectionIds.length - 1];
317
- }
318
- else if (isAtTop && stableSectionIds.length > 0) {
322
+ } else if (isAtTop && stableSectionIds.length > 0) {
319
323
  newActiveId = stableSectionIds[0];
320
- }
321
- else {
322
- const visibleScores = scores.filter((s) => s.isInViewport);
324
+ } else {
325
+ const visibleScores = scores.filter((s)=>s.isInViewport);
323
326
  const candidates = visibleScores.length > 0 ? visibleScores : scores;
324
- candidates.sort((a, b) => b.score - a.score);
327
+ candidates.sort((a, b)=>b.score - a.score);
325
328
  if (candidates.length > 0) {
326
329
  const bestCandidate = candidates[0];
327
- const currentScore = scores.find((s) => s.id === currentActiveId);
328
- const shouldSwitch = !currentScore ||
329
- !currentScore.isInViewport ||
330
- bestCandidate.score > currentScore.score + hysteresisMargin ||
331
- bestCandidate.id === currentActiveId;
330
+ const currentScore = scores.find((s)=>s.id === currentActiveId);
331
+ const shouldSwitch = !currentScore || !currentScore.isInViewport || bestCandidate.score > currentScore.score + hysteresisMargin || bestCandidate.id === currentActiveId;
332
332
  newActiveId = shouldSwitch ? bestCandidate.id : currentActiveId;
333
333
  }
334
334
  }
335
335
  if (newActiveId !== currentActiveId) {
336
336
  activeIdRef.current = newActiveId;
337
337
  setActiveId(newActiveId);
338
- callbackRefs.current.onActiveChange?.(newActiveId, currentActiveId);
338
+ callbackRefs.current.onActiveChange == null ? void 0 : callbackRefs.current.onActiveChange.call(callbackRefs.current, newActiveId, currentActiveId);
339
339
  }
340
- const currentInViewport = new Set(scores.filter((s) => s.isInViewport).map((s) => s.id));
340
+ const currentInViewport = new Set(scores.filter((s)=>s.isInViewport).map((s)=>s.id));
341
341
  const prevInViewport = prevSectionsInViewport.current;
342
- for (const id of currentInViewport) {
342
+ for (const id of currentInViewport){
343
343
  if (!prevInViewport.has(id)) {
344
- callbackRefs.current.onSectionEnter?.(id);
344
+ callbackRefs.current.onSectionEnter == null ? void 0 : callbackRefs.current.onSectionEnter.call(callbackRefs.current, id);
345
345
  }
346
346
  }
347
- for (const id of prevInViewport) {
347
+ for (const id of prevInViewport){
348
348
  if (!currentInViewport.has(id)) {
349
- callbackRefs.current.onSectionLeave?.(id);
349
+ callbackRefs.current.onSectionLeave == null ? void 0 : callbackRefs.current.onSectionLeave.call(callbackRefs.current, id);
350
350
  }
351
351
  }
352
352
  prevSectionsInViewport.current = currentInViewport;
@@ -358,20 +358,20 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
358
358
  isScrolling: isScrollingRef.current,
359
359
  maxScroll,
360
360
  viewportHeight,
361
- offset: effectiveOffset,
361
+ offset: effectiveOffset
362
362
  };
363
363
  const newSections = {};
364
- for (const s of scores) {
364
+ for (const s of scores){
365
365
  newSections[s.id] = {
366
366
  bounds: {
367
367
  top: s.bounds.top,
368
368
  bottom: s.bounds.bottom,
369
- height: s.bounds.height,
369
+ height: s.bounds.height
370
370
  },
371
371
  visibility: Math.round(s.visibilityRatio * 100) / 100,
372
372
  progress: Math.round(s.progress * 100) / 100,
373
373
  isInViewport: s.isInViewport,
374
- isActive: s.id === newActiveId,
374
+ isActive: s.id === newActiveId
375
375
  };
376
376
  }
377
377
  setScroll(newScrollState);
@@ -384,31 +384,37 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
384
384
  visibilityThreshold,
385
385
  hysteresisMargin,
386
386
  getSectionBounds,
387
- containerElement,
387
+ containerElement
388
388
  ]);
389
389
  recalculateRef.current = calculateActiveSection;
390
- useEffect(() => {
390
+ react.useEffect(()=>{
391
391
  const container = containerElement;
392
392
  const scrollTarget = container || window;
393
- const scheduleCalculate = () => {
393
+ const scheduleCalculate = ()=>{
394
394
  if (rafId.current) {
395
395
  cancelAnimationFrame(rafId.current);
396
396
  }
397
- rafId.current = requestAnimationFrame(() => {
397
+ rafId.current = requestAnimationFrame(()=>{
398
398
  rafId.current = null;
399
399
  calculateActiveSection();
400
400
  });
401
401
  };
402
- const handleScrollEnd = () => {
402
+ const handleScrollEnd = ()=>{
403
403
  isScrollingRef.current = false;
404
- setScroll((prev) => ({ ...prev, isScrolling: false }));
405
- callbackRefs.current.onScrollEnd?.();
404
+ setScroll((prev)=>({
405
+ ...prev,
406
+ isScrolling: false
407
+ }));
408
+ callbackRefs.current.onScrollEnd == null ? void 0 : callbackRefs.current.onScrollEnd.call(callbackRefs.current);
406
409
  };
407
- const handleScroll = () => {
410
+ const handleScroll = ()=>{
408
411
  if (!isScrollingRef.current) {
409
412
  isScrollingRef.current = true;
410
- setScroll((prev) => ({ ...prev, isScrolling: true }));
411
- callbackRefs.current.onScrollStart?.();
413
+ setScroll((prev)=>({
414
+ ...prev,
415
+ isScrolling: true
416
+ }));
417
+ callbackRefs.current.onScrollStart == null ? void 0 : callbackRefs.current.onScrollStart.call(callbackRefs.current);
412
418
  }
413
419
  if (scrollIdleTimeoutRef.current) {
414
420
  clearTimeout(scrollIdleTimeoutRef.current);
@@ -424,7 +430,7 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
424
430
  clearTimeout(throttleTimeoutId.current);
425
431
  }
426
432
  scheduleCalculate();
427
- throttleTimeoutId.current = setTimeout(() => {
433
+ throttleTimeoutId.current = setTimeout(()=>{
428
434
  isThrottled.current = false;
429
435
  throttleTimeoutId.current = null;
430
436
  if (hasPendingScroll.current) {
@@ -433,16 +439,20 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
433
439
  }
434
440
  }, debounceMs);
435
441
  };
436
- const handleResize = () => {
442
+ const handleResize = ()=>{
437
443
  scheduleCalculate();
438
444
  };
439
445
  calculateActiveSection();
440
- const deferredRecalcId = setTimeout(() => {
446
+ const deferredRecalcId = setTimeout(()=>{
441
447
  calculateActiveSection();
442
448
  }, 0);
443
- scrollTarget.addEventListener("scroll", handleScroll, { passive: true });
444
- window.addEventListener("resize", handleResize, { passive: true });
445
- return () => {
449
+ scrollTarget.addEventListener("scroll", handleScroll, {
450
+ passive: true
451
+ });
452
+ window.addEventListener("resize", handleResize, {
453
+ passive: true
454
+ });
455
+ return ()=>{
446
456
  clearTimeout(deferredRecalcId);
447
457
  scrollTarget.removeEventListener("scroll", handleScroll);
448
458
  window.removeEventListener("resize", handleResize);
@@ -462,18 +472,25 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
462
472
  clearTimeout(scrollIdleTimeoutRef.current);
463
473
  scrollIdleTimeoutRef.current = null;
464
474
  }
465
- scrollCleanupRef.current?.();
475
+ scrollCleanupRef.current == null ? void 0 : scrollCleanupRef.current.call(scrollCleanupRef);
466
476
  isThrottled.current = false;
467
477
  hasPendingScroll.current = false;
468
478
  isProgrammaticScrolling.current = false;
469
479
  isScrollingRef.current = false;
470
480
  };
471
- }, [calculateActiveSection, debounceMs, containerElement]);
472
- const activeIndex = useMemo(() => {
473
- if (!activeId)
474
- return -1;
475
- return sectionIndexMap.get(activeId) ?? -1;
476
- }, [activeId, sectionIndexMap]);
481
+ }, [
482
+ calculateActiveSection,
483
+ debounceMs,
484
+ containerElement
485
+ ]);
486
+ const activeIndex = react.useMemo(()=>{
487
+ var _sectionIndexMap_get;
488
+ if (!activeId) return -1;
489
+ return (_sectionIndexMap_get = sectionIndexMap.get(activeId)) != null ? _sectionIndexMap_get : -1;
490
+ }, [
491
+ activeId,
492
+ sectionIndexMap
493
+ ]);
477
494
  return {
478
495
  activeId,
479
496
  activeIndex,
@@ -482,7 +499,9 @@ export function useDomet(sectionIds, containerRef = null, options = {}) {
482
499
  registerRef,
483
500
  scrollToSection,
484
501
  sectionProps,
485
- navProps,
502
+ navProps
486
503
  };
487
504
  }
488
- export default useDomet;
505
+
506
+ exports.default = useDomet;
507
+ exports.useDomet = useDomet;