]> git.donarmstrong.com Git - lilypond.git/commitdiff
Issue 2337: avoid infinite loop: search next staff line directly
authorBenkő Pál <benko.pal@gmail.com>
Mon, 27 Feb 2012 06:40:31 +0000 (07:40 +0100)
committerDavid Kastrup <dak@gnu.org>
Mon, 27 Feb 2012 06:40:31 +0000 (07:40 +0100)
input/regression/rest-on-nonstandard-staff.ly
lily/rest.cc

index 4870f578cfc0df64c293991a4329240025f6d03d..f81aebdfbcbe5efcf83b0b689d12177e973086af 100644 (file)
@@ -55,4 +55,9 @@ mus = {
     \override Staff.StaffSymbol #'line-positions = #'(-4 -2 1 5)
     \mus
   }
+
+  \new Staff {
+    \stopStaff
+    \mus
+  }
 >>
index a25e6a93198298ef4d8ca778dbded2379e583365..0bb61444b4c025882f0bb924cb531350c246102d 100644 (file)
@@ -26,6 +26,7 @@
 #include "output-def.hh"
 #include "paper-score.hh"
 #include "staff-symbol-referencer.hh"
+#include "staff-symbol.hh"
 #include "stencil.hh"
 #include "grob.hh"
 
@@ -48,7 +49,7 @@ Rest::y_offset_callback (SCM smob)
         robust_scm2double (me->get_property ("staff-position"), 0) * 0.5 * ss;
 
       /*
-        semibreve rests were always positioned one off
+        semibreve rests are positioned one staff line off
       */
       if (duration_log == 0)
         amount += ss;
@@ -66,17 +67,25 @@ Rest::y_offset_callback (SCM smob)
 
       /*
         make a semibreve rest hang from the next line,
-        except for a single line staff;
-        assume the next line being integer steps away
+        except for a single line staff
       */
       if (duration_log == 0 && line_count > 1)
-        ++pos;
+        pos += 2;
 
       /*
         make sure rest is aligned to a staff line
       */
-      while (!Staff_symbol_referencer::on_line (me, pos))
-        ++pos;
+      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;
     }
@@ -112,14 +121,14 @@ Rest::glyph_name (Grob *me, int durlog, string style, bool try_ledgers)
       int const pos = int (Staff_symbol_referencer::get_position (me));
 
       /*
-       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
+        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
       */
       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));
+          && !(durlog == -1
+               && Staff_symbol_referencer::on_staff_line (me, pos + 2));
     }
 
   string actual_style (style.c_str ());