I used the Flocking example as a starting point, and made a flocking sketch that works in 3D, with multiple flocks being influenced by FFT band amplitudes. The problem i’m running into is getting each boid to rotate on the Z axis also as it flies in that direction.
The documentation looks like rotate( ) works for 2D rotation. There’s also a rotateZ( ) method, but I’m not sure how to combine a rotate( ) + rotateZ( ), or how to determine the correct amount for rotateZ( ). PVector.heading( ) only calculates 2D.
Here’s the method controlling the rotation:
// Draws triangle of boid pointing in direction of velocity
// Currently only rotates in XY directions. Needs to also rotate
// to face Z direction
void render()
{
float theta = velocity.heading() + radians(90);
fill(c1); // Boid color
//stroke(c2); // Boid outline color
noStroke(); // No outline runs smoother.
// Individual boid position translation matrix
pushMatrix();
translate(position.x, position.y, position.z);
ps.updateOrigin(new PVector(0.0f, r * 2.0f, 0.0f));
rotate(theta); // **HOW TO DO 3D ROTATION?**
beginShape(TRIANGLES);
vertex(0, -r * 2.0f);
vertex(-r, r * 2.0f);
vertex(r, r * 2.0f);
endShape();
// Adds particle out the rear of boid every jetFrames number of frames
if ( (frameCount % jetFrames) == 0 )
{
ps.addParticle();
}
ps.run();
popMatrix();
}
Here’s a video of it running in its current state:
Is there a simple/straightforward way to incorporate that third axis rotation? Or break rotate( ) out into rotateX( ), rotateY( ), and rotateZ( )?
(if you need to see more of the code, let me know. It’s a large class, and the sketch has 5 classes. Didn’t want to overload the post.)
After reading the 3D Rotation links (and re-reading a few times), i got a better grasp of what’s happening for each rotation axis and rotation( ). (It’s been a LONG time since i took a math class).
I broke out the rotate(theta) to a theta for each axis and i’m definitely getting the boids rotating to point in 3D directions! Some do appear to be flying backwards/sideways sometimes, which is a bit confusing (why only some, not all… or why not backwards on a specific axis?) But, i’ll do some more digging to make sure my calculations and implementations are correct. Making the Boids 3D pyramids might help visualize it, so i’ll work on that.
void render()
{
//float theta = velocity.heading() + radians(90);
PVector v1 = new PVector(velocity.x, velocity.y);
PVector v2 = new PVector(velocity.x, velocity.z);
PVector v3 = new PVector(velocity.y, velocity.z);
float thetaZ = v1.heading() + radians(90);
float thetaY = v2.heading() + radians(90);
float thetaX = v3.heading() + radians(90);
fill(c1); // Boid color
//stroke(c2); // Boid outline color
noStroke(); // No outline runs smoother.
// Individual boid position translation matrix
pushMatrix();
translate(position.x, position.y, position.z);
ps.updateOrigin(new PVector(0.0f, r * 2.0f, 0.0f));
//rotate(theta);
rotateZ(thetaZ);
rotateY(thetaY);
rotateX(thetaX);
beginShape(TRIANGLES);
vertex(0, -r * 2.0f);
vertex(-r, r * 2.0f);
vertex(r, r * 2.0f);
endShape();
// Adds particle out the rear of boid every jetFrames number of frames
if ( (frameCount % jetFrames) == 0 )
{
ps.addParticle();
}
ps.run();
popMatrix();
}
You could also try drawing them based on their current position and velocity each frame instead of trying to transform to the correct orientation and then drawing a standard shape. Use a method that takes the position and velocity as parameters and draws a triangle (or whatever) with the “front” vertex at position + velocity.
So, if i’m understanding you @rbrauer, have the vertexes of the shape calculated each frame based on position + velocity. So the lead point would always be at position and the base points would be at, say,
I did 3D flocking once (can’t find the code at the moment unfortunately) and I think I used something like that. I don’t remember exactly how it went, but I guess you would need a vector perpendicular to the velocity as well.
I’m not 100% certain why adding a thetaX and rotateX() breaks the rotation. It kinda makes sense when i close my eyes and visualize it. But, i’m not too concerned with figuring out the actual reason because it works!
@rbrauer Your code actually worked too, getting my boids to point in the correct direction. However, it broke my particle system shooting out the back of the boids. And before going down that rabbit hole figuring out how to fix that, i checked the Processing GitHub and had my idea. But, thanks again because it was oh-so-close.