@c -*- coding: utf-8; mode: texinfo; -*- @ignore Translation of GIT committish: FILL-IN-HEAD-COMMITTISH When revising a translation, copy the HEAD committish of the version that you are working on. For details, see the Contributors' Guide, node Updating translation committishes.. @end ignore @c \version "2.14.0" @node Interfaces for programmers @chapter Interfaces for programmers Advanced tweaks may be performed by using Scheme. If you are not familiar with Scheme, you may wish to read our @ref{Scheme tutorial}. @menu * Lilypond code blocks:: * Scheme functions:: * Music functions:: * Markup functions:: * Contexts for programmers:: * Callback functions:: * Inline Scheme code:: * Difficult tweaks:: @end menu @node Lilypond code blocks @section Lilypond code blocks Lilypond code blocks look like @example #@{ @var{Lilypond code} #@} @end example They can be used anywhere where you can write scheme code: the scheme reader actually is changed for accommodating Lilypond code blocks. When the Lilypond code block is being read, it is parsed superficially and replaced by a call to the Lilypond parser which is executed at runtime to interpret the Lilypond code block. The point of the superficial parsing is the interpretation of @code{$} signs which can be used for splicing in expressions from the surrounding lexical scheme context (like @code{let} variables and function parameters). @code{$} can be used in the following ways: @table @code @item $$ just passes a single @code{$} to the Lilypond parser. @item $@var{form} will evaluate the Scheme form at runtime and splice its value as an identifier @code{\form} into the Lilypond parser. Depending on the value type, it may be interpreted as several different syntactic entities. @item #$@var{form} will evaluate the Scheme form at runtime and splice its value as a Scheme expression into the Lilypond parser. @item #@var{form} Forms in Scheme expressions started with @code{#} are read and parsed recursively for @code{$} signs. Those are treated as follows: @item #@dots{}$@var{variable} splices the value of the variable into the surrounding expression. @item #@dots{}($ @var{form} @dots{}) splices the value of the form into the surrounding expression. As opposed to a Lilypond level @code{$@var{form}}, you need to separate the form with a blank, making @code{$} be recognizable as a separate Scheme symbol. @end table A LilyPond code block may contain anything that you can use on the right side of an assignment. In addition, an empty LilyPond block corresponds to a void music expression, and a LilyPond block containing multiple music events gets turned into a sequential music expression. @node Scheme functions @section Scheme functions @emph{Scheme functions} are scheme procedures that can create scheme expressions from input written in Lilypond syntax. They can be called in pretty much all places where using @code{#} for specifying a value in Scheme syntax is allowed. While scheme has functions of its own, this chapter is concerned with @emph{syntactic} functions, functions that receive arguments specified in Lilypond syntax. @menu * Scheme function definitions:: * Scheme function usage:: * Void scheme functions:: @end menu @node Scheme function definitions @subsection Scheme function definitions The general form for defining scheme functions is: @example function = #(define-scheme-function (parser location @var{arg1} @var{arg2} @dots{}) (@var{type1?} @var{type2?} @dots{}) @var{body}) @end example @noindent where @multitable @columnfractions .33 .66 @item @code{@var{argN}} @tab @var{n}th argument @item @code{@var{typeN?}} @tab a scheme @emph{type predicate} for which @code{@var{argN}} must return @code{#t}. Some of these predicates are specially recognized by the parser, see below. @item @code{@var{body}} @tab A sequence of scheme forms evaluated in order, the last one being used as the return value of the scheme function. It may contain LilyPond code blocks enclosed in hashed braces (@tie{}@w{@code{#@{@dots{}#@}}}@tie{}), like described in @ref{Lilypond code blocks}. Within LilyPond code blocks, use @code{$} to reference function arguments (eg., @samp{$arg1}) or to start an inline scheme expression containing function arguments (eg., @w{@samp{$(cons arg1 arg2)}}). @end multitable @noindent Some type predicates are specially recognized by the parser and will make the parser look for the respective arguments in Lilypond syntax rather than in Scheme syntax. Currently these are @code{ly:music?}, @code{markup?}, @code{ly:pitch?}, and @code{ly:duration?}. If you really want to input one of the special items as a Scheme rather than a Lilypond expression, you may write them as a Scheme expression that calls @code{ly:export} at its outermost level. Other type predicates, including user-defined ones, will make the respective argument only be accepted as a Scheme expression, usually introduced with @code{#} or as the result of calling a scheme function itself. For a list of available type predicates, see @ruser{Predefined type predicates}. @seealso Notation Reference: @ruser{Predefined type predicates}. Installed Files: @file{lily/music-scheme.cc}, @file{scm/c++.scm}, @file{scm/lily.scm}. @node Scheme function usage @subsection Scheme function usage Scheme functions can be called pretty much anywhere where a Scheme expression starting with @code{#} can be written. You call a scheme function by writing its name preceded by @code{\}, followed by its arguments. Apart from places where a Scheme value is required, there are a few places where @code{#} expressions are accepted and evaluated for their side effects but otherwise ignored. Mostly those are the places where an assignment would be acceptable as well. There are a few special places where an argument matching @code{ly:music?} has to be either a music identifier or a music expression enclosed in @code{@{}@dots{}@code{@}} or @code{<<}@dots{}@code{>>} explicitly, so that possibly following optional durations or postevents can't be confused with additional arguments. One obvious place is before a @code{ly:duration?} predicate. Another is as the last argument of a scheme function when it is used in a place where such optional parts could be considered either part of the music argument or not. In those rare cases, you have to delimit your music arguments appropriately to spare Lilypond from getting confused. @node Void scheme functions @subsection Void scheme functions Sometimes a function is only executed for its side effects. In that case, using a Scheme function means that its value will not usually be considered: @example noPointAndClick = #(define-scheme-function (parser location) () (ly:set-option 'point-and-click #f)) ... \noPointAndClick % disable point and click @end example @node Music functions @section Music functions @emph{Music functions} are scheme procedures that can create music expressions automatically, and can be used to greatly simplify the input file. @menu * Music function definitions:: * Music function usage:: * Simple substitution functions:: * Intermediate substitution functions:: * Mathematics in functions:: * Functions without arguments:: * Void music functions:: @end menu @node Music function definitions @subsection Music function definitions The general form for defining music functions is: @example function = #(define-music-function (parser location @var{arg1} @var{arg2} @dots{}) (@var{type1?} @var{type2?} @dots{}) @var{body}) @end example @noindent quite in analogy to @ref{Scheme function definitions}. More often than not, @var{body} will be a @ref{Lilypond code blocks, Lilypond code block}. For a list of available type predicates, see @ruser{Predefined type predicates}. @seealso Notation Reference: @ruser{Predefined type predicates}. Installed Files: @file{lily/music-scheme.cc}, @file{scm/c++.scm}, @file{scm/lily.scm}. @node Music function usage @subsection Music function usage Music functions may currently be used in three places. Depending on where they are used, restrictions apply in order to be able to parse them unambiguously. The result a music function returns must be compatible with the context in which it is called. @itemize @item At top level in a music expression. There are no special restrictions on the argument list. @item As a post-event. All trailing arguments of the music function with the predicate @code{ly:music?} will get parsed also as post-events. Note that returning post-events will also be acceptable for music functions called at top level, leading to a result roughly equivalent to @example s 1*0-\fun @end example @item As a chord constituent. All trailing arguments of the music function with the predicate @code{ly:music?} will get parsed also as chord constituents. @end itemize @noindent The special rules for trailing arguments make it possible to write polymorphic functions like @code{\tweak} that can be applied to different constructs. There is another somewhat special rule: if you have a predicate @code{ly:music?} directly before a @code{ly:duration?} predicate, then the corresponding music expression must be either a music identifier, or literal sequential or parallel music enclosed in @code{@{}@dots{}@code{@}} or @code{<<}@dots{}@code{>>} explicitly. Otherwise, Lilypond could get confused about where the music ends and the duration starts. @node Simple substitution functions @subsection Simple substitution functions Simple substitution functions are music functions whose output music expression is written in LilyPond format and contains function arguments in the output expression. They are described in @ruser{Substitution function examples}. @node Intermediate substitution functions @subsection Intermediate substitution functions Intermediate substitution functions involve a mix of Scheme code and LilyPond code in the music expression to be returned. Some @code{\override} commands require an argument consisting of a pair of numbers (called a @emph{cons cell} in Scheme). The pair can be directly passed into the music function, using a @code{pair?} variable: @example manualBeam = #(define-music-function (parser location beg-end) (pair?) #@{ \once \override Beam #'positions = $beg-end #@}) \relative c' @{ \manualBeam #'(3 . 6) c8 d e f @} @end example Alternatively, the numbers making up the pair can be passed as separate arguments, and the Scheme code used to create the pair can be included in the music expression: @lilypond[quote,verbatim,ragged-right] manualBeam = #(define-music-function (parser location beg end) (number? number?) #{ \once \override Beam #'positions = $(cons beg end) #}) \relative c' { \manualBeam #3 #6 c8 d e f } @end lilypond @node Mathematics in functions @subsection Mathematics in functions Music functions can involve Scheme programming in addition to simple substitution, @lilypond[quote,verbatim,ragged-right] AltOn = #(define-music-function (parser location mag) (number?) #{ \override Stem #'length = $(* 7.0 mag) \override NoteHead #'font-size = $(inexact->exact (* (/ 6.0 (log 2.0)) (log mag))) #}) AltOff = { \revert Stem #'length \revert NoteHead #'font-size } \relative c' { c2 \AltOn #0.5 c4 c \AltOn #1.5 c c \AltOff c2 } @end lilypond @noindent This example may be rewritten to pass in music expressions, @lilypond[quote,verbatim,ragged-right] withAlt = #(define-music-function (parser location mag music) (number? ly:music?) #{ \override Stem #'length = $(* 7.0 mag) \override NoteHead #'font-size = $(inexact->exact (* (/ 6.0 (log 2.0)) (log mag))) $music \revert Stem #'length \revert NoteHead #'font-size #}) \relative c' { c2 \withAlt #0.5 { c4 c } \withAlt #1.5 { c c } c2 } @end lilypond @node Functions without arguments @subsection Functions without arguments In most cases a function without arguments should be written with a variable, @example dolce = \markup@{ \italic \bold dolce @} @end example However, in rare cases it may be useful to create a music function without arguments, @example displayBarNum = #(define-music-function (parser location) () (if (eq? #t (ly:get-option 'display-bar-numbers)) #@{ \once \override Score.BarNumber #'break-visibility = ##f #@} #@{#@})) @end example To actually display bar numbers where this function is called, invoke @command{lilypond} with @example lilypond -d display-bar-numbers FILENAME.ly @end example @node Void music functions @subsection Void music functions A music function must return a music expression. If you want to execute a function only for its side effect, it might make more sense to use a scheme function instead. But there may be cases where you sometimes want to produce a music expression, and sometimes not (like in the previous example). Returning a @code{void} music expression via @code{#@{ #@}} will do that. @node Markup functions @section Markup functions Markups are implemented as special Scheme functions which produce a @code{Stencil} object given a number of arguments. @menu * Markup construction in Scheme:: * How markups work internally:: * New markup command definition:: * New markup list command definition:: @end menu @node Markup construction in Scheme @subsection Markup construction in Scheme @cindex defining markup commands The @code{markup} macro builds markup expressions in Scheme while providing a LilyPond-like syntax. For example, @example (markup #:column (#:line (#:bold #:italic "hello" #:raise 0.4 "world") #:larger #:line ("foo" "bar" "baz"))) @end example @noindent is equivalent to: @example #@{ \markup \column @{ \line @{ \bold \italic "hello" \raise #0.4 "world" @} \larger \line @{ foo bar baz @} @} #@} @end example @noindent This example demonstrates the main translation rules between regular LilyPond markup syntax and Scheme markup syntax. Using @code{#@{ @dots{} #@}} for entering in Lilypond syntax will often be most convenient, but we explain how to use the @code{markup} macro to get a Scheme-only solution. @quotation @multitable @columnfractions .3 .3 @item @b{LilyPond} @tab @b{Scheme} @item @code{\markup markup1} @tab @code{(markup markup1)} @item @code{\markup @{ markup1 markup2 ... @}} @tab @code{(markup markup1 markup2 ... )} @item @code{\markup-command} @tab @code{#:markup-command} @item @code{\variable} @tab @code{variable} @item @code{\center-column @{ ... @}} @tab @code{#:center-column ( ... )} @item @code{string} @tab @code{"string"} @item @code{#scheme-arg} @tab @code{scheme-arg} @end multitable @end quotation The whole Scheme language is accessible inside the @code{markup} macro. For example, You may use function calls inside @code{markup} in order to manipulate character strings. This is useful when defining new markup commands (see @ref{New markup command definition}). @knownissues The markup-list argument of commands such as @code{#:line}, @code{#:center}, and @code{#:column} cannot be a variable or the result of a function call. @lisp (markup #:line (function-that-returns-markups)) @end lisp @noindent is invalid. One should use the @code{make-line-markup}, @code{make-center-markup}, or @code{make-column-markup} functions instead, @lisp (markup (make-line-markup (function-that-returns-markups))) @end lisp @node How markups work internally @subsection How markups work internally In a markup like @example \raise #0.5 "text example" @end example @noindent @code{\raise} is actually represented by the @code{raise-markup} function. The markup expression is stored as @example (list raise-markup 0.5 (list simple-markup "text example")) @end example When the markup is converted to printable objects (Stencils), the @code{raise-markup} function is called as @example (apply raise-markup @var{\layout object} @var{list of property alists} 0.5 @var{the "text example" markup}) @end example The @code{raise-markup} function first creates the stencil for the @code{text example} string, and then it raises that Stencil by 0.5 staff space. This is a rather simple example; more complex examples are in the rest of this section, and in @file{scm/define-markup-commands.scm}. @node New markup command definition @subsection New markup command definition This section discusses the definition of new markup commands. @menu * Markup command definition syntax:: * On properties:: * A complete example:: * Adapting builtin commands:: @end menu @node Markup command definition syntax @unnumberedsubsubsec Markup command definition syntax New markup commands can be defined using the @code{define-markup-command} Scheme macro, at top-level. @lisp (define-markup-command (@var{command-name} @var{layout} @var{props} @var{arg1} @var{arg2} ...) (@var{arg1-type?} @var{arg2-type?} ...) [ #:properties ((@var{property1} @var{default-value1}) ...) ] ..command body..) @end lisp The arguments are @table @code @item @var{command-name} the markup command name @item layout the @q{layout} definition. @item props a list of associative lists, containing all active properties. @item @var{argi} @var{i}th command argument @item @var{argi-type?} a type predicate for the i@var{th} argument @end table If the command uses properties from the @code{props} arguments, the @code{#:properties} keyword can be used to specify which properties are used along with their default values. Arguments are distinguished according to their type: @itemize @item a markup, corresponding to type predicate @code{markup?}; @item a list of markups, corresponding to type predicate @code{markup-list?}; @item any other scheme object, corresponding to type predicates such as @code{list?}, @code{number?}, @code{boolean?}, etc. @end itemize There is no limitation on the order of arguments (after the standard @code{layout} and @code{props} arguments). However, markup functions taking a markup as their last argument are somewhat special as you can apply them to a markup list, and the result is a markup list where the markup function (with the specified leading arguments) has been applied to every element of the original markup list. Since replicating the leading arguments for applying a markup function to a markup list is cheap mostly for Scheme arguments, you avoid performance pitfalls by just using Scheme arguments for the leading arguments of markup functions that take a markup as their last argument. @node On properties @unnumberedsubsubsec On properties The @code{layout} and @code{props} arguments of markup commands bring a context for the markup interpretation: font size, line width, etc. The @code{layout} argument allows access to properties defined in @code{paper} blocks, using the @code{ly:output-def-lookup} function. For instance, the line width (the same as the one used in scores) is read using: @example (ly:output-def-lookup layout 'line-width) @end example The @code{props} argument makes some properties accessible to markup commands. For instance, when a book title markup is interpreted, all the variables defined in the @code{\header} block are automatically added to @code{props}, so that the book title markup can access the book title, composer, etc. It is also a way to configure the behaviour of a markup command: for example, when a command uses font size during processing, the font size is read from @code{props} rather than having a @code{font-size} argument. The caller of a markup command may change the value of the font size property in order to change the behaviour. Use the @code{#:properties} keyword of @code{define-markup-command} to specify which properties shall be read from the @code{props} arguments. The example in next section illustrates how to access and override properties in a markup command. @node A complete example @unnumberedsubsubsec A complete example The following example defines a markup command to draw a double box around a piece of text. Firstly, we need to build an approximative result using markups. Consulting the @ruser{Text markup commands} shows us the @code{\box} command is useful: @lilypond[quote,verbatim,ragged-right] \markup \box \box HELLO @end lilypond Now, we consider that more padding between the text and the boxes is preferable. According to the @code{\box} documentation, this command uses a @code{box-padding} property, which defaults to 0.2. The documentation also mentions how to override it: @lilypond[quote,verbatim,ragged-right] \markup \box \override #'(box-padding . 0.6) \box A @end lilypond Then, the padding between the two boxes is considered too small, so we override it too: @lilypond[quote,verbatim,ragged-right] \markup \override #'(box-padding . 0.4) \box \override #'(box-padding . 0.6) \box A @end lilypond Repeating this lengthy markup would be painful. This is where a markup command is needed. Thus, we write a @code{double-box} markup command, taking one argument (the text). This draws the two boxes, with some padding. @lisp #(define-markup-command (double-box layout props text) (markup?) "Draw a double box around text." (interpret-markup layout props #@{\markup \override #'(box-padding . 0.4) \box \override #'(box-padding . 0.6) \box @{ $text @}#@})) @end lisp or, equivalently @lisp #(define-markup-command (double-box layout props text) (markup?) "Draw a double box around text." (interpret-markup layout props (markup #:override '(box-padding . 0.4) #:box #:override '(box-padding . 0.6) #:box text))) @end lisp @code{text} is the name of the command argument, and @code{markup?} its type: it identifies it as a markup. The @code{interpret-markup} function is used in most of markup commands: it builds a stencil, using @code{layout}, @code{props}, and a markup. In the second case, this markup is built using the @code{markup} scheme macro, see @ref{Markup construction in Scheme}. The transformation from @code{\markup} expression to scheme markup expression is straight-forward. The new command can be used as follow: @example \markup \double-box A @end example It would be nice to make the @code{double-box} command customizable: here, the @code{box-padding} values are hard coded, and cannot be changed by the user. Also, it would be better to distinguish the padding between the two boxes, from the padding between the inner box and the text. So we will introduce a new property, @code{inter-box-padding}, for the padding between the two boxes. The @code{box-padding} will be used for the inner padding. The new code is now as follows: @lisp #(define-markup-command (double-box layout props text) (markup?) #:properties ((inter-box-padding 0.4) (box-padding 0.6)) "Draw a double box around text." (interpret-markup layout props #@{\markup \override #`(box-padding . ,$inter-box-padding) \box \override #`(box-padding . ,$box-padding) \box @{ $text @} #@})) @end lisp Again, the equivalent version using the markup macro would be: @lisp #(define-markup-command (double-box layout props text) (markup?) #:properties ((inter-box-padding 0.4) (box-padding 0.6)) "Draw a double box around text." (interpret-markup layout props (markup #:override `(box-padding . ,inter-box-padding) #:box #:override `(box-padding . ,box-padding) #:box text))) @end lisp Here, the @code{#:properties} keyword is used so that the @code{inter-box-padding} and @code{box-padding} properties are read from the @code{props} argument, and default values are given to them if the properties are not defined. Then, these values are used to override the @code{box-padding} properties used by the two @code{\box} commands. Note the backquote and the comma in the @code{\override} argument: they allow you to introduce a variable value into a literal expression. Now, the command can be used in a markup, and the boxes padding be customized: @lilypond[quote,verbatim,ragged-right] #(define-markup-command (double-box layout props text) (markup?) #:properties ((inter-box-padding 0.4) (box-padding 0.6)) "Draw a double box around text." (interpret-markup layout props #{\markup \override #`(box-padding . ,$inter-box-padding) \box \override #`(box-padding . ,$box-padding) \box { $text } #})) \markup \double-box A \markup \override #'(inter-box-padding . 0.8) \double-box A \markup \override #'(box-padding . 1.0) \double-box A @end lilypond @node Adapting builtin commands @unnumberedsubsubsec Adapting builtin commands A good way to start writing a new markup command, is to take example on a builtin one. Most of the markup commands provided with LilyPond can be found in file @file{scm/define-markup-commands.scm}. For instance, we would like to adapt the @code{\draw-line} command, to draw a double line instead. The @code{\draw-line} command is defined as follow (documentation stripped): @lisp (define-markup-command (draw-line layout props dest) (number-pair?) #:category graphic #:properties ((thickness 1)) "..documentation.." (let ((th (* (ly:output-def-lookup layout 'line-thickness) thickness)) (x (car dest)) (y (cdr dest))) (make-line-stencil th 0 0 x y))) @end lisp To define a new command based on an existing one, copy the definition, and change the command name. The @code{#:category} keyword can be safely removed, as it is only used for generating LilyPond documentation, and is of no use for user-defined markup commands. @lisp (define-markup-command (draw-double-line layout props dest) (number-pair?) #:properties ((thickness 1)) "..documentation.." (let ((th (* (ly:output-def-lookup layout 'line-thickness) thickness)) (x (car dest)) (y (cdr dest))) (make-line-stencil th 0 0 x y))) @end lisp Then, a property for setting the gap between two lines is added, called @code{line-gap}, defaulting e.g. to 0.6: @lisp (define-markup-command (draw-double-line layout props dest) (number-pair?) #:properties ((thickness 1) (line-gap 0.6)) "..documentation.." ... @end lisp Finally, the code for drawing two lines is added. Two calls to @code{make-line-stencil} are used to draw the lines, and the resulting stencils are combined using @code{ly:stencil-add}: @lilypond[quote,verbatim,ragged-right] #(define-markup-command (my-draw-line layout props dest) (number-pair?) #:properties ((thickness 1) (line-gap 0.6)) "..documentation.." (let* ((th (* (ly:output-def-lookup layout 'line-thickness) thickness)) (dx (car dest)) (dy (cdr dest)) (w (/ line-gap 2.0)) (x (cond ((= dx 0) w) ((= dy 0) 0) (else (/ w (sqrt (+ 1 (* (/ dx dy) (/ dx dy)))))))) (y (* (if (< (* dx dy) 0) 1 -1) (cond ((= dy 0) w) ((= dx 0) 0) (else (/ w (sqrt (+ 1 (* (/ dy dx) (/ dy dx)))))))))) (ly:stencil-add (make-line-stencil th x y (+ dx x) (+ dy y)) (make-line-stencil th (- x) (- y) (- dx x) (- dy y))))) \markup \my-draw-line #'(4 . 3) \markup \override #'(line-gap . 1.2) \my-draw-line #'(4 . 3) @end lilypond @node New markup list command definition @subsection New markup list command definition Markup list commands are defined with the @code{define-markup-list-command} Scheme macro, which is similar to the @code{define-markup-command} macro described in @ref{New markup command definition}, except that where the latter returns a single stencil, the former returns a list of stencils. In the following example, a @code{\paragraph} markup list command is defined, which returns a list of justified lines, the first one being indented. The indent width is taken from the @code{props} argument. @example #(define-markup-list-command (paragraph layout props args) (markup-list?) #:properties ((par-indent 2)) (interpret-markup-list layout props #@{\markuplines \justified-lines @{ \hspace #$par-indent $args @} #@})) @end example The version using just Scheme is more complex: @example #(define-markup-list-command (paragraph layout props args) (markup-list?) #:properties ((par-indent 2)) (interpret-markup-list layout props (make-justified-lines-markup-list (cons (make-hspace-markup par-indent) args)))) @end example Besides the usual @code{layout} and @code{props} arguments, the @code{paragraph} markup list command takes a markup list argument, named @code{args}. The predicate for markup lists is @code{markup-list?}. First, the function gets the indent width, a property here named @code{par-indent}, from the property list @code{props}. If the property is not found, the default value is @code{2}. Then, a list of justified lines is made using the built-in markup list command @code{\justified-lines}, which is related to the @code{make-justified-lines-markup-list} function. A horizontal space is added at the beginning using @code{\hspace} (or the @code{make-hspace-markup} function). Finally, the markup list is interpreted using the @code{interpret-markup-list} function. This new markup list command can be used as follows: @example \markuplines @{ \paragraph @{ The art of music typography is called \italic @{(plate) engraving.@} The term derives from the traditional process of music printing. Just a few decades ago, sheet music was made by cutting and stamping the music into a zinc or pewter plate in mirror image. @} \override-lines #'(par-indent . 4) \paragraph @{ The plate would be inked, the depressions caused by the cutting and stamping would hold ink. An image was formed by pressing paper to the plate. The stamping and cutting was completely done by hand. @} @} @end example @node Contexts for programmers @section Contexts for programmers @menu * Context evaluation:: * Running a function on all layout objects:: @end menu @node Context evaluation @subsection Context evaluation @cindex calling code during interpreting @funindex \applyContext Contexts can be modified during interpretation with Scheme code. The syntax for this is @example \applyContext @var{function} @end example @code{@var{function}} should be a Scheme function that takes a single argument: the context in which the @code{\applyContext} command is being called. The following code will print the current bar number on the standard output during the compile: @example \applyContext #(lambda (x) (format #t "\nWe were called in barnumber ~a.\n" (ly:context-property x 'currentBarNumber))) @end example @node Running a function on all layout objects @subsection Running a function on all layout objects @cindex calling code on layout objects @funindex \applyOutput The most versatile way of tuning an object is @code{\applyOutput} which works by inserting an event into the specified context (@rinternals{ApplyOutputEvent}). Its syntax is @example \applyOutput @var{context} @var{proc} @end example @noindent where @code{@var{proc}} is a Scheme function, taking three arguments. When interpreted, the function @code{@var{proc}} is called for every layout object found in the context @code{@var{context}} at the current time step, with the following arguments: @itemize @item the layout object itself, @item the context where the layout object was created, and @item the context where @code{\applyOutput} is processed. @end itemize In addition, the cause of the layout object, i.e., the music expression or object that was responsible for creating it, is in the object property @code{cause}. For example, for a note head, this is a @rinternals{NoteHead} event, and for a stem object, this is a @rinternals{Stem} object. Here is a function to use for @code{\applyOutput}; it blanks note-heads on the center-line and next to it: @lilypond[quote,verbatim,ragged-right] #(define (blanker grob grob-origin context) (if (and (memq 'note-head-interface (ly:grob-interfaces grob)) (< (abs (ly:grob-property grob 'staff-position)) 2)) (set! (ly:grob-property grob 'transparent) #t))) \relative c' { a'4 e8 <<\applyOutput #'Voice #blanker a c d>> b2 } @end lilypond @node Callback functions @section Callback functions Properties (like @code{thickness}, @code{direction}, etc.) can be set at fixed values with @code{\override}, e.g. @example \override Stem #'thickness = #2.0 @end example Properties can also be set to a Scheme procedure, @lilypond[fragment,verbatim,quote,relative=2] \override Stem #'thickness = #(lambda (grob) (if (= UP (ly:grob-property grob 'direction)) 2.0 7.0)) c b a g b a g b @end lilypond @noindent In this case, the procedure is executed as soon as the value of the property is requested during the formatting process. Most of the typesetting engine is driven by such callbacks. Properties that typically use callbacks include @table @code @item stencil The printing routine, that constructs a drawing for the symbol @item X-offset The routine that sets the horizontal position @item X-extent The routine that computes the width of an object @end table The procedure always takes a single argument, being the grob. If routines with multiple arguments must be called, the current grob can be inserted with a grob closure. Here is a setting from @code{AccidentalSuggestion}, @example `(X-offset . ,(ly:make-simple-closure `(,+ ,(ly:make-simple-closure (list ly:self-alignment-interface::centered-on-x-parent)) ,(ly:make-simple-closure (list ly:self-alignment-interface::x-aligned-on-self))))) @end example @noindent In this example, both @code{ly:self-alignment-interface::x-aligned-on-self} and @code{ly:self-alignment-interface::centered-on-x-parent} are called with the grob as argument. The results are added with the @code{+} function. To ensure that this addition is properly executed, the whole thing is enclosed in @code{ly:make-simple-closure}. In fact, using a single procedure as property value is equivalent to @example (ly:make-simple-closure (ly:make-simple-closure (list @var{proc}))) @end example @noindent The inner @code{ly:make-simple-closure} supplies the grob as argument to @var{proc}, the outer ensures that result of the function is returned, rather than the @code{simple-closure} object. From within a callback, the easiest method for evaluating a markup is to use grob-interpret-markup. For example: @example my-callback = #(lambda (grob) (grob-interpret-markup grob (markup "foo"))) @end example @node Inline Scheme code @section Inline Scheme code The main disadvantage of @code{\tweak} is its syntactical inflexibility. For example, the following produces a syntax error. @example F = \tweak #'font-size #-3 -\flageolet \relative c'' @{ c4^\F c4_\F @} @end example @noindent In other words, @code{\tweak} doesn't behave like an articulation regarding the syntax; in particular, it can't be attached with @code{^} and @code{_}. Using Scheme, this problem can be avoided. The route to the result is given in @ref{Adding articulation to notes (example)}, especially how to use @code{\displayMusic} as a helping guide. @example F = #(let ((m (make-music 'ArticulationEvent 'articulation-type "flageolet"))) (set! (ly:music-property m 'tweaks) (acons 'font-size -3 (ly:music-property m 'tweaks))) m) \relative c'' @{ c4^\F c4_\F @} @end example @noindent Here, the @code{tweaks} properties of the flageolet object @code{m} (created with @code{make-music}) are extracted with @code{ly:music-property}, a new key-value pair to change the font size is prepended to the property list with the @code{acons} Scheme function, and the result is finally written back with @code{set!}. The last element of the @code{let} block is the return value, @code{m} itself. @node Difficult tweaks @section Difficult tweaks There are a few classes of difficult adjustments. @itemize @item One type of difficult adjustment involves the appearance of spanner objects, such as slurs and ties. Usually, only one spanner object is created at a time, and it can be adjusted with the normal mechanism. However, occasionally a spanner crosses a line break. When this happens, the object is cloned. A separate object is created for every system in which the spanner appears. The new objects are clones of the original object and inherit all properties, including @code{\override}s. In other words, an @code{\override} always affects all pieces of a broken spanner. To change only one part of a spanner at a line break, it is necessary to hook into the formatting process. The @code{after-line-breaking} callback contains the Scheme procedure that is called after the line breaks have been determined and layout objects have been split over different systems. In the following example, we define a procedure @code{my-callback}. This procedure @itemize @item determines if the spanner has been split across line breaks @item if yes, retrieves all the split objects @item checks if this grob is the last of the split objects @item if yes, it sets @code{extra-offset}. @end itemize This procedure is installed into @rinternals{Tie}, so the last part of the broken tie is repositioned. @lilypond[quote,verbatim,ragged-right] #(define (my-callback grob) (let* ( ;; have we been split? (orig (ly:grob-original grob)) ;; if yes, get the split pieces (our siblings) (siblings (if (ly:grob? orig) (ly:spanner-broken-into orig) '()))) (if (and (>= (length siblings) 2) (eq? (car (last-pair siblings)) grob)) (ly:grob-set-property! grob 'extra-offset '(-2 . 5))))) \relative c'' { \override Tie #'after-line-breaking = #my-callback c1 ~ \break c2 ~ c } @end lilypond @noindent When applying this trick, the new @code{after-line-breaking} callback should also call the old one, if such a default exists. For example, if using this with @code{Hairpin}, @code{ly:spanner::kill-zero-spanned-time} should also be called. @item Some objects cannot be changed with @code{\override} for technical reasons. Examples of those are @code{NonMusicalPaperColumn} and @code{PaperColumn}. They can be changed with the @code{\overrideProperty} function, which works similar to @code{\once \override}, but uses a different syntax. @example \overrideProperty #"Score.NonMusicalPaperColumn" % Grob name #'line-break-system-details % Property name #'((next-padding . 20)) % Value @end example Note, however, that @code{\override}, applied to @code{NonMusicalPaperColumn} and @code{PaperColumn}, still works as expected within @code{\context} blocks. @end itemize @node LilyPond Scheme interfaces @chapter LilyPond Scheme interfaces This chapter covers the various tools provided by LilyPond to help Scheme programmers get information into and out of the music streams. TODO -- figure out what goes in here and how to organize it