hey @jeremydouglass! thanks for your help. tried to follow along with the tile example. still can’t seem to get it. ideally, i’d like every frame to be saved as a high res image until the animation stops playing (or for seconds). with what i’ve done so far, this does not seem to be happening. any ideas?
// Berkeley coordinates, added and dived by 3 (37.8716° N + 122.2727° W / 3)
ArrayList<MovingShape> movingShapeList = new ArrayList<MovingShape>();
color backgroundColor, strokeColor;
void setup() {
size(640, 640);
smooth(38);
// NYC coordinates, added and dived by 3 (40.7128° N + 74.0060° W / 3)
//Round down to 38 since smooth(int) requires whole number
rectMode(CENTER);
ellipseMode(CENTER);
backgroundColor = color(0);
strokeColor = color(255);
noFill();
strokeWeight(.0005f);
stroke(strokeColor);
initialize();
}
void draw() {
for (MovingShape currentObject : movingShapeList) {
currentObject.run();
}
}
void mousePressed() {
initialize();
}
void initialize() {
background(backgroundColor);
movingShapeList.clear();
for (int i = 0; i < 3; i++) {
movingShapeList.add(new MovingShape());
}
}
class MovingShape {
final PositionController currentPositionController;
final AngleController currentDirectionAngleController;
final AngleController currentRotationAngleController;
final ValueController currentObjectSizeController;
final ShapeDisplayController currentShapeDisplayer;
MovingShape() {
currentDirectionAngleController = new AngleController(true);
currentRotationAngleController = new AngleController(false);
currentPositionController = new PositionController(currentDirectionAngleController);
currentObjectSizeController = new ValueController(max(width, height) * 0.1f, max(width, height));
currentShapeDisplayer = new ShapeDisplayController(currentPositionController, currentRotationAngleController, currentObjectSizeController);
}
void run() {
currentDirectionAngleController.run();
currentRotationAngleController.run();
currentObjectSizeController.run();
currentPositionController.run();
currentShapeDisplayer.run();
}
}
abstract class Controller {
int properFrameCount;
void run() {
properFrameCount++;
}
}
final class PositionController extends Controller {
final AngleController directionAngleController;
public float xPosition, yPosition;
final float speed;
PositionController(AngleController c) {
directionAngleController = c;
xPosition = random(width * 0.025f, width * 0.075f);
yPosition = random(height * 0.025f, height * 0.075f);
speed = 23.1318667f;
// NYC coordinates, added and dived by 3 (33.8938° N + 35.5018° E / 3)
}
void run() {
super.run();
xPosition += speed * cos(directionAngleController.angle);
yPosition += speed * sin(directionAngleController.angle);
if (xPosition > width || xPosition < 0f) directionAngleController.angle = PI - directionAngleController.angle;
if (yPosition > height || yPosition < 0f) directionAngleController.angle = -directionAngleController.angle;
}
}
class AngleController extends Controller {
public float angle;
float angleVelocity;
float angleAcceleration;
final float maxAngleVelocity = TWO_PI / IDEAL_FRAME_RATE;
final float maxAngleAcceleration = TWO_PI / sq(IDEAL_FRAME_RATE);
final boolean angleChanges;
final boolean angleVelocityChanges;
final boolean angleChangesInterMittently;
AngleController(boolean enableIntermittent) {
angleChanges = (random(1f) < 0.7f);
angleVelocityChanges = (random(1f) < 0.7f);
if (enableIntermittent) angleChangesInterMittently = (random(1f) < 0.5f);
else angleChangesInterMittently = false;
angle = random(TWO_PI);
if (angleChanges) angleVelocity = random(-maxAngleVelocity, maxAngleVelocity);
if (angleVelocityChanges) angleAcceleration = random(maxAngleAcceleration);
}
AngleController() {
this(false);
}
void run() {
properFrameCount++;
if (angleChanges == false) return;
if (angleChangesInterMittently) if (properFrameCount % int(IDEAL_FRAME_RATE) != 0) return;
if (angleChangesInterMittently) angle += constrain((angleVelocity * IDEAL_FRAME_RATE) % TWO_PI, QUARTER_PI, TWO_PI - QUARTER_PI);
else angle += angleVelocity;
if (angleVelocityChanges == false) return;
angleVelocity += angleAcceleration;
if (angleVelocity > maxAngleVelocity || angleVelocity < -maxAngleVelocity) {
angleAcceleration = -angleAcceleration;
}
}
}
class ValueController extends Controller {
public float value;
float valueChangeRate;
final float minValue;
final float maxValue;
final float maxValueChangeRate;
final boolean valueChanges;
int properFrameCount;
ValueController(float minVal, float maxVal) {
valueChanges = (random(1f) < 0.7f);
minValue = minVal;
maxValue = maxVal;
value = random(max(maxValue * 0.1f, minValue), max(maxValue * 0.5f, minValue));
maxValueChangeRate = maxValue / IDEAL_FRAME_RATE;
if (valueChanges) valueChangeRate = random(maxValueChangeRate);
}
void run() {
super.run();
if (valueChanges == false) return;
value += valueChangeRate;
if (value > maxValue || value < minValue) valueChangeRate = -valueChangeRate;
}
}
class ShapeDisplayController extends Controller {
final PositionController position;
final AngleController rotation;
final ValueController objectSize;
final int shapeTypeNumber;
final float shapeParameter;
ShapeDisplayController(PositionController pos, AngleController rot, ValueController obj) {
position = pos;
rotation = rot;
objectSize = obj;
shapeTypeNumber = int(random(4f));
switch(shapeTypeNumber) {
case 1: // ellipse
case 2: // recatngle
shapeParameter = random(1f, 1.7f);
break;
default:
shapeParameter = 0f;
break;
}
}
void run() {
super.run();
pushMatrix();
translate(position.xPosition, position.yPosition);
rotate(rotation.angle);
switch(shapeTypeNumber) {
case 0:
drawLine(objectSize.value);
break;
case 1:
drawEllipse(objectSize.value);
break;
case 2:
drawRectangle(objectSize.value);
break;
case 3:
drawTriangle(objectSize.value);
break;
}
popMatrix();
}
void drawLine(float objectSize) {
line(-objectSize * 0.5f, -objectSize * 0.5f, objectSize * 0.5f, objectSize * 0.5f);
}
void drawEllipse(float objectSize) {
ellipse(0f, 0f, objectSize, objectSize * shapeParameter);
}
void drawRectangle(float objectSize) {
rect(0f, 0f, objectSize, objectSize * shapeParameter);
}
void drawTriangle(float objectSize) {
triangle(objectSize / sqrt(3f), 0f, -objectSize/(2f * sqrt(3f)), objectSize / 2f, -objectSize / (2f * sqrt(3)), -objectSize / 2f);
}
void saveHiRes(int scaleFactor) {
PGraphics hires = createGraphics(width*scaleFactor, height*scaleFactor, JAVA2D);
beginRecord(hires);
hires.scale(scaleFactor);
draw();
endRecord();
hires.save("SCREEN11.png");
hires.save("SCREEN11.tif");
saveFrame("file_####.png");
}
}