feat(landing): use new header style#494
Conversation
Drop the announcement ribbon offset, tighten the bar, and use RollText on main nav. Co-authored-by: Cursor <cursoragent@cursor.com>
Shared with the resources page branch — small util for ?ref= on outbound URLs. Co-authored-by: Cursor <cursoragent@cursor.com>
Document the roll-unit markup, data-roll-group hover, and latch playback. Register Roll text in the text overview; wire header nav with character stagger. Co-authored-by: Cursor <cursoragent@cursor.com>
Resolves CI typecheck failure on RollTextProps.type and ref assignment. Co-authored-by: Cursor <cursoragent@cursor.com>
Drop polymorphic as/type; wrap links and buttons on the parent. Decorative track stays aria-hidden; standalone labels stay tabbable via tabIndex 0. Co-authored-by: Cursor <cursoragent@cursor.com>
Keep roll motion on fixed label colors instead of parent hover:text-*, add disabled for active nav links, and tighten will-change to the animating phase. Co-authored-by: Cursor <cursoragent@cursor.com>
📝 WalkthroughWalkthroughAdds RollText, a new decorative text animation component that splits text into segments and animates them rolling into view with configurable stagger modes (none, word, character). Includes complete styling with CSS custom properties, Storybook stories, comprehensive documentation, site header integration, and a utility for appending analytics ref parameters to external links. ChangesRollText Animation Component
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes Possibly related PRs
Suggested reviewers
Poem
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches📝 Generate docstrings
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 7
🧹 Nitpick comments (1)
animata/text/roll-text.css (1)
9-9: 💤 Low valueMinor formatting: Add empty line before declaration.
Stylelint reports that an empty line is expected before the
font-kerningdeclaration for consistency with the project's CSS formatting rules.♻️ Proposed fix
--roll-layer-gap: 0.05em; --roll-line-height: 1.15; + font-kerning: none; line-height: var(--roll-line-height);🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@animata/text/roll-text.css` at line 9, Add a single blank line immediately before the font-kerning: none; declaration in roll-text.css so it matches the project's CSS formatting rules; locate the font-kerning declaration and insert an empty line above it, then re-run stylelint to confirm the formatting warning is resolved.Source: Linters/SAST tools
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@animata/text/roll-text.stories.tsx`:
- Line 46: The className on the JSX element in roll-text.stories.tsx contains an
invalid Tailwind token "font-(family-name:--font-display)"; replace that token
with a valid Tailwind approach by either using your configured utility (e.g.,
font-display) or Tailwind's arbitrary property syntax to reference the CSS
variable (use the [font-family:var(--font-display)] form), and update the
className string accordingly so it uses only valid Tailwind utility classes.
- Line 27: The className string "font-(family-name:--font-display) text-4xl
tracking-tight text-foreground" uses invalid Tailwind syntax; update the font
part to a valid Tailwind utility—either use the configured font family utility
like "font-display" if it exists, or use the arbitrary value syntax referencing
the CSS variable as "font-[var(--font-display)]" (keep the rest of the classes
unchanged). Locate the className property in roll-text.stories.tsx and replace
only the invalid font token accordingly.
In `@animata/text/roll-text.tsx`:
- Line 17: The component currently imports external CSS (roll-text.css) which
violates the guideline; remove the import statement and move the CSS rules into
an inline <style> block inside the RollText component file (either returned from
the component or at module scope within the same .tsx) by copying the contents
of roll-text.css into a JSX style tag (e.g., <style jsx>{`...`}</style>)
ensuring you preserve selectors like .roll-text, animations, and custom
properties such as --roll-duration so the RollText component, its class names,
and keyframes continue to work unchanged.
In `@components/site-header.tsx`:
- Around line 54-81: The active nav item uses the "text-accent" class (inside
the docsConfig.mainNav.map render where isActive is computed and applied to the
RollText component) which resolves to a purple accent; change that to the brand
yellow by replacing the conditional class value (isActive ? "text-accent" :
"text-muted-foreground") with a class that outputs `#ffcc00` (for example use
Tailwind's arbitrary color class text-[`#ffcc00`]) or alternatively update your
Tailwind/Theme accent token to the hex `#ffcc00` so the active state uses the
brand yellow.
In `@content/docs/text/index.mdx`:
- Line 161: The className contains invalid Tailwind syntax: replace
className="font-(family-name:--font-display) text-3xl tracking-tight
text-foreground" with a valid approach — either use a real Tailwind utility
(e.g. className="font-sans text-3xl tracking-tight text-foreground") or remove
the malformed font-... token and apply the CSS variable via the style prop (e.g.
style={{ fontFamily: 'var(--font-display)' }} alongside className="text-3xl
tracking-tight text-foreground"); update the className string or add the style
prop in the same element where that className appears.
In `@content/docs/text/roll-text.mdx`:
- Line 45: The examples use an invalid Tailwind className token
"font-(family-name:--font-display)"; update all RollText usages (e.g., the
<RollText ... /> instances) to use a valid Tailwind font class or an arbitrary
value syntax such as "font-[var(--font-display)]" or the theme-defined class
like "font-display" (whichever matches your project theme). Replace the invalid
token in every occurrence (lines referenced in the review) so the examples show
a valid Tailwind className.
In `@lib/outbound-ref.ts`:
- Around line 5-16: withOutboundRef currently constructs a URL from href using
the URL constructor which can throw for malformed but regex-passing inputs; wrap
the URL(...) call in a try/catch inside withOutboundRef (referencing function
name withOutboundRef and constant OUTBOUND_REF) and on error simply return the
original href (or a safe fallback) instead of letting the exception propagate,
ensuring the function remains a no-op for invalid URLs while preserving existing
behavior for valid ones.
---
Nitpick comments:
In `@animata/text/roll-text.css`:
- Line 9: Add a single blank line immediately before the font-kerning: none;
declaration in roll-text.css so it matches the project's CSS formatting rules;
locate the font-kerning declaration and insert an empty line above it, then
re-run stylelint to confirm the formatting warning is resolved.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: defaults
Review profile: CHILL
Plan: Pro
Run ID: d644c58b-1e90-45ca-a8ab-3f01ed2d0bbd
📒 Files selected for processing (9)
animata/text/roll-text.cssanimata/text/roll-text.stories.tsxanimata/text/roll-text.tsxapp/(main)/layout.tsxcomponents/site-header.tsxconfig/docs.tscontent/docs/text/index.mdxcontent/docs/text/roll-text.mdxlib/outbound-ref.ts
💤 Files with no reviewable changes (1)
- app/(main)/layout.tsx
| stagger: "character", | ||
| staggerMs: 32, | ||
| durationMs: 250, | ||
| className: "font-(family-name:--font-display) text-4xl tracking-tight text-foreground", |
There was a problem hiding this comment.
Invalid Tailwind className syntax.
The className font-(family-name:--font-display) is not valid Tailwind CSS syntax and will not apply the intended font-family styling. As per coding guidelines, use Tailwind CSS only for styling.
🎨 Proposed fix using Tailwind arbitrary value syntax
- className: "font-(family-name:--font-display) text-4xl tracking-tight text-foreground",
+ className: "font-[var(--font-display)] text-4xl tracking-tight text-foreground",Alternatively, if font-display is configured as a custom utility in tailwind.config.js:
- className: "font-(family-name:--font-display) text-4xl tracking-tight text-foreground",
+ className: "font-display text-4xl tracking-tight text-foreground",📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| className: "font-(family-name:--font-display) text-4xl tracking-tight text-foreground", | |
| className: "font-[var(--font-display)] text-4xl tracking-tight text-foreground", |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@animata/text/roll-text.stories.tsx` at line 27, The className string
"font-(family-name:--font-display) text-4xl tracking-tight text-foreground" uses
invalid Tailwind syntax; update the font part to a valid Tailwind utility—either
use the configured font family utility like "font-display" if it exists, or use
the arbitrary value syntax referencing the CSS variable as
"font-[var(--font-display)]" (keep the rest of the classes unchanged). Locate
the className property in roll-text.stories.tsx and replace only the invalid
font token accordingly.
Source: Coding guidelines
| <RollText | ||
| {...args} | ||
| groupHover | ||
| className="pointer-events-none font-(family-name:--font-display) text-2xl text-foreground" |
There was a problem hiding this comment.
Invalid Tailwind className syntax.
Same issue as the Primary story: font-(family-name:--font-display) is not valid Tailwind CSS syntax. As per coding guidelines, use Tailwind CSS only for styling.
🎨 Proposed fix
- className="pointer-events-none font-(family-name:--font-display) text-2xl text-foreground"
+ className="pointer-events-none font-[var(--font-display)] text-2xl text-foreground"Or, if using a configured utility:
- className="pointer-events-none font-(family-name:--font-display) text-2xl text-foreground"
+ className="pointer-events-none font-display text-2xl text-foreground"📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| className="pointer-events-none font-(family-name:--font-display) text-2xl text-foreground" | |
| className="pointer-events-none font-[var(--font-display)] text-2xl text-foreground" |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@animata/text/roll-text.stories.tsx` at line 46, The className on the JSX
element in roll-text.stories.tsx contains an invalid Tailwind token
"font-(family-name:--font-display)"; replace that token with a valid Tailwind
approach by either using your configured utility (e.g., font-display) or
Tailwind's arbitrary property syntax to reference the CSS variable (use the
[font-family:var(--font-display)] form), and update the className string
accordingly so it uses only valid Tailwind utility classes.
Source: Coding guidelines
|
|
||
| import { cn } from "@/lib/utils"; | ||
|
|
||
| import "./roll-text.css"; |
There was a problem hiding this comment.
Move CSS animations to an inline <style> block.
The component imports a separate CSS file, which violates the coding guidelines. As per coding guidelines, CSS animations for components in animata/**/*.tsx must belong in inline <style> blocks inside the component, not in separate CSS modules or styled-components.
♻️ Recommended refactor to move CSS inline
Remove the import and add the CSS content within a <style> JSX block in the component. Example structure:
-import "./roll-text.css";
-
export type RollStagger = "none" | "word" | "character";
export interface RollTextProps extends Omit<React.ComponentPropsWithoutRef<"span">, "children"> {Then, within the RollText component function body or at the end of the file, add:
// Add inside the component's return statement or at module level
<style jsx>{`
`@layer` components {
.roll-text {
--roll-duration: 450ms;
/* ... rest of CSS from roll-text.css ... */
}
}
`}</style>Or use a template literal style tag in the component's render return.
As per coding guidelines: "CSS animations must belong in inline <style> blocks inside the component, not in separate CSS modules or styled-components" applies to animata/**/*.tsx.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@animata/text/roll-text.tsx` at line 17, The component currently imports
external CSS (roll-text.css) which violates the guideline; remove the import
statement and move the CSS rules into an inline <style> block inside the
RollText component file (either returned from the component or at module scope
within the same .tsx) by copying the contents of roll-text.css into a JSX style
tag (e.g., <style jsx>{`...`}</style>) ensuring you preserve selectors like
.roll-text, animations, and custom properties such as --roll-duration so the
RollText component, its class names, and keyframes continue to work unchanged.
Source: Coding guidelines
| {docsConfig.mainNav.map((item) => { | ||
| const href = item.href as string; | ||
| const isActive = href === "/" ? pathname === "/" : pathname.startsWith(href); | ||
| return ( | ||
| <Link | ||
| key={index} | ||
| key={href} | ||
| href={href} | ||
| data-roll-group | ||
| className={cn( | ||
| "rounded-md px-3 py-1.5 text-[13px] font-medium transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring", | ||
| isActive | ||
| ? "bg-foreground/10 text-foreground" | ||
| : "text-muted-foreground hover:text-foreground", | ||
| "group/roll relative inline-flex items-center overflow-visible px-2 py-0.5 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring", | ||
| )} | ||
| aria-current={isActive ? "page" : undefined} | ||
| > | ||
| {item.title} | ||
| <RollText | ||
| groupHover | ||
| disabled={isActive} | ||
| text={item.title} | ||
| stagger="character" | ||
| staggerMs={32} | ||
| durationMs={200} | ||
| className={cn( | ||
| "pointer-events-none text-xs font-medium [font-kerning:none]", | ||
| isActive ? "text-accent" : "text-muted-foreground", | ||
| )} | ||
| /> | ||
| </Link> | ||
| ); | ||
| })} |
There was a problem hiding this comment.
🧩 Analysis chain
🏁 Script executed:
#!/bin/bash
# Description: Verify accent color is set to brand yellow `#ffcc00`
# Search for accent color definition in Tailwind config and CSS files
rg -n "accent.*#?ffcc00|ffcc00.*accent" --glob '*tailwind*.{js,ts,cjs,mjs}' --glob '**/*.css'Repository: codse/animata
Length of output: 39
🏁 Script executed:
#!/bin/bash
set -euo pipefail
echo "== Tailwind config files =="
fd -t f "tailwind.config.*" .
echo
echo "== Locate globals.css =="
fd -t f "globals.css" . || true
echo
echo "== Search for accent color mapping (Tailwind/theme variables) =="
rg -n "(--color-accent|--accent|accent-foreground|text-accent\b|`@theme`|theme\.)" --glob "**/*.{css,ts,tsx,js,jsx,cjs,mjs}" .
echo
echo "== Print relevant excerpts from globals.css (if present) =="
g=$(fd -t f "globals.css" . | head -n 1 || true)
if [ -n "${g}" ]; then
echo "--- File: $g (around --accent / --color-accent) ---"
rg -n "--color-accent|--accent\b|accent-foreground" "$g" || true
# Show a broader window around the first match region(s)
for pat in "--color-accent" "--accent" "accent-foreground"; do
line=$(rg -n "$pat" "$g" | head -n 1 | cut -d: -f1 || true)
if [ -n "$line" ]; then
start=$(( line>40 ? line-40 : 1 ))
end=$(( line+120 ))
echo "--- $pat around lines $start-$end ---"
sed -n "${start},${end}p" "$g" | nl -ba -w2 -s':'
fi
done
else
echo "globals.css not found via fd."
fiRepository: codse/animata
Length of output: 6946
Fix active nav highlight color to use brand yellow (#ffcc00)
text-accent in components/site-header.tsx resolves to --color-accent: hsl(var(--accent)), and --accent is 262 83% 58% (purple), so the active nav item isn’t using the required brand yellow #ffcc00. Update the active nav class to use #ffcc00 (or adjust the Tailwind accent token to #ffcc00) instead of text-accent.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@components/site-header.tsx` around lines 54 - 81, The active nav item uses
the "text-accent" class (inside the docsConfig.mainNav.map render where isActive
is computed and applied to the RollText component) which resolves to a purple
accent; change that to the brand yellow by replacing the conditional class value
(isActive ? "text-accent" : "text-muted-foreground") with a class that outputs
`#ffcc00` (for example use Tailwind's arbitrary color class text-[`#ffcc00`]) or
alternatively update your Tailwind/Theme accent token to the hex `#ffcc00` so the
active state uses the brand yellow.
Source: Coding guidelines
| text="Roll text" | ||
| stagger="character" | ||
| staggerMs={32} | ||
| className="font-(family-name:--font-display) text-3xl tracking-tight text-foreground" |
There was a problem hiding this comment.
Invalid Tailwind className syntax.
The className font-(family-name:--font-display) is not valid Tailwind CSS syntax. As per coding guidelines, use Tailwind CSS only for styling.
🎨 Proposed fix
- className="font-(family-name:--font-display) text-3xl tracking-tight text-foreground"
+ className="font-[var(--font-display)] text-3xl tracking-tight text-foreground"Or, if using a configured utility:
- className="font-(family-name:--font-display) text-3xl tracking-tight text-foreground"
+ className="font-display text-3xl tracking-tight text-foreground"📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| className="font-(family-name:--font-display) text-3xl tracking-tight text-foreground" | |
| className="font-[var(--font-display)] text-3xl tracking-tight text-foreground" |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@content/docs/text/index.mdx` at line 161, The className contains invalid
Tailwind syntax: replace className="font-(family-name:--font-display) text-3xl
tracking-tight text-foreground" with a valid approach — either use a real
Tailwind utility (e.g. className="font-sans text-3xl tracking-tight
text-foreground") or remove the malformed font-... token and apply the CSS
variable via the style prop (e.g. style={{ fontFamily: 'var(--font-display)' }}
alongside className="text-3xl tracking-tight text-foreground"); update the
className string or add the style prop in the same element where that className
appears.
Source: Coding guidelines
| ```tsx | ||
| import RollText from "@/animata/text/roll-text"; | ||
|
|
||
| <RollText text="Hello world" className="font-(family-name:--font-display) text-4xl text-foreground" /> |
There was a problem hiding this comment.
Invalid Tailwind className syntax in documentation examples.
Multiple code examples use font-(family-name:--font-display), which is not valid Tailwind CSS syntax. This will mislead developers copying these examples. As per coding guidelines, use Tailwind CSS only for styling.
🎨 Proposed fixes for all examples
Line 45:
-<RollText text="Hello world" className="font-(family-name:--font-display) text-4xl text-foreground" />
+<RollText text="Hello world" className="font-[var(--font-display)] text-4xl text-foreground" />Line 51:
-<RollText text="Word by word" stagger="word" staggerMs={50} className="text-4xl text-foreground" />
+<RollText text="Word by word" stagger="word" staggerMs={50} className="font-[var(--font-display)] text-4xl text-foreground" />Line 52:
-<RollText text="Letters" stagger="character" staggerMs={32} className="text-4xl text-foreground" />
+<RollText text="Letters" stagger="character" staggerMs={32} className="font-[var(--font-display)] text-4xl text-foreground" />Line 65:
- className="pointer-events-none text-2xl text-foreground"
+ className="pointer-events-none font-[var(--font-display)] text-2xl text-foreground"Also applies to: 51-52, 65-65
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@content/docs/text/roll-text.mdx` at line 45, The examples use an invalid
Tailwind className token "font-(family-name:--font-display)"; update all
RollText usages (e.g., the <RollText ... /> instances) to use a valid Tailwind
font class or an arbitrary value syntax such as "font-[var(--font-display)]" or
the theme-defined class like "font-display" (whichever matches your project
theme). Replace the invalid token in every occurrence (lines referenced in the
review) so the examples show a valid Tailwind className.
Source: Coding guidelines
| export function withOutboundRef(href: string, ref = OUTBOUND_REF) { | ||
| if (!/^https?:\/\//i.test(href)) { | ||
| return href; | ||
| } | ||
|
|
||
| const url = new URL(href); | ||
| if (!url.searchParams.has("ref")) { | ||
| url.searchParams.set("ref", ref); | ||
| } | ||
|
|
||
| return url.toString(); | ||
| } |
There was a problem hiding this comment.
Add error handling for malformed URLs.
The URL constructor on line 10 will throw a TypeError if href passes the regex test but is malformed (e.g., "http://" or "https://invalid"). While siteConfig.links values are well-formed in practice, as a general utility this function should handle edge cases gracefully.
🛡️ Proposed fix with try-catch wrapper
export function withOutboundRef(href: string, ref = OUTBOUND_REF) {
if (!/^https?:\/\//i.test(href)) {
return href;
}
+ try {
const url = new URL(href);
if (!url.searchParams.has("ref")) {
url.searchParams.set("ref", ref);
}
-
return url.toString();
+ } catch {
+ // Return original href if URL parsing fails
+ return href;
+ }
}🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@lib/outbound-ref.ts` around lines 5 - 16, withOutboundRef currently
constructs a URL from href using the URL constructor which can throw for
malformed but regex-passing inputs; wrap the URL(...) call in a try/catch inside
withOutboundRef (referencing function name withOutboundRef and constant
OUTBOUND_REF) and on error simply return the original href (or a safe fallback)
instead of letting the exception propagate, ensuring the function remains a
no-op for invalid URLs while preserving existing behavior for valid ones.
Summary by CodeRabbit
New Features
Documentation
Improvements