/*
This file is part of LilyPond, the GNU music typesetter.
- Copyright (C) 1997--2011 Han-Wen Nienhuys <hanwen@xs4all.nl>
+ Copyright (C) 1997--2012 Han-Wen Nienhuys <hanwen@xs4all.nl>
LilyPond is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
#include "output-def.hh"
#include "paper-score.hh"
#include "staff-symbol-referencer.hh"
+#include "staff-symbol.hh"
#include "stencil.hh"
#include "grob.hh"
Real ss = Staff_symbol_referencer::staff_space (me);
bool position_override = scm_is_number (me->get_property ("staff-position"));
- Real amount = robust_scm2double (me->get_property ("staff-position"), 0)
- * 0.5 * ss;
+ Real amount;
- if (line_count % 2)
+ if (position_override)
{
- if (duration_log == 0 && line_count > 1)
+ amount
+ = robust_scm2double (me->get_property ("staff-position"), 0) * 0.5 * ss;
+
+ /*
+ semibreve rests are positioned one staff line off
+ */
+ if (duration_log == 0)
amount += ss;
+
+ /*
+ trust the client on good positioning;
+ would be tempting to adjust position of rests longer than a quarter
+ to be properly aligned to staff lines,
+ but custom rest shapes may not need that sort of care.
+ */
}
else
- amount += ss / 2;
+ {
+ int pos = 4 * get_grob_direction (me);
- if (!position_override)
- amount += 2 * ss * get_grob_direction (me);
+ /*
+ make a semibreve rest hang from the next line,
+ except for a single line staff
+ */
+ if (duration_log == 0 && line_count > 1)
+ pos += 2;
+ /*
+ make sure rest is aligned to a staff line
+ */
+ if (Grob *staff = Staff_symbol_referencer::get_staff_symbol (me))
+ {
+ std::vector<Real> linepos = Staff_symbol::line_positions (staff);
+ std::sort (linepos.begin (), linepos.end ());
+ std::vector<Real>::const_iterator it
+ = std::lower_bound (linepos.begin (), linepos.end (), pos);
+ if (it != linepos.end ())
+ {
+ pos = (int)ceil (*it);
+ }
+ }
+
+ amount = ss * 0.5 * pos;
+ }
return scm_from_double (amount);
}
make this function easily usable in C++
*/
string
-Rest::glyph_name (Grob *me, int balltype, string style, bool try_ledgers)
+Rest::glyph_name (Grob *me, int durlog, string style, bool try_ledgers)
{
bool is_ledgered = false;
- if (try_ledgers && (balltype == -1 || balltype == 0 || balltype == 1))
+ if (try_ledgers && (durlog == -1 || durlog == 0 || durlog == 1))
{
- Real rad = Staff_symbol_referencer::staff_radius (me) * 2.0;
- Real pos = Staff_symbol_referencer::get_position (me);
+ int const pos = int (Staff_symbol_referencer::get_position (me));
/*
- Figure out when the rest is far enough outside the staff. This
- could bemore generic, but hey, we understand this even after
- dinner.
+ half rests need ledger if not lying on a staff line,
+ whole rests need ledger if not hanging from a staff line,
+ breve rests need ledger if neither lying on nor hanging from a staff line
*/
- is_ledgered |= (balltype == -1) && (pos <= -rad - 3 || pos >= +rad + 1);
- is_ledgered |= (balltype == 0) && (pos >= +rad + 2 || pos < -rad);
- is_ledgered |= (balltype == 1) && (pos <= -rad - 2 || pos > +rad);
+ if (-1 <= durlog && durlog <= 1)
+ is_ledgered = !Staff_symbol_referencer::on_staff_line (me, pos)
+ && !(durlog == -1
+ && Staff_symbol_referencer::on_staff_line (me, pos + 2));
}
string actual_style (style.c_str ());
There are no 32th/64th/128th mensural/neomensural rests. In
these cases, revert back to default style.
*/
- if (balltype > 4)
+ if (durlog > 4)
actual_style = "";
}
- if ((style == "classical") && (balltype != 2))
+ if ((style == "classical") && (durlog != 2))
{
/*
classical style: revert back to default style for any rest other
actual_style = "";
}
- return ("rests." + to_string (balltype) + (is_ledgered ? "o" : "")
+ return ("rests." + to_string (durlog) + (is_ledgered ? "o" : "")
+ actual_style);
}
SCM
Rest::brew_internal_stencil (Grob *me, bool ledgered)
{
- SCM balltype_scm = me->get_property ("duration-log");
- if (!scm_is_number (balltype_scm))
+ SCM durlog_scm = me->get_property ("duration-log");
+ if (!scm_is_number (durlog_scm))
return Stencil ().smobbed_copy ();
- int balltype = scm_to_int (balltype_scm);
+ int durlog = scm_to_int (durlog_scm);
string style = robust_symbol2string (me->get_property ("style"), "default");
Font_metric *fm = Font_interface::get_default_font (me);
- string font_char = glyph_name (me, balltype, style, ledgered);
+ string font_char = glyph_name (me, durlog, style, ledgered);
Stencil out = fm->find_by_name (font_char);
if (out.is_empty ())
me->warning (_f ("rest `%s' not found", font_char.c_str ()));
"minimum-distance "
"style "
);
-