AI CSS Animations

Lens Flare Background

A bright light in the corner throws a horizontal streak and a line of colored ghosts across the frame, and they swing through the center as the light drifts, like a camera panning past the sun.

Also known as: lens flare css animation, anamorphic flare background, cinematic light flare css.

HTML

<div class="bgx-lens-flare" aria-hidden="true">
  <div class="bgx-lens-flare-rig"><span></span><span></span><span></span><span></span><span></span><span></span></div>
</div>

CSS

.bgx-lens-flare {
  --c: var(--bgx-color, #3b82f6);
  font-size: var(--bgx-size, 16px);
  position: absolute;
  inset: 0;
  overflow: hidden;
  background: radial-gradient(ellipse 90% 90% at 20% 15%, oklch(from var(--c) 0.22 0.05 calc(h + 0)), #040509 70%);
  isolation: isolate;
}
.bgx-lens-flare-rig {
  position: absolute;
  left: 50%;
  top: 50%;
  animation: bgx-lens-flare-swing 8s cubic-bezier(0.45, 0, 0.55, 1) -2s infinite alternate;
}
.bgx-lens-flare-rig span {
  position: absolute;
  left: var(--at);
  width: var(--size);
  aspect-ratio: 1;
  translate: -50% -50%;
  border-radius: 50%;
  background: var(--paint);
  mix-blend-mode: screen;
}
.bgx-lens-flare-rig span:nth-child(1) {
  --at: -13em;
  --size: 9em;
  --paint: radial-gradient(closest-side, #fff 0 8%, oklch(from var(--c) 0.95 0.06 calc(h + 0) / 0.9) 16%, oklch(from var(--c) 0.75 0.16 calc(h + 0) / 0.35) 45%, transparent);
  animation: bgx-lens-flare-shimmer 2.6s ease-in-out infinite alternate;
}
.bgx-lens-flare-rig span:nth-child(1)::after {
  content: "";
  position: absolute;
  left: 50%;
  top: 50%;
  width: 46em;
  height: 0.5em;
  translate: -50% -50%;
  border-radius: 50%;
  background: radial-gradient(closest-side, #fff, oklch(from var(--c) 0.8 0.14 calc(h + 0) / 0.6) 40%, transparent);
  animation: bgx-lens-flare-level 8s cubic-bezier(0.45, 0, 0.55, 1) -2s infinite alternate;
}
.bgx-lens-flare-rig span:nth-child(2) { --at: 3em; --size: 1.6em; --paint: radial-gradient(closest-side, oklch(from var(--c) 0.85 0.12 calc(h + 60) / 0.55), transparent); }
.bgx-lens-flare-rig span:nth-child(3) { --at: 6.5em; --size: 3.4em; --paint: radial-gradient(closest-side, transparent 70%, oklch(from var(--c) 0.8 0.14 calc(h - 60) / 0.5) 88%, transparent); }
.bgx-lens-flare-rig span:nth-child(4) { --at: 9em; --size: 2.2em; --paint: oklch(from var(--c) 0.85 0.12 calc(h - 30) / 0.3); border-radius: 0; clip-path: polygon(25% 5%, 75% 5%, 100% 50%, 75% 95%, 25% 95%, 0 50%); }
.bgx-lens-flare-rig span:nth-child(5) { --at: 12em; --size: 5em; --paint: radial-gradient(closest-side, oklch(from var(--c) 0.75 0.15 calc(h + 30) / 0.18) 60%, oklch(from var(--c) 0.8 0.14 calc(h + 30) / 0.35) 90%, transparent); }
.bgx-lens-flare-rig span:nth-child(6) { --at: 17em; --size: 7.5em; --paint: radial-gradient(closest-side, transparent 60%, oklch(from var(--c) 0.85 0.1 calc(h - 110) / 0.25) 85%, transparent); }
@keyframes bgx-lens-flare-swing {
  from { transform: rotate(12deg); }
  to   { transform: rotate(30deg); }
}
@keyframes bgx-lens-flare-level {
  from { transform: rotate(-12deg); }
  to   { transform: rotate(-30deg); }
}
@keyframes bgx-lens-flare-shimmer {
  from { opacity: 0.85; transform: scale(0.94); }
  to   { opacity: 1; transform: scale(1.05); }
}

@media (prefers-reduced-motion: reduce) {
  .bgx-lens-flare, .bgx-lens-flare *, .bgx-lens-flare::before, .bgx-lens-flare::after, .bgx-lens-flare *::before, .bgx-lens-flare *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
  }
}

Customizing this snippet

  • Color: set --bgx-color on the element or a parent. Currently previewing #3b82f6.
  • Pattern scale: set --bgx-size. Every other dimension is in em, so the whole thing scales together. Currently previewing 16px.
  • Speed: change the duration on the transition or animation shorthand. Staggered delays are relative, so they keep their rhythm.
  • Reduced motion: the rule at the end of the CSS turns the motion off for people who asked their OS for less of it. Keep it.

Similar animated backgrounds