Reputation: 87
I'm trying to recreate an array of increasing sized circles that each are being divided to create points to create ellipses that pulsate. I know how to divide each circle by a num of points and draw ellipses. And I know how to create a series of concentric circles, but I can't seem to wrap my mind around putting them together. When I do, I receive a result that looks like this..
This result is happening because each individual ellipse is adding a number of ellipses in increasing distances from the original ellipse. Nevertheless, I'm not sure how to fix the original issue of having a series of circles divided by a number of points to create ellipses.
Thanks.
Blackhole b;
void setup() {
size(750, 500);
smooth();
b = new Blackhole();
}
void draw() {
b.divide();
b.display();
}
class Blackhole {
PVector location;
PVector velocity;
PVector acceleration;
PVector center;
float speed = 0;
int [] eSize = {0, 25, 50, 75, 100, 125, 150, 175};
float radius = 100;
int numPoints = 16;
float angle = TWO_PI/(float)numPoints;
float [] [] xyArray;
Blackhole() {
location = new PVector(width/2, height/2);
velocity = new PVector(0, 0);
acceleration = new PVector(.0, 0);
}
void divide() {
xyArray = new float [numPoints][3];
for (int i=0; i<numPoints; i++) {
float x = radius*sin(angle*i)+width/2;
float y = radius*cos(angle*i)+height/2;
xyArray[i][0] = x;
xyArray[i][1] = y;
}
}
void display() {
background(#202020);
speed = speed + 0.05;
float pulse = noise(speed);
pulse = map(pulse, 0, 1, 150, 175);
noFill();
stroke(255, 100);
for ( int j = 0; j < eSize.length; j++) {
for ( int i = 0; i < numPoints; i++) {
float x = xyArray[i][0];
float y = xyArray[i][1];
ellipse(width/2, height/2, pulse + eSize[j], pulse + eSize[j]);
ellipse(x, y, 5, 5);
}
}
}
}
Upvotes: 1
Views: 562
Reputation: 51837
Drawing a circle of circles shouldn't be complicated and you already understand how to the polar to cartesian coordinate system conversion. Something as simple as this would work:
/*
draws a large circle with each vertex drawn as a smaller circle
sides = circle detail, the more sides, the more detaild the circle will be
largeRadius = large circle radius
smallRadius = radius of each small circle
*/
void circleOfCircles(int sides,float largeRadius, float smallRadius){
float angleIncrement = TWO_PI / sides;
for(int i = 0 ; i < sides; i++){
float x = cos(angleIncrement * i) * largeRadius;
float y = sin(angleIncrement * i) * largeRadius;
ellipse(x,y,smallRadius,smallRadius);
}
}
Which using your values would look like this:
float speed = 0;
int [] eSize = {0, 25, 50, 75, 100, 125, 150, 175};
float radius = 100;
int numPoints = 16;
void setup(){
size(750,500);
smooth();
}
void draw(){
background(#202020);
translate(width * 0.5, height * 0.5);
speed = speed + 0.05;
float pulse = noise(speed);
pulse = map(pulse, 0.0, 1.0, 150, 175);
noFill();
stroke(255, 100);
for ( int j = 0; j < eSize.length; j++) {
circleOfCircles(numPoints,pulse + eSize[j], 5);
}
}
/*
draws a large circle with each vertex drawn as a smaller circle
sides = circle detail, the more sides, the more detaild the circle will be
largeRadius = large circle radius
smallRadius = radius of each small circle
*/
void circleOfCircles(int sides,float largeRadius, float smallRadius){
float angleIncrement = TWO_PI / sides;
for(int i = 0 ; i < sides; i++){
float x = cos(angleIncrement * i) * largeRadius;
float y = sin(angleIncrement * i) * largeRadius;
ellipse(x,y,smallRadius,smallRadius);
}
}
If the polar to cartesian conversion is confusing, you can simply isolate transformations using pushMatrix() and popMatrix():
void circleOfCircles(int sides,float largeRadius, float smallRadius){
float angleIncrement = TWO_PI / sides;
for(int i = 0 ; i < sides; i++){
pushMatrix();
rotate(angleIncrement * i);
translate(largeRadius,0);
ellipse(0,0,smallRadius,smallRadius);
popMatrix();
}
}
Generally it's best to keep things are simple as possible. You are using a class and that's great! It's good to encapsulate functionality. It will make it easier to plug into other sketches in the future.
However, I there are some unused variables in your class:
PVector location;
PVector velocity;
PVector acceleration;
PVector center;
Some of these are initialised in the constructor, but never used again.
The main issue in terms of drawing circles of circles is around the divide()
and xyArray
. In divide()
you are computing points around a circle with a single radius, although in display()
it looks like you want to use varying radii.
I've removed the divide()
function which removed the need to use the xyArray
and loop over it twice (once to set positions, then to read it). Notice instead of radius
, pulseRadius
is used now which takes pulse
and eSize
into account.
Here is a simplified version of your code using radius
, but also pulse
and eSize
which is probably what you were trying to do:
Blackhole b;
void setup() {
size(750, 500);
smooth();
b = new Blackhole();
}
void draw() {
background(#202020);
b.display();
}
class Blackhole {
float speed = 0;
int [] eSize = {0, 25, 50, 75, 100, 125, 150, 175};
float radius = 100;
int numPoints = 16;
float angle = TWO_PI/(float)numPoints;
Blackhole() {
}
void display() {
speed = speed + 0.05;
float pulse = noise(speed);
pulse = map(pulse, 0, 1, 150, 175);
noFill();
stroke(255, 100);
for ( int j = 0; j < eSize.length; j++) {
for ( int i = 0; i < numPoints; i++) {
float pulseRadius = radius + pulse + eSize[j];
float x = pulseRadius * sin(angle*i)+width/2;
float y = pulseRadius * cos(angle*i)+height/2;
ellipse(x, y, 5, 5);
}
}
}
}
Just as an exploration, here is a javascript demo of the code using a function and sine calls to vary the number of points in the large circle and the two radii.
int numPoints = 16;
void setup(){
size(750,500);
smooth();
noFill();
}
void draw(){
background(#202020);
translate(width * 0.5, height * 0.5);
for(int i = 0 ; i < numPoints; i++){
stroke(255, (i+1) * 10);
circleOfCircles((int)map(sin(frameCount * .001 + i),-1.0,1.0,12 , 64),//number of sides
map(sin(frameCount * .010 + i),-1.0,1.0,100,225),//large radius
map(sin(frameCount * .100 + i),-1.0,1.0, 1, 30));//small radius
}
}
/*
draws a large circle with each vertex drawn as a smaller circle
sides = circle detail, the more sides, the more detaild the circle will be
largeRadius = large circle radius
smallRadius = radius of each small circle
*/
void circleOfCircles(int sides,float largeRadius, float smallRadius){
float angleIncrement = TWO_PI / sides;
for(int i = 0 ; i < sides; i++){
pushMatrix();
rotate(angleIncrement * i);
translate(largeRadius,0);
ellipse(0,0,smallRadius,smallRadius);
popMatrix();
}
}
Have fun!
Upvotes: 1