Creating natural variation with the CSS random() function

Post on X
Copy URL
Share

The CSS random() function lets you work with random values using CSS alone. This new function, available starting with Safari 26.2, can introduce natural variation in element sizes, angles, animation start times, and more.

Previously, creating similar effects required assigning individual values with :nth-child(), calculating values from the order of elements with sibling-index(), or passing values from JavaScript’s Math.random(). With random(), you can write the desired ranges directly in CSS, such as “angles from 0 to 1turn” or “animation-delay from 0 to 600ms”.

This article introduces some of the visual effects you can create with the random() function.

Note: Please view the demos in this article in Safari 26.2 or later.

The basics of random()

The random() function returns a random value within a specified range. Since it is used as a CSS value, you can work directly with units appropriate to each property, including lengths, angles, times, and percentages.

The following example selects a value between 100px and 300px. When the same style is applied to multiple elements, each element gets its own random value.

.box {
  width: random(100px, 300px);
}

The third argument lets you specify the interval between possible values.

.box {
  width: random(100px, 300px, 50px);
}

In this example, the selected value is one of 100px, 150px, 200px, 250px, or 300px. This is useful when you want variation in fixed increments rather than a continuous range of values.

Demo 1: rebuilding a Like button with random()

Our earlier article, “SVG animations for Modern UI - CSS, SMIL, Web Animations API, MotionPath and Lottie”, introduced a Like button that sends particles outward around a heart when clicked. Here, we will recreate this effect with the random() function.

Making the particles fly in slightly different directions each time adds natural variation to the click animation. In this demo, the values that vary between particles are defined as CSS custom properties.

The following values are randomized:

  • Direction of travel
  • Travel distance
  • Animation duration
  • Start time
  • Color
.particle {
  /* Randomize the direction in which each particle travels */
  --particle-angle: random(0turn, 1turn);
  transform: rotate(var(--particle-angle));

  circle {
    --particle-distance: random(220px, 290px);
    --particle-duration: random(1200ms, 1800ms);
    --particle-delay: random(0ms, 160ms);

    /* Randomize hue, saturation, and lightness for different colors each time */
    fill: hsl(
      random(145deg, 335deg) random(55%, 85%)
        random(68%, 82%)
    );
  }
}

.is-playing {
  .particle {
    circle {
      /* Vary the duration and start time for each particle */
      animation: particle var(--particle-duration) ease-out
        var(--particle-delay) forwards;
    }
  }
}

@keyframes particle {
  0%,
  25% {
    opacity: 0;
    transform: translateX(130px);
  }

  30%,
  85% {
    opacity: 1;
  }

  100% {
    opacity: 0;
    /* Vary the travel distance for each particle */
    transform: translateX(var(--particle-distance));
  }
}

Values determined by random() remain unchanged for as long as the element exists, so the demo uses JavaScript to recreate the particle elements.

Demo 1 manages each randomized value separately in the CSS. This makes it easy to see which values are randomized and the range used for each.

Compare this with the implementation from the earlier article. Replacing the calculations for angles and destinations with random() makes the intent of these values easier to understand from the CSS.

Demo 2: randomizing hover animation timing for each character

The random() function also makes it easy to create a hover effect in which each character changes color at a different time. Varying animation-delay for each character creates natural timing differences within the same animation.

Demo 2 uses random() to set animation-delay on hover. Even though the same CSS is applied to every character, a separate delay is selected for each one.

.headline {
  &:hover {
    .char {
      /* Assign a different animation-delay to each character */
      animation: flash 500ms ease random(0ms, 600ms);
    }
  }
}

@keyframes flash {
  50% {
    color: #7c71f6;
  }
}

Demo 3: randomizing star positions, sizes, and twinkling

The random() function is particularly effective for decorations such as starry skies, which look more natural when they are irregular. Each page reload can display a sky with different star positions, sizes, and twinkling patterns.

The following code uses a single .star class to define each star’s position, size, glow intensity, twinkle duration, and start time.

.sky {
  .star {
    position: absolute;
    /* Vary the position, size, and glow intensity for each star */
    left: random(2%, 98%);
    top: random(3%, 96%);
    width: random(2px, 7px);
    aspect-ratio: 1;
    background: #fff;
    border-radius: 50%;
    box-shadow: 0 0 random(8px, 28px) rgb(184 176 255 / 95%);
    opacity: 0.18;
    animation: twinkle random(600ms, 1.8s) ease-in-out
      random(-1.8s, 0s) infinite alternate;
  }
}

@keyframes twinkle {
  to {
    opacity: 1;
    transform: scale(2.1);
  }
}

When should you use the random() function?

The random() function is well suited to creating visual variation rather than changing the information itself. Examples include confetti or petals scattered across a background, bubbles, particles, and animal footprints: decorations that would look unnatural if identical shapes were arranged in a regular pattern.

Small variations in the following values can make decorations and effects feel more natural:

  • Position
  • Angle
  • Size
  • Opacity
  • Travel distance
  • Animation duration
  • Animation start time

However, applying randomness to values that affect reading order or usability can make content harder to understand. For example, changing the order of an article list every time makes it harder to find a specific article. Varying the size of body text or main images makes line wrapping and spacing inconsistent, which can reduce readability. The positions and colors of buttons for important actions, such as purchasing, submitting, or deleting, should not change randomly either. Doing so can make the buttons harder to find and lead to unintended actions.

Browser support

The CSS random() function is available in Safari 26.2 and later.

Reference: Can I use…

Summary

The CSS random() function lets you assign different values to each element simply by specifying a range. Deliberately adding irregularity to decorations and animations creates natural movement and variation that uniform values cannot produce.

It is great to have more creative options with CSS alone. Try applying random() to a variety of visual effects!

Find ICS MEDIA articles more easily on Google

Add ICS MEDIA as a preferred source to see our articles more often in Top Stories and AI Search.

Add as a preferred source on Google
Share on social media
Your shares help us keep the site running.
Post on X
Copy URL
Share
IWAMA Hina

Front-end engineer. Studied graphic design as a student. Loves reading and cute things.

Articles by this staff