setup()
setup() runs once when the sketch loads. It's where you initialize your canvas, configure p5.js modes, and prepare interactive elements. The key insight here is that by calling handleSliderChange() at the end of setup(), you generate the initial geometry before the first draw, and then noLoop() ensures draw() is lightweight because geometry only regenerates when the slider moves.
function setup() {
createCanvas(1000, 1000);
angleMode(DEGREES);
noFill();
rectMode(CENTER);
// Pre-calculate square side length
sqSideLength = (width / 4) * 1.0;
// Create the slider for nPoints
// Range: 3 to 60 points, initial value 24, step of 1
nPointsSlider = createSlider(3, 60, 24, 1);
nPointsSlider.id('nPointsSlider'); // Add an ID for CSS targeting
nPointsSlider.position(10, 40); // Position it on the canvas
// Create a label for the slider
nPointsLabel = createP('Number of Points (nPoints): 24');
nPointsLabel.id('nPointsLabel'); // Add an ID for CSS targeting
nPointsLabel.position(10, 10); // Position it above the slider
// Add an event listener to the slider
// When the slider value changes, call handleSliderChange()
nPointsSlider.input(handleSliderChange);
// Initial call to draw the rosettes with the default slider value
handleSliderChange();
noLoop(); // Draw once, then only redraw on slider input
}
Line-by-line explanation (9 lines)
🔧 Subcomponents:
angleMode(DEGREES);
Tells all trigonometric functions (sin, cos, tan) to use degrees instead of radians, making angle math more intuitive
nPointsSlider = createSlider(3, 60, 24, 1);
Creates a slider element that lets users choose between 3 and 60 petals, starting at 24
nPointsSlider.input(handleSliderChange);
Links slider movement to the handleSliderChange() function so the pattern updates whenever the user moves the slider
noLoop(); // Draw once, then only redraw on slider input
Stops the draw() function from running 60 times per second; instead it only runs when redraw() is called, saving CPU for a static pattern
createCanvas(1000, 1000);- Creates a 1000×1000 pixel canvas where all the rosette geometry will be drawn
angleMode(DEGREES);- Switches angle units from radians to degrees (0–360), making trigonometric calculations easier to reason about
noFill();- Tells p5.js not to fill any shapes with color—only draw their outlines (strokes)
rectMode(CENTER);- Makes rectangles draw from their center point instead of their top-left corner (not used here, but set for completeness)
sqSideLength = (width / 4) * 1.0;- Pre-calculates the base size for petal geometry as one-quarter of the canvas width
nPointsSlider = createSlider(3, 60, 24, 1);- Creates an interactive slider: minimum 3 points, maximum 60, default 24, step size 1
nPointsSlider.input(handleSliderChange);- Wires the slider to call handleSliderChange() every time the user moves it
handleSliderChange();- Immediately generates the initial rosette pattern before the user touches the slider
noLoop();- Stops the draw() loop from repeating; it will only run when you explicitly call redraw()