Génération en Scheme de partitions complètes (y compris des parties d’ouvrage) sans utiliser l’analyseur

Une partition LilyPond, de manière interne, n’est rien d’autre qu’une expression Scheme générée par l’analyseur syntaxique de LilyPond. Il est donc possible, à l’aide de Scheme, de générer automatiquement une partition sans fichier source. Une expression musicale en Scheme sera transformée en partition par un appel à

(scorify-music music)

Ceci aura pour effet de générer un objet score auquel sera appliqué un bloc layout comportant la fonction

(let* ((layout (ly:output-def-clone $defaultlayout)))
   ; modification de la mise en forme, puis assignation :
   (ly:score-add-output-def! score layout)
  )

Il suffit alors de transmettre ce score à LilyPond pour qu’il le grave. Les trois fonctions – (add-score score), (add-text text) et (add-music music) – définies dans le code ci-dessous permettent de transmettre à LilyPond, aux fins de les graver, une partition complète, un markup ou simplement de la musique.

Cet exemple permet aussi de graver les pièces contenues dans un bloc \book { … } ainsi que des partitions de niveau supérieur. Chaque partition destinée à être gravée est alors ajoutée à la liste des partitions de niveau supérieur ; le toplevel-book-handler – fonction Scheme appelée pour traiter un book dès que le bloc \book { … } est clôturé – s’adapte pour prendre en charge tous les éléments score jusque là collectés dans l’ouvrage.

Attention : Pour des raisons techniques, seul le premier \book sera rendu puisque les autres commandes \book génèrent des fichiers additionnels.

#(define-public (add-score score)
   (ly:parser-define! 'toplevel-scores
                      (cons score (ly:parser-lookup 'toplevel-scores))))

#(define-public (add-text text)
   (add-score (list text)))

#(define-public (add-music music)
   (collect-music-aux (lambda (score)
                        (add-score score))
                      music))

#(define-public (toplevel-book-handler book)
   (map (lambda (score)
          (ly:book-add-score! book score))
        (reverse! (ly:parser-lookup 'toplevel-scores)))
   (ly:parser-define! 'toplevel-scores (list))
   (print-book-with-defaults book))

#(define-public (book-score-handler book score)
   (add-score score))

#(define-public (book-text-handler book text)
   (add-text text))

#(define-public (book-music-handler book music)
   (add-music music))


% Some example code to show how to use these functions.  Each call to
% `\oneNoteScore` constructs a global markup followed by a single
% staff with a single quarter note.  The pitch of this note is taken
% from the variable `pitch`; the start value 0 corresponds to pitch C.
% After emitting the score, variable `pitch` gets increased by 1.
%
% `\oneNoteScore` calls Scheme function `add-one-note-score` to do all
% the work.

#(define add-one-note-score #f)
#(let ((pitch 0))
   (set! add-one-note-score
         (lambda ()
           (let* ((music
                   (make-music
                    'EventChord
                    'elements (list (make-music
                                     'NoteEvent
                                     'duration (ly:make-duration 2 0 1/1)
                                     'pitch (ly:make-pitch 0 pitch 0)))))
                  (score (scorify-music music))
                  (layout (ly:output-def-clone $defaultlayout))
                  (note-name (case pitch
                               ((0) "do")
                               ((1) "ré")
                               ((2) "mi")
                               ((3) "fa")
                               ((4) "sol")
                               ((5) "la")
                               ((6) "si")
                               (else "huh")))
                  (title (markup #:large #:line
                                 ("Score with a" note-name))))
             (ly:score-add-output-def! score layout)
             (add-text title)
             (add-score score))
           (set! pitch (modulo (1+ pitch) 7)))))

oneNoteScore =
#(define-void-function () ()
   (add-one-note-score))

\book {
  \oneNoteScore

  \paper { tagline = ##f }
}


\book {
  \oneNoteScore
  \oneNoteScore

  \paper { tagline = ##f }
}

% Top-level scores are also handled correctly.
\oneNoteScore
\oneNoteScore

\paper { tagline = ##f }
[image of music]

LilyPond snippets v2.25.32 (development-branch).