@luanthnh/cntt-ui 0.1.7 → 0.1.9

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 (238) hide show
  1. package/package.json +5 -1
  2. package/.storybook/globals.d.ts +0 -1
  3. package/.storybook/main.ts +0 -29
  4. package/.storybook/preview.ts +0 -32
  5. package/assets/fonts/Montserrat-Black.eot +0 -0
  6. package/assets/fonts/Montserrat-Black.ttf +0 -0
  7. package/assets/fonts/Montserrat-Black.woff +0 -0
  8. package/assets/fonts/Montserrat-Black.woff2 +0 -0
  9. package/assets/fonts/Montserrat-BlackItalic.eot +0 -0
  10. package/assets/fonts/Montserrat-BlackItalic.ttf +0 -0
  11. package/assets/fonts/Montserrat-BlackItalic.woff +0 -0
  12. package/assets/fonts/Montserrat-BlackItalic.woff2 +0 -0
  13. package/assets/fonts/Montserrat-Bold.eot +0 -0
  14. package/assets/fonts/Montserrat-Bold.ttf +0 -0
  15. package/assets/fonts/Montserrat-Bold.woff +0 -0
  16. package/assets/fonts/Montserrat-Bold.woff2 +0 -0
  17. package/assets/fonts/Montserrat-BoldItalic.eot +0 -0
  18. package/assets/fonts/Montserrat-BoldItalic.ttf +0 -0
  19. package/assets/fonts/Montserrat-BoldItalic.woff +0 -0
  20. package/assets/fonts/Montserrat-BoldItalic.woff2 +0 -0
  21. package/assets/fonts/Montserrat-ExtraBold.eot +0 -0
  22. package/assets/fonts/Montserrat-ExtraBold.ttf +0 -0
  23. package/assets/fonts/Montserrat-ExtraBold.woff +0 -0
  24. package/assets/fonts/Montserrat-ExtraBold.woff2 +0 -0
  25. package/assets/fonts/Montserrat-ExtraBoldItalic.eot +0 -0
  26. package/assets/fonts/Montserrat-ExtraBoldItalic.ttf +0 -0
  27. package/assets/fonts/Montserrat-ExtraBoldItalic.woff +0 -0
  28. package/assets/fonts/Montserrat-ExtraBoldItalic.woff2 +0 -0
  29. package/assets/fonts/Montserrat-ExtraLight.eot +0 -0
  30. package/assets/fonts/Montserrat-ExtraLight.ttf +0 -0
  31. package/assets/fonts/Montserrat-ExtraLight.woff +0 -0
  32. package/assets/fonts/Montserrat-ExtraLight.woff2 +0 -0
  33. package/assets/fonts/Montserrat-ExtraLightItalic.eot +0 -0
  34. package/assets/fonts/Montserrat-ExtraLightItalic.ttf +0 -0
  35. package/assets/fonts/Montserrat-ExtraLightItalic.woff +0 -0
  36. package/assets/fonts/Montserrat-ExtraLightItalic.woff2 +0 -0
  37. package/assets/fonts/Montserrat-Italic.eot +0 -0
  38. package/assets/fonts/Montserrat-Italic.ttf +0 -0
  39. package/assets/fonts/Montserrat-Italic.woff +0 -0
  40. package/assets/fonts/Montserrat-Italic.woff2 +0 -0
  41. package/assets/fonts/Montserrat-Light.eot +0 -0
  42. package/assets/fonts/Montserrat-Light.ttf +0 -0
  43. package/assets/fonts/Montserrat-Light.woff +0 -0
  44. package/assets/fonts/Montserrat-Light.woff2 +0 -0
  45. package/assets/fonts/Montserrat-LightItalic.eot +0 -0
  46. package/assets/fonts/Montserrat-LightItalic.ttf +0 -0
  47. package/assets/fonts/Montserrat-LightItalic.woff +0 -0
  48. package/assets/fonts/Montserrat-LightItalic.woff2 +0 -0
  49. package/assets/fonts/Montserrat-Medium.eot +0 -0
  50. package/assets/fonts/Montserrat-Medium.ttf +0 -0
  51. package/assets/fonts/Montserrat-Medium.woff +0 -0
  52. package/assets/fonts/Montserrat-Medium.woff2 +0 -0
  53. package/assets/fonts/Montserrat-MediumItalic.eot +0 -0
  54. package/assets/fonts/Montserrat-MediumItalic.ttf +0 -0
  55. package/assets/fonts/Montserrat-MediumItalic.woff +0 -0
  56. package/assets/fonts/Montserrat-MediumItalic.woff2 +0 -0
  57. package/assets/fonts/Montserrat-Regular.eot +0 -0
  58. package/assets/fonts/Montserrat-Regular.ttf +0 -0
  59. package/assets/fonts/Montserrat-Regular.woff +0 -0
  60. package/assets/fonts/Montserrat-Regular.woff2 +0 -0
  61. package/assets/fonts/Montserrat-SemiBold.eot +0 -0
  62. package/assets/fonts/Montserrat-SemiBold.ttf +0 -0
  63. package/assets/fonts/Montserrat-SemiBold.woff +0 -0
  64. package/assets/fonts/Montserrat-SemiBold.woff2 +0 -0
  65. package/assets/fonts/Montserrat-SemiBoldItalic.eot +0 -0
  66. package/assets/fonts/Montserrat-SemiBoldItalic.ttf +0 -0
  67. package/assets/fonts/Montserrat-SemiBoldItalic.woff +0 -0
  68. package/assets/fonts/Montserrat-SemiBoldItalic.woff2 +0 -0
  69. package/assets/fonts/Montserrat-Thin.eot +0 -0
  70. package/assets/fonts/Montserrat-Thin.ttf +0 -0
  71. package/assets/fonts/Montserrat-Thin.woff +0 -0
  72. package/assets/fonts/Montserrat-Thin.woff2 +0 -0
  73. package/assets/fonts/Montserrat-ThinItalic.eot +0 -0
  74. package/assets/fonts/Montserrat-ThinItalic.ttf +0 -0
  75. package/assets/fonts/Montserrat-ThinItalic.woff +0 -0
  76. package/assets/fonts/Montserrat-ThinItalic.woff2 +0 -0
  77. package/assets/fonts/Montserrat-Variable.eot +0 -0
  78. package/assets/fonts/Montserrat-Variable.ttf +0 -0
  79. package/assets/fonts/Montserrat-Variable.woff +0 -0
  80. package/assets/fonts/Montserrat-Variable.woff2 +0 -0
  81. package/assets/fonts/Montserrat-VariableItalic.eot +0 -0
  82. package/assets/fonts/Montserrat-VariableItalic.ttf +0 -0
  83. package/assets/fonts/Montserrat-VariableItalic.woff +0 -0
  84. package/assets/fonts/Montserrat-VariableItalic.woff2 +0 -0
  85. package/assets/icons/arrow-left.svg +0 -1
  86. package/assets/icons/file.svg +0 -1
  87. package/assets/icons/globe.svg +0 -1
  88. package/assets/icons/logo-line.svg +0 -1
  89. package/assets/icons/next.svg +0 -1
  90. package/assets/icons/panel-left-expand.svg +0 -1
  91. package/assets/icons/placeholder.svg +0 -57
  92. package/assets/icons/vercel.svg +0 -1
  93. package/assets/icons/window.svg +0 -1
  94. package/assets/lotties/error-404.json +0 -19642
  95. package/assets/lotties/error.json +0 -2414
  96. package/assets/lotties/loader.json +0 -305
  97. package/components/Welcome.mdx +0 -74
  98. package/components/lenis/index.tsx +0 -48
  99. package/components/motion/auto-height.tsx +0 -56
  100. package/components/motion/cursor.tsx +0 -108
  101. package/components/motion/highlight.tsx +0 -605
  102. package/components/motion/number-ticker.tsx +0 -55
  103. package/components/motion/slot.tsx +0 -106
  104. package/components/motion/waves.tsx +0 -417
  105. package/components/primitives/tabs.tsx +0 -174
  106. package/components/ui/Accordion/index.stories.tsx +0 -39
  107. package/components/ui/Accordion/index.tsx +0 -170
  108. package/components/ui/Alert/index.stories.tsx +0 -39
  109. package/components/ui/Alert/index.tsx +0 -60
  110. package/components/ui/AlertDialog/index.stories.tsx +0 -47
  111. package/components/ui/AlertDialog/index.tsx +0 -172
  112. package/components/ui/AspectRatio/index.stories.tsx +0 -40
  113. package/components/ui/AspectRatio/index.tsx +0 -9
  114. package/components/ui/Avatar/index.stories.tsx +0 -39
  115. package/components/ui/Avatar/index.tsx +0 -44
  116. package/components/ui/Badge/index.stories.tsx +0 -64
  117. package/components/ui/Badge/index.tsx +0 -46
  118. package/components/ui/Breadcrumb/index.stories.tsx +0 -64
  119. package/components/ui/Breadcrumb/index.tsx +0 -102
  120. package/components/ui/Button/index.stories.tsx +0 -232
  121. package/components/ui/Button/index.tsx +0 -114
  122. package/components/ui/Calendar/index.stories.tsx +0 -20
  123. package/components/ui/Calendar/index.tsx +0 -149
  124. package/components/ui/Card/index.stories.tsx +0 -39
  125. package/components/ui/Card/index.tsx +0 -65
  126. package/components/ui/Carousel/index.stories.tsx +0 -37
  127. package/components/ui/Carousel/index.tsx +0 -242
  128. package/components/ui/Chart/index.stories.tsx +0 -53
  129. package/components/ui/Chart/index.tsx +0 -322
  130. package/components/ui/Checkbox/index.stories.tsx +0 -56
  131. package/components/ui/Checkbox/index.tsx +0 -167
  132. package/components/ui/CircleProcess/index.stories.tsx +0 -29
  133. package/components/ui/CircleProcess/index.tsx +0 -50
  134. package/components/ui/Collapsible/index.stories.tsx +0 -33
  135. package/components/ui/Collapsible/index.tsx +0 -124
  136. package/components/ui/Command/index.stories.tsx +0 -65
  137. package/components/ui/Command/index.tsx +0 -161
  138. package/components/ui/Container/index.stories.tsx +0 -22
  139. package/components/ui/Container/index.tsx +0 -30
  140. package/components/ui/ContextMenu/index.stories.tsx +0 -51
  141. package/components/ui/ContextMenu/index.tsx +0 -224
  142. package/components/ui/Dialog/index.stories.tsx +0 -44
  143. package/components/ui/Dialog/index.tsx +0 -156
  144. package/components/ui/Drawer/index.stories.tsx +0 -54
  145. package/components/ui/Drawer/index.tsx +0 -124
  146. package/components/ui/DropdownMenu/index.stories.tsx +0 -83
  147. package/components/ui/DropdownMenu/index.tsx +0 -231
  148. package/components/ui/Dropzone/index.stories.tsx +0 -18
  149. package/components/ui/Dropzone/index.tsx +0 -47
  150. package/components/ui/Form/date-field.tsx +0 -77
  151. package/components/ui/Form/index.stories.tsx +0 -67
  152. package/components/ui/Form/index.tsx +0 -188
  153. package/components/ui/Form/select-field.tsx +0 -55
  154. package/components/ui/Form/text-area-field.tsx +0 -37
  155. package/components/ui/Form/text-field.tsx +0 -72
  156. package/components/ui/HStack/index.stories.tsx +0 -48
  157. package/components/ui/HStack/index.tsx +0 -73
  158. package/components/ui/HoverCard/index.stories.tsx +0 -38
  159. package/components/ui/HoverCard/index.tsx +0 -38
  160. package/components/ui/Icons/index.stories.tsx +0 -27
  161. package/components/ui/Icons/index.tsx +0 -33
  162. package/components/ui/ImageWithFallback/index.stories.tsx +0 -32
  163. package/components/ui/ImageWithFallback/index.tsx +0 -34
  164. package/components/ui/Input/index.stories.tsx +0 -47
  165. package/components/ui/Input/index.tsx +0 -21
  166. package/components/ui/InputOtp/index.stories.tsx +0 -35
  167. package/components/ui/InputOtp/index.tsx +0 -70
  168. package/components/ui/Label/index.stories.tsx +0 -18
  169. package/components/ui/Label/index.tsx +0 -21
  170. package/components/ui/Marquee/index.stories.tsx +0 -71
  171. package/components/ui/Marquee/index.tsx +0 -65
  172. package/components/ui/Menubar/index.stories.tsx +0 -116
  173. package/components/ui/Menubar/index.tsx +0 -252
  174. package/components/ui/NavigationMenu/index.stories.tsx +0 -112
  175. package/components/ui/NavigationMenu/index.tsx +0 -185
  176. package/components/ui/NoData/index.stories.tsx +0 -24
  177. package/components/ui/NoData/index.tsx +0 -19
  178. package/components/ui/Pagination/index.stories.tsx +0 -53
  179. package/components/ui/Pagination/index.tsx +0 -114
  180. package/components/ui/Popover/index.stories.tsx +0 -31
  181. package/components/ui/Popover/index.tsx +0 -42
  182. package/components/ui/Progress/index.stories.tsx +0 -35
  183. package/components/ui/Progress/index.tsx +0 -28
  184. package/components/ui/RadioGroup/index.stories.tsx +0 -28
  185. package/components/ui/RadioGroup/index.tsx +0 -45
  186. package/components/ui/Resizable/index.stories.tsx +0 -44
  187. package/components/ui/Resizable/index.tsx +0 -54
  188. package/components/ui/ScrollArea/index.stories.tsx +0 -31
  189. package/components/ui/ScrollArea/index.tsx +0 -56
  190. package/components/ui/Select/index.stories.tsx +0 -64
  191. package/components/ui/Select/index.tsx +0 -170
  192. package/components/ui/Separator/index.stories.tsx +0 -31
  193. package/components/ui/Separator/index.tsx +0 -28
  194. package/components/ui/Sheet/index.stories.tsx +0 -45
  195. package/components/ui/Sheet/index.tsx +0 -130
  196. package/components/ui/Sidebar/index.stories.tsx +0 -82
  197. package/components/ui/Sidebar/index.tsx +0 -676
  198. package/components/ui/Skeleton/index.stories.tsx +0 -36
  199. package/components/ui/Skeleton/index.tsx +0 -13
  200. package/components/ui/Slider/index.stories.tsx +0 -48
  201. package/components/ui/Slider/index.tsx +0 -82
  202. package/components/ui/Slot/index.stories.tsx +0 -29
  203. package/components/ui/Slot/index.tsx +0 -106
  204. package/components/ui/Sonner/index.stories.tsx +0 -36
  205. package/components/ui/Sonner/index.tsx +0 -31
  206. package/components/ui/Switch/index.stories.tsx +0 -33
  207. package/components/ui/Switch/index.tsx +0 -28
  208. package/components/ui/Table/index.stories.tsx +0 -74
  209. package/components/ui/Table/index.tsx +0 -95
  210. package/components/ui/Tabs/index.stories.tsx +0 -38
  211. package/components/ui/Tabs/index.tsx +0 -78
  212. package/components/ui/Text/index.stories.tsx +0 -53
  213. package/components/ui/Text/index.tsx +0 -138
  214. package/components/ui/Textarea/index.stories.tsx +0 -25
  215. package/components/ui/Textarea/index.tsx +0 -18
  216. package/components/ui/Toggle/index.stories.tsx +0 -52
  217. package/components/ui/Toggle/index.tsx +0 -46
  218. package/components/ui/ToggleGroup/index.stories.tsx +0 -52
  219. package/components/ui/ToggleGroup/index.tsx +0 -69
  220. package/components/ui/Tooltip/index.stories.tsx +0 -29
  221. package/components/ui/Tooltip/index.tsx +0 -35
  222. package/components/ui/VStack/index.stories.tsx +0 -45
  223. package/components/ui/VStack/index.tsx +0 -69
  224. package/components/ui/colors.stories.tsx +0 -148
  225. package/eslint.config.js +0 -10
  226. package/hooks/index.ts +0 -3
  227. package/hooks/use-auto-height.tsx +0 -99
  228. package/hooks/use-controlled-state.tsx +0 -32
  229. package/hooks/use-mobile.ts +0 -19
  230. package/index.ts +0 -58
  231. package/lib/get-strict-context.ts +0 -15
  232. package/lib/utils.ts +0 -10
  233. package/scripts/generate-exports.ts +0 -32
  234. package/tsconfig.json +0 -12
  235. package/tsconfig.tsbuildinfo +0 -1
  236. package/tsup.config.ts +0 -11
  237. package/types/svg.d.ts +0 -10
  238. package/vercel.json +0 -5
@@ -1,106 +0,0 @@
1
- 'use client';
2
-
3
- import * as React from 'react';
4
- import { isMotionComponent, motion, type HTMLMotionProps } from 'motion/react';
5
-
6
- import { cn } from '@/lib/utils';
7
-
8
- type AnyProps = Record<string, unknown>;
9
-
10
- type DOMMotionProps<T extends HTMLElement = HTMLElement> = Omit<
11
- HTMLMotionProps<keyof HTMLElementTagNameMap>,
12
- 'ref'
13
- > & {
14
- ref?: React.Ref<T>;
15
- };
16
-
17
- type WithAsChild<Base extends object> =
18
- | (Base & { asChild: true; children: React.ReactElement })
19
- | (Base & { asChild?: false | undefined });
20
-
21
- type SlotProps<T extends HTMLElement = HTMLElement> = {
22
- children?: React.ReactElement;
23
- } & DOMMotionProps<T>;
24
-
25
- function mergeRefs<T>(...refs: (React.Ref<T> | undefined)[]): React.RefCallback<T> {
26
- return (node) => {
27
- refs.forEach((ref) => {
28
- if (!ref) return;
29
- if (typeof ref === 'function') {
30
- ref(node);
31
- } else {
32
- (ref as React.RefObject<T | null>).current = node;
33
- }
34
- });
35
- };
36
- }
37
-
38
- const motionComponentCache = new Map<React.ElementType, React.ElementType>();
39
-
40
- function getMotionComponent(Component: React.ElementType): React.ElementType {
41
- if (!motionComponentCache.has(Component)) {
42
- motionComponentCache.set(Component, motion.create(Component));
43
- }
44
- return motionComponentCache.get(Component)!;
45
- }
46
-
47
- function mergeProps<T extends HTMLElement>(
48
- childProps: AnyProps,
49
- slotProps: DOMMotionProps<T>,
50
- ): AnyProps {
51
- const merged: AnyProps = { ...childProps, ...slotProps };
52
-
53
- if (childProps.className || slotProps.className) {
54
- merged.className = cn(childProps.className as string, slotProps.className as string);
55
- }
56
-
57
- if (childProps.style || slotProps.style) {
58
- merged.style = {
59
- ...(childProps.style as React.CSSProperties),
60
- ...(slotProps.style as React.CSSProperties),
61
- };
62
- }
63
-
64
- return merged;
65
- }
66
-
67
- function Slot<T extends HTMLElement = HTMLElement>({ children, ...props }: SlotProps<T>) {
68
- const isValidElement = React.isValidElement(children);
69
- const childType = isValidElement ? children.type : null;
70
- const isAlreadyMotion =
71
- isValidElement &&
72
- childType !== null &&
73
- typeof childType === 'object' &&
74
- isMotionComponent(childType);
75
-
76
- const Base = React.useMemo(() => {
77
- if (!isValidElement || !childType) return null;
78
- return isAlreadyMotion
79
- ? (childType as React.ElementType)
80
- : getMotionComponent(childType as React.ElementType);
81
- }, [isValidElement, isAlreadyMotion, childType]);
82
-
83
- const childRef = isValidElement && children ? (children.props as AnyProps).ref : undefined;
84
- const childProps =
85
- isValidElement && children
86
- ? (({ ref: _ref, ...rest }) => rest)(children.props as AnyProps)
87
- : {};
88
-
89
- const mergedRef = React.useCallback(
90
- (node: T | null) => {
91
- mergeRefs(childRef as React.Ref<T>, props.ref)(node);
92
- },
93
- [childRef, props.ref],
94
- );
95
-
96
- if (!isValidElement || !Base || !children) return null;
97
-
98
- const mergedProps = mergeProps(childProps, props);
99
-
100
- return React.createElement(Base, {
101
- ...mergedProps,
102
- ref: mergedRef,
103
- });
104
- }
105
-
106
- export { Slot, type SlotProps, type WithAsChild, type DOMMotionProps, type AnyProps };
@@ -1,417 +0,0 @@
1
- import React, { CSSProperties, useEffect, useRef } from 'react';
2
-
3
- const RANDOM_SEED = Math.random();
4
-
5
- class Grad {
6
- x: number;
7
- y: number;
8
- z: number;
9
- constructor(x: number, y: number, z: number) {
10
- this.x = x;
11
- this.y = y;
12
- this.z = z;
13
- }
14
- dot2(x: number, y: number): number {
15
- return this.x * x + this.y * y;
16
- }
17
- }
18
-
19
- class Noise {
20
- grad3: Grad[];
21
- p: number[];
22
- perm: number[];
23
- gradP: Grad[];
24
-
25
- constructor(seed = 0) {
26
- this.grad3 = [
27
- new Grad(1, 1, 0),
28
- new Grad(-1, 1, 0),
29
- new Grad(1, -1, 0),
30
- new Grad(-1, -1, 0),
31
- new Grad(1, 0, 1),
32
- new Grad(-1, 0, 1),
33
- new Grad(1, 0, -1),
34
- new Grad(-1, 0, -1),
35
- new Grad(0, 1, 1),
36
- new Grad(0, -1, 1),
37
- new Grad(0, 1, -1),
38
- new Grad(0, -1, -1),
39
- ];
40
- this.p = [
41
- 151, 160, 137, 91, 90, 15, 131, 13, 201, 95, 96, 53, 194, 233, 7, 225, 140, 36, 103, 30, 69,
42
- 142, 8, 99, 37, 240, 21, 10, 23, 190, 6, 148, 247, 120, 234, 75, 0, 26, 197, 62, 94, 252, 219,
43
- 203, 117, 35, 11, 32, 57, 177, 33, 88, 237, 149, 56, 87, 174, 20, 125, 136, 171, 168, 68, 175,
44
- 74, 165, 71, 134, 139, 48, 27, 166, 77, 146, 158, 231, 83, 111, 229, 122, 60, 211, 133, 230,
45
- 220, 105, 92, 41, 55, 46, 245, 40, 244, 102, 143, 54, 65, 25, 63, 161, 1, 216, 80, 73, 209,
46
- 76, 132, 187, 208, 89, 18, 169, 200, 196, 135, 130, 116, 188, 159, 86, 164, 100, 109, 198,
47
- 173, 186, 3, 64, 52, 217, 226, 250, 124, 123, 5, 202, 38, 147, 118, 126, 255, 82, 85, 212,
48
- 207, 206, 59, 227, 47, 16, 58, 17, 182, 189, 28, 42, 223, 183, 170, 213, 119, 248, 152, 2, 44,
49
- 154, 163, 70, 221, 153, 101, 155, 167, 43, 172, 9, 129, 22, 39, 253, 19, 98, 108, 110, 79,
50
- 113, 224, 232, 178, 185, 112, 104, 218, 246, 97, 228, 251, 34, 242, 193, 238, 210, 144, 12,
51
- 191, 179, 162, 241, 81, 51, 145, 235, 249, 14, 239, 107, 49, 192, 214, 31, 181, 199, 106, 157,
52
- 184, 84, 204, 176, 115, 121, 50, 45, 127, 4, 150, 254, 138, 236, 205, 93, 222, 114, 67, 29,
53
- 24, 72, 243, 141, 128, 195, 78, 66, 215, 61, 156, 180,
54
- ];
55
- this.perm = new Array(512);
56
- this.gradP = new Array(512);
57
- this.seed(seed);
58
- }
59
- seed(seed: number) {
60
- if (seed > 0 && seed < 1) seed *= 65536;
61
- seed = Math.floor(seed);
62
- if (seed < 256) seed |= seed << 8;
63
- for (let i = 0; i < 256; i++) {
64
- const v = i & 1 ? this.p[i] ^ (seed & 255) : this.p[i] ^ ((seed >> 8) & 255);
65
- this.perm[i] = this.perm[i + 256] = v;
66
- this.gradP[i] = this.gradP[i + 256] = this.grad3[v % 12];
67
- }
68
- }
69
- fade(t: number): number {
70
- return t * t * t * (t * (t * 6 - 15) + 10);
71
- }
72
- lerp(a: number, b: number, t: number): number {
73
- return (1 - t) * a + t * b;
74
- }
75
- perlin2(x: number, y: number): number {
76
- let X = Math.floor(x),
77
- Y = Math.floor(y);
78
- x -= X;
79
- y -= Y;
80
- X &= 255;
81
- Y &= 255;
82
- const n00 = this.gradP[X + this.perm[Y]].dot2(x, y);
83
- const n01 = this.gradP[X + this.perm[Y + 1]].dot2(x, y - 1);
84
- const n10 = this.gradP[X + 1 + this.perm[Y]].dot2(x - 1, y);
85
- const n11 = this.gradP[X + 1 + this.perm[Y + 1]].dot2(x - 1, y - 1);
86
- const u = this.fade(x);
87
- return this.lerp(this.lerp(n00, n10, u), this.lerp(n01, n11, u), this.fade(y));
88
- }
89
- }
90
-
91
- interface Point {
92
- x: number;
93
- y: number;
94
- wave: { x: number; y: number };
95
- cursor: { x: number; y: number; vx: number; vy: number };
96
- }
97
-
98
- interface Mouse {
99
- x: number;
100
- y: number;
101
- lx: number;
102
- ly: number;
103
- sx: number;
104
- sy: number;
105
- v: number;
106
- vs: number;
107
- a: number;
108
- set: boolean;
109
- }
110
-
111
- interface Config {
112
- lineColor: string;
113
- waveSpeedX: number;
114
- waveSpeedY: number;
115
- waveAmpX: number;
116
- waveAmpY: number;
117
- friction: number;
118
- tension: number;
119
- maxCursorMove: number;
120
- xGap: number;
121
- yGap: number;
122
- }
123
-
124
- interface WavesProps {
125
- lineColor?: string;
126
- backgroundColor?: string;
127
- waveSpeedX?: number;
128
- waveSpeedY?: number;
129
- waveAmpX?: number;
130
- waveAmpY?: number;
131
- xGap?: number;
132
- yGap?: number;
133
- friction?: number;
134
- tension?: number;
135
- maxCursorMove?: number;
136
- style?: CSSProperties;
137
- className?: string;
138
- }
139
-
140
- const Waves: React.FC<WavesProps> = ({
141
- lineColor = '#e4e7ff',
142
- backgroundColor = 'transparent',
143
- waveSpeedX = 0.0125,
144
- waveSpeedY = 0.005,
145
- waveAmpX = 32,
146
- waveAmpY = 16,
147
- xGap = 10,
148
- yGap = 32,
149
- friction = 0.925,
150
- tension = 0.005,
151
- maxCursorMove = 100,
152
- style = {},
153
- className = '',
154
- }) => {
155
- const containerRef = useRef<HTMLDivElement>(null);
156
- const canvasRef = useRef<HTMLCanvasElement>(null);
157
- const ctxRef = useRef<CanvasRenderingContext2D | null>(null);
158
- const boundingRef = useRef<{
159
- width: number;
160
- height: number;
161
- left: number;
162
- top: number;
163
- }>({
164
- width: 0,
165
- height: 0,
166
- left: 0,
167
- top: 0,
168
- });
169
- const noiseRef = useRef(new Noise(RANDOM_SEED));
170
- const linesRef = useRef<Point[][]>([]);
171
- const mouseRef = useRef<Mouse>({
172
- x: -10,
173
- y: 0,
174
- lx: 0,
175
- ly: 0,
176
- sx: 0,
177
- sy: 0,
178
- v: 0,
179
- vs: 0,
180
- a: 0,
181
- set: false,
182
- });
183
-
184
- const configRef = useRef<Config>({
185
- lineColor,
186
- waveSpeedX,
187
- waveSpeedY,
188
- waveAmpX,
189
- waveAmpY,
190
- friction,
191
- tension,
192
- maxCursorMove,
193
- xGap,
194
- yGap,
195
- });
196
-
197
- const frameIdRef = useRef<number | null>(null);
198
-
199
- useEffect(() => {
200
- configRef.current = {
201
- lineColor,
202
- waveSpeedX,
203
- waveSpeedY,
204
- waveAmpX,
205
- waveAmpY,
206
- friction,
207
- tension,
208
- maxCursorMove,
209
- xGap,
210
- yGap,
211
- };
212
- }, [
213
- lineColor,
214
- waveSpeedX,
215
- waveSpeedY,
216
- waveAmpX,
217
- waveAmpY,
218
- friction,
219
- tension,
220
- maxCursorMove,
221
- xGap,
222
- yGap,
223
- ]);
224
-
225
- useEffect(() => {
226
- const canvas = canvasRef.current;
227
- const container = containerRef.current;
228
- if (!canvas || !container) return;
229
- ctxRef.current = canvas.getContext('2d');
230
-
231
- function setSize() {
232
- if (!container || !canvas) return;
233
- const rect = container.getBoundingClientRect();
234
- boundingRef.current = {
235
- width: rect.width,
236
- height: rect.height,
237
- left: rect.left,
238
- top: rect.top,
239
- };
240
- canvas.width = rect.width;
241
- canvas.height = rect.height;
242
- }
243
-
244
- function setLines() {
245
- const { width, height } = boundingRef.current;
246
- linesRef.current = [];
247
- const oWidth = width + 200,
248
- oHeight = height + 30;
249
- const { xGap, yGap } = configRef.current;
250
- const totalLines = Math.ceil(oWidth / xGap);
251
- const totalPoints = Math.ceil(oHeight / yGap);
252
- const xStart = (width - xGap * totalLines) / 2;
253
- const yStart = (height - yGap * totalPoints) / 2;
254
- for (let i = 0; i <= totalLines; i++) {
255
- const pts: Point[] = [];
256
- for (let j = 0; j <= totalPoints; j++) {
257
- pts.push({
258
- x: xStart + xGap * i,
259
- y: yStart + yGap * j,
260
- wave: { x: 0, y: 0 },
261
- cursor: { x: 0, y: 0, vx: 0, vy: 0 },
262
- });
263
- }
264
- linesRef.current.push(pts);
265
- }
266
- }
267
-
268
- function movePoints(time: number) {
269
- const lines = linesRef.current;
270
- const mouse = mouseRef.current;
271
- const noise = noiseRef.current;
272
- const { waveSpeedX, waveSpeedY, waveAmpX, waveAmpY, friction, tension, maxCursorMove } =
273
- configRef.current;
274
- lines.forEach((pts) => {
275
- pts.forEach((p) => {
276
- const move =
277
- noise.perlin2((p.x + time * waveSpeedX) * 0.002, (p.y + time * waveSpeedY) * 0.0015) *
278
- 12;
279
- p.wave.x = Math.cos(move) * waveAmpX;
280
- p.wave.y = Math.sin(move) * waveAmpY;
281
-
282
- const dx = p.x - mouse.sx,
283
- dy = p.y - mouse.sy;
284
- const dist = Math.hypot(dx, dy);
285
- const l = Math.max(175, mouse.vs);
286
- if (dist < l) {
287
- const s = 1 - dist / l;
288
- const f = Math.cos(dist * 0.001) * s;
289
- p.cursor.vx += Math.cos(mouse.a) * f * l * mouse.vs * 0.00065;
290
- p.cursor.vy += Math.sin(mouse.a) * f * l * mouse.vs * 0.00065;
291
- }
292
-
293
- p.cursor.vx += (0 - p.cursor.x) * tension;
294
- p.cursor.vy += (0 - p.cursor.y) * tension;
295
- p.cursor.vx *= friction;
296
- p.cursor.vy *= friction;
297
- p.cursor.x += p.cursor.vx * 2;
298
- p.cursor.y += p.cursor.vy * 2;
299
- p.cursor.x = Math.min(maxCursorMove, Math.max(-maxCursorMove, p.cursor.x));
300
- p.cursor.y = Math.min(maxCursorMove, Math.max(-maxCursorMove, p.cursor.y));
301
- });
302
- });
303
- }
304
-
305
- function moved(point: Point, withCursor = true): { x: number; y: number } {
306
- const x = point.x + point.wave.x + (withCursor ? point.cursor.x : 0);
307
- const y = point.y + point.wave.y + (withCursor ? point.cursor.y : 0);
308
- return { x: Math.round(x * 10) / 10, y: Math.round(y * 10) / 10 };
309
- }
310
-
311
- function drawLines() {
312
- const { width, height } = boundingRef.current;
313
- const ctx = ctxRef.current;
314
- if (!ctx) return;
315
- ctx.clearRect(0, 0, width, height);
316
- ctx.beginPath();
317
- ctx.strokeStyle = configRef.current.lineColor;
318
- linesRef.current.forEach((points) => {
319
- let p1 = moved(points[0], false);
320
- ctx.moveTo(p1.x, p1.y);
321
- points.forEach((p, idx) => {
322
- const isLast = idx === points.length - 1;
323
- p1 = moved(p, !isLast);
324
- const p2 = moved(points[idx + 1] || points[points.length - 1], !isLast);
325
- ctx.lineTo(p1.x, p1.y);
326
- if (isLast) ctx.moveTo(p2.x, p2.y);
327
- });
328
- });
329
- ctx.stroke();
330
- }
331
-
332
- function tick(t: number) {
333
- if (!container) return;
334
- const mouse = mouseRef.current;
335
- mouse.sx += (mouse.x - mouse.sx) * 0.1;
336
- mouse.sy += (mouse.y - mouse.sy) * 0.1;
337
- const dx = mouse.x - mouse.lx,
338
- dy = mouse.y - mouse.ly;
339
- const d = Math.hypot(dx, dy);
340
- mouse.v = d;
341
- mouse.vs += (d - mouse.vs) * 0.1;
342
- mouse.vs = Math.min(100, mouse.vs);
343
- mouse.lx = mouse.x;
344
- mouse.ly = mouse.y;
345
- mouse.a = Math.atan2(dy, dx);
346
- container.style.setProperty('--x', `${mouse.sx}px`);
347
- container.style.setProperty('--y', `${mouse.sy}px`);
348
-
349
- movePoints(t);
350
- drawLines();
351
- frameIdRef.current = requestAnimationFrame(tick);
352
- }
353
-
354
- function onResize() {
355
- setSize();
356
- setLines();
357
- }
358
- function onMouseMove(e: MouseEvent) {
359
- updateMouse(e.clientX, e.clientY);
360
- }
361
- function onTouchMove(e: TouchEvent) {
362
- const touch = e.touches[0];
363
- updateMouse(touch.clientX, touch.clientY);
364
- }
365
- function updateMouse(x: number, y: number) {
366
- const mouse = mouseRef.current;
367
- const b = boundingRef.current;
368
- mouse.x = x - b.left;
369
- mouse.y = y - b.top;
370
- if (!mouse.set) {
371
- mouse.sx = mouse.x;
372
- mouse.sy = mouse.y;
373
- mouse.lx = mouse.x;
374
- mouse.ly = mouse.y;
375
- mouse.set = true;
376
- }
377
- }
378
-
379
- setSize();
380
- setLines();
381
- frameIdRef.current = requestAnimationFrame(tick);
382
- window.addEventListener('resize', onResize);
383
- window.addEventListener('mousemove', onMouseMove);
384
- window.addEventListener('touchmove', onTouchMove, { passive: false });
385
-
386
- return () => {
387
- window.removeEventListener('resize', onResize);
388
- window.removeEventListener('mousemove', onMouseMove);
389
- window.removeEventListener('touchmove', onTouchMove);
390
- if (frameIdRef.current !== null) {
391
- cancelAnimationFrame(frameIdRef.current);
392
- }
393
- };
394
- }, []);
395
-
396
- return (
397
- <div
398
- ref={containerRef}
399
- style={{
400
- backgroundColor,
401
- ...style,
402
- }}
403
- className={`absolute top-0 left-0 h-full w-full overflow-hidden ${className}`}
404
- >
405
- <div
406
- className="absolute top-0 left-0 h-[0.5rem] w-[0.5rem] rounded-full bg-[#160000]"
407
- style={{
408
- transform: 'translate3d(calc(var(--x) - 50%), calc(var(--y) - 50%), 0)',
409
- willChange: 'transform',
410
- }}
411
- />
412
- <canvas ref={canvasRef} className="block h-full w-full" />
413
- </div>
414
- );
415
- };
416
-
417
- export default Waves;
@@ -1,174 +0,0 @@
1
- 'use client';
2
-
3
- import * as React from 'react';
4
- import { AnimatePresence, motion, type HTMLMotionProps, type Transition } from 'motion/react';
5
- import { Tabs as TabsPrimitive } from 'radix-ui';
6
-
7
- import { getStrictContext } from '@/lib/get-strict-context';
8
- import { useControlledState } from '@/hooks/use-controlled-state';
9
- import { AutoHeight, type AutoHeightProps } from '@/components/motion/auto-height';
10
- import {
11
- Highlight,
12
- HighlightItem,
13
- type HighlightItemProps,
14
- type HighlightProps,
15
- } from '@/components/motion/highlight';
16
-
17
- type TabsContextType = {
18
- value: string | undefined;
19
- setValue: TabsProps['onValueChange'];
20
- };
21
-
22
- const [TabsProvider, useTabs] = getStrictContext<TabsContextType>('TabsContext');
23
-
24
- type TabsProps = React.ComponentProps<typeof TabsPrimitive.Root>;
25
-
26
- function Tabs(props: TabsProps) {
27
- const [value, setValue] = useControlledState({
28
- value: props.value,
29
- defaultValue: props.defaultValue,
30
- onChange: props.onValueChange,
31
- });
32
-
33
- return (
34
- <TabsProvider value={{ value, setValue }}>
35
- <TabsPrimitive.Root data-slot="tabs" {...props} onValueChange={setValue} />
36
- </TabsProvider>
37
- );
38
- }
39
-
40
- type TabsHighlightProps = Omit<HighlightProps, 'controlledItems' | 'value'>;
41
-
42
- function TabsHighlight({
43
- transition = { type: 'spring', stiffness: 200, damping: 25 },
44
- ...props
45
- }: TabsHighlightProps) {
46
- const { value } = useTabs();
47
-
48
- return (
49
- <Highlight
50
- data-slot="tabs-highlight"
51
- controlledItems
52
- value={value}
53
- transition={transition}
54
- click={false}
55
- {...props}
56
- />
57
- );
58
- }
59
-
60
- type TabsListProps = React.ComponentProps<typeof TabsPrimitive.List>;
61
-
62
- function TabsList(props: TabsListProps) {
63
- return <TabsPrimitive.List data-slot="tabs-list" {...props} />;
64
- }
65
-
66
- type TabsHighlightItemProps = HighlightItemProps & {
67
- value: string;
68
- };
69
-
70
- function TabsHighlightItem(props: TabsHighlightItemProps) {
71
- return <HighlightItem data-slot="tabs-highlight-item" {...props} />;
72
- }
73
-
74
- type TabsTriggerProps = React.ComponentProps<typeof TabsPrimitive.Trigger>;
75
-
76
- function TabsTrigger(props: TabsTriggerProps) {
77
- return <TabsPrimitive.Trigger data-slot="tabs-trigger" {...props} />;
78
- }
79
-
80
- type TabsContentProps = React.ComponentProps<typeof TabsPrimitive.Content> & HTMLMotionProps<'div'>;
81
-
82
- function TabsContent({
83
- value,
84
- forceMount,
85
- transition = { duration: 0.5, ease: 'easeInOut' },
86
- ...props
87
- }: TabsContentProps) {
88
- return (
89
- <AnimatePresence mode="wait">
90
- <TabsPrimitive.Content asChild forceMount={forceMount} value={value}>
91
- <motion.div
92
- data-slot="tabs-content"
93
- layout
94
- layoutDependency={value}
95
- initial={{ opacity: 0, filter: 'blur(4px)' }}
96
- animate={{ opacity: 1, filter: 'blur(0px)' }}
97
- exit={{ opacity: 0, filter: 'blur(4px)' }}
98
- transition={transition}
99
- {...props}
100
- />
101
- </TabsPrimitive.Content>
102
- </AnimatePresence>
103
- );
104
- }
105
-
106
- type TabsContentsAutoProps = AutoHeightProps & {
107
- mode?: 'auto-height';
108
- children: React.ReactNode;
109
- transition?: Transition;
110
- };
111
-
112
- type TabsContentsLayoutProps = Omit<HTMLMotionProps<'div'>, 'transition'> & {
113
- mode: 'layout';
114
- children: React.ReactNode;
115
- transition?: Transition;
116
- };
117
-
118
- type TabsContentsProps = TabsContentsAutoProps | TabsContentsLayoutProps;
119
-
120
- const defaultTransition: Transition = {
121
- type: 'spring',
122
- stiffness: 200,
123
- damping: 30,
124
- };
125
-
126
- function isAutoMode(props: TabsContentsProps): props is TabsContentsAutoProps {
127
- return !('mode' in props) || props.mode === 'auto-height';
128
- }
129
-
130
- function TabsContents(props: TabsContentsProps) {
131
- const { value } = useTabs();
132
-
133
- if (isAutoMode(props)) {
134
- const { transition = defaultTransition, ...autoProps } = props;
135
-
136
- return (
137
- <AutoHeight data-slot="tabs-contents" deps={[value]} transition={transition} {...autoProps} />
138
- );
139
- }
140
-
141
- const {
142
- transition = defaultTransition,
143
- style,
144
- ...layoutProps
145
- } = props as TabsContentsLayoutProps;
146
-
147
- return (
148
- <motion.div
149
- data-slot="tabs-contents"
150
- layout="size"
151
- layoutDependency={value}
152
- style={{ overflow: 'hidden', ...style }}
153
- transition={{ layout: transition }}
154
- {...layoutProps}
155
- />
156
- );
157
- }
158
-
159
- export {
160
- Tabs,
161
- TabsHighlight,
162
- TabsHighlightItem,
163
- TabsList,
164
- TabsTrigger,
165
- TabsContent,
166
- TabsContents,
167
- type TabsProps,
168
- type TabsHighlightProps,
169
- type TabsHighlightItemProps,
170
- type TabsListProps,
171
- type TabsTriggerProps,
172
- type TabsContentProps,
173
- type TabsContentsProps,
174
- };