Elixir library for parsing and formatting chord sheets. An Elixir rewrite of ChordSheetJS (v14).
Input (parsers):
| Format | Atom | Example |
|---|---|---|
| ChordPro | :chord_pro |
{title: My Song}\n[Am]Hello |
| Chords over words | :chords_over_words |
Am\nHello |
| Ultimate Guitar | :ultimate_guitar |
[Verse]\nAm\nHello |
| Typst/conchord | :typst |
[Am] Hello [G] world |
| LaTeX (songs package) | :latex_songs |
\beginsong{Title}[by={Artist}] |
Output (formatters):
| Format | Atom |
|---|---|
| Plain text | :text |
| ChordPro | :chord_pro |
| Chords over words | :chords_over_words |
| Ultimate Guitar | :ultimate_guitar |
| HTML (div-based) | :html_div |
| HTML (table-based) | :html_table |
| LaTeX (songs package) | :latex_songs |
| Typst/conchord | :typst |
Add sonx to your list of dependencies in mix.exs:
def deps do
[
{:sonx, "~> 0.1"}
]
endParse a ChordPro string, inspect metadata, and format as plain text:
{:ok, song} = Sonx.parse(:chord_pro, "{title: My Song}\n{key: C}\n[Am]Hello [G]world")
Sonx.title(song)
# => "My Song"
Sonx.get_chords(song)
# => ["Am", "G"]
Sonx.format(:text, song)
# => "My Song\n\nAm G\nHello world"transposed = Sonx.transpose(song, 3)
Sonx.get_chords(transposed)
# => ["Cm", "A#"]
changed = Sonx.change_key(song, "G")
Sonx.get_chords(changed)
# => ["Em", "D"]{:ok, song} = Sonx.parse(:chord_pro, "[C#]Hello")
flat = Sonx.use_accidental(song, :flat)
Sonx.get_chords(flat)
# => ["Db"]The HTML formatters provide default CSS via css_string/1:
alias Sonx.Formatter.HtmlDivFormatter
html = Sonx.format(:html_div, song)
css = HtmlDivFormatter.css_string()
"<style>#{css}</style>\n#{html}"HtmlTableFormatter.css_string/1 works the same way.
The :chord_diagrams option enables guitar chord diagrams (opt-in, default false).
Only supported by the :latex_songs and :typst formatters.
Pass true for defaults, or a keyword list of formatter-specific options:
# LaTeX: inserts \gtab{Chord}{Frets} commands
Sonx.format(:latex_songs, song, chord_diagrams: true)
# Typst: adds sized-chordlib import and call (default N: 4, full width)
Sonx.format(:typst, song, chord_diagrams: true)
# Typst: customize sized-chordlib parameters
Sonx.format(:typst, song, chord_diagrams: [n: 6])
Sonx.format(:typst, song, chord_diagrams: [n: 6, width: "400pt"])Sonx.chord_diagrams/2 generates format-specific chord diagram markup
for injection into raw text (e.g. passthrough mode):
# LaTeX: generates \gtab lines from chord names (with barre notation)
Sonx.chord_diagrams(:latex_songs, ["Am", "F", "C"])
# => "\\gtab{Am}{X02210}\n\\gtab{F}{(133211)}\n\\gtab{C}{X32010}"
# Typst: generates sized-chordlib preamble
Sonx.chord_diagrams(:typst, n: 4, width: "310pt")
# => "#import \"@preview/conchord:0.4.0\": sized-chordlib\n#context sized-chordlib(N: 4, width: 310pt)"Songs can be serialized to JSON and back:
json = Sonx.to_json(song)
{:ok, restored} = Sonx.from_json(json)Input String → Parser → %Song{} → Formatter → Output String
All parsers produce a Sonx.ChordSheet.Song struct (the intermediate representation).
All formatters consume one. This makes it easy to mix and match any input format
with any output format, and to apply transformations (transpose, key change) in between.
See the Sonx module documentation for the full API reference.
GPL-3.0-or-later. See LICENSE.md.