The README described a CLI with a minimal web UI and told people to fix
charts in Yass. Rewrite it around how songtrace is used now: what it
does, its requirements up front (an NVIDIA GPU, tested on 12 GB, Docker
with the NVIDIA Container Toolkit, a Whisper server of your own, disk for
models and per-song files), a Docker quick start including writing songs
straight into a game's collection, then reviewing, editing and
rebuilding in the web UI. The command line moves near the end.
Regenerate the screenshot to show the note sheet: the screenshot script
now seeds the featured song with syllables, a chart, a pitch track and a
line break, and always scrolls to the review. The example config no
longer sets a real person as #CREATOR, and uses a reserved example host
for Whisper.
Checking whether the notes line up meant packaging the song, finding it in
the game and starting it there. The review panel now plays the song folder
itself: a transport above the lyrics, the line being sung highlighted, words
lighting up as they are reached, and a playhead sweeping each line against
its notes. Clicking a line or a word plays from there.
Playback is modelled on the game rather than on whatever is convenient: #MP3
is the audio and the clock, #VIDEO is muted background slaved to it, and the
times are the same seconds the notes were generated from. A word that lights
up late here is late in the game.
package now strips the audio track from the video it writes. It is the same
recording as the #MP3, so a player that does not mute the video plays both a
few frames apart, which is heard as an echo. The compatible-video branch
remuxes with -c copy -an rather than copying the file, so it still does not
re-encode. The browser player mutes the video as well, which covers song
folders built before this.
A new /api/jobs/{id}/media/{audio,video,cover} serves what the song's own
#MP3/#VIDEO/#COVER headers name, refusing anything resolving outside the song
folder. Range requests come from FileResponse, so seeking works.
Also, per review: CREATE SONG moves out of the form and into the top of the
queue, where it is always available, and a successful submission keeps the
fields it sent instead of emptying them.
Replace arbitrary demo pitches with the actual melody transcribed from
Gilbert DeBenedetti's public-domain "Level 4, Flowing" arrangement (E
minor, 6/8), converted to UltraStar semitones, with one note per word
across both demo lines.
The review panel used to show a full line of packed text with one
undifferentiated strip of notes below it, so it was impossible to tell
which notes belonged to which word. The forced-alignment stage already
produces per-word timestamps in alignment.json, but they were never
surfaced past the pipeline.
/api/jobs/{id}/review now includes each line's per-word timing, and the
frontend spaces words out by their real sung timing (karaoke-style)
instead of normal text flow, with the note strip sharing that same time
axis so each note lands directly under its word. Alternating lane
backgrounds make the word/note pairing unambiguous. Dropped lines and
jobs without alignment data keep the old plain-text rendering.