summaryrefslogtreecommitdiffhomepage
path: root/packages/ui/src/components/motion.tsx
diff options
context:
space:
mode:
authorKit Langton <[email protected]>2026-03-07 06:25:22 -0500
committerGitHub <[email protected]>2026-03-07 05:25:22 -0600
commitbbd0f3a25283b6f9567a04e79d7f6972950ab0a6 (patch)
tree56cb41ff9c67749c6fa894fef32bb14cefd73db3 /packages/ui/src/components/motion.tsx
parentb7e208b4f1e6641a1cbb1e13f59789c7b7f4c60a (diff)
downloadopencode-bbd0f3a25283b6f9567a04e79d7f6972950ab0a6.tar.gz
opencode-bbd0f3a25283b6f9567a04e79d7f6972950ab0a6.zip
STUPID SEXY TIMELINE (#16420)
Diffstat (limited to 'packages/ui/src/components/motion.tsx')
-rw-r--r--packages/ui/src/components/motion.tsx77
1 files changed, 77 insertions, 0 deletions
diff --git a/packages/ui/src/components/motion.tsx b/packages/ui/src/components/motion.tsx
new file mode 100644
index 000000000..6cdf01c73
--- /dev/null
+++ b/packages/ui/src/components/motion.tsx
@@ -0,0 +1,77 @@
+import { followValue } from "motion"
+import type { MotionValue } from "motion"
+
+export { animate, springValue } from "motion"
+export type { AnimationPlaybackControls } from "motion"
+
+/**
+ * Like `springValue` but preserves getters on the config object.
+ * `springValue` spreads config at creation, snapshotting getter values.
+ * This passes the config through to `followValue` intact, so getters
+ * on `visualDuration` etc. fire on every `.set()` call.
+ */
+export function tunableSpringValue<T extends string | number>(initial: T, config: SpringConfig): MotionValue<T> {
+ return followValue(initial, config as any)
+}
+
+let _growDuration = 0.5
+let _collapsibleDuration = 0.3
+
+export const GROW_SPRING = {
+ type: "spring" as const,
+ get visualDuration() {
+ return _growDuration
+ },
+ bounce: 0,
+}
+
+export const COLLAPSIBLE_SPRING = {
+ type: "spring" as const,
+ get visualDuration() {
+ return _collapsibleDuration
+ },
+ bounce: 0,
+}
+
+export const setGrowDuration = (v: number) => {
+ _growDuration = v
+}
+export const setCollapsibleDuration = (v: number) => {
+ _collapsibleDuration = v
+}
+export const getGrowDuration = () => _growDuration
+export const getCollapsibleDuration = () => _collapsibleDuration
+
+export type SpringConfig = { type: "spring"; visualDuration: number; bounce: number }
+
+export const FAST_SPRING = {
+ type: "spring" as const,
+ visualDuration: 0.35,
+ bounce: 0,
+}
+
+export const GLOW_SPRING = {
+ type: "spring" as const,
+ visualDuration: 0.4,
+ bounce: 0.15,
+}
+
+export const WIPE_MASK =
+ "linear-gradient(to right, rgba(0,0,0,1) 0%, rgba(0,0,0,1) 45%, rgba(0,0,0,0) 60%, rgba(0,0,0,0) 100%)"
+
+export const clearMaskStyles = (el: HTMLElement) => {
+ el.style.maskImage = ""
+ el.style.webkitMaskImage = ""
+ el.style.maskSize = ""
+ el.style.webkitMaskSize = ""
+ el.style.maskRepeat = ""
+ el.style.webkitMaskRepeat = ""
+ el.style.maskPosition = ""
+ el.style.webkitMaskPosition = ""
+}
+
+export const clearFadeStyles = (el: HTMLElement) => {
+ el.style.opacity = ""
+ el.style.filter = ""
+ el.style.transform = ""
+}