Sketch structure

A p5.js sketch is structured around three primary functions:

  • setup() – Runs once at the beginning to initialize the canvas and variables.
  • draw() – Continuously runs in a loop to update the visuals.
  • Interactive and custom functions – Respond to user input and help organize code.

Here’s a basic sketch structure in p5.js:

function setup() {
  // instantiate objects
}

function draw() {
  // main event loop
}

// interactive functions mouse / keyboard / touch

// custom functions

Setup

The setup() function runs once at the start of the program. It is used to:

  • Define the canvas size with createCanvas(width, height).
  • Initialize variables and objects for the sketch.

Example:

function setup() {
  createCanvas(400, 400);
  background(220); // Light gray background
}

This creates a 400x400 canvas with a light gray background.

ℹ️
To load external assets like images, fonts, or sounds in p5.js v2.x, define setup() as async and use await loadImage(...), await loadFont(...), etc.

Asset Loading Example

Here’s an example that loads an image and uses it as the background:

Code Explanation
let pola;

async function setup() {
  createCanvas(300, 300);
  pola = await loadImage('pola.jpg');
}

function draw() {
  background(pola);
  fill(0, 255, 0);
  circle(100, 200, 80);
  fill(0, 0, 255);
  circle(200, 200, 80);
  fill(255, 0, 0, 125);
  circle(mouseX, mouseY, 80);
}

Draw

The draw() function is the core of animation and interaction in p5.js. Unlike setup(), which runs once, draw() runs continuously, executing frame by frame. By default, this happens 60 times per second unless modified with frameRate().

Continuous Drawing

By default, visuals in draw() accumulate, meaning previous frames are not erased. This creates a layering effect, where each frame builds on the last. The example below shows this behavior, where a red circle follows the mouse, leaving a trailing effect.

Code Explanation
function setup() {  
  createCanvas(300, 300);  
}  

function draw() {  
  fill(0, 255, 0);  
  circle(100, 200, 80);  
  fill(0, 0, 255);  
  circle(200, 200, 80);  
  fill(255, 0, 0, 25);  
  circle(mouseX, mouseY, 80);  
}  
ℹ️
  • draw: Runs continuously, enabling animation and interaction.
  • mouseX / mouseY: Track the mouse position on the canvas.

Smooth Refresh

To avoid visuals stacking up, the background() function clears the canvas at the start of each frame, ensuring only the latest frame is displayed.

Code Explanation
function setup() {  
  createCanvas(300, 300);  
}  

function draw() {  
  background(70);  
  fill(0, 255, 0);  
  circle(100, 200, 80);  
  fill(0, 0, 255);  
  circle(200, 200, 80);  
  fill(255, 0, 0, 125);  
  circle(mouseX, mouseY, 80);  
}  
ℹ️
  • background: Clears the canvas each frame to prevent overlapping visuals.
  • Without background(), frames stack, leaving a trail effect.
  • With background(), only the current frame is visible, creating smooth motion.

Custom Functions

To keep code organized, you can define custom functions:

function drawCircle(x, y, size, color) {
  push();
  fill(color);
  circle(x, y, size);
  pop();
}

This helps structure the sketch better, making it modular and reusable.

Further Reading

📌 p5.js Reference: Sketch Structure – Learn more about setup(), draw(), and asset loading with await.