Skip to content

shadcn.io is an independent project built on shadcn/ui

Buttons

Pro

Shine Button for Svelte

A diagonal band of light sweeps across the button once when the pointer arrives. For Svelte with Ark UI, when a call to action deserves a little polish.

UI library: Ark UI

When the pointer arrives, the button takes keyboard focus or it's pressed, a diagonal band of light sweeps across it once, like a gleam on a polished surface. Leave and come back, and it sweeps again.

Use it on a pricing page's Upgrade button or a hero's main action, where a small reward for hovering fits. It's subtle enough for a serious product, and it doesn't loop. For light that keeps moving on its own, use the Shimmer Button. It wraps the Button, so every variant and size works. The sweep is a CSS keyframe animation the install adds to your stylesheet, with no JavaScript and no animation library; when the system asks for reduced motion, the light fades in where it stands instead of moving.

Preview width

Installation

Part of Pro
Pro unlocks the code and one-line install of every Pro button and text effect, plus the MCP for your AI editor.
Have Pro already? Sign in to open it.Opens here as soon as you're Pro.

Usage

<script lang="ts">
import { ShineButton } from "@/components/ui/shine-button";
</script>
<ShineButton>Upgrade now</ShineButton>

Demos

Color

shineColor takes any CSS color. By default the light is the label's color at a little over a third of its strength, which reads on every variant. Here an outline button shines in the primary color, and a filled one gets a brighter gleam from a stronger mix of its label color.

Preview width

Duration

duration is how long one sweep takes to cross the button, in milliseconds; the default is 700. A quick sweep suits a small button, and a slow one a large hero button.

Preview width

Accessibility

The light is decoration and hidden from assistive tech: the button is announced and activated as any Button. It sweeps on keyboard focus as well as on hover, so people who tab through the page see it too.

Tab
Move focus to the button; the light sweeps across.
Enter
Activate the button.
Space
Activate the button; the light sweeps while it's held.

FAQ

How do I make the shine stronger?

Pass a stronger color to shineColor, such as color-mix(in oklch, var(--primary-foreground) 70%, transparent). The Color demo does that on its second button.

Why doesn't the light sweep back when the pointer leaves?

On purpose: the sweep is an animation that runs while the hover lasts and ends with the band out of sight, and when the pointer leaves the band goes back unseen. So it only ever sweeps one way, the way a reflection does.

How do I change the speed?

Set duration in milliseconds, 700 by default, as in the Duration demo. It's written to a CSS variable on the button's light, --shine-button-duration, which the keyframes read.

Can it shine on a loop?

No, it sweeps once per hover or focus. For light that keeps moving on its own, use the Shimmer Button.

Does it shine on touch screens?

Touch screens have no hover, so the light sweeps while a finger presses the button: a long press shows the whole sweep, a quick tap only its start. The button works the same either way.

Which way does the light move in a right-to-left layout?

Right to left, the direction the page reads. In a left-to-right layout it moves left to right.

What happens with reduced motion?

The band doesn't move: it fades in across the middle of the button on hover, focus or a press, and fades out when they end.

API Reference

ShineButton

PropType
children?Snippet

The label, above the light.

clickEffect?boolean

Apply a click effect to the button.

Default
true
duration?number

How long one sweep of light takes to cross the button, in milliseconds.

Default
700
isLoading?boolean

Show a loading indicator.

Default
false
shineColor?string

The light's color, any CSS color. By default it's the label's color at a little over a third of its strength, which reads on every variant.

asChild?Snippet<[PropsFn]>

Render your own element: a snippet that gets the part's props to spread on it.

Type
Snippet<[PropsFn]>
class?string

Merged with the part's classes.

CSS variableType
--shine-button-colorstring

The light's color.

--shine-button-durationstring

One sweep across the button (700ms).