-
Notifications
You must be signed in to change notification settings - Fork 0
/
definition.ily
71 lines (67 loc) · 3.24 KB
/
definition.ily
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
\version "2.18.0"
\header {
snippet-title = "merge-rests-engraver"
snippet-author = "Jay Anderson"
snippet-source =
"http://www.mail-archive.com/lilypond-user%40gnu.org/msg69608.html"
snippet-description = \markup {
Merge rests of equal duration in different voice
}
tags = "merge, rest, rests, voice, voices"
status = "ready"
}
#(define has-one-or-less (lambda (lst) (or (null? lst) (null? (cdr lst)))))
#(define has-at-least-two (lambda (lst) (not (has-one-or-less lst))))
#(define (all-equal lst pred)
(or (has-one-or-less lst)
(and (pred (car lst) (cadr lst)) (all-equal (cdr lst) pred))))
#(define merge-rests-engraver
(lambda (context)
(let ((rest-same-length
(lambda (rest-a rest-b)
(eq? (ly:grob-property rest-a 'duration-log)
(ly:grob-property rest-b 'duration-log))))
(rests '()))
`((start-translation-timestep . ,(lambda (trans)
(set! rests '())))
(stop-translation-timestep . ,(lambda (trans)
(if (and (has-at-least-two
rests) (all-equal rests rest-same-length))
(for-each
(lambda (rest)
(ly:grob-set-property! rest 'Y-offset 0))
rests))))
(acknowledgers
(rest-interface . ,(lambda (engraver grob source-engraver)
(if (eq? 'Rest (assoc-ref
(ly:grob-property grob 'meta) 'name))
(set! rests (cons grob rests))))))))))
#(define merge-mmrests-engraver
(lambda (context)
(let* ((mmrest-same-length
(lambda (rest-a rest-b)
(eq? (ly:grob-property rest-a 'measure-count)
(ly:grob-property rest-b 'measure-count))))
(merge-mmrests
(lambda (rests)
(if (all-equal rests mmrest-same-length)
(let ((offset (if (eq? (ly:grob-property (car rests)
'measure-count) 1) 1 0)))
(for-each
(lambda (rest) (ly:grob-set-property! rest
'Y-offset offset))
rests)))))
(curr-rests '())
(rests '()))
`((start-translation-timestep . ,(lambda (trans)
(set! curr-rests '())))
(stop-translation-timestep . ,(lambda (trans)
(if (has-at-least-two curr-rests)
(set! rests (cons curr-rests rests)))))
(finalize . ,(lambda (translator)
(for-each merge-mmrests rests)))
(acknowledgers
(rest-interface . ,(lambda (engraver grob source-engraver)
(if (eq? 'MultiMeasureRest (assoc-ref
(ly:grob-property grob 'meta) 'name))
(set! curr-rests (cons grob curr-rests))))))))))