Blur Vignette Effect

Apple Vision Pro like Blur Effect, we can use it in images, video, card etc. let's make something great with this component

Read Docs to know more Blur Vignette

Video

Card

grid

UiLayout

Lorem, ipsum dolor sit amet consectetur adipisicing elit. Debitis, quaerat ab? Rerum facilis dignissimos voluptatum!

grid

UiLayout

Lorem, ipsum dolor sit amet consectetur adipisicing elit. Debitis, quaerat ab? Rerum facilis dignissimos voluptatum!

Image

grid
grid

Usage

blur-vignette.tsx
import React, { createContext, useContext } from 'react'
import { cn } from '@/lib/utils'
interface BlurVignetteContextProps {
  radius?: string
  inset?: string
  transitionLength?: string
  blur?: string
}
 
const BlurVignetteContext = createContext<BlurVignetteContextProps>({
  radius: '24px',
  inset: '20px',
  transitionLength: '44px',
  blur: '6px',
})
 
export const useBlurVignetteContext = () => useContext(BlurVignetteContext)
 
interface BlurVignetteProps {
  classname?: string
  children: React.ReactNode
  radius?: string
  inset?: string
  transitionLength?: string
  blur?: string
  blurclassname?: string
}
 
export const BlurVignette: React.FC<BlurVignetteProps> = ({
  classname,
  children,
  radius = '24px',
  inset = '20px',
  transitionLength = '44px',
  blur = '6px',
}) => {
  return (
    <BlurVignetteContext.Provider
      value={{ radius, inset, transitionLength, blur }}
    >
      <div
        className={cn('relative aspect-square overflow-hidden', classname)}
        style={{ borderRadius: radius }}
      >
        {children}
      </div>
    </BlurVignetteContext.Provider>
  )
}
interface BlurVignetteArticleProps {
  children?: React.ReactNode
  classname?: string
}
 
export const BlurVignetteArticle: React.FC<BlurVignetteArticleProps> = ({
  children,
  classname,
}) => {
  const { radius, inset, transitionLength, blur } = useBlurVignetteContext()
 
  return (
    <div
      className={cn(
        'blur-vignette bottom-0 left-0 w-full h-full z-[1]',
        classname
      )}
      style={
        {
          '--radius': radius,
          '--inset': inset,
          '--transition-length': transitionLength,
          '--blur': blur,
        } as React.CSSProperties
      }
    >
      {children}
    </div>
  )
}
 
global.css
@layer utilities {
  .blur-vignette {
    position: absolute;
    inset: 0;
    border-radius: var(--radius);
    -webkit-backdrop-filter: blur(var(--blur));
    backdrop-filter: blur(var(--blur));
    --r: max(var(--transition-length), calc(var(--radius) - var(--inset)));
    --corner-size: calc(var(--r) + var(--inset)) calc(var(--r) + var(--inset));
    --corner-gradient: transparent 0px, transparent calc(var(--r) - var(--transition-length)),
      black var(--r);
    --fill-gradient: black, black var(--inset), transparent calc(var(--inset) +
            var(--transition-length)),
      transparent calc(100% - var(--transition-length) - var(--inset)), black
        calc(100% - var(--inset));
    --fill-narrow-size: calc(100% - (var(--inset) + var(--r)) * 2);
    --fill-farther-position: calc(var(--inset) + var(--r));
    -webkit-mask-image: linear-gradient(to right, var(--fill-gradient)),
      linear-gradient(to bottom, var(--fill-gradient)), radial-gradient(
        at bottom right,
        var(--corner-gradient)
      ), radial-gradient(at bottom left, var(--corner-gradient)),
      radial-gradient(at top left, var(--corner-gradient)), radial-gradient(at
          top right, var(--corner-gradient));
    -webkit-mask-size:
      100% var(--fill-narrow-size),
      var(--fill-narrow-size) 100%,
      var(--corner-size),
      var(--corner-size),
      var(--corner-size),
      var(--corner-size);
    -webkit-mask-position:
      0 var(--fill-farther-position),
      var(--fill-farther-position) 0,
      0 0,
      100% 0,
      100% 100%,
      0 100%;
    -webkit-mask-repeat: no-repeat;
  }
}

Props

PropTypeDefaultDescription
classnamestringOptional CSS class for styling the main vignette container.
childrenReact.ReactNodeThe content to display inside the vignette effect.
radiusstring24pxThe radius for the vignette effect.
insetstring20pxThe inset value for the vignette effect.
transitionLengthstring44pxThe length of the transition effect applied to the vignette.
blurstring6pxThe blur amount for the vignette effect.
blurclassnamestringOptional CSS class for styling the blur effect container.