Imperial March in Arduino

Covid-19 keeps us at home. My son also has to do classes at home. He is quite engaged – at least for his level of motivation. To cheer him up a little, I came up with a nice project:

I googled the musical notes of the Imperial March and convinced him to practice them on his flute. He liked the idea. But he really got enthusiastic when I told him that it is quite easy to play these notes with the Arduino.

But before we started the project we figured out what creating sound means: Producing air waves. To play a certain note we need to know what frequency the wave has. Once we know the frequency of a note, all we have to do is find a way to produce air waves in the defined frequency. The easiest way on an Arduino to produce sounds is a Piezo element.

For example, if we’d like to play a‘ aka A4 (concert pitch) we need to create a wave of 440 Hz frequency.

Arduino IDE provides a special function to generate sounds: tone();

There are two variants of tone() available: One needs two parameter (pin and frequency) the other takes three parameter (pin, frequency and duration).

Required Hardware

Circuit

The circuit is very easy: Connect one pin of the Piezo with Arduino’s Ground and the other with any digital Arduino pin. We picked D8.

Code

#define a   440
#define f   349
#define c2  523
#define e2  659
#define f2  698

#define gn  800
#define hn  gn/2
#define vn  gn/4
#define an  gn/8

#define pin 8

void setup() {
}

void loop() {
  for(int i=0; i < 2; i++) {
    tone(pin, a, hn);
    delay(hn+100);
    tone(pin, a, hn);
    delay(hn+100);

    tone(pin, a, hn);
    delay(hn+100);
    tone(pin, f, vn+an);
    delay(vn+100+an);
    tone(pin, c2, an);
    delay(an+100);

    tone(pin, a, hn);
    delay(hn+100);
    tone(pin, f, vn+an);
    delay(vn+100+an);
    tone(pin, c2, an);
    delay(an+100);

    tone(pin, a, gn);
    delay(gn+200);

    tone(pin, e2, hn);
    delay(hn+100);
    tone(pin, e2, hn);
delay(hn+100);

    tone(pin, e2, hn);
    delay(hn+100);
    tone(pin, f2, vn+an);
    delay(vn+100+an);
    tone(pin, c2, an);
    delay(an+100);

    tone(pin, a, hn);
    delay(hn+100);
    tone(pin, f, vn+an);
    delay(vn+100+an);
    tone(pin, c2, an);
    delay(an+100);

    tone(pin, a, gn);
    delay(gn+200);
  }

  delay(10000);
}

The paragraphs in the code represent the bars of music.

The defines at the beginning define for each note the frequency. The other defines define the duration of a note, starting with a full note (gn from German Ganze Note), to half note (hn), quarter note (vn; from German Viertel Note) to eighth of a note /an; from German Achtel Note).

The tone function is always called with following parameters:

  • pin (8 in our case)
  • the note to play
  • the duration

To make it sound better we placed a delay after calling tone. The delay duration is calculated by the note to play plus 100 ms pause between two notes and sometimes (if a sixteenth of a note needed to be played a little bite more)

The result