Hi David,

On Sat, Oct 11, 2014 at 4:45 PM, David Bellows <[email protected]>
wrote:

> >The attached function will work with more complex music expressions.
>
> Nicely done! I really like the greater flexibility achieved based on using
> ledger lines. Fortunately in this project I don't use chords so that's not
> a problem
>
>
Well, in any case the attached now works with chords :)

The rule is that an ottava is only applied if all of the notes within the
chord have at least a certain number of ledger lines.

I'm thinking there ought to be some sort of resistance-to-change factor
which overrules the strict this-many-ledger-lines-gets-an-ottava rule.
Otherwise, if you hop between chords and single notes, you can get more
ottavas than is comfortable to read.

The code for build-new-elts needs to be refactored a bit.

less fortunately is that I need it for the bassa as well. But I will look
> over the code and see if I can't figure it out for myself.
>

Yes, you could insert an expression into build-new-elts which would look at
the number of ledger lines and insert a (list (makeMusic 'OttavaMusic
'ottava-number -1)) to create the 8va bassa.  Of course, you'd need one to
shut it off with (list (makeMusic 'OttavaMusic 'ottava-number 0)).

This will all be better once this thing has the ability to detect the
current clef.  It looks like that's possible, because calling \clef ...
adds a 'PropertySet event to the mix, and 'clefMiddleCPosition (which the
ledger-line counter is designed to work with) is available.

Detecting the clef would be useful for 8va bassa, because it's never used
with treble clef (as I remember from Gardner Read).

Anyway, hope this is helpful.

--David

P.S.  It's now \ottavate instead of \octavate
\version "2.19.10"

\header {
  tagline = ##f
}

#(define (ledger-line-no middle-C-pos p)
   "Returns the number of ledger-lines a pitch @var{p} will have with
middle C position @var{middle-C-pos} expressed as staff-steps from the
middle staff line."
   (let* ((ps (ly:pitch-steps p))
          (mid-staff-steps (- middle-C-pos))
          (top-line (+ mid-staff-steps 4))
          (bottom-line (- mid-staff-steps 4))
          (above? (> ps top-line))
          (below? (< ps bottom-line))
          (steps-outside-staff
           (cond
            (below? (- ps bottom-line))
            (above? (- ps top-line))
            (else 0))))
     (truncate (/ steps-outside-staff 2))))


ottavate =
#(define-music-function (parser location threshold mus)
   (integer? ly:music?)
   "Create an ottava for notes which have at least @var{threshold} ledger lines"
   (let ((up-an-octave (list (make-music 'OttavaMusic 'ottava-number 1)))
         (loco (list (make-music 'OttavaMusic 'ottava-number 0))))
     
     (define (build-new-elts mus-expr new-expr start-loco? start-ottava?)
       (if (null? mus-expr)
           ;; ensure that ottava does not extend past a localized
           ;; use of \octavate
           (append new-expr loco)
          
           (cond
            ((music-is-of-type? (car mus-expr) 'event-chord)
             (cond
              ((and
                start-ottava?
                (every (lambda (p)
                         (>= (ledger-line-no -6 (ly:music-property p 'pitch)) threshold))
                  (ly:music-property (car mus-expr) 'elements)))
               (build-new-elts
                (cdr mus-expr)
                (append
                 new-expr
                 up-an-octave
                 (list (car mus-expr)))
                #t #f))
              ((and 
                start-loco?
                (any (lambda (p)
                       (< (ledger-line-no -6 (ly:music-property p 'pitch)) threshold))
                  (ly:music-property (car mus-expr) 'elements)))
               (build-new-elts
                (cdr mus-expr)
                (append
                 new-expr
                 loco
                 (list (car mus-expr)))
                #f #t))
              (else (build-new-elts
                     (cdr mus-expr)
                     (append new-expr (list (car mus-expr)))
                     #t #t))))
            
            ((music-is-of-type? (car mus-expr) 'note-event)
             (let ((p (ly:music-property (car mus-expr) 'pitch)))
               (cond
                ((and (ly:pitch? p)
                      start-ottava?
                      (>= (ledger-line-no -6 p) threshold))
                 (build-new-elts
                  (cdr mus-expr)
                  (append
                   new-expr
                   up-an-octave
                   (list (car mus-expr)))
                  #t #f))
                ((and (ly:pitch? p)
                      start-loco?
                      (< (ledger-line-no -6 p) threshold))
                 (build-new-elts
                  (cdr mus-expr)
                  (append
                   new-expr
                   loco
                   (list (car mus-expr)))
                  #f #t))
                (else
                 (build-new-elts
                  (cdr mus-expr)
                  (append new-expr (list (car mus-expr)))
                  #t #t)))))
            
            (else 
             (build-new-elts
              (cdr mus-expr)
              (append new-expr (list (car mus-expr)))
              #t #t)))))
   
     (define (recurse music)
       (let ((elts (ly:music-property music 'elements))
             (e (ly:music-property music 'element)))
         (if (ly:music? e)
             (recurse e))
         (if (pair? elts)
             (if (or
                  
                  (any (lambda (elt) (music-is-of-type? elt 'note-event)) elts)
                  (any (lambda (elt) (music-is-of-type? elt 'event-chord)) elts))
                 (set! (ly:music-property music 'elements)
                       (build-new-elts elts '() #t #t))
                 (map recurse elts)))))
   
     (recurse mus)
     
     ;(display-scheme-music mus)
   
     mus))

%%%%%%%%%%% EXAMPLE %%%%%%%%%%%%

music = \relative c''' {
  \repeat volta 2 {
    a8 b c d e f g a
  }
}

{
  \ottavate #5 \music
  \ottavate #4 \music
  \ottavate #3 \music
  \ottavate #2 \music
}

musictwo = \new PianoStaff <<
  \new Staff { \music R1 }
  \new Staff { \unfoldRepeats \transpose c e { \music } }
>>

{
  \ottavate #3 \musictwo
}

musicthree =
\new PianoStaff <<
  \relative c''' {
    \new Staff {
      \key g \major
      \time 3/4
      \new Voice {
        <a c>8 <b d> <c e> <d fis> <e g> <fis a> <g b> <a c> <b d> <c e> <d fis> <e g>
        <e g> <d fis> <c e> <b d> <a c> <g b> <fis a> <e g> <d fis> <c e> <b d> <a c>
      }
    }
  }
  \relative c'' {
    \new Staff {
      \key g \major
      \new Voice {
        <a c>8 <b d> <c e> <d fis> <e g> <fis a> <g b> <a c> <b d> <c e> <d fis> <e g>
        <e g> <d fis> <c e> <b d> <a c> <g b> <fis a> <e g> <d fis> <c e> <b d> <a c>
      }
    }
  }
>>

{
  \ottavate #1 \musicthree
}
_______________________________________________
lilypond-user mailing list
[email protected]
https://lists.gnu.org/mailman/listinfo/lilypond-user

Reply via email to