@neo-ui-kit/react 0.0.0-stage → 1.0.1

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.
Files changed (270) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +213 -2
  3. package/dist/artwork/icons.json.d.ts +2 -0
  4. package/dist/artwork/illustrations.json.d.ts +2 -0
  5. package/dist/chunks/chunk-347P6ZE4.js +104 -0
  6. package/dist/chunks/chunk-BJSFN52W.js +417 -0
  7. package/dist/chunks/chunk-FCOU3ODR.js +63 -0
  8. package/dist/chunks/chunk-JZ4GDTH5.js +87 -0
  9. package/dist/chunks/chunk-UGDRXR7P.js +3362 -0
  10. package/dist/chunks/chunk-VK6GHRLV.js +335 -0
  11. package/dist/chunks/chunk-YKCUOZ7V.js +777 -0
  12. package/dist/components/artwork/DatabaseArt/DatabaseArt.d.ts +6 -0
  13. package/dist/components/artwork/DatabaseArt/styles.css +58 -0
  14. package/dist/components/artwork/Landscape/Landscape.d.ts +7 -0
  15. package/dist/components/artwork/Landscape/styles.css +79 -0
  16. package/dist/components/artwork/NeonWaves/NeonWaves.d.ts +15 -0
  17. package/dist/components/artwork/NeonWaves/styles.css +48 -0
  18. package/dist/components/artwork/Planet/Planet.d.ts +4 -0
  19. package/dist/components/artwork/Planet/styles.css +52 -0
  20. package/dist/components/artwork/QuantumField/QuantumField.d.ts +42 -0
  21. package/dist/components/artwork/QuantumField/QuantumFieldExperience.d.ts +22 -0
  22. package/dist/components/artwork/QuantumField/UPSTREAM-LICENSE.txt +21 -0
  23. package/dist/components/artwork/QuantumField/audio.d.ts +15 -0
  24. package/dist/components/artwork/QuantumField/renderer.d.ts +24 -0
  25. package/dist/components/artwork/QuantumField/styles.css +77 -0
  26. package/dist/components/artwork/ServerArt/ServerArt.d.ts +8 -0
  27. package/dist/components/artwork/ServerArt/styles.css +43 -0
  28. package/dist/components/artwork/Spectrum/Spectrum.d.ts +7 -0
  29. package/dist/components/artwork/Spectrum/styles.css +35 -0
  30. package/dist/components/artwork/layers.d.ts +15 -0
  31. package/dist/components/artwork/useArtwork.d.ts +8 -0
  32. package/dist/components/controls/Autocomplete/Autocomplete.d.ts +2 -0
  33. package/dist/components/controls/Autocomplete/styles.css +1 -0
  34. package/dist/components/controls/Button/Button.d.ts +2 -0
  35. package/dist/components/controls/Button/styles.css +1 -0
  36. package/dist/components/controls/Checkbox/Checkbox.d.ts +2 -0
  37. package/dist/components/controls/Checkbox/styles.css +70 -0
  38. package/dist/components/controls/Chip/Chip.d.ts +21 -0
  39. package/dist/components/controls/Chip/styles.css +74 -0
  40. package/dist/components/controls/ChipField.d.ts +25 -0
  41. package/dist/components/controls/ColorPicker/ColorPicker.d.ts +16 -0
  42. package/dist/components/controls/ColorPicker/color.d.ts +9 -0
  43. package/dist/components/controls/ColorPicker/styles.css +103 -0
  44. package/dist/components/controls/DatePicker/DatePicker.d.ts +19 -0
  45. package/dist/components/controls/DatePicker/styles.css +69 -0
  46. package/dist/components/controls/FilePicker/FilePicker.d.ts +2 -0
  47. package/dist/components/controls/FilePicker/styles.css +149 -0
  48. package/dist/components/controls/IconButton/IconButton.d.ts +2 -0
  49. package/dist/components/controls/IconButton/styles.css +4 -0
  50. package/dist/components/controls/InputBase/InputBase.d.ts +21 -0
  51. package/dist/components/controls/InputBase/styles.css +379 -0
  52. package/dist/components/controls/Link/Link.d.ts +11 -0
  53. package/dist/components/controls/Link/styles.css +50 -0
  54. package/dist/components/controls/NumberField/NumberField.d.ts +2 -0
  55. package/dist/components/controls/NumberField/styles.css +1 -0
  56. package/dist/components/controls/PeoplePicker/PeoplePicker.d.ts +37 -0
  57. package/dist/components/controls/PeoplePicker/styles.css +7 -0
  58. package/dist/components/controls/SegmentedControl/SegmentedControl.d.ts +2 -0
  59. package/dist/components/controls/SegmentedControl/styles.css +9 -0
  60. package/dist/components/controls/Select/Select.d.ts +8 -0
  61. package/dist/components/controls/Select/styles.css +142 -0
  62. package/dist/components/controls/Slider/Slider.d.ts +3 -0
  63. package/dist/components/controls/Slider/styles.css +138 -0
  64. package/dist/components/controls/SplitButton/SplitButton.d.ts +2 -0
  65. package/dist/components/controls/SplitButton/styles.css +169 -0
  66. package/dist/components/controls/Switch/Switch.d.ts +2 -0
  67. package/dist/components/controls/Switch/styles.css +54 -0
  68. package/dist/components/controls/Tab/Tab.d.ts +2 -0
  69. package/dist/components/controls/Tab/styles.css +111 -0
  70. package/dist/components/controls/Tabs/Tabs.d.ts +2 -0
  71. package/dist/components/controls/Tabs/styles.css +239 -0
  72. package/dist/components/controls/TagInput/TagInput.d.ts +24 -0
  73. package/dist/components/controls/TagInput/styles.css +24 -0
  74. package/dist/components/controls/TextArea/TextArea.d.ts +2 -0
  75. package/dist/components/controls/TextArea/styles.css +15 -0
  76. package/dist/components/controls/TextField/TextField.d.ts +2 -0
  77. package/dist/components/controls/ThemePicker/ThemePicker.d.ts +24 -0
  78. package/dist/components/controls/ThemePicker/styles.css +128 -0
  79. package/dist/components/controls/ToggleButton/ToggleButton.d.ts +2 -0
  80. package/dist/components/controls/ToggleButton/styles.css +49 -0
  81. package/dist/components/controls/internal.d.ts +62 -0
  82. package/dist/components/controls/shared.css +694 -0
  83. package/dist/components/controls/shared.d.ts +204 -0
  84. package/dist/components/editor/PianoRoll/PianoRoll.d.ts +65 -0
  85. package/dist/components/editor/PianoRoll/styles.css +186 -0
  86. package/dist/components/editor/shared.css +1 -0
  87. package/dist/components/effects/AnimatedBorder/AnimatedBorder.d.ts +9 -0
  88. package/dist/components/effects/AnimatedBorder/styles.css +7 -0
  89. package/dist/components/effects/Beacon/Beacon.d.ts +9 -0
  90. package/dist/components/effects/Beacon/styles.css +38 -0
  91. package/dist/components/effects/Equalizer/Equalizer.d.ts +14 -0
  92. package/dist/components/effects/Equalizer/styles.css +38 -0
  93. package/dist/components/effects/GlowText/GlowText.d.ts +9 -0
  94. package/dist/components/effects/GlowText/styles.css +56 -0
  95. package/dist/components/effects/ImageShine/ImageShine.d.ts +13 -0
  96. package/dist/components/effects/ImageShine/styles.css +66 -0
  97. package/dist/components/effects/Marquee/Marquee.d.ts +9 -0
  98. package/dist/components/effects/Marquee/styles.css +46 -0
  99. package/dist/components/effects/MelodixText/MelodixText.d.ts +15 -0
  100. package/dist/components/effects/MelodixText/styles.css +28 -0
  101. package/dist/components/effects/Reveal/Reveal.d.ts +13 -0
  102. package/dist/components/effects/Reveal/styles.css +25 -0
  103. package/dist/components/effects/Shimmer/Shimmer.d.ts +10 -0
  104. package/dist/components/effects/Shimmer/styles.css +48 -0
  105. package/dist/components/effects/Sparkles/Sparkles.d.ts +9 -0
  106. package/dist/components/effects/Sparkles/styles.css +28 -0
  107. package/dist/components/effects/Spotlight/Spotlight.d.ts +11 -0
  108. package/dist/components/effects/Spotlight/styles.css +45 -0
  109. package/dist/components/effects/Tilt/Tilt.d.ts +11 -0
  110. package/dist/components/effects/Tilt/styles.css +67 -0
  111. package/dist/components/feedback/Badge/Badge.d.ts +3 -0
  112. package/dist/components/feedback/Badge/styles.css +91 -0
  113. package/dist/components/feedback/CollapsibleSection/CollapsibleSection.d.ts +2 -0
  114. package/dist/components/feedback/CollapsibleSection/styles.css +76 -0
  115. package/dist/components/feedback/DataTable/DataTable.d.ts +16 -0
  116. package/dist/components/feedback/DataTable/styles.css +522 -0
  117. package/dist/components/feedback/Dialog/Dialog.d.ts +2 -0
  118. package/dist/components/feedback/Dialog/styles.css +82 -0
  119. package/dist/components/feedback/EmptyState/EmptyState.d.ts +2 -0
  120. package/dist/components/feedback/EmptyState/styles.css +80 -0
  121. package/dist/components/feedback/KeyValueList/KeyValueList.d.ts +2 -0
  122. package/dist/components/feedback/KeyValueList/styles.css +51 -0
  123. package/dist/components/feedback/Menu/Menu.d.ts +2 -0
  124. package/dist/components/feedback/Menu/styles.css +123 -0
  125. package/dist/components/feedback/MenuItem/MenuItem.d.ts +2 -0
  126. package/dist/components/feedback/MenuItem/styles.css +71 -0
  127. package/dist/components/feedback/MessageBar/MessageBar.d.ts +2 -0
  128. package/dist/components/feedback/MessageBar/styles.css +116 -0
  129. package/dist/components/feedback/Popover/Popover.d.ts +2 -0
  130. package/dist/components/feedback/Popover/styles.css +44 -0
  131. package/dist/components/feedback/ProgressBar/ProgressBar.d.ts +2 -0
  132. package/dist/components/feedback/ProgressBar/styles.css +76 -0
  133. package/dist/components/feedback/SignalBars/SignalBars.d.ts +11 -0
  134. package/dist/components/feedback/SignalBars/styles.css +31 -0
  135. package/dist/components/feedback/StatusIndicator/StatusIndicator.d.ts +2 -0
  136. package/dist/components/feedback/StatusIndicator/styles.css +88 -0
  137. package/dist/components/feedback/Steps/Steps.d.ts +2 -0
  138. package/dist/components/feedback/Steps/styles.css +152 -0
  139. package/dist/components/feedback/Toast/Toast.d.ts +2 -0
  140. package/dist/components/feedback/Toast/styles.css +89 -0
  141. package/dist/components/feedback/Tooltip/Tooltip.d.ts +15 -0
  142. package/dist/components/feedback/Tooltip/styles.css +38 -0
  143. package/dist/components/feedback/shared.css +22 -0
  144. package/dist/components/feedback/shared.d.ts +231 -0
  145. package/dist/components/forms/Form/Form.d.ts +35 -0
  146. package/dist/components/forms/Form/styles.css +1 -0
  147. package/dist/components/forms/FormFields/FormFields.d.ts +20 -0
  148. package/dist/components/forms/FormFields/styles.css +72 -0
  149. package/dist/components/foundation/Loader/Loader.d.ts +30 -0
  150. package/dist/components/foundation/LoaderGenerator/LoaderGenerator.d.ts +38 -0
  151. package/dist/components/foundation/LoaderGenerator/styles.css +104 -0
  152. package/dist/components/foundation/ThemeEditor/ThemeEditor.d.ts +15 -0
  153. package/dist/components/foundation/ThemeEditor/styles.css +97 -0
  154. package/dist/components/foundation/ThemeEditor/themeConfig.d.ts +47 -0
  155. package/dist/components/foundation/ThemeProvider/ThemeProvider.d.ts +32 -0
  156. package/dist/components/foundation/ThemeProvider/styles.css +59 -0
  157. package/dist/components/foundation/Typography/Typography.d.ts +17 -0
  158. package/dist/components/foundation/Typography/styles.css +115 -0
  159. package/dist/components/layout/Avatar/Avatar.d.ts +2 -0
  160. package/dist/components/layout/Avatar/HostSeal.d.ts +5 -0
  161. package/dist/components/layout/Avatar/styles.css +166 -0
  162. package/dist/components/layout/BrandMark/BrandMark.d.ts +2 -0
  163. package/dist/components/layout/BrandMark/styles.css +39 -0
  164. package/dist/components/layout/ButtonGroup/ButtonGroup.d.ts +12 -0
  165. package/dist/components/layout/ButtonGroup/styles.css +36 -0
  166. package/dist/components/layout/Card/Card.d.ts +14 -0
  167. package/dist/components/layout/Card/styles.css +37 -0
  168. package/dist/components/layout/DialogActions/DialogActions.d.ts +12 -0
  169. package/dist/components/layout/DialogActions/styles.css +31 -0
  170. package/dist/components/layout/DialogBody/DialogBody.d.ts +12 -0
  171. package/dist/components/layout/DialogBody/styles.css +28 -0
  172. package/dist/components/layout/Divider/Divider.d.ts +2 -0
  173. package/dist/components/layout/Divider/styles.css +58 -0
  174. package/dist/components/layout/FloatingPanel/FloatingPanel.d.ts +15 -0
  175. package/dist/components/layout/FloatingPanel/styles.css +47 -0
  176. package/dist/components/layout/FloatingPanel/useFloatingPanel.d.ts +54 -0
  177. package/dist/components/layout/Grid/Grid.d.ts +24 -0
  178. package/dist/components/layout/Grid/styles.css +90 -0
  179. package/dist/components/layout/Header/Header.d.ts +2 -0
  180. package/dist/components/layout/Header/styles.css +42 -0
  181. package/dist/components/layout/Icon/Icon.d.ts +4 -0
  182. package/dist/components/layout/Icon/styles.css +62 -0
  183. package/dist/components/layout/Illustration/Illustration.d.ts +2 -0
  184. package/dist/components/layout/Illustration/styles.css +104 -0
  185. package/dist/components/layout/ScrollArea/ScrollArea.d.ts +2 -0
  186. package/dist/components/layout/ScrollArea/styles.css +61 -0
  187. package/dist/components/layout/Stack/Stack.d.ts +21 -0
  188. package/dist/components/layout/Stack/styles.css +53 -0
  189. package/dist/components/layout/StatTile/StatTile.d.ts +20 -0
  190. package/dist/components/layout/StatTile/styles.css +90 -0
  191. package/dist/components/layout/TabPanel/TabPanel.d.ts +2 -0
  192. package/dist/components/layout/TabPanel/styles.css +16 -0
  193. package/dist/components/layout/Text/Text.d.ts +2 -0
  194. package/dist/components/layout/Text/styles.css +29 -0
  195. package/dist/components/layout/Toolbar/Toolbar.d.ts +12 -0
  196. package/dist/components/layout/Toolbar/styles.css +7 -0
  197. package/dist/components/layout/shared.css +79 -0
  198. package/dist/components/layout/shared.d.ts +64 -0
  199. package/dist/components/media/AudioPlayer/AudioPlayer.d.ts +2 -0
  200. package/dist/components/media/AudioPlayer/styles.css +86 -0
  201. package/dist/components/media/KaraokeLyrics/KaraokeLyrics.d.ts +25 -0
  202. package/dist/components/media/KaraokeLyrics/styles.css +56 -0
  203. package/dist/components/media/LevelMeter/LevelMeter.d.ts +7 -0
  204. package/dist/components/media/LevelMeter/styles.css +30 -0
  205. package/dist/components/media/MediaCard/MediaCard.d.ts +24 -0
  206. package/dist/components/media/MediaCard/styles.css +108 -0
  207. package/dist/components/media/MelodyRoll/MelodyRoll.d.ts +48 -0
  208. package/dist/components/media/MelodyRoll/styles.css +196 -0
  209. package/dist/components/media/PianoKeyboard/PianoKeyboard.d.ts +24 -0
  210. package/dist/components/media/PianoKeyboard/styles.css +83 -0
  211. package/dist/components/media/RotaryKnob/RotaryKnob.d.ts +3 -0
  212. package/dist/components/media/RotaryKnob/styles.css +319 -0
  213. package/dist/components/media/Sparkline/Sparkline.d.ts +2 -0
  214. package/dist/components/media/Sparkline/styles.css +70 -0
  215. package/dist/components/media/WaveDecoration/WaveDecoration.d.ts +2 -0
  216. package/dist/components/media/WaveDecoration/styles.css +2 -0
  217. package/dist/components/media/Waveform/Waveform.d.ts +9 -0
  218. package/dist/components/media/Waveform/styles.css +375 -0
  219. package/dist/components/media/Waveform/useWaveformPeaks.d.ts +11 -0
  220. package/dist/components/media/shared.css +7 -0
  221. package/dist/components/media/shared.d.ts +80 -0
  222. package/dist/components/navigation/Router/Router.d.ts +32 -0
  223. package/dist/components/navigation/Router/styles.css +1 -0
  224. package/dist/components.css +102 -0
  225. package/dist/core/artwork.d.ts +17 -0
  226. package/dist/core/base.d.ts +65 -0
  227. package/dist/core/environment.d.ts +5 -0
  228. package/dist/core/i18n.d.ts +34 -0
  229. package/dist/core/messages.d.ts +1 -0
  230. package/dist/core/motion/hooks.d.ts +17 -0
  231. package/dist/core/motion-engine.d.ts +13 -0
  232. package/dist/core/noise.d.ts +20 -0
  233. package/dist/core/providers/context.d.ts +4 -0
  234. package/dist/core/responsive.d.ts +13 -0
  235. package/dist/core.d.ts +8 -0
  236. package/dist/core.js +56 -0
  237. package/dist/editor.d.ts +2 -0
  238. package/dist/editor.js +8 -0
  239. package/dist/fonts/melodix/Melodix-100.woff2 +0 -0
  240. package/dist/fonts/melodix/Melodix-200.woff2 +0 -0
  241. package/dist/fonts/melodix/Melodix-300.woff2 +0 -0
  242. package/dist/fonts/melodix/Melodix-400.woff2 +0 -0
  243. package/dist/fonts/melodix/Melodix-500.woff2 +0 -0
  244. package/dist/fonts/melodix/Melodix-600.woff2 +0 -0
  245. package/dist/fonts/melodix/Melodix-700.woff2 +0 -0
  246. package/dist/fonts/melodix/Melodix-800.woff2 +0 -0
  247. package/dist/fonts/melodix/Melodix-900.woff2 +0 -0
  248. package/dist/fonts/melodix/MelodixText-100.woff2 +0 -0
  249. package/dist/fonts/melodix/MelodixText-200.woff2 +0 -0
  250. package/dist/fonts/melodix/MelodixText-300.woff2 +0 -0
  251. package/dist/fonts/melodix/MelodixText-400.woff2 +0 -0
  252. package/dist/fonts/melodix/MelodixText-500.woff2 +0 -0
  253. package/dist/fonts/melodix/MelodixText-600.woff2 +0 -0
  254. package/dist/fonts/melodix/MelodixText-700.woff2 +0 -0
  255. package/dist/fonts/melodix/MelodixText-800.woff2 +0 -0
  256. package/dist/fonts/melodix/MelodixText-900.woff2 +0 -0
  257. package/dist/fonts/melodix/OFL-PlayfairDisplay.txt +93 -0
  258. package/dist/fonts/melodix.css +123 -0
  259. package/dist/forms.d.ts +4 -0
  260. package/dist/forms.js +17 -0
  261. package/dist/index.d.ts +163 -0
  262. package/dist/index.js +9683 -0
  263. package/dist/router.d.ts +2 -0
  264. package/dist/router.js +11 -0
  265. package/dist/styles.css +2 -0
  266. package/dist/theme/base.css +221 -0
  267. package/dist/theme/tokens.css +196 -0
  268. package/dist/theme/typography.d.ts +24 -0
  269. package/dist/tokens.css +1 -0
  270. package/package.json +83 -4
@@ -0,0 +1,777 @@
1
+ import {
2
+ canObserveIntersection,
3
+ createResizeObserver,
4
+ reducedMotionQuery,
5
+ useMotion
6
+ } from "./chunk-FCOU3ODR.js";
7
+
8
+ // src/core/motion-engine.js
9
+ var uid = 0;
10
+ var U = {
11
+ uid: (p = "ad") => `${p}-${++uid}`,
12
+ svg(tag, attrs = {}) {
13
+ const n = document.createElementNS("http://www.w3.org/2000/svg", tag);
14
+ for (const [k, v] of Object.entries(attrs)) n.setAttribute(k, String(v));
15
+ return n;
16
+ }
17
+ };
18
+ var seen = /* @__PURE__ */ new WeakMap();
19
+ var running = /* @__PURE__ */ new Set();
20
+ var measurements = /* @__PURE__ */ new Set();
21
+ var raf = null;
22
+ var timer = null;
23
+ var last = 0;
24
+ var weakDevice = typeof navigator !== "undefined" && ((navigator.hardwareConcurrency || 8) <= 4 || (navigator.deviceMemory || 8) <= 4);
25
+ var FRAME = 1e3 / (weakDevice ? 20 : 30);
26
+ U.setMotionFrameRate = (fps) => {
27
+ FRAME = 1e3 / Math.max(1, Math.min(120, fps));
28
+ };
29
+ var looping = /* @__PURE__ */ new Set();
30
+ var pendingAnimations = /* @__PURE__ */ new Set();
31
+ var pendingTargets = /* @__PURE__ */ new Set();
32
+ var active = [];
33
+ var lastScan = -Infinity;
34
+ var needsScan = false;
35
+ var tickers = /* @__PURE__ */ new Set();
36
+ U.subscribeTick = (listener) => {
37
+ tickers.add(listener);
38
+ schedule();
39
+ return () => {
40
+ tickers.delete(listener);
41
+ schedule();
42
+ };
43
+ };
44
+ var isLoop = (animation) => {
45
+ if (!animation.animationName || !animation.animationName.startsWith("ad-")) return false;
46
+ const timing = animation.effect && animation.effect.getTiming();
47
+ return !!timing && timing.iterations === Infinity;
48
+ };
49
+ function scan(now, animations = pendingAnimations) {
50
+ lastScan = now;
51
+ needsScan = false;
52
+ for (const target of pendingTargets)
53
+ for (const animation of target.getAnimations?.() || []) pendingAnimations.add(animation);
54
+ pendingTargets.clear();
55
+ for (const animation of animations)
56
+ if (!looping.has(animation) && animation.playState === "running" && isLoop(animation)) {
57
+ animation.__adStart = now - (animation.currentTime || 0);
58
+ animation.pause();
59
+ looping.add(animation);
60
+ }
61
+ pendingAnimations.clear();
62
+ active = [];
63
+ for (const animation of looping) {
64
+ const target = animation.effect && animation.effect.target;
65
+ if (!target || !target.isConnected || animation.playState === "idle" || !isLoop(animation)) {
66
+ looping.delete(animation);
67
+ if (target && target.isConnected && animation.playState === "paused") animation.play();
68
+ continue;
69
+ }
70
+ const hidden = document.hidden || target.closest("[data-ad-offscreen], [data-ad-paused]");
71
+ if (hidden) {
72
+ animation.__adHeld = true;
73
+ continue;
74
+ }
75
+ if (animation.__adHeld) {
76
+ animation.__adStart = now - (animation.currentTime || 0);
77
+ animation.__adHeld = false;
78
+ }
79
+ active.push(animation);
80
+ }
81
+ }
82
+ function tick(now) {
83
+ raf = null;
84
+ if (needsScan || now - lastScan > 400) scan(now);
85
+ const deadline = performance.now() + 8;
86
+ for (const item of measurements) {
87
+ if (!item.element.isConnected) {
88
+ measurements.delete(item);
89
+ continue;
90
+ }
91
+ if (item.element._adInView === false) continue;
92
+ if (performance.now() >= deadline) break;
93
+ measurements.delete(item);
94
+ item.sync();
95
+ }
96
+ if (now - last >= FRAME - 6) {
97
+ for (const animation of active) animation.currentTime = now - animation.__adStart;
98
+ for (const scope of running) scope.tick(now);
99
+ for (const listener of tickers) listener(now);
100
+ last = now;
101
+ }
102
+ if (hasVisibleWork() && !document.hidden) {
103
+ timer = setTimeout(() => {
104
+ timer = null;
105
+ schedule();
106
+ }, Math.max(0, FRAME - (performance.now() - now) - 4));
107
+ }
108
+ }
109
+ function hasVisibleWork() {
110
+ if (needsScan || tickers.size || active.length) return true;
111
+ for (const item of measurements)
112
+ if (item.element.isConnected && item.element._adInView !== false) return true;
113
+ for (const scope of running)
114
+ if (scope.enabled) {
115
+ for (const node of scope.callbacks.keys())
116
+ if (node.isConnected && node._adInView !== false) return true;
117
+ }
118
+ return false;
119
+ }
120
+ function schedule() {
121
+ if (document.hidden || !hasVisibleWork()) {
122
+ if (raf !== null) cancelAnimationFrame(raf);
123
+ if (timer !== null) clearTimeout(timer);
124
+ raf = timer = null;
125
+ return;
126
+ }
127
+ if (raf === null && timer === null) raf = requestAnimationFrame(tick);
128
+ }
129
+ function refreshMotion() {
130
+ needsScan = true;
131
+ schedule();
132
+ }
133
+ var wake = () => {
134
+ for (const s of running) s.previous = null;
135
+ if (document.hidden) scan(performance.now());
136
+ refreshMotion();
137
+ };
138
+ if (typeof window !== "undefined" && typeof document !== "undefined") {
139
+ document.addEventListener("visibilitychange", wake);
140
+ const onAnimation = (event) => {
141
+ if (!event.animationName.startsWith("ad-")) return;
142
+ pendingTargets.add(event.target);
143
+ needsScan = true;
144
+ schedule();
145
+ };
146
+ document.addEventListener("animationstart", onAnimation);
147
+ document.addEventListener("animationcancel", onAnimation);
148
+ scan(performance.now(), document.getAnimations?.() || []);
149
+ schedule();
150
+ }
151
+ var scopeCount = 0;
152
+ var preferenceMedia = null;
153
+ var preferenceScopes = /* @__PURE__ */ new Set();
154
+ var onPreference = (event) => {
155
+ for (const scope of preferenceScopes)
156
+ if (!scope.explicit) scope.set(!event.matches, false);
157
+ };
158
+ var visibilityObserver = null;
159
+ var visibilityScopes = /* @__PURE__ */ new Map();
160
+ var observeScope = (node, scope) => {
161
+ if (!canObserveIntersection()) return;
162
+ let scopes = visibilityScopes.get(node);
163
+ if (!scopes) {
164
+ scopes = /* @__PURE__ */ new Set();
165
+ visibilityScopes.set(node, scopes);
166
+ visibilityObserver ??= new IntersectionObserver(
167
+ (entries) => {
168
+ for (const entry of entries) {
169
+ entry.target._adInView = entry.isIntersecting;
170
+ for (const watcher of visibilityScopes.get(entry.target) || []) watcher.previous = null;
171
+ }
172
+ schedule();
173
+ },
174
+ { rootMargin: "10%" }
175
+ );
176
+ visibilityObserver.observe(node);
177
+ }
178
+ scopes.add(scope);
179
+ };
180
+ var unobserveScope = (node, scope) => {
181
+ const scopes = visibilityScopes.get(node);
182
+ if (!scopes) return;
183
+ scopes.delete(scope);
184
+ if (scopes.size) return;
185
+ visibilityScopes.delete(node);
186
+ visibilityObserver.unobserve(node);
187
+ if (!visibilityScopes.size) {
188
+ visibilityObserver.disconnect();
189
+ visibilityObserver = null;
190
+ }
191
+ };
192
+ U.createMotion = (root = document) => {
193
+ scopeCount++;
194
+ if (!preferenceMedia) {
195
+ preferenceMedia = reducedMotionQuery();
196
+ preferenceMedia.addEventListener("change", onPreference);
197
+ }
198
+ const scope = {
199
+ root,
200
+ enabled: !preferenceMedia.matches,
201
+ time: 0,
202
+ previous: null,
203
+ explicit: false,
204
+ callbacks: /* @__PURE__ */ new Map(),
205
+ tick(now) {
206
+ if (!this.enabled) {
207
+ this.previous = null;
208
+ return;
209
+ }
210
+ let painted = false;
211
+ for (const [node, fn] of this.callbacks) {
212
+ if (!node.isConnected) {
213
+ this.callbacks.delete(node);
214
+ unobserveScope(node, this);
215
+ continue;
216
+ }
217
+ if (node._adInView === true || node._adInView !== false && node.getClientRects().length) {
218
+ if (!painted) {
219
+ if (this.previous !== null)
220
+ this.time += Math.min((now - this.previous) / 1e3, 0.1);
221
+ this.previous = now;
222
+ painted = true;
223
+ }
224
+ fn(this.time);
225
+ }
226
+ }
227
+ if (!painted) this.previous = null;
228
+ },
229
+ add(node, callback, immediate = true) {
230
+ this.callbacks.set(node, callback);
231
+ if (immediate) callback(this.time);
232
+ observeScope(node, this);
233
+ schedule();
234
+ return () => {
235
+ this.callbacks.delete(node);
236
+ unobserveScope(node, this);
237
+ schedule();
238
+ };
239
+ },
240
+ set(enabled, explicit = true) {
241
+ this.enabled = !!enabled;
242
+ this.explicit ||= explicit;
243
+ this.previous = null;
244
+ const target = root.dataset ? root : root.host || document.documentElement;
245
+ target.dataset.adMotion = enabled ? "on" : "off";
246
+ if (this.enabled) running.add(this);
247
+ else running.delete(this);
248
+ schedule();
249
+ return this.enabled;
250
+ },
251
+ dispose() {
252
+ if (this.disposed) return;
253
+ this.disposed = true;
254
+ --scopeCount;
255
+ running.delete(this);
256
+ for (const node of this.callbacks.keys()) unobserveScope(node, this);
257
+ this.callbacks.clear();
258
+ preferenceScopes.delete(this);
259
+ if (!preferenceScopes.size) {
260
+ preferenceMedia.removeEventListener("change", onPreference);
261
+ preferenceMedia = null;
262
+ }
263
+ schedule();
264
+ }
265
+ };
266
+ preferenceScopes.add(scope);
267
+ scope.set(scope.enabled, false);
268
+ return scope;
269
+ };
270
+ U.roundedPath = (w, h, corners) => {
271
+ const i = 0.65, R = w - i, B = h - i;
272
+ const factor = Math.min(
273
+ 1,
274
+ w / (corners[0][0] + corners[1][0]),
275
+ w / (corners[2][0] + corners[3][0]),
276
+ h / (corners[0][1] + corners[3][1]),
277
+ h / (corners[1][1] + corners[2][1])
278
+ );
279
+ const [tl, tr, br, bl] = corners.map(([x2, y2]) => {
280
+ x2 = Math.max(0, x2 * factor - i);
281
+ y2 = Math.max(0, y2 * factor - i);
282
+ return x2 && y2 ? [x2, y2] : [0, 0];
283
+ });
284
+ const segments = [];
285
+ let d = `M${i + tl[0]} ${i}`, x = i + tl[0], y = i;
286
+ const line = (toX, toY) => {
287
+ const fromX = x, fromY = y, dx = toX - x, dy = toY - y;
288
+ const length2 = Math.hypot(dx, dy);
289
+ segments.push({ length: length2, point: (distance) => ({ x: fromX + dx * distance / length2, y: fromY + dy * distance / length2 }) });
290
+ d += `L${toX} ${toY}`;
291
+ x = toX;
292
+ y = toY;
293
+ };
294
+ const arc = (cx, cy, [rx, ry], angle, toX, toY) => {
295
+ if (!rx || !ry) return line(toX, toY);
296
+ const point = (t) => ({ x: cx + rx * Math.cos(angle + t * Math.PI / 2), y: cy + ry * Math.sin(angle + t * Math.PI / 2) });
297
+ const distances = [0];
298
+ if (rx !== ry) {
299
+ let previous = point(0);
300
+ for (let step = 1; step <= 32; step++) {
301
+ const next = point(step / 32);
302
+ distances.push(distances[step - 1] + Math.hypot(next.x - previous.x, next.y - previous.y));
303
+ previous = next;
304
+ }
305
+ }
306
+ const length2 = rx === ry ? rx * Math.PI / 2 : distances[32];
307
+ segments.push({ length: length2, point(distance) {
308
+ if (rx === ry) return point(distance / length2);
309
+ let lo = 0, hi = 32;
310
+ while (hi - lo > 1) {
311
+ const middle = lo + hi >> 1;
312
+ if (distances[middle] < distance) lo = middle;
313
+ else hi = middle;
314
+ }
315
+ return point((lo + (distance - distances[lo]) / (distances[hi] - distances[lo])) / 32);
316
+ } });
317
+ d += `A${rx} ${ry} 0 0 1 ${toX} ${toY}`;
318
+ x = toX;
319
+ y = toY;
320
+ };
321
+ line(R - tr[0], i);
322
+ arc(R - tr[0], i + tr[1], tr, -Math.PI / 2, R, i + tr[1]);
323
+ line(R, B - br[1]);
324
+ arc(R - br[0], B - br[1], br, 0, R - br[0], B);
325
+ line(i + bl[0], B);
326
+ arc(i + bl[0], B - bl[1], bl, Math.PI / 2, i, B - bl[1]);
327
+ line(i, i + tl[1]);
328
+ arc(i + tl[0], i + tl[1], tl, Math.PI, i + tl[0], i);
329
+ d += "Z";
330
+ const length = segments.reduce((total, segment) => total + segment.length, 0);
331
+ return {
332
+ d,
333
+ point(fraction) {
334
+ let distance = fraction * length;
335
+ for (const segment of segments) {
336
+ if (segment.length && distance <= segment.length) return segment.point(distance);
337
+ distance -= segment.length;
338
+ }
339
+ return { x: i + tl[0], y: i };
340
+ }
341
+ };
342
+ };
343
+ var borders = /* @__PURE__ */ new WeakMap();
344
+ var AURA = [[25, 0.016], [22, 0.031], [19, 0.055], [16, 0.087], [13, 0.124], [10, 0.157], [7, 0.17], [4, 0.153]];
345
+ var borderSerial = 0;
346
+ var HALO = 16;
347
+ var CORE_STOPS = [
348
+ ["var(--ad-neutral-200)", 0],
349
+ ["var(--ad-neutral-200)", 4],
350
+ ["var(--ad-secondary)", 16],
351
+ ["rgb(from var(--ad-primary) r g b / 0.85)", 40],
352
+ ["rgb(from var(--ad-primary) r g b / 0.32)", 72],
353
+ ["rgb(from var(--ad-primary) r g b / 0)", 100]
354
+ ];
355
+ var AURA_STOPS = [
356
+ ["var(--ad-primary)", 0],
357
+ ["rgb(from var(--ad-primary) r g b / 0.7)", 40],
358
+ ["rgb(from var(--ad-primary) r g b / 0)", 100]
359
+ ];
360
+ var radial = (stops) => `radial-gradient(circle closest-side, ${stops.map(([color, at]) => `${color} ${at}%`).join(", ")})`;
361
+ var ringMask = (w, h, d, strokes) => {
362
+ const paths = strokes.map(([width, opacity]) => `<path d='${d}' stroke-width='${width}' stroke-opacity='${opacity}'/>`).join("");
363
+ return `url("data:image/svg+xml,${encodeURIComponent(
364
+ `<svg xmlns='http://www.w3.org/2000/svg' viewBox='${-HALO} ${-HALO} ${w + 2 * HALO} ${h + 2 * HALO}'><g fill='none' stroke='#000' stroke-linecap='round' stroke-linejoin='round'>${paths}</g></svg>`
365
+ )}")`;
366
+ };
367
+ U.attachBorder = (element, { shell = false, round = false, scope, defer = false } = {}) => {
368
+ if (borders.has(element)) return borders.get(element);
369
+ defer &&= !!scope;
370
+ if (defer && canObserveIntersection()) element._adInView = false;
371
+ let radius = round ? 28 : shell ? 102 : 116;
372
+ const overlay = document.createElement("div");
373
+ overlay.className = "ad-border";
374
+ overlay.setAttribute("aria-hidden", "true");
375
+ overlay.setAttribute("data-ad-component", "AnimatedBorder");
376
+ const edge = U.svg("svg", { fill: "none", preserveAspectRatio: "none" });
377
+ const path = U.svg("path", {
378
+ stroke: shell ? "rgb(from var(--ad-secondary) r g b / 0.65)" : "rgb(from var(--ad-primary) r g b / 0.16)",
379
+ "stroke-width": shell ? 1.1 : 0.6
380
+ });
381
+ edge.append(path);
382
+ const ring = (className) => {
383
+ const node = document.createElement("div");
384
+ node.className = className;
385
+ return node;
386
+ };
387
+ const aura = ring("ad-border-aura"), core = ring("ad-border-core");
388
+ overlay.append(edge, aura, core);
389
+ const instancePhase = ++borderSerial * 0.38196601125 % 1;
390
+ const lights = Array.from({ length: 2 }, (_, k) => {
391
+ const spot = (parent, stops) => {
392
+ const node = ring("ad-border-light");
393
+ node.style.background = radial(stops);
394
+ parent.append(node);
395
+ return node;
396
+ };
397
+ return {
398
+ radius,
399
+ phase: (k * 0.48 + 0.535 + instancePhase) % 1,
400
+ speed: round ? k ? 25 : 36 : k ? 86 : 125,
401
+ spots: [spot(aura, AURA_STOPS), spot(core, CORE_STOPS)],
402
+ at: null
403
+ };
404
+ });
405
+ const previousInlinePosition = element.style.position;
406
+ element.append(overlay);
407
+ const item = {
408
+ element,
409
+ overlay,
410
+ path,
411
+ lights,
412
+ length: 0,
413
+ elapsed: 0,
414
+ previousTime: null,
415
+ patchedPosition: false,
416
+ previousInlinePosition
417
+ };
418
+ item.paint = (time) => {
419
+ if (!item.length) return;
420
+ if (item.previousTime !== null)
421
+ item.elapsed += Math.min(0.1, Math.max(0, time - item.previousTime));
422
+ item.previousTime = time;
423
+ for (const light of lights) {
424
+ const p = item.contour.point((light.phase * item.length + item.elapsed * light.speed) % item.length / item.length);
425
+ light.at = p;
426
+ const transform = `translate3d(${(p.x - radius + HALO).toFixed(2)}px, ${(p.y - radius + HALO).toFixed(2)}px, 0)`;
427
+ for (const spot of light.spots) spot.style.transform = transform;
428
+ }
429
+ };
430
+ item.sync = () => {
431
+ const computed = getComputedStyle(element);
432
+ const sides = ["Top", "Right", "Bottom", "Left"];
433
+ const borderWidths = sides.map((side) => parseFloat(computed[`border${side}Width`]) || 0);
434
+ const [w, h] = [["width", 3, 1, "offsetWidth"], ["height", 0, 2, "offsetHeight"]].map(([axis, start, end, fallback]) => {
435
+ const value = parseFloat(computed[axis]);
436
+ return Number.isFinite(value) ? value + (computed.boxSizing === "border-box" ? 0 : [start, end].reduce((sum, side) => sum + borderWidths[side] + (parseFloat(computed[`padding${sides[side]}`]) || 0), 0)) : element[fallback];
437
+ });
438
+ if (!w || !h) return;
439
+ if (computed.position === "static") {
440
+ item.patchedPosition = true;
441
+ element.style.position = "relative";
442
+ }
443
+ const corners = ["TopLeft", "TopRight", "BottomRight", "BottomLeft"].map((corner) => {
444
+ const values = (computed[`border${corner}Radius`] || computed.borderTopLeftRadius).split(/\s+/);
445
+ return [w, h].map((size, axis) => {
446
+ const value = values[axis] || values[0];
447
+ return (parseFloat(value) || 0) * (value.includes("%") ? size / 100 : 1);
448
+ });
449
+ });
450
+ const geometry = `${w},${h},${corners},${borderWidths}`;
451
+ if (item.geometry === geometry) return;
452
+ item.geometry = geometry;
453
+ overlay.style.inset = borderWidths.map((width) => `${-width}px`).join(" ");
454
+ overlay.style.width = `calc(100% + ${borderWidths[1] + borderWidths[3]}px)`;
455
+ overlay.style.height = `calc(100% + ${borderWidths[0] + borderWidths[2]}px)`;
456
+ item.contour = U.roundedPath(w, h, corners);
457
+ const { d } = item.contour;
458
+ edge.setAttribute("viewBox", `0 0 ${w} ${h}`);
459
+ path.setAttribute("d", d);
460
+ for (const [node, strokes] of [[aura, AURA], [core, [[shell ? 1.9 : 1.35, 1]]]]) {
461
+ const mask = ringMask(w, h, d, strokes);
462
+ node.style.maskImage = mask;
463
+ node.style.webkitMaskImage = mask;
464
+ }
465
+ item.length = path.getTotalLength();
466
+ radius = round ? 28 : Math.min(260, Math.max(42, item.length * 0.153));
467
+ for (const light of lights) {
468
+ light.radius = radius;
469
+ for (const spot of light.spots) {
470
+ spot.style.width = `${radius * 2}px`;
471
+ spot.style.height = `${radius * 2}px`;
472
+ }
473
+ }
474
+ item.paint(scope?.time || 0);
475
+ };
476
+ const queueMeasurement = () => {
477
+ if (item.destroyed) return;
478
+ measurements.add(item);
479
+ schedule();
480
+ };
481
+ item.observer = createResizeObserver(defer ? queueMeasurement : item.sync);
482
+ item.observer.observe(element);
483
+ if (defer) queueMeasurement();
484
+ else item.sync();
485
+ const unsubscribe = scope?.add(element, item.paint, !defer);
486
+ item.destroy = () => {
487
+ item.destroyed = true;
488
+ measurements.delete(item);
489
+ unsubscribe?.();
490
+ item.observer.disconnect();
491
+ overlay.remove();
492
+ if (item.patchedPosition) element.style.position = item.previousInlinePosition;
493
+ borders.delete(element);
494
+ };
495
+ borders.set(element, item);
496
+ return item;
497
+ };
498
+ U.attachTabShape = (button) => {
499
+ if (seen.has(button)) return seen.get(button);
500
+ const id = U.uid("ad-tab-fill"), shape = U.svg("svg", {
501
+ class: "tab-shape ad-tab-shape",
502
+ "aria-hidden": "true",
503
+ fill: "none",
504
+ preserveAspectRatio: "none"
505
+ });
506
+ const defs = U.svg("defs"), grad = U.svg("linearGradient", { id, x1: 0, y1: 0, x2: 0, y2: 1 });
507
+ [
508
+ [0, "var(--ad-primary-700)", 0.77],
509
+ [0.38, "var(--ad-primary-900)", 0.86],
510
+ [0.76, "var(--ad-primary-900)", 0.94],
511
+ [1, "var(--ad-primary-600)", 0.94]
512
+ ].forEach(
513
+ ([offset, color, opacity]) => grad.append(
514
+ U.svg("stop", { offset, "stop-color": color, "stop-opacity": opacity })
515
+ )
516
+ );
517
+ defs.append(grad);
518
+ shape.append(defs);
519
+ const glow = U.svg("path", { class: "tab-shape__glow" }), edge = U.svg("path", { class: "tab-shape__edge", fill: `url(#${id})` }), floor = U.svg("path", { class: "tab-shape__floor" });
520
+ shape.append(glow, edge, floor);
521
+ const glints = U.svg("svg", {
522
+ class: "tab-shape ad-tab-shape ad-tab-shape-glint",
523
+ "aria-hidden": "true",
524
+ fill: "none",
525
+ preserveAspectRatio: "none"
526
+ });
527
+ const glint = ["wide", "near", "core"].map(
528
+ (part) => U.svg("path", { class: "tab-shape__glint", "data-part": part, pathLength: 100 })
529
+ );
530
+ glints.append(...glint);
531
+ button.prepend(shape, glints);
532
+ button.dataset.adShapeReady = "";
533
+ const position = () => {
534
+ const siblings = [...button.parentElement?.children || []].filter(
535
+ (node) => node instanceof HTMLElement && node.getAttribute("role") === "tab"
536
+ );
537
+ const index = siblings.indexOf(button);
538
+ return {
539
+ first: index === 0,
540
+ last: index === siblings.length - 1,
541
+ single: siblings.length === 1
542
+ };
543
+ };
544
+ const sync = () => {
545
+ const w = button.offsetWidth, h = button.offsetHeight;
546
+ if (!w || !h) return;
547
+ shape.setAttribute("viewBox", `0 0 ${w} ${h}`);
548
+ glints.setAttribute("viewBox", `0 0 ${w} ${h}`);
549
+ const { first, last: last2, single } = position();
550
+ const top = 1.5, bottom = h - 1.5, outer = 1.2;
551
+ const shoulder = Math.min(24, w * 0.11), corner = Math.min(34, w * 0.19), sideLift = Math.min(13, h * 0.28);
552
+ const notchWidth = Math.min(10, w * 0.05), notchDepth = Math.min(3.5, h * 0.08);
553
+ const radius = Math.min(10, h * 0.22, w * 0.05);
554
+ const leftOuter = single || first;
555
+ const rightOuter = single || last2;
556
+ let d = `M${w / 2 - notchWidth} ${bottom}`;
557
+ if (leftOuter) {
558
+ d += `H${outer + radius}Q${outer} ${bottom} ${outer} ${bottom - radius}V${top + radius}Q${outer} ${top} ${outer + radius} ${top}`;
559
+ } else {
560
+ d += `H${outer + 4.5}Q${outer + 1.5} ${bottom - 0.3} ${outer + 4.5} ${bottom - sideLift}L${shoulder} 13Q${shoulder + 4} ${top} ${corner} ${top}`;
561
+ }
562
+ d += `H${rightOuter ? w - (outer + radius) : w - corner}`;
563
+ if (rightOuter) {
564
+ d += `Q${w - outer} ${top} ${w - outer} ${top + radius}V${bottom - radius}Q${w - outer} ${bottom} ${w - (outer + radius)} ${bottom}`;
565
+ } else {
566
+ d += `Q${w - shoulder - 4} ${top} ${w - shoulder} 13L${w - (outer + 4.5)} ${bottom - sideLift}Q${w - (outer + 1.5)} ${bottom - 0.3} ${w - (outer + 4.5)} ${bottom}`;
567
+ }
568
+ d += `H${w / 2 + notchWidth}L${w / 2} ${bottom + notchDepth}L${w / 2 - notchWidth} ${bottom}Z`;
569
+ for (const path of [glow, edge, ...glint]) path.setAttribute("d", d);
570
+ const floorLeft = leftOuter ? outer + radius : outer + 5;
571
+ const floorRight = rightOuter ? w - (outer + radius) : w - (outer + 5);
572
+ floor.setAttribute(
573
+ "d",
574
+ `M${floorLeft} ${bottom}H${w / 2 - notchWidth - 1}L${w / 2} ${bottom + notchDepth}L${w / 2 + notchWidth + 1} ${bottom}H${floorRight}`
575
+ );
576
+ button.dataset.adTabEdge = single ? "single" : first ? "first" : last2 ? "last" : "middle";
577
+ };
578
+ const observer = createResizeObserver(sync);
579
+ observer.observe(button);
580
+ if (button.parentElement) observer.observe(button.parentElement);
581
+ sync();
582
+ const item = {
583
+ observer,
584
+ shape,
585
+ sync,
586
+ destroy() {
587
+ observer.disconnect();
588
+ shape.remove();
589
+ glints.remove();
590
+ button.removeAttribute("data-ad-shape-ready");
591
+ button.removeAttribute("data-ad-tab-edge");
592
+ seen.delete(button);
593
+ }
594
+ };
595
+ seen.set(button, item);
596
+ return item;
597
+ };
598
+ var createMotion = U.createMotion;
599
+ var attachBorder = U.attachBorder;
600
+ var attachTabShape = U.attachTabShape;
601
+ var setMotionFrameRate = U.setMotionFrameRate;
602
+ var subscribeTick = U.subscribeTick;
603
+ function getMotionStats() {
604
+ return {
605
+ scopes: scopeCount,
606
+ running: running.size,
607
+ scheduled: raf !== null || timer !== null,
608
+ callbacks: [...running].reduce((n, s) => n + s.callbacks.size, 0)
609
+ };
610
+ }
611
+
612
+ // src/core/motion/hooks.ts
613
+ import { useEffect, useLayoutEffect, useRef } from "react";
614
+ function useDecoration(ref, paint) {
615
+ const enabled = useMotion();
616
+ const painter = useRef(paint);
617
+ painter.current = paint;
618
+ const scope = useRef(null);
619
+ useLayoutEffect(() => {
620
+ const node = ref.current;
621
+ if (!node) return;
622
+ const controller = createMotion(node);
623
+ scope.current = controller;
624
+ const unsubscribe = controller.add(
625
+ node,
626
+ (time) => painter.current(time)
627
+ );
628
+ return () => {
629
+ unsubscribe();
630
+ controller.dispose();
631
+ scope.current = null;
632
+ };
633
+ }, [ref]);
634
+ useLayoutEffect(() => {
635
+ scope.current?.set(enabled);
636
+ }, [enabled]);
637
+ }
638
+ function useBorder(ref, enabled = true, shell = false, round = false) {
639
+ const motion = useMotion();
640
+ const scope = useRef(null);
641
+ useLayoutEffect(() => {
642
+ const node = ref.current;
643
+ if (!node || !enabled) return;
644
+ const controller = createMotion(node);
645
+ scope.current = controller;
646
+ const border = attachBorder(node, { shell, round, scope: controller, defer: true });
647
+ return () => {
648
+ border.destroy();
649
+ controller.dispose();
650
+ scope.current = null;
651
+ };
652
+ }, [ref, enabled, shell, round]);
653
+ useLayoutEffect(() => {
654
+ scope.current?.set(motion);
655
+ }, [motion, enabled, shell, round]);
656
+ }
657
+ function useTick(callback, active2 = true) {
658
+ const latest = useRef(callback);
659
+ latest.current = callback;
660
+ useEffect(() => {
661
+ if (!active2) return;
662
+ return subscribeTick((now) => latest.current(now));
663
+ }, [active2]);
664
+ }
665
+ var offscreenObserver = null;
666
+ var offscreenCount = 0;
667
+ var watchOffscreen = (node) => {
668
+ if (typeof IntersectionObserver === "undefined") return () => void 0;
669
+ offscreenObserver ??= new IntersectionObserver(
670
+ (entries) => {
671
+ for (const entry of entries) entry.target.toggleAttribute("data-ad-offscreen", !entry.isIntersecting);
672
+ refreshMotion();
673
+ },
674
+ { rootMargin: "12% 0px" }
675
+ );
676
+ offscreenObserver.observe(node);
677
+ offscreenCount++;
678
+ return () => {
679
+ offscreenObserver?.unobserve(node);
680
+ if (--offscreenCount === 0) {
681
+ offscreenObserver?.disconnect();
682
+ offscreenObserver = null;
683
+ }
684
+ node.removeAttribute("data-ad-offscreen");
685
+ refreshMotion();
686
+ };
687
+ };
688
+ function usePauseOffscreen(ref) {
689
+ useLayoutEffect(() => {
690
+ const node = ref.current;
691
+ if (!node) return;
692
+ return watchOffscreen(node);
693
+ }, [ref]);
694
+ }
695
+ function useTabShape(ref) {
696
+ useLayoutEffect(() => {
697
+ const node = ref.current;
698
+ if (!node) return;
699
+ const shape = attachTabShape(node);
700
+ return () => shape.destroy();
701
+ }, [ref]);
702
+ }
703
+ function useSmoothWheel(ref) {
704
+ const enabled = useMotion();
705
+ useEffect(() => {
706
+ const element = ref.current;
707
+ if (!element || !enabled || reducedMotionQuery().matches)
708
+ return;
709
+ let target = element.scrollTop;
710
+ let position = target;
711
+ let applied = target;
712
+ let frame = 0;
713
+ let last2 = 0;
714
+ const stop = () => {
715
+ cancelAnimationFrame(frame);
716
+ frame = 0;
717
+ last2 = 0;
718
+ };
719
+ const glide = (now) => {
720
+ const shift = element.scrollTop - applied;
721
+ if (Math.abs(shift) > 1.5) {
722
+ position += shift;
723
+ target += shift;
724
+ }
725
+ const elapsed = Math.min(64, now - (last2 || now - 16));
726
+ last2 = now;
727
+ target = Math.max(
728
+ 0,
729
+ Math.min(element.scrollHeight - element.clientHeight, target)
730
+ );
731
+ position += (target - position) * (1 - Math.exp(-elapsed / 95));
732
+ if (Math.abs(target - position) < 0.25) position = target;
733
+ element.scrollTop = position;
734
+ applied = element.scrollTop;
735
+ if (position === target) return stop();
736
+ frame = requestAnimationFrame(glide);
737
+ };
738
+ const onWheel = (event) => {
739
+ if (event.defaultPrevented || event.ctrlKey || Math.abs(event.deltaX) > Math.abs(event.deltaY))
740
+ return;
741
+ const delta = event.deltaMode === 1 ? event.deltaY * 16 : event.deltaY;
742
+ if (event.deltaMode === 0 && Math.abs(delta) < 40) return;
743
+ for (let node = event.target; node && node !== element; node = node.parentElement) {
744
+ const canScroll = node.scrollHeight > node.clientHeight + 1 && /auto|scroll/.test(getComputedStyle(node).overflowY);
745
+ if (canScroll && (delta < 0 ? node.scrollTop > 0 : node.scrollTop + node.clientHeight < node.scrollHeight - 1))
746
+ return;
747
+ }
748
+ if (element.scrollHeight <= element.clientHeight + 1 || !/auto|scroll/.test(getComputedStyle(element).overflowY))
749
+ return;
750
+ event.preventDefault();
751
+ if (!frame) target = position = applied = element.scrollTop;
752
+ target = Math.max(
753
+ 0,
754
+ Math.min(element.scrollHeight - element.clientHeight, target + delta)
755
+ );
756
+ if (!frame) frame = requestAnimationFrame(glide);
757
+ };
758
+ element.addEventListener("wheel", onWheel, { passive: false });
759
+ return () => {
760
+ element.removeEventListener("wheel", onWheel);
761
+ stop();
762
+ };
763
+ }, [ref, enabled]);
764
+ }
765
+
766
+ export {
767
+ refreshMotion,
768
+ setMotionFrameRate,
769
+ subscribeTick,
770
+ getMotionStats,
771
+ useDecoration,
772
+ useBorder,
773
+ useTick,
774
+ usePauseOffscreen,
775
+ useTabShape,
776
+ useSmoothWheel
777
+ };