Drawing one shape is useful.
Drawing hundreds of shapes automatically is where procedural graphics become truly exciting.
Many backgrounds, wallpapers, game textures, and motion graphics aren't made from large images.
Instead, a small mathematical shape is repeated over and over across the screen.
Because the computer generates every copy, the pattern stays perfectly sharp at every resolution.

From One Shape to Many
Up until now, we've mostly worked in the original UV space.
vec2 uv = vUv;
The UV coordinates range from 0.0 to 1.0.
That gives us one copy of a shape.
To create many copies, we need to repeat the UV coordinates.
Scaling the UV Coordinates
The easiest way is to multiply them.
vec2 uv = vUv * 5.0;
Instead of one square, the coordinate system now covers five copies across the screen.
The values become larger than 1.0.
Now we need a way to bring them back into the familiar 0.0 to 1.0 range.
Using fract()
We already learned about fract() in the first GLSL series.
It keeps only the decimal part of a number.
fract(2.75)
returns
0.75
Apply that idea to the UV coordinates.
uv = fract(uv);
Each section now behaves like its own miniature UV space.
Every tile ranges from 0.0 to 1.0.
Drawing a Circle in Every Tile
Now we can reuse our circle code.
float circle =
1.0 -
step(
0.30,
distance(uv, vec2(0.5))
);
Instead of drawing one circle, GLSL now draws a circle inside every repeated tile.
With only two extra lines of code, we've filled the screen with shapes.
Complete Shader
#ifdef GL_ES
precision mediump float;
#endif
varying vec2 vUv;
void main(){
vec2 uv = fract(vUv * 5.0);
float circle =
1.0 -
step(
0.30,
distance(uv, vec2(0.5))
);
gl_FragColor = vec4(vec3(circle),1.0);
}
Every tile contains an identical procedural circle.
No textures are required.
Changing the Grid Size
Increase the scale.
vUv * 8.0
The pattern becomes much denser.
Decrease it.
vUv * 3.0
Now each shape becomes larger.
One number controls the entire layout.
Repeating Other Shapes
The same technique works for every procedural shape.
Rounded rectangles.
vec2 p = fract(vUv * 6.0) - 0.5;
Stars.
vec2 p = fract(vUv * 4.0) - 0.5;
Hexagons.
vec2 p = fract(vUv * 7.0) - 0.5;
Once a shape works once, it can be repeated forever.
Adding Colour
Each repeated shape can have its own colour.
vec3 color = vec3(
uv.x,
uv.y,
1.0 - uv.x
);
color *= circle;
The pattern now changes colour across the screen while keeping the same repeated geometry.
Animating the Pattern
Move the UV coordinates over time.
uv.x += uTime * 0.2;
Or move them vertically.
uv.y += uTime * 0.2;
Because fract() wraps the coordinates automatically, the pattern scrolls forever.
There are no visible seams.
Rotating Every Tile
Every repeated tile can also rotate.
Although rotation requires a small amount of matrix mathematics, the same transformation can be applied to every tile independently.
This creates animated backgrounds often seen in games and music visualizers.
We'll explore rotations in a future tutorial.
Where Are Procedural Patterns Used?
Procedural patterns appear almost everywhere.
- Background textures.
- User interface designs.
- Motion graphics.
- Wallpapers.
- Loading screens.
- Game environments.
- Sci fi displays.
- Decorative animations.
- Audio visualizers.
- Abstract artwork.
Many of these effects begin with nothing more than repeated UV coordinates.
Try These Experiments
Repeat circles.
Repeat stars.
Repeat rounded rectangles.
Create a larger grid.
Create a smaller grid.
Scroll the pattern.
Change the colours.
Try combining several procedural shapes together.
A Small Challenge
Can you create these effects?
- A tiled pattern of glowing circles.
- A repeating field of stars.
- A colourful procedural wallpaper.
- A scrolling background.
- A simple game texture made entirely with mathematics.
Every challenge combines ideas from both GLSL series.
What We Learned
Today we learned that procedural shapes become much more powerful when they are repeated across the screen.
Using fract() with scaled UV coordinates, we transformed a single shape into an entire procedural pattern.
This simple technique is one of the foundations of procedural textures, animated backgrounds, and generative art.
Posted Using INLEO