Skip to content

Releases: TuesdayCrowd/audio-claudio

v2.0.0 — Transkun engine, notation quality, earned polyphony

Choose a tag to compare

@cddigi cddigi released this 11 Jul 23:36
da43fcd

Three transcription engines, each with its own earned, ranked guarantee (never flattened):

Engine Reach Guarantee
Monophonic (YIN) --mono Exact closed-loop recovery — count/pitch/onset bit-for-bit
Polyphonic (Basic Pitch) default Statistical — note-level F1 ≥ 0.75 @ ±50 ms (measured 79.6 %)
Transkun (Neural Semi-CRF, MIT) --model transkun Parity≥ 99 % PyTorch parity, measured 100 % @ ±25 ms + exact velocity; self-contained via ONNX, no Python

Highlights

  • Transkun engine — real durations, velocity, and sustain/soft pedal; the transformer/scorer/heads in a committed 53 MB ONNX, the mel front end + semi-CRF Viterbi decode reimplemented in C#. Note-identical to the reference PyTorch implementation, gated in CI.
  • Notation quality (corpus-measured) — automatic key detection, a temporal treble/bass hand-split (a hand crossing middle C keeps its notes), and opt-in triplets.
  • The polyphonic closed-loop gate and the general-corpus discipline from earlier v2 stages.

Deferred to v2.1: packaging / cross-platform (Stage 5) and the HuggingFace publish of the Transkun artifact (committed + publish-ready).

Public domain (UNLICENSE). Transkun model © 2021 Yujia Yan et al. (MIT).

🤖 Generated with Claude Code

Audio Claudio v0.1.2

Choose a tag to compare

@cddigi cddigi released this 08 Jul 23:14
3b1bfe7

Audio Claudio v0.1.2 — record, compare, and read your playing.

Built on v0.1.1's live browser notation, v0.1.2 is a suite of tools for actually practising with the transcriber — capture what you play, hear it back, and read it with note names.

What's new

  • --recordlisten/transcribe also write input.wav (your real captured audio, losslessly reconstructed from the analysis frames) and recreation.wav (the transcription synthesized back), time-aligned for side-by-side A/B in an editor like Audacity.
  • --skip-silence — collapses the long pauses out of both WAVs (kept aligned) so a halting practice take plays back as one continuous piece. Splices are de-clicked with a short tail fade.
  • --note-names — prints each note's name (C4, F♯5 …) beneath it in the notation (MusicXML <lyric>), so you can confirm middle C reads as C4.
  • Auto tempo — omit --tempo and it's estimated from your note spacing (median inter-onset interval); no more guessing. --tempo still overrides.
  • Browser recording controls — the listen --view page now has Start/Stop buttons for multiple takes per session, plus per-take Title, Record, Skip silence, and Note names controls. The title shows in the notation instead of "Untitled Score."
  • Per-session output — each take's files (raw.mid, score.mid, score.musicxml, the --record WAVs, and a log.txt of the run's console output) stay at stable paths in the out-dir and are archived to a start-timestamped <out-dir>/<YYYYMMDD_HHMMSS>/ folder.
  • CI hygiene — Actions bumped to node24; the scheduled nightly closed-loop retired to an on-demand deep-closed-loop workflow (detection is frozen, so a daily run only re-measured a constant).

Honest scope

Still monophonic, single staff. Tempo estimation assumes a mostly-even melody (it can be an octave off on syncopated input; --tempo overrides). On real microphone audio the reliably-detected range is roughly MIDI 42–93 — the live frame size bounds the low end and the very top decays too fast; widening it is Phase-2 pYIN work, alongside polyphony, treble/bass split, and a legato note-off for cleaner rhythm from uneven playing. The transcriber reports what it hears faithfully — fumbles included.

367 tests green (unit + property + closed loop) on a fresh CI clone. Public domain (UNLICENSE); every dependency permissively licensed.

🤖 Built in collaboration with Claude Code.

Audio Claudio v0.1.1

Choose a tag to compare

@cddigi cddigi released this 08 Jul 05:49
3ea007d

Audio Claudio v0.1.1 — watch the score write itself.

This is the v0.1.0 MVP plus one feature: live incremental notation. Play into the microphone and the staff renders in a browser tab, a note at a time, as you play — then snaps to the clean quantized score when you stop.

The headline — listen --view

claudio listen --tempo 100 --view

Opens a local page and streams the growing score to it. The same pipeline that was already proven correct against files (YIN pitch detection → onset segmentation → grid quantization → MusicXML) now also emits its running result to the browser after every detected onset. When you Ctrl+C, the session's raw.mid, score.mid, and score.musicxml are written exactly as before — --view is purely additive.

Confirmed working by ear and eye on the primary machine (macOS, default browser): the staves built up live from live input and snapped to the correct notation on stop.

How it's built (same discipline as the MVP)

The feature respects the project's hexagonal boundary — no new domain claims, just an adapter and a use case:

  • LiveScoreProjector (Application) — re-quantizes the growing note list on each onset into a Score. Pure; imports only the Domain.
  • LiveNotationServer (Infrastructure) — a BCL-only HttpListener + Server-Sent Events server. Each rendered Score is serialized through the existing MusicXmlScoreWriter, base64-encoded, and pushed to connected browsers over a capacity-1, drop-oldest outbox (the view always shows the latest score, never a backlog). No ASP.NET, no web framework.
  • OpenSheetMusicDisplay (wwwroot/, OSMD 2.0.0, BSD-3-Clause, vendored with its license) — renders the MusicXML to notation in the page.

--view cannot break plain listen: the live hooks are isolated (a throwing hook is caught and reported, capture continues) and the server start is guarded (if the port or browser is unavailable, listen degrades to its normal behavior). Plain claudio listen is byte-for-byte unchanged.

This also quietly corroborates the one remaining MVP follow-up (R11.2, the manual MuseScore-load check): the browser renders the same MusicXmlScoreWriter output correctly, so the emitted MusicXML is demonstrably valid and renderable.

Honest scope

Unchanged from v0.1.0: monophonic, declared (not estimated) tempo, single staff. The live view is a rendering of the same monophonic transcription — it does not add polyphony. Phase-2 items (polyphony via a neural model behind the same ITranscriber port, tempo estimation, pYIN pitch-hardening, treble/bass split) remain out of scope.

331 tests green (unit + property + closed loop + the new projection/server/asset tests) on a fresh CI clone. UNLICENSE (public domain); every dependency permissively licensed.

🤖 Built in collaboration with Claude Code.

Audio Claudio v0.1.0

Choose a tag to compare

@cddigi cddigi released this 08 Jul 00:57
abecb31

Audio Claudio v0.1.0 — the monophonic piano transcriber MVP.

Audiō Claudiō, "I hear, by means of Claude." A real-time monophonic piano transcriber in C# / .NET 10 (LTS): audio comes in from a microphone or a WAV file, note events come out, and the transcription is emitted as MIDI + MusicXML with synthesized playback. Public domain (UNLICENSE).

Built in open, spec-driven collaboration with Claude Code across all 13 build-spec steps (0–12). Hexagonal ports & adapters, with a domain that is provably clock-free, integer-sample-timed, and deterministic — the microphone is just one more adapter, added last, over a pipeline that was already proven correct against files.

The headline — the closed-loop trial balance

The repo contains both halves of the round trip (a transcriber and a synthesizer), so the synthesizer is the test oracle — no hand-labelled ground truth is ever needed:

generate a random constrained score → synthesize it → transcribe it back → demand the score returns, within tolerance.

transcribe ∘ synthesize ≈ id, stated honestly:

  • Note count, pitch, and onset recovered exactly across MIDI 33–96 (checked every push + a 1,000-case nightly).
  • Duration additionally exact across MIDI 33–71 — the corpus is capped to physically-audible durations, because a real piano's high notes decay before a long note ends (asking for a sustain the audio lacks would test the SoundFont, not the transcriber).
  • A rare (~0.4%) YIN octave-error / missed-onset residual, tracked by the nightly and documented — not a false 100% claim.

311 tests green (unit + property + closed loop) on a fresh CI clone.

Honest scope

Monophonic; declared (not estimated) tempo; single staff. See README.md for the full claim and limitations and DECISIONS.md for the design log. Open human follow-up: the manual MuseScore-load check (R11.2). Phase-2 (polyphony via a neural model behind the same ITranscriber port, tempo estimation, pYIN pitch-hardening, treble/bass split) is out of MVP scope.

Includes the MusicXML barline-duration fix: a note cut at a barline (or an odd rest gap) whose length isn't a single standard note value is now spelled as tied standard values / consecutive rests, rather than crashing the writer — surfaced by the first live listen run.

🤖 Built in collaboration with Claude Code.