<canvas id="c"></canvas>
<!-- https://generativeartistry.com/tutorials/joy-division/ -->
html{ display: grid; height: 100vh }
body{ margin: auto }
View Compiled
const ctx = c.getContext('2d')
const size = window.innerWidth / 4
const dpr = window.devicePixelRatio
const step = 10

c.width = size * dpr
c.height = size * dpr
ctx.scale(dpr, dpr)
ctx.lineWidth = 2

let lines = []

// Create lines
for(let i = step; i < size - step; i += step) {
  let line = []
  for(let j = step; j <= size - step; j+= step) {
    const distToCenter = Math.abs(j - size / 2)
    const variance = Math.max(size / 2 - 50 - distToCenter, 0)
    const random = Math.random() * (variance / 2) * 1
    // pass the points
    line.push({ x: j, y: i - random })
  }
  lines.push(line)
}

// Draw
for(let i = 8; i < lines.length; i++) {
  ctx.beginPath()
  ctx.moveTo(lines[i][0].x, lines[i][0].y)
  
  let j
  for(j = 0; j < lines[i].length - 2; j++) {
    // ctx.lineTo(lines[i][j].x, lines[i][j].y)
    const xc = (lines[i][j].x + lines[i][j + 1].x) / 2
    const yc = (lines[i][j].y + lines[i][j + 1].y) / 2
    ctx.quadraticCurveTo(lines[i][j].x, lines[i][j].y, xc, yc)
  }
  
  ctx.quadraticCurveTo(lines[i][j].x, lines[i][j].y, lines[i][j + 1].x, lines[i][j + 1].y)
  ctx.save()
  ctx.globalCompositeOperation = 'destination-out'
  ctx.fill()
  ctx.restore()
  ctx.stroke()
}

View Compiled
Run Pen

External CSS

This Pen doesn't use any external CSS resources.

External JavaScript

  1. https://codepen.io/josephrexme/pen/76fbdf03419eabebfeacce585559771a?v=2