public Flower( )
{
int idx = -1;
int last_idx = -1;
int petal_size = PETAL_MIN + rand() % PETAL_VAR;
int size = petal_size * 8;
int n_groups = rand() % 3 + 1;
this.ctex = new CairoTexture((uint)size, (uint)size);
// the using statement make sure the cr is disposed at the end,
// otherwise we get no bling
using (Cairo.Context cr = this.ctex.Create())
{
cr.Tolerance = 0.1;
// Clear
cr.Operator = Operator.Clear;
cr.Paint();
cr.Operator = Operator.Over;
cr.Translate(size / 2, size / 2);
// petals
for (int i = 0; i < n_groups; i++)
{
int n_petals = rand() % 5 + 4;
cr.Save();
cr.Rotate(rand() % 6);
do
{
idx = (rand() % (colors.Length / 3)) * 3;
} while (idx == last_idx);
cr.SetSourceRGBA(colors[idx], colors[idx + 1], colors[idx + 2], 0.5);
int pm1 = rand() % 20;
int pm2 = rand() % 4;
for (int j = 0; j < n_petals; j++)
{
cr.Save();
cr.Rotate(((2 * Math.PI) / n_petals) * j);
cr.NewPath();
cr.MoveTo(0, 0);
cr.RelCurveTo(petal_size, petal_size, (pm2 + 2) * petal_size,
petal_size, (2 * petal_size) + pm1, 0);
cr.RelCurveTo(0 + (pm2 * petal_size), -petal_size, -petal_size,
-petal_size, -((2 * petal_size) + pm1), 0);
cr.ClosePath();
cr.Fill();
cr.Restore();
}
petal_size -= rand() % (size / 8);
cr.Restore();
}
// flower center
do
{
idx = (rand() % (colors.Length / 4 / 3)) * 3;
} while (idx == last_idx);
if (petal_size < 0)
{
petal_size = rand() % 10;
}
cr.SetSourceRGBA(colors[idx], colors[idx + 1], colors[idx + 2], 0.5);
cr.Arc(0, 0, petal_size, 0, Math.PI * 2);
cr.Fill();
}
}