lilypond-user
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Snippet: Customizing markFormatter


From: Aaron Hill
Subject: Snippet: Customizing markFormatter
Date: Thu, 21 Mar 2019 15:16:16 -0700
User-agent: Roundcube Webmail/1.3.8

Hi folks,

There have been a few mentions of rehearsal marks recently and wanting to customize the appearance of \mark \default. Using \mark \markup gives you much freedom at the cost of requiring one to manually manage the numbering/naming of these marks.

The (what-I-presume-is-official) solution is instead to \set Score.markFormatter to a custom procedure and then simply use \mark \default as one would normally. This new procedure can leverage any existing formatting functions as desired. Consider the following:

%%%%
\version "2.19.82"
\paper { indent = 0 line-width = 4\in ragged-right = ##f }
{
  \set Score.markFormatter = #(lambda (mark context)
    #{ \markup \italic $(format-mark-barnumbers mark context) #} )
  \repeat unfold 3 { \mark \default b'4 4 4 4 | 2 2 | 1 }
}
%%%%

In an attempt to hide the Scheme-ness of the above approach, I put together the following music function which replaces placeholder strings within the provided markup with the output of the specified formatter function:

%%%%
\version "2.19.82"
\paper { indent = 0 line-width = 4\in ragged-right = ##f }

customMarkFormatter = #(define-music-function (markup) (markup?)
  (define (handle-formatter mark context markup)
    (let* ((sym (and (string? markup)
                     (string-prefix? "format-mark" markup)
                     (string->symbol markup)))
           (proc (and sym (defined? sym) (primitive-eval sym))))
      (if (procedure? proc) (proc mark context) markup)))
  (define (markup-fixup mark context markup)
    (if (list? markup)
      (map (lambda (elem) (markup-fixup mark context elem)) markup)
      (handle-formatter mark context markup)))
  #{ \set Score.markFormatter = #(lambda (mark context)
       (markup-fixup mark context markup)) #} )

#(define (format-mark-roman mark context)
  (make-bold-markup (format #f "address@hidden" mark)))

{
  \customMarkFormatter format-mark-roman
  \repeat unfold 3 { \mark \default b'4 4 4 4 | 2 2 | 1 }

  \customMarkFormatter \markup \rotate #30 format-mark-circle-numbers
  \repeat unfold 3 { \mark \default b'4 4 4 4 | 2 2 | 1 }

  \customMarkFormatter \markup
    { format-mark-box-letters \fontsize #-3 format-mark-barnumbers }
  \repeat unfold 3 { \mark \default b'4 4 4 4 | 2 2 | 1 }

  \customMarkFormatter format-mark-undefined
  \mark \default b'4 4 4 4 | 2 2 | 1
}
%%%%

The logic is to look for strings that begin with "format-mark" and then attempt to evaluate the procedure. Since all of the built-in formatting functions (as defined in translation-functions.scm) follow this naming convention, it made sense to require it to minimize the chance of evaluating an incorrect procedure.

The first example is just a trivial equivalent to \set Score.markFormatter = #format-mark-roman. The second and third show more customization with markup, where the third in particular demonstrates combining the results of two formatting functions. The final example covers the case of an undefined procedure.


-- Aaron Hill

Attachment: default-mark.1.png
Description: PNG image

Attachment: default-mark.2.png
Description: PNG image


reply via email to

[Prev in Thread] Current Thread [Next in Thread]