From cdd40f24796b2953943d2bdfa766131a5e76f27f Mon Sep 17 00:00:00 2001 From: Nick Burch Date: Fri, 21 Mar 2008 19:54:35 +0000 Subject: [PATCH] Get it to the point that existing .xslx files can be loaded+saved, and opened by excel without warning, and new files can be loaded but with a warning git-svn-id: https://svn.apache.org/repos/asf/poi/branches/ooxml@639779 13f79535-47bb-0310-9956-ffa450edef68 --- .../poi/xssf/model/SharedStringsTable.java | 9 +++++++- .../apache/poi/xssf/model/StylesTable.java | 21 +++++++++++++++++-- .../org/apache/poi/xssf/model/XSSFModel.java | 2 ++ .../xssf/usermodel/XSSFCreationHelper.java | 2 +- .../poi/xssf/usermodel/XSSFDataFormat.java | 13 +++++++++--- .../poi/xssf/usermodel/XSSFWorkbook.java | 13 +++++++++++- .../poi/xssf/usermodel/TestXSSFWorkbook.java | 18 ++++++++++++---- 7 files changed, 66 insertions(+), 12 deletions(-) diff --git a/src/ooxml/java/org/apache/poi/xssf/model/SharedStringsTable.java b/src/ooxml/java/org/apache/poi/xssf/model/SharedStringsTable.java index c6d8d2a862..769c7c312b 100644 --- a/src/ooxml/java/org/apache/poi/xssf/model/SharedStringsTable.java +++ b/src/ooxml/java/org/apache/poi/xssf/model/SharedStringsTable.java @@ -22,6 +22,8 @@ import java.io.InputStream; import java.io.OutputStream; import java.util.LinkedList; +import javax.xml.namespace.QName; + import org.apache.poi.ss.usermodel.SharedStringSource; import org.apache.xmlbeans.XmlException; import org.apache.xmlbeans.XmlOptions; @@ -95,6 +97,11 @@ public class SharedStringsTable implements SharedStringSource, XSSFModel { public void writeTo(OutputStream out) throws IOException { XmlOptions options = new XmlOptions(); options.setSaveOuter(); + options.setUseDefaultNamespace(); + + // Requests use of whitespace for easier reading + options.setSavePrettyPrint(); + SstDocument doc = SstDocument.Factory.newInstance(options); CTSst sst = doc.addNewSst(); sst.setCount(strings.size()); @@ -102,6 +109,6 @@ public class SharedStringsTable implements SharedStringSource, XSSFModel { for (String s : strings) { sst.addNewSi().setT(s); } - doc.save(out); + doc.save(out, options); } } diff --git a/src/ooxml/java/org/apache/poi/xssf/model/StylesTable.java b/src/ooxml/java/org/apache/poi/xssf/model/StylesTable.java index 3e8c0f54df..0cb06197ef 100644 --- a/src/ooxml/java/org/apache/poi/xssf/model/StylesTable.java +++ b/src/ooxml/java/org/apache/poi/xssf/model/StylesTable.java @@ -40,7 +40,9 @@ import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTNumFmt; import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTNumFmts; import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTStylesheet; import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTXf; -import org.openxmlformats.schemas.spreadsheetml.x2006.main.StyleSheetDocument;; +import org.openxmlformats.schemas.spreadsheetml.x2006.main.StyleSheetDocument; +import javax.xml.namespace.QName; + /** @@ -92,21 +94,27 @@ public class StylesTable implements StylesSource, XSSFModel { doc = StyleSheetDocument.Factory.parse(is); // Grab all the different bits we care about + if(doc.getStyleSheet().getNumFmts() != null) for (CTNumFmt nfmt : doc.getStyleSheet().getNumFmts().getNumFmtArray()) { numberFormats.put(nfmt.getNumFmtId(), nfmt.getFormatCode()); } + if(doc.getStyleSheet().getFonts() != null) for (CTFont font : doc.getStyleSheet().getFonts().getFontArray()) { fonts.add(font); } + if(doc.getStyleSheet().getFills() != null) for (CTFill fill : doc.getStyleSheet().getFills().getFillArray()) { fills.add(fill); } + if(doc.getStyleSheet().getBorders() != null) for (CTBorder border : doc.getStyleSheet().getBorders().getBorderArray()) { borders.add(border); } + if(doc.getStyleSheet().getCellStyleXfs() != null) for (CTXf xf : doc.getStyleSheet().getCellXfs().getXfArray()) { xfs.add(xf); } + if(doc.getStyleSheet().getCellStyleXfs() != null) for (CTXf xf : doc.getStyleSheet().getCellStyleXfs().getXfArray()) { styleXfs.add(xf); } @@ -221,6 +229,15 @@ public class StylesTable implements StylesSource, XSSFModel { public void writeTo(OutputStream out) throws IOException { XmlOptions options = new XmlOptions(); options.setSaveOuter(); + options.setUseDefaultNamespace(); + + // Requests use of whitespace for easier reading + options.setSavePrettyPrint(); + + // XXX This should not be needed, but apparently the setSaveOuter call above does not work in XMLBeans 2.2 + options.setSaveSyntheticDocumentElement( + new QName(CTStylesheet.type.getName().getNamespaceURI(), doc.getStyleSheet().getDomNode().getNodeName())); + // Work on the current one // Need to do this, as we don't handle @@ -254,6 +271,6 @@ public class StylesTable implements StylesSource, XSSFModel { // TODO // Save - doc.save(out); + doc.save(out, options); } } diff --git a/src/ooxml/java/org/apache/poi/xssf/model/XSSFModel.java b/src/ooxml/java/org/apache/poi/xssf/model/XSSFModel.java index 7fe1083e76..eedf391179 100644 --- a/src/ooxml/java/org/apache/poi/xssf/model/XSSFModel.java +++ b/src/ooxml/java/org/apache/poi/xssf/model/XSSFModel.java @@ -21,6 +21,8 @@ import java.io.InputStream; import java.io.OutputStream; public interface XSSFModel { + /** Read from the given InputStream */ public void readFrom(InputStream is) throws IOException; + /** Write to the supplied OutputStream, with default options */ public void writeTo(OutputStream out) throws IOException; } diff --git a/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFCreationHelper.java b/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFCreationHelper.java index 7941a86610..94eb5c1ec4 100644 --- a/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFCreationHelper.java +++ b/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFCreationHelper.java @@ -27,7 +27,7 @@ public class XSSFCreationHelper implements CreationHelper { workbook = wb; // Create the things we only ever need one of - dataFormat = new XSSFDataFormat(); + dataFormat = new XSSFDataFormat(workbook.getStylesSource()); } /** diff --git a/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFDataFormat.java b/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFDataFormat.java index 837b7ca5ef..6b5191d845 100644 --- a/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFDataFormat.java +++ b/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFDataFormat.java @@ -17,16 +17,23 @@ package org.apache.poi.xssf.usermodel; import org.apache.poi.ss.usermodel.DataFormat; +import org.apache.poi.ss.usermodel.StylesSource; /** - * TODO - figure out how this should really work for XSSF + * Handles data formats for XSSF. + * TODO Figure out if there are build in formats too */ public class XSSFDataFormat implements DataFormat { + private StylesSource stylesSource; + public XSSFDataFormat(StylesSource stylesSource) { + this.stylesSource = stylesSource; + } + public short getFormat(String format) { - return -1; + return (short)stylesSource.putNumberFormat(format); } public String getFormat(short index) { - return null; + return stylesSource.getNumberFormatAt((long)index); } } diff --git a/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFWorkbook.java b/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFWorkbook.java index d4ef042f02..71410a0861 100644 --- a/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFWorkbook.java +++ b/src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFWorkbook.java @@ -165,6 +165,7 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook { PackageRelationship rel = corePart.addRelationship(ppName, TargetMode.INTERNAL, REL); PackagePart part = corePart.getPackage().createPart(ppName, TYPE); + OutputStream out = part.getOutputStream(); model.writeTo(out); out.close(); @@ -188,6 +189,10 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook { CTBookView bv = bvs.addNewWorkbookView(); bv.setActiveTab(0); this.workbook.addNewSheets(); + + // We always require styles and shared strings + sharedStringSource = new SharedStringsTable(); + stylesSource = new StylesTable(); } public XSSFWorkbook(String path) throws IOException { @@ -203,11 +208,16 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook { // Load shared strings this.sharedStringSource = (SharedStringSource) SHARED_STRINGS.load(getCorePart()); + } catch(Exception e) { + throw new IOException("Unable to load shared strings - " + e.toString()); + } + try { // Load styles source this.stylesSource = (StylesSource) STYLES.load(getCorePart()); } catch(Exception e) { - throw new IOException(e.getMessage()); + e.printStackTrace(); + throw new IOException("Unable to load styles - " + e.toString()); } // Load individual sheets @@ -617,6 +627,7 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook { // Update our internal reference for the package part workbook.getSheets().getSheetArray(i).setId(rel.getId()); + workbook.getSheets().getSheetArray(i).setSheetId(sheetNumber); } // Write shared strings and styles diff --git a/src/ooxml/testcases/org/apache/poi/xssf/usermodel/TestXSSFWorkbook.java b/src/ooxml/testcases/org/apache/poi/xssf/usermodel/TestXSSFWorkbook.java index ca7dbb3736..8f52d618d0 100644 --- a/src/ooxml/testcases/org/apache/poi/xssf/usermodel/TestXSSFWorkbook.java +++ b/src/ooxml/testcases/org/apache/poi/xssf/usermodel/TestXSSFWorkbook.java @@ -23,6 +23,7 @@ import java.io.OutputStream; import junit.framework.TestCase; +import org.apache.poi.ss.usermodel.RichTextString; import org.apache.poi.ss.usermodel.Sheet; import org.apache.poi.ss.usermodel.StylesSource; import org.apache.poi.xssf.model.StylesTable; @@ -158,8 +159,10 @@ public class TestXSSFWorkbook extends TestCase { Sheet sheet2 = workbook.createSheet("sheet2"); Sheet sheet3 = workbook.createSheet("sheet3"); - sheet1.createRow(0); - sheet1.createRow(1); + RichTextString rts = workbook.getCreationHelper().createRichTextString("hello world"); + + sheet1.createRow(0).createCell((short)0).setCellValue(1.2); + sheet1.createRow(1).createCell((short)0).setCellValue(rts); sheet2.createRow(0); assertEquals(0, workbook.getSheetAt(0).getFirstRowNum()); @@ -184,9 +187,9 @@ public class TestXSSFWorkbook extends TestCase { PackagePart wbPart = pkg.getPart(PackagingURIHelper.createPartName("/xl/workbook.xml")); - // Links to the three sheets + // Links to the three sheets, shared strings and styles assertTrue(wbPart.hasRelationships()); - assertEquals(3, wbPart.getRelationships().size()); + assertEquals(5, wbPart.getRelationships().size()); // Load back the XSSFWorkbook workbook = new XSSFWorkbook(pkg); @@ -195,12 +198,19 @@ public class TestXSSFWorkbook extends TestCase { assertNotNull(workbook.getSheetAt(1)); assertNotNull(workbook.getSheetAt(2)); + assertNotNull(workbook.getSharedStringSource()); + assertNotNull(workbook.getStylesSource()); + assertEquals(0, workbook.getSheetAt(0).getFirstRowNum()); assertEquals(1, workbook.getSheetAt(0).getLastRowNum()); assertEquals(0, workbook.getSheetAt(1).getFirstRowNum()); assertEquals(0, workbook.getSheetAt(1).getLastRowNum()); assertEquals(-1, workbook.getSheetAt(2).getFirstRowNum()); assertEquals(-1, workbook.getSheetAt(2).getLastRowNum()); + + sheet1 = workbook.getSheetAt(0); + assertEquals(1.2, sheet1.getRow(0).getCell(0).getNumericCellValue(), 0.0001); + assertEquals("hello world", sheet1.getRow(1).getCell(0).getRichStringCellValue().getString()); } public void testExisting() throws Exception { -- 2.39.5