Index: . =================================================================== --- . (revision 614590) +++ . (working copy) @@ -68,12 +68,9 @@ /** Counter, increased every time a non-white-space is encountered */ private int nonWhiteSpaceCount; - private Block currentBlock; - private FObj currentFO; private int linefeedTreatment; private int whiteSpaceTreatment; private int whiteSpaceCollapse; - private FONode nextChild; private boolean endOfBlock; private boolean nextChildIsBlockLevel; private RecursiveCharIterator charIter; @@ -87,142 +84,127 @@ * firstTextNode * @param fo the FO for which to handle white-space * @param firstTextNode the node at which to start - */ - public void handleWhiteSpace(FObjMixed fo, FONode firstTextNode) { - - int foId = fo.getNameId(); - - if (foId == Constants.FO_BLOCK) { - if (nextChild != null && currentBlock != null) { - /* if already in a block, push the current block - * onto the stack of nested blocks - */ - nestedBlockStack.push(currentBlock); - } - currentBlock = (Block) fo; - } else if (foId == Constants.FO_RETRIEVE_MARKER) { - /* look for the nearest block ancestor, if any */ - FONode ancestor = fo; - do { - ancestor = ancestor.getParent(); - } while (ancestor.getNameId() != Constants.FO_BLOCK - && ancestor.getNameId() != Constants.FO_STATIC_CONTENT); - - if (ancestor.getNameId() == Constants.FO_BLOCK) { - currentBlock = (Block) ancestor; - } - } - - if (currentBlock != null) { - linefeedTreatment = currentBlock.getLinefeedTreatment(); - whiteSpaceCollapse = currentBlock.getWhitespaceCollapse(); - whiteSpaceTreatment = currentBlock.getWhitespaceTreatment(); - } else { - linefeedTreatment = Constants.EN_TREAT_AS_SPACE; - whiteSpaceCollapse = Constants.EN_TRUE; - whiteSpaceTreatment = Constants.EN_IGNORE_IF_SURROUNDING_LINEFEED; - } - - currentFO = fo; + * @param nextChild the child-node that will be added to the list after + * the last text-node + */ + public void handleWhiteSpace(FObjMixed fo, FONode firstTextNode, FONode nextChild) { + Block currentBlock = null; + int foId = fo.getNameId(); - if (firstTextNode == null) { - //nothing to do but initialize related properties - return; - } - - charIter = new RecursiveCharIterator(fo, firstTextNode); - inWhiteSpace = false; - - if (currentFO == currentBlock - || currentBlock == null - || (foId == Constants.FO_RETRIEVE_MARKER - && currentFO.getParent() == currentBlock)) { - afterLinefeed = ( - (firstTextNode == fo.firstChild) - || (firstTextNode.siblings[0].getNameId() - == Constants.FO_BLOCK)); - } - - endOfBlock = (nextChild == null && currentFO == currentBlock); - - if (nextChild != null) { - int nextChildId = this.nextChild.getNameId(); - nextChildIsBlockLevel = ( - nextChildId == Constants.FO_BLOCK - || nextChildId == Constants.FO_TABLE_AND_CAPTION - || nextChildId == Constants.FO_TABLE - || nextChildId == Constants.FO_LIST_BLOCK - || nextChildId == Constants.FO_BLOCK_CONTAINER); - } else { - nextChildIsBlockLevel = false; - } - - handleWhiteSpace(); - - if (currentFO == currentBlock - && pendingInlines != null - && !pendingInlines.isEmpty()) { - /* current FO is a block, and has pending inlines */ - if (endOfBlock || nextChildIsBlockLevel) { - if (nonWhiteSpaceCount == 0) { - /* handle white-space for all pending inlines*/ - PendingInline p; - for (int i = pendingInlines.size(); --i >= 0;) { - p = (PendingInline)pendingInlines.get(i); - charIter = (RecursiveCharIterator)p.firstTrailingWhiteSpace; - handleWhiteSpace(); - pendingInlines.remove(p); - } - } else { - /* there is non-white-space text between the pending - * inline(s) and the end of the block; - * clear list of pending inlines */ - pendingInlines.clear(); - } - } - } - - if (nextChild == null) { - if (currentFO != currentBlock) { - /* current FO is not a block, and is about to end */ - if (nonWhiteSpaceCount > 0 && pendingInlines != null) { - /* there is non-white-space text between the pending - * inline(s) and the end of the non-block node; - * clear list of pending inlines */ - pendingInlines.clear(); - } - if (inWhiteSpace) { - /* means there is at least one trailing space in the - inline FO that is about to end */ - addPendingInline(fo); - } - } else { - /* end of block: clear the references and pop the - * nested block stack */ - if (!nestedBlockStack.empty()) { - currentBlock = (Block) nestedBlockStack.pop(); - } else { - currentBlock = null; - } - currentFO = null; - charIter = null; - } - } - } - - /** - * Handle white-space for the fo that is passed in, starting at - * firstTextNode (when a nested FO is encountered) - * @param fo the FO for which to handle white-space - * @param firstTextNode the node at which to start - * @param nextChild the child-node that will be added to the list after - * the last text-node - */ - public void handleWhiteSpace(FObjMixed fo, FONode firstTextNode, FONode nextChild) { - this.nextChild = nextChild; - handleWhiteSpace(fo, firstTextNode); - this.nextChild = null; - } + if (foId == Constants.FO_BLOCK) { + currentBlock = (Block) fo; + /* remember nested blocks */ + if( nestedBlockStack.isEmpty() || fo != nestedBlockStack.peek()){ + if (nextChild != null) { + nestedBlockStack.push(currentBlock); + } + } else { + if (nextChild == null) { + nestedBlockStack.pop(); + } + } + } else if (foId == Constants.FO_RETRIEVE_MARKER) { + /* look for the nearest block ancestor, if any */ + FONode ancestor = fo; + do { + ancestor = ancestor.getParent(); + } + while (ancestor.getNameId() != Constants.FO_BLOCK && ancestor.getNameId() != Constants.FO_STATIC_CONTENT); + + if (ancestor.getNameId() == Constants.FO_BLOCK) { + currentBlock = (Block) ancestor; + } + } else if( !nestedBlockStack.isEmpty() ){ + currentBlock = (Block) nestedBlockStack.peek(); + } + + if (currentBlock != null) { + linefeedTreatment = currentBlock.getLinefeedTreatment(); + whiteSpaceCollapse = currentBlock.getWhitespaceCollapse(); + whiteSpaceTreatment = currentBlock.getWhitespaceTreatment(); + } else { + linefeedTreatment = Constants.EN_TREAT_AS_SPACE; + whiteSpaceCollapse = Constants.EN_TRUE; + whiteSpaceTreatment = Constants.EN_IGNORE_IF_SURROUNDING_LINEFEED; + } + + if (firstTextNode == null) { + // nothing to do but initialize related properties + return; + } + + charIter = new RecursiveCharIterator(fo, firstTextNode); + inWhiteSpace = false; + + if (fo == currentBlock || currentBlock == null || (foId == Constants.FO_RETRIEVE_MARKER && fo.getParent() == currentBlock)) { + afterLinefeed = ((firstTextNode == fo.firstChild) || (firstTextNode.siblings[0].getNameId() == Constants.FO_BLOCK)); + } + + endOfBlock = (nextChild == null && fo == currentBlock); + + if (nextChild != null) { + int nextChildId = nextChild.getNameId(); + nextChildIsBlockLevel = (nextChildId == Constants.FO_BLOCK || nextChildId == Constants.FO_TABLE_AND_CAPTION || nextChildId == Constants.FO_TABLE || nextChildId == Constants.FO_LIST_BLOCK || nextChildId == Constants.FO_BLOCK_CONTAINER); + } else { + nextChildIsBlockLevel = false; + } + + handleWhiteSpace(); + + if (fo == currentBlock && pendingInlines != null && !pendingInlines.isEmpty()) { + /* current FO is a block, and has pending inlines */ + if (endOfBlock || nextChildIsBlockLevel) { + if (nonWhiteSpaceCount == 0) { + /* handle white-space for all pending inlines */ + PendingInline p; + for (int i = pendingInlines.size(); --i >= 0;) { + p = (PendingInline) pendingInlines.get(i); + charIter = (RecursiveCharIterator) p.firstTrailingWhiteSpace; + handleWhiteSpace(); + pendingInlines.remove(p); + } + } else { + /* + * there is non-white-space text between the pending inline(s) and the + * end of the block; clear list of pending inlines + */ + pendingInlines.clear(); + } + } + } + + if (nextChild == null) { + if (fo != currentBlock) { + /* current FO is not a block, and is about to end */ + if (nonWhiteSpaceCount > 0 && pendingInlines != null) { + /* + * there is non-white-space text between the pending inline(s) and the + * end of the non-block node; clear list of pending inlines + */ + pendingInlines.clear(); + } + if (inWhiteSpace) { + /* + * means there is at least one trailing space in the inline FO that is + * about to end + */ + addPendingInline(fo); + } + } else { + charIter = null; + } + } + } + + /** + * Handle white-space for the fo that is passed in, starting at + * firstTextNode (when a nested FO is encountered) + * @param fo the FO for which to handle white-space + * @param firstTextNode the node at which to start + */ + public void handleWhiteSpace(FObjMixed fo, FONode firstTextNode) { + handleWhiteSpace(fo, firstTextNode, null); + } private void handleWhiteSpace() {