loopwind 0.22.0 → 0.23.0
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.
- package/dist/lib/render-core.d.ts +63 -0
- package/dist/lib/render-core.d.ts.map +1 -0
- package/dist/lib/render-core.js +65 -0
- package/dist/lib/render-core.js.map +1 -0
- package/dist/lib/renderer.d.ts.map +1 -1
- package/dist/lib/renderer.js +10 -7
- package/dist/lib/renderer.js.map +1 -1
- package/dist/lib/resvg-init.d.ts +15 -0
- package/dist/lib/resvg-init.d.ts.map +1 -0
- package/dist/lib/resvg-init.js +55 -0
- package/dist/lib/resvg-init.js.map +1 -0
- package/dist/lib/tailwind/colors.d.ts +8 -0
- package/dist/lib/tailwind/colors.d.ts.map +1 -0
- package/dist/lib/tailwind/colors.js +102 -0
- package/dist/lib/tailwind/colors.js.map +1 -0
- package/dist/lib/tailwind/index.d.ts +10 -0
- package/dist/lib/tailwind/index.d.ts.map +1 -0
- package/dist/lib/tailwind/index.js +9 -0
- package/dist/lib/tailwind/index.js.map +1 -0
- package/dist/lib/tailwind/resolvers.d.ts +28 -0
- package/dist/lib/tailwind/resolvers.d.ts.map +1 -0
- package/dist/lib/tailwind/resolvers.js +94 -0
- package/dist/lib/tailwind/resolvers.js.map +1 -0
- package/dist/lib/tailwind/types.d.ts +29 -0
- package/dist/lib/tailwind/types.d.ts.map +1 -0
- package/dist/lib/tailwind/types.js +8 -0
- package/dist/lib/tailwind/types.js.map +1 -0
- package/dist/lib/tailwind-config-loader.d.ts +8 -45
- package/dist/lib/tailwind-config-loader.d.ts.map +1 -1
- package/dist/lib/tailwind-config-loader.js +6 -429
- package/dist/lib/tailwind-config-loader.js.map +1 -1
- package/dist/lib/tailwind.d.ts +1 -1
- package/dist/lib/tailwind.d.ts.map +1 -1
- package/dist/lib/tailwind.js +1 -1
- package/dist/lib/tailwind.js.map +1 -1
- package/dist/lib/video-renderer.d.ts.map +1 -1
- package/dist/lib/video-renderer.js +6 -5
- package/dist/lib/video-renderer.js.map +1 -1
- package/dist/sdk/edge/index.d.ts +91 -0
- package/dist/sdk/edge/index.d.ts.map +1 -0
- package/dist/sdk/edge/index.js +187 -0
- package/dist/sdk/edge/index.js.map +1 -0
- package/dist/sdk/workers/index.d.ts +135 -0
- package/dist/sdk/workers/index.d.ts.map +1 -0
- package/dist/sdk/workers/index.js +271 -0
- package/dist/sdk/workers/index.js.map +1 -0
- package/dist/sdk/workers/tailwind-config.d.ts +48 -0
- package/dist/sdk/workers/tailwind-config.d.ts.map +1 -0
- package/dist/sdk/workers/tailwind-config.js +187 -0
- package/dist/sdk/workers/tailwind-config.js.map +1 -0
- package/dist/sdk/workers/tailwind.d.ts +9 -0
- package/dist/sdk/workers/tailwind.d.ts.map +1 -0
- package/dist/sdk/workers/tailwind.js +8 -0
- package/dist/sdk/workers/tailwind.js.map +1 -0
- package/package.json +6 -2
- package/test-cloudflare-worker/README.md +64 -0
- package/test-cloudflare-worker/dist/README.md +1 -0
- package/test-cloudflare-worker/dist/index.js +23743 -0
- package/test-cloudflare-worker/dist/index.js.map +8 -0
- package/test-cloudflare-worker/package-lock.json +1773 -0
- package/test-cloudflare-worker/package.json +25 -0
- package/test-cloudflare-worker/test-sdk.mjs +75 -0
- package/test-cloudflare-worker/wrangler.toml +14 -0
- package/test-video-720p.mjs +96 -0
- package/test-video-breakdown.mjs +98 -0
- package/test-video-perf-1080.mjs +67 -0
- package/test-video-perf.mjs +56 -0
- package/test-worker-1080p.mjs +103 -0
- package/test-worker-viability.mjs +140 -0
- package/website/astro.config.mjs +4 -9
- package/website/dist/_astro/PlaygroundEditor.DzFavsm8.js +26 -0
- package/website/dist/_astro/VideoPreviewClient.BrajhYmh.js +1 -0
- package/website/dist/_astro/agents.CZXv4DCM.css +1 -0
- package/website/dist/_astro/client.BHSq4mdQ.js +33 -0
- package/website/dist/_astro/index.CTbGshLK.js +9 -0
- package/website/dist/_astro/jsx-runtime.BjG_zV1W.js +9 -0
- package/website/dist/_routes.json +1 -0
- package/website/dist/_worker.js/_@astrojs-ssr-adapter.mjs +4 -4
- package/website/dist/_worker.js/_astro-internal_middleware.mjs +2 -2
- package/website/dist/_worker.js/chunks/Logo_Cud5QvBJ.mjs +22 -0
- package/website/dist/_worker.js/chunks/_@astro-renderers_-YVK7NHa.mjs +15015 -0
- package/website/dist/_worker.js/chunks/astro/{server_Y5_QHO8v.mjs → server_CsUrSZgd.mjs} +113 -2
- package/website/dist/_worker.js/chunks/{astro-designed-error-pages_BNTLO-TA.mjs → astro-designed-error-pages_1ELXm5Tt.mjs} +1 -1
- package/website/dist/_worker.js/chunks/{index_C1UTDwYg.mjs → index_BDWR1Q-q.mjs} +2 -2
- package/website/dist/_worker.js/chunks/{noop-middleware_DlWGj5t5.mjs → noop-middleware_B8fH5jha.mjs} +1 -1
- package/website/dist/_worker.js/index.js +38 -30
- package/website/dist/_worker.js/manifest_Bk6136-u.mjs +98 -0
- package/website/dist/_worker.js/pages/_image.astro.mjs +1 -1
- package/website/dist/_worker.js/pages/api/playground/render.astro.mjs +25562 -0
- package/website/dist/_worker.js/pages/api/playground/templates.astro.mjs +92 -0
- package/website/dist/_worker.js/pages/api/raw-markdown/_---path_.astro.mjs +1 -1
- package/website/dist/_worker.js/pages/playground/_example_.astro.mjs +95 -0
- package/website/dist/_worker.js/pages/playground.astro.mjs +1 -0
- package/website/dist/_worker.js/renderers.mjs +1 -56
- package/website/dist/agents/index.html +4 -2
- package/website/dist/animation/index.html +629 -3
- package/website/dist/config/index.html +4 -2
- package/website/dist/fonts/index.html +4 -2
- package/website/dist/getting-started/index.html +4 -2
- package/website/dist/helpers/index.html +196 -10
- package/website/dist/images/index.html +4 -2
- package/website/dist/index.html +4 -3
- package/website/dist/llm.txt +870 -20
- package/website/dist/playground/index.html +6 -0
- package/website/dist/preview/index.html +4 -2
- package/website/dist/sdk/index.html +639 -127
- package/website/dist/sitemap.xml +12 -12
- package/website/dist/styling/index.html +4 -2
- package/website/dist/templates/index.html +4 -2
- package/website/dist/video/index.html +47 -12
- package/website/package-lock.json +11 -1
- package/website/package.json +3 -1
- package/website/wrangler.toml +9 -0
- package/_dsgn/templates/dashed-stroke-test/template.tsx +0 -73
- package/_dsgn/templates/path-follow-test/template.tsx +0 -176
- package/_dsgn/templates/path-simple-test/template.tsx +0 -98
- package/_dsgn/templates/stroke-dash-test/meta.json +0 -12
- package/_dsgn/templates/stroke-dash-test/template.tsx +0 -53
- package/website/dist/_astro/agents.Yx-L_igG.css +0 -1
- package/website/dist/_worker.js/manifest_CT_D-YDe.mjs +0 -98
|
@@ -1,5 +1,7 @@
|
|
|
1
|
-
<!DOCTYPE html><html lang="en" data-astro-cid-mw7aashj> <head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><link rel="icon" type="image/svg+xml" href="/favicon.svg"><meta name="generator" content="Astro v4.16.19"><link rel="canonical" href="https://loopwind.dev/animation/"><!-- Primary Meta Tags --><title></title><meta name="title"><meta name="description" content="CLI-based Image & Video Generator for developers and AI Agents. Generate stunning visuals from React + Tailwind templates."><meta name="keywords" content="loopwind, image generation, video generation, React, Tailwind CSS, Satori, CLI tool, templates, shadcn/ui, AI agents, Cursor, automation, serverless, WASM, Open Graph, social media, marketing automation"><meta name="author" content="loopwind"><!-- Open Graph / Facebook --><meta property="og:type" content="website"><meta property="og:url" content="https://loopwind.dev/animation/"><meta property="og:title"><meta property="og:description" content="CLI-based Image & Video Generator for developers and AI Agents. Generate stunning visuals from React + Tailwind templates."><meta property="og:image" content="https://loopwind.dev/api/og/animation"><meta property="og:image:width" content="1200"><meta property="og:image:height" content="630"><meta property="og:image:alt"><meta property="og:site_name" content="loopwind"><meta property="og:locale" content="en_US"><!-- Twitter --><meta name="twitter:card" content="summary_large_image"><meta name="twitter:url" content="https://loopwind.dev/animation/"><meta name="twitter:title"><meta name="twitter:description" content="CLI-based Image & Video Generator for developers and AI Agents. Generate stunning visuals from React + Tailwind templates."><meta name="twitter:image" content="https://loopwind.dev/api/og/animation"><meta name="twitter:image:alt"><meta name="twitter:creator" content="@loopwind"><meta name="twitter:site" content="@loopwind"><!-- Theme Color --><meta name="theme-color" content="#0a0a0a"><meta name="theme-color" media="(prefers-color-scheme: dark)" content="#0a0a0a"><meta name="theme-color" media="(prefers-color-scheme: light)" content="#fafafa"><!-- Additional SEO --><meta name="robots" content="index, follow"><meta name="googlebot" content="index, follow"><meta name="language" content="English"><meta name="revisit-after" content="7 days"><meta name="rating" content="general"><!-- Mobile Web App --><meta name="mobile-web-app-capable" content="yes"><meta name="apple-mobile-web-app-capable" content="yes"><meta name="apple-mobile-web-app-status-bar-style" content="black-translucent"><meta name="apple-mobile-web-app-title" content="loopwind"><!-- Structured Data (JSON-LD) --><script type="application/ld+json">{"@context":"https://schema.org","@type":"SoftwareApplication","name":"loopwind","applicationCategory":"DeveloperApplication","operatingSystem":"Cross-platform","description":"CLI-based Image & Video Generator for developers and AI Agents. Generate stunning visuals from React + Tailwind templates.","url":"https://loopwind.dev/","author":{"@type":"Organization","name":"loopwind","url":"https://loopwind.dev/"},"offers":{"@type":"Offer","price":"0","priceCurrency":"USD"},"softwareVersion":"0.11.0","releaseNotes":"https://github.com/loopwind/loopwind/releases","screenshot":"https://loopwind.dev/api/og/animation","featureList":["Image generation from React templates","Video generation with animations","Tailwind CSS support","shadcn/ui design system","CLI-based workflow","Serverless rendering","TypeScript support","AI Agent friendly"]}</script><script type="application/ld+json">{"@context":"https://schema.org","@type":"Organization","name":"loopwind","url":"https://loopwind.dev/","logo":"https://loopwind.dev/favicon.svg","sameAs":["https://github.com/loopwind/loopwind","https://www.npmjs.com/package/loopwind"]}</script><script type="application/ld+json">{"@context":"https://schema.org","@type":"BreadcrumbList","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https://loopwind.dev/"},{"@type":"ListItem","position":2,"name":"Animation","item":"https://loopwind.dev/animation"}]}</script><link rel="stylesheet" href="/_astro/agents.
|
|
2
|
-
|
|
1
|
+
<!DOCTYPE html><html lang="en" data-astro-cid-mw7aashj> <head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><link rel="icon" type="image/svg+xml" href="/favicon.svg"><meta name="generator" content="Astro v4.16.19"><link rel="canonical" href="https://loopwind.dev/animation/"><!-- Primary Meta Tags --><title></title><meta name="title"><meta name="description" content="CLI-based Image & Video Generator for developers and AI Agents. Generate stunning visuals from React + Tailwind templates."><meta name="keywords" content="loopwind, image generation, video generation, React, Tailwind CSS, Satori, CLI tool, templates, shadcn/ui, AI agents, Cursor, automation, serverless, WASM, Open Graph, social media, marketing automation"><meta name="author" content="loopwind"><!-- Open Graph / Facebook --><meta property="og:type" content="website"><meta property="og:url" content="https://loopwind.dev/animation/"><meta property="og:title"><meta property="og:description" content="CLI-based Image & Video Generator for developers and AI Agents. Generate stunning visuals from React + Tailwind templates."><meta property="og:image" content="https://loopwind.dev/api/og/animation"><meta property="og:image:width" content="1200"><meta property="og:image:height" content="630"><meta property="og:image:alt"><meta property="og:site_name" content="loopwind"><meta property="og:locale" content="en_US"><!-- Twitter --><meta name="twitter:card" content="summary_large_image"><meta name="twitter:url" content="https://loopwind.dev/animation/"><meta name="twitter:title"><meta name="twitter:description" content="CLI-based Image & Video Generator for developers and AI Agents. Generate stunning visuals from React + Tailwind templates."><meta name="twitter:image" content="https://loopwind.dev/api/og/animation"><meta name="twitter:image:alt"><meta name="twitter:creator" content="@loopwind"><meta name="twitter:site" content="@loopwind"><!-- Theme Color --><meta name="theme-color" content="#0a0a0a"><meta name="theme-color" media="(prefers-color-scheme: dark)" content="#0a0a0a"><meta name="theme-color" media="(prefers-color-scheme: light)" content="#fafafa"><!-- Additional SEO --><meta name="robots" content="index, follow"><meta name="googlebot" content="index, follow"><meta name="language" content="English"><meta name="revisit-after" content="7 days"><meta name="rating" content="general"><!-- Mobile Web App --><meta name="mobile-web-app-capable" content="yes"><meta name="apple-mobile-web-app-capable" content="yes"><meta name="apple-mobile-web-app-status-bar-style" content="black-translucent"><meta name="apple-mobile-web-app-title" content="loopwind"><!-- Structured Data (JSON-LD) --><script type="application/ld+json">{"@context":"https://schema.org","@type":"SoftwareApplication","name":"loopwind","applicationCategory":"DeveloperApplication","operatingSystem":"Cross-platform","description":"CLI-based Image & Video Generator for developers and AI Agents. Generate stunning visuals from React + Tailwind templates.","url":"https://loopwind.dev/","author":{"@type":"Organization","name":"loopwind","url":"https://loopwind.dev/"},"offers":{"@type":"Offer","price":"0","priceCurrency":"USD"},"softwareVersion":"0.11.0","releaseNotes":"https://github.com/loopwind/loopwind/releases","screenshot":"https://loopwind.dev/api/og/animation","featureList":["Image generation from React templates","Video generation with animations","Tailwind CSS support","shadcn/ui design system","CLI-based workflow","Serverless rendering","TypeScript support","AI Agent friendly"]}</script><script type="application/ld+json">{"@context":"https://schema.org","@type":"Organization","name":"loopwind","url":"https://loopwind.dev/","logo":"https://loopwind.dev/favicon.svg","sameAs":["https://github.com/loopwind/loopwind","https://www.npmjs.com/package/loopwind"]}</script><script type="application/ld+json">{"@context":"https://schema.org","@type":"BreadcrumbList","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https://loopwind.dev/"},{"@type":"ListItem","position":2,"name":"Animation","item":"https://loopwind.dev/animation"}]}</script><link rel="stylesheet" href="/_astro/agents.CZXv4DCM.css">
|
|
2
|
+
<style>.hero[data-astro-cid-bbe6dxrz]{position:relative}html{scroll-behavior:smooth}.mobile-header[data-astro-cid-mw7aashj]{display:none}.toc-sidebar[data-astro-cid-mw7aashj]{scrollbar-width:thin;scrollbar-color:rgba(255,255,255,.1) transparent}.toc-sidebar[data-astro-cid-mw7aashj]::-webkit-scrollbar{width:4px}.toc-sidebar[data-astro-cid-mw7aashj]::-webkit-scrollbar-track{background:transparent}.toc-sidebar[data-astro-cid-mw7aashj]::-webkit-scrollbar-thumb{background-color:#ffffff1a;border-radius:2px}.toc-sidebar[data-astro-cid-mw7aashj]::-webkit-scrollbar-thumb:hover{background-color:#fff3}#copy-to-llm-btn[data-astro-cid-mw7aashj]{cursor:pointer}@media (max-width: 768px){.mobile-header[data-astro-cid-mw7aashj]{display:block}.desktop-sidebar[data-astro-cid-mw7aashj]{display:none}main[data-astro-cid-mw7aashj]{margin-left:0;margin-right:0!important;padding:5rem 1.5rem 1.5rem}.toc-sidebar[data-astro-cid-mw7aashj]{display:none}#copy-to-llm-btn[data-astro-cid-mw7aashj]{width:100%;justify-content:center}}@media (max-width: 1280px){.toc-sidebar[data-astro-cid-mw7aashj]{display:none!important}main[data-astro-cid-mw7aashj]{margin-right:0!important}}
|
|
3
|
+
</style><script type="module">const p=document.getElementById("mobile-menu-button"),l=document.getElementById("mobile-menu"),g=document.querySelectorAll(".mobile-menu-link");p?.addEventListener("click",()=>{l?.classList.toggle("hidden")});l?.addEventListener("click",o=>{o.target===l&&l.classList.add("hidden")});g.forEach(o=>{o.addEventListener("click",()=>{l?.classList.add("hidden")})});function m(){const o=document.getElementById("toc-nav");if(!o){console.log("TOC: No toc-nav element found");return}const n=document.querySelector("article");if(!n){console.log("TOC: No article element found");return}const c=n.querySelectorAll("h2, h3");if(c.length===0){console.log("TOC: No headings found");return}console.log(`TOC: Found ${c.length} headings`);const a=document.createElement("ul");a.className="space-y-0 text-sm border-l border-border/50",c.forEach(e=>{const t=e.tagName==="H2"?2:3,r=e.id||e.textContent?.toLowerCase().replace(/[^\w]+/g,"-");!e.id&&r&&(e.id=r);const s=document.createElement("li"),d=document.createElement("a");d.href=`#${r}`,d.textContent=e.textContent,d.className=`toc-link block py-1 px-3 -ml-px border-l-2 border-transparent transition-all no-underline ${t===3?"pl-6 text-xs text-muted-foreground/70":"text-sm text-muted-foreground"} hover:text-foreground hover:border-muted-foreground/50`,s.appendChild(d),a.appendChild(s)}),o.appendChild(a);const i=new IntersectionObserver(e=>{e.forEach(t=>{const r=t.target.id,s=o.querySelector(`a[href="#${r}"]`);t.isIntersecting&&(document.querySelectorAll(".toc-link").forEach(d=>{d.classList.remove("text-foreground","border-accent","font-medium")}),s?.classList.add("text-foreground","border-accent","font-medium"))})},{rootMargin:"-100px 0px -66%",threshold:0});c.forEach(e=>{i.observe(e)})}document.addEventListener("DOMContentLoaded",m);document.addEventListener("astro:page-load",m);function u(){const o=document.getElementById("copy-to-llm-btn"),n=document.getElementById("copy-btn-text");if(!o||!n){console.log("Copy to LLM: Button not found on this page");return}console.log("Copy to LLM: Initialized"),o.addEventListener("click",async()=>{const c=window.location.pathname,a=c.replace(/^\//,"").replace(/\/$/,""),e=`/api/raw-markdown/${a===""?"index":a}`;console.log("Copy to LLM clicked: pathname=",c,"apiUrl=",e);try{n.textContent="Copying...";const t=await fetch(e);if(console.log("Response status:",t.status),!t.ok)throw new Error(`HTTP error! status: ${t.status}`);const r=await t.text();console.log("Got markdown, length:",r.length),await navigator.clipboard.writeText(r),n.textContent="Copied!",setTimeout(()=>{n.textContent="Copy to LLM"},2e3)}catch(t){console.error("Copy failed:",t),n.textContent="Failed",setTimeout(()=>{n.textContent="Copy to LLM"},2e3)}})}document.addEventListener("DOMContentLoaded",u);document.addEventListener("astro:page-load",u);
|
|
4
|
+
</script></head> <body class="antialiased" data-astro-cid-mw7aashj> <div class="min-h-screen" data-astro-cid-mw7aashj> <!-- Mobile Header --> <header class="mobile-header fixed top-0 left-0 right-0 h-16 bg-card border-b border-border z-50 md:hidden" data-astro-cid-mw7aashj> <div class="flex items-center justify-between h-full px-4" data-astro-cid-mw7aashj> <a href="/" class="no-underline"> <h1 class="text-xl flex items-center gap-2 bg-linear-to-r from-brand-from to-brand-to bg-clip-text text-transparent"> <span class="text-2xl">➰</span> <span>loopwind</span> </h1> </a> <button id="mobile-menu-button" class="p-2 text-foreground hover:bg-accent rounded-md transition-colors" aria-label="Toggle menu" data-astro-cid-mw7aashj> <svg class="w-6 h-6" fill="none" stroke="currentColor" viewBox="0 0 24 24" data-astro-cid-mw7aashj> <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 6h16M4 12h16M4 18h16" data-astro-cid-mw7aashj></path> </svg> </button> </div> </header> <!-- Mobile Menu Overlay --> <div id="mobile-menu" class="mobile-menu fixed inset-0 bg-background/80 backdrop-blur-sm z-40 md:hidden hidden" data-astro-cid-mw7aashj> <div class="fixed top-0 left-0 h-screen w-64 bg-card border-r border-border overflow-y-auto" data-astro-cid-mw7aashj> <div class="p-6 pt-20" data-astro-cid-mw7aashj> <nav data-astro-cid-mw7aashj> <ul class="space-y-1" data-astro-cid-mw7aashj> <li data-astro-cid-mw7aashj> <a href="/" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Home </a> </li><li data-astro-cid-mw7aashj> <a href="/getting-started" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Getting Started </a> </li><li data-astro-cid-mw7aashj> <a href="/templates" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Templates </a> </li><li data-astro-cid-mw7aashj> <a href="/images" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Images </a> </li><li data-astro-cid-mw7aashj> <a href="/video" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Video </a> </li><li data-astro-cid-mw7aashj> <a href="/preview" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Preview </a> </li><li data-astro-cid-mw7aashj> <a href="/animation" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Animation </a> </li><li data-astro-cid-mw7aashj> <a href="/helpers" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Helpers </a> </li><li data-astro-cid-mw7aashj> <a href="/styling" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Styling </a> </li><li data-astro-cid-mw7aashj> <a href="/fonts" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Fonts </a> </li><li data-astro-cid-mw7aashj> <a href="/config" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> loopwind.json </a> </li><li data-astro-cid-mw7aashj> <a href="/sdk" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> SDK </a> </li><li data-astro-cid-mw7aashj> <a href="/playground" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Playground </a> </li><li data-astro-cid-mw7aashj> <a href="/agents" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Use with AI Agents </a> </li><li data-astro-cid-mw7aashj> <a href="/llm.txt" class="mobile-menu-link block px-3 py-2 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> llm.txt ⇱ </a> </li> </ul> </nav> </div> </div> </div> <!-- Desktop Sidebar --> <aside class="desktop-sidebar fixed top-0 left-0 h-screen w-64 border-r border-border bg-card overflow-y-auto z-10" data-astro-cid-mw7aashj> <div class="p-6" data-astro-cid-mw7aashj> <div class="block mb-3" data-astro-cid-mw7aashj> <a href="/" class="no-underline"> <h1 class="text-3xl flex items-center gap-2 bg-linear-to-r from-brand-from to-brand-to bg-clip-text text-transparent"> <span class="text-4xl">➰</span> <span>loopwind</span> </h1> </a> </div> <nav data-astro-cid-mw7aashj> <ul class="space-y-0" data-astro-cid-mw7aashj> <li data-astro-cid-mw7aashj> <a href="/" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Home </a> </li><li data-astro-cid-mw7aashj> <a href="/getting-started" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Getting Started </a> </li><li data-astro-cid-mw7aashj> <a href="/templates" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Templates </a> </li><li data-astro-cid-mw7aashj> <a href="/images" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Images </a> </li><li data-astro-cid-mw7aashj> <a href="/video" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Video </a> </li><li data-astro-cid-mw7aashj> <a href="/preview" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Preview </a> </li><li data-astro-cid-mw7aashj> <a href="/animation" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Animation </a> </li><li data-astro-cid-mw7aashj> <a href="/helpers" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Helpers </a> </li><li data-astro-cid-mw7aashj> <a href="/styling" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Styling </a> </li><li data-astro-cid-mw7aashj> <a href="/fonts" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Fonts </a> </li><li data-astro-cid-mw7aashj> <a href="/config" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> loopwind.json </a> </li><li data-astro-cid-mw7aashj> <a href="/sdk" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> SDK </a> </li><li data-astro-cid-mw7aashj> <a href="/playground" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Playground </a> </li><li data-astro-cid-mw7aashj> <a href="/agents" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> Use with AI Agents </a> </li><li data-astro-cid-mw7aashj> <a href="/llm.txt" class="block px-3 py-1.5 rounded-md text-sm transition-colors no-underline text-muted-foreground hover:text-foreground hover:bg-accent/50" data-astro-cid-mw7aashj> llm.txt ⇱ </a> </li> </ul> </nav> </div> </aside> <!-- Main content --> <main class="ml-64 mr-64" data-astro-cid-mw7aashj> <div class="p-12" data-astro-cid-mw7aashj> <button id="copy-to-llm-btn" class="mb-6 px-4 py-2 bg-accent hover:bg-accent/80 text-accent-foreground rounded-md text-sm font-medium transition-colors flex items-center gap-2" aria-label="Copy raw markdown to clipboard" data-astro-cid-mw7aashj> <svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24" data-astro-cid-mw7aashj> <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 16H6a2 2 0 01-2-2V6a2 2 0 012-2h8a2 2 0 012 2v2m-6 12h8a2 2 0 002-2v-8a2 2 0 00-2-2h-8a2 2 0 00-2 2v8a2 2 0 002 2z" data-astro-cid-mw7aashj></path> </svg> <span id="copy-btn-text" data-astro-cid-mw7aashj>Copy to LLM</span> </button> <article class="prose prose-invert max-w-4xl" data-astro-cid-mw7aashj> <h1 id="animation">Animation</h1>
|
|
3
5
|
<p>loopwind provides <strong>Tailwind-style animation classes</strong> that work with time to create smooth video animations without writing custom code.</p>
|
|
4
6
|
<blockquote>
|
|
5
7
|
<p><strong>Note:</strong> Animation classes only work with <strong>video templates</strong> and <strong>GIFs</strong>. For static images, animations will have no effect since there’s no time context.</p>
|
|
@@ -638,6 +640,197 @@
|
|
|
638
640
|
|
|
639
641
|
|
|
640
642
|
<table><thead><tr><th>Class</th><th>Description</th><th>Best For</th></tr></thead><tbody><tr><td><code>linear</code></td><td>Constant speed</td><td>Mechanical motion</td></tr><tr><td><code>ease-in</code></td><td>Slow start, fast end</td><td>Exit animations</td></tr><tr><td><code>ease-out</code></td><td>Fast start, slow end (default)</td><td>Enter animations</td></tr><tr><td><code>ease-in-out</code></td><td>Slow start and end</td><td>Subtle transitions</td></tr><tr><td><code>ease-in-cubic</code></td><td>Strong slow start</td><td>Dramatic exits</td></tr><tr><td><code>ease-out-cubic</code></td><td>Strong fast start</td><td>Impactful entrances</td></tr><tr><td><code>ease-in-out-cubic</code></td><td>Strong both ends</td><td>Emphasis animations</td></tr><tr><td><code>ease-in-quart</code></td><td>Very strong slow start</td><td>Powerful exits</td></tr><tr><td><code>ease-out-quart</code></td><td>Very strong fast start</td><td>Punchy entrances</td></tr><tr><td><code>ease-in-out-quart</code></td><td>Very strong both ends</td><td>Maximum drama</td></tr></tbody></table>
|
|
643
|
+
<h3 id="per-animation-type-easing">Per-Animation-Type Easing</h3>
|
|
644
|
+
<p>You can apply <strong>different easing functions</strong> to enter, exit, and loop animations on the same element using <code>enter-ease-*</code>, <code>exit-ease-*</code>, and <code>loop-ease-*</code> classes.</p>
|
|
645
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#6A737D">// Different easing for enter and exit</span></span>
|
|
646
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">h1</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-ease-out-cubic enter-fade-in/0/500 exit-ease-in exit-fade-out/2500/500'</span><span style="color:#E1E4E8">)}></span></span>
|
|
647
|
+
<span class="line"><span style="color:#E1E4E8"> Smooth entrance, sharp exit</span></span>
|
|
648
|
+
<span class="line"><span style="color:#E1E4E8"></</span><span style="color:#85E89D">h1</span><span style="color:#E1E4E8">></span></span>
|
|
649
|
+
<span class="line"></span>
|
|
650
|
+
<span class="line"><span style="color:#6A737D">// Loop with linear easing, enter with bounce</span></span>
|
|
651
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-ease-out enter-bounce-in/0/400 loop-ease-linear loop-fade/1000'</span><span style="color:#E1E4E8">)}></span></span>
|
|
652
|
+
<span class="line"><span style="color:#E1E4E8"> Bouncy entrance, linear loop</span></span>
|
|
653
|
+
<span class="line"><span style="color:#E1E4E8"></</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
654
|
+
<span class="line"></span>
|
|
655
|
+
<span class="line"><span style="color:#6A737D">// Default easing still works (applies to all animations)</span></span>
|
|
656
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'ease-in-out enter-fade-in/0/500 exit-fade-out/2500/500'</span><span style="color:#E1E4E8">)}></span></span>
|
|
657
|
+
<span class="line"><span style="color:#E1E4E8"> Same easing for both</span></span>
|
|
658
|
+
<span class="line"><span style="color:#E1E4E8"></</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
659
|
+
<span class="line"></span>
|
|
660
|
+
<span class="line"><span style="color:#6A737D">// Mix default with specific overrides</span></span>
|
|
661
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'ease-out enter-fade-in/0/500 exit-ease-in-cubic exit-fade-out/2500/500'</span><span style="color:#E1E4E8">)}></span></span>
|
|
662
|
+
<span class="line"><span style="color:#E1E4E8"> Default ease-out for enter, cubic-in for exit</span></span>
|
|
663
|
+
<span class="line"><span style="color:#E1E4E8"></</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
664
|
+
<span class="line"></span></code></pre>
|
|
665
|
+
<p><strong>How it works:</strong></p>
|
|
666
|
+
<ol>
|
|
667
|
+
<li><strong>Default easing</strong> (<code>ease-*</code>) applies to ALL animations if no specific override is set</li>
|
|
668
|
+
<li><strong>Specific easing</strong> (<code>enter-ease-*</code>, <code>exit-ease-*</code>, <code>loop-ease-*</code>) overrides the default for that animation type</li>
|
|
669
|
+
<li>If both are present, specific easing takes priority for its animation type</li>
|
|
670
|
+
</ol>
|
|
671
|
+
<p><strong>Available easing classes:</strong></p>
|
|
672
|
+
|
|
673
|
+
|
|
674
|
+
|
|
675
|
+
|
|
676
|
+
|
|
677
|
+
|
|
678
|
+
|
|
679
|
+
|
|
680
|
+
|
|
681
|
+
|
|
682
|
+
|
|
683
|
+
|
|
684
|
+
|
|
685
|
+
|
|
686
|
+
|
|
687
|
+
|
|
688
|
+
|
|
689
|
+
|
|
690
|
+
|
|
691
|
+
|
|
692
|
+
|
|
693
|
+
|
|
694
|
+
|
|
695
|
+
|
|
696
|
+
|
|
697
|
+
|
|
698
|
+
|
|
699
|
+
|
|
700
|
+
|
|
701
|
+
|
|
702
|
+
|
|
703
|
+
|
|
704
|
+
|
|
705
|
+
|
|
706
|
+
|
|
707
|
+
|
|
708
|
+
|
|
709
|
+
|
|
710
|
+
|
|
711
|
+
|
|
712
|
+
|
|
713
|
+
|
|
714
|
+
|
|
715
|
+
|
|
716
|
+
|
|
717
|
+
|
|
718
|
+
|
|
719
|
+
|
|
720
|
+
|
|
721
|
+
|
|
722
|
+
|
|
723
|
+
|
|
724
|
+
|
|
725
|
+
|
|
726
|
+
|
|
727
|
+
|
|
728
|
+
|
|
729
|
+
|
|
730
|
+
|
|
731
|
+
|
|
732
|
+
|
|
733
|
+
|
|
734
|
+
|
|
735
|
+
|
|
736
|
+
|
|
737
|
+
|
|
738
|
+
|
|
739
|
+
|
|
740
|
+
|
|
741
|
+
|
|
742
|
+
|
|
743
|
+
|
|
744
|
+
|
|
745
|
+
|
|
746
|
+
|
|
747
|
+
|
|
748
|
+
|
|
749
|
+
<table><thead><tr><th>Default (all animations)</th><th>Enter only</th><th>Exit only</th><th>Loop only</th></tr></thead><tbody><tr><td><code>ease-in</code></td><td><code>enter-ease-in</code></td><td><code>exit-ease-in</code></td><td><code>loop-ease-in</code></td></tr><tr><td><code>ease-out</code></td><td><code>enter-ease-out</code></td><td><code>exit-ease-out</code></td><td><code>loop-ease-out</code></td></tr><tr><td><code>ease-in-out</code></td><td><code>enter-ease-in-out</code></td><td><code>exit-ease-in-out</code></td><td><code>loop-ease-in-out</code></td></tr><tr><td><code>ease-in-cubic</code></td><td><code>enter-ease-in-cubic</code></td><td><code>exit-ease-in-cubic</code></td><td><code>loop-ease-in-cubic</code></td></tr><tr><td><code>ease-out-cubic</code></td><td><code>enter-ease-out-cubic</code></td><td><code>exit-ease-out-cubic</code></td><td><code>loop-ease-out-cubic</code></td></tr><tr><td><code>ease-in-out-cubic</code></td><td><code>enter-ease-in-out-cubic</code></td><td><code>exit-ease-in-out-cubic</code></td><td><code>loop-ease-in-out-cubic</code></td></tr><tr><td><code>ease-in-quart</code></td><td><code>enter-ease-in-quart</code></td><td><code>exit-ease-in-quart</code></td><td><code>loop-ease-in-quart</code></td></tr><tr><td><code>ease-out-quart</code></td><td><code>enter-ease-out-quart</code></td><td><code>exit-ease-out-quart</code></td><td><code>loop-ease-out-quart</code></td></tr><tr><td><code>ease-in-out-quart</code></td><td><code>enter-ease-in-out-quart</code></td><td><code>exit-ease-in-out-quart</code></td><td><code>loop-ease-in-out-quart</code></td></tr><tr><td><code>linear</code></td><td><code>enter-ease-linear</code></td><td><code>exit-ease-linear</code></td><td><code>loop-ease-linear</code></td></tr><tr><td><code>ease-spring</code></td><td><code>enter-ease-spring</code></td><td><code>exit-ease-spring</code></td><td><code>loop-ease-spring</code></td></tr></tbody></table>
|
|
750
|
+
<h3 id="spring-easing">Spring Easing</h3>
|
|
751
|
+
<p>Spring easing creates natural, physics-based bouncy animations. Use the built-in <code>ease-spring</code> easing or create custom springs with configurable parameters.</p>
|
|
752
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#6A737D">// Default spring easing</span></span>
|
|
753
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">h1</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'ease-spring enter-bounce-in/0/500'</span><span style="color:#E1E4E8">)}>Bouncy spring!</</span><span style="color:#85E89D">h1</span><span style="color:#E1E4E8">></span></span>
|
|
754
|
+
<span class="line"></span>
|
|
755
|
+
<span class="line"><span style="color:#6A737D">// Per-animation-type spring</span></span>
|
|
756
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-ease-spring enter-fade-in/0/500 exit-ease-out exit-fade-out/2500/500'</span><span style="color:#E1E4E8">)}></span></span>
|
|
757
|
+
<span class="line"><span style="color:#E1E4E8"> Spring entrance, smooth exit</span></span>
|
|
758
|
+
<span class="line"><span style="color:#E1E4E8"></</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
759
|
+
<span class="line"></span>
|
|
760
|
+
<span class="line"><span style="color:#6A737D">// Custom spring with parameters: ease-spring/mass/stiffness/damping</span></span>
|
|
761
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">h1</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'ease-spring/1/100/10 enter-scale-in/0/800'</span><span style="color:#E1E4E8">)}></span></span>
|
|
762
|
+
<span class="line"><span style="color:#E1E4E8"> Custom spring (mass=1, stiffness=100, damping=10)</span></span>
|
|
763
|
+
<span class="line"><span style="color:#E1E4E8"></</span><span style="color:#85E89D">h1</span><span style="color:#E1E4E8">></span></span>
|
|
764
|
+
<span class="line"></span>
|
|
765
|
+
<span class="line"><span style="color:#6A737D">// More bouncy spring (lower damping)</span></span>
|
|
766
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'ease-spring/1/170/8 enter-bounce-in-up/0/600'</span><span style="color:#E1E4E8">)}></span></span>
|
|
767
|
+
<span class="line"><span style="color:#E1E4E8"> Extra bouncy!</span></span>
|
|
768
|
+
<span class="line"><span style="color:#E1E4E8"></</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
769
|
+
<span class="line"></span>
|
|
770
|
+
<span class="line"><span style="color:#6A737D">// Stiffer spring (higher stiffness, faster)</span></span>
|
|
771
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'ease-spring/1/200/12 enter-fade-in-up/0/400'</span><span style="color:#E1E4E8">)}></span></span>
|
|
772
|
+
<span class="line"><span style="color:#E1E4E8"> Snappy spring</span></span>
|
|
773
|
+
<span class="line"><span style="color:#E1E4E8"></</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
774
|
+
<span class="line"></span>
|
|
775
|
+
<span class="line"><span style="color:#6A737D">// Per-animation-type custom springs</span></span>
|
|
776
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-ease-spring/1/150/10 enter-fade-in/0/500 exit-ease-spring/1/100/15 exit-fade-out/2500/500'</span><span style="color:#E1E4E8">)}></span></span>
|
|
777
|
+
<span class="line"><span style="color:#E1E4E8"> Different springs for enter and exit</span></span>
|
|
778
|
+
<span class="line"><span style="color:#E1E4E8"></</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
779
|
+
<span class="line"></span></code></pre>
|
|
780
|
+
<p><strong>Spring parameters:</strong></p>
|
|
781
|
+
|
|
782
|
+
|
|
783
|
+
|
|
784
|
+
|
|
785
|
+
|
|
786
|
+
|
|
787
|
+
|
|
788
|
+
|
|
789
|
+
|
|
790
|
+
|
|
791
|
+
|
|
792
|
+
|
|
793
|
+
|
|
794
|
+
|
|
795
|
+
|
|
796
|
+
|
|
797
|
+
|
|
798
|
+
|
|
799
|
+
|
|
800
|
+
|
|
801
|
+
|
|
802
|
+
|
|
803
|
+
|
|
804
|
+
|
|
805
|
+
|
|
806
|
+
|
|
807
|
+
|
|
808
|
+
|
|
809
|
+
|
|
810
|
+
<table><thead><tr><th>Parameter</th><th>Description</th><th>Effect when increased</th><th>Default</th></tr></thead><tbody><tr><td><strong>mass</strong></td><td>Mass of the spring</td><td>Slower, more inertia</td><td>1</td></tr><tr><td><strong>stiffness</strong></td><td>Spring stiffness</td><td>Faster, snappier</td><td>100</td></tr><tr><td><strong>damping</strong></td><td>Damping coefficient</td><td>Less bounce, smoother</td><td>10</td></tr></tbody></table>
|
|
811
|
+
<p><strong>Common spring presets:</strong></p>
|
|
812
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#6A737D">// Gentle bounce (default)</span></span>
|
|
813
|
+
<span class="line"><span style="color:#E1E4E8">ease</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">spring</span><span style="color:#F97583">/</span><span style="color:#79B8FF">1</span><span style="color:#F97583">/</span><span style="color:#79B8FF">100</span><span style="color:#F97583">/</span><span style="color:#79B8FF">10</span></span>
|
|
814
|
+
<span class="line"></span>
|
|
815
|
+
<span class="line"><span style="color:#6A737D">// Extra bouncy</span></span>
|
|
816
|
+
<span class="line"><span style="color:#E1E4E8">ease</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">spring</span><span style="color:#F97583">/</span><span style="color:#79B8FF">1</span><span style="color:#F97583">/</span><span style="color:#79B8FF">170</span><span style="color:#F97583">/</span><span style="color:#79B8FF">8</span></span>
|
|
817
|
+
<span class="line"></span>
|
|
818
|
+
<span class="line"><span style="color:#6A737D">// Snappy (no bounce)</span></span>
|
|
819
|
+
<span class="line"><span style="color:#E1E4E8">ease</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">spring</span><span style="color:#F97583">/</span><span style="color:#79B8FF">1</span><span style="color:#F97583">/</span><span style="color:#79B8FF">200</span><span style="color:#F97583">/</span><span style="color:#79B8FF">15</span></span>
|
|
820
|
+
<span class="line"></span>
|
|
821
|
+
<span class="line"><span style="color:#6A737D">// Slow and bouncy</span></span>
|
|
822
|
+
<span class="line"><span style="color:#E1E4E8">ease</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">spring</span><span style="color:#F97583">/</span><span style="color:#79B8FF">2</span><span style="color:#F97583">/</span><span style="color:#79B8FF">100</span><span style="color:#F97583">/</span><span style="color:#79B8FF">8</span></span>
|
|
823
|
+
<span class="line"></span>
|
|
824
|
+
<span class="line"><span style="color:#6A737D">// Fast and tight</span></span>
|
|
825
|
+
<span class="line"><span style="color:#E1E4E8">ease</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">spring</span><span style="color:#F97583">/</span><span style="color:#79B8FF">0.5</span><span style="color:#F97583">/</span><span style="color:#79B8FF">300</span><span style="color:#F97583">/</span><span style="color:#79B8FF">20</span></span>
|
|
826
|
+
<span class="line"></span></code></pre>
|
|
827
|
+
<p><strong>How spring works:</strong></p>
|
|
828
|
+
<ol>
|
|
829
|
+
<li><strong>Default <code>ease-spring</code></strong> - Uses a pre-calculated spring curve optimized for most use cases</li>
|
|
830
|
+
<li><strong>Custom <code>ease-spring/mass/stiffness/damping</code></strong> - Generates a physics-based spring curve using the <a href="https://www.kvin.me/css-springs">damped harmonic oscillator</a> formula</li>
|
|
831
|
+
<li>The spring automatically calculates its ideal duration to reach the final state</li>
|
|
832
|
+
<li>Works with all animation types: <code>ease-spring</code>, <code>enter-ease-spring</code>, <code>exit-ease-spring</code>, <code>loop-ease-spring</code></li>
|
|
833
|
+
</ol>
|
|
641
834
|
<h2 id="combining-enter-and-exit">Combining Enter and Exit</h2>
|
|
642
835
|
<p>You can use both enter and exit animations on the same element:</p>
|
|
643
836
|
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">export</span><span style="color:#F97583"> default</span><span style="color:#F97583"> function</span><span style="color:#B392F0"> EnterExit</span><span style="color:#E1E4E8">({ </span><span style="color:#FFAB70">tw</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">title</span><span style="color:#E1E4E8"> }) {</span></span>
|
|
@@ -857,13 +1050,446 @@
|
|
|
857
1050
|
<h3 id="when-to-use-programmatic-animations">When to Use Programmatic Animations</h3>
|
|
858
1051
|
<p>Use <code>progress</code>/<code>frame</code> instead of animation classes when you need:</p>
|
|
859
1052
|
<ul>
|
|
860
|
-
<li><strong>Custom easing functions</strong> (elastic,
|
|
1053
|
+
<li><strong>Custom easing functions</strong> (elastic, bounce with specific curves beyond built-in ease-spring)</li>
|
|
861
1054
|
<li><strong>Color cycling or gradients</strong> based on time</li>
|
|
862
1055
|
<li><strong>Mathematical animations</strong> (sine waves, spirals, etc.)</li>
|
|
863
1056
|
<li><strong>Complex multi-property animations</strong> that need precise coordination</li>
|
|
864
1057
|
<li><strong>Conditional logic</strong> based on specific frame numbers</li>
|
|
865
1058
|
</ul>
|
|
866
1059
|
<p>For everything else, prefer animation classes - they’re simpler and more maintainable.</p>
|
|
1060
|
+
<h3 id="animating-along-paths">Animating Along Paths</h3>
|
|
1061
|
+
<p>Animate elements along SVG paths with proper rotation using built-in <strong>path helpers</strong>:</p>
|
|
1062
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">export</span><span style="color:#F97583"> default</span><span style="color:#F97583"> function</span><span style="color:#B392F0"> PathFollowing</span><span style="color:#E1E4E8">({ </span><span style="color:#FFAB70">tw</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">progress</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">path</span><span style="color:#E1E4E8"> }) {</span></span>
|
|
1063
|
+
<span class="line"><span style="color:#6A737D"> // Follow a quadratic Bezier curve - one line!</span></span>
|
|
1064
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> rocket</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> path.</span><span style="color:#B392F0">followQuadratic</span><span style="color:#E1E4E8">(</span></span>
|
|
1065
|
+
<span class="line"><span style="color:#E1E4E8"> { x: </span><span style="color:#79B8FF">200</span><span style="color:#E1E4E8">, y: </span><span style="color:#79B8FF">400</span><span style="color:#E1E4E8"> }, </span><span style="color:#6A737D">// Start point</span></span>
|
|
1066
|
+
<span class="line"><span style="color:#E1E4E8"> { x: </span><span style="color:#79B8FF">960</span><span style="color:#E1E4E8">, y: </span><span style="color:#79B8FF">150</span><span style="color:#E1E4E8"> }, </span><span style="color:#6A737D">// Control point</span></span>
|
|
1067
|
+
<span class="line"><span style="color:#E1E4E8"> { x: </span><span style="color:#79B8FF">1720</span><span style="color:#E1E4E8">, y: </span><span style="color:#79B8FF">400</span><span style="color:#E1E4E8"> }, </span><span style="color:#6A737D">// End point</span></span>
|
|
1068
|
+
<span class="line"><span style="color:#E1E4E8"> progress</span></span>
|
|
1069
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1070
|
+
<span class="line"></span>
|
|
1071
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> (</span></span>
|
|
1072
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{{ display: </span><span style="color:#9ECBFF">'flex'</span><span style="color:#E1E4E8">, </span><span style="color:#F97583">...</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'relative w-full h-full bg-gray-900'</span><span style="color:#E1E4E8">) }}></span></span>
|
|
1073
|
+
<span class="line"><span style="color:#E1E4E8"> {</span><span style="color:#6A737D">/* Draw the path (optional) */</span><span style="color:#E1E4E8">}</span></span>
|
|
1074
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">svg</span><span style="color:#B392F0"> width</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"1920"</span><span style="color:#B392F0"> height</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"1080"</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{{ position: </span><span style="color:#9ECBFF">'absolute'</span><span style="color:#E1E4E8"> }}></span></span>
|
|
1075
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">path</span></span>
|
|
1076
|
+
<span class="line"><span style="color:#B392F0"> d</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"M 200 400 Q 960 150 1720 400"</span></span>
|
|
1077
|
+
<span class="line"><span style="color:#B392F0"> stroke</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"rgba(255,255,255,0.2)"</span></span>
|
|
1078
|
+
<span class="line"><span style="color:#B392F0"> strokeWidth</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#79B8FF">2</span><span style="color:#E1E4E8">}</span></span>
|
|
1079
|
+
<span class="line"><span style="color:#B392F0"> fill</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"none"</span></span>
|
|
1080
|
+
<span class="line"><span style="color:#E1E4E8"> /></span></span>
|
|
1081
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">svg</span><span style="color:#E1E4E8">></span></span>
|
|
1082
|
+
<span class="line"></span>
|
|
1083
|
+
<span class="line"><span style="color:#E1E4E8"> {</span><span style="color:#6A737D">/* Element following the path */</span><span style="color:#E1E4E8">}</span></span>
|
|
1084
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span></span>
|
|
1085
|
+
<span class="line"><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{{</span></span>
|
|
1086
|
+
<span class="line"><span style="color:#E1E4E8"> position: </span><span style="color:#9ECBFF">"absolute"</span><span style="color:#E1E4E8">,</span></span>
|
|
1087
|
+
<span class="line"><span style="color:#E1E4E8"> left: rocket.x,</span></span>
|
|
1088
|
+
<span class="line"><span style="color:#E1E4E8"> top: rocket.y,</span></span>
|
|
1089
|
+
<span class="line"><span style="color:#E1E4E8"> transform: </span><span style="color:#9ECBFF">`translate(-50%, -50%) rotate(${</span><span style="color:#E1E4E8">rocket</span><span style="color:#9ECBFF">.</span><span style="color:#E1E4E8">angle</span><span style="color:#9ECBFF">}deg)`</span><span style="color:#E1E4E8">,</span></span>
|
|
1090
|
+
<span class="line"><span style="color:#E1E4E8"> fontSize: </span><span style="color:#9ECBFF">'48px'</span></span>
|
|
1091
|
+
<span class="line"><span style="color:#E1E4E8"> }}</span></span>
|
|
1092
|
+
<span class="line"><span style="color:#E1E4E8"> ></span></span>
|
|
1093
|
+
<span class="line"><span style="color:#E1E4E8"> 🚀</span></span>
|
|
1094
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1095
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1096
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1097
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1098
|
+
<span class="line"></span></code></pre>
|
|
1099
|
+
<h3 id="text-path-animations">Text Path Animations</h3>
|
|
1100
|
+
<p>Combine <code>textPath</code> helpers with animation classes to create animated text along curves:</p>
|
|
1101
|
+
<p><strong>Rotating text around a circle:</strong></p>
|
|
1102
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">export</span><span style="color:#F97583"> default</span><span style="color:#F97583"> function</span><span style="color:#B392F0"> RotatingCircleText</span><span style="color:#E1E4E8">({ </span><span style="color:#FFAB70">tw</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">textPath</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">progress</span><span style="color:#E1E4E8"> }) {</span></span>
|
|
1103
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> (</span></span>
|
|
1104
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'relative w-full h-full bg-black'</span><span style="color:#E1E4E8">)}></span></span>
|
|
1105
|
+
<span class="line"><span style="color:#E1E4E8"> {</span><span style="color:#6A737D">/* Text rotates around circle using progress */</span><span style="color:#E1E4E8">}</span></span>
|
|
1106
|
+
<span class="line"><span style="color:#E1E4E8"> {textPath.</span><span style="color:#B392F0">onCircle</span><span style="color:#E1E4E8">(</span></span>
|
|
1107
|
+
<span class="line"><span style="color:#9ECBFF"> "SPINNING TEXT • AROUND • "</span><span style="color:#E1E4E8">,</span></span>
|
|
1108
|
+
<span class="line"><span style="color:#79B8FF"> 960</span><span style="color:#E1E4E8">, </span><span style="color:#6A737D">// center x</span></span>
|
|
1109
|
+
<span class="line"><span style="color:#79B8FF"> 540</span><span style="color:#E1E4E8">, </span><span style="color:#6A737D">// center y</span></span>
|
|
1110
|
+
<span class="line"><span style="color:#79B8FF"> 400</span><span style="color:#E1E4E8">, </span><span style="color:#6A737D">// radius</span></span>
|
|
1111
|
+
<span class="line"><span style="color:#E1E4E8"> progress, </span><span style="color:#6A737D">// rotation offset (0-1 animates full rotation)</span></span>
|
|
1112
|
+
<span class="line"><span style="color:#E1E4E8"> {</span></span>
|
|
1113
|
+
<span class="line"><span style="color:#E1E4E8"> fontSize: </span><span style="color:#9ECBFF">"3xl"</span><span style="color:#E1E4E8">,</span></span>
|
|
1114
|
+
<span class="line"><span style="color:#E1E4E8"> fontWeight: </span><span style="color:#9ECBFF">"bold"</span><span style="color:#E1E4E8">,</span></span>
|
|
1115
|
+
<span class="line"><span style="color:#E1E4E8"> color: </span><span style="color:#9ECBFF">"yellow-300"</span></span>
|
|
1116
|
+
<span class="line"><span style="color:#E1E4E8"> }</span></span>
|
|
1117
|
+
<span class="line"><span style="color:#E1E4E8"> )}</span></span>
|
|
1118
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1119
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1120
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1121
|
+
<span class="line"></span></code></pre>
|
|
1122
|
+
<p><strong>Animated text reveal along a path:</strong></p>
|
|
1123
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">export</span><span style="color:#F97583"> default</span><span style="color:#F97583"> function</span><span style="color:#B392F0"> PathTextReveal</span><span style="color:#E1E4E8">({ </span><span style="color:#FFAB70">tw</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">textPath</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">progress</span><span style="color:#E1E4E8"> }) {</span></span>
|
|
1124
|
+
<span class="line"><span style="color:#6A737D"> // Create custom path follower that animates position</span></span>
|
|
1125
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#B392F0"> pathFollower</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> (</span><span style="color:#FFAB70">t</span><span style="color:#E1E4E8">) </span><span style="color:#F97583">=></span><span style="color:#E1E4E8"> {</span></span>
|
|
1126
|
+
<span class="line"><span style="color:#6A737D"> // Only show characters up to current progress</span></span>
|
|
1127
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> visibleProgress</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> progress </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 1.5</span><span style="color:#E1E4E8">; </span><span style="color:#6A737D">// Extend range for smooth reveal</span></span>
|
|
1128
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> opacity</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583"><</span><span style="color:#E1E4E8"> visibleProgress </span><span style="color:#F97583">?</span><span style="color:#79B8FF"> 1</span><span style="color:#F97583"> :</span><span style="color:#79B8FF"> 0</span><span style="color:#E1E4E8">;</span></span>
|
|
1129
|
+
<span class="line"></span>
|
|
1130
|
+
<span class="line"><span style="color:#6A737D"> // Follow quadratic curve</span></span>
|
|
1131
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> pos</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> {</span></span>
|
|
1132
|
+
<span class="line"><span style="color:#E1E4E8"> x: (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 200</span><span style="color:#F97583"> +</span><span style="color:#79B8FF"> 2</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 960</span><span style="color:#F97583"> +</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 1720</span><span style="color:#E1E4E8">,</span></span>
|
|
1133
|
+
<span class="line"><span style="color:#E1E4E8"> y: (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 400</span><span style="color:#F97583"> +</span><span style="color:#79B8FF"> 2</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 150</span><span style="color:#F97583"> +</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 400</span><span style="color:#E1E4E8">,</span></span>
|
|
1134
|
+
<span class="line"><span style="color:#E1E4E8"> angle: </span><span style="color:#79B8FF">0</span></span>
|
|
1135
|
+
<span class="line"><span style="color:#E1E4E8"> };</span></span>
|
|
1136
|
+
<span class="line"></span>
|
|
1137
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> { </span><span style="color:#F97583">...</span><span style="color:#E1E4E8">pos, opacity };</span></span>
|
|
1138
|
+
<span class="line"><span style="color:#E1E4E8"> };</span></span>
|
|
1139
|
+
<span class="line"></span>
|
|
1140
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> (</span></span>
|
|
1141
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'relative w-full h-full bg-gray-900'</span><span style="color:#E1E4E8">)}></span></span>
|
|
1142
|
+
<span class="line"><span style="color:#E1E4E8"> {textPath.</span><span style="color:#B392F0">onPath</span><span style="color:#E1E4E8">(</span></span>
|
|
1143
|
+
<span class="line"><span style="color:#9ECBFF"> "REVEALING TEXT"</span><span style="color:#E1E4E8">,</span></span>
|
|
1144
|
+
<span class="line"><span style="color:#E1E4E8"> pathFollower,</span></span>
|
|
1145
|
+
<span class="line"><span style="color:#E1E4E8"> {</span></span>
|
|
1146
|
+
<span class="line"><span style="color:#E1E4E8"> fontSize: </span><span style="color:#9ECBFF">"4xl"</span><span style="color:#E1E4E8">,</span></span>
|
|
1147
|
+
<span class="line"><span style="color:#E1E4E8"> fontWeight: </span><span style="color:#9ECBFF">"bold"</span><span style="color:#E1E4E8">,</span></span>
|
|
1148
|
+
<span class="line"><span style="color:#E1E4E8"> color: </span><span style="color:#9ECBFF">"blue-300"</span></span>
|
|
1149
|
+
<span class="line"><span style="color:#E1E4E8"> }</span></span>
|
|
1150
|
+
<span class="line"><span style="color:#E1E4E8"> ).</span><span style="color:#B392F0">map</span><span style="color:#E1E4E8">((</span><span style="color:#FFAB70">char</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">i</span><span style="color:#E1E4E8">) </span><span style="color:#F97583">=></span><span style="color:#E1E4E8"> (</span></span>
|
|
1151
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> key</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{i} </span><span style="color:#B392F0">style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{{ </span><span style="color:#F97583">...</span><span style="color:#E1E4E8">char.props.style, opacity: char.props.style.opacity </span><span style="color:#F97583">||</span><span style="color:#79B8FF"> 1</span><span style="color:#E1E4E8"> }}></span></span>
|
|
1152
|
+
<span class="line"><span style="color:#E1E4E8"> {char}</span></span>
|
|
1153
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1154
|
+
<span class="line"><span style="color:#E1E4E8"> ))}</span></span>
|
|
1155
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1156
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1157
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1158
|
+
<span class="line"></span></code></pre>
|
|
1159
|
+
<p><strong>Staggered character entrance:</strong></p>
|
|
1160
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">export</span><span style="color:#F97583"> default</span><span style="color:#F97583"> function</span><span style="color:#B392F0"> StaggeredCircleText</span><span style="color:#E1E4E8">({ </span><span style="color:#FFAB70">tw</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">textPath</span><span style="color:#E1E4E8"> }) {</span></span>
|
|
1161
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> text</span><span style="color:#F97583"> =</span><span style="color:#9ECBFF"> "HELLO WORLD"</span><span style="color:#E1E4E8">;</span></span>
|
|
1162
|
+
<span class="line"></span>
|
|
1163
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> (</span></span>
|
|
1164
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'relative w-full h-full bg-slate-900'</span><span style="color:#E1E4E8">)}></span></span>
|
|
1165
|
+
<span class="line"><span style="color:#E1E4E8"> {textPath.</span><span style="color:#B392F0">onCircle</span><span style="color:#E1E4E8">(</span></span>
|
|
1166
|
+
<span class="line"><span style="color:#E1E4E8"> text,</span></span>
|
|
1167
|
+
<span class="line"><span style="color:#79B8FF"> 960</span><span style="color:#E1E4E8">, </span><span style="color:#79B8FF">540</span><span style="color:#E1E4E8">, </span><span style="color:#79B8FF">400</span><span style="color:#E1E4E8">, </span><span style="color:#79B8FF">0</span><span style="color:#E1E4E8">,</span></span>
|
|
1168
|
+
<span class="line"><span style="color:#E1E4E8"> { fontSize: </span><span style="color:#9ECBFF">"4xl"</span><span style="color:#E1E4E8">, fontWeight: </span><span style="color:#9ECBFF">"bold"</span><span style="color:#E1E4E8">, color: </span><span style="color:#9ECBFF">"white"</span><span style="color:#E1E4E8"> }</span></span>
|
|
1169
|
+
<span class="line"><span style="color:#E1E4E8"> ).</span><span style="color:#B392F0">map</span><span style="color:#E1E4E8">((</span><span style="color:#FFAB70">char</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">i</span><span style="color:#E1E4E8">) </span><span style="color:#F97583">=></span><span style="color:#E1E4E8"> {</span></span>
|
|
1170
|
+
<span class="line"><span style="color:#6A737D"> // Stagger fade-in: each character starts 50ms later</span></span>
|
|
1171
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> staggerDelay</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> i </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 50</span><span style="color:#E1E4E8">;</span></span>
|
|
1172
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> (</span></span>
|
|
1173
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span></span>
|
|
1174
|
+
<span class="line"><span style="color:#B392F0"> key</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{i}</span></span>
|
|
1175
|
+
<span class="line"><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{{</span></span>
|
|
1176
|
+
<span class="line"><span style="color:#F97583"> ...</span><span style="color:#E1E4E8">char.props.style,</span></span>
|
|
1177
|
+
<span class="line"><span style="color:#F97583"> ...</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">`enter-fade-in/${</span><span style="color:#E1E4E8">staggerDelay</span><span style="color:#9ECBFF">}/300 enter-scale-100/${</span><span style="color:#E1E4E8">staggerDelay</span><span style="color:#9ECBFF">}/300`</span><span style="color:#E1E4E8">)</span></span>
|
|
1178
|
+
<span class="line"><span style="color:#E1E4E8"> }}</span></span>
|
|
1179
|
+
<span class="line"><span style="color:#E1E4E8"> ></span></span>
|
|
1180
|
+
<span class="line"><span style="color:#E1E4E8"> {char.props.children}</span></span>
|
|
1181
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1182
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1183
|
+
<span class="line"><span style="color:#E1E4E8"> })}</span></span>
|
|
1184
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1185
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1186
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1187
|
+
<span class="line"></span></code></pre>
|
|
1188
|
+
<p><strong>Text with bounce entrance along arc:</strong></p>
|
|
1189
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">export</span><span style="color:#F97583"> default</span><span style="color:#F97583"> function</span><span style="color:#B392F0"> BouncyArcText</span><span style="color:#E1E4E8">({ </span><span style="color:#FFAB70">tw</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">textPath</span><span style="color:#E1E4E8"> }) {</span></span>
|
|
1190
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> (</span></span>
|
|
1191
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'relative w-full h-full bg-gradient-to-br from-purple-600 to-blue-500'</span><span style="color:#E1E4E8">)}></span></span>
|
|
1192
|
+
<span class="line"><span style="color:#E1E4E8"> {</span><span style="color:#6A737D">/* Draw the arc path */</span><span style="color:#E1E4E8">}</span></span>
|
|
1193
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">svg</span><span style="color:#B392F0"> width</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"1920"</span><span style="color:#B392F0"> height</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"1080"</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{{ position: </span><span style="color:#9ECBFF">'absolute'</span><span style="color:#E1E4E8"> }}></span></span>
|
|
1194
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">path</span></span>
|
|
1195
|
+
<span class="line"><span style="color:#B392F0"> d</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"M 300 900 A 600 600 0 0 1 1620 900"</span></span>
|
|
1196
|
+
<span class="line"><span style="color:#B392F0"> stroke</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"rgba(255,255,255,0.2)"</span></span>
|
|
1197
|
+
<span class="line"><span style="color:#B392F0"> strokeWidth</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#79B8FF">2</span><span style="color:#E1E4E8">}</span></span>
|
|
1198
|
+
<span class="line"><span style="color:#B392F0"> fill</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"none"</span></span>
|
|
1199
|
+
<span class="line"><span style="color:#B392F0"> strokeDasharray</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"5 5"</span></span>
|
|
1200
|
+
<span class="line"><span style="color:#E1E4E8"> /></span></span>
|
|
1201
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">svg</span><span style="color:#E1E4E8">></span></span>
|
|
1202
|
+
<span class="line"></span>
|
|
1203
|
+
<span class="line"><span style="color:#E1E4E8"> {</span><span style="color:#6A737D">/* Text follows arc with staggered bounce */</span><span style="color:#E1E4E8">}</span></span>
|
|
1204
|
+
<span class="line"><span style="color:#E1E4E8"> {textPath.</span><span style="color:#B392F0">onArc</span><span style="color:#E1E4E8">(</span></span>
|
|
1205
|
+
<span class="line"><span style="color:#9ECBFF"> "BOUNCING ON ARC"</span><span style="color:#E1E4E8">,</span></span>
|
|
1206
|
+
<span class="line"><span style="color:#79B8FF"> 960</span><span style="color:#E1E4E8">, </span><span style="color:#6A737D">// cx</span></span>
|
|
1207
|
+
<span class="line"><span style="color:#79B8FF"> 300</span><span style="color:#E1E4E8">, </span><span style="color:#6A737D">// cy</span></span>
|
|
1208
|
+
<span class="line"><span style="color:#79B8FF"> 600</span><span style="color:#E1E4E8">, </span><span style="color:#6A737D">// radius</span></span>
|
|
1209
|
+
<span class="line"><span style="color:#79B8FF"> 180</span><span style="color:#E1E4E8">, </span><span style="color:#6A737D">// start angle</span></span>
|
|
1210
|
+
<span class="line"><span style="color:#79B8FF"> 360</span><span style="color:#E1E4E8">, </span><span style="color:#6A737D">// end angle</span></span>
|
|
1211
|
+
<span class="line"><span style="color:#E1E4E8"> { fontSize: </span><span style="color:#9ECBFF">"3xl"</span><span style="color:#E1E4E8">, fontWeight: </span><span style="color:#9ECBFF">"bold"</span><span style="color:#E1E4E8">, color: </span><span style="color:#9ECBFF">"white"</span><span style="color:#E1E4E8"> }</span></span>
|
|
1212
|
+
<span class="line"><span style="color:#E1E4E8"> ).</span><span style="color:#B392F0">map</span><span style="color:#E1E4E8">((</span><span style="color:#FFAB70">char</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">i</span><span style="color:#E1E4E8">) </span><span style="color:#F97583">=></span><span style="color:#E1E4E8"> (</span></span>
|
|
1213
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span></span>
|
|
1214
|
+
<span class="line"><span style="color:#B392F0"> key</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{i}</span></span>
|
|
1215
|
+
<span class="line"><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{{</span></span>
|
|
1216
|
+
<span class="line"><span style="color:#F97583"> ...</span><span style="color:#E1E4E8">char.props.style,</span></span>
|
|
1217
|
+
<span class="line"><span style="color:#F97583"> ...</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">`ease-out enter-bounce-in-up/${</span><span style="color:#E1E4E8">i</span><span style="color:#F97583"> *</span><span style="color:#79B8FF"> 80</span><span style="color:#9ECBFF">}/500`</span><span style="color:#E1E4E8">)</span></span>
|
|
1218
|
+
<span class="line"><span style="color:#E1E4E8"> }}</span></span>
|
|
1219
|
+
<span class="line"><span style="color:#E1E4E8"> ></span></span>
|
|
1220
|
+
<span class="line"><span style="color:#E1E4E8"> {char.props.children}</span></span>
|
|
1221
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1222
|
+
<span class="line"><span style="color:#E1E4E8"> ))}</span></span>
|
|
1223
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1224
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1225
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1226
|
+
<span class="line"></span></code></pre>
|
|
1227
|
+
<p><strong>Loop animation with text on curve:</strong></p>
|
|
1228
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">export</span><span style="color:#F97583"> default</span><span style="color:#F97583"> function</span><span style="color:#B392F0"> LoopingCurveText</span><span style="color:#E1E4E8">({ </span><span style="color:#FFAB70">tw</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">textPath</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">frame</span><span style="color:#E1E4E8"> }) {</span></span>
|
|
1229
|
+
<span class="line"><span style="color:#6A737D"> // Calculate wave effect using frame</span></span>
|
|
1230
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> waveOffset</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> Math.</span><span style="color:#B392F0">sin</span><span style="color:#E1E4E8">(frame </span><span style="color:#F97583">/</span><span style="color:#79B8FF"> 30</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> Math.</span><span style="color:#79B8FF">PI</span><span style="color:#F97583"> *</span><span style="color:#79B8FF"> 2</span><span style="color:#E1E4E8">) </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 0.1</span><span style="color:#E1E4E8">;</span></span>
|
|
1231
|
+
<span class="line"></span>
|
|
1232
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> (</span></span>
|
|
1233
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'relative w-full h-full bg-black'</span><span style="color:#E1E4E8">)}></span></span>
|
|
1234
|
+
<span class="line"><span style="color:#E1E4E8"> {textPath.</span><span style="color:#B392F0">onQuadratic</span><span style="color:#E1E4E8">(</span></span>
|
|
1235
|
+
<span class="line"><span style="color:#9ECBFF"> "WAVY TEXT"</span><span style="color:#E1E4E8">,</span></span>
|
|
1236
|
+
<span class="line"><span style="color:#E1E4E8"> { x: </span><span style="color:#79B8FF">200</span><span style="color:#E1E4E8">, y: </span><span style="color:#79B8FF">400</span><span style="color:#E1E4E8"> },</span></span>
|
|
1237
|
+
<span class="line"><span style="color:#E1E4E8"> { x: </span><span style="color:#79B8FF">960</span><span style="color:#E1E4E8">, y: </span><span style="color:#79B8FF">150</span><span style="color:#E1E4E8"> },</span></span>
|
|
1238
|
+
<span class="line"><span style="color:#E1E4E8"> { x: </span><span style="color:#79B8FF">1720</span><span style="color:#E1E4E8">, y: </span><span style="color:#79B8FF">400</span><span style="color:#E1E4E8"> },</span></span>
|
|
1239
|
+
<span class="line"><span style="color:#E1E4E8"> { fontSize: </span><span style="color:#9ECBFF">"4xl"</span><span style="color:#E1E4E8">, fontWeight: </span><span style="color:#9ECBFF">"bold"</span><span style="color:#E1E4E8">, color: </span><span style="color:#9ECBFF">"pink-300"</span><span style="color:#E1E4E8"> }</span></span>
|
|
1240
|
+
<span class="line"><span style="color:#E1E4E8"> ).</span><span style="color:#B392F0">map</span><span style="color:#E1E4E8">((</span><span style="color:#FFAB70">char</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">i</span><span style="color:#E1E4E8">) </span><span style="color:#F97583">=></span><span style="color:#E1E4E8"> (</span></span>
|
|
1241
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span></span>
|
|
1242
|
+
<span class="line"><span style="color:#B392F0"> key</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{i}</span></span>
|
|
1243
|
+
<span class="line"><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{{</span></span>
|
|
1244
|
+
<span class="line"><span style="color:#F97583"> ...</span><span style="color:#E1E4E8">char.props.style,</span></span>
|
|
1245
|
+
<span class="line"><span style="color:#E1E4E8"> transform: </span><span style="color:#9ECBFF">`${</span><span style="color:#E1E4E8">char</span><span style="color:#9ECBFF">.</span><span style="color:#E1E4E8">props</span><span style="color:#9ECBFF">.</span><span style="color:#E1E4E8">style</span><span style="color:#9ECBFF">.</span><span style="color:#E1E4E8">transform</span><span style="color:#9ECBFF">} translateY(${</span><span style="color:#E1E4E8">Math</span><span style="color:#9ECBFF">.</span><span style="color:#B392F0">sin</span><span style="color:#9ECBFF">((</span><span style="color:#E1E4E8">i</span><span style="color:#F97583"> +</span><span style="color:#E1E4E8"> frame</span><span style="color:#9ECBFF">) </span><span style="color:#F97583">/</span><span style="color:#79B8FF"> 5</span><span style="color:#9ECBFF">) </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 10</span><span style="color:#9ECBFF">}px)`</span></span>
|
|
1246
|
+
<span class="line"><span style="color:#E1E4E8"> }}</span></span>
|
|
1247
|
+
<span class="line"><span style="color:#E1E4E8"> ></span></span>
|
|
1248
|
+
<span class="line"><span style="color:#E1E4E8"> {char.props.children}</span></span>
|
|
1249
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1250
|
+
<span class="line"><span style="color:#E1E4E8"> ))}</span></span>
|
|
1251
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1252
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1253
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1254
|
+
<span class="line"></span></code></pre>
|
|
1255
|
+
<p><strong>Tips for animating text paths:</strong></p>
|
|
1256
|
+
<ol>
|
|
1257
|
+
<li><strong>Use <code>progress</code> for smooth rotation</strong> on circles and arcs</li>
|
|
1258
|
+
<li><strong>Map over returned characters</strong> to apply individual animations</li>
|
|
1259
|
+
<li><strong>Combine with animation classes</strong> like <code>enter-fade-in</code>, <code>enter-bounce-in</code>, etc.</li>
|
|
1260
|
+
<li><strong>Stagger character animations</strong> by calculating delays: <code>i * delayMs</code></li>
|
|
1261
|
+
<li><strong>Use <code>frame</code> for continuous effects</strong> like waves or pulsing</li>
|
|
1262
|
+
<li><strong>Preserve the original transform</strong> when adding animations: <code>transform: '${char.props.style.transform} ...'</code></li>
|
|
1263
|
+
</ol>
|
|
1264
|
+
<p><strong>Common path types:</strong></p>
|
|
1265
|
+
<p><strong>Quadratic Bezier</strong> (Q command):</p>
|
|
1266
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#6A737D">// Position: (1-t)²·P0 + 2(1-t)t·P1 + t²·P2</span></span>
|
|
1267
|
+
<span class="line"><span style="color:#F97583">function</span><span style="color:#B392F0"> pointOnQuadraticBezier</span><span style="color:#E1E4E8">(</span><span style="color:#FFAB70">p0</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">p1</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">p2</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">t</span><span style="color:#E1E4E8">) {</span></span>
|
|
1268
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> x</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p0.x </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 2</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p1.x </span><span style="color:#F97583">+</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p2.x;</span></span>
|
|
1269
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> y</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p0.y </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 2</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p1.y </span><span style="color:#F97583">+</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p2.y;</span></span>
|
|
1270
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> { x, y };</span></span>
|
|
1271
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1272
|
+
<span class="line"></span>
|
|
1273
|
+
<span class="line"><span style="color:#6A737D">// Tangent angle</span></span>
|
|
1274
|
+
<span class="line"><span style="color:#F97583">function</span><span style="color:#B392F0"> angleOnQuadraticBezier</span><span style="color:#E1E4E8">(</span><span style="color:#FFAB70">p0</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">p1</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">p2</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">t</span><span style="color:#E1E4E8">) {</span></span>
|
|
1275
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> dx</span><span style="color:#F97583"> =</span><span style="color:#79B8FF"> 2</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> (p1.x </span><span style="color:#F97583">-</span><span style="color:#E1E4E8"> p0.x) </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 2</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> (p2.x </span><span style="color:#F97583">-</span><span style="color:#E1E4E8"> p1.x);</span></span>
|
|
1276
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> dy</span><span style="color:#F97583"> =</span><span style="color:#79B8FF"> 2</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> (p1.y </span><span style="color:#F97583">-</span><span style="color:#E1E4E8"> p0.y) </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 2</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> (p2.y </span><span style="color:#F97583">-</span><span style="color:#E1E4E8"> p1.y);</span></span>
|
|
1277
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> Math.</span><span style="color:#B392F0">atan2</span><span style="color:#E1E4E8">(dy, dx) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">180</span><span style="color:#F97583"> /</span><span style="color:#E1E4E8"> Math.</span><span style="color:#79B8FF">PI</span><span style="color:#E1E4E8">);</span></span>
|
|
1278
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1279
|
+
<span class="line"></span></code></pre>
|
|
1280
|
+
<p><strong>Cubic Bezier</strong> (C command):</p>
|
|
1281
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#6A737D">// Position: (1-t)³·P0 + 3(1-t)²t·P1 + 3(1-t)t²·P2 + t³·P3</span></span>
|
|
1282
|
+
<span class="line"><span style="color:#F97583">function</span><span style="color:#B392F0"> pointOnCubicBezier</span><span style="color:#E1E4E8">(</span><span style="color:#FFAB70">p0</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">p1</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">p2</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">p3</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">t</span><span style="color:#E1E4E8">) {</span></span>
|
|
1283
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> mt</span><span style="color:#F97583"> =</span><span style="color:#79B8FF"> 1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t;</span></span>
|
|
1284
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> mt2</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> mt </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> mt;</span></span>
|
|
1285
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> mt3</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> mt2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> mt;</span></span>
|
|
1286
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> t2</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t;</span></span>
|
|
1287
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> t3</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> t2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t;</span></span>
|
|
1288
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> x</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> mt3 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p0.x </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p1.x </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p2.x </span><span style="color:#F97583">+</span><span style="color:#E1E4E8"> t3 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p3.x;</span></span>
|
|
1289
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> y</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> mt3 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p0.y </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p1.y </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p2.y </span><span style="color:#F97583">+</span><span style="color:#E1E4E8"> t3 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p3.y;</span></span>
|
|
1290
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> { x, y };</span></span>
|
|
1291
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1292
|
+
<span class="line"></span>
|
|
1293
|
+
<span class="line"><span style="color:#6A737D">// Tangent angle</span></span>
|
|
1294
|
+
<span class="line"><span style="color:#F97583">function</span><span style="color:#B392F0"> angleOnCubicBezier</span><span style="color:#E1E4E8">(</span><span style="color:#FFAB70">p0</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">p1</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">p2</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">p3</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">t</span><span style="color:#E1E4E8">) {</span></span>
|
|
1295
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> mt</span><span style="color:#F97583"> =</span><span style="color:#79B8FF"> 1</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8"> t;</span></span>
|
|
1296
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> mt2</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> mt </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> mt;</span></span>
|
|
1297
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> t2</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t;</span></span>
|
|
1298
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> dx</span><span style="color:#F97583"> =</span><span style="color:#F97583"> -</span><span style="color:#79B8FF">3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p0.x </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p1.x </span><span style="color:#F97583">-</span><span style="color:#79B8FF"> 6</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p1.x </span><span style="color:#F97583">-</span><span style="color:#79B8FF"> 3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> t2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p2.x </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 6</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p2.x </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> t2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p3.x;</span></span>
|
|
1299
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> dy</span><span style="color:#F97583"> =</span><span style="color:#F97583"> -</span><span style="color:#79B8FF">3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p0.y </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p1.y </span><span style="color:#F97583">-</span><span style="color:#79B8FF"> 6</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p1.y </span><span style="color:#F97583">-</span><span style="color:#79B8FF"> 3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> t2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p2.y </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 6</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> mt </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> t </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p2.y </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 3</span><span style="color:#F97583"> *</span><span style="color:#E1E4E8"> t2 </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> p3.y;</span></span>
|
|
1300
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> Math.</span><span style="color:#B392F0">atan2</span><span style="color:#E1E4E8">(dy, dx) </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> (</span><span style="color:#79B8FF">180</span><span style="color:#F97583"> /</span><span style="color:#E1E4E8"> Math.</span><span style="color:#79B8FF">PI</span><span style="color:#E1E4E8">);</span></span>
|
|
1301
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1302
|
+
<span class="line"></span></code></pre>
|
|
1303
|
+
<p><strong>Circle</strong>:</p>
|
|
1304
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">function</span><span style="color:#B392F0"> pointOnCircle</span><span style="color:#E1E4E8">(</span><span style="color:#FFAB70">cx</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">cy</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">radius</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">angleRadians</span><span style="color:#E1E4E8">) {</span></span>
|
|
1305
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> {</span></span>
|
|
1306
|
+
<span class="line"><span style="color:#E1E4E8"> x: cx </span><span style="color:#F97583">+</span><span style="color:#E1E4E8"> radius </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> Math.</span><span style="color:#B392F0">cos</span><span style="color:#E1E4E8">(angleRadians),</span></span>
|
|
1307
|
+
<span class="line"><span style="color:#E1E4E8"> y: cy </span><span style="color:#F97583">+</span><span style="color:#E1E4E8"> radius </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> Math.</span><span style="color:#B392F0">sin</span><span style="color:#E1E4E8">(angleRadians)</span></span>
|
|
1308
|
+
<span class="line"><span style="color:#E1E4E8"> };</span></span>
|
|
1309
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1310
|
+
<span class="line"></span>
|
|
1311
|
+
<span class="line"><span style="color:#6A737D">// Usage</span></span>
|
|
1312
|
+
<span class="line"><span style="color:#F97583">const</span><span style="color:#79B8FF"> angleRadians</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> progress </span><span style="color:#F97583">*</span><span style="color:#E1E4E8"> Math.</span><span style="color:#79B8FF">PI</span><span style="color:#F97583"> *</span><span style="color:#79B8FF"> 2</span><span style="color:#E1E4E8">;</span></span>
|
|
1313
|
+
<span class="line"><span style="color:#F97583">const</span><span style="color:#79B8FF"> pos</span><span style="color:#F97583"> =</span><span style="color:#B392F0"> pointOnCircle</span><span style="color:#E1E4E8">(</span><span style="color:#79B8FF">300</span><span style="color:#E1E4E8">, </span><span style="color:#79B8FF">300</span><span style="color:#E1E4E8">, </span><span style="color:#79B8FF">100</span><span style="color:#E1E4E8">, angleRadians);</span></span>
|
|
1314
|
+
<span class="line"><span style="color:#F97583">const</span><span style="color:#79B8FF"> tangentAngle</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> (angleRadians </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 180</span><span style="color:#F97583"> /</span><span style="color:#E1E4E8"> Math.</span><span style="color:#79B8FF">PI</span><span style="color:#E1E4E8">) </span><span style="color:#F97583">+</span><span style="color:#79B8FF"> 90</span><span style="color:#E1E4E8">; </span><span style="color:#6A737D">// Tangent is perpendicular</span></span>
|
|
1315
|
+
<span class="line"></span></code></pre>
|
|
1316
|
+
<p><strong>Tips:</strong></p>
|
|
1317
|
+
<ul>
|
|
1318
|
+
<li>Use <code>progress</code> (0-1) for smooth animation</li>
|
|
1319
|
+
<li>The <code>translate(-50%, -50%)</code> centers the element on the path</li>
|
|
1320
|
+
<li>Combine rotation with the translate: <code>translate(-50%, -50%) rotate(${angle}deg)</code></li>
|
|
1321
|
+
<li>For text following a path, you can animate individual characters at different progress values</li>
|
|
1322
|
+
</ul>
|
|
1323
|
+
<h2 id="svg-stroke-animations">SVG Stroke Animations</h2>
|
|
1324
|
+
<p>Animate SVG path strokes with the <strong>stroke-dash</strong> classes, perfect for drawing or erasing line art, icons, and illustrations.</p>
|
|
1325
|
+
<h3 id="how-it-works">How It Works</h3>
|
|
1326
|
+
<p>SVG stroke animations use <code>strokeDasharray</code> and <code>strokeDashoffset</code> CSS properties to create drawing effects:</p>
|
|
1327
|
+
<ol>
|
|
1328
|
+
<li><strong>Enter animations</strong> - Draw the stroke from start to finish</li>
|
|
1329
|
+
<li><strong>Exit animations</strong> - Erase the stroke from finish to start</li>
|
|
1330
|
+
<li><strong>Loop animations</strong> - Continuously draw and erase</li>
|
|
1331
|
+
</ol>
|
|
1332
|
+
<h3 id="format">Format</h3>
|
|
1333
|
+
<p>All stroke-dash animations require the <strong>path length</strong> in brackets:</p>
|
|
1334
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#E1E4E8">enter</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">stroke</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">dash</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">[length]</span><span style="color:#F97583">/</span><span style="color:#E1E4E8">start</span><span style="color:#F97583">/</span><span style="color:#E1E4E8">duration</span></span>
|
|
1335
|
+
<span class="line"><span style="color:#E1E4E8">exit</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">stroke</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">dash</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">[length]</span><span style="color:#F97583">/</span><span style="color:#E1E4E8">start</span><span style="color:#F97583">/</span><span style="color:#E1E4E8">duration</span></span>
|
|
1336
|
+
<span class="line"><span style="color:#E1E4E8">loop</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">stroke</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">dash</span><span style="color:#F97583">-</span><span style="color:#E1E4E8">[length]</span><span style="color:#F97583">/</span><span style="color:#E1E4E8">duration</span></span>
|
|
1337
|
+
<span class="line"></span></code></pre>
|
|
1338
|
+
<h3 id="basic-examples">Basic Examples</h3>
|
|
1339
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">export</span><span style="color:#F97583"> default</span><span style="color:#F97583"> function</span><span style="color:#B392F0"> SVGAnimation</span><span style="color:#E1E4E8">({ </span><span style="color:#FFAB70">tw</span><span style="color:#E1E4E8"> }) {</span></span>
|
|
1340
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> (</span></span>
|
|
1341
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">svg</span><span style="color:#B392F0"> width</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"400"</span><span style="color:#B392F0"> height</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"200"</span><span style="color:#B392F0"> viewBox</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"0 0 400 200"</span><span style="color:#E1E4E8">></span></span>
|
|
1342
|
+
<span class="line"><span style="color:#E1E4E8"> {</span><span style="color:#6A737D">/* Draw a curve over 1 second */</span><span style="color:#E1E4E8">}</span></span>
|
|
1343
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">path</span></span>
|
|
1344
|
+
<span class="line"><span style="color:#B392F0"> d</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"M10 150 Q 95 10 180 150"</span></span>
|
|
1345
|
+
<span class="line"><span style="color:#B392F0"> stroke</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"black"</span></span>
|
|
1346
|
+
<span class="line"><span style="color:#B392F0"> strokeWidth</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#79B8FF">4</span><span style="color:#E1E4E8">}</span></span>
|
|
1347
|
+
<span class="line"><span style="color:#B392F0"> fill</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"none"</span></span>
|
|
1348
|
+
<span class="line"><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-stroke-dash-[300]/0/1000'</span><span style="color:#E1E4E8">)}</span></span>
|
|
1349
|
+
<span class="line"><span style="color:#E1E4E8"> /></span></span>
|
|
1350
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">svg</span><span style="color:#E1E4E8">></span></span>
|
|
1351
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1352
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1353
|
+
<span class="line"></span></code></pre>
|
|
1354
|
+
<h3 id="enter-animations-drawing">Enter Animations (Drawing)</h3>
|
|
1355
|
+
<p>Draw strokes from 0% to 100%:</p>
|
|
1356
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#6A737D">// Draw a 300px path over 1 second</span></span>
|
|
1357
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-stroke-dash-[300]/0/1000'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1358
|
+
<span class="line"></span>
|
|
1359
|
+
<span class="line"><span style="color:#6A737D">// Draw with spring easing</span></span>
|
|
1360
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'ease-spring enter-stroke-dash-[500]/0/1500'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1361
|
+
<span class="line"></span>
|
|
1362
|
+
<span class="line"><span style="color:#6A737D">// Stagger multiple paths</span></span>
|
|
1363
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-stroke-dash-[200]/0/600'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1364
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-stroke-dash-[200]/200/600'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1365
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-stroke-dash-[200]/400/600'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1366
|
+
<span class="line"></span></code></pre>
|
|
1367
|
+
<h3 id="exit-animations-erasing">Exit Animations (Erasing)</h3>
|
|
1368
|
+
<p>Erase strokes from 100% to 0%:</p>
|
|
1369
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#6A737D">// Erase starting at 2000ms, lasting 500ms</span></span>
|
|
1370
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'exit-stroke-dash-[300]/2000/500'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1371
|
+
<span class="line"></span>
|
|
1372
|
+
<span class="line"><span style="color:#6A737D">// Draw then erase the same path</span></span>
|
|
1373
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-stroke-dash-[400]/0/800 exit-stroke-dash-[400]/2200/800'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1374
|
+
<span class="line"></span></code></pre>
|
|
1375
|
+
<h3 id="loop-animations-1">Loop Animations</h3>
|
|
1376
|
+
<p>Continuously draw and erase:</p>
|
|
1377
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#6A737D">// Loop every 2 seconds (draws in first half, erases in second half)</span></span>
|
|
1378
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'loop-stroke-dash-[300]/2000'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1379
|
+
<span class="line"></span>
|
|
1380
|
+
<span class="line"><span style="color:#6A737D">// Faster loop</span></span>
|
|
1381
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'loop-stroke-dash-[200]/1000'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1382
|
+
<span class="line"></span></code></pre>
|
|
1383
|
+
<h3 id="getting-path-length">Getting Path Length</h3>
|
|
1384
|
+
<p>To find the path length for your SVG:</p>
|
|
1385
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#6A737D">// In browser console or component:</span></span>
|
|
1386
|
+
<span class="line"><span style="color:#F97583">const</span><span style="color:#79B8FF"> path</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> document.</span><span style="color:#B392F0">querySelector</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'path'</span><span style="color:#E1E4E8">);</span></span>
|
|
1387
|
+
<span class="line"><span style="color:#F97583">const</span><span style="color:#79B8FF"> length</span><span style="color:#F97583"> =</span><span style="color:#E1E4E8"> path.</span><span style="color:#B392F0">getTotalLength</span><span style="color:#E1E4E8">();</span></span>
|
|
1388
|
+
<span class="line"><span style="color:#E1E4E8">console.</span><span style="color:#B392F0">log</span><span style="color:#E1E4E8">(length); </span><span style="color:#6A737D">// e.g., 347.89</span></span>
|
|
1389
|
+
<span class="line"></span></code></pre>
|
|
1390
|
+
<p>Then use that value:</p>
|
|
1391
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-stroke-dash-[347.89]/0/1000'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1392
|
+
<span class="line"></span></code></pre>
|
|
1393
|
+
<h3 id="complete-example">Complete Example</h3>
|
|
1394
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">export</span><span style="color:#F97583"> default</span><span style="color:#F97583"> function</span><span style="color:#B392F0"> DrawingEffect</span><span style="color:#E1E4E8">({ </span><span style="color:#FFAB70">tw</span><span style="color:#E1E4E8"> }) {</span></span>
|
|
1395
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> (</span></span>
|
|
1396
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'flex items-center justify-center w-full h-full bg-gray-900'</span><span style="color:#E1E4E8">)}></span></span>
|
|
1397
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">svg</span><span style="color:#B392F0"> width</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"600"</span><span style="color:#B392F0"> height</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"400"</span><span style="color:#B392F0"> viewBox</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"0 0 600 400"</span><span style="color:#E1E4E8">></span></span>
|
|
1398
|
+
<span class="line"><span style="color:#E1E4E8"> {</span><span style="color:#6A737D">/* Checkmark icon drawn in sequence */</span><span style="color:#E1E4E8">}</span></span>
|
|
1399
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">path</span></span>
|
|
1400
|
+
<span class="line"><span style="color:#B392F0"> d</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"M100 200 L 200 300 L 400 100"</span></span>
|
|
1401
|
+
<span class="line"><span style="color:#B392F0"> stroke</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"#10b981"</span></span>
|
|
1402
|
+
<span class="line"><span style="color:#B392F0"> strokeWidth</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#79B8FF">8</span><span style="color:#E1E4E8">}</span></span>
|
|
1403
|
+
<span class="line"><span style="color:#B392F0"> fill</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"none"</span></span>
|
|
1404
|
+
<span class="line"><span style="color:#B392F0"> strokeLinecap</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"round"</span></span>
|
|
1405
|
+
<span class="line"><span style="color:#B392F0"> strokeLinejoin</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"round"</span></span>
|
|
1406
|
+
<span class="line"><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'ease-out enter-stroke-dash-[600]/0/1200'</span><span style="color:#E1E4E8">)}</span></span>
|
|
1407
|
+
<span class="line"><span style="color:#E1E4E8"> /></span></span>
|
|
1408
|
+
<span class="line"></span>
|
|
1409
|
+
<span class="line"><span style="color:#E1E4E8"> {</span><span style="color:#6A737D">/* Circle drawn after checkmark */</span><span style="color:#E1E4E8">}</span></span>
|
|
1410
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">circle</span></span>
|
|
1411
|
+
<span class="line"><span style="color:#B392F0"> cx</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"250"</span></span>
|
|
1412
|
+
<span class="line"><span style="color:#B392F0"> cy</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"200"</span></span>
|
|
1413
|
+
<span class="line"><span style="color:#B392F0"> r</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"150"</span></span>
|
|
1414
|
+
<span class="line"><span style="color:#B392F0"> stroke</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"#10b981"</span></span>
|
|
1415
|
+
<span class="line"><span style="color:#B392F0"> strokeWidth</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#79B8FF">6</span><span style="color:#E1E4E8">}</span></span>
|
|
1416
|
+
<span class="line"><span style="color:#B392F0"> fill</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"none"</span></span>
|
|
1417
|
+
<span class="line"><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'ease-out enter-stroke-dash-[942]/1000/1000'</span><span style="color:#E1E4E8">)}</span></span>
|
|
1418
|
+
<span class="line"><span style="color:#E1E4E8"> /></span></span>
|
|
1419
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">svg</span><span style="color:#E1E4E8">></span></span>
|
|
1420
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1421
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1422
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1423
|
+
<span class="line"></span></code></pre>
|
|
1424
|
+
<h3 id="combining-with-other-animations">Combining with Other Animations</h3>
|
|
1425
|
+
<p>Stroke animations work alongside other animation classes:</p>
|
|
1426
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#6A737D">// Fade in while drawing</span></span>
|
|
1427
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">path</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-stroke-dash-[300]/0/1000 enter-fade-in/0/1000'</span><span style="color:#E1E4E8">)} /></span></span>
|
|
1428
|
+
<span class="line"></span>
|
|
1429
|
+
<span class="line"><span style="color:#6A737D">// Draw with pulsing color</span></span>
|
|
1430
|
+
<span class="line"><span style="color:#E1E4E8"><</span><span style="color:#85E89D">svg</span><span style="color:#E1E4E8">></span></span>
|
|
1431
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">path</span></span>
|
|
1432
|
+
<span class="line"><span style="color:#B392F0"> stroke</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"url(#gradient)"</span></span>
|
|
1433
|
+
<span class="line"><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'enter-stroke-dash-[500]/0/1500'</span><span style="color:#E1E4E8">)}</span></span>
|
|
1434
|
+
<span class="line"><span style="color:#E1E4E8"> /></span></span>
|
|
1435
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">defs</span><span style="color:#E1E4E8">></span></span>
|
|
1436
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#79B8FF">linearGradient</span><span style="color:#B392F0"> id</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"gradient"</span><span style="color:#E1E4E8">></span></span>
|
|
1437
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">stop</span><span style="color:#B392F0"> offset</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"0%"</span><span style="color:#B392F0"> stopColor</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"#8b5cf6"</span><span style="color:#E1E4E8"> /></span></span>
|
|
1438
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">stop</span><span style="color:#B392F0"> offset</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"100%"</span><span style="color:#B392F0"> stopColor</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"#ec4899"</span><span style="color:#E1E4E8"> /></span></span>
|
|
1439
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#79B8FF">linearGradient</span><span style="color:#E1E4E8">></span></span>
|
|
1440
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">defs</span><span style="color:#E1E4E8">></span></span>
|
|
1441
|
+
<span class="line"><span style="color:#E1E4E8"></</span><span style="color:#85E89D">svg</span><span style="color:#E1E4E8">></span></span>
|
|
1442
|
+
<span class="line"></span></code></pre>
|
|
1443
|
+
<h3 id="animated-dashed-strokes-marching-ants">Animated Dashed Strokes (Marching Ants)</h3>
|
|
1444
|
+
<p>For <strong>marching ants</strong> or <strong>animated dashed patterns</strong>, use <code>frame</code> or <code>progress</code> directly instead of animation classes:</p>
|
|
1445
|
+
<pre class="astro-code github-dark" style="background-color:#24292e;color:#e1e4e8;overflow-x:auto" tabindex="0" data-language="tsx"><code><span class="line"><span style="color:#F97583">export</span><span style="color:#F97583"> default</span><span style="color:#F97583"> function</span><span style="color:#B392F0"> MarchingAnts</span><span style="color:#E1E4E8">({ </span><span style="color:#FFAB70">tw</span><span style="color:#E1E4E8">, </span><span style="color:#FFAB70">frame</span><span style="color:#E1E4E8"> }) {</span></span>
|
|
1446
|
+
<span class="line"><span style="color:#6A737D"> // Calculate animated offset (loops every 30 frames)</span></span>
|
|
1447
|
+
<span class="line"><span style="color:#F97583"> const</span><span style="color:#79B8FF"> dashOffset</span><span style="color:#F97583"> =</span><span style="color:#F97583"> -</span><span style="color:#E1E4E8">(frame </span><span style="color:#F97583">%</span><span style="color:#79B8FF"> 30</span><span style="color:#E1E4E8">) </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 2</span><span style="color:#E1E4E8">;</span></span>
|
|
1448
|
+
<span class="line"></span>
|
|
1449
|
+
<span class="line"><span style="color:#F97583"> return</span><span style="color:#E1E4E8"> (</span></span>
|
|
1450
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">div</span><span style="color:#B392F0"> style</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#B392F0">tw</span><span style="color:#E1E4E8">(</span><span style="color:#9ECBFF">'flex items-center justify-center w-full h-full bg-gray-900'</span><span style="color:#E1E4E8">)}></span></span>
|
|
1451
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">svg</span><span style="color:#B392F0"> width</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"600"</span><span style="color:#B392F0"> height</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"400"</span><span style="color:#B392F0"> viewBox</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"0 0 600 400"</span><span style="color:#E1E4E8">></span></span>
|
|
1452
|
+
<span class="line"><span style="color:#E1E4E8"> {</span><span style="color:#6A737D">/* Marching ants border */</span><span style="color:#E1E4E8">}</span></span>
|
|
1453
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">rect</span></span>
|
|
1454
|
+
<span class="line"><span style="color:#B392F0"> x</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"50"</span></span>
|
|
1455
|
+
<span class="line"><span style="color:#B392F0"> y</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"50"</span></span>
|
|
1456
|
+
<span class="line"><span style="color:#B392F0"> width</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"500"</span></span>
|
|
1457
|
+
<span class="line"><span style="color:#B392F0"> height</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"300"</span></span>
|
|
1458
|
+
<span class="line"><span style="color:#B392F0"> fill</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"none"</span></span>
|
|
1459
|
+
<span class="line"><span style="color:#B392F0"> stroke</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"#3b82f6"</span></span>
|
|
1460
|
+
<span class="line"><span style="color:#B392F0"> strokeWidth</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#79B8FF">3</span><span style="color:#E1E4E8">}</span></span>
|
|
1461
|
+
<span class="line"><span style="color:#B392F0"> strokeDasharray</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"10 5"</span></span>
|
|
1462
|
+
<span class="line"><span style="color:#B392F0"> strokeDashoffset</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{dashOffset}</span></span>
|
|
1463
|
+
<span class="line"><span style="color:#E1E4E8"> /></span></span>
|
|
1464
|
+
<span class="line"></span>
|
|
1465
|
+
<span class="line"><span style="color:#E1E4E8"> {</span><span style="color:#6A737D">/* Animated circle with different speed */</span><span style="color:#E1E4E8">}</span></span>
|
|
1466
|
+
<span class="line"><span style="color:#E1E4E8"> <</span><span style="color:#85E89D">circle</span></span>
|
|
1467
|
+
<span class="line"><span style="color:#B392F0"> cx</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"300"</span></span>
|
|
1468
|
+
<span class="line"><span style="color:#B392F0"> cy</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"200"</span></span>
|
|
1469
|
+
<span class="line"><span style="color:#B392F0"> r</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"80"</span></span>
|
|
1470
|
+
<span class="line"><span style="color:#B392F0"> fill</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"none"</span></span>
|
|
1471
|
+
<span class="line"><span style="color:#B392F0"> stroke</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"#10b981"</span></span>
|
|
1472
|
+
<span class="line"><span style="color:#B392F0"> strokeWidth</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{</span><span style="color:#79B8FF">4</span><span style="color:#E1E4E8">}</span></span>
|
|
1473
|
+
<span class="line"><span style="color:#B392F0"> strokeDasharray</span><span style="color:#F97583">=</span><span style="color:#9ECBFF">"15 8"</span></span>
|
|
1474
|
+
<span class="line"><span style="color:#B392F0"> strokeDashoffset</span><span style="color:#F97583">=</span><span style="color:#E1E4E8">{dashOffset </span><span style="color:#F97583">*</span><span style="color:#79B8FF"> 1.5</span><span style="color:#E1E4E8">}</span></span>
|
|
1475
|
+
<span class="line"><span style="color:#E1E4E8"> /></span></span>
|
|
1476
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">svg</span><span style="color:#E1E4E8">></span></span>
|
|
1477
|
+
<span class="line"><span style="color:#E1E4E8"> </</span><span style="color:#85E89D">div</span><span style="color:#E1E4E8">></span></span>
|
|
1478
|
+
<span class="line"><span style="color:#E1E4E8"> );</span></span>
|
|
1479
|
+
<span class="line"><span style="color:#E1E4E8">}</span></span>
|
|
1480
|
+
<span class="line"></span></code></pre>
|
|
1481
|
+
<p><strong>Tips:</strong></p>
|
|
1482
|
+
<ul>
|
|
1483
|
+
<li><code>strokeDasharray="10 5"</code> - 10px dash, 5px gap</li>
|
|
1484
|
+
<li><code>strokeDashoffset={dashOffset}</code> - animates the pattern position</li>
|
|
1485
|
+
<li>Negative offset moves forward, positive moves backward</li>
|
|
1486
|
+
<li>Different speeds: multiply by different values (e.g., <code>dashOffset * 2</code>)</li>
|
|
1487
|
+
</ul>
|
|
1488
|
+
<p>This technique is different from <code>stroke-dash</code> classes:</p>
|
|
1489
|
+
<ul>
|
|
1490
|
+
<li><strong><code>stroke-dash</code> classes</strong> - Draw/erase the stroke (reveal animation)</li>
|
|
1491
|
+
<li><strong>Marching ants</strong> - Move a dashed pattern along the stroke</li>
|
|
1492
|
+
</ul>
|
|
867
1493
|
<h2 id="performance-tips">Performance Tips</h2>
|
|
868
1494
|
<ol>
|
|
869
1495
|
<li><strong>Use Tailwind classes</strong> when possible - they’re optimized for the renderer</li>
|