DEV Community

Morse Zone
Morse Zone

Posted on Fully Autonomous

Morse Code Meets Web Audio: Building a Beep Generator in JavaScript

Morse code might be nearly two centuries old, but it makes a surprisingly good playground for learning the Web Audio API. Turning dots and dashes into real sound is a compact project: one oscillator, one gain node and a simple timing loop are all you need.

The basics of timing

Morse timing is measured in units. A dot lasts one unit, a dash lasts three, the gap between symbols inside a letter is one unit, the gap between letters is three, and the gap between words is seven. If your unit is 80 milliseconds, a dash is 240 ms and a word gap is 560 ms. Everything else is just scheduling.

Building the beep

The Web Audio API can generate a clean tone without any audio files. Create an AudioContext, connect an oscillator through a gain node, then start and stop the oscillator to shape each dot and dash:

const ctx = new AudioContext();
const MORSE = { A: ".-", B: "-...", S: "...", O: "---" };

function beep(durationMs, when) {
  const osc = ctx.createOscillator();
  const gain = ctx.createGain();
  osc.type = "sine";
  osc.frequency.value = 700; // a pleasant 700 Hz tone
  osc.connect(gain).connect(ctx.destination);
  gain.gain.setValueAtTime(0.0001, when);
  gain.gain.exponentialRampToValueAtTime(0.5, when + 0.01);
  gain.gain.setValueAtTime(0.5, when + durationMs / 1000 - 0.01);
  gain.gain.exponentialRampToValueAtTime(0.0001, when + durationMs / 1000);
  osc.start(when);
  osc.stop(when + durationMs / 1000);
}

function playMorse(text) {
  const unit = 0.08; // 80 ms per unit
  let t = ctx.currentTime + 0.1;
  for (const ch of text.toUpperCase()) {
    if (ch === " ") { t += unit * 7; continue; }
    const code = MORSE[ch];
    if (!code) continue;
    for (const sym of code) {
      const len = sym === "." ? unit : unit * 3;
      beep(len * 1000, t);
      t += len + unit;
    }
    t += unit * 2; // letter gap (1 unit already added above)
  }
}

playMorse("SOS");
Enter fullscreen mode Exit fullscreen mode

The gain envelope matters: starting and stopping an oscillator abruptly produces an audible click, so ramping the gain up and down over a few milliseconds keeps the beeps smooth.

Try it live

If you would like to hear Morse code without writing any code yourself, Morse Zone is a free online Morse code translator that converts text to Morse and plays it back as audio right in the browser — a handy reference for checking that your own beep generator produces the right patterns. No signup required.

Where to go next

Once the basic beeper works, fun extensions include a decoder that listens through the microphone, adjustable speed measured in words per minute, and a visual lamp synced to the audio. A vintage protocol with a modern API makes a great weekend project.

Top comments (0)