\version "2.14.0" \header { texidoc = " This snippet defines a function, mixedMeter, that can be used to make subdivided time signatures. It automatically sets the measure length and beam grouping correctly. For now, the implementation is really ugly. Hopefully somebody can clean up. If the function is saved in mixed-meter.ly then the given example would be entered as \\include \"mixed-meter.ly\" @{ \\mixedMeter #'(3 2 2 3 8) \\repeat unfold 10 c'8 \\repeat unfold 20 c'16 @} " doctitle = "Mixed Meter - automatic compound time signatures" } #(ly:load "markup.scm") #(define (compound-time . args) (let* ((revargs (reverse args)) (num (car revargs)) (dens (reverse (cdr revargs)))) (make-override-markup '(baseline-skip . 0) (make-number-markup (make-line-markup (cons (make-column-markup (list (car dens) num)) (map (lambda (den) (make-line-markup (list (make-vcenter-markup "+") (make-column-markup (list den num))))) (cdr dens)))))))) #(define (sum-list lst) (if (pair? lst) (+ (car lst) (sum-list (cdr lst))) 0)) #(ly:load "auto-beam.scm") #(define (make-auto-beam-setting setting num den . rest) (context-spec-music (make-apply-context (lambda (c) (override-property-setting c 'autoBeamSettings setting (ly:make-moment num den)))) (if (and (pair? rest) (symbol? (car rest))) (car rest) 'Voice))) mixedMeter = #(define-music-function (parser location args) (pair?) #{ #(let* ((revargs (reverse $args)) (num (car revargs)) (dens (reverse (cdr revargs)))) (letrec ((make-auto-beam-settings (lambda (lst accum) (if (pair? lst) (begin (cons (make-auto-beam-setting `(end * * ,(sum-list dens) ,num) accum num) (make-auto-beam-settings (cdr lst) (+ accum (car lst))))) '())))) (ly:export (make-music 'SequentialMusic 'elements (make-auto-beam-settings (cdr dens) (car dens)))))) \override Staff.TimeSignature #'stencil = #ly:text-interface::print \override Staff.TimeSignature #'text = #(apply compound-time (map number->string $args)) \set Staff.beatGrouping = #(reverse (cdr (reverse $args))) \set Timing.measureLength = #(ly:make-moment (sum-list (cdr (reverse $args))) (car (reverse $args))) \set Timing.beatLength = #(ly:make-moment 1 (car (reverse $args))) #} ) %%% CUT HERE! { \mixedMeter #'(3 2 2 3 8) \repeat unfold 10 c'8 \repeat unfold 20 c'16 }