lilypond-user
[Top][All Lists]
Advanced

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

Re: Set a temporary tempo change


From: Aaron Hill
Subject: Re: Set a temporary tempo change
Date: Mon, 18 Nov 2019 07:54:48 -0800
User-agent: Roundcube Webmail/1.3.8

On 2019-11-18 6:24 am, David Kastrup wrote:
Aaron Hill <address@hidden> writes:
Not sure if this is really the right way to do things:

It isn't.  It maintains the "stack" in a global variable rather than
some context property, meaning that when several iterations interlock
(like with tempo being changed in several contexts or in polyrhythmic
situations), chaos will ensue.

Ah... you're no fun. To misquote Willy Wonka, "A little [chaos] now and then is relished by the wisest men." (:

But seriously, I was imagining only the simplest use case. So, here's yet again another take:

%%%%
\version "2.19.83"

#(begin
  (set-object-property! 'tempoStack 'translation-type? list?)
  (set-object-property! 'tempoStack 'translation-doc
    "A stack to keep track of previous tempi.")
  (set! all-translation-properties
    (cons 'tempoStack all-translation-properties)))

pushTempo = #(define-music-function () ()
  (define (pushTempoHelper ctx)
    (let ((tempoStack (ly:context-property ctx 'tempoStack '()))
          (tempo (ly:context-property ctx 'tempoWholesPerMinute #f)))
      (set! tempoStack (cons tempo tempoStack))
      (ly:context-set-property! ctx 'tempoStack tempoStack)))
  #{ \context Score \applyContext $pushTempoHelper #})
popTempo = #(define-music-function () ()
  (define (popTempoHelper ctx)
    (let ((tempoStack (ly:context-property ctx 'tempoStack '())))
      (if (null? tempoStack)
        (ly:input-warning (*location*)
          "Unable to pop a tempo. Did you forget to \\pushTempo?")
        (let ((tempo (car tempoStack)))
          (set! tempoStack (cdr tempoStack))
          (ly:context-set-property! ctx 'tempoStack tempoStack)
          (if tempo
            (ly:context-set-property! ctx 'tempoWholesPerMinute tempo)
            (ly:context-unset-property ctx 'tempoWholesPerMinute))))))
  #{ \context Score \applyContext $popTempoHelper #})

\score {
  {
    \markLengthOn
    \tempo "I. Default"
    { b'4 4 4 4 } \bar "||"
    \pushTempo \tempo "II. Andante" 4=90
    { b'4 4 4 4 } \bar "||"
    \pushTempo \tempo "III. Allegro" 4=140
    { b'4 4 4 4 } \bar "||"
    \popTempo \tempo "Tempo II"
    { b'4 4 4 4 } \bar "||"
    \popTempo \tempo "Tempo I"
    { b'4 4 4 4 } \bar "||"
    \popTempo \tempo "Tempo 0?!"
    { b'4 4 4 4 } \bar "|."
  }
  \layout {} \midi {}
}
%%%%

I tried to follow the pattern in define-context-properties.scm, but there is no documentation in LM, NR, Extending nor Internals on this topic. David, would you kindly let me know if I am overlooking something?


-- Aaron Hill



reply via email to

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