
// heart
float x = 16 * pow(sin(angle), 3);
float y = 13 * cos(angle)
- 5 * cos(2 * angle)
- 2 * cos(3 * angle)
- cos(4 * angle);
Code
// glv
// 2026-02-14
// Have a heart
void setup()
{
size(600, 600);
noStroke();
frameRate(30);
}
void draw()
{
background(0);
translate(width/2, height/2);
fill(255, 0, 0);
sequence(2, 50);
// Optional for creating animated gif
//saveFrame("/data/line-######.png");
}
// framesPerStep: how many frames to wait before increasing the heart detail
// maxSteps: stop once stepIndex exceeds this value
void sequence(int framesPerStep, int maxSteps)
{
int frameIndex = frameCount - 1;
int stepIndex = frameIndex / framesPerStep; // advances every N frames
println(stepIndex);
makeHeart(stepIndex, 15);
if (stepIndex > maxSteps)
{
makeHeart(150, 15);
fill(255, 255, 0);
textSize(60);
textAlign(CENTER, CENTER);
text("Happy Valentine's Day!", 0, -240);
noLoop();
}
}
void makeHeart(int sampleCount, int scale)
{
beginShape();
for (int sampleIndex = 0; sampleIndex < sampleCount - 1; sampleIndex++)
{
strokeWeight(2);
PVector p = heartPoint(sampleCount, sampleIndex, scale);
vertex(p.x, p.y);
}
endShape(CLOSE);
}
PVector heartPoint(int sampleCount, int sampleIndex, int scale)
{
float angle = sampleIndex * (TAU / (sampleCount - 1));
// heart
float x = 16 * pow(sin(angle), 3);
float y = 13 * cos(angle)
- 5 * cos(2 * angle)
- 2 * cos(3 * angle)
- cos(4 * angle);
float xScaled = scale * x;
float yScaled = -scale * y;
return new PVector(xScaled, yScaled);
}
Reference:
Valentine's Day - Wikipedia
Parametric equation - Wikipedia
Heart symbol - Wikipedia
![]()