diff options
106 files changed, 2103 insertions, 960 deletions
diff --git a/src/documentation/content/xdocs/changes.xml b/src/documentation/content/xdocs/changes.xml index d8c366b2be..0fb5cac07c 100644 --- a/src/documentation/content/xdocs/changes.xml +++ b/src/documentation/content/xdocs/changes.xml @@ -44,6 +44,8 @@ <action dev="POI-DEVELOPERS" type="add">Created a common interface for handling Excel files, irrespective of if they are .xls or .xlsx</action> </release> <release version="3.0.3-beta1" date="2008-04-??"> + <action dev="POI-DEVELOPERS" type="add">30311 - Conditional Formatting - improved API, added HSSFSheetConditionalFormatting</action> + <action dev="POI-DEVELOPERS" type="fix">Update the formula parser code to use a HSSFWorkbook, rather than the low level model.Workbook, to make things cleaner and make supporting XSSF formulas in future much easier</action> <action dev="POI-DEVELOPERS" type="fix">Fix the logger used by POIFSFileSystem, so that commons-logging isn't required when not used</action> <action dev="POI-DEVELOPERS" type="add">Update HSLFSlideShow and HSSFWorkbook to take advantage of POIFS updates, and allow reading embeded documents</action> <action dev="POI-DEVELOPERS" type="add">Improve how POIFS works with directory entries, and update HWPFDocument to support reading an embeded word document</action> diff --git a/src/documentation/content/xdocs/status.xml b/src/documentation/content/xdocs/status.xml index 2b7cf09eb1..cef12de4c8 100644 --- a/src/documentation/content/xdocs/status.xml +++ b/src/documentation/content/xdocs/status.xml @@ -41,6 +41,8 @@ <action dev="POI-DEVELOPERS" type="add">Created a common interface for handling Excel files, irrespective of if they are .xls or .xlsx</action> </release> <release version="3.0.3-beta1" date="2008-04-??"> + <action dev="POI-DEVELOPERS" type="add">30311 - Conditional Formatting - improved API, added HSSFSheetConditionalFormatting</action> + <action dev="POI-DEVELOPERS" type="fix">Update the formula parser code to use a HSSFWorkbook, rather than the low level model.Workbook, to make things cleaner and make supporting XSSF formulas in future much easier</action> <action dev="POI-DEVELOPERS" type="fix">Fix the logger used by POIFSFileSystem, so that commons-logging isn't required when not used</action> <action dev="POI-DEVELOPERS" type="add">Update HSLFSlideShow and HSSFWorkbook to take advantage of POIFS updates, and allow reading embeded documents</action> <action dev="POI-DEVELOPERS" type="add">Improve how POIFS works with directory entries, and update HWPFDocument to support reading an embeded word document</action> diff --git a/src/java/org/apache/poi/hssf/dev/FormulaViewer.java b/src/java/org/apache/poi/hssf/dev/FormulaViewer.java index eb28c9006f..91d342099b 100644 --- a/src/java/org/apache/poi/hssf/dev/FormulaViewer.java +++ b/src/java/org/apache/poi/hssf/dev/FormulaViewer.java @@ -32,6 +32,7 @@ import java.util.List; import org.apache.poi.poifs.filesystem.POIFSFileSystem; import org.apache.poi.hssf.record.*; import org.apache.poi.hssf.record.formula.*; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.model.*; /** @@ -99,7 +100,7 @@ public class FormulaViewer StringBuffer buf = new StringBuffer(); if (token instanceof ExpPtg) return; - buf.append(name=((OperationPtg) token).toFormulaString((Workbook)null)); + buf.append(name=((OperationPtg) token).toFormulaString((HSSFWorkbook)null)); buf.append(sep); switch (token.getPtgClass()) { case Ptg.CLASS_REF : @@ -168,7 +169,7 @@ public class FormulaViewer StringBuffer buf = new StringBuffer(); for (int i=0;i<numptgs;i++) { token = (Ptg) tokens.get(i); - buf.append( token.toFormulaString((Workbook)null)); + buf.append( token.toFormulaString((HSSFWorkbook)null)); switch (token.getPtgClass()) { case Ptg.CLASS_REF : buf.append("(R)"); @@ -188,7 +189,7 @@ public class FormulaViewer private String composeFormula(FormulaRecord record) { - return org.apache.poi.hssf.model.FormulaParser.toFormulaString((Workbook)null,record.getParsedExpression()); + return org.apache.poi.hssf.model.FormulaParser.toFormulaString((HSSFWorkbook)null,record.getParsedExpression()); } /** diff --git a/src/java/org/apache/poi/hssf/model/FormulaParser.java b/src/java/org/apache/poi/hssf/model/FormulaParser.java index 7219284743..05b4d80f4a 100644 --- a/src/java/org/apache/poi/hssf/model/FormulaParser.java +++ b/src/java/org/apache/poi/hssf/model/FormulaParser.java @@ -27,6 +27,7 @@ import java.util.regex.Pattern; import org.apache.poi.hssf.record.formula.*; import org.apache.poi.hssf.record.formula.function.FunctionMetadata; import org.apache.poi.hssf.record.formula.function.FunctionMetadataRegistry; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * This class parses a formula string into a List of tokens in RPN order. @@ -86,7 +87,7 @@ public final class FormulaParser { */ private char look; - private Workbook book; + private HSSFWorkbook book; /** @@ -101,14 +102,14 @@ public final class FormulaParser { * model.Workbook, then use the convenience method on * usermodel.HSSFFormulaEvaluator */ - public FormulaParser(String formula, Workbook book){ + public FormulaParser(String formula, HSSFWorkbook book){ formulaString = formula; pointer=0; this.book = book; formulaLength = formulaString.length(); } - public static Ptg[] parse(String formula, Workbook book) { + public static Ptg[] parse(String formula, HSSFWorkbook book) { FormulaParser fp = new FormulaParser(formula, book); fp.parse(); return fp.getRPNPtg(); @@ -251,7 +252,7 @@ public final class FormulaParser { Match('!'); String sheetName = name; String first = GetName(); - short externIdx = book.checkExternSheet(book.getSheetIndex(sheetName)); + short externIdx = book.getExternalSheetIndex(book.getSheetIndex(sheetName)); if (look == ':') { Match(':'); String second=GetName(); @@ -282,9 +283,9 @@ public final class FormulaParser { return new ReferencePtg(name); } - for(int i = 0; i < book.getNumNames(); i++) { + for(int i = 0; i < book.getNumberOfNames(); i++) { // named range name matching is case insensitive - if(book.getNameRecord(i).getNameText().equalsIgnoreCase(name)) { + if(book.getNameAt(i).getNameName().equalsIgnoreCase(name)) { return new NamePtg(name, book); } } @@ -926,7 +927,7 @@ end; * @param lptgs list of Ptg, can be null or empty * @return a human readable String */ - public static String toFormulaString(Workbook book, List lptgs) { + public static String toFormulaString(HSSFWorkbook book, List lptgs) { String retval = null; if (lptgs == null || lptgs.size() == 0) return "#NAME"; Ptg[] ptgs = new Ptg[lptgs.size()]; @@ -952,7 +953,7 @@ end; * @param ptgs array of Ptg, can be null or empty * @return a human readable String */ - public static String toFormulaString(Workbook book, Ptg[] ptgs) { + public static String toFormulaString(HSSFWorkbook book, Ptg[] ptgs) { if (ptgs == null || ptgs.length == 0) { // TODO - what is the justification for returning "#NAME" (which is not "#NAME?", btw) return "#NAME"; diff --git a/src/java/org/apache/poi/hssf/record/CFRuleRecord.java b/src/java/org/apache/poi/hssf/record/CFRuleRecord.java index 0890f1f32d..2b1705abe2 100644 --- a/src/java/org/apache/poi/hssf/record/CFRuleRecord.java +++ b/src/java/org/apache/poi/hssf/record/CFRuleRecord.java @@ -26,9 +26,11 @@ import org.apache.poi.hssf.record.cf.BorderFormatting; import org.apache.poi.hssf.record.cf.FontFormatting; import org.apache.poi.hssf.record.cf.PatternFormatting; import org.apache.poi.hssf.record.formula.Ptg; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.util.BitField; import org.apache.poi.util.BitFieldFactory; import org.apache.poi.util.LittleEndian; +import org.apache.poi.util.StringUtil; /** * Conditional Formatting Rule Record. @@ -62,7 +64,7 @@ public final class CFRuleRecord extends Record private int field_5_options; - private static final BitField modificationBits = bf(0x83FFFFFF); // Bits: font,align,bord,patt,prot + private static final BitField modificationBits = bf(0x003FFFFF); // Bits: font,align,bord,patt,prot private static final BitField alignHor = bf(0x00000001); // 0 = Horizontal alignment modified private static final BitField alignVer = bf(0x00000002); // 0 = Vertical alignment modified private static final BitField alignWrap = bf(0x00000004); // 0 = Text wrapped flag modified @@ -152,7 +154,7 @@ public final class CFRuleRecord extends Record /** * Creates a new comparison operation rule */ - public static CFRuleRecord create(Workbook workbook, String formulaText) { + public static CFRuleRecord create(HSSFWorkbook workbook, String formulaText) { Ptg[] formula1 = parseFormula(formulaText, workbook); return new CFRuleRecord(CONDITION_TYPE_FORMULA, ComparisonOperator.NO_COMPARISON, formula1, null); @@ -160,7 +162,7 @@ public final class CFRuleRecord extends Record /** * Creates a new comparison operation rule */ - public static CFRuleRecord create(Workbook workbook, byte comparisonOperation, + public static CFRuleRecord create(HSSFWorkbook workbook, byte comparisonOperation, String formulaText1, String formulaText2) { Ptg[] formula1 = parseFormula(formulaText1, workbook); Ptg[] formula2 = parseFormula(formulaText2, workbook); @@ -607,6 +609,8 @@ public final class CFRuleRecord extends Record { StringBuffer buffer = new StringBuffer(); buffer.append("[CFRULE]\n"); + buffer.append(" OPTION FLAGS=0x"+Integer.toHexString(getOptions())); + /* if( containsFontFormattingBlock()) { buffer.append(fontFormatting.toString()); @@ -619,7 +623,7 @@ public final class CFRuleRecord extends Record { buffer.append(patternFormatting.toString()); } - buffer.append("[/CFRULE]\n"); + buffer.append("[/CFRULE]\n");*/ return buffer.toString(); } @@ -651,7 +655,7 @@ public final class CFRuleRecord extends Record /** * @return <code>null</code> if <tt>formula</tt> was null. */ - private static Ptg[] parseFormula(String formula, Workbook workbook) + private static Ptg[] parseFormula(String formula, HSSFWorkbook workbook) { if(formula == null) { return null; diff --git a/src/java/org/apache/poi/hssf/record/NameRecord.java b/src/java/org/apache/poi/hssf/record/NameRecord.java index a06bc8aedd..23af4b17cc 100644 --- a/src/java/org/apache/poi/hssf/record/NameRecord.java +++ b/src/java/org/apache/poi/hssf/record/NameRecord.java @@ -18,12 +18,17 @@ package org.apache.poi.hssf.record; +import java.util.Iterator; import java.util.List; import java.util.Stack; -import java.util.Iterator; -import org.apache.poi.hssf.model.Workbook; -import org.apache.poi.hssf.record.formula.*; +import org.apache.poi.hssf.record.formula.Area3DPtg; +import org.apache.poi.hssf.record.formula.DeletedArea3DPtg; +import org.apache.poi.hssf.record.formula.DeletedRef3DPtg; +import org.apache.poi.hssf.record.formula.Ptg; +import org.apache.poi.hssf.record.formula.Ref3DPtg; +import org.apache.poi.hssf.record.formula.UnionPtg; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.util.AreaReference; import org.apache.poi.hssf.util.RangeAddress; import org.apache.poi.util.HexDump; @@ -645,7 +650,7 @@ public class NameRecord extends Record { /** gets the reference , the area only (range) * @return area reference */ - public String getAreaReference(Workbook book){ + public String getAreaReference(HSSFWorkbook book){ if (field_13_name_definition == null || field_13_name_definition.isEmpty()) return "Error"; Ptg ptg = (Ptg) field_13_name_definition.peek(); String result = ""; @@ -679,7 +684,7 @@ public class NameRecord extends Record { * return an empty string if nothing is possible * for it. */ - private String getAreaRefString(Ptg ptg,Workbook book) { + private String getAreaRefString(Ptg ptg,HSSFWorkbook book) { if (ptg.getClass() == Area3DPtg.class){ return ptg.toFormulaString(book); } else if (ptg.getClass() == Ref3DPtg.class){ diff --git a/src/java/org/apache/poi/hssf/record/formula/AbstractFunctionPtg.java b/src/java/org/apache/poi/hssf/record/formula/AbstractFunctionPtg.java index f0fc1fccf4..82d85ccebb 100644 --- a/src/java/org/apache/poi/hssf/record/formula/AbstractFunctionPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/AbstractFunctionPtg.java @@ -17,7 +17,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.formula.function.FunctionMetadata; import org.apache.poi.hssf.record.formula.function.FunctionMetadataRegistry; @@ -73,7 +73,7 @@ public abstract class AbstractFunctionPtg extends OperationPtg { return field_2_fnc_index == FUNCTION_INDEX_EXTERNAL; } - public String toFormulaString(Workbook book) { + public String toFormulaString(HSSFWorkbook book) { return getName(); } diff --git a/src/java/org/apache/poi/hssf/record/formula/AddPtg.java b/src/java/org/apache/poi/hssf/record/formula/AddPtg.java index 12c49f1148..4f79d76027 100644 --- a/src/java/org/apache/poi/hssf/record/formula/AddPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/AddPtg.java @@ -23,7 +23,7 @@ */ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -75,7 +75,7 @@ public class AddPtg } /** Implementation of method from Ptg */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "+"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/Area3DPtg.java b/src/java/org/apache/poi/hssf/record/formula/Area3DPtg.java index 9075920897..5a02394c7c 100644 --- a/src/java/org/apache/poi/hssf/record/formula/Area3DPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/Area3DPtg.java @@ -17,7 +17,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.util.AreaReference; import org.apache.poi.hssf.util.CellReference; @@ -273,7 +273,7 @@ public class Area3DPtg extends Ptg implements AreaI * @return text representation of this area reference that can be used in text * formulas. The sheet name will get properly delimited if required. */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { // First do the sheet name StringBuffer retval = new StringBuffer(); diff --git a/src/java/org/apache/poi/hssf/record/formula/AreaAPtg.java b/src/java/org/apache/poi/hssf/record/formula/AreaAPtg.java index 515d07dd41..6ff0b05b16 100644 --- a/src/java/org/apache/poi/hssf/record/formula/AreaAPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/AreaAPtg.java @@ -29,7 +29,7 @@ import org.apache.poi.util.BitField; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.util.AreaReference; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * Specifies a rectangular area of cells A1:A4 for instance. diff --git a/src/java/org/apache/poi/hssf/record/formula/AreaErrPtg.java b/src/java/org/apache/poi/hssf/record/formula/AreaErrPtg.java index ed48431dee..187957e587 100644 --- a/src/java/org/apache/poi/hssf/record/formula/AreaErrPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/AreaErrPtg.java @@ -20,7 +20,7 @@ package org.apache.poi.hssf.record.formula; import org.apache.poi.util.LittleEndian; import org.apache.poi.util.BitField; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -66,7 +66,7 @@ public class AreaErrPtg extends AreaPtg array[offset] = (byte) (sid + ptgClass); } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "#REF!"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/AreaNAPtg.java b/src/java/org/apache/poi/hssf/record/formula/AreaNAPtg.java index da24158ace..6b0eb908ac 100644 --- a/src/java/org/apache/poi/hssf/record/formula/AreaNAPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/AreaNAPtg.java @@ -29,7 +29,7 @@ import org.apache.poi.util.BitField; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.util.AreaReference; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * Specifies a rectangular area of cells A1:A4 for instance. @@ -58,7 +58,7 @@ public class AreaNAPtg return "AreaNAPtg"; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { throw new RuntimeException("Coding Error: This method should never be called. This ptg should be converted"); } diff --git a/src/java/org/apache/poi/hssf/record/formula/AreaNPtg.java b/src/java/org/apache/poi/hssf/record/formula/AreaNPtg.java index 9507e37a8e..71e413fead 100644 --- a/src/java/org/apache/poi/hssf/record/formula/AreaNPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/AreaNPtg.java @@ -29,7 +29,7 @@ import org.apache.poi.util.BitField; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.util.AreaReference; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * Specifies a rectangular area of cells A1:A4 for instance. @@ -61,7 +61,7 @@ public class AreaNPtg return "AreaNPtg"; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { throw new RuntimeException("Coding Error: This method should never be called. This ptg should be converted"); } diff --git a/src/java/org/apache/poi/hssf/record/formula/AreaNVPtg.java b/src/java/org/apache/poi/hssf/record/formula/AreaNVPtg.java index c91ed502c9..2ebf019829 100644 --- a/src/java/org/apache/poi/hssf/record/formula/AreaNVPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/AreaNVPtg.java @@ -29,7 +29,7 @@ import org.apache.poi.util.BitField; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.util.AreaReference; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * Specifies a rectangular area of cells A1:A4 for instance. @@ -59,7 +59,7 @@ public class AreaNVPtg return "AreaNVPtg"; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { throw new RuntimeException("Coding Error: This method should never be called. This ptg should be converted"); } diff --git a/src/java/org/apache/poi/hssf/record/formula/AreaPtg.java b/src/java/org/apache/poi/hssf/record/formula/AreaPtg.java index be34e0074a..27e4d1759c 100644 --- a/src/java/org/apache/poi/hssf/record/formula/AreaPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/AreaPtg.java @@ -24,7 +24,7 @@ import org.apache.poi.util.BitFieldFactory; import org.apache.poi.hssf.util.AreaReference; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -303,11 +303,11 @@ public class AreaPtg field_4_last_column = column; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return toFormulaString(this, book); } - protected static String toFormulaString(AreaI area, Workbook book) { + protected static String toFormulaString(AreaI area, HSSFWorkbook book) { CellReference topLeft = new CellReference(area.getFirstRow(),area.getFirstColumn(),!area.isFirstRowRelative(),!area.isFirstColRelative()); CellReference botRight = new CellReference(area.getLastRow(),area.getLastColumn(),!area.isLastRowRelative(),!area.isLastColRelative()); diff --git a/src/java/org/apache/poi/hssf/record/formula/AreaVPtg.java b/src/java/org/apache/poi/hssf/record/formula/AreaVPtg.java index 42dc11fa32..e5e3d525cc 100644 --- a/src/java/org/apache/poi/hssf/record/formula/AreaVPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/AreaVPtg.java @@ -29,7 +29,7 @@ import org.apache.poi.util.BitField; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.util.AreaReference; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * Specifies a rectangular area of cells A1:A4 for instance. diff --git a/src/java/org/apache/poi/hssf/record/formula/ArrayPtg.java b/src/java/org/apache/poi/hssf/record/formula/ArrayPtg.java index 12166b7967..01942be55c 100644 --- a/src/java/org/apache/poi/hssf/record/formula/ArrayPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/ArrayPtg.java @@ -23,7 +23,7 @@ import org.apache.poi.util.BitFieldFactory; import org.apache.poi.util.StringUtil; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordFormatException; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.record.SSTRecord; @@ -198,7 +198,7 @@ public class ArrayPtg extends Ptg return size; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { StringBuffer b = new StringBuffer(); b.append("{"); diff --git a/src/java/org/apache/poi/hssf/record/formula/ArrayPtgA.java b/src/java/org/apache/poi/hssf/record/formula/ArrayPtgA.java index 0319175ba4..616f737b84 100644 --- a/src/java/org/apache/poi/hssf/record/formula/ArrayPtgA.java +++ b/src/java/org/apache/poi/hssf/record/formula/ArrayPtgA.java @@ -23,7 +23,7 @@ import org.apache.poi.util.BitFieldFactory; import org.apache.poi.util.StringUtil; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordFormatException; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.record.SSTRecord; diff --git a/src/java/org/apache/poi/hssf/record/formula/ArrayPtgV.java b/src/java/org/apache/poi/hssf/record/formula/ArrayPtgV.java index 49a28c97cc..94aa32383f 100644 --- a/src/java/org/apache/poi/hssf/record/formula/ArrayPtgV.java +++ b/src/java/org/apache/poi/hssf/record/formula/ArrayPtgV.java @@ -23,7 +23,7 @@ import org.apache.poi.util.BitFieldFactory; import org.apache.poi.util.StringUtil; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordFormatException; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.record.SSTRecord; diff --git a/src/java/org/apache/poi/hssf/record/formula/AttrPtg.java b/src/java/org/apache/poi/hssf/record/formula/AttrPtg.java index d355fbfa1f..351d44a421 100644 --- a/src/java/org/apache/poi/hssf/record/formula/AttrPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/AttrPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.util.LittleEndian; @@ -209,11 +209,11 @@ public final class AttrPtg extends OperationPtg { if(space.isSet(field_1_options)) { return operands[ 0 ]; } else if (optiIf.isSet(field_1_options)) { - return toFormulaString((Workbook)null) + "(" + operands[ 0 ] +")"; + return toFormulaString((HSSFWorkbook)null) + "(" + operands[ 0 ] +")"; } else if (optGoto.isSet(field_1_options)) { - return toFormulaString((Workbook)null) + operands[0]; //goto isn't a real formula element should not show up + return toFormulaString((HSSFWorkbook)null) + operands[0]; //goto isn't a real formula element should not show up } else { - return toFormulaString((Workbook)null) + "(" + operands[ 0 ] + ")"; + return toFormulaString((HSSFWorkbook)null) + "(" + operands[ 0 ] + ")"; } } @@ -228,7 +228,7 @@ public final class AttrPtg extends OperationPtg { return -1; } - public String toFormulaString(Workbook book) { + public String toFormulaString(HSSFWorkbook book) { if(semiVolatile.isSet(field_1_options)) { return "ATTR(semiVolatile)"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/BoolPtg.java b/src/java/org/apache/poi/hssf/record/formula/BoolPtg.java index 0248f8466f..80c9f39d79 100644 --- a/src/java/org/apache/poi/hssf/record/formula/BoolPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/BoolPtg.java @@ -17,7 +17,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -70,7 +70,7 @@ public class BoolPtg return SIZE; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return field_1_value ? "TRUE" : "FALSE"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/ConcatPtg.java b/src/java/org/apache/poi/hssf/record/formula/ConcatPtg.java index 41d2de0cba..951872f43b 100644 --- a/src/java/org/apache/poi/hssf/record/formula/ConcatPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/ConcatPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -64,7 +64,7 @@ public class ConcatPtg return 2; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return CONCAT; } diff --git a/src/java/org/apache/poi/hssf/record/formula/DividePtg.java b/src/java/org/apache/poi/hssf/record/formula/DividePtg.java index cde67c5dc8..70fa62e58b 100644 --- a/src/java/org/apache/poi/hssf/record/formula/DividePtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/DividePtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -65,7 +65,7 @@ public class DividePtg return 2; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "/"; } @@ -74,7 +74,7 @@ public class DividePtg StringBuffer buffer = new StringBuffer(); buffer.append(operands[ 0 ]); - buffer.append(toFormulaString((Workbook)null)); + buffer.append(toFormulaString((HSSFWorkbook)null)); buffer.append(operands[ 1 ]); return buffer.toString(); } diff --git a/src/java/org/apache/poi/hssf/record/formula/EqualPtg.java b/src/java/org/apache/poi/hssf/record/formula/EqualPtg.java index 26f66e4fe2..a08a863d1c 100644 --- a/src/java/org/apache/poi/hssf/record/formula/EqualPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/EqualPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -64,7 +64,7 @@ public class EqualPtg return 2; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "="; } @@ -74,7 +74,7 @@ public class EqualPtg buffer.append(operands[ 0 ]); - buffer.append(toFormulaString((Workbook)null)); + buffer.append(toFormulaString((HSSFWorkbook)null)); buffer.append(operands[ 1 ]); return buffer.toString(); } diff --git a/src/java/org/apache/poi/hssf/record/formula/ErrPtg.java b/src/java/org/apache/poi/hssf/record/formula/ErrPtg.java index 26cc2e027b..a16992f943 100644 --- a/src/java/org/apache/poi/hssf/record/formula/ErrPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/ErrPtg.java @@ -19,7 +19,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.usermodel.HSSFErrorConstants; @@ -70,7 +70,7 @@ public final class ErrPtg extends Ptg { array[offset + 1] = (byte)field_1_error_code; } - public String toFormulaString(Workbook book) { + public String toFormulaString(HSSFWorkbook book) { return HSSFErrorConstants.getText(field_1_error_code); } diff --git a/src/java/org/apache/poi/hssf/record/formula/ExpPtg.java b/src/java/org/apache/poi/hssf/record/formula/ExpPtg.java index a7fc0274ad..0cd54e5f55 100644 --- a/src/java/org/apache/poi/hssf/record/formula/ExpPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/ExpPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordFormatException; import org.apache.poi.hssf.record.RecordInputStream; @@ -73,7 +73,7 @@ public class ExpPtg return field_2_first_col; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { throw new RecordFormatException("Coding Error: Expected ExpPtg to be converted from Shared to Non-Shared Formula by ValueRecordsAggregate, but it wasn't"); } diff --git a/src/java/org/apache/poi/hssf/record/formula/GreaterEqualPtg.java b/src/java/org/apache/poi/hssf/record/formula/GreaterEqualPtg.java index d8d08fecb8..677d78c3e5 100755 --- a/src/java/org/apache/poi/hssf/record/formula/GreaterEqualPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/GreaterEqualPtg.java @@ -19,7 +19,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; @@ -67,7 +67,7 @@ public class GreaterEqualPtg return 2; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return ">="; } @@ -77,7 +77,7 @@ public class GreaterEqualPtg buffer.append(operands[ 0 ]); - buffer.append(toFormulaString((Workbook)null)); + buffer.append(toFormulaString((HSSFWorkbook)null)); buffer.append(operands[ 1 ]); return buffer.toString(); diff --git a/src/java/org/apache/poi/hssf/record/formula/GreaterThanPtg.java b/src/java/org/apache/poi/hssf/record/formula/GreaterThanPtg.java index 6d66307b3d..6501203edc 100644 --- a/src/java/org/apache/poi/hssf/record/formula/GreaterThanPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/GreaterThanPtg.java @@ -25,7 +25,7 @@ package org.apache.poi.hssf.record.formula; import java.util.List; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -97,7 +97,7 @@ public class GreaterThanPtg * Implementation of method from Ptg * @param book the Sheet References */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return this.GREATERTHAN; } diff --git a/src/java/org/apache/poi/hssf/record/formula/IntPtg.java b/src/java/org/apache/poi/hssf/record/formula/IntPtg.java index f4106b6aa8..f3dd16f068 100644 --- a/src/java/org/apache/poi/hssf/record/formula/IntPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/IntPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; import org.apache.poi.util.LittleEndian; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -72,7 +72,7 @@ public final class IntPtg extends Ptg { return SIZE; } - public String toFormulaString(Workbook book) { + public String toFormulaString(HSSFWorkbook book) { return String.valueOf(getValue()); } public byte getDefaultOperandClass() { diff --git a/src/java/org/apache/poi/hssf/record/formula/IntersectionPtg.java b/src/java/org/apache/poi/hssf/record/formula/IntersectionPtg.java index 9b225912ed..8f5bddc190 100644 --- a/src/java/org/apache/poi/hssf/record/formula/IntersectionPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/IntersectionPtg.java @@ -17,7 +17,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -59,7 +59,7 @@ public class IntersectionPtg extends OperationPtg } /** Implementation of method from Ptg */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return " "; } diff --git a/src/java/org/apache/poi/hssf/record/formula/LessEqualPtg.java b/src/java/org/apache/poi/hssf/record/formula/LessEqualPtg.java index c395ed3b1c..f42966394b 100755 --- a/src/java/org/apache/poi/hssf/record/formula/LessEqualPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/LessEqualPtg.java @@ -20,7 +20,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; @@ -68,7 +68,7 @@ public class LessEqualPtg return 2; } - public String toFormulaString( Workbook book ) + public String toFormulaString( HSSFWorkbook book ) { return "<="; } @@ -77,7 +77,7 @@ public class LessEqualPtg { StringBuffer buffer = new StringBuffer(); buffer.append( operands[0] ); - buffer.append( toFormulaString( (Workbook) null ) ); + buffer.append( toFormulaString( (HSSFWorkbook) null ) ); buffer.append( operands[1] ); return buffer.toString(); } diff --git a/src/java/org/apache/poi/hssf/record/formula/LessThanPtg.java b/src/java/org/apache/poi/hssf/record/formula/LessThanPtg.java index 4bccd9274e..c23658d2db 100644 --- a/src/java/org/apache/poi/hssf/record/formula/LessThanPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/LessThanPtg.java @@ -27,7 +27,7 @@ package org.apache.poi.hssf.record.formula; import java.util.List; //POI -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -106,7 +106,7 @@ public class LessThanPtg * Implementation of method from Ptg * @param book the Sheet References */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return this.LESSTHAN; } diff --git a/src/java/org/apache/poi/hssf/record/formula/MemAreaPtg.java b/src/java/org/apache/poi/hssf/record/formula/MemAreaPtg.java index ee0b761854..ec33d10921 100644 --- a/src/java/org/apache/poi/hssf/record/formula/MemAreaPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/MemAreaPtg.java @@ -25,7 +25,7 @@ package org.apache.poi.hssf.record.formula; import org.apache.poi.util.LittleEndian; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -83,7 +83,7 @@ public class MemAreaPtg return SIZE; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return ""; // TODO: Not sure how to format this. -- DN } diff --git a/src/java/org/apache/poi/hssf/record/formula/MemErrPtg.java b/src/java/org/apache/poi/hssf/record/formula/MemErrPtg.java index bfc33c1284..359c76e668 100644 --- a/src/java/org/apache/poi/hssf/record/formula/MemErrPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/MemErrPtg.java @@ -25,7 +25,7 @@ package org.apache.poi.hssf.record.formula; import org.apache.poi.util.LittleEndian; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -57,7 +57,7 @@ public class MemErrPtg array[offset] = (byte) (sid + ptgClass); } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "ERR#"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/MemFuncPtg.java b/src/java/org/apache/poi/hssf/record/formula/MemFuncPtg.java index 89d4cae329..63c07a79e7 100644 --- a/src/java/org/apache/poi/hssf/record/formula/MemFuncPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/MemFuncPtg.java @@ -24,7 +24,7 @@ package org.apache.poi.hssf.record.formula; import org.apache.poi.util.LittleEndian; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -60,7 +60,7 @@ public class MemFuncPtg extends ControlPtg LittleEndian.putShort( array, offset + 1, (short)field_1_len_ref_subexpression ); } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return ""; } diff --git a/src/java/org/apache/poi/hssf/record/formula/MissingArgPtg.java b/src/java/org/apache/poi/hssf/record/formula/MissingArgPtg.java index 17a31a4e6a..d539405cd0 100644 --- a/src/java/org/apache/poi/hssf/record/formula/MissingArgPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/MissingArgPtg.java @@ -17,7 +17,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -55,7 +55,7 @@ public class MissingArgPtg } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return " "; } diff --git a/src/java/org/apache/poi/hssf/record/formula/MultiplyPtg.java b/src/java/org/apache/poi/hssf/record/formula/MultiplyPtg.java index 626eff2b8e..cbc0b67002 100644 --- a/src/java/org/apache/poi/hssf/record/formula/MultiplyPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/MultiplyPtg.java @@ -16,7 +16,7 @@ ==================================================================== */ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -68,7 +68,7 @@ public class MultiplyPtg } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "*"; } @@ -77,9 +77,9 @@ public class MultiplyPtg { StringBuffer buffer = new StringBuffer(); - buffer.append(operands[ 0 ].toFormulaString((Workbook)null)); + buffer.append(operands[ 0 ].toFormulaString((HSSFWorkbook)null)); buffer.append("*"); - buffer.append(operands[ 1 ].toFormulaString((Workbook)null)); + buffer.append(operands[ 1 ].toFormulaString((HSSFWorkbook)null)); return buffer.toString(); } @@ -87,7 +87,7 @@ public class MultiplyPtg StringBuffer buffer = new StringBuffer(); buffer.append(operands[ 0 ]); - buffer.append(toFormulaString((Workbook)null)); + buffer.append(toFormulaString((HSSFWorkbook)null)); buffer.append(operands[ 1 ]); return buffer.toString(); } diff --git a/src/java/org/apache/poi/hssf/record/formula/NamePtg.java b/src/java/org/apache/poi/hssf/record/formula/NamePtg.java index 5405481a09..9d93f1e982 100644 --- a/src/java/org/apache/poi/hssf/record/formula/NamePtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/NamePtg.java @@ -18,7 +18,8 @@ package org.apache.poi.hssf.record.formula; import org.apache.poi.util.LittleEndian; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFName; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.NameRecord; import org.apache.poi.hssf.record.RecordInputStream; @@ -48,26 +49,24 @@ public class NamePtg * in the workbook. The search for the name record is case insensitive. If it is not found, * it gets created. */ - public NamePtg(String name, Workbook book) { + public NamePtg(String name, HSSFWorkbook book) { field_1_label_index = (short)(1+getOrCreateNameRecord(book, name)); // convert to 1-based } /** * @return zero based index of the found or newly created defined name record. */ - private static final int getOrCreateNameRecord(Workbook book, String name) { - // perhaps this logic belongs in Workbook - int countNames = book.getNumNames(); - NameRecord rec; + private static final int getOrCreateNameRecord(HSSFWorkbook book, String name) { + // perhaps this logic belongs in Workbook? + int countNames = book.getNumberOfNames(); for (int i = 0; i < countNames; i++) { - rec = book.getNameRecord(i); - if (name.equalsIgnoreCase(rec.getNameText())) { + if(name.equalsIgnoreCase( book.getNameName(i) )) { return i; } } - rec = new NameRecord(); - rec.setNameText(name); - rec.setNameTextLength((byte) name.length()); - book.addName(rec); + + HSSFName nameObj = book.createName(); + nameObj.setNameName(name); + return countNames; } @@ -100,10 +99,9 @@ public class NamePtg return SIZE; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { - NameRecord rec = book.getNameRecord(field_1_label_index - 1); - return rec.getNameText(); + return book.getNameName(field_1_label_index - 1); } public byte getDefaultOperandClass() {return Ptg.CLASS_REF;} diff --git a/src/java/org/apache/poi/hssf/record/formula/NameXPtg.java b/src/java/org/apache/poi/hssf/record/formula/NameXPtg.java index ccf5ab6fcd..3036800b10 100644 --- a/src/java/org/apache/poi/hssf/record/formula/NameXPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/NameXPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; import org.apache.poi.util.LittleEndian; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -61,7 +61,7 @@ public final class NameXPtg extends Ptg { return SIZE; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { // -1 to convert definedNameIndex from 1-based to zero-based return book.resolveNameXText(field_1_ixals, field_2_ilbl-1); diff --git a/src/java/org/apache/poi/hssf/record/formula/NotEqualPtg.java b/src/java/org/apache/poi/hssf/record/formula/NotEqualPtg.java index 8eea4d8004..5dbbec8754 100755 --- a/src/java/org/apache/poi/hssf/record/formula/NotEqualPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/NotEqualPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -64,7 +64,7 @@ public class NotEqualPtg return 2; } - public String toFormulaString( Workbook book ) + public String toFormulaString( HSSFWorkbook book ) { return "<>"; } @@ -75,7 +75,7 @@ public class NotEqualPtg buffer.append( operands[0] ); - buffer.append( toFormulaString( (Workbook) null ) ); + buffer.append( toFormulaString( (HSSFWorkbook) null ) ); buffer.append( operands[1] ); return buffer.toString(); diff --git a/src/java/org/apache/poi/hssf/record/formula/NumberPtg.java b/src/java/org/apache/poi/hssf/record/formula/NumberPtg.java index 43617f2909..8ec67345b4 100644 --- a/src/java/org/apache/poi/hssf/record/formula/NumberPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/NumberPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; import org.apache.poi.util.LittleEndian; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -78,7 +78,7 @@ public class NumberPtg return SIZE; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "" + getValue(); } diff --git a/src/java/org/apache/poi/hssf/record/formula/ParenthesisPtg.java b/src/java/org/apache/poi/hssf/record/formula/ParenthesisPtg.java index 374458a15d..402dbd3774 100644 --- a/src/java/org/apache/poi/hssf/record/formula/ParenthesisPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/ParenthesisPtg.java @@ -20,7 +20,7 @@ package org.apache.poi.hssf.record.formula; import java.util.List; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -71,7 +71,7 @@ public class ParenthesisPtg return 1; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "()"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/PercentPtg.java b/src/java/org/apache/poi/hssf/record/formula/PercentPtg.java index 9db4d6c43b..0c59bb7acb 100644 --- a/src/java/org/apache/poi/hssf/record/formula/PercentPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/PercentPtg.java @@ -23,7 +23,7 @@ */ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -74,7 +74,7 @@ public class PercentPtg } /** Implementation of method from Ptg */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "%"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/PowerPtg.java b/src/java/org/apache/poi/hssf/record/formula/PowerPtg.java index 73f41fa49c..0dbb3ba283 100644 --- a/src/java/org/apache/poi/hssf/record/formula/PowerPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/PowerPtg.java @@ -19,7 +19,7 @@ package org.apache.poi.hssf.record.formula; import java.util.List; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -66,7 +66,7 @@ public class PowerPtg return 2; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "^"; } @@ -76,7 +76,7 @@ public class PowerPtg buffer.append(operands[ 0 ]); - buffer.append(toFormulaString((Workbook)null)); + buffer.append(toFormulaString((HSSFWorkbook)null)); buffer.append(operands[ 1 ]); return buffer.toString(); } diff --git a/src/java/org/apache/poi/hssf/record/formula/Ptg.java b/src/java/org/apache/poi/hssf/record/formula/Ptg.java index f006509c23..0e8c7741ac 100644 --- a/src/java/org/apache/poi/hssf/record/formula/Ptg.java +++ b/src/java/org/apache/poi/hssf/record/formula/Ptg.java @@ -21,7 +21,7 @@ import java.util.List; import java.util.ArrayList; import java.util.Stack; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -418,7 +418,7 @@ public abstract class Ptg /** * return a string representation of this token alone */ - public abstract String toFormulaString(Workbook book); + public abstract String toFormulaString(HSSFWorkbook book); /** * dump a debug representation (hexdump) to a string */ diff --git a/src/java/org/apache/poi/hssf/record/formula/RangePtg.java b/src/java/org/apache/poi/hssf/record/formula/RangePtg.java index 51df7844a4..4726a70c17 100644 --- a/src/java/org/apache/poi/hssf/record/formula/RangePtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/RangePtg.java @@ -17,7 +17,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -59,7 +59,7 @@ public class RangePtg extends OperationPtg } /** Implementation of method from Ptg */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return ":"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/Ref3DPtg.java b/src/java/org/apache/poi/hssf/record/formula/Ref3DPtg.java index 7fb2c9c43a..f9f5c6e202 100644 --- a/src/java/org/apache/poi/hssf/record/formula/Ref3DPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/Ref3DPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.util.CellReference; import org.apache.poi.hssf.util.RangeAddress; @@ -162,8 +162,8 @@ public class Ref3DPtg extends Ptg { } // TODO - find a home for this method - // There is already a method on Workbook called getSheetName but it seems to do something different. - static String getSheetName(Workbook book, int externSheetIndex) { + // There is already a method on HSSFWorkbook called getSheetName but it seems to do something different. + static String getSheetName(HSSFWorkbook book, int externSheetIndex) { // TODO - there are 3 ways this method can return null. Is each valid? if (book == null) { return null; @@ -179,7 +179,7 @@ public class Ref3DPtg extends Ptg { * @return text representation of this cell reference that can be used in text * formulas. The sheet name will get properly delimited if required. */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { StringBuffer retval = new StringBuffer(); String sheetName = getSheetName(book, field_1_index_extern_sheet); diff --git a/src/java/org/apache/poi/hssf/record/formula/RefErrorPtg.java b/src/java/org/apache/poi/hssf/record/formula/RefErrorPtg.java index 4d655756d4..c29b55bf94 100755 --- a/src/java/org/apache/poi/hssf/record/formula/RefErrorPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/RefErrorPtg.java @@ -21,7 +21,7 @@ import org.apache.poi.util.LittleEndian; import org.apache.poi.util.BitField; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -74,7 +74,7 @@ public class RefErrorPtg extends Ptg return SIZE; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { //TODO -- should we store a cellreference instance in this ptg?? but .. memory is an issue, i believe! return "#REF!"; diff --git a/src/java/org/apache/poi/hssf/record/formula/RefNAPtg.java b/src/java/org/apache/poi/hssf/record/formula/RefNAPtg.java index 4e05e1387d..6f18e4b94e 100644 --- a/src/java/org/apache/poi/hssf/record/formula/RefNAPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/RefNAPtg.java @@ -28,7 +28,7 @@ import org.apache.poi.util.BitField; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * RefNAPtg @@ -57,7 +57,7 @@ public class RefNAPtg extends ReferencePtg return "RefNAPtg"; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { throw new RuntimeException("Coding Error: This method should never be called. This ptg should be converted"); } diff --git a/src/java/org/apache/poi/hssf/record/formula/RefNPtg.java b/src/java/org/apache/poi/hssf/record/formula/RefNPtg.java index e062f0c4e4..e7522e7e5f 100644 --- a/src/java/org/apache/poi/hssf/record/formula/RefNPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/RefNPtg.java @@ -27,7 +27,7 @@ import org.apache.poi.util.BitField; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * RefNPtg @@ -58,7 +58,7 @@ public class RefNPtg extends ReferencePtg return "RefNPtg"; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { throw new RuntimeException("Coding Error: This method should never be called. This ptg should be converted"); } diff --git a/src/java/org/apache/poi/hssf/record/formula/RefNVPtg.java b/src/java/org/apache/poi/hssf/record/formula/RefNVPtg.java index 615a9c0b0a..40b111b3ec 100644 --- a/src/java/org/apache/poi/hssf/record/formula/RefNVPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/RefNVPtg.java @@ -23,7 +23,7 @@ import org.apache.poi.util.BitField; import org.apache.poi.hssf.record.RecordInputStream; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * RefNVPtg @@ -54,7 +54,7 @@ public class RefNVPtg extends ReferencePtg return "RefNVPtg"; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { throw new RuntimeException("Coding Error: This method should never be called. This ptg should be converted"); } diff --git a/src/java/org/apache/poi/hssf/record/formula/ReferencePtg.java b/src/java/org/apache/poi/hssf/record/formula/ReferencePtg.java index 4983c9d070..3df731c7ac 100644 --- a/src/java/org/apache/poi/hssf/record/formula/ReferencePtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/ReferencePtg.java @@ -22,7 +22,7 @@ import org.apache.poi.util.BitField; import org.apache.poi.util.BitFieldFactory; import org.apache.poi.hssf.util.CellReference; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -176,7 +176,7 @@ public class ReferencePtg extends Ptg { return SIZE; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { //TODO -- should we store a cellreference instance in this ptg?? but .. memory is an issue, i believe! return (new CellReference(getRowAsInt(),getColumn(),!isRowRelative(),!isColRelative())).formatAsString(); diff --git a/src/java/org/apache/poi/hssf/record/formula/StringPtg.java b/src/java/org/apache/poi/hssf/record/formula/StringPtg.java index 491b6c6c36..ca6fb55dc6 100644 --- a/src/java/org/apache/poi/hssf/record/formula/StringPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/StringPtg.java @@ -17,7 +17,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.util.BitField; import org.apache.poi.util.BitFieldFactory; import org.apache.poi.util.StringUtil; @@ -109,7 +109,7 @@ public class StringPtg } } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "\""+getValue()+"\""; } diff --git a/src/java/org/apache/poi/hssf/record/formula/SubtractPtg.java b/src/java/org/apache/poi/hssf/record/formula/SubtractPtg.java index 384db9357b..37af74ba9e 100644 --- a/src/java/org/apache/poi/hssf/record/formula/SubtractPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/SubtractPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; import java.util.List; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -63,7 +63,7 @@ public class SubtractPtg return 2; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "-"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/UnaryMinusPtg.java b/src/java/org/apache/poi/hssf/record/formula/UnaryMinusPtg.java index 31efdcd63c..7c134b97d1 100644 --- a/src/java/org/apache/poi/hssf/record/formula/UnaryMinusPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/UnaryMinusPtg.java @@ -19,7 +19,7 @@ package org.apache.poi.hssf.record.formula; import java.util.List; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -69,7 +69,7 @@ public class UnaryMinusPtg extends OperationPtg } /** Implementation of method from Ptg */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "+"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/UnaryPlusPtg.java b/src/java/org/apache/poi/hssf/record/formula/UnaryPlusPtg.java index ce3ba7cf4a..148c83fa41 100644 --- a/src/java/org/apache/poi/hssf/record/formula/UnaryPlusPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/UnaryPlusPtg.java @@ -19,7 +19,7 @@ package org.apache.poi.hssf.record.formula; import java.util.List; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -69,7 +69,7 @@ public class UnaryPlusPtg extends OperationPtg } /** Implementation of method from Ptg */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "+"; } diff --git a/src/java/org/apache/poi/hssf/record/formula/UnionPtg.java b/src/java/org/apache/poi/hssf/record/formula/UnionPtg.java index 40298a0cff..8d00ec34df 100644 --- a/src/java/org/apache/poi/hssf/record/formula/UnionPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/UnionPtg.java @@ -17,7 +17,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -59,7 +59,7 @@ public class UnionPtg extends OperationPtg } /** Implementation of method from Ptg */ - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return ","; } diff --git a/src/java/org/apache/poi/hssf/record/formula/UnknownPtg.java b/src/java/org/apache/poi/hssf/record/formula/UnknownPtg.java index 1badf51970..56493d906a 100644 --- a/src/java/org/apache/poi/hssf/record/formula/UnknownPtg.java +++ b/src/java/org/apache/poi/hssf/record/formula/UnknownPtg.java @@ -16,7 +16,7 @@ ==================================================================== */ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.record.RecordInputStream; /** @@ -51,7 +51,7 @@ public class UnknownPtg return size; } - public String toFormulaString(Workbook book) + public String toFormulaString(HSSFWorkbook book) { return "UNKNOWN"; } diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFBorderFormatting.java b/src/java/org/apache/poi/hssf/usermodel/HSSFBorderFormatting.java index ba2d587624..33e1d3a850 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFBorderFormatting.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFBorderFormatting.java @@ -17,6 +17,7 @@ package org.apache.poi.hssf.usermodel; +import org.apache.poi.hssf.record.CFRuleRecord; import org.apache.poi.hssf.record.cf.BorderFormatting; /** @@ -58,18 +59,15 @@ public final class HSSFBorderFormatting public final static short BORDER_SLANTED_DASH_DOT = BorderFormatting.BORDER_SLANTED_DASH_DOT; + private final CFRuleRecord cfRuleRecord; private final BorderFormatting borderFormatting; - public HSSFBorderFormatting() + protected HSSFBorderFormatting(CFRuleRecord cfRuleRecord) { - borderFormatting = new BorderFormatting(); + this.cfRuleRecord = cfRuleRecord; + this.borderFormatting = cfRuleRecord.getBorderFormatting(); } - protected HSSFBorderFormatting(BorderFormatting borderFormatting) - { - this.borderFormatting = borderFormatting; - } - protected BorderFormatting getBorderFormattingBlock() { return borderFormatting; @@ -138,60 +136,110 @@ public final class HSSFBorderFormatting public void setBackwardDiagonalOn(boolean on) { borderFormatting.setBackwardDiagonalOn(on); + if( on ) + { + cfRuleRecord.setTopLeftBottomRightBorderModified(on); + } } public void setBorderBottom(short border) { borderFormatting.setBorderBottom(border); + if( border != 0) + { + cfRuleRecord.setBottomBorderModified(true); + } } public void setBorderDiagonal(short border) { borderFormatting.setBorderDiagonal(border); + if( border != 0) + { + cfRuleRecord.setBottomLeftTopRightBorderModified(true); + cfRuleRecord.setTopLeftBottomRightBorderModified(true); + } } public void setBorderLeft(short border) { borderFormatting.setBorderLeft(border); + if( border != 0) + { + cfRuleRecord.setLeftBorderModified(true); + } } public void setBorderRight(short border) { borderFormatting.setBorderRight(border); + if( border != 0) + { + cfRuleRecord.setRightBorderModified(true); + } } public void setBorderTop(short border) { borderFormatting.setBorderTop(border); + if( border != 0) + { + cfRuleRecord.setTopBorderModified(true); + } } public void setBottomBorderColor(short color) { borderFormatting.setBottomBorderColor(color); + if( color != 0) + { + cfRuleRecord.setBottomBorderModified(true); + } } public void setDiagonalBorderColor(short color) { borderFormatting.setDiagonalBorderColor(color); + if( color != 0) + { + cfRuleRecord.setBottomLeftTopRightBorderModified(true); + cfRuleRecord.setTopLeftBottomRightBorderModified(true); + } } public void setForwardDiagonalOn(boolean on) { borderFormatting.setForwardDiagonalOn(on); + if( on ) + { + cfRuleRecord.setBottomLeftTopRightBorderModified(on); + } } public void setLeftBorderColor(short color) { borderFormatting.setLeftBorderColor(color); + if( color != 0) + { + cfRuleRecord.setLeftBorderModified(true); + } } public void setRightBorderColor(short color) { borderFormatting.setRightBorderColor(color); + if( color != 0) + { + cfRuleRecord.setRightBorderModified(true); + } } public void setTopBorderColor(short color) { borderFormatting.setTopBorderColor(color); + if( color != 0) + { + cfRuleRecord.setTopBorderModified(true); + } } } diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFCell.java b/src/java/org/apache/poi/hssf/usermodel/HSSFCell.java index 2a605c8a75..0d2cfade4c 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFCell.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFCell.java @@ -118,7 +118,7 @@ public class HSSFCell implements Cell private int cellType; private HSSFRichTextString stringValue; private short encoding = ENCODING_UNCHANGED; - private Workbook book; + private HSSFWorkbook book; private Sheet sheet; private CellValueRecordInterface record; private HSSFComment comment; @@ -141,7 +141,7 @@ public class HSSFCell implements Cell */ //protected HSSFCell(Workbook book, Sheet sheet, short row, short col) - protected HSSFCell(Workbook book, Sheet sheet, int row, short col) + protected HSSFCell(HSSFWorkbook book, Sheet sheet, int row, short col) { checkBounds(col); stringValue = null; @@ -170,7 +170,7 @@ public class HSSFCell implements Cell */ //protected HSSFCell(Workbook book, Sheet sheet, short row, short col, - protected HSSFCell(Workbook book, Sheet sheet, int row, short col, + protected HSSFCell(HSSFWorkbook book, Sheet sheet, int row, short col, int type) { checkBounds(col); @@ -193,7 +193,7 @@ public class HSSFCell implements Cell */ //protected HSSFCell(Workbook book, Sheet sheet, short row, - protected HSSFCell(Workbook book, Sheet sheet, int row, + protected HSSFCell(HSSFWorkbook book, Sheet sheet, int row, CellValueRecordInterface cval) { record = cval; @@ -204,7 +204,7 @@ public class HSSFCell implements Cell switch (cellType) { case CELL_TYPE_STRING : - stringValue = new HSSFRichTextString(book, (LabelSSTRecord ) cval); + stringValue = new HSSFRichTextString(book.getWorkbook(), (LabelSSTRecord ) cval); break; case CELL_TYPE_BLANK : @@ -214,7 +214,7 @@ public class HSSFCell implements Cell stringValue=new HSSFRichTextString(((FormulaRecordAggregate) cval).getStringValue()); break; } - ExtendedFormatRecord xf = book.getExFormatAt(cval.getXFIndex()); + ExtendedFormatRecord xf = book.getWorkbook().getExFormatAt(cval.getXFIndex()); setCellStyle(new HSSFCellStyle(( short ) cval.getXFIndex(), xf, book)); } @@ -270,7 +270,7 @@ public class HSSFCell implements Cell * @return */ protected Workbook getBoundWorkbook() { - return book; + return book.getWorkbook(); } /** @@ -416,9 +416,9 @@ public class HSSFCell implements Cell // jmh { // jmh str.setUncompressedUnicode(); // jmh } - sst = book.addSSTString(str); + sst = book.getWorkbook().addSSTString(str); lrec.setSSTIndex(sst); - getRichStringCellValue().setUnicodeString(book.getSSTString(sst)); + getRichStringCellValue().setUnicodeString(book.getWorkbook().getSSTString(sst)); } } record = lrec; @@ -545,7 +545,7 @@ public class HSSFCell implements Cell */ public void setCellValue(Date value) { - setCellValue(HSSFDateUtil.getExcelDate(value, this.book.isUsing1904DateWindowing())); + setCellValue(HSSFDateUtil.getExcelDate(value, this.book.getWorkbook().isUsing1904DateWindowing())); } /** @@ -565,7 +565,7 @@ public class HSSFCell implements Cell */ public void setCellValue(Calendar value) { - setCellValue( HSSFDateUtil.getExcelDate(value, this.book.isUsing1904DateWindowing()) ); + setCellValue( HSSFDateUtil.getExcelDate(value, this.book.getWorkbook().isUsing1904DateWindowing()) ); } /** @@ -623,11 +623,11 @@ public class HSSFCell implements Cell int index = 0; UnicodeString str = hvalue.getUnicodeString(); - index = book.addSSTString(str); + index = book.getWorkbook().addSSTString(str); (( LabelSSTRecord ) record).setSSTIndex(index); stringValue = hvalue; - stringValue.setWorkbookReferences(book, (( LabelSSTRecord ) record)); - stringValue.setUnicodeString(book.getSSTString(index)); + stringValue.setWorkbookReferences(book.getWorkbook(), (( LabelSSTRecord ) record)); + stringValue.setUnicodeString(book.getWorkbook().getSSTString(index)); } public void setCellFormula(String formula) { @@ -737,7 +737,7 @@ public class HSSFCell implements Cell "You cannot get a date value from an error cell"); } double value=this.getNumericCellValue(); - if (book.isUsing1904DateWindowing()) { + if (book.getWorkbook().isUsing1904DateWindowing()) { return HSSFDateUtil.getJavaDate(value,true); } else { @@ -922,7 +922,7 @@ public class HSSFCell implements Cell public HSSFCellStyle getCellStyle() { short styleIndex=record.getXFIndex(); - ExtendedFormatRecord xf = book.getExFormatAt(styleIndex); + ExtendedFormatRecord xf = book.getWorkbook().getExFormatAt(styleIndex); return new HSSFCellStyle(styleIndex, xf, book); } diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFConditionalFormatting.java b/src/java/org/apache/poi/hssf/usermodel/HSSFConditionalFormatting.java index 6a08c4b304..53706b58a6 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFConditionalFormatting.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFConditionalFormatting.java @@ -16,7 +16,6 @@ ==================================================================== */ package org.apache.poi.hssf.usermodel; -import org.apache.poi.hssf.model.Workbook; import org.apache.poi.hssf.record.CFHeaderRecord; import org.apache.poi.hssf.record.CFRuleRecord; import org.apache.poi.hssf.record.aggregates.CFRecordsAggregate; @@ -50,52 +49,46 @@ import org.apache.poi.ss.util.Region; * To create a new Conditional Formatting set use the following approach: * * <PRE> + * + * // Define a Conditional Formatting rule, which triggers formatting + * // when cell's value is greater or equal than 100.0 and + * // applies patternFormatting defined below. + * HSSFConditionalFormattingRule rule = sheet.createConditionalFormattingRule( + * ComparisonOperator.GE, + * "100.0", // 1st formula + * null // 2nd formula is not used for comparison operator GE + * ); + * * // Create pattern with red background - * HSSFPatternFormatting patternFormatting = new HSSFPatternFormatting(); + * HSSFPatternFormatting patternFmt = rule.cretePatternFormatting(); * patternFormatting.setFillBackgroundColor(HSSFColor.RED.index); * + * // Define a region containing first column * Region [] regions = * { - * // Define a region containing first column * new Region(1,(short)1,-1,(short)1) * }; * - * HSSFConditionalFormattingRule[] rules = - * { - * // Define a Conditional Formatting rule, which triggers formatting - * // when cell's value is greater or equal than 100.0 and - * // applies patternFormatting defined above. - * - * sheet.createConditionalFormattingRule( - * HSSFConditionalFormattingRule.COMPARISON_OPERATOR_GE, - * "100.0", // 1st formula - * null, // 2nd formula is not used for comparison operator GE - * null, // do not override Font Formatting - * null, // do not override Border Formatting - * patternFormatting - * ) - * }; - * - * // Apply Conditional Formatting rules defined above to the regions - * sheet.addConditionalFormatting(regions, rules); + * // Apply Conditional Formatting rule defined above to the regions + * sheet.addConditionalFormatting(regions, rule); * </PRE> * * @author Dmitriy Kumshayev */ public final class HSSFConditionalFormatting { - private final Workbook workbook; + private final HSSFWorkbook _workbook; private final CFRecordsAggregate cfAggregate; - HSSFConditionalFormatting(HSSFSheet sheet, CFRecordsAggregate cfAggregate) + HSSFConditionalFormatting(HSSFWorkbook workbook, CFRecordsAggregate cfAggregate) { - if(sheet == null) { - throw new IllegalArgumentException("sheet must not be null"); + if(workbook == null) { + throw new IllegalArgumentException("workbook must not be null"); } if(cfAggregate == null) { throw new IllegalArgumentException("cfAggregate must not be null"); } - workbook = sheet.workbook.getWorkbook(); + _workbook = workbook; this.cfAggregate = cfAggregate; } CFRecordsAggregate getCFRecordsAggregate() { @@ -141,7 +134,7 @@ public final class HSSFConditionalFormatting public HSSFConditionalFormattingRule getRule(int idx) { CFRuleRecord ruleRecord = cfAggregate.getRule(idx); - return new HSSFConditionalFormattingRule(workbook, ruleRecord); + return new HSSFConditionalFormattingRule(_workbook, ruleRecord); } /** diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFConditionalFormattingRule.java b/src/java/org/apache/poi/hssf/usermodel/HSSFConditionalFormattingRule.java index 490ff4d342..1d4100655a 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFConditionalFormattingRule.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFConditionalFormattingRule.java @@ -18,7 +18,6 @@ package org.apache.poi.hssf.usermodel; import org.apache.poi.hssf.model.FormulaParser; -import org.apache.poi.hssf.model.Workbook; import org.apache.poi.hssf.record.CFRuleRecord; import org.apache.poi.hssf.record.CFRuleRecord.ComparisonOperator; import org.apache.poi.hssf.record.cf.BorderFormatting; @@ -40,33 +39,36 @@ public final class HSSFConditionalFormattingRule private static final byte CELL_COMPARISON = CFRuleRecord.CONDITION_TYPE_CELL_VALUE_IS; private final CFRuleRecord cfRuleRecord; - private final Workbook workbook; + private final HSSFWorkbook workbook; - HSSFConditionalFormattingRule(Workbook pWorkbook, CFRuleRecord pRuleRecord) { + HSSFConditionalFormattingRule(HSSFWorkbook pWorkbook, CFRuleRecord pRuleRecord) { workbook = pWorkbook; cfRuleRecord = pRuleRecord; } - HSSFConditionalFormattingRule(Workbook pWorkbook, CFRuleRecord pRuleRecord, - HSSFFontFormatting fontFmt, HSSFBorderFormatting bordFmt, HSSFPatternFormatting patternFmt) { - this(pWorkbook, pRuleRecord); - setFontFormatting(fontFmt); - setBorderFormatting(bordFmt); - setPatternFormatting(patternFmt); - } CFRuleRecord getCfRuleRecord() { return cfRuleRecord; } - - /** - * @param fontFmt pass <code>null</code> to signify 'font unchanged' - */ - public void setFontFormatting(HSSFFontFormatting fontFmt) + private HSSFFontFormatting getFontFormatting(boolean create) { - FontFormatting block = fontFmt==null ? null : fontFmt.getFontFormattingBlock(); - cfRuleRecord.setFontFormatting(block); + FontFormatting fontFormatting = cfRuleRecord.getFontFormatting(); + if ( fontFormatting != null) + { + cfRuleRecord.setFontFormatting(fontFormatting); + return new HSSFFontFormatting(cfRuleRecord); + } + else if( create ) + { + fontFormatting = new FontFormatting(); + cfRuleRecord.setFontFormatting(fontFormatting); + return new HSSFFontFormatting(cfRuleRecord); + } + else + { + return null; + } } /** @@ -74,50 +76,89 @@ public final class HSSFConditionalFormattingRule */ public HSSFFontFormatting getFontFormatting() { - FontFormatting ff = cfRuleRecord.getFontFormatting(); - if ( ff == null ) { - return null; - } - return new HSSFFontFormatting(ff); + return getFontFormatting(false); } - /** - * @param borderFmt pass <code>null</code> to signify 'border unchanged' + * create a new font formatting structure if it does not exist, + * otherwise just return existing object. + * @return - font formatting object, never returns <code>null</code>. */ - public void setBorderFormatting(HSSFBorderFormatting borderFmt) + public HSSFFontFormatting createFontFormatting() + { + return getFontFormatting(true); + } + + private HSSFBorderFormatting getBorderFormatting(boolean create) { - BorderFormatting block = borderFmt==null ? null : borderFmt.getBorderFormattingBlock(); - cfRuleRecord.setBorderFormatting(block); + BorderFormatting borderFormatting = cfRuleRecord.getBorderFormatting(); + if ( borderFormatting != null) + { + cfRuleRecord.setBorderFormatting(borderFormatting); + return new HSSFBorderFormatting(cfRuleRecord); + } + else if( create ) + { + borderFormatting = new BorderFormatting(); + cfRuleRecord.setBorderFormatting(borderFormatting); + return new HSSFBorderFormatting(cfRuleRecord); + } + else + { + return null; + } } /** * @return - border formatting object if defined, <code>null</code> otherwise */ public HSSFBorderFormatting getBorderFormatting() { - BorderFormatting bf = cfRuleRecord.getBorderFormatting(); - if ( bf == null ) { - return null; - } - return new HSSFBorderFormatting(bf); + return getBorderFormatting(false); } /** - * @param patternFmt pass <code>null</code> to signify 'pattern unchanged' + * create a new border formatting structure if it does not exist, + * otherwise just return existing object. + * @return - border formatting object, never returns <code>null</code>. */ - public void setPatternFormatting(HSSFPatternFormatting patternFmt) + public HSSFBorderFormatting createBorderFormatting() { - PatternFormatting block = patternFmt==null ? null : patternFmt.getPatternFormattingBlock(); - cfRuleRecord.setPatternFormatting(block); + return getBorderFormatting(true); } + + private HSSFPatternFormatting getPatternFormatting(boolean create) + { + PatternFormatting patternFormatting = cfRuleRecord.getPatternFormatting(); + if ( patternFormatting != null) + { + cfRuleRecord.setPatternFormatting(patternFormatting); + return new HSSFPatternFormatting(cfRuleRecord); + } + else if( create ) + { + patternFormatting = new PatternFormatting(); + cfRuleRecord.setPatternFormatting(patternFormatting); + return new HSSFPatternFormatting(cfRuleRecord); + } + else + { + return null; + } + } + /** * @return - pattern formatting object if defined, <code>null</code> otherwise */ public HSSFPatternFormatting getPatternFormatting() { - PatternFormatting pf = cfRuleRecord.getPatternFormatting(); - if ( pf == null ) { - return null; - } - return new HSSFPatternFormatting(pf); + return getPatternFormatting(false); + } + /** + * create a new pattern formatting structure if it does not exist, + * otherwise just return existing object. + * @return - pattern formatting object, never returns <code>null</code>. + */ + public HSSFPatternFormatting createPatternFormatting() + { + return getPatternFormatting(true); } public String getFormula1() diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFFontFormatting.java b/src/java/org/apache/poi/hssf/usermodel/HSSFFontFormatting.java index a701eb63af..774bc1ea4d 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFFontFormatting.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFFontFormatting.java @@ -17,6 +17,7 @@ package org.apache.poi.hssf.usermodel; +import org.apache.poi.hssf.record.CFRuleRecord; import org.apache.poi.hssf.record.cf.FontFormatting; /** * High level representation for Font Formatting component @@ -33,28 +34,23 @@ public final class HSSFFontFormatting public final static short SS_SUPER = FontFormatting.SS_SUPER; /** Escapement type - Subscript */ public final static short SS_SUB = FontFormatting.SS_SUB; - + /** Underline type - None */ public final static byte U_NONE = FontFormatting.U_NONE; - /** Underline type - Single */ + /** Underline type - Single */ public final static byte U_SINGLE = FontFormatting.U_SINGLE; - /** Underline type - Double */ + /** Underline type - Double */ public final static byte U_DOUBLE = FontFormatting.U_DOUBLE; /** Underline type - Single Accounting */ public final static byte U_SINGLE_ACCOUNTING = FontFormatting.U_SINGLE_ACCOUNTING; - /** Underline type - Double Accounting */ + /** Underline type - Double Accounting */ public final static byte U_DOUBLE_ACCOUNTING = FontFormatting.U_DOUBLE_ACCOUNTING; - + private final FontFormatting fontFormatting; - public HSSFFontFormatting() - { - fontFormatting = new FontFormatting(); - } - - protected HSSFFontFormatting(FontFormatting ff) + protected HSSFFontFormatting(CFRuleRecord cfRuleRecord) { - fontFormatting = ff; + this.fontFormatting = cfRuleRecord.getFontFormatting(); } protected FontFormatting getFontFormattingBlock() diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFFormulaEvaluator.java b/src/java/org/apache/poi/hssf/usermodel/HSSFFormulaEvaluator.java index 3da5f96882..57ec250038 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFFormulaEvaluator.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFFormulaEvaluator.java @@ -20,12 +20,8 @@ package org.apache.poi.hssf.usermodel; import org.apache.poi.hssf.model.FormulaParser; import org.apache.poi.hssf.record.formula.OperationPtg; import org.apache.poi.hssf.record.formula.Ptg; -import org.apache.poi.ss.usermodel.Cell; -import org.apache.poi.ss.usermodel.CreationHelper; import org.apache.poi.ss.usermodel.FormulaEvaluator; -import org.apache.poi.ss.usermodel.Sheet; import org.apache.poi.ss.usermodel.Workbook; -import org.apache.poi.ss.usermodel.FormulaEvaluator.CellValue; /** * @author Amol S. Deshmukh < amolweb at ya hoo dot com > @@ -44,7 +40,7 @@ public class HSSFFormulaEvaluator extends FormulaEvaluator { * formula evaluated. */ public static FormulaParser getUnderlyingParser(HSSFWorkbook workbook, String formula) { - return new FormulaParser(formula, workbook.getWorkbook()); + return new FormulaParser(formula, workbook); } @@ -57,7 +53,7 @@ public class HSSFFormulaEvaluator extends FormulaEvaluator { */ void inspectPtgs(String formula) { HSSFWorkbook hssfWb = (HSSFWorkbook)workbook; - FormulaParser fp = new FormulaParser(formula, hssfWb.getWorkbook()); + FormulaParser fp = new FormulaParser(formula, hssfWb); fp.parse(); Ptg[] ptgs = fp.getRPNPtg(); System.out.println("<ptg-group>"); diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFName.java b/src/java/org/apache/poi/hssf/usermodel/HSSFName.java index 501373e35f..4152e3ae19 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFName.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFName.java @@ -29,7 +29,7 @@ import org.apache.poi.ss.usermodel.Name; */ public class HSSFName implements Name { - private Workbook book; + private HSSFWorkbook book; private NameRecord name; /** Creates new HSSFName - called by HSSFWorkbook to create a sheet from @@ -40,7 +40,7 @@ public class HSSFName implements Name { * @param book lowlevel Workbook object associated with the sheet. */ - protected HSSFName(Workbook book, NameRecord name) { + protected HSSFName(HSSFWorkbook book, NameRecord name) { this.book = book; this.name = name; } @@ -53,7 +53,7 @@ public class HSSFName implements Name { String result ; short indexToExternSheet = name.getExternSheetNumber(); - result = book.findSheetNameFromExternSheet(indexToExternSheet); + result = book.getWorkbook().findSheetNameFromExternSheet(indexToExternSheet); return result; } @@ -77,11 +77,12 @@ public class HSSFName implements Name { public void setNameName(String nameName){ name.setNameText(nameName); name.setNameTextLength((byte)nameName.length()); + Workbook wb = book.getWorkbook(); //Check to ensure no other names have the same case-insensitive name - for ( int i = book.getNumNames()-1; i >=0; i-- ) + for ( int i = wb.getNumNames()-1; i >=0; i-- ) { - NameRecord rec = book.getNameRecord(i); + NameRecord rec = wb.getNameRecord(i); if (rec != name) { if (rec.getNameText().equalsIgnoreCase(getNameName())) throw new IllegalArgumentException("The workbook already contains this name (case-insensitive)"); @@ -111,7 +112,7 @@ public class HSSFName implements Name { private void setSheetName(String sheetName){ int sheetNumber = book.getSheetIndex(sheetName); - short externSheetNumber = book.checkExternSheet(sheetNumber); + short externSheetNumber = book.getExternalSheetIndex(sheetNumber); name.setExternSheetNumber(externSheetNumber); // name.setIndexToSheet(externSheetNumber); diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFPatternFormatting.java b/src/java/org/apache/poi/hssf/usermodel/HSSFPatternFormatting.java index b94d19601a..cb1ae9365e 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFPatternFormatting.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFPatternFormatting.java @@ -17,6 +17,7 @@ package org.apache.poi.hssf.usermodel; +import org.apache.poi.hssf.record.CFRuleRecord; import org.apache.poi.hssf.record.cf.PatternFormatting; /** @@ -66,15 +67,13 @@ public class HSSFPatternFormatting /** Least Dots */ public final static short LEAST_DOTS = PatternFormatting.LEAST_DOTS; - private PatternFormatting patternFormatting; + private final CFRuleRecord cfRuleRecord; + private final PatternFormatting patternFormatting; - public HSSFPatternFormatting() + protected HSSFPatternFormatting(CFRuleRecord cfRuleRecord) { - patternFormatting = new PatternFormatting(); - } - protected HSSFPatternFormatting(PatternFormatting patternFormatting) - { - this.patternFormatting = patternFormatting; + this.cfRuleRecord = cfRuleRecord; + this.patternFormatting = cfRuleRecord.getPatternFormatting(); } protected PatternFormatting getPatternFormattingBlock() @@ -116,6 +115,10 @@ public class HSSFPatternFormatting public void setFillBackgroundColor(short bg) { patternFormatting.setFillBackgroundColor(bg); + if( bg != 0) + { + cfRuleRecord.setPatternBackgroundColorModified(true); + } } /** @@ -125,6 +128,10 @@ public class HSSFPatternFormatting public void setFillForegroundColor(short fg) { patternFormatting.setFillForegroundColor(fg); + if( fg != 0) + { + cfRuleRecord.setPatternColorModified(true); + } } /** @@ -134,5 +141,9 @@ public class HSSFPatternFormatting public void setFillPattern(short fp) { patternFormatting.setFillPattern(fp); + if( fp != 0) + { + cfRuleRecord.setPatternStyleModified(true); + } } } diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFRow.java b/src/java/org/apache/poi/hssf/usermodel/HSSFRow.java index 06a704d7f0..5a154c6fac 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFRow.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFRow.java @@ -55,7 +55,7 @@ public final class HSSFRow implements Comparable, Row { * reference to containing low level Workbook */ - private Workbook book; + private HSSFWorkbook book; /** * reference to containing Sheet @@ -77,7 +77,7 @@ public final class HSSFRow implements Comparable, Row { */ //protected HSSFRow(Workbook book, Sheet sheet, short rowNum) - protected HSSFRow(Workbook book, Sheet sheet, int rowNum) + protected HSSFRow(HSSFWorkbook book, Sheet sheet, int rowNum) { this.rowNum = rowNum; this.book = book; @@ -101,7 +101,7 @@ public final class HSSFRow implements Comparable, Row { * @see org.apache.poi.hssf.usermodel.HSSFSheet#createRow(int) */ - protected HSSFRow(Workbook book, Sheet sheet, RowRecord record) + protected HSSFRow(HSSFWorkbook book, Sheet sheet, RowRecord record) { this.book = book; this.sheet = sheet; diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFSheet.java b/src/java/org/apache/poi/hssf/usermodel/HSSFSheet.java index 992a0f5ee7..230d4bea38 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFSheet.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFSheet.java @@ -49,7 +49,6 @@ import org.apache.poi.hssf.record.SCLRecord; import org.apache.poi.hssf.record.VCenterRecord; import org.apache.poi.hssf.record.WSBoolRecord; import org.apache.poi.hssf.record.WindowTwoRecord; -import org.apache.poi.hssf.record.aggregates.CFRecordsAggregate; import org.apache.poi.hssf.record.formula.Ptg; import org.apache.poi.hssf.record.formula.ReferencePtg; import org.apache.poi.hssf.util.HSSFCellRangeAddress; @@ -210,7 +209,7 @@ public class HSSFSheet implements org.apache.poi.ss.usermodel.Sheet */ public HSSFRow createRow(int rownum) { - HSSFRow row = new HSSFRow(book, sheet, rownum); + HSSFRow row = new HSSFRow(workbook, sheet, rownum); addRow(row, true); return row; @@ -225,7 +224,7 @@ public class HSSFSheet implements org.apache.poi.ss.usermodel.Sheet private HSSFRow createRowFromRecord(RowRecord row) { - HSSFRow hrow = new HSSFRow(book, sheet, row); + HSSFRow hrow = new HSSFRow(workbook, sheet, row); addRow(hrow, false); return hrow; @@ -411,7 +410,7 @@ public class HSSFSheet implements org.apache.poi.ss.usermodel.Sheet //formula fields ( size and data ) String str_formula = obj_validation.getFirstFormula(); - FormulaParser fp = new FormulaParser(str_formula, book); + FormulaParser fp = new FormulaParser(str_formula, workbook); fp.parse(); Stack ptg_arr = new Stack(); Ptg[] ptg = fp.getRPNPtg(); @@ -435,7 +434,7 @@ public class HSSFSheet implements org.apache.poi.ss.usermodel.Sheet if ( obj_validation.getSecondFormula() != null ) { str_formula = obj_validation.getSecondFormula(); - fp = new FormulaParser(str_formula, book); + fp = new FormulaParser(str_formula, workbook); fp.parse(); ptg_arr = new Stack(); ptg = fp.getRPNPtg(); @@ -1281,7 +1280,7 @@ public class HSSFSheet implements org.apache.poi.ss.usermodel.Sheet // Since it's a formula cell, process the // formula string, and look to see if // it contains any references - FormulaParser fp = new FormulaParser(c.getCellFormula(), workbook.getWorkbook()); + FormulaParser fp = new FormulaParser(c.getCellFormula(), workbook); fp.parse(); // Look for references, and update if needed @@ -1856,137 +1855,7 @@ public class HSSFSheet implements org.apache.poi.ss.usermodel.Sheet return null; } - - /** - * A factory method allowing to create a conditional formatting rule - * with a cell comparison operator and - * formatting rules such as font format, border format and pattern format - * - * @param comparisonOperation - a constant value from - * <tt>{@link HSSFConditionalFormattingRule.ComparisonOperator}</tt>: <p> - * <ul> - * <li>BETWEEN</li> - * <li>NOT_BETWEEN</li> - * <li>EQUAL</li> - * <li>NOT_EQUAL</li> - * <li>GT</li> - * <li>LT</li> - * <li>GE</li> - * <li>LE</li> - * </ul> - * </p> - * @param formula1 - formula for the valued, compared with the cell - * @param formula2 - second formula (only used with - * {@link HSSFConditionalFormattingRule#COMPARISON_OPERATOR_BETWEEN}) and - * {@link HSSFConditionalFormattingRule#COMPARISON_OPERATOR_NOT_BETWEEN} operations) - * @param fontFmt - font formatting rules (may be <code>null</code>) - * @param bordFmt - border formatting rules (may be <code>null</code>) - * @param patternFmt - pattern formatting rules (may be <code>null</code>) - */ - public HSSFConditionalFormattingRule createConditionalFormattingRule( - byte comparisonOperation, - String formula1, - String formula2, - HSSFFontFormatting fontFmt, - HSSFBorderFormatting bordFmt, - HSSFPatternFormatting patternFmt) { - - Workbook wb = workbook.getWorkbook(); - CFRuleRecord rr = CFRuleRecord.create(wb, comparisonOperation, formula1, formula2); - return new HSSFConditionalFormattingRule(wb, rr, fontFmt, bordFmt, patternFmt); - } - - /** - * A factory method allowing to create a conditional formatting rule with a formula - * and formatting rules such as font format, border format and pattern format. <br> - * - * The formatting rules are applied by Excel when the value of the formula not equal to 0. - * - * @param formula - formula for the valued, compared with the cell - * @param fontFmt - font formatting rules (may be <code>null</code>) - * @param bordFmt - border formatting rules (may be <code>null</code>) - * @param patternFmt - pattern formatting rules (may be <code>null</code>) - */ - public HSSFConditionalFormattingRule createConditionalFormattingRule( - String formula, - HSSFFontFormatting fontFmt, - HSSFBorderFormatting bordFmt, - HSSFPatternFormatting patternFmt) { - Workbook wb = workbook.getWorkbook(); - CFRuleRecord rr = CFRuleRecord.create(wb, formula); - return new HSSFConditionalFormattingRule(wb, rr, fontFmt, bordFmt, patternFmt); - } - - /** - * Adds a copy of HSSFConditionalFormatting object to the sheet - * <p>This method could be used to copy HSSFConditionalFormatting object - * from one sheet to another. For example: - * <pre> - * HSSFConditionalFormatting cf = sheet.getConditionalFormattingAt(index); - * newSheet.addConditionalFormatting(cf); - * </pre> - * - * @param cf HSSFConditionalFormatting object - * @return index of the new Conditional Formatting object - */ - public int addConditionalFormatting( HSSFConditionalFormatting cf ) { - CFRecordsAggregate cfraClone = cf.getCFRecordsAggregate().cloneCFAggregate(); - - return sheet.addConditionalFormatting(cfraClone); - } - - /** - * Allows to add a new Conditional Formatting set to the sheet. - * - * @param regions - list of rectangular regions to apply conditional formatting rules - * @param hcfRules - set of up to three conditional formatting rules - * - * @return index of the newly created Conditional Formatting object - */ - - public int addConditionalFormatting(Region [] regions, HSSFConditionalFormattingRule [] hcfRules) { - if (regions == null) { - throw new IllegalArgumentException("regions must not be null"); - } - if (hcfRules == null) { - throw new IllegalArgumentException("hcfRules must not be null"); - } - - CFRuleRecord[] rules = new CFRuleRecord[hcfRules.length]; - for (int i = 0; i != hcfRules.length; i++) { - rules[i] = hcfRules[i].getCfRuleRecord(); - } - CFRecordsAggregate cfra = new CFRecordsAggregate(regions, rules); - return sheet.addConditionalFormatting(cfra); - } - - /** - * gets Conditional Formatting object at a particular index - * - * @param index - * of the Conditional Formatting object to fetch - * @return Conditional Formatting object - */ - public HSSFConditionalFormatting getConditionalFormattingAt(int index) { - CFRecordsAggregate cf = sheet.getCFRecordsAggregateAt(index); - if (cf == null) { - return null; - } - return new HSSFConditionalFormatting(this,cf); - } - - /** - * @return number of Conditional Formatting objects of the sheet - */ - public int getNumConditionalFormattings() { - return sheet.getNumConditionalFormattings(); - } - - /** - * removes a Conditional Formatting object by index - * @param index of a Conditional Formatting object to remove - */ - public void removeConditionalFormatting(int index) { - sheet.removeConditionalFormatting(index); + public HSSFSheetConditionalFormatting getSheetConditionalFormatting() { + return new HSSFSheetConditionalFormatting(workbook, sheet); } } diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFSheetConditionalFormatting.java b/src/java/org/apache/poi/hssf/usermodel/HSSFSheetConditionalFormatting.java new file mode 100644 index 0000000000..c042456a4f --- /dev/null +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFSheetConditionalFormatting.java @@ -0,0 +1,196 @@ +/* ====================================================================
+ 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;
+
+import org.apache.poi.hssf.model.Sheet;
+import org.apache.poi.hssf.record.CFRuleRecord;
+import org.apache.poi.hssf.record.aggregates.CFRecordsAggregate;
+import org.apache.poi.ss.util.Region;
+
+/**
+ * The 'Conditional Formatting' facet of <tt>HSSFSheet</tt>
+ *
+ * @author Dmitriy Kumshayev
+ */
+public final class HSSFSheetConditionalFormatting {
+
+ private final HSSFWorkbook _workbook;
+ private final Sheet _sheet;
+
+ /* package */ HSSFSheetConditionalFormatting(HSSFWorkbook workbook, Sheet sheet) {
+ _workbook = workbook;
+ _sheet = sheet;
+ }
+
+ /**
+ * A factory method allowing to create a conditional formatting rule
+ * with a cell comparison operator
+ *
+ * @param comparisonOperation - a constant value from
+ * <tt>{@link HSSFConditionalFormattingRule.ComparisonOperator}</tt>: <p>
+ * <ul>
+ * <li>BETWEEN</li>
+ * <li>NOT_BETWEEN</li>
+ * <li>EQUAL</li>
+ * <li>NOT_EQUAL</li>
+ * <li>GT</li>
+ * <li>LT</li>
+ * <li>GE</li>
+ * <li>LE</li>
+ * </ul>
+ * </p>
+ * @param formula1 - formula for the valued, compared with the cell
+ * @param formula2 - second formula (only used with
+ * {@link HSSFConditionalFormattingRule#COMPARISON_OPERATOR_BETWEEN}) and
+ * {@link HSSFConditionalFormattingRule#COMPARISON_OPERATOR_NOT_BETWEEN} operations)
+ */
+ public HSSFConditionalFormattingRule createConditionalFormattingRule(
+ byte comparisonOperation,
+ String formula1,
+ String formula2) {
+
+ HSSFWorkbook wb = _workbook;
+ CFRuleRecord rr = CFRuleRecord.create(wb, comparisonOperation, formula1, formula2);
+ return new HSSFConditionalFormattingRule(wb, rr);
+ }
+
+ /**
+ * A factory method allowing to create a conditional formatting rule with a formula.<br>
+ *
+ * The formatting rules are applied by Excel when the value of the formula not equal to 0.
+ *
+ * @param formula - formula for the valued, compared with the cell
+ */
+ public HSSFConditionalFormattingRule createConditionalFormattingRule(String formula) {
+ HSSFWorkbook wb = _workbook;
+ CFRuleRecord rr = CFRuleRecord.create(wb, formula);
+ return new HSSFConditionalFormattingRule(wb, rr);
+ }
+
+ /**
+ * Adds a copy of HSSFConditionalFormatting object to the sheet
+ * <p>This method could be used to copy HSSFConditionalFormatting object
+ * from one sheet to another. For example:
+ * <pre>
+ * HSSFConditionalFormatting cf = sheet.getConditionalFormattingAt(index);
+ * newSheet.addConditionalFormatting(cf);
+ * </pre>
+ *
+ * @param cf HSSFConditionalFormatting object
+ * @return index of the new Conditional Formatting object
+ */
+ public int addConditionalFormatting( HSSFConditionalFormatting cf ) {
+ CFRecordsAggregate cfraClone = cf.getCFRecordsAggregate().cloneCFAggregate();
+
+ return _sheet.addConditionalFormatting(cfraClone);
+ }
+
+ /**
+ * Allows to add a new Conditional Formatting set to the sheet.
+ *
+ * @param regions - list of rectangular regions to apply conditional formatting rules
+ * @param cfRules - set of up to three conditional formatting rules
+ *
+ * @return index of the newly created Conditional Formatting object
+ */
+
+ public int addConditionalFormatting(Region[] regions, HSSFConditionalFormattingRule[] cfRules) {
+ if (regions == null) {
+ throw new IllegalArgumentException("regions must not be null");
+ }
+ if (cfRules == null) {
+ throw new IllegalArgumentException("cfRules must not be null");
+ }
+ if (cfRules.length == 0) {
+ throw new IllegalArgumentException("cfRules must not be empty");
+ }
+ if (cfRules.length > 3) {
+ throw new IllegalArgumentException("Number of rules must not exceed 3");
+ }
+
+ CFRuleRecord[] rules = new CFRuleRecord[cfRules.length];
+ for (int i = 0; i != cfRules.length; i++) {
+ rules[i] = cfRules[i].getCfRuleRecord();
+ }
+ CFRecordsAggregate cfra = new CFRecordsAggregate(regions, rules);
+ return _sheet.addConditionalFormatting(cfra);
+ }
+
+ public int addConditionalFormatting(Region[] regions,
+ HSSFConditionalFormattingRule rule1)
+ {
+ return addConditionalFormatting(regions,
+ new HSSFConditionalFormattingRule[]
+ {
+ rule1
+ });
+ }
+
+ public int addConditionalFormatting(Region[] regions,
+ HSSFConditionalFormattingRule rule1,
+ HSSFConditionalFormattingRule rule2)
+ {
+ return addConditionalFormatting(regions,
+ new HSSFConditionalFormattingRule[]
+ {
+ rule1, rule2
+ });
+ }
+
+ public int addConditionalFormatting(Region[] regions,
+ HSSFConditionalFormattingRule rule1,
+ HSSFConditionalFormattingRule rule2,
+ HSSFConditionalFormattingRule rule3)
+ {
+ return addConditionalFormatting(regions,
+ new HSSFConditionalFormattingRule[]
+ {
+ rule1, rule2, rule3
+ });
+ }
+
+ /**
+ * gets Conditional Formatting object at a particular index
+ *
+ * @param index
+ * of the Conditional Formatting object to fetch
+ * @return Conditional Formatting object
+ */
+ public HSSFConditionalFormatting getConditionalFormattingAt(int index) {
+ CFRecordsAggregate cf = _sheet.getCFRecordsAggregateAt(index);
+ if (cf == null) {
+ return null;
+ }
+ return new HSSFConditionalFormatting(_workbook, cf);
+ }
+
+ /**
+ * @return number of Conditional Formatting objects of the sheet
+ */
+ public int getNumConditionalFormattings() {
+ return _sheet.getNumConditionalFormattings();
+ }
+
+ /**
+ * removes a Conditional Formatting object by index
+ * @param index of a Conditional Formatting object to remove
+ */
+ public void removeConditionalFormatting(int index) {
+ _sheet.removeConditionalFormatting(index);
+ }
+}
diff --git a/src/java/org/apache/poi/hssf/usermodel/HSSFWorkbook.java b/src/java/org/apache/poi/hssf/usermodel/HSSFWorkbook.java index 57f44148b8..4135694830 100644 --- a/src/java/org/apache/poi/hssf/usermodel/HSSFWorkbook.java +++ b/src/java/org/apache/poi/hssf/usermodel/HSSFWorkbook.java @@ -62,6 +62,7 @@ import org.apache.poi.hssf.record.formula.Area3DPtg; import org.apache.poi.hssf.record.formula.MemFuncPtg; import org.apache.poi.hssf.record.formula.UnionPtg; import org.apache.poi.hssf.util.CellReference; +import org.apache.poi.hssf.util.SheetReferences; import org.apache.poi.poifs.filesystem.DirectoryNode; import org.apache.poi.poifs.filesystem.POIFSFileSystem; import org.apache.poi.ss.usermodel.CreationHelper; @@ -266,7 +267,7 @@ public class HSSFWorkbook extends POIDocument implements org.apache.poi.ss.userm } for (int i = 0 ; i < workbook.getNumNames() ; ++i){ - HSSFName name = new HSSFName(workbook, workbook.getNameRecord(i)); + HSSFName name = new HSSFName(this, workbook.getNameRecord(i)); names.add(name); } } @@ -539,6 +540,17 @@ public class HSSFWorkbook extends POIDocument implements org.apache.poi.ss.userm } return -1; } + + /** + * Returns the external sheet index of the sheet + * with the given internal index, creating one + * if needed. + * Used by some of the more obscure formula and + * named range things. + */ + public short getExternalSheetIndex(int internalSheetIndex) { + return workbook.checkExternSheet(internalSheetIndex); + } /** * create an HSSFSheet for this HSSFWorkbook, adds it to the sheets and returns @@ -668,6 +680,10 @@ public class HSSFWorkbook extends POIDocument implements org.apache.poi.ss.userm } return retval; } + + public SheetReferences getSheetReferences() { + return workbook.getSheetReferences(); + } /** * removes sheet at the given index @@ -811,7 +827,7 @@ public class HSSFWorkbook extends POIDocument implements org.apache.poi.ss.userm if (isNewRecord) { - HSSFName newName = new HSSFName(workbook, nameRecord); + HSSFName newName = new HSSFName(this, nameRecord); names.add(newName); } @@ -1122,6 +1138,17 @@ public class HSSFWorkbook extends POIDocument implements org.apache.poi.ss.userm return result; } + + /** + * TODO - make this less cryptic / move elsewhere + * @param refIndex Index to REF entry in EXTERNSHEET record in the Link Table + * @param definedNameIndex zero-based to DEFINEDNAME or EXTERNALNAME record + * @return the string representation of the defined or external name + */ + public String resolveNameXText(int refIndex, int definedNameIndex) { + return workbook.resolveNameXText(refIndex, definedNameIndex); + } + /** * Sets the printarea for the sheet provided @@ -1180,7 +1207,7 @@ public class HSSFWorkbook extends POIDocument implements org.apache.poi.ss.userm if (name == null) return null; //adding one here because 0 indicates a global named region; doesnt make sense for print areas - return name.getAreaReference(workbook); + return name.getAreaReference(this); } /** @@ -1197,7 +1224,7 @@ public class HSSFWorkbook extends POIDocument implements org.apache.poi.ss.userm public HSSFName createName(){ NameRecord nameRecord = workbook.createName(); - HSSFName newName = new HSSFName(workbook, nameRecord); + HSSFName newName = new HSSFName(this, nameRecord); names.add(newName); diff --git a/src/scratchpad/examples/src/org/apache/poi/hslf/examples/ApacheconEU08.java b/src/scratchpad/examples/src/org/apache/poi/hslf/examples/ApacheconEU08.java index 0f28c2a8c9..962349876a 100755 --- a/src/scratchpad/examples/src/org/apache/poi/hslf/examples/ApacheconEU08.java +++ b/src/scratchpad/examples/src/org/apache/poi/hslf/examples/ApacheconEU08.java @@ -459,6 +459,7 @@ public class ApacheconEU08 { TextBox box2 = new TextBox();
TextRun tr2 = box2.getTextRun();
tr2.setRunType(TextHeaderAtom.BODY_TYPE);
+ tr2.getRichTextRuns()[0].setFontSize(32);
tr2.setText(
"Support for more PowerPoint functionality\r" +
"Rendering slides into java.awt.Graphics2D");
@@ -477,6 +478,7 @@ public class ApacheconEU08 { TextBox box4 = new TextBox();
TextRun tr4 = box4.getTextRun();
tr4.setRunType(TextHeaderAtom.BODY_TYPE);
+ tr4.getRichTextRuns()[0].setFontSize(32);
tr4.setText(
"Integration with Apache FOP - Formatting Objects Processor");
box4.setAnchor(new Rectangle(36, 290, 648, 90));
diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/AutoShape.java b/src/scratchpad/src/org/apache/poi/hslf/model/AutoShape.java index b3ddce37da..cf65a9b13c 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/model/AutoShape.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/AutoShape.java @@ -20,11 +20,15 @@ package org.apache.poi.hslf.model; import org.apache.poi.ddf.*; /** - * Represents a autoshape in a PowerPoint drawing + * Represents an AutoShape. + * <p> + * AutoShapes are drawing objects with a particular shape that may be customized through smart resizing and adjustments. + * See {@link ShapeTypes} + * </p> * * @author Yegor Kozlov */ -public class AutoShape extends SimpleShape { +public class AutoShape extends TextShape { protected AutoShape(EscherContainerRecord escherRecord, Shape parent){ super(escherRecord, parent); @@ -40,23 +44,62 @@ public class AutoShape extends SimpleShape { } protected EscherContainerRecord createSpContainer(int shapeType, boolean isChild){ - EscherContainerRecord spcont = super.createSpContainer(isChild); + _escherContainer = super.createSpContainer(isChild); - EscherSpRecord spRecord = spcont.getChildById(EscherSpRecord.RECORD_ID); - short type = (short)((shapeType << 4) | 0x2); - spRecord.setOptions(type); + setShapeType(shapeType); //set default properties for an autoshape - EscherOptRecord opt = (EscherOptRecord)getEscherChild(spcont, EscherOptRecord.RECORD_ID); + setEscherProperty(EscherProperties.PROTECTION__LOCKAGAINSTGROUPING, 0x40000); + setEscherProperty(EscherProperties.FILL__FILLCOLOR, 0x8000004); + setEscherProperty(EscherProperties.FILL__FILLCOLOR, 0x8000004); + setEscherProperty(EscherProperties.FILL__FILLBACKCOLOR, 0x8000000); + setEscherProperty(EscherProperties.FILL__NOFILLHITTEST, 0x100010); + setEscherProperty(EscherProperties.LINESTYLE__COLOR, 0x8000001); + setEscherProperty(EscherProperties.LINESTYLE__NOLINEDRAWDASH, 0x80008); + setEscherProperty(EscherProperties.SHADOWSTYLE__COLOR, 0x8000002); - opt.addEscherProperty(new EscherSimpleProperty(EscherProperties.FILL__FILLCOLOR, 0x8000004)); - opt.addEscherProperty(new EscherSimpleProperty(EscherProperties.FILL__FILLBACKCOLOR, 0x8000000)); - opt.addEscherProperty(new EscherSimpleProperty(EscherProperties.FILL__NOFILLHITTEST, 0x100010)); - opt.addEscherProperty(new EscherSimpleProperty(EscherProperties.LINESTYLE__COLOR, 0x8000001)); - opt.addEscherProperty(new EscherSimpleProperty(EscherProperties.LINESTYLE__NOLINEDRAWDASH, 0x80008)); - opt.addEscherProperty(new EscherSimpleProperty(EscherProperties.SHADOWSTYLE__COLOR, 0x8000002)); + return _escherContainer; + } + + protected void setDefaultTextProperties(TextRun _txtrun){ + setVerticalAlignment(TextBox.AnchorMiddle); + setHorizontalAlignment(TextBox.AlignCenter); + setWordWrap(TextBox.WrapNone); + } - return spcont; + /** + * Gets adjust value which controls smart resizing of the auto-shape. + * + * <p> + * The adjustment values are given in shape coordinates: + * the origin is at the top-left, positive-x is to the right, positive-y is down. + * The region from (0,0) to (S,S) maps to the geometry box of the shape (S=21600 is a constant). + * </p> + * + * @param idx the adjust index in the [0, 9] range + * @return the adjustment value + */ + public int getAdjustmentValue(int idx){ + if(idx < 0 || idx > 9) throw new IllegalArgumentException("The index of an adjustment value must be in the [0, 9] range"); + + return getEscherProperty((short)(EscherProperties.GEOMETRY__ADJUSTVALUE + idx)); } + /** + * Sets adjust value which controls smart resizing of the auto-shape. + * + * <p> + * The adjustment values are given in shape coordinates: + * the origin is at the top-left, positive-x is to the right, positive-y is down. + * The region from (0,0) to (S,S) maps to the geometry box of the shape (S=21600 is a constant). + * </p> + * + * @param idx the adjust index in the [0, 9] range + * @param val the adjustment value + */ + public void setAdjustmentValue(int idx, int val){ + if(idx < 0 || idx > 9) throw new IllegalArgumentException("The index of an adjustment value must be in the [0, 9] range"); + + setEscherProperty((short)(EscherProperties.GEOMETRY__ADJUSTVALUE + idx), val); + } } diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/Line.java b/src/scratchpad/src/org/apache/poi/hslf/model/Line.java index 0d3f616e92..9237183689 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/model/Line.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/Line.java @@ -106,14 +106,14 @@ public class Line extends SimpleShape { } protected EscherContainerRecord createSpContainer(boolean isChild){ - EscherContainerRecord spcont = super.createSpContainer(isChild); + _escherContainer = super.createSpContainer(isChild); - EscherSpRecord spRecord = spcont.getChildById(EscherSpRecord.RECORD_ID); + EscherSpRecord spRecord = _escherContainer.getChildById(EscherSpRecord.RECORD_ID); short type = (ShapeTypes.Line << 4) | 0x2; spRecord.setOptions(type); //set default properties for a line - EscherOptRecord opt = (EscherOptRecord)getEscherChild(spcont, EscherOptRecord.RECORD_ID); + EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); //default line properties setEscherProperty(opt, EscherProperties.GEOMETRY__SHAPEPATH, 4); @@ -123,7 +123,7 @@ public class Line extends SimpleShape { setEscherProperty(opt, EscherProperties.LINESTYLE__NOLINEDRAWDASH, 0xA0008); setEscherProperty(opt, EscherProperties.SHADOWSTYLE__COLOR, 0x8000002); - return spcont; + return _escherContainer; } } diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/PPFont.java b/src/scratchpad/src/org/apache/poi/hslf/model/PPFont.java new file mode 100755 index 0000000000..8b4de90509 --- /dev/null +++ b/src/scratchpad/src/org/apache/poi/hslf/model/PPFont.java @@ -0,0 +1,243 @@ +/* ====================================================================
+ 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.hslf.model;
+
+import org.apache.poi.hslf.record.FontEntityAtom;
+
+/**
+ * Represents a Font used in a presenation.
+ * <p>
+ * In PowerPoint Font is a shared resource and can be shared among text object in the presentation.
+ * </p>
+ * Some commonly used fonts are predefined in static constants.
+ *
+ * @author Yegor Kozlov
+ */
+public class PPFont {
+ /**
+ * ANSI character set
+ */
+ public final static byte ANSI_CHARSET = 0;
+
+ /**
+ * Default character set.
+ */
+ public final static byte DEFAULT_CHARSET = 1;
+
+ /**
+ * Symbol character set
+ */
+ public final static byte SYMBOL_CHARSET = 2;
+
+
+ /**
+ * Constants for the pitch and family of the font.
+ * The two low-order bits specify the pitch of the font and can be one of the following values
+ */
+ public final static byte DEFAULT_PITCH = 0;
+ public final static byte FIXED_PITCH = 1;
+ public final static byte VARIABLE_PITCH = 2;
+
+ /**
+ * Don't care or don't know.
+ */
+ public final static byte FF_DONTCARE = 0;
+ /**
+ * Fonts with variable stroke width (proportional) and with serifs. Times New Roman is an example.
+ */
+ public final static byte FF_ROMAN = 16;
+ /**
+ * Fonts with variable stroke width (proportional) and without serifs. Arial is an example.
+ */
+ public final static byte FF_SWISS = 32;
+ /**
+ * Fonts designed to look like handwriting. Script and Cursive are examples.
+ */
+ public final static byte FF_SCRIPT = 64;
+ /**
+ * Fonts with constant stroke width (monospace), with or without serifs.
+ * Monospace fonts are usually modern. CourierNew is an example
+ */
+ public final static byte FF_MODERN = 48;
+ /**
+ * Novelty fonts. Old English is an example
+ */
+ public final static byte FF_DECORATIVE = 80;
+
+
+ protected int charset;
+ protected int type;
+ protected int flags;
+ protected int pitch;
+ protected String name;
+
+ /**
+ * Creates a new instance of PPFont
+ */
+ public PPFont(){
+
+ }
+
+ /**
+ * Creates a new instance of PPFont and initialize it from the supplied font atom
+ */
+ public PPFont(FontEntityAtom fontAtom){
+ name = fontAtom.getFontName();
+ charset = fontAtom.getCharSet();
+ type = fontAtom.getFontType();
+ flags = fontAtom.getFontFlags();
+ pitch = fontAtom.getPitchAndFamily();
+ }
+
+ /**
+ * set the name for the font (i.e. Arial)
+ *
+ * @param val String representing the name of the font to use
+ */
+ public void setFontName(String val){
+ name = val;
+ }
+
+ /**
+ * get the name for the font (i.e. Arial)
+ *
+ * @return String representing the name of the font to use
+ */
+ public String getFontName(){
+ return name;
+ }
+
+ /**
+ * set the character set
+ *
+ * @param val - characterset
+ */
+ public void setCharSet(int val){
+ charset = val;
+ }
+
+ /**
+ * get the character set
+ *
+ * @return charset - characterset
+ */
+ public int getCharSet(){
+ return charset;
+ }
+
+ /**
+ * set the font flags
+ * Bit 1: If set, font is subsetted
+ *
+ * @param val - the font flags
+ */
+ public void setFontFlags(int val){
+ flags = val;
+ }
+
+ /**
+ * get the character set
+ * Bit 1: If set, font is subsetted
+ *
+ * @return the font flags
+ */
+ public int getFontFlags(){
+ return flags;
+ }
+
+ /**
+ * set the font type
+ * <p>
+ * Bit 1: Raster Font
+ * Bit 2: Device Font
+ * Bit 3: TrueType Font
+ * </p>
+ *
+ * @param val - the font type
+ */
+ public void setFontType(int val){
+ type = val;
+ }
+
+ /**
+ * get the font type
+ * <p>
+ * Bit 1: Raster Font
+ * Bit 2: Device Font
+ * Bit 3: TrueType Font
+ * </p>
+ *
+ * @return the font type
+ */
+ public int getFontType(){
+ return type;
+ }
+
+ /**
+ * set lfPitchAndFamily
+ *
+ *
+ * @param val - Corresponds to the lfPitchAndFamily field of the Win32 API LOGFONT structure
+ */
+ public void setPitchAndFamily(int val){
+ pitch = val;
+ }
+
+ /**
+ * get lfPitchAndFamily
+ *
+ * @return corresponds to the lfPitchAndFamily field of the Win32 API LOGFONT structure
+ */
+ public int getPitchAndFamily(){
+ return pitch;
+ }
+
+ public static final PPFont ARIAL;
+ public static final PPFont TIMES_NEW_ROMAN ;
+ public static final PPFont COURIER_NEW;
+ public static final PPFont WINGDINGS;
+ static {
+ ARIAL = new PPFont();
+ ARIAL.setFontName("Arial");
+ ARIAL.setCharSet(ANSI_CHARSET);
+ ARIAL.setFontType(4);
+ ARIAL.setFontFlags(0);
+ ARIAL.setPitchAndFamily(VARIABLE_PITCH | FF_SWISS);
+
+ TIMES_NEW_ROMAN = new PPFont();
+ TIMES_NEW_ROMAN.setFontName("Times New Roman");
+ TIMES_NEW_ROMAN.setCharSet(ANSI_CHARSET);
+ TIMES_NEW_ROMAN.setFontType(4);
+ TIMES_NEW_ROMAN.setFontFlags(0);
+ TIMES_NEW_ROMAN.setPitchAndFamily(VARIABLE_PITCH | FF_ROMAN);
+
+ COURIER_NEW = new PPFont();
+ COURIER_NEW.setFontName("Courier New");
+ COURIER_NEW.setCharSet(ANSI_CHARSET);
+ COURIER_NEW.setFontType(4);
+ COURIER_NEW.setFontFlags(0);
+ COURIER_NEW.setPitchAndFamily(FIXED_PITCH | FF_MODERN);
+
+ WINGDINGS = new PPFont();
+ WINGDINGS.setFontName("Wingdings");
+ WINGDINGS.setCharSet(SYMBOL_CHARSET);
+ WINGDINGS.setFontType(4);
+ WINGDINGS.setFontFlags(0);
+ WINGDINGS.setPitchAndFamily(VARIABLE_PITCH | FF_DONTCARE);
+ }
+}
diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/Picture.java b/src/scratchpad/src/org/apache/poi/hslf/model/Picture.java index 90efd5f3ee..910d5c8503 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/model/Picture.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/Picture.java @@ -120,20 +120,20 @@ public class Picture extends SimpleShape { * @return the create Picture object */ protected EscherContainerRecord createSpContainer(int idx, boolean isChild) { - EscherContainerRecord spContainer = super.createSpContainer(isChild); - spContainer.setOptions((short)15); + _escherContainer = super.createSpContainer(isChild); + _escherContainer.setOptions((short)15); - EscherSpRecord spRecord = spContainer.getChildById(EscherSpRecord.RECORD_ID); + EscherSpRecord spRecord = _escherContainer.getChildById(EscherSpRecord.RECORD_ID); spRecord.setOptions((short)((ShapeTypes.PictureFrame << 4) | 0x2)); //set default properties for a picture - EscherOptRecord opt = (EscherOptRecord)getEscherChild(spContainer, EscherOptRecord.RECORD_ID); + EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); setEscherProperty(opt, EscherProperties.PROTECTION__LOCKAGAINSTGROUPING, 8388736); //another weird feature of powerpoint: for picture id we must add 0x4000. setEscherProperty(opt, (short)(EscherProperties.BLIP__BLIPTODISPLAY + 0x4000), idx); - return spContainer; + return _escherContainer; } /** diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/Placeholder.java b/src/scratchpad/src/org/apache/poi/hslf/model/Placeholder.java index dd0132ebe0..f0bc74558f 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/model/Placeholder.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/Placeholder.java @@ -49,15 +49,15 @@ public class Placeholder extends TextBox { * @return the created <code>EscherContainerRecord</code> which holds shape data */ protected EscherContainerRecord createSpContainer(boolean isChild){ - EscherContainerRecord spcont = super.createSpContainer(isChild); + _escherContainer = super.createSpContainer(isChild); - EscherSpRecord spRecord = spcont.getChildById(EscherSpRecord.RECORD_ID); + EscherSpRecord spRecord = _escherContainer.getChildById(EscherSpRecord.RECORD_ID); spRecord.setFlags(EscherSpRecord.FLAG_HAVEANCHOR | EscherSpRecord.FLAG_HAVEMASTER); EscherClientDataRecord cldata = new EscherClientDataRecord(); cldata.setOptions((short)15); - EscherOptRecord opt = (EscherOptRecord)getEscherChild(spcont, EscherOptRecord.RECORD_ID); + EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); //Placeholders can't be grouped setEscherProperty(opt, EscherProperties.PROTECTION__LOCKAGAINSTGROUPING, 262144); @@ -86,7 +86,7 @@ public class Placeholder extends TextBox { cldata.setRemainingData(out.toByteArray()); //append placeholder container before EscherTextboxRecord - List lst = spcont.getChildRecords(); + List lst = _escherContainer.getChildRecords(); for (int i = 0; i < lst.size(); i++) { EscherRecord rec = (EscherRecord)lst.get(i); if(rec.getRecordId() == EscherTextboxRecord.RECORD_ID){ @@ -94,6 +94,6 @@ public class Placeholder extends TextBox { } } - return spcont; + return _escherContainer; } } diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/ShapeFactory.java b/src/scratchpad/src/org/apache/poi/hslf/model/ShapeFactory.java index 66c95e50cf..76b43ebb8a 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/model/ShapeFactory.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/ShapeFactory.java @@ -17,6 +17,10 @@ package org.apache.poi.hslf.model; import org.apache.poi.ddf.*; +import org.apache.poi.util.POILogger; +import org.apache.poi.util.POILogFactory; + +import java.util.List; /** * Create a <code>Shape</code> object depending on its type @@ -24,27 +28,53 @@ import org.apache.poi.ddf.*; * @author Yegor Kozlov */ public class ShapeFactory { + // For logging + protected static POILogger logger = POILogFactory.getLogger(ShapeFactory.class); /** * Create a new shape from the data provided. */ public static Shape createShape(EscherContainerRecord spContainer, Shape parent){ if (spContainer.getRecordId() == EscherContainerRecord.SPGR_CONTAINER){ - return new ShapeGroup(spContainer, parent); + return createShapeGroup(spContainer, parent); + } else { + return createSimpeShape(spContainer, parent); + + } + } + + public static ShapeGroup createShapeGroup(EscherContainerRecord spContainer, Shape parent){ + ShapeGroup group = null; + UnknownEscherRecord opt = (UnknownEscherRecord)Shape.getEscherChild((EscherContainerRecord)spContainer.getChild(0), (short)0xF122); + if(opt != null){ + try { + EscherPropertyFactory f = new EscherPropertyFactory(); + List props = f.createProperties( opt.getData(), 0, opt.getInstance() ); + EscherSimpleProperty p = (EscherSimpleProperty)props.get(0); + if(p.getPropertyNumber() == 0x39F && p.getPropertyValue() == 1){ + group = new ShapeGroup(spContainer, parent); + } else { + group = new ShapeGroup(spContainer, parent); + } + } catch (Exception e){ + logger.log(POILogger.WARN, e.getMessage()); + group = new ShapeGroup(spContainer, parent); + } + } else { + group = new ShapeGroup(spContainer, parent); } + return group; + } + + public static Shape createSimpeShape(EscherContainerRecord spContainer, Shape parent){ Shape shape; EscherSpRecord spRecord = spContainer.getChildById(EscherSpRecord.RECORD_ID); int type = spRecord.getOptions() >> 4; switch (type){ case ShapeTypes.TextBox: - case ShapeTypes.Rectangle: - EscherTextboxRecord txtbox = (EscherTextboxRecord)Shape.getEscherChild(spContainer, EscherTextboxRecord.RECORD_ID); - if (txtbox == null) - shape = new AutoShape(spContainer, parent); - else - shape = new TextBox(spContainer, parent); + shape = new TextBox(spContainer, parent); break; case ShapeTypes.PictureFrame: shape = new Picture(spContainer, parent); @@ -53,16 +83,21 @@ public class ShapeFactory { shape = new Line(spContainer, parent); break; case ShapeTypes.NotPrimitive: - if ((spRecord.getFlags() & EscherSpRecord.FLAG_GROUP) != 0) - shape = new ShapeGroup(spContainer, parent); - else + EscherOptRecord opt = (EscherOptRecord)Shape.getEscherChild(spContainer, EscherOptRecord.RECORD_ID); + EscherProperty prop = Shape.getEscherProperty(opt, EscherProperties.GEOMETRY__VERTICES); + if(prop != null) + shape = new Freeform(spContainer, parent); + else { + + logger.log(POILogger.WARN, "Creating AutoShape for a NotPrimitive shape"); shape = new AutoShape(spContainer, parent); + } break; default: shape = new AutoShape(spContainer, parent); break; } return shape; - } + } } diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/ShapeGroup.java b/src/scratchpad/src/org/apache/poi/hslf/model/ShapeGroup.java index dbcc8069c2..b22ed8d70b 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/model/ShapeGroup.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/ShapeGroup.java @@ -19,6 +19,7 @@ package org.apache.poi.hslf.model; import org.apache.poi.ddf.*; import org.apache.poi.util.LittleEndian; import org.apache.poi.util.POILogger; +import org.apache.poi.hslf.record.EscherTextboxWrapper; import java.util.ArrayList; import java.util.List; @@ -154,9 +155,10 @@ public class ShapeGroup extends Shape{ shape.setSheet(sheet); shape.afterInsert(sheet); - if(shape instanceof TextBox) { - TextBox tbox = (TextBox)shape; - getSheet().getPPDrawing().addTextboxWrapper(tbox._txtbox); + if (shape instanceof TextShape) { + TextShape tbox = (TextShape) shape; + EscherTextboxWrapper txWrapper = tbox.getEscherTextboxWrapper(); + if(txWrapper != null) getSheet().getPPDrawing().addTextboxWrapper(txWrapper); } } diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/Sheet.java b/src/scratchpad/src/org/apache/poi/hslf/model/Sheet.java index 135b625f1d..abf2fec589 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/model/Sheet.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/Sheet.java @@ -257,11 +257,12 @@ public abstract class Sheet { shape.setSheet(this); shape.afterInsert(this); - // If it's a TextBox, we need to tell the PPDrawing, as it has to + // If it's a TextShape, we need to tell the PPDrawing, as it has to // track TextboxWrappers specially - if (shape instanceof TextBox) { - TextBox tbox = (TextBox) shape; - ppdrawing.addTextboxWrapper(tbox._txtbox); + if (shape instanceof TextShape) { + TextShape tbox = (TextShape) shape; + EscherTextboxWrapper txWrapper = tbox.getEscherTextboxWrapper(); + if(txWrapper != null) ppdrawing.addTextboxWrapper(txWrapper); } } diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/SimpleShape.java b/src/scratchpad/src/org/apache/poi/hslf/model/SimpleShape.java index 85d672fe89..0831d453b5 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/model/SimpleShape.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/SimpleShape.java @@ -48,19 +48,19 @@ public class SimpleShape extends Shape { * @return the record container which holds this shape */ protected EscherContainerRecord createSpContainer(boolean isChild) { - EscherContainerRecord spContainer = new EscherContainerRecord(); - spContainer.setRecordId( EscherContainerRecord.SP_CONTAINER ); - spContainer.setOptions((short)15); + _escherContainer = new EscherContainerRecord(); + _escherContainer.setRecordId( EscherContainerRecord.SP_CONTAINER ); + _escherContainer.setOptions((short)15); EscherSpRecord sp = new EscherSpRecord(); int flags = EscherSpRecord.FLAG_HAVEANCHOR | EscherSpRecord.FLAG_HASSHAPETYPE; if (isChild) flags |= EscherSpRecord.FLAG_CHILD; sp.setFlags(flags); - spContainer.addChildRecord(sp); + _escherContainer.addChildRecord(sp); EscherOptRecord opt = new EscherOptRecord(); opt.setRecordId(EscherOptRecord.RECORD_ID); - spContainer.addChildRecord(opt); + _escherContainer.addChildRecord(opt); EscherRecord anchor; if(isChild) anchor = new EscherChildAnchorRecord(); @@ -75,9 +75,9 @@ public class SimpleShape extends Shape { LittleEndian.putInt(header, 4, 8); anchor.fillFields(header, 0, null); } - spContainer.addChildRecord(anchor); + _escherContainer.addChildRecord(anchor); - return spContainer; + return _escherContainer; } /** diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/Table.java b/src/scratchpad/src/org/apache/poi/hslf/model/Table.java index a9f21b54f3..947c41af63 100755 --- a/src/scratchpad/src/org/apache/poi/hslf/model/Table.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/Table.java @@ -20,10 +20,10 @@ package org.apache.poi.hslf.model; import org.apache.poi.ddf.*;
import org.apache.poi.util.LittleEndian;
-import java.util.ArrayList;
+import java.util.*;
import java.util.List;
-import java.util.Iterator;
import java.awt.*;
+import java.awt.geom.Rectangle2D;
/**
* Represents a table in a PowerPoint presentation
@@ -144,6 +144,54 @@ public class Table extends ShapeGroup { }
+ protected void initTable(){
+ Shape[] sh = getShapes();
+ Arrays.sort(sh, new Comparator(){
+ public int compare( Object o1, Object o2 ) {
+ Rectangle anchor1 = ((Shape)o1).getAnchor();
+ Rectangle anchor2 = ((Shape)o2).getAnchor();
+ int delta = anchor1.y - anchor2.y;
+ if(delta == 0) delta = anchor1.x - anchor2.y;
+ return delta;
+ }
+ });
+ int y0 = -1;
+ int maxrowlen = 0;
+ ArrayList lst = new ArrayList();
+ ArrayList row = null;
+ for (int i = 0; i < sh.length; i++) {
+ if(sh[i] instanceof TextShape){
+ Rectangle anchor = sh[i].getAnchor();
+ if(anchor.y != y0){
+ y0 = anchor.y;
+ if(row != null) maxrowlen = Math.max(maxrowlen, row.size());
+ row = new ArrayList();
+ lst.add(row);
+ }
+ row.add(sh[i]);
+ }
+ }
+ cells = new TableCell[lst.size()][maxrowlen];
+ for (int i = 0; i < lst.size(); i++) {
+ row = (ArrayList)lst.get(i);
+ for (int j = 0; j < row.size(); j++) {
+ TextShape tx = (TextShape)row.get(j);
+ cells[i][j] = new TableCell(tx.getSpContainer(), getParent());
+ cells[i][j].setSheet(tx.getSheet());
+ }
+ }
+ }
+
+ /**
+ * Assign the <code>SlideShow</code> this shape belongs to
+ *
+ * @param sheet owner of this shape
+ */
+ public void setSheet(Sheet sheet){
+ super.setSheet(sheet);
+ if(cells == null) initTable();
+ }
+
/**
* Sets the row height.
*
diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/TableCell.java b/src/scratchpad/src/org/apache/poi/hslf/model/TableCell.java index bb93e06b71..36789ad91a 100755 --- a/src/scratchpad/src/org/apache/poi/hslf/model/TableCell.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/TableCell.java @@ -63,15 +63,15 @@ public class TableCell extends TextBox { }
protected EscherContainerRecord createSpContainer(boolean isChild){
- EscherContainerRecord spContainer = super.createSpContainer(isChild);
- EscherOptRecord opt = (EscherOptRecord)getEscherChild(spContainer, EscherOptRecord.RECORD_ID);
+ _escherContainer = super.createSpContainer(isChild);
+ EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID);
setEscherProperty(opt, EscherProperties.TEXT__TEXTID, 0);
setEscherProperty(opt, EscherProperties.TEXT__SIZE_TEXT_TO_FIT_SHAPE, 0x20000);
setEscherProperty(opt, EscherProperties.FILL__NOFILLHITTEST, 0x150001);
setEscherProperty(opt, EscherProperties.SHADOWSTYLE__SHADOWOBSURED, 0x20000);
setEscherProperty(opt, EscherProperties.PROTECTION__LOCKAGAINSTGROUPING, 0x40000);
- return spContainer;
+ return _escherContainer;
}
protected void anchorBorder(int type, Line line){
diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/TextBox.java b/src/scratchpad/src/org/apache/poi/hslf/model/TextBox.java index 1f9a489a78..a1d45ffbae 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/model/TextBox.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/TextBox.java @@ -38,55 +38,7 @@ import java.io.IOException; * * @author Yegor Kozlov */ -public class TextBox extends SimpleShape { - - /** - * How to anchor the text - */ - public static final int AnchorTop = 0; - public static final int AnchorMiddle = 1; - public static final int AnchorBottom = 2; - public static final int AnchorTopCentered = 3; - public static final int AnchorMiddleCentered = 4; - public static final int AnchorBottomCentered = 5; - public static final int AnchorTopBaseline = 6; - public static final int AnchorBottomBaseline = 7; - public static final int AnchorTopCenteredBaseline = 8; - public static final int AnchorBottomCenteredBaseline = 9; - - /** - * How to wrap the text - */ - public static final int WrapSquare = 0; - public static final int WrapByPoints = 1; - public static final int WrapNone = 2; - public static final int WrapTopBottom = 3; - public static final int WrapThrough = 4; - - /** - * How to align the text - */ - public static final int AlignLeft = 0; - public static final int AlignCenter = 1; - public static final int AlignRight = 2; - public static final int AlignJustify = 3; - - /** - * Low-level object which holds actual text and format data - */ - protected TextRun _txtrun; - - /** - * Escher container which holds text attributes such as - * TextHeaderAtom, TextBytesAtom ot TextCharsAtom, StyleTextPropAtom etc. - */ - protected EscherTextboxWrapper _txtbox; - - /** - * Is the TextBox missing the text records which actually - * store the text? - */ - private boolean _missingTextRecords = false; +public class TextBox extends TextShape { /** * Create a TextBox object and initialize it from the supplied Record container. @@ -97,8 +49,6 @@ public class TextBox extends SimpleShape { protected TextBox(EscherContainerRecord escherRecord, Shape parent){ super(escherRecord, parent); - EscherTextboxRecord textbox = (EscherTextboxRecord)Shape.getEscherChild(_escherContainer, EscherTextboxRecord.RECORD_ID); - _txtbox = new EscherTextboxWrapper(textbox); } /** @@ -108,8 +58,7 @@ public class TextBox extends SimpleShape { * in a table then the parent is Table. */ public TextBox(Shape parent){ - super(null, parent); - _escherContainer = createSpContainer(parent instanceof ShapeGroup); + super(parent); } /** @@ -121,376 +70,31 @@ public class TextBox extends SimpleShape { } /** - * Create a new textBox and initialize internal structures + * Create a new TextBox and initialize its internal structures * * @return the created <code>EscherContainerRecord</code> which holds shape data */ protected EscherContainerRecord createSpContainer(boolean isChild){ - EscherContainerRecord spcont = super.createSpContainer(isChild); - - EscherSpRecord spRecord = spcont.getChildById(EscherSpRecord.RECORD_ID); - short type = (ShapeTypes.TextBox << 4) | 0x2; - spRecord.setOptions(type); - - //set default properties for a textbox - EscherOptRecord opt = (EscherOptRecord)getEscherChild(spcont, EscherOptRecord.RECORD_ID); - setEscherProperty(opt, EscherProperties.TEXT__TEXTID, 0); - - setEscherProperty(opt, EscherProperties.FILL__FILLCOLOR, 0x8000004); - setEscherProperty(opt, EscherProperties.FILL__FILLBACKCOLOR, 0x8000000); - setEscherProperty(opt, EscherProperties.FILL__NOFILLHITTEST, 0x100000); - setEscherProperty(opt, EscherProperties.LINESTYLE__COLOR, 0x8000001); - setEscherProperty(opt, EscherProperties.LINESTYLE__NOLINEDRAWDASH, 0x80000); - setEscherProperty(opt, EscherProperties.SHADOWSTYLE__COLOR, 0x8000002); - - //create EscherTextboxWrapper - _txtbox = new EscherTextboxWrapper(); - - TextHeaderAtom tha = new TextHeaderAtom(); - tha.setParentRecord(_txtbox); // TextHeaderAtom is parent aware - _txtbox.appendChildRecord(tha); - - TextCharsAtom tca = new TextCharsAtom(); - _txtbox.appendChildRecord(tca); - - StyleTextPropAtom sta = new StyleTextPropAtom(0); - _txtbox.appendChildRecord(sta); - - _txtrun = new TextRun(tha,tca,sta); - _txtrun.setText(""); - spcont.addChildRecord(_txtbox.getEscherRecord()); - - return spcont; - } - - /** - * Returns the text contained in this text frame. - * - * @return the text string for this textbox. - */ - public String getText(){ - return _txtrun == null ? null : _txtrun.getText(); - } - - /** - * Sets the text contained in this text frame. - * - * @param text the text string used by this object. - */ - public void setText(String text){ - _txtrun.setText(text); - } - - /** - * When a textbox is added to a sheet we need to tell upper-level - * <code>PPDrawing</code> about it. - * - * @param sh the sheet we are adding to - */ - protected void afterInsert(Sheet sh){ - PPDrawing ppdrawing = sh.getPPDrawing(); - ppdrawing.addTextboxWrapper(_txtbox); - // Ensure the escher layer knows about the added records - try { - _txtbox.writeOut(null); - } catch (IOException e){ - throw new HSLFException(e); - } - if(getAnchor().equals(new java.awt.Rectangle()) && !"".equals(getText())) resizeToFitText(); - } - - /** - * Adjust the size of the TextBox so it encompasses the text inside it. - */ - public void resizeToFitText(){ - try{ - FontRenderContext frc = new FontRenderContext(null, true, true); - RichTextRun rt = _txtrun.getRichTextRuns()[0]; - int size = rt.getFontSize(); - int style = 0; - if (rt.isBold()) style |= Font.BOLD; - if (rt.isItalic()) style |= Font.ITALIC; - String fntname = rt.getFontName(); - Font font = new Font(fntname, style, size); - - TextLayout layout = new TextLayout(getText(), font, frc); - int width = Math.round(layout.getAdvance()); - int height = Math.round(layout.getAscent()); - - Dimension txsize = new Dimension(width, height); - java.awt.Rectangle anchor = getAnchor(); - anchor.setSize(txsize); - setAnchor(anchor); - } catch (Exception e){ - e.printStackTrace(); - - } - } - - /** - * Returns the type of vertical alignment for the text. - * One of the <code>Anchor*</code> constants defined in this class. - * - * @return the type of alignment - */ - public int getVerticalAlignment(){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__ANCHORTEXT); - int valign; - if (prop == null){ - int type = getTextRun().getRunType(); - switch (type){ - case TextHeaderAtom.TITLE_TYPE: - case TextHeaderAtom.CENTER_TITLE_TYPE: - valign = TextBox.AnchorMiddle; - break; - default: - valign = TextBox.AnchorTop; - break; - } - } else { - valign = prop.getPropertyValue(); - } - return valign; - } - - /** - * Sets the type of vertical alignment for the text. - * One of the <code>Anchor*</code> constants defined in this class. - * - * @param align - the type of alignment - */ - public void setVerticalAlignment(int align){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - setEscherProperty(opt, EscherProperties.TEXT__ANCHORTEXT, align); - } - - public void setHorizontalAlignment(int align){ - _txtrun.getRichTextRuns()[0].setAlignment(align); - } - public int getHorizontalAlignment(){ - return _txtrun.getRichTextRuns()[0].getAlignment(); - } - - /** - * Returns the distance (in points) between the bottom of the text frame - * and the bottom of the inscribed rectangle of the shape that contains the text. - * Default value is 1/20 inch. - * - * @return the botom margin - */ - public int getMarginBottom(){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__TEXTBOTTOM); - int val = prop == null ? EMU_PER_INCH/20 : prop.getPropertyValue(); - return val/EMU_PER_POINT; - } - - /** - * Sets the botom margin. - * @see #getMarginBottom() - * - * @param margin the bottom margin - */ - public void setMarginBottom(int margin){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - setEscherProperty(opt, EscherProperties.TEXT__TEXTBOTTOM, margin*EMU_PER_POINT); - } - - /** - * Returns the distance (in EMUs) between the left edge of the text frame - * and the left edge of the inscribed rectangle of the shape that contains - * the text. - * Default value is 1/10 inch. - * - * @return the left margin - */ - public int getMarginLeft(){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__TEXTBOTTOM); - int val = prop == null ? EMU_PER_INCH/10 : prop.getPropertyValue(); - return val/EMU_PER_POINT; - } + _escherContainer = super.createSpContainer(isChild); - /** - * Sets the left margin. - * @see #getMarginLeft() - * - * @param margin the left margin - */ - public void setMarginLeft(int margin){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - setEscherProperty(opt, EscherProperties.TEXT__TEXTLEFT, margin*EMU_PER_POINT); - } + setShapeType(ShapeTypes.TextBox); - /** - * Returns the distance (in EMUs) between the right edge of the - * text frame and the right edge of the inscribed rectangle of the shape - * that contains the text. - * Default value is 1/10 inch. - * - * @return the right margin - */ - public int getMarginRight(){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__TEXTRIGHT); - int val = prop == null ? EMU_PER_INCH/10 : prop.getPropertyValue(); - return val/EMU_PER_POINT; - } + //set default properties for a TextBox + setEscherProperty(EscherProperties.FILL__FILLCOLOR, 0x8000004); + setEscherProperty(EscherProperties.FILL__FILLBACKCOLOR, 0x8000000); + setEscherProperty(EscherProperties.FILL__NOFILLHITTEST, 0x100000); + setEscherProperty(EscherProperties.LINESTYLE__COLOR, 0x8000001); + setEscherProperty(EscherProperties.LINESTYLE__NOLINEDRAWDASH, 0x80000); + setEscherProperty(EscherProperties.SHADOWSTYLE__COLOR, 0x8000002); - /** - * Sets the right margin. - * @see #getMarginRight() - * - * @param margin the right margin - */ - public void setMarginRight(int margin){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - setEscherProperty(opt, EscherProperties.TEXT__TEXTRIGHT, margin*EMU_PER_POINT); - } + _txtrun = createTextRun(); - /** - * Returns the distance (in EMUs) between the top of the text frame - * and the top of the inscribed rectangle of the shape that contains the text. - * Default value is 1/20 inch. - * - * @return the top margin - */ - public int getMarginTop(){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__TEXTTOP); - int val = prop == null ? EMU_PER_INCH/20 : prop.getPropertyValue(); - return val/EMU_PER_POINT; + return _escherContainer; } - /** - * Sets the top margin. - * @see #getMarginTop() - * - * @param margin the top margin - */ - public void setMarginTop(int margin){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - setEscherProperty(opt, EscherProperties.TEXT__TEXTTOP, margin*EMU_PER_POINT); + protected void setDefaultTextProperties(TextRun _txtrun){ + setVerticalAlignment(TextBox.AnchorTop); + setEscherProperty(EscherProperties.TEXT__SIZE_TEXT_TO_FIT_SHAPE, 0x20002); } - - /** - * Returns the value indicating word wrap. - * One of the <code>Wrap*</code> constants defined in this class. - * - * @return the value indicating word wrap - */ - public int getWordWrap(){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__WRAPTEXT); - return prop == null ? WrapSquare : prop.getPropertyValue(); - } - - /** - * Specifies how the text should be wrapped - * - * @param wrap the value indicating how the text should be wrapped - */ - public void setWordWrap(int wrap){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - setEscherProperty(opt, EscherProperties.TEXT__WRAPTEXT, wrap); - } - - /** - * @return id for the text. - */ - public int getTextId(){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__TEXTID); - return prop == null ? 0 : prop.getPropertyValue(); - } - - /** - * Sets text ID - * - * @param id of the text - */ - public void setTextId(int id){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - setEscherProperty(opt, EscherProperties.TEXT__TEXTID, id); - } - - /** - * The color used to fill this shape. - * - * @param color the background color - */ - public void setBackgroundColor(Color color){ - EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID); - int rgb = new Color(color.getBlue(), color.getGreen(), color.getRed(), 0).getRGB(); - setEscherProperty(opt, EscherProperties.FILL__FILLBACKCOLOR, rgb); - } - - /** - * @return the TextRun object for this text box - */ - public TextRun getTextRun(){ - return _txtrun; - } - - public void setSheet(Sheet sheet){ - _sheet = sheet; - - // Initialize _txtrun object. - // (We can't do it in the constructor because the sheet - // is not assigned then, it's only built once we have - // all the records) - if(_txtrun == null) initTextRun(); - if(_txtrun == null) { - // No text records found, skip - _missingTextRecords = true; - return; - } else { - _missingTextRecords = false; - } - - // Supply the sheet to our child RichTextRuns - _txtrun.setSheet(sheet); - RichTextRun[] rt = _txtrun.getRichTextRuns(); - for (int i = 0; i < rt.length; i++) { - rt[i].supplySlideShow(_sheet.getSlideShow()); - } - } - - private void initTextRun(){ - OutlineTextRefAtom ota = null; - - // Find the interesting child records - Record[] child = _txtbox.getChildRecords(); - for (int i = 0; i < child.length; i++) { - if (child[i] instanceof OutlineTextRefAtom) { - ota = (OutlineTextRefAtom)child[i]; - break; - } - } - - Sheet sheet = getSheet(); - TextRun[] runs = sheet.getTextRuns(); - if (ota != null) { - int idx = ota.getTextIndex(); - for (int i = 0; i < runs.length; i++) { - if(runs[i].getIndex() == idx){ - _txtrun = runs[i]; - } - } - if(_txtrun == null) { - logger.log(POILogger.WARN, "text run not found for OutlineTextRefAtom.TextIndex=" + idx); - } - } else { - int shapeId = _escherContainer.getChildById(EscherSpRecord.RECORD_ID).getShapeId(); - if(runs != null) for (int i = 0; i < runs.length; i++) { - if(runs[i].getShapeId() == shapeId){ - _txtrun = runs[i]; - break; - } - } - } - - } } diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/TextRun.java b/src/scratchpad/src/org/apache/poi/hslf/model/TextRun.java index 586932e739..5834e2eaec 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/model/TextRun.java +++ b/src/scratchpad/src/org/apache/poi/hslf/model/TextRun.java @@ -24,12 +24,7 @@ import java.util.LinkedList; import java.util.Vector; import org.apache.poi.hslf.model.textproperties.TextPropCollection; -import org.apache.poi.hslf.record.Record; -import org.apache.poi.hslf.record.RecordContainer; -import org.apache.poi.hslf.record.StyleTextPropAtom; -import org.apache.poi.hslf.record.TextBytesAtom; -import org.apache.poi.hslf.record.TextCharsAtom; -import org.apache.poi.hslf.record.TextHeaderAtom; +import org.apache.poi.hslf.record.*; import org.apache.poi.hslf.usermodel.RichTextRun; import org.apache.poi.hslf.usermodel.SlideShow; import org.apache.poi.util.StringUtil; @@ -50,6 +45,7 @@ public class TextRun protected TextBytesAtom _byteAtom; protected TextCharsAtom _charAtom; protected StyleTextPropAtom _styleAtom; + protected TextSpecInfoAtom _specAtom; protected boolean _isUnicode; protected RichTextRun[] _rtRuns; private SlideShow slideShow; @@ -477,6 +473,18 @@ public class TextRun // Recreate rich text run with no styling _rtRuns[0] = new RichTextRun(this,0,s.length()); } + + /** + * If TextSpecInfoAtom is present, we must update the text size, + * otherwise the ppt will be corrupted + */ + if(_records != null) for (int i = 0; i < _records.length; i++) { + if(_records[i] instanceof TextSpecInfoAtom){ + TextSpecInfoAtom specAtom = (TextSpecInfoAtom)_records[i]; + specAtom.setTextSize(s.length()); + } + + } } /** diff --git a/src/scratchpad/src/org/apache/poi/hslf/model/TextShape.java b/src/scratchpad/src/org/apache/poi/hslf/model/TextShape.java new file mode 100755 index 0000000000..3c45b34b0b --- /dev/null +++ b/src/scratchpad/src/org/apache/poi/hslf/model/TextShape.java @@ -0,0 +1,516 @@ +
+/* ====================================================================
+ 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.hslf.model;
+
+import org.apache.poi.ddf.*;
+import org.apache.poi.hslf.record.*;
+import org.apache.poi.hslf.usermodel.RichTextRun;
+import org.apache.poi.hslf.exceptions.HSLFException;
+import org.apache.poi.util.POILogger;
+
+import java.awt.*;
+import java.awt.geom.Rectangle2D;
+import java.awt.geom.AffineTransform;
+import java.awt.font.FontRenderContext;
+import java.awt.font.TextLayout;
+import java.io.IOException;
+
+/**
+ * A common superclass of all shapes that can hold text.
+ *
+ * @author Yegor Kozlov
+ */
+public abstract class TextShape extends SimpleShape {
+
+ /**
+ * How to anchor the text
+ */
+ public static final int AnchorTop = 0;
+ public static final int AnchorMiddle = 1;
+ public static final int AnchorBottom = 2;
+ public static final int AnchorTopCentered = 3;
+ public static final int AnchorMiddleCentered = 4;
+ public static final int AnchorBottomCentered = 5;
+ public static final int AnchorTopBaseline = 6;
+ public static final int AnchorBottomBaseline = 7;
+ public static final int AnchorTopCenteredBaseline = 8;
+ public static final int AnchorBottomCenteredBaseline = 9;
+
+ /**
+ * How to wrap the text
+ */
+ public static final int WrapSquare = 0;
+ public static final int WrapByPoints = 1;
+ public static final int WrapNone = 2;
+ public static final int WrapTopBottom = 3;
+ public static final int WrapThrough = 4;
+
+ /**
+ * How to align the text
+ */
+ public static final int AlignLeft = 0;
+ public static final int AlignCenter = 1;
+ public static final int AlignRight = 2;
+ public static final int AlignJustify = 3;
+
+ /**
+ * TextRun object which holds actual text and format data
+ */
+ protected TextRun _txtrun;
+
+ /**
+ * Escher container which holds text attributes such as
+ * TextHeaderAtom, TextBytesAtom ot TextCharsAtom, StyleTextPropAtom etc.
+ */
+ protected EscherTextboxWrapper _txtbox;
+
+ /**
+ * Used to calculate text bounds
+ */
+ protected static final FontRenderContext _frc = new FontRenderContext(null, true, true);
+
+ /**
+ * Create a TextBox object and initialize it from the supplied Record container.
+ *
+ * @param escherRecord <code>EscherSpContainer</code> container which holds information about this shape
+ * @param parent the parent of the shape
+ */
+ protected TextShape(EscherContainerRecord escherRecord, Shape parent){
+ super(escherRecord, parent);
+
+ }
+
+ /**
+ * Create a new TextBox. This constructor is used when a new shape is created.
+ *
+ * @param parent the parent of this Shape. For example, if this text box is a cell
+ * in a table then the parent is Table.
+ */
+ public TextShape(Shape parent){
+ super(null, parent);
+ _escherContainer = createSpContainer(parent instanceof ShapeGroup);
+ }
+
+ /**
+ * Create a new TextBox. This constructor is used when a new shape is created.
+ *
+ */
+ public TextShape(){
+ this(null);
+ }
+
+ public TextRun createTextRun(){
+ _txtbox = getEscherTextboxWrapper();
+ if(_txtbox == null) _txtbox = new EscherTextboxWrapper();
+
+ _txtrun = getTextRun();
+ if(_txtrun == null){
+ TextHeaderAtom tha = new TextHeaderAtom();
+ tha.setParentRecord(_txtbox);
+ _txtbox.appendChildRecord(tha);
+
+ TextCharsAtom tca = new TextCharsAtom();
+ _txtbox.appendChildRecord(tca);
+
+ StyleTextPropAtom sta = new StyleTextPropAtom(0);
+ _txtbox.appendChildRecord(sta);
+
+ _txtrun = new TextRun(tha,tca,sta);
+ _txtrun.setText("");
+
+ _escherContainer.addChildRecord(_txtbox.getEscherRecord());
+
+ setDefaultTextProperties(_txtrun);
+ }
+
+ return _txtrun;
+ }
+
+ /**
+ * Set default properties for the TextRun.
+ * Depending on the text and shape type the defaults are different:
+ * TextBox: align=left, valign=top
+ * AutoShape: align=center, valign=middle
+ *
+ */
+ protected void setDefaultTextProperties(TextRun _txtrun){
+
+ }
+
+ /**
+ * Returns the text contained in this text frame.
+ *
+ * @return the text string for this textbox.
+ */
+ public String getText(){
+ TextRun tx = getTextRun();
+ return tx == null ? null : tx.getText();
+ }
+
+ /**
+ * Sets the text contained in this text frame.
+ *
+ * @param text the text string used by this object.
+ */
+ public void setText(String text){
+ TextRun tx = getTextRun();
+ if(tx == null){
+ tx = createTextRun();
+ }
+ tx.setText(text);
+ setTextId(text.hashCode());
+ }
+
+ /**
+ * When a textbox is added to a sheet we need to tell upper-level
+ * <code>PPDrawing</code> about it.
+ *
+ * @param sh the sheet we are adding to
+ */
+ protected void afterInsert(Sheet sh){
+ EscherTextboxWrapper _txtbox = getEscherTextboxWrapper();
+ if(_txtbox != null){
+ PPDrawing ppdrawing = sh.getPPDrawing();
+ ppdrawing.addTextboxWrapper(_txtbox);
+ // Ensure the escher layer knows about the added records
+ try {
+ _txtbox.writeOut(null);
+ } catch (IOException e){
+ throw new HSLFException(e);
+ }
+ if(getAnchor().equals(new Rectangle()) && !"".equals(getText())) resizeToFitText();
+ }
+ }
+
+ protected EscherTextboxWrapper getEscherTextboxWrapper(){
+ if(_txtbox == null){
+ EscherTextboxRecord textRecord = (EscherTextboxRecord)Shape.getEscherChild(_escherContainer, EscherTextboxRecord.RECORD_ID);
+ if(textRecord != null) _txtbox = new EscherTextboxWrapper(textRecord);
+ }
+ return _txtbox;
+ }
+ /**
+ * Adjust the size of the TextShape so it encompasses the text inside it.
+ *
+ * @return a <code>Rectangle2D</code> that is the bounds of this <code>TextShape</code>.
+ */
+ public Rectangle2D resizeToFitText(){
+ String txt = getText();
+ if(txt == null || txt.length() == 0) return new Rectangle2D.Float();
+
+ RichTextRun rt = getTextRun().getRichTextRuns()[0];
+ int size = rt.getFontSize();
+ int style = 0;
+ if (rt.isBold()) style |= Font.BOLD;
+ if (rt.isItalic()) style |= Font.ITALIC;
+ String fntname = rt.getFontName();
+ Font font = new Font(fntname, style, size);
+
+ float width = 0, height = 0;
+ String[] lines = txt.split("\r");
+ for (int i = 0; i < lines.length; i++) {
+ if(lines[i].length() == 0) continue;
+
+ TextLayout layout = new TextLayout(lines[i], font, _frc);
+
+ width = Math.max(width, layout.getAdvance());
+
+ /**
+ * Even if top and bottom margins are set to 0 PowerPoint
+ * always sets extra space between the text and its bounding box.
+ *
+ * The approximation height = ascent*2 works good enough in most cases
+ */
+ height = Math.max(height, 2*layout.getAscent());
+ }
+
+ width += getMarginLeft() + getMarginRight();
+ height += getMarginTop() + getMarginBottom();
+
+ Rectangle2D anchor = getAnchor2D();
+ anchor.setRect(anchor.getX(), anchor.getY(), width, height);
+ setAnchor(anchor);
+
+ return anchor;
+ }
+
+ /**
+ * Returns the type of vertical alignment for the text.
+ * One of the <code>Anchor*</code> constants defined in this class.
+ *
+ * @return the type of alignment
+ */
+ public int getVerticalAlignment(){
+ EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID);
+ EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__ANCHORTEXT);
+ int valign;
+ if (prop == null){
+ int type = getTextRun().getRunType();
+ switch (type){
+ case TextHeaderAtom.TITLE_TYPE:
+ case TextHeaderAtom.CENTER_TITLE_TYPE:
+ valign = TextShape.AnchorMiddle;
+ break;
+ default:
+ valign = TextShape.AnchorTop;
+ break;
+ }
+ } else {
+ valign = prop.getPropertyValue();
+ }
+ return valign;
+ }
+
+ /**
+ * Sets the type of vertical alignment for the text.
+ * One of the <code>Anchor*</code> constants defined in this class.
+ *
+ * @param align - the type of alignment
+ */
+ public void setVerticalAlignment(int align){
+ setEscherProperty(EscherProperties.TEXT__ANCHORTEXT, align);
+ }
+
+ /**
+ * Sets the type of horizontal alignment for the text.
+ * One of the <code>Align*</code> constants defined in this class.
+ *
+ * @param align - the type of horizontal alignment
+ */
+ public void setHorizontalAlignment(int align){
+ TextRun tx = getTextRun();
+ if(tx != null) tx.getRichTextRuns()[0].setAlignment(align);
+ }
+
+ /**
+ * Gets the type of horizontal alignment for the text.
+ * One of the <code>Align*</code> constants defined in this class.
+ *
+ * @return align - the type of horizontal alignment
+ */
+ public int getHorizontalAlignment(){
+ TextRun tx = getTextRun();
+ return tx == null ? -1 : tx.getRichTextRuns()[0].getAlignment();
+ }
+
+ /**
+ * Returns the distance (in points) between the bottom of the text frame
+ * and the bottom of the inscribed rectangle of the shape that contains the text.
+ * Default value is 1/20 inch.
+ *
+ * @return the botom margin
+ */
+ public float getMarginBottom(){
+ EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID);
+ EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__TEXTBOTTOM);
+ int val = prop == null ? EMU_PER_INCH/20 : prop.getPropertyValue();
+ return (float)val/EMU_PER_POINT;
+ }
+
+ /**
+ * Sets the botom margin.
+ * @see #getMarginBottom()
+ *
+ * @param margin the bottom margin
+ */
+ public void setMarginBottom(float margin){
+ setEscherProperty(EscherProperties.TEXT__TEXTBOTTOM, (int)(margin*EMU_PER_POINT));
+ }
+
+ /**
+ * Returns the distance (in points) between the left edge of the text frame
+ * and the left edge of the inscribed rectangle of the shape that contains
+ * the text.
+ * Default value is 1/10 inch.
+ *
+ * @return the left margin
+ */
+ public float getMarginLeft(){
+ EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID);
+ EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__TEXTBOTTOM);
+ int val = prop == null ? EMU_PER_INCH/10 : prop.getPropertyValue();
+ return (float)val/EMU_PER_POINT;
+ }
+
+ /**
+ * Sets the left margin.
+ * @see #getMarginLeft()
+ *
+ * @param margin the left margin
+ */
+ public void setMarginLeft(float margin){
+ setEscherProperty(EscherProperties.TEXT__TEXTLEFT, (int)(margin*EMU_PER_POINT));
+ }
+
+ /**
+ * Returns the distance (in points) between the right edge of the
+ * text frame and the right edge of the inscribed rectangle of the shape
+ * that contains the text.
+ * Default value is 1/10 inch.
+ *
+ * @return the right margin
+ */
+ public float getMarginRight(){
+ EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID);
+ EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__TEXTRIGHT);
+ int val = prop == null ? EMU_PER_INCH/10 : prop.getPropertyValue();
+ return (float)val/EMU_PER_POINT;
+ }
+
+ /**
+ * Sets the right margin.
+ * @see #getMarginRight()
+ *
+ * @param margin the right margin
+ */
+ public void setMarginRight(float margin){
+ setEscherProperty(EscherProperties.TEXT__TEXTRIGHT, (int)(margin*EMU_PER_POINT));
+ }
+
+ /**
+ * Returns the distance (in points) between the top of the text frame
+ * and the top of the inscribed rectangle of the shape that contains the text.
+ * Default value is 1/20 inch.
+ *
+ * @return the top margin
+ */
+ public float getMarginTop(){
+ EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID);
+ EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__TEXTTOP);
+ int val = prop == null ? EMU_PER_INCH/20 : prop.getPropertyValue();
+ return (float)val/EMU_PER_POINT;
+ }
+
+ /**
+ * Sets the top margin.
+ * @see #getMarginTop()
+ *
+ * @param margin the top margin
+ */
+ public void setMarginTop(float margin){
+ setEscherProperty(EscherProperties.TEXT__TEXTTOP, (int)(margin*EMU_PER_POINT));
+ }
+
+
+ /**
+ * Returns the value indicating word wrap.
+ *
+ * @return the value indicating word wrap.
+ * Must be one of the <code>Wrap*</code> constants defined in this class.
+ */
+ public int getWordWrap(){
+ EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID);
+ EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__WRAPTEXT);
+ return prop == null ? WrapSquare : prop.getPropertyValue();
+ }
+
+ /**
+ * Specifies how the text should be wrapped
+ *
+ * @param wrap the value indicating how the text should be wrapped.
+ * Must be one of the <code>Wrap*</code> constants defined in this class.
+ */
+ public void setWordWrap(int wrap){
+ setEscherProperty(EscherProperties.TEXT__WRAPTEXT, wrap);
+ }
+
+ /**
+ * @return id for the text.
+ */
+ public int getTextId(){
+ EscherOptRecord opt = (EscherOptRecord)getEscherChild(_escherContainer, EscherOptRecord.RECORD_ID);
+ EscherSimpleProperty prop = (EscherSimpleProperty)getEscherProperty(opt, EscherProperties.TEXT__TEXTID);
+ return prop == null ? 0 : prop.getPropertyValue();
+ }
+
+ /**
+ * Sets text ID
+ *
+ * @param id of the text
+ */
+ public void setTextId(int id){
+ setEscherProperty(EscherProperties.TEXT__TEXTID, id);
+ }
+
+ /**
+ * @return the TextRun object for this text box
+ */
+ public TextRun getTextRun(){
+ if(_txtrun == null) initTextRun();
+ return _txtrun;
+ }
+
+ public void setSheet(Sheet sheet) {
+ _sheet = sheet;
+
+ // Initialize _txtrun object.
+ // (We can't do it in the constructor because the sheet
+ // is not assigned then, it's only built once we have
+ // all the records)
+ TextRun tx = getTextRun();
+ if (tx != null) {
+ // Supply the sheet to our child RichTextRuns
+ tx.setSheet(_sheet);
+ RichTextRun[] rt = tx.getRichTextRuns();
+ for (int i = 0; i < rt.length; i++) {
+ rt[i].supplySlideShow(_sheet.getSlideShow());
+ }
+ }
+
+ }
+
+ protected void initTextRun(){
+ EscherTextboxWrapper txtbox = getEscherTextboxWrapper();
+ Sheet sheet = getSheet();
+
+ if(sheet == null || txtbox == null) return;
+
+ OutlineTextRefAtom ota = null;
+
+ Record[] child = txtbox.getChildRecords();
+ for (int i = 0; i < child.length; i++) {
+ if (child[i] instanceof OutlineTextRefAtom) {
+ ota = (OutlineTextRefAtom)child[i];
+ break;
+ }
+ }
+
+ TextRun[] runs = _sheet.getTextRuns();
+ if (ota != null) {
+ int idx = ota.getTextIndex();
+ for (int i = 0; i < runs.length; i++) {
+ if(runs[i].getIndex() == idx){
+ _txtrun = runs[i];
+ break;
+ }
+ }
+ if(_txtrun == null) {
+ logger.log(POILogger.WARN, "text run not found for OutlineTextRefAtom.TextIndex=" + idx);
+ }
+ } else {
+ int shapeId = _escherContainer.getChildById(EscherSpRecord.RECORD_ID).getShapeId();
+ if(runs != null) for (int i = 0; i < runs.length; i++) {
+ if(runs[i].getShapeId() == shapeId){
+ _txtrun = runs[i];
+ break;
+ }
+ }
+ }
+ }
+}
diff --git a/src/scratchpad/src/org/apache/poi/hslf/record/FontCollection.java b/src/scratchpad/src/org/apache/poi/hslf/record/FontCollection.java index 521e8468b3..c0d55ac0ee 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/record/FontCollection.java +++ b/src/scratchpad/src/org/apache/poi/hslf/record/FontCollection.java @@ -75,16 +75,20 @@ public class FontCollection extends RecordContainer { * @return zero based index of the font in the collection */ public int addFont(String name) { - for (int i = 0; i < fonts.size(); i++) { - if(fonts.get(i).equals(name)){ - //if the font is already present return its index - return i; - } - } + int idx = getFontIndex(name); + if(idx != -1) return idx; + return addFont(name, 0, 0, 4, 34); + } + + public int addFont(String name, int charset, int flags, int type, int pitch) { FontEntityAtom fnt = new FontEntityAtom(); fnt.setFontIndex(fonts.size() << 4); fnt.setFontName(name); + fnt.setCharSet(charset); + fnt.setFontFlags(flags); + fnt.setFontType(type); + fnt.setPitchAndFamily(pitch); fonts.add(name); // Append new child to the end @@ -92,8 +96,25 @@ public class FontCollection extends RecordContainer { return fonts.size()-1; //the added font is the last in the list } - - /** + + /** + * @return zero based index of the font in the collection or -1 if not found + */ + public int getFontIndex(String name) { + for (int i = 0; i < fonts.size(); i++) { + if(fonts.get(i).equals(name)){ + //if the font is already present return its index + return i; + } + } + return -1; + } + + public int getNumberOfFonts() { + return fonts.size(); + } + + /** * Get the name of the font at the given ID, or null if there is * no font at that ID. * @param id diff --git a/src/scratchpad/src/org/apache/poi/hslf/record/FontEntityAtom.java b/src/scratchpad/src/org/apache/poi/hslf/record/FontEntityAtom.java index e4899bd6e1..76cb4c264b 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/record/FontEntityAtom.java +++ b/src/scratchpad/src/org/apache/poi/hslf/record/FontEntityAtom.java @@ -61,7 +61,7 @@ public class FontEntityAtom extends RecordAtom { /** * Create a new instance of <code>FontEntityAtom</code> */ - protected FontEntityAtom() { + public FontEntityAtom() { _recdata = new byte[68]; _header = new byte[8]; @@ -124,15 +124,100 @@ public class FontEntityAtom extends RecordAtom { } } - protected void setFontIndex(int idx){ + public void setFontIndex(int idx){ LittleEndian.putShort(_header, 0, (short)idx); } - protected int getFontIndex(){ - return LittleEndian.getShort(_header, 0); + public int getFontIndex(){ + return LittleEndian.getShort(_header, 0) >> 4; } - /** + /** + * set the character set + * + * @param charset - characterset + */ + public void setCharSet(int charset){ + _recdata[64] = (byte)charset; + } + + /** + * get the character set + * + * @return charset - characterset + */ + public int getCharSet(){ + return _recdata[64]; + } + + /** + * set the font flags + * Bit 1: If set, font is subsetted + * + * @param flags - the font flags + */ + public void setFontFlags(int flags){ + _recdata[65] = (byte)flags; + } + + /** + * get the character set + * Bit 1: If set, font is subsetted + * + * @return the font flags + */ + public int getFontFlags(){ + return _recdata[65]; + } + + /** + * set the font type + * <p> + * Bit 1: Raster Font + * Bit 2: Device Font + * Bit 3: TrueType Font + * </p> + * + * @param type - the font type + */ + public void setFontType(int type){ + _recdata[66] = (byte)type; + } + + /** + * get the font type + * <p> + * Bit 1: Raster Font + * Bit 2: Device Font + * Bit 3: TrueType Font + * </p> + * + * @return the font type + */ + public int getFontType(){ + return _recdata[66]; + } + + /** + * set lfPitchAndFamily + * + * + * @param val - Corresponds to the lfPitchAndFamily field of the Win32 API LOGFONT structure + */ + public void setPitchAndFamily(int val){ + _recdata[67] = (byte)val; + } + + /** + * get lfPitchAndFamily + * + * @return corresponds to the lfPitchAndFamily field of the Win32 API LOGFONT structure + */ + public int getPitchAndFamily(){ + return _recdata[67]; + } + + /** * Write the contents of the record back, so it can be written to disk */ public void writeOut(OutputStream out) throws IOException { diff --git a/src/scratchpad/src/org/apache/poi/hslf/record/RecordTypes.java b/src/scratchpad/src/org/apache/poi/hslf/record/RecordTypes.java index 69173bf5bb..a1bc499453 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/record/RecordTypes.java +++ b/src/scratchpad/src/org/apache/poi/hslf/record/RecordTypes.java @@ -92,7 +92,7 @@ public class RecordTypes { public static final Type TextBookmarkAtom = new Type(4007,null); public static final Type TextBytesAtom = new Type(4008,TextBytesAtom.class); public static final Type TxSIStyleAtom = new Type(4009,null); - public static final Type TextSpecInfoAtom = new Type(4010,null); + public static final Type TextSpecInfoAtom = new Type(4010, TextSpecInfoAtom.class); public static final Type DefaultRulerAtom = new Type(4011,null); public static final Type FontEntityAtom = new Type(4023,FontEntityAtom.class); public static final Type FontEmbeddedData = new Type(4024,null); diff --git a/src/scratchpad/src/org/apache/poi/hslf/record/TextSpecInfoAtom.java b/src/scratchpad/src/org/apache/poi/hslf/record/TextSpecInfoAtom.java new file mode 100755 index 0000000000..a8915f0498 --- /dev/null +++ b/src/scratchpad/src/org/apache/poi/hslf/record/TextSpecInfoAtom.java @@ -0,0 +1,85 @@ +/* ====================================================================
+ 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.hslf.record;
+
+import org.apache.poi.util.LittleEndian;
+
+import java.io.OutputStream;
+import java.io.IOException;
+
+/**
+ * The special info runs contained in this text.
+ * Special info runs consist of character properties which don?t follow styles.
+ *
+ * @author Yegor Kozlov
+ */
+public class TextSpecInfoAtom extends RecordAtom {
+ /**
+ * Record header.
+ */
+ private byte[] _header;
+
+ /**
+ * Record data.
+ */
+ private byte[] _data;
+
+ /**
+ * Constructs the link related atom record from its
+ * source data.
+ *
+ * @param source the source data as a byte array.
+ * @param start the start offset into the byte array.
+ * @param len the length of the slice in the byte array.
+ */
+ protected TextSpecInfoAtom(byte[] source, int start, int len) {
+ // Get the header.
+ _header = new byte[8];
+ System.arraycopy(source,start,_header,0,8);
+
+ // Get the record data.
+ _data = new byte[len-8];
+ System.arraycopy(source,start+8,_data,0,len-8);
+
+ }
+ /**
+ * Gets the record type.
+ * @return the record type.
+ */
+ public long getRecordType() { return RecordTypes.TextSpecInfoAtom.typeID; }
+
+ /**
+ * Write the contents of the record back, so it can be written
+ * to disk
+ *
+ * @param out the output stream to write to.
+ * @throws java.io.IOException if an error occurs.
+ */
+ public void writeOut(OutputStream out) throws IOException {
+ out.write(_header);
+ out.write(_data);
+ }
+
+ /**
+ * Update the text length
+ *
+ * @param size the text length
+ */
+ public void setTextSize(int size){
+ LittleEndian.putInt(_data, 0, size);
+ }
+}
diff --git a/src/scratchpad/src/org/apache/poi/hslf/usermodel/SlideShow.java b/src/scratchpad/src/org/apache/poi/hslf/usermodel/SlideShow.java index 9ce9a12c9d..21e30ac2a9 100644 --- a/src/scratchpad/src/org/apache/poi/hslf/usermodel/SlideShow.java +++ b/src/scratchpad/src/org/apache/poi/hslf/usermodel/SlideShow.java @@ -757,4 +757,50 @@ public class SlideShow } return addPicture(data, format); } + + /** + * Add a font in this presentation + * + * @param font the font to add + * @return 0-based index of the font + */ + public int addFont(PPFont font) { + FontCollection fonts = getDocumentRecord().getEnvironment().getFontCollection(); + int idx = fonts.getFontIndex(font.getFontName()); + if(idx == -1){ + idx = fonts.addFont(font.getFontName(), font.getCharSet(), font.getFontFlags(), font.getFontType(), font.getPitchAndFamily()); + } + return idx; + } + + /** + * Get a font by index + * + * @param idx 0-based index of the font + * @return of an instance of <code>PPFont</code> or <code>null</code> if not found + */ + public PPFont getFont(int idx) { + PPFont font = null; + FontCollection fonts = getDocumentRecord().getEnvironment().getFontCollection(); + Record[] ch = fonts.getChildRecords(); + for (int i = 0; i < ch.length; i++) { + if(ch[i] instanceof FontEntityAtom) { + FontEntityAtom atom = (FontEntityAtom)ch[i]; + if(atom.getFontIndex() == idx){ + font = new PPFont(atom); + break; + } + } + } + return font; + } + + /** + * get the number of fonts in the presentation + * + * @return number of fonts + */ + public int getNumberOfFonts() { + return getDocumentRecord().getEnvironment().getFontCollection().getNumberOfFonts(); + } } diff --git a/src/scratchpad/testcases/org/apache/poi/hslf/data/empty.ppt b/src/scratchpad/testcases/org/apache/poi/hslf/data/empty.ppt Binary files differindex 23e1e94ca8..20d2398e39 100644 --- a/src/scratchpad/testcases/org/apache/poi/hslf/data/empty.ppt +++ b/src/scratchpad/testcases/org/apache/poi/hslf/data/empty.ppt diff --git a/src/scratchpad/testcases/org/apache/poi/hslf/data/text_shapes.ppt b/src/scratchpad/testcases/org/apache/poi/hslf/data/text_shapes.ppt Binary files differnew file mode 100755 index 0000000000..c36183ac35 --- /dev/null +++ b/src/scratchpad/testcases/org/apache/poi/hslf/data/text_shapes.ppt diff --git a/src/scratchpad/testcases/org/apache/poi/hslf/model/TestPPFont.java b/src/scratchpad/testcases/org/apache/poi/hslf/model/TestPPFont.java new file mode 100755 index 0000000000..b6864ea16b --- /dev/null +++ b/src/scratchpad/testcases/org/apache/poi/hslf/model/TestPPFont.java @@ -0,0 +1,56 @@ +
+/* ====================================================================
+ 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.hslf.model;
+
+import junit.framework.TestCase;
+import org.apache.poi.hslf.usermodel.SlideShow;
+
+import java.io.IOException;
+
+/**
+ * Test adding fonts to the presenataion resources
+ *
+ * @author Yegor Kozlov
+ */
+public class TestPPFont extends TestCase{
+
+ public void testCreate() throws IOException {
+ SlideShow ppt = new SlideShow();
+ assertEquals(1, ppt.getNumberOfFonts());
+ assertEquals("Arial", ppt.getFont(0).getFontName());
+
+ //adding the same font twice
+ assertEquals(0, ppt.addFont(PPFont.ARIAL));
+ assertEquals(1, ppt.getNumberOfFonts());
+
+ assertEquals(1, ppt.addFont(PPFont.TIMES_NEW_ROMAN));
+ assertEquals(2, ppt.addFont(PPFont.COURIER_NEW));
+ assertEquals(3, ppt.addFont(PPFont.WINGDINGS));
+
+ assertEquals(4, ppt.getNumberOfFonts());
+
+ assertEquals(PPFont.TIMES_NEW_ROMAN.getFontName(), ppt.getFont(1).getFontName());
+ assertEquals(PPFont.COURIER_NEW.getFontName(), ppt.getFont(2).getFontName());
+
+ PPFont font3 = ppt.getFont(3);
+ assertEquals(PPFont.WINGDINGS.getFontName(), font3.getFontName());
+ assertEquals(PPFont.SYMBOL_CHARSET, font3.getCharSet());
+ assertEquals(PPFont.VARIABLE_PITCH, font3.getPitchAndFamily());
+ }
+}
diff --git a/src/scratchpad/testcases/org/apache/poi/hslf/model/TestShapes.java b/src/scratchpad/testcases/org/apache/poi/hslf/model/TestShapes.java index 1fe8f7e5e6..c2e081ee5c 100644 --- a/src/scratchpad/testcases/org/apache/poi/hslf/model/TestShapes.java +++ b/src/scratchpad/testcases/org/apache/poi/hslf/model/TestShapes.java @@ -218,8 +218,8 @@ public class TestShapes extends TestCase { ArrayList lst2 = new ArrayList(); Shape[] sh = sl[k].getShapes(); for (int i = 0; i < sh.length; i++) { - if (sh[i] instanceof TextBox){ - TextBox tbox = (TextBox)sh[i]; + if (sh[i] instanceof TextShape){ + TextShape tbox = (TextShape)sh[i]; lst2.add(tbox.getText()); } } diff --git a/src/scratchpad/testcases/org/apache/poi/hslf/model/TestTextShape.java b/src/scratchpad/testcases/org/apache/poi/hslf/model/TestTextShape.java new file mode 100755 index 0000000000..25a8db9187 --- /dev/null +++ b/src/scratchpad/testcases/org/apache/poi/hslf/model/TestTextShape.java @@ -0,0 +1,160 @@ +
+/* ====================================================================
+ 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.hslf.model;
+
+import junit.framework.TestCase;
+
+import java.io.*;
+import java.util.ArrayList;
+
+import org.apache.poi.hslf.usermodel.SlideShow;
+import org.apache.poi.hslf.record.TextHeaderAtom;
+
+/**
+ * Verify behavior of <code>TextShape</code> and its sub-classes
+ *
+ * @author Yegor Kozlov
+ */
+public class TestTextShape extends TestCase {
+ protected String cwd = System.getProperty("HSLF.testdata.path");
+
+ public void testCreateAutoShape(){
+ TextShape shape = new AutoShape(ShapeTypes.Trapezoid);
+ assertNull(shape.getTextRun());
+ assertNull(shape.getText());
+ assertNull(shape.getEscherTextboxWrapper());
+
+ TextRun run = shape.createTextRun();
+ assertNotNull(run);
+ assertNotNull(shape.getTextRun());
+ assertNotNull(shape.getEscherTextboxWrapper());
+ assertEquals("", shape.getText());
+ assertSame(run, shape.createTextRun());
+
+ }
+
+ public void testCreateTextBox(){
+ TextShape shape = new TextBox();
+ TextRun run = shape.getTextRun();
+ assertNotNull(run);
+ assertNotNull(shape.getText());
+ assertNotNull(shape.getEscherTextboxWrapper());
+
+ assertSame(run, shape.createTextRun());
+ assertNotNull(shape.getTextRun());
+ assertNotNull(shape.getEscherTextboxWrapper());
+ assertEquals("", shape.getText());
+
+ }
+
+ /**
+ * Verify we can get text from TextShape in the following cases:
+ * - placeholders
+ * - normal TextBox object
+ * - text in auto-shapes
+ */
+ public void testRead() throws IOException {
+ FileInputStream is = new FileInputStream(new File(cwd, "text_shapes.ppt"));
+ SlideShow ppt = new SlideShow(is);
+ is.close();
+
+ ArrayList lst1 = new ArrayList();
+ Slide slide = ppt.getSlides()[0];
+ Shape[] shape = slide.getShapes();
+ for (int i = 0; i < shape.length; i++) {
+ assertTrue("Expected TextShape but found " + shape[i].getClass().getName(), shape[i] instanceof TextShape);
+ TextShape tx = (TextShape)shape[i];
+ TextRun run = tx.getTextRun();
+ assertNotNull(run);
+ int runType = run.getRunType();
+
+ int type = shape[i].getShapeType();
+ switch (type){
+ case ShapeTypes.TextBox:
+ assertEquals("Text in a TextBox", run.getText());
+ break;
+ case ShapeTypes.Rectangle:
+ if(runType == TextHeaderAtom.OTHER_TYPE)
+ assertEquals("Rectangle", run.getText());
+ else if(runType == TextHeaderAtom.TITLE_TYPE)
+ assertEquals("Title Placeholder", run.getText());
+ break;
+ case ShapeTypes.Octagon:
+ assertEquals("Octagon", run.getText());
+ break;
+ case ShapeTypes.Ellipse:
+ assertEquals("Ellipse", run.getText());
+ break;
+ case ShapeTypes.RoundRectangle:
+ assertEquals("RoundRectangle", run.getText());
+ break;
+ default:
+ fail("Unexpected shape: " + shape[i].getShapeName());
+
+ }
+ lst1.add(run.getText());
+ }
+
+ ArrayList lst2 = new ArrayList();
+ TextRun[] run = slide.getTextRuns();
+ for (int i = 0; i < run.length; i++) {
+ lst2.add(run[i].getText());
+ }
+
+ assertTrue(lst1.containsAll(lst2));
+ }
+
+ public void testReadWrite() throws IOException {
+ SlideShow ppt = new SlideShow();
+ Slide slide = ppt.createSlide();
+
+ TextShape shape1 = new TextBox();
+ TextRun run1 = shape1.createTextRun();
+ run1.setText("Hello, World!");
+ slide.addShape(shape1);
+
+ shape1.moveTo(100, 100);
+
+ TextShape shape2 = new AutoShape(ShapeTypes.Arrow);
+ TextRun run2 = shape2.createTextRun();
+ run2.setText("Testing TextShape");
+ slide.addShape(shape2);
+ shape2.moveTo(300, 300);
+
+ ByteArrayOutputStream out = new ByteArrayOutputStream();
+ ppt.write(out);
+ out.close();
+
+ ppt = new SlideShow(new ByteArrayInputStream(out.toByteArray()));
+ slide = ppt.getSlides()[0];
+ Shape[] shape = slide.getShapes();
+
+ assertTrue(shape[0] instanceof TextShape);
+ shape1 = (TextShape)shape[0];
+ assertEquals(ShapeTypes.TextBox, shape1.getShapeType());
+ assertEquals("Hello, World!", shape1.getTextRun().getText());
+
+ assertTrue(shape[1] instanceof TextShape);
+ shape1 = (TextShape)shape[1];
+ assertEquals(ShapeTypes.Arrow, shape1.getShapeType());
+ assertEquals("Testing TextShape", shape1.getTextRun().getText());
+ }
+
+}
diff --git a/src/scratchpad/testcases/org/apache/poi/hslf/usermodel/TestBugs.java b/src/scratchpad/testcases/org/apache/poi/hslf/usermodel/TestBugs.java index 36e45501ec..19e7af6417 100644 --- a/src/scratchpad/testcases/org/apache/poi/hslf/usermodel/TestBugs.java +++ b/src/scratchpad/testcases/org/apache/poi/hslf/usermodel/TestBugs.java @@ -316,8 +316,8 @@ public class TestBugs extends TestCase { ArrayList lst = new ArrayList();
Shape[] shape = slide.getShapes();
for (int i = 0; i < shape.length; i++) {
- if( shape[i] instanceof TextBox){
- TextRun textRun = ((TextBox)shape[i]).getTextRun();
+ if( shape[i] instanceof TextShape){
+ TextRun textRun = ((TextShape)shape[i]).getTextRun();
if(textRun != null) lst.add(textRun);
}
diff --git a/src/testcases/org/apache/poi/hssf/model/TestFormulaParser.java b/src/testcases/org/apache/poi/hssf/model/TestFormulaParser.java index 2589aa90dd..31b4dd180a 100644 --- a/src/testcases/org/apache/poi/hssf/model/TestFormulaParser.java +++ b/src/testcases/org/apache/poi/hssf/model/TestFormulaParser.java @@ -142,7 +142,7 @@ public final class TestFormulaParser extends TestCase { assertEquals(true, flag.getValue()); assertEquals("Y", y.getValue()); assertEquals("N", n.getValue()); - assertEquals("IF", funif.toFormulaString((Workbook) null)); + assertEquals("IF", funif.toFormulaString((HSSFWorkbook) null)); assertTrue("Goto ptg exists", goto1.isGoto()); } @@ -283,7 +283,7 @@ public final class TestFormulaParser extends TestCase { } public void testMacroFunction() { - Workbook w = Workbook.createWorkbook(); + HSSFWorkbook w = new HSSFWorkbook(); FormulaParser fp = new FormulaParser("FOO()", w); fp.parse(); Ptg[] ptg = fp.getRPNPtg(); @@ -589,8 +589,7 @@ public final class TestFormulaParser extends TestCase { * a formula consisting of a single no-arg function got rendered without the function braces */ public void testToFormulaStringZeroArgFunction() { - - Workbook book = Workbook.createWorkbook(); // not really used in this test + HSSFWorkbook book = new HSSFWorkbook(); Ptg[] ptgs = { new FuncPtg(10, 0), @@ -889,7 +888,7 @@ public final class TestFormulaParser extends TestCase { } } public void testFuncPtgSelection() { - Workbook book = Workbook.createWorkbook(); + HSSFWorkbook book = new HSSFWorkbook(); Ptg[] ptgs; ptgs = FormulaParser.parse("countif(A1:A2, 1)", book); assertEquals(3, ptgs.length); diff --git a/src/testcases/org/apache/poi/hssf/record/TestCFRuleRecord.java b/src/testcases/org/apache/poi/hssf/record/TestCFRuleRecord.java index 8f7593f09f..afc44e7043 100644 --- a/src/testcases/org/apache/poi/hssf/record/TestCFRuleRecord.java +++ b/src/testcases/org/apache/poi/hssf/record/TestCFRuleRecord.java @@ -19,11 +19,11 @@ package org.apache.poi.hssf.record; import junit.framework.TestCase; -import org.apache.poi.hssf.model.Workbook; import org.apache.poi.hssf.record.CFRuleRecord.ComparisonOperator; import org.apache.poi.hssf.record.cf.BorderFormatting; import org.apache.poi.hssf.record.cf.FontFormatting; import org.apache.poi.hssf.record.cf.PatternFormatting; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.hssf.util.HSSFColor; import org.apache.poi.util.LittleEndian; @@ -38,7 +38,7 @@ public final class TestCFRuleRecord extends TestCase public void testCreateCFRuleRecord () { - Workbook workbook = Workbook.createWorkbook(); + HSSFWorkbook workbook = new HSSFWorkbook(); CFRuleRecord record = CFRuleRecord.create(workbook, "7"); testCFRuleRecord(record); @@ -278,7 +278,7 @@ public final class TestCFRuleRecord extends TestCase } public void testWrite() { - Workbook workbook = Workbook.createWorkbook(); + HSSFWorkbook workbook = new HSSFWorkbook(); CFRuleRecord rr = CFRuleRecord.create(workbook, ComparisonOperator.BETWEEN, "5", "10"); PatternFormatting patternFormatting = new PatternFormatting(); @@ -293,7 +293,8 @@ public final class TestCFRuleRecord extends TestCase int flags = LittleEndian.getInt(data, 10); assertEquals("unused flags should be 111", 0x00380000, flags & 0x00380000); assertEquals("undocumented flags should be 0000", 0, flags & 0x03C00000); // Otherwise Excel gets unhappy - assertEquals(0xA03FFFFF, flags); + // check all remaining flag bits (some are not well understood yet) + assertEquals(0x203FFFFF, flags); } diff --git a/src/testcases/org/apache/poi/hssf/record/aggregates/TestCFRecordsAggregate.java b/src/testcases/org/apache/poi/hssf/record/aggregates/TestCFRecordsAggregate.java index f605097768..2ae8230d5e 100644 --- a/src/testcases/org/apache/poi/hssf/record/aggregates/TestCFRecordsAggregate.java +++ b/src/testcases/org/apache/poi/hssf/record/aggregates/TestCFRecordsAggregate.java @@ -24,12 +24,12 @@ import java.util.List; import junit.framework.TestCase; -import org.apache.poi.hssf.model.Workbook; import org.apache.poi.hssf.record.CFHeaderRecord; import org.apache.poi.hssf.record.CFRuleRecord; import org.apache.poi.hssf.record.RecordFactory; import org.apache.poi.hssf.record.CFRuleRecord.ComparisonOperator; import org.apache.poi.hssf.record.cf.CellRange; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * Tests the serialization and deserialization of the CFRecordsAggregate @@ -42,7 +42,7 @@ public final class TestCFRecordsAggregate extends TestCase public void testCFRecordsAggregate() { - Workbook workbook = Workbook.createWorkbook(); + HSSFWorkbook workbook = new HSSFWorkbook(); List recs = new ArrayList(); CFHeaderRecord header = new CFHeaderRecord(); CFRuleRecord rule1 = CFRuleRecord.create(workbook, "7"); diff --git a/src/testcases/org/apache/poi/hssf/record/formula/AbstractPtgTestCase.java b/src/testcases/org/apache/poi/hssf/record/formula/AbstractPtgTestCase.java index b8d223a4a8..db29380a9c 100644 --- a/src/testcases/org/apache/poi/hssf/record/formula/AbstractPtgTestCase.java +++ b/src/testcases/org/apache/poi/hssf/record/formula/AbstractPtgTestCase.java @@ -51,13 +51,9 @@ public abstract class AbstractPtgTestCase extends TestCase { /** * Creates a new Workbook and adds one sheet with the specified name */ - protected static final Workbook createWorkbookWithSheet(String sheetName) { - - Workbook book = Workbook.createWorkbook(); - // this creates sheet if it doesn't exist - book.checkExternSheet(0); - // TODO - this call alone does not create the sheet even though the javadoc says it does - book.setSheetName(0, sheetName); + protected static final HSSFWorkbook createWorkbookWithSheet(String sheetName) { + HSSFWorkbook book = new HSSFWorkbook(); + book.createSheet(sheetName); return book; } } diff --git a/src/testcases/org/apache/poi/hssf/record/formula/TestArea3DPtg.java b/src/testcases/org/apache/poi/hssf/record/formula/TestArea3DPtg.java index 2af50d4b93..e83a59b42d 100644 --- a/src/testcases/org/apache/poi/hssf/record/formula/TestArea3DPtg.java +++ b/src/testcases/org/apache/poi/hssf/record/formula/TestArea3DPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * Tests for Area3DPtg @@ -35,7 +35,7 @@ public final class TestArea3DPtg extends AbstractPtgTestCase { Area3DPtg target = new Area3DPtg("A1:B1", (short)0); String sheetName = "my sheet"; - Workbook book = createWorkbookWithSheet(sheetName); + HSSFWorkbook book = createWorkbookWithSheet(sheetName); assertEquals("'my sheet'!A1:B1", target.toFormulaString(book)); book.setSheetName(0, "Sheet1"); @@ -44,7 +44,4 @@ public final class TestArea3DPtg extends AbstractPtgTestCase { book.setSheetName(0, "C64"); assertEquals("'C64'!A1:B1", target.toFormulaString(book)); } - - - } diff --git a/src/testcases/org/apache/poi/hssf/record/formula/TestRef3DPtg.java b/src/testcases/org/apache/poi/hssf/record/formula/TestRef3DPtg.java index b5fbe3b80d..4de0c7bdb2 100644 --- a/src/testcases/org/apache/poi/hssf/record/formula/TestRef3DPtg.java +++ b/src/testcases/org/apache/poi/hssf/record/formula/TestRef3DPtg.java @@ -18,7 +18,7 @@ package org.apache.poi.hssf.record.formula; -import org.apache.poi.hssf.model.Workbook; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * Tests for Ref3DPtg @@ -31,7 +31,7 @@ public final class TestRef3DPtg extends AbstractPtgTestCase { Ref3DPtg target = new Ref3DPtg("A1", (short)0); - Workbook book = createWorkbookWithSheet("my sheet"); + HSSFWorkbook book = createWorkbookWithSheet("my sheet"); assertEquals("'my sheet'!A1", target.toFormulaString(book)); diff --git a/src/testcases/org/apache/poi/hssf/record/formula/function/TestParseMissingBuiltInFuncs.java b/src/testcases/org/apache/poi/hssf/record/formula/function/TestParseMissingBuiltInFuncs.java index fdad5f44d8..1e26fa706e 100644 --- a/src/testcases/org/apache/poi/hssf/record/formula/function/TestParseMissingBuiltInFuncs.java +++ b/src/testcases/org/apache/poi/hssf/record/formula/function/TestParseMissingBuiltInFuncs.java @@ -26,6 +26,7 @@ import org.apache.poi.hssf.record.formula.AbstractFunctionPtg; import org.apache.poi.hssf.record.formula.FuncPtg; import org.apache.poi.hssf.record.formula.FuncVarPtg; import org.apache.poi.hssf.record.formula.Ptg; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; /** * Tests parsing of some built-in functions that were not properly * registered in POI as bug #44675, #44733 (March/April 2008). @@ -35,7 +36,7 @@ import org.apache.poi.hssf.record.formula.Ptg; public final class TestParseMissingBuiltInFuncs extends TestCase { private static Ptg[] parse(String formula) { - Workbook book = Workbook.createWorkbook(); + HSSFWorkbook book = new HSSFWorkbook(); return FormulaParser.parse(formula, book); } private static void confirmFunc(String formula, int expPtgArraySize, boolean isVarArgFunc, int funcIx) { @@ -57,7 +58,7 @@ public final class TestParseMissingBuiltInFuncs extends TestCase { assertEquals(expCls, ptgF.getClass()); // check that parsed Ptg array converts back to formula text OK - Workbook book = Workbook.createWorkbook(); + HSSFWorkbook book = new HSSFWorkbook(); String reRenderedFormula = FormulaParser.toFormulaString(book, ptgs); assertEquals(formula, reRenderedFormula); } diff --git a/src/testcases/org/apache/poi/hssf/usermodel/TestFormulaEvaluatorBugs.java b/src/testcases/org/apache/poi/hssf/usermodel/TestFormulaEvaluatorBugs.java index 007cbd5760..19069d32b2 100644 --- a/src/testcases/org/apache/poi/hssf/usermodel/TestFormulaEvaluatorBugs.java +++ b/src/testcases/org/apache/poi/hssf/usermodel/TestFormulaEvaluatorBugs.java @@ -203,7 +203,7 @@ public final class TestFormulaEvaluatorBugs extends TestCase { assertEquals(2, ptg.getLastColumn()); assertEquals(0, ptg.getFirstRow()); assertEquals(65535, ptg.getLastRow()); - assertEquals("C:C", ptg.toFormulaString(wb.getWorkbook())); + assertEquals("C:C", ptg.toFormulaString(wb)); // Will show as C:C, but won't know how many // rows it covers as we don't have the sheet diff --git a/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFConditionalFormatting.java b/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFConditionalFormatting.java index 930970ea22..6dbcf815dc 100644 --- a/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFConditionalFormatting.java +++ b/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFConditionalFormatting.java @@ -34,22 +34,26 @@ public final class TestHSSFConditionalFormatting extends TestCase HSSFSheet sheet = workbook.createSheet(); String formula = "7"; - HSSFFontFormatting fontFmt = new HSSFFontFormatting(); + HSSFSheetConditionalFormatting sheetCF = sheet.getSheetConditionalFormatting(); + + HSSFConditionalFormattingRule rule1 = sheetCF.createConditionalFormattingRule(formula); + HSSFFontFormatting fontFmt = rule1.createFontFormatting(); fontFmt.setFontStyle(true, false); - HSSFBorderFormatting bordFmt = new HSSFBorderFormatting(); + HSSFBorderFormatting bordFmt = rule1.createBorderFormatting(); bordFmt.setBorderBottom(HSSFBorderFormatting.BORDER_THIN); bordFmt.setBorderTop(HSSFBorderFormatting.BORDER_THICK); bordFmt.setBorderLeft(HSSFBorderFormatting.BORDER_DASHED); bordFmt.setBorderRight(HSSFBorderFormatting.BORDER_DOTTED); - HSSFPatternFormatting patternFmt = new HSSFPatternFormatting(); - patternFmt.setFillBackgroundColor(HSSFColor.RED.index); + HSSFPatternFormatting patternFmt = rule1.createPatternFormatting(); + patternFmt.setFillBackgroundColor(HSSFColor.YELLOW.index); + + HSSFConditionalFormattingRule rule2 = sheetCF.createConditionalFormattingRule(ComparisonOperator.BETWEEN, "1", "2"); HSSFConditionalFormattingRule [] cfRules = { - sheet.createConditionalFormattingRule(formula, fontFmt, bordFmt, patternFmt), - sheet.createConditionalFormattingRule(ComparisonOperator.BETWEEN, "1", "2", fontFmt, bordFmt, patternFmt) + rule1, rule2 }; short col = 1; @@ -58,14 +62,14 @@ public final class TestHSSFConditionalFormatting extends TestCase new Region(0,col,65535,col) }; - sheet.addConditionalFormatting(regions, cfRules); - sheet.addConditionalFormatting(regions, cfRules); + sheetCF.addConditionalFormatting(regions, cfRules); + sheetCF.addConditionalFormatting(regions, cfRules); // Verification - assertEquals(2, sheet.getNumConditionalFormattings()); - sheet.removeConditionalFormatting(1); - assertEquals(1, sheet.getNumConditionalFormattings()); - HSSFConditionalFormatting cf = sheet.getConditionalFormattingAt(0); + assertEquals(2, sheetCF.getNumConditionalFormattings()); + sheetCF.removeConditionalFormatting(1); + assertEquals(1, sheetCF.getNumConditionalFormattings()); + HSSFConditionalFormatting cf = sheetCF.getConditionalFormattingAt(0); assertNotNull(cf); regions = cf.getFormattingRegions(); @@ -79,7 +83,7 @@ public final class TestHSSFConditionalFormatting extends TestCase assertEquals(2, cf.getNumberOfRules()); - HSSFConditionalFormattingRule rule1 = cf.getRule(0); + rule1 = cf.getRule(0); assertEquals("7",rule1.getFormula1()); assertNull(rule1.getFormula2()); @@ -98,11 +102,10 @@ public final class TestHSSFConditionalFormatting extends TestCase HSSFPatternFormatting r1pf = rule1.getPatternFormatting(); assertNotNull(r1pf); - assertEquals(HSSFColor.RED.index,r1pf.getFillBackgroundColor()); + assertEquals(HSSFColor.YELLOW.index,r1pf.getFillBackgroundColor()); - HSSFConditionalFormattingRule rule2 = cf.getRule(1); + rule2 = cf.getRule(1); assertEquals("2",rule2.getFormula2()); assertEquals("1",rule2.getFormula1()); } - } diff --git a/src/testcases/org/apache/poi/hssf/util/TestAreaReference.java b/src/testcases/org/apache/poi/hssf/util/TestAreaReference.java index a72c039cb8..5eb2abb6e6 100644 --- a/src/testcases/org/apache/poi/hssf/util/TestAreaReference.java +++ b/src/testcases/org/apache/poi/hssf/util/TestAreaReference.java @@ -211,12 +211,12 @@ public final class TestAreaReference extends TestCase { Area3DPtg ptgB = (Area3DPtg)def.get(1); Area3DPtg ptgC = (Area3DPtg)def.get(2); UnionPtg ptgD = (UnionPtg)def.get(3); - assertEquals("", ptgA.toFormulaString(workbook)); - assertEquals(refA, ptgB.toFormulaString(workbook)); - assertEquals(refB, ptgC.toFormulaString(workbook)); - assertEquals(",", ptgD.toFormulaString(workbook)); + assertEquals("", ptgA.toFormulaString(wb)); + assertEquals(refA, ptgB.toFormulaString(wb)); + assertEquals(refB, ptgC.toFormulaString(wb)); + assertEquals(",", ptgD.toFormulaString(wb)); - assertEquals(ref, nr.getAreaReference(workbook)); + assertEquals(ref, nr.getAreaReference(wb)); // Check the high level definition int idx = wb.getNameIndex("test"); |