Hi Kevin,

After I made some adjustments to my score, I was still able to find a problem 
which only happens on rare occasions. That is, the bar widths don't expand 
according to the time signatures' width when time signatures exceed the bar 
lines (see attachment).

Later I found out that this problem is caused by the extra-spacing-width 
property. Being set to #'(+inf.0 . -inf.0) by default, the time signatures' 
lengths are not aware by the bar widths. I tried to set extra-spacing-width to 
#'(0 . 0.8) (Time signature objects' default value), this solves the problem, 
however, the problem about the markup text being pushed to the left when using 
\textLengthOn occurs again.

I think some possible solutions for this problem would be either to make text 
scripts from other staves unaware of the time signature text scripts or to 
expand bar widths when the text scripts' widths are exceeding them.

Thanks,
Leo
\version "2.19.0"

#(define (Time_signature_markup_engraver context)
   (let ((time-sig '())
         (time-sig-copy #f)
         (previous-was-grace #f)) ; to avoid printing twice at grace notes
     (make-engraver
      (acknowledgers
       ((time-signature-interface engraver grob source-engraver)
        (let* ((current-moment (ly:context-current-moment context))
               (grace-nom (ly:moment-grace-numerator current-moment)))
          (if (not (eqv? 0 grace-nom))
              (begin
               (set! previous-was-grace #t)
               (set! time-sig grob))
              (if (and (eqv? 0 grace-nom) previous-was-grace)
                  (begin
                   (set! previous-was-grace #f)
                   (set! time-sig '()))
                  (set! time-sig grob))))))
      ((process-acknowledged engraver)
       (and (not (null? time-sig))
            (let* ((time-sig-copy (ly:engraver-make-grob
                                   engraver
                                   'TextScript
                                   time-sig))
                   (copy-prop (lambda (prop)
                                (ly:grob-set-property!
                                 time-sig-copy
                                 prop
                                 (ly:grob-property time-sig prop))))
                   (timing-context (ly:context-find context 'Timing))
                   (timing-time-sig
                    (ly:context-grob-definition timing-context 'TimeSignature))
                   (timing-time-sig-stencil
                    (ly:assoc-get 'stencil timing-time-sig '()))
                   (prop-list '(fraction style font-size cause)))
              (map copy-prop prop-list)
              (ly:grob-set-property! time-sig-copy 'stencil
                timing-time-sig-stencil)
              (ly:grob-set-parent! time-sig-copy Y time-sig)
              (ly:grob-set-parent! time-sig-copy X time-sig)
              (set! time-sig '())
              )))
      ((stop-translation-timestep engraver)
       (set! time-sig-copy #f)))))

#(define (remove-except-at-line-end grob)
   (if (not (equal? (ly:item-break-dir grob) LEFT))
       (ly:grob-set-property! grob 'stencil #f)))

#(define (remove-at-end grob)
   (if (equal? (ly:item-break-dir grob) LEFT)
       (ly:grob-set-property! grob 'stencil #f)))

#(define (center-over-barline grob)
   (if (equal? (ly:item-break-dir grob) 0)
       (let* ((x-extent (ly:grob-property grob 'X-extent))
              (width (interval-length x-extent)))
         (ly:grob-set-property! grob 'X-offset (* -1 (/ width 2))))))

#(define (center-over-barline-and-remove-at-end grob)
   (begin
    (remove-at-end grob)
    (center-over-barline grob)))

#(define (left-align-at-end grob)
   (and (and (ly:item? grob)
             (equal? (ly:item-break-dir grob) LEFT))
        (ly:grob-set-property! grob 'self-alignment-X 1)))

timeSignatures = {
  \tempo 4 = 80
  \time 4/4 s1
  \time 3/8 s4.
  \time 3/4 s2.
  \time 4/4 s1
  \time 2/4 \acciaccatura s8 s2
  \compoundMeter #'((3 8) (1 16) (1 16) (1 16))
  s4. s16 s16 s16
  \time 4/4 \acciaccatura s8 s1
}

\score {
  \layout {
    \context {
      \Score
      \override MetronomeMark.break-align-symbols = #'(staff-bar time-signature)
      \remove "Bar_number_engraver"
    }
    \context {
      \Staff
      \override MultiMeasureRest.spacing-pair = #'(break-alignment . staff-bar)
      \override TimeSignature.stencil = ##f
      %\remove "Time_signature_engraver"
    }
    \context {
      \Score
    }
  }
  <<
    {
    \new Dynamics \with {
      \consists "Time_signature_engraver"
      \consists \Time_signature_markup_engraver
      \override TimeSignature.font-size = #8
      \override TimeSignature.font-name = #"Roboto Bold"
      \override TimeSignature.before-line-breaking = #remove-except-at-line-end
      \override TimeSignature.break-align-symbol = #'staff-bar
      %\override TextScript.font-size = #8
      \override TextScript.font-name = #"Roboto Bold"
      \override TextScript.before-line-breaking = #remove-at-end
      %The example is a bit exaggerated, but it demonstrates the problem.
      %↓ use this command to make bar widths aware of the time signature markups' width.
      %\override TextScript.extra-spacing-width = #'(0 . 0.8)
      \override TextScript.direction = #UP
      \override TextScript.Y-offset = #0
      \numericTimeSignature
    }
    {
      \timeSignatures
    }
    }
    %{
    \new Dynamics \with {
      \consists "Time_signature_engraver"
      \override TimeSignature.font-size = #8
      \override TimeSignature.break-align-symbol = #'staff-bar
      \override TimeSignature.break-align-anchor = ##f
      \override TimeSignature.extra-spacing-width = #'(0 . 0)
      \numericTimeSignature
    }
    {
      \timeSignatures
    }
    %}
    
    \new StaffGroup \with {} <<
   
      \new Staff \with {
        \consists "Bar_number_engraver"
      }
      \relative c' {
        \textLengthOn
        \time 4/4
        c4 ( _\markup \column {
          "← Objects failed to appear"
          "below the time signature"
          "when using \\textLengthOn"
        }
        \textLengthOff
        d4 e4 f4 )
        \time 3/8
        a'4 ( g8 ) 
        \time 3/4
        R2. 
        \time 4/4
        c1
        
        \time 2/4
        a8 ^\markup \column {
          "← Time signature appear twice" 
          "when one staff has a grace note" 
          "as the first note in a bar"
        } g8 f8 e8
        
        \compoundMeter #'((3 8) (1 16) (1 16) (1 16))
        a2 g16
        
        \time 4/4
        c4 c c c
        
      }
   
      \new Staff \relative c' {
        \time 4/4
        R1
        \time 3/8
        R4.
        \clef bass
        \time 3/4
        a,2. \> \startTextSpan 
        \break
        \time 4/4
        c2 _\markup \column {
          "  "
          "↑"
          "Harpin stops below the time signature"
        }
        ^\markup \column {
          "TextSpanner stops below the time signature"
          "↓"
        }
        e2 \! \stopTextSpan
        \clef treble
        \time 2/4
        \acciaccatura f'8 a8
        g8 f8 e8
        \compoundMeter #'((3 8) (1 16) (1 16) (1 16))
        a2 g16
        \time 4/4
        \acciaccatura f'8
        c4 c c c
      }
   >>
      \new Staff \relative c' { 
        \clef bass 
        \time 4/4
        R1 
        \time 3/8
        R4. 
        \time 3/4
        R2. 
        \time 4/4
        c1
        \time 2/4
        a8 g8 f8 e8
        \compoundMeter #'((3 8) (1 16) (1 16) (1 16))
        a2 g16
        \time 4/4
        c4 c c c
      }
    >>
  
}

Reply via email to