Skip to main content

LeadSheet

Renders a single-voice melody on a treble-clef staff with chord symbols above and optional lyrics below. Uses the Bravura SMuFL font for all music glyphs.

Twinkle Twinkle Little Star
Traditional
CTwinkletwinkleFGlittlestarCHowIwonderGCwhatyouare

Font setup

LeadSheet uses the Bravura SMuFL font for all music glyphs. Import the bundled font CSS once at your app root:

import 'react-notation/music-font.css'

Nothing will render without it — staff lines draw fine, but all glyphs (clef, noteheads, rests, accidentals, time signature) will be invisible.

Usage

import {
LeadSheet,
createScore, createTrack, createMeasure,
createNote, createChord, createLyric,
} from 'react-notation'
import 'react-notation/style.css'
import 'react-notation/music-font.css'

const score = createScore({
title: 'My Melody',
timeSignature: { beats: 4, value: 4 },
keySignature: { root: 'G', mode: 'major' },
tracks: [
createTrack({
clef: 'treble',
measures: [
createMeasure({
number: 1,
events: [
createNote({ pitch: { step: 'G', octave: 4 }, duration: 'quarter', beat: 1 }),
createNote({ pitch: { step: 'A', octave: 4 }, duration: 'quarter', beat: 2 }),
createNote({ pitch: { step: 'B', octave: 4 }, duration: 'half', beat: 3 }),
createChord({ symbol: 'G', root: 'G', quality: 'major', beat: 1, duration: 'whole' }),
],
}),
],
}),
],
})

<LeadSheet score={score} measuresPerLine={4} />

Data model

LeadSheet renders the first track of a MusicScore (or the track at trackIndex). Each Measure can contain a mix of event types:

Event typeRendered as
NoteNotehead on the staff at the correct pitch position, with stem, ledger lines, and optional accidental
RestRest glyph centred in the measure
ChordText symbol above the staff, aligned to the event's beat
LyricText below the staff, aligned to the event's beat

Events with the same beat value are laid out at the same horizontal position, so a Note and a Chord at beat 1 will align vertically.

Pitches and accidentals

Pitches are specified on the Note.pitch object:

// G4 — no accidental
createNote({ pitch: { step: 'G', octave: 4 }, duration: 'quarter', beat: 1 })

// F#4 — sharp rendered automatically
createNote({ pitch: { step: 'F', octave: 4, alter: 1 }, duration: 'quarter', beat: 2 })

// Bb4 — flat
createNote({ pitch: { step: 'B', octave: 4, alter: -1 }, duration: 'quarter', beat: 3 })

alter: 1 = sharp, alter: -1 = flat, alter: 0 = natural (explicit natural sign). Omitting alter renders no accidental symbol.

Beaming

Eighth and sixteenth notes that share the same integer beat index are automatically beamed:

// These four notes form two beam groups (beats 1 and 2)
createNote({ pitch: { step: 'C', octave: 5 }, duration: 'eighth', beat: 1 }),
createNote({ pitch: { step: 'D', octave: 5 }, duration: 'eighth', beat: 1.5 }),
createNote({ pitch: { step: 'E', octave: 5 }, duration: 'eighth', beat: 2 }),
createNote({ pitch: { step: 'F', octave: 5 }, duration: 'eighth', beat: 2.5 }),

Single beamable notes on their own beat get individual flags.

Ties

Set tied: true on a Note to draw a tie arc to the next note of the same pitch:

createNote({ pitch: { step: 'C', octave: 5 }, duration: 'half', beat: 1, tied: true }),
createNote({ pitch: { step: 'C', octave: 5 }, duration: 'half', beat: 3 }),

Section labels and rehearsal marks

These are set on Measure:

createMeasure({ number: 5, section: 'Chorus', events: [...] })
createMeasure({ number: 9, rehearsalMark: 'B', events: [...] })

section appears above the staff in italic. rehearsalMark appears in a box above the staff. When breakAtSections is true (default), a section label forces a new staff line.

Barlines

Set measure.barline to control the barline drawn at the end of a measure:

ValueAppearance
'single'Standard thin barline (default)
'double'Two thin lines
'final'Thin + thick — end of piece
'repeat-start'Thick + thin + dots
'repeat-end'Dots + thin + thick

Props

PropTypeDefaultDescription
scoreMusicScoreRequired. Score to render.
trackIndexnumber0Index of the track to render.
measuresPerLinenumber4Maximum measures per staff line.
breakAtSectionsbooleantrueStart a new line at section labels.
staffSpacenumber10Distance between adjacent staff lines in pixels. All sizing derives from this.
showChordsbooleantrueRender chord symbols above the staff.
showLyricsbooleantrueRender lyrics below the staff.
showTitlebooleantrueRender score title and composer.
showMeasureNumbersbooleanfalseRender bar numbers above each measure.
editorScoreEditorFrom useScore. Enables selection mode.
onSelect(sel: Selection) => voidFired when a note, rest, or chord is clicked.
classNamestringAdditional CSS class on the root <div>.
...restHTMLAttributes<HTMLDivElement>All standard div props forwarded.

LeadSheet is a forwardRef component.

Interactive / editor mode

Pass a ScoreEditor (from useScore) to enable selection. Notes, rests, and chords become focusable and receive data-notation-* attributes:

import { LeadSheet, useScore } from 'react-notation'

function Editor() {
const editor = useScore(initialScore)
return (
<LeadSheet
score={editor.score}
editor={editor}
onSelect={(sel) => console.log('selected', sel)}
/>
)
}

Note input (changing pitch/duration via keyboard) is not yet supported — selection only. See the editing guide for the full useScore API.

Theming

LeadSheet reads these --notation-* CSS tokens in addition to the base tokens:

TokenDefaultControls
--notation-music-font-familyBravura, serifFont for all SMuFL glyphs
--notation-staff-line-colorcurrentColorStaff lines and barlines
--notation-staff-line-width1Staff line stroke width (px)
--notation-note-colorcurrentColorNoteheads, stems, beams, rests, accidentals
--notation-staff-chord-colorinheritChord symbols above the staff
--notation-staff-lyric-colorinheritLyrics below the staff
--notation-font-familyGeorgia, serifSection labels, rehearsal marks, title
--notation-color-section-labelinheritSection label and bar number color

Override via ThemeProvider or plain CSS.

Known limitations

  • Only treble clef is supported. Bass clef, alto, and tenor are planned for M7.
  • Beat spacing is even — no proportional (optical) spacing.
  • Automatic key signature courtesy accidentals are not shown.
  • Note input / pitch editing via keyboard is deferred to M7.
  • Barre and articulation marks (staccato, accent, fermata) are not yet rendered.