From: Javen O'Neal Date: Sat, 4 Nov 2017 07:17:44 +0000 (+0000) Subject: bug 61474, github #81: add ColumnShifter interface; deduplicate some code in RowShift... X-Git-Url: https://source.dussan.org/?a=commitdiff_plain;h=4b92e7c67a5e8057b990a4ec2344a76dd3ee23dc;p=poi.git bug 61474, github #81: add ColumnShifter interface; deduplicate some code in RowShifter, CFRecordsAggregate git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@1814256 13f79535-47bb-0310-9956-ffa450edef68 --- diff --git a/src/java/org/apache/poi/hssf/record/aggregates/CFRecordsAggregate.java b/src/java/org/apache/poi/hssf/record/aggregates/CFRecordsAggregate.java index 87cb834633..afd69c48a2 100644 --- a/src/java/org/apache/poi/hssf/record/aggregates/CFRecordsAggregate.java +++ b/src/java/org/apache/poi/hssf/record/aggregates/CFRecordsAggregate.java @@ -29,9 +29,8 @@ import org.apache.poi.hssf.record.CFRuleBase; import org.apache.poi.hssf.record.CFRuleRecord; import org.apache.poi.hssf.record.Record; import org.apache.poi.ss.formula.FormulaShifter; -import org.apache.poi.ss.formula.ptg.AreaErrPtg; -import org.apache.poi.ss.formula.ptg.AreaPtg; import org.apache.poi.ss.formula.ptg.Ptg; +import org.apache.poi.ss.usermodel.helpers.BaseRowColShifter; import org.apache.poi.ss.util.CellRangeAddress; import org.apache.poi.util.POILogFactory; import org.apache.poi.util.POILogger; @@ -223,7 +222,7 @@ public final class CFRecordsAggregate extends RecordAggregate { boolean changed = false; List temp = new ArrayList<>(); for (CellRangeAddress craOld : cellRanges) { - CellRangeAddress craNew = shiftRange(shifter, craOld, currentExternSheetIx); + CellRangeAddress craNew = BaseRowColShifter.shiftRange(shifter, craOld, currentExternSheetIx); if (craNew == null) { changed = true; continue; @@ -264,23 +263,4 @@ public final class CFRecordsAggregate extends RecordAggregate { } return true; } - - private static CellRangeAddress shiftRange(FormulaShifter shifter, CellRangeAddress cra, int currentExternSheetIx) { - // FormulaShifter works well in terms of Ptgs - so convert CellRangeAddress to AreaPtg (and back) here - AreaPtg aptg = new AreaPtg(cra.getFirstRow(), cra.getLastRow(), cra.getFirstColumn(), cra.getLastColumn(), false, false, false, false); - Ptg[] ptgs = { aptg, }; - - if (!shifter.adjustFormula(ptgs, currentExternSheetIx)) { - return cra; - } - Ptg ptg0 = ptgs[0]; - if (ptg0 instanceof AreaPtg) { - AreaPtg bptg = (AreaPtg) ptg0; - return new CellRangeAddress(bptg.getFirstRow(), bptg.getLastRow(), bptg.getFirstColumn(), bptg.getLastColumn()); - } - if (ptg0 instanceof AreaErrPtg) { - return null; - } - throw new IllegalStateException("Unexpected shifted ptg class (" + ptg0.getClass().getName() + ")"); - } } diff --git a/src/java/org/apache/poi/hssf/usermodel/helpers/HSSFColumnShifter.java b/src/java/org/apache/poi/hssf/usermodel/helpers/HSSFColumnShifter.java new file mode 100644 index 0000000000..051e24ad5d --- /dev/null +++ b/src/java/org/apache/poi/hssf/usermodel/helpers/HSSFColumnShifter.java @@ -0,0 +1,66 @@ +/* ==================================================================== + 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. +==================================================================== */ + +package org.apache.poi.hssf.usermodel.helpers; + +import org.apache.poi.hssf.usermodel.HSSFSheet; +import org.apache.poi.ss.formula.FormulaShifter; +import org.apache.poi.ss.formula.eval.NotImplementedException; +import org.apache.poi.ss.usermodel.helpers.ColumnShifter; +import org.apache.poi.util.Beta; +import org.apache.poi.util.NotImplemented; +import org.apache.poi.util.POILogFactory; +import org.apache.poi.util.POILogger; + +/** + * Helper for shifting columns up or down + */ +// non-Javadoc: When possible, code should be implemented in the ColumnShifter abstract class to avoid duplication with +// {@link org.apache.poi.xssf.usermodel.helpers.XSSFColumnShifter} +@Beta +public final class HSSFColumnShifter extends ColumnShifter { + private static final POILogger logger = POILogFactory.getLogger(HSSFColumnShifter.class); + + public HSSFColumnShifter(HSSFSheet sh) { + super(sh); + } + + @Override + @NotImplemented + public void updateNamedRanges(FormulaShifter formulaShifter) { + throw new NotImplementedException("HSSFColumnShifter.updateNamedRanges"); + } + + @Override + @NotImplemented + public void updateFormulas(FormulaShifter formulaShifter) { + throw new NotImplementedException("updateFormulas"); + } + + @Override + @NotImplemented + public void updateConditionalFormatting(FormulaShifter formulaShifter) { + throw new NotImplementedException("updateConditionalFormatting"); + } + + @Override + @NotImplemented + public void updateHyperlinks(FormulaShifter formulaShifter) { + throw new NotImplementedException("updateHyperlinks"); + } + +} diff --git a/src/java/org/apache/poi/hssf/usermodel/helpers/HSSFRowShifter.java b/src/java/org/apache/poi/hssf/usermodel/helpers/HSSFRowShifter.java index 1c57e5b1dc..0e8a5b43ae 100644 --- a/src/java/org/apache/poi/hssf/usermodel/helpers/HSSFRowShifter.java +++ b/src/java/org/apache/poi/hssf/usermodel/helpers/HSSFRowShifter.java @@ -29,9 +29,9 @@ import org.apache.poi.util.POILogger; /** * Helper for shifting rows up or down - * - * When possible, code should be implemented in the RowShifter abstract class to avoid duplication with {@link org.apache.poi.xssf.usermodel.helpers.XSSFRowShifter} */ +// non-Javadoc: When possible, code should be implemented in the RowShifter abstract class to avoid duplication with +// {@link org.apache.poi.xssf.usermodel.helpers.XSSFRowShifter} public final class HSSFRowShifter extends RowShifter { private static final POILogger logger = POILogFactory.getLogger(HSSFRowShifter.class); diff --git a/src/java/org/apache/poi/ss/usermodel/helpers/BaseRowColShifter.java b/src/java/org/apache/poi/ss/usermodel/helpers/BaseRowColShifter.java new file mode 100644 index 0000000000..306e515220 --- /dev/null +++ b/src/java/org/apache/poi/ss/usermodel/helpers/BaseRowColShifter.java @@ -0,0 +1,54 @@ +/* ==================================================================== + 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. +==================================================================== */ + +package org.apache.poi.ss.usermodel.helpers; + + +import org.apache.poi.ss.formula.FormulaShifter; +import org.apache.poi.ss.formula.ptg.AreaErrPtg; +import org.apache.poi.ss.formula.ptg.AreaPtg; +import org.apache.poi.ss.formula.ptg.Ptg; +import org.apache.poi.ss.util.CellRangeAddress; +import org.apache.poi.util.Internal; + +/** + * Class for code common to {@link RowShifter} and {@link ColumnShifter} + * Helper for shifting rows up or down and columns left and right + */ +@Internal +public abstract class BaseRowColShifter { + + public static CellRangeAddress shiftRange(FormulaShifter formulaShifter, CellRangeAddress cra, int currentExternSheetIx) { + // FormulaShifter works well in terms of Ptgs - so convert CellRangeAddress to AreaPtg (and back) here + AreaPtg aptg = new AreaPtg(cra.getFirstRow(), cra.getLastRow(), cra.getFirstColumn(), cra.getLastColumn(), false, false, false, false); + Ptg[] ptgs = { aptg, }; + + if (!formulaShifter.adjustFormula(ptgs, currentExternSheetIx)) { + return cra; + } + Ptg ptg0 = ptgs[0]; + if (ptg0 instanceof AreaPtg) { + AreaPtg bptg = (AreaPtg) ptg0; + return new CellRangeAddress(bptg.getFirstRow(), bptg.getLastRow(), bptg.getFirstColumn(), bptg.getLastColumn()); + } + if (ptg0 instanceof AreaErrPtg) { + return null; + } + throw new IllegalStateException("Unexpected shifted ptg class (" + ptg0.getClass().getName() + ")"); + } + +} diff --git a/src/java/org/apache/poi/ss/usermodel/helpers/ColumnShifter.java b/src/java/org/apache/poi/ss/usermodel/helpers/ColumnShifter.java new file mode 100644 index 0000000000..7769f30c58 --- /dev/null +++ b/src/java/org/apache/poi/ss/usermodel/helpers/ColumnShifter.java @@ -0,0 +1,136 @@ +/* ==================================================================== + 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. +==================================================================== */ + +package org.apache.poi.ss.usermodel.helpers; + +import java.util.ArrayList; +import java.util.HashSet; +import java.util.List; +import java.util.Set; + +import org.apache.poi.ss.formula.FormulaShifter; +import org.apache.poi.ss.usermodel.Sheet; +import org.apache.poi.ss.util.CellRangeAddress; +import org.apache.poi.util.Beta; + +/** + * Helper for shifting columns up or down + */ +// non-Javadoc: This abstract class exists to consolidate duplicated code between XSSFColumnShifter and HSSFColumnShifter +// (currently methods sprinkled throughout HSSFSheet) +@Beta +public abstract class ColumnShifter extends BaseRowColShifter { + protected final Sheet sheet; + + public ColumnShifter(Sheet sh) { + sheet = sh; + } + + /** + * Shifts, grows, or shrinks the merged regions due to a column shift. + * Merged regions that are completely overlaid by shifting will be deleted. + * + * @param startColumn the column to start shifting + * @param endColumn the column to end shifting + * @param n the number of columns to shift + * @return an array of affected merged regions, doesn't contain deleted ones + */ + public List shiftMergedRegions(int startColumn, int endColumn, int n) { + List shiftedRegions = new ArrayList<>(); + Set removedIndices = new HashSet<>(); + //move merged regions completely if they fall within the new region boundaries when they are shifted + int size = sheet.getNumMergedRegions(); + for (int i = 0; i < size; i++) { + CellRangeAddress merged = sheet.getMergedRegion(i); + + // remove merged region that are replaced by the shifting, + // i.e. where the area includes something in the overwritten area + if(removalNeeded(merged, startColumn, endColumn, n)) { + removedIndices.add(i); + continue; + } + + boolean inStart = (merged.getFirstColumn() >= startColumn || merged.getLastColumn() >= startColumn); + boolean inEnd = (merged.getFirstColumn() <= endColumn || merged.getLastColumn() <= endColumn); + + //don't check if it's not within the shifted area + if (!inStart || !inEnd) { + continue; + } + + //only shift if the region outside the shifted columns is not merged too + if (!merged.containsColumn(startColumn - 1) && !merged.containsColumn(endColumn + 1)) { + merged.setFirstColumn(merged.getFirstColumn() + n); + merged.setLastColumn(merged.getLastColumn() + n); + //have to remove/add it back + shiftedRegions.add(merged); + removedIndices.add(i); + } + } + + if(!removedIndices.isEmpty()) { + sheet.removeMergedRegions(removedIndices); + } + + //read so it doesn't get shifted again + for (CellRangeAddress region : shiftedRegions) { + sheet.addMergedRegion(region); + } + return shiftedRegions; + } + + private boolean removalNeeded(CellRangeAddress merged, int startColumn, int endColumn, int n) { + final int movedColumns = endColumn - startColumn + 1; + + // build a range of the columns that are overwritten, i.e. the target-area, but without + // columns that are moved along + final CellRangeAddress overwrite; + if(n > 0) { + // area is moved down => overwritten area is [endColumn + n - movedColumns, endColumn + n] + overwrite = new CellRangeAddress(Math.max(endColumn + 1, endColumn + n - movedColumns), endColumn + n, 0, 0); + } else { + // area is moved up => overwritten area is [startColumn + n, startColumn + n + movedColumns] + overwrite = new CellRangeAddress(startColumn + n, Math.min(startColumn - 1, startColumn + n + movedColumns), 0, 0); + } + + // if the merged-region and the overwritten area intersect, we need to remove it + return merged.intersects(overwrite); + } + + /** + * Updated named ranges + */ + public abstract void updateNamedRanges(FormulaShifter formulaShifter); + + /** + * Update formulas. + */ + public abstract void updateFormulas(FormulaShifter formulaShifter); + + + public abstract void updateConditionalFormatting(FormulaShifter formulaShifter); + + /** + * Shift the Hyperlink anchors (not the hyperlink text, even if the hyperlink + * is of type LINK_DOCUMENT and refers to a cell that was shifted). Hyperlinks + * do not track the content they point to. + * + * @param formulaShifter the formula shifting policy + */ + public abstract void updateHyperlinks(FormulaShifter formulaShifter); + +} diff --git a/src/java/org/apache/poi/ss/usermodel/helpers/RowShifter.java b/src/java/org/apache/poi/ss/usermodel/helpers/RowShifter.java index 19df59bd19..09566e4dcb 100644 --- a/src/java/org/apache/poi/ss/usermodel/helpers/RowShifter.java +++ b/src/java/org/apache/poi/ss/usermodel/helpers/RowShifter.java @@ -30,10 +30,12 @@ import org.apache.poi.util.Internal; /** * Helper for shifting rows up or down - * - * This abstract class exists to consolidate duplicated code between XSSFRowShifter and HSSFRowShifter (currently methods sprinkled throughout HSSFSheet) */ -public abstract class RowShifter { +// non-Javadoc: This abstract class exists to consolidate duplicated code between +// {@link org.apache.poi.hssf.usermodel.helpers.HSSFRowShifter} and +// {@link org.apache.poi.xssf.usermodel.helpers.XSSFRowShifter} +// (currently methods sprinkled throughout HSSFSheet) +public abstract class RowShifter extends BaseRowColShifter { protected final Sheet sheet; public RowShifter(Sheet sh) { diff --git a/src/ooxml/java/org/apache/poi/xssf/usermodel/helpers/XSSFColumnShifter.java b/src/ooxml/java/org/apache/poi/xssf/usermodel/helpers/XSSFColumnShifter.java new file mode 100644 index 0000000000..de51707b11 --- /dev/null +++ b/src/ooxml/java/org/apache/poi/xssf/usermodel/helpers/XSSFColumnShifter.java @@ -0,0 +1,83 @@ +/* ==================================================================== + 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. +==================================================================== */ + +package org.apache.poi.xssf.usermodel.helpers; + +import org.apache.poi.ss.formula.*; +import org.apache.poi.ss.formula.eval.NotImplementedException; +import org.apache.poi.ss.usermodel.*; +import org.apache.poi.ss.usermodel.helpers.ColumnShifter; +import org.apache.poi.util.Beta; +import org.apache.poi.util.NotImplemented; +import org.apache.poi.util.POILogFactory; +import org.apache.poi.util.POILogger; +import org.apache.poi.xssf.usermodel.*; + +/** + * Helper for shifting columns up or down + */ +// non-Javadoc: When possible, code should be implemented in the ColumnShifter abstract class to avoid duplication with +// {@link org.apache.poi.hssf.usermodel.helpers.HSSFColumnShifter} +@Beta +public final class XSSFColumnShifter extends ColumnShifter { + private static final POILogger logger = POILogFactory.getLogger(XSSFColumnShifter.class); + + public XSSFColumnShifter(XSSFSheet sh) { + super(sh); + } + + /** + * Updated named ranges + */ + @NotImplemented + @Override + public void updateNamedRanges(FormulaShifter formulaShifter) { + throw new NotImplementedException("updateNamedRanges"); + } + + /** + * Update formulas. + */ + @NotImplemented + @Override + public void updateFormulas(FormulaShifter formulaShifter) { + throw new NotImplementedException("updateFormulas"); + } + + private void updateSheetFormulas(Sheet sh, FormulaShifter formulaShifter) { + throw new NotImplementedException("updateSheetFormulas"); + } + + @NotImplemented + @Override + public void updateConditionalFormatting(FormulaShifter formulaShifter) { + throw new NotImplementedException("updateConditionalformatting"); + } + + /** + * Shift the Hyperlink anchors (not the hyperlink text, even if the hyperlink + * is of type LINK_DOCUMENT and refers to a cell that was shifted). Hyperlinks + * do not track the content they point to. + * + * @param formulaShifter + */ + @Override + public void updateHyperlinks(FormulaShifter formulaShifter) { + XSSFRowColShifter.updateHyperlinks(sheet, formulaShifter); + } + +} diff --git a/src/ooxml/java/org/apache/poi/xssf/usermodel/helpers/XSSFRowColShifter.java b/src/ooxml/java/org/apache/poi/xssf/usermodel/helpers/XSSFRowColShifter.java new file mode 100644 index 0000000000..ef450a1bea --- /dev/null +++ b/src/ooxml/java/org/apache/poi/xssf/usermodel/helpers/XSSFRowColShifter.java @@ -0,0 +1,59 @@ +/* ==================================================================== + 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. +==================================================================== */ + +package org.apache.poi.xssf.usermodel.helpers; + +import org.apache.poi.ss.formula.*; +import org.apache.poi.ss.usermodel.*; +import org.apache.poi.ss.usermodel.helpers.BaseRowColShifter; +import org.apache.poi.ss.util.CellRangeAddress; +import org.apache.poi.util.Internal; +import org.apache.poi.util.POILogFactory; +import org.apache.poi.util.POILogger; +import org.apache.poi.xssf.usermodel.*; + +import java.util.List; + +/** + * Class for code common to {@link XSSFRowShifter} and {@link XSSFColumnShifter} + */ +@Internal +/*private*/ final class XSSFRowColShifter extends BaseRowColShifter { + private static final POILogger logger = POILogFactory.getLogger(XSSFRowColShifter.class); + + private XSSFRowColShifter() { /*no instances for static classes*/} + + /*package*/ static void updateHyperlinks(Sheet sheet, FormulaShifter formulaShifter) { + int sheetIndex = sheet.getWorkbook().getSheetIndex(sheet); + List hyperlinkList = sheet.getHyperlinkList(); + + for (Hyperlink hyperlink : hyperlinkList) { + XSSFHyperlink xhyperlink = (XSSFHyperlink) hyperlink; + String cellRef = xhyperlink.getCellRef(); + CellRangeAddress cra = CellRangeAddress.valueOf(cellRef); + CellRangeAddress shiftedRange = shiftRange(formulaShifter, cra, sheetIndex); + if (shiftedRange != null && shiftedRange != cra) { + // shiftedRange should not be null. If shiftedRange is null, that means + // that a hyperlink wasn't deleted at the beginning of shiftRows when + // identifying rows that should be removed because they will be overwritten + xhyperlink.setCellReference(shiftedRange.formatAsString()); + } + } + } + + +} diff --git a/src/ooxml/java/org/apache/poi/xssf/usermodel/helpers/XSSFRowShifter.java b/src/ooxml/java/org/apache/poi/xssf/usermodel/helpers/XSSFRowShifter.java index 04257917d8..7ef0b3f475 100644 --- a/src/ooxml/java/org/apache/poi/xssf/usermodel/helpers/XSSFRowShifter.java +++ b/src/ooxml/java/org/apache/poi/xssf/usermodel/helpers/XSSFRowShifter.java @@ -25,11 +25,8 @@ import org.apache.poi.ss.formula.FormulaParser; import org.apache.poi.ss.formula.FormulaRenderer; import org.apache.poi.ss.formula.FormulaShifter; import org.apache.poi.ss.formula.FormulaType; -import org.apache.poi.ss.formula.ptg.AreaErrPtg; -import org.apache.poi.ss.formula.ptg.AreaPtg; import org.apache.poi.ss.formula.ptg.Ptg; import org.apache.poi.ss.usermodel.Cell; -import org.apache.poi.ss.usermodel.Hyperlink; import org.apache.poi.ss.usermodel.Name; import org.apache.poi.ss.usermodel.Row; import org.apache.poi.ss.usermodel.Sheet; @@ -41,7 +38,6 @@ import org.apache.poi.util.POILogFactory; import org.apache.poi.util.POILogger; import org.apache.poi.xssf.usermodel.XSSFCell; import org.apache.poi.xssf.usermodel.XSSFEvaluationWorkbook; -import org.apache.poi.xssf.usermodel.XSSFHyperlink; import org.apache.poi.xssf.usermodel.XSSFRow; import org.apache.poi.xssf.usermodel.XSSFSheet; import org.apache.poi.xssf.usermodel.XSSFWorkbook; @@ -54,9 +50,9 @@ import org.openxmlformats.schemas.spreadsheetml.x2006.main.STCellFormulaType; /** * Helper for shifting rows up or down - * - * When possible, code should be implemented in the RowShifter abstract class to avoid duplication with {@link org.apache.poi.hssf.usermodel.helpers.HSSFRowShifter} */ +// non-Javadoc: When possible, code should be implemented in the RowShifter abstract class to avoid duplication with +// {@link org.apache.poi.hssf.usermodel.helpers.HSSFRowShifter} public final class XSSFRowShifter extends RowShifter { private static final POILogger logger = POILogFactory.getLogger(XSSFRowShifter.class); @@ -253,40 +249,8 @@ public final class XSSFRowShifter extends RowShifter { */ @Override public void updateHyperlinks(FormulaShifter formulaShifter) { - int sheetIndex = sheet.getWorkbook().getSheetIndex(sheet); - List hyperlinkList = sheet.getHyperlinkList(); - - for (Hyperlink hyperlink : hyperlinkList) { - XSSFHyperlink xhyperlink = (XSSFHyperlink) hyperlink; - String cellRef = xhyperlink.getCellRef(); - CellRangeAddress cra = CellRangeAddress.valueOf(cellRef); - CellRangeAddress shiftedRange = shiftRange(formulaShifter, cra, sheetIndex); - if (shiftedRange != null && shiftedRange != cra) { - // shiftedRange should not be null. If shiftedRange is null, that means - // that a hyperlink wasn't deleted at the beginning of shiftRows when - // identifying rows that should be removed because they will be overwritten - xhyperlink.setCellReference(shiftedRange.formatAsString()); - } - } + XSSFRowColShifter.updateHyperlinks(sheet, formulaShifter); } - private static CellRangeAddress shiftRange(FormulaShifter formulaShifter, CellRangeAddress cra, int currentExternSheetIx) { - // FormulaShifter works well in terms of Ptgs - so convert CellRangeAddress to AreaPtg (and back) here - AreaPtg aptg = new AreaPtg(cra.getFirstRow(), cra.getLastRow(), cra.getFirstColumn(), cra.getLastColumn(), false, false, false, false); - Ptg[] ptgs = { aptg, }; - - if (!formulaShifter.adjustFormula(ptgs, currentExternSheetIx)) { - return cra; - } - Ptg ptg0 = ptgs[0]; - if (ptg0 instanceof AreaPtg) { - AreaPtg bptg = (AreaPtg) ptg0; - return new CellRangeAddress(bptg.getFirstRow(), bptg.getLastRow(), bptg.getFirstColumn(), bptg.getLastColumn()); - } - if (ptg0 instanceof AreaErrPtg) { - return null; - } - throw new IllegalStateException("Unexpected shifted ptg class (" + ptg0.getClass().getName() + ")"); - } }