1<!DOCTYPE html><html lang="en"> <head><meta name="sentry-route-name" content="%2Fproblem"/><meta charset="utf-8"><!-- Persona attribute BEFORE first paint (no-flicker rule, same pattern 2 as dark-mode gates): the header CTA's maker label is CSS keyed off 3 html[data-persona], so the right label renders on the very first 4 frame instead of swapping at DOMContentLoaded. Keys owned by 5 dev-entry.js (ritual_dev_entry / ritual_maker_entry). -->
5<script> 6 try { 7 var p = 8 localStorage.getItem("ritual_maker_entry") === "1" 9 ? "maker" 10 : localStorage.getItem("ritual_dev_entry") === "1" 11 ? "developer" 12 : ""; 13 if (p) document.documentElement.setAttribute("data-persona", p); 14 } catch (e) { 15 /* storage blocked: default CTA renders */ 16 } 17 </script>
17<!-- Same no-flicker rule, for the verified developer coming back from the 18 email link. The CLI is a client:only island, so the marketing page is 19 what paints while React loads, and they watched the page they had just 20 left reassemble itself before the console they came back for arrived. 21 Stamping html here covers that gap from the first frame; CliHeroPlugin 22 mounts straight into fullscreen underneath it and clears the flag. 23 24 The style is INLINE rather than in cli.css: that sheet ships with the 25 island's chunk, which by definition has not loaded yet at the moment 26 this needs to be painted. 27 28 Scoped to the developer pages, since ?return=1 is a common enough 29 param to belong to something else elsewhere. -->
29<script> 30 try { 31 if ( 32 location.pathname.indexOf("/product/developer") === 0 && 33 new URLSearchParams(location.search).get("return") === "1" 34 ) { 35 document.documentElement.setAttribute("data-cli-return", ""); 36 /* Never strand them on a dark screen: if the island fails to mount 37 (JS blocked, chunk 404), the page comes back on its own. Longer 38 than a slow mount, shorter than a visitor's patience. */ 39 setTimeout(function () { 40 document.documentElement.removeAttribute("data-cli-return"); 41 }, 8000); 42 } 43 } catch (e) { 44 /* no URL API / blocked: the old flash is the fallback, not a failure */ 45 } 46 </script>
46<style> 47 /* #1B1A2A is --cli-bg, hardcoded for the same reason the style is inline: 48 the sheet that defines the token has not arrived yet. */ 49 html[data-cli-return] { 50 background: #1b1a2a; 51 } 52 html[data-cli-return]::before { 53 content: ""; 54 position: fixed; 55 inset: 0; 56 background: #1b1a2a; 57 /* Under the takeover (100) so the console draws over it, above 58 everything else so the page underneath never shows. */ 59 z-index: 99; 60 /* A full-screen overlay that ate clicks would be its own bug. */ 61 pointer-events: none; 62 } 63 html[data-cli-return] body { 64 overflow: hidden; 65 } 66 </style><link rel="icon" type="image/png" href="/favicon.png"><link rel="apple-touch-icon" href="/favicon.png"><!-- interactive-widget=resizes-content: the on-screen keyboard SHRINKS the 67 layout viewport, so the prelogin CLI's fullscreen input + action button 68 sit above the keyboard instead of behind it on mobile. Harmless on 69 pages without the CLI (only changes keyboard-resize behavior). --><meta name="viewport" content="width=device-width, initial-scale=1, interactive-widget=resizes-content"><meta name="generator" content="Astro v6.4.8"><meta name="description" content="Why AI tools lose context, what it costs, and how Ritual fixes it."><link rel="canonical" href="https://ritual.work/problem/"><!-- Open Graph --><meta property="og:type" content="website"><meta property="og:title" content="The Problem â Ritual"><meta property="og:description" content="Why AI tools lose context, what it costs, and how Ritual fixes it."><meta property="og:url" content="https://ritual.work/problem/"><meta property="og:image" content="https://ritual.work/hero-graph.png"><meta property="og:site_name" content="Ritual"><!-- Twitter --><meta name="twitter:card" content="summary_large_image"><meta name="twitter:title" content="The Problem â Ritual"><meta name="twitter:description" content="Why AI tools lose context, what it costs, and how Ritual fixes it."><meta name="twitter:image" content="https://ritual.work/hero-graph.png"><link rel="preconnect" href="https://fonts.googleapis.com"><link rel="preconnect" href="https://fonts.gstatic.com" crossorigin><link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&display=swap"><title>The Problem â Ritual</title>
69<script>(function(){const posthogKey = "phc_uDVTitoexBzZHYAc46FpaX2uRMhA8EWmZFNPfEDDykAM"; 70const posthogHost = "https://us.i.posthog.com"; 71const releaseSha = "0db980f"; 72 73 !function(t,e){var o,n,p,r;e.__SV||(window.posthog=e,e._i=[],e.init=function(i,s,a){function g(t,e){var o=e.split(".");2==o.length&&(t=t[o[0]],e=o[1]),t[e]=function(){t.push([e].concat(Array.prototype.slice.call(arguments,0)))}}(p=t.createElement("script")).type="text/javascript",p.async=!0,p.src=s.api_host+"/static/array.js",(r=t.getElementsByTagName("script")[0]).parentNode.insertBefore(p,r);var u=e;for(void 0!==a?u=e[a]=[]:a="posthog",u.people=u.people||[],u.toString=function(t){var e="posthog";return"posthog"!==a&&(e+="."+a),t||(e+=" (stub)"),e},u.people.toString=function(){return u.toString(1)+".people (stub)"},o="capture identify alias people.set people.set_once set_config register register_once register_for_session unregister unregister_for_session opt_out_capturing has_opted_out_capturing opt_in_capturing reset isFeatureEnabled onFeatureFlags getFeatureFlag getFeatureFlagPayload reloadFeatureFlags group updateEarlyAccessFeatureEnrollment getEarlyAccessFeatures getActiveMatchingSurveys getSurveys getNextSurveyStep onSessionId".split(" "),n=0;n<o.length;n++)g(u,o[n]);e._i.push([i,s,a])},e.__SV=1)}(document,window.posthog||[]); 74 75 // Don't send analytics from local dev hosts â keeps localhost test 76 // events (and their localhost $current_url / fake UTMs) out of the 77 // production PostHog project. The stub still exists, so capture/register 78 // calls below are harmless no-ops and the CTA-routing logic still runs. 79 var phHost = location.hostname; 80 var phIsDevHost = 81 phHost === "localhost" || 82 phHost === "127.0.0.1" || 83 phHost === "0.0.0.0" || 84 phHost === "::1" || 85 phHost === "[::1]" || 86 phHost.slice(-6) === ".local"; 87 if (!phIsDevHost) { 88 // Scope replay to the developer funnel â watch where users stall on 89 // /product/developer + the quickstart, without recording the whole site. 90 var phPath = location.pathname; 91 var phFunnelPage = 92 phPath.indexOf('/product/developer') === 0 || 93 phPath.indexOf('/product/makers') === 0 || 94 phPath.indexOf('/docs/quickstart') === 0; 95 96 posthog.init(posthogKey, { 97 api_host: posthogHost, 98 person_profiles: 'identified_only', 99 // Session replay stays OFF by default; `loaded` below turns it on for 100 // the funnel pages only. Inputs are masked, and anything tagged 101 // .ph-no-capture (e.g. the minted token) is masked in the replay too. 102 // (Also needs Session Replay enabled in the PostHog project settings.) 103 disable_session_recording: true, 104 session_recording: { maskAllInputs: true, maskTextSelector: '.ph-no-capture' }, 105 // MUST start replay from `loaded`, NOT synchronously after init(). 106 // 107 // This call used to sit right below init() behind a 108 // `posthog.startSessionRecording && â¦` guard, and it never once ran. 109 // At that moment window.posthog is still the SNIPPET STUB, which only 110 // proxies a fixed method list â capture, identify, register, 111 // onFeatureFlags and friends. `startSessionRecording` is NOT on that 112 // list, so the guard evaluated falsy and skipped silently, forever. 113 // Verified in-browser 2026-08-06 against production: at snippet time 114 // `!!posthog.startSessionRecording` is false; after the SDK loads it is 115 // a function, and `sessionRecording.status` reads "disabled" because 116 // nothing ever started it. $recording_status was "disabled" on all 117 // 1,782 developer-page events in the preceding two days. 118 // 119 // `loaded` fires with the REAL SDK, so the method exists. Same class of 120 // bug as the arm-resolution race this PR fixes: code assuming PostHog 121 // is ready when only its stub is. 122 loaded: function (ph) { 123 if (!phFunnelPage) return; 124 try { ph.startSessionRecording(); } catch (_) {} 125 }, 126 }); 127 // Deploy provenance on every client event (see frontmatter comment). 128 // `register` IS on the stub's proxy list, so this one is safe here. 129 if (releaseSha) { 130 posthog.register({ release_sha: releaseSha }); 131 } 132 } 133 134 // CTA click delegation: any element (or ancestor up to 6 levels)
135 // with data-ph-cta becomes a tracked CTA. We also pick up the 136 // resolved destination so "Get started" â /ritual-mcp/docs#install 137 // tells us where they went without needing a separate prop. 138 (function () { 139 function readCta(el) { 140 for (var i = 0; i < 6 && el && el !== document; i++) { 141 if (el.dataset && el.dataset.phCta) { 142 return { 143 cta: el.dataset.phCta, 144 location: el.dataset.phCtaLocation || null, 145 href: el.getAttribute && (el.getAttribute("href") || el.getAttribute("formaction")) || null, 146 text: (el.innerText || el.textContent || "").trim().slice(0, 80) || null, 147 }; 148 } 149 el = el.parentElement; 150 } 151 return null; 152 } 153 document.addEventListener("click", function (ev) { 154 var info = readCta(ev.target); 155 if (!info) return; 156 try { 157 window.posthog && window.posthog.capture && window.posthog.capture("cta_clicked", info); 158 } catch (_) {} 159 }, { capture: true }); 160 // Form submit tracking: tag the <form> with data-ph-cta to 161 // capture the actual submission (more meaningful than a click 162 // for the waitlist form). 163 document.addEventListener("submit", function (ev) { 164 var info = readCta(ev.target); 165 if (!info) return; 166 try { 167 window.posthog && window.posthog.capture && window.posthog.capture("cta_submitted", info); 168 } catch (_) {} 169 }, { capture: true }); 170 })(); 171 // Developer-entrant detection + CTA routing lives in the bundled 172 // module src/scripts/dev-entry.js (mounted via DevEntryRouting.astro), 173 // which can import the shared Keycloak/connect-flow constants. Kept 174 // out of this inline snippet so we don't duplicate auth config here. 175 })();</script>
175<script type="module" src="/_astro/DevEntryRouting.astro_astro_type_script_index_0_lang.BMf2VZsx.js"></script>
175<link rel="stylesheet" href="/_astro/PostHogScript.CAMvvd4h.css"><style>.reveal[data-astro-cid-foqmza75],.reveal-step[data-astro-cid-foqmza75]{opacity:0;transform:translateY(16px);transition:opacity .7s cubic-bezier(.22,1,.36,1),transform .7s cubic-bezier(.22,1,.36,1)}.reveal[data-astro-cid-foqmza75].is-visible,.reveal-step[data-astro-cid-foqmza75].is-visible{opacity:1;transform:translateY(0)}.reveal-step[data-astro-cid-foqmza75].is-visible{transition-delay:var(--step-delay, 0ms)}.chain-slice[data-astro-cid-foqmza75]{opacity:0;transform:translateY(10px) scale(.94);transition:opacity .7s cubic-bezier(.22,1,.36,1),transform .7s cubic-bezier(.22,1,.36,1);transform-origin:center center;pointer-events:none}.chain-row[data-astro-cid-foqmza75].is-visible .chain-slice[data-astro-cid-foqmza75]{opacity:1;transform:translateY(0) scale(1)}.chain-row[data-astro-cid-foqmza75].is-visible .chain-slice-1[data-astro-cid-foqmza75]{transition-delay:.1s}.chain-row[data-astro-cid-foqmza75].is-visible .chain-slice-2[data-astro-cid-foqmza75]{transition-delay:.24s}.chain-row[data-astro-cid-foqmza75].is-visible .chain-slice-3[data-astro-cid-foqmza75]{transition-delay:.38s}.chain-row[data-astro-cid-foqmza75].is-visible .chain-slice-4[data-astro-cid-foqmza75]{transition-delay:.52s}.chain-row[data-astro-cid-foqmza75].is-visible .chain-slice-5[data-astro-cid-foqmza75]{transition-delay:.66s}.problem-card[data-astro-cid-foqmza75]{border:2px solid transparent}.problem-card[data-astro-cid-foqmza75] .card-icon-wrap[data-astro-cid-foqmza75]{background-color:var(--color-accent-100);transition:background-color .3s ease,transform .3s ease}.problem-card[data-astro-cid-foqmza75] .card-icon-wrap[data-astro-cid-foqmza75] img[data-astro-cid-foqmza75]{transition:transform .3s ease,opacity .3s ease}.problem-card[data-astro-cid-foqmza75].is-focused{border-color:var(--color-accent-500)}.problem-card[data-astro-cid-foqmza75].is-focused .card-icon-wrap[data-astro-cid-foqmza75]{animation:icon-pulse 2.2s cubic-bezier(.4,0,.6,1) .22s infinite}.problem-card[data-astro-cid-foqmza75].is-focused .card-icon-wrap[data-astro-cid-foqmza75] img[data-astro-cid-foqmza75]{animation:icon-fade 2.2s ease-in-out .22s infinite}@keyframes icon-pulse{0%,to{transform:scale(1);background-color:var(--color-accent-100)}50%{transform:scale(1.06);background-color:var(--color-accent-50)}}@keyframes icon-fade{0%,to{opacity:1;transform:scale(1)}50%{opacity:.7;transform:scale(.96)}}@media(prefers-reduced-motion:reduce){.reveal[data-astro-cid-foqmza75],.reveal-step[data-astro-cid-foqmza75],.chain-slice[data-astro-cid-foqmza75],.problem-card[data-astro-cid-foqmza75],.problem-card[data-astro-cid-foqmza75].is-focused,.problem-card[data-astro-cid-foqmza75] .card-icon-wrap[data-astro-cid-foqmza75],.problem-card[data-astro-cid-foqmza75] .card-icon-wrap[data-astro-cid-foqmza75] img[data-astro-cid-foqmza75]{animation:none!important;transition:none!important;opacity:1!important;transform:none!important;stroke-dashoffset:0!important}} 176.cta-label-maker,html[data-persona=maker] .cta-label-default{display:none}html[data-persona=maker] .cta-label-maker{display:inline} 177</style>
177<script type="module" src="/_astro/page.Bm8nvw0p.js"></script>
177</head> <body class="min-h-screen flex flex-col"> <header class="sticky top-0 z-50 bg-canvas/85 backdrop-blur border-b border-ink-100"> <div class="mx-auto max-w-7xl px-6 h-20 flex items-center justify-between"> <a href="/" class="flex items-center gap-2" aria-label="Ritual home"> <img src="/ritual-logo.svg" alt="Ritual" class="h-9 w-auto"> </a> <!-- Desktop nav --> <nav class="hidden md:flex items-center gap-2 text-base text-ink-700"> <a href="/" class="px-4 py-2.5 rounded-md hover:text-ink-900 transition-colors"> Home </a><a href="/problem" class="px-4 py-2.5 rounded-md hover:text-ink-900 transition-colors"> Problem </a><div class="relative group"> <button type="button" class="inline-flex items-center gap-1 px-4 py-2.5 rounded-md hover:text-ink-900 transition-colors" aria-haspopup="true" aria-expanded="false"> Product <svg viewBox="0 0 20 20" fill="currentColor" aria-hidden="true" class="h-4 w-4 transition-transform group-hover:rotate-180"> <path fill-rule="evenodd" d="M5.23 7.21a.75.75 0 011.06.02L10 11.06l3.71-3.83a.75.75 0 111.08 1.04l-4.25 4.39a.75.75 0 01-1.08 0L5.21 8.27a.75.75 0 01.02-1.06z" clip-rule="evenodd"></path> </svg> </button> <div class="invisible opacity-0 translate-y-1 group-hover:visible group-hover:opacity-100 group-hover:translate-y-0 group-focus-within:visible group-focus-within:opacity-100 group-focus-within:translate-y-0 transition-all absolute left-0 top-full pt-2 w-72"> <div class="rounded-xl bg-white shadow-lg ring-1 ring-ink-100 p-2"> <a href="/product/builder" class="block px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Product</div> <div class="text-xs text-ink-500 mt-0.5">Clear and compelling PRDs</div> </a><a href="/product/developer" class="block px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Developer</div> <div class="text-xs text-ink-500 mt-0.5">Agentic coding without the drift</div> </a><a href="/product/makers" class="block px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Prototyping</div> <div class="text-xs text-ink-500 mt-0.5">Turn ideas into better builds</div> </a> </div> </div> </div><div class="relative group"> <button type="button" class="inline-flex items-center gap-1 px-4 py-2.5 rounded-md hover:text-ink-900 transition-colors" aria-haspopup="true" aria-expanded="false"> Use Cases <svg viewBox="0 0 20 20" fill="currentColor" aria-hidden="true" class="h-4 w-4 transition-transform group-hover:rotate-180"> <path fill-rule="evenodd" d="M5.23 7.21a.75.75 0 011.06.02L10 11.06l3.71-3.83a.75.75 0 111.08 1.04l-4.25 4.39a.75.75 0 01-1.08 0L5.21 8.27a.75.75 0 01.02-1.06z" clip-rule="evenodd"></path> </svg> </button> <div class="invisible opacity-0 translate-y-1 group-hover:visible group-hover:opacity-100 group-hover:translate-y-0 group-focus-within:visible group-focus-within:opacity-100 group-focus-within:translate-y-0 transition-all absolute left-0 top-full pt-2 w-72"> <div class="rounded-xl bg-white shadow-lg ring-1 ring-ink-100 p-2"> <a href="/use-cases/agentic-coding" class="block px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Agentic Coding</div> <div class="text-xs text-ink-500 mt-0.5">Context & constraints for coding agents</div> </a><a href="/use-cases/requirements" class="block px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Product Requirements</div> <div class="text-xs text-ink-500 mt-0.5">Build-ready specs without the rework</div> </a><a href="/use-cases/prototyping" class="block px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Prototyping</div> <div class="text-xs text-ink-500 mt-0.5">Turn ideas into better builds</div> </a><a href="/use-cases/strategy" class="block px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Strategy & Transformation</div> <div class="text-xs text-ink-500 mt-0.5">Turn initiatives into actionable explorations</div> </a> </div> </div> </div><a href="/about" class="px-4 py-2.5 rounded-md hover:text-ink-900 transition-colors"> About </a><a href="/technology" class="px-4 py-2.5 rounded-md hover:text-ink-900 transition-colors"> Technology </a> </nav> <div class="flex items-center gap-2"> <a href="https://app.ritual.work" target="_blank" rel="noopener noreferrer" data-ph-cta="get_started" data-ph-cta-location="header" class="hidden sm:inline-flex items-center rounded-full bg-ink-900 text-white text-base px-5 py-2.5 hover:bg-ink-700 transition-colors"> <span class="cta-label-default">Get started for free</span><span class="cta-label-maker">
177Build Now</span> </a> <!-- Mobile menu toggle --> <button type="button" class="md:hidden inline-flex items-center justify-center h-11 w-11 rounded-md text-ink-700 hover:bg-ink-50 transition-colors" aria-label="Toggle menu" aria-expanded="false" aria-controls="mobile-menu" data-mobile-toggle> <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="h-5 w-5 [data-open=true]_&]:hidden" aria-hidden="true"> <line x1="3" y1="6" x2="21" y2="6"></line> <line x1="3" y1="12" x2="21" y2="12"></line> <line x1="3" y1="18" x2="21" y2="18"></line> </svg> </button> </div> </div> <!-- Mobile menu panel --> <div id="mobile-menu" class="md:hidden hidden border-t border-ink-100 bg-canvas" data-mobile-panel> <nav class="mx-auto max-w-7xl px-6 py-4 flex flex-col gap-1.5 text-sm"> <a href="/" class="flex items-center min-h-[44px] px-3 py-2.5 rounded-lg text-ink-900 hover:bg-ink-50 transition-colors"> Home </a><a href="/problem" class="flex items-center min-h-[44px] px-3 py-2.5 rounded-lg text-ink-900 hover:bg-ink-50 transition-colors"> Problem </a><div class="py-1"> <div class="px-3 py-2 text-xs font-semibold uppercase tracking-wider text-ink-400"> Product </div> <a href="/product/builder" class="flex flex-col justify-center min-h-[44px] px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Product</div> <div class="text-xs text-ink-500 mt-0.5">Clear and compelling PRDs</div> </a><a href="/product/developer" class="flex flex-col justify-center min-h-[44px] px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Developer</div> <div class="text-xs text-ink-500 mt-0.5">Agentic coding without the drift</div> </a><a href="/product/makers" class="flex flex-col justify-center min-h-[44px] px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Prototyping</div> <div class="text-xs text-ink-500 mt-0.5">Turn ideas into better builds</div> </a> </div><div class="py-1"> <div class="px-3 py-2 text-xs font-semibold uppercase tracking-wider text-ink-400"> Use Cases </div> <a href="/use-cases/agentic-coding" class="flex flex-col justify-center min-h-[44px] px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Agentic Coding</div> <div class="text-xs text-ink-500 mt-0.5">Context & constraints for coding agents</div> </a><a href="/use-cases/requirements" class="flex flex-col justify-center min-h-[44px] px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Product Requirements</div> <div class="text-xs text-ink-500 mt-0.5">Build-ready specs without the rework</div> </a><a href="/use-cases/prototyping" class="flex flex-col justify-center min-h-[44px] px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Prototyping</div> <div class="text-xs text-ink-500 mt-0.5">Turn ideas into better builds</div> </a><a href="/use-cases/strategy" class="flex flex-col justify-center min-h-[44px] px-3 py-2.5 rounded-lg hover:bg-ink-50 transition-colors"> <div class="text-sm font-semibold text-ink-900">Strategy & Transformation</div> <div class="text-xs text-ink-500 mt-0.5">Turn initiatives into actionable explorations</div> </a> </div><a href="/about" class="flex items-center min-h-[44px] px-3 py-2.5 rounded-lg text-ink-900 hover:bg-ink-50 transition-colors"> About </a><a href="/technology" class="flex items-center min-h-[44px] px-3 py-2.5 rounded-lg text-ink-900 hover:bg-ink-50 transition-colors"> Technology </a> <a href="https://app.ritual.work" target="_blank" rel="noopener noreferrer" data-ph-cta="get_started" data-ph-cta-location="header_mobile" class="mt-2 inline-flex items-center justify-center min-h-[44px] rounded-full bg-ink-900 text-white text-sm px-4 py-2.5 hover:bg-ink-700 transition-colors"> <span class="cta-label-default">Get started for free</span><span class="cta-label-maker">
177Build Now</span> </a> </nav> </div> </header>
177<script> 178 (function () { 179 var p = document.documentElement.getAttribute("data-persona"); 180 if (!p) return; 181 if (p === "developer" && location.pathname.indexOf("/product/developer") === 0) return; 182 document 183 .querySelectorAll('a[data-ph-cta-location="header"], a[data-ph-cta-location="header_mobile"]') 184 .forEach(function (a) { 185 if (p === "maker") { 186 a.setAttribute("href", "/product/makers#nc-idea"); 187 a.setAttribute("data-ph-cta", "nav_build_now"); 188 } else { 189 a.setAttribute("href", "/product/developer"); 190 a.setAttribute("data-ph-cta", "nav_dev_hero"); 191 } 192 a.removeAttribute("target"); 193 a.removeAttribute("rel"); 194 }); 195 })(); 196</script>
196
196<script> 197 (function () { 198 function init() { 199 var btn = document.querySelector("[data-mobile-toggle]"); 200 var panel = document.querySelector("[data-mobile-panel]"); 201 if (!btn || !panel) return; 202 btn.addEventListener("click", function () { 203 var open = panel.classList.toggle("hidden") === false; 204 btn.setAttribute("aria-expanded", open ? "true" : "false"); 205 }); 206 } 207 if (document.readyState === "loading") { 208 document.addEventListener("DOMContentLoaded", init); 209 } else { 210 init(); 211 } 212 })(); 213</script>
213 <main class="flex-1"> <section class="relative overflow-hidden bg-gradient-to-b from-accent-50/40 via-canvas to-canvas" data-astro-cid-foqmza75> <div class="mx-auto max-w-6xl px-6 pt-12 md:pt-20 pb-10 md:pb-12" data-astro-cid-foqmza75> <div class="text-center reveal" data-reveal data-astro-cid-foqmza75> <p class="text-lg md:text-2xl font-semibold tracking-[0.2em] uppercase text-accent-600" data-astro-cid-foqmza75> The Problem </p> <h1 class="mt-4 text-4xl md:text-5xl lg:text-6xl font-bold leading-[1.05] tracking-tight text-ink-900 text-balance" data-astro-cid-foqmza75> AI Tools Lose Context at Every Step </h1> <p class="mt-6 text-base md:text-lg text-ink-500 max-w-2xl mx-auto" data-astro-cid-foqmza75> As AI agents work through multi-step tasks, critical information gets lost, forgotten, or pushed out of memory â breaking the chain of understanding. </p> </div> <!-- Chain illustration (no background) --> <div class="reveal mt-6 md:mt-8 max-w-5xl mx-auto" data-reveal data-astro-cid-foqmza75> <!-- Chain image sliced into 5 --> <div class="chain-row relative flex justify-center items-center" data-astro-cid-foqmza75> <div class="chain-stage relative w-full max-w-3xl mx-auto" style="aspect-ratio: 1135 / 346;" data-astro-cid-foqmza75> <img src="/chain-link.png" alt="" class="chain-slice chain-slice-1 absolute inset-0 w-full h-full object-contain select-none" style="clip-path: inset(0 80% 0 0);" aria-hidden="true" data-astro-cid-foqmza75> <img src="/chain-link.png" alt="" class="chain-slice chain-slice-2 absolute inset-0 w-full h-full object-contain select-none" style="clip-path: inset(0 60% 0 20%);" aria-hidden="true" data-astro-cid-foqmza75> <img src="/chain-link.png" alt="" class="chain-slice chain-slice-3 absolute inset-0 w-full h-full object-contain select-none" style="clip-path: inset(0 40% 0 40%);" aria-hidden="true" data-astro-cid-foqmza75> <img src="/chain-link.png" alt="" class="chain-slice chain-slice-4 absolute inset-0 w-full h-full object-contain select-none" style="clip-path: inset(0 20% 0 60%);" aria-hidden="true" data-astro-cid-foqmza75> <img src="/chain-link.png" alt="Five chain links progressively breaking apart" class="chain-slice chain-slice-5 absolute inset-0 w-full h-full object-contain select-none" style="clip-path: inset(0 0 0 80%);" data-astro-cid-foqmza75> </div> </div> </div> <!-- Problem cards (one in focus at a time, rotates automatically). 214 No data-reveal here â we want the sand-panel band to peek up 215 from below the fold on first load so the user has a visual 216 cue that there's more to scroll to. Without this, the chain 217 sat above an invisible block and the page felt like it ended 218 at the hero. --> <div class="mt-12 md:mt-16 max-w-6xl mx-auto" data-problem-cards data-astro-cid-foqmza75> <div class="rounded-3xl bg-gradient-to-br from-sand-100 to-accent-50 ring-1 ring-accent-100 p-5 sm:p-8 md:p-10" data-astro-cid-foqmza75> <div class="grid md:grid-cols-3 gap-4 md:gap-6" data-astro-cid-foqmza75> <div class="problem-card bg-white rounded-2xl p-6 md:p-7 flex items-start gap-5 shadow-sm transition-all duration-500 is-focused" data-astro-cid-foqmza75> <span class="card-icon-wrap w-16 h-16 rounded-xl flex items-center justify-center flex-shrink-0" data-astro-cid-foqmza75> <img src="/db-small.png" alt="" width="44" height="44" class="w-11 h-11" aria-hidden="true" data-astro-cid-foqmza75> </span> <div class="min-w-0 pt-0.5" data-astro-cid-foqmza75> <h3 class="text-lg md:text-xl font-bold text-ink-900 mb-1.5 leading-tight" data-astro-cid-foqmza75>No Persistence</h3> <p class="text-ink-500 text-sm md:text-[15px] leading-snug" data-astro-cid-foqmza75>Data vanishes between sessions</p> </div> </div><div class="problem-card bg-white rounded-2xl p-6 md:p-7 flex items-start gap-5 shadow-sm transition-all duration-500" data-astro-cid-foqmza75> <span class="card-icon-wrap w-16 h-16 rounded-xl flex items-center justify-center flex-shrink-0" data-astro-cid-foqmza75> <img src="/memory-small.png" alt="" width="44" height="44" class="w-11 h-11" aria-hidden="true" data-astro-cid-foqmza75> </span> <div class="min-w-0 pt-0.5" data-astro-cid-foqmza75> <h3 class="text-lg md:text-xl font-bold text-ink-900 mb-1.5 leading-tight" data-astro-cid-foqmza75>Memory Reset</h3> <p class="text-ink-500 text-sm md:text-[15px] leading-snug" data-astro-cid-foqmza75>Each conversation starts fresh</p> </div> </div><div class="problem-card bg-white rounded-2xl p-6 md:p-7 flex items-start gap-5 shadow-sm transition-all duration-500" data-astro-cid-foqmza75> <span class="card-icon-wrap w-16 h-16 rounded-xl flex items-center justify-center flex-shrink-0" data-astro-cid-foqmza75> <img src="/context-small.png" alt="" width="44" height="44" class="w-11 h-11" aria-hidden="true" data-astro-cid-foqmza75> </span> <div class="min-w-0 pt-0.5" data-astro-cid-foqmza75> <h3 class="text-lg md:text-xl font-bold text-ink-900 mb-1.5 leading-tight" data-astro-cid-foqmza75>Context Overflow</h3> <p class="text-ink-500 text-sm md:text-[15px] leading-snug" data-astro-cid-foqmza75>Old info pushed out of window</p> </div> </div> </div> </div> </div> <!-- Sound familiar? (below carousel) --> <div class="reveal mt-14 md:mt-20 max-w-6xl mx-auto text-center" data-reveal data-astro-cid-foqmza75> <p class="text-base md:text-xl font-semibold tracking-[0.2em] uppercase text-ink-400 mb-6 md:mb-7" data-astro-cid-foqmza75> 219Sound familiar? This happens with... 220</p> <div class="flex flex-wrap md:flex-nowrap justify-center items-center gap-2 md:gap-4" data-astro-cid-foqmza75> <span class="reveal-step inline-flex items-center justify-center rounded-full bg-white border border-accent-500 md:border-2 px-3 md:px-6 py-1.5 md:py-3.5 text-xs md:text-base font-medium text-ink-700 shadow-[0_2px_8px_-2px_rgba(238,113,0,0.18)] md:shadow-[0_4px_14px_-2px_rgba(238,113,0,0.18)] whitespace-nowrap" style="--step-delay: 0ms" data-reveal-step data-astro-cid-foqmza75> Vibe coding (Claude, Cursor) </span><span class="reveal-step inline-flex items-center justify-center rounded-full bg-white border border-accent-500 md:border-2 px-3 md:px-6 py-1.5 md:py-3.5 text-xs md:text-base font-medium text-ink-700 shadow-[0_2px_8px_-2px_rgba(238,113,0,0.18)] md:shadow-[0_4px_14px_-2px_rgba(238,113,0,0.18)] whitespace-nowrap" style="--step-delay: 80ms" data-reveal-step data-astro-cid-foqmza75> Cursor rules </span><span class="reveal-step inline-flex items-center justify-center rounded-full bg-white border border-accent-500 md:border-2 px-3 md:px-6 py-1.5 md:py-3.5 text-xs md:text-base font-medium text-ink-700 shadow-[0_2px_8px_-2px_rgba(238,113,0,0.18)] md:shadow-[0_4px_14px_-2px_rgba(238,113,0,0.18)] whitespace-nowrap" style="--step-delay: 160ms" data-reveal-step data-astro-cid-foqmza75> Custom GPTs </span><span class="reveal-step inline-flex items-center justify-center rounded-full bg-white border border-accent-500 md:border-2 px-3 md:px-6 py-1.5 md:py-3.5 text-xs md:text-base font-medium text-ink-700 shadow-[0_2px_8px_-2px_rgba(238,113,0,0.18)] md:shadow-[0_4px_14px_-2px_rgba(238,113,0,0.18)] whitespace-nowrap" style="--step-delay: 240ms" data-reveal-step data-astro-cid-foqmza75>
220 Your normal prompting approach </span> </div> </div> </div> </section> <section class="bg-canvas" data-astro-cid-foqmza75> <div class="mx-auto max-w-5xl px-6 py-10 md:py-12" data-astro-cid-foqmza75> <div class="text-center reveal" data-reveal data-astro-cid-foqmza75> <p class="text-lg md:text-2xl font-semibold tracking-[0.2em] uppercase text-accent-600" data-astro-cid-foqmza75>The Symptoms</p> <h2 class="mt-4 text-3xl md:text-4xl lg:text-5xl font-bold text-ink-900 text-balance" data-astro-cid-foqmza75> 221What Context Loss Looks Like in Your Output 222</h2> <p class="mt-6 text-base md:text-lg text-ink-500 max-w-2xl mx-auto" data-astro-cid-foqmza75> 223These red flags show up in AI-generated code and responses when context has drifted or been lost entirely. 224</p> </div> <div class="mt-12 md:mt-14 grid sm:grid-cols-2 gap-5 md:gap-6 max-w-5xl mx-auto" data-astro-cid-foqmza75> <div class="reveal-step flex items-start gap-4 bg-white border border-accent-300 rounded-2xl p-6 md:p-7 transition-colors duration-300 hover:border-accent-500" style="--step-delay: 0ms" data-reveal-step data-astro-cid-foqmza75> <span class="w-10 h-10 rounded-lg bg-red-100 flex items-center justify-center flex-shrink-0" data-astro-cid-foqmza75> <svg width="18" height="18" viewBox="0 0 16 16" fill="none" aria-hidden="true" data-astro-cid-foqmza75> <path d="M4 4L12 12M12 4L4 12" stroke="#ef4444" stroke-width="2.5" stroke-linecap="round" data-astro-cid-foqmza75></path> </svg> </span> <div class="min-w-0" data-astro-cid-foqmza75> <h3 class="font-bold text-ink-900 text-lg mb-1.5" data-astro-cid-foqmza75>Hallucinations</h3> <p class="text-ink-500 text-sm md:text-[15px] leading-snug" data-astro-cid-foqmza75>Confident but fabricated information</p> </div> </div><div class="reveal-step flex items-start gap-4 bg-white border border-accent-300 rounded-2xl p-6 md:p-7 transition-colors duration-300 hover:border-accent-500" style="--step-delay: 80ms" data-reveal-step data-astro-cid-foqmza75> <span class="w-10 h-10 rounded-lg bg-red-100 flex items-center justify-center flex-shrink-0" data-astro-cid-foqmza75> <svg width="18" height="18" viewBox="0 0 16 16" fill="none" aria-hidden="true" data-astro-cid-foqmza75> <path d="M4 4L12 12M12 4L4 12" stroke="#ef4444" stroke-width="2.5" stroke-linecap="round" data-astro-cid-foqmza75></path> </svg> </span> <div class="min-w-0" data-astro-cid-foqmza75> <h3 class="font-bold text-ink-900 text-lg mb-1.5" data-astro-cid-foqmza75>Context Drift</h3> <p class="text-ink-500 text-sm md:text-[15px] leading-snug" data-astro-cid-foqmza75>Gradually loses track of requirements</p> </div> </div><div class="reveal-step flex items-start gap-4 bg-white border border-accent-300 rounded-2xl p-6 md:p-7 transition-colors duration-300 hover:border-accent-500" style="--step-delay: 160ms" data-reveal-step data-astro-cid-foqmza75> <span class="w-10 h-10 rounded-lg bg-red-100 flex items-center justify-center flex-shrink-0" data-astro-cid-foqmza75> <svg width="18" height="18" viewBox="0 0 16 16" fill="none" aria-hidden="true" data-astro-cid-foqmza75> <path d="M4 4L12 12M12 4L4 12" stroke="#ef4444" stroke-width="2.5" stroke-linecap="round" data-astro-cid-foqmza75></path> </svg> </span> <div class="min-w-0" data-astro-cid-foqmza75> <h3 class="font-bold text-ink-900 text-lg mb-1.5" data-astro-cid-foqmza75>Unresolved Trade-offs</h3> <p class="text-ink-500 text-sm md:text-[15px] leading-snug" data-astro-cid-foqmza75>Ignores competing constraints</p> </div> </div><div class="reveal-step flex items-start gap-4 bg-white border border-accent-300 rounded-2xl p-6 md:p-7 transition-colors duration-300 hover:border-accent-500" style="--step-delay: 240ms" data-reveal-step data-astro-cid-foqmza75> <span class="w-10 h-10 rounded-lg bg-red-100 flex items-center justify-center flex-shrink-0" data-astro-cid-foqmza75> <svg width="18" height="18" viewBox="0 0 16 16" fill="none" aria-hidden="true" data-astro-cid-foqmza75> <path d="M4 4L12 12M12 4L4 12" stroke="#ef4444" stroke-width="2.5" stroke-linecap="round" data-astro-cid-foqmza75></path> </svg> </span> <div class="min-w-0" data-astro-cid-foqmza75> <h3 class="font-bold text-ink-900 text-lg mb-1.5" data-astro-cid-foqmza75>Guesswork</h3> <p class="text-ink-500 text-sm md:text-[15px] leading-snug" data-astro-cid-foqmza75>Fills gaps with assumptions</p> </div> </div><div class="reveal-step flex items-start gap-4 bg-white border border-accent-300 rounded-2xl p-6 md:p-7 transition-colors duration-300 hover:border-accent-500" style="--step-delay: 320ms" data-reveal-step data-astro-cid-foqmza75> <span class="w-10 h-10 rounded-lg bg-red-100 flex items-center justify-center flex-shrink-0" data-astro-cid-foqmza75> <svg width="18" height="18" viewBox="0 0 16 16" fill="none" aria-hidden="true" data-astro-cid-foqmza75> <path d="M4 4L12 12M12 4L4 12" stroke="#ef4444" stroke-width="2.5" stroke-linecap="round" data-astro-cid-foqmza75></path> </svg> </span> <div class="min-w-0" data-astro-cid-foqmza75> <h3 class="font-bold text-ink-900 text-lg mb-1.5" data-astro-cid-foqmza75>Flawed Assumptions</h3> <p class="text-ink-500 text-sm md:text-[15px] leading-snug" data-astro-cid-foqmza75>Builds on incorrect premises</p> </div> </div><div class="reveal-step flex items-start gap-4 bg-white border border-accent-300 rounded-2xl p-6 md:p-7 transition-colors duration-300 hover:border-accent-500" style="--step-delay: 400ms" data-reveal-step data-astro-cid-foqmza75> <span class="w-10 h-10 rounded-lg bg-red-100 flex items-center justify-center flex-shrink-0" data-astro-cid-foqmza75> <svg width="18" height="18" viewBox="0 0 16 16" fill="none" aria-hidden="true" data-astro-cid-foqmza75> <path d="M4 4L12 12M12 4L4 12" stroke="#ef4444" stroke-width="2.5" stroke-linecap="round" data-astro-cid-foqmza75></path> </svg> </span> <div class="min-w-0" data-astro-cid-foqmza75> <h3 class="font-bold text-ink-900 text-lg mb-1.5" data-astro-cid-foqmza75>Weak Reasoning</h3> <p class="text-ink-500 text-sm md:text-[15px] leading-snug" data-astro-cid-foqmza75>Shallow logic without full picture</p> </div> </div> </div> </div> </section> <section class="bg-canvas" data-astro-cid-foqmza75> <div class="mx-auto max-w-7xl px-6 pt-8 md:pt-10 pb-10 md:pb-12" data-astro-cid-foqmza75> <div class="text-center reveal" data-reveal data-astro-cid-foqmza75> <p class="text-lg md:text-2xl font-semibold tracking-[0.2em] uppercase text-accent-600" data-astro-cid-foqmza75>The Impact</p> <h2 class="mt-4 text-3xl md:text-4xl lg:text-5xl font-bold text-ink-900 text-balance" data-astro-cid-foqmza75> 225Lost Context Means Lost Productivity 226</h2> <p class="mt-6 text-base md:text-lg text-ink-500 max-w-2xl mx-auto" data-astro-cid-foqmza75> 227When AI tools forget what they knew, developers pay the price in rework, frustration, and wasted t
227ime. 228</p> </div> <div class="mt-12 md:mt-14 max-w-4xl mx-auto space-y-4 md:space-y-5" data-astro-cid-foqmza75> <div class="reveal-step bg-canvas-soft rounded-2xl px-6 md:px-8 py-7 md:py-8 ring-1 ring-ink-100 transition-all duration-300 hover:-translate-y-0.5 hover:shadow-md" style="--step-delay: 0ms" data-reveal-step data-astro-cid-foqmza75> <div class="text-4xl md:text-5xl font-bold bg-gradient-to-r from-accent-500 to-accent-700 bg-clip-text text-transparent mb-3" data-astro-cid-foqmza75> 47% </div> <h3 class="text-2xl md:text-3xl font-bold text-ink-900 mb-2" data-astro-cid-foqmza75>Time Re-explaining</h3> <p class="text-ink-500 leading-relaxed text-sm md:text-base" data-astro-cid-foqmza75>Developers spend nearly half their AI interaction time re-explaining context that was already provided in earlier sessions.</p> </div><div class="reveal-step bg-canvas-soft rounded-2xl px-6 md:px-8 py-7 md:py-8 ring-1 ring-ink-100 transition-all duration-300 hover:-translate-y-0.5 hover:shadow-md" style="--step-delay: 120ms" data-reveal-step data-astro-cid-foqmza75> <div class="text-4xl md:text-5xl font-bold bg-gradient-to-r from-accent-500 to-accent-700 bg-clip-text text-transparent mb-3" data-astro-cid-foqmza75> 3.2x </div> <h3 class="text-2xl md:text-3xl font-bold text-ink-900 mb-2" data-astro-cid-foqmza75>More Iterations</h3> <p class="text-ink-500 leading-relaxed text-sm md:text-base" data-astro-cid-foqmza75>Tasks requiring cross-session knowledge take 3.2x more back-and-forth cycles to complete correctly.</p> </div><div class="reveal-step bg-canvas-soft rounded-2xl px-6 md:px-8 py-7 md:py-8 ring-1 ring-ink-100 transition-all duration-300 hover:-translate-y-0.5 hover:shadow-md" style="--step-delay: 240ms" data-reveal-step data-astro-cid-foqmza75> <div class="text-4xl md:text-5xl font-bold bg-gradient-to-r from-accent-500 to-accent-700 bg-clip-text text-transparent mb-3" data-astro-cid-foqmza75> 68% </div> <h3 class="text-2xl md:text-3xl font-bold text-ink-900 mb-2" data-astro-cid-foqmza75>PRs Need Rework</h3> <p class="text-ink-500 leading-relaxed text-sm md:text-base" data-astro-cid-foqmza75>The majority of AI-generated pull requests require significant revision because agents lack awareness of project conventions.</p> </div> </div> </div> </section> <section class="bg-night-900 text-white"> <div class="mx-auto max-w-7xl px-6 py-20 text-center"> <h2 class="text-3xl md:text-4xl font-bold tracking-tight"> 229Ready to own the <span class="bg-gradient-to-r from-accent-500 to-sand-300 bg-clip-text text-transparent">frontier</span>? 230 </h2> <p class="mt-4 text-ink-300 max-w-xl mx-auto text-sm md:text-base">Join thousands of users already using our platform to drive growth and innovation.</p> <div class="mt-8 flex items-center justify-center gap-3"> <a href="https://app.ritual.work" target="_blank" rel="noopener noreferrer" data-ph-cta="get_started" data-ph-cta-location="cta_section_primary" class="inline-flex items-center rounded-full bg-white text-ink-900 text-sm font-medium px-5 py-2.5 hover:bg-ink-100 transition-colors"> Get Started </a> <a href="https://calendly.com/mike-hkg/30min" target="_blank" rel="noopener noreferrer" data-ph-cta="book_demo" data-ph-cta-location="cta_section_secondary" class="inline-flex items-center rounded-full border border-white/30 text-white text-sm font-medium px-5 py-2.5 hover:bg-white/10 transition-colors"> Schedule a Demo </a> </div> </div> </section> </main> <footer class="bg-canvas border-t border-ink-100"> <div class="mx-auto max-w-7xl px-6 py-10 md:py-14"> <div class="grid grid-cols-2 md:grid-cols-4 gap-8 md:gap-10"> <div class="col-span-2 md:col-span-1"> <a href="/" class="flex items-center gap-2" aria-label="Ritual home"> <img src="/ritual-logo.svg" alt="Ritual" class="h-7 w-auto"> </a> <p class="mt-4 text-sm text-ink-500 max-w-xs"> 231Move from idea to action with AIâpowered collaboration. 232</p> <div class="mt-5 flex items-center gap-3"> <a href="https://www.linkedin.com/company/ritualai" target="_blank" rel="noopener noreferrer" aria-label="Ritual on LinkedIn" class="inline-flex h-9 w-9 items-center justify-center rounded-full ring-1 ring-ink-100 text-ink-500 hover:text-ink-900 hover:ring-ink-300 transition-colors"> <svg viewBox="0 0 24 24" fill="currentColor" aria-hidden="true" class="h-4 w-4"> <path d="M20.452 20.452h-3.554v-5.569c0-1.328-.027-3.037-1.852-3.037-1.853 0-2.136 1.445-2.136 2.939v5.667H9.356V9h3.414v1.561h.046c.477-.9 1.637-1.852 3.37-1.852 3.602 0 4.266 2.37 4.266 5.455v6.288zM5.337 7.433a2.062 2.062 0 01-2.063-2.064 2.063 2.063 0 112.063 2.064zM7.119 20.452H3.553V9h3.566v11.452zM22.225 0H1.771C.792 0 0 .774 0 1.729v20.542C0 23.227.792 24 1.771 24h20.451C23.2 24 24 23.227 24 22.271V1.729C24 .774 23.2 0 22.222 0h.003z"></path> </svg> </a> </div> </div> <div> <h4 class="text-sm font-semibold text-ink-900">Product</h4> <ul class="mt-4 space-y-3"> <li> <a href="/product/builder" class="text-sm text-ink-500 hover:text-ink-900 transition-colors"> Product </a> </li><li> <a href="/product/developer" class="text-sm text-ink-500 hover:text-ink-900 transition-colors"> Developer </a> </li><li> <a href="/product/makers" class="text-sm text-ink-500 hover:text-ink-900 transition-colors"> Prototyping </a> </li> </ul> </div><div> <h4 class="text-sm font-semibold text-ink-900">Resources</h4> <ul class="mt-4 space-y-3"> <li> <a href="/docs/quickstart" class="text-sm text-ink-500 hover:text-ink-900 transition-colors"> Quick start </a> </li><li> <a href="/faq" class="text-sm text-ink-500 hover:text-ink-900 transition-colors"> FAQ </a> </li><li> <a href="/support" class="text-sm text-ink-500 hover:text-ink-900 transition-colors"> Support </a> </li><li> <a href="/security" class="text-sm text-ink-500 hover:text-ink-900 transition-colors"> Security </a> </li> </ul> </div><div> <h4 class="text-sm font-semibold text-ink-900">Company</h4> <ul class="mt-4 space-y-3"> <li> <a href="/about" class="text-sm text-ink-500 hover:text-ink-900 transition-colors"> About </a> </li> </ul> </div> </div> <div class="mt-14 pt-6 border-t border-ink-100 text-center text-xs text-ink-400"> 233© 2025 Ritual. All rights reserved. 234</div> </div> </footer> </body></html>
234<script> 235 (function () { 236 function initReveal() { 237 var targets = document.querySelectorAll( 238 "[data-reveal], [data-reveal-step], .chain-row" 239 ); 240 if (!("IntersectionObserver" in window)) { 241 targets.forEach(function (el) { el.classList.add("is-visible"); }); 242 return; 243 } 244 var io = new IntersectionObserver(function (entries) { 245 entries.forEach(function (entry) { 246 if (entry.isIntersecting) { 247 entry.target.classList.add("is-visible"); 248 io.unobserve(entry.target); 249 } 250 }); 251 }, { threshold: 0.15, rootMargin: "0px 0px -40px 0px" }); 252 targets.forEach(function (el) { io.observe(el); }); 253 } 254 255 function initProblemCards() { 256 var root = document.querySelector("[data-problem-cards]"); 257 if (!root) return; 258 var cards = root.querySelectorAll(".problem-card"); 259 if (cards.length === 0) return; 260 261 var current = 0; 262 var rotateMs = 3000; 263 var timer = null; 264 var paused = false; 265 266 function setFocus(i) { 267 current = i; 268 cards.forEach(function (card, idx) { 269 card.classList.toggle("is-focused", idx === i); 270 }); 271 } 272 function startRotate() { 273 stopRotate(); 274 if (paused) return; 275 timer = window.setInterval(function () { 276 setFocus((current + 1) % cards.length); 277 }, rotateMs); 278 } 279 function stopRotate() { 280 if (timer) { window.clearInterval(timer); timer = null; } 281 } 282 283 // Pause auto-rotate when the user hovers the card row â gives them 284 // a chance to read without the focus moving out from under them. 285 // Resume on leave. NOT paused on click (cards are non-interactive). 286 root.addEventListener("mouseenter", function () { paused = true; stopRotate(); }); 287 root.addEventListener("mouseleave", function () { paused = false; startRotate(); }); 288 289 // Only start rotating once the section scrolls into view â no 290 // sense burning a setInterval while the user is reading the hero. 291 if ("IntersectionObserver" in window) { 292 var startIO = new IntersectionObserver(function (entries) { 293 entries.forEach(function (entry) { 294 if (entry.isIntersecting) { 295 startRotate(); 296 startIO.unobserve(entry.target); 297 } 298 }); 299 }, { threshold: 0.3 }); 300 startIO.observe(root); 301 } else { 302 startRotate(); 303 } 304 } 305 306 function init() { 307 initReveal(); 308 initProblemCards(); 309 } 310 if (document.readyState === "loading") { 311 document.addEventListener("DOMContentLoaded", init); 312 } else { 313 init(); 314 } 315 })(); 316</script>
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.