Analog mono synth · rev 0.1

TouchSynth

A small analog synthesizer on a 100 × 100 mm circuit board. It has no knobs and no switches: you play and edit it on 13 capacitive touch keys, and a small RISC-V microcontroller steers a discrete oscillator, a transistor ladder filter and a VCA.

Design report (PDF) Source
CH32V003 / V002 / V00624 dB/oct ladder 4-layer PCBabout USD 3.65 of parts

Everything you hear on this page comes either from the first assembled board or from the model that was used to design it. Each recording says which.

Top side of the TouchSynth PCB: analog circuit blocks in the upper half, a one-octave touch keyboard with SHIFT, minus and plus pads in the lower half.
Render of the board. The keys work: click or tap them, or use A W S E D … on your keyboard. That sound is a rough sketch made by your browser (a saw through a low-pass), not the circuit.
Listen

Recorded from the first board

The synth plays one note at a time, so each piece was recorded from the line output one part per take and then mixed. Every piece also exists as a render of the behavioural model. Switch between Board 1 and Model while it plays to compare the two.

How it works

A digital brain, an analog voice

The microcontroller produces no audio. It sets the timing of the oscillator and sends four control voltages; the sound itself is made by op-amps and transistors.

Oscillator

An op-amp integrator ramps up and the MCU timer resets it once per period, so the pitch is as exact as the timer. The charging current follows the pitch, which keeps the saw the same size from C1 to C8.

Filter

A 24 dB/oct ladder of matched transistor pairs with an exponential converter. The resonance goes up to self-oscillation, where the filter sings a sine wave of its own.

Amplifier

A differential-pair VCA. Such a circuit lets a little of the control voltage through as a thump on every note; a small R-2R DAC trims that away, and the firmware can find the setting itself.

Touch keys

Thirteen keys from C to C′ plus SHIFT, − and +, all plain copper pads on the board. SHIFT and a key select what − and + edit; the 16 LEDs show the value.

Sound tour

One clip per feature

Nineteen short clips that take the voice apart: the waveforms, the filter, the envelopes and the modulation. These are renders of the behavioural model, each shown with its waveform and spectrogram. Clips play one after the other.

Board 1

Simulated first, then measured

Every block was simulated in ngspice before layout, and the board carries a loopback from its output into the MCU's ADC, so it can test itself from a PC. The first board passed all the functional tests that were run (two, touch scan rate and MIDI, were not). One result is marginal: the broadband noise is about −55 dB against a −60 dB target.

±0.3 centpitch error at 11 notes from C2 to C7, relative to the MCU clock
2.01 oct/Vfilter tracking from 89 Hz to 12.1 kHz (simulated: 2.05)
0 ± 2 mVVCA thump after trimming, down from −33 mV
−0.9 / +1.2 %saw amplitude over five octaves, uncalibrated
25 mAsupply current at 9 V, MCU running, LEDs off
40 / 196BOM lines and machine-placed parts, all JLCPCB Basic or Promotional Extended
Three plots: filter frequency against cutoff voltage, output level against resonance voltage, harmonic levels against a four-pole fit.
The filter on board 1 against the simulation: tracking, the onset of self-oscillation, and the low-pass slope.
Plots of oscillator pitch error and saw amplitude over the note range on board 1.
The oscillator on board 1: pitch and saw amplitude over the keyboard range.
How it was made

Generated from one Python file

The whole design lives in one file of parts, values and nets. Scripts turn it into the simulation netlists, the KiCad schematic, the placed and routed PCB and the fabrication data, so the simulated circuit and the built circuit cannot drift apart. The design was done by cpldcpu together with Claude; the development log records every prompt of those sessions.

design.py→ngspice→behavioural model→KiCad schematic→placement + routing→JLCPCB→firmware→bench tests
Front copper layer
F.Cu · signal
Inner layer 1, ground plane
In1.Cu · GND
Inner layer 2, split power plane
In2.Cu · power
Back copper layer
B.Cu · signal
0:00 / 0:00