]> git.donarmstrong.com Git - lilypond.git/blobdiff - lily/page-breaking.cc
Fix 1112.
[lilypond.git] / lily / page-breaking.cc
index 2251e50bc19a5848dea569f315fc4c858d4d06f4..aeeb7bb1b7eb555db4f37ea162524178d72c8050 100644 (file)
@@ -99,9 +99,18 @@ compress_lines (const vector<Line_details> &orig)
        {
          Line_details const &old = ret.back ();
          Line_details compressed = orig[i];
-         Real padding = orig[i].title_ ? old.title_padding_ : old.padding_;
+         /*
+           We must account for the padding between the lines that we are compressing.
+           The padding values come from "old," which is the upper system here. Note
+           the meaning of tight-spacing: if a system has tight-spacing, then the padding
+           _before_ it is ignored.
+         */
+         Real padding = 0;
+         if (!orig[i].tight_spacing_)
+           padding = orig[i].title_ ? old.title_padding_ : old.padding_;
 
          compressed.shape_ = old.shape_.piggyback (orig[i].shape_, padding);
+         compressed.first_refpoint_offset_ += compressed.shape_.rest_[UP] - old.shape_.rest_[UP];
          compressed.space_ += old.space_;
          compressed.inverse_hooke_ += old.inverse_hooke_;
 
@@ -525,7 +534,8 @@ Page_breaking::find_chunks_and_breaks (Break_predicate is_break)
     {
       if (system_specs_[i].pscore_)
        {
-         vector<Grob*> cols;
+         vector<Grob*> cols = system_specs_[i].pscore_->root_system ()->used_columns ();
+         vector<Grob*> forced_line_break_cols;
 
          SCM system_count = system_specs_[i].pscore_->layout ()->c_variable ("system-count");
          if (scm_is_number (system_count))
@@ -536,19 +546,26 @@ Page_breaking::find_chunks_and_breaks (Break_predicate is_break)
              Constrained_breaking breaking (system_specs_[i].pscore_);
              vector<Line_details> details = breaking.line_details (0, VPOS, scm_to_int (system_count));
 
-             cols.push_back (system_specs_[i].pscore_->root_system ()->used_columns ()[0]);
              for (vsize j = 0; j < details.size (); j++)
-               cols.push_back (details[j].last_column_);
+               forced_line_break_cols.push_back (details[j].last_column_);
            }
-         else
-           cols = system_specs_[i].pscore_->root_system ()->used_columns ();
 
-         int last_chunk_idx = 0;
+         int last_forced_line_break_idx = 0;
+         vsize forced_line_break_idx = 0;
          vector<vsize> line_breaker_columns;
          line_breaker_columns.push_back (0);
 
          for (vsize j = 1; j < cols.size (); j++)
            {
+             if (forced_line_break_cols.size ())
+               {
+                 if (forced_line_break_idx >= forced_line_break_cols.size ()
+                     || forced_line_break_cols[forced_line_break_idx] != cols[j])
+                   continue;
+                 else
+                   forced_line_break_idx++;
+               }
+
              bool last = (j == cols.size () - 1);
              bool break_point = is_break (cols[j]);
              bool chunk_end = cols[j]->get_property ("page-break-permission") == force_sym;
@@ -564,14 +581,14 @@ Page_breaking::find_chunks_and_breaks (Break_predicate is_break)
              // since it mixes Break_positions from breaks_ and
              // chunks_.
              if (scm_is_number (system_count))
-               cur_pos.forced_line_count_ = j - last_chunk_idx;
+               cur_pos.forced_line_count_ = forced_line_break_idx - last_forced_line_break_idx;
 
              if (break_point || (i == system_specs_.size () - 1 && last))
                breaks_.push_back (cur_pos);
              if (chunk_end || last)
                {
                  chunks_.push_back (cur_pos);
-                 last_chunk_idx = j;
+                 last_forced_line_break_idx = forced_line_break_idx;
                }
 
              if ((break_point || chunk_end) && !last)
@@ -841,19 +858,38 @@ Page_breaking::compute_line_heights ()
   Real prev_hanging = 0;
   Real prev_hanging_begin = 0;
   Real prev_hanging_rest = 0;
+  Real prev_refpoint_hanging = 0;
   for (vsize i = 0; i < cached_line_details_.size (); i++)
     {
       Line_shape shape = cached_line_details_[i].shape_;
       Real a = shape.begin_[UP];
       Real b = shape.rest_[UP];
-      Real midline_hanging = max (prev_hanging_begin + a, prev_hanging_rest + b);
-      Real hanging_begin = midline_hanging - shape.begin_[DOWN];
-      Real hanging_rest = midline_hanging - shape.rest_[DOWN];
+      bool title = cached_line_details_[i].title_;
+      Real refpoint_hanging = max (prev_hanging_begin + a, prev_hanging_rest + b);
+
+      if (i > 0)
+       {
+         Real padding = 0;
+         if (!cached_line_details_[i].tight_spacing_)
+           padding = title
+             ? cached_line_details_[i-1].title_padding_
+             : cached_line_details_[i-1].padding_;
+         Real min_dist = title
+           ? cached_line_details_[i-1].title_min_distance_
+           : cached_line_details_[i-1].min_distance_;
+         refpoint_hanging = max (refpoint_hanging + padding,
+                                 prev_refpoint_hanging + min_dist
+                                 + cached_line_details_[i].first_refpoint_offset_);
+       }
+
+      Real hanging_begin = refpoint_hanging - shape.begin_[DOWN];
+      Real hanging_rest = refpoint_hanging - shape.rest_[DOWN];
       Real hanging = max (hanging_begin, hanging_rest);
       cached_line_details_[i].tallness_ = hanging - prev_hanging;
       prev_hanging = hanging;
       prev_hanging_begin = hanging_begin;
       prev_hanging_rest = hanging_rest;
+      prev_refpoint_hanging = refpoint_hanging;
     }
 }
 
@@ -875,20 +911,13 @@ Page_breaking::min_page_count (vsize configuration, vsize first_page_num)
 
   for (vsize i = 0; i < cached_line_details_.size (); i++)
     {
-      Real padding = 0;
       Real ext_len;
       if (cur_rod_height > 0)
-        {
-          padding = cached_line_details_[i].title_ ?
-            cached_line_details_[i-1].title_padding_ :
-            cached_line_details_[i-1].padding_;
-          ext_len = cached_line_details_[i].tallness_;
-        }
+       ext_len = cached_line_details_[i].tallness_;
       else
-        {
-          ext_len = cached_line_details_[i].full_height();
-        }
-      Real next_rod_height = cur_rod_height + ext_len + padding;
+       ext_len = cached_line_details_[i].full_height();
+
+      Real next_rod_height = cur_rod_height + ext_len;
       Real next_spring_height = cur_spring_height + cached_line_details_[i].space_;
       Real next_height = next_rod_height + (ragged () ? next_spring_height : 0)
        + min_whitespace_at_bottom_of_page (cached_line_details_[i]);
@@ -1277,6 +1306,7 @@ Page_breaking::space_systems_on_2_pages (vsize configuration, vsize first_page_n
        p1.systems_per_page_.push_back (p2.systems_per_page_[0]);
        p1.force_.push_back (p2.force_[0]);
        p1.penalty_ += p2.penalty_ - cached_line_details_[i].turn_penalty_;
+       p1.system_count_status_ |= p2.system_count_status_;
        return p1;
       }