summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMarkus Mohrhard <markus.mohrhard@collabora.co.uk>2014-03-01 12:44:03 +0100
committerMarkus Mohrhard <markus.mohrhard@googlemail.com>2014-03-01 16:23:09 +0100
commite34870c2396db160c15e3e9bbf3efabf55ee2839 (patch)
treeefcdb1fe313e793ba14999e34eac4d6ade8c596e
parent6ba394e6119fee2c5424b6c3b5eb3f4276cc2769 (diff)
support OOXML strict documents in Calc
Change-Id: I277d76aeec28e173d913ccc1506464afe4d09c6d
-rw-r--r--include/oox/core/contexthandler.hxx1
-rw-r--r--include/oox/core/filterbase.hxx5
-rw-r--r--include/oox/core/relations.hxx11
-rw-r--r--include/oox/core/xmlfilterbase.hxx2
-rw-r--r--oox/source/core/contexthandler.cxx5
-rw-r--r--oox/source/core/relations.cxx37
-rw-r--r--oox/source/core/xmlfilterbase.cxx30
-rw-r--r--sc/source/filter/oox/excelfilter.cxx2
-rw-r--r--sc/source/filter/oox/workbookfragment.cxx17
-rw-r--r--sc/source/filter/oox/worksheetfragment.cxx8
10 files changed, 101 insertions, 17 deletions
diff --git a/include/oox/core/contexthandler.hxx b/include/oox/core/contexthandler.hxx
index 272927a7c96e..2dda0122e11f 100644
--- a/include/oox/core/contexthandler.hxx
+++ b/include/oox/core/contexthandler.hxx
@@ -71,6 +71,7 @@ public:
OUString getFragmentPathFromRelId( const OUString& rRelId ) const;
/** Returns the full fragment path for the first relation of the passed type. */
OUString getFragmentPathFromFirstType( const OUString& rType ) const;
+ OUString getFragmentPathFromFirstTypeFromOfficeDoc( const OUString& rType ) const;
// com.sun.star.xml.sax.XFastContextHandler interface ---------------------
diff --git a/include/oox/core/filterbase.hxx b/include/oox/core/filterbase.hxx
index 96e488ccc441..45c1ef591132 100644
--- a/include/oox/core/filterbase.hxx
+++ b/include/oox/core/filterbase.hxx
@@ -20,7 +20,6 @@
#ifndef INCLUDED_OOX_CORE_FILTERBASE_HXX
#define INCLUDED_OOX_CORE_FILTERBASE_HXX
-#include <memory>
#include <com/sun/star/beans/NamedValue.hpp>
#include <com/sun/star/document/XExporter.hpp>
#include <com/sun/star/document/XFilter.hpp>
@@ -37,6 +36,8 @@
#include <oox/helper/storagebase.hxx>
#include <oox/dllapi.h>
+#include <boost/scoped_ptr.hpp>
+
namespace com { namespace sun { namespace star {
namespace awt { struct DeviceInfo; }
namespace frame { class XFrame; }
@@ -283,7 +284,7 @@ private:
const ::com::sun::star::uno::Reference< ::com::sun::star::io::XStream >& rxOutStream ) const = 0;
private:
- ::std::auto_ptr< FilterBaseImpl > mxImpl;
+ boost::scoped_ptr< FilterBaseImpl > mxImpl;
};
// ============================================================================
diff --git a/include/oox/core/relations.hxx b/include/oox/core/relations.hxx
index c94e293efafc..05d00adbfeeb 100644
--- a/include/oox/core/relations.hxx
+++ b/include/oox/core/relations.hxx
@@ -30,11 +30,16 @@ namespace core {
// ============================================================================
-/** Expands to an OUString containing an 'officeDocument' relation type created
+/** Expands to an OUString containing an 'officeDocument' transitional relation type created
from the passed literal(!) ASCII(!) character array. */
#define CREATE_OFFICEDOC_RELATION_TYPE( ascii ) \
( "http://schemas.openxmlformats.org/officeDocument/2006/relationships/" ascii )
+/** Expands to an OUString containing an 'officeDocument' strict relation type created
+ from the passed literal(!) ASCII(!) character array. */
+#define CREATE_OFFICEDOC_RELATION_TYPE_STRICT( ascii ) \
+ ( "http://purl.oclc.org/ooxml/officeDocument/relationships/" ascii )
+
/** Expands to an OUString containing a 'package' relation type created from
the passed literal(!) ASCII(!) character array. */
#define CREATE_PACKAGE_RELATION_TYPE( ascii ) \
@@ -74,8 +79,11 @@ public:
const Relation* getRelationFromRelId( const OUString& rId ) const;
/** Returns the first relation with the passed type. */
const Relation* getRelationFromFirstType( const OUString& rType ) const;
+ /** Returns the first relation with the passed type. */
+ const Relation* getRelationFromFirstTypeFromOfficeDoc( const OUString& rType ) const;
/** Finds all relations associated with the passed type. */
RelationsRef getRelationsFromType( const OUString& rType ) const;
+ RelationsRef getRelationsFromTypeFromOfficeDoc( const OUString& rType ) const;
/** Returns the external target of the relation with the passed relation identifier. */
OUString getExternalTargetFromRelId( const OUString& rRelId ) const;
@@ -88,6 +96,7 @@ public:
OUString getFragmentPathFromRelId( const OUString& rRelId ) const;
/** Returns the full fragment path for the first relation of the passed type. */
OUString getFragmentPathFromFirstType( const OUString& rType ) const;
+ OUString getFragmentPathFromFirstTypeFromOfficeDoc( const OUString& rType ) const;
private:
OUString maFragmentPath;
diff --git a/include/oox/core/xmlfilterbase.hxx b/include/oox/core/xmlfilterbase.hxx
index 604f220c4a1d..351910d29926 100644
--- a/include/oox/core/xmlfilterbase.hxx
+++ b/include/oox/core/xmlfilterbase.hxx
@@ -101,6 +101,8 @@ public:
used for fragments referred by the root relations. */
OUString getFragmentPathFromFirstType( const OUString& rType );
+ OUString getFragmentPathFromFirstTypeFromOfficeDoc( const OUString& rPart );
+
/** Imports a fragment using the passed fragment handler, which contains
the full path to the fragment stream.
diff --git a/oox/source/core/contexthandler.cxx b/oox/source/core/contexthandler.cxx
index 296ed71b9132..806d97503330 100644
--- a/oox/source/core/contexthandler.cxx
+++ b/oox/source/core/contexthandler.cxx
@@ -77,6 +77,11 @@ OUString ContextHandler::getFragmentPathFromFirstType( const OUString& rType ) c
return mxBaseData->mxRelations->getFragmentPathFromFirstType( rType );
}
+OUString ContextHandler::getFragmentPathFromFirstTypeFromOfficeDoc( const OUString& rType ) const
+{
+ return mxBaseData->mxRelations->getFragmentPathFromFirstTypeFromOfficeDoc( rType );
+}
+
void ContextHandler::implSetLocator( const Reference< XLocator >& rxLocator )
{
mxBaseData->mxLocator = rxLocator;
diff --git a/oox/source/core/relations.cxx b/oox/source/core/relations.cxx
index 5b726a514e06..37425317ca76 100644
--- a/oox/source/core/relations.cxx
+++ b/oox/source/core/relations.cxx
@@ -43,7 +43,20 @@ OUString lclAppendFileName( const OUString& rPath, const OUString& rFileName )
OUStringBuffer( rPath ).append( '/' ).append( rFileName ).makeStringAndClear();
}
-} // namespace
+OUString createOfficeDocRelationTypeTransitional(const OUString& rType)
+{
+ static const OUString aTransitionalBase("http://schemas.openxmlformats.org/officeDocument/2006/relationships/");
+ return aTransitionalBase + rType;
+}
+
+OUString createOfficeDocRelationTypeStrict(const OUString& rType)
+{
+ static const OUString aStrictBase("http://purl.oclc.org/ooxml/officeDocument/relationships/");
+ return aStrictBase + rType;
+}
+
+}
+
@@ -75,6 +88,16 @@ RelationsRef Relations::getRelationsFromType( const OUString& rType ) const
return xRelations;
}
+RelationsRef Relations::getRelationsFromTypeFromOfficeDoc( const OUString& rType ) const
+{
+ RelationsRef xRelations( new Relations( maFragmentPath ) );
+ for( const_iterator aIt = begin(), aEnd = end(); aIt != aEnd; ++aIt )
+ if( aIt->second.maType.equalsIgnoreAsciiCase( createOfficeDocRelationTypeTransitional(rType) ) ||
+ aIt->second.maType.equalsIgnoreAsciiCase( createOfficeDocRelationTypeStrict(rType) ))
+ (*xRelations)[ aIt->first ] = aIt->second;
+ return xRelations;
+}
+
OUString Relations::getExternalTargetFromRelId( const OUString& rRelId ) const
{
const Relation* pRelation = getRelationFromRelId( rRelId );
@@ -132,7 +155,17 @@ OUString Relations::getFragmentPathFromFirstType( const OUString& rType ) const
return pRelation ? getFragmentPathFromRelation( *pRelation ) : OUString();
}
-
+OUString Relations::getFragmentPathFromFirstTypeFromOfficeDoc( const OUString& rType ) const
+{
+ OUString aTransitionalType(createOfficeDocRelationTypeTransitional(rType));
+ const Relation* pRelation = getRelationFromFirstType( aTransitionalType );
+ if(!pRelation)
+ {
+ OUString aStrictType = createOfficeDocRelationTypeStrict(rType);
+ pRelation = getRelationFromFirstType( aStrictType );
+ }
+ return pRelation ? getFragmentPathFromRelation( *pRelation ) : OUString();
+}
} // namespace core
} // namespace oox
diff --git a/oox/source/core/xmlfilterbase.cxx b/oox/source/core/xmlfilterbase.cxx
index adbecaa4fdb6..ecf902e52f53 100644
--- a/oox/source/core/xmlfilterbase.cxx
+++ b/oox/source/core/xmlfilterbase.cxx
@@ -233,6 +233,36 @@ OUString XmlFilterBase::getFragmentPathFromFirstType( const OUString& rType )
return importRelations( OUString() )->getFragmentPathFromFirstType( rType );
}
+namespace {
+
+OUString getTransitionalRelationshipOfficeDocType(const OUString& rPart)
+{
+ static const OUString aBase("http://schemas.openxmlformats.org/officeDocument/2006/relationships/");
+ return aBase + rPart;
+}
+
+OUString getStrictRelationshipOfficeDocType(const OUString& rPart)
+{
+ static const OUString aBase("http://purl.oclc.org/ooxml/officeDocument/relationships/");
+ return aBase + rPart;
+}
+
+}
+
+OUString XmlFilterBase::getFragmentPathFromFirstTypeFromOfficeDoc( const OUString& rPart )
+{
+ // importRelations() caches the relations map for subsequence calls
+ const OUString aTransitionalRelationshipType = getTransitionalRelationshipOfficeDocType(rPart);
+ OUString aFragment = importRelations( OUString() )->getFragmentPathFromFirstType( aTransitionalRelationshipType );
+ if(aFragment.isEmpty())
+ {
+ const OUString aStrictRelationshipType = getStrictRelationshipOfficeDocType(rPart);
+ aFragment = importRelations( OUString() )->getFragmentPathFromFirstType( aStrictRelationshipType );
+ }
+
+ return aFragment;
+}
+
bool XmlFilterBase::importFragment( const rtl::Reference<FragmentHandler>& rxHandler )
{
return importFragment(rxHandler, mxImpl->maFastParser);
diff --git a/sc/source/filter/oox/excelfilter.cxx b/sc/source/filter/oox/excelfilter.cxx
index 0bc886cd1a18..063d5f1bb919 100644
--- a/sc/source/filter/oox/excelfilter.cxx
+++ b/sc/source/filter/oox/excelfilter.cxx
@@ -101,7 +101,7 @@ bool ExcelFilter::importDocument() throw()
this variable (nonpro only). */
//OOX_DUMP_FILE( ::oox::dump::xlsb::Dumper );
- OUString aWorkbookPath = getFragmentPathFromFirstType( CREATE_OFFICEDOC_RELATION_TYPE( "officeDocument" ) );
+ OUString aWorkbookPath = getFragmentPathFromFirstTypeFromOfficeDoc( "officeDocument" );
if( aWorkbookPath.isEmpty() )
return false;
diff --git a/sc/source/filter/oox/workbookfragment.cxx b/sc/source/filter/oox/workbookfragment.cxx
index 625c5ffee9af..5342fde0401b 100644
--- a/sc/source/filter/oox/workbookfragment.cxx
+++ b/sc/source/filter/oox/workbookfragment.cxx
@@ -360,26 +360,26 @@ void WorkbookFragment::finalizeImport()
ISegmentProgressBarRef xGlobalSegment = getProgressBar().createSegment( PROGRESS_LENGTH_GLOBALS );
// read the theme substream
- OUString aThemeFragmentPath = getFragmentPathFromFirstType( CREATE_OFFICEDOC_RELATION_TYPE( "theme" ) );
+ OUString aThemeFragmentPath = getFragmentPathFromFirstTypeFromOfficeDoc( "theme" );
if( !aThemeFragmentPath.isEmpty() )
importOoxFragment( new ThemeFragmentHandler( getFilter(), aThemeFragmentPath, getTheme() ) );
xGlobalSegment->setPosition( 0.25 );
// read the styles substream (requires finalized theme buffer)
- OUString aStylesFragmentPath = getFragmentPathFromFirstType( CREATE_OFFICEDOC_RELATION_TYPE( "styles" ) );
+ OUString aStylesFragmentPath = getFragmentPathFromFirstTypeFromOfficeDoc( "styles" );
if( !aStylesFragmentPath.isEmpty() )
importOoxFragment( new StylesFragment( *this, aStylesFragmentPath ) );
xGlobalSegment->setPosition( 0.5 );
// read the shared string table substream (requires finalized styles buffer)
- OUString aSstFragmentPath = getFragmentPathFromFirstType( CREATE_OFFICEDOC_RELATION_TYPE( "sharedStrings" ) );
+ OUString aSstFragmentPath = getFragmentPathFromFirstTypeFromOfficeDoc( "sharedStrings" );
if( !aSstFragmentPath.isEmpty() )
if (!importOoxFragment( new SharedStringsFragment( *this, aSstFragmentPath ) ))
importOoxFragment(new SharedStringsFragment(*this, aSstFragmentPath.replaceFirst("sharedStrings","SharedStrings")));
xGlobalSegment->setPosition( 0.75 );
// read the connections substream
- OUString aConnFragmentPath = getFragmentPathFromFirstType( CREATE_OFFICEDOC_RELATION_TYPE( "connections" ) );
+ OUString aConnFragmentPath = getFragmentPathFromFirstTypeFromOfficeDoc( "connections" );
if( !aConnFragmentPath.isEmpty() )
importOoxFragment( new ConnectionsFragment( *this, aConnFragmentPath ) );
xGlobalSegment->setPosition( 1.0 );
@@ -412,14 +412,17 @@ void WorkbookFragment::finalizeImport()
// get the sheet type according to the relations type
WorksheetType eSheetType = SHEETTYPE_EMPTYSHEET;
- if( pRelation->maType == CREATE_OFFICEDOC_RELATION_TYPE( "worksheet" ) )
+ if( pRelation->maType == CREATE_OFFICEDOC_RELATION_TYPE( "worksheet" ) ||
+ pRelation->maType == CREATE_OFFICEDOC_RELATION_TYPE_STRICT( "worksheet" ))
eSheetType = SHEETTYPE_WORKSHEET;
- else if( pRelation->maType == CREATE_OFFICEDOC_RELATION_TYPE( "chartsheet" ) )
+ else if( pRelation->maType == CREATE_OFFICEDOC_RELATION_TYPE( "chartsheet" ) ||
+ pRelation->maType == CREATE_OFFICEDOC_RELATION_TYPE_STRICT( "chartsheet" ))
eSheetType = SHEETTYPE_CHARTSHEET;
else if( (pRelation->maType == CREATE_MSOFFICE_RELATION_TYPE( "xlMacrosheet" )) ||
(pRelation->maType == CREATE_MSOFFICE_RELATION_TYPE( "xlIntlMacrosheet" )) )
eSheetType = SHEETTYPE_MACROSHEET;
- else if( pRelation->maType == CREATE_OFFICEDOC_RELATION_TYPE( "dialogsheet" ) )
+ else if( pRelation->maType == CREATE_OFFICEDOC_RELATION_TYPE( "dialogsheet" ) ||
+ pRelation->maType == CREATE_OFFICEDOC_RELATION_TYPE_STRICT(" dialogsheet" ))
eSheetType = SHEETTYPE_DIALOGSHEET;
OSL_ENSURE( eSheetType != SHEETTYPE_EMPTYSHEET, "WorkbookFragment::finalizeImport - unknown sheet type" );
if( eSheetType != SHEETTYPE_EMPTYSHEET )
diff --git a/sc/source/filter/oox/worksheetfragment.cxx b/sc/source/filter/oox/worksheetfragment.cxx
index 81b6411b945b..9ad408a8bf92 100644
--- a/sc/source/filter/oox/worksheetfragment.cxx
+++ b/sc/source/filter/oox/worksheetfragment.cxx
@@ -203,12 +203,12 @@ WorksheetFragment::WorksheetFragment( const WorksheetHelper& rHelper, const OUSt
WorksheetFragmentBase( rHelper, rFragmentPath )
{
// import data tables related to this worksheet
- RelationsRef xTableRels = getRelations().getRelationsFromType( CREATE_OFFICEDOC_RELATION_TYPE( "table" ) );
+ RelationsRef xTableRels = getRelations().getRelationsFromTypeFromOfficeDoc( "table" );
for( Relations::const_iterator aIt = xTableRels->begin(), aEnd = xTableRels->end(); aIt != aEnd; ++aIt )
importOoxFragment( new TableFragment( *this, getFragmentPathFromRelation( aIt->second ) ) );
// import comments related to this worksheet
- OUString aCommentsFragmentPath = getFragmentPathFromFirstType( CREATE_OFFICEDOC_RELATION_TYPE( "comments" ) );
+ OUString aCommentsFragmentPath = getFragmentPathFromFirstTypeFromOfficeDoc( "comments" );
if( !aCommentsFragmentPath.isEmpty() )
importOoxFragment( new CommentsFragment( *this, aCommentsFragmentPath ) );
}
@@ -473,12 +473,12 @@ void WorksheetFragment::initializeImport()
initializeWorksheetImport();
// import query table fragments related to this worksheet
- RelationsRef xQueryRels = getRelations().getRelationsFromType( CREATE_OFFICEDOC_RELATION_TYPE( "queryTable" ) );
+ RelationsRef xQueryRels = getRelations().getRelationsFromTypeFromOfficeDoc( "queryTable" );
for( Relations::const_iterator aIt = xQueryRels->begin(), aEnd = xQueryRels->end(); aIt != aEnd; ++aIt )
importOoxFragment( new QueryTableFragment( *this, getFragmentPathFromRelation( aIt->second ) ) );
// import pivot table fragments related to this worksheet
- RelationsRef xPivotRels = getRelations().getRelationsFromType( CREATE_OFFICEDOC_RELATION_TYPE( "pivotTable" ) );
+ RelationsRef xPivotRels = getRelations().getRelationsFromTypeFromOfficeDoc( "pivotTable" );
for( Relations::const_iterator aIt = xPivotRels->begin(), aEnd = xPivotRels->end(); aIt != aEnd; ++aIt )
importOoxFragment( new PivotTableFragment( *this, getFragmentPathFromRelation( aIt->second ) ) );
}