Canvas Reveal Effect
- Source
- Aceternity UI ↗
- Author
- Aceternity UI
- Licence
- Aceternity UI licence (free component)
Loading…
Hovering a card floods it with a WebGL dot-matrix that blooms outward.
Code
"use client";
import React from "react";
import { AnimatePresence, motion } from "motion/react";
import { Fit } from "./_fit";
import { CanvasRevealEffect } from "@/lab/aceternity/ui/canvas-reveal-effect";
export default function CanvasRevealEffectDemo() {
return (
<Fit width={1080} height={560}>
<div className="h-full flex flex-row items-center justify-center bg-white dark:bg-black w-full gap-4 mx-auto px-8">
<Card title="Sheetal is Nisha" icon={<AceternityIcon />}>
<CanvasRevealEffect
animationSpeed={5.1}
containerClassName="bg-emerald-900"
/>
</Card>
<Card title="Nisha is Munni" icon={<AceternityIcon />}>
<CanvasRevealEffect
animationSpeed={3}
containerClassName="bg-black"
colors={[
[236, 72, 153],
[232, 121, 249],
]}
dotSize={2}
/>
{/* Radial gradient for the cute fade */}
<div className="absolute inset-0 [mask-image:radial-gradient(400px_at_center,white,transparent)] bg-black/50 dark:bg-black/90" />
</Card>
<Card title="Munni is Aditi" icon={<AceternityIcon />}>
<CanvasRevealEffect
animationSpeed={3}
containerClassName="bg-sky-600"
colors={[[125, 211, 252]]}
/>
</Card>
</div>
</Fit>
);
}
const Card = ({
title,
icon,
children,
}: {
title: string;
icon: React.ReactNode;
children?: React.ReactNode;
}) => {
const [hovered, setHovered] = React.useState(false);
return (
<div
onMouseEnter={() => setHovered(true)}
onMouseLeave={() => setHovered(false)}
className="border border-black/[0.2] group/canvas-card flex items-center justify-center dark:border-white/[0.2] max-w-sm w-full mx-auto p-4 relative h-[30rem]"
>
<Icon className="absolute h-6 w-6 -top-3 -left-3 dark:text-white text-black" />
<Icon className="absolute h-6 w-6 -bottom-3 -left-3 dark:text-white text-black" />
<Icon className="absolute h-6 w-6 -top-3 -right-3 dark:text-white text-black" />
<Icon className="absolute h-6 w-6 -bottom-3 -right-3 dark:text-white text-black" />
<AnimatePresence>
{hovered && (
<motion.div
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
className="h-full w-full absolute inset-0"
>
{children}
</motion.div>
)}
</AnimatePresence>
<div className="relative z-20">
<div className="text-center group-hover/canvas-card:-translate-y-4 group-hover/canvas-card:opacity-0 transition duration-200 w-full mx-auto flex items-center justify-center">
{icon}
</div>
<h2 className="dark:text-white text-xl opacity-0 group-hover/canvas-card:opacity-100 relative z-10 text-black mt-4 font-bold group-hover/canvas-card:text-white group-hover/canvas-card:-translate-y-2 transition duration-200">
{title}
</h2>
</div>
</div>
);
};
const AceternityIcon = () => {
return (
<svg
width="66"
height="65"
viewBox="0 0 66 65"
fill="none"
xmlns="http://www.w3.org/2000/svg"
className="h-10 w-10 text-black dark:text-white group-hover/canvas-card:text-white "
>
<path
d="M8 8.05571C8 8.05571 54.9009 18.1782 57.8687 30.062C60.8365 41.9458 9.05432 57.4696 9.05432 57.4696"
stroke="currentColor"
strokeWidth="15"
strokeMiterlimit="3.86874"
strokeLinecap="round"
style={{ mixBlendMode: "darken" }}
/>
</svg>
);
};
const Icon = ({ className, ...rest }: React.SVGProps<SVGSVGElement>) => {
return (
<svg
xmlns="http://www.w3.org/2000/svg"
fill="none"
viewBox="0 0 24 24"
strokeWidth="1.5"
stroke="currentColor"
className={className}
{...rest}
>
<path strokeLinecap="round" strokeLinejoin="round" d="M12 6v12m6-6H6" />
</svg>
);
};
Prompt
Build "Canvas Reveal Effect", a canvas animation. What it does: Hovering a card floods it with a WebGL dot-matrix that blooms outward. Write it as a single self-contained React component in TypeScript that fills its parent (w-full h-full), styled with Tailwind CSS, using @react-three/fiber, motion, three. Technique: WebGL, the Motion library, inline SVG. It sits on a dark background, in a 16:10 frame. Respect prefers-reduced-motion with a still state, pause work when the element is off screen, and keep it accessible. Original: https://ui.aceternity.com/components/canvas-reveal-effect (Aceternity UI, Aceternity UI licence (free component)).