Skip to content

Uniform sampling of a triangle by dividing it into smaller parts?

An answer to this question on Stack Overflow.

Question

To sample a triangle ABC uniformly, I can use the following formula:

P = (1 - sqrt(r1)) * A + (sqrt(r1)(1 - r2)) * B + (r2sqrt(r1)) * C

where r1 and r2 are random numbers between 0 and 1. The more samples you take, the better. But what if I want to get a better distribution, while keeping then number of samples low?

For example if I had a square, I can implicitly divide it into an N x N grid and generate a random sample inside the smaller grid squares. Like this:

float u = (x + rnd(seed)) / width;
float v = (y + rnd(seed)) / height;

The point is I force the sampling to cover the entire grid at a lower sample resolution.

How can I achieve this with a triangle? The only way I can think of is to explicitly subdivide it into a number of triangles using a library like Triangle. But is there a way to do this implicitly like with a square, without having to actually divide the triangle?

Answer

I'd suggest using Poisson disk sampling (short academic paper link, pretty visualization link, wiki link, code link) to generate a configuration within the bounding box of your triangle and then cropping to the area bounded by the triangle.

I suggest starting with the short academic paper. The principle at work here is pretty easy to understand. There are many variations of this idea floating around out there, so get a handle on it and find the one that works for you.

Field generated with Poisson disk sampling