options(crayon.enabled = TRUE)
sgr_wrap <- function(x, options){
  paste0("<pre class=\"r-output\"><code>", fansi::sgr_to_html(x = htmltools::htmlEscape(x)), "</code></pre>")
}
knitr::knit_hooks$set(output = sgr_wrap)
knitr::opts_chunk$set(
  collapse = TRUE, comment = "#>", message = FALSE, warning = FALSE, error = FALSE, tidy = FALSE, out.width = "100%"
)
library(tabr)

This section introduces the use of chords in tabr. All of the functionality surrounding individual notes in phrases generalizes to chords. Chords symbols can also be displayed above sheet music staves and chord diagrams can be included at the top of sheet music scores using a chord chart. These topics are covered in the subsequent section on tracks and scores. This section here focuses on using chords in phrase() where their notation will become part of the content engraved in the sheet music staves.

Chord syntax

Like individual pitches, chords and other combinations of simultaneous pitches can be specified in multiple equivalent ways. The only difference is that there are no spaces between the notes. The following are equivalent ways to specify the same open C major chord. This is shown for completeness, but remember that octave tick format should be used; number format has limited utility in other contexts.

phrase("cegc'e' c3e3g3c4e4 cegc4e4", 4)

When the notes of a chord are tied over to the next, it is convenient to use tie() to avoid having to write the ~ explicitly for each note in the chord.

tie("cegc'e'")

Similar to notes, explicit string numbers passed to the string argument also remove spaces between individual string numbers. Recall the inferred strings when only the first (lowest number) string is given, as well as the expansion operator. Recycling only works when it is a single value.

chords <- "cegc'e' c3e3g3c4e4 cegc4e4"
x <- phrase(chords, 4, "54321 54321 54321")
identical(phrase(chords, 4, "5*3"), x)
identical(phrase("cegc'e'*3", 4, 5), x)

Chord syntax for fretboard diagrams

Chord diagrams refer to the fretboard diagrams commonly displayed in sheet music written for guitar. These chord diagram specifications are passed to score(), discussed in the next section that brings together the overall process of moving from phrases to tracks to a score. Here, the syntax used to specify chords for chord diagrams is introduced. Below are some chords that appear in a song.

Note that minor chord names, indicated by m, are one of the available chord modifiers. These modifiers come after the separator :. This is different from how key signatures can be expressed throughout most of tabr, with just a "dm" for example, but the modifiers that follow the colon have more general uses for chord diagrams. There will be more examples of this in a moment.

The chords also require position descriptions, because the same chord can be played many ways. This is the part that fully defines the chord diagram. As is standard, x means a string is not played and o refers to an open string. The numbers refer to the fret. The string is six characters representing strings six through one (low to high pitch) from left to right.

chord_names <- c("d:m", "f", "g:m", "a")
chord_positions <- c("xxo231", "133211", "355333", "xo222o")

Named vector input

If the chord positions are a named vector, there is no need to pass both positions and names separately to chord_set(). It will check the first argument for names before looking to the second argument.

chords <- chord_set(chord_positions, chord_names)
chords

names(chord_positions) <- chord_names
identical(chords, chord_set(chord_positions))

Analogous to phrase(), chord_set() is a simple function that manipulates the input strings into a named character vector of chord entries in a format understood by LilyPond.

Chord chart

Next, to demonstrate the chord chart, make a dummy song and include the chord set. The output for the dummy song now contains a chord chart centered at the top of the first page of sheet music.

p("r", 1) |> track() |> score(chords) |> tab("ex13.pdf")

Details

The next example highlights several facts about chord specification for fretboard diagrams and chord charts.

chords <- c("xo22oo", "o223o", "xxx565", "786", "10 10 10 8", "o231", "765", "o22oo", NA, NA)
names(chords) <- c("a:sus2", "a:sus4", "f/c", "g:m/d", "f", "d:m", "d:m", "a:sus2", "r", "s")
chords <- chord_set(chords)
p("r", 1) |> track() |> score(chords) |> tab("ex14.pdf")

Chord symbols and sequences

You have already seen chord symbols, placed above the fretboard diagrams above. Chord symbols refer to the shorthand chord notation, or chord labels, often shown above chord diagrams as well as above a music staff at the beginning of measures or at each chord change. These are the familiar labels such as C Dm F# F/C. The next use of chords is placement above the staff in time. This is the chord sequence.

In order to place chord symbols in time above a music staff, it is necessary to specify their sequence and the duration of each chord, just like is required for all the notes and chords shown inside the staff that are created from a sequence of phrase objects. The two examples below uses a simple melody of arpeggiated, broken chords played using the chords C, F and G. Those chord symbols are shown above the staff at the appropriate point in time based on the defined chord sequence.

notes <- "c e g c' e' c' g e g b d' g' f a c' f' c e g e c"
info <- c("8*20 2", "4*20 1")
strings <- pc(c(5:1, 2:4, 4:1, 4:1, 5:3, 4:5)) # almost not needed, but for 1st 2 notes of G chord
p1 <- p(notes, info[1], strings)
p2 <- p(notes, info[2], strings)
chords <- chord_set(c(c = "32o1o", f = "3211", g = "5433", r = NA, s = NA))

Chord sequence

In the first version, there is a chord change halfway through a measure. Assign beat duration information for each chord in the sequence just as you would with the info argument to phrase(), e.g., half a measure is given with 2. The C chord is played for a full measure both times while the F and G chords each last half a measure. The chord sequence is named just like chords above. This is how the correct chord symbol is applied above the staff at the correct time. Taking the names directly from chords as a chord dictionary for the song is the suggested way to avoid having to type chord symbols repeatedly.

Finally, score() takes a chord_seq argument after the chords argument. Building on the previous example, here both are passed to score().

chord_seq <- c(1, 2, 2, 1)
names(chord_seq) <- names(chords)[c(1, 3:1)] # C G F C
track(p1) |> score(chords, chord_seq) |> tab("ex15.pdf")

Using rests

Version two double the duration of all notes. Now the C chord lasts for two full measures while the F and G chords are played for one measure each. You can always specify a chord for every measure, in this case providing the C chord in the sequence twice in a row for one measure each. However, this example uses rests. Note the inclusion of r and s in the current chords vector.

To illustrate how rests factor into chord sequences, a silent rest is used for measure two. This avoids showing the C chord twice in a row without a chord change in between. Nothing is shown above the staff at this point in time. The final measure of the phrase uses a regular rest, which is not silent. This leads to the "no chord" symbol N.C. being printed above the staff. You do not show a chord as lasting longer than a measure by providing values less than one. This example also shows a very simple but also very common case where a song does have every chord in its chord sequence last for exactly one measure.

chord_seq <- rep(1, 6)
names(chord_seq) <- names(chords)[c(1, 5, 3:1, 4)] # C (s) G F C (r)
track(p2) |> score(chords, chord_seq) |> tab("ex16.pdf")

Overall picture

Since the chord chart is included and was only shown in prior examples zoomed in, here is the result above showing the full sheet, which includes the staves and chord symbols, the chord chart positioned top center, and for perspective the page numbering in the top right corner.

To sum up, chords are used in tabr in three ways. Using phrase(), they appear among other notes in staves as the core component of the music transcription. They are also used by score() to generate chord charts using fretboard diagrams that summarize all the chords that occur in a song. Finally, the same chord symbols can be listed in sequence with corresponding durations to be applied above a music staff, showing the chord progression throughout the song in proper time.

unlink("*.mid")


leonawicz/tabr documentation built on Sept. 24, 2023, 2:49 p.m.