]> source.dussan.org Git - xmlgraphics-fop.git/commitdiff
Clean-up for accessing column-count and column-gap in area tree.
authorJeremias Maerki <jeremias@apache.org>
Sun, 20 Mar 2005 12:46:11 +0000 (12:46 +0000)
committerJeremias Maerki <jeremias@apache.org>
Sun, 20 Mar 2005 12:46:11 +0000 (12:46 +0000)
Renamed RegionOuter to SideRegion.
Start for multi-column layout (only plain multi-columns, no spans, no column balancing, yet).
More consequent use of BlockSequence instead of KnuthSequence in page breaking so the info where a sequence is to be placed (even/odd page...) is easily available.
Hard breaks now handled under control of the breaker instead of in getParentArea().

git-svn-id: https://svn.apache.org/repos/asf/xmlgraphics/fop/branches/Temp_KnuthStylePageBreaking@198518 13f79535-47bb-0310-9956-ffa450edef68

13 files changed:
src/java/org/apache/fop/area/BodyRegion.java
src/java/org/apache/fop/area/MainReference.java
src/java/org/apache/fop/area/Span.java
src/java/org/apache/fop/fo/pagination/RegionBA.java
src/java/org/apache/fop/fo/pagination/RegionOuter.java [deleted file]
src/java/org/apache/fop/fo/pagination/RegionSE.java
src/java/org/apache/fop/fo/pagination/SideRegion.java [new file with mode: 0644]
src/java/org/apache/fop/layoutmgr/AbstractBreaker.java
src/java/org/apache/fop/layoutmgr/BlockContainerLayoutManager.java
src/java/org/apache/fop/layoutmgr/BlockLayoutManager.java
src/java/org/apache/fop/layoutmgr/PageSequenceLayoutManager.java
src/java/org/apache/fop/layoutmgr/StaticContentLayoutManager.java
src/java/org/apache/fop/render/AbstractRenderer.java

index c4223db8b66dffd8ea3fba2497f1a13967e5cafe..7b8faa958ead8f15837664efd24fba974e38374d 100644 (file)
@@ -41,7 +41,7 @@ public class BodyRegion extends RegionReference {
     public BodyRegion() {
         super(Constants.FO_REGION_BODY);
         addTrait(Trait.IS_REFERENCE_AREA, Boolean.TRUE);
-        mainReference = new MainReference();
+        mainReference = new MainReference(this);
     }
 
     /**
@@ -89,6 +89,11 @@ public class BodyRegion extends RegionReference {
         this.columnGap = colGap;
     }
 
+    /** @return the column-gap value */
+    public int getColumnGap() {
+        return this.columnGap;
+    }
+    
     /**
      * Set the before float area.
      *
@@ -98,15 +103,6 @@ public class BodyRegion extends RegionReference {
         beforeFloat = bf;
     }
 
-    /**
-     * Set the main reference area.
-     *
-     * @param mr the main reference area
-     */
-    public void setMainReference(MainReference mr) {
-        mainReference = mr;
-    }
-
     /**
      * Set the footnote area.
      *
index 5274d49558ba28d3cdbbbcdfca652313250953f0..a63b2733269d84e8b76d1adee025156b217bd058 100644 (file)
@@ -28,15 +28,17 @@ import java.util.Iterator;
  * See fo:region-body definition in the XSL Rec for more information.
  */
 public class MainReference extends Area {
+
+    private BodyRegion parent;
     private List spanAreas = new java.util.ArrayList();
-    private int columnGap;
     private int width;
     private boolean isEmpty = true;
 
     /**
      * Constructor
      */
-    public MainReference() {
+    public MainReference(BodyRegion parent) {
+        this.parent = parent;
         addTrait(Trait.IS_REFERENCE_AREA, Boolean.TRUE);
     }
       
@@ -86,13 +88,14 @@ public class MainReference extends Area {
         return isEmpty;
     }
 
-    /**
-     * Get the column gap in millipoints.
-     *
-     * @return the column gap in millipoints
-     */
+    /** @return the number of columns */
+    public int getColumnCount() {
+        return parent.getColumnCount();
+    }
+
+    /** @return the column gap in millipoints */
     public int getColumnGap() {
-        return columnGap;
+        return parent.getColumnGap();
     }
 
     /**
index ff289d2ca2890714cd671e83a597999e1e7cf9f4..d27383238a11bd2590e12114beaaf8bfd750e6fc 100644 (file)
@@ -54,7 +54,7 @@ public class Span extends Area {
      * @return the newly made NormalFlow object
      */
     public NormalFlow addAdditionalNormalFlow() {
-        if (flowAreas.size() >= columnCount) { // internal error
+        if (!hasMoreAvailableFlows()) { // internal error
             throw new IllegalStateException("Maximum number of flow areas (" +
                     columnCount + ") for this span reached.");
         }
@@ -98,7 +98,18 @@ public class Span extends Area {
      * @return the flow area for the requested column
      */
     public NormalFlow getNormalFlow(int columnNumber) {
-        return (NormalFlow) flowAreas.get(columnNumber);
+        if (columnNumber < flowAreas.size()) {
+            return (NormalFlow) flowAreas.get(columnNumber);
+        } else {
+            return null;
+        }
+    }
+
+    /**
+     * @return true if this span can provide additional flow areas.
+     */
+    public boolean hasMoreAvailableFlows() {
+        return (getNormalFlowCount() < getColumnCount());
     }
 
 }
index 8a72cbd77d6327efa9ec1165b928db8c2f66420e..6d35dae20c581e0aea7507ab823d3d90d6101f1d 100644 (file)
@@ -28,7 +28,7 @@ import org.apache.fop.fo.PropertyList;
 /**
  * Abstract base class for fo:region-before and fo:region-after.
  */
-public abstract class RegionBA extends RegionOuter {
+public abstract class RegionBA extends SideRegion {
     // The value of properties relevant for fo:region-[before|after].
     private int precedence;
     // End of property values
diff --git a/src/java/org/apache/fop/fo/pagination/RegionOuter.java b/src/java/org/apache/fop/fo/pagination/RegionOuter.java
deleted file mode 100644 (file)
index 1fb5ce1..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright 2005 The Apache Software Foundation.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.fop.fo.pagination;
-
-import java.awt.Rectangle;
-
-import org.apache.fop.apps.FOPException;
-import org.apache.fop.datatypes.FODimension;
-import org.apache.fop.datatypes.Length;
-import org.apache.fop.fo.FONode;
-import org.apache.fop.fo.PropertyList;
-
-/**
- * @author Jeremias Maerki
- */
-public abstract class RegionOuter extends Region {
-
-    private Length extent;
-    
-    /**
-     * @see org.apache.fop.fo.FONode#FONode(FONode)
-     */
-    protected RegionOuter(FONode parent) {
-        super(parent);
-    }
-
-    /**
-     * @see org.apache.fop.fo.FObj#bind(PropertyList)
-     */
-    public void bind(PropertyList pList) throws FOPException {
-        super.bind(pList);
-        extent = pList.get(PR_EXTENT).getLength();
-    }
-    
-    /**
-     * @return the "extent" property.
-     */
-    public Length getExtent() {
-        return extent;
-    }
-
-    
-
-    
-}
index 25ca6680feb26882890f63c51b32d650be40d731..9100c098156654401725ebd30a40c4af79964b18 100644 (file)
@@ -28,7 +28,7 @@ import org.apache.fop.fo.PropertyList;
 /**
  * Abstract base class for fo:region-start and fo:region-end.
  */
-public abstract class RegionSE extends RegionOuter {
+public abstract class RegionSE extends SideRegion {
     // The value of properties relevant for fo:region-[start|end].
     // End of property values
 
diff --git a/src/java/org/apache/fop/fo/pagination/SideRegion.java b/src/java/org/apache/fop/fo/pagination/SideRegion.java
new file mode 100644 (file)
index 0000000..1475bc3
--- /dev/null
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2005 The Apache Software Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/* $Id$ */
+
+package org.apache.fop.fo.pagination;
+
+import org.apache.fop.apps.FOPException;
+import org.apache.fop.datatypes.Length;
+import org.apache.fop.fo.FONode;
+import org.apache.fop.fo.PropertyList;
+
+/**
+ * Common base class for side regions (before, after, start, end).
+ */
+public abstract class SideRegion extends Region {
+
+    private Length extent;
+    
+    /** @see org.apache.fop.fo.FONode#FONode(FONode) */
+    protected SideRegion(FONode parent) {
+        super(parent);
+    }
+
+    /** @see org.apache.fop.fo.FObj#bind(PropertyList) */
+    public void bind(PropertyList pList) throws FOPException {
+        super.bind(pList);
+        extent = pList.get(PR_EXTENT).getLength();
+    }
+    
+    /** @return the "extent" property. */
+    public Length getExtent() {
+        return extent;
+    }
+    
+}
index 027dfccb11651d9c9d7cc290e1eb34eac62580b1..5e9d08f9010aecf4e2ffb89101ce7b1587cda545 100644 (file)
@@ -48,10 +48,7 @@ public abstract class AbstractBreaker {
         }
     }
 
-    private class BlockSequence extends KnuthSequence {
-        static final int ANY_PAGE = 0;
-        static final int ODD_PAGE = 1;
-        static final int EVEN_PAGE = 2;
+    public class BlockSequence extends KnuthSequence {
 
         private int startOn;
 
@@ -59,6 +56,10 @@ public abstract class AbstractBreaker {
             super();
             startOn = iStartOn;
         }
+        
+        public int getStartOn() {
+            return this.startOn;
+        }
 
         public BlockSequence endBlockSequence() {
             KnuthSequence temp = super.endSequence();
@@ -88,18 +89,26 @@ public abstract class AbstractBreaker {
     protected abstract void addAreas(PositionIterator posIter, LayoutContext context);
     protected abstract LayoutManager getTopLevelLM();
     protected abstract LayoutManager getCurrentChildLM();
+    protected abstract LinkedList getNextKnuthElements(LayoutContext context, int alignment);
 
     /** @return true if there's no content that could be handled. */
     public boolean isEmpty() {
         return (blockLists.size() == 0);
     }
     
+    protected void startPart(BlockSequence list) {
+        //nop
+    }
+    
+    protected abstract void finishPart();
+
     protected LayoutContext createLayoutContext() {
         return new LayoutContext(0);
     }
     
     public void doLayout(int flowBPD) {
         LayoutContext childLC = createLayoutContext();
+        childLC.setStackLimit(new MinOptMax(flowBPD));
 
         //System.err.println("Vertical alignment: " +
         // currentSimplePageMaster.getRegion(FO_REGION_BODY).getDisplayAlign());
@@ -117,7 +126,7 @@ public abstract class AbstractBreaker {
         System.out.println("PLM> flow BPD =" + flowBPD);
         
         //*** Phase 1: Get Knuth elements ***
-        int nextSequenceStartsOn = BlockSequence.ANY_PAGE;
+        int nextSequenceStartsOn = Constants.EN_ANY;
         while (hasMoreContent()) {
             nextSequenceStartsOn = getNextBlockList(childLC, nextSequenceStartsOn, blockLists);
         }
@@ -129,8 +138,8 @@ public abstract class AbstractBreaker {
             
             //debug code start
             System.err.println("  blockListIndex = " + blockListIndex);
-            String pagina = (blockList.startOn == BlockSequence.ANY_PAGE) ? "any page"
-                    : (blockList.startOn == BlockSequence.ODD_PAGE) ? "odd page"
+            String pagina = (blockList.startOn == Constants.EN_ANY) ? "any page"
+                    : (blockList.startOn == Constants.EN_ODD_PAGE) ? "odd page"
                             : "even page";
             System.err.println("  sequence starts on " + pagina);
             logBlocklist(blockList);
@@ -142,7 +151,7 @@ public abstract class AbstractBreaker {
                     alignment, alignmentLast);
             int iOptPageNumber;
 
-            KnuthSequence effectiveList;
+            BlockSequence effectiveList;
             if (alignment == Constants.EN_JUSTIFY) {
                 /* justification */
                 effectiveList = justifyBoxes(blockList, alg, flowBPD);
@@ -171,7 +180,7 @@ public abstract class AbstractBreaker {
      * @param effectiveList effective Knuth element list (after adjustments)
      */
     protected abstract void doPhase3(PageBreakingAlgorithm alg, int partCount, 
-            KnuthSequence originalList, KnuthSequence effectiveList);
+            BlockSequence originalList, BlockSequence effectiveList);
     
     /**
      * Phase 3 of Knuth algorithm: Adds the areas 
@@ -181,20 +190,22 @@ public abstract class AbstractBreaker {
      * @param effectiveList effective Knuth element list (after adjustments)
      */
     protected void addAreas(PageBreakingAlgorithm alg, int partCount, 
-            KnuthSequence originalList, KnuthSequence effectiveList) {
+            BlockSequence originalList, BlockSequence effectiveList) {
         LayoutContext childLC;
         // add areas
         ListIterator effectiveListIterator = effectiveList.listIterator();
         int startElementIndex = 0;
         int endElementIndex = 0;
         for (int p = 0; p < partCount; p++) {
-            int displayAlign = getCurrentDisplayAlign();
-            
             PageBreakPosition pbp = (PageBreakPosition) alg.getPageBreaks().get(p);
             endElementIndex = pbp.getLeafPos();
-            System.out.println("PLM> page: " + (p + 1)
+            System.out.println("PLM> part: " + (p + 1)
                     + ", break at position " + endElementIndex);
 
+            startPart(effectiveList);
+            
+            int displayAlign = getCurrentDisplayAlign();
+            
             // ignore the first elements added by the
             // PageSequenceLayoutManager
             startElementIndex += (startElementIndex == 0) 
@@ -271,9 +282,6 @@ public abstract class AbstractBreaker {
             startElementIndex = pbp.getLeafPos() + 1;
         }
     }
-    protected abstract void finishPart();
-    
-    protected abstract LinkedList getNextKnuthElements(LayoutContext context, int alignment);
     
     /**
      * Gets the next block list (sequence) and adds it to a list of block lists if it's not empty.
@@ -297,15 +305,20 @@ public abstract class AbstractBreaker {
                 switch (breakPenalty.getBreakClass()) {
                 case Constants.EN_PAGE:
                     System.err.println("PLM> break - PAGE");
-                    nextSequenceStartsOn = BlockSequence.ANY_PAGE;
+                    nextSequenceStartsOn = Constants.EN_ANY;
+                    break;
+                case Constants.EN_COLUMN:
+                    System.err.println("PLM> break - COLUMN");
+                    //TODO Fix this when implementing multi-column layout
+                    nextSequenceStartsOn = Constants.EN_COLUMN;
                     break;
                 case Constants.EN_ODD_PAGE:
                     System.err.println("PLM> break - ODD PAGE");
-                    nextSequenceStartsOn = BlockSequence.ODD_PAGE;
+                    nextSequenceStartsOn = Constants.EN_ODD_PAGE;
                     break;
                 case Constants.EN_EVEN_PAGE:
                     System.err.println("PLM> break - EVEN PAGE");
-                    nextSequenceStartsOn = BlockSequence.EVEN_PAGE;
+                    nextSequenceStartsOn = Constants.EN_EVEN_PAGE;
                     break;
                 default:
                     throw new IllegalStateException("Invalid break class: " 
@@ -375,7 +388,7 @@ public abstract class AbstractBreaker {
      * @param availableBPD the available BPD 
      * @return the effective list
      */
-    private KnuthSequence justifyBoxes(BlockSequence blockList, PageBreakingAlgorithm alg, int availableBPD) {
+    private BlockSequence justifyBoxes(BlockSequence blockList, PageBreakingAlgorithm alg, int availableBPD) {
         int iOptPageNumber;
         iOptPageNumber = alg.findBreakingPoints(blockList, availableBPD, 1,
                 true, true);
@@ -532,7 +545,7 @@ public abstract class AbstractBreaker {
         // create a new sequence: the new elements will contain the
         // Positions
         // which will be used in the addAreas() phase
-        KnuthSequence effectiveList = new KnuthSequence();
+        BlockSequence effectiveList = new BlockSequence(blockList.getStartOn());
         effectiveList.addAll(getCurrentChildLM().getChangedKnuthElements(
                 blockList.subList(0, blockList.size() - blockList.ignoreAtEnd),
                 /* 0, */0));
index cb1aab7490aabcbe3b438e312a7719c92e7a8830..31e4e512020d6df213f1e42b49e218e2e55ec194 100644 (file)
@@ -470,8 +470,8 @@ public class BlockContainerLayoutManager extends BlockStackingLayoutManager
         
         //Info for deferred adding of areas
         private PageBreakingAlgorithm deferredAlg;
-        private KnuthSequence deferredOriginalList;
-        private KnuthSequence deferredEffectiveList;
+        private BlockSequence deferredOriginalList;
+        private BlockSequence deferredEffectiveList;
         
         public BlockContainerBreaker(BlockContainerLayoutManager bclm, MinOptMax ipd) {
             this.bclm = bclm;
@@ -536,7 +536,7 @@ public class BlockContainerLayoutManager extends BlockStackingLayoutManager
         }
         
         protected void doPhase3(PageBreakingAlgorithm alg, int partCount, 
-                KnuthSequence originalList, KnuthSequence effectiveList) {
+                BlockSequence originalList, BlockSequence effectiveList) {
             //Defer adding of areas until addAreas is called by the parent LM
             this.deferredAlg = alg;
             this.deferredOriginalList = originalList;
index d36a6f904e2ba345bacd49b0d2dae76133d9b128..34375c44a134155c4df6d6f45e9949cf96bce90f 100644 (file)
@@ -1310,6 +1310,9 @@ public class BlockLayoutManager extends BlockStackingLayoutManager
         if (curBlockArea == null) {
             curBlockArea = new Block();
 
+            TraitSetter.addBreaks(curBlockArea, 
+                    fobj.getBreakBefore(), fobj.getBreakAfter());
+
             // Must get dimensions from parent area
             //Don't optimize this line away. It can have ugly side-effects.
             /*Area parentArea =*/ parentLM.getParentArea(curBlockArea);
@@ -1322,8 +1325,6 @@ public class BlockLayoutManager extends BlockStackingLayoutManager
             TraitSetter.addMargins(curBlockArea,
                     fobj.getCommonBorderPaddingBackground(), 
                     fobj.getCommonMarginBlock());
-            TraitSetter.addBreaks(curBlockArea, 
-                    fobj.getBreakBefore(), fobj.getBreakAfter());
 
             // Set up dimensions
             // Get reference IPD from parentArea
index b0b9d908cf68a1c82749b944a44e3b6e08595789..52179432102d137e2756addf0f1ac42390e9bc97 100644 (file)
@@ -46,7 +46,7 @@ import org.apache.fop.fo.flow.Marker;
 import org.apache.fop.fo.pagination.PageSequence;
 import org.apache.fop.fo.pagination.Region;
 import org.apache.fop.fo.pagination.RegionBody;
-import org.apache.fop.fo.pagination.RegionOuter;
+import org.apache.fop.fo.pagination.SideRegion;
 import org.apache.fop.fo.pagination.SimplePageMaster;
 import org.apache.fop.fo.pagination.StaticContent;
 import org.apache.fop.fo.properties.CommonMarginBlock;
@@ -65,6 +65,7 @@ import org.apache.fop.traits.MinOptMax;
 public class PageSequenceLayoutManager extends AbstractLayoutManager {
     private PageSequence pageSeq;
 
+    /*
     private static class BlockBreakPosition extends LeafPosition {
         protected BreakPoss breakps;
 
@@ -72,7 +73,7 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
             super(lm, 0);
             breakps = bp;
         }
-    }
+    }*/
 
 
     private int startPageNum = 0;
@@ -117,7 +118,7 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
     //private HashMap staticContentLMs = new HashMap(4);
 
     private FlowLayoutManager childFLM = null;
-
+    
     /**
      * Constructor - activated by AreaTreeHandler for each
      * fo:page-sequence in the input FO stream
@@ -153,7 +154,7 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
      */
     public void activateLayout() {
         startPageNum = pageSeq.getStartingPageNumber();
-        currentPageNum = startPageNum;
+        currentPageNum = startPageNum - 1;
         pageNumberString = pageSeq.makeFormattedPageNumber(currentPageNum);
 
         LineArea title = null;
@@ -185,11 +186,18 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
     private class PageBreaker extends AbstractBreaker {
         
         private PageSequenceLayoutManager pslm;
+        private boolean firstPart = true;
         
         public PageBreaker(PageSequenceLayoutManager pslm) {
             this.pslm = pslm;
         }
         
+        protected LayoutContext createLayoutContext() {
+            LayoutContext lc = new LayoutContext(0);
+            lc.setRefIPD(flowIPD);
+            return lc;
+        }
+        
         protected LayoutManager getTopLevelLM() {
             return pslm;
         }
@@ -211,18 +219,32 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
         }
         
         protected void doPhase3(PageBreakingAlgorithm alg, int partCount, 
-                KnuthSequence originalList, KnuthSequence effectiveList) {
+                BlockSequence originalList, BlockSequence effectiveList) {
             //Directly add areas after finding the breaks
             addAreas(alg, partCount, originalList, effectiveList);
         }
         
-        protected void finishPart() {
+        protected void startPart(BlockSequence list) {
+            if (curPage == null) {
+                throw new IllegalStateException("curPage must not be null");
+            } else {
+                //firstPart is necessary because we need the first page before we start the 
+                //algorithm so we have a BPD and IPD. This may subject to change later when we
+                //start handling more complex cases.
+                if (!firstPart) {
+                    if (curSpan.hasMoreAvailableFlows()) {
+                        curFlow = curSpan.addAdditionalNormalFlow();
+                    } else {
+                        handleBreak(list.getStartOn());
+                    }
+                }
+            }
             // add static areas and resolve any new id areas
             // finish page and add to area tree
-            finishPage();
-            currentPageNum++;
-            pageNumberString = pageSeq
-                    .makeFormattedPageNumber(currentPageNum);
+            firstPart = false;
+        }
+        
+        protected void finishPart() {
         }
         
         protected LayoutManager getCurrentChildLM() {
@@ -259,8 +281,8 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
 /*LF*/      }
 
             LayoutContext childLC = new LayoutContext(0);
-            childLC.setStackLimit(new MinOptMax(flowBPD));
-            childLC.setRefIPD(flowIPD);
+            childLC.setStackLimit(context.getStackLimit());
+            childLC.setRefIPD(context.getRefIPD());
 
             if (!curLM.isFinished()) {
                 pageSeq.setLayoutDimension(PercentBase.REFERENCE_AREA_IPD, flowIPD);
@@ -419,6 +441,9 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
     private PageViewport makeNewPage(boolean bIsBlank, boolean bIsLast) {
         finishPage();
 
+        currentPageNum++;
+        pageNumberString = pageSeq.makeFormattedPageNumber(currentPageNum);
+
         try {
             // create a new page
             currentSimplePageMaster = pageSeq.getSimplePageMasterToUse(
@@ -437,22 +462,34 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
 
         curPage.setPageNumberString(pageNumberString);
         if (log.isDebugEnabled()) {
-            log.debug("[" + curPage.getPageNumberString() + "]");
+            log.debug("[" + curPage.getPageNumberString() + (bIsBlank ? "*" : "") + "]");
         }
 
         flowBPD = (int) curPage.getBodyRegion().getBPD();
-        createSpan(curPage.getBodyRegion().getColumnCount());
+        createSpan(curPage.getBodyRegion(), false);
         return curPage;
     }
 
-    private void createSpan(int numCols) {
+    /**
+     * Creates a new span reference area.
+     * @param bodyRegion The region-body to create the span for
+     * @param spanned true if a spanned region should be created
+     */
+    private void createSpan(BodyRegion bodyRegion, boolean spanned) {
         // get Width or Height as IPD for span
         RegionViewport rv = curPage.getPage().getRegionViewport(FO_REGION_BODY);
         int ipdWidth = (int) rv.getRegion().getIPD() -
             rv.getBorderAndPaddingWidthStart() - rv.getBorderAndPaddingWidthEnd();
 
-        // currently hardcoding to one column, replace with numCols when ready
-        curSpan = new Span(1 /* numCols */, ipdWidth);
+        //TODO currently hardcoding to one column, replace with numCols when ready
+        if (spanned) {
+            curSpan = new Span(1, ipdWidth);
+        } else {
+            int colWidth 
+                = (ipdWidth - (bodyRegion.getColumnCount() - 1) * bodyRegion.getColumnGap()) 
+                    / bodyRegion.getColumnCount();
+            curSpan = new Span(bodyRegion.getColumnCount(), colWidth);
+        }
 
         //curSpan.setPosition(BPD, newpos);
         curPage.getBodyRegion().getMainReference().addSpan(curSpan);
@@ -460,7 +497,7 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
     }
 
     private void layoutStaticContent(int regionID) {
-        RegionOuter reg = (RegionOuter)currentSimplePageMaster.getRegion(regionID);
+        SideRegion reg = (SideRegion)currentSimplePageMaster.getRegion(regionID);
         if (reg == null) {
             return;
         }
@@ -526,11 +563,61 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
         layoutStaticContent(FO_REGION_END);
         // Queue for ID resolution and rendering
         areaTreeModel.addPage(curPage);
+        log.debug("page finished: " + curPage.getPageNumberString() + ", current num: " + currentPageNum);
         curPage = null;
         curSpan = null;
         curFlow = null;
     }
 
+    private void prepareNormalFlowArea(Area childArea) {
+        // Need span, break
+        int breakVal = Constants.EN_AUTO;
+        Integer breakBefore = (Integer)childArea.getTrait(Trait.BREAK_BEFORE);
+        if (breakBefore != null) {
+            breakVal = breakBefore.intValue();
+        }
+        if (breakVal != Constants.EN_AUTO) {
+            // We may be forced to make new page
+            handleBreak(breakVal);
+        } else if (curPage == null) {
+            log.debug("curPage is null. Making new page");
+            makeNewPage(false, false);
+        }
+        // Now we should be on the right kind of page
+        boolean bNeedNewSpan = false;
+        /* Determine if a new span is needed.  From the XSL
+         * fo:region-body definition, if an fo:block has a span="ALL"
+         * (i.e., span all columns defined for the region-body), it
+         * must be placed in a span-reference-area whose 
+         * column-count = 1.  If its span-value is "NONE", 
+         * place in a normal Span whose column-count is what
+         * is defined for the region-body. 
+         */  // temporarily hardcoded to EN_NONE.
+        int span = Constants.EN_NONE; // childArea.getSpan()
+        int numColsNeeded;
+        if (span == Constants.EN_ALL) {
+            numColsNeeded = 1;
+        } else { // EN_NONE
+            numColsNeeded = curPage.getBodyRegion().getColumnCount();
+        }
+        if (curSpan == null) {  // should never happen, remove?
+            bNeedNewSpan = true;
+        } else if (numColsNeeded != curSpan.getColumnCount()) {
+            // need a new Span, with numColsNeeded columns
+            if (curSpan.getColumnCount() > 1) {
+                // finished with current span, so balance 
+                // its columns to make them the same "height"
+                // balanceColumns();  // TODO: implement
+            }
+            bNeedNewSpan = true;
+        }
+        if (bNeedNewSpan) {
+            createSpan(curPage.getBodyRegion(), (span == Constants.EN_ALL));
+        } else if (curFlow == null) {  // should not happen
+            curFlow = curSpan.addAdditionalNormalFlow();
+        }
+    }
+    
     /**
      * This is called from FlowLayoutManager when it needs to start
      * a new flow container (while generating areas).
@@ -543,53 +630,8 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
     public Area getParentArea(Area childArea) {
         int aclass = childArea.getAreaClass();
         if (aclass == Area.CLASS_NORMAL) {
-            // todo: how to get properties from the Area???
-            // Need span, break
-            int breakVal = Constants.EN_AUTO;
-            Integer breakBefore = (Integer)childArea.getTrait(Trait.BREAK_BEFORE);
-            if (breakBefore != null) {
-                breakVal = breakBefore.intValue();
-            }
-            if (breakVal != Constants.EN_AUTO) {
-                // We may be forced to make new page
-                handleBreak(breakVal);
-            } else if (curPage == null) {
-                log.debug("curPage is null. Making new page");
-                makeNewPage(false, false);
-            }
-            // Now we should be on the right kind of page
-            boolean bNeedNewSpan = false;
-            /* Determine if a new span is needed.  From the XSL
-             * fo:region-body definition, if an fo:block has a span="ALL"
-             * (i.e., span all columns defined for the region-body), it
-             * must be placed in a span-reference-area whose 
-             * column-count = 1.  If its span-value is "NONE", 
-             * place in a normal Span whose column-count is what
-             * is defined for the region-body. 
-             */  // temporarily hardcoded to EN_NONE.
-            int span = Constants.EN_NONE; // childArea.getSpan()
-            int numColsNeeded;
-            if (span == Constants.EN_ALL) {
-                numColsNeeded = 1;
-            } else { // EN_NONE
-                numColsNeeded = curPage.getBodyRegion().getColumnCount();
-            }
-            if (curSpan == null) {  // should never happen, remove?
-                bNeedNewSpan = true;
-            } else if (numColsNeeded != curSpan.getColumnCount()) {
-                // need a new Span, with numColsNeeded columns
-                if (curSpan.getColumnCount() > 1) {
-                    // finished with current span, so balance 
-                    // its columns to make them the same "height"
-                    // balanceColumns();  // TODO: implement
-                }
-                bNeedNewSpan = true;
-            }
-            if (bNeedNewSpan) {
-                createSpan(numColsNeeded);
-            } else if (curFlow == null) {  // should not happen
-                curFlow = curSpan.addAdditionalNormalFlow();
-            }
+            //We now do this in PageBreaker
+            //prepareNormalFlowArea(childArea);
             return curFlow;
         } else {
             if (curPage == null) {
@@ -625,8 +667,7 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
      */
     private void handleBreak(int breakVal) {
         if (breakVal == Constants.EN_COLUMN) {
-            if (curSpan != null
-                    && curSpan.getNormalFlowCount() < curSpan.getColumnCount()) {
+            if (curSpan != null && curSpan.hasMoreAvailableFlows()) {
                 // Move to next column
                 curFlow = curSpan.addAdditionalNormalFlow();
                 return;
@@ -634,6 +675,7 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
             // else need new page
             breakVal = Constants.EN_PAGE;
         }
+        log.debug("handling break after page " + currentPageNum + " breakVal=" + breakVal);
         if (needEmptyPage(breakVal)) {
             curPage = makeNewPage(true, false);
         }
@@ -652,17 +694,15 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
      */
     private boolean needEmptyPage(int breakValue) {
 
-        if (breakValue == Constants.EN_PAGE || curPage.getPage().isEmpty()) {
+        if (breakValue == Constants.EN_PAGE || ((curPage != null) && curPage.getPage().isEmpty())) {
             // any page is OK or we already have an empty page
             return false;
-        }
-        else {
+        } else {
             /* IF we are on the kind of page we need, we'll need a new page. */
             if (currentPageNum % 2 != 0) {
                 // Current page is odd
                 return (breakValue == Constants.EN_ODD_PAGE);
-            }
-            else {
+            } else {
                 return (breakValue == Constants.EN_EVEN_PAGE);
             }
         }
@@ -676,7 +716,7 @@ public class PageSequenceLayoutManager extends AbstractLayoutManager {
             if (breakValue == Constants.EN_PAGE) {
                 return false;
             }
-            else if (currentPageNum%2 != 0) {
+            else if (currentPageNum % 2 != 0) {
                 // Current page is odd
                 return (breakValue == Constants.EN_EVEN_PAGE);
             }
index 02229b4de75cac5fdf7fc4ab6c35c5add8880644..8fdc7b248ce639e45fcbcbbc57cfdf29dd5eced8 100644 (file)
@@ -22,7 +22,7 @@ import org.apache.fop.area.RegionReference;
 import org.apache.fop.area.Area;
 import org.apache.fop.area.Block;
 import org.apache.fop.fo.pagination.Region;
-import org.apache.fop.fo.pagination.RegionOuter;
+import org.apache.fop.fo.pagination.SideRegion;
 import org.apache.fop.fo.pagination.StaticContent;
 import org.apache.fop.traits.MinOptMax;
 
@@ -233,7 +233,7 @@ public class StaticContentLayoutManager extends BlockStackingLayoutManager {
         log.error("Cannot add marker to static areas");
     }
     
-    public void doLayout(RegionOuter region, StaticContentLayoutManager lm, MinOptMax ipd) {
+    public void doLayout(SideRegion region, StaticContentLayoutManager lm, MinOptMax ipd) {
         StaticContentBreaker breaker = new StaticContentBreaker(region, lm, ipd);
         breaker.doLayout(lm.getRegionReference().getBPD());
         if (breaker.isOverflow()) {
@@ -306,7 +306,7 @@ public class StaticContentLayoutManager extends BlockStackingLayoutManager {
         }
         
         protected void doPhase3(PageBreakingAlgorithm alg, int partCount, 
-                KnuthSequence originalList, KnuthSequence effectiveList) {
+                BlockSequence originalList, BlockSequence effectiveList) {
             //Directly add areas after finding the breaks
             addAreas(alg, partCount, originalList, effectiveList);
             if (partCount > 1) {
index 2492ab129b1c6e8b8b5fc3c863774af81bbda7fe..3e03c924f0884d5a8bf63ec066bf5e94fe5260f7 100644 (file)
@@ -374,19 +374,24 @@ public abstract class AbstractRenderer
 
         Span span = null;
         List spans = mr.getSpans();
+        int saveBPPos = currentBPPosition;
         for (int count = 0; count < spans.size(); count++) {
             span = (Span) spans.get(count);
             int offset = (mr.getWidth()
-                    - (span.getColumnCount() - 1) * mr.getColumnGap())
-                    / span.getColumnCount() + mr.getColumnGap();
+                    - (mr.getColumnCount() - 1) * mr.getColumnGap())
+                    / mr.getColumnCount() + mr.getColumnGap();
             for (int c = 0; c < span.getColumnCount(); c++) {
                 NormalFlow flow = (NormalFlow) span.getNormalFlow(c);
 
-                renderFlow(flow);
-                currentIPPosition += offset;
+                if (flow != null) {
+                    currentBPPosition = saveBPPos;
+                    renderFlow(flow);
+                    currentIPPosition += flow.getIPD();
+                    currentIPPosition += offset;
+                }
             }
             currentIPPosition = saveIPPos;
-            currentBPPosition += span.getHeight();
+            currentBPPosition = saveBPPos + span.getHeight();
         }
     }