xmlgraphics-fop-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Luca Furini <lfur...@parpignol.cs.unibo.it>
Subject Re: Keep-with-next handling
Date Fri, 17 Jun 2005 10:33:41 GMT
Jeremias Maerki wrote:

> Could work for most cases although it would probably be difficult again
> on tables and a little less so on lists. I had to do some special stuff
> on tables and have still not solved everything. For example:
> +---------------+----------------+
> | cell1 line1   | cell2 line1    |
> |               | cell2 line2    |
> +---------------+----------------+
> | cell3 line1   | cell4 line1    |
> +---------------+----------------+
> A keep-with-previous on the second row should create a "glue" (not a
> knuth glue) not only between cell2 line2 and cell4 line1 but also
> between cell2 line1 and cell3 line1. This means that in the combined
> element list you get multiple infinite penalties. Your alternative
> approach might really help here. But I keep coming to the conclusion
> that I might have to get the cell content element lists of the following
> row (group) before I can finish the combined element list for the
> current one (because you might have a keep-with-previous in there).

As the combined list is created for a single row group at a time, I think 
that the presence of keeps could be signaled using a couple of boolean 
     getCombinedKnuthElementsForRowGroup(..., bKeepWithPrevious, bKeepWithNext)

In order to compute this boolean values, it should be enough to look for 
keep constraints in the first and last cell LM of each column in the row 
group; for example, if the table has M columns
     bKeepWithPrevious = cell[1,1].mustKeepWithPrevious()
                         || cell[1,2].mustKeepWithPrevious()
                         || ...
                         || cell[1,M].mustKeepWithPrevious()
     bKeepWithNext = cell[N,1].mustKeepWithNext()
                     || cell[P,2].mustKeepWithNext()
                     || ...
                     || cell[Q,M].mustKeepWithNext()
where N,P and Q are the last row indexes in the first, second and last 
column (which could be different if there are row spans).

During the creation of the combined list:
  - if there is a keep-with-previous, the first step must be get something 
from each column (it must be the greater among the column steps);
  - if there is a keep-with-next, the last step must be "synchronized" 
between all columns: is is allowed to place the last fragment of a column 
only if it will create the last combined element.

So, if a row group has both keep-with-previous and keep-with-next and one 
of the columns contains just a single line (or a single group of lines 
that cannot be parted) the combined list will have just a single step and 
no inner breaking points.

The synchronization of the last step could be achieved this way:

     // initializations

     bSynchronizeLastStep = bKeepWithNext
     for (each column) {
         // compute normally the width of the next sub-sequence
         if (bKeepWithNext
             && we have reached the end of the column sequence) {
             // signal this is the last step, for example
             width[i] = -width[i]
         } else {
             bLastStep = false

     if (bSynchronizeLastStep) {
         // take the "greater" last step
         step = - min{width[i]};
     } else {
         // the normal behaviour

This is not enough: if there are both a keep-with-previus constraint and a 
keep-with-next constraint, the whole process could be performed several 
times until the computed step is ok (because a column could have inner 
breaking points while another has none):

     bStepOk = false;
     while (!bStepOK) {
         // step computation

         bStepOK = true;
         if ((this is the first step)
             && bKeepWithPrevious) {
             for (each column) {
                 bStepOk = bStepOk
                     && (the remaining width is < than the total width)

Sorry for the long message, but everything seems quite complicated when 
applied to tables! :-)

I also must add that these are just thoughts: as I did not yet try and 
implement them, they could prove to be completely wrong.


View raw message