X-Git-Url: https://git.donarmstrong.com/?a=blobdiff_plain;f=lily%2Fmusic-scheme.cc;h=de5442e9664d0fa71d3d387d8a42e70b49ebc373;hb=97a0169312a260933246ab224e4f8b0969871dd5;hp=55f1333bf5dbb297d3f00426865113b7c6c5a871;hpb=82bc9ad690e201aaa55694f8b92261ae7338f56a;p=lilypond.git diff --git a/lily/music-scheme.cc b/lily/music-scheme.cc index 55f1333bf5..de5442e966 100644 --- a/lily/music-scheme.cc +++ b/lily/music-scheme.cc @@ -1,7 +1,7 @@ /* This file is part of LilyPond, the GNU music typesetter. - Copyright (C) 2005--2014 Han-Wen Nienhuys + Copyright (C) 2005--2015 Han-Wen Nienhuys LilyPond is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -20,6 +20,8 @@ #include "music.hh" #include "duration.hh" +#include "input.hh" +#include "lily-imports.hh" #include "program-option.hh" #include "warn.hh" @@ -28,8 +30,8 @@ LY_DEFINE (ly_music_length, "ly:music-length", "Get the length of music expression @var{mus} and return" " it as a @code{Moment} object.") { - LY_ASSERT_TYPE (unsmob_music, mus, 1); - Music *sc = unsmob_music (mus); + LY_ASSERT_SMOB (Music, mus, 1); + Music *sc = unsmob (mus); return sc->get_length ().smobbed_copy (); } @@ -39,7 +41,7 @@ LY_DEFINE (ly_music_property, "ly:music-property", " @var{mus}. If no value is found, return @var{val} or" " @code{'()} if @var{val} is not specified.") { - LY_ASSERT_TYPE (unsmob_music, mus, 1); + LY_ASSERT_SMOB (Music, mus, 1); return ly_prob_property (mus, sym, val); } @@ -48,7 +50,7 @@ LY_DEFINE (ly_music_set_property_x, "ly:music-set-property!", "Set property @var{sym} in music expression @var{mus} to" " @var{val}.") { - LY_ASSERT_TYPE (unsmob_music, mus, 1); + LY_ASSERT_SMOB (Music, mus, 1); return ly_prob_set_property_x (mus, sym, val); } @@ -71,14 +73,14 @@ LY_DEFINE (ly_music_p, "ly:music?", 1, 0, 0, (SCM obj), "Is @var{obj} a music object?") { - return scm_from_bool (unsmob_music (obj)); + return ly_bool2scm (unsmob (obj)); } LY_DEFINE (ly_event_p, "ly:event?", 1, 0, 0, (SCM obj), "Is @var{obj} a proper (non-rhythmic) event object?") { - if (Music *m = unsmob_music (obj)) + if (Music *m = unsmob (obj)) { return scm_from_bool (m->is_mus_type ("post-event")); } @@ -92,8 +94,8 @@ LY_DEFINE (ly_music_mutable_properties, "ly:music-mutable-properties", " The immutable properties are not available, since they are" " constant and initialized by the @code{make-music} function.") { - LY_ASSERT_TYPE (unsmob_music, mus, 1); - Music *m = unsmob_music (mus); + LY_ASSERT_SMOB (Music, mus, 1); + Music *m = unsmob (mus); return m->get_property_alist (true); } @@ -101,42 +103,69 @@ LY_DEFINE (ly_music_list_p, "ly:music-list?", 1, 0, 0, (SCM lst), "Is @var{lst} a list of music objects?") { - if (scm_list_p (lst) == SCM_BOOL_T) - while (scm_is_pair (lst)) - { - if (!unsmob_music (scm_car (lst))) - return SCM_BOOL_F; - lst = scm_cdr (lst); - } + if (!ly_is_list (lst)) + return SCM_BOOL_F; + + while (scm_is_pair (lst)) + { + if (!unsmob (scm_car (lst))) + return SCM_BOOL_F; + lst = scm_cdr (lst); + } return SCM_BOOL_T; } LY_DEFINE (ly_music_deep_copy, "ly:music-deep-copy", - 1, 0, 0, (SCM m), + 1, 1, 0, (SCM m, SCM origin), "Copy @var{m} and all sub expressions of@tie{}@var{m}." " @var{m} may be an arbitrary type; cons cells and music" - " are copied recursively.") + " are copied recursively. If @var{origin} is given," + " it is used as the origin for one level of music by calling" + " @code{ly:set-origin!} on the copy.") { - if (unsmob_music (m)) - return unsmob_music (m)->clone ()->unprotect (); - if (scm_is_pair (m)) - { - SCM copy = SCM_EOL; - do - { - copy = scm_cons (ly_music_deep_copy (scm_car (m)), copy); - m = scm_cdr (m); - } - while (scm_is_pair (m)); - // Oh, come on, GUILE. Why do you require the second argument - // of scm_reverse_x to be a proper list? That makes no sense. - // return scm_reverse_x (copy, ly_music_deep_copy (m)); - SCM last_cons = copy; - copy = scm_reverse_x (copy, SCM_EOL); - scm_set_cdr_x (last_cons, ly_music_deep_copy (m)); - return copy; - } + m = music_deep_copy (m); + + if (SCM_UNBNDP (origin)) + return m; + + if (Music *mus = unsmob (origin)) + origin = mus->get_property ("origin"); + + if (scm_is_false (origin) || scm_is_null (origin)) + return m; + + LY_ASSERT_SMOB (Input, origin, 2); + + set_origin (m, origin); + return m; +} + +LY_DEFINE (ly_set_origin_x, "ly:set-origin!", + 1, 1, 0, (SCM m, SCM origin), + "This sets the origin given in @var{origin} to @var{m}. " + " @var{m} will typically be a music expression or a list" + " of music. List structures are searched recursively," + " but recursion stops at the changed music expressions" + " themselves. " + " @var{origin} is generally of type @code{ly:input-location?}," + " defaulting to @code{(*location*)}. Other valid values for" + " @code{origin} are a music expression which is then used as" + " the source of location information, or @code{#f}" + " or @code{'()} in which case no action is performed. " + " The return value is @var{m} itself.") +{ + if (SCM_UNBNDP (origin)) + origin = scm_fluid_ref (Lily::f_location); + else if (Music *mus = unsmob (origin)) + origin = mus->get_property ("origin"); + + if (scm_is_false (origin) || scm_is_null (origin)) + return m; + + LY_ASSERT_SMOB (Input, origin, 2); + + set_origin (m, origin); return m; } @@ -145,11 +174,11 @@ LY_DEFINE (ly_music_transpose, "ly:music-transpose", "Transpose @var{m} such that central@tie{}C is mapped" " to@tie{}@var{p}. Return@tie{}@var{m}.") { - LY_ASSERT_TYPE (unsmob_music, m, 1); + LY_ASSERT_SMOB (Music, m, 1); LY_ASSERT_SMOB (Pitch, p, 2); - Music *sc = unsmob_music (m); - Pitch *sp = unsmob_pitch (p); + Music *sc = unsmob (m); + Pitch *sp = unsmob (p); sc->transpose (*sp); // SCM_UNDEFINED ? @@ -163,11 +192,11 @@ LY_DEFINE (ly_music_compress, "ly:music-compress", 2, 0, 0, (SCM m, SCM factor), "Compress music object@tie{}@var{m} by moment @var{factor}.") { - LY_ASSERT_TYPE (unsmob_music, m, 1); - LY_ASSERT_TYPE (unsmob_moment, factor, 2); + LY_ASSERT_SMOB (Music, m, 1); + LY_ASSERT_SMOB (Moment, factor, 2); - Music *sc = unsmob_music (m); - sc->compress (*unsmob_moment (factor)); + Music *sc = unsmob (m); + sc->compress (*unsmob (factor)); return sc->self_scm (); } @@ -176,11 +205,11 @@ LY_DEFINE (ly_make_music_relative_x, "ly:make-music-relative!", "Make @var{music} relative to @var{pitch}," " return final pitch.") { - LY_ASSERT_TYPE (unsmob_music, music, 1); - LY_ASSERT_TYPE (unsmob_pitch, pitch, 2); + LY_ASSERT_SMOB (Music, music, 1); + LY_ASSERT_SMOB (Pitch, pitch, 2); - Pitch start = *unsmob_pitch (pitch); - Music *m = unsmob_music (music); + Pitch start = *unsmob (pitch); + Music *m = unsmob (music); Pitch last = m->to_relative_octave (start); return last.smobbed_copy (); @@ -191,10 +220,10 @@ LY_DEFINE (ly_music_duration_length, "ly:music-duration-length", 1, 0, 0, "Extract the duration field from @var{mus} and return the" " length.") { - LY_ASSERT_TYPE (unsmob_music, mus, 1); - Music *m = unsmob_music (mus); + LY_ASSERT_SMOB (Music, mus, 1); + Music *m = unsmob (mus); - Duration *d = unsmob_duration (m->get_property ("duration")); + Duration *d = unsmob (m->get_property ("duration")); Moment len; if (d) @@ -209,13 +238,13 @@ LY_DEFINE (ly_music_duration_compress, "ly:music-duration-compress", 2, 0, 0, "Compress @var{mus} by factor @var{fact}, which is a" " @code{Moment}.") { - LY_ASSERT_TYPE (unsmob_music, mus, 1); + LY_ASSERT_SMOB (Music, mus, 1); LY_ASSERT_SMOB (Moment, fact, 2); - Music *m = unsmob_music (mus); - Moment *f = unsmob_moment (fact); + Music *m = unsmob (mus); + Moment *f = unsmob (fact); - Duration *d = unsmob_duration (m->get_property ("duration")); + Duration *d = unsmob (m->get_property ("duration")); if (d) m->set_property ("duration", d->compressed (f->main_part_).smobbed_copy ()); return SCM_UNSPECIFIED; @@ -234,7 +263,7 @@ LY_DEFINE (ly_transpose_key_alist, "ly:transpose-key-alist", " pitch @var{pit}.") { SCM newlist = SCM_EOL; - Pitch *p = unsmob_pitch (pit); + Pitch *p = unsmob (pit); for (SCM s = l; scm_is_pair (s); s = scm_cdr (s)) { @@ -266,4 +295,3 @@ LY_DEFINE (ly_transpose_key_alist, "ly:transpose-key-alist", } return scm_reverse_x (newlist, SCM_EOL); } -