Tutorial: Your First Drawing

In this tutorial you draw a house on a hill, with the sun in the sky, using rectangles, a circle, a triangle and some words. It takes about ten minutes and needs no JavaScript beyond the basics.

1. Make the file

From the new-document menu (), choose Code, then JavaScript, and call the file house.js. It opens as code only, because an empty JavaScript file is not a scene yet.

2. Paint the sky

Type this and press Run:

function draw() {
  background("lightskyblue")
}

The preview opens beside your code and turns blue. The canvas is the picture in the preview.

  • function draw() { … } is a function the canvas calls every frame. Anything between its braces is drawn again and again, so your picture stays put even when the canvas changes size.
  • background("lightskyblue") paints the whole canvas that colour. A colour is a name in quotes; there are about 140 names, and Colours lists other ways to write one.

From now on there is nothing to press: about half a second after you stop typing, the drawing runs again.

3. Add the ground

Add these lines inside draw(), under the sky and before the closing }. The braces are what put a line inside the function; the two spaces at the start of each line are there to make that easy to see.

function draw() {
  background("lightskyblue")

  const ground = height * 0.7
  rect(0, ground, width, height - ground, "yellowgreen")
}

rect(x, y, width, height, colour) draws a filled rectangle. x, y is its top-left corner, and (0, 0) is the top-left corner of the canvas. y counts down from the top, so height * 0.7 is 70% of the way down. The green rectangle starts there and fills the rest: width and height are the size of the canvas. const ground = … gives that number a name to use in the lines below.

4. The whole picture

Here is the finished drawing. Read the comments to see which lines draw what.

function draw() {
  // sky and ground
  background("lightskyblue")
  const ground = height * 0.7
  rect(0, ground, width, height - ground, "yellowgreen")

  // the sun
  circle(width - 80, 80, 45, "gold")

  // the house
  const x = width / 2 - 100      // left edge of the house
  const w = 200, h = 140         // its width and height
  const top = ground - h         // its top edge
  rect(x, top, w, h, "bisque")

  // the roof: a triangle, by its three corners
  triangle(x - 20, top, x + w / 2, top - 90, x + w + 20, top, "firebrick")

  // the door, and a window with a white frame
  rect(x + 80, ground - 70, 40, 70, "saddlebrown")
  rect(x + 20, top + 30, 45, 40, "lightcyan", { outline: "white", thickness: 4 })

  // a name for the picture
  text("My house", 20, 44, "white", 28)
}
  • circle(x, y, radius, colour) draws a filled circle. x, y is its centre.
  • text(words, x, y, colour, size) writes words, starting at x, y.
  • triangle(x1, y1, x2, y2, x3, y3, colour) draws a triangle from its three corners: the roof.
  • The window has { outline: "white", thickness: 4 } at the end: a filled shape with a border. Every shape can have one.

The house is placed with x, w, h and top, and everything else is worked out from them. Change const w = 200, h = 140 to const w = 260, h = 100 and the whole house, roof and door included, changes with it.

5. The long way

There is no ctx in the house: the plain functions drew all of it. ctx is the canvas's own drawing surface, and each plain function is a short way of writing what it does. The sun, written the long way, is these four lines:

ctx.fillStyle = "gold"
ctx.beginPath()
ctx.arc(width - 80, 80, 45, 0, degrees(360))
ctx.fill()

A circle the long way is an arc that goes all the way round, from 0 to a full turn. degrees(360) is a full turn: it lets you say any angle in degrees. You never need to write a circle like this, but every drawing example you find elsewhere does, and now you can read it. Drawing in 2D shows the rest of what ctx can do.

Try this

  • Change the colours. Any colour name works, or a code such as "#ff8800".
  • Add a cloud: three white circles that overlap.
  • Add a path to the door with a thick line: line(x1, y1, x2, y2, colour, thickness) draws from one point to another, so try line(width / 2, height * 0.7, width / 2, height, "tan", 30).
  • Make it night: a dark blue sky, a pale moon instead of the sun, and "yellow" windows.
  • Make the sun move: add let t = 0 above draw(), an update(dt) function that does t += dt, and draw the sun at 80 + t * 20 across.