+ if (!stem_l () || !rest_b ())
+ return;
+
+ Beam * b = stem_l ()->beam_l ();
+ if (!b || !b->visible_stem_count ())
+ return;
+
+ /* ugh. Should be done by beam.
+ (what? should be done --jcn)
+ scary too?: height is calculated during post_processing
+ */
+ Real beam_dy = 0;
+ Real beam_y = 0;
+
+ SCM s = b->get_elt_property ("height");
+ if (gh_number_p (s))
+ beam_dy = gh_scm2double (s);
+
+ s = b->get_elt_property ("y-position");
+ if (gh_number_p (s))
+ beam_y = gh_scm2double (s);
+
+
+ Real x0 = b->first_visible_stem ()->hpos_f ();
+ Real dx = b->last_visible_stem ()->hpos_f () - x0;
+ Real dydx = beam_dy && dx ? beam_dy/dx : 0;
+
+ Direction d = stem_l ()->get_direction ();
+ Real beamy = (stem_l ()->hpos_f () - x0) * dydx + beam_y;
+
+ s = get_elt_property ("rests");
+ Score_element * se = unsmob_element (gh_car (s));
+ Staff_symbol_referencer_interface si (se);
+
+ Real staff_space = si.staff_space ();
+ Real rest_dim = extent (Y_AXIS)[d]*2.0 /staff_space ;
+
+ Real minimum_dist
+ = paper_l ()->get_var ("restcollision_minimum_beamdist") ;
+ Real dist =
+ minimum_dist + -d * (beamy - rest_dim) >? 0;
+
+ int stafflines = si.line_count ();
+
+ // move discretely by half spaces.
+ int discrete_dist = int (ceil (dist ));
+
+ // move by whole spaces inside the staff.
+ if (discrete_dist < stafflines+1)
+ discrete_dist = int (ceil (discrete_dist / 2.0)* 2.0);
+
+ translate_rests (-d * discrete_dist);
+}
+
+
+Interval
+Note_column::rest_dim () const
+{
+ Interval restdim;
+ SCM s = get_elt_property ("rests");
+ for (; gh_pair_p (s); s = gh_cdr (s))
+ {
+ Score_element * sc = unsmob_element ( gh_car (s));
+ restdim.unite (sc->extent (Y_AXIS));
+ }
+
+ return restdim;
+}
+
+Note_head*
+Note_column::first_head () const
+{
+ Stem * st = stem_l ();
+ return st? st->first_head (): 0;