Cartoon flowers are another type of graphic that can be procedurally generated. Many flowers have the same graphical structure : a central part (kernel) and a repeating structure ("petal") that is rotated around this central part.
![]() |
![]() |
![]() |
The petal itself has horizontal symmetry :

This means that in order to generate a random flower, it is enough to generate half of a petal, then construct the other half symmetrically and finally rotate it a number of times around a central location:

We want the petal to vary more or less gently, without sharp edges and without huge variations. To do that, we'll construct it as a series of connected quads. We'll start with several basic parameters:
With these parameters, the algorithm proceeds as follows:

The above method can be implemented in a few lines using the following Java code:
GeneralPath petal = new GeneralPath();
int flowerSize = 128;
int upsize=flowerSize/5;
int aperture = rnd.nextInt(5)+5;
int cp = rnd.nextInt(5)+3;
int[] fx = new int[2*cp+3];
int[] fy = new int[2*cp+3];
petal.moveTo(flowerSize/2-aperture,upsize+flowerSize);
fx[2*cp+2] = flowerSize/2-aperture;
fy[2*cp+2] = upsize+flowerSize;
for (int i = cp; i >= 0; i--) {
fx[2*i] = rnd.nextInt(flowerSize/2);
fy[2*i] = upsize+flowerSize/cp*i;
fx[2*i+1] = rnd.nextInt(flowerSize/2);
fy[2*i+1] = upsize+fy[2*i]+rnd.nextInt(flowerSize/cp*(i+1)-flowerSize/cp*i);
petal.quadTo(fx[2*i+1],fy[2*i+1],fx[2*i],fy[2*i]);
}
// Connecting quad
petal.quadTo(flowerSize/2,upsize+rnd.nextInt(upsize)-2*upsize,flowerSize-fx[0],upsize);
// Compute reflected points
for (int i = 0; i <= cp; i++) {
petal.quadTo(flowerSize-fx[2*i+1],fy[2*i+1],flowerSize-fx[2*i+2],fy[2*i+2]);
}
petal.closePath();
Once we have this path, we can proceed to make the flower by rotating the filled path around a central point located at (size/2, size). We can parametrize this process by deciding how many petals we want. Since we generally want all petals spread along the full circumferece, the rotation angle for each one will be 360/petals. Also, it helps if we fill each petal not with a solid color but a gradient oriented diagonally.
Here's the part of the code that builds the flower:
int kernelSize = 20;
int petals = 10;
Color flowerColor = new Color(0x00AAFF);
Color kernelColor = new Color(0x00FFFF);
BufferedImage flowerImage =
new BufferedImage(2*flowerSize,2*flowerSize,BufferedImage.TYPE_INT_ARGB);
Graphics2D gFlower = flowerImage.createGraphics();
double angle = 2*Math.PI/petals;
gFlower.translate(flowerSize/2,0);
// Draw the petals
for (int i = 0; i <= petals; i++) {
gFlower.setPaint(
new GradientPaint(0,0,flowerColor,flowerSize,flowerSize,new Color(0)));
gFlower.fill(petal);
gFlower.setColor(new Color(0));
gFlower.draw(petal);
gFlower.rotate(-angle,flowerSize/2,flowerSize);
}
// Draw the kernel
if (kernelSize != 0) {
gFlower = flowerImage.createGraphics();
gFlower.setColor(new Color(0));
gFlower.fillOval( flowerSize-kernelSize,flowerSize-kernelSize,
2*kernelSize,2*kernelSize);
gFlower.setColor(kernelColor);
gFlower.fillOval( flowerSize-kernelSize+1,flowerSize-kernelSize+1,
2*kernelSize-2,2*kernelSize-2);
}
Here are some results that you can obtain with the above two snippets combined:
![]() |
![]() |
![]() |
The FlowerTutorial.java application included contains the above code and is a fully-working application.
|
FlowerTutorial.java ( 3 Kb ) |