# 7. Sound

The sound verbs need the SDL build and an audio device. Without one they refuse by
name, and a machine with no sound card still runs the interpreter — only `SOUND` and
`PLAY` fail, and they say so.

## SOUND

```basic requires=akgl
10 SOUND 1, 4000, 60
```

Voice, frequency, duration. Voices are numbered from 1. The duration is in *jiffies* —
sixtieths of a second — as on a C128, so 60 is one second.

**The frequency is a SID register value, not hertz.** As on a C128 the pitch is
`frequency * 1022730 / 16777216` — the NTSC system clock over the oscillator's 24-bit
accumulator — so the 4000 above is about 244 Hz, and the argument ranges from 0 to
65535. Work the notes you need out once and write the arithmetic down beside them: 4298
is C4, 8579 is C5, 17175 is C6. `PLAY` takes note names and does the conversion for you.

Further arguments give a frequency sweep: a step, a direction and a range, which is
what makes a siren or a laser.

**`SOUND` does not block.** On a C128 the note starts and the program carries on; here
the same is true, and it has to be — an embedded interpreter that stopped the host's
frame loop for a second would freeze the game.

## PLAY

`PLAY` takes a string of notes:

```basic requires=akgl
10 PLAY "C D E F G"
```

Within the string:

| | |
|---|---|
| `A` to `G` | a note |
| `#` `$` | sharp, flat |
| `O` *n* | octave |
| `V` *n* | voice |
| `T` *n* | envelope preset |
| `U` *n* | volume |
| `W`, `H`, `Q`, `I`, `S` | whole, half, quarter, eighth, sixteenth notes |
| `R` | rest |
| `.` | dotted |

Notes are queued and released in time, paced by the host's clock. A program that
`PLAY`s and then carries on works the way you expect; a program that `PLAY`s and then
immediately `QUIT`s may not hear all of it.

`M` — measure — is accepted and does nothing. There is no bar-line accounting to do.

## TEMPO

```basic requires=akgl
10 TEMPO 8
```

How fast `PLAY` releases its queue. The number is the same range a C128 uses; the
constant that turns it into milliseconds is a calibration choice rather than a
transcription, so it may not match a real machine exactly.

## ENVELOPE and VOL

```basic requires=akgl
10 ENVELOPE 0, 5, 9, 4, 6
20 VOL 8
```

`ENVELOPE` defines one of the ten presets `PLAY`'s `T` selects: attack, decay, sustain
and release. `VOL` sets the overall volume, 0 to 15.

## FILTER

`FILTER` parses and then **refuses at execution**:

```basic
10 FILTER 1000, 1, 0, 0, 8
```

```output
? 10 : RUNTIME ERROR FILTER needs a filter stage this device does not have

```

It sets the SID's filter cutoff, band switches and resonance. The audio backend
synthesises raw waveforms and mixes them; there is no filter stage to configure and
SDL supplies no primitive to build one from. Refusing is deliberate — a program that
asks for a low-pass and gets an unfiltered square wave has been lied to.

This is the one verb still waiting on a capability from the graphics library. It is
filed there rather than worked around here.

## The clock

Everything with a duration — `SOUND`, `PLAY`, `TEMPO`, and `SLEEP` from Chapter 2's
neighbourhood — is paced by a clock the *host* provides. The standalone interpreter
sets it from a monotonic timer every step, so it just works.

An embedded host that never sets the clock gets durations that expire immediately:
audible, but never a hang. That is the intended failure direction.
