git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@1061288 13f79535-47bb-0310-9956-ffa450edef68tags/REL_3_8_BETA1
<changes> | <changes> | ||||
<release version="3.8-beta1" date="2010-??-??"> | <release version="3.8-beta1" date="2010-??-??"> | ||||
<action dev="poi-developers" type="add">49928 - allow overridden built-in formats in HSSFCellStyle</action> | |||||
<action dev="POI-DEVELOPERS" type="add">50607 - Added implementation for CLEAN(), CHAR() and ADDRESS()</action> | <action dev="POI-DEVELOPERS" type="add">50607 - Added implementation for CLEAN(), CHAR() and ADDRESS()</action> | ||||
<action dev="poi-developers" type="add">50587 - Improved documentation on user-defined functions</action> | <action dev="poi-developers" type="add">50587 - Improved documentation on user-defined functions</action> | ||||
<action dev="poi-developers" type="add">Inside ExtractorFactory, support finding embedded OOXML documents and providing extractors for them</action> | <action dev="poi-developers" type="add">Inside ExtractorFactory, support finding embedded OOXML documents and providing extractors for them</action> |
import org.apache.poi.hssf.util.HSSFColor; | import org.apache.poi.hssf.util.HSSFColor; | ||||
import org.apache.poi.ss.formula.EvaluationWorkbook.ExternalName; | import org.apache.poi.ss.formula.EvaluationWorkbook.ExternalName; | ||||
import org.apache.poi.ss.formula.EvaluationWorkbook.ExternalSheet; | import org.apache.poi.ss.formula.EvaluationWorkbook.ExternalSheet; | ||||
import org.apache.poi.ss.usermodel.BuiltinFormats; | |||||
import org.apache.poi.util.Internal; | import org.apache.poi.util.Internal; | ||||
import org.apache.poi.util.POILogFactory; | import org.apache.poi.util.POILogFactory; | ||||
import org.apache.poi.util.POILogger; | import org.apache.poi.util.POILogger; | ||||
// we'll need multiple editions for | // we'll need multiple editions for | ||||
// the different formats | // the different formats | ||||
switch (id) { | switch (id) { | ||||
case 0: return new FormatRecord(5, "\"$\"#,##0_);\\(\"$\"#,##0\\)"); | |||||
case 1: return new FormatRecord(6, "\"$\"#,##0_);[Red]\\(\"$\"#,##0\\)"); | |||||
case 2: return new FormatRecord(7, "\"$\"#,##0.00_);\\(\"$\"#,##0.00\\)"); | |||||
case 3: return new FormatRecord(8, "\"$\"#,##0.00_);[Red]\\(\"$\"#,##0.00\\)"); | |||||
case 4: return new FormatRecord(0x2a, "_(\"$\"* #,##0_);_(\"$\"* \\(#,##0\\);_(\"$\"* \"-\"_);_(@_)"); | |||||
case 5: return new FormatRecord(0x29, "_(* #,##0_);_(* \\(#,##0\\);_(* \"-\"_);_(@_)"); | |||||
case 6: return new FormatRecord(0x2c, "_(\"$\"* #,##0.00_);_(\"$\"* \\(#,##0.00\\);_(\"$\"* \"-\"??_);_(@_)"); | |||||
case 7: return new FormatRecord(0x2b, "_(* #,##0.00_);_(* \\(#,##0.00\\);_(* \"-\"??_);_(@_)"); | |||||
case 0: return new FormatRecord(5, BuiltinFormats.getBuiltinFormat(5)); | |||||
case 1: return new FormatRecord(6, BuiltinFormats.getBuiltinFormat(6)); | |||||
case 2: return new FormatRecord(7, BuiltinFormats.getBuiltinFormat(7)); | |||||
case 3: return new FormatRecord(8, BuiltinFormats.getBuiltinFormat(8)); | |||||
case 4: return new FormatRecord(0x2a, BuiltinFormats.getBuiltinFormat(0x2a)); | |||||
case 5: return new FormatRecord(0x29, BuiltinFormats.getBuiltinFormat(0x29)); | |||||
case 6: return new FormatRecord(0x2c, BuiltinFormats.getBuiltinFormat(0x2c)); | |||||
case 7: return new FormatRecord(0x2b, BuiltinFormats.getBuiltinFormat(0x2b)); | |||||
} | } | ||||
throw new IllegalArgumentException("Unexpected id " + id); | throw new IllegalArgumentException("Unexpected id " + id); | ||||
} | } |
Iterator<FormatRecord> i = workbook.getFormats().iterator(); | Iterator<FormatRecord> i = workbook.getFormats().iterator(); | ||||
while (i.hasNext()) { | while (i.hasNext()) { | ||||
FormatRecord r = i.next(); | FormatRecord r = i.next(); | ||||
if (_formats.size() < r.getIndexCode() + 1) { | |||||
_formats.setSize(r.getIndexCode() + 1); | |||||
} | |||||
ensureFormatsSize(r.getIndexCode()); | |||||
_formats.set(r.getIndexCode(), r.getFormatString()); | _formats.set(r.getIndexCode(), r.getFormatString()); | ||||
} | } | ||||
} | } | ||||
* @return index of format. | * @return index of format. | ||||
*/ | */ | ||||
public short getFormat(String pFormat) { | public short getFormat(String pFormat) { | ||||
// Normalise the format string | |||||
String format; | String format; | ||||
if (pFormat.toUpperCase().equals("TEXT")) { | if (pFormat.toUpperCase().equals("TEXT")) { | ||||
format = "@"; | format = "@"; | ||||
format = pFormat; | format = pFormat; | ||||
} | } | ||||
// Merge in the built in formats if we haven't already | |||||
if (!_movedBuiltins) { | if (!_movedBuiltins) { | ||||
for (int i=0; i<_builtinFormats.length; i++) { | for (int i=0; i<_builtinFormats.length; i++) { | ||||
if (_formats.size() < i + 1) { | |||||
_formats.setSize(i + 1); | |||||
ensureFormatsSize(i); | |||||
if (_formats.get(i) == null) { | |||||
_formats.set(i, _builtinFormats[i]); | |||||
} else { | |||||
// The workbook overrides this default format | |||||
} | } | ||||
_formats.set(i, _builtinFormats[i]); | |||||
} | } | ||||
_movedBuiltins = true; | _movedBuiltins = true; | ||||
} | } | ||||
ListIterator<String> i; | |||||
i = _formats.listIterator(); | |||||
int ind; | |||||
while (i.hasNext()) { | |||||
ind = i.nextIndex(); | |||||
if (format.equals(i.next())) { | |||||
return (short) ind; | |||||
} | |||||
// See if we can find it | |||||
for(int i=0; i<_formats.size(); i++) { | |||||
if(format.equals(_formats.get(i))) { | |||||
return (short)i; | |||||
} | |||||
} | } | ||||
ind = _workbook.getFormat(format, true); | |||||
if (_formats.size() <= ind) | |||||
_formats.setSize(ind + 1); | |||||
_formats.set(ind, format); | |||||
return (short) ind; | |||||
// We can't find it, so add it as a new one | |||||
short index = _workbook.getFormat(format, true); | |||||
ensureFormatsSize(index); | |||||
_formats.set(index, format); | |||||
return index; | |||||
} | } | ||||
/** | /** | ||||
if (_movedBuiltins) { | if (_movedBuiltins) { | ||||
return _formats.get(index); | return _formats.get(index); | ||||
} | } | ||||
String fmt = _formats.get(index); | |||||
if (_builtinFormats.length > index && _builtinFormats[index] != null) { | if (_builtinFormats.length > index && _builtinFormats[index] != null) { | ||||
return _builtinFormats[index]; | |||||
// It's in the built in range | |||||
if (fmt != null) { | |||||
// It's been overriden, use that value | |||||
return fmt; | |||||
} else { | |||||
// Standard built in format | |||||
return _builtinFormats[index]; | |||||
} | |||||
} | } | ||||
return _formats.get(index); | |||||
return fmt; | |||||
} | } | ||||
/** | /** | ||||
public static int getNumberOfBuiltinBuiltinFormats() { | public static int getNumberOfBuiltinBuiltinFormats() { | ||||
return _builtinFormats.length; | return _builtinFormats.length; | ||||
} | } | ||||
/** | |||||
* Ensures that the formats list can hold entries | |||||
* up to and including the entry with this index | |||||
*/ | |||||
private void ensureFormatsSize(int index) { | |||||
if(_formats.size() <= index) { | |||||
_formats.setSize(index+1); | |||||
} | |||||
} | |||||
} | } |
import org.apache.poi.ss.usermodel.BaseTestDataFormat; | import org.apache.poi.ss.usermodel.BaseTestDataFormat; | ||||
import org.apache.poi.ss.usermodel.BuiltinFormats; | import org.apache.poi.ss.usermodel.BuiltinFormats; | ||||
import org.apache.poi.ss.usermodel.DataFormatter; | |||||
import org.apache.poi.ss.usermodel.DataFormat; | |||||
import org.apache.poi.xssf.XSSFITestDataProvider; | import org.apache.poi.xssf.XSSFITestDataProvider; | ||||
import org.apache.poi.xssf.XSSFTestDataSamples; | import org.apache.poi.xssf.XSSFTestDataSamples; | ||||
*/ | */ | ||||
public void test49928(){ | public void test49928(){ | ||||
XSSFWorkbook wb = XSSFTestDataSamples.openSampleWorkbook("49928.xlsx"); | XSSFWorkbook wb = XSSFTestDataSamples.openSampleWorkbook("49928.xlsx"); | ||||
DataFormatter df = new DataFormatter(); | |||||
XSSFSheet sheet = wb.getSheetAt(0); | |||||
XSSFCell cell = sheet.getRow(0).getCell(0); | |||||
XSSFCellStyle style = cell.getCellStyle(); | |||||
String poundFmt = "\"\u00a3\"#,##0;[Red]\\-\"\u00a3\"#,##0"; | |||||
// not expected normally, id of a custom format should be gerater | |||||
// than BuiltinFormats.FIRST_USER_DEFINED_FORMAT_INDEX | |||||
short poundFmtIdx = 6; | |||||
assertEquals(poundFmt, style.getDataFormatString()); | |||||
assertEquals(poundFmtIdx, style.getDataFormat()); | |||||
assertEquals("\u00a31", df.formatCellValue(cell)); | |||||
XSSFDataFormat dataFormat = wb.createDataFormat(); | |||||
assertEquals(poundFmtIdx, dataFormat.getFormat(poundFmt)); | |||||
assertEquals(poundFmt, dataFormat.getFormat(poundFmtIdx)); | |||||
doTest49928Core(wb); | |||||
// an attempt to register an existing format returns its index | // an attempt to register an existing format returns its index | ||||
int poundFmtIdx = wb.getSheetAt(0).getRow(0).getCell(0).getCellStyle().getDataFormat(); | |||||
assertEquals(poundFmtIdx, wb.getStylesSource().putNumberFormat(poundFmt)); | assertEquals(poundFmtIdx, wb.getStylesSource().putNumberFormat(poundFmt)); | ||||
// now create a custom format with Pound (\u00a3) | // now create a custom format with Pound (\u00a3) | ||||
DataFormat dataFormat = wb.createDataFormat(); | |||||
short customFmtIdx = dataFormat.getFormat("\u00a3##.00[Yellow]"); | short customFmtIdx = dataFormat.getFormat("\u00a3##.00[Yellow]"); | ||||
assertTrue(customFmtIdx > BuiltinFormats.FIRST_USER_DEFINED_FORMAT_INDEX ); | assertTrue(customFmtIdx > BuiltinFormats.FIRST_USER_DEFINED_FORMAT_INDEX ); | ||||
assertEquals("\u00a3##.00[Yellow]", dataFormat.getFormat(customFmtIdx)); | assertEquals("\u00a3##.00[Yellow]", dataFormat.getFormat(customFmtIdx)); | ||||
} | } | ||||
} | } |
package org.apache.poi.hssf.usermodel; | package org.apache.poi.hssf.usermodel; | ||||
import org.apache.poi.hssf.HSSFITestDataProvider; | import org.apache.poi.hssf.HSSFITestDataProvider; | ||||
import org.apache.poi.hssf.HSSFTestDataSamples; | |||||
import org.apache.poi.ss.usermodel.BaseTestDataFormat; | import org.apache.poi.ss.usermodel.BaseTestDataFormat; | ||||
import org.apache.poi.ss.usermodel.BuiltinFormats; | |||||
import org.apache.poi.ss.usermodel.DataFormat; | |||||
/** | /** | ||||
* Tests for {@link HSSFDataFormat} | * Tests for {@link HSSFDataFormat} | ||||
public TestHSSFDataFormat() { | public TestHSSFDataFormat() { | ||||
super(HSSFITestDataProvider.instance); | super(HSSFITestDataProvider.instance); | ||||
} | } | ||||
/** | |||||
* [Bug 49928] formatCellValue returns incorrect value for \u00a3 formatted cells | |||||
*/ | |||||
public void test49928(){ | |||||
HSSFWorkbook wb = HSSFTestDataSamples.openSampleWorkbook("49928.xls"); | |||||
doTest49928Core(wb); | |||||
// an attempt to register an existing format returns its index | |||||
int poundFmtIdx = wb.getSheetAt(0).getRow(0).getCell(0).getCellStyle().getDataFormat(); | |||||
assertEquals(poundFmtIdx, wb.createDataFormat().getFormat(poundFmt)); | |||||
// now create a custom format with Pound (\u00a3) | |||||
DataFormat dataFormat = wb.createDataFormat(); | |||||
short customFmtIdx = dataFormat.getFormat("\u00a3##.00[Yellow]"); | |||||
assertTrue(customFmtIdx >= BuiltinFormats.FIRST_USER_DEFINED_FORMAT_INDEX ); | |||||
assertEquals("\u00a3##.00[Yellow]", dataFormat.getFormat(customFmtIdx)); | |||||
} | |||||
} | } |
import junit.framework.TestCase; | import junit.framework.TestCase; | ||||
import org.apache.poi.ss.ITestDataProvider; | import org.apache.poi.ss.ITestDataProvider; | ||||
import org.apache.poi.xssf.XSSFTestDataSamples; | |||||
import org.apache.poi.xssf.usermodel.XSSFCell; | |||||
import org.apache.poi.xssf.usermodel.XSSFCellStyle; | |||||
import org.apache.poi.xssf.usermodel.XSSFDataFormat; | |||||
import org.apache.poi.xssf.usermodel.XSSFSheet; | |||||
import org.apache.poi.xssf.usermodel.XSSFWorkbook; | |||||
/** | /** | ||||
* Tests of implementation of {@link DataFormat} | * Tests of implementation of {@link DataFormat} | ||||
//read and verify the string representation | //read and verify the string representation | ||||
assertEquals(customFmt, df.getFormat((short)customIdx)); | assertEquals(customFmt, df.getFormat((short)customIdx)); | ||||
} | } | ||||
/** | |||||
* [Bug 49928] formatCellValue returns incorrect value for \u00a3 formatted cells | |||||
*/ | |||||
public abstract void test49928(); | |||||
protected final String poundFmt = "\"\u00a3\"#,##0;[Red]\\-\"\u00a3\"#,##0"; | |||||
public void doTest49928Core(Workbook wb){ | |||||
DataFormatter df = new DataFormatter(); | |||||
Sheet sheet = wb.getSheetAt(0); | |||||
Cell cell = sheet.getRow(0).getCell(0); | |||||
CellStyle style = cell.getCellStyle(); | |||||
String poundFmt = "\"\u00a3\"#,##0;[Red]\\-\"\u00a3\"#,##0"; | |||||
// not expected normally, id of a custom format should be greater | |||||
// than BuiltinFormats.FIRST_USER_DEFINED_FORMAT_INDEX | |||||
short poundFmtIdx = 6; | |||||
assertEquals(poundFmt, style.getDataFormatString()); | |||||
assertEquals(poundFmtIdx, style.getDataFormat()); | |||||
assertEquals("\u00a31", df.formatCellValue(cell)); | |||||
DataFormat dataFormat = wb.createDataFormat(); | |||||
assertEquals(poundFmtIdx, dataFormat.getFormat(poundFmt)); | |||||
assertEquals(poundFmt, dataFormat.getFormat(poundFmtIdx)); | |||||
} | |||||
} | } |