]> source.dussan.org Git - poi.git/commitdiff
Merged revisions 638786-638802,638805-638811,638813-638814,638816-639230,639233-63924...
authorNick Burch <nick@apache.org>
Thu, 7 Aug 2008 18:21:32 +0000 (18:21 +0000)
committerNick Burch <nick@apache.org>
Thu, 7 Aug 2008 18:21:32 +0000 (18:21 +0000)
https://svn.apache.org/repos/asf/poi/trunk

........
  r683023 | josh | 2008-08-06 00:03:33 +0100 (Wed, 06 Aug 2008) | 1 line

  Fix JDK 1.4 compilation (after r682511 /bug 45538)
........
  r683081 | josh | 2008-08-06 02:39:44 +0100 (Wed, 06 Aug 2008) | 1 line

  refactoring aggregate records to a separate hierarchy. just starting
........
  r683093 | josh | 2008-08-06 04:06:18 +0100 (Wed, 06 Aug 2008) | 1 line

  should have been submitted with r683081
........
  r683096 | josh | 2008-08-06 04:23:10 +0100 (Wed, 06 Aug 2008) | 1 line

  should have been submitted with r683081
........
  r683128 | josh | 2008-08-06 07:20:59 +0100 (Wed, 06 Aug 2008) | 1 line

  removed TODO comment and formatted
........
  r683132 | josh | 2008-08-06 07:27:39 +0100 (Wed, 06 Aug 2008) | 1 line

  Partial fix for bug 45570 - Converted instance BitField fields to static
........
  r683167 | josh | 2008-08-06 09:42:40 +0100 (Wed, 06 Aug 2008) | 1 line

  Added conditional format records to BiffViewer
........

git-svn-id: https://svn.apache.org/repos/asf/poi/branches/ooxml@683670 13f79535-47bb-0310-9956-ffa450edef68

57 files changed:
build.xml
src/java/org/apache/poi/hssf/dev/BiffViewer.java
src/java/org/apache/poi/hssf/model/RecordOrderer.java [new file with mode: 0644]
src/java/org/apache/poi/hssf/model/Sheet.java
src/java/org/apache/poi/hssf/record/AreaFormatRecord.java
src/java/org/apache/poi/hssf/record/AreaRecord.java
src/java/org/apache/poi/hssf/record/AxisOptionsRecord.java
src/java/org/apache/poi/hssf/record/BarRecord.java
src/java/org/apache/poi/hssf/record/BoundSheetRecord.java
src/java/org/apache/poi/hssf/record/CFRuleRecord.java
src/java/org/apache/poi/hssf/record/CategorySeriesAxisRecord.java
src/java/org/apache/poi/hssf/record/ChartFormatRecord.java
src/java/org/apache/poi/hssf/record/CommonObjectDataSubRecord.java
src/java/org/apache/poi/hssf/record/DatRecord.java
src/java/org/apache/poi/hssf/record/DataFormatRecord.java
src/java/org/apache/poi/hssf/record/FormulaRecord.java
src/java/org/apache/poi/hssf/record/FrameRecord.java
src/java/org/apache/poi/hssf/record/HorizontalPageBreakRecord.java
src/java/org/apache/poi/hssf/record/LegendRecord.java
src/java/org/apache/poi/hssf/record/LineFormatRecord.java
src/java/org/apache/poi/hssf/record/LinkedDataRecord.java
src/java/org/apache/poi/hssf/record/MergeCellsRecord.java
src/java/org/apache/poi/hssf/record/PageBreakRecord.java
src/java/org/apache/poi/hssf/record/Record.java
src/java/org/apache/poi/hssf/record/RecordBase.java [new file with mode: 0644]
src/java/org/apache/poi/hssf/record/SeriesLabelsRecord.java
src/java/org/apache/poi/hssf/record/SheetPropertiesRecord.java
src/java/org/apache/poi/hssf/record/StyleRecord.java
src/java/org/apache/poi/hssf/record/TableRecord.java
src/java/org/apache/poi/hssf/record/TextObjectBaseRecord.java
src/java/org/apache/poi/hssf/record/TextRecord.java
src/java/org/apache/poi/hssf/record/TickRecord.java
src/java/org/apache/poi/hssf/record/ValueRangeRecord.java
src/java/org/apache/poi/hssf/record/VerticalPageBreakRecord.java
src/java/org/apache/poi/hssf/record/WindowTwoRecord.java
src/java/org/apache/poi/hssf/record/aggregates/CFRecordsAggregate.java
src/java/org/apache/poi/hssf/record/aggregates/ColumnInfoRecordsAggregate.java
src/java/org/apache/poi/hssf/record/aggregates/ConditionalFormattingTable.java [new file with mode: 0644]
src/java/org/apache/poi/hssf/record/aggregates/DataValidityTable.java
src/java/org/apache/poi/hssf/record/aggregates/MergedCellsTable.java [new file with mode: 0644]
src/java/org/apache/poi/hssf/record/aggregates/RecordAggregate.java
src/java/org/apache/poi/hssf/record/formula/Area3DPtg.java
src/java/org/apache/poi/hssf/record/formula/Ref3DPtg.java
src/java/org/apache/poi/hssf/usermodel/HSSFCell.java
src/java/org/apache/poi/hssf/usermodel/HSSFSheet.java
src/java/org/apache/poi/ss/util/CellRangeAddressList.java
src/ooxml/interfaces-jdk15/org/apache/poi/ss/usermodel/Sheet.java
src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFSheet.java
src/scratchpad/src/org/apache/poi/hssf/usermodel/HSSFChart.java
src/scratchpad/testcases/org/apache/poi/hssf/usermodel/TestHSSFChart.java
src/testcases/org/apache/poi/hssf/extractor/TestExcelExtractor.java
src/testcases/org/apache/poi/hssf/model/TestSheet.java
src/testcases/org/apache/poi/hssf/model/TestSheetAdditional.java
src/testcases/org/apache/poi/hssf/record/TestMergeCellsRecord.java
src/testcases/org/apache/poi/hssf/record/aggregates/TestCFRecordsAggregate.java
src/testcases/org/apache/poi/hssf/record/aggregates/TestColumnInfoRecordsAggregate.java
src/testcases/org/apache/poi/hssf/usermodel/TestBugs.java

index dab532f4802616df1fc2ff6f982723f0cfe294c7..abece8810eacfff0b457347877f09983c87500ff 100644 (file)
--- a/build.xml
+++ b/build.xml
@@ -459,7 +459,8 @@ under the License.
       fork="yes" srcdir="${scratchpad.src.test}">
       <classpath>
         <path refid="scratchpad.classpath"/>
-        <pathelement path="${scratchpad.output.dir}"/>
+        <pathelement location="${main.output.test.dir}"/>
+        <pathelement location="${scratchpad.output.dir}"/>
         <pathelement location="${junit.jar1.dir}"/>
       </classpath>
     </javac>
@@ -694,6 +695,7 @@ under the License.
             <classpath>
                 <path refid="scratchpad.classpath"/>
                 <pathelement location="${main.output.dir}"/>
+                <pathelement location="${main.output.test.dir}"/>
                 <pathelement location="${scratchpad.output.dir}"/>
                 <pathelement location="${scratchpad.output.test.dir}"/>
                 <pathelement location="${junit.jar1.dir}"/>
index 175b920881c5eb8774e7b3bf6a7c8bb5796ae629..15177d0d95ab5069926aa37b36c07c9ddc8c9996 100644 (file)
@@ -129,6 +129,8 @@ public final class BiffViewer {
             case BoolErrRecord.sid:        return new BoolErrRecord(in);
             case BottomMarginRecord.sid:   return new BottomMarginRecord(in);
             case BoundSheetRecord.sid:     return new BoundSheetRecord(in);
+            case CFHeaderRecord.sid:       return new CFHeaderRecord(in);
+            case CFRuleRecord.sid:         return new CFRuleRecord(in);
             case CalcCountRecord.sid:      return new CalcCountRecord(in);
             case CalcModeRecord.sid:       return new CalcModeRecord(in);
             case CategorySeriesAxisRecord.sid: return new CategorySeriesAxisRecord(in);
@@ -288,10 +290,10 @@ public final class BiffViewer {
             }
             PrintStream ps;
             if (false) { // set to true to output to file
-               OutputStream os = new FileOutputStream(inFileName + ".out");
-               ps = new PrintStream(os);
+                OutputStream os = new FileOutputStream(inFileName + ".out");
+                ps = new PrintStream(os);
             } else {
-               ps = System.out;
+                ps = System.out;
             }
             BiffViewer viewer = new BiffViewer(inputFile, ps);
 
diff --git a/src/java/org/apache/poi/hssf/model/RecordOrderer.java b/src/java/org/apache/poi/hssf/model/RecordOrderer.java
new file mode 100644 (file)
index 0000000..ae44559
--- /dev/null
@@ -0,0 +1,326 @@
+/* ====================================================================
+   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.model;
+
+import java.util.List;
+
+import org.apache.poi.hssf.record.BOFRecord;
+import org.apache.poi.hssf.record.CalcCountRecord;
+import org.apache.poi.hssf.record.CalcModeRecord;
+import org.apache.poi.hssf.record.DateWindow1904Record;
+import org.apache.poi.hssf.record.DefaultRowHeightRecord;
+import org.apache.poi.hssf.record.DeltaRecord;
+import org.apache.poi.hssf.record.DimensionsRecord;
+import org.apache.poi.hssf.record.EOFRecord;
+import org.apache.poi.hssf.record.GridsetRecord;
+import org.apache.poi.hssf.record.GutsRecord;
+import org.apache.poi.hssf.record.HorizontalPageBreakRecord;
+import org.apache.poi.hssf.record.HyperlinkRecord;
+import org.apache.poi.hssf.record.IndexRecord;
+import org.apache.poi.hssf.record.IterationRecord;
+import org.apache.poi.hssf.record.PaneRecord;
+import org.apache.poi.hssf.record.PrecisionRecord;
+import org.apache.poi.hssf.record.PrintGridlinesRecord;
+import org.apache.poi.hssf.record.PrintHeadersRecord;
+import org.apache.poi.hssf.record.Record;
+import org.apache.poi.hssf.record.RecordBase;
+import org.apache.poi.hssf.record.RefModeRecord;
+import org.apache.poi.hssf.record.SCLRecord;
+import org.apache.poi.hssf.record.SaveRecalcRecord;
+import org.apache.poi.hssf.record.SelectionRecord;
+import org.apache.poi.hssf.record.UncalcedRecord;
+import org.apache.poi.hssf.record.VerticalPageBreakRecord;
+import org.apache.poi.hssf.record.WindowTwoRecord;
+import org.apache.poi.hssf.record.aggregates.ConditionalFormattingTable;
+import org.apache.poi.hssf.record.aggregates.DataValidityTable;
+import org.apache.poi.hssf.record.aggregates.MergedCellsTable;
+
+/**
+ * Finds correct insert positions for records in workbook streams<p/>
+ * 
+ * See OOO excelfileformat.pdf sec. 4.2.5 'Record Order in a BIFF8 Workbook Stream'
+ * 
+ * @author Josh Micich
+ */
+final class RecordOrderer {
+       // TODO - add UninterpretedRecord as base class for many of these
+       // unimplemented sids
+       
+       // TODO - simplify logic using a generalised record ordering
+
+       private RecordOrderer() {
+               // no instances of this class
+       }
+       /**
+        * Adds the specified new record in the correct place in sheet records list
+        * 
+        */
+       public static void addNewSheetRecord(List sheetRecords, RecordBase newRecord) {
+               int index = findSheetInsertPos(sheetRecords, newRecord.getClass());
+               sheetRecords.add(index, newRecord);
+       }
+
+       private static int findSheetInsertPos(List records, Class recClass) {
+               if (recClass == DataValidityTable.class) {
+                       return findDataValidationTableInsertPos(records);
+               }
+               if (recClass == MergedCellsTable.class) {
+                       return findInsertPosForNewMergedRecordTable(records);
+               }
+               if (recClass == ConditionalFormattingTable.class) {
+                       return findInsertPosForNewCondFormatTable(records);
+               }
+               if (recClass == GutsRecord.class) {
+                       return getGutsRecordInsertPos(records);
+               }
+               if (recClass == HorizontalPageBreakRecord.class) {
+                       return getPageBreakRecordInsertPos(records, true);
+               }
+               if (recClass == VerticalPageBreakRecord.class) {
+                       return getPageBreakRecordInsertPos(records, false);
+               }
+               throw new RuntimeException("Unexpected record class (" + recClass.getName() + ")");
+       }
+
+       private static int getPageBreakRecordInsertPos(List records, boolean isHorizonal) {
+               int dimensionsIndex = getDimensionsIndex(records);
+               int i = dimensionsIndex-1;
+               while (i > 0) {
+                       i--;
+                       Object rb = records.get(i);
+                       if (isPageBreakPriorRecord(rb, isHorizonal)) {
+                               return i+1;
+                       }
+               }
+               throw new RuntimeException("Did not find insert point for GUTS");
+       }
+       private static boolean isPageBreakPriorRecord(Object rb, boolean newRecIsHorizontal) {
+               if (rb instanceof Record) {
+                       Record record = (Record) rb;
+                       switch (record.getSid()) {
+                               case BOFRecord.sid:
+                               case IndexRecord.sid:
+                               // calc settings block
+                                       case UncalcedRecord.sid:
+                                       case CalcCountRecord.sid:
+                                       case CalcModeRecord.sid:
+                                       case PrecisionRecord.sid:
+                                       case RefModeRecord.sid:
+                                       case DeltaRecord.sid:
+                                       case IterationRecord.sid:
+                                       case DateWindow1904Record.sid:
+                                       case SaveRecalcRecord.sid:
+                               // end calc settings
+                               case PrintHeadersRecord.sid:
+                               case PrintGridlinesRecord.sid:
+                               case GridsetRecord.sid:
+                               case DefaultRowHeightRecord.sid:
+                               case 0x0081: // SHEETPR
+                                       return true;
+                       }
+                       switch (record.getSid()) {
+                               // page settings block
+                               case HorizontalPageBreakRecord.sid:
+                                       if (!newRecIsHorizontal) {
+                                               return true;
+                                       }
+                                       return false;
+                               case VerticalPageBreakRecord.sid:
+                                       return false;
+                               // next is case HeaderRecord.sid: case FooterRecord.sid:
+                               // then more records in page settings block     
+                       
+                       }
+               }
+               return false;
+       }
+       /**
+        * Find correct position to add new CFHeader record
+        */
+       private static int findInsertPosForNewCondFormatTable(List records) {
+
+               for (int i = records.size() - 2; i >= 0; i--) { // -2 to skip EOF record
+                       Object rb = records.get(i);
+                       if (rb instanceof MergedCellsTable) {
+                               return i + 1;
+                       }
+                       Record rec = (Record) rb;
+                       switch (rec.getSid()) {
+                               case WindowTwoRecord.sid:
+                               case SCLRecord.sid:
+                               case PaneRecord.sid:
+                               case SelectionRecord.sid:
+                               case 0x0099:// STANDARDWIDTH
+                               // MergedCellsTable usually here 
+                               case 0x015f:// LABELRANGES
+                               case 0x00ef:// PHONETICPR
+                                       return i + 1;
+                       }
+               }
+               throw new RuntimeException("Did not find Window2 record");
+       }
+
+       private static int findInsertPosForNewMergedRecordTable(List records) {
+               for (int i = records.size() - 2; i >= 0; i--) { // -2 to skip EOF record
+                       Object rb = records.get(i);
+                       Record rec = (Record) rb;
+                       switch (rec.getSid()) {
+                               case WindowTwoRecord.sid:
+                               case SCLRecord.sid:
+                               case PaneRecord.sid:
+                               case SelectionRecord.sid:
+                               case 0x0099:// STANDARDWIDTH
+                                       return i + 1;
+                       }
+               }
+               throw new RuntimeException("Did not find Window2 record");
+       }
+
+       
+       /**
+        * Finds the index where the sheet validations header record should be inserted
+        * @param records the records for this sheet
+        * 
+        * + WINDOW2
+        * o SCL
+        * o PANE
+        * oo SELECTION
+        * o STANDARDWIDTH
+        * oo MERGEDCELLS
+        * o LABELRANGES
+        * o PHONETICPR
+        * o Conditional Formatting Table
+        * o Hyperlink Table
+        * o Data Validity Table
+        * o SHEETLAYOUT
+        * o SHEETPROTECTION
+        * o RANGEPROTECTION
+        * + EOF
+        */
+       private static int findDataValidationTableInsertPos(List records) {
+               int i = records.size() - 1;
+               if (!(records.get(i) instanceof EOFRecord)) {
+                       throw new IllegalStateException("Last sheet record should be EOFRecord");
+               }
+               while (i > 0) {
+                       i--;
+                       Object rb = records.get(i);
+                       if (isDVTPriorRecord(rb)) {
+                               Record nextRec = (Record) records.get(i + 1);
+                               if (!isDVTSubsequentRecord(nextRec.getSid())) {
+                                       throw new IllegalStateException("Unexpected (" + nextRec.getClass().getName()
+                                                       + ") found after (" + rb.getClass().getName() + ")");
+                               }
+                               return i+1;
+                       }
+                       Record rec = (Record) rb;
+                       if (!isDVTSubsequentRecord(rec.getSid())) {
+                               throw new IllegalStateException("Unexpected (" + rec.getClass().getName()
+                                               + ") while looking for DV Table insert pos");
+                       }
+               }
+               return 0;
+       }
+
+
+       private static boolean isDVTPriorRecord(Object rb) {
+               if (rb instanceof MergedCellsTable || rb instanceof ConditionalFormattingTable) {
+                       return true;
+               }
+               short sid = ((Record)rb).getSid();
+               switch(sid) {
+                       case WindowTwoRecord.sid:
+                       case 0x00A0: // SCL
+                       case PaneRecord.sid:
+                       case SelectionRecord.sid:
+                       case 0x0099: // STANDARDWIDTH
+                       // MergedCellsTable
+                       case 0x015F: // LABELRANGES
+                       case 0x00EF: // PHONETICPR
+                       // ConditionalFormattingTable
+                       case HyperlinkRecord.sid:
+                       case 0x0800: // QUICKTIP
+                               return true;
+               }
+               return false;
+       }
+
+       private static boolean isDVTSubsequentRecord(short sid) {
+               switch(sid) {
+                       case 0x0862: // SHEETLAYOUT
+                       case 0x0867: // SHEETPROTECTION
+                       case 0x0868: // RANGEPROTECTION
+                       case EOFRecord.sid:
+                               return true;
+               }
+               return false;
+       }
+       /**
+        * DIMENSIONS record is always present
+        */
+       private static int getDimensionsIndex(List records) {
+               int nRecs = records.size();
+               for(int i=0; i<nRecs; i++) {
+                       if(records.get(i) instanceof DimensionsRecord) {
+                               return i;
+                       }
+               }
+               // worksheet stream is seriously broken
+               throw new RuntimeException("DimensionsRecord not found");
+       }
+
+       private static int getGutsRecordInsertPos(List records) {
+               int dimensionsIndex = getDimensionsIndex(records);
+               int i = dimensionsIndex-1;
+               while (i > 0) {
+                       i--;
+                       Object rb = records.get(i);
+                       if (isGutsPriorRecord(rb)) {
+                               return i+1;
+                       }
+               }
+               throw new RuntimeException("Did not find insert point for GUTS");
+       }
+
+       private static boolean isGutsPriorRecord(Object rb) {
+               if (rb instanceof Record) {
+                       Record record = (Record) rb;
+                       switch (record.getSid()) {
+                               case BOFRecord.sid:
+                               case IndexRecord.sid:
+                               // calc settings block
+                                       case UncalcedRecord.sid:
+                                       case CalcCountRecord.sid:
+                                       case CalcModeRecord.sid:
+                                       case PrecisionRecord.sid:
+                                       case RefModeRecord.sid:
+                                       case DeltaRecord.sid:
+                                       case IterationRecord.sid:
+                                       case DateWindow1904Record.sid:
+                                       case SaveRecalcRecord.sid:
+                               // end calc settings
+                               case PrintHeadersRecord.sid:
+                               case PrintGridlinesRecord.sid:
+                               case GridsetRecord.sid:
+                                       return true;
+                               // DefaultRowHeightRecord.sid is next
+                       }
+               }
+               return false;
+       }
+}
index 1f9cfdff407fd24332b99afcb39db153bc1ee2d1..a17984b49cbc603d8f8844a319544cbb10262d16 100644 (file)
 
 package org.apache.poi.hssf.model;
 
-import org.apache.poi.hssf.record.*; // normally I don't do this, buy we literally mean ALL
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+import org.apache.poi.hssf.record.BOFRecord;
+import org.apache.poi.hssf.record.BottomMarginRecord;
+import org.apache.poi.hssf.record.CFHeaderRecord;
+import org.apache.poi.hssf.record.CalcCountRecord;
+import org.apache.poi.hssf.record.CalcModeRecord;
+import org.apache.poi.hssf.record.CellValueRecordInterface;
+import org.apache.poi.hssf.record.ColumnInfoRecord;
+import org.apache.poi.hssf.record.DBCellRecord;
+import org.apache.poi.hssf.record.DVALRecord;
+import org.apache.poi.hssf.record.DefaultColWidthRecord;
+import org.apache.poi.hssf.record.DefaultRowHeightRecord;
+import org.apache.poi.hssf.record.DeltaRecord;
+import org.apache.poi.hssf.record.DimensionsRecord;
+import org.apache.poi.hssf.record.DrawingRecord;
+import org.apache.poi.hssf.record.EOFRecord;
+import org.apache.poi.hssf.record.EscherAggregate;
+import org.apache.poi.hssf.record.FooterRecord;
+import org.apache.poi.hssf.record.GridsetRecord;
+import org.apache.poi.hssf.record.GutsRecord;
+import org.apache.poi.hssf.record.HCenterRecord;
+import org.apache.poi.hssf.record.HeaderRecord;
+import org.apache.poi.hssf.record.HorizontalPageBreakRecord;
+import org.apache.poi.hssf.record.IndexRecord;
+import org.apache.poi.hssf.record.IterationRecord;
+import org.apache.poi.hssf.record.LeftMarginRecord;
+import org.apache.poi.hssf.record.Margin;
+import org.apache.poi.hssf.record.MergeCellsRecord;
+import org.apache.poi.hssf.record.ObjRecord;
+import org.apache.poi.hssf.record.ObjectProtectRecord;
+import org.apache.poi.hssf.record.PageBreakRecord;
+import org.apache.poi.hssf.record.PaneRecord;
+import org.apache.poi.hssf.record.PasswordRecord;
+import org.apache.poi.hssf.record.PrintGridlinesRecord;
+import org.apache.poi.hssf.record.PrintHeadersRecord;
+import org.apache.poi.hssf.record.PrintSetupRecord;
+import org.apache.poi.hssf.record.ProtectRecord;
+import org.apache.poi.hssf.record.Record;
+import org.apache.poi.hssf.record.RecordBase;
+import org.apache.poi.hssf.record.RefModeRecord;
+import org.apache.poi.hssf.record.RightMarginRecord;
+import org.apache.poi.hssf.record.RowRecord;
+import org.apache.poi.hssf.record.SCLRecord;
+import org.apache.poi.hssf.record.SaveRecalcRecord;
+import org.apache.poi.hssf.record.ScenarioProtectRecord;
+import org.apache.poi.hssf.record.SelectionRecord;
+import org.apache.poi.hssf.record.SharedFormulaRecord;
+import org.apache.poi.hssf.record.StringRecord;
+import org.apache.poi.hssf.record.TopMarginRecord;
+import org.apache.poi.hssf.record.UncalcedRecord;
+import org.apache.poi.hssf.record.VCenterRecord;
+import org.apache.poi.hssf.record.VerticalPageBreakRecord;
+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.aggregates.ColumnInfoRecordsAggregate;
+import org.apache.poi.hssf.record.aggregates.ConditionalFormattingTable;
 import org.apache.poi.hssf.record.aggregates.DataValidityTable;
 import org.apache.poi.hssf.record.aggregates.FormulaRecordAggregate;
+import org.apache.poi.hssf.record.aggregates.MergedCellsTable;
+import org.apache.poi.hssf.record.aggregates.RecordAggregate;
 import org.apache.poi.hssf.record.aggregates.RowRecordsAggregate;
 import org.apache.poi.hssf.record.aggregates.ValueRecordsAggregate;
-import org.apache.poi.hssf.record.aggregates.CFRecordsAggregate;
+import org.apache.poi.hssf.record.aggregates.RecordAggregate.RecordVisitor;
 import org.apache.poi.ss.util.CellRangeAddress;
 import org.apache.poi.hssf.util.PaneInformation;
-
 import org.apache.poi.util.POILogFactory;
 import org.apache.poi.util.POILogger;
 
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;   
-
 /**
  * Low level model implementation of a Sheet (one workbook contains many sheets)
  * This file contains the low level binary records starting at the sheets BOF and
@@ -72,30 +127,30 @@ public final class Sheet implements Model {
     protected DefaultColWidthRecord      defaultcolwidth   =     null;
     protected DefaultRowHeightRecord     defaultrowheight  =     null;
     protected GridsetRecord              gridset           =     null;
+       private   GutsRecord                 _gutsRecord;
     protected PrintSetupRecord           printSetup        =     null;
     protected HeaderRecord               header            =     null;
     protected FooterRecord               footer            =     null;
     protected PrintGridlinesRecord       printGridlines    =     null;
     protected WindowTwoRecord            windowTwo         =     null;
-    protected MergeCellsRecord           merged            =     null;
     protected Margin[]                   margins           =     null;
-    protected List                       mergedRecords     =     new ArrayList();
-    protected int                        numMergedRegions  =     0;
+    private   MergedCellsTable           _mergedCellsTable;
     protected SelectionRecord            selection         =     null;
-    protected ColumnInfoRecordsAggregate columns           =     null;
+    /** always present in this POI object, not always written to Excel file */
+    /*package*/ColumnInfoRecordsAggregate _columnInfos;
     protected ValueRecordsAggregate      cells             =     null;
-    protected RowRecordsAggregate        rows              =     null;
+    protected RowRecordsAggregate        _rowsAggregate              =     null;
     private   Iterator                   valueRecIterator  =     null;
     private   Iterator                   rowRecIterator    =     null;
     protected int                        eofLoc            =     0;
     protected ProtectRecord              protect           =     null;
-    protected PageBreakRecord            rowBreaks         =     null;
-    protected PageBreakRecord            colBreaks         =     null;
+    protected PageBreakRecord            _rowBreaksRecord;
+    protected PageBreakRecord            _columnBreaksRecord;
     private   DataValidityTable          _dataValidityTable=     null;
     protected ObjectProtectRecord        objprotect        =     null;
     protected ScenarioProtectRecord      scenprotect       =     null;
     protected PasswordRecord             password          =     null;
-    protected List                       condFormatting    =     new ArrayList();
+    private   ConditionalFormattingTable condFormatting;
 
     /** Add an UncalcedRecord if not true indicating formulas have not been calculated */
     protected boolean _isUncalced = false;
@@ -139,13 +194,70 @@ public final class Sheet implements Model {
         Sheet     retval             = new Sheet();
         ArrayList records            = new ArrayList(recs.size() / 5);
         boolean   isfirstcell        = true;
-        boolean   isfirstrow         = true;
         int       bofEofNestingLevel = 0;
 
         for (int k = offset; k < recs.size(); k++)
         {
             Record rec = ( Record ) recs.get(k);
+            if (rec.isValue() != (rec instanceof CellValueRecordInterface)) {
+               if (rec instanceof SharedFormulaRecord) {
+                       
+               } else {
+               "".length();
+               }
+            }
 
+            if ( rec.getSid() == DBCellRecord.sid ) {
+                continue;
+            }
+            if ( rec.getSid() == IndexRecord.sid ) {
+                // ignore INDEX record because it is only needed by Excel, 
+                // and POI always re-calculates its contents 
+                continue;
+            }
+            if ( rec.getSid() == StringRecord.sid ) {
+                continue;
+            }
+            
+            if ( rec.getSid() == CFHeaderRecord.sid ) {
+                RecordStream rs = new RecordStream(recs, k);
+                retval.condFormatting = new ConditionalFormattingTable(rs);
+                k += rs.getCountRead()-1;
+                records.add(retval.condFormatting);
+                continue;
+            }
+            
+            if (rec.getSid() == ColumnInfoRecord.sid) {
+                RecordStream rs = new RecordStream(recs, k);
+                retval._columnInfos = new ColumnInfoRecordsAggregate(rs);
+                k += rs.getCountRead()-1;
+                records.add(retval._columnInfos);
+                continue;
+            }
+            if ( rec.getSid() == DVALRecord.sid) {
+                RecordStream rs = new RecordStream(recs, k);
+                retval._dataValidityTable = new DataValidityTable(rs);
+                k += rs.getCountRead() - 1; // TODO - convert this method result to be zero based
+                records.add(retval._dataValidityTable);
+                continue; // TODO
+            }
+            if ( rec.getSid() == RowRecord.sid )
+            {
+                RowRecord row = (RowRecord)rec;
+                if (retval._rowsAggregate == null) {
+                    retval._rowsAggregate = new RowRecordsAggregate();
+                    records.add(retval._rowsAggregate); //only add the aggregate once
+                               }
+                retval._rowsAggregate.insertRow(row);
+                continue;
+            }
+            if (rec.getSid() == MergeCellsRecord.sid) {
+                RecordStream rs = new RecordStream(recs, k);
+                retval._mergedCellsTable = new MergedCellsTable(rs);
+                records.add(retval._mergedCellsTable);
+                continue; // TODO
+            }
+            
             if (rec.getSid() == BOFRecord.sid)
             {
                 bofEofNestingLevel++;
@@ -169,53 +281,15 @@ public final class Sheet implements Model {
             else if (rec.getSid() == DimensionsRecord.sid)
             {
                 // Make a columns aggregate if one hasn't ready been created.
-                if (retval.columns == null)
+                if (retval._columnInfos == null)
                 {
-                    retval.columns = new ColumnInfoRecordsAggregate();
-                    records.add(retval.columns);
+                    retval._columnInfos = new ColumnInfoRecordsAggregate();
+                    records.add(retval._columnInfos);
                 }
 
                 retval.dims    = ( DimensionsRecord ) rec;
                 retval.dimsloc = records.size();
             }
-            else if (rec.getSid() == MergeCellsRecord.sid)
-            {
-                retval.mergedRecords.add(rec);
-                retval.merged = ( MergeCellsRecord ) rec;
-                retval.numMergedRegions += retval.merged.getNumAreas();
-            }
-            else if ( rec.getSid() == CFHeaderRecord.sid )
-            {
-                CFRecordsAggregate cfAgg = CFRecordsAggregate.createCFAggregate(recs, k);
-                retval.condFormatting.add(cfAgg);
-                rec = cfAgg;
-            }
-            else if ( rec.getSid() == CFRuleRecord.sid )
-            {
-                // Skip it since it is processed by CFRecordsAggregate
-                rec = null;
-            }
-            else if (rec.getSid() == ColumnInfoRecord.sid)
-            {
-                ColumnInfoRecord col = (ColumnInfoRecord)rec;
-                if (retval.columns != null)
-                {
-                    rec = null; //only add the aggregate once
-                }
-                else
-                {
-                    rec = retval.columns = new ColumnInfoRecordsAggregate();
-                }
-                retval.columns.insertColumn(col);
-            }
-            else if (rec.getSid() == DefaultColWidthRecord.sid)
-            {
-                retval.defaultcolwidth = ( DefaultColWidthRecord ) rec;
-            }
-            else if (rec.getSid() == DefaultRowHeightRecord.sid)
-            {
-                retval.defaultrowheight = ( DefaultRowHeightRecord ) rec;
-            }
             else if ( rec.isValue() && bofEofNestingLevel == 1 )
             {
                 if ( isfirstcell )
@@ -230,22 +304,13 @@ public final class Sheet implements Model {
                     rec = null;
                 }
             }
-            else if ( rec.getSid() == StringRecord.sid )
+            else  if (rec.getSid() == DefaultColWidthRecord.sid)
             {
-                rec = null;
+                retval.defaultcolwidth = ( DefaultColWidthRecord ) rec;
             }
-            else if ( rec.getSid() == RowRecord.sid )
+            else if (rec.getSid() == DefaultRowHeightRecord.sid)
             {
-                RowRecord row = (RowRecord)rec;
-                if (!isfirstrow) rec = null; //only add the aggregate once
-
-                if ( isfirstrow )
-                {
-                    retval.rows = new RowRecordsAggregate();
-                    rec = retval.rows;
-                    isfirstrow = false;
-                }
-                retval.rows.insertRow(row);
+                retval.defaultrowheight = ( DefaultRowHeightRecord ) rec;
             }
             else if ( rec.getSid() == PrintGridlinesRecord.sid )
             {
@@ -291,22 +356,6 @@ public final class Sheet implements Model {
             {
                 retval.windowTwo = (WindowTwoRecord) rec;
             }
-            else if ( rec.getSid() == DBCellRecord.sid )
-            {
-                rec = null;
-            }
-            else if ( rec.getSid() == IndexRecord.sid )
-            {
-                // ignore INDEX record because it is only needed by Excel, 
-                // and POI always re-calculates its contents 
-                rec = null;
-            }
-            else if ( rec.getSid() == DVALRecord.sid) {
-                RecordStream rs = new RecordStream(recs, k);
-                retval._dataValidityTable = new DataValidityTable(rs);
-                k += rs.getCountRead() - 1; // TODO - convert this method result to be zero based
-                rec = retval._dataValidityTable;
-            }
             else if ( rec.getSid() == ProtectRecord.sid )
             {
                 retval.protect = (ProtectRecord) rec;
@@ -323,13 +372,13 @@ public final class Sheet implements Model {
             {
                 retval.password = (PasswordRecord) rec;
             }
-            else if (rec.getSid() == PageBreakRecord.HORIZONTAL_SID)
+            else if (rec.getSid() == HorizontalPageBreakRecord.sid)
             {
-                retval.rowBreaks = (PageBreakRecord)rec;
+                retval._rowBreaksRecord = (HorizontalPageBreakRecord)rec;
             }
-            else if (rec.getSid() == PageBreakRecord.VERTICAL_SID)
+            else if (rec.getSid() == VerticalPageBreakRecord.sid)
             {
-                retval.colBreaks = (PageBreakRecord)rec;
+                retval._columnBreaksRecord = (VerticalPageBreakRecord)rec;
             }
 
             if (rec != null)
@@ -337,6 +386,9 @@ public final class Sheet implements Model {
                 records.add(rec);
             }
         }
+        if (retval.dimsloc < 0) {
+               throw new RuntimeException("DimensionsRecord was not found");
+        }
         retval.records = records;
         retval.checkRows();
         retval.checkCells();
@@ -345,6 +397,17 @@ public final class Sheet implements Model {
         return retval;
     }
 
+    private static final class RecordCloner implements RecordVisitor {
+
+               private final List _destList;
+
+               public RecordCloner(List destList) {
+                       _destList = destList;
+               }
+               public void visitRecord(Record r) {
+                       _destList.add(r.clone());
+               }
+    }
     /**
      * Clones the low level records of this sheet and returns the new sheet instance.
      * This method is implemented by adding methods for deep cloning to all records that
@@ -356,7 +419,13 @@ public final class Sheet implements Model {
     {
       ArrayList clonedRecords = new ArrayList(this.records.size());
       for (int i=0; i<this.records.size();i++) {
-        Record rec = (Record)((Record)this.records.get(i)).clone();
+        RecordBase rb = (RecordBase) this.records.get(i);
+        if (rb instanceof RecordAggregate) {
+               ((RecordAggregate)rb).visitContainedRecords(new RecordCloner(clonedRecords));
+               // TODO - make sure this logic works for the other RecordAggregates
+               continue;
+        }
+               Record rec = (Record)((Record)rb).clone();
         //Need to pull out the Row record and the Value records from their
         //Aggregates.
         //This is probably the best way to do it since we probably dont want the createSheet
@@ -452,10 +521,10 @@ public final class Sheet implements Model {
         records.add( retval.createWSBool() );
         
         // 'Page Settings Block'
-        retval.rowBreaks = new PageBreakRecord(PageBreakRecord.HORIZONTAL_SID);
-        records.add(retval.rowBreaks);
-        retval.colBreaks = new PageBreakRecord(PageBreakRecord.VERTICAL_SID);
-        records.add(retval.colBreaks);
+        retval._rowBreaksRecord = new HorizontalPageBreakRecord();
+        records.add(retval._rowBreaksRecord);
+        retval._columnBreaksRecord = new VerticalPageBreakRecord();
+        records.add(retval._columnBreaksRecord);
 
         retval.header = createHeader();
         records.add( retval.header );
@@ -473,7 +542,7 @@ public final class Sheet implements Model {
         records.add( retval.defaultcolwidth);
         ColumnInfoRecordsAggregate columns = new ColumnInfoRecordsAggregate();
         records.add( columns );
-        retval.columns = columns;
+        retval._columnInfos = columns;
         retval.dims    =  createDimensions();
         records.add(retval.dims);
         retval.dimsloc = records.size()-1;
@@ -509,14 +578,23 @@ public final class Sheet implements Model {
 
     private void checkRows()
     {
-        if (rows == null)
+        if (_rowsAggregate == null)
         {
-            rows = new RowRecordsAggregate();
-            records.add(getDimsLoc() + 1, rows);
+            _rowsAggregate = new RowRecordsAggregate();
+            records.add(getDimsLoc() + 1, _rowsAggregate);
         }
     }
+    private MergedCellsTable getMergedRecords() {
+       if (_mergedCellsTable == null) {
+               MergedCellsTable mct = new MergedCellsTable();
+               RecordOrderer.addNewSheetRecord(records, mct);
+               _mergedCellsTable = mct;
+       }
+       return _mergedCellsTable;
+    }
 
-    public int addMergedRegion(int rowFrom, int colFrom, int rowTo, int colTo) {
+
+       public int addMergedRegion(int rowFrom, int colFrom, int rowTo, int colTo) {
         // Validate input
         if (rowTo < rowFrom) {
             throw new IllegalArgumentException("The 'to' row (" + rowTo
@@ -527,159 +605,57 @@ public final class Sheet implements Model {
                     + ") must not be less than the 'from' col (" + colFrom + ")");
         }
 
-        if (merged == null || merged.getNumAreas() == 1027)
-        {
-            merged = createMergedCells();
-            mergedRecords.add(merged);
-            records.add(records.size() - 1, merged);
-        }
-        merged.addArea(rowFrom, colFrom, rowTo, colTo);
-        return numMergedRegions++;
+        MergedCellsTable mrt = getMergedRecords();
+               mrt.addArea(rowFrom, colFrom, rowTo, colTo);
+        return mrt.getNumberOfMergedRegions()-1;
     }
 
     public void removeMergedRegion(int index)
     {
         //safety checks
-        if (index >= numMergedRegions || mergedRecords.size() == 0)
-           return;
-
-        int pos = 0;
-        int startNumRegions = 0;
-
-        //optimisation for current record
-        if (numMergedRegions - index < merged.getNumAreas())
-        {
-            pos = mergedRecords.size() - 1;
-            startNumRegions = numMergedRegions - merged.getNumAreas();
-        }
-        else
-        {
-            for (int n = 0; n < mergedRecords.size(); n++)
-            {
-                MergeCellsRecord record = (MergeCellsRecord) mergedRecords.get(n);
-                if (startNumRegions + record.getNumAreas() > index)
-                {
-                    pos = n;
-                    break;
-                }
-                startNumRegions += record.getNumAreas();
-            }
-        }
-
-        MergeCellsRecord rec = (MergeCellsRecord) mergedRecords.get(pos);
-        rec.removeAreaAt(index - startNumRegions);
-        numMergedRegions--;
-        if (rec.getNumAreas() == 0)
-        {
-            mergedRecords.remove(pos);
-            //get rid of the record from the sheet
-            records.remove(merged);
-            if (merged == rec) {
-                //pull up the LAST record for operations when we finally
-                //support continue records for mergedRegions
-                if (mergedRecords.size() > 0) {
-                    merged = (MergeCellsRecord) mergedRecords.get(mergedRecords.size() - 1);
-                } else {
-                    merged = null;
-                }
-            }
-        }
+        MergedCellsTable mrt = getMergedRecords();
+               if (index >= mrt.getNumberOfMergedRegions()) {
+                       return;
+               }
+               mrt.remove(index);
     }
 
-    public CellRangeAddress getMergedRegionAt(int index)
-    {
+    public CellRangeAddress getMergedRegionAt(int index) {
         //safety checks
-        if (index >= numMergedRegions || mergedRecords.size() == 0)
-            return null;
-
-        int pos = 0;
-        int startNumRegions = 0;
-
-        //optimisation for current record
-        if (numMergedRegions - index < merged.getNumAreas())
-        {
-            pos = mergedRecords.size() - 1;
-            startNumRegions = numMergedRegions - merged.getNumAreas();
-        }
-        else
-        {
-            for (int n = 0; n < mergedRecords.size(); n++)
-            {
-                MergeCellsRecord record = (MergeCellsRecord) mergedRecords.get(n);
-                if (startNumRegions + record.getNumAreas() > index)
-                {
-                    pos = n;
-                    break;
-                }
-                startNumRegions += record.getNumAreas();
-            }
-        }
-        return ((MergeCellsRecord) mergedRecords.get(pos)).getAreaAt(index - startNumRegions);
+        MergedCellsTable mrt = getMergedRecords();
+               if (index >=  mrt.getNumberOfMergedRegions()) {
+                       return null;
+               }
+               return mrt.get(index);
     }
 
-    public int getNumMergedRegions()
-    {
-        return numMergedRegions;
+    public int getNumMergedRegions() {
+        return getMergedRecords().getNumberOfMergedRegions();
+    }
+    private ConditionalFormattingTable getConditionalFormattingTable() {
+       if (condFormatting == null) {
+               condFormatting = new ConditionalFormattingTable();
+               RecordOrderer.addNewSheetRecord(records, condFormatting);
+       }
+               return condFormatting;
     }
-    // Find correct position to add new CF record
-    private int findConditionalFormattingPosition()
-    {
-        // This is default.
-        // If the algorithm does not find the right position,
-        // this one will be used (this is a position before EOF record)
-        int index = records.size()-2;
-
-        for( int i=index; i>=0; i-- )
-        {
-            Record rec = (Record)records.get(i);
-            short sid = rec.getSid();
-
-            // CFRecordsAggregate records already exist, just add to the end
-            if (rec instanceof CFRecordsAggregate)    { return i+1; }
 
-            if( sid == (short)0x00ef )                { return i+1; }// PHONETICPR
-            if( sid == (short)0x015f )                { return i+1; }// LABELRANGES
-            if( sid == MergeCellsRecord.sid )        { return i+1; }
-            if( sid == (short)0x0099 )                { return i+1; }// STANDARDWIDTH
-            if( sid == SelectionRecord.sid )        { return i+1; }
-            if( sid == PaneRecord.sid )                { return i+1; }
-            if( sid == SCLRecord.sid )                 { return i+1; }
-            if( sid == WindowTwoRecord.sid )        { return i+1; }
-        }
 
-        return index;
+       public int addConditionalFormatting(CFRecordsAggregate cfAggregate) {
+               ConditionalFormattingTable cft = getConditionalFormattingTable();
+        return cft.add(cfAggregate);
     }
 
-    public int addConditionalFormatting(CFRecordsAggregate cfAggregate)
-    {
-        int index = findConditionalFormattingPosition();
-        records.add(index, cfAggregate);
-        condFormatting.add(cfAggregate);
-        return condFormatting.size()-1;
+    public void removeConditionalFormatting(int index) {
+       getConditionalFormattingTable().remove(index);
     }
 
-    public void removeConditionalFormatting(int index)
-    {
-        if (index >= 0 && index <= condFormatting.size()-1 )
-        {
-            CFRecordsAggregate cfAggregate = getCFRecordsAggregateAt(index);
-            records.remove(cfAggregate);
-            condFormatting.remove(index);
-        }
-    }
-
-    public CFRecordsAggregate getCFRecordsAggregateAt(int index)
-    {
-        if (index >= 0 && index <= condFormatting.size()-1 )
-        {
-            return (CFRecordsAggregate) condFormatting.get(index);
-        }
-        return null;
+    public CFRecordsAggregate getCFRecordsAggregateAt(int index) {
+       return getConditionalFormattingTable().get(index);
     }
 
-    public int getNumConditionalFormattings()
-    {
-        return condFormatting.size();
+    public int getNumConditionalFormattings() {
+        return getConditionalFormattingTable().size();
     }
 
     /**
@@ -699,13 +675,13 @@ public final class Sheet implements Model {
             log.logFormatted(POILogger.DEBUG, "returning % + % + % - 2 = %", new int[]
             {
                 records.size(), cells.getPhysicalNumberOfCells(),
-                rows.getPhysicalNumberOfRows(),
+                _rowsAggregate.getPhysicalNumberOfRows(),
                 records.size() + cells.getPhysicalNumberOfCells()
-                + rows.getPhysicalNumberOfRows() - 2
+                + _rowsAggregate.getPhysicalNumberOfRows() - 2
             });
         }
         return records.size() + cells.getPhysicalNumberOfCells()
-               + rows.getPhysicalNumberOfRows() - 2;
+               + _rowsAggregate.getPhysicalNumberOfRows() - 2;
     }
 
     /**
@@ -814,7 +790,7 @@ public final class Sheet implements Model {
 
         for (int k = 0; k < records.size(); k++)
         {
-            Record record = (( Record ) records.get(k));
+               RecordBase record = (RecordBase) records.get(k);
 
             // Don't write out UncalcedRecord entries, as
             //  we handle those specially just below
@@ -833,7 +809,7 @@ public final class Sheet implements Model {
             }
 
             // If the BOF record was just serialized then add the IndexRecord
-            if (record.getSid() == BOFRecord.sid) {
+            if (record instanceof BOFRecord) {
               if (!haveSerializedIndex) {
                 haveSerializedIndex = true;
                 // Add an optional UncalcedRecord. However, we should add
@@ -846,7 +822,7 @@ public final class Sheet implements Model {
                 }
                 //Can there be more than one BOF for a sheet? If not then we can
                 //remove this guard. So be safe it is left here.
-                if (rows != null) {
+                if (_rowsAggregate != null) {
                   pos += serializeIndexRecord(k, pos, data);
                 }
               }
@@ -865,8 +841,8 @@ public final class Sheet implements Model {
     private int serializeIndexRecord(final int bofRecordIndex, final int indexRecordOffset,
             byte[] data) {
         IndexRecord index = new IndexRecord();
-        index.setFirstRow(rows.getFirstRowNum());
-        index.setLastRowAdd1(rows.getLastRowNum() + 1);
+        index.setFirstRow(_rowsAggregate.getFirstRowNum());
+        index.setLastRowAdd1(_rowsAggregate.getLastRowNum() + 1);
         // Calculate the size of the records from the end of the BOF
         // and up to the RowRecordsAggregate...
 
@@ -874,7 +850,7 @@ public final class Sheet implements Model {
         int sizeOfInitialSheetRecords = 0;
         // start just after BOF record (INDEX is not present in this list)
         for (int j = bofRecordIndex + 1; j < records.size(); j++) {
-            Record tmpRec = ((Record) records.get(j));
+            RecordBase tmpRec = ((RecordBase) records.get(j));
             if (tmpRec instanceof UncalcedRecord) {
                 continue;
             }
@@ -891,7 +867,7 @@ public final class Sheet implements Model {
         // Note: The offsets are relative to the Workbook BOF. Assume that this is
         // 0 for now.....
 
-        int blockCount = rows.getRowBlockCount();
+        int blockCount = _rowsAggregate.getRowBlockCount();
         // Calculate the size of this IndexRecord
         int indexRecSize = IndexRecord.getRecordSizeForBlockCount(blockCount);
 
@@ -902,15 +878,15 @@ public final class Sheet implements Model {
             // The offset of each DBCELL record needs to be updated in the INDEX record
 
             // account for row records in this row-block
-            currentOffset += rows.getRowBlockSize(block);
+            currentOffset += _rowsAggregate.getRowBlockSize(block);
             // account for cell value records after those
-            currentOffset += null == cells ? 0 : cells.getRowCellBlockSize(rows
-                    .getStartRowNumberForBlock(block), rows.getEndRowNumberForBlock(block));
+            currentOffset += null == cells ? 0 : cells.getRowCellBlockSize(_rowsAggregate
+                    .getStartRowNumberForBlock(block), _rowsAggregate.getEndRowNumberForBlock(block));
 
             // currentOffset is now the location of the DBCELL record for this row-block
             index.addDbcell(currentOffset);
             // Add space required to write the DBCELL record (whose reference was just added).
-            currentOffset += (8 + (rows.getRowCountForBlock(block) * 2));
+            currentOffset += (8 + (_rowsAggregate.getRowCountForBlock(block) * 2));
         }
         return index.serialize(indexRecordOffset, data);
     }
@@ -1031,11 +1007,11 @@ public final class Sheet implements Model {
         }
         //IndexRecord index = null;
          //If the row exists remove it, so that any cells attached to the row are removed
-         RowRecord existingRow = rows.getRow(row.getRowNumber());
+         RowRecord existingRow = _rowsAggregate.getRow(row.getRowNumber());
          if (existingRow != null)
-           rows.removeRow(existingRow);
+           _rowsAggregate.removeRow(existingRow);
 
-        rows.insertRow(row);
+        _rowsAggregate.insertRow(row);
 
         if (log.check( POILogger.DEBUG ))
             log.log(POILogger.DEBUG, "exit addRow");
@@ -1054,7 +1030,7 @@ public final class Sheet implements Model {
         checkRows();
 
         setLoc(getDimsLoc());
-        rows.removeRow(row);
+        _rowsAggregate.removeRow(row);
     }
 
     /**
@@ -1108,7 +1084,7 @@ public final class Sheet implements Model {
             log.log(POILogger.DEBUG, "getNextRow loc= " + loc);
         if (rowRecIterator == null)
         {
-            rowRecIterator = rows.getIterator();
+            rowRecIterator = _rowsAggregate.getIterator();
         }
         if (!rowRecIterator.hasNext())
         {
@@ -1136,7 +1112,7 @@ public final class Sheet implements Model {
     public RowRecord getRow(int rownum) {
         if (log.check( POILogger.DEBUG ))
             log.log(POILogger.DEBUG, "getNextRow loc= " + loc);
-        return rows.getRow(rownum);
+        return _rowsAggregate.getRow(rownum);
     }
 
     /**
@@ -1258,6 +1234,15 @@ public final class Sheet implements Model {
         retval.setColLevelMax(( short ) 0);
         return retval;
     }
+    private GutsRecord getGutsRecord() {
+       if (_gutsRecord == null) {
+               GutsRecord result = createGuts();
+               RecordOrderer.addNewSheetRecord(records, result);
+                       _gutsRecord = result;
+               }
+
+               return _gutsRecord;
+    }
 
     /**
      * creates the DefaultRowHeight Record and sets its options to 0 and rowheight to 0xff
@@ -1422,43 +1407,22 @@ public final class Sheet implements Model {
 
     /**
      * get the width of a given column in units of 1/256th of a character width
-     * @param column index
+     * @param columnIndex index
      * @see org.apache.poi.hssf.record.DefaultColWidthRecord
      * @see org.apache.poi.hssf.record.ColumnInfoRecord
      * @see #setColumnWidth(short,short)
      * @return column width in units of 1/256th of a character width
      */
 
-    public short getColumnWidth(short column)
-    {
-        short            retval = 0;
-        ColumnInfoRecord ci     = null;
+    public short getColumnWidth(short columnIndex) {
 
-        if (columns != null)
-        {
-            int count=columns.getNumColumns();
-            for ( int k=0;k<count;k++ )
-            {
-                ci = columns.getColInfo(k);
-                if ((ci.getFirstColumn() <= column)
-                        && (column <= ci.getLastColumn()))
-                {
-                    break;
-                }
-                ci = null;
-            }
+        ColumnInfoRecord ci = _columnInfos.findColumnInfo(columnIndex);
+        if (ci != null) {
+               return ci.getColumnWidth();
         }
-        if (ci != null)
-        {
-            retval = ci.getColumnWidth();
-        }
-        else
-        {
-            //default column width is measured in characters
-            //multiply
-            retval = (short)(256*defaultcolwidth.getColWidth());
-        }
-        return retval;
+        //default column width is measured in characters
+        //multiply
+        return (short)(256*defaultcolwidth.getColWidth());
     }
 
     /**
@@ -1470,37 +1434,28 @@ public final class Sheet implements Model {
      * Returns the index to the default ExtendedFormatRecord (0xF)
      * if no ColumnInfoRecord exists that includes the column
      * index specified.
-     * @param column
+     * @param columnIndex
      * @return index of ExtendedFormatRecord associated with
      * ColumnInfoRecord that includes the column index or the
      * index of the default ExtendedFormatRecord (0xF)
      */
-    public short getXFIndexForColAt(short column) {
-        short retval = 0;
-        ColumnInfoRecord ci = null;
-        if (columns != null) {
-          int count=columns.getNumColumns();
-          for ( int k=0;k<count;k++ )
-          {
-                ci = columns.getColInfo(k);
-                if ((ci.getFirstColumn() <= column)
-                        && (column <= ci.getLastColumn())) {
-                    break;
-                }
-                ci = null;
-            }
-        }
-        retval = (ci != null) ? ci.getXFIndex() : 0xF;
-        return retval;
-    }
-
-    /**
-     * set the width for a given column in 1/256th of a character width units
-     * @param column - the column number
-     * @param width (in units of 1/256th of a character width)
-     */
-    public void setColumnWidth(short column, short width)
-    {
+    public short getXFIndexForColAt(short columnIndex) {
+        ColumnInfoRecord ci = _columnInfos.findColumnInfo(columnIndex);
+        if (ci != null) {
+            return ci.getXFIndex();
+           }
+           return 0xF;
+       }
+
+    /**
+        * set the width for a given column in 1/256th of a character width units
+        * 
+        * @param column -
+        *            the column number
+        * @param width
+        *            (in units of 1/256th of a character width)
+        */
+    public void setColumnWidth(short column, short width) {
         setColumn( column, new Short(width), null, null, null);
     }
 
@@ -1512,30 +1467,12 @@ public final class Sheet implements Model {
      * @see #setColumnHidden(short,boolean)
      * @return whether the column is hidden or not.
      */
-
-    public boolean isColumnHidden(short column)
-    {
-        boolean          retval = false;
-        ColumnInfoRecord ci     = null;
-
-        if (columns != null)
-        {
-            for ( Iterator iterator = columns.getIterator(); iterator.hasNext(); )
-            {
-                ci = ( ColumnInfoRecord ) iterator.next();
-                if ((ci.getFirstColumn() <= column)
-                        && (column <= ci.getLastColumn()))
-                {
-                    break;
-                }
-                ci = null;
-            }
-        }
-        if (ci != null)
-        {
-            retval = ci.getHidden();
-        }
-        return retval;
+    public boolean isColumnHidden(short columnIndex) {
+       ColumnInfoRecord cir = _columnInfos.findColumnInfo(columnIndex);
+       if (cir == null) {
+               return false;
+       }
+       return cir.getHidden();
     }
 
     /**
@@ -1548,20 +1485,12 @@ public final class Sheet implements Model {
         setColumn( column, null, null, new Boolean(hidden), null);
     }
 
-    public void setColumn(short column, Short width, Integer level, Boolean hidden, Boolean collapsed)
-    {
-        if (columns == null)
-            columns = new ColumnInfoRecordsAggregate();
-
-        columns.setColumn( column, null, width, level, hidden, collapsed );
+    public void setColumn(short column, Short width, Integer level, Boolean hidden, Boolean collapsed) {
+        _columnInfos.setColumn( column, null, width, level, hidden, collapsed );
     }
 
-    public void setColumn(short column, Short xfStyle, Short width, Integer level, Boolean hidden, Boolean collapsed)
-    {
-        if (columns == null)
-            columns = new ColumnInfoRecordsAggregate();
-
-        columns.setColumn( column, xfStyle, width, level, hidden, collapsed );
+    public void setColumn(short column, Short xfStyle, Short width, Integer level, Boolean hidden, Boolean collapsed) {
+        _columnInfos.setColumn( column, xfStyle, width, level, hidden, collapsed );
     }
 
 
@@ -1576,18 +1505,12 @@ public final class Sheet implements Model {
     {
 
         // Set the level for each column
-        columns.groupColumnRange( fromColumn, toColumn, indent);
+        _columnInfos.groupColumnRange( fromColumn, toColumn, indent);
 
         // Determine the maximum overall level
-        int maxLevel = 0;
-        int count=columns.getNumColumns();
-        for ( int k=0;k<count;k++ )
-        {
-            ColumnInfoRecord columnInfoRecord = columns.getColInfo(k);
-            maxLevel = Math.max(columnInfoRecord.getOutlineLevel(), maxLevel);
-        }
+        int maxLevel = _columnInfos.getMaxOutlineLevel();
 
-        GutsRecord guts = (GutsRecord) findFirstRecordBySid( GutsRecord.sid );
+        GutsRecord guts = getGutsRecord();
         guts.setColLevelMax( (short) ( maxLevel+1 ) );
         if (maxLevel == 0) {
             guts.setTopColGutter( (short)0 );
@@ -1721,10 +1644,6 @@ public final class Sheet implements Model {
         }
     }
 
-    private static  MergeCellsRecord createMergedCells() {
-        return new MergeCellsRecord();
-    }
-
     /**
      * get the location of the DimensionsRecord (which is the last record before the value section)
      * @return location in the array of records of the DimensionsRecord
@@ -1750,24 +1669,27 @@ public final class Sheet implements Model {
         }
     }
 
+    /**
+     * @return the serialized size of this sheet
+     */
     public int getSize()
     {
         int retval = 0;
 
         for ( int k = 0; k < records.size(); k++) {
-            Record record = (Record) records.get(k);
+               RecordBase record = (RecordBase) records.get(k);
             if (record instanceof UncalcedRecord) {
                 // skip the UncalcedRecord if present, it's only encoded if the isUncalced flag is set
                 continue;
             }
             retval += record.getRecordSize();
         }
-        if (rows != null) {
+        if (_rowsAggregate != null) {
             // Add space for the IndexRecord and DBCell records
-            final int nBlocks = rows.getRowBlockCount();
+            final int nBlocks = _rowsAggregate.getRowBlockCount();
             int nRows = 0;
             if (cells != null) {
-                for (Iterator itr = rows.getIterator(); itr.hasNext();) {
+                for (Iterator itr = _rowsAggregate.getIterator(); itr.hasNext();) {
                     RowRecord row = (RowRecord)itr.next();
                     if (cells.rowHasCells(row.getRowNumber())) {
                         nRows++;
@@ -1804,16 +1726,11 @@ public final class Sheet implements Model {
 
     public Record findFirstRecordBySid(short sid)
     {
-        for (Iterator iterator = records.iterator(); iterator.hasNext(); )
-        {
-            Record record = ( Record ) iterator.next();
-
-            if (record.getSid() == sid)
-            {
-                return record;
-            }
-        }
-        return null;
+       int ix = findFirstRecordLocBySid(sid);
+       if (ix < 0) {
+               return null;
+       }
+       return (Record) records.get(ix);
     }
 
     /**
@@ -1839,24 +1756,23 @@ public final class Sheet implements Model {
     }
 
     /**
-     * Finds the first occurance of a record matching a particular sid and
+     * Finds the first occurrence of a record matching a particular sid and
      * returns it's position.
      * @param sid   the sid to search for
      * @return  the record position of the matching record or -1 if no match
      *          is made.
      */
-    public int findFirstRecordLocBySid( short sid )
-    {
-        int index = 0;
-        for (Iterator iterator = records.iterator(); iterator.hasNext(); )
-        {
-            Record record = ( Record ) iterator.next();
-
-            if (record.getSid() == sid)
-            {
-                return index;
+    public int findFirstRecordLocBySid( short sid ) { // TODO - remove this method
+        int max = records.size();
+        for (int i=0; i< max; i++) {
+               Object rb = records.get(i);
+            if (!(rb instanceof Record)) {
+               continue;
+            }
+            Record record = (Record) rb;
+            if (record.getSid() == sid) {
+                return i;
             }
-            index++;
         }
         return -1;
     }
@@ -2324,7 +2240,7 @@ public final class Sheet implements Model {
     {
         for ( Iterator iterator = getRecords().iterator(); iterator.hasNext(); )
         {
-            Record r = (Record) iterator.next();
+            RecordBase r = (RecordBase) iterator.next();
             if (r instanceof EscherAggregate)
                 r.getRecordSize();   // Trigger flatterning of user model and corresponding update of dgg record.
         }
@@ -2337,16 +2253,14 @@ public final class Sheet implements Model {
      * @param stop Ending "main" value to shift breaks
      * @param count number of units (rows/columns) to shift by
      */
-    public void shiftBreaks(PageBreakRecord breaks, short start, short stop, int count) {
+    private static void shiftBreaks(PageBreakRecord breaks, int start, int stop, int count) {
 
-        if(rowBreaks == null)
-            return;
         Iterator iterator = breaks.getBreaksIterator();
         List shiftedBreak = new ArrayList();
         while(iterator.hasNext())
         {
             PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
-            short breakLocation = breakItem.main;
+            int breakLocation = breakItem.main;
             boolean inStart = (breakLocation >= start);
             boolean inEnd = (breakLocation <= stop);
             if(inStart && inEnd)
@@ -2361,17 +2275,31 @@ public final class Sheet implements Model {
         }
     }
 
+    private PageBreakRecord getRowBreaksRecord() {
+       if (_rowBreaksRecord == null) {
+                       _rowBreaksRecord = new HorizontalPageBreakRecord();
+                       RecordOrderer.addNewSheetRecord(records, _rowBreaksRecord);
+                       dimsloc++;
+               }
+               return _rowBreaksRecord;
+    }
+    
+    private PageBreakRecord getColumnBreaksRecord() {
+       if (_columnBreaksRecord == null) {
+               _columnBreaksRecord = new VerticalPageBreakRecord();
+                       RecordOrderer.addNewSheetRecord(records, _columnBreaksRecord);
+                       dimsloc++;
+               }
+               return _columnBreaksRecord;
+    }
+    
+    
     /**
      * Sets a page break at the indicated row
      * @param row
      */
     public void setRowBreak(int row, short fromCol, short toCol) {
-        if (rowBreaks == null) {
-            int loc = findFirstRecordLocBySid(WindowTwoRecord.sid);
-            rowBreaks = new PageBreakRecord(PageBreakRecord.HORIZONTAL_SID);
-            records.add(loc, rowBreaks);
-        }
-        rowBreaks.addBreak((short)row, fromCol, toCol);
+        getRowBreaksRecord().addBreak((short)row, fromCol, toCol);
     }
 
     /**
@@ -2379,9 +2307,9 @@ public final class Sheet implements Model {
      * @param row
      */
     public void removeRowBreak(int row) {
-        if (rowBreaks == null)
+        if (getRowBreaks() == null)
             throw new IllegalArgumentException("Sheet does not define any row breaks");
-        rowBreaks.removeBreak((short)row);
+        getRowBreaksRecord().removeBreak((short)row);
     }
 
     /**
@@ -2390,7 +2318,7 @@ public final class Sheet implements Model {
      * @return true if the specified row has a page break
      */
     public boolean isRowBroken(int row) {
-        return (rowBreaks == null) ? false : rowBreaks.getBreak((short)row) != null;
+        return getRowBreaksRecord().getBreak(row) != null;
     }
 
     /**
@@ -2398,12 +2326,7 @@ public final class Sheet implements Model {
      *
      */
     public void setColumnBreak(short column, short fromRow, short toRow) {
-        if (colBreaks == null) {
-            int loc = findFirstRecordLocBySid(WindowTwoRecord.sid);
-            colBreaks = new PageBreakRecord(PageBreakRecord.VERTICAL_SID);
-            records.add(loc, colBreaks);
-        }
-        colBreaks.addBreak(column, fromRow, toRow);
+        getColumnBreaksRecord().addBreak(column, fromRow, toRow);
     }
 
     /**
@@ -2411,19 +2334,16 @@ public final class Sheet implements Model {
      *
      */
     public void removeColumnBreak(short column) {
-        if (colBreaks == null)
-            throw new IllegalArgumentException("Sheet does not define any column breaks");
-
-        colBreaks.removeBreak(column);
+       getColumnBreaksRecord().removeBreak(column);
     }
 
     /**
      * Queries if the specified column has a page break
      *
-     * @return true if the specified column has a page break
+     * @return <code>true</code> if the specified column has a page break
      */
     public boolean isColumnBroken(short column) {
-        return (colBreaks == null) ? false : colBreaks.getBreak(column) != null;
+        return getColumnBreaksRecord().getBreak(column) != null;
     }
 
     /**
@@ -2433,7 +2353,7 @@ public final class Sheet implements Model {
      * @param count
      */
     public void shiftRowBreaks(int startingRow, int endingRow, int count) {
-        shiftBreaks(rowBreaks, (short)startingRow, (short)endingRow, (short)count);
+        shiftBreaks(getRowBreaksRecord(), startingRow, endingRow, count);
     }
 
     /**
@@ -2443,50 +2363,46 @@ public final class Sheet implements Model {
      * @param count
      */
     public void shiftColumnBreaks(short startingCol, short endingCol, short count) {
-        shiftBreaks(colBreaks, startingCol, endingCol, count);
+        shiftBreaks(getColumnBreaksRecord(), startingCol, endingCol, count);
     }
 
     /**
-     * Returns all the row page breaks
-     * @return all the row page breaks
+     * @return all the horizontal page breaks, never <code>null</code>
      */
-    public Iterator getRowBreaks() {
-        return rowBreaks.getBreaksIterator();
+    public int[] getRowBreaks() {
+        return getRowBreaksRecord().getBreaks();
     }
 
     /**
-     * Returns the number of row page breaks
      * @return the number of row page breaks
      */
     public int getNumRowBreaks(){
-        return (rowBreaks == null) ? 0 : (int)rowBreaks.getNumBreaks();
+        return getRowBreaksRecord().getNumBreaks();
     }
 
     /**
-     * Returns all the column page breaks
-     * @return all the column page breaks
+     * @return all the column page breaks, never <code>null</code>
      */
-    public Iterator getColumnBreaks(){
-        return colBreaks.getBreaksIterator();
+    public int[] getColumnBreaks(){
+        return getColumnBreaksRecord().getBreaks();
     }
 
     /**
-     * Returns the number of column page breaks
      * @return the number of column page breaks
      */
     public int getNumColumnBreaks(){
-        return (colBreaks == null) ? 0 : (int)colBreaks.getNumBreaks();
+        return getColumnBreaksRecord().getNumBreaks();
     }
 
     public void setColumnGroupCollapsed( short columnNumber, boolean collapsed )
     {
         if (collapsed)
         {
-            columns.collapseColumn( columnNumber );
+            _columnInfos.collapseColumn( columnNumber );
         }
         else
         {
-            columns.expandColumn( columnNumber );
+            _columnInfos.expandColumn( columnNumber );
         }
     }
 
@@ -2577,7 +2493,7 @@ public final class Sheet implements Model {
     private void recalcRowGutter()
     {
         int maxLevel = 0;
-        Iterator iterator = rows.getIterator();
+        Iterator iterator = _rowsAggregate.getIterator();
         while ( iterator.hasNext() )
         {
             RowRecord rowRecord = (RowRecord) iterator.next();
@@ -2585,11 +2501,7 @@ public final class Sheet implements Model {
         }
 
         // Grab the guts record, adding if needed
-        GutsRecord guts = (GutsRecord) findFirstRecordBySid( GutsRecord.sid );
-        if(guts == null) {
-            guts = new GutsRecord();
-            records.add(guts);
-        }
+        GutsRecord guts = getGutsRecord();
         // Set the levels onto it
         guts.setRowLevelMax( (short) ( maxLevel + 1 ) );
         guts.setLeftRowGutter( (short) ( 29 + (12 * (maxLevel)) ) );
@@ -2599,16 +2511,18 @@ public final class Sheet implements Model {
     {
         if (collapse)
         {
-            rows.collapseRow( row );
+            _rowsAggregate.collapseRow( row );
         }
         else
         {
-            rows.expandRow( row );
+            _rowsAggregate.expandRow( row );
         }
     }
     public DataValidityTable getOrCreateDataValidityTable() {
         if (_dataValidityTable == null) {
-            _dataValidityTable = DataValidityTable.createForSheet(records);
+               DataValidityTable result = new DataValidityTable();
+               RecordOrderer.addNewSheetRecord(records, result);
+            _dataValidityTable = result;
         }
         return _dataValidityTable;
     }
index 6482112e6fde2c19c1a540344add11edf6dce8b5..843128120efb22d8fcba5f09a0eec2411b19220b 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The area format record is used to define the colours and patterns for an area.
@@ -30,16 +29,16 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class AreaFormatRecord
-    extends Record
-{
-    public final static short      sid                             = 0x100a;
+public final class AreaFormatRecord extends Record {
+    public final static short sid = 0x100A;
+    
+    private static final BitField automatic = BitFieldFactory.getInstance(0x1);
+    private static final BitField invert    = BitFieldFactory.getInstance(0x2);
+    
     private  int        field_1_foregroundColor;
     private  int        field_2_backgroundColor;
     private  short      field_3_pattern;
     private  short      field_4_formatFlags;
-    private  BitField   automatic                                   = BitFieldFactory.getInstance(0x1);
-    private  BitField   invert                                      = BitFieldFactory.getInstance(0x2);
     private  short      field_5_forecolorIndex;
     private  short      field_6_backcolorIndex;
 
@@ -297,10 +296,4 @@ public class AreaFormatRecord
     {
         return invert.isSet(field_4_formatFlags);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 32aa57eed2641b50dad0469f247a1aed36a550ba..fd652894606a81566ef223dbbf689f9b667dc793 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The area record is used to define a area chart.
@@ -30,14 +29,12 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class AreaRecord
-    extends Record
-{
+public final class AreaRecord extends Record {
     public final static short      sid                             = 0x101A;
     private  short      field_1_formatFlags;
-    private  BitField   stacked                                     = BitFieldFactory.getInstance(0x1);
-    private  BitField   displayAsPercentage                         = BitFieldFactory.getInstance(0x2);
-    private  BitField   shadow                                      = BitFieldFactory.getInstance(0x4);
+    private static final BitField stacked             = BitFieldFactory.getInstance(0x1);
+    private static final BitField displayAsPercentage = BitFieldFactory.getInstance(0x2);
+    private static final BitField shadow              = BitFieldFactory.getInstance(0x4);
 
 
     public AreaRecord()
@@ -197,10 +194,4 @@ public class AreaRecord
     {
         return shadow.isSet(field_1_formatFlags);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index be359b80a84e8864965a3027204b0d8da5f3f04d..8be3f200be2ece1b9a10d1199cdc0117d6901bd0 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The axis options record provides unit information and other various tidbits about the axis.
@@ -30,27 +29,27 @@ import org.apache.poi.util.*;
 
  * @author Andrew C. Oliver(acoliver at apache.org)
  */
-public class AxisOptionsRecord
-    extends Record
-{
-    public final static short      sid                             = 0x1062;
-    private  short      field_1_minimumCategory;
-    private  short      field_2_maximumCategory;
-    private  short      field_3_majorUnitValue;
-    private  short      field_4_majorUnit;
-    private  short      field_5_minorUnitValue;
-    private  short      field_6_minorUnit;
-    private  short      field_7_baseUnit;
-    private  short      field_8_crossingPoint;
-    private  short      field_9_options;
-    private  BitField   defaultMinimum                              = BitFieldFactory.getInstance(0x1);
-    private  BitField   defaultMaximum                              = BitFieldFactory.getInstance(0x2);
-    private  BitField   defaultMajor                                = BitFieldFactory.getInstance(0x4);
-    private  BitField   defaultMinorUnit                            = BitFieldFactory.getInstance(0x8);
-    private  BitField   isDate                                      = BitFieldFactory.getInstance(0x10);
-    private  BitField   defaultBase                                 = BitFieldFactory.getInstance(0x20);
-    private  BitField   defaultCross                                = BitFieldFactory.getInstance(0x40);
-    private  BitField   defaultDateSettings                         = BitFieldFactory.getInstance(0x80);
+public final class AxisOptionsRecord extends Record {
+    public final static short sid = 0x1062;
+
+    private static final BitField defaultMinimum      = BitFieldFactory.getInstance(0x01);
+    private static final BitField defaultMaximum      = BitFieldFactory.getInstance(0x02);
+    private static final BitField defaultMajor        = BitFieldFactory.getInstance(0x04);
+    private static final BitField defaultMinorUnit    = BitFieldFactory.getInstance(0x08);
+    private static final BitField isDate              = BitFieldFactory.getInstance(0x10);
+    private static final BitField defaultBase         = BitFieldFactory.getInstance(0x20);
+    private static final BitField defaultCross        = BitFieldFactory.getInstance(0x40);
+    private static final BitField defaultDateSettings = BitFieldFactory.getInstance(0x80);
+
+    private short field_1_minimumCategory;
+    private short field_2_maximumCategory;
+    private short field_3_majorUnitValue;
+    private short field_4_majorUnit;
+    private short field_5_minorUnitValue;
+    private short field_6_minorUnit;
+    private short field_7_baseUnit;
+    private short field_8_crossingPoint;
+    private short field_9_options;
 
 
     public AxisOptionsRecord()
@@ -488,10 +487,4 @@ public class AxisOptionsRecord
     {
         return defaultDateSettings.isSet(field_9_options);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 794247e3a4472f9e1affe1557f5f83774f24e326..0c88385ba8e6cf72d2d04f6be65193b0e364a1cc 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The bar record is used to define a bar chart.
@@ -30,17 +29,17 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class BarRecord
-    extends Record
-{
-    public final static short      sid                             = 0x1017;
+public final class BarRecord extends Record {
+    public final static short sid = 0x1017;
+
+    private static final BitField   horizontal          = BitFieldFactory.getInstance(0x1);
+    private static final BitField   stacked             = BitFieldFactory.getInstance(0x2);
+    private static final BitField   displayAsPercentage = BitFieldFactory.getInstance(0x4);
+    private static final BitField   shadow              = BitFieldFactory.getInstance(0x8);
+
     private  short      field_1_barSpace;
     private  short      field_2_categorySpace;
     private  short      field_3_formatFlags;
-    private  BitField   horizontal                                  = BitFieldFactory.getInstance(0x1);
-    private  BitField   stacked                                     = BitFieldFactory.getInstance(0x2);
-    private  BitField   displayAsPercentage                         = BitFieldFactory.getInstance(0x4);
-    private  BitField   shadow                                      = BitFieldFactory.getInstance(0x8);
 
 
     public BarRecord()
@@ -264,10 +263,4 @@ public class BarRecord
     {
         return shadow.isSet(field_3_formatFlags);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 78daff2ebbc9a7034e86eb04ab8753b2500a7443..2ef4c67d2c251920303aafafe09c9d294ad704ab 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
+import org.apache.poi.util.BitField;
 import org.apache.poi.util.BitFieldFactory;
 import org.apache.poi.util.LittleEndian;
 import org.apache.poi.util.StringUtil;
@@ -33,12 +32,10 @@ import org.apache.poi.util.StringUtil;
  * @author Sergei Kozello (sergeikozello at mail.ru)
  * @version 2.0-pre
  */
+public final class BoundSheetRecord extends Record {
+    public final static short sid = 0x0085;
 
-public class BoundSheetRecord
-        extends Record
-{
-    private static final short HIDDEN_FLAG_MASK = 0x01;
-    public final static short sid = 0x85;
+       private static final BitField hiddenFlag = BitFieldFactory.getInstance(0x01);
     private int field_1_position_of_BOF;
     private short field_2_option_flags;
     private byte field_3_sheetname_length;
@@ -305,10 +302,10 @@ public class BoundSheetRecord
     }
 
     public boolean isHidden() {
-           return BitFieldFactory.getInstance(HIDDEN_FLAG_MASK).isSet(field_2_option_flags);
+           return hiddenFlag.isSet(field_2_option_flags);
     }
 
     public void setHidden(boolean hidden) {
-           field_2_option_flags = BitFieldFactory.getInstance(HIDDEN_FLAG_MASK).setShortBoolean(field_2_option_flags, hidden);
+           field_2_option_flags = hiddenFlag.setShortBoolean(field_2_option_flags, hidden);
     }
 }
index d000b5311dce906f228338a83da0cf51f8a788b6..06256c5cc59679bbccaab682be02417124550b90 100644 (file)
@@ -31,8 +31,7 @@ import org.apache.poi.util.LittleEndian;
  * Conditional Formatting Rule Record.
  * @author Dmitriy Kumshayev
  */
-public final class CFRuleRecord extends Record
-{
+public final class CFRuleRecord extends Record {
 
        public static final short sid = 0x01B1;
 
index 7e38d6f6e6caa29abdbef040c13c4794b2143ecd..0521ea709cdfa53f0f5b703bed367105d52b727d 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * This record refers to a category or series axis and is used to specify label/tickmark frequency.
@@ -30,17 +29,17 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class CategorySeriesAxisRecord
-    extends Record
-{
-    public final static short      sid                             = 0x1020;
+public final class CategorySeriesAxisRecord extends Record {
+    public final static short sid = 0x1020;
+
+    private static final BitField valueAxisCrossing = BitFieldFactory.getInstance(0x1);
+    private static final BitField crossesFarRight   = BitFieldFactory.getInstance(0x2);
+    private static final BitField reversed          = BitFieldFactory.getInstance(0x4);
+    
     private  short      field_1_crossingPoint;
     private  short      field_2_labelFrequency;
     private  short      field_3_tickMarkFrequency;
     private  short      field_4_options;
-    private  BitField   valueAxisCrossing                           = BitFieldFactory.getInstance(0x1);
-    private  BitField   crossesFarRight                             = BitFieldFactory.getInstance(0x2);
-    private  BitField   reversed                                    = BitFieldFactory.getInstance(0x4);
 
 
     public CategorySeriesAxisRecord()
@@ -268,10 +267,4 @@ public class CategorySeriesAxisRecord
     {
         return reversed.isSet(field_4_options);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 7a36914903b6a038e984f90ca0bb96c11b2cd53f..f5fd1d9530d2ac056f2eaaf2dc3fd5aa411667a8 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-import org.apache.poi.util.LittleEndian;
 import org.apache.poi.util.BitField;
 import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * Class ChartFormatRecord
@@ -30,19 +28,17 @@ import org.apache.poi.util.BitFieldFactory;
  * @author Glen Stampoultzis (glens at apache.org)
  * @version %I%, %G%
  */
-
-public class ChartFormatRecord
-    extends Record
-{
+public final class ChartFormatRecord extends Record {
     public static final short sid = 0x1014;
 
+    private static final BitField varyDisplayPattern = BitFieldFactory.getInstance(0x01);
+
     // ignored?
     private int               field1_x_position;   // lower left
     private int               field2_y_position;   // lower left
     private int               field3_width;
     private int               field4_height;
     private short             field5_grbit;
-    private BitField          varyDisplayPattern = BitFieldFactory.getInstance(0x01);
 
     public ChartFormatRecord()
     {
index c4768ab0c791b1082fb68002ac7a9ca025b05825..dd29f0d65c807d9acaf86020f0a3d5d5d4a1b090 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The common object data record is used to store all common preferences for an excel object.
  * NOTE: This source is automatically generated please do not modify this file.  Either subclass or
  *       remove the record in src/records/definitions.
-
+ *
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class CommonObjectDataSubRecord
-    extends SubRecord
-{
-    public final static short      sid                             = 0x15;
+public final class CommonObjectDataSubRecord extends SubRecord {
+    public final static short sid = 0x0015;
+
+    private static final BitField locked    = BitFieldFactory.getInstance(0x0001);
+    private static final BitField printable = BitFieldFactory.getInstance(0x0010);
+    private static final BitField autofill  = BitFieldFactory.getInstance(0x2000);
+    private static final BitField autoline  = BitFieldFactory.getInstance(0x4000);
+
+    public final static short OBJECT_TYPE_GROUP              = 0;
+    public final static short OBJECT_TYPE_LINE               = 1;
+    public final static short OBJECT_TYPE_RECTANGLE          = 2;
+    public final static short OBJECT_TYPE_OVAL               = 3;
+    public final static short OBJECT_TYPE_ARC                = 4;
+    public final static short OBJECT_TYPE_CHART              = 5;
+    public final static short OBJECT_TYPE_TEXT               = 6;
+    public final static short OBJECT_TYPE_BUTTON             = 7;
+    public final static short OBJECT_TYPE_PICTURE            = 8;
+    public final static short OBJECT_TYPE_POLYGON            = 9;
+    public final static short OBJECT_TYPE_RESERVED1          = 10;
+    public final static short OBJECT_TYPE_CHECKBOX           = 11;
+    public final static short OBJECT_TYPE_OPTION_BUTTON      = 12;
+    public final static short OBJECT_TYPE_EDIT_BOX           = 13;
+    public final static short OBJECT_TYPE_LABEL              = 14;
+    public final static short OBJECT_TYPE_DIALOG_BOX         = 15;
+    public final static short OBJECT_TYPE_SPINNER            = 16;
+    public final static short OBJECT_TYPE_SCROLL_BAR         = 17;
+    public final static short OBJECT_TYPE_LIST_BOX           = 18;
+    public final static short OBJECT_TYPE_GROUP_BOX          = 19;
+    public final static short OBJECT_TYPE_COMBO_BOX          = 20;
+    public final static short OBJECT_TYPE_RESERVED2          = 21;
+    public final static short OBJECT_TYPE_RESERVED3          = 22;
+    public final static short OBJECT_TYPE_RESERVED4          = 23;
+    public final static short OBJECT_TYPE_RESERVED5          = 24;
+    public final static short OBJECT_TYPE_COMMENT            = 25;
+    public final static short OBJECT_TYPE_RESERVED6          = 26;
+    public final static short OBJECT_TYPE_RESERVED7          = 27;
+    public final static short OBJECT_TYPE_RESERVED8          = 28;
+    public final static short OBJECT_TYPE_RESERVED9          = 29;
+    public final static short OBJECT_TYPE_MICROSOFT_OFFICE_DRAWING = 30;
+    
     private  short      field_1_objectType;
-    public final static short       OBJECT_TYPE_GROUP              = 0;
-    public final static short       OBJECT_TYPE_LINE               = 1;
-    public final static short       OBJECT_TYPE_RECTANGLE          = 2;
-    public final static short       OBJECT_TYPE_OVAL               = 3;
-    public final static short       OBJECT_TYPE_ARC                = 4;
-    public final static short       OBJECT_TYPE_CHART              = 5;
-    public final static short       OBJECT_TYPE_TEXT               = 6;
-    public final static short       OBJECT_TYPE_BUTTON             = 7;
-    public final static short       OBJECT_TYPE_PICTURE            = 8;
-    public final static short       OBJECT_TYPE_POLYGON            = 9;
-    public final static short       OBJECT_TYPE_RESERVED1          = 10;
-    public final static short       OBJECT_TYPE_CHECKBOX           = 11;
-    public final static short       OBJECT_TYPE_OPTION_BUTTON      = 12;
-    public final static short       OBJECT_TYPE_EDIT_BOX           = 13;
-    public final static short       OBJECT_TYPE_LABEL              = 14;
-    public final static short       OBJECT_TYPE_DIALOG_BOX         = 15;
-    public final static short       OBJECT_TYPE_SPINNER            = 16;
-    public final static short       OBJECT_TYPE_SCROLL_BAR         = 17;
-    public final static short       OBJECT_TYPE_LIST_BOX           = 18;
-    public final static short       OBJECT_TYPE_GROUP_BOX          = 19;
-    public final static short       OBJECT_TYPE_COMBO_BOX          = 20;
-    public final static short       OBJECT_TYPE_RESERVED2          = 21;
-    public final static short       OBJECT_TYPE_RESERVED3          = 22;
-    public final static short       OBJECT_TYPE_RESERVED4          = 23;
-    public final static short       OBJECT_TYPE_RESERVED5          = 24;
-    public final static short       OBJECT_TYPE_COMMENT            = 25;
-    public final static short       OBJECT_TYPE_RESERVED6          = 26;
-    public final static short       OBJECT_TYPE_RESERVED7          = 27;
-    public final static short       OBJECT_TYPE_RESERVED8          = 28;
-    public final static short       OBJECT_TYPE_RESERVED9          = 29;
-    public final static short       OBJECT_TYPE_MICROSOFT_OFFICE_DRAWING = 30;
     private  short      field_2_objectId;
     private  short      field_3_option;
-    private  BitField   locked                                      = BitFieldFactory.getInstance(0x1);
-    private  BitField   printable                                   = BitFieldFactory.getInstance(0x10);
-    private  BitField   autofill                                    = BitFieldFactory.getInstance(0x2000);
-    private  BitField   autoline                                    = BitFieldFactory.getInstance(0x4000);
     private  int        field_4_reserved1;
     private  int        field_5_reserved2;
     private  int        field_6_reserved3;
@@ -431,8 +431,4 @@ public class CommonObjectDataSubRecord
     {
         return autoline.isSet(field_3_option);
     }
-
-
-}  // END OF CLASS
-
-
+}
index 10459969168f7a973a6b63fde32a577ba447935d..476b13291b682e557bb5a165871c6eadbbe17940 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The dat record is used to store options for the chart.
@@ -30,15 +29,15 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class DatRecord
-    extends Record
-{
-    public final static short      sid                             = 0x1063;
+public final class DatRecord extends Record {
+    public final static short sid = 0x1063;
+
+    private static final BitField horizontalBorder = BitFieldFactory.getInstance(0x1);
+    private static final BitField verticalBorder   = BitFieldFactory.getInstance(0x2);
+    private static final BitField border           = BitFieldFactory.getInstance(0x4);
+    private static final BitField showSeriesKey    = BitFieldFactory.getInstance(0x8);
+
     private  short      field_1_options;
-    private  BitField   horizontalBorder                            = BitFieldFactory.getInstance(0x1);
-    private  BitField   verticalBorder                              = BitFieldFactory.getInstance(0x2);
-    private  BitField   border                                      = BitFieldFactory.getInstance(0x4);
-    private  BitField   showSeriesKey                               = BitFieldFactory.getInstance(0x8);
 
 
     public DatRecord()
@@ -216,10 +215,4 @@ public class DatRecord
     {
         return showSeriesKey.isSet(field_1_options);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 027e0c1afd82188c22f8344df4770b2da8e384a5..f86834daaed8ee2377cda9f6b3206dbdce9b59b3 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The data format record is used to index into a series.
  * NOTE: This source is automatically generated please do not modify this file.  Either subclass or
  *       remove the record in src/records/definitions.
-
+ *
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class DataFormatRecord
-    extends Record
-{
-    public final static short      sid                             = 0x1006;
-    private  short      field_1_pointNumber;
-    private  short      field_2_seriesIndex;
-    private  short      field_3_seriesNumber;
-    private  short      field_4_formatFlags;
-    private  BitField   useExcel4Colors                             = BitFieldFactory.getInstance(0x1);
+public final class DataFormatRecord extends Record {
+    public final static short sid = 0x1006;
+
+    private static final BitField useExcel4Colors = BitFieldFactory.getInstance(0x1);
+
+    private short field_1_pointNumber;
+    private short field_2_seriesIndex;
+    private short field_3_seriesNumber;
+    private short field_4_formatFlags;
 
 
     public DataFormatRecord()
@@ -228,10 +227,4 @@ public class DataFormatRecord
     {
         return useExcel4Colors.isSet(field_4_formatFlags);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 1583aa039b11613a15ca18810cf128a854a7c6cd..1aaa155a238efa340a77abacb1636ff2efa8dd19 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
-/*
- * FormulaRecord.java
- *
- * Created on October 28, 2001, 5:44 PM
- */
 package org.apache.poi.hssf.record;
 
 import java.util.List;
@@ -39,24 +32,22 @@ import org.apache.poi.util.LittleEndian;
  * @author Jason Height (jheight at chariot dot net dot au)
  * @version 2.0-pre
  */
-
 public final class FormulaRecord
     extends Record
     implements CellValueRecordInterface, Comparable
 {
     
-    public static final short sid =
-        0x06;   // docs say 406...because of a bug Microsoft support site article #Q184647)
-    
-    //private short             field_1_row;
+    public static final short sid = 0x0006;   // docs say 406...because of a bug Microsoft support site article #Q184647)
+
+    private static final BitField alwaysCalc = BitFieldFactory.getInstance(0x0001);
+    private static final BitField calcOnLoad = BitFieldFactory.getInstance(0x0002);
+    private static final BitField sharedFormula = BitFieldFactory.getInstance(0x0008);    
+
     private int             field_1_row;
     private short             field_2_column;
     private short             field_3_xf;
     private double            field_4_value;
     private short             field_5_options;
-    private BitField          alwaysCalc = BitFieldFactory.getInstance(0x0001);
-    private BitField          calcOnLoad = BitFieldFactory.getInstance(0x0002);
-    private BitField          sharedFormula = BitFieldFactory.getInstance(0x0008);    
     private int               field_6_zero;
     private short             field_7_expression_len;
     private Stack             field_8_parsed_expr;
index 19ef9e0c620377448b7d37605bf39e8161163d61..e4a2bf6c3a1ac813232ac9610e3ae68edf4a099b 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The frame record indicates whether there is a border around the displayed text of a chart.
@@ -30,16 +29,16 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class FrameRecord
-    extends Record
-{
-    public final static short      sid                             = 0x1032;
+public final class FrameRecord extends Record {
+    public final static short sid  = 0x1032;
+
+    private static final BitField autoSize     = BitFieldFactory.getInstance(0x1);
+    private static final BitField autoPosition = BitFieldFactory.getInstance(0x2);
+
     private  short      field_1_borderType;
     public final static short       BORDER_TYPE_REGULAR            = 0;
     public final static short       BORDER_TYPE_SHADOW             = 1;
     private  short      field_2_options;
-    private  BitField   autoSize                                    = BitFieldFactory.getInstance(0x1);
-    private  BitField   autoPosition                                = BitFieldFactory.getInstance(0x2);
 
 
     public FrameRecord()
@@ -211,10 +210,4 @@ public class FrameRecord
     {
         return autoPosition.isSet(field_2_options);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
\ No newline at end of file
index 05b642a44db746b6e167528a14f56170c9574f31..a6846300cb9de30167f89a8c1568de30bb3e490e 100644 (file)
@@ -1,60 +1,67 @@
-
 /* ====================================================================
  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.
-==================================================================== */
-        
+ 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.record;
 
+import java.util.Iterator;
+
 /**
- * HorizontalPageBreak record that stores page breaks at rows
- * <p>
- * This class is just used so that SID compares work properly in the RecordFactory
+ * HorizontalPageBreak (0x001B) record that stores page breaks at rows <p/>
+ * 
  * @see PageBreakRecord
- * @author Danny Mui (dmui at apache dot org) 
+ * @author Danny Mui (dmui at apache dot org)
  */
-public class HorizontalPageBreakRecord extends PageBreakRecord {
+public final class HorizontalPageBreakRecord extends PageBreakRecord {
+
+       public static final short sid = 0x001B;
 
-    public static final short sid = PageBreakRecord.HORIZONTAL_SID; 
-    
        /**
-        * 
+        * Creates an empty horizontal page break record
         */
        public HorizontalPageBreakRecord() {
-               super();
+               //
        }
 
        /**
-        * @param sid
-        */
-       public HorizontalPageBreakRecord(short sid) {
-               super(sid);
-       }
-
-   /**
-     * @param in the RecordInputstream to read the record from
+        * @param in
+        *            the RecordInputstream to read the record from
         */
        public HorizontalPageBreakRecord(RecordInputStream in) {
                super(in);
        }
 
-       /* (non-Javadoc)
-        * @see org.apache.poi.hssf.record.Record#getSid()
-        */
+       protected void validateSid(short id) {
+               if (id != getSid()) {
+                       throw new RecordFormatException(
+                                       "NOT A HorizontalPageBreak or VerticalPageBreak RECORD!! " + id);
+               }
+       }
+
        public short getSid() {
                return sid;
        }
 
+       public Object clone() {
+               PageBreakRecord result = new HorizontalPageBreakRecord();
+               Iterator iterator = getBreaksIterator();
+               while (iterator.hasNext()) {
+                       Break original = (Break) iterator.next();
+                       result.addBreak(original.main, original.subFrom, original.subTo);
+               }
+               return result;
+       }
 }
index 40ddb887c27d15739d8a79ca6dc7a778ac24373d..e9c529ea3c49d4deda8b869d2c5240ba729202a8 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * Defines a legend for a chart.
@@ -30,10 +29,16 @@ import org.apache.poi.util.*;
 
  * @author Andrew C. Oliver (acoliver at apache.org)
  */
-public class LegendRecord
-    extends Record
-{
-    public final static short      sid                             = 0x1015;
+public final class LegendRecord extends Record {
+    public final static short sid = 0x1015;
+
+    private static final BitField autoPosition     = BitFieldFactory.getInstance(0x01);
+    private static final BitField autoSeries       = BitFieldFactory.getInstance(0x02);
+    private static final BitField autoXPositioning = BitFieldFactory.getInstance(0x04);
+    private static final BitField autoYPositioning = BitFieldFactory.getInstance(0x08);
+    private static final BitField vertical         = BitFieldFactory.getInstance(0x10);
+    private static final BitField dataTable        = BitFieldFactory.getInstance(0x20);
+
     private  int        field_1_xAxisUpperLeft;
     private  int        field_2_yAxisUpperLeft;
     private  int        field_3_xSize;
@@ -50,12 +55,6 @@ public class LegendRecord
     public final static byte        SPACING_MEDIUM                 = 1;
     public final static byte        SPACING_OPEN                   = 2;
     private  short      field_7_options;
-    private  BitField   autoPosition                                = BitFieldFactory.getInstance(0x1);
-    private  BitField   autoSeries                                  = BitFieldFactory.getInstance(0x2);
-    private  BitField   autoXPositioning                            = BitFieldFactory.getInstance(0x4);
-    private  BitField   autoYPositioning                            = BitFieldFactory.getInstance(0x8);
-    private  BitField   vertical                                    = BitFieldFactory.getInstance(0x10);
-    private  BitField   dataTable                                   = BitFieldFactory.getInstance(0x20);
 
 
     public LegendRecord()
@@ -437,10 +436,4 @@ public class LegendRecord
     {
         return dataTable.isSet(field_7_options);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 5e359ab828f9b4d0d2a1139ea12d443d8ed2b8b0..8caa8e4a4b0b053da13c7f23fb54fc959a555f44 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * Describes a line format record.  The line format record controls how a line on a chart appears.
@@ -30,10 +29,13 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class LineFormatRecord
-    extends Record
-{
-    public final static short      sid                             = 0x1007;
+public final class LineFormatRecord extends Record {
+    public final static short sid = 0x1007;
+
+    private static final BitField auto      = BitFieldFactory.getInstance(0x1);
+    private static final BitField drawTicks = BitFieldFactory.getInstance(0x4);
+    private static final BitField unknown   = BitFieldFactory.getInstance(0x4);
+
     private  int        field_1_lineColor;
     private  short      field_2_linePattern;
     public final static short       LINE_PATTERN_SOLID             = 0;
@@ -51,9 +53,6 @@ public class LineFormatRecord
     public final static short       WEIGHT_MEDIUM                  = 1;
     public final static short       WEIGHT_WIDE                    = 2;
     private  short      field_4_format;
-    private  BitField   auto                                        = BitFieldFactory.getInstance(0x1);
-    private  BitField   drawTicks                                   = BitFieldFactory.getInstance(0x4);
-    private  BitField   unknown                                     = BitFieldFactory.getInstance(0x4);
     private  short      field_5_colourPaletteIndex;
 
 
@@ -342,10 +341,4 @@ public class LineFormatRecord
     {
         return unknown.isSet(field_4_format);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 46d52bf094cbbeeeabd82e6112d34f5e588d233c..093c1a86cbf48a0f65be6203c918e010944336a3 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * Describes a linked data record.  This record referes to the series data or text.
@@ -30,10 +29,11 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class LinkedDataRecord
-    extends Record
-{
-    public final static short      sid                             = 0x1051;
+public final class LinkedDataRecord extends Record {
+    public final static short sid  = 0x1051;
+
+    private static final BitField customNumberFormat= BitFieldFactory.getInstance(0x1);
+    
     private  byte       field_1_linkType;
     public final static byte        LINK_TYPE_TITLE_OR_TEXT        = 0;
     public final static byte        LINK_TYPE_VALUES               = 1;
@@ -45,7 +45,6 @@ public class LinkedDataRecord
     public final static byte        REFERENCE_TYPE_NOT_USED        = 3;
     public final static byte        REFERENCE_TYPE_ERROR_REPORTED  = 4;
     private  short      field_3_options;
-    private  BitField   customNumberFormat                          = BitFieldFactory.getInstance(0x1);
     private  short      field_4_indexNumberFmtRecord;
     private  LinkedDataFormulaField field_5_formulaOfLink;
 
@@ -86,7 +85,7 @@ public class LinkedDataRecord
         field_2_referenceType          = in.readByte();
         field_3_options                = in.readShort();
         field_4_indexNumberFmtRecord   = in.readShort();
-        field_5_formulaOfLink = new org.apache.poi.hssf.record.LinkedDataFormulaField();
+        field_5_formulaOfLink = new LinkedDataFormulaField();
         field_5_formulaOfLink.fillField(in);
     }
 
@@ -156,7 +155,7 @@ public class LinkedDataRecord
         rec.field_2_referenceType = field_2_referenceType;
         rec.field_3_options = field_3_options;
         rec.field_4_indexNumberFmtRecord = field_4_indexNumberFmtRecord;
-        rec.field_5_formulaOfLink = ((org.apache.poi.hssf.record.LinkedDataFormulaField)field_5_formulaOfLink.clone());;
+        rec.field_5_formulaOfLink = ((LinkedDataFormulaField)field_5_formulaOfLink.clone());;
         return rec;
     }
 
@@ -286,10 +285,4 @@ public class LinkedDataRecord
     {
         return customNumberFormat.isSet(field_3_options);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 2e0a417e02213dca41fb40e6d041895dc079f1a9..525749dffa02b35ad3cfe4e7cb06766e5e63fad6 100644 (file)
@@ -32,68 +32,51 @@ import org.apache.poi.util.LittleEndian;
  */
 public final class MergeCellsRecord extends Record {
     public final static short sid = 0x00E5;
-    private CellRangeAddressList _regions;
-
-    /** 
-     * Creates an empty <tt>MergedCellsRecord</tt>
-     */
-    public MergeCellsRecord() {
-       _regions = new CellRangeAddressList();
+    /** sometimes the regions array is shared with other MergedCellsRecords */ 
+    private CellRangeAddress[] _regions;
+    private final int _startIndex;
+    private final int _numberOfRegions;
+
+    public MergeCellsRecord(CellRangeAddress[] regions, int startIndex, int numberOfRegions) {
+               _regions = regions;
+               _startIndex = startIndex;
+               _numberOfRegions = numberOfRegions;
     }
-
     /**
      * Constructs a MergedCellsRecord and sets its fields appropriately
      * @param in the RecordInputstream to read the record from
      */
     public MergeCellsRecord(RecordInputStream in) {
-        super(in);
+       int nRegions = in.readUShort();
+       CellRangeAddress[] cras = new CellRangeAddress[nRegions];
+       for (int i = 0; i < nRegions; i++) {
+                       cras[i] = new org.apache.poi.hssf.util.CellRangeAddress(in);
+               }
+       _numberOfRegions = nRegions;
+       _startIndex = 0;
+       _regions = cras;
     }
-
     protected void fillFields(RecordInputStream in) {
-       _regions = new org.apache.poi.hssf.util.CellRangeAddressList(in);
+       throw new RuntimeException("obsolete");
     }
-
     /**
      * get the number of merged areas.  If this drops down to 0 you should just go
      * ahead and delete the record.
      * @return number of areas
      */
     public short getNumAreas() {
-        return (short)_regions.countRanges();
-    }
-
-    /**
-     * Add an area to consider a merged cell.  The index returned is only gauranteed to
-     * be correct provided you do not add ahead of or remove ahead of it  (in which case
-     * you should increment or decrement appropriately....in other words its an arrayList)
-     *
-     * @param firstRow - the upper left hand corner's row
-     * @param firstCol - the upper left hand corner's col
-     * @param lastRow - the lower right hand corner's row
-     * @param lastCol - the lower right hand corner's col
-     * @return new index of said area (don't depend on it if you add/remove)
-     */
-    public void addArea(int firstRow, int firstCol, int lastRow, int lastCol) {
-       _regions.addCellRangeAddress(firstRow, firstCol, lastRow, lastCol);
-    }
-
-    /**
-     * essentially unmerge the cells in the "area" stored at the passed in index
-     * @param areaIndex
-     */
-    public void removeAreaAt(int areaIndex) {
-        _regions.remove(areaIndex);
+        return (short)_numberOfRegions;
     }
 
     /**
      * @return MergedRegion at the given index representing the area that is Merged (r1,c1 - r2,c2)
      */
     public CellRangeAddress getAreaAt(int index) {
-        return _regions.getCellRangeAddress(index);
+        return _regions[_startIndex + index];
     }
 
     public int getRecordSize() {
-       return 4 + _regions.getSize();
+       return 4 + CellRangeAddressList.getEncodedSize(_numberOfRegions);
     }
 
     public short getSid() {
@@ -101,11 +84,16 @@ public final class MergeCellsRecord extends Record {
     }
 
     public int serialize(int offset, byte [] data) {
-        int dataSize = _regions.getSize();
+        int dataSize = CellRangeAddressList.getEncodedSize(_numberOfRegions);
 
-        LittleEndian.putShort(data, offset + 0, sid);
+        LittleEndian.putUShort(data, offset + 0, sid);
         LittleEndian.putUShort(data, offset + 2, dataSize);
-        _regions.serialize(offset + 4, data);
+        int nItems = _numberOfRegions;
+        LittleEndian.putUShort(data, offset + 4, nItems);
+        int pos = 6;
+        for (int i = 0; i < _numberOfRegions; i++) {
+                       pos += _regions[_startIndex + i].serialize(offset+pos, data);
+               }
         return 4 + dataSize;
     }
 
@@ -113,17 +101,16 @@ public final class MergeCellsRecord extends Record {
         StringBuffer retval = new StringBuffer();
 
         retval.append("[MERGEDCELLS]").append("\n");
-        retval.append("     .sid        =").append(sid).append("\n");
         retval.append("     .numregions =").append(getNumAreas())
             .append("\n");
-        for (int k = 0; k < _regions.countRanges(); k++) {
-            CellRangeAddress region = _regions.getCellRangeAddress(k);
+        for (int k = 0; k < _numberOfRegions; k++) {
+            CellRangeAddress region = _regions[_startIndex + k];
 
             retval.append("     .rowfrom    =").append(region.getFirstRow())
                 .append("\n");
-            retval.append("     .colfrom    =").append(region.getFirstColumn())
-                .append("\n");
             retval.append("     .rowto      =").append(region.getLastRow())
+               .append("\n");
+            retval.append("     .colfrom    =").append(region.getFirstColumn())
                 .append("\n");
             retval.append("     .colto      =").append(region.getLastColumn())
                 .append("\n");
@@ -140,13 +127,11 @@ public final class MergeCellsRecord extends Record {
     }
 
     public Object clone() {
-        MergeCellsRecord rec = new MergeCellsRecord();        
-        for (int k = 0; k < _regions.countRanges(); k++) {
-            CellRangeAddress oldRegion = _regions.getCellRangeAddress(k);
-           rec.addArea(oldRegion.getFirstRow(), oldRegion.getFirstColumn(), 
-                          oldRegion.getLastRow(), oldRegion.getLastColumn());
-        }
-        
-        return rec;
+       int nRegions = _numberOfRegions;
+       CellRangeAddress[] clonedRegions = new CellRangeAddress[nRegions];
+               for (int i = 0; i < clonedRegions.length; i++) {
+                       clonedRegions[i] = _regions[_startIndex + i].copy();
+               }
+        return new MergeCellsRecord(clonedRegions, 0, nRegions);
     }
 }
index 83eade95d2b509c9156f258f5dcde4e85ee47c08..f11e3395cdaf27c722258ae4286436bd39b3a552 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
+
 package org.apache.poi.hssf.record;
 
 import java.util.ArrayList;
-import java.util.Collections;
 import java.util.HashMap;
 import java.util.Iterator;
 import java.util.List;
@@ -29,140 +27,128 @@ import org.apache.poi.util.LittleEndian;
 
 /**
  * <p>Record that contains the functionality page breaks (horizontal and vertical)</p>
- * 
+ *
  * <p>The other two classes just specifically set the SIDS for record creation.</p>
- * 
+ *
  * <p>REFERENCE:  Microsoft Excel SDK page 322 and 420</p>
- * 
+ *
  * @see HorizontalPageBreakRecord
  * @see VerticalPageBreakRecord
  * @author Danny Mui (dmui at apache dot org)
  */
-public class PageBreakRecord extends Record {
-   public static final short HORIZONTAL_SID = (short)0x1B;
-   public static final short VERTICAL_SID = (short)0x1A;
-   public short sid;
-   private short numBreaks;
-   private List breaks;
-   private Map BreakMap;
-      
+public abstract class PageBreakRecord extends Record {
+    private static final boolean IS_EMPTY_RECORD_WRITTEN = false;
+    private static final int[] EMPTY_INT_ARRAY = { };
+
+    private List _breaks;
+    private Map _breakMap;
+
     /**
-     * Since both records store 2byte integers (short), no point in 
+     * Since both records store 2byte integers (short), no point in
      * differentiating it in the records.
      * <p>
      * The subs (rows or columns, don't seem to be able to set but excel sets
      * them automatically)
      */
-    public class Break
-    {
+    public class Break {
 
-        public short main;
-        public short subFrom;
-        public short subTo;
+        public static final int ENCODED_SIZE = 6;
+        public int main;
+        public int subFrom;
+        public int subTo;
 
-        public Break(short main, short subFrom, short subTo)
+        public Break(int main, int subFrom, int subTo)
         {
             this.main = main;
             this.subFrom = subFrom;
             this.subTo = subTo;
         }
-    }
 
-    public PageBreakRecord()
-    {
+        public Break(RecordInputStream in) {
+            main = in.readUShort() - 1;
+            subFrom = in.readUShort();
+            subTo = in.readUShort();
+        }
 
+        public int serialize(int offset, byte[] data) {
+            LittleEndian.putUShort(data, offset + 0, main + 1);
+            LittleEndian.putUShort(data, offset + 2, subFrom);
+            LittleEndian.putUShort(data, offset + 4, subTo);
+            return ENCODED_SIZE;
+        }
     }
 
-    /**
-     * 
-     * @param sid
-     */
-    public PageBreakRecord(short sid) {
-       super();
-       this.sid = sid;
+    protected PageBreakRecord() {
+        _breaks = new ArrayList();
+        _breakMap = new HashMap();
     }
 
-    public PageBreakRecord(RecordInputStream in)
-    {
+    protected PageBreakRecord(RecordInputStream in) {
         super(in);
-        this.sid = in.getSid();
     }
 
     protected void fillFields(RecordInputStream in)
     {
-        short loadedBreaks = in.readShort();
-        setNumBreaks(loadedBreaks);
-        for(int k = 0; k < loadedBreaks; k++)
-        {
-            addBreak((short)(in.readShort()-1), in.readShort(), in.readShort());
+        int nBreaks = in.readShort();
+        _breaks = new ArrayList(nBreaks + 2);
+        _breakMap = new HashMap();
+
+        for(int k = 0; k < nBreaks; k++) {
+            Break br = new Break(in);
+            _breaks.add(br);
+            _breakMap.put(new Integer(br.main), br);
         }
 
     }
 
-    public short getSid()
-    {
-        return sid;
+    private int getDataSize() {
+        return 2 + _breaks.size() * Break.ENCODED_SIZE;
+    }
+    public int getRecordSize() {
+        int nBreaks = _breaks.size();
+        if (!IS_EMPTY_RECORD_WRITTEN && nBreaks < 1) {
+            return 0;
+        }
+        return 4 + getDataSize();
     }
 
-    public int serialize(int offset, byte data[])
-    {
-        int recordsize = getRecordSize();
+
+    public final int serialize(int offset, byte data[]) {
+        int nBreaks = _breaks.size();
+        if (!IS_EMPTY_RECORD_WRITTEN && nBreaks < 1) {
+            return 0;
+        }
+        int dataSize = getDataSize();
+        LittleEndian.putUShort(data, offset + 0, getSid());
+        LittleEndian.putUShort(data, offset + 2, dataSize);
+        LittleEndian.putUShort(data, offset + 4, nBreaks);
         int pos = 6;
-        LittleEndian.putShort(data, offset + 0, getSid());
-        LittleEndian.putShort(data, offset + 2, (short)(recordsize - 4));
-        LittleEndian.putShort(data, offset + 4, getNumBreaks());
-        for(Iterator iterator = getBreaksIterator(); iterator.hasNext();)
-        {
-            Break Break = (Break)iterator.next();
-            LittleEndian.putShort(data, offset + pos, (short)(Break.main + 1));
-            pos += 2;
-            LittleEndian.putShort(data, offset + pos, Break.subFrom);
-            pos += 2;
-            LittleEndian.putShort(data, offset + pos, Break.subTo);
-            pos += 2;
+        for (int i=0; i<nBreaks; i++) {
+            Break br = (Break)_breaks.get(i);
+            pos += br.serialize(offset+pos, data);
         }
 
-        return recordsize;
+        return 4 + dataSize;
     }
 
-    protected void validateSid(short id)
-    {
-        if(id != HORIZONTAL_SID && id != VERTICAL_SID)
-            throw new RecordFormatException("NOT A HorizontalPageBreak or VerticalPageBreak RECORD!! " + id);
-        else
-            return;
-    }
-
-    public short getNumBreaks()
-    {
-        return breaks != null ? (short)breaks.size() : numBreaks;
+    public int getNumBreaks() {
+        return _breaks.size();
     }
 
-    public void setNumBreaks(short numBreaks)
-    {
-        this.numBreaks = numBreaks;
-    }
-
-    public Iterator getBreaksIterator()
-    {
-        if(breaks == null)
-            return Collections.EMPTY_LIST.iterator();
-        else
-            return breaks.iterator();
+    public final Iterator getBreaksIterator() {
+        return _breaks.iterator();
     }
 
     public String toString()
     {
         StringBuffer retval = new StringBuffer();
-        
-        if (getSid() != HORIZONTAL_SID && getSid()!= VERTICAL_SID) 
-            return "[INVALIDPAGEBREAK]\n     .sid ="+getSid()+"[INVALIDPAGEBREAK]";
-        
+
+
         String label;
         String mainLabel;
         String subLabel;
-        
-        if (getSid() == HORIZONTAL_SID) {
+
+        if (getSid() == HorizontalPageBreakRecord.sid) {
            label = "HORIZONTALPAGEBREAK";
            mainLabel = "row";
            subLabel = "col";
@@ -171,7 +157,7 @@ public class PageBreakRecord extends Record {
            mainLabel = "column";
            subLabel = "row";
         }
-        
+
         retval.append("["+label+"]").append("\n");
         retval.append("     .sid        =").append(getSid()).append("\n");
         retval.append("     .numbreaks =").append(getNumBreaks()).append("\n");
@@ -179,7 +165,7 @@ public class PageBreakRecord extends Record {
         for(int k = 0; k < getNumBreaks(); k++)
         {
             Break region = (Break)iterator.next();
-            
+
             retval.append("     .").append(mainLabel).append(" (zero-based) =").append(region.main).append("\n");
             retval.append("     .").append(subLabel).append("From    =").append(region.subFrom).append("\n");
             retval.append("     .").append(subLabel).append("To      =").append(region.subTo).append("\n");
@@ -192,46 +178,33 @@ public class PageBreakRecord extends Record {
    /**
     * Adds the page break at the specified parameters
     * @param main Depending on sid, will determine row or column to put page break (zero-based)
-    * @param subFrom No user-interface to set (defaults to minumum, 0)
+    * @param subFrom No user-interface to set (defaults to minimum, 0)
     * @param subTo No user-interface to set
     */
-    public void addBreak(short main, short subFrom, short subTo)
-    {
-        if(breaks == null)
-        {
-            breaks = new ArrayList(getNumBreaks() + 10);
-            BreakMap = new HashMap();
-        }
+    public void addBreak(int main, int subFrom, int subTo) {
+
         Integer key = new Integer(main);
-        Break region = (Break)BreakMap.get(key);
-        if(region != null)
-        {
+        Break region = (Break)_breakMap.get(key);
+        if(region == null) {
+            region = new Break(main, subFrom, subTo);
+            _breakMap.put(key, region);
+            _breaks.add(region);
+        } else {
             region.main = main;
             region.subFrom = subFrom;
             region.subTo = subTo;
-        } else
-        {
-            region = new Break(main, subFrom, subTo);
-            breaks.add(region);
         }
-        BreakMap.put(key, region);
     }
 
     /**
      * Removes the break indicated by the parameter
      * @param main (zero-based)
      */
-    public void removeBreak(short main)
-    {
+    public final void removeBreak(int main) {
         Integer rowKey = new Integer(main);
-        Break region = (Break)BreakMap.get(rowKey);
-        breaks.remove(region);
-        BreakMap.remove(rowKey);
-    }
-
-    public int getRecordSize()
-    {
-        return 6 + getNumBreaks() * 6;
+        Break region = (Break)_breakMap.get(rowKey);
+        _breaks.remove(region);
+        _breakMap.remove(rowKey);
     }
 
     /**
@@ -239,26 +212,21 @@ public class PageBreakRecord extends Record {
      * @param main FIXME: Document this!
      * @return The Break or null if no break exists at the row/col specified.
      */
-    public Break getBreak(short main)
-    {
-       if (BreakMap == null)
-               return null;
+    public final Break getBreak(int main) {
         Integer rowKey = new Integer(main);
-        return (Break)BreakMap.get(rowKey);
+        return (Break)_breakMap.get(rowKey);
     }
 
-   /* Clones the page break record 
-    * @see java.lang.Object#clone()
-    */
-   public Object clone() {
-      PageBreakRecord record = new PageBreakRecord(getSid());      
-      Iterator iterator = getBreaksIterator();
-      while (iterator.hasNext()) {
-         Break original = (Break)iterator.next();
-         record.addBreak(original.main, original.subFrom, original.subTo);
-      }
-      return record;
-   }
-
-    
+    public final int[] getBreaks() {
+        int count = getNumBreaks();
+        if (count < 1) {
+            return EMPTY_INT_ARRAY;
+        }
+        int[] result = new int[count];
+        for (int i=0; i<count; i++) {
+            Break breakItem = (Break)_breaks.get(i);
+            result[i] = breakItem.main;
+        }
+        return result;
+    }
 }
index c1b8a0cfdab32a34c5e20a9eb6735125b10c3496..3af38601ff8871b522051bbae033b583d7419be3 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
@@ -15,7 +14,6 @@
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
@@ -32,15 +30,13 @@ import java.io.ByteArrayInputStream;
  * @author Jason Height (jheight at chariot dot net dot au)
  * @version 2.0-pre
  */
-
-public abstract class Record
-{
+public abstract class Record extends RecordBase {
 
     /**
      * instantiates a blank record strictly for ID matching
      */
 
-    public Record()
+    protected Record()
     {
     }
 
@@ -49,7 +45,7 @@ public abstract class Record
      *
      * @param in the RecordInputstream to read the record from
      */
-    public Record(RecordInputStream in)
+    protected Record(RecordInputStream in)
     {
         validateSid(in.getSid());
         fillFields(in);
@@ -89,17 +85,6 @@ public abstract class Record
         return retval;
     }
 
-    /**
-     * called by the class that is responsible for writing this sucker.
-     * Subclasses should implement this so that their data is passed back in a
-     * byte array.
-     *
-     * @param offset to begin writing at
-     * @param data byte array containing instance data
-     * @return number of bytes written
-     */
-
-    public abstract int serialize(int offset, byte [] data);
 
     /**
      * gives the current serialized size of the record. Should include the sid and reclength (4 bytes).
diff --git a/src/java/org/apache/poi/hssf/record/RecordBase.java b/src/java/org/apache/poi/hssf/record/RecordBase.java
new file mode 100644 (file)
index 0000000..6314eb0
--- /dev/null
@@ -0,0 +1,42 @@
+/* ====================================================================
+   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.record;
+
+/**
+ * Common base class of {@link Record} and {@link RecordAggregate}
+ * 
+ * @author Josh Micich
+ */
+public abstract class RecordBase {
+       /**
+        * called by the class that is responsible for writing this sucker.
+        * Subclasses should implement this so that their data is passed back in a
+        * byte array.
+        * 
+        * @param offset to begin writing at
+        * @param data byte array containing instance data
+        * @return number of bytes written
+        */
+       public abstract int serialize(int offset, byte[] data);
+
+       /**
+        * gives the current serialized size of the record. Should include the sid
+        * and reclength (4 bytes).
+        */
+       public abstract int getRecordSize();
+}
index e2066b8b0bb30980555048889ddef5506cafd391..e18ae4be83023eb1a54c524ac3d78d4d8bb9c772 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The series label record defines the type of label associated with the data format record.
@@ -30,18 +29,17 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class SeriesLabelsRecord
-    extends Record
-{
-    public final static short      sid                             = 0x100c;
-    private  short      field_1_formatFlags;
-    private  BitField   showActual                                  = BitFieldFactory.getInstance(0x1);
-    private  BitField   showPercent                                 = BitFieldFactory.getInstance(0x2);
-    private  BitField   labelAsPercentage                           = BitFieldFactory.getInstance(0x4);
-    private  BitField   smoothedLine                                = BitFieldFactory.getInstance(0x8);
-    private  BitField   showLabel                                   = BitFieldFactory.getInstance(0x10);
-    private  BitField   showBubbleSizes                             = BitFieldFactory.getInstance(0x20);
+public final class SeriesLabelsRecord extends Record {
+    public final static short      sid = 0x100c;
+
+    private static final BitField showActual        = BitFieldFactory.getInstance(0x01);
+    private static final BitField showPercent       = BitFieldFactory.getInstance(0x02);
+    private static final BitField labelAsPercentage = BitFieldFactory.getInstance(0x04);
+    private static final BitField smoothedLine      = BitFieldFactory.getInstance(0x08);
+    private static final BitField showLabel         = BitFieldFactory.getInstance(0x10);
+    private static final BitField showBubbleSizes   = BitFieldFactory.getInstance(0x20);
 
+    private  short      field_1_formatFlags;
 
     public SeriesLabelsRecord()
     {
@@ -256,10 +254,4 @@ public class SeriesLabelsRecord
     {
         return showBubbleSizes.isSet(field_1_formatFlags);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 84fc3efc1019d3f0b6bfdd0431254b200ac07a48..c919278b4286b5c545bb463cb65cc0eaf0fff880 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * Describes a chart sheet properties record.
@@ -30,16 +29,16 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class SheetPropertiesRecord
-    extends Record
-{
-    public final static short      sid                             = 0x1044;
+public final class SheetPropertiesRecord extends Record {
+    public final static short sid = 0x1044;
+    
+    private static final BitField chartTypeManuallyFormatted = BitFieldFactory.getInstance(0x01);
+    private static final BitField plotVisibleOnly            = BitFieldFactory.getInstance(0x02);
+    private static final BitField doNotSizeWithWindow        = BitFieldFactory.getInstance(0x04);
+    private static final BitField defaultPlotDimensions      = BitFieldFactory.getInstance(0x08);
+    private static final BitField autoPlotArea               = BitFieldFactory.getInstance(0x10);
+    
     private  short      field_1_flags;
-    private  BitField   chartTypeManuallyFormatted                  = BitFieldFactory.getInstance(0x1);
-    private  BitField   plotVisibleOnly                             = BitFieldFactory.getInstance(0x2);
-    private  BitField   doNotSizeWithWindow                         = BitFieldFactory.getInstance(0x4);
-    private  BitField   defaultPlotDimensions                       = BitFieldFactory.getInstance(0x8);
-    private  BitField   autoPlotArea                                = BitFieldFactory.getInstance(0x10);
     private  byte       field_2_empty;
     public final static byte        EMPTY_NOT_PLOTTED              = 0;
     public final static byte        EMPTY_ZERO                     = 1;
@@ -274,10 +273,4 @@ public class SheetPropertiesRecord
     {
         return autoPlotArea.isSet(field_1_flags);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 65ca23cf34324e29773cd8e38277439971348320..6990a5efdc3e975403423d798ada4c1679410141 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-import org.apache.poi.util.LittleEndian;
-import org.apache.poi.util.StringUtil;
 import org.apache.poi.util.BitField;
 import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.LittleEndian;
+import org.apache.poi.util.StringUtil;
 
 /**
  * Title:        Style Record<P>
@@ -32,11 +30,11 @@ import org.apache.poi.util.BitFieldFactory;
  * @author aviks : string fixes for UserDefined Style
  * @version 2.0-pre
  */
+public final class StyleRecord extends Record {
+    public final static short sid = 0x0293;
+
+    private static final BitField fHighByte = BitFieldFactory.getInstance(0x01);
 
-public class StyleRecord
-    extends Record
-{
-    public final static short sid                = 0x293;
     public final static short STYLE_USER_DEFINED = 0;
     public final static short STYLE_BUILT_IN     = 1;
 
@@ -50,7 +48,6 @@ public class StyleRecord
     // only for user defined styles
     private short              field_2_name_length; //OO doc says 16 bit length, so we believe
     private byte               field_3_string_options;
-    private BitField fHighByte;
     private String             field_4_name;
 
     public StyleRecord()
@@ -77,8 +74,6 @@ public class StyleRecord
 
     protected void fillFields(RecordInputStream in)
     {
-        fHighByte = BitFieldFactory.getInstance(0x01); //have to init here, since we are being called
-                                        //from super, and class level init hasnt been done. 
         field_1_xf_index = in.readShort();
         if (getType() == STYLE_BUILT_IN)
         {
index 7a48e5e0e7c394292512e287fc47dd31bd6ab96d..237b2cb40ef633e86d76cc8ad25784f32d46cd4e 100644 (file)
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
+package org.apache.poi.hssf.record;
+
+import org.apache.poi.hssf.record.formula.TblPtg;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.LittleEndian;
 /**
  * TableRecord - The record specifies a data table.
  * This record is preceded by a single Formula record that
  * 
  * See p536 of the June 08 binary docs
  */
-package org.apache.poi.hssf.record;
-
-import org.apache.poi.hssf.record.formula.TblPtg;
-import org.apache.poi.util.BitField;
-import org.apache.poi.util.BitFieldFactory;
-import org.apache.poi.util.LittleEndian;
-
-public class TableRecord extends Record {
+public final class TableRecord extends Record {
     public static final short sid = 566;
+    
+    private static final BitField alwaysCalc      = BitFieldFactory.getInstance(0x0001);
+    private static final BitField reserved1       = BitFieldFactory.getInstance(0x0002);
+    private static final BitField rowOrColInpCell = BitFieldFactory.getInstance(0x0004);
+    private static final BitField oneOrTwoVar     = BitFieldFactory.getInstance(0x0008);
+    private static final BitField rowDeleted      = BitFieldFactory.getInstance(0x0010);
+    private static final BitField colDeleted      = BitFieldFactory.getInstance(0x0020);
+    private static final BitField reserved2       = BitFieldFactory.getInstance(0x0040);
+    private static final BitField reserved3       = BitFieldFactory.getInstance(0x0080);
+    
     private short field_1_ref_rowFirst;
     private short field_2_ref_rowLast;
     private short field_3_ref_colFirst;
@@ -45,14 +53,6 @@ public class TableRecord extends Record {
     private short field_9_rowInputCol;
     private short field_10_colInputCol;
     
-    private BitField alwaysCalc      = BitFieldFactory.getInstance(0x0001);
-    private BitField reserved1       = BitFieldFactory.getInstance(0x0002);
-    private BitField rowOrColInpCell = BitFieldFactory.getInstance(0x0004);
-    private BitField oneOrTwoVar     = BitFieldFactory.getInstance(0x0008);
-    private BitField rowDeleted      = BitFieldFactory.getInstance(0x0010);
-    private BitField colDeleted      = BitFieldFactory.getInstance(0x0020);
-    private BitField reserved2       = BitFieldFactory.getInstance(0x0040);
-    private BitField reserved3       = BitFieldFactory.getInstance(0x0080);
 
        protected void fillFields(RecordInputStream in) {
                field_1_ref_rowFirst = in.readShort();
index 4d3dbb43b15c0a1ba0c5b41e5be0988a7c1336e5..2d649247b5fc9777b582bfa8a0faaecb28db7c21 100644 (file)
@@ -32,25 +32,25 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class TextObjectBaseRecord
-    extends Record
-{
+public class TextObjectBaseRecord extends Record {
     public final static short      sid                             = 0x1B6;
+    
+    private static final BitField reserved1               = BitFieldFactory.getInstance(0x0001);
+    private static final BitField HorizontalTextAlignment = BitFieldFactory.getInstance(0x000E);
+    private static final BitField VerticalTextAlignment   = BitFieldFactory.getInstance(0x0070);
+    private static final BitField reserved2               = BitFieldFactory.getInstance(0x0180);
+    private static final BitField textLocked              = BitFieldFactory.getInstance(0x0200);
+    private static final BitField reserved3               = BitFieldFactory.getInstance(0xFC00);
+    
     private  short      field_1_options;
-    private  BitField   reserved1                                   = BitFieldFactory.getInstance(0x1);
-    private BitField   HorizontalTextAlignment                    = BitFieldFactory.getInstance(0x000E);
     public final static short  HORIZONTAL_TEXT_ALIGNMENT_LEFT_ALIGNED = 1;
     public final static short  HORIZONTAL_TEXT_ALIGNMENT_CENTERED = 2;
     public final static short  HORIZONTAL_TEXT_ALIGNMENT_RIGHT_ALIGNED = 3;
     public final static short  HORIZONTAL_TEXT_ALIGNMENT_JUSTIFIED = 4;
-    private BitField   VerticalTextAlignment                      = BitFieldFactory.getInstance(0x0070);
     public final static short  VERTICAL_TEXT_ALIGNMENT_TOP    = 1;
     public final static short  VERTICAL_TEXT_ALIGNMENT_CENTER = 2;
     public final static short  VERTICAL_TEXT_ALIGNMENT_BOTTOM = 3;
     public final static short  VERTICAL_TEXT_ALIGNMENT_JUSTIFY = 4;
-    private BitField   reserved2                                  = BitFieldFactory.getInstance(0x0180);
-    private  BitField   textLocked                                  = BitFieldFactory.getInstance(0x200);
-    private BitField   reserved3                                  = BitFieldFactory.getInstance(0xFC00);
     private  short      field_2_textOrientation;
     public final static short       TEXT_ORIENTATION_NONE          = 0;
     public final static short       TEXT_ORIENTATION_TOP_TO_BOTTOM = 1;
@@ -452,10 +452,4 @@ public class TextObjectBaseRecord
     {
         return reserved3.getShortValue(field_1_options);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 702dfbe163242375bb6dea13a35083f5125cf278..0840fe19324c275f91f7d8ac5f20bd5ffabbf1dd 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The text record is used to define text stored on a chart.
@@ -30,10 +29,26 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class TextRecord
-    extends Record
-{
+public final class TextRecord extends Record {
     public final static short      sid                             = 0x1025;
+    
+    private static final BitField dataLabelPlacement            = BitFieldFactory.getInstance(0x000F);
+    private static final BitField autoColor                     = BitFieldFactory.getInstance(0x0001);
+    private static final BitField showKey                       = BitFieldFactory.getInstance(0x0002);
+    private static final BitField showValue                     = BitFieldFactory.getInstance(0x0004);
+    private static final BitField vertical                      = BitFieldFactory.getInstance(0x0008);
+    private static final BitField autoGeneratedText             = BitFieldFactory.getInstance(0x0010);
+    private static final BitField generated                     = BitFieldFactory.getInstance(0x0020);
+    private static final BitField autoLabelDeleted              = BitFieldFactory.getInstance(0x0040);
+    private static final BitField autoBackground                = BitFieldFactory.getInstance(0x0080);
+    private static final BitField rotation                      = BitFieldFactory.getInstance(0x0700);
+
+    private static final BitField showCategoryLabelAsPercentage = BitFieldFactory.getInstance(0x0800);
+    private static final BitField showValueAsPercentage         = BitFieldFactory.getInstance(0x1000);
+    private static final BitField showBubbleSizes               = BitFieldFactory.getInstance(0x2000);
+    private static final BitField showLabel                     = BitFieldFactory.getInstance(0x4000);
+    
+    
     private  byte       field_1_horizontalAlignment;
     public final static byte        HORIZONTAL_ALIGNMENT_LEFT      = 1;
     public final static byte        HORIZONTAL_ALIGNMENT_CENTER    = 2;
@@ -53,26 +68,12 @@ public class TextRecord
     private  int        field_7_width;
     private  int        field_8_height;
     private  short      field_9_options1;
-    private  BitField   autoColor                                   = BitFieldFactory.getInstance(0x1);
-    private  BitField   showKey                                     = BitFieldFactory.getInstance(0x2);
-    private  BitField   showValue                                   = BitFieldFactory.getInstance(0x4);
-    private  BitField   vertical                                    = BitFieldFactory.getInstance(0x8);
-    private  BitField   autoGeneratedText                           = BitFieldFactory.getInstance(0x10);
-    private  BitField   generated                                   = BitFieldFactory.getInstance(0x20);
-    private  BitField   autoLabelDeleted                            = BitFieldFactory.getInstance(0x40);
-    private  BitField   autoBackground                              = BitFieldFactory.getInstance(0x80);
-    private BitField   rotation                                   = BitFieldFactory.getInstance(0x0700);
     public final static short  ROTATION_NONE                  = 0;
     public final static short  ROTATION_TOP_TO_BOTTOM         = 1;
     public final static short  ROTATION_ROTATED_90_DEGREES    = 2;
     public final static short  ROTATION_ROTATED_90_DEGREES_CLOCKWISE = 3;
-    private  BitField   showCategoryLabelAsPercentage               = BitFieldFactory.getInstance(0x800);
-    private  BitField   showValueAsPercentage                       = BitFieldFactory.getInstance(0x1000);
-    private  BitField   showBubbleSizes                             = BitFieldFactory.getInstance(0x2000);
-    private  BitField   showLabel                                   = BitFieldFactory.getInstance(0x4000);
     private  short      field_10_indexOfColorValue;
     private  short      field_11_options2;
-    private BitField   dataLabelPlacement                         = BitFieldFactory.getInstance(0x000F);
     public final static short  DATA_LABEL_PLACEMENT_CHART_DEPENDENT = 0;
     public final static short  DATA_LABEL_PLACEMENT_OUTSIDE   = 1;
     public final static short  DATA_LABEL_PLACEMENT_INSIDE    = 2;
@@ -740,10 +741,4 @@ public class TextRecord
     {
         return dataLabelPlacement.getShortValue(field_11_options2);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 325dffc40c3c6b7512cc9e51405931808a0f06b4..1b950e3ed428c02eea6e3627efce6de933dbcd1b 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The Tick record defines how tick marks and label positioning/formatting
@@ -30,10 +29,14 @@ import org.apache.poi.util.*;
 
  * @author Andrew C. Oliver(acoliver at apache.org)
  */
-public class TickRecord
-    extends Record
-{
-    public final static short      sid                             = 0x101e;
+public final class TickRecord extends Record {
+    public final static short sid = 0x101E;
+    
+    private static final BitField autoTextColor      = BitFieldFactory.getInstance(0x1);
+    private static final BitField autoTextBackground = BitFieldFactory.getInstance(0x2);
+    private static final BitField rotation           = BitFieldFactory.getInstance(0x1c);
+    private static final BitField autorotate         = BitFieldFactory.getInstance(0x20);
+    
     private  byte       field_1_majorTickType;
     private  byte       field_2_minorTickType;
     private  byte       field_3_labelPosition;
@@ -44,10 +47,6 @@ public class TickRecord
     private  int        field_8_zero3;
     private  int        field_9_zero4;
     private  short      field_10_options;
-    private  BitField   autoTextColor                               = BitFieldFactory.getInstance(0x1);
-    private  BitField   autoTextBackground                          = BitFieldFactory.getInstance(0x2);
-    private BitField   rotation                                   = BitFieldFactory.getInstance(0x1c);
-    private  BitField   autorotate                                  = BitFieldFactory.getInstance(0x20);
     private  short      field_11_tickColor;
     private  short      field_12_zero5;
 
@@ -442,10 +441,4 @@ public class TickRecord
     {
         return autorotate.isSet(field_10_options);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 44b26659e41c99f34b02c1b7c38f292f44019a8c..6c94c5c54cca35191e05792bbbdc90a71af2f8e2 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
-
-
-import org.apache.poi.util.*;
+import org.apache.poi.util.BitField;
+import org.apache.poi.util.BitFieldFactory;
+import org.apache.poi.util.HexDump;
+import org.apache.poi.util.LittleEndian;
 
 /**
  * The value range record defines the range of the value axis.
@@ -30,25 +29,25 @@ import org.apache.poi.util.*;
 
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class ValueRangeRecord
-    extends Record
-{
-    public final static short      sid                             = 0x101f;
+public final class ValueRangeRecord extends Record {
+    public final static short sid = 0x101f;
+    
+    private static final BitField automaticMinimum           = BitFieldFactory.getInstance(0x0001);
+    private static final BitField automaticMaximum           = BitFieldFactory.getInstance(0x0002);
+    private static final BitField automaticMajor             = BitFieldFactory.getInstance(0x0004);
+    private static final BitField automaticMinor             = BitFieldFactory.getInstance(0x0008);
+    private static final BitField automaticCategoryCrossing  = BitFieldFactory.getInstance(0x0010);
+    private static final BitField logarithmicScale           = BitFieldFactory.getInstance(0x0020);
+    private static final BitField valuesInReverse            = BitFieldFactory.getInstance(0x0040);
+    private static final BitField crossCategoryAxisAtMaximum = BitFieldFactory.getInstance(0x0080);
+    private static final BitField reserved                   = BitFieldFactory.getInstance(0x0100);
+    
     private  double     field_1_minimumAxisValue;
     private  double     field_2_maximumAxisValue;
     private  double     field_3_majorIncrement;
     private  double     field_4_minorIncrement;
     private  double     field_5_categoryAxisCross;
     private  short      field_6_options;
-    private  BitField   automaticMinimum                            = BitFieldFactory.getInstance(0x1);
-    private  BitField   automaticMaximum                            = BitFieldFactory.getInstance(0x2);
-    private  BitField   automaticMajor                              = BitFieldFactory.getInstance(0x4);
-    private  BitField   automaticMinor                              = BitFieldFactory.getInstance(0x8);
-    private  BitField   automaticCategoryCrossing                   = BitFieldFactory.getInstance(0x10);
-    private  BitField   logarithmicScale                            = BitFieldFactory.getInstance(0x20);
-    private  BitField   valuesInReverse                             = BitFieldFactory.getInstance(0x40);
-    private  BitField   crossCategoryAxisAtMaximum                  = BitFieldFactory.getInstance(0x80);
-    private  BitField   reserved                                    = BitFieldFactory.getInstance(0x100);
 
 
     public ValueRangeRecord()
@@ -432,10 +431,4 @@ public class ValueRangeRecord
     {
         return reserved.isSet(field_6_options);
     }
-
-
-}  // END OF CLASS
-
-
-
-
+}
index 6c715494f86bdaf589d0ff891d24deb1369908b9..fccb7ccdaac0271ccf58fbe36266c228d915bf2e 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
+
 package org.apache.poi.hssf.record;
 
+import java.util.Iterator;
+
 /**
- * VerticalPageBreak record that stores page breaks at columns
- * <p>
- * This class is just used so that SID compares work properly in the RecordFactory
+ * VerticalPageBreak (0x001A) record that stores page breaks at columns<p/>
+ * 
  * @see PageBreakRecord
- * @author Danny Mui (dmui at apache dot org) 
+ * @author Danny Mui (dmui at apache dot org)
  */
-public class VerticalPageBreakRecord extends PageBreakRecord {
-       
-    public static final short sid = PageBreakRecord.VERTICAL_SID;
-    
+public final class VerticalPageBreakRecord extends PageBreakRecord {
+
+       public static final short sid = 0x001A;
+
        /**
-        * 
+        * Creates an empty vertical page break record
         */
        public VerticalPageBreakRecord() {
-               super();
-       }
 
-       /**
-        * @param sid
-        */
-       public VerticalPageBreakRecord(short sid) {
-               super(sid);
        }
 
        /**
-     * @param in the RecordInputstream to read the record from
+        * @param in the RecordInputstream to read the record from
         */
        public VerticalPageBreakRecord(RecordInputStream in) {
                super(in);
        }
 
-       /* (non-Javadoc)
-        * @see org.apache.poi.hssf.record.Record#getSid()
-        */
+       protected void validateSid(short id) {
+               if (id != getSid()) {
+                       throw new RecordFormatException(
+                                       "NOT A HorizontalPageBreak or VerticalPageBreak RECORD!! " + id);
+               }
+       }
+
        public short getSid() {
                return sid;
        }
 
+       public Object clone() {
+               PageBreakRecord result = new VerticalPageBreakRecord();
+               Iterator iterator = getBreaksIterator();
+               while (iterator.hasNext()) {
+                       Break original = (Break) iterator.next();
+                       result.addBreak(original.main, original.subFrom, original.subTo);
+               }
+               return result;
+       }
 }
index e2bb6d5609d618f20911e576333dc251faa9bc0c..6e60ef41a6974e0898ba08d41f24ad3a36f624c9 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
@@ -15,7 +14,6 @@
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.record;
 
@@ -31,34 +29,27 @@ import org.apache.poi.util.LittleEndian;
  * @author Jason Height (jheight at chariot dot net dot au)
  * @version 2.0-pre
  */
-
-public class WindowTwoRecord
-    extends Record
-{
-    public final static short sid = 0x23e;
-    private short             field_1_options;
+public final class WindowTwoRecord extends Record {
+    public final static short sid = 0x023E;
 
     // bitfields
-    private BitField          displayFormulas         = BitFieldFactory.getInstance(0x01);
-    private BitField          displayGridlines        = BitFieldFactory.getInstance(0x02);
-    private BitField          displayRowColHeadings   = BitFieldFactory.getInstance(0x04);
-    private BitField          freezePanes             = BitFieldFactory.getInstance(0x08);
-    private BitField          displayZeros            = BitFieldFactory.getInstance(0x10);
-    private BitField          defaultHeader           =
-        BitFieldFactory.getInstance(0x20);   // if false use color in field 4
-
-    // if true use default foreground
-    // for headers
-    private BitField          arabic                  =
-        BitFieldFactory.getInstance(0x40);   // for our desert dwelling friends
-    private BitField          displayGuts             = BitFieldFactory.getInstance(0x80);
-    private BitField          freezePanesNoSplit      = BitFieldFactory.getInstance(0x100);
-    private BitField          selected                = BitFieldFactory.getInstance(0x200);
-    private BitField          active                  = BitFieldFactory.getInstance(0x400);
-    private BitField          savedInPageBreakPreview = BitFieldFactory.getInstance(0x800);
-
+    private static final BitField displayFormulas         = BitFieldFactory.getInstance(0x01);
+    private static final BitField displayGridlines        = BitFieldFactory.getInstance(0x02);
+    private static final BitField displayRowColHeadings   = BitFieldFactory.getInstance(0x04);
+    private static final BitField freezePanes             = BitFieldFactory.getInstance(0x08);
+    private static final BitField displayZeros            = BitFieldFactory.getInstance(0x10);
+    /**  if false use color in field 4 if true use default foreground for headers */
+    private static final BitField defaultHeader           = BitFieldFactory.getInstance(0x20);   
+    private static final BitField arabic                  = BitFieldFactory.getInstance(0x040);
+    private static final BitField displayGuts             = BitFieldFactory.getInstance(0x080);
+    private static final BitField freezePanesNoSplit      = BitFieldFactory.getInstance(0x100);
+    private static final BitField selected                = BitFieldFactory.getInstance(0x200);
+    private static final BitField active                  = BitFieldFactory.getInstance(0x400);
+    private static final BitField savedInPageBreakPreview = BitFieldFactory.getInstance(0x800);
     // 4-7 reserved
     // end bitfields
+
+    private short             field_1_options;
     private short             field_2_top_row;
     private short             field_3_left_col;
     private int               field_4_header_color;
index cc74b98f699a3101ed3ffdef3049fb762d08d4ec..9fd2412a98de225d7560e1a409bdbff068dc57c0 100644 (file)
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
+
 package org.apache.poi.hssf.record.aggregates;
 
 import java.util.ArrayList;
 import java.util.Iterator;
 import java.util.List;
 
+import org.apache.poi.hssf.model.RecordStream;
 import org.apache.poi.hssf.record.CFHeaderRecord;
 import org.apache.poi.hssf.record.CFRuleRecord;
 import org.apache.poi.hssf.record.Record;
 import org.apache.poi.hssf.record.RecordInputStream;
 import org.apache.poi.ss.util.Region;
 import org.apache.poi.ss.util.CellRangeAddress;
-import org.apache.poi.util.POILogFactory;
-import org.apache.poi.util.POILogger;
 
 /**
  * CFRecordsAggregate - aggregates Conditional Formatting records CFHeaderRecord 
@@ -37,15 +37,12 @@ import org.apache.poi.util.POILogger;
  * @author Dmitriy Kumshayev
  *
  */
-public final class CFRecordsAggregate extends Record
-{
+public final class CFRecordsAggregate extends Record {
        /** Excel allows up to 3 conditional formating rules */
        private static final int MAX_CONDTIONAL_FORMAT_RULES = 3;
 
        public final static short sid = -2008; // not a real BIFF record
 
-       private static POILogger log = POILogFactory.getLogger(CFRecordsAggregate.class);
-
        private final CFHeaderRecord header;
 
        /** List of CFRuleRecord objects */
@@ -79,9 +76,8 @@ public final class CFRecordsAggregate extends Record
         * @param offset - position of {@link CFHeaderRecord} object in the list of Record objects
         * @return CFRecordsAggregate object
         */
-       public static CFRecordsAggregate createCFAggregate(List recs, int pOffset)
-       {
-               Record rec = ( Record ) recs.get(pOffset);
+       public static CFRecordsAggregate createCFAggregate(RecordStream rs) {
+               Record rec = rs.getNext();
                if (rec.getSid() != CFHeaderRecord.sid) {
                        throw new IllegalStateException("next record sid was " + rec.getSid() 
                                        + " instead of " + CFHeaderRecord.sid + " as expected");
@@ -91,35 +87,10 @@ public final class CFRecordsAggregate extends Record
                int nRules = header.getNumberOfConditionalFormats();
 
                CFRuleRecord[] rules = new CFRuleRecord[nRules];
-               int offset = pOffset;
-               int countFound = 0;
-               while (countFound < rules.length) {
-                       offset++;
-                       if(offset>=recs.size()) {
-                               break;
-                       }
-                       rec = (Record)recs.get(offset);
-                       if(rec instanceof CFRuleRecord) {
-                               rules[countFound] = (CFRuleRecord) rec;
-                               countFound++;
-                       } else {
-                               break;
-                       }
-               }
-
-               if (countFound < nRules)
-               { // TODO -(MAR-2008) can this ever happen? write junit 
-                       
-                       if (log.check(POILogger.DEBUG))
-                       {
-                               log.log(POILogger.DEBUG, "Expected  " + nRules + " Conditional Formats, "
-                                               + "but found " + countFound + " rules");
-                       }
-                       header.setNumberOfConditionalFormats(nRules);
-                       CFRuleRecord[] lessRules = new CFRuleRecord[countFound];
-                       System.arraycopy(rules, 0, lessRules, 0, countFound);
-                       rules = lessRules;
+               for (int i = 0; i < rules.length; i++) {
+                       rules[i] = (CFRuleRecord) rs.getNext();
                }
+               
                return new CFRecordsAggregate(header, rules);
        }
 
index 6df796c2aa76098274d0ecf6d2b6e5bf1c8ad347..b24d8c5b451a6236d0635aa1781862ed052f04e5 100644 (file)
@@ -1,72 +1,52 @@
-/*
-* 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.record.aggregates;
+/* ====================================================================
+   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.
+==================================================================== */
 
-import org.apache.poi.hssf.record.ColumnInfoRecord;
-import org.apache.poi.hssf.record.Record;
-import org.apache.poi.hssf.record.RecordInputStream;
+package org.apache.poi.hssf.record.aggregates;
 
 import java.util.ArrayList;
-import java.util.Iterator;
 import java.util.List;
 
+import org.apache.poi.hssf.model.RecordStream;
+import org.apache.poi.hssf.record.ColumnInfoRecord;
+import org.apache.poi.hssf.record.Record;
+
 /**
  * @author Glen Stampoultzis
  * @version $Id$
  */
-public class ColumnInfoRecordsAggregate
-    extends Record
-{
-//    int     size     = 0;
-    List records = null;
-
-    public ColumnInfoRecordsAggregate()
-    {
-        records = new ArrayList();
-    }
-
-    /** You never fill an aggregate */
-    protected void fillFields(RecordInputStream in)
-    {
-    }
-
-    /** Not required by an aggregate */
-    protected void validateSid(short id)
-    {
-    }
-
-    /** It's an aggregate... just made something up */
-    public short getSid()
-    {
-        return -1012;
-    }
-
-    public int getRecordSize()
-    {
-        int size = 0;
-        for ( Iterator iterator = records.iterator(); iterator.hasNext(); )
-            size += ( (ColumnInfoRecord) iterator.next() ).getRecordSize();
-        return size;
-    }
-
-    public Iterator getIterator()
-    {
-        return records.iterator();
-    }
+public final class ColumnInfoRecordsAggregate extends RecordAggregate {
+       private final List records;
+
+       /**
+        * Creates an empty aggregate
+        */
+       public ColumnInfoRecordsAggregate() {
+               records = new ArrayList();
+       }
+    public ColumnInfoRecordsAggregate(RecordStream rs) {
+        this();
+        
+        while(rs.peekNextClass() == ColumnInfoRecord.class) {
+               records.add(rs.getNext());
+        }
+        if (records.size() < 1) {
+               throw new RuntimeException("No column info records found");
+        }
+   }
 
     /**
      * Performs a deep clone of the record
@@ -105,25 +85,14 @@ public class ColumnInfoRecordsAggregate
         return records.size();
     }
 
-    /**
-     * called by the class that is responsible for writing this sucker.
-     * Subclasses should implement this so that their data is passed back in a
-     * byte array.
-     *
-     * @param offset    offset to begin writing at
-     * @param data      byte array containing instance data
-     * @return          number of bytes written
-     */
-    public int serialize(int offset, byte [] data)
-    {
-        Iterator itr = records.iterator();
-        int      pos = offset;
-
-        while (itr.hasNext())
-        {
-            pos += (( Record ) itr.next()).serialize(pos, data);
-        }
-        return pos - offset;
+    public void visitContainedRecords(RecordVisitor rv) {
+       int nItems = records.size();
+       if (nItems < 1) {
+               return;
+       }
+       for(int i=0; i<nItems; i++) {
+               rv.visitRecord((Record)records.get(i));
+       }
     }
 
     public int findStartOfColumnOutlineGroup(int idx)
@@ -178,8 +147,7 @@ public class ColumnInfoRecordsAggregate
         return idx;
     }
 
-    public ColumnInfoRecord getColInfo(int idx)
-    {
+    private ColumnInfoRecord getColInfo(int idx) {
         return (ColumnInfoRecord) records.get( idx );
     }
 
@@ -191,7 +159,7 @@ public class ColumnInfoRecordsAggregate
             columnInfo.setHidden( hidden );
             if (idx + 1 < records.size())
             {
-                ColumnInfoRecord nextColumnInfo = (ColumnInfoRecord) records.get( idx + 1 );
+                ColumnInfoRecord nextColumnInfo = getColInfo(idx + 1);
                 if (columnInfo.getLastColumn() + 1 == nextColumnInfo.getFirstColumn())
                 {
                     if (nextColumnInfo.getOutlineLevel() < level)
@@ -279,7 +247,7 @@ public class ColumnInfoRecordsAggregate
             return;
 
         // Find the start of the group.
-        ColumnInfoRecord columnInfo = (ColumnInfoRecord) records.get( findStartOfColumnOutlineGroup( idx ) );
+        ColumnInfoRecord columnInfo = getColInfo( findStartOfColumnOutlineGroup( idx ) );
 
         // Hide all the columns until the end of the group
         columnInfo = writeHidden( columnInfo, idx, true );
@@ -331,7 +299,7 @@ public class ColumnInfoRecordsAggregate
      * @see org.apache.poi.hssf.record.ColumnInfoRecord
      * @return record containing a ColumnInfoRecord
      */
-    public static Record createColInfo()
+    public static ColumnInfoRecord createColInfo()
     {
         ColumnInfoRecord retval = new ColumnInfoRecord();
 
@@ -452,7 +420,7 @@ public class ColumnInfoRecordsAggregate
             ci.setCollapsed( collapsed.booleanValue() );
     }
 
-    public int findColumnIdx(int column, int fromIdx)
+    private int findColumnIdx(int column, int fromIdx)
     {
         if (column < 0)
             throw new IllegalArgumentException( "column parameter out of range: " + column );
@@ -462,7 +430,7 @@ public class ColumnInfoRecordsAggregate
         ColumnInfoRecord ci;
         for (int k = fromIdx; k < records.size(); k++)
         {
-            ci = ( ColumnInfoRecord ) records.get(k);
+            ci = getColInfo(k);
             if ((ci.getFirstColumn() <= column)
                     && (column <= ci.getLastColumn()))
             {
@@ -477,8 +445,8 @@ public class ColumnInfoRecordsAggregate
     {
         if (columnIdx == 0)
             return;
-        ColumnInfoRecord previousCol = (ColumnInfoRecord) records.get( columnIdx - 1);
-        ColumnInfoRecord currentCol = (ColumnInfoRecord) records.get( columnIdx );
+        ColumnInfoRecord previousCol = getColInfo( columnIdx - 1);
+        ColumnInfoRecord currentCol = getColInfo( columnIdx );
         boolean adjacentColumns = previousCol.getLastColumn() == currentCol.getFirstColumn() - 1;
         if (!adjacentColumns)
             return;
@@ -513,7 +481,7 @@ public class ColumnInfoRecordsAggregate
             int columnIdx = findColumnIdx( i, Math.max(0,fromIdx) );
             if (columnIdx != -1)
             {
-                level = ((ColumnInfoRecord)records.get( columnIdx )).getOutlineLevel();
+                level = getColInfo(columnIdx).getOutlineLevel();
                 if (indent) level++; else level--;
                 level = Math.max(0, level);
                 level = Math.min(7, level);
@@ -525,6 +493,30 @@ public class ColumnInfoRecordsAggregate
         }
 
     }
+    /**
+     * Finds the <tt>ColumnInfoRecord</tt> which contains the specified columnIndex
+     * @param columnIndex index of the column (not the index of the ColumnInfoRecord)
+     * @return <code>null</code> if no column info found for the specified column
+     */
+       public ColumnInfoRecord findColumnInfo(int columnIndex) {
+               int nInfos = records.size();
+               for(int i=0; i< nInfos; i++) {
+                       ColumnInfoRecord ci = getColInfo(i);
+                       if (ci.getFirstColumn() <= columnIndex && columnIndex <= ci.getLastColumn()) {
+                               return ci;
+                       }
+               }
+               return null;
+       }
+       public int getMaxOutlineLevel() {
+        int result = 0;
+        int count=records.size();
+        for (int i=0; i<count; i++) {
+            ColumnInfoRecord columnInfoRecord = getColInfo(i);
+            result = Math.max(columnInfoRecord.getOutlineLevel(), result);
+        }
+        return result;
+       }
 
 
 }
diff --git a/src/java/org/apache/poi/hssf/record/aggregates/ConditionalFormattingTable.java b/src/java/org/apache/poi/hssf/record/aggregates/ConditionalFormattingTable.java
new file mode 100644 (file)
index 0000000..34e9ca8
--- /dev/null
@@ -0,0 +1,88 @@
+/* ====================================================================
+   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.record.aggregates;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.poi.hssf.model.RecordStream;
+import org.apache.poi.hssf.record.CFHeaderRecord;
+import org.apache.poi.hssf.record.Record;
+
+/**
+ * Holds all the conditional formatting for a workbook sheet.<p/>
+ * 
+ * See OOO exelfileformat.pdf sec 4.12 'Conditional Formatting Table'
+ * 
+ * @author Josh Micich
+ */
+public final class ConditionalFormattingTable extends RecordAggregate {
+
+       private final List _cfHeaders;
+
+       /**
+        * Creates an empty ConditionalFormattingTable
+        */
+       public ConditionalFormattingTable() {
+               _cfHeaders = new ArrayList();
+       }
+
+       public ConditionalFormattingTable(RecordStream rs) {
+
+               List temp = new ArrayList();
+               while (rs.peekNextClass() == CFHeaderRecord.class) {
+                       temp.add(CFRecordsAggregate.createCFAggregate(rs));
+               }
+               _cfHeaders = temp;
+       }
+
+       public void visitContainedRecords(RecordVisitor rv) {
+               for (int i = 0; i < _cfHeaders.size(); i++) {
+                       rv.visitRecord((Record) _cfHeaders.get(i));
+               }
+       }
+
+       /**
+        * @return index of the newly added CF header aggregate
+        */
+       public int add(CFRecordsAggregate cfAggregate) {
+               _cfHeaders.add(cfAggregate);
+               return _cfHeaders.size() - 1;
+       }
+
+       public int size() {
+               return _cfHeaders.size();
+       }
+
+       public CFRecordsAggregate get(int index) {
+               checkIndex(index);
+               return (CFRecordsAggregate) _cfHeaders.get(index);
+       }
+
+       public void remove(int index) {
+               checkIndex(index);
+               _cfHeaders.remove(index);
+       }
+
+       private void checkIndex(int index) {
+               if (index < 0 || index >= _cfHeaders.size()) {
+                       throw new IllegalArgumentException("Specified CF index " + index
+                                       + " is outside the allowable range (0.." + (_cfHeaders.size() - 1) + ")");
+               }
+       }
+}
index 133386d7dfd5b59e7c929dcdcc718ebcdab585d1..f4861b011b64ad17b8deec7983d97a72a0735df5 100644 (file)
@@ -21,17 +21,9 @@ import java.util.ArrayList;
 import java.util.List;\r
 \r
 import org.apache.poi.hssf.model.RecordStream;\r
-import org.apache.poi.hssf.record.CFHeaderRecord;\r
-import org.apache.poi.hssf.record.CFRuleRecord;\r
 import org.apache.poi.hssf.record.DVALRecord;\r
 import org.apache.poi.hssf.record.DVRecord;\r
-import org.apache.poi.hssf.record.EOFRecord;\r
-import org.apache.poi.hssf.record.HyperlinkRecord;\r
-import org.apache.poi.hssf.record.MergeCellsRecord;\r
-import org.apache.poi.hssf.record.PaneRecord;\r
 import org.apache.poi.hssf.record.Record;\r
-import org.apache.poi.hssf.record.SelectionRecord;\r
-import org.apache.poi.hssf.record.WindowTwoRecord;\r
 \r
 /**\r
  * Manages the DVALRecord and DVRecords for a single sheet<br/>\r
@@ -40,7 +32,6 @@ import org.apache.poi.hssf.record.WindowTwoRecord;
  */\r
 public final class DataValidityTable extends RecordAggregate {\r
 \r
-       private static final short sid = -0x01B2; // not a real record\r
        private final DVALRecord _headerRec;\r
        /**\r
         * The list of data validations for the current sheet.\r
@@ -57,120 +48,21 @@ public final class DataValidityTable extends RecordAggregate {
                _validationList = temp;\r
        }\r
 \r
-       private DataValidityTable() {\r
+       public DataValidityTable() {\r
                _headerRec = new DVALRecord();\r
                _validationList = new ArrayList();\r
        }\r
 \r
-       public short getSid() {\r
-               return sid;\r
-       }\r
-\r
-       public int serialize(int offset, byte[] data) {\r
-               int result = _headerRec.serialize(offset, data);\r
-               for (int i = 0; i < _validationList.size(); i++) {\r
-                       result += ((Record) _validationList.get(i)).serialize(offset + result, data);\r
+       public void visitContainedRecords(RecordVisitor rv) {\r
+               if (_validationList.isEmpty()) {\r
+                       return;\r
                }\r
-               return result;\r
-       }\r
-\r
-       public int getRecordSize() {\r
-               int result = _headerRec.getRecordSize();\r
-               for (int i = _validationList.size() - 1; i >= 0; i--) {\r
-                       result += ((Record) _validationList.get(i)).getRecordSize();\r
+               rv.visitRecord(_headerRec);\r
+               for (int i = 0; i < _validationList.size(); i++) {\r
+                       rv.visitRecord((Record) _validationList.get(i));\r
                }\r
-               return result;\r
-       }\r
-\r
-       /**\r
-        * Creates a new <tt>DataValidityTable</tt> and inserts it in the right\r
-        * place in the sheetRecords list.\r
-        */\r
-       public static DataValidityTable createForSheet(List sheetRecords) {\r
-               int index = findDVTableInsertPos(sheetRecords);\r
-\r
-               DataValidityTable result = new DataValidityTable();\r
-               sheetRecords.add(index, result);\r
-               return result;\r
        }\r
        \r
-    /**\r
-     * Finds the index where the sheet validations header record should be inserted\r
-     * @param records the records for this sheet\r
-     * \r
-     * + WINDOW2\r
-     * o SCL\r
-     * o PANE\r
-     * oo SELECTION\r
-     * o STANDARDWIDTH\r
-     * oo MERGEDCELLS\r
-     * o LABELRANGES\r
-     * o PHONETICPR\r
-     * o Conditional Formatting Table\r
-     * o Hyperlink Table\r
-     * o Data Validity Table\r
-     * o SHEETLAYOUT\r
-     * o SHEETPROTECTION\r
-     * o RANGEPROTECTION\r
-     * + EOF\r
-     */\r
-    private static int findDVTableInsertPos(List records) {\r
-               int i = records.size() - 1;\r
-               if (!(records.get(i) instanceof EOFRecord)) {\r
-                       throw new IllegalStateException("Last sheet record should be EOFRecord");\r
-               }\r
-               while (i > 0) {\r
-                       i--;\r
-                       Record rec = (Record) records.get(i);\r
-                       if (isPriorRecord(rec.getSid())) {\r
-                               Record nextRec = (Record) records.get(i + 1);\r
-                               if (!isSubsequentRecord(nextRec.getSid())) {\r
-                                       throw new IllegalStateException("Unexpected (" + nextRec.getClass().getName()\r
-                                                       + ") found after (" + rec.getClass().getName() + ")");\r
-                               }\r
-                               return i;\r
-                       }\r
-                       if (!isSubsequentRecord(rec.getSid())) {\r
-                               throw new IllegalStateException("Unexpected (" + rec.getClass().getName()\r
-                                               + ") while looking for DV Table insert pos");\r
-                       }\r
-               }\r
-               return 0;\r
-       }\r
-\r
-       // TODO - add UninterpretedRecord as base class for many of these\r
-       // unimplemented sids\r
-\r
-       private static boolean isPriorRecord(short sid) {\r
-               switch(sid) {\r
-                       case WindowTwoRecord.sid:\r
-                       case 0x00A0: // SCL\r
-                       case PaneRecord.sid:\r
-                       case SelectionRecord.sid:\r
-                       case 0x0099: // STANDARDWIDTH\r
-                       case MergeCellsRecord.sid:\r
-                       case 0x015F: // LABELRANGES\r
-                       case 0x00EF: // PHONETICPR\r
-                       case CFHeaderRecord.sid:\r
-                       case CFRuleRecord.sid:\r
-                       case HyperlinkRecord.sid:\r
-                       case 0x0800: // QUICKTIP\r
-                               return true;\r
-               }\r
-               return false;\r
-       }\r
-\r
-       private static boolean isSubsequentRecord(short sid) {\r
-               switch(sid) {\r
-                       case 0x0862: // SHEETLAYOUT\r
-                       case 0x0867: // SHEETPROTECTION\r
-                       case 0x0868: // RANGEPROTECTION\r
-                       case EOFRecord.sid:\r
-                               return true;\r
-               }\r
-               return false;\r
-       }\r
-\r
        public void addDataValidation(DVRecord dvRecord) {\r
                _validationList.add(dvRecord);\r
                _headerRec.setDVRecNo(_validationList.size());\r
diff --git a/src/java/org/apache/poi/hssf/record/aggregates/MergedCellsTable.java b/src/java/org/apache/poi/hssf/record/aggregates/MergedCellsTable.java
new file mode 100644 (file)
index 0000000..b7384a0
--- /dev/null
@@ -0,0 +1,122 @@
+/* ====================================================================
+   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.record.aggregates;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.poi.hssf.model.RecordStream;
+import org.apache.poi.hssf.record.MergeCellsRecord;
+import org.apache.poi.hssf.util.CellRangeAddress;
+import org.apache.poi.hssf.util.CellRangeAddressList;
+
+/**
+ * 
+ * @author Josh Micich
+ */
+public final class MergedCellsTable extends RecordAggregate {
+       private static int MAX_MERGED_REGIONS = 1027; // enforced by the 8224 byte limit
+
+       private final List _mergedRegions;
+
+       /**
+        * Creates an empty aggregate
+        */
+       public MergedCellsTable() {
+               _mergedRegions = new ArrayList();
+       }
+
+       public MergedCellsTable(RecordStream rs) {
+               List temp = new ArrayList();
+               while (rs.peekNextClass() == MergeCellsRecord.class) {
+                       MergeCellsRecord mcr = (MergeCellsRecord) rs.getNext();
+                       int nRegions = mcr.getNumAreas();
+                       for (int i = 0; i < nRegions; i++) {
+                               temp.add(mcr.getAreaAt(i));
+                       }
+               }
+               _mergedRegions = temp;
+       }
+
+       public int getRecordSize() {
+               // a bit cheaper than the default impl
+               int nRegions = _mergedRegions.size();
+               if (nRegions < 1) {
+                       // no need to write a single empty MergeCellsRecord
+                       return 0;
+               }
+               int nMergedCellsRecords = nRegions / MAX_MERGED_REGIONS;
+               int nLeftoverMergedRegions = nRegions % MAX_MERGED_REGIONS;
+
+               int result = nMergedCellsRecords
+                               * (4 + CellRangeAddressList.getEncodedSize(MAX_MERGED_REGIONS)) + 4
+                               + CellRangeAddressList.getEncodedSize(nLeftoverMergedRegions);
+               return result;
+       }
+
+       public void visitContainedRecords(RecordVisitor rv) {
+               int nRegions = _mergedRegions.size();
+               if (nRegions < 1) {
+                       // no need to write a single empty MergeCellsRecord
+                       return;
+               }
+
+               int nFullMergedCellsRecords = nRegions / MAX_MERGED_REGIONS;
+               int nLeftoverMergedRegions = nRegions % MAX_MERGED_REGIONS;
+               CellRangeAddress[] cras = new CellRangeAddress[nRegions];
+               _mergedRegions.toArray(cras);
+
+               for (int i = 0; i < nFullMergedCellsRecords; i++) {
+                       int startIx = i * MAX_MERGED_REGIONS;
+                       rv.visitRecord(new MergeCellsRecord(cras, startIx, MAX_MERGED_REGIONS));
+               }
+               if (nLeftoverMergedRegions > 0) {
+                       int startIx = nFullMergedCellsRecords * MAX_MERGED_REGIONS;
+                       rv.visitRecord(new MergeCellsRecord(cras, startIx, nLeftoverMergedRegions));
+               }
+       }
+
+       public void add(MergeCellsRecord mcr) {
+               _mergedRegions.add(mcr);
+       }
+
+       public CellRangeAddress get(int index) {
+               checkIndex(index);
+               return (CellRangeAddress) _mergedRegions.get(index);
+       }
+
+       public void remove(int index) {
+               checkIndex(index);
+               _mergedRegions.remove(index);
+       }
+
+       private void checkIndex(int index) {
+               if (index < 0 || index >= _mergedRegions.size()) {
+                       throw new IllegalArgumentException("Specified CF index " + index
+                                       + " is outside the allowable range (0.." + (_mergedRegions.size() - 1) + ")");
+               }
+       }
+
+       public void addArea(int rowFrom, int colFrom, int rowTo, int colTo) {
+               _mergedRegions.add(new CellRangeAddress(rowFrom, rowTo, colFrom, colTo));
+       }
+
+       public int getNumberOfMergedRegions() {
+               return _mergedRegions.size();
+       }
+}
index 3a86871e8b2f220dc7531defea31fcde053fb3e2..ce0bf894527205cb4683b40763de5851a05ff7d1 100644 (file)
@@ -18,6 +18,7 @@
 package org.apache.poi.hssf.record.aggregates;\r
 \r
 import org.apache.poi.hssf.record.Record;\r
+import org.apache.poi.hssf.record.RecordBase;\r
 import org.apache.poi.hssf.record.RecordInputStream;\r
 \r
 /**\r
@@ -27,15 +28,66 @@ import org.apache.poi.hssf.record.RecordInputStream;
  * \r
  * @author Josh Micich\r
  */\r
-public abstract class RecordAggregate extends Record {\r
-       // TODO - convert existing aggregate classes to proper subclasses of this one\r
+public abstract class RecordAggregate extends RecordBase {\r
+       // TODO - delete these methods when all subclasses have been converted\r
        protected final void validateSid(short id) {\r
-               // TODO - break class hierarchy and make separate from Record\r
                throw new RuntimeException("Should not be called");\r
        }\r
        protected final void fillFields(RecordInputStream in) {\r
                throw new RuntimeException("Should not be called");\r
        }\r
-       // force subclassses to provide better implementation than default\r
-       public abstract int getRecordSize();\r
+    public final short getSid() {\r
+               throw new RuntimeException("Should not be called");\r
+    }\r
+\r
+       public abstract void visitContainedRecords(RecordVisitor rv);\r
+       \r
+       public final int serialize(int offset, byte[] data) {\r
+               SerializingRecordVisitor srv = new SerializingRecordVisitor(data, offset);\r
+               visitContainedRecords(srv);\r
+               return srv.countBytesWritten();\r
+       }\r
+       public int getRecordSize() {\r
+               RecordSizingVisitor rsv = new RecordSizingVisitor();\r
+               visitContainedRecords(rsv);\r
+               return rsv.getTotalSize();\r
+       }\r
+       \r
+       public interface RecordVisitor {\r
+               void visitRecord(Record r);\r
+       }\r
+       \r
+       private static final class SerializingRecordVisitor implements RecordVisitor {\r
+\r
+               private final byte[] _data;\r
+               private final int _startOffset;\r
+               private int _countBytesWritten;\r
+\r
+               public SerializingRecordVisitor(byte[] data, int startOffset) {\r
+                       _data = data;\r
+                       _startOffset = startOffset;\r
+                       _countBytesWritten = 0;\r
+               }\r
+               public int countBytesWritten() {\r
+                       return _countBytesWritten;\r
+               }\r
+               public void visitRecord(Record r) {\r
+                       int currentOffset = _startOffset + _countBytesWritten;\r
+                       _countBytesWritten += r.serialize(currentOffset, _data);\r
+               }\r
+       }\r
+       private static final class RecordSizingVisitor implements RecordVisitor {\r
+\r
+               private int _totalSize;\r
+               \r
+               public RecordSizingVisitor() {\r
+                       _totalSize = 0;\r
+               }\r
+               public int getTotalSize() {\r
+                       return _totalSize;\r
+               }\r
+               public void visitRecord(Record r) {\r
+                       _totalSize += r.getRecordSize();\r
+               }\r
+       }\r
 }\r
index 8deaa919f11e5ca2e1376571958040ab8b687607..3c9404ac395b25c72bf4dea1d035b39f0be31d4d 100644 (file)
@@ -25,7 +25,6 @@ import org.apache.poi.util.BitField;
 import org.apache.poi.util.BitFieldFactory;
 import org.apache.poi.util.LittleEndian;
 
-
 /**
  * Title:        Area 3D Ptg - 3D reference (Sheet + Area)<P>
  * Description:  Defined a area in Extern Sheet. <P>
@@ -38,14 +37,16 @@ import org.apache.poi.util.LittleEndian;
 public final class Area3DPtg extends OperandPtg implements AreaI {
        public final static byte sid = 0x3b;
        private final static int SIZE = 11; // 10 + 1 for Ptg
+       
+       private static final BitField rowRelative = BitFieldFactory.getInstance(0x8000);
+       private static final BitField colRelative = BitFieldFactory.getInstance(0x4000);
+       
        private short field_1_index_extern_sheet;
        private int field_2_first_row;
        private int field_3_last_row;
        private int field_4_first_column;
        private int field_5_last_column;
 
-       private BitField rowRelative = BitFieldFactory.getInstance( 0x8000 );
-       private BitField colRelative = BitFieldFactory.getInstance( 0x4000 );
 
        /** Creates new AreaPtg */
        public Area3DPtg()
index 52a5518e40e025702b12d58f103742d0146834ab..6b48036fe7e3488b2057cc2c9575894f33a2807d 100644 (file)
@@ -36,6 +36,10 @@ import org.apache.poi.util.LittleEndian;
  */
 public final class Ref3DPtg extends OperandPtg {
     public final static byte sid  = 0x3a;
+
+    private static final BitField rowRelative = BitFieldFactory.getInstance(0x8000);
+    private static final BitField colRelative = BitFieldFactory.getInstance(0x4000);
+
     private final static int  SIZE = 7; // 6 + 1 for Ptg
     private short             field_1_index_extern_sheet;
     /** The row index - zero based unsigned 16 bit value */
@@ -46,8 +50,6 @@ public final class Ref3DPtg extends OperandPtg {
      * - bit 15 - isColumnRelative 
      */
     private int             field_3_column;
-    private BitField         rowRelative = BitFieldFactory.getInstance(0x8000);
-    private BitField         colRelative = BitFieldFactory.getInstance(0x4000);
 
     /** Creates new AreaPtg */
     public Ref3DPtg() {}
index f110d71f9341997ae412fc962cedb551fe40f399..9abcebcd74edc686b5dabdf854c39a883d41cf8b 100644 (file)
@@ -48,6 +48,7 @@ import org.apache.poi.hssf.record.NoteRecord;
 import org.apache.poi.hssf.record.NumberRecord;
 import org.apache.poi.hssf.record.ObjRecord;
 import org.apache.poi.hssf.record.Record;
+import org.apache.poi.hssf.record.RecordBase;
 import org.apache.poi.hssf.record.StringRecord;
 import org.apache.poi.hssf.record.SubRecord;
 import org.apache.poi.hssf.record.TextObjectRecord;
@@ -1154,7 +1155,7 @@ public class HSSFCell implements Cell
         HSSFComment comment = null;
         HashMap txshapes = new HashMap(); //map shapeId and TextObjectRecord
         for (Iterator it = sheet.getRecords().iterator(); it.hasNext(); ) {
-           Record rec = ( Record ) it.next();
+           RecordBase rec = (RecordBase) it.next();
            if (rec instanceof NoteRecord){
                NoteRecord note = (NoteRecord)rec;
                if (note.getRow() == row && note.getColumn() == column){
@@ -1196,7 +1197,7 @@ public class HSSFCell implements Cell
      */
     public HSSFHyperlink getHyperlink(){
         for (Iterator it = sheet.getRecords().iterator(); it.hasNext(); ) {
-            Record rec = ( Record ) it.next();
+            RecordBase rec = (RecordBase) it.next();
             if (rec instanceof HyperlinkRecord){
                 HyperlinkRecord link = (HyperlinkRecord)rec;
                 if(link.getFirstColumn() == record.getColumn() && link.getFirstRow() == record.getRow()){
index dcf68b9cf3eb8fcf5c03179e0e2474ccefa69abd..7dd85e364a91487fc7a1b56029fb91c1c788ae3a 100644 (file)
@@ -1464,43 +1464,19 @@ public class HSSFSheet implements org.apache.poi.ss.usermodel.Sheet
     }
 
     /**
-     * Retrieves all the horizontal page breaks
-     * @return all the horizontal page breaks, or null if there are no row page breaks
+     * @return row indexes of all the horizontal page breaks, never <code>null</code>
      */
     public int[] getRowBreaks(){
         //we can probably cache this information, but this should be a sparsely used function
-        int count = sheet.getNumRowBreaks();
-        if (count > 0) {
-          int[] returnValue = new int[count];
-          Iterator iterator = sheet.getRowBreaks();
-          int i = 0;
-          while (iterator.hasNext()) {
-            PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
-            returnValue[i++] = breakItem.main;
-          }
-          return returnValue;
-        }
-        return null;
+        return sheet.getRowBreaks();
     }
 
     /**
-     * Retrieves all the vertical page breaks
-     * @return all the vertical page breaks, or null if there are no column page breaks
+     * @return column indexes of all the vertical page breaks, never <code>null</code>
      */
-    public short[] getColumnBreaks(){
+    public int[] getColumnBreaks(){
         //we can probably cache this information, but this should be a sparsely used function
-        int count = sheet.getNumColumnBreaks();
-        if (count > 0) {
-          short[] returnValue = new short[count];
-          Iterator iterator = sheet.getColumnBreaks();
-          int i = 0;
-          while (iterator.hasNext()) {
-            PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
-            returnValue[i++] = breakItem.main;
-          }
-          return returnValue;
-        }
-        return null;
+        return sheet.getColumnBreaks();
     }
 
 
index 8773c34eecdd5e9182935dd4c471bb5d0b5ca509..72b5882488ed155cc9c3880656a8cfcbade46120 100644 (file)
@@ -99,7 +99,14 @@ public class CellRangeAddressList {
        }
 
        public int getSize() {
-               return 2 + CellRangeAddress.getEncodedSize(_list.size());
+               return getEncodedSize(_list.size());
+       }
+       /**
+        * @return the total size of for the specified number of ranges,
+        *  including the initial 2 byte range count
+        */
+       public static int getEncodedSize(int numberOfRanges) {
+               return 2 + CellRangeAddress.getEncodedSize(numberOfRanges);
        }
 
        public int serialize(int offset, byte[] data) {
index 055f8452d840776d9cdb540cbd48a228b228b73f..b04b5d453c8be26a0b49cc09f5bc46b7255afbb7 100644 (file)
@@ -631,7 +631,7 @@ public interface Sheet extends Iterable<Row> {
      * Retrieves all the vertical page breaks
      * @return all the vertical page breaks, or null if there are no column page breaks
      */
-    short[] getColumnBreaks();
+    int[] getColumnBreaks();
 
     /**
      * Sets a page break at the indicated column
index a76711a7f32c90545b5fc9ac38d911a96bb3dbdc..f619be8d2fa29e35fde337a63b2c4a0442cb8eb4 100644 (file)
@@ -312,15 +312,15 @@ public class XSSFSheet implements Sheet {
        return null;
     }
 
-    public short[] getColumnBreaks() {
+    public int[] getColumnBreaks() {
         CTBreak[] brkArray = getSheetTypeColumnBreaks().getBrkArray();
         if (brkArray.length == 0) {
             return null;
         }
-        short[] breaks = new short[brkArray.length];
+        int[] breaks = new int[brkArray.length];
         for (int i = 0 ; i < brkArray.length ; i++) {
             CTBreak brk = brkArray[i];
-            breaks[i] = (short) brk.getId();
+            breaks[i] = (int)brk.getId();
         }
         return breaks;
     }
index e3f5bb23e92a2a8d825ffc6f2c2fdf372e33a66f..ab7cc61ef1cee15383ba56455c4b42b513296d7b 100644 (file)
@@ -1,4 +1,3 @@
-
 /* ====================================================================
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
@@ -15,7 +14,6 @@
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-        
 
 package org.apache.poi.hssf.usermodel;
 
@@ -56,7 +54,7 @@ import org.apache.poi.hssf.record.PlotAreaRecord;
 import org.apache.poi.hssf.record.PlotGrowthRecord;
 import org.apache.poi.hssf.record.PrintSetupRecord;
 import org.apache.poi.hssf.record.ProtectRecord;
-import org.apache.poi.hssf.record.Record;
+import org.apache.poi.hssf.record.RecordBase;
 import org.apache.poi.hssf.record.SCLRecord;
 import org.apache.poi.hssf.record.SeriesIndexRecord;
 import org.apache.poi.hssf.record.SeriesRecord;
@@ -76,8 +74,7 @@ import org.apache.poi.hssf.record.formula.Area3DPtg;
  *
  * @author Glen Stampoultzis (glens at apache.org)
  */
-public class HSSFChart
-{
+public final class HSSFChart {
        private ChartRecord chartRecord;
        
        private LegendRecord legendRecord;
@@ -90,897 +87,897 @@ public class HSSFChart
                this.chartRecord = chartRecord;
        }
 
-    /**
-     * Creates a bar chart.  API needs some work. :)
-     * <p>
-     * NOTE:  Does not yet work...  checking it in just so others
-     * can take a look.
-     */
-    public void createBarChart( HSSFWorkbook workbook, HSSFSheet sheet )
-    {
-
-        List records = new ArrayList();
-        records.add( createMSDrawingObjectRecord() );
-        records.add( createOBJRecord() );
-        records.add( createBOFRecord() );
-        records.add( createHeaderRecord() );
-        records.add( createFooterRecord() );
-        records.add( createHCenterRecord() );
-        records.add( createVCenterRecord() );
-        records.add( createPrintSetupRecord() );
-        // unknown 33
-        records.add( createFontBasisRecord1() );
-        records.add( createFontBasisRecord2() );
-        records.add( createProtectRecord() );
-        records.add( createUnitsRecord() );
-        records.add( createChartRecord( 0, 0, 30434904, 19031616 ) );
-        records.add( createBeginRecord() );
-        records.add( createSCLRecord( (short) 1, (short) 1 ) );
-        records.add( createPlotGrowthRecord( 65536, 65536 ) );
-        records.add( createFrameRecord1() );
-        records.add( createBeginRecord() );
-        records.add( createLineFormatRecord(true) );
-        records.add( createAreaFormatRecord1() );
-        records.add( createEndRecord() );
-        records.add( createSeriesRecord() );
-        records.add( createBeginRecord() );
-        records.add( createTitleLinkedDataRecord() );
-        records.add( createValuesLinkedDataRecord() );
-        records.add( createCategoriesLinkedDataRecord() );
-        records.add( createDataFormatRecord() );
-        //        records.add(createBeginRecord());
-        // unknown
-        //        records.add(createEndRecord());
-        records.add( createSeriesToChartGroupRecord() );
-        records.add( createEndRecord() );
-        records.add( createSheetPropsRecord() );
-        records.add( createDefaultTextRecord( DefaultDataLabelTextPropertiesRecord.CATEGORY_DATA_TYPE_ALL_TEXT_CHARACTERISTIC ) );
-        records.add( createAllTextRecord() );
-        records.add( createBeginRecord() );
-        // unknown
-        records.add( createFontIndexRecord( 5 ) );
-        records.add( createDirectLinkRecord() );
-        records.add( createEndRecord() );
-        records.add( createDefaultTextRecord( (short) 3 ) ); // eek, undocumented text type
-        records.add( createUnknownTextRecord() );
-        records.add( createBeginRecord() );
-        records.add( createFontIndexRecord( (short) 6 ) );
-        records.add( createDirectLinkRecord() );
-        records.add( createEndRecord() );
-
-        records.add( createAxisUsedRecord( (short) 1 ) );
-        createAxisRecords( records );
-
-        records.add( createEndRecord() );
-        records.add( createDimensionsRecord() );
-        records.add( createSeriesIndexRecord(2) );
-        records.add( createSeriesIndexRecord(1) );
-        records.add( createSeriesIndexRecord(3) );
-        records.add( createEOFRecord() );
-
-
-
-        sheet.insertChartRecords( records );
-        workbook.insertChartRecord();
-    }
-    
-    /**
-     * Returns all the charts for the given sheet.
-     * 
-     * NOTE: You won't be able to do very much with
-     *  these charts yet, as this is very limited support
-     */
-    public static HSSFChart[] getSheetCharts(HSSFSheet sheet) {
-       List charts = new ArrayList();
-       HSSFChart lastChart = null;
-       
-       // Find records of interest
-       List records = sheet.getSheet().getRecords();
-       for(Iterator it = records.iterator(); it.hasNext();) {
-               Record r = (Record)it.next();
-               
-               if(r instanceof ChartRecord) {
-                       lastChart = new HSSFChart((ChartRecord)r);
-                       charts.add(lastChart);
-               }
-               if(r instanceof LegendRecord) {
-                       lastChart.legendRecord = (LegendRecord)r;
-               }
-               if(r instanceof SeriesRecord) {
-                       HSSFSeries series = lastChart.new HSSFSeries( (SeriesRecord)r );
-                       lastChart.series.add(series);
-               }
-               if(r instanceof ChartTitleFormatRecord) {
-                       lastChart.chartTitleFormat =
-                               (ChartTitleFormatRecord)r;
-               }
-               if(r instanceof SeriesTextRecord) {
-                       // Applies to a series, unless we've seen
-                       //  a legend already
-                       SeriesTextRecord str = (SeriesTextRecord)r;
-                       if(lastChart.legendRecord == null &&
-                                       lastChart.series.size() > 0) {
-                               HSSFSeries series = (HSSFSeries)
-                                       lastChart.series.get(lastChart.series.size()-1);
-                               series.seriesTitleText = str;
-                       } else {
-                               lastChart.chartTitleText = str;
-                       }
-               }
-       }
-       
-       return (HSSFChart[])
-               charts.toArray( new HSSFChart[charts.size()] );
-    }
-
-    /** Get the X offset of the chart */
-    public int getChartX() { return chartRecord.getX(); }
-    /** Get the Y offset of the chart */
-    public int getChartY() { return chartRecord.getY(); }
-    /** Get the width of the chart. {@link ChartRecord} */
-    public int getChartWidth() { return chartRecord.getWidth(); }
-    /** Get the height of the chart. {@link ChartRecord} */
-    public int getChartHeight() { return chartRecord.getHeight(); }
-
-    /** Sets the X offset of the chart */
-    public void setChartX(int x) { chartRecord.setX(x); }
-    /** Sets the Y offset of the chart */
-    public void setChartY(int y) { chartRecord.setY(y); }
-    /** Sets the width of the chart. {@link ChartRecord} */
-    public void setChartWidth(int width) { chartRecord.setWidth(width); }
-    /** Sets the height of the chart. {@link ChartRecord} */
-    public void setChartHeight(int height) { chartRecord.setHeight(height); }
-    
-    /**
-     * Returns the series of the chart
-     */
-    public HSSFSeries[] getSeries() {
-       return (HSSFSeries[])
-               series.toArray(new HSSFSeries[series.size()]);
-    }
-    
-    /**
-     * Returns the chart's title, if there is one,
-     *  or null if not
-     */
-    public String getChartTitle() {
-       if(chartTitleText != null) {
-               return chartTitleText.getText();
-       }
-       return null;
-    }
-    
-    /**
-     * Changes the chart's title, but only if there 
-     *  was one already.
-     * TODO - add in the records if not
-     */
-    public void setChartTitle(String title) {
-       if(chartTitleText != null) {
-               chartTitleText.setText(title);
-       } else {
-               throw new IllegalStateException("No chart title found to change");
-       }
-    }
-    
-
-    private EOFRecord createEOFRecord()
-    {
-        return new EOFRecord();
-    }
-
-    private SeriesIndexRecord createSeriesIndexRecord( int index )
-    {
-        SeriesIndexRecord r = new SeriesIndexRecord();
-        r.setIndex((short)index);
-        return r;
-    }
-
-    private DimensionsRecord createDimensionsRecord()
-    {
-        DimensionsRecord r = new DimensionsRecord();
-        r.setFirstRow(0);
-        r.setLastRow(31);
-        r.setFirstCol((short)0);
-        r.setLastCol((short)1);
-        return r;
-    }
-
-    private HCenterRecord createHCenterRecord()
-    {
-        HCenterRecord r = new HCenterRecord();
-        r.setHCenter(false);
-        return r;
-    }
-
-    private VCenterRecord createVCenterRecord()
-    {
-        VCenterRecord r = new VCenterRecord();
-        r.setVCenter(false);
-        return r;
-    }
-
-    private PrintSetupRecord createPrintSetupRecord()
-    {
-        PrintSetupRecord r = new PrintSetupRecord();
-        r.setPaperSize((short)0);
-        r.setScale((short)18);
-        r.setPageStart((short)1);
-        r.setFitWidth((short)1);
-        r.setFitHeight((short)1);
-        r.setLeftToRight(false);
-        r.setLandscape(false);
-        r.setValidSettings(true);
-        r.setNoColor(false);
-        r.setDraft(false);
-        r.setNotes(false);
-        r.setNoOrientation(false);
-        r.setUsePage(false);
-        r.setHResolution((short)0);
-        r.setVResolution((short)0);
-        r.setHeaderMargin(0.5);
-        r.setFooterMargin(0.5);
-        r.setCopies((short)15); // what the ??
-        return r;
-    }
-
-    private FontBasisRecord createFontBasisRecord1()
-    {
-        FontBasisRecord r = new FontBasisRecord();
-        r.setXBasis((short)9120);
-        r.setYBasis((short)5640);
-        r.setHeightBasis((short)200);
-        r.setScale((short)0);
-        r.setIndexToFontTable((short)5);
-        return r;
-    }
-
-    private FontBasisRecord createFontBasisRecord2()
-    {
-        FontBasisRecord r = createFontBasisRecord1();
-        r.setIndexToFontTable((short)6);
-        return r;
-    }
-
-    private ProtectRecord createProtectRecord()
-    {
-        ProtectRecord r = new ProtectRecord();
-        r.setProtect(false);
-        return r;
-    }
-
-    private FooterRecord createFooterRecord()
-    {
-        FooterRecord r = new FooterRecord();
-        r.setFooter(null);
-        return r;
-    }
-
-    private HeaderRecord createHeaderRecord()
-    {
-        HeaderRecord r = new HeaderRecord();
-        r.setHeader(null);
-        return r;
-    }
-
-    private BOFRecord createBOFRecord()
-    {
-        BOFRecord r = new BOFRecord();
-        r.setVersion((short)600);
-        r.setType((short)20);
-        r.setBuild((short)0x1CFE);
-        r.setBuildYear((short)1997);
-        r.setHistoryBitMask(0x40C9);
-        r.setRequiredVersion(106);
-        return r;
-    }
-
-    private UnknownRecord createOBJRecord()
-    {
-        byte[] data = {
-            (byte) 0x15, (byte) 0x00, (byte) 0x12, (byte) 0x00, (byte) 0x05, (byte) 0x00, (byte) 0x02, (byte) 0x00, (byte) 0x11, (byte) 0x60, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0xB8, (byte) 0x03,
-            (byte) 0x87, (byte) 0x03, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00,
-        };
-
-        return new UnknownRecord( (short) 0x005D, data );
-    }
-
-    private UnknownRecord createMSDrawingObjectRecord()
-    {
-        // Since we haven't created this object yet we'll just put in the raw
-        // form for the moment.
-
-        byte[] data = {
-            (byte)0x0F, (byte)0x00, (byte)0x02, (byte)0xF0, (byte)0xC0, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x10, (byte)0x00, (byte)0x08, (byte)0xF0, (byte)0x08, (byte)0x00, (byte)0x00, (byte)0x00,
-            (byte)0x02, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x02, (byte)0x04, (byte)0x00, (byte)0x00, (byte)0x0F, (byte)0x00, (byte)0x03, (byte)0xF0, (byte)0xA8, (byte)0x00, (byte)0x00, (byte)0x00,
-            (byte)0x0F, (byte)0x00, (byte)0x04, (byte)0xF0, (byte)0x28, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x01, (byte)0x00, (byte)0x09, (byte)0xF0, (byte)0x10, (byte)0x00, (byte)0x00, (byte)0x00,
-            (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
-            (byte)0x02, (byte)0x00, (byte)0x0A, (byte)0xF0, (byte)0x08, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x04, (byte)0x00, (byte)0x00, (byte)0x05, (byte)0x00, (byte)0x00, (byte)0x00,
-            (byte)0x0F, (byte)0x00, (byte)0x04, (byte)0xF0, (byte)0x70, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x92, (byte)0x0C, (byte)0x0A, (byte)0xF0, (byte)0x08, (byte)0x00, (byte)0x00, (byte)0x00,
-            (byte)0x02, (byte)0x04, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x0A, (byte)0x00, (byte)0x00, (byte)0x93, (byte)0x00, (byte)0x0B, (byte)0xF0, (byte)0x36, (byte)0x00, (byte)0x00, (byte)0x00,
-            (byte)0x7F, (byte)0x00, (byte)0x04, (byte)0x01, (byte)0x04, (byte)0x01, (byte)0xBF, (byte)0x00, (byte)0x08, (byte)0x00, (byte)0x08, (byte)0x00, (byte)0x81, (byte)0x01, (byte)0x4E, (byte)0x00,
-            (byte)0x00, (byte)0x08, (byte)0x83, (byte)0x01, (byte)0x4D, (byte)0x00, (byte)0x00, (byte)0x08, (byte)0xBF, (byte)0x01, (byte)0x10, (byte)0x00, (byte)0x11, (byte)0x00, (byte)0xC0, (byte)0x01,
-            (byte)0x4D, (byte)0x00, (byte)0x00, (byte)0x08, (byte)0xFF, (byte)0x01, (byte)0x08, (byte)0x00, (byte)0x08, (byte)0x00, (byte)0x3F, (byte)0x02, (byte)0x00, (byte)0x00, (byte)0x02, (byte)0x00,
-            (byte)0xBF, (byte)0x03, (byte)0x00, (byte)0x00, (byte)0x08, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x10, (byte)0xF0, (byte)0x12, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
-            (byte)0x04, (byte)0x00, (byte)0xC0, (byte)0x02, (byte)0x0A, (byte)0x00, (byte)0xF4, (byte)0x00, (byte)0x0E, (byte)0x00, (byte)0x66, (byte)0x01, (byte)0x20, (byte)0x00, (byte)0xE9, (byte)0x00,
-            (byte)0x00, (byte)0x00, (byte)0x11, (byte)0xF0, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00
-        };
-
-        return new UnknownRecord((short)0x00EC, data);
-    }
-
-    private void createAxisRecords( List records )
-    {
-        records.add( createAxisParentRecord() );
-        records.add( createBeginRecord() );
-        records.add( createAxisRecord( AxisRecord.AXIS_TYPE_CATEGORY_OR_X_AXIS ) );
-        records.add( createBeginRecord() );
-        records.add( createCategorySeriesAxisRecord() );
-        records.add( createAxisOptionsRecord() );
-        records.add( createTickRecord1() );
-        records.add( createEndRecord() );
-        records.add( createAxisRecord( AxisRecord.AXIS_TYPE_VALUE_AXIS ) );
-        records.add( createBeginRecord() );
-        records.add( createValueRangeRecord() );
-        records.add( createTickRecord2() );
-        records.add( createAxisLineFormatRecord( AxisLineFormatRecord.AXIS_TYPE_MAJOR_GRID_LINE ) );
-        records.add( createLineFormatRecord(false) );
-        records.add( createEndRecord() );
-        records.add( createPlotAreaRecord() );
-        records.add( createFrameRecord2() );
-        records.add( createBeginRecord() );
-        records.add( createLineFormatRecord2() );
-        records.add( createAreaFormatRecord2() );
-        records.add( createEndRecord() );
-        records.add( createChartFormatRecord() );
-        records.add( createBeginRecord() );
-        records.add( createBarRecord() );
-        // unknown 1022
-        records.add( createLegendRecord() );
-        records.add( createBeginRecord() );
-        // unknown 104f
-        records.add( createTextRecord() );
-        records.add( createBeginRecord() );
-        // unknown 104f
-        records.add( createLinkedDataRecord() );
-        records.add( createEndRecord() );
-        records.add( createEndRecord() );
-        records.add( createEndRecord() );
-        records.add( createEndRecord() );
-    }
-
-    private LinkedDataRecord createLinkedDataRecord()
-    {
-        LinkedDataRecord r = new LinkedDataRecord();
-        r.setLinkType(LinkedDataRecord.LINK_TYPE_TITLE_OR_TEXT);
-        r.setReferenceType(LinkedDataRecord.REFERENCE_TYPE_DIRECT);
-        r.setCustomNumberFormat(false);
-        r.setIndexNumberFmtRecord((short)0);
-        r.setFormulaOfLink( new LinkedDataFormulaField() );
-        return r;
-    }
-
-    private TextRecord createTextRecord()
-    {
-        TextRecord r = new TextRecord();
-        r.setHorizontalAlignment(TextRecord.HORIZONTAL_ALIGNMENT_CENTER);
-        r.setVerticalAlignment(TextRecord.VERTICAL_ALIGNMENT_CENTER);
-        r.setDisplayMode((short)1);
-        r.setRgbColor(0x00000000);
-        r.setX(-37);
-        r.setY(-60);
-        r.setWidth(0);
-        r.setHeight(0);
-        r.setAutoColor(true);
-        r.setShowKey(false);
-        r.setShowValue(false);
-        r.setVertical(false);
-        r.setAutoGeneratedText(true);
-        r.setGenerated(true);
-        r.setAutoLabelDeleted(false);
-        r.setAutoBackground(true);
-        r.setRotation((short)0);
-        r.setShowCategoryLabelAsPercentage(false);
-        r.setShowValueAsPercentage(false);
-        r.setShowBubbleSizes(false);
-        r.setShowLabel(false);
-        r.setIndexOfColorValue((short)77);
-        r.setDataLabelPlacement((short)0);
-        r.setTextRotation((short)0);
-        return r;
-    }
-
-    private LegendRecord createLegendRecord()
-    {
-        LegendRecord r = new LegendRecord();
-        r.setXAxisUpperLeft(3542);
-        r.setYAxisUpperLeft(1566);
-        r.setXSize(437);
-        r.setYSize(213);
-        r.setType(LegendRecord.TYPE_RIGHT);
-        r.setSpacing(LegendRecord.SPACING_MEDIUM);
-        r.setAutoPosition(true);
-        r.setAutoSeries(true);
-        r.setAutoXPositioning(true);
-        r.setAutoYPositioning(true);
-        r.setVertical(true);
-        r.setDataTable(false);
-        return r;
-    }
-
-    private BarRecord createBarRecord()
-    {
-        BarRecord r = new BarRecord();
-        r.setBarSpace((short)0);
-        r.setCategorySpace((short)150);
-        r.setHorizontal(false);
-        r.setStacked(false);
-        r.setDisplayAsPercentage(false);
-        r.setShadow(false);
-        return r;
-    }
-
-    private ChartFormatRecord createChartFormatRecord()
-    {
-        ChartFormatRecord r = new ChartFormatRecord();
-        r.setXPosition(0);
-        r.setYPosition(0);
-        r.setWidth(0);
-        r.setHeight(0);
-        r.setVaryDisplayPattern(false);
-        return r;
-    }
-
-    private PlotAreaRecord createPlotAreaRecord()
-    {
-        PlotAreaRecord r = new PlotAreaRecord(  );
-        return r;
-    }
-
-    private AxisLineFormatRecord createAxisLineFormatRecord( short format )
-    {
-        AxisLineFormatRecord r = new AxisLineFormatRecord();
-        r.setAxisType( format );
-        return r;
-    }
-
-    private ValueRangeRecord createValueRangeRecord()
-    {
-        ValueRangeRecord r = new ValueRangeRecord();
-        r.setMinimumAxisValue( 0.0 );
-        r.setMaximumAxisValue( 0.0 );
-        r.setMajorIncrement( 0 );
-        r.setMinorIncrement( 0 );
-        r.setCategoryAxisCross( 0 );
-        r.setAutomaticMinimum( true );
-        r.setAutomaticMaximum( true );
-        r.setAutomaticMajor( true );
-        r.setAutomaticMinor( true );
-        r.setAutomaticCategoryCrossing( true );
-        r.setLogarithmicScale( false );
-        r.setValuesInReverse( false );
-        r.setCrossCategoryAxisAtMaximum( false );
-        r.setReserved( true );    // what's this do??
-        return r;
-    }
-
-    private TickRecord createTickRecord1()
-    {
-        TickRecord r = new TickRecord();
-        r.setMajorTickType( (byte) 2 );
-        r.setMinorTickType( (byte) 0 );
-        r.setLabelPosition( (byte) 3 );
-        r.setBackground( (byte) 1 );
-        r.setLabelColorRgb( 0 );
-        r.setZero1( (short) 0 );
-        r.setZero2( (short) 0 );
-        r.setZero3( (short) 45 );
-        r.setAutorotate( true );
-        r.setAutoTextBackground( true );
-        r.setRotation( (short) 0 );
-        r.setAutorotate( true );
-        r.setTickColor( (short) 77 );
-        return r;
-    }
-
-    private TickRecord createTickRecord2()
-    {
-        TickRecord r = createTickRecord1();
-        r.setZero3((short)0);
-        return r;
-    }
-
-    private AxisOptionsRecord createAxisOptionsRecord()
-    {
-        AxisOptionsRecord r = new AxisOptionsRecord();
-        r.setMinimumCategory( (short) -28644 );
-        r.setMaximumCategory( (short) -28715 );
-        r.setMajorUnitValue( (short) 2 );
-        r.setMajorUnit( (short) 0 );
-        r.setMinorUnitValue( (short) 1 );
-        r.setMinorUnit( (short) 0 );
-        r.setBaseUnit( (short) 0 );
-        r.setCrossingPoint( (short) -28644 );
-        r.setDefaultMinimum( true );
-        r.setDefaultMaximum( true );
-        r.setDefaultMajor( true );
-        r.setDefaultMinorUnit( true );
-        r.setIsDate( true );
-        r.setDefaultBase( true );
-        r.setDefaultCross( true );
-        r.setDefaultDateSettings( true );
-        return r;
-    }
-
-    private CategorySeriesAxisRecord createCategorySeriesAxisRecord()
-    {
-        CategorySeriesAxisRecord r = new CategorySeriesAxisRecord();
-        r.setCrossingPoint( (short) 1 );
-        r.setLabelFrequency( (short) 1 );
-        r.setTickMarkFrequency( (short) 1 );
-        r.setValueAxisCrossing( true );
-        r.setCrossesFarRight( false );
-        r.setReversed( false );
-        return r;
-    }
-
-    private AxisRecord createAxisRecord( short axisType )
-    {
-        AxisRecord r = new AxisRecord();
-        r.setAxisType( axisType );
-        return r;
-    }
-
-    private AxisParentRecord createAxisParentRecord()
-    {
-        AxisParentRecord r = new AxisParentRecord();
-        r.setAxisType( AxisParentRecord.AXIS_TYPE_MAIN );
-        r.setX( 479 );
-        r.setY( 221 );
-        r.setWidth( 2995 );
-        r.setHeight( 2902 );
-        return r;
-    }
-
-    private AxisUsedRecord createAxisUsedRecord( short numAxis )
-    {
-        AxisUsedRecord r = new AxisUsedRecord();
-        r.setNumAxis( numAxis );
-        return r;
-    }
-
-    private LinkedDataRecord createDirectLinkRecord()
-    {
-        LinkedDataRecord r = new LinkedDataRecord();
-        r.setLinkType( LinkedDataRecord.LINK_TYPE_TITLE_OR_TEXT );
-        r.setReferenceType( LinkedDataRecord.REFERENCE_TYPE_DIRECT );
-        r.setCustomNumberFormat( false );
-        r.setIndexNumberFmtRecord( (short) 0 );
-        r.setFormulaOfLink( new LinkedDataFormulaField() );
-        return r;
-    }
-
-    private FontIndexRecord createFontIndexRecord( int index )
-    {
-        FontIndexRecord r = new FontIndexRecord();
-        r.setFontIndex( (short) index );
-        return r;
-    }
-
-    private TextRecord createAllTextRecord()
-    {
-        TextRecord r = new TextRecord();
-        r.setHorizontalAlignment( TextRecord.HORIZONTAL_ALIGNMENT_CENTER );
-        r.setVerticalAlignment( TextRecord.VERTICAL_ALIGNMENT_CENTER );
-        r.setDisplayMode( TextRecord.DISPLAY_MODE_TRANSPARENT );
-        r.setRgbColor( 0 );
-        r.setX( -37 );
-        r.setY( -60 );
-        r.setWidth( 0 );
-        r.setHeight( 0 );
-        r.setAutoColor( true );
-        r.setShowKey( false );
-        r.setShowValue( true );
-        r.setVertical( false );
-        r.setAutoGeneratedText( true );
-        r.setGenerated( true );
-        r.setAutoLabelDeleted( false );
-        r.setAutoBackground( true );
-        r.setRotation( (short) 0 );
-        r.setShowCategoryLabelAsPercentage( false );
-        r.setShowValueAsPercentage( false );
-        r.setShowBubbleSizes( false );
-        r.setShowLabel( false );
-        r.setIndexOfColorValue( (short) 77 );
-        r.setDataLabelPlacement( (short) 0 );
-        r.setTextRotation( (short) 0 );
-        return r;
-    }
-
-    private TextRecord createUnknownTextRecord()
-    {
-        TextRecord r = new TextRecord();
-        r.setHorizontalAlignment( TextRecord.HORIZONTAL_ALIGNMENT_CENTER );
-        r.setVerticalAlignment( TextRecord.VERTICAL_ALIGNMENT_CENTER );
-        r.setDisplayMode( TextRecord.DISPLAY_MODE_TRANSPARENT );
-        r.setRgbColor( 0 );
-        r.setX( -37 );
-        r.setY( -60 );
-        r.setWidth( 0 );
-        r.setHeight( 0 );
-        r.setAutoColor( true );
-        r.setShowKey( false );
-        r.setShowValue( false );
-        r.setVertical( false );
-        r.setAutoGeneratedText( true );
-        r.setGenerated( true );
-        r.setAutoLabelDeleted( false );
-        r.setAutoBackground( true );
-        r.setRotation( (short) 0 );
-        r.setShowCategoryLabelAsPercentage( false );
-        r.setShowValueAsPercentage( false );
-        r.setShowBubbleSizes( false );
-        r.setShowLabel( false );
-        r.setIndexOfColorValue( (short) 77 );
-        r.setDataLabelPlacement( (short) 11088 );
-        r.setTextRotation( (short) 0 );
-        return r;
-    }
-
-    private DefaultDataLabelTextPropertiesRecord createDefaultTextRecord( short categoryDataType )
-    {
-        DefaultDataLabelTextPropertiesRecord r = new DefaultDataLabelTextPropertiesRecord();
-        r.setCategoryDataType( categoryDataType );
-        return r;
-    }
-
-    private SheetPropertiesRecord createSheetPropsRecord()
-    {
-        SheetPropertiesRecord r = new SheetPropertiesRecord();
-        r.setChartTypeManuallyFormatted( false );
-        r.setPlotVisibleOnly( true );
-        r.setDoNotSizeWithWindow( false );
-        r.setDefaultPlotDimensions( true );
-        r.setAutoPlotArea( false );
-        return r;
-    }
-
-    private SeriesToChartGroupRecord createSeriesToChartGroupRecord()
-    {
-        return new SeriesToChartGroupRecord();
-    }
-
-    private DataFormatRecord createDataFormatRecord()
-    {
-        DataFormatRecord r = new DataFormatRecord();
-        r.setPointNumber( (short) -1 );
-        r.setSeriesIndex( (short) 0 );
-        r.setSeriesNumber( (short) 0 );
-        r.setUseExcel4Colors( false );
-        return r;
-    }
-
-    private LinkedDataRecord createCategoriesLinkedDataRecord()
-    {
-        LinkedDataRecord r = new LinkedDataRecord();
-        r.setLinkType( LinkedDataRecord.LINK_TYPE_CATEGORIES );
-        r.setReferenceType( LinkedDataRecord.REFERENCE_TYPE_WORKSHEET );
-        r.setCustomNumberFormat( false );
-        r.setIndexNumberFmtRecord( (short) 0 );
-        LinkedDataFormulaField formula = new LinkedDataFormulaField();
-        Stack tokens = new Stack();
-        Area3DPtg p = new Area3DPtg();
-        p.setExternSheetIndex( (short) 0 );
-        p.setFirstColumn( (short) 1 );
-        p.setLastColumn( (short) 1 );
-        p.setFirstRow( (short) 0 );
-        p.setLastRow( (short) 31 );
-        tokens.add( p );
-        formula.setFormulaTokens( tokens );
-        r.setFormulaOfLink( formula );
-        return r;
-    }
-
-    private LinkedDataRecord createValuesLinkedDataRecord()
-    {
-        LinkedDataRecord r = new LinkedDataRecord();
-        r.setLinkType( LinkedDataRecord.LINK_TYPE_VALUES );
-        r.setReferenceType( LinkedDataRecord.REFERENCE_TYPE_WORKSHEET );
-        r.setCustomNumberFormat( false );
-        r.setIndexNumberFmtRecord( (short) 0 );
-        LinkedDataFormulaField formula = new LinkedDataFormulaField();
-        Stack tokens = new Stack();
-        Area3DPtg p = new Area3DPtg();
-        p.setExternSheetIndex( (short) 0 );
-        p.setFirstColumn( (short) 0 );
-        p.setLastColumn( (short) 0 );
-        p.setFirstRow( (short) 0 );
-        p.setLastRow( (short) 31 );
-        tokens.add( p );
-        formula.setFormulaTokens( tokens );
-        r.setFormulaOfLink( formula );
-        return r;
-    }
-
-    private LinkedDataRecord createTitleLinkedDataRecord()
-    {
-        LinkedDataRecord r = new LinkedDataRecord();
-        r.setLinkType( LinkedDataRecord.LINK_TYPE_TITLE_OR_TEXT );
-        r.setReferenceType( LinkedDataRecord.REFERENCE_TYPE_DIRECT );
-        r.setCustomNumberFormat( false );
-        r.setIndexNumberFmtRecord( (short) 0 );
-        r.setFormulaOfLink( new LinkedDataFormulaField() );
-        return r;
-    }
-
-    private SeriesRecord createSeriesRecord()
-    {
-        SeriesRecord r = new SeriesRecord();
-        r.setCategoryDataType( SeriesRecord.CATEGORY_DATA_TYPE_NUMERIC );
-        r.setValuesDataType( SeriesRecord.VALUES_DATA_TYPE_NUMERIC );
-        r.setNumCategories( (short) 32 );
-        r.setNumValues( (short) 31 );
-        r.setBubbleSeriesType( SeriesRecord.BUBBLE_SERIES_TYPE_NUMERIC );
-        r.setNumBubbleValues( (short) 0 );
-        return r;
-    }
-
-    private EndRecord createEndRecord()
-    {
-        return new EndRecord();
-    }
-
-    private AreaFormatRecord createAreaFormatRecord1()
-    {
-        AreaFormatRecord r = new AreaFormatRecord();
-        r.setForegroundColor( 16777215 );     // RGB Color
-        r.setBackgroundColor( 0 );            // RGB Color
-        r.setPattern( (short) 1 );             // TODO: Add Pattern constants to record
-        r.setAutomatic( true );
-        r.setInvert( false );
-        r.setForecolorIndex( (short) 78 );
-        r.setBackcolorIndex( (short) 77 );
-        return r;
-    }
-
-    private AreaFormatRecord createAreaFormatRecord2()
-    {
-        AreaFormatRecord r = new AreaFormatRecord();
-        r.setForegroundColor(0x00c0c0c0);
-        r.setBackgroundColor(0x00000000);
-        r.setPattern((short)1);
-        r.setAutomatic(false);
-        r.setInvert(false);
-        r.setForecolorIndex((short)22);
-        r.setBackcolorIndex((short)79);
-        return r;
-    }
-
-    private LineFormatRecord createLineFormatRecord( boolean drawTicks )
-    {
-        LineFormatRecord r = new LineFormatRecord();
-        r.setLineColor( 0 );
-        r.setLinePattern( LineFormatRecord.LINE_PATTERN_SOLID );
-        r.setWeight( (short) -1 );
-        r.setAuto( true );
-        r.setDrawTicks( drawTicks );
-        r.setColourPaletteIndex( (short) 77 );  // what colour is this?
-        return r;
-    }
-
-    private LineFormatRecord createLineFormatRecord2()
-    {
-        LineFormatRecord r = new LineFormatRecord();
-        r.setLineColor( 0x00808080 );
-        r.setLinePattern( (short) 0 );
-        r.setWeight( (short) 0 );
-        r.setAuto( false );
-        r.setDrawTicks( false );
-        r.setUnknown( false );
-        r.setColourPaletteIndex( (short) 23 );
-        return r;
-    }
-
-    private FrameRecord createFrameRecord1()
-    {
-        FrameRecord r = new FrameRecord();
-        r.setBorderType( FrameRecord.BORDER_TYPE_REGULAR );
-        r.setAutoSize( false );
-        r.setAutoPosition( true );
-        return r;
-    }
-
-    private FrameRecord createFrameRecord2()
-    {
-        FrameRecord r = new FrameRecord();
-        r.setBorderType( FrameRecord.BORDER_TYPE_REGULAR );
-        r.setAutoSize( true );
-        r.setAutoPosition( true );
-        return r;
-    }
-
-    private PlotGrowthRecord createPlotGrowthRecord( int horizScale, int vertScale )
-    {
-        PlotGrowthRecord r = new PlotGrowthRecord();
-        r.setHorizontalScale( horizScale );
-        r.setVerticalScale( vertScale );
-        return r;
-    }
-
-    private SCLRecord createSCLRecord( short numerator, short denominator )
-    {
-        SCLRecord r = new SCLRecord();
-        r.setDenominator( denominator );
-        r.setNumerator( numerator );
-        return r;
-    }
-
-    private BeginRecord createBeginRecord()
-    {
-        return new BeginRecord();
-    }
-
-    private ChartRecord createChartRecord( int x, int y, int width, int height )
-    {
-        ChartRecord r = new ChartRecord();
-        r.setX( x );
-        r.setY( y );
-        r.setWidth( width );
-        r.setHeight( height );
-        return r;
-    }
-
-    private UnitsRecord createUnitsRecord()
-    {
-        UnitsRecord r = new UnitsRecord();
-        r.setUnits( (short) 0 );
-        return r;
-    }
-
-    
-    /**
-     * A series in a chart
-     */
-    public class HSSFSeries {
-       private SeriesRecord series;
-       private SeriesTextRecord seriesTitleText;
-       
-       private HSSFSeries(SeriesRecord series) {
-               this.series = series;
-       }
-       
-       public short getNumValues() {
-               return series.getNumValues();
-       }
-       /**
-        * See {@link SeriesRecord}
-        */
-       public short getValueType() {
-               return series.getValuesDataType();
-       }
-       
-        /**
-         * Returns the series' title, if there is one,
-         *  or null if not
-         */
-        public String getSeriesTitle() {
-               if(seriesTitleText != null) {
-                       return seriesTitleText.getText();
-               }
-               return null;
-        }
-        
-        /**
-         * Changes the series' title, but only if there 
-         *  was one already.
-         * TODO - add in the records if not
-         */
-        public void setSeriesTitle(String title) {
-               if(seriesTitleText != null) {
-                       seriesTitleText.setText(title);
-               } else {
-                       throw new IllegalStateException("No series title found to change");
-               }
-        }
-    }
+       /**
+        * Creates a bar chart.  API needs some work. :)
+        * <p>
+        * NOTE:  Does not yet work...  checking it in just so others
+        * can take a look.
+        */
+       public void createBarChart( HSSFWorkbook workbook, HSSFSheet sheet )
+       {
+
+               List records = new ArrayList();
+               records.add( createMSDrawingObjectRecord() );
+               records.add( createOBJRecord() );
+               records.add( createBOFRecord() );
+               records.add( createHeaderRecord() );
+               records.add( createFooterRecord() );
+               records.add( createHCenterRecord() );
+               records.add( createVCenterRecord() );
+               records.add( createPrintSetupRecord() );
+               // unknown 33
+               records.add( createFontBasisRecord1() );
+               records.add( createFontBasisRecord2() );
+               records.add( createProtectRecord() );
+               records.add( createUnitsRecord() );
+               records.add( createChartRecord( 0, 0, 30434904, 19031616 ) );
+               records.add( createBeginRecord() );
+               records.add( createSCLRecord( (short) 1, (short) 1 ) );
+               records.add( createPlotGrowthRecord( 65536, 65536 ) );
+               records.add( createFrameRecord1() );
+               records.add( createBeginRecord() );
+               records.add( createLineFormatRecord(true) );
+               records.add( createAreaFormatRecord1() );
+               records.add( createEndRecord() );
+               records.add( createSeriesRecord() );
+               records.add( createBeginRecord() );
+               records.add( createTitleLinkedDataRecord() );
+               records.add( createValuesLinkedDataRecord() );
+               records.add( createCategoriesLinkedDataRecord() );
+               records.add( createDataFormatRecord() );
+               //              records.add(createBeginRecord());
+               // unknown
+               //              records.add(createEndRecord());
+               records.add( createSeriesToChartGroupRecord() );
+               records.add( createEndRecord() );
+               records.add( createSheetPropsRecord() );
+               records.add( createDefaultTextRecord( DefaultDataLabelTextPropertiesRecord.CATEGORY_DATA_TYPE_ALL_TEXT_CHARACTERISTIC ) );
+               records.add( createAllTextRecord() );
+               records.add( createBeginRecord() );
+               // unknown
+               records.add( createFontIndexRecord( 5 ) );
+               records.add( createDirectLinkRecord() );
+               records.add( createEndRecord() );
+               records.add( createDefaultTextRecord( (short) 3 ) ); // eek, undocumented text type
+               records.add( createUnknownTextRecord() );
+               records.add( createBeginRecord() );
+               records.add( createFontIndexRecord( (short) 6 ) );
+               records.add( createDirectLinkRecord() );
+               records.add( createEndRecord() );
+
+               records.add( createAxisUsedRecord( (short) 1 ) );
+               createAxisRecords( records );
+
+               records.add( createEndRecord() );
+               records.add( createDimensionsRecord() );
+               records.add( createSeriesIndexRecord(2) );
+               records.add( createSeriesIndexRecord(1) );
+               records.add( createSeriesIndexRecord(3) );
+               records.add( createEOFRecord() );
+
+
+
+               sheet.insertChartRecords( records );
+               workbook.insertChartRecord();
+       }
+       
+       /**
+        * Returns all the charts for the given sheet.
+        
+        * NOTE: You won't be able to do very much with
+        *  these charts yet, as this is very limited support
+        */
+       public static HSSFChart[] getSheetCharts(HSSFSheet sheet) {
+               List charts = new ArrayList();
+               HSSFChart lastChart = null;
+               
+               // Find records of interest
+               List records = sheet.getSheet().getRecords();
+               for(Iterator it = records.iterator(); it.hasNext();) {
+                       RecordBase r = (RecordBase)it.next();
+                       
+                       if(r instanceof ChartRecord) {
+                               lastChart = new HSSFChart((ChartRecord)r);
+                               charts.add(lastChart);
+                       }
+                       if(r instanceof LegendRecord) {
+                               lastChart.legendRecord = (LegendRecord)r;
+                       }
+                       if(r instanceof SeriesRecord) {
+                               HSSFSeries series = lastChart.new HSSFSeries( (SeriesRecord)r );
+                               lastChart.series.add(series);
+                       }
+                       if(r instanceof ChartTitleFormatRecord) {
+                               lastChart.chartTitleFormat =
+                                       (ChartTitleFormatRecord)r;
+                       }
+                       if(r instanceof SeriesTextRecord) {
+                               // Applies to a series, unless we've seen
+                               //  a legend already
+                               SeriesTextRecord str = (SeriesTextRecord)r;
+                               if(lastChart.legendRecord == null &&
+                                               lastChart.series.size() > 0) {
+                                       HSSFSeries series = (HSSFSeries)
+                                               lastChart.series.get(lastChart.series.size()-1);
+                                       series.seriesTitleText = str;
+                               } else {
+                                       lastChart.chartTitleText = str;
+                               }
+                       }
+               }
+               
+               return (HSSFChart[])
+                       charts.toArray( new HSSFChart[charts.size()] );
+       }
+
+       /** Get the X offset of the chart */
+       public int getChartX() { return chartRecord.getX(); }
+       /** Get the Y offset of the chart */
+       public int getChartY() { return chartRecord.getY(); }
+       /** Get the width of the chart. {@link ChartRecord} */
+       public int getChartWidth() { return chartRecord.getWidth(); }
+       /** Get the height of the chart. {@link ChartRecord} */
+       public int getChartHeight() { return chartRecord.getHeight(); }
+
+       /** Sets the X offset of the chart */
+       public void setChartX(int x) { chartRecord.setX(x); }
+       /** Sets the Y offset of the chart */
+       public void setChartY(int y) { chartRecord.setY(y); }
+       /** Sets the width of the chart. {@link ChartRecord} */
+       public void setChartWidth(int width) { chartRecord.setWidth(width); }
+       /** Sets the height of the chart. {@link ChartRecord} */
+       public void setChartHeight(int height) { chartRecord.setHeight(height); }
+       
+       /**
+        * Returns the series of the chart
+        */
+       public HSSFSeries[] getSeries() {
+               return (HSSFSeries[])
+                       series.toArray(new HSSFSeries[series.size()]);
+       }
+       
+       /**
+        * Returns the chart's title, if there is one,
+        *  or null if not
+        */
+       public String getChartTitle() {
+               if(chartTitleText != null) {
+                       return chartTitleText.getText();
+               }
+               return null;
+       }
+       
+       /**
+        * Changes the chart's title, but only if there 
+        *  was one already.
+        * TODO - add in the records if not
+        */
+       public void setChartTitle(String title) {
+               if(chartTitleText != null) {
+                       chartTitleText.setText(title);
+               } else {
+                       throw new IllegalStateException("No chart title found to change");
+               }
+       }
+       
+
+       private EOFRecord createEOFRecord()
+       {
+               return new EOFRecord();
+       }
+
+       private SeriesIndexRecord createSeriesIndexRecord( int index )
+       {
+               SeriesIndexRecord r = new SeriesIndexRecord();
+               r.setIndex((short)index);
+               return r;
+       }
+
+       private DimensionsRecord createDimensionsRecord()
+       {
+               DimensionsRecord r = new DimensionsRecord();
+               r.setFirstRow(0);
+               r.setLastRow(31);
+               r.setFirstCol((short)0);
+               r.setLastCol((short)1);
+               return r;
+       }
+
+       private HCenterRecord createHCenterRecord()
+       {
+               HCenterRecord r = new HCenterRecord();
+               r.setHCenter(false);
+               return r;
+       }
+
+       private VCenterRecord createVCenterRecord()
+       {
+               VCenterRecord r = new VCenterRecord();
+               r.setVCenter(false);
+               return r;
+       }
+
+       private PrintSetupRecord createPrintSetupRecord()
+       {
+               PrintSetupRecord r = new PrintSetupRecord();
+               r.setPaperSize((short)0);
+               r.setScale((short)18);
+               r.setPageStart((short)1);
+               r.setFitWidth((short)1);
+               r.setFitHeight((short)1);
+               r.setLeftToRight(false);
+               r.setLandscape(false);
+               r.setValidSettings(true);
+               r.setNoColor(false);
+               r.setDraft(false);
+               r.setNotes(false);
+               r.setNoOrientation(false);
+               r.setUsePage(false);
+               r.setHResolution((short)0);
+               r.setVResolution((short)0);
+               r.setHeaderMargin(0.5);
+               r.setFooterMargin(0.5);
+               r.setCopies((short)15); // what the ??
+               return r;
+       }
+
+       private FontBasisRecord createFontBasisRecord1()
+       {
+               FontBasisRecord r = new FontBasisRecord();
+               r.setXBasis((short)9120);
+               r.setYBasis((short)5640);
+               r.setHeightBasis((short)200);
+               r.setScale((short)0);
+               r.setIndexToFontTable((short)5);
+               return r;
+       }
+
+       private FontBasisRecord createFontBasisRecord2()
+       {
+               FontBasisRecord r = createFontBasisRecord1();
+               r.setIndexToFontTable((short)6);
+               return r;
+       }
+
+       private ProtectRecord createProtectRecord()
+       {
+               ProtectRecord r = new ProtectRecord();
+               r.setProtect(false);
+               return r;
+       }
+
+       private FooterRecord createFooterRecord()
+       {
+               FooterRecord r = new FooterRecord();
+               r.setFooter(null);
+               return r;
+       }
+
+       private HeaderRecord createHeaderRecord()
+       {
+               HeaderRecord r = new HeaderRecord();
+               r.setHeader(null);
+               return r;
+       }
+
+       private BOFRecord createBOFRecord()
+       {
+               BOFRecord r = new BOFRecord();
+               r.setVersion((short)600);
+               r.setType((short)20);
+               r.setBuild((short)0x1CFE);
+               r.setBuildYear((short)1997);
+               r.setHistoryBitMask(0x40C9);
+               r.setRequiredVersion(106);
+               return r;
+       }
+
+       private UnknownRecord createOBJRecord()
+       {
+               byte[] data = {
+                       (byte) 0x15, (byte) 0x00, (byte) 0x12, (byte) 0x00, (byte) 0x05, (byte) 0x00, (byte) 0x02, (byte) 0x00, (byte) 0x11, (byte) 0x60, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0xB8, (byte) 0x03,
+                       (byte) 0x87, (byte) 0x03, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00,
+               };
+
+               return new UnknownRecord( (short) 0x005D, data );
+       }
+
+       private UnknownRecord createMSDrawingObjectRecord()
+       {
+               // Since we haven't created this object yet we'll just put in the raw
+               // form for the moment.
+
+               byte[] data = {
+                       (byte)0x0F, (byte)0x00, (byte)0x02, (byte)0xF0, (byte)0xC0, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x10, (byte)0x00, (byte)0x08, (byte)0xF0, (byte)0x08, (byte)0x00, (byte)0x00, (byte)0x00,
+                       (byte)0x02, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x02, (byte)0x04, (byte)0x00, (byte)0x00, (byte)0x0F, (byte)0x00, (byte)0x03, (byte)0xF0, (byte)0xA8, (byte)0x00, (byte)0x00, (byte)0x00,
+                       (byte)0x0F, (byte)0x00, (byte)0x04, (byte)0xF0, (byte)0x28, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x01, (byte)0x00, (byte)0x09, (byte)0xF0, (byte)0x10, (byte)0x00, (byte)0x00, (byte)0x00,
+                       (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
+                       (byte)0x02, (byte)0x00, (byte)0x0A, (byte)0xF0, (byte)0x08, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x04, (byte)0x00, (byte)0x00, (byte)0x05, (byte)0x00, (byte)0x00, (byte)0x00,
+                       (byte)0x0F, (byte)0x00, (byte)0x04, (byte)0xF0, (byte)0x70, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x92, (byte)0x0C, (byte)0x0A, (byte)0xF0, (byte)0x08, (byte)0x00, (byte)0x00, (byte)0x00,
+                       (byte)0x02, (byte)0x04, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x0A, (byte)0x00, (byte)0x00, (byte)0x93, (byte)0x00, (byte)0x0B, (byte)0xF0, (byte)0x36, (byte)0x00, (byte)0x00, (byte)0x00,
+                       (byte)0x7F, (byte)0x00, (byte)0x04, (byte)0x01, (byte)0x04, (byte)0x01, (byte)0xBF, (byte)0x00, (byte)0x08, (byte)0x00, (byte)0x08, (byte)0x00, (byte)0x81, (byte)0x01, (byte)0x4E, (byte)0x00,
+                       (byte)0x00, (byte)0x08, (byte)0x83, (byte)0x01, (byte)0x4D, (byte)0x00, (byte)0x00, (byte)0x08, (byte)0xBF, (byte)0x01, (byte)0x10, (byte)0x00, (byte)0x11, (byte)0x00, (byte)0xC0, (byte)0x01,
+                       (byte)0x4D, (byte)0x00, (byte)0x00, (byte)0x08, (byte)0xFF, (byte)0x01, (byte)0x08, (byte)0x00, (byte)0x08, (byte)0x00, (byte)0x3F, (byte)0x02, (byte)0x00, (byte)0x00, (byte)0x02, (byte)0x00,
+                       (byte)0xBF, (byte)0x03, (byte)0x00, (byte)0x00, (byte)0x08, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x10, (byte)0xF0, (byte)0x12, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
+                       (byte)0x04, (byte)0x00, (byte)0xC0, (byte)0x02, (byte)0x0A, (byte)0x00, (byte)0xF4, (byte)0x00, (byte)0x0E, (byte)0x00, (byte)0x66, (byte)0x01, (byte)0x20, (byte)0x00, (byte)0xE9, (byte)0x00,
+                       (byte)0x00, (byte)0x00, (byte)0x11, (byte)0xF0, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00
+               };
+
+               return new UnknownRecord((short)0x00EC, data);
+       }
+
+       private void createAxisRecords( List records )
+       {
+               records.add( createAxisParentRecord() );
+               records.add( createBeginRecord() );
+               records.add( createAxisRecord( AxisRecord.AXIS_TYPE_CATEGORY_OR_X_AXIS ) );
+               records.add( createBeginRecord() );
+               records.add( createCategorySeriesAxisRecord() );
+               records.add( createAxisOptionsRecord() );
+               records.add( createTickRecord1() );
+               records.add( createEndRecord() );
+               records.add( createAxisRecord( AxisRecord.AXIS_TYPE_VALUE_AXIS ) );
+               records.add( createBeginRecord() );
+               records.add( createValueRangeRecord() );
+               records.add( createTickRecord2() );
+               records.add( createAxisLineFormatRecord( AxisLineFormatRecord.AXIS_TYPE_MAJOR_GRID_LINE ) );
+               records.add( createLineFormatRecord(false) );
+               records.add( createEndRecord() );
+               records.add( createPlotAreaRecord() );
+               records.add( createFrameRecord2() );
+               records.add( createBeginRecord() );
+               records.add( createLineFormatRecord2() );
+               records.add( createAreaFormatRecord2() );
+               records.add( createEndRecord() );
+               records.add( createChartFormatRecord() );
+               records.add( createBeginRecord() );
+               records.add( createBarRecord() );
+               // unknown 1022
+               records.add( createLegendRecord() );
+               records.add( createBeginRecord() );
+               // unknown 104f
+               records.add( createTextRecord() );
+               records.add( createBeginRecord() );
+               // unknown 104f
+               records.add( createLinkedDataRecord() );
+               records.add( createEndRecord() );
+               records.add( createEndRecord() );
+               records.add( createEndRecord() );
+               records.add( createEndRecord() );
+       }
+
+       private LinkedDataRecord createLinkedDataRecord()
+       {
+               LinkedDataRecord r = new LinkedDataRecord();
+               r.setLinkType(LinkedDataRecord.LINK_TYPE_TITLE_OR_TEXT);
+               r.setReferenceType(LinkedDataRecord.REFERENCE_TYPE_DIRECT);
+               r.setCustomNumberFormat(false);
+               r.setIndexNumberFmtRecord((short)0);
+               r.setFormulaOfLink( new LinkedDataFormulaField() );
+               return r;
+       }
+
+       private TextRecord createTextRecord()
+       {
+               TextRecord r = new TextRecord();
+               r.setHorizontalAlignment(TextRecord.HORIZONTAL_ALIGNMENT_CENTER);
+               r.setVerticalAlignment(TextRecord.VERTICAL_ALIGNMENT_CENTER);
+               r.setDisplayMode((short)1);
+               r.setRgbColor(0x00000000);
+               r.setX(-37);
+               r.setY(-60);
+               r.setWidth(0);
+               r.setHeight(0);
+               r.setAutoColor(true);
+               r.setShowKey(false);
+               r.setShowValue(false);
+               r.setVertical(false);
+               r.setAutoGeneratedText(true);
+               r.setGenerated(true);
+               r.setAutoLabelDeleted(false);
+               r.setAutoBackground(true);
+               r.setRotation((short)0);
+               r.setShowCategoryLabelAsPercentage(false);
+               r.setShowValueAsPercentage(false);
+               r.setShowBubbleSizes(false);
+               r.setShowLabel(false);
+               r.setIndexOfColorValue((short)77);
+               r.setDataLabelPlacement((short)0);
+               r.setTextRotation((short)0);
+               return r;
+       }
+
+       private LegendRecord createLegendRecord()
+       {
+               LegendRecord r = new LegendRecord();
+               r.setXAxisUpperLeft(3542);
+               r.setYAxisUpperLeft(1566);
+               r.setXSize(437);
+               r.setYSize(213);
+               r.setType(LegendRecord.TYPE_RIGHT);
+               r.setSpacing(LegendRecord.SPACING_MEDIUM);
+               r.setAutoPosition(true);
+               r.setAutoSeries(true);
+               r.setAutoXPositioning(true);
+               r.setAutoYPositioning(true);
+               r.setVertical(true);
+               r.setDataTable(false);
+               return r;
+       }
+
+       private BarRecord createBarRecord()
+       {
+               BarRecord r = new BarRecord();
+               r.setBarSpace((short)0);
+               r.setCategorySpace((short)150);
+               r.setHorizontal(false);
+               r.setStacked(false);
+               r.setDisplayAsPercentage(false);
+               r.setShadow(false);
+               return r;
+       }
+
+       private ChartFormatRecord createChartFormatRecord()
+       {
+               ChartFormatRecord r = new ChartFormatRecord();
+               r.setXPosition(0);
+               r.setYPosition(0);
+               r.setWidth(0);
+               r.setHeight(0);
+               r.setVaryDisplayPattern(false);
+               return r;
+       }
+
+       private PlotAreaRecord createPlotAreaRecord()
+       {
+               PlotAreaRecord r = new PlotAreaRecord(  );
+               return r;
+       }
+
+       private AxisLineFormatRecord createAxisLineFormatRecord( short format )
+       {
+               AxisLineFormatRecord r = new AxisLineFormatRecord();
+               r.setAxisType( format );
+               return r;
+       }
+
+       private ValueRangeRecord createValueRangeRecord()
+       {
+               ValueRangeRecord r = new ValueRangeRecord();
+               r.setMinimumAxisValue( 0.0 );
+               r.setMaximumAxisValue( 0.0 );
+               r.setMajorIncrement( 0 );
+               r.setMinorIncrement( 0 );
+               r.setCategoryAxisCross( 0 );
+               r.setAutomaticMinimum( true );
+               r.setAutomaticMaximum( true );
+               r.setAutomaticMajor( true );
+               r.setAutomaticMinor( true );
+               r.setAutomaticCategoryCrossing( true );
+               r.setLogarithmicScale( false );
+               r.setValuesInReverse( false );
+               r.setCrossCategoryAxisAtMaximum( false );
+               r.setReserved( true );  // what's this do??
+               return r;
+       }
+
+       private TickRecord createTickRecord1()
+       {
+               TickRecord r = new TickRecord();
+               r.setMajorTickType( (byte) 2 );
+               r.setMinorTickType( (byte) 0 );
+               r.setLabelPosition( (byte) 3 );
+               r.setBackground( (byte) 1 );
+               r.setLabelColorRgb( 0 );
+               r.setZero1( (short) 0 );
+               r.setZero2( (short) 0 );
+               r.setZero3( (short) 45 );
+               r.setAutorotate( true );
+               r.setAutoTextBackground( true );
+               r.setRotation( (short) 0 );
+               r.setAutorotate( true );
+               r.setTickColor( (short) 77 );
+               return r;
+       }
+
+       private TickRecord createTickRecord2()
+       {
+               TickRecord r = createTickRecord1();
+               r.setZero3((short)0);
+               return r;
+       }
+
+       private AxisOptionsRecord createAxisOptionsRecord()
+       {
+               AxisOptionsRecord r = new AxisOptionsRecord();
+               r.setMinimumCategory( (short) -28644 );
+               r.setMaximumCategory( (short) -28715 );
+               r.setMajorUnitValue( (short) 2 );
+               r.setMajorUnit( (short) 0 );
+               r.setMinorUnitValue( (short) 1 );
+               r.setMinorUnit( (short) 0 );
+               r.setBaseUnit( (short) 0 );
+               r.setCrossingPoint( (short) -28644 );
+               r.setDefaultMinimum( true );
+               r.setDefaultMaximum( true );
+               r.setDefaultMajor( true );
+               r.setDefaultMinorUnit( true );
+               r.setIsDate( true );
+               r.setDefaultBase( true );
+               r.setDefaultCross( true );
+               r.setDefaultDateSettings( true );
+               return r;
+       }
+
+       private CategorySeriesAxisRecord createCategorySeriesAxisRecord()
+       {
+               CategorySeriesAxisRecord r = new CategorySeriesAxisRecord();
+               r.setCrossingPoint( (short) 1 );
+               r.setLabelFrequency( (short) 1 );
+               r.setTickMarkFrequency( (short) 1 );
+               r.setValueAxisCrossing( true );
+               r.setCrossesFarRight( false );
+               r.setReversed( false );
+               return r;
+       }
+
+       private AxisRecord createAxisRecord( short axisType )
+       {
+               AxisRecord r = new AxisRecord();
+               r.setAxisType( axisType );
+               return r;
+       }
+
+       private AxisParentRecord createAxisParentRecord()
+       {
+               AxisParentRecord r = new AxisParentRecord();
+               r.setAxisType( AxisParentRecord.AXIS_TYPE_MAIN );
+               r.setX( 479 );
+               r.setY( 221 );
+               r.setWidth( 2995 );
+               r.setHeight( 2902 );
+               return r;
+       }
+
+       private AxisUsedRecord createAxisUsedRecord( short numAxis )
+       {
+               AxisUsedRecord r = new AxisUsedRecord();
+               r.setNumAxis( numAxis );
+               return r;
+       }
+
+       private LinkedDataRecord createDirectLinkRecord()
+       {
+               LinkedDataRecord r = new LinkedDataRecord();
+               r.setLinkType( LinkedDataRecord.LINK_TYPE_TITLE_OR_TEXT );
+               r.setReferenceType( LinkedDataRecord.REFERENCE_TYPE_DIRECT );
+               r.setCustomNumberFormat( false );
+               r.setIndexNumberFmtRecord( (short) 0 );
+               r.setFormulaOfLink( new LinkedDataFormulaField() );
+               return r;
+       }
+
+       private FontIndexRecord createFontIndexRecord( int index )
+       {
+               FontIndexRecord r = new FontIndexRecord();
+               r.setFontIndex( (short) index );
+               return r;
+       }
+
+       private TextRecord createAllTextRecord()
+       {
+               TextRecord r = new TextRecord();
+               r.setHorizontalAlignment( TextRecord.HORIZONTAL_ALIGNMENT_CENTER );
+               r.setVerticalAlignment( TextRecord.VERTICAL_ALIGNMENT_CENTER );
+               r.setDisplayMode( TextRecord.DISPLAY_MODE_TRANSPARENT );
+               r.setRgbColor( 0 );
+               r.setX( -37 );
+               r.setY( -60 );
+               r.setWidth( 0 );
+               r.setHeight( 0 );
+               r.setAutoColor( true );
+               r.setShowKey( false );
+               r.setShowValue( true );
+               r.setVertical( false );
+               r.setAutoGeneratedText( true );
+               r.setGenerated( true );
+               r.setAutoLabelDeleted( false );
+               r.setAutoBackground( true );
+               r.setRotation( (short) 0 );
+               r.setShowCategoryLabelAsPercentage( false );
+               r.setShowValueAsPercentage( false );
+               r.setShowBubbleSizes( false );
+               r.setShowLabel( false );
+               r.setIndexOfColorValue( (short) 77 );
+               r.setDataLabelPlacement( (short) 0 );
+               r.setTextRotation( (short) 0 );
+               return r;
+       }
+
+       private TextRecord createUnknownTextRecord()
+       {
+               TextRecord r = new TextRecord();
+               r.setHorizontalAlignment( TextRecord.HORIZONTAL_ALIGNMENT_CENTER );
+               r.setVerticalAlignment( TextRecord.VERTICAL_ALIGNMENT_CENTER );
+               r.setDisplayMode( TextRecord.DISPLAY_MODE_TRANSPARENT );
+               r.setRgbColor( 0 );
+               r.setX( -37 );
+               r.setY( -60 );
+               r.setWidth( 0 );
+               r.setHeight( 0 );
+               r.setAutoColor( true );
+               r.setShowKey( false );
+               r.setShowValue( false );
+               r.setVertical( false );
+               r.setAutoGeneratedText( true );
+               r.setGenerated( true );
+               r.setAutoLabelDeleted( false );
+               r.setAutoBackground( true );
+               r.setRotation( (short) 0 );
+               r.setShowCategoryLabelAsPercentage( false );
+               r.setShowValueAsPercentage( false );
+               r.setShowBubbleSizes( false );
+               r.setShowLabel( false );
+               r.setIndexOfColorValue( (short) 77 );
+               r.setDataLabelPlacement( (short) 11088 );
+               r.setTextRotation( (short) 0 );
+               return r;
+       }
+
+       private DefaultDataLabelTextPropertiesRecord createDefaultTextRecord( short categoryDataType )
+       {
+               DefaultDataLabelTextPropertiesRecord r = new DefaultDataLabelTextPropertiesRecord();
+               r.setCategoryDataType( categoryDataType );
+               return r;
+       }
+
+       private SheetPropertiesRecord createSheetPropsRecord()
+       {
+               SheetPropertiesRecord r = new SheetPropertiesRecord();
+               r.setChartTypeManuallyFormatted( false );
+               r.setPlotVisibleOnly( true );
+               r.setDoNotSizeWithWindow( false );
+               r.setDefaultPlotDimensions( true );
+               r.setAutoPlotArea( false );
+               return r;
+       }
+
+       private SeriesToChartGroupRecord createSeriesToChartGroupRecord()
+       {
+               return new SeriesToChartGroupRecord();
+       }
+
+       private DataFormatRecord createDataFormatRecord()
+       {
+               DataFormatRecord r = new DataFormatRecord();
+               r.setPointNumber( (short) -1 );
+               r.setSeriesIndex( (short) 0 );
+               r.setSeriesNumber( (short) 0 );
+               r.setUseExcel4Colors( false );
+               return r;
+       }
+
+       private LinkedDataRecord createCategoriesLinkedDataRecord()
+       {
+               LinkedDataRecord r = new LinkedDataRecord();
+               r.setLinkType( LinkedDataRecord.LINK_TYPE_CATEGORIES );
+               r.setReferenceType( LinkedDataRecord.REFERENCE_TYPE_WORKSHEET );
+               r.setCustomNumberFormat( false );
+               r.setIndexNumberFmtRecord( (short) 0 );
+               LinkedDataFormulaField formula = new LinkedDataFormulaField();
+               Stack tokens = new Stack();
+               Area3DPtg p = new Area3DPtg();
+               p.setExternSheetIndex( (short) 0 );
+               p.setFirstColumn( (short) 1 );
+               p.setLastColumn( (short) 1 );
+               p.setFirstRow( (short) 0 );
+               p.setLastRow( (short) 31 );
+               tokens.add( p );
+               formula.setFormulaTokens( tokens );
+               r.setFormulaOfLink( formula );
+               return r;
+       }
+
+       private LinkedDataRecord createValuesLinkedDataRecord()
+       {
+               LinkedDataRecord r = new LinkedDataRecord();
+               r.setLinkType( LinkedDataRecord.LINK_TYPE_VALUES );
+               r.setReferenceType( LinkedDataRecord.REFERENCE_TYPE_WORKSHEET );
+               r.setCustomNumberFormat( false );
+               r.setIndexNumberFmtRecord( (short) 0 );
+               LinkedDataFormulaField formula = new LinkedDataFormulaField();
+               Stack tokens = new Stack();
+               Area3DPtg p = new Area3DPtg();
+               p.setExternSheetIndex( (short) 0 );
+               p.setFirstColumn( (short) 0 );
+               p.setLastColumn( (short) 0 );
+               p.setFirstRow( (short) 0 );
+               p.setLastRow( (short) 31 );
+               tokens.add( p );
+               formula.setFormulaTokens( tokens );
+               r.setFormulaOfLink( formula );
+               return r;
+       }
+
+       private LinkedDataRecord createTitleLinkedDataRecord()
+       {
+               LinkedDataRecord r = new LinkedDataRecord();
+               r.setLinkType( LinkedDataRecord.LINK_TYPE_TITLE_OR_TEXT );
+               r.setReferenceType( LinkedDataRecord.REFERENCE_TYPE_DIRECT );
+               r.setCustomNumberFormat( false );
+               r.setIndexNumberFmtRecord( (short) 0 );
+               r.setFormulaOfLink( new LinkedDataFormulaField() );
+               return r;
+       }
+
+       private SeriesRecord createSeriesRecord()
+       {
+               SeriesRecord r = new SeriesRecord();
+               r.setCategoryDataType( SeriesRecord.CATEGORY_DATA_TYPE_NUMERIC );
+               r.setValuesDataType( SeriesRecord.VALUES_DATA_TYPE_NUMERIC );
+               r.setNumCategories( (short) 32 );
+               r.setNumValues( (short) 31 );
+               r.setBubbleSeriesType( SeriesRecord.BUBBLE_SERIES_TYPE_NUMERIC );
+               r.setNumBubbleValues( (short) 0 );
+               return r;
+       }
+
+       private EndRecord createEndRecord()
+       {
+               return new EndRecord();
+       }
+
+       private AreaFormatRecord createAreaFormatRecord1()
+       {
+               AreaFormatRecord r = new AreaFormatRecord();
+               r.setForegroundColor( 16777215 );        // RGB Color
+               r.setBackgroundColor( 0 );                      // RGB Color
+               r.setPattern( (short) 1 );                       // TODO: Add Pattern constants to record
+               r.setAutomatic( true );
+               r.setInvert( false );
+               r.setForecolorIndex( (short) 78 );
+               r.setBackcolorIndex( (short) 77 );
+               return r;
+       }
+
+       private AreaFormatRecord createAreaFormatRecord2()
+       {
+               AreaFormatRecord r = new AreaFormatRecord();
+               r.setForegroundColor(0x00c0c0c0);
+               r.setBackgroundColor(0x00000000);
+               r.setPattern((short)1);
+               r.setAutomatic(false);
+               r.setInvert(false);
+               r.setForecolorIndex((short)22);
+               r.setBackcolorIndex((short)79);
+               return r;
+       }
+
+       private LineFormatRecord createLineFormatRecord( boolean drawTicks )
+       {
+               LineFormatRecord r = new LineFormatRecord();
+               r.setLineColor( 0 );
+               r.setLinePattern( LineFormatRecord.LINE_PATTERN_SOLID );
+               r.setWeight( (short) -1 );
+               r.setAuto( true );
+               r.setDrawTicks( drawTicks );
+               r.setColourPaletteIndex( (short) 77 );  // what colour is this?
+               return r;
+       }
+
+       private LineFormatRecord createLineFormatRecord2()
+       {
+               LineFormatRecord r = new LineFormatRecord();
+               r.setLineColor( 0x00808080 );
+               r.setLinePattern( (short) 0 );
+               r.setWeight( (short) 0 );
+               r.setAuto( false );
+               r.setDrawTicks( false );
+               r.setUnknown( false );
+               r.setColourPaletteIndex( (short) 23 );
+               return r;
+       }
+
+       private FrameRecord createFrameRecord1()
+       {
+               FrameRecord r = new FrameRecord();
+               r.setBorderType( FrameRecord.BORDER_TYPE_REGULAR );
+               r.setAutoSize( false );
+               r.setAutoPosition( true );
+               return r;
+       }
+
+       private FrameRecord createFrameRecord2()
+       {
+               FrameRecord r = new FrameRecord();
+               r.setBorderType( FrameRecord.BORDER_TYPE_REGULAR );
+               r.setAutoSize( true );
+               r.setAutoPosition( true );
+               return r;
+       }
+
+       private PlotGrowthRecord createPlotGrowthRecord( int horizScale, int vertScale )
+       {
+               PlotGrowthRecord r = new PlotGrowthRecord();
+               r.setHorizontalScale( horizScale );
+               r.setVerticalScale( vertScale );
+               return r;
+       }
+
+       private SCLRecord createSCLRecord( short numerator, short denominator )
+       {
+               SCLRecord r = new SCLRecord();
+               r.setDenominator( denominator );
+               r.setNumerator( numerator );
+               return r;
+       }
+
+       private BeginRecord createBeginRecord()
+       {
+               return new BeginRecord();
+       }
+
+       private ChartRecord createChartRecord( int x, int y, int width, int height )
+       {
+               ChartRecord r = new ChartRecord();
+               r.setX( x );
+               r.setY( y );
+               r.setWidth( width );
+               r.setHeight( height );
+               return r;
+       }
+
+       private UnitsRecord createUnitsRecord()
+       {
+               UnitsRecord r = new UnitsRecord();
+               r.setUnits( (short) 0 );
+               return r;
+       }
+
+       
+       /**
+        * A series in a chart
+        */
+       public class HSSFSeries {
+               private SeriesRecord series;
+               private SeriesTextRecord seriesTitleText;
+               
+               /* package */ HSSFSeries(SeriesRecord series) {
+                       this.series = series;
+               }
+               
+               public short getNumValues() {
+                       return series.getNumValues();
+               }
+               /**
+                * See {@link SeriesRecord}
+                */
+               public short getValueType() {
+                       return series.getValuesDataType();
+               }
+               
+               /**
+                * Returns the series' title, if there is one,
+                *  or null if not
+                */
+               public String getSeriesTitle() {
+                       if(seriesTitleText != null) {
+                               return seriesTitleText.getText();
+                       }
+                       return null;
+               }
+               
+               /**
+                * Changes the series' title, but only if there 
+                *  was one already.
+                * TODO - add in the records if not
+                */
+               public void setSeriesTitle(String title) {
+                       if(seriesTitleText != null) {
+                               seriesTitleText.setText(title);
+                       } else {
+                               throw new IllegalStateException("No series title found to change");
+                       }
+               }
+       }
 }
index d28b8a8777fc0a73287e2336ea5982650e4f0d2c..d244d3372ec1b9f77e7fdc12a3634a3c7f56fbfb 100644 (file)
    See the License for the specific language governing permissions and
    limitations under the License.
 ==================================================================== */
-package org.apache.poi.hssf.usermodel;
-
-import java.io.File;
-import java.io.FileInputStream;
 
-import org.apache.poi.hssf.record.SeriesRecord;
+package org.apache.poi.hssf.usermodel;
 
 import junit.framework.TestCase;
 
-public class TestHSSFChart extends TestCase {
-       private String dirName;
+import org.apache.poi.hssf.HSSFTestDataSamples;
+import org.apache.poi.hssf.record.SeriesRecord;
 
-       protected void setUp() throws Exception {
-               dirName = System.getProperty("HSSF.testdata.path");
-       }
+public final class TestHSSFChart extends TestCase {
 
        public void testSingleChart() throws Exception {
-               HSSFWorkbook wb = new HSSFWorkbook(
-                               new FileInputStream(new File(dirName, "WithChart.xls"))
-               );
+               HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("WithChart.xls");
                
                HSSFSheet s1 = wb.getSheetAt(0);
                HSSFSheet s2 = wb.getSheetAt(1);
@@ -62,9 +54,7 @@ public class TestHSSFChart extends TestCase {
        }
 
        public void testTwoCharts() throws Exception {
-               HSSFWorkbook wb = new HSSFWorkbook(
-                               new FileInputStream(new File(dirName, "WithTwoCharts.xls"))
-               );
+               HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("WithTwoCharts.xls");
                
                HSSFSheet s1 = wb.getSheetAt(0);
                HSSFSheet s2 = wb.getSheetAt(1);
@@ -96,9 +86,7 @@ public class TestHSSFChart extends TestCase {
        }
        
        public void testThreeCharts() throws Exception {
-               HSSFWorkbook wb = new HSSFWorkbook(
-                               new FileInputStream(new File(dirName, "WithThreeCharts.xls"))
-               );
+               HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("WithThreeCharts.xls");
                
                HSSFSheet s1 = wb.getSheetAt(0);
                HSSFSheet s2 = wb.getSheetAt(1);
index 0913ab7250ce009d887a12ce30ff2cc1f6876c73..cb028edfa56c9b705e6c3b400b8c63b3e19a0416 100644 (file)
@@ -32,7 +32,7 @@ import org.apache.poi.poifs.filesystem.POIFSFileSystem;
  */
 public final class TestExcelExtractor extends TestCase {
 
-       private static final ExcelExtractor createExtractor(String sampleFileName) {
+       private static ExcelExtractor createExtractor(String sampleFileName) {
                
                InputStream is = HSSFTestDataSamples.openSampleFileStream(sampleFileName);
                
@@ -192,18 +192,16 @@ public final class TestExcelExtractor extends TestCase {
         * Embded in a non-excel file
         */
        public void testWithEmbeded() throws Exception {
+               // TODO - encapsulate sys prop 'POIFS.testdata.path' similar to HSSFTestDataSamples
                String pdirname = System.getProperty("POIFS.testdata.path");
                String filename = pdirname + "/word_with_embeded.doc";
                POIFSFileSystem fs = new POIFSFileSystem(
                                new FileInputStream(filename)
                );
                
-               DirectoryNode objPool = (DirectoryNode)
-                       fs.getRoot().getEntry("ObjectPool");
-               DirectoryNode dirA = (DirectoryNode)
-                       objPool.getEntry("_1269427460");
-               DirectoryNode dirB = (DirectoryNode)
-                       objPool.getEntry("_1269427461");
+               DirectoryNode objPool = (DirectoryNode) fs.getRoot().getEntry("ObjectPool");
+               DirectoryNode dirA = (DirectoryNode) objPool.getEntry("_1269427460");
+               DirectoryNode dirB = (DirectoryNode) objPool.getEntry("_1269427461");
 
                HSSFWorkbook wbA = new HSSFWorkbook(dirA, fs, true);
                HSSFWorkbook wbB = new HSSFWorkbook(dirB, fs, true);
@@ -224,16 +222,15 @@ public final class TestExcelExtractor extends TestCase {
         * Excel embeded in excel
         */
        public void testWithEmbededInOwn() throws Exception {
+               // TODO - encapsulate sys prop 'POIFS.testdata.path' similar to HSSFTestDataSamples
                String pdirname = System.getProperty("POIFS.testdata.path");
                String filename = pdirname + "/excel_with_embeded.xls";
                POIFSFileSystem fs = new POIFSFileSystem(
                                new FileInputStream(filename)
                );
                
-       DirectoryNode dirA = (DirectoryNode)
-                       fs.getRoot().getEntry("MBD0000A3B5");
-               DirectoryNode dirB = (DirectoryNode)
-                       fs.getRoot().getEntry("MBD0000A3B4");
+               DirectoryNode dirA = (DirectoryNode) fs.getRoot().getEntry("MBD0000A3B5");
+               DirectoryNode dirB = (DirectoryNode) fs.getRoot().getEntry("MBD0000A3B4");
                
                HSSFWorkbook wbA = new HSSFWorkbook(dirA, fs, true);
                HSSFWorkbook wbB = new HSSFWorkbook(dirB, fs, true);
@@ -260,15 +257,15 @@ public final class TestExcelExtractor extends TestCase {
         * Test that we get text from headers and footers
         */
        public void test45538() throws Exception {
-               String[] files = new String[] {
+               String[] files = {
                        "45538_classic_Footer.xls", "45538_form_Footer.xls",    
                        "45538_classic_Header.xls", "45538_form_Header.xls"
                };
                for(int i=0; i<files.length; i++) {
                        ExcelExtractor extractor = createExtractor(files[i]);
                        String text = extractor.getText();
-                       assertTrue("Unable to find expected word in text\n" + text, text.contains("testdoc"));
-                       assertTrue("Unable to find expected word in text\n" + text, text.contains("test phrase"));
+                       assertTrue("Unable to find expected word in text\n" + text, text.indexOf("testdoc") >=0);
+                       assertTrue("Unable to find expected word in text\n" + text, text.indexOf("test phrase") >= 0);
                }
        }
 }
index 4589ee5b131a80874934e869c9dcb9965bbf0b55..22defb942e9e4fffa111f66529a836b29a133768 100644 (file)
 
 package org.apache.poi.hssf.model;
 
+import java.io.ByteArrayInputStream;
+import java.util.ArrayList;
+import java.util.List;
+
 import junit.framework.AssertionFailedError;
 import junit.framework.TestCase;
 
 import org.apache.poi.hssf.eventmodel.ERFListener;
 import org.apache.poi.hssf.eventmodel.EventRecordFactory;
-import org.apache.poi.hssf.record.*;
+import org.apache.poi.hssf.record.BOFRecord;
+import org.apache.poi.hssf.record.BlankRecord;
+import org.apache.poi.hssf.record.CellValueRecordInterface;
+import org.apache.poi.hssf.record.ColumnInfoRecord;
+import org.apache.poi.hssf.record.DimensionsRecord;
+import org.apache.poi.hssf.record.EOFRecord;
+import org.apache.poi.hssf.record.IndexRecord;
+import org.apache.poi.hssf.record.MergeCellsRecord;
+import org.apache.poi.hssf.record.Record;
+import org.apache.poi.hssf.record.RowRecord;
+import org.apache.poi.hssf.record.StringRecord;
+import org.apache.poi.hssf.record.UncalcedRecord;
 import org.apache.poi.hssf.record.aggregates.ColumnInfoRecordsAggregate;
 import org.apache.poi.hssf.record.aggregates.RowRecordsAggregate;
 import org.apache.poi.hssf.record.aggregates.ValueRecordsAggregate;
-
-import java.io.ByteArrayInputStream;
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
+import org.apache.poi.hssf.util.CellRangeAddress;
 
 /**
  * Unit test for the Sheet class.
@@ -55,10 +66,24 @@ public final class TestSheet extends TestCase {
         assertTrue( sheet.records.get(pos++) instanceof EOFRecord );
     }
 
+    private static final class MergedCellListener implements ERFListener {
+
+        private int _count;
+        public MergedCellListener() {
+            _count = 0;
+        }
+        public boolean processRecord(Record rec) {
+            _count++;
+            return true;
+        }
+        public int getCount() {
+            return _count;
+        }
+    }
+    
     public void testAddMergedRegion() {
         Sheet sheet = Sheet.createSheet();
         int regionsToAdd = 4096;
-        int startRecords = sheet.getRecords().size();
 
         //simple test that adds a load of regions
         for (int n = 0; n < regionsToAdd; n++)
@@ -71,11 +96,18 @@ public final class TestSheet extends TestCase {
         assertTrue(sheet.getNumMergedRegions() == regionsToAdd);
 
         //test that the regions were spread out over the appropriate number of records
-        int recordsAdded    = sheet.getRecords().size() - startRecords;
+        byte[] sheetData = new byte[sheet.getSize()];
+        sheet.serialize(0, sheetData);
+        MergedCellListener mcListener = new MergedCellListener();
+        EventRecordFactory erf = new EventRecordFactory(mcListener, new short[] { MergeCellsRecord.sid, });
+//        POIFSFileSystem poifs = new POIFSFileSystem(new ByteArrayInputStream(sheetData));
+        erf.processRecords(new ByteArrayInputStream(sheetData));
+        int recordsAdded    = mcListener.getCount();
         int recordsExpected = regionsToAdd/1027;
         if ((regionsToAdd % 1027) != 0)
             recordsExpected++;
-        assertTrue("The " + regionsToAdd + " merged regions should have been spread out over " + recordsExpected + " records, not " + recordsAdded, recordsAdded == recordsExpected);
+        assertTrue("The " + regionsToAdd + " merged regions should have been spread out over " 
+                + recordsExpected + " records, not " + recordsAdded, recordsAdded == recordsExpected);
         // Check we can't add one with invalid date
         try {
             sheet.addMergedRegion(10, (short)10, 9, (short)12);
@@ -97,22 +129,23 @@ public final class TestSheet extends TestCase {
         Sheet sheet = Sheet.createSheet();
         int regionsToAdd = 4096;
 
-        for (int n = 0; n < regionsToAdd; n++)
-            sheet.addMergedRegion(0, (short) 0, 1, (short) 1);
+        for (int n = 0; n < regionsToAdd; n++) {
+            sheet.addMergedRegion(n, 0, n, 1);
+        }
 
-        int records = sheet.getRecords().size();
+        int nSheetRecords = sheet.getRecords().size();
 
         //remove a third from the beginning
         for (int n = 0; n < regionsToAdd/3; n++)
         {
             sheet.removeMergedRegion(0);
             //assert they have been deleted
-            assertTrue("Num of regions should be " + (regionsToAdd - n - 1) + " not " + sheet.getNumMergedRegions(), sheet.getNumMergedRegions() == regionsToAdd - n - 1);
+            assertEquals("Num of regions", regionsToAdd - n - 1, sheet.getNumMergedRegions());
         }
-
-        //assert any record removing was done
-        int recordsRemoved = (regionsToAdd/3)/1027; //doesn't work for particular values of regionsToAdd
-        assertTrue("Expected " + recordsRemoved + " record to be removed from the starting " + records + ".  Currently there are " + sheet.getRecords().size() + " records", records - sheet.getRecords().size() == recordsRemoved);
+        
+        // merge records are removed from within the MergedCellsTable, 
+        // so the sheet record count should not change 
+        assertEquals("Sheet Records", nSheetRecords, sheet.getRecords().size());
     }
 
     /**
@@ -125,8 +158,11 @@ public final class TestSheet extends TestCase {
     public void testMovingMergedRegion() {
         List records = new ArrayList();
 
-        MergeCellsRecord merged = new MergeCellsRecord();
-        merged.addArea(0, (short)0, 1, (short)2);
+        CellRangeAddress[] cras = {
+            new CellRangeAddress(0, 1, 0, 2),
+        };
+        MergeCellsRecord merged = new MergeCellsRecord(cras, 0, cras.length);
+        records.add(new DimensionsRecord());
         records.add(new RowRecord(0));
         records.add(new RowRecord(1));
         records.add(new RowRecord(2));
@@ -155,6 +191,7 @@ public final class TestSheet extends TestCase {
     public void testRowAggregation() {
         List records = new ArrayList();
 
+        records.add(new DimensionsRecord());
         records.add(new RowRecord(0));
         records.add(new RowRecord(1));
         records.add(new StringRecord());
@@ -196,10 +233,9 @@ public final class TestSheet extends TestCase {
         boolean is0 = false;
         boolean is11 = false;
 
-        Iterator iterator = sheet.getRowBreaks();
-        while (iterator.hasNext()) {
-            PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
-            int main = breakItem.main;
+        int[] rowBreaks = sheet.getRowBreaks();
+        for (int i = 0; i < rowBreaks.length; i++) {
+            int main = rowBreaks[i];
             if (main != 0 && main != 10 && main != 11) fail("Invalid page break");
             if (main == 0)     is0 = true;
             if (main == 10) is10= true;
@@ -253,10 +289,9 @@ public final class TestSheet extends TestCase {
         boolean is1 = false;
         boolean is15 = false;
 
-        Iterator iterator = sheet.getColumnBreaks();
-        while (iterator.hasNext()) {
-            PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
-            int main = breakItem.main;
+        int[] colBreaks = sheet.getColumnBreaks();
+        for (int i = 0; i < colBreaks.length; i++) {
+            int main = colBreaks[i];
             if (main != 0 && main != 1 && main != 10 && main != 15) fail("Invalid page break");
             if (main == 0)  is0 = true;
             if (main == 1)  is1 = true;
@@ -297,9 +332,8 @@ public final class TestSheet extends TestCase {
         xfindex = sheet.getXFIndexForColAt((short) 1);
         assertEquals(DEFAULT_IDX, xfindex);
 
-        // TODO change return type to ColumnInfoRecord 
-        ColumnInfoRecord nci = (ColumnInfoRecord)ColumnInfoRecordsAggregate.createColInfo();
-        sheet.columns.insertColumn(nci);
+        ColumnInfoRecord nci = ColumnInfoRecordsAggregate.createColInfo();
+        sheet._columnInfos.insertColumn(nci);
 
         // single column ColumnInfoRecord
         nci.setFirstColumn((short) 2);
@@ -361,6 +395,7 @@ public final class TestSheet extends TestCase {
         List records = new ArrayList();
         records.add(new BOFRecord());
         records.add(new UncalcedRecord());
+        records.add(new DimensionsRecord());
         records.add(new EOFRecord());
         Sheet sheet = Sheet.createSheet(records, 0, 0);
 
@@ -369,7 +404,7 @@ public final class TestSheet extends TestCase {
         if (serializedSize != estimatedSize) {
             throw new AssertionFailedError("Identified bug 45066 b");
         }
-        assertEquals(50, serializedSize);
+        assertEquals(68, serializedSize);
     }
 
     /**
@@ -393,7 +428,7 @@ public final class TestSheet extends TestCase {
 
 
         int dbCellRecordPos = getDbCellRecordPos(sheet);
-        if (dbCellRecordPos == 264) {
+        if (dbCellRecordPos == 252) {
             // The overt symptom of the bug
             // DBCELL record pos is calculated wrong if VRA comes before RRA
             throw new AssertionFailedError("Identified  bug 45145");
@@ -405,7 +440,7 @@ public final class TestSheet extends TestCase {
         assertEquals(RowRecordsAggregate.class, recs.get(rraIx).getClass());
         assertEquals(ValueRecordsAggregate.class, recs.get(rraIx+1).getClass());
 
-        assertEquals(254, dbCellRecordPos);
+        assertEquals(242, dbCellRecordPos);
     }
 
     /**
index f86c2941a970cdb3681acb3ccffb9381decc31bf..0962b9148aaf3feee84298a62cbda598b8d007c4 100644 (file)
@@ -29,8 +29,7 @@ public final class TestSheetAdditional extends TestCase {
        
        public void testGetCellWidth() {
                Sheet sheet = Sheet.createSheet();
-               // TODO change return type to ColumnInfoRecord 
-               ColumnInfoRecord nci = (ColumnInfoRecord)ColumnInfoRecordsAggregate.createColInfo();
+               ColumnInfoRecord nci = ColumnInfoRecordsAggregate.createColInfo();
 
                // Prepare test model
                nci.setFirstColumn((short)5);
@@ -38,7 +37,7 @@ public final class TestSheetAdditional extends TestCase {
                nci.setColumnWidth((short)100);
                
                
-               sheet.columns.insertColumn(nci);
+               sheet._columnInfos.insertColumn(nci);
 
                assertEquals((short)100,sheet.getColumnWidth((short)5));
                assertEquals((short)100,sheet.getColumnWidth((short)6));
@@ -58,6 +57,3 @@ public final class TestSheetAdditional extends TestCase {
        }
 
 }
-
-
-
index 9df7e3b26830e1b2e4972569b3ab46f9f4751b9e..c0a8f9fe74b9ff2614f797a994d30072f63d143f 100644 (file)
@@ -33,8 +33,8 @@ public final class TestMergeCellsRecord extends TestCase {
     * @throws Exception
     */
    public void testCloneReferences() throws Exception {
-      MergeCellsRecord merge = new MergeCellsRecord();
-      merge.addArea(0, (short)0, 1, (short)2);
+      CellRangeAddress[] cras = { new CellRangeAddress(0, 1, 0, 2), };
+      MergeCellsRecord merge = new MergeCellsRecord(cras, 0, cras.length);
       MergeCellsRecord clone = (MergeCellsRecord)merge.clone();
       
       assertNotSame("Merged and cloned objects are the same", merge, clone);
@@ -47,7 +47,6 @@ public final class TestMergeCellsRecord extends TestCase {
       assertEquals("New Clone Col From doesnt match", mergeRegion.getFirstColumn(), cloneRegion.getFirstColumn());
       assertEquals("New Clone Col To doesnt match", mergeRegion.getLastColumn(), cloneRegion.getLastColumn());      
       
-      merge.removeAreaAt(0);
-      assertNotNull("Clone's item not removed", clone.getAreaAt(0));
+      assertFalse(merge.getAreaAt(0) == clone.getAreaAt(0));
    }
 }
index efe352b24463e056152a2a52d44d8f49c286b438..844430fb733a60618cadb72b6f8df0bdda9f9ec6 100644 (file)
@@ -24,6 +24,7 @@ import java.util.List;
 
 import junit.framework.TestCase;
 
+import org.apache.poi.hssf.model.RecordStream;
 import org.apache.poi.hssf.record.CFHeaderRecord;
 import org.apache.poi.hssf.record.CFRuleRecord;
 import org.apache.poi.hssf.record.RecordFactory;
@@ -59,7 +60,7 @@ public final class TestCFRecordsAggregate extends TestCase
                recs.add(rule2);
                recs.add(rule3);
                CFRecordsAggregate record;
-               record = CFRecordsAggregate.createCFAggregate(recs, 0);
+               record = CFRecordsAggregate.createCFAggregate(new RecordStream(recs, 0));
 
                // Serialize
                byte [] serializedRecord = record.serialize();
@@ -81,7 +82,7 @@ public final class TestCFRecordsAggregate extends TestCase
                assertEquals(2, cellRanges.length);
                assertEquals(3, header.getNumberOfConditionalFormats());
 
-               record = CFRecordsAggregate.createCFAggregate(recs, 0);
+               record = CFRecordsAggregate.createCFAggregate(new RecordStream(recs, 0));
 
                record = record.cloneCFAggregate();
 
index 20fded35e99125764cd07a76028a15cd05e5b801..2988290616d29cbda560e9d2fec9a902af0d520b 100644 (file)
@@ -19,42 +19,39 @@ package org.apache.poi.hssf.record.aggregates;
 
 import junit.framework.TestCase;
 import org.apache.poi.hssf.record.ColumnInfoRecord;
+import org.apache.poi.hssf.record.RecordBase;
 
 /**
  * @author Glen Stampoultzis
  */
-public final class TestColumnInfoRecordsAggregate extends TestCase
-{
-    ColumnInfoRecordsAggregate columnInfoRecordsAggregate;
-
-    public void testGetRecordSize() throws Exception
-    {
-        columnInfoRecordsAggregate = new ColumnInfoRecordsAggregate();
-        columnInfoRecordsAggregate.insertColumn( createColumn( (short)1, (short)3 ));
-        columnInfoRecordsAggregate.insertColumn( createColumn( (short)4, (short)7 ));
-        columnInfoRecordsAggregate.insertColumn( createColumn( (short)8, (short)8 ));
-//        columnInfoRecordsAggregate.setColumn( (short)2, new Short( (short)200 ), new Integer( 1 ), new Boolean( true ), null);
-        columnInfoRecordsAggregate.groupColumnRange( (short)2, (short)5, true );
-        assertEquals(6, columnInfoRecordsAggregate.getNumColumns());
-
-        assertEquals(columnInfoRecordsAggregate.getRecordSize(), columnInfoRecordsAggregate.serialize().length);
-
-        columnInfoRecordsAggregate = new ColumnInfoRecordsAggregate();
-        columnInfoRecordsAggregate.groupColumnRange( (short)3, (short)6, true );
-
-        assertEquals(columnInfoRecordsAggregate.getRecordSize(), serializedSize());
-    }
-
-    private int serializedSize()
-    {
-        return columnInfoRecordsAggregate.serialize(0, new byte[columnInfoRecordsAggregate.getRecordSize()]);
-    }
-
-    private ColumnInfoRecord createColumn( short firstCol, short lastCol )
-    {
-        ColumnInfoRecord columnInfoRecord = new ColumnInfoRecord( );
-        columnInfoRecord.setFirstColumn(firstCol);
-        columnInfoRecord.setLastColumn(lastCol);
-        return columnInfoRecord;
-    }
+public final class TestColumnInfoRecordsAggregate extends TestCase {
+
+       public void testGetRecordSize() {
+               ColumnInfoRecordsAggregate agg = new ColumnInfoRecordsAggregate();
+               agg.insertColumn(createColumn(1, 3));
+               agg.insertColumn(createColumn(4, 7));
+               agg.insertColumn(createColumn(8, 8));
+               agg.groupColumnRange((short) 2, (short) 5, true);
+               assertEquals(6, agg.getNumColumns());
+
+               confirmSerializedSize(agg);
+
+               agg = new ColumnInfoRecordsAggregate();
+               agg.groupColumnRange((short) 3, (short) 6, true);
+               confirmSerializedSize(agg);
+       }
+
+       private static void confirmSerializedSize(RecordBase cirAgg) {
+               int estimatedSize = cirAgg.getRecordSize();
+               byte[] buf = new byte[estimatedSize];
+               int serializedSize = cirAgg.serialize(0, buf);
+               assertEquals(estimatedSize, serializedSize);
+       }
+
+       private static ColumnInfoRecord createColumn(int firstCol, int lastCol) {
+               ColumnInfoRecord columnInfoRecord = new ColumnInfoRecord();
+               columnInfoRecord.setFirstColumn((short) firstCol);
+               columnInfoRecord.setLastColumn((short) lastCol);
+               return columnInfoRecord;
+       }
 }
\ No newline at end of file
index 541fb893a5783c6164310d26071547a03194675e..646321d3d2eb638c9e457aaa83db0904aca652a9 100644 (file)
@@ -660,7 +660,7 @@ public final class TestBugs extends TestCase {
 
             HSSFSheet sheet = wb.getSheetAt( 0 );
             int[] breaks = sheet.getRowBreaks();
-            assertNull(breaks);
+            assertEquals(0, breaks.length);
 
             //add 3 row breaks
             for (int j = 1; j <= 3; j++) {