A simple screen saver component inspired by the classic DVD logo animation.
npx shadcn@latest add @refinery/dvd-screensaver| Name | Type | Description |
|---|---|---|
| text | string | Main logo text. |
| subText | string | Secondary label below the logo. |
| speed | number | Movement speed multiplier for the bounce. |
| className | string | Additional CSS classes for the wrapper. |
The main logic to make the logo hit around the borders is based on position + velocity. The logo has (x,y) coordinates and a (vx, vy) velocity vector. Every animation frame, the position is updated by adding the velocity. When the logo hits a boundary (like the edge of the container), we reverse the corresponding velocity component to make it bounce back (vx = -vx & vy = -vy). A corner hit happens when both 'vx' and 'vy' flip in the same frame. To make it rare, randomize the velocity after each bounce. We will hold x, y, vx and vy in useRef since we want to update them without causing re-renders on every frame, and we will update them inside a 'requestAnimationFrame' loop and apply the position via 'transform: translate()' directly on DOM node for performance. The color change on bounce is done by keeping an index of current color and updating it on each bounce. To add a little extra feedback on bounces, we trigger a quick 'cornerFlash' state when a corner hit is detected, which shows a brief flash effect using an absolutely positioned div with a fade-out transition. The component takes, 'text', 'subText', 'speed' and 'className' as props to allow some customization. The 'speed' prop controls how fast the logo moves by scaling the velocity vector. To make it look great, add your brand-name as text and one word about your brand as subText. The animation loop is paused when the user clicks on the container, and resumes on the next click.