2 note-column.cc -- implement Note_column
4 source file of the GNU LilyPond music typesetter
6 (c) 1997--2004 Han-Wen Nienhuys <hanwen@cs.uu.nl>
8 #include <math.h> // ceil
10 #include "axis-group-interface.hh"
11 #include "note-column.hh"
14 #include "output-def.hh"
15 #include "group-interface.hh"
16 #include "staff-symbol-referencer.hh"
18 #include "note-head.hh"
19 #include "accidental-placement.hh"
22 TODO: figure out if we can prune this class. This is just an
23 annoying layer between (rest)collision & (note-head + stem)
27 Note_column::has_rests (Grob*me)
29 return unsmob_grob (me->get_property ("rest"));
33 Note_column::shift_compare (Grob *const &p1, Grob *const&p2)
35 SCM s1 = p1->get_property ("horizontal-shift");
36 SCM s2 = p2->get_property ("horizontal-shift");
38 int h1 = (ly_c_number_p (s1))? ly_scm2int (s1) :0;
39 int h2 = (ly_c_number_p (s2)) ? ly_scm2int (s2):0;
44 Note_column::get_stem (Grob*me)
46 SCM s = me->get_property ("stem");
47 return unsmob_item (s);
51 Note_column::head_positions_interval (Grob *me)
57 SCM h = me->get_property ("note-heads");
58 for (; ly_c_pair_p (h); h = ly_cdr (h))
60 Grob *se = unsmob_grob (ly_car (h));
62 int j = Staff_symbol_referencer::get_rounded_position (se);
63 iv.unite (Slice (j,j));
69 Note_column::dir (Grob* me)
71 Grob *stem = unsmob_grob (me->get_property ("stem"));
72 if (stem && Stem::has_interface (stem))
73 return Stem::get_direction (stem);
74 else if (ly_c_pair_p (me->get_property ("note-heads")))
75 return (Direction)sign (head_positions_interval (me).center ());
77 programming_error ("Note column without heads and stem!");
83 Note_column::set_stem (Grob*me,Grob * stem)
85 me->set_property ("stem", stem->self_scm ());
86 me->add_dependency (stem);
87 Axis_group_interface::add_element (me, stem);
92 Note_column::get_rest (Grob*me)
94 return unsmob_grob (me->get_property ("rest"));
98 Note_column::add_head (Grob*me,Grob *h)
101 if (Rest::has_interface (h))
103 if (ly_c_pair_p (me->get_property ("note-heads")))
106 me->set_property ("rest", h->self_scm ());
108 else if (Note_head::has_interface (h))
110 if (unsmob_grob (me->get_property ("rest")))
112 Pointer_group_interface::add_grob (me, ly_symbol2scm ("note-heads"),h);
116 me->warning ("Can't have rests and note heads together on a stem.");
118 Axis_group_interface::add_element (me, h);
122 translate the rest symbols vertically by amount DY, but only if
123 they have no staff-position set.
126 Note_column::translate_rests (Grob*me, int dy)
128 Grob * r = unsmob_grob (me->get_property ("rest"));
129 if (r && !ly_c_number_p (r->get_property ("staff-position")))
131 r->translate_axis (dy * Staff_symbol_referencer::staff_space (r)/2.0, Y_AXIS);
137 Note_column::set_dotcol (Grob*me,Grob *d)
139 Axis_group_interface::add_element (me, d);
146 Note_column::first_head (Grob*me)
148 Grob * st = get_stem (me);
149 return st? Stem::first_head (st): 0;
154 Return the first Accidentals grob that we find in a note-head.
157 Note_column::accidentals (Grob *me)
159 SCM heads = me->get_property ("note-heads");
161 for (;ly_c_pair_p (heads); heads =ly_cdr (heads))
163 Grob * h = unsmob_grob (ly_car (heads));
164 acc = h ? unsmob_grob (h->get_property ("accidental-grob")) : 0;
172 if (Accidental_placement::has_interface (acc->get_parent (X_AXIS)))
173 return acc->get_parent (X_AXIS);
181 ADD_INTERFACE (Note_column,"note-column-interface",
182 "Stem and noteheads combined",
183 "arpeggio note-heads rest-collision rest horizontal-shift stem accidentals force-hshift");