How to draw a perfect flower

I tried to draw a zinnia, but the first petal is always at the bottom and cannot form a perfect loop with the last petal. How can I modify the code?

float r=400;
float kuan=200;
float chang=400;

void setup() {
  fullScreen();
  background(#82A584);
  stroke(#D8A2AA);
  strokeWeight(6);
  fill(#FA677D);
}

void draw() {
  translate(width/2, height/2);
  for (int i=4; i>0; i--) {
    scale(0.8);
    for (int j = 0; j<18; j++) {
      ellipse(0, -r, kuan, chang);
      rotate(TWO_PI/18);
    }
  }
}

Welcome to the forum

Not sure what you mean by this :thinking:

I modified your code to get this image. Is this what you want to achieve?

1 Like

Hello @Ruka,

This may help:

image

:)

This is not the image I want to achieve, but thank you for you reply. :smile:

This is the image I want. Thank you for you reply. I will try to complete the code. :smile:

Now, I have two methods to solve the overlapping issue.

The first method is using the PGraphics.

PGraphics pg2;
int numCircles = 18;
float r=400;
float kuan=200;
float chang=400;

void setup() {
  fullScreen();
  noLoop();
  pg2 = createGraphics(width, height);
  background(#82A584);
}

void draw() {
  // draw the picture
  pg2.beginDraw();
  pg2.translate(width/2, height/2);
  pg2.fill(#FA677D);
  pg2.strokeWeight(6);
  pg2.stroke(#D8A2AA);
  for (int i = 0; i < numCircles; i++) {
    pg2.rotate(TWO_PI/numCircles);
    pg2.ellipse(0, r, kuan, chang);
  }
  pg2.endDraw();

  // cut the picture
  PImage img2 = pg2.get(width/2, 0, width, height);

  // paste the picture
  translate(width/2, height/2);
  for (int i = 4; i>0; i-=1) {
    scale(0.8);
    image(img2, 0, -height/2);
    rotate(PI);
    image(img2, 0, -height/2);
  }
  line(-width*2,0,width*2,0);
  line(0,-height*2,0,height*2);
  save("zinnia_PGraphics.png");
}


The result is good, but the code itself is not a loop.

The second one is using the P3D.

int pedalNum = 18;
float r=400;
float kuan=400;
float chang=400;

void setup() {
  fullScreen(P3D);
  noLoop();
  background(#82A584);
  stroke(#D8A2AA);
  strokeWeight(6);
  fill(#FA677D);
}

void draw() {
  translate(width/2, height/2, 0);
  for (int i = 4; i>0; i--) {
    scale(0.7);
    translate(0,0,400);
    for (int j = 0; j<pedalNum; j++) {
      push();   
      rotateZ(TWO_PI/pedalNum*j);
      rotateY(PI/3);
      ellipse(0, -r, kuan, chang);
      pop();
    }
  }
  translate(0,0,200);
  stroke(120);
  line(-width,0,width,0);
  line(0,-height,0,height);
  save("zinnia_P3D.png");
}


The code is a correct loop, but pedals are slanted. I don’t know the reason why the pedal is slanted and how to eliminate the slant. Can someone help to improve the code?

1 Like

See references:
ortho() / Reference / Processing.org
perspective() / Reference / Processing.org

They are still slanted just the view has changed.

You may want to look at the tutorials for this and work on translation and rotations in 3D.

Try a slight angle so they overlap.

Hints and tips:

void draw() {
  translate(width/2, height/2, 0);
  
  rotateX(PI/2); //Side view!
  
  push();
  for (int i = 4; i>0; i--) {
    scale(0.7);
    //translate(0, 0, 40);
    for (int j = 0; j<pedalNum; j++) {
      push();   
      rotateZ(TWO_PI/pedalNum*j);
      rotateY(PI/3);                //This seems a bit too much!
      ellipse(0, -r, kuan, chang);
      pop();
    }
  }
  pop(); 
}

:)

1 Like

Thank you for you patient and inspirational reply. :smile:
I finally figured out that it is the default perspective projection leads to the slant. Using the orthographic projection ortho() will eliminate the slant.
Parameters of the pedal and rotation angle have also been modified.

int pedalNum = 18;
int layer = 4;
float radius = 400;
float pedalWidth = 200;
float pedalHeight = 400;

void setup() {
  fullScreen(P3D);
  background(#82A584);
  stroke(#D8A2AA);
  strokeWeight(6);
  fill(#FA677D);
  ortho(); // eliminate the slant
  noLoop();
}

void draw() {
  translate(width/2, height/2, 0);
  for (int i = layer; i>0; i--) {
    scale(0.7);
    translate(0, 0, 400);
    for (int j = 0; j<pedalNum; j++) {
      drawPedal(TWO_PI/pedalNum*j);
    }
  }
}

void drawPedal(float angle) {
  push();
  rotateZ(angle);
  rotateY(radians(3));
  ellipse(0, -radius, pedalWidth, pedalHeight);
  pop();
}

1 Like

Consider drawing multiple shapes in a loop for each petal and decreasing the size and transitioning the stroke color:

I did the above with grayscale but you can do some cool transitions!

Example for a circle:

size(300, 300);
strokeWeight(10);  
  
for(int j=0; j<128; j+=9) // Adjusted steps until appeared smooth
  {
  stroke(255-(128-j)); //Transition from one color to next
  println(j, 255-(128-j));
  circle(150, 150, 255-j);
  }

I did not use these but they are there to experiment with in future:

Examples on website for these.

:)