ASF Bugzilla – Attachment 20041 Details for
Bug 41044
[PATCH] FOP memory usage patches.
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Help
|
New Account
|
Log In
Remember
[x]
|
Forgot Password
Login:
[x]
[patch]
Updated patch against svn head.
rsw_delprops4.patch (text/plain), 86.78 KB, created by
Richard Wheeldon
on 2007-04-25 08:35:29 UTC
(
hide
)
Description:
Updated patch against svn head.
Filename:
MIME Type:
Creator:
Richard Wheeldon
Created:
2007-04-25 08:35:29 UTC
Size:
86.78 KB
patch
obsolete
>Index: fop >=================================================================== >--- fop (revision 532293) >+++ fop (working copy) >@@ -243,7 +243,12 @@ > > # Execute FOP using eval/exec to preserve spaces in paths, > # java options, and FOP args >-fop_exec_command="exec \"$JAVACMD\" $LOGCHOICE $LOGLEVEL -classpath \"$LOCALCLASSPATH\" $FOP_OPTS org.apache.fop.cli.Main $fop_exec_args" >+ >+# Add the following options for extra debug: >+# JMP: -Xrunjmp >+# Hat: -Xrunhprof:file=dump.hprof,format=b >+ >+fop_exec_command="exec \"$JAVACMD\" -Xrunhprof:file=dump.hprof,format=b $LOGCHOICE $LOGLEVEL -classpath \"$LOCALCLASSPATH\" $FOP_OPTS org.apache.fop.cli.Main $fop_exec_args" > if $fop_exec_debug ; then > echo $fop_exec_command > fi >Index: src/java/org/apache/fop/render/txt/TXTFOEventHandlerMaker.java >=================================================================== >--- src/java/org/apache/fop/render/txt/TXTFOEventHandlerMaker.java (revision 532293) >+++ src/java/org/apache/fop/render/txt/TXTFOEventHandlerMaker.java (working copy) >@@ -1,53 +0,0 @@ >-/* >- * Licensed to the Apache Software Foundation (ASF) under one or more >- * contributor license agreements. See the NOTICE file distributed with >- * this work for additional information regarding copyright ownership. >- * The ASF licenses this file to You 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.render.txt; >- >-import java.io.OutputStream; >- >-import org.apache.fop.apps.FOPException; >-import org.apache.fop.apps.FOUserAgent; >-import org.apache.fop.apps.MimeConstants; >-import org.apache.fop.fo.FOEventHandler; >-import org.apache.fop.render.AbstractFOEventHandlerMaker; >- >-/** >- * Maker class for the special FOEventHandler for TXT support. >- */ >-public class TXTFOEventHandlerMaker extends AbstractFOEventHandlerMaker { >- >- private static final String[] MIMES = new String[] { >- MimeConstants.MIME_PLAIN_TEXT}; >- >- /** @see org.apache.fop.render.AbstractFOEventHandlerMaker */ >- public FOEventHandler makeFOEventHandler(FOUserAgent ua, OutputStream out) throws FOPException { >- return new TXTHandler(ua, out); >- } >- >- /** @see org.apache.fop.render.AbstractFOEventHandlerMaker#needsOutputStream() */ >- public boolean needsOutputStream() { >- return true; >- } >- >- /** @see org.apache.fop.render.AbstractFOEventHandlerMaker#getSupportedMimeTypes() */ >- public String[] getSupportedMimeTypes() { >- return MIMES; >- } >- >-} >Index: src/java/org/apache/fop/render/txt/TXTHandler.java >=================================================================== >--- src/java/org/apache/fop/render/txt/TXTHandler.java (revision 532293) >+++ src/java/org/apache/fop/render/txt/TXTHandler.java (working copy) >@@ -1,572 +0,0 @@ >-/* >- * Licensed to the Apache Software Foundation (ASF) under one or more >- * contributor license agreements. See the NOTICE file distributed with >- * this work for additional information regarding copyright ownership. >- * The ASF licenses this file to You 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.render.txt; >- >-import java.io.OutputStream; >-import java.util.Arrays; >-import java.util.Iterator; >-import java.util.List; >- >-import org.apache.fop.apps.FOPException; >-import org.apache.fop.apps.FOUserAgent; >-import org.apache.fop.apps.MimeConstants; >-import org.apache.fop.area.AreaTreeHandler; >-import org.apache.fop.datatypes.CompoundDatatype; >-import org.apache.fop.datatypes.Length; >-import org.apache.fop.datatypes.PercentBaseContext; >-import org.apache.fop.fo.Constants; >-import org.apache.fop.fo.FONode; >-import org.apache.fop.fo.FOText; >-import org.apache.fop.fo.expr.NumericProperty; >-import org.apache.fop.fo.expr.RelativeNumericProperty; >-import org.apache.fop.fo.flow.Block; >-import org.apache.fop.fo.flow.BlockContainer; >-import org.apache.fop.fo.flow.ExternalGraphic; >-import org.apache.fop.fo.flow.Inline; >-import org.apache.fop.fo.flow.ListBlock; >-import org.apache.fop.fo.flow.ListItem; >-import org.apache.fop.fo.flow.PageNumber; >-import org.apache.fop.fo.flow.Table; >-import org.apache.fop.fo.flow.TableCell; >-import org.apache.fop.fo.flow.TableColumn; >-import org.apache.fop.fo.pagination.PageSequence; >-import org.apache.fop.fo.properties.CommonAbsolutePosition; >-import org.apache.fop.fo.properties.CommonBorderPaddingBackground; >-import org.apache.fop.fo.properties.CommonFont; >-import org.apache.fop.fo.properties.CommonMarginBlock; >-import org.apache.fop.fo.properties.FixedLength; >-import org.apache.fop.fo.properties.Property; >-import org.apache.fop.fo.properties.SpaceProperty; >-import org.apache.fop.layoutmgr.BlockLayoutManager; >- >-/** >- * Handler for formatting objects in case of rendering to txt. >- * >- * This handler gets page-sequence, modifies formatting objects and return them >- * to superclass. So areas are generated from modified FO. Idea of modifying is >- * to quantize FO properties, making them divisible by width of char or height >- * of char. >- */ >-public class TXTHandler extends AreaTreeHandler { >- >- /** Percent base context. Needed for line-height. */ >- private static final PercentBaseContext CONTEXT >- = new BlockLayoutManager(new Block(null)); >- >- /** Modified font size in millipoints. */ >- private static final int MODIFIED_FONT_SIZE = 10000; >- >- /** Quantum for each side (BEFORE, AFTER, START, END). */ >- private final int[] quantum = {TXTRenderer.CHAR_HEIGHT, >- TXTRenderer.CHAR_HEIGHT, TXTRenderer.CHAR_WIDTH, >- TXTRenderer.CHAR_WIDTH}; >- >- /** Keeps overpatching for each side. */ >- private int[] overPatching = new int[4]; >- >- /** >- * Keeps last overpatching for each side. Needed for selective modifying of >- * start-indent and end-indent. >- */ >- private int[] lastOverPatching = new int[4]; >- >- /** >- * Constructs a newly allocated <code>TXTHandler</code> object. >- * >- * @param userAgent FOUserAgent >- * @param stream OutputStream >- * @throws FOPException if the RenderPagesModel cannot be created >- */ >- public TXTHandler(FOUserAgent userAgent, OutputStream stream) >- throws FOPException { >- super(userAgent, MimeConstants.MIME_PLAIN_TEXT, stream); >- } >- >- /** >- * Sets a component <code>CP_LENGTH</code> of <code>cd</code> to >- * <code>value</code>. >- >- * @param cd CompoundDatatype >- * @param value new integer value >- */ >- private static void setLength(CompoundDatatype cd, int value) { >- cd.setComponent(Constants.CP_LENGTH, new FixedLength(value), true); >- } >- >- /** >- * Sets components <code>CP_MINIMUM, CP_OPTIMUM, CP_MAXIMUM</code> of >- * <code>cd</code> to <code>p</code>. >- * >- * @param cd instance of CompoundDatatype for modifying. >- * @param p property for setting. >- */ >- private static void setMinOptMax(CompoundDatatype cd, Property p) { >- cd.setComponent(Constants.CP_MINIMUM, p, true); >- cd.setComponent(Constants.CP_OPTIMUM, p, true); >- cd.setComponent(Constants.CP_MAXIMUM, p, true); >- } >- >- /** >- * Modifies border of side. If there is no border of given side, does >- * nothing, otherwise sets border-width to half of char width or char height >- * depending on side. <p> >- * Difference between values of new border-width and old border-width is >- * saved in <code>lastOverPatching</code>. >- * >- * @param side side to modify. >- * @param bpb instance of CommonBorderPaddingBackground for modifying. >- */ >- private void modifyBorder(int side, CommonBorderPaddingBackground bpb) { >- CommonBorderPaddingBackground.BorderInfo bi = bpb.getBorderInfo(side); >- >- if (bi != null) { >- int width = bpb.getBorderWidth(side, false); >- setLength(bi.getWidth(), quantum[side] / 2); >- lastOverPatching[side] += bpb.getBorderWidth(side, false) - width; >- } >- } >- >- /** >- * Modifies padding of side. First rounds padding to nearest integer, >- * divisible by char width or char height depending on side. If border of >- * given side is available, modifies padding in such a way, so sum of border >- * width and padding will be divisible by char width or char height, >- * depending on side. <p> >- * Difference between values of new padding and old padding is saved >- * in <code>lastOverPatching</code>. >- * >- * @param side side to modify. >- * @param bpb instance of CommonBorderPaddingBackground for modifying. >- */ >- private void modifyPadding(int side, CommonBorderPaddingBackground bpb) { >- int oldPadding = bpb.getPadding(side, false, null); >- int newPadding = Helper.round(oldPadding, quantum[side]); >- if (bpb.getBorderInfo(side) != null) { >- newPadding = Math.max(newPadding, quantum[side]) >- - bpb.getBorderWidth(side, false); >- } >- >- setLength(bpb.getPaddingLengthProperty(side), newPadding); >- lastOverPatching[side] += newPadding - oldPadding; >- } >- >- /** >- * Modifies borders and paddings of <code>bpb</code>. >- * >- * @param bpb instance of CommonBorderPaddingBackground for modifying. >- */ >- private void modifyBPB(CommonBorderPaddingBackground bpb) { >- modifyBorder(CommonBorderPaddingBackground.BEFORE, bpb); >- modifyBorder(CommonBorderPaddingBackground.AFTER, bpb); >- modifyBorder(CommonBorderPaddingBackground.START, bpb); >- modifyBorder(CommonBorderPaddingBackground.END, bpb); >- >- modifyPadding(CommonBorderPaddingBackground.BEFORE, bpb); >- modifyPadding(CommonBorderPaddingBackground.AFTER, bpb); >- modifyPadding(CommonBorderPaddingBackground.START, bpb); >- modifyPadding(CommonBorderPaddingBackground.END, bpb); >- } >- >- /** >- * Rounds optimum value of <code>space</code> to nearest integer, >- * divisible by <code>q</code>. >- * >- * @param space instance of SpaceProperty. >- * @param q integer. >- */ >- private void modifySpace(SpaceProperty space, int q) { >- int value = space.getOptimum(null).getLength().getValue(); >- setMinOptMax(space, new FixedLength(Helper.round(value, q))); >- } >- >- /** >- * @param length instance of Length. >- * @param q integer. >- * @return instance of Length, having value nearest to value of >- * <code>length</code>, and divisible by <code>q</code>. >- */ >- private Length roundLength(Length length, int q) { >- int x = Helper.round(length.getValue(), q); >- return new FixedLength(x); >- } >- >- /** >- * @param length instance of Length. >- * @param q integer. >- * @return instance of Length, having minimal value, greater value of >- * <code>length</code>, and divisible by <code>q</code>. >- */ >- private Length ceilLength(Length length, int q) { >- int x = Helper.ceil(length.getValue(), q); >- return new FixedLength(x); >- } >- >- /** >- * Modifies indent for given side. Summarizes value of indent and modifing >- * error (i.e. overPatching). Rounds result to nearest integer, divisible by >- * quantum. >- * >- * @param indent Length to modify. >- * @param side an integer, representing side. >- * @return modified Length. >- */ >- private Length modifyIndent(Length indent, int side) { >- if (indent instanceof NumericProperty) { >- overPatching[side] += lastOverPatching[side]; >- } >- int newValue = indent.getValue() + overPatching[side]; >- newValue = Helper.round(newValue, quantum[side]); >- return new FixedLength(newValue); >- } >- >- /** >- * Modifies Common Margin Properties-Block: >- * <ul> >- * <li>margin-top, margin-left, margin-bottom, margin-right >- * <li>start-indent, end-indent >- * <li>space-before, space-after. >- * </ul> >- * >- * @param cmb instance of CommonMarginBlock to modify. >- */ >- private void modifyCommonMarginBlock(CommonMarginBlock cmb) { >- cmb.marginTop = roundLength(cmb.marginTop, TXTRenderer.CHAR_HEIGHT); >- cmb.marginBottom = roundLength(cmb.marginBottom, >- TXTRenderer.CHAR_HEIGHT); >- cmb.marginLeft = roundLength(cmb.marginLeft, TXTRenderer.CHAR_WIDTH); >- cmb.marginRight = roundLength(cmb.marginRight, TXTRenderer.CHAR_WIDTH); >- >- modifySpace(cmb.spaceBefore, TXTRenderer.CHAR_HEIGHT); >- modifySpace(cmb.spaceAfter, TXTRenderer.CHAR_HEIGHT); >- >- if (!(cmb.startIndent instanceof RelativeNumericProperty)) { >- cmb.startIndent = modifyIndent(cmb.startIndent, >- CommonBorderPaddingBackground.START); >- } >- if (!(cmb.endIndent instanceof RelativeNumericProperty)) { >- cmb.endIndent = modifyIndent(cmb.endIndent, >- CommonBorderPaddingBackground.END); >- } >- } >- >- /** >- * Modifies fo:table attributes: >- * <ul> >- * <li>Common Margin Properties Block >- * <li>Common Border, Padding, and Background Properties >- * <li>columns. >- * </ul> >- * >- * @param table Table to modify. >- */ >- private void modifyTable(Table table) { >- CommonMarginBlock cmb = table.getCommonMarginBlock(); >- if (table.getBorderCollapse() == Constants.EN_COLLAPSE) { >- // If border-collapse == "collapse", add space-after in order to >- // impove interaction with other FO. >- int value = cmb.spaceAfter.getOptimum(null).getLength().getValue(); >- value += TXTRenderer.CHAR_HEIGHT; >- setMinOptMax(cmb.spaceAfter, new FixedLength(value)); >- } >- modifyCommonMarginBlock(cmb); >- >- modifyBPB(table.getCommonBorderPaddingBackground()); >- >- // modify all table-columns >- List columnList = table.getColumns(); >- Iterator iter = columnList.iterator(); >- while (iter.hasNext()) { >- modifyTableColumn((TableColumn) iter.next()); >- } >- } >- >- /** >- * Modifies fo:table-column attributes: >- * <ul> >- * <li>width. >- * </ul> >- * >- * @param column TableColumn to modify. >- */ >- private void modifyTableColumn(TableColumn column) { >- column.setColumnWidth(ceilLength(column.getColumnWidth(), >- TXTRenderer.CHAR_WIDTH)); >- } >- >- /** >- * Modifies padding of fo:table-cell. >- * >- * @param side side. >- * @param bpb instance of CommonBorderPaddingBackground to modify. >- */ >- private void modifyCellPadding(int side, CommonBorderPaddingBackground bpb) { >- if (bpb.getBorderInfo(side) == null) { >- int oldPadding = bpb.getPadding(side, false, null); >- int newPadding = oldPadding + quantum[side] / 2; >- setLength(bpb.getPaddingLengthProperty(side), newPadding); >- } >- } >- >- /** >- * Modifies table-cell properties: >- * <ul> >- * <li>Common Border, Padding, and Background Properties. >- * </ul> >- * >- * @param c TableCell to modify. >- */ >- private void modifyTableCell(TableCell c) { >- CommonBorderPaddingBackground bpb = c >- .getCommonBorderPaddingBackground(); >- modifyBPB(bpb); >- modifyCellPadding(CommonBorderPaddingBackground.BEFORE, bpb); >- modifyCellPadding(CommonBorderPaddingBackground.AFTER, bpb); >- modifyCellPadding(CommonBorderPaddingBackground.START, bpb); >- modifyCellPadding(CommonBorderPaddingBackground.END, bpb); >- } >- >- /** >- * Modifies Common Absolute Position Properties: >- * <ul> >- * <li>left >- * <li>top. >- * </ul> >- * >- * @param cap CommonAbsolutePosition to modify. >- */ >- private void modifyCommonAbsolutePosition(CommonAbsolutePosition cap) { >- if (cap.absolutePosition == Constants.EN_ABSOLUTE) { >- cap.left = roundLength(cap.left, TXTRenderer.CHAR_WIDTH); >- cap.top = roundLength(cap.top, TXTRenderer.CHAR_HEIGHT); >- } >- } >- >- /** >- * Modifies line-height property. Sets a value of line-height to max(char >- * height; lowest integer, divisible by char height). >- * >- * @param lineHeight SpaceProperty to modify. >- */ >- private void modifyLineHeight(SpaceProperty lineHeight) { >- Property p = lineHeight.getOptimum(null); >- int value = p.getLength().getValue(CONTEXT); >- >- int height = TXTRenderer.CHAR_HEIGHT; >- int newValue = Math.max(Helper.floor(value, height), height); >- setMinOptMax(lineHeight, new FixedLength(newValue)); >- } >- >- /** >- * Modifies Common Font Properties: >- * <ul> >- * <li>font-family = Courier; >- * <li>font-size = MODIFIED_FONT_SIZE; >- * <li>font-stretch = EN_NORMAL; >- * <li>font-weight = EN_NORMAL. >- * </ul> >- * >- * @param cf the font to modify. >- */ >- private void modifyCommonFont(CommonFont cf) { >- if (cf != null) { >- cf.overrideFontFamily("Courier"); >- cf.fontSize = new FixedLength(MODIFIED_FONT_SIZE); >- cf.fontStretch = Constants.EN_NORMAL; >- cf.fontWeight = Constants.EN_NORMAL; >- } >- } >- >- /** >- * Modifies fo:block: >- * <ul> >- * <li>Common Border, Padding, and Background Properties >- * <li>Common Margin Properties-Block >- * <li>Common Font Properties >- * <li>line-height. >- * </ul> >- * >- * @param block Block to modify. >- */ >- private void modifyBlock(Block block) { >- modifyBPB(block.getCommonBorderPaddingBackground()); >- modifyCommonMarginBlock(block.getCommonMarginBlock()); >- modifyCommonFont(block.getCommonFont()); >- modifyLineHeight(block.getLineHeight()); >- } >- >- /** >- * Modifies fo:block-container: >- * <ul> >- * <li>Common Border, Padding, and Background Properties >- * <li>Common Margin Properties-Block >- * <li>Common Absolute Position Properties. >- * </ul> >- * >- * @param bc BlockContainer to modify. >- */ >- private void modifyBlockContainer(BlockContainer bc) { >- modifyBPB(bc.getCommonBorderPaddingBackground()); >- modifyCommonMarginBlock(bc.getCommonMarginBlock()); >- modifyCommonAbsolutePosition(bc.getCommonAbsolutePosition()); >- } >- >- /** >- * Modifies fo:inline: >- * <ul> >- * <li>Common Font Properties >- * </ul> >- * >- * @param inline Inline to modify. >- */ >- private void modifyInline(Inline inline) { >- modifyCommonFont(inline.getCommonFont()); >- } >- >- /** >- * Modifies FOText: >- * <ul> >- * <li>Common Font Properties >- * </ul> >- * >- * @param text FOText to modify. >- */ >- private void modifyFOText(FOText text) { >- modifyCommonFont(text.getCommonFont()); >- } >- >- /** >- * Modifies fo:external-graphic: >- * <ul> >- * <li>Common Border, Padding, and Background Properties >- * <li>line-height. >- * </ul> >- * >- * @param eg ExternalGraphic to modify. >- */ >- private void modifyExternalGraphic(ExternalGraphic eg) { >- modifyBPB(eg.getCommonBorderPaddingBackground()); >- modifyLineHeight(eg.getLineHeight()); >- } >- >- /** >- * Modifies fo:list-block: >- * <ul> >- * <li>Common Border, Padding, and Background Properties >- * <li>Common Margin Properties-Block. >- * </ul> >- * >- * @param lb ListBlock to modify. >- */ >- private void modifyListBlock(ListBlock lb) { >- modifyBPB(lb.getCommonBorderPaddingBackground()); >- modifyCommonMarginBlock(lb.getCommonMarginBlock()); >- } >- >- /** >- * Modifies fo:list-item: >- * <ul> >- * <li>Common Border, Padding, and Background Properties >- * <li>Common Margin Properties-Block. >- * </ul> >- * <p> >- * Make refinement for fo:list-item-label and fo:list-item-body. >- * >- * @param li ListItem to modify. >- */ >- private void modifyListItem(ListItem li) { >- modifyBPB(li.getCommonBorderPaddingBackground()); >- modifyCommonMarginBlock(li.getCommonMarginBlock()); >- refinement(li.getLabel()); >- refinement(li.getBody()); >- } >- >- /** >- * Does refinement for particular node. Modifies node's properties and >- * refines its children recursively. >- * >- * @param node the node to refine. >- */ >- private void refinement(FONode node) { >- int[] saveOverPatching = (int[]) overPatching.clone(); >- Arrays.fill(lastOverPatching, 0); >- >- if (node instanceof Block) { >- modifyBlock((Block) node); >- } else if (node instanceof BlockContainer) { >- modifyBlockContainer((BlockContainer) node); >- } else if (node instanceof Inline) { >- modifyInline((Inline) node); >- } else if (node instanceof FOText) { >- modifyFOText((FOText) node); >- } else if (node instanceof Table) { >- modifyTable((Table) node); >- Arrays.fill(overPatching, 0); >- } else if (node instanceof TableCell) { >- modifyTableCell((TableCell) node); >- } else if (node instanceof ExternalGraphic) { >- modifyExternalGraphic((ExternalGraphic) node); >- } else if (node instanceof ListBlock) { >- modifyListBlock((ListBlock) node); >- } else if (node instanceof ListItem) { >- modifyListItem((ListItem) node); >- } else if (node instanceof PageNumber) { >- modifyCommonFont(((PageNumber) node).getCommonFont()); >- } >- >- Iterator it = node.getChildNodes(); >- if (it != null) { >- while (it.hasNext()) { >- refinement((FONode) it.next()); >- } >- } >- overPatching = saveOverPatching; >- } >- >- /** >- * Run refinement for: >- * <ul> >- * <li>mainflow (xsl-region-body) >- * <li>staticflow (xsl-region-before, xsl-region-after, xsl-region-start, >- * xsl-region-end). >- * </ul> >- * >- * @param pageSequence PageSequence to refine. >- */ >- public void endPageSequence(PageSequence pageSequence) { >- Arrays.fill(overPatching, 0); >- >- refinement(pageSequence.getMainFlow()); >- >- if (pageSequence.getStaticContent("xsl-region-before") != null) { >- refinement(pageSequence.getStaticContent("xsl-region-before")); >- } >- if (pageSequence.getStaticContent("xsl-region-after") != null) { >- refinement(pageSequence.getStaticContent("xsl-region-after")); >- } >- if (pageSequence.getStaticContent("xsl-region-start") != null) { >- refinement(pageSequence.getStaticContent("xsl-region-start")); >- } >- if (pageSequence.getStaticContent("xsl-region-end") != null) { >- refinement(pageSequence.getStaticContent("xsl-region-end")); >- } >- >- super.endPageSequence(pageSequence); >- } >-} >Index: src/java/org/apache/fop/layoutmgr/table/GridUnit.java >=================================================================== >--- src/java/org/apache/fop/layoutmgr/table/GridUnit.java (revision 532293) >+++ src/java/org/apache/fop/layoutmgr/table/GridUnit.java (working copy) >@@ -281,14 +281,8 @@ > public void resolveBorder(GridUnit other, int side, int resFlags) { > CollapsingBorderModel borderModel = CollapsingBorderModel.getBorderModelFor( > getTable().getBorderCollapse()); >- if (effectiveBorders == null) { >- effectiveBorders = new CommonBorderPaddingBackground(); >- } >- effectiveBorders.setBorderInfo(borderModel.determineWinner(this, other, >- side, resFlags), side); >- if (cell != null) { >- effectiveBorders.setPadding(cell.getCommonBorderPaddingBackground()); >- } >+ BorderInfo bi = borderModel.determineWinner(this, other, side, resFlags); >+ effectiveBorders = CommonBorderPaddingBackground.getInstance(effectiveBorders, cell, bi, side); > if (log.isDebugEnabled()) { > log.debug(this + " resolved borders: " > + "before=" + effectiveBorders.getBorderBeforeWidth(false) + ", " >Index: src/java/org/apache/fop/datatypes/CompoundDatatype.java >=================================================================== >--- src/java/org/apache/fop/datatypes/CompoundDatatype.java (revision 532293) >+++ src/java/org/apache/fop/datatypes/CompoundDatatype.java (working copy) >@@ -39,6 +39,7 @@ > * Returns a component of the compound datatype. > * @param cmpId ID of the component > * @return the value of the component >+ * @deprecated Fop is moving towards a system of immutable properties. > */ > Property getComponent(int cmpId); > } >Index: src/java/org/apache/fop/datatypes/LengthBase.java >=================================================================== >--- src/java/org/apache/fop/datatypes/LengthBase.java (revision 532293) >+++ src/java/org/apache/fop/datatypes/LengthBase.java (working copy) >@@ -28,7 +28,7 @@ > import org.apache.fop.fo.flow.Character; > import org.apache.fop.fo.flow.ExternalGraphic; > import org.apache.fop.fo.flow.InstreamForeignObject; >-import org.apache.fop.layoutmgr.inline.LeafNodeLayoutManager; >+import org.apache.fop.fo.properties.Property; > > /** > * Models a length which can be used as a factor in a percentage length >@@ -71,15 +71,15 @@ > /** > * The FO for which this property is to be calculated. > */ >- protected /* final */ FObj fobj; >+ private final FObj fobj; > > /** > * One of the defined types of LengthBase > */ >- private /* final */ int baseType; >+ private final int baseType; > > /** For percentages based on other length properties */ >- private Length baseLength; >+ private final Length baseLength; > > /** > * Constructor >@@ -101,6 +101,13 @@ > default: > // TODO: pacify CheckStyle > // throw new RuntimeException(); >+ /** >+ This is the behaviour of the old code - probably not the desired >+ behaviour. Throwing IllegalArgumentException causes all sorts of >+ problems, including failure to process simple fos such as readme.fo >+ Not initializing anything gives null - RSW >+ */ >+ baseLength = null; > break; > } > } >@@ -134,6 +141,19 @@ > } > return baseLen; > } >+ >+ public int hashCode() { >+ return baseType + (baseLength==null ? 29 : baseLength.hashCode()) << 4; >+ } >+ >+ public boolean equals(Object obj) { >+ if (! (obj instanceof LengthBase)) >+ return false; >+ LengthBase lb = (LengthBase)obj; >+ return lb.baseType == this.baseType && >+ Property.eq(lb.baseLength, this.baseLength); >+ } > >+ > } > >Index: src/java/org/apache/fop/apps/FOUserAgent.java >=================================================================== >--- src/java/org/apache/fop/apps/FOUserAgent.java (revision 532293) >+++ src/java/org/apache/fop/apps/FOUserAgent.java (working copy) >@@ -80,6 +80,7 @@ > private File outputFile = null; > private Renderer rendererOverride = null; > private FOEventHandler foEventHandlerOverride = null; >+ private boolean locatorEnabled = false; // TODO: Should be true by default (for error messages). > > /** Producer: Metadata element for the system/software that produces > * the document. (Some renderers can store this in the document.) >@@ -501,5 +502,24 @@ > public XMLHandlerRegistry getXMLHandlerRegistry() { > return getFactory().getXMLHandlerRegistry(); > } >+ /** >+ * Enables use of SAXLocators to provide location information in error >+ * messages. Since this a somewhat expensive feature in terms of memory >+ * usage, many end user may which to disable it. >+ * @return true if context information should be stored on each node in the FO tree. >+ */ >+ public void setLocatorEnabled(boolean en) { >+ locatorEnabled = en; >+ } >+ >+ /** >+ * Are SAXLocators enabled? >+ * @see #setLocatorEnabled(boolean) >+ * @return true if context information should be stored on each node in the FO tree. >+ */ >+ public boolean isLocatorEnabled() { >+ return locatorEnabled; >+ } >+ > } > >Index: src/java/org/apache/fop/fo/properties/CommonHyphenation.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/CommonHyphenation.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/CommonHyphenation.java (working copy) >@@ -29,46 +29,49 @@ > * Public "structure" allows direct member access. > */ > public class CommonHyphenation { >+ >+ private static final PropertyCache cache = new PropertyCache(); >+ > /** > * The "language" property. > */ >- public String language; >+ public final String language; > > /** > * The "country" property. > */ >- public String country; >+ public final String country; > > /** > * The "script" property. > */ >- public String script; >+ public final String script; > > /** > * The "hyphenate" property. > */ >- public int hyphenate; >+ public final int hyphenate; > > /** > * The "hyphenation-character" property. > */ >- public char hyphenationCharacter; >+ public final char hyphenationCharacter; > > /** > * The "hyphenation-push-character" property. > */ >- public int hyphenationPushCharacterCount; >+ public final int hyphenationPushCharacterCount; > > /** > * The "hyphenation-remain-character-count" property. > */ >- public int hyphenationRemainCharacterCount; >+ public final int hyphenationRemainCharacterCount; > > /** > * Create a CommonHyphenation object. >- * @param pList The PropertyList with propery values. >+ * @param pList The PropertyList with property values. > */ >- public CommonHyphenation(PropertyList pList) throws PropertyException { >+ private CommonHyphenation(PropertyList pList) throws PropertyException { > language = pList.get(Constants.PR_LANGUAGE).getString(); > country = pList.get(Constants.PR_COUNTRY).getString(); > script = pList.get(Constants.PR_SCRIPT).getString(); >@@ -81,4 +84,26 @@ > > } > >+ public int hashCode() { >+ return Property.hc(language) << 1 + >+ Property.hc(country) << 4 + >+ Property.hc(script) << 9 + >+ hyphenate; >+ } >+ >+ public boolean equals(Object obj) { >+ CommonHyphenation c = (CommonHyphenation)obj; >+ return Property.eq(language, language) && >+ Property.eq(country, country) && >+ Property.eq(script, script) && >+ hyphenate == c.hyphenate && >+ hyphenationCharacter == c.hyphenationCharacter && >+ hyphenationPushCharacterCount == c.hyphenationPushCharacterCount && >+ hyphenationRemainCharacterCount == c.hyphenationRemainCharacterCount; >+ } >+ >+ public static CommonHyphenation getInstance(PropertyList pList) throws PropertyException { >+ CommonHyphenation c = new CommonHyphenation(pList); >+ return (CommonHyphenation)cache.fetch(c); >+ } > } >Index: src/java/org/apache/fop/fo/properties/CommonAccessibility.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/CommonAccessibility.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/CommonAccessibility.java (working copy) >@@ -28,32 +28,44 @@ > * See Sec 7.4 of the XSL-FO Standard. > * Public "structure" allows direct member access. > */ >-public class CommonAccessibility { >+public final class CommonAccessibility { >+ >+ private static final PropertyCache cache = new PropertyCache(); >+ > /** > * The "source-doc" property. > */ >- public String sourceDoc = null; >+ public final String sourceDoc; > > /** > * The "role" property. > */ >- public String role = null; >+ public final String role; > > /** > * Create a CommonAbsolutePosition object. > * @param pList The PropertyList with propery values. > */ >- public CommonAccessibility(PropertyList pList) throws PropertyException { >- sourceDoc = pList.get(Constants.PR_SOURCE_DOCUMENT).getString(); >- if ("none".equals(sourceDoc)) { >- sourceDoc = null; >- } >- role = pList.get(Constants.PR_ROLE).getString(); >- if ("none".equals(role)) { >- role = null; >- } >- >+ private CommonAccessibility(PropertyList pList) throws PropertyException { >+ String s = pList.get(Constants.PR_SOURCE_DOCUMENT).getString(); >+ sourceDoc = ("none".equals(s)) ? null : s; >+ String r = pList.get(Constants.PR_ROLE).getString(); >+ role = ("none".equals(r)) ? null : r; > } > >+ public int hashCode() { >+ return sourceDoc == null ? 0 : sourceDoc.hashCode() + >+ role == null ? 0 : role.hashCode() << 1; >+ } > >+ public boolean equals(Object obj) { >+ CommonAccessibility ca = (CommonAccessibility)obj; >+ return Property.eq(ca.sourceDoc, this.sourceDoc) && >+ Property.eq(ca.role, this.role); >+ } >+ >+ public static CommonAccessibility getInstance(PropertyList pList) throws PropertyException { >+ CommonAccessibility ca = new CommonAccessibility(pList); >+ return (CommonAccessibility)cache.fetch(ca); >+ } > } >Index: src/java/org/apache/fop/fo/properties/BorderWidthPropertyMaker.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/BorderWidthPropertyMaker.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/BorderWidthPropertyMaker.java (working copy) >@@ -63,7 +63,7 @@ > // Calculate the values as described in 7.7.20. > Property style = propertyList.get(borderStyleId); > if (style.getEnum() == Constants.EN_NONE) { >- return new FixedLength(0); >+ return FixedLength.getInstance(0); > } > return p; > } >Index: src/java/org/apache/fop/fo/properties/LengthRangeProperty.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/LengthRangeProperty.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/LengthRangeProperty.java (working copy) >@@ -84,7 +84,7 @@ > log.warn(FObj.decorateWithContextInfo( > "Replaced negative value (" + len + ") for " + getName() > + " with 0mpt", fo)); >- p = new FixedLength(0); >+ p = FixedLength.getInstance(0); > } > } > } >@@ -106,8 +106,7 @@ > if (isNegativeLength(len)) { > log.warn("Replaced negative value (" + len + ") for " + getName() > + " with 0mpt"); >- val.setComponent(subpropertyId, >- new FixedLength(0), false); >+ val.setComponent(subpropertyId, FixedLength.getInstance(0), false); > return baseProperty; > } > } >@@ -136,6 +135,7 @@ > > /** > * @see org.apache.fop.datatypes.CompoundDatatype#getComponent(int) >+ * @deprecated LengthRangeProperty should be immutable > */ > public Property getComponent(int cmpId) { > if (cmpId == CP_MINIMUM) { >@@ -155,6 +155,7 @@ > * LengthRange. > * @param bIsDefault If true, this is set as a "default" value > * and not a user-specified explicit value. >+ * @deprecated LengthRangeProperty should be immutable > */ > protected void setMinimum(Property minimum, boolean bIsDefault) { > this.minimum = minimum; >@@ -170,6 +171,7 @@ > * @param max A Length value specifying the maximum value for this > * @param bIsDefault If true, this is set as a "default" value > * and not a user-specified explicit value. >+ * @deprecated LengthRangeProperty should be immutable > */ > protected void setMaximum(Property max, boolean bIsDefault) { > maximum = max; >@@ -185,6 +187,7 @@ > * @param opt A Length value specifying the optimum value for this > * @param bIsDefault If true, this is set as a "default" value > * and not a user-specified explicit value. >+ * @deprecated LengthRangeProperty should be immutable > */ > protected void setOptimum(Property opt, boolean bIsDefault) { > optimum = opt; >@@ -298,5 +301,21 @@ > public Object getObject() { > return this; > } >- >+ >+ public int hashCode() { >+ return bfSet + minimum.hashCode() << 4 + >+ optimum.hashCode() << 8 + maximum.hashCode() << 12; >+ } >+ >+ public boolean equals(Object obj) { >+ if (! (obj instanceof LengthRangeProperty)) >+ return false; >+ LengthRangeProperty lrp = (LengthRangeProperty)obj; >+ return this.bfSet == lrp.bfSet && >+ this.consistent == lrp.consistent && >+ Property.eq(this.minimum, lrp.minimum) && >+ Property.eq(this.optimum, lrp.optimum) && >+ Property.eq(this.maximum, lrp.maximum); >+ } >+ > } >Index: src/java/org/apache/fop/fo/properties/EnumProperty.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/EnumProperty.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/EnumProperty.java (working copy) >@@ -65,7 +65,7 @@ > } > } > >- private static final Map propertyCache = new WeakHashMap(); >+ private static final PropertyCache cache = new PropertyCache(); > > private final int value; > private final String text; >@@ -80,14 +80,7 @@ > } > > public static EnumProperty getInstance(int explicitValue, String text) { >- EnumProperty ep = new EnumProperty(explicitValue, text); >- EnumProperty cacheEntry = (EnumProperty)propertyCache.get(ep); >- if (cacheEntry == null) { >- propertyCache.put(ep, ep); >- return ep; >- } else { >- return cacheEntry; >- } >+ return (EnumProperty)cache.fetch(new EnumProperty(explicitValue, text)); > } > > /** >@@ -110,10 +103,8 @@ > public boolean equals(Object obj) { > if (obj instanceof EnumProperty) { > EnumProperty ep = (EnumProperty)obj; >- return (ep.value == this.value) >- && ((ep.text == this.text) >- || (ep.text != null >- && ep.text.equals(this.text))); >+ return this.value == ep.value && >+ Property.eq(this.text, ep.text); > } else { > return false; > } >Index: src/java/org/apache/fop/fo/properties/CommonAbsolutePosition.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/CommonAbsolutePosition.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/CommonAbsolutePosition.java (working copy) >@@ -30,30 +30,33 @@ > * Public "structure" allows direct member access. > */ > public class CommonAbsolutePosition { >+ >+ private static final PropertyCache cache = new PropertyCache(); >+ > /** > * The "absolute-position" property. > */ >- public int absolutePosition; >+ public final int absolutePosition; > > /** > * The "top" property. > */ >- public Length top; >+ public final Length top; > > /** > * The "right" property. > */ >- public Length right; >+ public final Length right; > > /** > * The "bottom" property. > */ >- public Length bottom; >+ public final Length bottom; > > /** > * The "left" property. > */ >- public Length left; >+ public final Length left; > > /** > * Create a CommonAbsolutePosition object. >@@ -82,4 +85,27 @@ > sb.append("}"); > return sb.toString(); > } >+ >+ public int hashCode() { >+ return absolutePosition + >+ Property.hc(top) << 2 + >+ Property.hc(right) << 4 + >+ Property.hc(bottom) << 6 + >+ Property.hc(left) << 8; >+ } >+ >+ public boolean equals(Object obj) { >+ CommonAbsolutePosition cap = (CommonAbsolutePosition)obj; >+ return cap.absolutePosition == absolutePosition && >+ Property.eq(cap.top, top) && >+ Property.eq(cap.right, right) && >+ Property.eq(cap.bottom, bottom) && >+ Property.eq(cap.left, left); >+ } >+ >+ public static CommonAbsolutePosition getInstance(PropertyList pList) throws PropertyException { >+ CommonAbsolutePosition cap = new CommonAbsolutePosition(pList); >+ return (CommonAbsolutePosition)cache.fetch(cap); >+ } >+ > } >Index: src/java/org/apache/fop/fo/properties/EnumNumber.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/EnumNumber.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/EnumNumber.java (working copy) >@@ -27,7 +27,7 @@ > */ > public class EnumNumber extends NumberProperty { > >- private static final Map cache = new WeakHashMap(); >+ private static final PropertyCache cache = new PropertyCache(); > > private final EnumProperty enumProperty; > >@@ -37,12 +37,8 @@ > } > > public static EnumNumber getInstance(Property enumProperty) { >- EnumNumber en = (EnumNumber)cache.get(enumProperty); >- if (en == null) { >- en = new EnumNumber((EnumProperty)enumProperty); >- cache.put(enumProperty, en); >- } >- return en; >+ EnumNumber en = new EnumNumber((EnumProperty)enumProperty); >+ return (EnumNumber)cache.fetch(en); > } > > public int getEnum() { >@@ -81,5 +77,19 @@ > return enumProperty.getObject(); > } > >+ /** >+ * @see java.lang.Object#equals(Object) >+ */ >+ public boolean equals(Object obj) { >+ if (obj instanceof EnumNumber) { >+ EnumNumber ep = (EnumNumber)obj; >+ return Property.eq(this.enumProperty, ep.enumProperty); >+ } else { >+ return false; >+ } >+ } > >+ public int hashCode() { >+ return enumProperty.hashCode(); >+ } > } >Index: src/java/org/apache/fop/fo/properties/Property.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/Property.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/Property.java (working copy) >@@ -199,4 +199,31 @@ > } > return null; > } >+ >+ /** >+ Utility method which returns true iff obj1.equals(obj2) >+ or obj1 and obj2 are both null. Performs a deep equality >+ comparison if obj1 and obj2 are both arrays. >+ */ >+ public static final boolean eq(Object obj1, Object obj2) { >+ if (obj1 instanceof Object[]) { >+ if (obj1==null && obj2==null) return true; >+ if (obj1==null || obj2==null) return false; >+ if (! (obj1 instanceof Object[])) return false; >+ Object[] arr1 = (Object[])obj1; >+ Object[] arr2 = (Object[])obj2; >+ if (arr1.length != arr2.length) return false; >+ for (int i = 0; i < arr1.length; i++) >+ if (!eq(arr1[i], arr2[i])) >+ return false; >+ return true; >+ } else { >+ return (obj1 == obj2) || >+ (obj1 != null && obj2 != null && obj1.equals(obj2)); >+ } >+ } >+ >+ static final int hc(Object obj) { >+ return obj == null ? 0 : obj.hashCode(); >+ } > } >Index: src/java/org/apache/fop/fo/properties/CondLengthProperty.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/CondLengthProperty.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/CondLengthProperty.java (working copy) >@@ -162,4 +162,14 @@ > return this; > } > >+ public int hashCode() { >+ return length.hashCode() + conditionality.hashCode(); >+ } >+ >+ public boolean equals(Object obj) { >+ if (! (obj instanceof CondLengthProperty)) return false; >+ CondLengthProperty c = (CondLengthProperty)obj; >+ return Property.eq(length, c.length) && >+ Property.eq(conditionality, c.conditionality); >+ } > } >Index: src/java/org/apache/fop/fo/properties/NumberProperty.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/NumberProperty.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/NumberProperty.java (working copy) >@@ -69,7 +69,7 @@ > > } > >- private Number number; >+ private final Number number; > > /** > * Constructor for Number input >@@ -172,7 +172,7 @@ > /** @see org.apache.fop.fo.properties.Property#getLength() */ > public Length getLength() { > //Assume pixels (like in HTML) when there's no unit >- return new FixedLength(getNumericValue(), "px"); >+ return FixedLength.getInstance(getNumericValue(), "px"); > } > > /** >@@ -187,4 +187,14 @@ > return Color.black; > } > >+ public int hashCode() { >+ return number.hashCode(); >+ } >+ >+ public boolean equals(Object obj) { >+ if (! (obj instanceof NumberProperty)) >+ return false; >+ NumberProperty n = (NumberProperty)obj; >+ return Property.eq(number, n.number); >+ } > } >Index: src/java/org/apache/fop/fo/properties/SpaceProperty.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/SpaceProperty.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/SpaceProperty.java (working copy) >@@ -167,4 +167,13 @@ > return this; > } > >+ public boolean equals(Object obj) { >+ if (! (obj instanceof SpaceProperty)) >+ return false; >+ SpaceProperty c = (SpaceProperty)obj; >+ return super.equals(obj) && >+ Property.eq(precedence, c.precedence) && >+ Property.eq(conditionality, c.conditionality); >+ } >+ > } >Index: src/java/org/apache/fop/fo/properties/FixedLength.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/FixedLength.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/FixedLength.java (working copy) >@@ -25,31 +25,45 @@ > * An absolute length quantity in XSL > */ > public class FixedLength extends LengthProperty { >+ >+ private static final PropertyCache cache = new PropertyCache(); >+ > private int millipoints; > >+ private FixedLength(int millis) { >+ millipoints = millis; >+ } >+ > /** >- * Set the length given >+ * Obtain an instance given a number of units and a font size. > * @param numRelUnits the number of relative units > * @param iCurFontSize the current font size in base units. >+ * @return A new or previously cached instance of FixedLength > */ >- public FixedLength(double numRelUnits, int iCurFontSize) { >- millipoints = (int) (numRelUnits * (double)iCurFontSize); >+ public static FixedLength getInstance(double numRelUnits, int iCurFontSize) { >+ FixedLength fl = new FixedLength((int) (numRelUnits * (double)iCurFontSize)); >+ return (FixedLength)cache.fetch(fl); > } > > /** >- * Set the length given a number of units and a unit name. >+ * Obtain an instance given a number of units and a unit name. > * @param numUnits quantity of input units > * @param units input unit specifier (in, cm, etc.) >+ * @return A new or previously cached instance of FixedLength > */ >- public FixedLength(double numUnits, String units) { >- convert(numUnits, units); >+ public static FixedLength getInstance(double numUnits, String units) { >+ FixedLength fl = new FixedLength(convert(numUnits, units)); >+ return (FixedLength)cache.fetch(fl); > } > > /** >+ * Obtain an instance given a number of units. > * @param baseUnits the length as a number of base units (millipoints) >+ * @return A new or previously cached instance of FixedLength > */ >- public FixedLength(int baseUnits) { >- millipoints = baseUnits; >+ public static FixedLength getInstance(int baseUnits) { >+ FixedLength fl = new FixedLength(baseUnits); >+ return (FixedLength)cache.fetch(fl); > } > > /** >@@ -58,7 +72,7 @@ > * @param dvalue quantity of input units > * @param unit input unit specifier (in, cm, etc.) > */ >- protected void convert(double dvalue, String unit) { >+ private static int convert(double dvalue, String unit) { > // TODO: the whole routine smells fishy. > > int assumedResolution = 1; // points/pixel = 72dpi >@@ -90,9 +104,9 @@ > log.error("Unknown length unit '" + unit + "'"); > } > if (unit.equals("mpt")) { >- millipoints = (int)dvalue; >+ return (int)dvalue; > } else { >- millipoints = (int)(dvalue * 1000); >+ return (int)(dvalue * 1000); > } > } > >@@ -139,5 +153,15 @@ > return millipoints + "mpt"; > } > >+ public boolean equals(Object obj) { >+ if (!(obj instanceof FixedLength)) >+ return false; >+ FixedLength fl = (FixedLength)obj; >+ return millipoints == fl.millipoints; >+ } >+ >+ public int hashCode() { >+ return millipoints; >+ } > } > >Index: src/java/org/apache/fop/fo/properties/CommonMarginBlock.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/CommonMarginBlock.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/CommonMarginBlock.java (working copy) >@@ -30,51 +30,59 @@ > * Public "structure" allows direct member access. > */ > public class CommonMarginBlock { >+ >+ private static final PropertyCache cache = new PropertyCache(); >+ > /** > * The "margin-top" property. > */ >- public Length marginTop; >+ public final Length marginTop; > > /** > * The "margin-bottom" property. > */ >- public Length marginBottom; >+ public final Length marginBottom; > > /** > * The "margin-left" property. > */ >- public Length marginLeft; >+ public final Length marginLeft; > > /** > * The "margin-right" property. > */ >- public Length marginRight; >+ public final Length marginRight; > > /** > * The "space-before" property. > */ >- public SpaceProperty spaceBefore; >+ public final SpaceProperty spaceBefore; > > /** > * The "space-after" property. > */ >- public SpaceProperty spaceAfter; >+ public final SpaceProperty spaceAfter; > > /** > * The "start-indent" property. > */ >- public Length startIndent; >+ public final Length startIndent; > > /** > * The "end-indent" property. > */ >- public Length endIndent; >+ public final Length endIndent; > >+ public static final CommonMarginBlock getInstance(PropertyList pList) throws PropertyException { >+ CommonMarginBlock c = new CommonMarginBlock(pList); >+ return (CommonMarginBlock)cache.fetch(c); >+ } >+ > /** > * Create a CommonMarginBlock object. > * @param pList The PropertyList with propery values. > */ >- public CommonMarginBlock(PropertyList pList) throws PropertyException { >+ private CommonMarginBlock(PropertyList pList) throws PropertyException { > marginTop = pList.get(Constants.PR_MARGIN_TOP).getLength(); > marginBottom = pList.get(Constants.PR_MARGIN_BOTTOM).getLength(); > marginLeft = pList.get(Constants.PR_MARGIN_LEFT).getLength(); >@@ -98,5 +106,30 @@ > + "Indents (start, end): (" > + startIndent + ", " + endIndent + ")\n"; > } >+ >+ public int hashCode() { >+ return marginTop.hashCode() << 1 + >+ marginBottom.hashCode() << 2 + >+ marginLeft.hashCode() << 4 + >+ marginRight.hashCode() << 6 + >+ spaceBefore.hashCode() << 8 + >+ spaceAfter.hashCode() << 10 + >+ startIndent.hashCode() << 12 + >+ endIndent.hashCode() << 14; >+ } >+ >+ public boolean equals(Object obj) { >+ if (!(obj instanceof CommonMarginBlock)) >+ return false; >+ CommonMarginBlock cmb = (CommonMarginBlock)obj; >+ return Property.eq(this.marginTop, cmb.marginTop) && >+ Property.eq(this.marginBottom, cmb.marginBottom) && >+ Property.eq(this.marginLeft, cmb.marginLeft) && >+ Property.eq(this.marginRight, cmb.marginRight) && >+ Property.eq(this.spaceBefore, cmb.spaceBefore) && >+ Property.eq(this.spaceAfter, cmb.spaceAfter) && >+ Property.eq(this.startIndent, cmb.startIndent) && >+ Property.eq(this.endIndent, cmb.endIndent); >+ } > > } >Index: src/java/org/apache/fop/fo/properties/PercentLength.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/PercentLength.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/PercentLength.java (working copy) >@@ -32,15 +32,13 @@ > * The percentage itself, expressed as a decimal value, e.g. for 95%, set > * the value to .95 > */ >- private double factor; >+ private final double factor; > > /** > * A PercentBase implementation that contains the base length to which the > * {@link #factor} should be applied to compute the actual length > */ >- private PercentBase lbase = null; >- >- private double resolvedValue; >+ private final PercentBase lbase; > > /** > * Main constructor. Construct an object based on a factor (the percent, >@@ -92,8 +90,7 @@ > */ > public double getNumericValue(PercentBaseContext context) { > try { >- resolvedValue = factor * lbase.getBaseLength(context); >- return resolvedValue; >+ return factor * lbase.getBaseLength(context); > } catch (PropertyException exc) { > log.error(exc); > return 0; >@@ -123,4 +120,17 @@ > return (new Double(factor * 100.0).toString()) + "%"; > } > >+ public int hashCode() { >+ return lbase.hashCode(); >+ } >+ >+ public boolean equals(Object obj) { >+ if (! (obj instanceof PercentLength)) >+ return false; >+ PercentLength pl = (PercentLength)obj; >+ return pl.factor == this.factor && >+ Property.eq(pl.lbase, this.lbase); >+ } >+ >+ > } >Index: src/java/org/apache/fop/fo/properties/PropertyMaker.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/PropertyMaker.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/PropertyMaker.java (working copy) >@@ -68,7 +68,7 @@ > /** > * @return the name of the property for this Maker > */ >- public int getPropId() { >+ public final int getPropId() { > return propId; > } > >Index: src/java/org/apache/fop/fo/properties/IndentPropertyMaker.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/IndentPropertyMaker.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/IndentPropertyMaker.java (working copy) >@@ -108,7 +108,7 @@ > //Margin is used > Numeric margin = propertyList.get(marginProp).getNumeric(); > >- Numeric v = new FixedLength(0); >+ Numeric v = FixedLength.getInstance(0); > if (!propertyList.getFObj().generatesReferenceAreas()) { > // The inherited_value_of([start|end]-indent) > v = NumericOp.addition(v, propertyList.getInherited(baseMaker.propId).getNumeric()); >@@ -173,7 +173,7 @@ > if (isInherited(propertyList) || !marginNearest) { > return null; > } else { >- return new FixedLength(0); >+ return FixedLength.getInstance(0); > } > } else { > return indent; >@@ -182,7 +182,7 @@ > //Margin is used > Numeric margin = propertyList.get(marginProp).getNumeric(); > >- Numeric v = new FixedLength(0); >+ Numeric v = FixedLength.getInstance(0); > if (isInherited(propertyList)) { > // The inherited_value_of([start|end]-indent) > v = NumericOp.addition(v, propertyList.getInherited(baseMaker.propId).getNumeric()); >Index: src/java/org/apache/fop/fo/properties/PropertyCache.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/PropertyCache.java (revision 0) >+++ src/java/org/apache/fop/fo/properties/PropertyCache.java (revision 0) >@@ -0,0 +1,50 @@ >+/* >+ * Licensed to the Apache Software Foundation (ASF) under one or more >+ * contributor license agreements. See the NOTICE file distributed with >+ * this work for additional information regarding copyright ownership. >+ * The ASF licenses this file to You 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.properties; >+ >+import java.util.Map; >+import java.util.WeakHashMap; >+ >+/** >+ Thin wrapper around a HashMap to implement the property caching idiom >+ in which a new Property instance is created then tested against cached >+ instances created previously. If an existing property is found, this is >+ retained and the newly created one is instantly eligible for garbage >+ collection. >+*/ >+public class PropertyCache { >+ >+ private Map cache = new WeakHashMap(); >+ >+ /** >+ Checks if the given object is present in the cache - if so, returns >+ a reference to the cached value. Otherwise the given object is added >+ to the cache and returned. >+ */ >+ public synchronized Object fetch(Object obj) { >+ Object cacheEntry = cache.get(obj); >+ if (cacheEntry == null) { >+ cache.put(obj, obj); >+ return obj; >+ } else { >+ return cacheEntry; >+ } >+ } >+} >Index: src/java/org/apache/fop/fo/properties/CommonRelativePosition.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/CommonRelativePosition.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/CommonRelativePosition.java (working copy) >@@ -30,30 +30,33 @@ > * Public "structure" allows direct member access. > */ > public class CommonRelativePosition { >+ >+ private static final PropertyCache cache = new PropertyCache(); >+ > /** > * The "relative-position" property. > */ >- public int relativePosition; >+ public final int relativePosition; > > /** > * The "top" property. > */ >- public Length top; >+ public final Length top; > > /** > * The "right" property. > */ >- public Length right; >+ public final Length right; > > /** > * The "bottom" property. > */ >- public Length bottom; >+ public final Length bottom; > > /** > * The "left" property. > */ >- public Length left; >+ public final Length left; > > /** > * Create a CommonRelativePosition object. >@@ -67,4 +70,25 @@ > right = pList.get(Constants.PR_RIGHT).getLength(); > } > >+ public int hashCode() { >+ return relativePosition + >+ Property.hc(top) << 2 + >+ Property.hc(right) << 4 + >+ Property.hc(bottom) << 6 + >+ Property.hc(left) << 8; >+ } >+ >+ public boolean equals(Object obj) { >+ CommonRelativePosition c = (CommonRelativePosition)obj; >+ return c.relativePosition == relativePosition && >+ Property.eq(c.top, top) && >+ Property.eq(c.right, right) && >+ Property.eq(c.bottom, bottom) && >+ Property.eq(c.left, left); >+ } >+ >+ public static CommonRelativePosition getInstance(PropertyList pList) throws PropertyException { >+ CommonRelativePosition c = new CommonRelativePosition(pList); >+ return (CommonRelativePosition)cache.fetch(c); >+ } > } >Index: src/java/org/apache/fop/fo/properties/CommonBorderPaddingBackground.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/CommonBorderPaddingBackground.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/CommonBorderPaddingBackground.java (working copy) >@@ -28,6 +28,7 @@ > import org.apache.fop.fo.FObj; > import org.apache.fop.fo.PropertyList; > import org.apache.fop.fo.expr.PropertyException; >+import org.apache.fop.fo.flow.TableCell; > import org.apache.fop.image.FopImage; > import org.apache.fop.image.ImageFactory; > >@@ -36,40 +37,39 @@ > * See Sec. 7.7 of the XSL-FO Standard. > */ > public class CommonBorderPaddingBackground { >+ >+ private static final PropertyCache cache = new PropertyCache(); >+ > /** > * The "background-attachment" property. > */ >- public int backgroundAttachment; >+ public final int backgroundAttachment; > > /** > * The "background-color" property. > */ >- public Color backgroundColor; >+ public final Color backgroundColor; > > /** > * The "background-image" property. > */ >- public String backgroundImage; >+ public final String backgroundImage; > > /** > * The "background-repeat" property. > */ >- public int backgroundRepeat; >+ public final int backgroundRepeat; > > /** > * The "background-position-horizontal" property. > */ >- public Length backgroundPositionHorizontal; >+ public final Length backgroundPositionHorizontal; > > /** > * The "background-position-vertical" property. > */ >- public Length backgroundPositionVertical; >+ public final Length backgroundPositionVertical; > >- >- private FopImage fopimage; >- >- > /** the "before" edge */ > public static final int BEFORE = 0; > /** the "after" edge */ >@@ -123,16 +123,71 @@ > sb.append("}"); > return sb.toString(); > } >+ >+ public int hashCode() { >+ return mStyle + mColor.hashCode() << 4 + mWidth.hashCode() << 7; >+ } >+ >+ public boolean equals(Object obj) { >+ if (!( obj instanceof BorderInfo)) >+ return false; >+ BorderInfo b = (BorderInfo)obj; >+ return this.mStyle == b.mStyle && >+ Property.eq(this.mColor, b.mColor) && >+ Property.eq(this.mWidth, b.mWidth); >+ } > } >+ >+ private final FopImage fopimage; > >- private BorderInfo[] borderInfo = new BorderInfo[4]; >- private CondLengthProperty[] padding = new CondLengthProperty[4]; >+ private final BorderInfo[] borderInfo = new BorderInfo[4]; > >+ /** >+ Padding lengths, indexed by BEFORE, AFTER, START, END >+ */ >+ private CondLengthProperty[] padding = new CondLengthProperty[4]; // TODO: Should be final >+ > /** >- * Construct a CommonBorderPaddingBackground object. >+ Returns a new CommonBorderPaddingBackground instance with appropriate changes >+ made to border and padding. >+ @param src The original CBPB whose properties to take. >+ @param cell >+ */ >+ public static final CommonBorderPaddingBackground getInstance(CommonBorderPaddingBackground src, >+ TableCell cell, >+ BorderInfo bi, int side) { >+ if (bi==null && cell==null) { >+ return src; >+ } >+ CommonBorderPaddingBackground nc = new CommonBorderPaddingBackground(src, cell, bi, side); >+ return (CommonBorderPaddingBackground)cache.fetch(nc); >+ } >+ >+ public static final CommonBorderPaddingBackground getInstance(PropertyList pList) throws PropertyException { >+ CommonBorderPaddingBackground c = new CommonBorderPaddingBackground(pList, pList.getFObj()); >+ return (CommonBorderPaddingBackground)cache.fetch(c); >+ } >+ >+ /** >+ * See the above get instance() method. > */ >- public CommonBorderPaddingBackground() { >- >+ private CommonBorderPaddingBackground(CommonBorderPaddingBackground src, TableCell cell, >+ BorderInfo bi, int side) { >+ this.backgroundAttachment = src.backgroundAttachment; >+ this.backgroundColor = src.backgroundColor; >+ this.backgroundImage = src.backgroundImage; >+ this.backgroundRepeat = src.backgroundRepeat; >+ this.backgroundPositionHorizontal = src.backgroundPositionHorizontal; >+ this.backgroundPositionVertical = src.backgroundPositionVertical; >+ this.fopimage = src.fopimage; >+ if (cell!=null) { >+ CondLengthProperty[] srcPadding = cell.getCommonBorderPaddingBackground().padding; >+ for (int i = 0; i < padding.length ; i++) >+ this.padding[i] = srcPadding[i]; >+ } >+ if (bi!=null) { >+ this.borderInfo[side] = bi; >+ } > } > > /** >@@ -141,19 +196,22 @@ > * @param fobj The FO to create this instance for. > * @throws PropertyException if there's an error while binding the properties > */ >- public CommonBorderPaddingBackground(PropertyList pList, FObj fobj) throws PropertyException { >+ private CommonBorderPaddingBackground(PropertyList pList, FObj fobj) throws PropertyException { > > backgroundAttachment = pList.get(Constants.PR_BACKGROUND_ATTACHMENT).getEnum(); >- backgroundColor = pList.get(Constants.PR_BACKGROUND_COLOR).getColor( >+ Color bc = pList.get(Constants.PR_BACKGROUND_COLOR).getColor( > fobj == null ? null : fobj.getUserAgent()); >- if (backgroundColor.getAlpha() == 0) { >- backgroundColor = null; >- } >+ backgroundColor = bc.getAlpha() == 0 ? null : bc; > >- backgroundImage = pList.get(Constants.PR_BACKGROUND_IMAGE).getString(); >- if (backgroundImage == null || "none".equals(backgroundImage)) { >+ String bi = pList.get(Constants.PR_BACKGROUND_IMAGE).getString(); >+ if (bi == null || "none".equals(bi)) { > backgroundImage = null; >+ backgroundRepeat = 0; >+ backgroundPositionHorizontal = null; >+ backgroundPositionVertical = null; >+ fopimage = null; > } else { >+ backgroundImage = bi; > backgroundRepeat = pList.get(Constants.PR_BACKGROUND_REPEAT).getEnum(); > backgroundPositionHorizontal = pList.get( > Constants.PR_BACKGROUND_POSITION_HORIZONTAL).getLength(); >@@ -220,6 +278,7 @@ > * Sets a border. > * @param info the border information > * @param side the side to apply the info to >+ * @deprecated CommonBorderPaddingBackground should be immutable. > */ > public void setBorderInfo(BorderInfo info, int side) { > this.borderInfo[side] = info; >@@ -232,10 +291,11 @@ > public BorderInfo getBorderInfo(int side) { > return this.borderInfo[side]; > } >- >+ > /** > * Set padding. > * @param source the padding info to copy from >+ * @deprecated CommonBorderPaddingBackground should be immutable. > */ > public void setPadding(CommonBorderPaddingBackground source) { > this.padding = source.padding; >@@ -405,4 +465,32 @@ > return (borderInfo[BEFORE] != null || borderInfo[AFTER] != null > || borderInfo[START] != null || borderInfo[END] != null); > } >+ >+ public int hashCode() { >+ return Property.hc(backgroundColor) << 1 + >+ Property.hc(backgroundImage) << 3 + >+ backgroundRepeat << 5 + >+ Property.hc(backgroundPositionHorizontal) << 7 + >+ Property.hc(backgroundPositionVertical); >+ } >+ >+ public boolean equals(Object obj) { >+ if (!(obj instanceof CommonBorderPaddingBackground)) >+ return false; >+ CommonBorderPaddingBackground c = (CommonBorderPaddingBackground)obj; >+ return backgroundAttachment == c.backgroundAttachment && >+ backgroundRepeat == c.backgroundRepeat && >+ Property.eq(backgroundColor, c.backgroundColor) && >+ Property.eq(backgroundImage, c.backgroundImage) && >+ Property.eq(backgroundPositionHorizontal, c.backgroundPositionHorizontal) && >+ Property.eq(backgroundPositionVertical, c.backgroundPositionVertical) && >+ Property.eq(padding[BEFORE], c.padding[BEFORE]) && >+ Property.eq(padding[AFTER], c.padding[AFTER]) && >+ Property.eq(padding[START], c.padding[START]) && >+ Property.eq(padding[END], c.padding[END]) && >+ Property.eq(borderInfo, c.borderInfo) && >+ (fopimage == c.fopimage || >+ (fopimage!=null && >+ fopimage.getOriginalURI().equals(c.fopimage.getOriginalURI()))); >+ } > } >Index: src/java/org/apache/fop/fo/properties/CommonAural.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/CommonAural.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/CommonAural.java (working copy) >@@ -121,6 +121,13 @@ > * Create a CommonAbsolutePosition object. > * @param pList The PropertyList with propery values. > */ >- public CommonAural(PropertyList pList) { >+ private CommonAural(PropertyList pList) { > } >+ >+ /** >+ Placeholder. See CommonAccessibility for the correct instantiation idiom. >+ */ >+ public static CommonAural getInstance(PropertyList pList) { >+ return null; >+ } > } >Index: src/java/org/apache/fop/fo/properties/CommonFont.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/CommonFont.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/CommonFont.java (working copy) >@@ -38,45 +38,47 @@ > */ > public class CommonFont { > >+ private static final PropertyCache cache = new PropertyCache(); >+ > /** > * The "font-family" property. > */ >- private String[] fontFamily; >+ private final String[] fontFamily; > > /** > * The "font-selection-strategy" property. > */ >- public int fontSelectionStrategy; >+ public final int fontSelectionStrategy; > > /** > * The "font-size" property. > */ >- public Length fontSize; >+ public final Length fontSize; > > /** > * The "font-stretch" property. > */ >- public int fontStretch; >+ public final int fontStretch; > > /** > * The "font-size-adjust" property. > */ >- public Numeric fontSizeAdjust; >+ public final Numeric fontSizeAdjust; > > /** > * The "font-style" property. > */ >- public int fontStyle; >+ public final int fontStyle; > > /** > * The "font-variant" property. > */ >- public int fontVariant; >+ public final int fontVariant; > > /** > * The "font-weight" property. > */ >- public int fontWeight; >+ public final int fontWeight; > > private Font fontState; > >@@ -84,15 +86,17 @@ > * Create a CommonFont object. > * @param pList The PropertyList to get properties from. > */ >- public CommonFont(PropertyList pList) throws PropertyException { >+ private CommonFont(PropertyList pList) throws PropertyException { > List lst = pList.get(Constants.PR_FONT_FAMILY).getList(); >- fontFamily = new String[lst.size()]; >- for (int i = 0, c = lst.size(); i < c; i++) { >- fontFamily[i] = ((Property)lst.get(i)).getString(); >- } >- if (fontFamily.length == 0) { >+ int lstSize = lst.size(); >+ if (lstSize == 0) { > //Shouldn't happen, but we never know. > fontFamily = new String[] {"any"}; >+ } else { >+ fontFamily = new String[lstSize]; >+ for (int i = 0, c = lstSize; i < c; i++) { >+ fontFamily[i] = ((Property)lst.get(i)).getString(); >+ } > } > fontSelectionStrategy = pList.get(Constants.PR_FONT_SELECTION_STRATEGY).getEnum(); > fontSize = pList.get(Constants.PR_FONT_SIZE).getLength(); >@@ -103,6 +107,11 @@ > fontWeight = pList.get(Constants.PR_FONT_WEIGHT).getEnum(); > } > >+ public static CommonFont getInstance(PropertyList pList) throws PropertyException { >+ CommonFont cf = new CommonFont(pList); >+ return (CommonFont)cache.fetch(cf); >+ } >+ > /** @return the first font-family name in the list */ > public String getFirstFontFamily() { > return this.fontFamily[0]; >@@ -114,15 +123,6 @@ > } > > /** >- * Overrides the font-family. >- * @param value the new font-family >- */ >- public void overrideFontFamily(String value) { >- this.fontFamily = new String[] {value}; >- >- } >- >- /** > * Create and return a Font object based on the properties. > * > * @param fontInfo >@@ -175,4 +175,22 @@ > return fontState; > } > >+ public int hashCode() { >+ return fontStretch + fontStyle + fontVariant + fontWeight; >+ } >+ >+ public boolean equals(Object obj) { >+ if (! (obj instanceof CommonFont)) >+ return false; >+ CommonFont cf = (CommonFont)obj; >+ return fontSelectionStrategy == cf.fontSelectionStrategy && >+ fontStretch == cf.fontStretch && >+ fontStyle == cf.fontStyle && >+ fontVariant == cf.fontVariant && >+ fontWeight == cf.fontWeight && >+ fontFamily.length == cf.fontFamily.length && >+ Property.eq(fontSize, cf.fontSize) && >+ Property.eq(fontSizeAdjust, cf.fontSizeAdjust) && >+ Property.eq(fontFamily, cf.fontFamily); >+ } > } >Index: src/java/org/apache/fop/fo/properties/ColorProperty.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/ColorProperty.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/ColorProperty.java (working copy) >@@ -138,5 +138,22 @@ > public Object getObject() { > return this; > } >+ >+ /** >+ * @see java.lang.Object#equals(Object) >+ */ >+ public boolean equals(Object obj) { >+ if (obj instanceof ColorProperty) { >+ ColorProperty cp = (ColorProperty)obj; >+ return Property.eq(cp.color, this.color); >+ } else { >+ return false; >+ } >+ } >+ >+ public int hashCode() { >+ return color.hashCode(); >+ } >+ > } > >Index: src/java/org/apache/fop/fo/properties/LengthProperty.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/LengthProperty.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/LengthProperty.java (working copy) >@@ -59,7 +59,7 @@ > } > if (p instanceof NumberProperty) { > //Assume pixels (like in HTML) when there's no unit >- return new FixedLength(p.getNumeric().getNumericValue(), "px"); >+ return FixedLength.getInstance(p.getNumeric().getNumericValue(), "px"); > } > Length val = p.getLength(); > if (val != null) { >Index: src/java/org/apache/fop/fo/properties/FontSizePropertyMaker.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/FontSizePropertyMaker.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/FontSizePropertyMaker.java (working copy) >@@ -55,9 +55,9 @@ > Property pp = propertyList.getFromParent(this.getPropId()); > int baseFontSize = computeClosestAbsoluteFontSize(pp.getLength().getValue()); > if (p.getEnum() == EN_LARGER) { >- return new FixedLength((int)Math.round((baseFontSize * FONT_SIZE_GROWTH_FACTOR))); >+ return FixedLength.getInstance((int)Math.round((baseFontSize * FONT_SIZE_GROWTH_FACTOR))); > } else { >- return new FixedLength((int)Math.round((baseFontSize / FONT_SIZE_GROWTH_FACTOR))); >+ return FixedLength.getInstance((int)Math.round((baseFontSize / FONT_SIZE_GROWTH_FACTOR))); > } > } > return super.convertProperty(p, propertyList, fo); >Index: src/java/org/apache/fop/fo/properties/KeepProperty.java >=================================================================== >--- src/java/org/apache/fop/fo/properties/KeepProperty.java (revision 532293) >+++ src/java/org/apache/fop/fo/properties/KeepProperty.java (working copy) >@@ -165,4 +165,19 @@ > return this; > } > >+ public int hashCode() { >+ return withinLine.hashCode() << 3 + >+ withinColumn.hashCode() << 7 + >+ withinPage.hashCode() << 9; >+ } >+ >+ public boolean equals(Object obj) { >+ if (! (obj instanceof KeepProperty)) >+ return false; >+ KeepProperty c = (KeepProperty)obj; >+ return Property.eq(this.withinLine, c.withinLine) && >+ Property.eq(this.withinColumn, c.withinColumn) && >+ Property.eq(this.withinPage, c.withinPage); >+ } >+ > } >Index: src/java/org/apache/fop/fo/PropertyList.java >=================================================================== >--- src/java/org/apache/fop/fo/PropertyList.java (revision 532293) >+++ src/java/org/apache/fop/fo/PropertyList.java (working copy) >@@ -38,6 +38,7 @@ > import org.apache.fop.fo.properties.CommonRelativePosition; > import org.apache.fop.fo.properties.CommonTextDecoration; > import org.apache.fop.fo.properties.Property; >+import org.apache.fop.fo.properties.PropertyCache; > import org.apache.fop.fo.properties.PropertyMaker; > import org.apache.fop.util.QName; > >@@ -46,6 +47,8 @@ > */ > public abstract class PropertyList { > >+ private static final PropertyCache cache = new PropertyCache(); >+ > // writing-mode index > private int writingMode; > >@@ -53,7 +56,7 @@ > > /** reference to the parent FO's propertyList **/ > protected PropertyList parentPropertyList = null; >- private FObj fobj = null; >+ private final FObj fobj; > > private static Log log = LogFactory.getLog(PropertyList.class); > >@@ -171,8 +174,9 @@ > > PropertyMaker propertyMaker = findMaker(propId & Constants.PROPERTY_MASK); > if (propertyMaker != null) { >- return propertyMaker.get(propId & Constants.COMPOUND_MASK, this, >- bTryInherit, bTryDefault); >+ Property p = propertyMaker.get(propId & Constants.COMPOUND_MASK, this, >+ bTryInherit, bTryDefault); >+ return (Property)cache.fetch(p); > } > return null; > } >@@ -520,7 +524,7 @@ > return null; > } > } >- >+ > /** > * @param propID ID of property > * @return new Property object >@@ -529,7 +533,7 @@ > private Property makeProperty(int propId) throws PropertyException { > PropertyMaker propertyMaker = findMaker(propId); > if (propertyMaker != null) { >- return propertyMaker.make(this); >+ return (Property)cache.fetch(propertyMaker.make(this)); > } else { > //log.error("property " + propertyName > // + " ignored"); >@@ -574,7 +578,7 @@ > */ > public CommonBorderPaddingBackground getBorderPaddingBackgroundProps() > throws PropertyException { >- return new CommonBorderPaddingBackground(this, getFObj()); >+ return CommonBorderPaddingBackground.getInstance(this); > } > > /** >@@ -583,7 +587,7 @@ > * @throws PropertyException if there's a problem while processing the properties > */ > public CommonHyphenation getHyphenationProps() throws PropertyException { >- return new CommonHyphenation(this); >+ return CommonHyphenation.getInstance(this); > } > > /** >@@ -592,7 +596,7 @@ > * @throws PropertyException if there's a problem while processing the properties > */ > public CommonMarginBlock getMarginBlockProps() throws PropertyException { >- return new CommonMarginBlock(this); >+ return CommonMarginBlock.getInstance(this); > } > > /** >@@ -601,7 +605,7 @@ > * @throws PropertyException if there's a problem while processing the properties > */ > public CommonMarginInline getMarginInlineProps() throws PropertyException { >- return new CommonMarginInline(this); >+ return new CommonMarginInline(this); // TODO: Replace with getInstance() > } > > /** >@@ -610,7 +614,7 @@ > * @throws PropertyException if there's a problem while processing the properties > */ > public CommonAccessibility getAccessibilityProps() throws PropertyException { >- return new CommonAccessibility(this); >+ return CommonAccessibility.getInstance(this); > } > > /** >@@ -619,8 +623,7 @@ > * @throws PropertyException if there's a problem while processing the properties > */ > public CommonAural getAuralProps() throws PropertyException { >- CommonAural props = new CommonAural(this); >- return props; >+ return CommonAural.getInstance(this); > } > > /** >@@ -629,7 +632,7 @@ > * @throws PropertyException if there's a problem while processing the properties > */ > public CommonRelativePosition getRelativePositionProps() throws PropertyException { >- return new CommonRelativePosition(this); >+ return CommonRelativePosition.getInstance(this); > } > > /** >@@ -638,7 +641,7 @@ > * @throws PropertyException if there's a problem while processing the properties > */ > public CommonAbsolutePosition getAbsolutePositionProps() throws PropertyException { >- return new CommonAbsolutePosition(this); >+ return CommonAbsolutePosition.getInstance(this); > } > > >@@ -648,7 +651,7 @@ > * @throws PropertyException if there's a problem while processing the properties > */ > public CommonFont getFontProps() throws PropertyException { >- return new CommonFont(this); >+ return CommonFont.getInstance(this); > } > > /** >Index: src/java/org/apache/fop/fo/flow/Block.java >=================================================================== >--- src/java/org/apache/fop/fo/flow/Block.java (revision 532293) >+++ src/java/org/apache/fop/fo/flow/Block.java (working copy) >@@ -52,8 +52,6 @@ > private boolean initialPropertySetFound = false; > > // The value of properties relevant for fo:block. >- private CommonAccessibility commonAccessibility; >- private CommonAural commonAural; > private CommonBorderPaddingBackground commonBorderPaddingBackground; > private CommonFont commonFont; > private CommonHyphenation commonHyphenation; >@@ -83,7 +81,10 @@ > private int whiteSpaceCollapse; > private Numeric widows; > private int wrapOption; >+ > // Unused but valid items, commented out for performance: >+ // private CommonAccessibility commonAccessibility; >+ // private CommonAural commonAural; > // private Length textDepth; > // private Length textAltitude; > // private int visibility; >@@ -101,8 +102,6 @@ > * @see org.apache.fop.fo.FObj#bind(PropertyList) > */ > public void bind(PropertyList pList) throws FOPException { >- commonAccessibility = pList.getAccessibilityProps(); >- commonAural = pList.getAuralProps(); > commonBorderPaddingBackground = pList.getBorderPaddingBackgroundProps(); > commonFont = pList.getFontProps(); > commonHyphenation = pList.getHyphenationProps(); >@@ -348,20 +347,6 @@ > } > > /** >- * @return Returns the commonAccessibility. >- */ >- public CommonAccessibility getCommonAccessibility() { >- return this.commonAccessibility; >- } >- >- /** >- * @return Returns the commonAural. >- */ >- public CommonAural getCommonAural() { >- return this.commonAural; >- } >- >- /** > * @return Returns the commonRelativePosition. > */ > public CommonRelativePosition getCommonRelativePosition() { >Index: src/java/org/apache/fop/fo/StaticPropertyList.java >=================================================================== >--- src/java/org/apache/fop/fo/StaticPropertyList.java (revision 532293) >+++ src/java/org/apache/fop/fo/StaticPropertyList.java (working copy) >@@ -24,8 +24,8 @@ > * the explicit set properties and another array to store cached values. > */ > public class StaticPropertyList extends PropertyList { >- private Property[] explicit; >- private Property[] values; >+ private final Property[] explicit; >+ private final Property[] values; > > /** > * Construct a StaticPropertyList. >Index: src/java/org/apache/fop/fo/FOTreeBuilder.java >=================================================================== >--- src/java/org/apache/fop/fo/FOTreeBuilder.java (revision 532293) >+++ src/java/org/apache/fop/fo/FOTreeBuilder.java (working copy) >@@ -110,11 +110,10 @@ > * true no Locator is passed to the FO tree nodes which would copy the information into > * a SAX LocatorImpl instance. > * @return true if no context information should be stored on each node in the FO tree. >+ * @deprecated Use FOUserAgent.isLocatorEnabled() instead. > */ > protected boolean isLocatorDisabled() { >- //TODO make this configurable through the FOUserAgent so people can optimize memory >- //consumption. >- return false; >+ return !userAgent.isLocatorEnabled(); > } > > /** >@@ -127,7 +126,7 @@ > > /** @return a Locator instance if it is available and not disabled */ > protected Locator getEffectiveLocator() { >- return (isLocatorDisabled() ? null : this.locator); >+ return (userAgent.isLocatorEnabled() ? this.locator : null); > } > > /** >Index: src/java/org/apache/fop/fo/expr/PropertyParser.java >=================================================================== >--- src/java/org/apache/fop/fo/expr/PropertyParser.java (revision 532293) >+++ src/java/org/apache/fop/fo/expr/PropertyParser.java (working copy) >@@ -293,7 +293,7 @@ > prop = (Property) NumericOp.multiply(new NumberProperty(numPart.doubleValue()), > propInfo.currentFontSize()); > } else { >- prop = new FixedLength(numPart.doubleValue(), unitPart); >+ prop = FixedLength.getInstance(numPart.doubleValue(), unitPart); > } > break; > >Index: build.xml >=================================================================== >--- build.xml (revision 532293) >+++ build.xml (working copy) >@@ -152,7 +152,7 @@ > > <property name="javac.debug" value="on"/> > <property name="javac.optimize" value="off"/> >- <property name="javac.deprecation" value="on"/> >+ <property name="javac.deprecation" value="off"/> > <property name="javac.source" value="1.3"/> > <property name="javac.target" value="1.3"/> > <property name="javac.fork" value="no"/>
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 41044
:
19176
|
19177
|
19220
|
19221
|
19289
|
19410
| 20041