/*
head-grav.cc -- part of GNU LilyPond
- (c) 1997--2003 Han-Wen Nienhuys <hanwen@cs.uu.nl>
+ (c) 1997--2004 Han-Wen Nienhuys <hanwen@cs.uu.nl>
*/
#include <ctype.h>
#include "item.hh"
#include "score-engraver.hh"
#include "warn.hh"
+#include "spanner.hh"
+#include "tie.hh"
+#include "global-context.hh"
/*
We copy the reqs into scratch note reqs, to make sure that we get
all durations exactly right.
- */
+*/
class Completion_heads_engraver : public Engraver
{
Link_array<Item> notes_;
+ Link_array<Item> prev_notes_;
+ Link_array<Grob> ties_;
Link_array<Item> dots_;
Link_array<Music> note_reqs_;
}
else
{
- orig = unsmob_duration (note_reqs_[0]->get_mus_property ("duration"));
+ orig = unsmob_duration (note_reqs_[0]->get_property ("duration"));
note_dur = *orig;
}
Moment nb = next_barline_moment ();
Moment next = now;
next.main_part_ += note_dur.get_length ();
- top_engraver ()->add_moment_to_process (next);
+
+ get_global_context ()->add_moment_to_process (next);
do_nothing_until_ = next.main_part_;
}
for (int i = 0;
left_to_do_ && i < note_reqs_.size (); i++)
{
- Item *note = new Item (get_property ("NoteHead"));
+ Item *note = make_item ("NoteHead");
Music * req = note_reqs_[i];
if (scratch_note_reqs_.size())
{
req = scratch_note_reqs_[i];
- SCM pits = note_reqs_[i]->get_mus_property ("pitch");
- req->set_mus_property ("pitch",pits);
+ SCM pits = note_reqs_[i]->get_property ("pitch");
+ req->set_property ("pitch",pits);
}
- req->set_mus_property ("duration", note_dur.smobbed_copy ());
- note->set_grob_property ("duration-log",
+ req->set_property ("duration", note_dur.smobbed_copy ());
+ note->set_property ("duration-log",
gh_int2scm (note_dur.duration_log ()));
int dots= note_dur.dot_count ();
if (dots)
{
- Item * d = new Item (get_property ("Dots"));
+ Item * d = make_item ("Dots");
Rhythmic_head::set_dots (note, d);
/*
measly attempt to save an eeny-weenie bit of memory.
*/
- if (dots != gh_scm2int (d->get_grob_property ("dot-count")))
- d->set_grob_property ("dot-count", gh_int2scm (dots));
+ if (dots != gh_scm2int (d->get_property ("dot-count")))
+ d->set_property ("dot-count", gh_int2scm (dots));
d->set_parent (note, Y_AXIS);
announce_grob (d, SCM_EOL);
dots_.push (d);
}
- Pitch *pit =unsmob_pitch (req->get_mus_property ("pitch"));
+ Pitch *pit =unsmob_pitch (req->get_property ("pitch"));
int pos = pit->steps ();
SCM c0 = get_property ("centralCPosition");
if (gh_number_p (c0))
pos += gh_scm2int (c0);
- note->set_grob_property ("staff-position", gh_int2scm (pos));
+ note->set_property ("staff-position", gh_int2scm (pos));
announce_grob (note,req->self_scm ());
notes_.push (note);
}
+
+ if (prev_notes_.size() == notes_.size ())
+ {
+ for (int i= 0; i < notes_.size(); i++)
+ {
+ Grob * p = make_spanner ("Tie");
+ Tie::set_interface (p); // cannot remove yet!
+
+ Tie::set_head (p, LEFT, prev_notes_[i]);
+ Tie::set_head (p, RIGHT, notes_[i]);
+
+ ties_.push (p);
+ announce_grob(p, SCM_EOL);
+ }
+ }
left_to_do_ -= note_dur.get_length ();
-
/*
don't do complicated arithmetic with grace notes.
*/
{
left_to_do_ = Rational (0,0);
}
-
}
void
Completion_heads_engraver::stop_translation_timestep ()
{
+ for (int i = ties_.size (); i--;)
+ typeset_grob (ties_[i]);
+ ties_.clear();
+
for (int i=0; i < notes_.size (); i++)
{
typeset_grob (notes_[i]);
}
+ if (notes_.size())
+ prev_notes_ = notes_;
notes_.clear ();
for (int i=0; i < dots_.size (); i++)
for (int i = scratch_note_reqs_.size(); i--;)
{
scm_gc_unprotect_object (scratch_note_reqs_[i]->self_scm () );
-
}
+
scratch_note_reqs_.clear();
}
-Music * tie_req = 0;
-
void
Completion_heads_engraver::start_translation_timestep ()
{
if (note_end_mom_.main_part_ <= now.main_part_)
{
note_reqs_.clear ();
- }
-
- if (left_to_do_)
- {
- if (!tie_req)
- tie_req = make_music_by_name (ly_symbol2scm ("TieEvent"));
-
- bool succ = daddy_trans_->try_music (tie_req);
- if (!succ)
- {
- programming_error ("Completion_heads_engraver: no-one to make tie.");
- }
+ prev_notes_.clear ();
}
}
/* descr */ "This engraver replaces "
"@code{Note_heads_engraver}. It plays some trickery to "
"break long notes and automatically tie them into the next measure.",
-/* creats*/ "NoteHead Dots",
+/* creats*/ "NoteHead Dots Tie",
/* accepts */ "busy-playing-event note-event",
/* acks */ "",
/* reads */ "centralCPosition measurePosition measureLength",