<action dev="POI-DEVELOPERS" type="add">Created a common interface for handling Excel files, irrespective of if they are .xls or .xlsx</action>
</release>
<release version="3.1-beta2" date="2008-05-??">
+ <action dev="POI-DEVELOPERS" type="fix">44523 - fixed workbook sheet selection and focus</action>
+ <action dev="POI-DEVELOPERS" type="fix">45000 - Fixed NPE in ListLevel when numberText is null</action>
+ <action dev="POI-DEVELOPERS" type="fix">44985 - Properly update TextSpecInfoAtom when the parent text is changed</action>
+ <action dev="POI-DEVELOPERS" type="fix">41187 - fixed HSSFSheet to properly read xls files without ROW records</action>
+ <action dev="POI-DEVELOPERS" type="fix">44950 - fixed HSSFFormulaEvaluator.evaluateInCell() and Area3DEval.getValue() also added validation for number of elements in AreaEvals</action>
<action dev="POI-DEVELOPERS" type="fix">42570 - fixed LabelRecord to use empty string instead of null when the length is zero.</action>
<action dev="POI-DEVELOPERS" type="fix">42564 - fixed ArrayPtg to use ConstantValueParser. Fixed a few other ArrayPtg encoding issues.</action>
<action dev="POI-DEVELOPERS" type="fix">Follow-on from 28754 - StringPtg.toFormulaString() should escape double quotes</action>
<action dev="POI-DEVELOPERS" type="add">Created a common interface for handling Excel files, irrespective of if they are .xls or .xlsx</action>
</release>
<release version="3.1-beta2" date="2008-05-??">
+ <action dev="POI-DEVELOPERS" type="fix">44523 - fixed workbook sheet selection and focus</action>
+ <action dev="POI-DEVELOPERS" type="fix">45000 - Fixed NPE in ListLevel when numberText is null</action>
+ <action dev="POI-DEVELOPERS" type="fix">44985 - Properly update TextSpecInfoAtom when the parent text is changed</action>
+ <action dev="POI-DEVELOPERS" type="fix">41187 - fixed HSSFSheet to properly read xls files without ROW records</action>
+ <action dev="POI-DEVELOPERS" type="fix">44950 - fixed HSSFFormulaEvaluator.evaluateInCell() and Area3DEval.getValue() also added validation for number of elements in AreaEvals</action>
<action dev="POI-DEVELOPERS" type="fix">42570 - fixed LabelRecord to use empty string instead of null when the length is zero.</action>
<action dev="POI-DEVELOPERS" type="fix">42564 - fixed ArrayPtg to use ConstantValueParser. Fixed a few other ArrayPtg encoding issues.</action>
<action dev="POI-DEVELOPERS" type="fix">Follow-on from 28754 - StringPtg.toFormulaString() should escape double quotes</action>
3. Checkout the tagged version\r
{code}\r
cd tags\r
-svn checkout https://svn.apache.org/repos/asf/poi/tags/TAG\r
+svn checkout https://svn.apache.org/repos/asf/poi/tags/$TAG\r
{code}\r
\r
4. Merge (if required)\r
\r
{code}\r
cd $TAG\r
-$ svn merge https://svn.apache.org/repos/asf/poi/tags/TAG \\r
+$ svn merge https://svn.apache.org/repos/asf/poi/tags/$TAG \\r
https://svn.apache.org/repos/asf/poi/trunk\r
{code}\r
\r
-
/* ====================================================================
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
limitations under the License.
==================================================================== */
-
package org.apache.poi.hssf.model;
import org.apache.poi.hssf.record.*;
* @see org.apache.poi.hssf.usermodel.HSSFSheet
* @version 1.0-pre
*/
-
-public class Sheet implements Model
-{
+public final class Sheet implements Model {
public static final short LeftMargin = 0;
public static final short RightMargin = 1;
public static final short TopMargin = 2;
protected ObjectProtectRecord objprotect = null;
protected ScenarioProtectRecord scenprotect = null;
protected PasswordRecord password = null;
- protected List condFormatting = new ArrayList();;
+ protected List condFormatting = new ArrayList();
- /** Add an UncalcedRecord if not true indicating formulas have not been calculated */
+ /** Add an UncalcedRecord if not true indicating formulas have not been calculated */
protected boolean uncalced = false;
public static final byte PANE_LOWER_RIGHT = (byte)0;
public static final byte PANE_UPPER_LEFT = (byte)3;
/**
- * Creates new Sheet with no intialization --useless at this point
+ * Creates new Sheet with no initialization --useless at this point
* @see #createSheet(List,int,int)
*/
public Sheet()
}
}
else if (rec.getSid() == UncalcedRecord.sid) {
- retval.uncalced = true;
+ retval.uncalced = true;
}
else if (rec.getSid() == DimensionsRecord.sid)
{
}
else if ( rec.getSid() == CFHeaderRecord.sid )
{
- CFRecordsAggregate cfAgg = CFRecordsAggregate.createCFAggregate(recs, k);
- retval.condFormatting.add(cfAgg);
- rec = cfAgg;
+ 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;
+ // Skip it since it is processed by CFRecordsAggregate
+ rec = null;
}
else if (rec.getSid() == ColumnInfoRecord.sid)
{
if ( isfirstrow )
{
retval.rows = new RowRecordsAggregate();
- rec = retval.rows;
+ rec = retval.rows;
isfirstrow = false;
}
retval.rows.insertRow(row);
else if ( rec.getSid() == GridsetRecord.sid )
{
retval.gridset = (GridsetRecord) rec;
- }
+ }
else if ( rec.getSid() == HeaderRecord.sid && bofEofNestingLevel == 1)
{
retval.header = (HeaderRecord) rec;
{
rec = null;
}
-
- else if ( rec.getSid() == ProtectRecord.sid )
- {
- retval.protect = (ProtectRecord) rec;
- }
- else if ( rec.getSid() == ObjectProtectRecord.sid )
- {
- retval.objprotect = (ObjectProtectRecord) rec;
- }
- else if ( rec.getSid() == ScenarioProtectRecord.sid )
- {
- retval.scenprotect = (ScenarioProtectRecord) rec;
- }
- else if ( rec.getSid() == PasswordRecord.sid )
- {
- retval.password = (PasswordRecord) rec;
- }
- else if (rec.getSid() == PageBreakRecord.HORIZONTAL_SID)
- {
- retval.rowBreaks = (PageBreakRecord)rec;
- }
- else if (rec.getSid() == PageBreakRecord.VERTICAL_SID)
- {
- retval.colBreaks = (PageBreakRecord)rec;
- }
-
+
+ else if ( rec.getSid() == ProtectRecord.sid )
+ {
+ retval.protect = (ProtectRecord) rec;
+ }
+ else if ( rec.getSid() == ObjectProtectRecord.sid )
+ {
+ retval.objprotect = (ObjectProtectRecord) rec;
+ }
+ else if ( rec.getSid() == ScenarioProtectRecord.sid )
+ {
+ retval.scenprotect = (ScenarioProtectRecord) rec;
+ }
+ else if ( rec.getSid() == PasswordRecord.sid )
+ {
+ retval.password = (PasswordRecord) rec;
+ }
+ else if (rec.getSid() == PageBreakRecord.HORIZONTAL_SID)
+ {
+ retval.rowBreaks = (PageBreakRecord)rec;
+ }
+ else if (rec.getSid() == PageBreakRecord.VERTICAL_SID)
+ {
+ retval.colBreaks = (PageBreakRecord)rec;
+ }
+
if (rec != null)
{
records.add(rec);
/**
* 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
- * can be added to a sheet. The <b>Record</b> object does not implement cloneable.
+ * can be added to a sheet. The <b>Record</b> object does not implement cloneable.
* When adding a new record, implement a public clone method if and only if the record
- * belongs to a sheet.
+ * belongs to a sheet.
*/
public Sheet cloneSheet()
{
ValueRecordsAggregate vrAgg = (ValueRecordsAggregate)rec;
for (Iterator cellIter = vrAgg.getIterator();cellIter.hasNext();) {
Record valRec = (Record)cellIter.next();
-
+
if (valRec instanceof FormulaRecordAggregate) {
FormulaRecordAggregate fmAgg = (FormulaRecordAggregate)valRec;
Record fmAggRec = fmAgg.getFormulaRecord();
records.add(retval.rowBreaks);
retval.colBreaks = new PageBreakRecord(PageBreakRecord.VERTICAL_SID);
records.add(retval.colBreaks);
-
+
retval.header = (HeaderRecord) retval.createHeader();
- records.add( retval.header );
+ records.add( retval.header );
retval.footer = (FooterRecord) retval.createFooter();
records.add( retval.footer );
records.add( retval.createHCenter() );
retval.dimsloc = records.size()-1;
records.add(retval.windowTwo = retval.createWindowTwo());
retval.setLoc(records.size() - 1);
- retval.selection =
+ retval.selection =
(SelectionRecord) retval.createSelection();
records.add(retval.selection);
- retval.protect = (ProtectRecord) retval.createProtect();
- records.add(retval.protect);
+ retval.protect = (ProtectRecord) retval.createProtect();
+ records.add(retval.protect);
records.add(retval.createEOF());
}
}
- //public int addMergedRegion(short rowFrom, short colFrom, short rowTo,
- public int addMergedRegion(int rowFrom, short colFrom, int rowTo,
- short colTo)
- {
- // Validate input
- if(rowTo < rowFrom) {
- throw new IllegalArgumentException("The row to ("+rowTo+") must be >= the row from ("+rowFrom+")");
- }
- if(colTo < colFrom) {
- throw new IllegalArgumentException("The col to ("+colTo+") must be >= the col from ("+colFrom+")");
- }
-
+ public int addMergedRegion(int rowFrom, short colFrom, int rowTo, short colTo) {
+ // Validate input
+ if (rowTo < rowFrom) {
+ throw new IllegalArgumentException("The 'to' row (" + rowTo
+ + ") must not be less than the 'from' row (" + rowFrom + ")");
+ }
+ if (colTo < colFrom) {
+ throw new IllegalArgumentException("The 'to' col (" + colTo
+ + ") must not be less than the 'from' col (" + colFrom + ")");
+ }
+
if (merged == null || merged.getNumAreas() == 1027)
{
merged = ( MergeCellsRecord ) createMergedCells();
- mergedRecords.add(merged);
+ mergedRecords.add(merged);
records.add(records.size() - 1, merged);
}
merged.addArea(rowFrom, colFrom, rowTo, colTo);
- return numMergedRegions++;
+ return numMergedRegions++;
}
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();
+ startNumRegions = numMergedRegions - merged.getNumAreas();
}
else
{
pos = n;
break;
}
- startNumRegions += record.getNumAreas();
+ startNumRegions += record.getNumAreas();
}
}
numMergedRegions--;
if (rec.getNumAreas() == 0)
{
- mergedRecords.remove(pos);
- //get rid of the record from the sheet
- records.remove(merged);
+ 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;
- }
+ //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;
+ }
}
}
}
//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 = n;
break;
}
- startNumRegions += record.getNumAreas();
+ startNumRegions += record.getNumAreas();
}
}
return ((MergeCellsRecord) mergedRecords.get(pos)).getAreaAt(index - startNumRegions);
// 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;
+ // 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)
{
- int index = findConditionalFormattingPosition();
- records.add(index, cfAggregate);
- condFormatting.add(cfAggregate);
- return condFormatting.size()-1;
+ int index = findConditionalFormattingPosition();
+ records.add(index, cfAggregate);
+ condFormatting.add(cfAggregate);
+ return condFormatting.size()-1;
}
public void removeConditionalFormatting(int index)
{
if (index >= 0 && index <= condFormatting.size()-1 )
{
- CFRecordsAggregate cfAggregate = getCFRecordsAggregateAt(index);
- records.remove(cfAggregate);
- condFormatting.remove(index);
+ 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 (CFRecordsAggregate) condFormatting.get(index);
}
return null;
}
-
+
public int getNumConditionalFormattings()
{
- return condFormatting.size();
+ return condFormatting.size();
}
/**
*
* @see org.apache.poi.hssf.record.DimensionsRecord
*/
-
- //public void setDimensions(short firstrow, short firstcol, short lastrow,
public void setDimensions(int firstrow, short firstcol, int lastrow,
short lastcol)
{
/**
* set the locator for where we should look for the next value record. The
- * algorythm will actually start here and find the correct location so you
+ * algorithm will actually start here and find the correct location so you
* can set this to 0 and watch performance go down the tubes but it will work.
* After a value is set this is automatically advanced. Its also set by the
* create method. So you probably shouldn't mess with this unless you have
for (int k = 0; k < records.size(); k++)
{
Record record = (( Record ) records.get(k));
-
+
// Don't write out UncalcedRecord entries, as
// we handle those specially just below
if (record instanceof UncalcedRecord) {
- continue;
+ continue;
}
-
+
// Once the rows have been found in the list of records, start
// writing out the blocked row information. This includes the DBCell references
if (record instanceof RowRecordsAggregate) {
} else {
pos += record.serialize(pos, data ); // rec.length;
}
-
+
// If the BOF record was just serialized then add the IndexRecord
if (record.getSid() == BOFRecord.sid) {
// Add an optional UncalcedRecord
if (uncalced) {
- UncalcedRecord rec = new UncalcedRecord();
- pos += rec.serialize(pos, data);
+ UncalcedRecord rec = new UncalcedRecord();
+ pos += rec.serialize(pos, data);
}
//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.
log.log(POILogger.DEBUG, "Sheet.serialize returning ");
return pos-offset;
}
-
+
private int serializeIndexRecord(final int BOFRecordIndex, final int offset, byte[] data) {
IndexRecord index = new IndexRecord();
index.setFirstRow(rows.getFirstRowNum());
}
return index.serialize(offset, data);
}
-
+
/**
* Create a row record. (does not add it to the records contained in this sheet)
* @return LabelSSTRecord newly created containing your SST Index, row,col.
* @see org.apache.poi.hssf.record.SSTRecord
*/
-
- //public LabelSSTRecord createLabelSST(short row, short col, int index)
public LabelSSTRecord createLabelSST(int row, short col, int index)
{
log.logFormatted(POILogger.DEBUG, "create labelsst row,col,index %,%,%",
*
* @return NumberRecord for that row, col containing that value as added to the sheet
*/
-
- //public NumberRecord createNumber(short row, short col, double value)
public NumberRecord createNumber(int row, short col, double value)
{
log.logFormatted(POILogger.DEBUG, "create number row,col,value %,%,%",
});
NumberRecord rec = new NumberRecord();
- //rec.setRow(( short ) row);
rec.setRow(row);
rec.setColumn(col);
rec.setValue(value);
* @param row - the row the BlankRecord is a member of
* @param col - the column the BlankRecord is a member of
*/
-
- //public BlankRecord createBlank(short row, short col)
public BlankRecord createBlank(int row, short col)
{
- //log.logFormatted(POILogger.DEBUG, "create blank row,col %,%", new short[]
log.logFormatted(POILogger.DEBUG, "create blank row,col %,%", new int[]
{
row, col
});
BlankRecord rec = new BlankRecord();
- //rec.setRow(( short ) row);
rec.setRow(row);
rec.setColumn(col);
rec.setXFIndex(( short ) 0x0f);
* @param formula - a String representing the formula. To be parsed to PTGs
* @return bogus/useless formula record
*/
-
- //public FormulaRecord createFormula(short row, short col, String formula)
public FormulaRecord createFormula(int row, short col, String formula)
{
log.logFormatted(POILogger.DEBUG, "create formula row,col,formula %,%,%",
- //new short[]
new int[]
{
row, col
* @param row the row to add the cell value to
* @param col the cell value record itself.
*/
-
- //public void addValueRecord(short row, CellValueRecordInterface col)
public void addValueRecord(int row, CellValueRecordInterface col)
{
checkCells();
d.setFirstCol(col.getColumn());
}
cells.insertCell(col);
-
- /*
- * for (int k = loc; k < records.size(); k++)
- * {
- * Record rec = ( Record ) records.get(k);
- *
- * if (rec.getSid() == RowRecord.sid)
- * {
- * RowRecord rowrec = ( RowRecord ) rec;
- *
- * if (rowrec.getRowNumber() == col.getRow())
- * {
- * records.add(k + 1, col);
- * loc = k;
- * if (rowrec.getLastCol() <= col.getColumn())
- * {
- * rowrec.setLastCol((( short ) (col.getColumn() + 1)));
- * }
- * break;
- * }
- * }
- * }
- */
}
/**
* @param col - a record supporting the CellValueRecordInterface.
* @see org.apache.poi.hssf.record.CellValueRecordInterface
*/
-
- //public void removeValueRecord(short row, CellValueRecordInterface col)
public void removeValueRecord(int row, CellValueRecordInterface col)
{
checkCells();
new int[]{row, dimsloc} );
loc = dimsloc;
cells.removeCell(col);
-
- /*
- * for (int k = loc; k < records.size(); k++)
- * {
- * Record rec = ( Record ) records.get(k);
- *
- * // checkDimsLoc(rec,k);
- * if (rec.isValue())
- * {
- * CellValueRecordInterface cell =
- * ( CellValueRecordInterface ) rec;
- *
- * if ((cell.getRow() == col.getRow())
- * && (cell.getColumn() == col.getColumn()))
- * {
- * records.remove(k);
- * break;
- * }
- * }
- * }
- */
}
/**
//The ValueRecordsAggregate use a tree map underneath.
//The tree Map uses the CellValueRecordInterface as both the
//key and the value, if we dont do a remove, then
- //the previous instance of the key is retained, effectively using
+ //the previous instance of the key is retained, effectively using
//double the memory
cells.removeCell(newval);
cells.insertCell(newval);
-
- /*
- * CellValueRecordInterface oldval = getNextValueRecord();
- *
- * while (oldval != null)
- * {
- * if (oldval.isEqual(newval))
- * {
- * records.set(( short ) (getLoc() - 1), newval);
- * return;
- * }
- * oldval = getNextValueRecord();
- * }
- * addValueRecord(newval.getRow(), newval);
- * setLoc(dimsloc);
- */
}
/**
rows.insertRow(row);
- /*
- * for (int k = loc; k < records.size(); k++)
- * {
- * Record rec = ( Record ) records.get(k);
- *
- * if (rec.getSid() == IndexRecord.sid)
- * {
- * index = ( IndexRecord ) rec;
- * }
- * if (rec.getSid() == RowRecord.sid)
- * {
- * RowRecord rowrec = ( RowRecord ) rec;
- *
- * if (rowrec.getRowNumber() > row.getRowNumber())
- * {
- * records.add(k, row);
- * loc = k;
- * break;
- * }
- * }
- * if (rec.getSid() == WindowTwoRecord.sid)
- * {
- * records.add(k, row);
- * loc = k;
- * break;
- * }
- * }
- * if (index != null)
- * {
- * if (index.getLastRowAdd1() <= row.getRowNumber())
- * {
- * index.setLastRowAdd1(row.getRowNumber() + 1);
- * }
- * }
- */
if (log.check( POILogger.DEBUG ))
log.log(POILogger.DEBUG, "exit addRow");
}
public void removeRow(RowRecord row)
{
checkRows();
- // IndexRecord index = null;
setLoc(getDimsLoc());
rows.removeRow(row);
-
- /*
- * for (int k = loc; k < records.size(); k++)
- * {
- * Record rec = ( Record ) records.get(k);
- *
- * // checkDimsLoc(rec,k);
- * if (rec.getSid() == RowRecord.sid)
- * {
- * RowRecord rowrec = ( RowRecord ) rec;
- *
- * if (rowrec.getRowNumber() == row.getRowNumber())
- * {
- * records.remove(k);
- * break;
- * }
- * }
- * if (rec.getSid() == WindowTwoRecord.sid)
- * {
- * break;
- * }
- * }
- */
}
/**
return null;
}
return ( CellValueRecordInterface ) valueRecIterator.next();
-
- /*
- * if (this.getLoc() < records.size())
- * {
- * for (int k = getLoc(); k < records.size(); k++)
- * {
- * Record rec = ( Record ) records.get(k);
- *
- * this.setLoc(k + 1);
- * if (rec instanceof CellValueRecordInterface)
- * {
- * return ( CellValueRecordInterface ) rec;
- * }
- * }
- * }
- * return null;
- */
- }
-
- /**
- * get the NEXT RowRecord or CellValueRecord(from LOC). The first record that
- * is a Row record or CellValueRecord(starting at LOC) will be returned.
- * <P>
- * This method is "loc" sensitive. Meaning you need to set LOC to where you
- * want it to start searching. If you don't know do this: setLoc(getDimsLoc).
- * When adding several rows you can just start at the last one by leaving loc
- * at what this sets it to. For this method, set loc to dimsloc to start with.
- * subsequent calls will return rows in (physical) sequence or NULL when you get to the end.
- *
- * @return RowRecord representing the next row record or CellValueRecordInterface
- * representing the next cellvalue or NULL if there are no more
- * @see #setLoc(int)
- *
- */
-
-/* public Record getNextRowOrValue()
- {
- POILogger.DEBUG((new StringBuffer("getNextRow loc= ")).append(loc)
- .toString());
- if (this.getLoc() < records.size())
- {
- for (int k = this.getLoc(); k < records.size(); k++)
- {
- Record rec = ( Record ) records.get(k);
-
- this.setLoc(k + 1);
- if (rec.getSid() == RowRecord.sid)
- {
- return rec;
- }
- else if (rec.isValue())
- {
- return rec;
- }
- }
- }
- return null;
}
- */
/**
* get the NEXT RowRecord (from LOC). The first record that is a Row record
return null;
}
return ( RowRecord ) rowRecIterator.next();
-
-/* if (this.getLoc() < records.size())
- {
- for (int k = this.getLoc(); k < records.size(); k++)
- {
- Record rec = ( Record ) records.get(k);
-
- this.setLoc(k + 1);
- if (rec.getSid() == RowRecord.sid)
- {
- return ( RowRecord ) rec;
- }
- }
- }*/
}
/**
* @see #setLoc(int)
*
*/
-
- //public RowRecord getRow(short rownum)
- public RowRecord getRow(int rownum)
- {
+ public RowRecord getRow(int rownum) {
if (log.check( POILogger.DEBUG ))
log.log(POILogger.DEBUG, "getNextRow loc= " + loc);
return rows.getRow(rownum);
-
- /*
- * if (this.getLoc() < records.size())
- * {
- * for (int k = this.getLoc(); k < records.size(); k++)
- * {
- * Record rec = ( Record ) records.get(k);
- *
- * this.setLoc(k + 1);
- * if (rec.getSid() == RowRecord.sid)
- * {
- * if ((( RowRecord ) rec).getRowNumber() == rownum)
- * {
- * return ( RowRecord ) rec;
- * }
- * }
- * }
- * }
- */
-
- // return null;
}
/**
retval.setVersion(( short ) 0x600);
retval.setType(( short ) 0x010);
- // retval.setBuild((short)0x10d3);
retval.setBuild(( short ) 0x0dbb);
retval.setBuildYear(( short ) 1996);
retval.setHistoryBitMask(0xc1);
* @see org.apache.poi.hssf.record.ColumnInfoRecord
* @return record containing a ColumnInfoRecord
*/
-
+ // TODO change return type to ColumnInfoRecord
protected Record createColInfo()
{
return ColumnInfoRecordsAggregate.createColInfo();
public boolean isGridsPrinted()
{
- if (gridset == null) {
- gridset = (GridsetRecord)createGridset();
- //Insert the newlycreated Gridset record at the end of the record (just before the EOF)
- int loc = findFirstRecordLocBySid(EOFRecord.sid);
- records.add(loc, gridset);
- }
+ if (gridset == null) {
+ gridset = (GridsetRecord)createGridset();
+ //Insert the newlycreated Gridset record at the end of the record (just before the EOF)
+ int loc = findFirstRecordLocBySid(EOFRecord.sid);
+ records.add(loc, gridset);
+ }
return !gridset.getGridset();
}
}
return retval;
}
-
+
/**
- * get the index to the ExtendedFormatRecord "associated" with
- * the column at specified 0-based index. (In this case, an
- * ExtendedFormatRecord index is actually associated with a
+ * get the index to the ExtendedFormatRecord "associated" with
+ * the column at specified 0-based index. (In this case, an
+ * ExtendedFormatRecord index is actually associated with a
* ColumnInfoRecord which spans 1 or more columns)
* <br/>
* Returns the index to the default ExtendedFormatRecord (0xF)
* if no ColumnInfoRecord exists that includes the column
- * index specified.
+ * index specified.
* @param column
* @return index of ExtendedFormatRecord associated with
* ColumnInfoRecord that includes the column index or the
retval.setNumRefs(( short ) 0x0);
return retval;
}
-
- public short getTopRow()
+
+ public short getTopRow()
{
- return (windowTwo==null) ? (short) 0 : windowTwo.getTopRow();
+ return (windowTwo==null) ? (short) 0 : windowTwo.getTopRow();
}
-
- public void setTopRow(short topRow)
+
+ public void setTopRow(short topRow)
{
- if (windowTwo!=null)
- {
- windowTwo.setTopRow(topRow);
- }
+ if (windowTwo!=null)
+ {
+ windowTwo.setTopRow(topRow);
+ }
}
-
+
/**
* Sets the left column to show in desktop window pane.
* @param leftCol the left column to show in desktop window pane
*/
public void setLeftCol(short leftCol){
- if (windowTwo!=null)
- {
- windowTwo.setLeftCol(leftCol);
- }
+ if (windowTwo!=null)
+ {
+ windowTwo.setLeftCol(leftCol);
+ }
}
-
- public short getLeftCol()
+
+ public short getLeftCol()
{
- return (windowTwo==null) ? (short) 0 : windowTwo.getLeftCol();
+ return (windowTwo==null) ? (short) 0 : windowTwo.getLeftCol();
}
-
-
-
+
+
+
/**
* Returns the active row
*
}
return selection.getActiveCellRow();
}
-
+
/**
* Sets the active row
*
selection.setActiveCellRow(row);
}
}
-
+
/**
* Returns the active column
*
}
return selection.getActiveCellCol();
}
-
+
/**
* Sets the active column
*
}
// Add space for UncalcedRecord
if (uncalced) {
- retval += UncalcedRecord.getStaticRecordSize();
+ retval += UncalcedRecord.getStaticRecordSize();
}
-
+
return retval;
}
*/
public HeaderRecord getHeader ()
{
- return header;
+ return header;
}
+ public WindowTwoRecord getWindowTwo() {
+ return windowTwo;
+ }
/**
* Sets the HeaderRecord.
* @param newHeader The new HeaderRecord for the sheet.
*/
public void setHeader (HeaderRecord newHeader)
{
- header = newHeader;
+ header = newHeader;
}
/**
*/
public FooterRecord getFooter ()
{
- return footer;
+ return footer;
}
/**
*/
public void setFooter (FooterRecord newFooter)
{
- footer = newFooter;
+ footer = newFooter;
}
/**
*/
public PrintSetupRecord getPrintSetup ()
{
- return printSetup;
+ return printSetup;
}
/**
*/
public void setPrintSetup (PrintSetupRecord newPrintSetup)
{
- printSetup = newPrintSetup;
+ printSetup = newPrintSetup;
}
/**
*/
public PrintGridlinesRecord getPrintGridlines ()
{
- return printGridlines;
+ return printGridlines;
}
/**
*/
public void setPrintGridlines (PrintGridlinesRecord newPrintGridlines)
{
- printGridlines = newPrintGridlines;
+ printGridlines = newPrintGridlines;
}
/**
* @return the size of the margin
*/
public double getMargin(short margin) {
- if (getMargins()[margin] != null)
- return margins[margin].getMargin();
- else {
- switch ( margin )
- {
- case LeftMargin:
- return .75;
- case RightMargin:
- return .75;
- case TopMargin:
- return 1.0;
- case BottomMargin:
- return 1.0;
- default :
- throw new RuntimeException( "Unknown margin constant: " + margin );
- }
- }
+ if (getMargins()[margin] != null)
+ return margins[margin].getMargin();
+ else {
+ switch ( margin )
+ {
+ case LeftMargin:
+ return .75;
+ case RightMargin:
+ return .75;
+ case TopMargin:
+ return 1.0;
+ case BottomMargin:
+ return 1.0;
+ default :
+ throw new RuntimeException( "Unknown margin constant: " + margin );
+ }
+ }
}
/**
* @param size the size of the margin
*/
public void setMargin(short margin, double size) {
- Margin m = getMargins()[margin];
- if (m == null) {
- switch ( margin )
- {
- case LeftMargin:
- m = new LeftMarginRecord();
- records.add( getDimsLoc() + 1, m );
- break;
- case RightMargin:
- m = new RightMarginRecord();
- records.add( getDimsLoc() + 1, m );
- break;
- case TopMargin:
- m = new TopMarginRecord();
- records.add( getDimsLoc() + 1, m );
- break;
- case BottomMargin:
- m = new BottomMarginRecord();
- records.add( getDimsLoc() + 1, m );
- break;
- default :
- throw new RuntimeException( "Unknown margin constant: " + margin );
- }
- margins[margin] = m;
- }
- m.setMargin( size );
+ Margin m = getMargins()[margin];
+ if (m == null) {
+ switch ( margin )
+ {
+ case LeftMargin:
+ m = new LeftMarginRecord();
+ records.add( getDimsLoc() + 1, m );
+ break;
+ case RightMargin:
+ m = new RightMarginRecord();
+ records.add( getDimsLoc() + 1, m );
+ break;
+ case TopMargin:
+ m = new TopMarginRecord();
+ records.add( getDimsLoc() + 1, m );
+ break;
+ case BottomMargin:
+ m = new BottomMarginRecord();
+ records.add( getDimsLoc() + 1, m );
+ break;
+ default :
+ throw new RuntimeException( "Unknown margin constant: " + margin );
+ }
+ margins[margin] = m;
+ }
+ m.setMargin( size );
}
public int getEofLoc()
*/
public void createFreezePane(int colSplit, int rowSplit, int topRow, int leftmostColumn )
{
- int paneLoc = findFirstRecordLocBySid(PaneRecord.sid);
- if (paneLoc != -1)
- records.remove(paneLoc);
-
+ int paneLoc = findFirstRecordLocBySid(PaneRecord.sid);
+ if (paneLoc != -1)
+ records.remove(paneLoc);
+
int loc = findFirstRecordLocBySid(WindowTwoRecord.sid);
PaneRecord pane = new PaneRecord();
pane.setX((short)colSplit);
*/
public void createSplitPane(int xSplitPos, int ySplitPos, int topRow, int leftmostColumn, int activePane )
{
- int paneLoc = findFirstRecordLocBySid(PaneRecord.sid);
- if (paneLoc != -1)
- records.remove(paneLoc);
-
+ int paneLoc = findFirstRecordLocBySid(PaneRecord.sid);
+ if (paneLoc != -1)
+ records.remove(paneLoc);
+
int loc = findFirstRecordLocBySid(WindowTwoRecord.sid);
PaneRecord r = new PaneRecord();
r.setX((short)xSplitPos);
sel.setPane(PANE_LOWER_RIGHT);
}
-
+
/**
* Returns the information regarding the currently configured pane (split or freeze).
* @return null if no pane configured, or the pane information.
PaneRecord rec = (PaneRecord)findFirstRecordBySid(PaneRecord.sid);
if (rec == null)
return null;
-
+
return new PaneInformation(rec.getX(), rec.getY(), rec.getTopRow(),
- rec.getLeftColumn(), (byte)rec.getActivePane(), windowTwo.getFreezePanes());
+ rec.getLeftColumn(), (byte)rec.getActivePane(), windowTwo.getFreezePanes());
}
public SelectionRecord getSelection()
*/
public ProtectRecord getProtect()
{
- if (protect == null) {
- protect = (ProtectRecord)createProtect();
- //Insert the newlycreated protect record at the end of the record (just before the EOF)
- int loc = findFirstRecordLocBySid(EOFRecord.sid);
- records.add(loc, protect);
- }
+ if (protect == null) {
+ protect = (ProtectRecord)createProtect();
+ //Insert the newlycreated protect record at the end of the record (just before the EOF)
+ int loc = findFirstRecordLocBySid(EOFRecord.sid);
+ records.add(loc, protect);
+ }
return protect;
}
*/
public PasswordRecord getPassword()
{
- if (password == null) {
- password = createPassword();
- //Insert the newly created password record at the end of the record (just before the EOF)
- int loc = findFirstRecordLocBySid(EOFRecord.sid);
- records.add(loc, password);
- }
+ if (password == null) {
+ password = createPassword();
+ //Insert the newly created password record at the end of the record (just before the EOF)
+ int loc = findFirstRecordLocBySid(EOFRecord.sid);
+ records.add(loc, password);
+ }
return password;
}
* @return whether gridlines are displayed
*/
public boolean isDisplayGridlines() {
- return windowTwo.getDisplayGridlines();
+ return windowTwo.getDisplayGridlines();
}
/**
* @return whether formulas are displayed
*/
public boolean isDisplayFormulas() {
- return windowTwo.getDisplayFormulas();
+ return windowTwo.getDisplayFormulas();
}
/**
* @return whether RowColHeadings are displayed
*/
public boolean isDisplayRowColHeadings() {
- return windowTwo.getDisplayRowColHeadings();
+ return windowTwo.getDisplayRowColHeadings();
}
-
+
/**
- * @return whether an uncalced record must be inserted or not at generation
- */
- public boolean getUncalced() {
- return uncalced;
- }
- /**
- * @param uncalced whether an uncalced record must be inserted or not at generation
- */
- public void setUncalced(boolean uncalced) {
- this.uncalced = uncalced;
- }
+ * @return whether an uncalced record must be inserted or not at generation
+ */
+ public boolean getUncalced() {
+ return uncalced;
+ }
+ /**
+ * @param uncalced whether an uncalced record must be inserted or not at generation
+ */
+ public void setUncalced(boolean uncalced) {
+ this.uncalced = uncalced;
+ }
- /**
+ /**
* Returns the array of margins. If not created, will create.
*
* @return the array of marings.
protected Margin[] getMargins() {
if (margins == null)
margins = new Margin[4];
- return margins;
+ return margins;
}
/**
boolean noDrawingRecordsFound = (loc == -1);
if (noDrawingRecordsFound)
{
- if(!createIfMissing) {
- // None found, and not allowed to add in
- return -1;
- }
-
+ if(!createIfMissing) {
+ // None found, and not allowed to add in
+ return -1;
+ }
+
EscherAggregate aggregate = new EscherAggregate( drawingManager );
loc = findFirstRecordLocBySid(EscherAggregate.sid);
if (loc == -1)
* @param breaks The page record to be shifted
* @param start Starting "main" value to shift breaks
* @param stop Ending "main" value to shift breaks
- * @param count number of units (rows/columns) to shift by
+ * @param count number of units (rows/columns) to shift by
*/
public void shiftBreaks(PageBreakRecord breaks, short start, short 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;
- boolean inStart = (breakLocation >= start);
- boolean inEnd = (breakLocation <= stop);
- if(inStart && inEnd)
- shiftedBreak.add(breakItem);
- }
-
- iterator = shiftedBreak.iterator();
- while (iterator.hasNext()) {
- PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
- breaks.removeBreak(breakItem.main);
- breaks.addBreak((short)(breakItem.main+count), breakItem.subFrom, breakItem.subTo);
- }
- }
-
+
+ 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;
+ boolean inStart = (breakLocation >= start);
+ boolean inEnd = (breakLocation <= stop);
+ if(inStart && inEnd)
+ shiftedBreak.add(breakItem);
+ }
+
+ iterator = shiftedBreak.iterator();
+ while (iterator.hasNext()) {
+ PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
+ breaks.removeBreak(breakItem.main);
+ breaks.addBreak((short)(breakItem.main+count), breakItem.subFrom, breakItem.subTo);
+ }
+ }
+
/**
* Sets a page break at the indicated row
* @param row
*/
- public void setRowBreak(int row, short fromCol, short toCol) {
- if (rowBreaks == null) {
+ 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);
+ }
+ rowBreaks.addBreak((short)row, fromCol, toCol);
}
/**
* @param row
*/
public void removeRowBreak(int row) {
- if (rowBreaks == null)
- throw new IllegalArgumentException("Sheet does not define any row breaks");
- rowBreaks.removeBreak((short)row);
+ if (rowBreaks == null)
+ throw new IllegalArgumentException("Sheet does not define any row breaks");
+ rowBreaks.removeBreak((short)row);
}
/**
* @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 (rowBreaks == null) ? false : rowBreaks.getBreak((short)row) != null;
}
/**
*
*/
public void setColumnBreak(short column, short fromRow, short toRow) {
- if (colBreaks == null) {
+ if (colBreaks == null) {
int loc = findFirstRecordLocBySid(WindowTwoRecord.sid);
colBreaks = new PageBreakRecord(PageBreakRecord.VERTICAL_SID);
records.add(loc, colBreaks);
- }
- colBreaks.addBreak(column, fromRow, toRow);
+ }
+ colBreaks.addBreak(column, fromRow, toRow);
}
/**
*
*/
public void removeColumnBreak(short column) {
- if (colBreaks == null)
- throw new IllegalArgumentException("Sheet does not define any column breaks");
-
- colBreaks.removeBreak(column);
+ if (colBreaks == null)
+ throw new IllegalArgumentException("Sheet does not define any column breaks");
+
+ colBreaks.removeBreak(column);
}
/**
* @return true if the specified column has a page break
*/
public boolean isColumnBroken(short column) {
- return (colBreaks == null) ? false : colBreaks.getBreak(column) != null;
+ return (colBreaks == null) ? false : colBreaks.getBreak(column) != null;
}
-
+
/**
* Shifts the horizontal page breaks for the indicated count
* @param startingRow
* @param count
*/
public void shiftRowBreaks(int startingRow, int endingRow, int count) {
- shiftBreaks(rowBreaks, (short)startingRow, (short)endingRow, (short)count);
+ shiftBreaks(rowBreaks, (short)startingRow, (short)endingRow, (short)count);
}
/**
* @param count
*/
public void shiftColumnBreaks(short startingCol, short endingCol, short count) {
- shiftBreaks(colBreaks, startingCol, endingCol, count);
+ shiftBreaks(colBreaks, startingCol, endingCol, count);
}
-
+
/**
* Returns all the row page breaks
* @return all the row page breaks
*/
public Iterator getRowBreaks() {
- return rowBreaks.getBreaksIterator();
+ return rowBreaks.getBreaksIterator();
}
-
+
/**
* 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 (rowBreaks == null) ? 0 : (int)rowBreaks.getNumBreaks();
}
-
+
/**
* Returns all the column page breaks
* @return all the column page breaks
*/
public Iterator getColumnBreaks(){
- return colBreaks.getBreaksIterator();
+ return colBreaks.getBreaksIterator();
}
-
+
/**
* 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 (colBreaks == null) ? 0 : (int)colBreaks.getNumBreaks();
}
public void setColumnGroupCollapsed( short columnNumber, boolean collapsed )
records.add(protIdx+2,srec);
scenprotect = srec;
}
- }
+ }
/**
- * unprotect objects in the sheet (will not protect them, but any set to false are
+ * unprotect objects in the sheet (will not protect them, but any set to false are
* unprotected.
* @param sheet is unprotected (false = unprotect)
* @param objects are unprotected (false = unprotect)
* @param scenarios are unprotected (false = unprotect)
*/
public void unprotectSheet( boolean sheet, boolean objects, boolean scenarios ) {
- int protIdx = -1;
+
if (!sheet) {
ProtectRecord prec = getProtect();
prec.setProtect(sheet);
PasswordRecord pass = getPassword();
pass.setPassword((short)00);
- }
+ }
if(objprotect != null && !objects) {
objprotect.setProtect(false);
}
if(scenprotect != null && !scenarios) {
scenprotect.setProtect(false);
}
- }
+ }
/**
* @return {sheet is protected, objects are proteced, scenarios are protected}
*/
public boolean[] isProtected() {
- return new boolean[] { (protect != null && protect.getProtect()),
+ return new boolean[] { (protect != null && protect.getProtect()),
(objprotect != null && objprotect.getProtect()),
(scenprotect != null && scenprotect.getProtect())};
}
-
-// private void collapseColumn( short columnNumber )
-// {
-// int idx = findColumnIdx( columnNumber, 0 );
-// if (idx == -1)
-// return;
-//
-// // Find the start of the group.
-// ColumnInfoRecord columnInfo = (ColumnInfoRecord) columnSizes.get( findStartOfColumnOutlineGroup( idx ) );
-//
-// // Hide all the columns until the end of the group
-// columnInfo = writeHidden( columnInfo, idx, true );
-//
-// // Write collapse field
-// setColumn( (short) ( columnInfo.getLastColumn() + 1 ), null, null, null, Boolean.TRUE);
-// }
-
-// private void expandColumn( short columnNumber )
-// {
-// int idx = findColumnIdx( columnNumber, 0 );
-// if (idx == -1)
-// return;
-//
-// // If it is already exapanded do nothing.
-// if (!isColumnGroupCollapsed(idx))
-// return;
-//
-// // Find the start of the group.
-// int startIdx = findStartOfColumnOutlineGroup( idx );
-// ColumnInfoRecord columnInfo = getColInfo( startIdx );
-//
-// // Find the end of the group.
-// int endIdx = findEndOfColumnOutlineGroup( idx );
-// ColumnInfoRecord endColumnInfo = getColInfo( endIdx );
-//
-// // expand:
-// // colapsed bit must be unset
-// // hidden bit gets unset _if_ surrounding groups are expanded you can determine
-// // this by looking at the hidden bit of the enclosing group. You will have
-// // to look at the start and the end of the current group to determine which
-// // is the enclosing group
-// // hidden bit only is altered for this outline level. ie. don't uncollapse contained groups
-// if (!isColumnGroupHiddenByParent( idx ))
-// {
-// for (int i = startIdx; i <= endIdx; i++)
-// {
-// if (columnInfo.getOutlineLevel() == getColInfo(i).getOutlineLevel())
-// getColInfo(i).setHidden( false );
-// }
-// }
-//
-// // Write collapse field
-// setColumn( (short) ( columnInfo.getLastColumn() + 1 ), null, null, null, Boolean.FALSE);
-// }
-
-// private boolean isColumnGroupCollapsed( int idx )
-// {
-// int endOfOutlineGroupIdx = findEndOfColumnOutlineGroup( idx );
-// if (endOfOutlineGroupIdx >= columnSizes.size())
-// return false;
-// if (getColInfo(endOfOutlineGroupIdx).getLastColumn() + 1 != getColInfo(endOfOutlineGroupIdx + 1).getFirstColumn())
-// return false;
-// else
-// return getColInfo(endOfOutlineGroupIdx+1).getCollapsed();
-// }
-
-// private boolean isColumnGroupHiddenByParent( int idx )
-// {
-// // Look out outline details of end
-// int endLevel;
-// boolean endHidden;
-// int endOfOutlineGroupIdx = findEndOfColumnOutlineGroup( idx );
-// if (endOfOutlineGroupIdx >= columnSizes.size())
-// {
-// endLevel = 0;
-// endHidden = false;
-// }
-// else if (getColInfo(endOfOutlineGroupIdx).getLastColumn() + 1 != getColInfo(endOfOutlineGroupIdx + 1).getFirstColumn())
-// {
-// endLevel = 0;
-// endHidden = false;
-// }
-// else
-// {
-// endLevel = getColInfo( endOfOutlineGroupIdx + 1).getOutlineLevel();
-// endHidden = getColInfo( endOfOutlineGroupIdx + 1).getHidden();
-// }
-//
-// // Look out outline details of start
-// int startLevel;
-// boolean startHidden;
-// int startOfOutlineGroupIdx = findStartOfColumnOutlineGroup( idx );
-// if (startOfOutlineGroupIdx <= 0)
-// {
-// startLevel = 0;
-// startHidden = false;
-// }
-// else if (getColInfo(startOfOutlineGroupIdx).getFirstColumn() - 1 != getColInfo(startOfOutlineGroupIdx - 1).getLastColumn())
-// {
-// startLevel = 0;
-// startHidden = false;
-// }
-// else
-// {
-// startLevel = getColInfo( startOfOutlineGroupIdx - 1).getOutlineLevel();
-// startHidden = getColInfo( startOfOutlineGroupIdx - 1 ).getHidden();
-// }
-//
-// if (endLevel > startLevel)
-// {
-// return endHidden;
-// }
-// else
-// {
-// return startHidden;
-// }
-// }
-
-// private ColumnInfoRecord getColInfo(int idx)
-// {
-// return columns.getColInfo( idx );
-// }
-
-// private int findStartOfColumnOutlineGroup(int idx)
-// {
-// // Find the start of the group.
-// ColumnInfoRecord columnInfo = (ColumnInfoRecord) columnSizes.get( idx );
-// int level = columnInfo.getOutlineLevel();
-// while (idx != 0)
-// {
-// ColumnInfoRecord prevColumnInfo = (ColumnInfoRecord) columnSizes.get( idx - 1 );
-// if (columnInfo.getFirstColumn() - 1 == prevColumnInfo.getLastColumn())
-// {
-// if (prevColumnInfo.getOutlineLevel() < level)
-// {
-// break;
-// }
-// idx--;
-// columnInfo = prevColumnInfo;
-// }
-// else
-// {
-// break;
-// }
-// }
-//
-// return idx;
-// }
-
-// private int findEndOfColumnOutlineGroup(int idx)
-// {
-// // Find the end of the group.
-// ColumnInfoRecord columnInfo = (ColumnInfoRecord) columnSizes.get( idx );
-// int level = columnInfo.getOutlineLevel();
-// while (idx < columnSizes.size() - 1)
-// {
-// ColumnInfoRecord nextColumnInfo = (ColumnInfoRecord) columnSizes.get( idx + 1 );
-// if (columnInfo.getLastColumn() + 1 == nextColumnInfo.getFirstColumn())
-// {
-// if (nextColumnInfo.getOutlineLevel() < level)
-// {
-// break;
-// }
-// idx++;
-// columnInfo = nextColumnInfo;
-// }
-// else
-// {
-// break;
-// }
-// }
-//
-// return idx;
-// }
+
public void groupRowRange(int fromRow, int toRow, boolean indent)
{
// Grab the guts record, adding if needed
GutsRecord guts = (GutsRecord) findFirstRecordBySid( GutsRecord.sid );
if(guts == null) {
- guts = new GutsRecord();
- records.add(guts);
+ guts = new GutsRecord();
+ records.add(guts);
}
// Set the levels onto it
guts.setRowLevelMax( (short) ( maxLevel + 1 ) );
rows.expandRow( row );
}
}
-
-
-// private void collapseRow( int rowNumber )
-// {
-//
-// // Find the start of the group.
-// int startRow = rows.findStartOfRowOutlineGroup( rowNumber );
-// RowRecord rowRecord = (RowRecord) rows.getRow( startRow );
-//
-// // Hide all the columns until the end of the group
-// int lastRow = rows.writeHidden( rowRecord, startRow, true );
-//
-// // Write collapse field
-// if (getRow(lastRow + 1) != null)
-// {
-// getRow(lastRow + 1).setColapsed( true );
-// }
-// else
-// {
-// RowRecord row = createRow( lastRow + 1);
-// row.setColapsed( true );
-// rows.insertRow( row );
-// }
-// }
-
-// private int findStartOfRowOutlineGroup(int row)
-// {
-// // Find the start of the group.
-// RowRecord rowRecord = rows.getRow( row );
-// int level = rowRecord.getOutlineLevel();
-// int currentRow = row;
-// while (rows.getRow( currentRow ) != null)
-// {
-// rowRecord = rows.getRow( currentRow );
-// if (rowRecord.getOutlineLevel() < level)
-// return currentRow + 1;
-// currentRow--;
-// }
-//
-// return currentRow + 1;
-// }
-
-// private int writeHidden( RowRecord rowRecord, int row, boolean hidden )
-// {
-// int level = rowRecord.getOutlineLevel();
-// while (rowRecord != null && rows.getRow(row).getOutlineLevel() >= level)
-// {
-// rowRecord.setZeroHeight( hidden );
-// row++;
-// rowRecord = rows.getRow( row );
-// }
-// return row - 1;
-// }
-
-// private int findEndOfRowOutlineGroup( int row )
-// {
-// int level = getRow( row ).getOutlineLevel();
-// int currentRow;
-// for (currentRow = row; currentRow < rows.getLastRowNum(); currentRow++)
-// {
-// if (getRow(currentRow) == null || getRow(currentRow).getOutlineLevel() < level)
-// {
-// break;
-// }
-// }
-//
-// return currentRow-1;
-// }
-
-// private boolean isRowGroupCollapsed( int row )
-// {
-// int collapseRow = rows.findEndOfRowOutlineGroup( row ) + 1;
-//
-// if (getRow(collapseRow) == null)
-// return false;
-// else
-// return getRow( collapseRow ).getColapsed();
-// }
-
-
-// private boolean isRowGroupHiddenByParent( int row )
-// {
-// // Look out outline details of end
-// int endLevel;
-// boolean endHidden;
-// int endOfOutlineGroupIdx = rows.findEndOfRowOutlineGroup( row );
-// if (getRow( endOfOutlineGroupIdx + 1 ) == null)
-// {
-// endLevel = 0;
-// endHidden = false;
-// }
-// else
-// {
-// endLevel = getRow( endOfOutlineGroupIdx + 1).getOutlineLevel();
-// endHidden = getRow( endOfOutlineGroupIdx + 1).getZeroHeight();
-// }
-//
-// // Look out outline details of start
-// int startLevel;
-// boolean startHidden;
-// int startOfOutlineGroupIdx = rows.findStartOfRowOutlineGroup( row );
-// if (startOfOutlineGroupIdx - 1 < 0 || getRow(startOfOutlineGroupIdx - 1) == null)
-// {
-// startLevel = 0;
-// startHidden = false;
-// }
-// else
-// {
-// startLevel = getRow( startOfOutlineGroupIdx - 1).getOutlineLevel();
-// startHidden = getRow( startOfOutlineGroupIdx - 1 ).getZeroHeight();
-// }
-//
-// if (endLevel > startLevel)
-// {
-// return endHidden;
-// }
-// else
-// {
-// return startHidden;
-// }
-// }
-
}
-
/* ====================================================================
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.HexDump;
+import org.apache.poi.util.LittleEndian;
/**
* Describes the frozen and unfozen panes.
* @author Glen Stampoultzis (glens at apache.org)
*/
-public class PaneRecord
- extends Record
-{
+public final class PaneRecord extends Record {
public final static short sid = 0x41;
private short field_1_x;
private short field_2_y;
public final static short ACTIVE_PANE_LOWER_RIGHT = 0;
public final static short ACTIVE_PANE_UPPER_RIGHT = 1;
public final static short ACTIVE_PANE_LOWER_LEFT = 2;
+ // TODO - remove obsolete field (it was deprecated May-2008 v3.1)
+ /** @deprecated use ACTIVE_PANE_UPPER_LEFT */
public final static short ACTIVE_PANE_UPER_LEFT = 3;
+ public final static short ACTIVE_PANE_UPPER_LEFT = 3;
public PaneRecord()
field_3_topRow = in.readShort();
field_4_leftColumn = in.readShort();
field_5_activePane = in.readShort();
-
}
public String toString()
* ACTIVE_PANE_LOWER_RIGHT
* ACTIVE_PANE_UPPER_RIGHT
* ACTIVE_PANE_LOWER_LEFT
- * ACTIVE_PANE_UPER_LEFT
+ * ACTIVE_PANE_UPPER_LEFT
*/
public short getActivePane()
{
* ACTIVE_PANE_LOWER_RIGHT
* ACTIVE_PANE_UPPER_RIGHT
* ACTIVE_PANE_LOWER_LEFT
- * ACTIVE_PANE_UPER_LEFT
+ * ACTIVE_PANE_UPPER_LEFT
*/
public void setActivePane(short field_5_activePane)
{
this.field_5_activePane = field_5_activePane;
}
-
-
-} // END OF CLASS
-
-
-
-
+}
-
/* ====================================================================
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;
* @author Jason Height (jheight at chariot dot net dot au)
* @version 2.0-pre
*/
-
-public class RowRecord
- extends Record
- implements Comparable
-{
- public final static short sid = 0x208;
+public final class RowRecord extends Record implements Comparable {
+ public final static short sid = 0x208;
- /** The maximum row number that excel can handle (zero bazed) ie 65536 rows is
+ private static final int OPTION_BITS_ALWAYS_SET = 0x0100;
+ private static final int DEFAULT_HEIGHT_BIT = 0x8000;
+
+ /** The maximum row number that excel can handle (zero based) ie 65536 rows is
* max number of rows.
*/
public final static int MAX_ROW_NUMBER = 65535;
- //private short field_1_row_number;
- private int field_1_row_number;
+ private int field_1_row_number;
private short field_2_first_col;
private short field_3_last_col; // plus 1
private short field_4_height;
// for generated sheets.
private short field_6_reserved;
- private short field_7_option_flags;
+ /** 16 bit options flags */
+ private int field_7_option_flags;
private static final BitField outlineLevel = BitFieldFactory.getInstance(0x07);
// bit 3 reserved
private static final BitField formatted = BitFieldFactory.getInstance(0x80);
private short field_8_xf_index; // only if isFormatted
- public RowRecord()
- {
+ public RowRecord(int rowNumber) {
+ field_1_row_number = rowNumber;
+ field_2_first_col = -1;
+ field_3_last_col = -1;
+ field_4_height = (short)DEFAULT_HEIGHT_BIT;
+ field_4_height = (short)DEFAULT_HEIGHT_BIT;
+ field_5_optimize = ( short ) 0;
+ field_6_reserved = ( short ) 0;
+ field_7_option_flags = OPTION_BITS_ALWAYS_SET; // seems necessary for outlining
+
+ field_8_xf_index = ( short ) 0xf;
}
/**
protected void fillFields(RecordInputStream in)
{
- //field_1_row_number = LittleEndian.getShort(data, 0 + offset);
field_1_row_number = in.readUShort();
field_2_first_col = in.readShort();
field_3_last_col = in.readShort();
public void setOptionFlags(short options)
{
- field_7_option_flags = options;
+ field_7_option_flags = options | OPTION_BITS_ALWAYS_SET;
}
// option bitfields
public void setOutlineLevel(short ol)
{
- field_7_option_flags =
- outlineLevel.setShortValue(field_7_option_flags, ol);
+ field_7_option_flags = outlineLevel.setValue(field_7_option_flags, ol);
}
/**
- * set whether or not to colapse this row
- * @param c - colapse or not
+ * set whether or not to collapse this row
+ * @param c - collapse or not
* @see #setOptionFlags(short)
*/
public void setColapsed(boolean c)
{
- field_7_option_flags = colapsed.setShortBoolean(field_7_option_flags,
- c);
+ field_7_option_flags = colapsed.setBoolean(field_7_option_flags, c);
}
/**
public void setZeroHeight(boolean z)
{
- field_7_option_flags =
- zeroHeight.setShortBoolean(field_7_option_flags, z);
+ field_7_option_flags = zeroHeight.setBoolean(field_7_option_flags, z);
}
/**
public void setBadFontHeight(boolean f)
{
- field_7_option_flags =
- badFontHeight.setShortBoolean(field_7_option_flags, f);
+ field_7_option_flags = badFontHeight.setBoolean(field_7_option_flags, f);
}
/**
public void setFormatted(boolean f)
{
- field_7_option_flags = formatted.setShortBoolean(field_7_option_flags,
- f);
+ field_7_option_flags = formatted.setBoolean(field_7_option_flags, f);
}
// end bitfields
public short getOptionFlags()
{
- return field_7_option_flags;
+ return (short)field_7_option_flags;
}
// option bitfields
public short getOutlineLevel()
{
- return outlineLevel.getShortValue(field_7_option_flags);
+ return (short)outlineLevel.getValue(field_7_option_flags);
}
/**
{
LittleEndian.putShort(data, 0 + offset, sid);
LittleEndian.putShort(data, 2 + offset, ( short ) 16);
- //LittleEndian.putShort(data, 4 + offset, getRowNumber());
LittleEndian.putShort(data, 4 + offset, ( short ) getRowNumber());
LittleEndian.putShort(data, 6 + offset, getFirstCol() == -1 ? (short)0 : getFirstCol());
LittleEndian.putShort(data, 8 + offset, getLastCol() == -1 ? (short)0 : getLastCol());
LittleEndian.putShort(data, 14 + offset, field_6_reserved);
LittleEndian.putShort(data, 16 + offset, getOptionFlags());
-// LittleEndian.putShort(data,18,getOutlineLevel());
LittleEndian.putShort(data, 18 + offset, getXFIndex());
return getRecordSize();
}
}
public Object clone() {
- RowRecord rec = new RowRecord();
- rec.field_1_row_number = field_1_row_number;
+ RowRecord rec = new RowRecord(field_1_row_number);
rec.field_2_first_col = field_2_first_col;
rec.field_3_last_col = field_3_last_col;
rec.field_4_height = field_4_height;
BitFieldFactory.getInstance(0x20); // display tabs at the bottom
// all the rest are "reserved"
- private short field_6_selected_tab;
- private short field_7_displayed_tab;
+ private int field_6_active_sheet;
+ private int field_7_first_visible_tab;
private short field_8_num_selected_tabs;
private short field_9_tab_width_ratio;
field_3_width = in.readShort();
field_4_height = in.readShort();
field_5_options = in.readShort();
- field_6_selected_tab = in.readShort();
- field_7_displayed_tab = in.readShort();
+ field_6_active_sheet = in.readShort();
+ field_7_first_visible_tab = in.readShort();
field_8_num_selected_tabs = in.readShort();
field_9_tab_width_ratio = in.readShort();
}
// end bitfields
+ public void setActiveSheetIndex(int index) {
+ field_6_active_sheet = index;
+ }
/**
- * set the selected tab number
- * @param s tab number
+ * deprecated May 2008
+ * @deprecated - Misleading name - use setActiveSheetIndex()
*/
-
public void setSelectedTab(short s)
{
- field_6_selected_tab = s;
+ setActiveSheetIndex(s);
}
/**
- * set the displayed tab number
- * @param t tab number
+ * Sets the first visible sheet in the worksheet tab-bar. This method does <b>not</b>
+ * hide, select or focus sheets. It just sets the scroll position in the tab-bar.
+ * @param t the sheet index of the tab that will become the first in the tab-bar
*/
+ public void setFirstVisibleTab(int t) {
+ field_7_first_visible_tab = t;
+ }
- public void setDisplayedTab(short t)
- {
- field_7_displayed_tab = t;
+ /**
+ * deprecated May 2008
+ * @deprecated - Misleading name - use setFirstVisibleTab()
+ */
+ public void setDisplayedTab(short t) {
+ setFirstVisibleTab(t);
}
/**
// end options bitfields
+
/**
- * get the selected tab number
- * @return Tab number
+ * @return the index of the currently displayed sheet
+ */
+ public int getActiveSheetIndex() {
+ return field_6_active_sheet;
+ }
+ /**
+ * deprecated May 2008
+ * @deprecated - Misleading name - use getActiveSheetIndex()
*/
-
public short getSelectedTab()
{
- return field_6_selected_tab;
+ return (short) getActiveSheetIndex();
}
/**
- * get the displayed tab number
- * @return Tab number
+ * @return the first visible sheet in the worksheet tab-bar.
+ * I.E. the scroll position of the tab-bar.
+ */
+ public int getFirstVisibleTab() {
+ return field_7_first_visible_tab;
+ }
+ /**
+ * deprecated May 2008
+ * @deprecated - Misleading name - use getFirstVisibleTab()
*/
-
public short getDisplayedTab()
{
- return field_7_displayed_tab;
+ return (short) getFirstVisibleTab();
}
/**
.append(getDisplayVerticalScrollbar()).append("\n");
buffer.append(" .tabs = ").append(getDisplayTabs())
.append("\n");
- buffer.append(" .selectedtab = ")
- .append(Integer.toHexString(getSelectedTab())).append("\n");
- buffer.append(" .displayedtab = ")
- .append(Integer.toHexString(getDisplayedTab())).append("\n");
+ buffer.append(" .activeSheet = ")
+ .append(Integer.toHexString(getActiveSheetIndex())).append("\n");
+ buffer.append(" .firstVisibleTab = ")
+ .append(Integer.toHexString(getFirstVisibleTab())).append("\n");
buffer.append(" .numselectedtabs = ")
.append(Integer.toHexString(getNumSelectedTabs())).append("\n");
buffer.append(" .tabwidthratio = ")
LittleEndian.putShort(data, 8 + offset, getWidth());
LittleEndian.putShort(data, 10 + offset, getHeight());
LittleEndian.putShort(data, 12 + offset, getOptions());
- LittleEndian.putShort(data, 14 + offset, getSelectedTab());
- LittleEndian.putShort(data, 16 + offset, getDisplayedTab());
+ LittleEndian.putUShort(data, 14 + offset, getActiveSheetIndex());
+ LittleEndian.putUShort(data, 16 + offset, getFirstVisibleTab());
LittleEndian.putShort(data, 18 + offset, getNumSelectedTabs());
LittleEndian.putShort(data, 20 + offset, getTabWidthRatio());
return getRecordSize();
private BitField displayGuts = BitFieldFactory.getInstance(0x80);
private BitField freezePanesNoSplit = BitFieldFactory.getInstance(0x100);
private BitField selected = BitFieldFactory.getInstance(0x200);
- private BitField paged = BitFieldFactory.getInstance(0x400);
+ private BitField active = BitFieldFactory.getInstance(0x400);
private BitField savedInPageBreakPreview = BitFieldFactory.getInstance(0x800);
// 4-7 reserved
* is the sheet currently displayed in the window
* @param p displayed or not
*/
-
- public void setPaged(boolean p)
- {
- field_1_options = paged.setShortBoolean(field_1_options, p);
+ public void setActive(boolean p) {
+ field_1_options = active.setShortBoolean(field_1_options, p);
+ }
+ /**
+ * deprecated May 2008
+ * @deprecated use setActive()
+ */
+ public void setPaged(boolean p) {
+ setActive(p);
}
-
/**
* was the sheet saved in page break view
* @param p pagebreaksaved or not
* @return displayed or not
*/
- public boolean getPaged()
- {
- return paged.isSet(field_1_options);
+ public boolean isActive() {
+ return active.isSet(field_1_options);
+ }
+ /**
+ * deprecated May 2008
+ * @deprecated use isActive()
+ */
+ public boolean getPaged() {
+ return isActive();
}
/**
.append(getFreezePanesNoSplit()).append("\n");
buffer.append(" .selected = ").append(getSelected())
.append("\n");
- buffer.append(" .paged = ").append(getPaged())
+ buffer.append(" .active = ").append(isActive())
.append("\n");
buffer.append(" .svdinpgbrkpv= ")
.append(getSavedInPageBreakPreview()).append("\n");
* @author Jason Height (jheight at chariot dot net dot au)
*/
-public class RowRecordsAggregate
- extends Record
-{
- int firstrow = -1;
- int lastrow = -1;
- Map records = null;
- int size = 0;
+public final class RowRecordsAggregate extends Record {
+ private int firstrow = -1;
+ private int lastrow = -1;
+ private Map records = null; // TODO - use a proper key in this map
+ private int size = 0;
/** Creates a new instance of ValueRecordsAggregate */
public RowRecordsAggregate()
{
- records = new TreeMap();
+ records = new TreeMap();
}
public void insertRow(RowRecord row)
records.remove(row);
}
- public RowRecord getRow(int rownum)
- {
- // Row must be between 0 and 65535
- if(rownum < 0 || rownum > 65535) {
- throw new IllegalArgumentException("The row number must be between 0 and 65535");
- }
+ public RowRecord getRow(int rownum) {
+ // Row must be between 0 and 65535
+ if(rownum < 0 || rownum > 65535) {
+ throw new IllegalArgumentException("The row number must be between 0 and 65535");
+ }
- RowRecord row = new RowRecord();
- row.setRowNumber(rownum);
+ RowRecord row = new RowRecord(rownum);
return ( RowRecord ) records.get(row);
}
// Find the start of the group.
int startRow = findStartOfRowOutlineGroup( rowNumber );
- RowRecord rowRecord = (RowRecord) getRow( startRow );
+ RowRecord rowRecord = getRow( startRow );
// Hide all the columns until the end of the group
int lastRow = writeHidden( rowRecord, startRow, true );
* @return RowRecord created for the passed in row number
* @see org.apache.poi.hssf.record.RowRecord
*/
- public static RowRecord createRow(int row)
- {
- RowRecord rowrec = new RowRecord();
-
- //rowrec.setRowNumber(( short ) row);
- rowrec.setRowNumber(row);
- rowrec.setHeight(( short ) 0xff);
- rowrec.setOptimize(( short ) 0x0);
- rowrec.setOptionFlags(( short ) 0x100); // seems necessary for outlining
- rowrec.setXFIndex(( short ) 0xf);
- return rowrec;
+ public static RowRecord createRow(int rowNumber) {
+ return new RowRecord(rowNumber);
}
public boolean isRowGroupCollapsed( int row )
int endIdx = findEndOfRowOutlineGroup( idx );
// expand:
- // colapsed bit must be unset
+ // collapsed bit must be unset
// hidden bit gets unset _if_ surrounding groups are expanded you can determine
// this by looking at the hidden bit of the enclosing group. You will have
// to look at the start and the end of the current group to determine which
// is the enclosing group
- // hidden bit only is altered for this outline level. ie. don't uncollapse contained groups
+ // hidden bit only is altered for this outline level. ie. don't un-collapse contained groups
if ( !isRowGroupHiddenByParent( idx ) )
{
for ( int i = startIdx; i <= endIdx; i++ )
public final static int SIZE = 3;
private int numParams=0;
- /**
- * FuncPtgs are defined to be 4 bytes but the actual FuncPtg uses only 2 bytes.
- * If we have leftOvers that are read from the file we should serialize them back out.
- * <p>
- * If the leftovers are removed, a prompt "Warning: Data may have been lost occurs in Excel"
- */
- //protected byte[] leftOvers = null;
-
- private FuncPtg() {
- //Required for clone methods
- }
-
/**Creates new function pointer from a byte array
* usually called while reading an excel file.
*/
}
public Object clone() {
- FuncPtg ptg = new FuncPtg();
- //ptg.field_1_num_args = field_1_num_args;
- ptg.field_2_fnc_index = field_2_fnc_index;
- ptg.setClass(ptgClass);
- return ptg;
+ FuncPtg ptg = new FuncPtg(field_2_fnc_index);
+ ptg.setClass(ptgClass);
+ return ptg;
}
public int getSize() {
/**
* @author Amol S. Deshmukh < amolweb at ya hoo dot com >
- *
+ *
*/
-public final class Area2DEval implements AreaEval {
-// TODO -refactor with Area3DEval
- private final AreaPtg _delegate;
+public final class Area2DEval extends AreaEvalBase {
- private final ValueEval[] _values;
-
- public Area2DEval(Ptg ptg, ValueEval[] values) {
- if(ptg == null) {
- throw new IllegalArgumentException("ptg must not be null");
- }
- if(values == null) {
- throw new IllegalArgumentException("values must not be null");
- }
- for(int i=values.length-1; i>=0; i--) {
- if(values[i] == null) {
- throw new IllegalArgumentException("value array elements must not be null");
- }
- }
- // TODO - check size of array vs size of AreaPtg
- _delegate = (AreaPtg) ptg;
- _values = values;
- }
-
- public int getFirstColumn() {
- return _delegate.getFirstColumn();
- }
-
- public int getFirstRow() {
- return _delegate.getFirstRow();
- }
-
- public int getLastColumn() {
- return _delegate.getLastColumn();
- }
-
- public int getLastRow() {
- return _delegate.getLastRow();
- }
-
- public ValueEval[] getValues() {
- return _values;
- }
-
- public ValueEval getValueAt(int row, int col) {
- ValueEval retval;
- int index = ((row-getFirstRow())*(getLastColumn()-getFirstColumn()+1))+(col-getFirstColumn());
- if (index <0 || index >= _values.length)
- retval = ErrorEval.VALUE_INVALID;
- else
- retval = _values[index];
- return retval;
- }
-
- public boolean contains(int row, int col) {
- return (getFirstRow() <= row) && (getLastRow() >= row)
- && (getFirstColumn() <= col) && (getLastColumn() >= col);
- }
-
- public boolean containsRow(int row) {
- return (getFirstRow() <= row) && (getLastRow() >= row);
- }
-
- public boolean containsColumn(short col) {
- return (getFirstColumn() <= col) && (getLastColumn() >= col);
- }
-
- public boolean isColumn() {
- return _delegate.getFirstColumn() == _delegate.getLastColumn();
- }
-
- public boolean isRow() {
- return _delegate.getFirstRow() == _delegate.getLastRow();
- }
-}
+ public Area2DEval(Ptg ptg, ValueEval[] values) {
+ super((AreaPtg) ptg, values);
+ }
+}
\ No newline at end of file
/**
* @author Amol S. Deshmukh < amolweb at ya hoo dot com >
- *
+ *
*/
-public final class Area3DEval implements AreaEval {
- // TODO -refactor with Area3DEval
- private final Area3DPtg _delegate;
+public final class Area3DEval extends AreaEvalBase {
- private final ValueEval[] _values;
+ private final int _externSheetIndex;
- public Area3DEval(Ptg ptg, ValueEval[] values) {
- if(ptg == null) {
- throw new IllegalArgumentException("ptg must not be null");
- }
- if(values == null) {
- throw new IllegalArgumentException("values must not be null");
- }
- for(int i=values.length-1; i>=0; i--) {
- if(values[i] == null) {
- throw new IllegalArgumentException("value array elements must not be null");
- }
- }
- // TODO - check size of array vs size of AreaPtg
- _values = values;
- _delegate = (Area3DPtg) ptg;
- }
+ public Area3DEval(Ptg ptg, ValueEval[] values) {
+ super((Area3DPtg) ptg, values);
+ _externSheetIndex = ((Area3DPtg) ptg).getExternSheetIndex();
+ }
- public int getFirstColumn() {
- return _delegate.getFirstColumn();
- }
-
- public int getFirstRow() {
- return _delegate.getFirstRow();
- }
-
- public int getLastColumn() {
- return (short) _delegate.getLastColumn();
- }
-
- public int getLastRow() {
- return _delegate.getLastRow();
- }
-
- public ValueEval[] getValues() {
- return _values;
- }
-
- public ValueEval getValueAt(int row, int col) {
- ValueEval retval;
- int index = (row-getFirstRow())*(col-getFirstColumn());
- if (index <0 || index >= _values.length)
- retval = ErrorEval.VALUE_INVALID;
- else
- retval = _values[index];
- return retval;
- }
-
- public boolean contains(int row, int col) {
- return (getFirstRow() <= row) && (getLastRow() >= row)
- && (getFirstColumn() <= col) && (getLastColumn() >= col);
- }
-
- public boolean containsRow(int row) {
- return (getFirstRow() <= row) && (getLastRow() >= row);
- }
-
- public boolean containsColumn(short col) {
- return (getFirstColumn() <= col) && (getLastColumn() >= col);
- }
-
-
- public boolean isColumn() {
- return _delegate.getFirstColumn() == _delegate.getLastColumn();
- }
-
- public boolean isRow() {
- return _delegate.getFirstRow() == _delegate.getLastRow();
- }
-
- public int getExternSheetIndex() {
- return _delegate.getExternSheetIndex();
- }
+ public int getExternSheetIndex() {
+ return _externSheetIndex;
+ }
}
--- /dev/null
+/*
+ * 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.formula.eval;
+
+import org.apache.poi.hssf.record.formula.AreaI;
+
+/**
+ * @author Josh Micich
+ */
+abstract class AreaEvalBase implements AreaEval {
+
+ private final int _firstColumn;
+ private final int _firstRow;
+ private final int _lastColumn;
+ private final int _lastRow;
+ private final ValueEval[] _values;
+ private final int _nColumns;
+ private final int _nRows;
+
+ protected AreaEvalBase(AreaI ptg, ValueEval[] values) {
+ if (values == null) {
+ throw new IllegalArgumentException("values must not be null");
+ }
+ _firstRow = ptg.getFirstRow();
+ _firstColumn = ptg.getFirstColumn();
+ _lastRow = ptg.getLastRow();
+ _lastColumn = ptg.getLastColumn();
+
+ _nColumns = _lastColumn - _firstColumn + 1;
+ _nRows = _lastRow - _firstRow + 1;
+
+ int expectedItemCount = _nRows * _nColumns;
+ if ((values.length != expectedItemCount)) {
+ // Note - this math may need alteration when POI starts to support full column or full row refs
+ throw new IllegalArgumentException("Array size should be (" + expectedItemCount
+ + ") but was (" + values.length + ")");
+ }
+
+
+
+ for (int i = values.length - 1; i >= 0; i--) {
+ if (values[i] == null) {
+ throw new IllegalArgumentException("value array elements must not be null");
+ }
+ }
+ _values = values;
+ }
+
+ public final int getFirstColumn() {
+ return _firstColumn;
+ }
+
+ public final int getFirstRow() {
+ return _firstRow;
+ }
+
+ public final int getLastColumn() {
+ return _lastColumn;
+ }
+
+ public final int getLastRow() {
+ return _lastRow;
+ }
+
+ public final ValueEval[] getValues() {
+ // TODO - clone() - but some junits rely on not cloning at the moment
+ return _values;
+ }
+
+ public final ValueEval getValueAt(int row, int col) {
+ int rowOffsetIx = row - _firstRow;
+ int colOffsetIx = col - _firstColumn;
+
+ if(rowOffsetIx < 0 || rowOffsetIx >= _nRows) {
+ throw new IllegalArgumentException("Specified row index (" + row
+ + ") is outside the allowed range (" + _firstRow + ".." + _lastRow + ")");
+ }
+ if(colOffsetIx < 0 || colOffsetIx >= _nColumns) {
+ throw new IllegalArgumentException("Specified column index (" + col
+ + ") is outside the allowed range (" + _firstColumn + ".." + col + ")");
+ }
+
+ int index = rowOffsetIx * _nColumns + colOffsetIx;
+ return _values[index];
+ }
+
+ public final boolean contains(int row, int col) {
+ return _firstRow <= row && _lastRow >= row
+ && _firstColumn <= col && _lastColumn >= col;
+ }
+
+ public final boolean containsRow(int row) {
+ return (_firstRow <= row) && (_lastRow >= row);
+ }
+
+ public final boolean containsColumn(short col) {
+ return (_firstColumn <= col) && (_lastColumn >= col);
+ }
+
+ public final boolean isColumn() {
+ return _firstColumn == _lastColumn;
+ }
+
+ public final boolean isRow() {
+ return _firstRow == _lastRow;
+ }
+}
final class FunctionMetadataReader {
private static final String METADATA_FILE_NAME = "functionMetadata.txt";
+
+ /** plain ASCII text metadata file uses three dots for ellipsis */
+ private static final String ELLIPSIS = "...";
private static final Pattern TAB_DELIM_PATTERN = Pattern.compile("\t");
private static final Pattern SPACE_DELIM_PATTERN = Pattern.compile(" ");
private static final byte[] EMPTY_BYTE_ARRAY = { };
- // special characters from the ooo document
- private static final int CHAR_ELLIPSIS_8230 = 8230;
- private static final int CHAR_NDASH_8211 = 8211;
-
private static final String[] DIGIT_ENDING_FUNCTION_NAMES = {
// Digits at the end of a function might be due to a left-over footnote marker.
// except in these cases
throw new RuntimeException("resource '" + METADATA_FILE_NAME + "' not found");
}
- BufferedReader br = null;
+ BufferedReader br;
try {
br = new BufferedReader(new InputStreamReader(is,"UTF-8"));
- } catch(UnsupportedEncodingException e) { /* never happens */ }
+ } catch(UnsupportedEncodingException e) {
+ throw new RuntimeException(e);
+ }
FunctionDataBuilder fdb = new FunctionDataBuilder(400);
try {
}
String[] array = SPACE_DELIM_PATTERN.split(codes);
int nItems = array.length;
- if(array[nItems-1].charAt(0) == CHAR_ELLIPSIS_8230) {
+ if(ELLIPSIS.equals(array[nItems-1])) {
+ // final ellipsis is optional, and ignored
+ // (all unspecified params are assumed to be the same as the last)
nItems --;
}
byte[] result = new byte[nItems];
if(codes.length() == 1) {
switch (codes.charAt(0)) {
case '-':
- case CHAR_NDASH_8211: // this is what the ooo doc has
return true;
}
}
int row=record.getRow();
short col=record.getColumn();
short styleIndex=record.getXFIndex();
- if ((cellType != CELL_TYPE_ERROR) && (cellType != CELL_TYPE_FORMULA))
- {
+ if (cellType != CELL_TYPE_ERROR) {
setCellType(CELL_TYPE_ERROR, false, row, col, styleIndex);
}
(( BoolErrRecord ) record).setValue(value);
import java.util.NoSuchElementException;
import org.apache.poi.hssf.model.Sheet;
-import org.apache.poi.hssf.model.Workbook;
import org.apache.poi.hssf.record.CellValueRecordInterface;
import org.apache.poi.hssf.record.RowRecord;
import org.apache.poi.ss.usermodel.Cell;
// used for collections
public final static int INITIAL_CAPACITY = 5;
- //private short rowNum;
+
private int rowNum;
private HSSFCell[] cells=new HSSFCell[INITIAL_CAPACITY];
-// private short firstcell = -1;
-// private short lastcell = -1;
/**
* reference to low level representation
private Sheet sheet;
- protected HSSFRow()
+ // TODO - ditch this constructor
+ HSSFRow()
{
}
* @param rowNum the row number of this row (0 based)
* @see org.apache.poi.hssf.usermodel.HSSFSheet#createRow(int)
*/
-
- //protected HSSFRow(Workbook book, Sheet sheet, short rowNum)
- protected HSSFRow(HSSFWorkbook book, Sheet sheet, int rowNum)
+ HSSFRow(HSSFWorkbook book, Sheet sheet, int rowNum)
{
this.rowNum = rowNum;
this.book = book;
this.sheet = sheet;
- row = new RowRecord();
- row.setOptionFlags( (short)0x100 ); // seems necessary for outlining to work.
- row.setHeight((short) 0xff);
- row.setLastCol((short) -1);
- row.setFirstCol((short) -1);
+ row = new RowRecord(rowNum);
setRowNum(rowNum);
}
* @param record the low level api object this row should represent
* @see org.apache.poi.hssf.usermodel.HSSFSheet#createRow(int)
*/
-
- protected HSSFRow(HSSFWorkbook book, Sheet sheet, RowRecord record)
+ HSSFRow(HSSFWorkbook book, Sheet sheet, RowRecord record)
{
this.book = book;
this.sheet = sheet;
* @param rowNum the row number (0-based)
* @throws IndexOutOfBoundsException if the row number is not within the range 0-65535.
*/
-
- //public void setRowNum(short rowNum)
- public void setRowNum(int rowNum)
- {
- if ((rowNum < 0) || (rowNum > RowRecord.MAX_ROW_NUMBER))
- throw new IndexOutOfBoundsException("Row number must be between 0 and "+RowRecord.MAX_ROW_NUMBER+", was <"+rowNum+">");
+ public void setRowNum(int rowNum) {
+ if ((rowNum < 0) || (rowNum > RowRecord.MAX_ROW_NUMBER)) {
+ throw new IllegalArgumentException("Invalid row number (" + rowNum
+ + ") outside allowable range (0.." + RowRecord.MAX_ROW_NUMBER + ")");
+ }
this.rowNum = rowNum;
if (row != null)
{
* get row number this row represents
* @return the row number (0 based)
*/
-
- //public short getRowNum()
public int getRowNum()
{
return rowNum;
{
int sloc = sheet.getLoc();
RowRecord row = sheet.getNextRow();
+ boolean rowRecordsAlreadyPresent = row!=null;
while (row != null)
{
if ( ( lastrow == null ) || ( lastrow.getRowNum() != cval.getRow() ) )
{
hrow = getRow( cval.getRow() );
+ if (hrow == null) {
+ // Some tools (like Perl module Spreadsheet::WriteExcel - bug 41187) skip the RowRecords
+ // Excel, OpenOffice.org and GoogleDocs are all OK with this, so POI should be too.
+ if (rowRecordsAlreadyPresent) {
+ // if at least one row record is present, all should be present.
+ throw new RuntimeException("Unexpected missing row when some rows already present");
+ }
+ // create the row record on the fly now.
+ RowRecord rowRec = new RowRecord(cval.getRow());
+ sheet.addRow(rowRec);
+ hrow = createRowFromRecord(rowRec);
+ }
}
if ( hrow != null )
{
return new HSSFFooter( getSheet().getFooter() );
}
+ /**
+ * Note - this is not the same as whether the sheet is focused (isActive)
+ * @return <code>true</code> if this sheet is currently selected
+ */
+ public boolean isSelected() {
+ return getSheet().getWindowTwo().getSelected();
+ }
/**
* Sets whether sheet is selected.
* @param sel Whether to select the sheet or deselect the sheet.
*/
public void setSelected( boolean sel )
{
- getSheet().setSelected( sel );
+ getSheet().getWindowTwo().setSelected(sel);
+ }
+ /**
+ * @return <code>true</code> if this sheet is currently focused
+ */
+ public boolean isActive() {
+ return getSheet().getWindowTwo().isActive();
+ }
+ /**
+ * Sets whether sheet is selected.
+ * @param sel Whether to select the sheet or deselect the sheet.
+ */
+ public void setActive(boolean sel )
+ {
+ getSheet().getWindowTwo().setActive(sel);
}
/**
* @param column the column index
*/
public void autoSizeColumn(short column) {
+ autoSizeColumn(column, false);
+ }
+
+ /**
+ * Adjusts the column width to fit the contents.
+ *
+ * This process can be relatively slow on large sheets, so this should
+ * normally only be called once per column, at the end of your
+ * processing.
+ *
+ * You can specify whether the content of merged cells should be considered or ignored.
+ * Default is to ignore merged cells.
+ *
+ * @param column the column index
+ * @param useMergedCells whether to use the contents of merged cells when calculating the width of the column
+ */
+ public void autoSizeColumn(short column, boolean useMergedCells) {
AttributedString str;
TextLayout layout;
/**
* '0' looks to be a good choice.
*/
char defaultChar = '0';
-
+
/**
* This is the multiple that the font height is scaled by when determining the
* boundary of rotated text.
*/
double fontHeightMultiple = 2.0;
-
+
FontRenderContext frc = new FontRenderContext(null, true, true);
HSSFWorkbook wb = new HSSFWorkbook(book);
int defaultCharWidth = (int)layout.getAdvance();
double width = -1;
+ rows:
for (Iterator it = rowIterator(); it.hasNext();) {
HSSFRow row = (HSSFRow) it.next();
HSSFCell cell = row.getCell(column);
- boolean isCellInMergedRegion = false;
- for (int i = 0 ; i < getNumMergedRegions() && ! isCellInMergedRegion; i++) {
- isCellInMergedRegion = getMergedRegionAt(i).contains(row.getRowNum(), column);
+ if (cell == null) continue;
+
+ int colspan = 1;
+ for (int i = 0 ; i < getNumMergedRegions(); i++) {
+ if (getMergedRegionAt(i).contains(row.getRowNum(), column)) {
+ if (!useMergedCells) {
+ // If we're not using merged cells, skip this one and move on to the next.
+ continue rows;
+ }
+ cell = row.getCell(getMergedRegionAt(i).getColumnFrom());
+ colspan = 1+ getMergedRegionAt(i).getColumnTo() - getMergedRegionAt(i).getColumnFrom();
+ }
}
- if (cell == null | isCellInMergedRegion) continue;
-
HSSFCellStyle style = cell.getCellStyle();
HSSFFont font = wb.getFontAt(style.getFontIndex());
- //the number of spaces to indent the text in the cell
- int indention = style.getIndention();
if (cell.getCellType() == HSSFCell.CELL_TYPE_STRING) {
HSSFRichTextString rt = cell.getRichStringCellValue();
trans.concatenate(
AffineTransform.getScaleInstance(1, fontHeightMultiple)
);
- width = Math.max(width, layout.getOutline(trans).getBounds().getWidth() / defaultCharWidth + indention);
+ width = Math.max(width, ((layout.getOutline(trans).getBounds().getWidth() / colspan) / defaultCharWidth) + cell.getCellStyle().getIndention());
} else {
- width = Math.max(width, layout.getBounds().getWidth() / defaultCharWidth + indention);
+ width = Math.max(width, ((layout.getBounds().getWidth() / colspan) / defaultCharWidth) + cell.getCellStyle().getIndention());
}
}
} else {
trans.concatenate(
AffineTransform.getScaleInstance(1, fontHeightMultiple)
);
- width = Math.max(width, layout.getOutline(trans).getBounds().getWidth() / defaultCharWidth + indention);
+ width = Math.max(width, ((layout.getOutline(trans).getBounds().getWidth() / colspan) / defaultCharWidth) + cell.getCellStyle().getIndention());
} else {
- width = Math.max(width, layout.getBounds().getWidth() / defaultCharWidth + indention);
+ width = Math.max(width, ((layout.getBounds().getWidth() / colspan) / defaultCharWidth) + cell.getCellStyle().getIndention());
}
}
}
- if (width != -1) {
- if (width > Short.MAX_VALUE) { //calculated width can be greater that Short.MAX_VALUE!
- width = Short.MAX_VALUE;
- }
- sheet.setColumnWidth(column, (short) (width * 256));
+ }
+ if (width != -1) {
+ if (width > Short.MAX_VALUE) { //width can be bigger that Short.MAX_VALUE!
+ width = Short.MAX_VALUE;
}
+ sheet.setColumnWidth(column, (short) (width * 256));
}
}
workbook.setSheetOrder(sheetname, pos);
}
+ private void validateSheetIndex(int index) {
+ int lastSheetIx = sheets.size() - 1;
+ if (index < 0 || index > lastSheetIx) {
+ throw new IllegalArgumentException("Sheet index ("
+ + index +") is out of range (0.." + lastSheetIx + ")");
+ }
+ }
+
/**
- * sets the tab whose data is actually seen when the sheet is opened.
- * This may be different from the "selected sheet" since excel seems to
- * allow you to show the data of one sheet when another is seen "selected"
- * in the tabs (at the bottom).
- * @see org.apache.poi.hssf.usermodel.HSSFSheet#setSelected(boolean)
- * @param index
+ * Selects a single sheet. This may be different to
+ * the 'active' sheet (which is the sheet with focus).
+ */
+ public void setSelectedTab(int index) {
+
+ validateSheetIndex(index);
+ int nSheets = sheets.size();
+ for (int i=0; i<nSheets; i++) {
+ getSheetAt(i).setSelected(i == index);
+ }
+ workbook.getWindowOne().setNumSelectedTabs((short)1);
+ }
+ /**
+ * deprecated May 2008
+ * @deprecated use setSelectedTab(int)
*/
public void setSelectedTab(short index) {
- workbook.getWindowOne().setSelectedTab(index);
+ setSelectedTab((int)index);
+ }
+ public void setSelectedTabs(int[] indexes) {
+
+ for (int i = 0; i < indexes.length; i++) {
+ validateSheetIndex(indexes[i]);
+ }
+ int nSheets = sheets.size();
+ for (int i=0; i<nSheets; i++) {
+ boolean bSelect = false;
+ for (int j = 0; j < indexes.length; j++) {
+ if (indexes[j] == i) {
+ bSelect = true;
+ break;
+ }
+
+ }
+ getSheetAt(i).setSelected(bSelect);
+ }
+ workbook.getWindowOne().setNumSelectedTabs((short)indexes.length);
+ }
+ /**
+ * Convenience method to set the active sheet. The active sheet is is the sheet
+ * which is currently displayed when the workbook is viewed in Excel.
+ * 'Selected' sheet(s) is a distinct concept.
+ */
+ public void setActiveSheet(int index) {
+
+ validateSheetIndex(index);
+ int nSheets = sheets.size();
+ for (int i=0; i<nSheets; i++) {
+ getSheetAt(i).setActive(i == index);
+ }
+ workbook.getWindowOne().setActiveSheetIndex(index);
}
/**
* in the tabs (at the bottom).
* @see org.apache.poi.hssf.usermodel.HSSFSheet#setSelected(boolean)
*/
+ public int getActiveSheetIndex() {
+ return workbook.getWindowOne().getActiveSheetIndex();
+ }
+ /**
+ * deprecated May 2008
+ * @deprecated - Misleading name - use getActiveSheetIndex()
+ */
public short getSelectedTab() {
- return workbook.getWindowOne().getSelectedTab();
+ return (short) getActiveSheetIndex();
}
+
/**
* sets the first tab that is displayed in the list of tabs
* in excel.
* @param index
*/
+ public void setFirstVisibleTab(int index) {
+ workbook.getWindowOne().setFirstVisibleTab(index);
+ }
+ /**
+ * deprecated May 2008
+ * @deprecated - Misleading name - use setFirstVisibleTab()
+ */
public void setDisplayedTab(short index) {
- workbook.getWindowOne().setDisplayedTab(index);
+ setFirstVisibleTab(index);
}
/**
- * sets the first tab that is displayed in the list of tabs
- * in excel.
+ * sets the first tab that is displayed in the list of tabs in excel.
+ */
+ public int getFirstVisibleTab() {
+ return workbook.getWindowOne().getFirstVisibleTab();
+ }
+ /**
+ * deprecated May 2008
+ * @deprecated - Misleading name - use getFirstVisibleTab()
*/
public short getDisplayedTab() {
- return workbook.getWindowOne().getDisplayedTab();
+ return (short) getFirstVisibleTab();
}
/**
public HSSFSheet createSheet()
{
-
-// if (getNumberOfSheets() == 3)
-// throw new RuntimeException("You cannot have more than three sheets in HSSF 1.0");
HSSFSheet sheet = new HSSFSheet(this);
sheets.add(sheet);
- workbook.setSheetName(sheets.size() - 1,
- "Sheet" + (sheets.size() - 1));
- WindowTwoRecord windowTwo = (WindowTwoRecord) sheet.getSheet().findFirstRecordBySid(WindowTwoRecord.sid);
- windowTwo.setSelected(sheets.size() == 1);
- windowTwo.setPaged(sheets.size() == 1);
+ workbook.setSheetName(sheets.size() - 1, "Sheet" + (sheets.size() - 1));
+ boolean isOnlySheet = sheets.size() == 1;
+ sheet.setSelected(isOnlySheet);
+ sheet.setActive(isOnlySheet);
return sheet;
}
*/
public HSSFSheet cloneSheet(int sheetNum) {
- HSSFSheet srcSheet = (HSSFSheet)sheets.get(sheetNum);
- String srcName = workbook.getSheetName(sheetNum);
- if (srcSheet != null) {
+ validateSheetIndex(sheetNum);
+ HSSFSheet srcSheet = (HSSFSheet) sheets.get(sheetNum);
+ String srcName = workbook.getSheetName(sheetNum);
HSSFSheet clonedSheet = srcSheet.cloneSheet(this);
- WindowTwoRecord windowTwo = (WindowTwoRecord) clonedSheet.getSheet().findFirstRecordBySid(WindowTwoRecord.sid);
- windowTwo.setSelected(sheets.size() == 1);
- windowTwo.setPaged(sheets.size() == 1);
+ clonedSheet.setSelected(false);
+ clonedSheet.setActive(false);
sheets.add(clonedSheet);
- int i=1;
+ int i = 1;
while (true) {
- //Try and find the next sheet name that is unique
+ // Try and find the next sheet name that is unique
String name = srcName;
String index = Integer.toString(i++);
- if (name.length()+index.length()+2<31)
- name = name + "("+index+")";
- else name = name.substring(0, 31-index.length()-2)+"("+index+")";
+ if (name.length() + index.length() + 2 < 31) {
+ name = name + "(" + index + ")";
+ } else {
+ name = name.substring(0, 31 - index.length() - 2) + "(" + index + ")";
+ }
//If the sheet name is unique, then set it otherwise move on to the next number.
if (workbook.getSheetIndex(name) == -1) {
}
}
return clonedSheet;
- }
- return null;
}
/**
- * create an HSSFSheet for this HSSFWorkbook, adds it to the sheets and returns
- * the high level representation. Use this to create new sheets.
- *
- * @param sheetname sheetname to set for the sheet.
+ * create an HSSFSheet for this HSSFWorkbook, adds it to the sheets and
+ * returns the high level representation. Use this to create new sheets.
+ *
+ * @param sheetname
+ * sheetname to set for the sheet.
* @return HSSFSheet representing the new sheet.
- * @throws IllegalArgumentException if there is already a sheet present with a case-insensitive
- * match for the specified name.
+ * @throws IllegalArgumentException
+ * if there is already a sheet present with a case-insensitive
+ * match for the specified name.
*/
public HSSFSheet createSheet(String sheetname)
sheets.add(sheet);
workbook.setSheetName(sheets.size() - 1, sheetname);
- WindowTwoRecord windowTwo = (WindowTwoRecord) sheet.getSheet().findFirstRecordBySid(WindowTwoRecord.sid);
- windowTwo.setSelected(sheets.size() == 1);
- windowTwo.setPaged(sheets.size() == 1);
+ boolean isOnlySheet = sheets.size() == 1;
+ sheet.setSelected(isOnlySheet);
+ sheet.setActive(isOnlySheet);
return sheet;
}
HSSFPrintSetup printSetup = sheet.getPrintSetup();
printSetup.setValidSettings(false);
- WindowTwoRecord w2 = (WindowTwoRecord) sheet.getSheet().findFirstRecordBySid(WindowTwoRecord.sid);
- w2.setPaged(true);
+ sheet.setActive(true);
}
private NameRecord findExistingRowColHeaderNameRecord( int sheetIndex )
catch (ArrayIndexOutOfBoundsException ignored)
{
throw new IOException("Cannot remove block[ " + index
- + " ]; out of range");
+ + " ]; out of range[ 0 - " +
+ (_blocks.length-1) + " ]");
}
return result;
}
log.log(POILogger.ERROR,
"Unable to read entire block; " + count
+ type + " read before EOF; expected "
- + blockSize + " bytes. Your document"
- + " has probably been truncated!"
+ + blockSize + " bytes. Your document "
+ + "was either written by software that "
+ + "ignores the spec, or has been truncated!"
);
}
else {
cell.setCellValue(cv.getBooleanValue());
break;
case Cell.CELL_TYPE_ERROR:
- cell.setCellType(Cell.CELL_TYPE_ERROR);
- cell.setCellValue(cv.getErrorValue());
+ cell.setCellErrorValue(cv.getErrorValue());
break;
case Cell.CELL_TYPE_NUMERIC:
cell.setCellType(Cell.CELL_TYPE_NUMERIC);
int getCellType();
short getCellNum();
- byte getErrorCellValue();
String getCellFormula();
+ byte getErrorCellValue();
+ void setCellErrorValue(byte value);
+
HSSFCellStyle getCellStyle();
boolean getBooleanCellValue();
<const name="lower right" value="0"/>
<const name="upper right" value="1"/>
<const name="lower left" value="2"/>
- <const name="uper left" value="3"/>
+ <const name="upper left" value="3"/>
</field>
</fields>
</record>
7 MAX 1 30 V R \r
8 ROW 0 1 V R \r
9 COLUMN 0 1 V R \r
-10 NA 0 0 V – \r
+10 NA 0 0 V - \r
11 NPV 2 30 V V R \r
12 STDEV 1 30 V R \r
13 DOLLAR 1 2 V V V \r
16 COS 1 1 V V \r
17 TAN 1 1 V V \r
18 ARCTAN 1 1 V V \r
-19 PI 0 0 V – \r
+19 PI 0 0 V - \r
20 SQRT 1 1 V V \r
21 EXP 1 1 V V \r
22 LN 1 1 V V \r
31 MID 3 3 V V V V \r
32 LEN 1 1 V V \r
33 VALUE 1 1 V V \r
-34 TRUE 0 0 V – \r
-35 FALSE 0 0 V – \r
+34 TRUE 0 0 V - \r
+35 FALSE 0 0 V - \r
36 AND 1 30 V R \r
37 OR 1 30 V R \r
38 NOT 1 1 V V \r
60 RATE 3 6 V V V V V V V \r
61 MIRR 3 3 V R V V \r
62 IRR 1 2 V R V \r
-63 RAND 0 0 V – x \r
+63 RAND 0 0 V - x \r
64 MATCH 2 3 V V R R \r
65 DATE 3 3 V V V V \r
66 TIME 3 3 V V V V \r
71 HOUR 1 1 V V \r
72 MINUTE 1 1 V V \r
73 SECOND 1 1 V V \r
-74 NOW 0 0 V – x \r
+74 NOW 0 0 V - x \r
75 AREAS 1 1 V R \r
76 ROWS 1 1 V R \r
77 COLUMNS 1 1 V R \r
215 JIS 1 1 V V x\r
219 ADDRESS 2 5 V V V V V V \r
220 DAYS360 2 2 V V V x\r
-221 TODAY 0 0 V – x \r
+221 TODAY 0 0 V - x \r
222 VDB 5 7 V V V V V V V V \r
-227 MEDIAN 1 30 V R … \r
-228 SUMPRODUCT 1 30 V A … \r
+227 MEDIAN 1 30 V R ... \r
+228 SUMPRODUCT 1 30 V A ... \r
229 SINH 1 1 V V \r
230 COSH 1 1 V V \r
231 TANH 1 1 V V \r
247 DB 4 5 V V V V V V \r
252 FREQUENCY 2 2 A R R \r
261 ERROR.TYPE 1 1 V V \r
-269 AVEDEV 1 30 V R … \r
+269 AVEDEV 1 30 V R ... \r
270 BETADIST 3 5 V V V V V V \r
271 GAMMALN 1 1 V V \r
272 BETAINV 3 5 V V V V V V \r
315 SLOPE 2 2 V A A \r
316 TTEST 4 4 V A A V V \r
317 PROB 3 4 V A A V V \r
-318 DEVSQ 1 30 V R … \r
-319 GEOMEAN 1 30 V R … \r
-320 HARMEAN 1 30 V R … \r
-321 SUMSQ 0 30 V R … \r
-322 KURT 1 30 V R … \r
-323 SKEW 1 30 V R … \r
+318 DEVSQ 1 30 V R ... \r
+319 GEOMEAN 1 30 V R ... \r
+320 HARMEAN 1 30 V R ... \r
+321 SUMSQ 0 30 V R ... \r
+322 KURT 1 30 V R ... \r
+323 SKEW 1 30 V R ... \r
324 ZTEST 2 3 V R V V \r
325 LARGE 2 2 V R V \r
326 SMALL 2 2 V R V \r
358 GETPIVOTDATA 2 30 \r
359 HYPERLINK 1 2 V V V \r
360 PHONETIC 1 1 V R \r
-361 AVERAGEA 1 30 V R … \r
-362 MAXA 1 30 V R … \r
-363 MINA 1 30 V R … \r
-364 STDEVPA 1 30 V R … \r
-365 VARPA 1 30 V R … \r
-366 STDEVA 1 30 V R … \r
-367 VARA 1 30 V R … \r
+361 AVERAGEA 1 30 V R ... \r
+362 MAXA 1 30 V R ... \r
+363 MINA 1 30 V R ... \r
+364 STDEVPA 1 30 V R ... \r
+365 VARPA 1 30 V R ... \r
+366 STDEVA 1 30 V R ... \r
+367 VARA 1 30 V R ... \r
7 MAX 1 30 V R \r
8 ROW 0 1 V R \r
9 COLUMN 0 1 V R \r
-10 NA 0 0 V – \r
+10 NA 0 0 V - \r
11 NPV 2 30 V V R \r
12 STDEV 1 30 V R \r
13 DOLLAR 1 2 V V V \r
16 COS 1 1 V V \r
17 TAN 1 1 V V \r
18 ATAN 1 1 V V \r
-19 PI 0 0 V – \r
+19 PI 0 0 V - \r
20 SQRT 1 1 V V \r
21 EXP 1 1 V V \r
22 LN 1 1 V V \r
31 MID 3 3 V V V V \r
32 LEN 1 1 V V \r
33 VALUE 1 1 V V \r
-34 TRUE 0 0 V – \r
-35 FALSE 0 0 V – \r
+34 TRUE 0 0 V - \r
+35 FALSE 0 0 V - \r
36 AND 1 30 V R \r
37 OR 1 30 V R \r
38 NOT 1 1 V V \r
60 RATE 3 6 V V V V V V V \r
61 MIRR 3 3 V R V V \r
62 IRR 1 2 V R V \r
-63 RAND 0 0 V – x \r
+63 RAND 0 0 V - x \r
64 MATCH 2 3 V V R R \r
65 DATE 3 3 V V V V \r
66 TIME 3 3 V V V V \r
71 HOUR 1 1 V V \r
72 MINUTE 1 1 V V \r
73 SECOND 1 1 V V \r
-74 NOW 0 0 V – x \r
+74 NOW 0 0 V - x \r
75 AREAS 1 1 V R \r
76 ROWS 1 1 V R \r
77 COLUMNS 1 1 V R \r
215 JIS 1 1 V V x\r
219 ADDRESS 2 5 V V V V V V \r
220 DAYS360 2 2 V V V x\r
-221 TODAY 0 0 V – x \r
+221 TODAY 0 0 V - x \r
222 VDB 5 7 V V V V V V V V \r
-227 MEDIAN 1 30 V R … \r
-228 SUMPRODUCT 1 30 V A … \r
+227 MEDIAN 1 30 V R ... \r
+228 SUMPRODUCT 1 30 V A ... \r
229 SINH 1 1 V V \r
230 COSH 1 1 V V \r
231 TANH 1 1 V V \r
247 DB 4 5 V V V V V V \r
252 FREQUENCY 2 2 A R R \r
261 ERROR.TYPE 1 1 V V \r
-269 AVEDEV 1 30 V R … \r
+269 AVEDEV 1 30 V R ... \r
270 BETADIST 3 5 V V V V V V \r
271 GAMMALN 1 1 V V \r
272 BETAINV 3 5 V V V V V V \r
315 SLOPE 2 2 V A A \r
316 TTEST 4 4 V A A V V \r
317 PROB 3 4 V A A V V \r
-318 DEVSQ 1 30 V R … \r
-319 GEOMEAN 1 30 V R … \r
-320 HARMEAN 1 30 V R … \r
-321 SUMSQ 0 30 V R … \r
-322 KURT 1 30 V R … \r
-323 SKEW 1 30 V R … \r
+318 DEVSQ 1 30 V R ... \r
+319 GEOMEAN 1 30 V R ... \r
+320 HARMEAN 1 30 V R ... \r
+321 SUMSQ 0 30 V R ... \r
+322 KURT 1 30 V R ... \r
+323 SKEW 1 30 V R ... \r
324 ZTEST 2 3 V R V V \r
325 LARGE 2 2 V R V \r
326 SMALL 2 2 V R V \r
358 GETPIVOTDATA 2 30 \r
359 HYPERLINK 1 2 V V V \r
360 PHONETIC 1 1 V R \r
-361 AVERAGEA 1 30 V R … \r
-362 MAXA 1 30 V R … \r
-363 MINA 1 30 V R … \r
-364 STDEVPA 1 30 V R … \r
-365 VARPA 1 30 V R … \r
-366 STDEVA 1 30 V R … \r
-367 VARA 1 30 V R … \r
+361 AVERAGEA 1 30 V R ... \r
+362 MAXA 1 30 V R ... \r
+363 MINA 1 30 V R ... \r
+364 STDEVPA 1 30 V R ... \r
+365 VARPA 1 30 V R ... \r
+366 STDEVA 1 30 V R ... \r
+367 VARA 1 30 V R ... \r
String name = ole.getInstanceName();\r
if ("Worksheet".equals(name)) {\r
\r
- //save xls on disk\r
- FileOutputStream out = new FileOutputStream(name + "-("+(j)+").xls");\r
- InputStream dis = data.getData();\r
- byte[] chunk = new byte[2048];\r
- int count;\r
- while ((count = dis.read(chunk)) >= 0) {\r
- out.write(chunk,0,count);\r
- }\r
- is.close();\r
- out.close();\r
+ //read xls\r
+ HSSFWorkbook wb = new HSSFWorkbook(data.getData());\r
+\r
} else if ("Document".equals(name)) {\r
HWPFDocument doc = new HWPFDocument(data.getData());\r
//read the word document\r
doc.write(out);\r
out.close();\r
} else {\r
- System.err.println("Processing " + name);\r
+ FileOutputStream out = new FileOutputStream(ole.getProgID() + "-"+(j+1)+".dat");\r
+ InputStream dis = data.getData();\r
+ byte[] chunk = new byte[2048];\r
+ int count;\r
+ while ((count = dis.read(chunk)) >= 0) {\r
+ out.write(chunk,0,count);\r
+ }\r
+ is.close();\r
+ out.close();\r
}\r
}\r
\r
case ShapeTypes.TextBox:
shape = new TextBox(spContainer, parent);
break;
+ case ShapeTypes.HostControl:
case ShapeTypes.PictureFrame: {
EscherOptRecord opt = (EscherOptRecord)Shape.getEscherChild(spContainer, EscherOptRecord.RECORD_ID);
EscherProperty prop = Shape.getEscherProperty(opt, EscherProperties.BLIP__PICTUREID);
protected TextBytesAtom _byteAtom;
protected TextCharsAtom _charAtom;
protected StyleTextPropAtom _styleAtom;
- protected TextSpecInfoAtom _specAtom;
protected boolean _isUnicode;
protected RichTextRun[] _rtRuns;
private SlideShow slideShow;
* touch the stylings.
*/
private void storeText(String s) {
- // Remove a single trailing \n, as there is an implicit one at the
+ // Remove a single trailing \r, as there is an implicit one at the
// end of every record
- if(s.endsWith("\n")) {
+ if(s.endsWith("\r")) {
s = s.substring(0, s.length()-1);
}
_isUnicode = true;
}
}
+ /**
+ * If TextSpecInfoAtom is present, we must update the text size in it,
+ * otherwise the ppt will be corrupted
+ */
+ if(_records != null) for (int i = 0; i < _records.length; i++) {
+ if(_records[i] instanceof TextSpecInfoAtom){
+ TextSpecInfoAtom specAtom = (TextSpecInfoAtom)_records[i];
+ if((s.length() + 1) != specAtom.getCharactersCovered()){
+ specAtom.reset(s.length() + 1);
+ }
+ }
+ }
}
/**
* as the the first character has.
* If you care about styling, do setText on a RichTextRun instead
*/
- public synchronized void setText(String s) {
+ public synchronized void setRawText(String s) {
// Save the new text to the atoms
storeText(s);
RichTextRun fst = _rtRuns[0];
_rtRuns[0] = new RichTextRun(this,0,s.length());
}
- /**
- * If TextSpecInfoAtom is present, we must update the text size,
- * otherwise the ppt will be corrupted
- */
- if(_records != null) for (int i = 0; i < _records.length; i++) {
- if(_records[i] instanceof TextSpecInfoAtom){
- TextSpecInfoAtom specAtom = (TextSpecInfoAtom)_records[i];
- specAtom.setTextSize(s.length());
- }
-
- }
}
- /**
+ /**
+ * Changes the text.
+ * Converts '\r' into '\n'
+ */
+ public synchronized void setText(String s) {
+ String text = normalize(s);
+ setRawText(text);
+ }
+
+ /**
* Ensure a StyleTextPropAtom is present for this run,
* by adding if required. Normally for internal TextRun use.
*/
return null;
}
+
+ /**
+ * Returns a new string with line breaks converted into internal ppt representation
+ */
+ public String normalize(String s){
+ String ns = s.replaceAll("\\r?\\n", "\r");
+ return ns;
+ }
}
--- /dev/null
+/* ====================================================================\r
+ Licensed to the Apache Software Foundation (ASF) under one or more\r
+ contributor license agreements. See the NOTICE file distributed with\r
+ this work for additional information regarding copyright ownership.\r
+ The ASF licenses this file to You under the Apache License, Version 2.0\r
+ (the "License"); you may not use this file except in compliance with\r
+ the License. You may obtain a copy of the License at\r
+\r
+ http://www.apache.org/licenses/LICENSE-2.0\r
+\r
+ Unless required by applicable law or agreed to in writing, software\r
+ distributed under the License is distributed on an "AS IS" BASIS,\r
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r
+ See the License for the specific language governing permissions and\r
+ limitations under the License.\r
+==================================================================== */\r
+\r
+package org.apache.poi.hslf.record;\r
+\r
+import java.io.OutputStream;\r
+import java.io.IOException;\r
+\r
+import org.apache.poi.util.LittleEndian;\r
+import org.apache.poi.util.POILogger;\r
+\r
+/**\r
+ * Container for OLE Control object. It contains:\r
+ * <p>\r
+ * 1. ExControlAtom (4091)\r
+ * 2. ExOleObjAtom (4035)\r
+ * 3. CString (4026), Instance MenuName (1) used for menus and the Links dialog box.\r
+ * 4. CString (4026), Instance ProgID (2) that stores the OLE Programmatic Identifier.\r
+ * A ProgID is a string that uniquely identifies a given object.\r
+ * 5. CString (4026), Instance ClipboardName (3) that appears in the paste special dialog.\r
+ * 6. MetaFile( 4033), optional\r
+ * </p>\r
+ *\r
+ *\r
+ * @author Yegor kozlov\r
+ */\r
+public class ExControl extends ExEmbed {\r
+\r
+ // Links to our more interesting children\r
+ private ExControlAtom ctrlAtom;\r
+\r
+ /**\r
+ * Set things up, and find our more interesting children\r
+ *\r
+ * @param source the source data as a byte array.\r
+ * @param start the start offset into the byte array.\r
+ * @param len the length of the slice in the byte array.\r
+ */\r
+ protected ExControl(byte[] source, int start, int len) {\r
+ super(source, start, len);\r
+ }\r
+\r
+ /**\r
+ * Create a new ExEmbed, with blank fields\r
+ */\r
+ public ExControl() {\r
+ super();\r
+\r
+ _children[0] = ctrlAtom = new ExControlAtom();\r
+ }\r
+\r
+ /**\r
+ * Gets the {@link ExControlAtom}.\r
+ *\r
+ * @return the {@link ExControlAtom}.\r
+ */\r
+ public ExControlAtom getExControlAtom()\r
+ {\r
+ return ctrlAtom;\r
+ }\r
+\r
+ /**\r
+ * Returns the type (held as a little endian in bytes 3 and 4)\r
+ * that this class handles.\r
+ *\r
+ * @return the record type.\r
+ */\r
+ public long getRecordType() {\r
+ return RecordTypes.ExControl.typeID;\r
+ }\r
+\r
+ protected RecordAtom getEmbedAtom(Record[] children){\r
+ RecordAtom atom = null;\r
+ if(_children[0] instanceof ExControlAtom) {\r
+ atom = (ExControlAtom)_children[0];\r
+ } else {\r
+ logger.log(POILogger.ERROR, "First child record wasn't a ExControlAtom, was of type " + _children[0].getRecordType());\r
+ }\r
+ return atom;\r
+ }\r
+}\r
--- /dev/null
+/* ====================================================================\r
+ Licensed to the Apache Software Foundation (ASF) under one or more\r
+ contributor license agreements. See the NOTICE file distributed with\r
+ this work for additional information regarding copyright ownership.\r
+ The ASF licenses this file to You under the Apache License, Version 2.0\r
+ (the "License"); you may not use this file except in compliance with\r
+ the License. You may obtain a copy of the License at\r
+\r
+ http://www.apache.org/licenses/LICENSE-2.0\r
+\r
+ Unless required by applicable law or agreed to in writing, software\r
+ distributed under the License is distributed on an "AS IS" BASIS,\r
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r
+ See the License for the specific language governing permissions and\r
+ limitations under the License.\r
+==================================================================== */\r
+\r
+package org.apache.poi.hslf.record;\r
+\r
+import java.io.IOException;\r
+import java.io.OutputStream;\r
+\r
+import org.apache.poi.util.LittleEndian;\r
+\r
+/**\r
+ * Contains a long integer, slideID, which stores the unique slide identifier of the slide\r
+ * where this control resides.\r
+ *\r
+ * @author Yegor Kozlov\r
+ */\r
+public class ExControlAtom extends RecordAtom {\r
+\r
+\r
+ /**\r
+ * Record header.\r
+ */\r
+ private byte[] _header;\r
+\r
+ /**\r
+ * slideId.\r
+ */\r
+ private int _id;\r
+\r
+ /**\r
+ * Constructs a brand new embedded object atom record.\r
+ */\r
+ protected ExControlAtom() {\r
+ _header = new byte[8];\r
+\r
+ LittleEndian.putShort(_header, 2, (short) getRecordType());\r
+ LittleEndian.putInt(_header, 4, 4);\r
+\r
+ }\r
+\r
+ /**\r
+ * Constructs the ExControlAtom record from its source data.\r
+ *\r
+ * @param source the source data as a byte array.\r
+ * @param start the start offset into the byte array.\r
+ * @param len the length of the slice in the byte array.\r
+ */\r
+ protected ExControlAtom(byte[] source, int start, int len) {\r
+ // Get the header.\r
+ _header = new byte[8];\r
+ System.arraycopy(source, start, _header, 0, 8);\r
+\r
+ _id = LittleEndian.getInt(source, start + 8);\r
+ }\r
+\r
+ public int getSlideId() {\r
+ return _id;\r
+ }\r
+\r
+ /**\r
+ * Gets the record type.\r
+ * @return the record type.\r
+ */\r
+ public long getRecordType() {\r
+ return RecordTypes.ExControlAtom.typeID;\r
+ }\r
+\r
+ /**\r
+ * Write the contents of the record back, so it can be written\r
+ * to disk\r
+ *\r
+ * @param out the output stream to write to.\r
+ * @throws java.io.IOException if an error occurs.\r
+ */\r
+ public void writeOut(OutputStream out) throws IOException {\r
+ out.write(_header);\r
+ byte[] data = new byte[4];\r
+ LittleEndian.putInt(data, _id);\r
+ out.write(data);\r
+ }\r
+\r
+}\r
private byte[] _header;
// Links to our more interesting children
- private ExEmbedAtom embedAtom;
+ private RecordAtom embedAtom;
private ExOleObjAtom oleObjAtom;
private CString menuName;
private CString progId;
private void findInterestingChildren() {
// First child should be the ExHyperlinkAtom
- if(_children[0] instanceof ExEmbedAtom) {
- embedAtom = (ExEmbedAtom)_children[0];
- } else {
- logger.log(POILogger.ERROR, "First child record wasn't a ExEmbedAtom, was of type " + _children[0].getRecordType());
- }
+ embedAtom = getEmbedAtom(_children);
// Second child should be the ExOleObjAtom
if (_children[1] instanceof ExOleObjAtom) {
}
}
+ protected RecordAtom getEmbedAtom(Record[] children){
+ RecordAtom atom = null;
+ if(_children[0] instanceof ExEmbedAtom) {
+ atom = (ExEmbedAtom)_children[0];
+ } else {
+ logger.log(POILogger.ERROR, "First child record wasn't a ExEmbedAtom, was of type " + _children[0].getRecordType());
+ }
+ return atom;
+ }
+
/**
* Gets the {@link ExEmbedAtom}.
*
*/
public ExEmbedAtom getExEmbedAtom()
{
- return embedAtom;
+ return (ExEmbedAtom)embedAtom;
}
/**
package org.apache.poi.hslf.record;
-import java.io.ByteArrayInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
+import java.io.*;
import java.util.zip.InflaterInputStream;
+import java.util.zip.DeflaterOutputStream;
import org.apache.poi.util.LittleEndian;
return new InflaterInputStream(compressedStream);
}
+ /**
+ * Sets the embedded data.
+ *
+ * @param data the embedded data.
+ */
+ public void setData(byte[] data) throws IOException {
+ ByteArrayOutputStream out = new ByteArrayOutputStream();
+ //first four bytes is the length of the raw data
+ byte[] b = new byte[4];
+ LittleEndian.putInt(b, data.length);
+ out.write(b);
+
+ DeflaterOutputStream def = new DeflaterOutputStream(out);
+ def.write(data, 0, data.length);
+ def.finish();
+ _data = out.toByteArray();
+ LittleEndian.putInt(_header, 4, _data.length);
+ }
+
/**
* Gets the record type.
*
public static final Type RecolorInfoAtom = new Type(4071,null);
public static final Type ExQuickTimeMovie = new Type(4074,null);
public static final Type ExQuickTimeMovieData = new Type(4075,null);
- public static final Type ExControl = new Type(4078,null);
+ public static final Type ExControl = new Type(4078,ExControl.class);
public static final Type SlideListWithText = new Type(4080,SlideListWithText.class);
public static final Type InteractiveInfo = new Type(4082,InteractiveInfo.class);
public static final Type InteractiveInfoAtom = new Type(4083,InteractiveInfoAtom.class);
\r
import java.io.OutputStream;\r
import java.io.IOException;\r
+import java.util.ArrayList;\r
\r
/**\r
* The special info runs contained in this text.\r
public void setTextSize(int size){\r
LittleEndian.putInt(_data, 0, size);\r
}\r
+\r
+ /**\r
+ * Reset the content to one info run with the default values\r
+ * @param size the site of parent text\r
+ */\r
+ public void reset(int size){\r
+ _data = new byte[10];\r
+ // 01 00 00 00\r
+ LittleEndian.putInt(_data, 0, size);\r
+ // 01 00 00 00\r
+ LittleEndian.putInt(_data, 4, 1); //mask\r
+ // 00 00\r
+ LittleEndian.putShort(_data, 8, (short)0); //langId\r
+\r
+ // Update the size (header bytes 5-8)\r
+ LittleEndian.putInt(_header, 4, _data.length);\r
+ }\r
+\r
+ /**\r
+ * Get the number of characters covered by this records\r
+ *\r
+ * @return the number of characters covered by this records\r
+ */\r
+ public int getCharactersCovered(){\r
+ int covered = 0;\r
+ TextSpecInfoRun[] runs = getTextSpecInfoRuns();\r
+ for (int i = 0; i < runs.length; i++) covered += runs[i].len;\r
+ return covered;\r
+ }\r
+\r
+ public TextSpecInfoRun[] getTextSpecInfoRuns(){\r
+ ArrayList lst = new ArrayList();\r
+ int pos = 0;\r
+ int[] bits = {1, 0, 2};\r
+ while(pos < _data.length) {\r
+ TextSpecInfoRun run = new TextSpecInfoRun();\r
+ run.len = LittleEndian.getInt(_data, pos); pos += 4;\r
+ run.mask = LittleEndian.getInt(_data, pos); pos += 4;\r
+ for (int i = 0; i < bits.length; i++) {\r
+ if((run.mask & 1 << bits[i]) != 0){\r
+ switch (bits[i]){\r
+ case 0:\r
+ run.spellInfo = LittleEndian.getShort(_data, pos); pos += 2;\r
+ break;\r
+ case 1:\r
+ run.langId = LittleEndian.getShort(_data, pos); pos += 2;\r
+ break;\r
+ case 2:\r
+ run.altLangId = LittleEndian.getShort(_data, pos); pos += 2;\r
+ break;\r
+ }\r
+ }\r
+ }\r
+ lst.add(run);\r
+ }\r
+ return (TextSpecInfoRun[])lst.toArray(new TextSpecInfoRun[lst.size()]);\r
+\r
+ }\r
+\r
+ public static class TextSpecInfoRun {\r
+ //Length of special info run.\r
+ protected int len;\r
+\r
+ //Special info mask of this run;\r
+ protected int mask;\r
+\r
+ // info fields as indicated by the mask.\r
+ // -1 means the bit is not set\r
+ protected short spellInfo = -1;\r
+ protected short langId = -1;\r
+ protected short altLangId = -1;\r
+\r
+ /**\r
+ * Spelling status of this text. See Spell Info table below.\r
+ *\r
+ * <p>Spell Info Types:</p>\r
+ * <li>0 Unchecked\r
+ * <li>1 Previously incorrect, needs rechecking\r
+ * <li>2 Correct\r
+ * <li>3 Incorrect\r
+ *\r
+ * @return Spelling status of this text\r
+ */\r
+ public short getSpellInfo(){\r
+ return spellInfo;\r
+ }\r
+\r
+ /**\r
+ * Windows LANGID for this text.\r
+ *\r
+ * @return Windows LANGID for this text.\r
+ */\r
+ public short getLangId(){\r
+ return spellInfo;\r
+ }\r
+\r
+ /**\r
+ * Alternate Windows LANGID of this text;\r
+ * must be a valid non-East Asian LANGID if the text has an East Asian language,\r
+ * otherwise may be an East Asian LANGID or language neutral (zero).\r
+ *\r
+ * @return Alternate Windows LANGID of this text\r
+ */\r
+ public short getAltLangId(){\r
+ return altLangId;\r
+ }\r
+\r
+ /**\r
+ * @return Length of special info run.\r
+ */\r
+ public int length(){\r
+ return len;\r
+ }\r
+ }\r
}\r
package org.apache.poi.hslf.usermodel;
import java.io.InputStream;
+import java.io.IOException;
import org.apache.poi.hslf.record.ExOleObjStg;
return storage.getData();
}
+ /**
+ * Sets the embedded data.
+ *
+ * @param data the embedded data.
+ */
+ public void setData(byte[] data) throws IOException {
+ storage.setData(data);
+ }
+
/**
* Return the record that contains the object data.
*
* Change the text
*/
public void setText(String text) {
- length = text.length();
- parentRun.changeTextInRichTextRun(this,text);
+ String s = parentRun.normalize(text);
+ setRawText(s);
}
+ /**
+ * Change the text
+ */
+ public void setRawText(String text) {
+ length = text.length();
+ parentRun.changeTextInRichTextRun(this,text);
+ }
+
/**
* Tells the RichTextRun its new position in the parent TextRun
* @param startAt
-
/* ====================================================================
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
limitations under the License.
==================================================================== */
-
package org.apache.poi.hwpf.model;
+import java.util.Arrays;
+
import org.apache.poi.util.BitField;
import org.apache.poi.util.LittleEndian;
-import org.apache.poi.hwpf.usermodel.CharacterProperties;
-import org.apache.poi.hwpf.usermodel.ParagraphProperties;
-
-import org.apache.poi.hwpf.sprm.ParagraphSprmCompressor;
-import org.apache.poi.hwpf.sprm.CharacterSprmCompressor;
-
-import java.util.Arrays;
-
-public class ListLevel
+/**
+ *
+ */
+public final class ListLevel
{
+ private static final int RGBXCH_NUMS_SIZE = 9;
+
private int _iStartAt;
private byte _nfc;
private byte _info;
_grpprlPapx = new byte[0];
_grpprlChpx = new byte[0];
_numberText = new char[0];
- _rgbxchNums = new byte[9];
+ _rgbxchNums = new byte[RGBXCH_NUMS_SIZE];
if (numbered)
{
_nfc = buf[offset++];
_info = buf[offset++];
- _rgbxchNums = new byte[9];
- for (int x = 0; x < 9; x++)
- {
- _rgbxchNums[x] = buf[offset++];
- }
- _ixchFollow = buf[offset++];
+ _rgbxchNums = new byte[RGBXCH_NUMS_SIZE];
+ System.arraycopy(buf, offset, _rgbxchNums, 0, RGBXCH_NUMS_SIZE);
+ offset += RGBXCH_NUMS_SIZE;
+
+ _ixchFollow = buf[offset++];
_dxaSpace = LittleEndian.getInt(buf, offset);
offset += LittleEndian.INT_SIZE;
_dxaIndent = LittleEndian.getInt(buf, offset);
offset += LittleEndian.INT_SIZE;
buf[offset++] = _nfc;
buf[offset++] = _info;
- System.arraycopy(_rgbxchNums, 0, buf, offset, _rgbxchNums.length);
- offset += _rgbxchNums.length;
+ System.arraycopy(_rgbxchNums, 0, buf, offset, RGBXCH_NUMS_SIZE);
+ offset += RGBXCH_NUMS_SIZE;
buf[offset++] = _ixchFollow;
LittleEndian.putInt(buf, offset, _dxaSpace);
offset += LittleEndian.INT_SIZE;
System.arraycopy(_grpprlPapx, 0, buf, offset, _cbGrpprlPapx);
offset += _cbGrpprlPapx;
- LittleEndian.putShort(buf, offset, (short)_numberText.length);
- offset += LittleEndian.SHORT_SIZE;
- for (int x = 0; x < _numberText.length; x++)
- {
- LittleEndian.putShort(buf, offset, (short)_numberText[x]);
+ if (_numberText == null) {
+ // TODO - write junit to test this flow
+ LittleEndian.putUShort(buf, offset, 0);
+ } else {
+ LittleEndian.putUShort(buf, offset, _numberText.length);
offset += LittleEndian.SHORT_SIZE;
+ for (int x = 0; x < _numberText.length; x++)
+ {
+ LittleEndian.putUShort(buf, offset, _numberText[x]);
+ offset += LittleEndian.SHORT_SIZE;
+ }
}
return buf;
}
public int getSizeInBytes()
{
- if (_numberText!=null)
- {
- return 28 + _cbGrpprlChpx + _cbGrpprlPapx + (_numberText.length * LittleEndian.SHORT_SIZE) + 2;
- } else {
- return 28 + _cbGrpprlChpx + _cbGrpprlPapx + 2;
- }
+ int result =
+ 6 // int byte byte
+ + RGBXCH_NUMS_SIZE
+ + 13 // byte int int byte byte short
+ + _cbGrpprlChpx
+ + _cbGrpprlPapx
+ + 2; // numberText length
+ if (_numberText != null) {
+ result += _numberText.length * LittleEndian.SHORT_SIZE;
+ }
+ return result;
}
}
--- /dev/null
+\r
+/* ====================================================================\r
+ Licensed to the Apache Software Foundation (ASF) under one or more\r
+ contributor license agreements. See the NOTICE file distributed with\r
+ this work for additional information regarding copyright ownership.\r
+ The ASF licenses this file to You under the Apache License, Version 2.0\r
+ (the "License"); you may not use this file except in compliance with\r
+ the License. You may obtain a copy of the License at\r
+\r
+ http://www.apache.org/licenses/LICENSE-2.0\r
+\r
+ Unless required by applicable law or agreed to in writing, software\r
+ distributed under the License is distributed on an "AS IS" BASIS,\r
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r
+ See the License for the specific language governing permissions and\r
+ limitations under the License.\r
+==================================================================== */\r
+ \r
+\r
+\r
+package org.apache.poi.hslf.record;\r
+\r
+import org.apache.poi.hslf.HSLFSlideShow;\r
+import org.apache.poi.hslf.model.textproperties.CharFlagsTextProp;\r
+import org.apache.poi.hslf.model.textproperties.TextProp;\r
+import org.apache.poi.hslf.model.textproperties.TextPropCollection;\r
+import org.apache.poi.hslf.record.StyleTextPropAtom.*;\r
+import org.apache.poi.hslf.usermodel.SlideShow;\r
+import org.apache.poi.util.HexDump;\r
+\r
+import junit.framework.TestCase;\r
+import java.io.ByteArrayOutputStream;\r
+import java.util.LinkedList;\r
+import java.util.Arrays;\r
+\r
+/**\r
+ * Tests TextSpecInfoAtom\r
+ *\r
+ * @author Yegor Kozlov\r
+ */\r
+public class TestTextSpecInfoAtom extends TestCase {\r
+\r
+ //from a real file\r
+ private byte[] data_1 = new byte[] {\r
+ 0x00, 0x00, (byte)0xAA, 0x0F, 0x2C, 0x00, 0x00, 0x00,\r
+ 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,\r
+ 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x00,\r
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x01,\r
+ 0x00, 0x00, 0x00, 0x03, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00\r
+ };\r
+\r
+\r
+ public void testRead() throws Exception {\r
+ TextSpecInfoAtom spec = new TextSpecInfoAtom(data_1, 0, data_1.length);\r
+ TextSpecInfoAtom.TextSpecInfoRun[] run = spec.getTextSpecInfoRuns();\r
+ assertEquals(5, run.length);\r
+\r
+ assertEquals(10, run[0].length());\r
+ assertEquals(1, run[1].length());\r
+ assertEquals(70, run[2].length());\r
+ assertEquals(9, run[3].length());\r
+ assertEquals(32, run[4].length());\r
+\r
+ }\r
+\r
+ public void testWrite() throws Exception {\r
+ TextSpecInfoAtom spec = new TextSpecInfoAtom(data_1, 0, data_1.length);\r
+ ByteArrayOutputStream out = new ByteArrayOutputStream();\r
+ spec.writeOut(out);\r
+\r
+ byte[] result = out.toByteArray();\r
+ assertTrue(Arrays.equals(result, data_1));\r
+ }\r
+\r
+ public void testReset() throws Exception {\r
+ TextSpecInfoAtom spec = new TextSpecInfoAtom(data_1, 0, data_1.length);\r
+ spec.reset(32); //length of the parent text\r
+\r
+ TextSpecInfoAtom.TextSpecInfoRun[] run = spec.getTextSpecInfoRuns();\r
+ assertEquals(1, run.length);\r
+\r
+ assertEquals(32, run[0].length());\r
+\r
+ //serialize and read again\r
+ ByteArrayOutputStream out = new ByteArrayOutputStream();\r
+ spec.writeOut(out);\r
+\r
+ byte[] result = out.toByteArray();\r
+ TextSpecInfoAtom spec2 = new TextSpecInfoAtom(result, 0, result.length);\r
+ TextSpecInfoAtom.TextSpecInfoRun[] run2 = spec2.getTextSpecInfoRuns();\r
+ assertEquals(1, run2.length);\r
+\r
+ assertEquals(32, run2[0].length());\r
+ }\r
+}\r
import org.apache.poi.hssf.eventmodel.TestEventRecordFactory;
import org.apache.poi.hssf.eventmodel.TestModelFactory;
-import org.apache.poi.hssf.model.TestDrawingManager;
-import org.apache.poi.hssf.model.TestFormulaParser;
-import org.apache.poi.hssf.model.TestSheet;
+import org.apache.poi.hssf.model.AllModelTests;
import org.apache.poi.hssf.record.AllRecordTests;
import org.apache.poi.hssf.usermodel.AllUserModelTests;
import org.apache.poi.hssf.util.TestAreaReference;
TestSuite suite = new TestSuite("Tests for org.apache.poi.hssf");
// $JUnit-BEGIN$
+ suite.addTest(AllModelTests.suite());
suite.addTest(AllUserModelTests.suite());
suite.addTest(AllRecordTests.suite());
- suite.addTest(new TestSuite(TestFormulaParser.class));
suite.addTest(new TestSuite(TestAreaReference.class));
suite.addTest(new TestSuite(TestCellReference.class));
suite.addTest(new TestSuite(TestRangeAddress.class));
suite.addTest(new TestSuite(TestSheetReferences.class));
suite.addTest(new TestSuite(TestEventRecordFactory.class));
suite.addTest(new TestSuite(TestModelFactory.class));
- suite.addTest(new TestSuite(TestDrawingManager.class));
- suite.addTest(new TestSuite(TestSheet.class));
// $JUnit-END$
return suite;
}
--- /dev/null
+/* ====================================================================
+ 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 junit.framework.Test;
+import junit.framework.TestSuite;
+
+/**
+ * Collects all tests for <tt>org.apache.poi.hssf.model</tt>.
+ *
+ * @author Josh Micich
+ */
+public final class AllModelTests {
+
+ public static Test suite() {
+ TestSuite result = new TestSuite(AllModelTests.class.getName());
+ result.addTestSuite(TestDrawingManager.class);
+ result.addTestSuite(TestDrawingManager2.class);
+ result.addTestSuite(TestFormulaParser.class);
+ result.addTestSuite(TestFormulaParserEval.class);
+ result.addTestSuite(TestSheet.class);
+ result.addTestSuite(TestSheetAdditional.class);
+ return result;
+ }
+}
-
/* ====================================================================
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.model;
*
* @author Glen Stampoultzis (glens at apache.org)
*/
-public class TestSheet extends TestCase
-{
+public final class TestSheet extends TestCase {
public void testCreateSheet() throws Exception
{
// Check we're adding row and cell aggregates
if ((regionsToAdd % 1027) != 0)
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);
+ fail("Expected an exception to occur");
+ } catch(IllegalArgumentException e) {
+ // occurs during successful test
+ assertEquals("The 'to' row (9) must not be less than the 'from' row (10)", e.getMessage());
+ }
+ try {
+ sheet.addMergedRegion(10, (short)10, 12, (short)9);
+ fail("Expected an exception to occur");
+ } catch(IllegalArgumentException e) {
+ // occurs during successful test
+ assertEquals("The 'to' col (9) must not be less than the 'from' col (10)", e.getMessage());
+ }
}
public void testRemoveMergedRegion()
MergeCellsRecord merged = new MergeCellsRecord();
merged.addArea(0, (short)0, 1, (short)2);
- records.add(new RowRecord());
- records.add(new RowRecord());
- records.add(new RowRecord());
+ records.add(new RowRecord(0));
+ records.add(new RowRecord(1));
+ records.add(new RowRecord(2));
records.add(merged);
Sheet sheet = Sheet.createSheet(records, 0);
*/
public void testRowAggregation() {
List records = new ArrayList();
- RowRecord row = new RowRecord();
- row.setRowNumber(0);
- records.add(row);
-
- row = new RowRecord();
- row.setRowNumber(1);
- records.add(row);
+ records.add(new RowRecord(0));
+ records.add(new RowRecord(1));
records.add(new StringRecord());
-
- row = new RowRecord();
- row.setRowNumber(2);
- records.add(row);
-
+ records.add(new RowRecord(2));
Sheet sheet = Sheet.createSheet(records, 0);
assertNotNull("Row [2] was skipped", sheet.getRow(2));
Iterator iterator = sheet.getRowBreaks();
while (iterator.hasNext()) {
PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
- int main = (int)breakItem.main;
+ int main = breakItem.main;
if (main != 0 && main != 10 && main != 11) fail("Invalid page break");
- if (main == 0) is0 = true;
+ if (main == 0) is0 = true;
if (main == 10) is10= true;
if (main == 11) is11 = true;
}
assertFalse("row should be removed", sheet.isRowBroken(10));
assertEquals("no more breaks", 0, sheet.getNumRowBreaks());
-
-
}
/**
Iterator iterator = sheet.getColumnBreaks();
while (iterator.hasNext()) {
PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
- int main = (int)breakItem.main;
+ int main = breakItem.main;
if (main != 0 && main != 1 && main != 10 && main != 15) fail("Invalid page break");
- if (main == 0) is0 = true;
- if (main == 1) is1 = true;
+ if (main == 0) is0 = true;
+ if (main == 1) is1 = true;
if (main == 10) is10= true;
if (main == 15) is15 = true;
}
* works as designed.
*/
public void testXFIndexForColumn() {
- try{
- final short TEST_IDX = 10;
- final short DEFAULT_IDX = 0xF; // 15
- short xfindex = Short.MIN_VALUE;
- Sheet sheet = Sheet.createSheet();
-
- // without ColumnInfoRecord
- xfindex = sheet.getXFIndexForColAt((short) 0);
- assertEquals(DEFAULT_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 1);
- assertEquals(DEFAULT_IDX, xfindex);
-
- ColumnInfoRecord nci = ( ColumnInfoRecord ) sheet.createColInfo();
- sheet.columns.insertColumn(nci);
-
- // single column ColumnInfoRecord
- nci.setFirstColumn((short) 2);
- nci.setLastColumn((short) 2);
- nci.setXFIndex(TEST_IDX);
- xfindex = sheet.getXFIndexForColAt((short) 0);
- assertEquals(DEFAULT_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 1);
- assertEquals(DEFAULT_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 2);
- assertEquals(TEST_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 3);
- assertEquals(DEFAULT_IDX, xfindex);
-
- // ten column ColumnInfoRecord
- nci.setFirstColumn((short) 2);
- nci.setLastColumn((short) 11);
- nci.setXFIndex(TEST_IDX);
- xfindex = sheet.getXFIndexForColAt((short) 1);
- assertEquals(DEFAULT_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 2);
- assertEquals(TEST_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 6);
- assertEquals(TEST_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 11);
- assertEquals(TEST_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 12);
- assertEquals(DEFAULT_IDX, xfindex);
-
- // single column ColumnInfoRecord starting at index 0
- nci.setFirstColumn((short) 0);
- nci.setLastColumn((short) 0);
- nci.setXFIndex(TEST_IDX);
- xfindex = sheet.getXFIndexForColAt((short) 0);
- assertEquals(TEST_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 1);
- assertEquals(DEFAULT_IDX, xfindex);
-
- // ten column ColumnInfoRecord starting at index 0
- nci.setFirstColumn((short) 0);
- nci.setLastColumn((short) 9);
- nci.setXFIndex(TEST_IDX);
- xfindex = sheet.getXFIndexForColAt((short) 0);
- assertEquals(TEST_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 7);
- assertEquals(TEST_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 9);
- assertEquals(TEST_IDX, xfindex);
- xfindex = sheet.getXFIndexForColAt((short) 10);
- assertEquals(DEFAULT_IDX, xfindex);
- }
- catch(Exception e){e.printStackTrace();fail(e.getMessage());}
+ final short TEST_IDX = 10;
+ final short DEFAULT_IDX = 0xF; // 15
+ short xfindex = Short.MIN_VALUE;
+ Sheet sheet = Sheet.createSheet();
+
+ // without ColumnInfoRecord
+ xfindex = sheet.getXFIndexForColAt((short) 0);
+ assertEquals(DEFAULT_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 1);
+ assertEquals(DEFAULT_IDX, xfindex);
+
+ ColumnInfoRecord nci = ( ColumnInfoRecord ) sheet.createColInfo();
+ sheet.columns.insertColumn(nci);
+
+ // single column ColumnInfoRecord
+ nci.setFirstColumn((short) 2);
+ nci.setLastColumn((short) 2);
+ nci.setXFIndex(TEST_IDX);
+ xfindex = sheet.getXFIndexForColAt((short) 0);
+ assertEquals(DEFAULT_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 1);
+ assertEquals(DEFAULT_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 2);
+ assertEquals(TEST_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 3);
+ assertEquals(DEFAULT_IDX, xfindex);
+
+ // ten column ColumnInfoRecord
+ nci.setFirstColumn((short) 2);
+ nci.setLastColumn((short) 11);
+ nci.setXFIndex(TEST_IDX);
+ xfindex = sheet.getXFIndexForColAt((short) 1);
+ assertEquals(DEFAULT_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 2);
+ assertEquals(TEST_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 6);
+ assertEquals(TEST_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 11);
+ assertEquals(TEST_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 12);
+ assertEquals(DEFAULT_IDX, xfindex);
+
+ // single column ColumnInfoRecord starting at index 0
+ nci.setFirstColumn((short) 0);
+ nci.setLastColumn((short) 0);
+ nci.setXFIndex(TEST_IDX);
+ xfindex = sheet.getXFIndexForColAt((short) 0);
+ assertEquals(TEST_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 1);
+ assertEquals(DEFAULT_IDX, xfindex);
+
+ // ten column ColumnInfoRecord starting at index 0
+ nci.setFirstColumn((short) 0);
+ nci.setLastColumn((short) 9);
+ nci.setXFIndex(TEST_IDX);
+ xfindex = sheet.getXFIndexForColAt((short) 0);
+ assertEquals(TEST_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 7);
+ assertEquals(TEST_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 9);
+ assertEquals(TEST_IDX, xfindex);
+ xfindex = sheet.getXFIndexForColAt((short) 10);
+ assertEquals(DEFAULT_IDX, xfindex);
}
-
}
+
import java.lang.reflect.Field;
import java.util.ArrayList;
-import java.util.Iterator;
import java.util.List;
import junit.framework.TestCase;
import org.apache.poi.hssf.record.ColumnInfoRecord;
-import org.apache.poi.hssf.record.MergeCellsRecord;
-import org.apache.poi.hssf.record.PageBreakRecord;
-import org.apache.poi.hssf.record.RowRecord;
-import org.apache.poi.hssf.record.StringRecord;
/**
* @author Tony Poppleton
*/
-public class TestSheetAdditional extends TestCase
-{
- /**
- * Constructor for SheetTest.
- * @param arg0
- */
- public TestSheetAdditional(String arg0)
- {
- super(arg0);
- }
+public final class TestSheetAdditional extends TestCase {
- 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++)
- {
- int index = sheet.addMergedRegion(0, (short) 0, 1, (short) 1);
- assertTrue("Merged region index expected to be " + n + " got " + index, index == n);
- }
-
- //test all the regions were indeed added
- assertTrue(sheet.getNumMergedRegions() == regionsToAdd);
-
- //test that the regions were spread out over the appropriate number of records
- int recordsAdded = sheet.getRecords().size() - startRecords;
- 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);
-
- // Check we can't add one with invalud date
- try {
- sheet.addMergedRegion(10, (short)10, 9, (short)12);
- fail();
- } catch(IllegalArgumentException e) {}
- try {
- sheet.addMergedRegion(10, (short)10, 12, (short)9);
- fail();
- } catch(IllegalArgumentException e) {}
- }
-
- public void testRemoveMergedRegion()
- {
- Sheet sheet = Sheet.createSheet();
- int regionsToAdd = 4096;
-
- for (int n = 0; n < regionsToAdd; n++)
- sheet.addMergedRegion(0, (short) 0, 1, (short) 1);
-
- int records = 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);
- }
-
- //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);
- }
-
- /**
- * Bug: 22922 (Reported by Xuemin Guan)
- * <p>
- * Remove mergedregion fails when a sheet loses records after an initial CreateSheet
- * fills up the records.
- *
- */
- public void testMovingMergedRegion() {
- List records = new ArrayList();
-
- MergeCellsRecord merged = new MergeCellsRecord();
- merged.addArea(0, (short)0, 1, (short)2);
- records.add(new RowRecord());
- records.add(new RowRecord());
- records.add(new RowRecord());
- records.add(merged);
-
- Sheet sheet = Sheet.createSheet(records, 0);
- sheet.records.remove(0);
-
- //stub object to throw off list INDEX operations
- sheet.removeMergedRegion(0);
- assertEquals("Should be no more merged regions", 0, sheet.getNumMergedRegions());
- }
-
- public void testGetMergedRegionAt()
- {
- //TODO
- }
-
- public void testGetNumMergedRegions()
- {
- //TODO
- }
-
- public void DISBALEDtestGetCellWidth() throws Exception
- {
+ public void testGetCellWidth() {
Sheet sheet = Sheet.createSheet();
ColumnInfoRecord nci = ( ColumnInfoRecord ) sheet.createColInfo();
nci.setLastColumn((short)10);
nci.setColumnWidth((short)100);
- Field f = null;
- f = Sheet.class.getDeclaredField("columnSizes");
- f.setAccessible(true);
- List columnSizes = new ArrayList();
- f.set(sheet,columnSizes);
- columnSizes.add(nci);
- sheet.records.add(1 + sheet.dimsloc, nci);
- sheet.dimsloc++;
+
+ sheet.columns.insertColumn(nci);
assertEquals((short)100,sheet.getColumnWidth((short)5));
assertEquals((short)100,sheet.getColumnWidth((short)6));
assertEquals((short)100,sheet.getColumnWidth((short)10));
}
- /**
- * Makes sure all rows registered for this sheet are aggregated, they were being skipped
- *
- */
- public void testRowAggregation() {
- List records = new ArrayList();
- RowRecord row = new RowRecord();
- row.setRowNumber(0);
- records.add(row);
-
- row = new RowRecord();
- row.setRowNumber(1);
- records.add(row);
-
- records.add(new StringRecord());
-
- row = new RowRecord();
- row.setRowNumber(2);
- records.add(row);
-
-
- Sheet sheet = Sheet.createSheet(records, 0);
- assertNotNull("Row [2] was skipped", sheet.getRow(2));
-
- }
-
- /**
- * Make sure page break functionality works (in memory)
- *
- */
- public void testRowPageBreaks(){
- short colFrom = 0;
- short colTo = 255;
-
- Sheet sheet = Sheet.createSheet();
- sheet.setRowBreak(0, colFrom, colTo);
-
- assertTrue("no row break at 0", sheet.isRowBroken(0));
- assertEquals("1 row break available", 1, sheet.getNumRowBreaks());
-
- sheet.setRowBreak(0, colFrom, colTo);
- sheet.setRowBreak(0, colFrom, colTo);
-
- assertTrue("no row break at 0", sheet.isRowBroken(0));
- assertEquals("1 row break available", 1, sheet.getNumRowBreaks());
-
- sheet.setRowBreak(10, colFrom, colTo);
- sheet.setRowBreak(11, colFrom, colTo);
-
- assertTrue("no row break at 10", sheet.isRowBroken(10));
- assertTrue("no row break at 11", sheet.isRowBroken(11));
- assertEquals("3 row break available", 3, sheet.getNumRowBreaks());
-
-
- boolean is10 = false;
- boolean is0 = false;
- boolean is11 = false;
-
- Iterator iterator = sheet.getRowBreaks();
- while (iterator.hasNext()) {
- PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
- int main = (int)breakItem.main;
- if (main != 0 && main != 10 && main != 11) fail("Invalid page break");
- if (main == 0) is0 = true;
- if (main == 10) is10= true;
- if (main == 11) is11 = true;
- }
-
- assertTrue("one of the breaks didnt make it", is0 && is10 && is11);
-
- sheet.removeRowBreak(11);
- assertFalse("row should be removed", sheet.isRowBroken(11));
-
- sheet.removeRowBreak(0);
- assertFalse("row should be removed", sheet.isRowBroken(0));
-
- sheet.removeRowBreak(10);
- assertFalse("row should be removed", sheet.isRowBroken(10));
-
- assertEquals("no more breaks", 0, sheet.getNumRowBreaks());
-
-
- }
-
- /**
- * Make sure column pag breaks works properly (in-memory)
- *
- */
- public void testColPageBreaks(){
- short rowFrom = 0;
- short rowTo = (short)65535;
-
- Sheet sheet = Sheet.createSheet();
- sheet.setColumnBreak((short)0, rowFrom, rowTo);
-
- assertTrue("no col break at 0", sheet.isColumnBroken((short)0));
- assertEquals("1 col break available", 1, sheet.getNumColumnBreaks());
-
- sheet.setColumnBreak((short)0, rowFrom, rowTo);
-
- assertTrue("no col break at 0", sheet.isColumnBroken((short)0));
- assertEquals("1 col break available", 1, sheet.getNumColumnBreaks());
-
- sheet.setColumnBreak((short)1, rowFrom, rowTo);
- sheet.setColumnBreak((short)10, rowFrom, rowTo);
- sheet.setColumnBreak((short)15, rowFrom, rowTo);
-
- assertTrue("no col break at 1", sheet.isColumnBroken((short)1));
- assertTrue("no col break at 10", sheet.isColumnBroken((short)10));
- assertTrue("no col break at 15", sheet.isColumnBroken((short)15));
- assertEquals("4 col break available", 4, sheet.getNumColumnBreaks());
-
- boolean is10 = false;
- boolean is0 = false;
- boolean is1 = false;
- boolean is15 = false;
-
- Iterator iterator = sheet.getColumnBreaks();
- while (iterator.hasNext()) {
- PageBreakRecord.Break breakItem = (PageBreakRecord.Break)iterator.next();
- int main = (int)breakItem.main;
- if (main != 0 && main != 1 && main != 10 && main != 15) fail("Invalid page break");
- if (main == 0) is0 = true;
- if (main == 1) is1 = true;
- if (main == 10) is10= true;
- if (main == 15) is15 = true;
- }
-
- assertTrue("one of the breaks didnt make it", is0 && is1 && is10 && is15);
-
- sheet.removeColumnBreak((short)15);
- assertFalse("column break should not be there", sheet.isColumnBroken((short)15));
-
- sheet.removeColumnBreak((short)0);
- assertFalse("column break should not be there", sheet.isColumnBroken((short)0));
-
- sheet.removeColumnBreak((short)1);
- assertFalse("column break should not be there", sheet.isColumnBroken((short)1));
-
- sheet.removeColumnBreak((short)10);
- assertFalse("column break should not be there", sheet.isColumnBroken((short)10));
-
- assertEquals("no more breaks", 0, sheet.getNumColumnBreaks());
- }
-
}
-
/* ====================================================================
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.aggregates;
-import org.apache.poi.hssf.record.*;
+import junit.framework.TestCase;
-public class TestRowRecordsAggregate extends junit.framework.TestCase {
- public TestRowRecordsAggregate(String name) {
- super (name);
- }
+import org.apache.poi.hssf.record.RowRecord;
+
+/**
+ *
+ */
+public final class TestRowRecordsAggregate extends TestCase {
public void testRowGet() {
RowRecordsAggregate rra = new RowRecordsAggregate();
- RowRecord rr = new RowRecord();
- rr.setRowNumber(( short ) 4);
+ RowRecord rr = new RowRecord(4);
rra.insertRow(rr);
- RowRecord rr2 = new RowRecord(); rr2.setRowNumber((short) 1);
- rra.insertRow(rr2);
+ rra.insertRow(new RowRecord(1));
RowRecord rr1 = rra.getRow(4);
- assertTrue("Row Record should not be null", rr1!=null);
- assertTrue("Row number is 1",rr1.getRowNumber() == 4);
+ assertNotNull(rr1);
+ assertEquals("Row number is 1", 4, rr1.getRowNumber());
assertTrue("Row record retrieved is identical ", rr1 == rr);
}
-
- public static void main(String [] args) {
- System.out
- .println("Testing org.apache.poi.hssf.record.aggregates.RowRecordAggregate");
- junit.textui.TestRunner.run(TestRowRecordsAggregate.class);
- }
}
-
/* ====================================================================
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
*
* @author Danny Mui (dmui at apache dot org)
*/
+public final class TestFuncPtg extends TestCase {
-public class TestFuncPtg extends TestCase
-{
-
- public TestFuncPtg( String name )
- {
- super( name );
- }
-
-
- public static void main( java.lang.String[] args )
- {
- junit.textui.TestRunner.run( TestFuncPtg.class );
- }
-
- /**
- * Make sure the left overs are re-serialized on excel file reads to avoid
- * the "Warning: Data may have been lost" prompt in excel.
- * <p/>
- * This ptg represents a LEN function extracted from excel
- */
-
- public void testLeftOvers()
- {
- byte[] fakeData = new byte[4];
-
- //fakeData[0] = (byte) 0x41;
- fakeData[0] = (byte) 0x20; //function index
- fakeData[1] = (byte) 0;
- fakeData[2] = (byte) 8;
+ public void testRead() {
+ // This ptg represents a LEN function extracted from excel
+ byte[] fakeData = {
+ 0x20, //function index
+ 0,
+ };
FuncPtg ptg = new FuncPtg( new TestcaseRecordInputStream((short)0, (short)fakeData.length, fakeData) );
- assertEquals( "Len formula index is not 32(20H)", (int) 0x20, ptg.getFunctionIndex() );
+ assertEquals( "Len formula index is not 32(20H)", 0x20, ptg.getFunctionIndex() );
assertEquals( "Number of operands in the len formula", 1, ptg.getNumberOfOperands() );
assertEquals( "Function Name", "LEN", ptg.getName() );
assertEquals( "Ptg Size", 3, ptg.getSize() );
- //assertEquals("first leftover byte is not 0", (byte)0, ptg.leftOvers[0]);
- //assertEquals("second leftover byte is not 8", (byte)8, ptg.leftOvers[1]);
-
+ }
+
+ public void testClone() {
+ FuncPtg funcPtg = new FuncPtg(27); // ROUND() - takes 2 args
+
+ FuncPtg clone = (FuncPtg) funcPtg.clone();
+ if (clone.getNumberOfOperands() == 0) {
+ fail("clone() did copy field numberOfOperands");
+ }
+ assertEquals(2, clone.getNumberOfOperands());
+ assertEquals("ROUND", clone.getName());
}
}
public class AllFormulaEvalTests {
public static Test suite() {
- TestSuite result = new TestSuite("Tests for org.apache.poi.hssf.record.formula.eval");
+ TestSuite result = new TestSuite(AllFormulaEvalTests.class.getName());
+ result.addTestSuite(TestAreaEval.class);
result.addTestSuite(TestCircularReferences.class);
result.addTestSuite(TestExternalFunction.class);
result.addTestSuite(TestFormulaBugs.class);
--- /dev/null
+/* ====================================================================
+ 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.formula.eval;
+
+import junit.framework.AssertionFailedError;
+import junit.framework.TestCase;
+
+import org.apache.poi.hssf.record.formula.Area3DPtg;
+
+/**
+ * Tests for <tt>AreaEval</tt>
+ *
+ * @author Josh Micich
+ */
+public final class TestAreaEval extends TestCase {
+
+ public void testGetValue_bug44950() {
+
+ Area3DPtg ptg = new Area3DPtg("B2:D3", (short)0);
+ NumberEval one = new NumberEval(1);
+ ValueEval[] values = {
+ one,
+ new NumberEval(2),
+ new NumberEval(3),
+ new NumberEval(4),
+ new NumberEval(5),
+ new NumberEval(6),
+ };
+ AreaEval ae = new Area3DEval(ptg, values);
+ if (one == ae.getValueAt(1, 2)) {
+ throw new AssertionFailedError("Identified bug 44950 a");
+ }
+ confirm(1, ae, 1, 1);
+ confirm(2, ae, 1, 2);
+ confirm(3, ae, 1, 3);
+ confirm(4, ae, 2, 1);
+ confirm(5, ae, 2, 2);
+ confirm(6, ae, 2, 3);
+
+ }
+
+ private static void confirm(int expectedValue, AreaEval ae, int row, int col) {
+ NumberEval v = (NumberEval) ae.getValueAt(row, col);
+ assertEquals(expectedValue, v.getNumberValue(), 0.0);
+ }
+
+}
private static final String SOURCE_DOC_FILE_NAME = "excelfileformat.odt";
+ /**
+ * For simplicity, the output file is strictly simple ASCII.
+ * This method detects any unexpected characters.
+ */
+ /* package */ static boolean isSimpleAscii(char c) {
+
+ if (c>=0x21 && c<=0x7E) {
+ // everything from '!' to '~' (includes letters, digits, punctuation
+ return true;
+ }
+ // some specific whitespace chars below 0x21:
+ switch(c) {
+ case ' ':
+ case '\t':
+ case '\r':
+ case '\n':
+ return true;
+ }
+ return false;
+ }
+
+
private static final class FunctionData {
+ // special characters from the ooo document
+ private static final int CHAR_ELLIPSIS_8230 = 8230;
+ private static final int CHAR_NDASH_8211 = 8211;
private final int _index;
private final boolean _hasFootnote;
_name = funcName;
_minParams = minParams;
_maxParams = maxParams;
- _returnClass = returnClass;
- _paramClasses = paramClasses;
+ _returnClass = convertSpecialChars(returnClass);
+ _paramClasses = convertSpecialChars(paramClasses);
_isVolatile = isVolatile;
}
+ private static String convertSpecialChars(String ss) {
+ StringBuffer sb = new StringBuffer(ss.length() + 4);
+ for(int i=0; i<ss.length(); i++) {
+ char c = ss.charAt(i);
+ if (isSimpleAscii(c)) {
+ sb.append(c);
+ continue;
+ }
+ switch (c) {
+ case CHAR_NDASH_8211:
+ sb.append('-');
+ continue;
+ case CHAR_ELLIPSIS_8230:
+ sb.append("...");
+ continue;
+ }
+ throw new RuntimeException("bad char (" + ((int)c) + ") in string '" + ss + "'");
+ }
+ return sb.toString();
+ }
public int getIndex() {
return _index;
}
throw new RuntimeException(e);
}
}
+ /**
+ * To be sure that no tricky unicode chars make it through to the output file.
+ */
+ private static final class SimpleAsciiOutputStream extends OutputStream {
+
+ private final OutputStream _os;
+
+ public SimpleAsciiOutputStream(OutputStream os) {
+ _os = os;
+ }
+ public void write(int b) throws IOException {
+ checkByte(b);
+ _os.write(b);
+ }
+ private static void checkByte(int b) {
+ if (!isSimpleAscii((char)b)) {
+ throw new RuntimeException("Encountered char (" + b + ") which was not simple ascii as expected");
+ }
+ }
+ public void write(byte[] b, int off, int len) throws IOException {
+ for (int i = 0; i < len; i++) {
+ checkByte(b[i + off]);
+
+ }
+ _os.write(b, off, len);
+ }
+ }
private static void processFile(File effDocFile, File outFile) {
OutputStream os;
} catch (FileNotFoundException e) {
throw new RuntimeException(e);
}
- PrintStream ps = null;
+ os = new SimpleAsciiOutputStream(os);
+ PrintStream ps;
try {
- ps = new PrintStream(os,true, "UTF-8");
- } catch(UnsupportedEncodingException e) {}
+ ps = new PrintStream(os, true, "UTF-8");
+ } catch(UnsupportedEncodingException e) {
+ throw new RuntimeException(e);
+ }
outputLicenseHeader(ps);
Class genClass = ExcelFileFormatDocFunctionExtractor.class;
args = new Eval[] {
EvalFactory.createAreaEval("D1:F5", 3, 5), // 15
EvalFactory.createRefEval("A1"),
- EvalFactory.createAreaEval("A1:F6", 7, 6), // 42
+ EvalFactory.createAreaEval("A1:G6", 7, 6), // 42
new NumberEval(0),
};
confirmCountA(59, args);
BoolEval.TRUE,
BlankEval.INSTANCE,
};
- range = createAreaEval("A1:B2", values);
+ range = createAreaEval("A1:B3", values);
confirmCountIf(2, range, BoolEval.TRUE);
// when criteria is numeric
new NumberEval(2),
new NumberEval(2),
BoolEval.TRUE,
- BlankEval.INSTANCE,
};
- range = createAreaEval("A1:B2", values);
+ range = createAreaEval("A1:B3", values);
confirmCountIf(3, range, new NumberEval(2));
// note - same results when criteria is a string that parses as the number with the same value
confirmCountIf(3, range, new StringEval("2.00"));
See the License for the specific language governing permissions and
limitations under the License.
==================================================================== */
-
package org.apache.poi.hssf.record.formula.functions;
*/
public final class TestIndex extends TestCase {
- public TestIndex(String testName) {
- super(testName);
- }
-
private static final double[] TEST_VALUES0 = {
1, 2,
3, 4,
7, 8,
9, 10,
11, 12,
- 13, // excess array element. TODO - Area2DEval currently has no validation to ensure correct size of values array
};
/**
result.addTestSuite(TestEscherGraphics2d.class);
result.addTestSuite(TestFontDetails.class);
result.addTestSuite(TestFormulas.class);
+ result.addTestSuite(TestFormulaEvaluatorBugs.class);
+ result.addTestSuite(TestFormulaEvaluatorDocs.class);
result.addTestSuite(TestHSSFCell.class);
result.addTestSuite(TestHSSFClientAnchor.class);
- result.addTestSuite(TestHSSFConditionalFormatting.class);
result.addTestSuite(TestHSSFComment.class);
+ result.addTestSuite(TestHSSFConditionalFormatting.class);
result.addTestSuite(TestHSSFDateUtil.class);
result.addTestSuite(TestHSSFHeaderFooter.class);
result.addTestSuite(TestHSSFHyperlink.class);
result.addTestSuite(TestHSSFSheet.class);
result.addTestSuite(TestHSSFSheetOrder.class);
result.addTestSuite(TestHSSFSheetSetOrder.class);
+ result.addTestSuite(TestHSSFTextbox.class);
result.addTestSuite(TestHSSFWorkbook.class);
result.addTestSuite(TestNamedRange.class);
result.addTestSuite(TestOLE2Embeding.class);
+ result.addTestSuite(TestPOIFSProperties.class);
result.addTestSuite(TestReadWriteChart.class);
result.addTestSuite(TestSanityChecker.class);
result.addTestSuite(TestSheetHiding.class);
result.addTestSuite(TestSheetShiftRows.class);
if (false) { // deliberately avoiding this one
- result.addTestSuite(TestUnfixedBugs.class);
- }
- result.addTestSuite(TestUnicodeWorkbook.class);
+ result.addTestSuite(TestUnfixedBugs.class);
+ }
+ result.addTestSuite(TestUnicodeWorkbook.class);
result.addTestSuite(TestUppercaseWorkbook.class);
result.addTestSuite(TestWorkbook.class);
import java.util.Iterator;
import java.util.List;
+import junit.framework.AssertionFailedError;
import junit.framework.TestCase;
import org.apache.poi.hssf.HSSFTestDataSamples;
import org.apache.poi.hssf.record.aggregates.FormulaRecordAggregate;
import org.apache.poi.hssf.record.formula.AreaPtg;
import org.apache.poi.hssf.record.formula.FuncVarPtg;
+
/**
*
*/
*/
public void test44636() throws Exception {
// Open the existing file, tweak one value and
- // re-calculate
+ // re-calculate
HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("44636.xls");
- HSSFSheet sheet = wb.getSheetAt (0);
- HSSFRow row = sheet.getRow (0);
+ HSSFSheet sheet = wb.getSheetAt(0);
+ HSSFRow row = sheet.getRow(0);
- row.getCell((short)0).setCellValue(4.2);
- row.getCell((short)2).setCellValue(25);
+ row.getCell((short) 0).setCellValue(4.2);
+ row.getCell((short) 2).setCellValue(25);
HSSFFormulaEvaluator.evaluateAllFormulaCells(wb);
- assertEquals(4.2*25, row.getCell((short)3).getNumericCellValue(), 0.0001);
+ assertEquals(4.2 * 25, row.getCell((short) 3).getNumericCellValue(), 0.0001);
// Save
- File existing = new File(tmpDirName,"44636-existing.xls");
+ File existing = new File(tmpDirName, "44636-existing.xls");
FileOutputStream out = new FileOutputStream(existing);
wb.write(out);
out.close();
System.err.println("Existing file for bug #44636 written to " + existing.toString());
-
// Now, do a new file from scratch
wb = new HSSFWorkbook();
sheet = wb.createSheet();
row = sheet.createRow(0);
- row.createCell((short)0).setCellValue(1.2);
- row.createCell((short)1).setCellValue(4.2);
+ row.createCell((short) 0).setCellValue(1.2);
+ row.createCell((short) 1).setCellValue(4.2);
row = sheet.createRow(1);
- row.createCell((short)0).setCellFormula("SUM(A1:B1)");
+ row.createCell((short) 0).setCellFormula("SUM(A1:B1)");
HSSFFormulaEvaluator.evaluateAllFormulaCells(wb);
- assertEquals(5.4, row.getCell((short)0).getNumericCellValue(), 0.0001);
+ assertEquals(5.4, row.getCell((short) 0).getNumericCellValue(), 0.0001);
// Save
- File scratch = new File(tmpDirName,"44636-scratch.xls");
+ File scratch = new File(tmpDirName, "44636-scratch.xls");
out = new FileOutputStream(scratch);
wb.write(out);
out.close();
HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("44297.xls");
HSSFRow row;
- HSSFCell cell;
+ HSSFCell cell;
- HSSFSheet sheet = wb.getSheetAt(0);
+ HSSFSheet sheet = wb.getSheetAt(0);
HSSFFormulaEvaluator eva = new HSSFFormulaEvaluator(sheet, wb);
row = sheet.getRow(0);
- cell = row.getCell((short)0);
+ cell = row.getCell((short) 0);
assertEquals("31+46", cell.getCellFormula());
eva.setCurrentRow(row);
assertEquals(77, eva.evaluate(cell).getNumberValue(), 0);
row = sheet.getRow(1);
- cell = row.getCell((short)0);
+ cell = row.getCell((short) 0);
assertEquals("30+53", cell.getCellFormula());
eva.setCurrentRow(row);
assertEquals(83, eva.evaluate(cell).getNumberValue(), 0);
row = sheet.getRow(2);
- cell = row.getCell((short)0);
+ cell = row.getCell((short) 0);
assertEquals("SUM(A1:A2)", cell.getCellFormula());
eva.setCurrentRow(row);
assertEquals(160, eva.evaluate(cell).getNumberValue(), 0);
row = sheet.getRow(4);
- cell = row.getCell((short)0);
+ cell = row.getCell((short) 0);
assertEquals("32767+32768", cell.getCellFormula());
eva.setCurrentRow(row);
assertEquals(65535, eva.evaluate(cell).getNumberValue(), 0);
row = sheet.getRow(7);
- cell = row.getCell((short)0);
+ cell = row.getCell((short) 0);
assertEquals("32744+42333", cell.getCellFormula());
eva.setCurrentRow(row);
assertEquals(75077, eva.evaluate(cell).getNumberValue(), 0);
row = sheet.getRow(8);
- cell = row.getCell((short)0);
+ cell = row.getCell((short) 0);
assertEquals("327680.0/32768", cell.getCellFormula());
eva.setCurrentRow(row);
assertEquals(10, eva.evaluate(cell).getNumberValue(), 0);
row = sheet.getRow(9);
- cell = row.getCell((short)0);
+ cell = row.getCell((short) 0);
assertEquals("32767+32769", cell.getCellFormula());
eva.setCurrentRow(row);
assertEquals(65536, eva.evaluate(cell).getNumberValue(), 0);
row = sheet.getRow(10);
- cell = row.getCell((short)0);
+ cell = row.getCell((short) 0);
assertEquals("35000+36000", cell.getCellFormula());
eva.setCurrentRow(row);
assertEquals(71000, eva.evaluate(cell).getNumberValue(), 0);
row = sheet.getRow(11);
- cell = row.getCell((short)0);
+ cell = row.getCell((short) 0);
assertEquals("-1000000.0-3000000.0", cell.getCellFormula());
eva.setCurrentRow(row);
assertEquals(-4000000, eva.evaluate(cell).getNumberValue(), 0);
HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("SingleLetterRanges.xls");
- HSSFSheet sheet = wb.getSheetAt(0);
+ HSSFSheet sheet = wb.getSheetAt(0);
HSSFFormulaEvaluator eva = new HSSFFormulaEvaluator(sheet, wb);
- // =index(C:C,2,1) -> 2
+ // =index(C:C,2,1) -> 2
HSSFRow rowIDX = sheet.getRow(3);
- // =sum(C:C) -> 6
+ // =sum(C:C) -> 6
HSSFRow rowSUM = sheet.getRow(4);
- // =sum(C:D) -> 66
+ // =sum(C:D) -> 66
HSSFRow rowSUM2D = sheet.getRow(5);
// Test the sum
- HSSFCell cellSUM = rowSUM.getCell((short)0);
+ HSSFCell cellSUM = rowSUM.getCell((short) 0);
- FormulaRecordAggregate frec =
- (FormulaRecordAggregate)cellSUM.getCellValueRecord();
+ FormulaRecordAggregate frec = (FormulaRecordAggregate) cellSUM.getCellValueRecord();
List ops = frec.getFormulaRecord().getParsedExpression();
assertEquals(2, ops.size());
assertEquals(AreaPtg.class, ops.get(0).getClass());
assertEquals(FuncVarPtg.class, ops.get(1).getClass());
- // Actually stored as C1 to C65536
- // (last row is -1 === 65535)
- AreaPtg ptg = (AreaPtg)ops.get(0);
+ // Actually stored as C1 to C65536
+ // (last row is -1 === 65535)
+ AreaPtg ptg = (AreaPtg) ops.get(0);
assertEquals(2, ptg.getFirstColumn());
assertEquals(2, ptg.getLastColumn());
assertEquals(0, ptg.getFirstRow());
assertEquals("C:C", ptg.toFormulaString(wb));
// Will show as C:C, but won't know how many
- // rows it covers as we don't have the sheet
- // to hand when turning the Ptgs into a string
+ // rows it covers as we don't have the sheet
+ // to hand when turning the Ptgs into a string
assertEquals("SUM(C:C)", cellSUM.getCellFormula());
eva.setCurrentRow(rowSUM);
// But the evaluator knows the sheet, so it
- // can do it properly
+ // can do it properly
assertEquals(6, eva.evaluate(cellSUM).getNumberValue(), 0);
-
// Test the index
// Again, the formula string will be right but
- // lacking row count, evaluated will be right
- HSSFCell cellIDX = rowIDX.getCell((short)0);
+ // lacking row count, evaluated will be right
+ HSSFCell cellIDX = rowIDX.getCell((short) 0);
assertEquals("INDEX(C:C,2,1)", cellIDX.getCellFormula());
eva.setCurrentRow(rowIDX);
assertEquals(2, eva.evaluate(cellIDX).getNumberValue(), 0);
// Across two colums
- HSSFCell cellSUM2D = rowSUM2D.getCell((short)0);
+ HSSFCell cellSUM2D = rowSUM2D.getCell((short) 0);
assertEquals("SUM(C:D)", cellSUM2D.getCellFormula());
eva.setCurrentRow(rowSUM2D);
assertEquals(66, eva.evaluate(cellSUM2D).getNumberValue(), 0);
HSSFSheet sheet = wb.createSheet();
wb.setSheetName(0, "Sheet1");
HSSFRow row = sheet.createRow(0);
- HSSFCell cell = row.createCell((short)0);
+ HSSFCell cell = row.createCell((short) 0);
cell.setCellFormula("1=1");
}
assertEquals(true, cell.getBooleanCellValue());
}
-
+
public void testClassCast_bug44861() throws Exception {
- HSSFWorkbook wb = HSSFTestDataSamples.
- openSampleWorkbook("44861.xls");
-
+ HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("44861.xls");
+
// Check direct
HSSFFormulaEvaluator.evaluateAllFormulaCells(wb);
-
+
// And via calls
int numSheets = wb.getNumberOfSheets();
- for(int i=0; i<numSheets; i++) {
+ for (int i = 0; i < numSheets; i++) {
HSSFSheet s = wb.getSheetAt(i);
- HSSFFormulaEvaluator eval = new HSSFFormulaEvaluator(s,wb);
-
- for(Iterator rows = s.rowIterator(); rows.hasNext();) {
- HSSFRow r = (HSSFRow)rows.next();
- eval.setCurrentRow(r);
-
- for(Iterator cells = r.cellIterator(); cells.hasNext();) {
- HSSFCell c = (HSSFCell)cells.next();
- eval.evaluateFormulaCell(c);
- }
+ HSSFFormulaEvaluator eval = new HSSFFormulaEvaluator(s, wb);
+
+ for (Iterator rows = s.rowIterator(); rows.hasNext();) {
+ HSSFRow r = (HSSFRow) rows.next();
+ eval.setCurrentRow(r);
+
+ for (Iterator cells = r.cellIterator(); cells.hasNext();) {
+ HSSFCell c = (HSSFCell) cells.next();
+ eval.evaluateFormulaCell(c);
+ }
+ }
+ }
+ }
+
+ public void testEvaluateInCellWithErrorCode_bug44950() {
+ HSSFWorkbook wb = new HSSFWorkbook();
+ HSSFSheet sheet = wb.createSheet("Sheet1");
+ HSSFRow row = sheet.createRow(1);
+ HSSFCell cell = row.createCell((short) 0);
+ cell.setCellFormula("na()"); // this formula evaluates to an Excel error code '#N/A'
+ HSSFFormulaEvaluator fe = new HSSFFormulaEvaluator(sheet, wb);
+ fe.setCurrentRow(row);
+ try {
+ fe.evaluateInCell(cell);
+ } catch (NumberFormatException e) {
+ if (e.getMessage().equals("You cannot get an error value from a non-error cell")) {
+ throw new AssertionFailedError("Identified bug 44950 b");
}
+ throw e;
}
}
}
\ No newline at end of file
package org.apache.poi.hssf.usermodel;
-import java.io.ByteArrayInputStream;
-import java.io.ByteArrayOutputStream;
-
import junit.framework.TestCase;
+import org.apache.poi.hssf.HSSFTestDataSamples;
+
/**
* Test HSSFRow is okay.
*
public void testLastAndFirstColumns() {
HSSFWorkbook workbook = new HSSFWorkbook();
HSSFSheet sheet = workbook.createSheet();
- HSSFRow row = sheet.createRow((short) 0);
+ HSSFRow row = sheet.createRow(0);
assertEquals(-1, row.getFirstCellNum());
assertEquals(-1, row.getLastCellNum());
assertEquals(4, row.getLastCellNum());
}
- public void testRemoveCell() throws Exception {
+ /**
+ * Make sure that there is no cross-talk between rows especially with getFirstCellNum and getLastCellNum
+ * This test was added in response to bug report 44987.
+ */
+ public void testBoundsInMultipleRows() {
+ HSSFWorkbook workbook = new HSSFWorkbook();
+ HSSFSheet sheet = workbook.createSheet();
+ HSSFRow rowA = sheet.createRow(0);
+
+ rowA.createCell((short) 10);
+ rowA.createCell((short) 5);
+ assertEquals(5, rowA.getFirstCellNum());
+ assertEquals(11, rowA.getLastCellNum());
+
+ HSSFRow rowB = sheet.createRow(1);
+ rowB.createCell((short) 15);
+ rowB.createCell((short) 30);
+ assertEquals(15, rowB.getFirstCellNum());
+ assertEquals(31, rowB.getLastCellNum());
+
+ assertEquals(5, rowA.getFirstCellNum());
+ assertEquals(11, rowA.getLastCellNum());
+ rowA.createCell((short) 50);
+ assertEquals(51, rowA.getLastCellNum());
+
+ assertEquals(31, rowB.getLastCellNum());
+ }
+
+ public void testRemoveCell() {
HSSFWorkbook workbook = new HSSFWorkbook();
HSSFSheet sheet = workbook.createSheet();
HSSFRow row = sheet.createRow((short) 0);
assertEquals(0, data[6]);
assertEquals(0, data[8]);
- ByteArrayOutputStream baos = new ByteArrayOutputStream();
- workbook.write(baos);
- baos.close();
- ByteArrayInputStream inputStream = new ByteArrayInputStream(baos.toByteArray());
- workbook = new HSSFWorkbook(inputStream);
+ workbook = HSSFTestDataSamples.writeOutAndReadBack(workbook);
sheet = workbook.getSheetAt(0);
- inputStream.close();
- assertEquals(-1, sheet.getRow((short) 0).getLastCellNum());
- assertEquals(-1, sheet.getRow((short) 0).getFirstCellNum());
+ assertEquals(-1, sheet.getRow(0).getLastCellNum());
+ assertEquals(-1, sheet.getRow(0).getFirstCellNum());
}
public void testMoveCell() {
try {
sheet.createRow(-1);
fail("IndexOutOfBoundsException should have been thrown");
- } catch (IndexOutOfBoundsException ex) {
+ } catch (IllegalArgumentException e) {
// expected during successful test
+ assertEquals("Invalid row number (-1) outside allowable range (0..65535)", e.getMessage());
}
//Test high row bound
try {
sheet.createRow(65536);
fail("IndexOutOfBoundsException should have been thrown");
- } catch (IndexOutOfBoundsException ex) {
+ } catch (IllegalArgumentException e) {
// expected during successful test
+ assertEquals("Invalid row number (65536) outside allowable range (0..65535)", e.getMessage());
}
}
import java.io.FileInputStream;
import java.io.FileOutputStream;
+import junit.framework.AssertionFailedError;
import junit.framework.TestCase;
import org.apache.poi.hssf.HSSFTestDataSamples;
public void testCloneSheet() {
HSSFWorkbook workbook = new HSSFWorkbook();
HSSFSheet sheet = workbook.createSheet("Test Clone");
- HSSFRow row = sheet.createRow((short) 0);
+ HSSFRow row = sheet.createRow(0);
HSSFCell cell = row.createCell((short) 0);
- cell.setCellValue("clone_test");
- HSSFSheet cloned = workbook.cloneSheet(0);
-
+ HSSFCell cell2 = row.createCell((short) 1);
+ cell.setCellValue(new HSSFRichTextString("clone_test"));
+ cell2.setCellFormula("sin(1)");
+
+ HSSFSheet clonedSheet = workbook.cloneSheet(0);
+ HSSFRow clonedRow = clonedSheet.getRow(0);
+
//Check for a good clone
- assertEquals(cloned.getRow((short)0).getCell((short)0).getStringCellValue(), "clone_test");
+ assertEquals(clonedRow.getCell(0).getRichStringCellValue().getString(), "clone_test");
//Check that the cells are not somehow linked
- cell.setCellValue("Difference Check");
- assertEquals(cloned.getRow((short)0).getCell((short)0).getStringCellValue(), "clone_test");
+ cell.setCellValue(new HSSFRichTextString("Difference Check"));
+ cell2.setCellFormula("cos(2)");
+ if ("Difference Check".equals(clonedRow.getCell(0).getRichStringCellValue().getString())) {
+ fail("string cell not properly cloned");
+ }
+ if ("COS(2)".equals(clonedRow.getCell(1).getCellFormula())) {
+ fail("formula cell not properly cloned");
+ }
+ assertEquals(clonedRow.getCell(0).getRichStringCellValue().getString(), "clone_test");
+ assertEquals(clonedRow.getCell(1).getCellFormula(), "SIN(1)");
}
/** tests that the sheet name for multiple clones of the same sheet is unique
HSSFSheet sheet = workbook.createSheet("Test Clone");
HSSFRow row = sheet.createRow((short) 0);
HSSFCell cell = row.createCell((short) 0);
- cell.setCellValue("clone_test");
+ cell.setCellValue(new HSSFRichTextString("clone_test"));
//Clone the sheet multiple times
workbook.cloneSheet(0);
workbook.cloneSheet(0);
HSSFSheet sheet = wb.createSheet();
HSSFRow row = sheet.createRow(0);
HSSFCell cell = row.createCell((short)0);
- cell.setCellValue("first row, first cell");
+ cell.setCellValue(new HSSFRichTextString("first row, first cell"));
row = sheet.createRow(1);
cell = row.createCell((short)1);
- cell.setCellValue("second row, second cell");
+ cell.setCellValue(new HSSFRichTextString("second row, second cell"));
Region region = new Region(1, (short)0, 1, (short)1);
sheet.addMergedRegion(region);
/** cell with formula becomes null on cloning a sheet*/
public void test35084() {
-
- HSSFWorkbook wb = new HSSFWorkbook();
- HSSFSheet s =wb.createSheet("Sheet1");
- HSSFRow r = s.createRow(0);
- r.createCell((short)0).setCellValue(1);
- r.createCell((short)1).setCellFormula("A1*2");
- HSSFSheet s1 = wb.cloneSheet(0);
- r=s1.getRow(0);
- assertEquals("double" ,r.getCell((short)0).getNumericCellValue(),(double)1,0); //sanity check
- assertNotNull(r.getCell((short)1));
- assertEquals("formula", r.getCell((short)1).getCellFormula(), "A1*2");
- }
+
+ HSSFWorkbook wb = new HSSFWorkbook();
+ HSSFSheet s = wb.createSheet("Sheet1");
+ HSSFRow r = s.createRow(0);
+ r.createCell((short) 0).setCellValue(1);
+ r.createCell((short) 1).setCellFormula("A1*2");
+ HSSFSheet s1 = wb.cloneSheet(0);
+ r = s1.getRow(0);
+ assertEquals("double", r.getCell((short) 0).getNumericCellValue(), 1, 0); // sanity check
+ assertNotNull(r.getCell((short) 1));
+ assertEquals("formula", r.getCell((short) 1).getCellFormula(), "A1*2");
+ }
/** test that new default column styles get applied */
public void testDefaultColumnStyle() {
- HSSFWorkbook wb = new HSSFWorkbook();
- HSSFCellStyle style = wb.createCellStyle();
- HSSFSheet s = wb.createSheet();
- s.setDefaultColumnStyle((short)0, style);
- HSSFRow r = s.createRow(0);
- HSSFCell c = r.createCell((short)0);
- assertEquals("style should match", style.getIndex(), c.getCellStyle().getIndex());
+ HSSFWorkbook wb = new HSSFWorkbook();
+ HSSFCellStyle style = wb.createCellStyle();
+ HSSFSheet s = wb.createSheet();
+ s.setDefaultColumnStyle((short) 0, style);
+ HSSFRow r = s.createRow(0);
+ HSSFCell c = r.createCell((short) 0);
+ assertEquals("style should match", style.getIndex(), c.getCellStyle().getIndex());
}
assertTrue(wb3.getSheetAt(3).getForceFormulaRecalculation());
}
-
- 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
HSSFWorkbook wb = openSample("colwidth.xls");
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
+ //columns D-F have custom width
for (char i = 'D'; i <= 'F'; i++) {
short w = (short)(256*12);
assertEquals(w, sh.getColumnWidth((short)i));
}
+ }
+
+ /**
+ * Some utilities write Excel files without the ROW records.
+ * Excel, ooo, and google docs are OK with this.
+ * Now POI is too.
+ */
+ public void testMissingRowRecords_bug41187() {
+ HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("ex41187-19267.xls");
+ HSSFSheet sheet = wb.getSheetAt(0);
+ HSSFRow row = sheet.getRow(0);
+ if(row == null) {
+ throw new AssertionFailedError("Identified bug 41187 a");
+ }
+ if (row.getHeight() == 0) {
+ throw new AssertionFailedError("Identified bug 41187 b");
+ }
+ assertEquals("Hi Excel!", row.getCell(0).getRichStringCellValue().getString());
+ // check row height for 'default' flag
+ assertEquals((short)0x8000, row.getHeight());
+
+ HSSFTestDataSamples.writeOutAndReadBack(wb);
}
}
// Single chart, two sheets
b = openSample("44010-SingleChart.xls");
assertEquals(2, b.getNumberOfSheets());
+ assertEquals("Graph2", b.getSheetName(1));
s = b.getSheetAt(1);
assertEquals(0, s.getFirstRowNum());
- assertEquals(0, s.getLastRowNum());
+ assertEquals(8, s.getLastRowNum());
// Has chart on 1st sheet??
// FIXME
assertEquals(2, b.getNumberOfSheets());
s = b.getSheetAt(1);
assertEquals(0, s.getFirstRowNum());
- assertEquals(0, s.getLastRowNum());
+ assertEquals(8, s.getLastRowNum());
// Two charts, three sheets
s = b.getSheetAt(1);
assertEquals(0, s.getFirstRowNum());
- assertEquals(0, s.getLastRowNum());
+ assertEquals(8, s.getLastRowNum());
s = b.getSheetAt(2);
assertEquals(0, s.getFirstRowNum());
- assertEquals(0, s.getLastRowNum());
+ assertEquals(8, s.getLastRowNum());
// Has chart on 1st sheet??
// FIXME
s = b.getSheetAt(1);
assertEquals(0, s.getFirstRowNum());
- assertEquals(0, s.getLastRowNum());
+ assertEquals(8, s.getLastRowNum());
s = b.getSheetAt(2);
assertEquals(0, s.getFirstRowNum());
- assertEquals(0, s.getLastRowNum());
+ assertEquals(8, s.getLastRowNum());
}
private static HSSFWorkbook writeRead(HSSFWorkbook b) {
- return HSSFTestDataSamples.writeOutAndReadBack(b);
+ return HSSFTestDataSamples.writeOutAndReadBack(b);
}
}
\ No newline at end of file
package org.apache.poi.poifs.filesystem;
+import java.io.ByteArrayOutputStream;
+import java.io.File;
+import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
assertTrue("input stream was not closed", testIS.isClosed()); // but still should close
}
+
+ /**
+ * Test for bug # 48898 - problem opening an OLE2
+ * file where the last block is short (i.e. not a full
+ * multiple of 512 bytes)
+ *
+ * As yet, this problem remains. One school of thought is
+ * not not issue an EOF when we discover the last block
+ * is short, but this seems a bit wrong.
+ * The other is to fix the handling of the last block in
+ * POIFS, since it seems to be slight wrong
+ */
+ public void DISABLEDtestShortLastBlock() throws Exception {
+ String[] files = new String[] {
+ "ShortLastBlock.qwp", "ShortLastBlock.wps"
+ };
+ String pdirname = System.getProperty("POIFS.testdata.path");
+
+ for(int i=0; i<files.length; i++) {
+ File f = new File(pdirname, files[i]);
+ assertTrue(f.exists());
+
+ // Open the file up
+ POIFSFileSystem fs = new POIFSFileSystem(
+ new FileInputStream(f)
+ );
+
+ // Write it into a temp output array
+ ByteArrayOutputStream baos = new ByteArrayOutputStream();
+ fs.writeFilesystem(baos);
+
+ // Check sizes
+ }
+ }
private static InputStream openSampleStream(String sampleFileName) {
return HSSFTestDataSamples.openSampleFileStream(sampleFileName);
}
assertEquals(
- "7 - Unable to read entire block; "+bts+" read before EOF; expected 512 bytes. Your document has probably been truncated!",
+ "7 - Unable to read entire block; "+bts+" read before EOF; expected 512 bytes. Your document was either written by software that ignores the spec, or has been truncated!",
(String)(logger.logged.get(0))
);
} else {