]> source.dussan.org Git - poi.git/commitdiff
Merged revisions 638786-638802,638805-638811,638813-638814,638816-639230,639233-63924...
authorNick Burch <nick@apache.org>
Sat, 5 Apr 2008 13:38:52 +0000 (13:38 +0000)
committerNick Burch <nick@apache.org>
Sat, 5 Apr 2008 13:38:52 +0000 (13:38 +0000)
https://svn.apache.org/repos/asf/poi/trunk

........
  r643625 | josh | 2008-04-01 23:18:25 +0100 (Tue, 01 Apr 2008) | 1 line

  Bug #44733 - DPRODUCT function should be index 189, not 191
........
  r643654 | josh | 2008-04-02 00:53:51 +0100 (Wed, 02 Apr 2008) | 1 line

  fix for bug 44710 - Incorrect skip() of second formula in DATAVALIDATION record
........
  r643670 | klute | 2008-04-02 01:50:45 +0100 (Wed, 02 Apr 2008) | 1 line

  44694 - HPSF: Support for property sets without sections
........
  r643672 | klute | 2008-04-02 01:55:52 +0100 (Wed, 02 Apr 2008) | 1 line

  Restored an entry that had been deleted by chance.
........
  r643831 | yegor | 2008-04-02 11:20:31 +0100 (Wed, 02 Apr 2008) | 1 line

  added set accessor to indentation level
........
  r643834 | yegor | 2008-04-02 11:25:18 +0100 (Wed, 02 Apr 2008) | 1 line

  Fixed inconsistency between HSSFSHeet.getColumnWidth and HSSFSheet.getDefaultColumnWidth: getColumnWidth should always return width measured in 1/256th units.
........
  r644343 | nick | 2008-04-03 16:04:52 +0100 (Thu, 03 Apr 2008) | 1 line

  Make a bit of a start on being able to edit chart titles, based on the email to user@poi from Russ on the 2nd of April. Not quite there though
........
  r644473 | josh | 2008-04-03 21:25:53 +0100 (Thu, 03 Apr 2008) | 1 line

  Fix for bug 44739 - Conditional formatting (regions with max row/col index)
........
  r644509 | josh | 2008-04-03 22:17:26 +0100 (Thu, 03 Apr 2008) | 1 line

  Follow up fix after r644473 (bug 44739) TestHSSFConditionalFormatting had a bug and wasn't yet included in the test suite hierarchy
........

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

27 files changed:
src/documentation/content/xdocs/changes.xml
src/documentation/content/xdocs/status.xml
src/java/org/apache/poi/hpsf/MutablePropertySet.java
src/java/org/apache/poi/hpsf/PropertySet.java
src/java/org/apache/poi/hssf/model/Sheet.java
src/java/org/apache/poi/hssf/record/CFHeaderRecord.java
src/java/org/apache/poi/hssf/record/DVRecord.java
src/java/org/apache/poi/hssf/record/cf/CellRange.java
src/resources/main/org/apache/poi/hssf/record/formula/function/functionMetadata.txt
src/scratchpad/src/org/apache/poi/hslf/usermodel/RichTextRun.java
src/scratchpad/src/org/apache/poi/hssf/usermodel/HSSFChart.java
src/scratchpad/testcases/org/apache/poi/hssf/usermodel/TestHSSFChart.java [new file with mode: 0644]
src/testcases/org/apache/poi/hpsf/data/Test_Humor-Generation.ppt [new file with mode: 0644]
src/testcases/org/apache/poi/hssf/data/WithThreeCharts.xls [new file with mode: 0755]
src/testcases/org/apache/poi/hssf/data/WithThreeCharts.xlsx [new file with mode: 0755]
src/testcases/org/apache/poi/hssf/data/colwidth.xls [new file with mode: 0755]
src/testcases/org/apache/poi/hssf/data/missingFuncs44675.xls
src/testcases/org/apache/poi/hssf/record/AllRecordTests.java
src/testcases/org/apache/poi/hssf/record/TestCFHeaderRecord.java
src/testcases/org/apache/poi/hssf/record/cf/TestCellRange.java
src/testcases/org/apache/poi/hssf/record/formula/AllFormulaTests.java
src/testcases/org/apache/poi/hssf/record/formula/function/TestParseMissingBuiltInFuncs.java
src/testcases/org/apache/poi/hssf/record/formula/function/TestReadMissingBuiltInFuncs.java
src/testcases/org/apache/poi/hssf/usermodel/AllUserModelTests.java
src/testcases/org/apache/poi/hssf/usermodel/TestHSSFConditionalFormatting.java [new file with mode: 0644]
src/testcases/org/apache/poi/hssf/usermodel/TestHSSFConfditionalFormatting.java [deleted file]
src/testcases/org/apache/poi/hssf/usermodel/TestHSSFSheet.java

index 5722a7be458761b55cc06067a0d218ca06dbd004..e2e6faef7e08311028eb5c8f9f07e704abdd13e1 100644 (file)
@@ -37,7 +37,9 @@
 
                <!-- Don't forget to update status.xml too! -->
         <release version="3.0.3-beta1" date="2008-04-??">
+           <action dev="POI-DEVELOPERS" type="fix">44739 - Small fixes for conditional formatting (regions with max row/col index)</action>
            <action dev="POI-DEVELOPERS" type="add">Implement Sheet.removeShape(Shape shape) in HSLF</action>
+           <action dev="RK" type="add">44694 - HPSF: Support for property sets without sections</action>
            <action dev="POI-DEVELOPERS" type="add">Various fixes: Recognising var-arg built-in functions #44675, ExternalNameRecord serialisation bug #44695, PMT() bug #44691</action>
            <action dev="POI-DEVELOPERS" type="add">30311 - More work on Conditional Formatting</action>
            <action dev="POI-DEVELOPERS" type="add">Move the Formula Evaluator code out of scratchpad</action>
index 9d35cb7fd10d8c89485891087d5932ce8469f9b6..7a1d2e9717947d9516efda26c76e01196f41af0d 100644 (file)
@@ -34,6 +34,8 @@
        <!-- Don't forget to update changes.xml too! -->
     <changes>
         <release version="3.0.3-beta1" date="2008-04-??">
+           <action dev="POI-DEVELOPERS" type="fix">44739 - Small fixes for conditional formatting (regions with max row/col index)</action>
+           <action dev="RK" type="add">44694 - HPSF: Support for property sets without sections</action>
            <action dev="POI-DEVELOPERS" type="add">Implement Sheet.removeShape(Shape shape) in HSLF</action>
            <action dev="POI-DEVELOPERS" type="add">Various fixes: Recognising var-arg built-in functions #44675, ExternalNameRecord serialisation bug #44695, PMT() bug #44691</action>
            <action dev="POI-DEVELOPERS" type="add">30311 - More work on Conditional Formatting</action>
index 34281b90c13dad9fe60708096c13b8f28d495afb..5ecbfeee3d9a3181312ef10d6d26b13bff1e0224 100644 (file)
@@ -92,6 +92,8 @@ public class MutablePropertySet extends PropertySet
         osVersion = ps.getOSVersion();
         setClassID(ps.getClassID());
         clearSections();
+        if (sections == null)
+            sections = new LinkedList();
         for (final Iterator i = ps.getSections().iterator(); i.hasNext();)
         {
             final MutableSection s = new MutableSection((Section) (i.next()));
index 0bfbb8f32f528e20cd5cd6d02e36c40a2eb6fe2a..b39ba08bfa95caaa5cfe3f7d65bbe5d6a001e7ff 100644 (file)
@@ -387,7 +387,7 @@ public class PropertySet
         o += ClassID.LENGTH;
         final long sectionCount = LittleEndian.getUInt(src, o);
         o += LittleEndian.INT_SIZE;
-        if (sectionCount < 1)
+        if (sectionCount < 0)
             return false;
         return true;
     }
@@ -426,9 +426,9 @@ public class PropertySet
         o += ClassID.LENGTH;
         final int sectionCount = LittleEndian.getInt(src, o);
         o += LittleEndian.INT_SIZE;
-        if (sectionCount <= 0)
+        if (sectionCount < 0)
             throw new HPSFRuntimeException("Section count " + sectionCount +
-                                           " must be greater than 0.");
+                                           " is negative.");
 
         /*
          * Read the sections, which are following the header. They
@@ -468,6 +468,8 @@ public class PropertySet
      */
     public boolean isSummaryInformation()
     {
+        if (sections.size() <= 0)
+            return false;
         return Util.equal(((Section) sections.get(0)).getFormatID().getBytes(),
                           SectionIDMap.SUMMARY_INFORMATION_ID);
     }
@@ -483,6 +485,8 @@ public class PropertySet
      */
     public boolean isDocumentSummaryInformation()
     {
+        if (sections.size() <= 0)
+            return false;
         return Util.equal(((Section) sections.get(0)).getFormatID().getBytes(),
                           SectionIDMap.DOCUMENT_SUMMARY_INFORMATION_ID[0]);
     }
index 451cde7579481469a7c846f7065813d0c828fe94..2af25e7481bce0c7aeb282258ad90d7d35133a94 100644 (file)
@@ -1879,12 +1879,12 @@ public class Sheet implements Model
     }
 
     /**
-     * get the width of a given column in units of 1/20th of a point width (twips?)
+     * get the width of a given column in units of 1/256th of a character width
      * @param column 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/20th of a point (twips?)
+     * @return column width in units of 1/256th of a character width
      */
 
     public short getColumnWidth(short column)
@@ -1912,7 +1912,9 @@ public class Sheet implements Model
         }
         else
         {
-            retval = defaultcolwidth.getColWidth();
+            //default column width is measured in characters
+            //multiply
+            retval = (short)(256*defaultcolwidth.getColWidth());
         }
         return retval;
     }
@@ -1951,9 +1953,9 @@ public class Sheet implements Model
     }
 
     /**
-     * set the width for a given column in 1/20th of a character width units
+     * 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/20th of a character width)
+     * @param width (in units of 1/256th of a character width)
      */
     public void setColumnWidth(short column, short width)
     {
index 7f2d5c319782da76973e618016cc30bd8289449e..d74d54ab1732d6c82239d8e5db751d252846346c 100644 (file)
@@ -58,12 +58,12 @@ public final class CFHeaderRecord extends Record
        {
                field_1_numcf = in.readShort();
                field_2_need_recalculation = in.readShort();
-               field_3_enclosing_cell_range = new CellRange(in.readShort(),in.readShort(),in.readShort(),in.readShort());
+               field_3_enclosing_cell_range = new CellRange(in.readUShort(), in.readUShort(), in.readUShort(), in.readUShort());
                int numCellRanges = in.readShort();
                CellRange[] crs = new CellRange[numCellRanges];
                for( int i=0; i<numCellRanges; i++)
                {
-                       crs[i] = new CellRange(in.readShort(),in.readShort(),in.readShort(),in.readShort());
+                       crs[i] = new CellRange(in.readUShort(),in.readUShort(),in.readUShort(),in.readUShort());
                }
                field_4_cell_ranges = crs;
        }
index a7b68a1743ff9f4d7cb13df8bec30e1ad40ca62c..c4e37114d958c209741624cb376cc7bbb2911e5a 100644 (file)
@@ -28,7 +28,7 @@ import org.apache.poi.util.LittleEndian;
 import org.apache.poi.util.StringUtil;
 
 /**
- * Title:        DV Record<P>
+ * Title:        DATAVALIDATION Record (0x01BE)<p/>
  * Description:  This record stores data validation settings and a list of cell ranges
  *               which contain these settings. The data validation settings of a sheet
  *               are stored in a sequential list of DV records. This list is followed by
@@ -36,7 +36,7 @@ import org.apache.poi.util.StringUtil;
  * @author Dragos Buleandra (dragos.buleandra@trade2b.ro)
  * @version 2.0-pre
  */
-public class DVRecord extends Record
+public final class DVRecord extends Record
 {
     public final static short sid = 0x01BE;
 
@@ -170,11 +170,6 @@ public class DVRecord extends Record
        this.field_not_used_1 = in.readShort();
 
        //read first formula data condition
-       // Not sure if this was needed or not...
-//       try {
-//        in.skip(this.field_size_first_formula);
-//       } catch(IOException e) { throw new IllegalStateException(e); } 
-
        int token_pos = 0;
        while (token_pos < this.field_size_first_formula)
        {
@@ -187,14 +182,14 @@ public class DVRecord extends Record
        this.field_not_used_2 = in.readShort();
 
        //read sec formula data condition
-       //Not sure if this was needed or not...
-       try {
-           in.skip(this.field_size_sec_formula);
-       } catch(IOException e) {
-           e.printStackTrace();
-           throw new IllegalStateException(e.getMessage());
+       if (false) { // TODO - prior to bug 44710 this 'skip' was being executed. write a junit to confirm this fix
+           try {
+               in.skip(this.field_size_sec_formula);
+           } catch(IOException e) {
+               e.printStackTrace();
+               throw new IllegalStateException(e.getMessage());
+           }
        }
-
        token_pos = 0;
        while (token_pos < this.field_size_sec_formula)
        {
@@ -516,7 +511,7 @@ public class DVRecord extends Record
 
     /**@todo DVRecord = Serializare */
 
-    private class StringHandler
+    private static final class StringHandler
     {
         private int     _string_length       = 0x0001;
         private byte    _string_unicode_flag = 0x00;
index 16093ee582dfd9a4fb25e032bc29f5ce9830e95c..f45b79b003a88c86a513334731ea2c8f3863ae98 100644 (file)
@@ -29,12 +29,10 @@ import org.apache.poi.hssf.util.Region;
  */
 public final class CellRange
 {
-       /** 
-        * max index for both row and column<p/>
-        * 
-        * Note - this value converts to <tt>-1</tt> when cast to a <tt>short</tt> 
-        */
-       private static final int MAX_INDEX = Integer.MAX_VALUE;
+       /** max 65536 rows in BIFF8 */
+       private static final int LAST_ROW_INDEX = 0x00FFFF; 
+       /** max 256 columns in BIFF8 */
+       private static final int LAST_COLUMN_INDEX = 0x00FF;
 
        private static final Region[] EMPTY_REGION_ARRAY = { };
        
@@ -57,54 +55,46 @@ public final class CellRange
                                        + ", " + firstColumn + ", " + lastColumn + ")");
                }
                _firstRow = firstRow;
-               _lastRow = convertM1ToMax(lastRow);
+               _lastRow = convertM1ToMax(lastRow, LAST_ROW_INDEX);
                _firstColumn = firstColumn;
-               _lastColumn = convertM1ToMax(lastColumn);
+               _lastColumn = convertM1ToMax(lastColumn, LAST_COLUMN_INDEX);
        }
        
-       private static int convertM1ToMax(int lastIx) {
+       /** 
+        * Range arithmetic is easier when using a large positive number for 'max row or column' 
+        * instead of <tt>-1</tt>. 
+        */
+       private static int convertM1ToMax(int lastIx, int maxIndex) {
                if(lastIx < 0) {
-                       return MAX_INDEX;
-               }
-               return lastIx;
-       }
-       private static int convertMaxToM1(int lastIx) {
-               if(lastIx == MAX_INDEX) {
-                       return -1;
+                       return maxIndex;
                }
                return lastIx;
        }
 
        public boolean isFullColumnRange() {
-               return _firstColumn == 0 && _lastColumn == MAX_INDEX;
+               return _firstRow == 0 && _lastRow == LAST_ROW_INDEX;
        }
        public boolean isFullRowRange() {
-               return _firstRow == 0 && _lastRow == MAX_INDEX;
+               return _firstColumn == 0 && _lastColumn == LAST_COLUMN_INDEX;
        }
        
-       public CellRange(Region r) {
-               this(r.getRowFrom(), r.getRowTo(), r.getColumnFrom(), r.getColumnTo());
+       private static CellRange createFromRegion(Region r) {
+               return new CellRange(r.getRowFrom(), r.getRowTo(), r.getColumnFrom(), r.getColumnTo());
        }
 
-       
-       
        private static boolean isValid(int firstRow, int lastRow, int firstColumn, int lastColumn)
        {
-               if(lastRow == -1) {
-                       if(firstRow !=0) {
-                               return false;
-                       }
+               if(lastRow < 0 || lastRow > LAST_ROW_INDEX) {
+                       return false;
                }
-               if(firstRow < 0 || lastRow < -1) {
+               if(firstRow < 0 || firstRow > LAST_ROW_INDEX) {
                        return false;
                }
                
-               if(lastColumn == -1) {
-                       if(firstColumn !=0) {
-                               return false;
-                       }
+               if(lastColumn < 0 || lastColumn > LAST_COLUMN_INDEX) {
+                       return false;
                }
-               if(firstColumn < 0 || lastColumn < -1) {
+               if(firstColumn < 0 || firstColumn > LAST_COLUMN_INDEX) {
                        return false;
                }
                return true;
@@ -114,23 +104,17 @@ public final class CellRange
        {
                return _firstRow;
        }
-       /**
-        * @return <tt>-1</tt> for whole column ranges
-        */
        public int getLastRow()
        {
-               return convertMaxToM1(_lastRow);
+               return _lastRow;
        }
        public int getFirstColumn()
        {
                return _firstColumn;
        }
-       /**
-        * @return <tt>-1</tt> for whole row ranges
-        */
        public int getLastColumn()
        {
-               return convertMaxToM1(_lastColumn);
+               return _lastColumn;
        }
        
        public static final int NO_INTERSECTION = 1;
@@ -374,7 +358,7 @@ public final class CellRange
                CellRange[] result = new CellRange[regions.length];
                for( int i=0; i<regions.length; i++)
                {
-                       result[i] = new CellRange(regions[i]);
+                       result[i] = createFromRegion(regions[i]);
                }
                return result;
        }
@@ -404,10 +388,8 @@ public final class CellRange
 
                
        private Region convertToRegion() {
-               int lastRow = convertMaxToM1(_lastRow);
-               int lastColumn = convertMaxToM1(_lastColumn);
                
-               return new Region(_firstRow, (short)_firstColumn, lastRow, (short)lastColumn);
+               return new Region(_firstRow, (short)_firstColumn, _lastRow, (short)_lastColumn);
        }
 
 
index 237fbf094f20c231cce044f7401d33e259493c14..590b455c4716267790689ba849b8f12b99419abb 100644 (file)
 169    COUNTA  0       30      V       R               \r
 183    PRODUCT 0       30      V       R               \r
 184    FACT    1       1       V       V               \r
+189    DPRODUCT        3       3       V       R R R           \r
 190    ISNONTEXT       1       1       V       V               \r
-191    DPRODUCT        3       3       V       R R R           \r
 193    STDEVP  1       30      V       R               \r
 194    VARP    1       30      V       R               \r
 195    DSTDEVP 3       3       V       R R R           \r
index fe03755079c2eb1da3507466e293ff30da82d542..b250285ac91a3b4e2ad55ca70a2af78d07e13b93 100644 (file)
@@ -424,6 +424,15 @@ public class RichTextRun {
         return paragraphStyle == null ? 0 : paragraphStyle.getReservedField();
     }
 
+    /**
+     * Sets indentation level
+     *
+     * @param level indentation level. Must be in the range [0, 5]
+     */
+    public void setIndentLevel(int level) {
+        if(paragraphStyle != null ) paragraphStyle.setReservedField((short)level);
+    }
+
     /**
      * Sets whether this rich text run has bullets
      */
index bf9b0cc2369e4de84f2cb0d880ccf004dc201c95..d708a5c1daf31f8ba73675101c1b77f17075c336 100644 (file)
@@ -23,6 +23,7 @@ import org.apache.poi.hssf.record.*;
 import org.apache.poi.hssf.record.formula.Area3DPtg;
 
 import java.util.ArrayList;
+import java.util.Iterator;
 import java.util.List;
 import java.util.Stack;
 
@@ -33,6 +34,15 @@ import java.util.Stack;
  */
 public class HSSFChart
 {
+       private ChartRecord chartRecord;
+       private SeriesRecord seriesRecord;
+       
+       private ChartTitleFormatRecord chartTitleFormat;
+       private SeriesTextRecord chartTitleText;
+       
+       private HSSFChart(ChartRecord chartRecord) {
+               this.chartRecord = chartRecord;
+       }
 
     /**
      * Creates a bar chart.  API needs some work. :)
@@ -107,6 +117,74 @@ public class HSSFChart
         sheet.insertChartRecords( records );
         workbook.insertChartRecord();
     }
+    
+    /**
+     * Returns all the charts for the given sheet.
+     * 
+     * NOTE:  Does not yet work...  checking it in just so others
+     * can take a look.
+     */
+    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();
+               System.err.println(r);
+               
+               if(r instanceof DrawingRecord) {
+                       DrawingRecord dr = (DrawingRecord)r;
+               }
+               
+               if(r instanceof ChartRecord) {
+                       lastChart = new HSSFChart((ChartRecord)r);
+                       charts.add(lastChart);
+               }
+               if(r instanceof SeriesRecord) {
+                       lastChart.seriesRecord = (SeriesRecord)r;
+               }
+               if(r instanceof ChartTitleFormatRecord) {
+                       lastChart.chartTitleFormat =
+                               (ChartTitleFormatRecord)r;
+               }
+               if(r instanceof SeriesTextRecord) {
+                       lastChart.chartTitleText =
+                               (SeriesTextRecord)r;
+               }
+       }
+       
+       return (HSSFChart[])
+               charts.toArray( new HSSFChart[charts.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()
     {
diff --git a/src/scratchpad/testcases/org/apache/poi/hssf/usermodel/TestHSSFChart.java b/src/scratchpad/testcases/org/apache/poi/hssf/usermodel/TestHSSFChart.java
new file mode 100644 (file)
index 0000000..2a069c3
--- /dev/null
@@ -0,0 +1,61 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+package org.apache.poi.hssf.usermodel;
+
+import java.io.File;
+import java.io.FileInputStream;
+
+import junit.framework.TestCase;
+
+public class TestHSSFChart extends TestCase {
+       private String dirName;
+
+       protected void setUp() throws Exception {
+               dirName = System.getProperty("HSSF.testdata.path");
+       }
+
+       public void testSingleChart() throws Exception {
+               
+       }
+
+       public void testTwoCharts() throws Exception {
+               
+       }
+
+       public void BROKENtestThreeCharts() throws Exception {
+               HSSFWorkbook wb = new HSSFWorkbook(
+                               new FileInputStream(new File(dirName, "WithThreeCharts.xls"))
+               );
+               
+               HSSFSheet s1 = wb.getSheetAt(0);
+               HSSFSheet s2 = wb.getSheetAt(1);
+               HSSFSheet s3 = wb.getSheetAt(2);
+               
+               assertEquals(0, HSSFChart.getSheetCharts(s1).length);
+               assertEquals(2, HSSFChart.getSheetCharts(s2).length);
+               assertEquals(1, HSSFChart.getSheetCharts(s3).length);
+               
+               HSSFChart[] charts;
+               
+               charts = HSSFChart.getSheetCharts(s2);
+               assertNull(charts[0].getChartTitle());
+               assertEquals("Pie Chart Title Thingy", charts[1].getChartTitle());
+               
+               charts = HSSFChart.getSheetCharts(s3);
+               assertEquals("Sheet 3 Chart with Title", charts[1].getChartTitle());
+       }
+}
diff --git a/src/testcases/org/apache/poi/hpsf/data/Test_Humor-Generation.ppt b/src/testcases/org/apache/poi/hpsf/data/Test_Humor-Generation.ppt
new file mode 100644 (file)
index 0000000..e5763cc
Binary files /dev/null and b/src/testcases/org/apache/poi/hpsf/data/Test_Humor-Generation.ppt differ
diff --git a/src/testcases/org/apache/poi/hssf/data/WithThreeCharts.xls b/src/testcases/org/apache/poi/hssf/data/WithThreeCharts.xls
new file mode 100755 (executable)
index 0000000..157bf33
Binary files /dev/null and b/src/testcases/org/apache/poi/hssf/data/WithThreeCharts.xls differ
diff --git a/src/testcases/org/apache/poi/hssf/data/WithThreeCharts.xlsx b/src/testcases/org/apache/poi/hssf/data/WithThreeCharts.xlsx
new file mode 100755 (executable)
index 0000000..e7398e2
Binary files /dev/null and b/src/testcases/org/apache/poi/hssf/data/WithThreeCharts.xlsx differ
diff --git a/src/testcases/org/apache/poi/hssf/data/colwidth.xls b/src/testcases/org/apache/poi/hssf/data/colwidth.xls
new file mode 100755 (executable)
index 0000000..7ffd3a4
Binary files /dev/null and b/src/testcases/org/apache/poi/hssf/data/colwidth.xls differ
index 71f874370ffe246151e5ed0b07a5a6f3b13d641b..4a68472450d05e10e9947ac06d505f2944726e8a 100644 (file)
Binary files a/src/testcases/org/apache/poi/hssf/data/missingFuncs44675.xls and b/src/testcases/org/apache/poi/hssf/data/missingFuncs44675.xls differ
index 32b16cf6561b99a478460b72bc71f565d10af936..78128dbe19621e320ba4211b048aa5e54c116565 100755 (executable)
 
 package org.apache.poi.hssf.record;
 
-import org.apache.poi.hssf.record.aggregates.AllRecordAggregateTests;
-import org.apache.poi.hssf.record.formula.AllFormulaTests;
-import org.apache.poi.hssf.record.formula.functions.AllIndividualFunctionEvaluationTests;
-
 import junit.framework.Test;
 import junit.framework.TestSuite;
 
+import org.apache.poi.hssf.record.aggregates.AllRecordAggregateTests;
+import org.apache.poi.hssf.record.cf.TestCellRange;
+import org.apache.poi.hssf.record.formula.AllFormulaTests;
+
 /**
  * Collects all tests for package <tt>org.apache.poi.hssf.record</tt>.
  * 
@@ -104,6 +104,7 @@ public final class AllRecordTests {
                result.addTestSuite(TestUnicodeString.class);
                result.addTestSuite(TestUnitsRecord.class);
                result.addTestSuite(TestValueRangeRecord.class);
+               result.addTestSuite(TestCellRange.class);
                return result;
        }
 }
index 2a6faaccdd9c83d10161fdaf77ccfb8f381f6f35..e883503674bf5bcaf9d743a0a826911145c1f182 100644 (file)
@@ -17,6 +17,7 @@
 
 package org.apache.poi.hssf.record;
 
+import junit.framework.AssertionFailedError;
 import junit.framework.TestCase;
 
 import org.apache.poi.hssf.record.cf.CellRange;
@@ -34,8 +35,8 @@ public final class TestCFHeaderRecord extends TestCase
        {
                CFHeaderRecord record = new CFHeaderRecord();
                CellRange[] ranges = {
-                       new CellRange(0,-1,5,5),
-                       new CellRange(0,-1,6,6),
+                       new CellRange(0,0xFFFF,5,5),
+                       new CellRange(0,0xFFFF,6,6),
                        new CellRange(0,1,0,1),
                        new CellRange(0,1,2,3),
                        new CellRange(2,3,0,1),
@@ -46,7 +47,7 @@ public final class TestCFHeaderRecord extends TestCase
                assertEquals(6,ranges.length);
                CellRange enclosingCellRange = record.getEnclosingCellRange();
                assertEquals(0, enclosingCellRange.getFirstRow());
-               assertEquals(-1, enclosingCellRange.getLastRow());
+               assertEquals(65535, enclosingCellRange.getLastRow());
                assertEquals(0, enclosingCellRange.getFirstColumn());
                assertEquals(6, enclosingCellRange.getLastColumn());
                record.setNeedRecalculation(true);
@@ -56,7 +57,7 @@ public final class TestCFHeaderRecord extends TestCase
        }
        
        public void testSerialization() {
-               byte[] recordData = new byte[]
+               byte[] recordData = 
                {
                        (byte)0x03, (byte)0x00,
                        (byte)0x01,     (byte)0x00,
@@ -66,7 +67,7 @@ public final class TestCFHeaderRecord extends TestCase
                        (byte)0x00,     (byte)0x00,
                        (byte)0x03,     (byte)0x00,
                        
-                       (byte)0x04,     (byte)0x00,
+                       (byte)0x04,     (byte)0x00, // nRegions
                        
                        (byte)0x00,     (byte)0x00,
                        (byte)0x01,     (byte)0x00,
@@ -93,44 +94,88 @@ public final class TestCFHeaderRecord extends TestCase
 
                assertEquals("#CFRULES", 3, record.getNumberOfConditionalFormats());
                assertTrue(record.getNeedRecalculation());
-               CellRange enclosingCellRange = record.getEnclosingCellRange();
-               assertEquals(0, enclosingCellRange.getFirstRow());
-               assertEquals(3, enclosingCellRange.getLastRow());
-               assertEquals(0, enclosingCellRange.getFirstColumn());
-               assertEquals(3, enclosingCellRange.getLastColumn());
+               confirm(record.getEnclosingCellRange(), 0, 3, 0, 3);
                CellRange[] ranges = record.getCellRanges();
-               CellRange range0 = ranges[0];
-               assertEquals(0, range0.getFirstRow());
-               assertEquals(1, range0.getLastRow());
-               assertEquals(0, range0.getFirstColumn());
-               assertEquals(1, range0.getLastColumn());
-               CellRange range1 = ranges[1];
-               assertEquals(0, range1.getFirstRow());
-               assertEquals(1, range1.getLastRow());
-               assertEquals(2, range1.getFirstColumn());
-               assertEquals(3, range1.getLastColumn());
-               CellRange range2 = ranges[2];
-               assertEquals(2, range2.getFirstRow());
-               assertEquals(3, range2.getLastRow());
-               assertEquals(0, range2.getFirstColumn());
-               assertEquals(1, range2.getLastColumn());
-               CellRange range3 = ranges[3];
-               assertEquals(2, range3.getFirstRow());
-               assertEquals(3, range3.getLastRow());
-               assertEquals(2, range3.getFirstColumn());
-               assertEquals(3, range3.getLastColumn());
+               assertEquals(4, ranges.length);
+               confirm(ranges[0], 0, 1, 0, 1);
+               confirm(ranges[1], 0, 1, 2, 3);
+               confirm(ranges[2], 2, 3, 0, 1);
+               confirm(ranges[3], 2, 3, 2, 3);
                assertEquals(recordData.length+4, record.getRecordSize());
 
                byte[] output = record.serialize();
 
                assertEquals("Output size", recordData.length+4, output.length); //includes sid+recordlength
 
-               for (int i = 0; i < recordData.length;i++) 
+               for (int i = 0; i < recordData.length; i++) 
                {
                        assertEquals("CFHeaderRecord doesn't match", recordData[i], output[i+4]);
                }
        }
        
+       public void testExtremeRows() {
+               byte[] recordData = {
+                       (byte)0x13, (byte)0x00, // nFormats
+                       (byte)0x00,     (byte)0x00,
+                       
+                       (byte)0x00,     (byte)0x00,
+                       (byte)0xFF,     (byte)0xFF,
+                       (byte)0x00,     (byte)0x00,
+                       (byte)0xFF,     (byte)0x00,
+                       
+                       (byte)0x03,     (byte)0x00, // nRegions
+                       
+                       (byte)0x40,     (byte)0x9C,
+                       (byte)0x50,     (byte)0xC3,
+                       (byte)0x02,     (byte)0x00,
+                       (byte)0x02,     (byte)0x00,
+                       
+                       (byte)0x00,     (byte)0x00,
+                       (byte)0xFF,     (byte)0xFF,
+                       (byte)0x05,     (byte)0x00,
+                       (byte)0x05,     (byte)0x00,
+                       
+                       (byte)0x07,     (byte)0x00,
+                       (byte)0x07,     (byte)0x00,
+                       (byte)0x00,     (byte)0x00,
+                       (byte)0xFF,     (byte)0x00,
+               };
+
+               CFHeaderRecord record;
+               try {
+                       record = new CFHeaderRecord(new TestcaseRecordInputStream(CFHeaderRecord.sid, (short)recordData.length, recordData));
+               } catch (IllegalArgumentException e) {
+                       if(e.getMessage().equals("invalid cell range (-25536, 2, -15536, 2)")) {
+                               throw new AssertionFailedError("Identified bug 44739b");
+                       }
+                       throw e;
+               }
+
+               assertEquals("#CFRULES", 19, record.getNumberOfConditionalFormats());
+               assertFalse(record.getNeedRecalculation());
+               confirm(record.getEnclosingCellRange(), 0, 65535, 0, 255);
+               CellRange[] ranges = record.getCellRanges();
+               assertEquals(3, ranges.length);
+               confirm(ranges[0], 40000, 50000, 2, 2);
+               confirm(ranges[1], 0, 65535, 5, 5);
+               confirm(ranges[2], 7, 7, 0, 255);
+
+               byte[] output = record.serialize();
+
+               assertEquals("Output size", recordData.length+4, output.length); //includes sid+recordlength
+
+               for (int i = 0; i < recordData.length;i++) {
+                       assertEquals("CFHeaderRecord doesn't match", recordData[i], output[i+4]);
+               }
+       }
+       
+
+       private static void confirm(CellRange cr, int expFirstRow, int expLastRow, int expFirstCol, int expLastColumn) {
+               assertEquals("first row", expFirstRow, cr.getFirstRow());
+               assertEquals("last row", expLastRow, cr.getLastRow());
+               assertEquals("first column", expFirstCol, cr.getFirstColumn());
+               assertEquals("last column", expLastColumn, cr.getLastColumn());
+       }
 
        public static void main(String[] ignored_args)
        {
index ade097e6979e786252f1a930a89c7f6bc2032dea..2ba196d55a189951c0ffda48ac00702f0de2a8b3 100644 (file)
@@ -17,62 +17,76 @@ limitations under the License.
 
 package org.apache.poi.hssf.record.cf;
 
+import junit.framework.AssertionFailedError;
 import junit.framework.TestCase;
 
 /**
  * Tests CellRange operations.
  */
-public class TestCellRange extends TestCase
+public final class TestCellRange extends TestCase
 {
-       private static final CellRange biggest     = new CellRange( 0, -1, 0,-1);
-       private static final CellRange tenthColumn = new CellRange( 0, -1,10,10);
-       private static final CellRange tenthRow    = new CellRange(10, 10, 0,-1);
-       private static final CellRange box10x10    = new CellRange( 0, 10, 0,10);
-       private static final CellRange box9x9      = new CellRange( 0,  9, 0, 9);
-       private static final CellRange box10to20c  = new CellRange( 0, 10,10,20);
-       private static final CellRange oneCell     = new CellRange(10, 10,10,10);
+       private static final CellRange biggest     = createCR( 0, -1, 0,-1);
+       private static final CellRange tenthColumn = createCR( 0, -1,10,10);
+       private static final CellRange tenthRow    = createCR(10, 10, 0,-1);
+       private static final CellRange box10x10    = createCR( 0, 10, 0,10);
+       private static final CellRange box9x9      = createCR( 0,  9, 0, 9);
+       private static final CellRange box10to20c  = createCR( 0, 10,10,20);
+       private static final CellRange oneCell     = createCR(10, 10,10,10);
 
-       boolean [][] contanis = new boolean[][]
+       private static final CellRange[] sampleRanges = {
+               biggest, tenthColumn, tenthRow, box10x10, box9x9, box10to20c, oneCell,
+       };
+       
+       /** cross-reference of <tt>contains()</tt> operations for sampleRanges against itself */
+       private static final boolean [][] containsExpectedResults = 
     {
-                       //           biggest, tenthColumn, tenthRow, box10x10, box9x9, box10to20c, oneCell
-  /*biggest    */ new boolean[]{true,       true ,    true ,    true ,  true ,      true ,  true},     
-  /*tenthColumn*/ new boolean[]{false,      true ,    false,    false,  false,      false,  true},     
-  /*tenthRow   */ new boolean[]{false,      false,    true ,    false,  false,      false,  true},     
-  /*box10x10   */ new boolean[]{false,      false,    false,    true ,  true ,      false,  true},     
-  /*box9x9     */ new boolean[]{false,      false,    false,    false,  true ,      false, false},     
-  /*box10to20c */ new boolean[]{false,      false,    false,    false,  false,      true ,  true},     
-  /*oneCell    */ new boolean[]{false,      false,    false,    false,  false,      false,  true},     
+       //               biggest, tenthColumn, tenthRow, box10x10, box9x9, box10to20c, oneCell
+       /*biggest    */ {true,       true ,    true ,    true ,    true ,      true ,  true},   
+       /*tenthColumn*/ {false,      true ,    false,    false,    false,      false,  true},   
+       /*tenthRow   */ {false,      false,    true ,    false,    false,      false,  true},   
+       /*box10x10   */ {false,      false,    false,    true ,    true ,      false,  true},   
+       /*box9x9     */ {false,      false,    false,    false,    true ,      false, false},   
+       /*box10to20c */ {false,      false,    false,    false,    false,      true ,  true},   
+       /*oneCell    */ {false,      false,    false,    false,    false,      false,  true},   
      } ;
-       
-       
-       public void testContainsMethod()
-       {
-               CellRange [] ranges = new CellRange[]{biggest,tenthColumn,tenthRow,box10x10,box9x9,box10to20c,oneCell};
-               testContainsMethod(contanis,ranges);
+
+       /**
+        * @param lastRow pass -1 for max row index 
+        * @param lastCol pass -1 for max col index
+        */
+       private static CellRange createCR(int firstRow, int lastRow, int firstCol, int lastCol) {
+               // max row & max col limit as per BIFF8
+               return new CellRange(
+                               firstRow, 
+                               lastRow == -1 ? 0xFFFF : lastRow, 
+                               firstCol,
+                               lastCol == -1 ? 0x00FF : lastCol);
        }
        
-       private void testContainsMethod(boolean[][]contains,CellRange[] ranges)
+       public void testContainsMethod()
        {
+               CellRange [] ranges = sampleRanges;
                for(int i=0; i!=ranges.length;i++)
                {
                        for(int j=0; j!=ranges.length;j++)
                        {
-                               assertEquals("("+i+","+j+"): ",contains[i][j],ranges[i].contains(ranges[j]));
+                               boolean expectedResult = containsExpectedResults[i][j];
+                               assertEquals("("+i+","+j+"): ", expectedResult, ranges[i].contains(ranges[j]));
                        }
                }
        }
 
-       private static final CellRange col1     = new CellRange( 0, -1, 1,1);
-       private static final CellRange col2     = new CellRange( 0, -1, 2,2);
-       private static final CellRange row1     = new CellRange( 1,  1, 0,-1);
-       private static final CellRange row2     = new CellRange( 2,  2, 0,-1);
+       private static final CellRange col1     = createCR( 0, -1, 1,1);
+       private static final CellRange col2     = createCR( 0, -1, 2,2);
+       private static final CellRange row1     = createCR( 1,  1, 0,-1);
+       private static final CellRange row2     = createCR( 2,  2, 0,-1);
 
-       private static final CellRange box0     = new CellRange( 0, 2, 0,2);
-       private static final CellRange box1     = new CellRange( 0, 1, 0,1);
-       private static final CellRange box2     = new CellRange( 0, 1, 2,3);
-       private static final CellRange box3     = new CellRange( 2, 3, 0,1);
-       private static final CellRange box4     = new CellRange( 2, 3, 2,3);
-       private static final CellRange box5     = new CellRange( 1, 3, 1,3);
+       private static final CellRange box0     = createCR( 0, 2, 0,2);
+       private static final CellRange box1     = createCR( 0, 1, 0,1);
+       private static final CellRange box2     = createCR( 0, 1, 2,3);
+       private static final CellRange box3     = createCR( 2, 3, 0,1);
+       private static final CellRange box4     = createCR( 2, 3, 2,3);
+       private static final CellRange box5     = createCR( 1, 3, 1,3);
 
        public void testHasSharedBorderMethod()
        {
@@ -119,8 +133,8 @@ public class TestCellRange extends TestCase
 
        public void testIntersectMethod()
        {
-               assertEquals( CellRange.OVERLAP,box0.intersect(box5));
-               assertEquals( CellRange.OVERLAP,box5.intersect(box0));
+               assertEquals(CellRange.OVERLAP,box0.intersect(box5));
+               assertEquals(CellRange.OVERLAP,box5.intersect(box0));
                assertEquals(CellRange.NO_INTERSECTION,box1.intersect(box4));
                assertEquals(CellRange.NO_INTERSECTION,box4.intersect(box1));
                assertEquals(CellRange.NO_INTERSECTION,box2.intersect(box3));
@@ -135,4 +149,31 @@ public class TestCellRange extends TestCase
                assertEquals(CellRange.INSIDE,tenthColumn.intersect(tenthColumn));
                assertEquals(CellRange.INSIDE,tenthRow.intersect(tenthRow));
        }
+       
+       /**
+        * Cell ranges like the following are valid
+        * =$C:$IV,$B$1:$B$8,$B$10:$B$65536,$A:$A
+        */
+       public void testCreate() {
+               CellRange cr;
+               
+               cr = createCR(0, -1, 2, 255); // $C:$IV
+               confirmRange(cr, false, true);
+               cr = createCR(0, 7, 1, 1); // $B$1:$B$8
+               
+               try {
+                       cr = createCR(9, -1, 1, 1); // $B$65536
+               } catch (IllegalArgumentException e) {
+                       if(e.getMessage().startsWith("invalid cell range")) {
+                               throw new AssertionFailedError("Identified bug 44739");
+                       }
+                       throw e;
+               }
+               cr = createCR(0, -1, 0, 0); // $A:$A
+       }
+
+       private static void confirmRange(CellRange cr, boolean isFullRow, boolean isFullColumn) {
+               assertEquals("isFullRowRange", isFullRow, cr.isFullRowRange());
+               assertEquals("isFullColumnRange", isFullColumn, cr.isFullColumnRange());
+       }
 }
index 645709bb6e355e79fff7023b7f8dea005ffa8116..3a704502230367f8bc7a7fcaebd254415cf076cf 100644 (file)
@@ -29,7 +29,7 @@ import junit.framework.TestSuite;
  * 
  * @author Josh Micich
  */
-public class AllFormulaTests {
+public final class AllFormulaTests {
        
        public static Test suite() {
                TestSuite result = new TestSuite(AllFormulaTests.class.getName());
@@ -50,7 +50,6 @@ public class AllFormulaTests {
                result.addTestSuite(TestReferencePtg.class);
                result.addTestSuite(TestSheetNameFormatter.class);
                result.addTestSuite(TestUnionPtg.class);
-               result.addTest(AllFormulaFunctionTests.suite());
                return result;
        }
 }
index 3671d37c1a8382f1b835696d345eaf366711c0ae..fdad5f44d8f9ef7c8788e105af648404066ad15d 100644 (file)
@@ -27,6 +27,9 @@ import org.apache.poi.hssf.record.formula.FuncPtg;
 import org.apache.poi.hssf.record.formula.FuncVarPtg;
 import org.apache.poi.hssf.record.formula.Ptg;
 /**
+ * Tests parsing of some built-in functions that were not properly
+ * registered in POI as bug #44675, #44733 (March/April 2008).
+ * 
  * @author Josh Micich
  */
 public final class TestParseMissingBuiltInFuncs extends TestCase {
@@ -39,6 +42,7 @@ public final class TestParseMissingBuiltInFuncs extends TestCase {
                Ptg[] ptgs = parse(formula);
                Ptg ptgF = ptgs[ptgs.length-1];  // func is last RPN token in all these formulas
                
+               // Check critical things in the Ptg array encoding.
                if(!(ptgF instanceof AbstractFunctionPtg)) {
                    throw new RuntimeException("function token missing");
                }
@@ -47,11 +51,15 @@ public final class TestParseMissingBuiltInFuncs extends TestCase {
                        throw new AssertionFailedError("Failed to recognise built-in function in formula '" 
                                        + formula + "'");
                }
-               
                assertEquals(expPtgArraySize, ptgs.length);
                assertEquals(funcIx, func.getFunctionIndex());
                Class expCls = isVarArgFunc ? FuncVarPtg.class : FuncPtg.class;
                assertEquals(expCls, ptgF.getClass());
+               
+               // check that parsed Ptg array converts back to formula text OK
+               Workbook book = Workbook.createWorkbook();
+               String reRenderedFormula = FormulaParser.toFormulaString(book, ptgs);
+               assertEquals(formula, reRenderedFormula);
        }
        
        public void testDatedif() {
@@ -76,4 +84,7 @@ public final class TestParseMissingBuiltInFuncs extends TestCase {
        public void testIsnontext() {
                confirmFunc("ISNONTEXT(\"abc\")", 2, false, 190);
        }
+       public void testDproduct() {
+               confirmFunc("DPRODUCT(C1:E5,\"HarvestYield\",G1:H2)", 4, false, 189);
+       }
 }
index f1e6bcfacf22d35eae424d8ee48c4ebccfc01764..14799bd0a77ed0467aa97e583ece3e3e8dd8c2dd 100644 (file)
@@ -21,7 +21,9 @@ import java.io.File;
 import java.io.FileInputStream;
 import java.io.IOException;
 import java.io.InputStream;
+import java.lang.reflect.InvocationTargetException;
 
+import org.apache.poi.hssf.record.RecordFormatException;
 import org.apache.poi.hssf.usermodel.HSSFSheet;
 import org.apache.poi.hssf.usermodel.HSSFWorkbook;
 
@@ -29,24 +31,31 @@ import junit.framework.AssertionFailedError;
 import junit.framework.TestCase;
 /**
  * Tests reading from a sample spreadsheet some built-in functions that were not properly
- * registered in POI as bug #44675 (March 2008).
+ * registered in POI as bug #44675, #44733 (March/April 2008).
  * 
  * @author Josh Micich
  */
 public final class TestReadMissingBuiltInFuncs extends TestCase {
 
-       private HSSFSheet sht;
+       /**
+        * This spreadsheet has examples of calls to the interesting built-in functions in cells A1:A7
+        */
+       private static final String SAMPLE_SPREADSHEET_FILE_NAME = "missingFuncs44675.xls";
+       private static HSSFSheet _sheet;
 
-       protected void setUp() {
-               String cwd = System.getProperty("HSSF.testdata.path");
-               HSSFWorkbook wb;
-               try {
-                       InputStream is = new FileInputStream(new File(cwd, "missingFuncs44675.xls"));
-                       wb = new HSSFWorkbook(is);
-               } catch (IOException e) {
-                       throw new RuntimeException(e);
+       private static HSSFSheet getSheet() {
+               if (_sheet == null) {
+                       String cwd = System.getProperty("HSSF.testdata.path");
+                       HSSFWorkbook wb;
+                       try {
+                               InputStream is = new FileInputStream(new File(cwd, SAMPLE_SPREADSHEET_FILE_NAME));
+                               wb = new HSSFWorkbook(is);
+                       } catch (IOException e) {
+                               throw new RuntimeException(e);
+                       }
+                       _sheet = wb.getSheetAt(0);
                }
-               sht = wb.getSheetAt(0);
+               return _sheet;
        }
 
        public void testDatedif() {
@@ -128,9 +137,30 @@ public final class TestReadMissingBuiltInFuncs extends TestCase {
                }
                assertEquals("ISNONTEXT(\"abc\")", formula);
        }
+       public void testDproduct() {
+               
+               String formula = getCellFormula(6);
+               assertEquals("DPRODUCT(C1:E5,\"HarvestYield\",G1:H2)", formula);
+       }
 
        private String getCellFormula(int rowIx) {
-               String result = sht.getRow(rowIx).getCell((short)0).getCellFormula();
+               HSSFSheet sheet;
+               try {
+                       sheet = getSheet();
+               } catch (RecordFormatException e) {
+                       if(e.getCause() instanceof InvocationTargetException) {
+                               InvocationTargetException ite = (InvocationTargetException) e.getCause();
+                               if(ite.getTargetException() instanceof RuntimeException) {
+                                       RuntimeException re = (RuntimeException) ite.getTargetException();
+                                       if(re.getMessage().equals("Invalid built-in function index (189)")) {
+                                               throw afe("DPRODUCT() registered with wrong index");
+                                       }
+                               }
+                       }
+                       // some other unexpected error
+                       throw e;
+               }
+               String result = sheet.getRow(rowIx).getCell((short)0).getCellFormula();
                if (false) {
                        System.err.println(result);
                }
index cbc555da36abda243b5c6b589c54793b7c9c152a..6d6b053a63d8f1e23f9c5d1d9abe4392344fd543 100755 (executable)
@@ -40,6 +40,7 @@ public class AllUserModelTests {
                result.addTestSuite(TestFormulas.class);
                result.addTestSuite(TestHSSFCell.class);
                result.addTestSuite(TestHSSFClientAnchor.class);
+               result.addTestSuite(TestHSSFConditionalFormatting.class);
                result.addTestSuite(TestHSSFComment.class);
                result.addTestSuite(TestHSSFDateUtil.class);
                result.addTestSuite(TestHSSFHeaderFooter.class);
diff --git a/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFConditionalFormatting.java b/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFConditionalFormatting.java
new file mode 100644 (file)
index 0000000..5dcc61a
--- /dev/null
@@ -0,0 +1,90 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+package org.apache.poi.hssf.usermodel;
+
+import junit.framework.TestCase;
+
+import org.apache.poi.hssf.record.CFRuleRecord.ComparisonOperator;
+import org.apache.poi.hssf.util.HSSFColor;
+import org.apache.poi.hssf.util.Region;
+/**
+ * 
+ * @author Dmitriy Kumshayev
+ */
+public final class TestHSSFConditionalFormatting extends TestCase
+{
+       public void testLastAndFirstColumns() 
+       {
+               HSSFWorkbook workbook = new HSSFWorkbook();
+               HSSFSheet sheet = workbook.createSheet();
+               String formula = "7";
+
+               HSSFFontFormatting fontFmt = new HSSFFontFormatting();
+               fontFmt.setFontStyle(true, false);
+
+               HSSFBorderFormatting bordFmt = new HSSFBorderFormatting();
+               bordFmt.setBorderBottom(HSSFBorderFormatting.BORDER_THIN);
+               bordFmt.setBorderTop(HSSFBorderFormatting.BORDER_THICK);
+               bordFmt.setBorderLeft(HSSFBorderFormatting.BORDER_DASHED);
+               bordFmt.setBorderRight(HSSFBorderFormatting.BORDER_DOTTED);
+
+               HSSFPatternFormatting patternFmt = new HSSFPatternFormatting();
+               patternFmt.setFillBackgroundColor(HSSFColor.RED.index);
+
+               HSSFConditionalFormattingRule [] cfRules =
+               {
+                       sheet.createConditionalFormattingRule(formula, fontFmt, bordFmt, patternFmt),
+                       sheet.createConditionalFormattingRule(ComparisonOperator.BETWEEN, "1", "2", fontFmt, bordFmt, patternFmt)
+               };
+
+               short col = 1;
+               Region [] regions =
+               {
+                       new Region(0,col,65535,col)
+               };
+
+               sheet.addConditionalFormatting(regions, cfRules);
+               sheet.addConditionalFormatting(regions, cfRules);
+
+               // Verification
+               assertEquals(2, sheet.getNumConditionalFormattings());
+               sheet.removeConditionalFormatting(1);
+               assertEquals(1, sheet.getNumConditionalFormattings());
+               HSSFConditionalFormatting cf = sheet.getConditionalFormattingAt(0);
+               assertNotNull(cf);
+
+               regions = cf.getFormattingRegions();
+               assertNotNull(regions);
+               assertEquals(1, regions.length);
+               Region r = regions[0];
+               assertEquals(1, r.getColumnFrom());
+               assertEquals(1, r.getColumnTo());
+               assertEquals(0, r.getRowFrom());
+               assertEquals(65535, r.getRowTo());
+
+               assertEquals(2, cf.getNumberOfRules());
+
+               HSSFConditionalFormattingRule rule1 = cf.getRule(0);
+               assertEquals("7",rule1.getFormula1()); 
+               assertNull(rule1.getFormula2());
+
+               HSSFConditionalFormattingRule rule2 = cf.getRule(1);
+               assertEquals("2",rule2.getFormula2()); 
+               assertEquals("1",rule2.getFormula1()); 
+       }
+}
diff --git a/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFConfditionalFormatting.java b/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFConfditionalFormatting.java
deleted file mode 100644 (file)
index 6186d22..0000000
+++ /dev/null
@@ -1,90 +0,0 @@
-/* ====================================================================
-   Licensed to the Apache Software Foundation (ASF) under one or more
-   contributor license agreements.  See the NOTICE file distributed with
-   this work for additional information regarding copyright ownership.
-   The ASF licenses this file to You under the Apache License, Version 2.0
-   (the "License"); you may not use this file except in compliance with
-   the License.  You may obtain a copy of the License at
-
-       http://www.apache.org/licenses/LICENSE-2.0
-
-   Unless required by applicable law or agreed to in writing, software
-   distributed under the License is distributed on an "AS IS" BASIS,
-   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-   See the License for the specific language governing permissions and
-   limitations under the License.
-==================================================================== */
-
-package org.apache.poi.hssf.usermodel;
-
-import junit.framework.TestCase;
-
-import org.apache.poi.hssf.record.CFRuleRecord.ComparisonOperator;
-import org.apache.poi.hssf.util.HSSFColor;
-import org.apache.poi.hssf.util.Region;
-/**
- * 
- * @author Dmitriy Kumshayev
- */
-public final class TestHSSFConfditionalFormatting extends TestCase
-{
-       public void testLastAndFirstColumns() 
-       {
-               HSSFWorkbook workbook = new HSSFWorkbook();
-               HSSFSheet sheet = workbook.createSheet();
-               String formula = "7";
-
-               HSSFFontFormatting fontFmt = new HSSFFontFormatting();
-               fontFmt.setFontStyle(true, false);
-
-               HSSFBorderFormatting bordFmt = new HSSFBorderFormatting();
-               bordFmt.setBorderBottom(HSSFBorderFormatting.BORDER_THIN);
-               bordFmt.setBorderTop(HSSFBorderFormatting.BORDER_THICK);
-               bordFmt.setBorderLeft(HSSFBorderFormatting.BORDER_DASHED);
-               bordFmt.setBorderRight(HSSFBorderFormatting.BORDER_DOTTED);
-
-               HSSFPatternFormatting patternFmt = new HSSFPatternFormatting();
-               patternFmt.setFillBackgroundColor(HSSFColor.RED.index);
-
-               HSSFConditionalFormattingRule [] cfRules =
-               {
-                       sheet.createConditionalFormattingRule(formula, fontFmt, bordFmt, patternFmt),
-                       sheet.createConditionalFormattingRule(ComparisonOperator.BETWEEN, "1", "2", fontFmt, bordFmt, patternFmt)
-               };
-
-               short col = 1;
-               Region [] regions =
-               {
-                       new Region(0,col,-1,col)
-               };
-
-               sheet.addConditionalFormatting(regions, cfRules);
-               sheet.addConditionalFormatting(regions, cfRules);
-
-               // Verification
-               assertEquals(2, sheet.getNumConditionalFormattings());
-               sheet.removeConditionalFormatting(1);
-               assertEquals(1, sheet.getNumConditionalFormattings());
-               HSSFConditionalFormatting cf = sheet.getConditionalFormattingAt(0);
-               assertNotNull(cf);
-
-               regions = cf.getFormattingRegions();
-               assertNotNull(regions);
-               assertEquals(1, regions.length);
-               Region r = regions[0];
-               assertEquals(1, r.getColumnFrom());
-               assertEquals(1, r.getColumnTo());
-               assertEquals(0, r.getRowFrom());
-               assertEquals(-1, r.getRowTo());
-
-               assertEquals(2, cf.getNumberOfRules());
-
-               HSSFConditionalFormattingRule rule1 = cf.getRule(0);
-               assertEquals("7",rule1.getFormula1()); 
-               assertNull(rule1.getFormula2());
-
-               HSSFConditionalFormattingRule rule2 = cf.getRule(1);
-               assertEquals("2",rule2.getFormula2()); 
-               assertEquals("1",rule2.getFormula1()); 
-       }
-}
index a4a31feabf93fc380714136a96367e8c49b3abc8..13eafa4fd89b6bf0b7495e55f15baad5ef45aff6 100644 (file)
@@ -870,5 +870,65 @@ public class TestHSSFSheet
     
     public static void main(java.lang.String[] args) {
                 junit.textui.TestRunner.run(TestHSSFSheet.class);
-       }    
+       }
+
+    public void testColumnWidth() throws Exception {
+        //check we can correctly read column widths from a reference workbook
+        String filename = System.getProperty("HSSF.testdata.path") + "/colwidth.xls";
+        HSSFWorkbook wb = new HSSFWorkbook(new FileInputStream(filename));
+
+        //reference values
+        int[] ref = {365, 548, 731, 914, 1097, 1280, 1462, 1645, 1828, 2011, 2194, 2377, 2560, 2742, 2925, 3108, 3291, 3474, 3657};
+
+        HSSFSheet sh = wb.getSheetAt(0);
+        for (char i = 'A'; i <= 'S'; i++) {
+            int idx = i - 'A';
+            int w = sh.getColumnWidth((short)idx);
+            assertEquals(ref[idx], w);
+        }
+
+        //the second sheet doesn't have overridden column widths
+        sh = wb.getSheetAt(1);
+        int def_width = sh.getDefaultColumnWidth();
+        for (char i = 'A'; i <= 'S'; i++) {
+            int idx = i - 'A';
+            int w = sh.getColumnWidth((short)idx);
+            //getDefaultColumnWidth returns width measued in characters
+            //getColumnWidth returns width measued in 1/256th units
+            assertEquals(def_width*256, w);
+        }
+
+        //test new workbook
+        wb = new HSSFWorkbook();
+        sh = wb.createSheet();
+        sh.setDefaultColumnWidth((short)10);
+        assertEquals(10, sh.getDefaultColumnWidth());
+        assertEquals(256*10, sh.getColumnWidth((short)0));
+        assertEquals(256*10, sh.getColumnWidth((short)1));
+        assertEquals(256*10, sh.getColumnWidth((short)2));
+        for (char i = 'D'; i <= 'F'; i++) {
+            short w = (short)(256*12);
+            sh.setColumnWidth((short)i, w);
+            assertEquals(w, sh.getColumnWidth((short)i));
+        }
+
+        //serialize and read again
+        ByteArrayOutputStream out = new ByteArrayOutputStream();
+        wb.write(out);
+        out.close();
+
+        wb = new HSSFWorkbook(new ByteArrayInputStream(out.toByteArray()));
+        sh = wb.getSheetAt(0);
+        assertEquals(10, sh.getDefaultColumnWidth());
+        //columns A-C have default width
+        assertEquals(256*10, sh.getColumnWidth((short)0));
+        assertEquals(256*10, sh.getColumnWidth((short)1));
+        assertEquals(256*10, sh.getColumnWidth((short)2));
+        //columns D-F have custom wodth
+        for (char i = 'D'; i <= 'F'; i++) {
+            short w = (short)(256*12);
+            assertEquals(w, sh.getColumnWidth((short)i));
+        }
+
+    }
 }