From 055f5f638d5e2894f47f6a725a47832f2083a4b3 Mon Sep 17 00:00:00 2001 From: Alexander Dyuzhev Date: Mon, 18 Nov 2024 23:36:02 +0300 Subject: [PATCH] updated for Apache FOP 2.10, #301 --- Makefile | 2 +- README.adoc | 10 +++---- pom.xml | 12 ++++---- .../org/apache/fop/apps/FopConfParser.java | 18 +++++++++++ .../org/apache/fop/events/EventFormatter.java | 8 ++--- .../BlockContainerLayoutManager.java | 8 ++--- .../layoutmgr/BlockStackingLayoutManager.java | 18 +++++------ .../fop/layoutmgr/FlowLayoutManager.java | 8 ++--- .../apache/fop/layoutmgr/LayoutContext.java | 16 +++++----- .../layoutmgr/StaticContentLayoutManager.java | 2 +- .../inline/InlineContainerLayoutManager.java | 10 +++---- .../layoutmgr/inline/LineLayoutManager.java | 30 ++++++++++--------- .../layoutmgr/inline/TextLayoutManager.java | 18 ++++++----- .../org/apache/fop/pdf/PDFStructElem.java | 20 ++++++++++++- .../fop/render/intermediate/IFParser.java | 29 ++++++++++++++++-- .../extensions/DocumentNavigationHandler.java | 19 +++++++++++- .../fop/render/pdf/PDFRenderingUtil.java | 5 ++++ .../fop/svg/font/FOPGVTGlyphVector.java | 4 +++ 18 files changed, 164 insertions(+), 73 deletions(-) diff --git a/Makefile b/Makefile index 7c946f80..fed964d5 100644 --- a/Makefile +++ b/Makefile @@ -6,7 +6,7 @@ SHELL ?= /bin/bash endif #JAR_VERSION := $(shell mvn -q -Dexec.executable="echo" -Dexec.args='$${project.version}' --non-recursive exec:exec -DforceStdout) -JAR_VERSION := 2.09 +JAR_VERSION := 2.10 JAR_FILE := mn2pdf-$(JAR_VERSION).jar all: target/$(JAR_FILE) diff --git a/README.adoc b/README.adoc index 1a38935c..b4a2031a 100644 --- a/README.adoc +++ b/README.adoc @@ -17,14 +17,14 @@ You will need the Java Development Kit (JDK) version 8, Update 241 (8u241) or hi [source,sh] ---- -java -Xss5m -Xmx2048m -jar target/mn2pdf-2.09.jar --xml-file --xsl-file --pdf-file [--syntax-highlight] +java -Xss5m -Xmx2048m -jar target/mn2pdf-2.10.jar --xml-file --xsl-file --pdf-file [--syntax-highlight] ---- e.g. [source,sh] ---- -java -Xss5m -Xmx2048m -jar target/mn2pdf-2.09.jar --xml-file tests/G.191.xml --xsl-file tests/itu.recommendation.xsl --pdf-file tests/G.191.pdf +java -Xss5m -Xmx2048m -jar target/mn2pdf-2.10.jar --xml-file tests/G.191.xml --xsl-file tests/itu.recommendation.xsl --pdf-file tests/G.191.pdf ---- === PDF encryption features @@ -100,7 +100,7 @@ Update version in `pom.xml`, e.g.: ---- org.metanorma.fop mn2pdf -2.09 +2.10 Metanorma XML to PDF converter ---- @@ -111,8 +111,8 @@ Tag the same version in Git: [source,xml] ---- -git tag v2.09 -git push origin v2.09 +git tag v2.10 +git push origin v2.10 ---- Then the corresponding GitHub release will be automatically created at: diff --git a/pom.xml b/pom.xml index dee2a65f..9cec2660 100644 --- a/pom.xml +++ b/pom.xml @@ -5,7 +5,7 @@ 4.0.0 org.metanorma.fop mn2pdf - 2.09 + 2.10 Metanorma XML to PDF converter jar https://www.metanorma.org @@ -150,12 +150,12 @@ org.apache.xmlgraphics fop - 2.9 + 2.10 org.apache.xmlgraphics fop-pdf-images - 2.9 + 2.10 org.apache.pdfbox @@ -190,7 +190,7 @@ org.apache.xmlgraphics xmlgraphics-commons - 2.8 + 2.10 xalan @@ -217,7 +217,7 @@ org.apache.xmlgraphics batik-all - 1.16 + 1.18 org.python @@ -249,7 +249,7 @@ org.apache.pdfbox pdfbox - 2.0.24 + 2.0.27 diff --git a/src/main/java/org/apache/fop/apps/FopConfParser.java b/src/main/java/org/apache/fop/apps/FopConfParser.java index daff13e3..369c472b 100644 --- a/src/main/java/org/apache/fop/apps/FopConfParser.java +++ b/src/main/java/org/apache/fop/apps/FopConfParser.java @@ -59,6 +59,8 @@ public class FopConfParser { private static final String TABLE_BORDER_OVERPAINT = "table-border-overpaint"; private static final String SIMPLE_LINE_BREAKING = "simple-line-breaking"; private static final String SKIP_PAGE_POSITION_ONLY_ALLOWED = "skip-page-position-only-allowed"; + private static final String LEGACY_SKIP_PAGE_POSITION_ONLY = "legacy-skip-page-position-only"; + private static final String LEGACY_LAST_PAGE_CHANGE_IPD = "legacy-last-page-change-ipd"; private final Log log = LogFactory.getLog(FopConfParser.class); @@ -299,6 +301,22 @@ private void configure(final URI baseURI, final ResourceResolver resourceResolve LogUtil.handleException(log, e, false); } } + if (cfg.getChild(LEGACY_SKIP_PAGE_POSITION_ONLY, false) != null) { + try { + fopFactoryBuilder.setLegacySkipPagePositionOnly( + cfg.getChild(LEGACY_SKIP_PAGE_POSITION_ONLY).getValueAsBoolean()); + } catch (ConfigurationException e) { + LogUtil.handleException(log, e, false); + } + } + if (cfg.getChild(LEGACY_LAST_PAGE_CHANGE_IPD, false) != null) { + try { + fopFactoryBuilder.setLegacyLastPageChangeIPD( + cfg.getChild(LEGACY_LAST_PAGE_CHANGE_IPD).getValueAsBoolean()); + } catch (ConfigurationException e) { + LogUtil.handleException(log, e, false); + } + } // configure font manager new FontManagerConfigurator(cfg, baseURI, fopFactoryBuilder.getBaseURI(), resourceResolver) diff --git a/src/main/java/org/apache/fop/events/EventFormatter.java b/src/main/java/org/apache/fop/events/EventFormatter.java index d4825f86..55fd8766 100644 --- a/src/main/java/org/apache/fop/events/EventFormatter.java +++ b/src/main/java/org/apache/fop/events/EventFormatter.java @@ -31,10 +31,10 @@ import org.apache.fop.events.model.EventSeverity; import org.apache.fop.layoutmgr.LayoutManager; -import org.apache.fop.util.XMLResourceBundle; -import org.apache.fop.util.text.AdvancedMessageFormat; -import org.apache.fop.util.text.AdvancedMessageFormat.Part; -import org.apache.fop.util.text.AdvancedMessageFormat.PartFactory; +import org.apache.fop.utils.XMLResourceBundle; +import org.apache.fop.utils.text.AdvancedMessageFormat; +import org.apache.fop.utils.text.AdvancedMessageFormat.Part; +import org.apache.fop.utils.text.AdvancedMessageFormat.PartFactory; /** * Converts events into human-readable, localized messages. diff --git a/src/main/java/org/apache/fop/layoutmgr/BlockContainerLayoutManager.java b/src/main/java/org/apache/fop/layoutmgr/BlockContainerLayoutManager.java index 3b4f116c..8e30a15e 100644 --- a/src/main/java/org/apache/fop/layoutmgr/BlockContainerLayoutManager.java +++ b/src/main/java/org/apache/fop/layoutmgr/BlockContainerLayoutManager.java @@ -187,7 +187,7 @@ public int getContentAreaBPD() { /** {@inheritDoc} */ @Override - public List getNextKnuthElements(LayoutContext context, int alignment) { + public List getNextKnuthElements(LayoutContext context, int alignment) { return getNextKnuthElements(context, alignment, null, null, null); } @@ -208,7 +208,7 @@ protected LayoutContext makeChildLayoutContext(LayoutContext context) { /** {@inheritDoc} */ @Override - public List getNextKnuthElements(LayoutContext context, int alignment, Stack lmStack, + public List getNextKnuthElements(LayoutContext context, int alignment, Stack lmStack, Position restartPosition, LayoutManager restartAtLM) { resetSpaces(); @@ -674,14 +674,14 @@ protected LayoutContext createLayoutContext() { return lc; } - protected List getNextKnuthElements(LayoutContext context, int alignment) { + protected List getNextKnuthElements(LayoutContext context, int alignment) { LayoutManager curLM; // currently active LM List returnList = new LinkedList(); while ((curLM = getChildLM()) != null) { LayoutContext childLC = makeChildLayoutContext(context); - List returnedList = null; + List returnedList = null; if (!curLM.isFinished()) { returnedList = curLM.getNextKnuthElements(childLC, alignment); } diff --git a/src/main/java/org/apache/fop/layoutmgr/BlockStackingLayoutManager.java b/src/main/java/org/apache/fop/layoutmgr/BlockStackingLayoutManager.java index 3794f38a..d5c53ab1 100644 --- a/src/main/java/org/apache/fop/layoutmgr/BlockStackingLayoutManager.java +++ b/src/main/java/org/apache/fop/layoutmgr/BlockStackingLayoutManager.java @@ -237,13 +237,13 @@ protected int updateContentAreaIPDwithOverconstrainedAdjust(int contentIPD) { /** {@inheritDoc} */ @Override - public List getNextKnuthElements(LayoutContext context, int alignment) { + public List getNextKnuthElements(LayoutContext context, int alignment) { return getNextKnuthElements(context, alignment, null, null, null); } /** {@inheritDoc} */ @Override - public List getNextKnuthElements(LayoutContext context, int alignment, + public List getNextKnuthElements(LayoutContext context, int alignment, Stack lmStack, Position restartPosition, LayoutManager restartAtLM) { isRestartAtLM = restartAtLM != null; referenceIPD = context.getRefIPD(); @@ -670,12 +670,12 @@ public void discardSpace(KnuthGlue spaceGlue) { /** {@inheritDoc} */ @Override - public List getChangedKnuthElements(List oldList, int alignment) { + public List getChangedKnuthElements(List oldList, int alignment) { ListIterator oldListIterator = oldList.listIterator(); KnuthElement currElement = null; KnuthElement prevElement = null; List returnedList = new LinkedList(); - List returnList = new LinkedList(); + List returnList = new LinkedList<>(); int fromIndex = 0; // "unwrap" the Positions stored in the elements @@ -992,7 +992,7 @@ protected SpaceProperty getSpaceAfterProperty() { * @param isFirst true if this is the first time a layout manager instance needs to generate * border and padding */ - protected void addKnuthElementsForBorderPaddingBefore(List returnList, boolean isFirst) { + protected void addKnuthElementsForBorderPaddingBefore(List returnList, boolean isFirst) { //Border and Padding (before) CommonBorderPaddingBackground borderAndPadding = getBorderPaddingBackground(); if (borderAndPadding != null) { @@ -1019,7 +1019,7 @@ protected void addKnuthElementsForBorderPaddingBefore(List returnList, boolean i * @param isLast true if this is the last time a layout manager instance needs to generate * border and padding */ - protected void addKnuthElementsForBorderPaddingAfter(List returnList, boolean isLast) { + protected void addKnuthElementsForBorderPaddingAfter(List returnList, boolean isLast) { //Border and Padding (after) CommonBorderPaddingBackground borderAndPadding = getBorderPaddingBackground(); if (borderAndPadding != null) { @@ -1165,7 +1165,7 @@ public int getLastIndex() { * @param sourceList source list * @param targetList target list receiving the wrapped position elements */ - protected void wrapPositionElements(List sourceList, List targetList) { + protected void wrapPositionElements(List sourceList, List targetList) { wrapPositionElements(sourceList, targetList, false); } @@ -1176,7 +1176,7 @@ protected void wrapPositionElements(List sourceList, List targetList) { * @param targetList target list receiving the wrapped position elements * @param force if true, every Position is wrapped regardless of its LM of origin */ - protected void wrapPositionElements(List sourceList, List targetList, boolean force) { + protected void wrapPositionElements(List sourceList, List targetList, boolean force) { ListIterator listIter = sourceList.listIterator(); Object tempElement; @@ -1202,7 +1202,7 @@ protected void wrapPositionElements(List sourceList, List targetList, boolean fo * @param targetList target list receiving the wrapped position elements * @param force if true, every Position is wrapped regardless of its LM of origin */ - protected void wrapPositionElement(ListElement el, List targetList, boolean force) { + protected void wrapPositionElement(ListElement el, List targetList, boolean force) { if (force || el.getLayoutManager() != this) { el.setPosition(notifyPos(new NonLeafPosition(this, el.getPosition()))); } diff --git a/src/main/java/org/apache/fop/layoutmgr/FlowLayoutManager.java b/src/main/java/org/apache/fop/layoutmgr/FlowLayoutManager.java index 4289f157..db3f0a36 100644 --- a/src/main/java/org/apache/fop/layoutmgr/FlowLayoutManager.java +++ b/src/main/java/org/apache/fop/layoutmgr/FlowLayoutManager.java @@ -66,7 +66,7 @@ public FlowLayoutManager(PageSequenceLayoutManager pslm, Flow node) { /** {@inheritDoc} */ @Override - public List getNextKnuthElements(LayoutContext context, int alignment) { + public List getNextKnuthElements(LayoutContext context, int alignment) { return getNextKnuthElements(context, alignment, null, null); } @@ -80,7 +80,7 @@ public List getNextKnuthElements(LayoutContext context, int alignment) { * @return the list of KnuthElements * @see LayoutManager#getNextKnuthElements(LayoutContext,int) */ - List getNextKnuthElements(LayoutContext context, int alignment, + List getNextKnuthElements(LayoutContext context, int alignment, Position restartPosition, LayoutManager restartLM) { List elements = new LinkedList(); @@ -290,11 +290,11 @@ public Keep getKeepWithPrevious() { /** {@inheritDoc} */ @Override - public List getChangedKnuthElements(List oldList, int alignment) { + public List getChangedKnuthElements(List oldList, int alignment) { ListIterator oldListIterator = oldList.listIterator(); KnuthElement returnedElement; List returnedList = new LinkedList(); - List returnList = new LinkedList(); + List returnList = new LinkedList<>(); KnuthElement prevElement = null; KnuthElement currElement = null; int fromIndex = 0; diff --git a/src/main/java/org/apache/fop/layoutmgr/LayoutContext.java b/src/main/java/org/apache/fop/layoutmgr/LayoutContext.java index 109ce649..86d4d619 100644 --- a/src/main/java/org/apache/fop/layoutmgr/LayoutContext.java +++ b/src/main/java/org/apache/fop/layoutmgr/LayoutContext.java @@ -85,13 +85,13 @@ public final class LayoutContext { * A list of pending marks (border and padding) on the after edge when a page break occurs. * May be null. */ - private List pendingAfterMarks; + private List pendingAfterMarks; /** * A list of pending marks (border and padding) on the before edge when a page break occurs. * May be null. */ - private List pendingBeforeMarks; + private List pendingBeforeMarks; /** Current hyphenation context. May be null. */ private HyphContext hyphContext; @@ -178,10 +178,10 @@ private LayoutContext(int flags) { /** @param source from which pending marks are copied */ public void copyPendingMarksFrom(LayoutContext source) { if (source.pendingAfterMarks != null) { - this.pendingAfterMarks = new java.util.ArrayList(source.pendingAfterMarks); + this.pendingAfterMarks = new java.util.ArrayList<>(source.pendingAfterMarks); } if (source.pendingBeforeMarks != null) { - this.pendingBeforeMarks = new java.util.ArrayList(source.pendingBeforeMarks); + this.pendingBeforeMarks = new java.util.ArrayList<>(source.pendingBeforeMarks); } } @@ -335,7 +335,7 @@ public SpaceSpecifier getTrailingSpace() { */ public void addPendingAfterMark(UnresolvedListElementWithLength element) { if (this.pendingAfterMarks == null) { - this.pendingAfterMarks = new java.util.ArrayList(); + this.pendingAfterMarks = new java.util.ArrayList<>(); } this.pendingAfterMarks.add(element); } @@ -344,7 +344,7 @@ public void addPendingAfterMark(UnresolvedListElementWithLength element) { * @return the pending border and padding elements at the after edge * @see #addPendingAfterMark(UnresolvedListElementWithLength) */ - public List getPendingAfterMarks() { + public List getPendingAfterMarks() { if (this.pendingAfterMarks != null) { return Collections.unmodifiableList(this.pendingAfterMarks); } else { @@ -368,7 +368,7 @@ public void clearPendingMarks() { */ public void addPendingBeforeMark(UnresolvedListElementWithLength element) { if (this.pendingBeforeMarks == null) { - this.pendingBeforeMarks = new java.util.ArrayList(); + this.pendingBeforeMarks = new java.util.ArrayList<>(); } this.pendingBeforeMarks.add(element); } @@ -377,7 +377,7 @@ public void addPendingBeforeMark(UnresolvedListElementWithLength element) { * @return the pending border and padding elements at the before edge * @see #addPendingBeforeMark(UnresolvedListElementWithLength) */ - public List getPendingBeforeMarks() { + public List getPendingBeforeMarks() { if (this.pendingBeforeMarks != null) { return Collections.unmodifiableList(this.pendingBeforeMarks); } else { diff --git a/src/main/java/org/apache/fop/layoutmgr/StaticContentLayoutManager.java b/src/main/java/org/apache/fop/layoutmgr/StaticContentLayoutManager.java index 54ba4560..d14f5922 100644 --- a/src/main/java/org/apache/fop/layoutmgr/StaticContentLayoutManager.java +++ b/src/main/java/org/apache/fop/layoutmgr/StaticContentLayoutManager.java @@ -72,7 +72,7 @@ public StaticContentLayoutManager(PageSequenceLayoutManager pslm, } /** {@inheritDoc} */ - public List getNextKnuthElements(LayoutContext context, int alignment) { + public List getNextKnuthElements(LayoutContext context, int alignment) { throw new IllegalStateException(); } diff --git a/src/main/java/org/apache/fop/layoutmgr/inline/InlineContainerLayoutManager.java b/src/main/java/org/apache/fop/layoutmgr/inline/InlineContainerLayoutManager.java index a8a9c4ca..c66eec72 100644 --- a/src/main/java/org/apache/fop/layoutmgr/inline/InlineContainerLayoutManager.java +++ b/src/main/java/org/apache/fop/layoutmgr/inline/InlineContainerLayoutManager.java @@ -299,11 +299,11 @@ public boolean handleOverflow(int milliPoints) { return true; } - public List addALetterSpaceTo(List oldList) { + public List addALetterSpaceTo(List oldList) { return oldList; } - public List addALetterSpaceTo(List oldList, int depth) { + public List addALetterSpaceTo(List oldList, int depth) { return oldList; } @@ -314,15 +314,15 @@ public String getWordChars(Position pos) { public void hyphenate(Position pos, HyphContext hyphContext) { } - public boolean applyChanges(List oldList) { + public boolean applyChanges(List oldList) { return false; } - public boolean applyChanges(List oldList, int depth) { + public boolean applyChanges(List oldList, int depth) { return false; } - public List getChangedKnuthElements(List oldList, int alignment, int depth) { + public List getChangedKnuthElements(List oldList, int alignment, int depth) { return oldList; } diff --git a/src/main/java/org/apache/fop/layoutmgr/inline/LineLayoutManager.java b/src/main/java/org/apache/fop/layoutmgr/inline/LineLayoutManager.java index 721c8790..ebca2cad 100644 --- a/src/main/java/org/apache/fop/layoutmgr/inline/LineLayoutManager.java +++ b/src/main/java/org/apache/fop/layoutmgr/inline/LineLayoutManager.java @@ -108,7 +108,7 @@ public class LineLayoutManager extends InlineStackingLayoutManager * Each value holds the start and end indexes into a List of * inline break positions. */ - static class LineBreakPosition extends LeafPosition { + public static class LineBreakPosition extends LeafPosition { private final int parIndex; // index of the Paragraph this Position refers to private final int startIndex; //index of the first element this Position refers to private final int availableShrink; @@ -610,7 +610,7 @@ private int getEffectiveAlignment(int alignment, int alignmentLast) { /** {@inheritDoc} */ @Override - public List getNextKnuthElements(LayoutContext context, int alignment) { + public List getNextKnuthElements(LayoutContext context, int alignment) { if (alignmentContext == null) { FontInfo fi = fobj.getFOEventHandler().getFontInfo(); FontTriplet[] fontkeys = fobj.getCommonFont().getFontState(fi); @@ -652,7 +652,7 @@ public List getNextKnuthElements(LayoutContext context, int alignment) { * @return the list of KnuthElements * @see LayoutManager#getNextKnuthElements(LayoutContext,int) */ - public List getNextKnuthElements(LayoutContext context, int alignment, + public List getNextKnuthElements(LayoutContext context, int alignment, LeafPosition restartPosition) { int parIndex = 0; int restartPositionIdx = 0; @@ -663,7 +663,9 @@ public List getNextKnuthElements(LayoutContext context, int alignment, } for (int i = 0; i < parIndex; i++) { - knuthParagraphs.remove(0); + if (knuthParagraphs.size() > 1) { + knuthParagraphs.remove(0); + } } parIndex = 0; @@ -709,7 +711,7 @@ private void collectInlineKnuthElements(LayoutContext context) { InlineLevelLayoutManager curLM; while ((curLM = (InlineLevelLayoutManager) getChildLM()) != null) { - List inlineElements = curLM.getNextKnuthElements(inlineLC, effectiveAlignment); + List inlineElements = curLM.getNextKnuthElements(inlineLC, effectiveAlignment); if (inlineElements == null || inlineElements.size() == 0) { /* curLM.getNextKnuthElements() returned null or an empty list; * this can happen if there is nothing more to layout, @@ -718,7 +720,7 @@ private void collectInlineKnuthElements(LayoutContext context) { } if (lastPar != null) { - KnuthSequence firstSeq = (KnuthSequence) inlineElements.get(0); + KnuthSequence firstSeq = inlineElements.get(0); // finish last paragraph before a new block sequence if (!firstSeq.isInlineSequence()) { @@ -936,7 +938,7 @@ private LineLayoutPossibilities findOptimalBreakingPoints(int alignment, Paragra */ private List postProcessLineBreaks(int alignment, LayoutContext context) { - List returnList = new LinkedList(); + List returnList = new LinkedList<>(); int endIndex = -1; for (int p = 0; p < knuthParagraphs.size(); p++) { @@ -1223,14 +1225,14 @@ public void discardSpace(KnuthGlue spaceGlue) { /** {@inheritDoc} */ @Override - public List getChangedKnuthElements(List oldList, int alignment, int depth) { + public List getChangedKnuthElements(List oldList, int alignment, int depth) { return getChangedKnuthElements(oldList, alignment); } /** {@inheritDoc} */ @Override - public List getChangedKnuthElements(List oldList, int alignment) { - List returnList = new LinkedList(); + public List getChangedKnuthElements(List oldList, int alignment) { + List returnList = new LinkedList<>(); for (int p = 0; p < knuthParagraphs.size(); p++) { LineLayoutPossibilities llPoss = lineLayoutsList[p]; //log.debug("demerits of the chosen layout: " + llPoss.getChosenDemerits()); @@ -1284,7 +1286,7 @@ private void findHyphenationPoints(Paragraph currPar) { // hyphenate every word ListIterator currParIterator = currPar.listIterator(currPar.ignoreAtStart); // list of TLM involved in hyphenation - List updateList = new LinkedList(); + List updateList = new LinkedList<>(); KnuthElement firstElement; KnuthElement nextElement; // current InlineLevelLayoutManager @@ -1369,7 +1371,7 @@ private void findHyphenationPoints(Paragraph currPar) { processUpdates(currPar, updateList); } - private void processUpdates(Paragraph par, List updateList) { + private void processUpdates(Paragraph par, List updateList) { // create iterator for the updateList ListIterator updateListIterator = updateList.listIterator(); Update currUpdate; @@ -1397,7 +1399,7 @@ private void processUpdates(Paragraph par, List updateList) { .applyChanges(par.subList(fromIndex + elementsAdded, toIndex + elementsAdded))) { // insert the new KnuthElements - List newElements = currUpdate.inlineLM.getChangedKnuthElements( + List newElements = currUpdate.inlineLM.getChangedKnuthElements( par.subList(fromIndex + elementsAdded, toIndex + elementsAdded), /*flaggedPenalty,*/ effectiveAlignment); @@ -1628,7 +1630,7 @@ private void addBlockArea(LayoutContext context, Position pos, boolean isLastPos * The positionList must contain one area-generating position, * which creates one line area. */ - List positionList = new ArrayList(1); + List positionList = new ArrayList<>(1); Position innerPosition = pos.getPosition(); positionList.add(innerPosition); diff --git a/src/main/java/org/apache/fop/layoutmgr/inline/TextLayoutManager.java b/src/main/java/org/apache/fop/layoutmgr/inline/TextLayoutManager.java index a9b4d5d5..693edf5a 100644 --- a/src/main/java/org/apache/fop/layoutmgr/inline/TextLayoutManager.java +++ b/src/main/java/org/apache/fop/layoutmgr/inline/TextLayoutManager.java @@ -46,6 +46,7 @@ import org.apache.fop.layoutmgr.KnuthSequence; import org.apache.fop.layoutmgr.LayoutContext; import org.apache.fop.layoutmgr.LeafPosition; +import org.apache.fop.layoutmgr.ListElement; import org.apache.fop.layoutmgr.Position; import org.apache.fop.layoutmgr.PositionIterator; import org.apache.fop.layoutmgr.TraitSetter; @@ -116,7 +117,7 @@ private PendingChange(final GlyphMapping mapping, final int index) { private int changeOffset; private int thisStart; private int tempStart; - private List changeList = new LinkedList(); + private List changeList = new LinkedList<>(); private AlignmentContext alignmentContext; @@ -334,6 +335,7 @@ private void addMappingAreas(GlyphMapping mapping, int wordSpaceCount, int lette textArea.setTextLetterSpaceAdjust(letterSpaceDim); textArea.setTextWordSpaceAdjust(wordSpaceDim - spaceCharIPD - 2 * textArea.getTextLetterSpaceAdjust()); + textArea.setFromFootnote(isFromFootnote()); if (context.getIPDAdjust() != 0) { // add information about space width textArea.setSpaceDifference(wordSpaceIPD.getOpt() - spaceCharIPD @@ -762,7 +764,7 @@ private GlyphMapping getGlyphMapping(int index) { } /** {@inheritDoc} */ - public List getNextKnuthElements(final LayoutContext context, final int alignment) { + public List getNextKnuthElements(final LayoutContext context, final int alignment) { lineStartBAP = context.getLineStartBorderAndPaddingWidth(); lineEndBAP = context.getLineEndBorderAndPaddingWidth(); @@ -1004,12 +1006,12 @@ private GlyphMapping processWord(final int alignment, final KnuthSequence sequen } /** {@inheritDoc} */ - public List addALetterSpaceTo(List oldList) { + public List addALetterSpaceTo(List oldList) { return addALetterSpaceTo(oldList, 0); } /** {@inheritDoc} */ - public List addALetterSpaceTo(final List oldList, int depth) { + public List addALetterSpaceTo(final List oldList, int depth) { // old list contains only a box, or the sequence: box penalty glue box; // look at the Position stored in the first element in oldList // which is always a box @@ -1127,12 +1129,12 @@ public void hyphenate(Position pos, HyphContext hyphContext) { } /** {@inheritDoc} */ - public boolean applyChanges(final List oldList) { + public boolean applyChanges(final List oldList) { return applyChanges(oldList, 0); } /** {@inheritDoc} */ - public boolean applyChanges(final List oldList, int depth) { + public boolean applyChanges(final List oldList, int depth) { // make sure the LM appears unfinished in between this call // and the next call to getChangedKnuthElements() @@ -1204,12 +1206,12 @@ public boolean applyChanges(final List oldList, int depth) { } /** {@inheritDoc} */ - public List getChangedKnuthElements(final List oldList, final int alignment) { + public List getChangedKnuthElements(final List oldList, final int alignment) { if (isFinished()) { return null; } - final LinkedList returnList = new LinkedList(); + final LinkedList returnList = new LinkedList<>(); for (; returnedIndices[0] <= returnedIndices[1]; returnedIndices[0]++) { GlyphMapping mapping = getGlyphMapping(returnedIndices[0]); diff --git a/src/main/java/org/apache/fop/pdf/PDFStructElem.java b/src/main/java/org/apache/fop/pdf/PDFStructElem.java index 78950119..e476f39e 100644 --- a/src/main/java/org/apache/fop/pdf/PDFStructElem.java +++ b/src/main/java/org/apache/fop/pdf/PDFStructElem.java @@ -50,6 +50,7 @@ public class PDFStructElem extends StructureHierarchyMember protected List kids; private List attributes; + private PDFObject parent; /** * Creates PDFStructElem with no entries. @@ -71,7 +72,9 @@ public PDFStructElem(PDFObject parent, StructureType structureType) { // Note tag shall have ID entry (see https://github.com/metanorma/mn2pdf/issues/288) put("ID", generateHexID(16)); } - setParent(parent); + if (parent != null) { + put("P", null); + } } private String generateHexID(int length) { @@ -88,6 +91,10 @@ private PDFStructElem(PDFObject parent) { if (parent instanceof PDFStructElem) { parentElement = (PDFStructElem) parent; } + this.parent = parent; + if (parent != null) { + setDocument(parent.getDocument()); + } } /** @@ -115,11 +122,22 @@ public void setParent(PDFObject parent) { @Override public void addKid(PDFObject kid) { if (kids == null) { + assignObjectNumber(); kids = new ArrayList(); } kids.add(kid); } + private void assignObjectNumber() { + if (parentElement != null) { + parentElement.assignObjectNumber(); + } + if (getDocument() != null && !hasObjectNumber()) { + getDocument().assignObjectNumber(this); + } + setParent(parent); + } + /** * Sets the given mcid as the kid of this structure element. This element * will then add itself to its parent structure element if it has not diff --git a/src/main/java/org/apache/fop/render/intermediate/IFParser.java b/src/main/java/org/apache/fop/render/intermediate/IFParser.java index fe0ed916..8b76b87f 100644 --- a/src/main/java/org/apache/fop/render/intermediate/IFParser.java +++ b/src/main/java/org/apache/fop/render/intermediate/IFParser.java @@ -58,13 +58,14 @@ import org.apache.fop.fo.extensions.InternalElementMapping; import org.apache.fop.render.intermediate.extensions.DocumentNavigationExtensionConstants; import org.apache.fop.render.intermediate.extensions.DocumentNavigationHandler; +import org.apache.fop.render.intermediate.extensions.GoToXYAction; import org.apache.fop.traits.BorderProps; import org.apache.fop.traits.RuleStyle; import org.apache.fop.util.ColorUtil; import org.apache.fop.util.ContentHandlerFactory; import org.apache.fop.util.ContentHandlerFactoryRegistry; import org.apache.fop.util.DOMBuilderContentHandlerFactory; -import org.apache.fop.util.DefaultErrorListener; +import org.apache.fop.utils.DefaultErrorListener; import org.apache.fop.util.LanguageTags; import org.apache.fop.util.XMLUtil; @@ -164,6 +165,7 @@ private static class Handler extends DefaultHandler { private Map structureTreeElements = new HashMap(); + private Map unresolvedIds = new HashMap<>(); private class StructureTreeHandler extends DefaultHandler { @@ -308,12 +310,24 @@ public void startElement(String uri, String localName, String qName, Attributes .noStructureTreeInXML(this); } handled = startIFElement(localName, attributes); + + if (EL_ID.equals(localName) && documentHandler.getDocumentNavigationHandler() != null) { + if (this.navParser == null) { + this.navParser = new DocumentNavigationHandler( + documentHandler.getDocumentNavigationHandler(), + structureTreeElements, unresolvedIds); + } + delegate = this.navParser; + delegateDepth++; + delegate.startDocument(); + delegate.startElement(uri, localName, qName, attributes); + } } } else if (DocumentNavigationExtensionConstants.NAMESPACE.equals(uri)) { if (this.navParser == null) { this.navParser = new DocumentNavigationHandler( this.documentHandler.getDocumentNavigationHandler(), - structureTreeElements); + structureTreeElements, unresolvedIds); } delegate = this.navParser; delegateDepth++; @@ -410,6 +424,9 @@ public void endElement(String uri, String localName, String qName) throws SAXExc ElementHandler elementHandler = elementHandlers.get(localName); if (elementHandler != null) { try { + if (elementHandler instanceof DocumentHandler) { + addUnresolvedIds(); + } elementHandler.endElement(); } catch (IFException ife) { handleIFException(ife); @@ -425,6 +442,14 @@ public void endElement(String uri, String localName, String qName) throws SAXExc } } + private void addUnresolvedIds() throws IFException { + for (GoToXYAction action : unresolvedIds.values()) { + if (action != null) { + documentHandler.getDocumentNavigationHandler().addResolvedAction(action); + } + } + } + // ============== Element handlers for the intermediate format ============= private interface ElementHandler { diff --git a/src/main/java/org/apache/fop/render/intermediate/extensions/DocumentNavigationHandler.java b/src/main/java/org/apache/fop/render/intermediate/extensions/DocumentNavigationHandler.java index cedf68e9..9def891f 100644 --- a/src/main/java/org/apache/fop/render/intermediate/extensions/DocumentNavigationHandler.java +++ b/src/main/java/org/apache/fop/render/intermediate/extensions/DocumentNavigationHandler.java @@ -38,6 +38,8 @@ import org.apache.fop.render.intermediate.PageIndexContext; import org.apache.fop.util.XMLUtil; +import static org.apache.fop.render.intermediate.IFConstants.EL_ID; + /** * ContentHandler that handles the IF document navigation namespace. */ @@ -46,9 +48,11 @@ public class DocumentNavigationHandler extends DefaultHandler /** Logger instance */ protected static final Log log = LogFactory.getLog(DocumentNavigationHandler.class); + private static final String NAME = "name"; private StringBuffer content = new StringBuffer(); private Stack objectStack = new Stack(); + private Map unresolvedIds; private IFDocumentNavigationHandler navHandler; @@ -62,16 +66,27 @@ public class DocumentNavigationHandler extends DefaultHandler * @param structureTreeElements the elements representing the structure of the document */ public DocumentNavigationHandler(IFDocumentNavigationHandler navHandler, - Map structureTreeElements) { + Map structureTreeElements, Map unresolvedIds) { this.navHandler = navHandler; assert structureTreeElements != null; this.structureTreeElements = structureTreeElements; + this.unresolvedIds = unresolvedIds; } /** {@inheritDoc} */ public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException { boolean handled = false; + if (EL_ID.equals(localName)) { + String idref = attributes.getValue(NAME); + if (unresolvedIds.containsKey(idref)) { + GoToXYAction action = new GoToXYAction(idref); + action.setPageIndex(navHandler.getPageIndex()); + action.setTargetLocation(new Point(0, 0)); + unresolvedIds.put(idref, action); + } + handled = true; + } if (NAMESPACE.equals(uri)) { if (BOOKMARK_TREE.getLocalName().equals(localName)) { if (!objectStack.isEmpty()) { @@ -124,6 +139,7 @@ public void startElement(String uri, String localName, String qName, Attributes final Point location; if (pageIndex < 0) { location = null; + unresolvedIds.put(id, null); } else { if (hasNavigation() && !inBookmark() && pageIndexRelative >= 0) { int currentPageIndex = navHandler.getPageIndex(); @@ -136,6 +152,7 @@ public void startElement(String uri, String localName, String qName, Attributes final int y = XMLUtil .getAttributeAsInt(attributes, "y"); location = new Point(x, y); + unresolvedIds.remove(id); } action = new GoToXYAction(id, pageIndex, location, new PageIndexRelative(pageIndex, pageIndexRelative)); diff --git a/src/main/java/org/apache/fop/render/pdf/PDFRenderingUtil.java b/src/main/java/org/apache/fop/render/pdf/PDFRenderingUtil.java index 8ef0bbd0..d3542faf 100644 --- a/src/main/java/org/apache/fop/render/pdf/PDFRenderingUtil.java +++ b/src/main/java/org/apache/fop/render/pdf/PDFRenderingUtil.java @@ -74,6 +74,7 @@ import org.apache.fop.pdf.PDFPageLabels; import org.apache.fop.pdf.PDFReference; import org.apache.fop.pdf.PDFSetOCGStateAction; +import org.apache.fop.pdf.PDFSignParams; import org.apache.fop.pdf.PDFTransitionAction; import org.apache.fop.pdf.PDFXMode; import org.apache.fop.pdf.Version; @@ -638,6 +639,10 @@ public PDFDocument setupPDFDocument(OutputStream out) throws IOException { return this.pdfDoc; } + public PDFSignParams getSignParams() { + return rendererConfig.getSignParams(); + } + /** * Generates a page label in the PDF document. * @param pageIndex the index of the page diff --git a/src/main/java/org/apache/fop/svg/font/FOPGVTGlyphVector.java b/src/main/java/org/apache/fop/svg/font/FOPGVTGlyphVector.java index 6866cde2..d96c2b61 100644 --- a/src/main/java/org/apache/fop/svg/font/FOPGVTGlyphVector.java +++ b/src/main/java/org/apache/fop/svg/font/FOPGVTGlyphVector.java @@ -320,6 +320,10 @@ public int[][] getGlyphPositionAdjustments() { return gposAdjustments; } + public List getAssociations() { + return associations; + } + public Point2D getGlyphPosition(int glyphIndex) { int positionIndex = glyphIndex * 2; return new Point2D.Float(positions[positionIndex], positions[positionIndex + 1]);