diff options
author | Markus Mohrhard <markus.mohrhard@googlemail.com> | 2015-05-15 04:36:13 +0200 |
---|---|---|
committer | Markus Mohrhard <markus.mohrhard@googlemail.com> | 2015-05-15 05:25:11 +0200 |
commit | 52077be6a1053f6c9c0118d6c116780fc27d43b5 (patch) | |
tree | 49410694101eb4431a7839f647048401aa758037 | |
parent | 7fde89045f21019c84f461da566369440e1106dd (diff) |
support iconSets in extLst entries
Change-Id: Iec293ec3541b87b16f5a8097d51b878166814670
-rw-r--r-- | oox/source/core/xmlfilterbase.cxx | 2 | ||||
-rw-r--r-- | oox/source/token/namespaces-strict.txt | 4 | ||||
-rw-r--r-- | oox/source/token/namespaces.hxx.tail | 2 | ||||
-rw-r--r-- | oox/source/token/namespaces.txt | 4 | ||||
-rw-r--r-- | oox/source/token/tokens.txt | 1 | ||||
-rw-r--r-- | sc/source/filter/inc/condformatbuffer.hxx | 8 | ||||
-rw-r--r-- | sc/source/filter/inc/condformatcontext.hxx | 10 | ||||
-rw-r--r-- | sc/source/filter/inc/extlstcontext.hxx | 21 | ||||
-rw-r--r-- | sc/source/filter/oox/condformatbuffer.cxx | 28 | ||||
-rw-r--r-- | sc/source/filter/oox/condformatcontext.cxx | 45 | ||||
-rw-r--r-- | sc/source/filter/oox/extlstcontext.cxx | 182 |
11 files changed, 255 insertions, 52 deletions
diff --git a/oox/source/core/xmlfilterbase.cxx b/oox/source/core/xmlfilterbase.cxx index 772142b7bf4c..cde386b59944 100644 --- a/oox/source/core/xmlfilterbase.cxx +++ b/oox/source/core/xmlfilterbase.cxx @@ -146,7 +146,7 @@ struct NamespaceIds: public rtl::StaticWithInit< NMSP_mce, NMSP_mceTest, NMSP_dsp, - NMSP_xlsExtLst + NMSP_xls14Lst }; Sequence< beans::Pair< OUString, sal_Int32 > > aRet(SAL_N_ELEMENTS(namespaceIds)); diff --git a/oox/source/token/namespaces-strict.txt b/oox/source/token/namespaces-strict.txt index 39a4fb58324a..9359f8b48094 100644 --- a/oox/source/token/namespaces-strict.txt +++ b/oox/source/token/namespaces-strict.txt @@ -78,5 +78,5 @@ a14 http://schemas.microsoft.com/office/drawingml/2010/main # extlst namespaces -# xlsExtLst for features introduced by excel 2010 -xlsExtLst http://schemas.microsoft.com/office/spreadsheetml/2009/9/main +# xls14Lst for features introduced by excel 2010 +xls14Lst http://schemas.microsoft.com/office/spreadsheetml/2009/9/main diff --git a/oox/source/token/namespaces.hxx.tail b/oox/source/token/namespaces.hxx.tail index 378b0daf135a..de5cc21d86a6 100644 --- a/oox/source/token/namespaces.hxx.tail +++ b/oox/source/token/namespaces.hxx.tail @@ -46,7 +46,7 @@ inline sal_Int32 getNamespace( sal_Int32 nToken ) { return nToken & NMSP_MASK; } #define VMLX_TOKEN( token ) OOX_TOKEN( vmlExcel, token ) #define XDR_TOKEN( token ) OOX_TOKEN( dmlSpreadDr, token ) #define XLS_TOKEN( token ) OOX_TOKEN( xls, token ) -#define XLS_EXT_TOKEN( token ) OOX_TOKEN( xlsExtLst, token ) +#define XLS14_TOKEN( token ) OOX_TOKEN( xls14Lst, token ) #define XM_TOKEN( token ) OOX_TOKEN( xm, token ) #define XML_TOKEN( token ) OOX_TOKEN( xml, token ) #define VMLPPT_TOKEN( token ) OOX_TOKEN( vmlPowerpoint, token ) diff --git a/oox/source/token/namespaces.txt b/oox/source/token/namespaces.txt index 98792d076342..face9d62db10 100644 --- a/oox/source/token/namespaces.txt +++ b/oox/source/token/namespaces.txt @@ -78,5 +78,5 @@ a14 http://schemas.microsoft.com/office/drawing/2010/main # extlst namespaces -# xlsExtLst for features introduced by excel 2010 -xlsExtLst http://schemas.microsoft.com/office/spreadsheetml/2009/9/main +# xls14Lst for features introduced by excel 2010 +xls14Lst http://schemas.microsoft.com/office/spreadsheetml/2009/9/main diff --git a/oox/source/token/tokens.txt b/oox/source/token/tokens.txt index 8a2dd9b1eb66..c26e957f6d6b 100644 --- a/oox/source/token/tokens.txt +++ b/oox/source/token/tokens.txt @@ -1136,6 +1136,7 @@ centerGroup centered certificateBanner cf +cfIcon cfRule cfvo ch diff --git a/sc/source/filter/inc/condformatbuffer.hxx b/sc/source/filter/inc/condformatbuffer.hxx index 32042cef3d63..3e6f05a90d28 100644 --- a/sc/source/filter/inc/condformatbuffer.hxx +++ b/sc/source/filter/inc/condformatbuffer.hxx @@ -75,6 +75,7 @@ struct ColorScaleRuleModelEntry bool mbMax; bool mbPercent; bool mbPercentile; + bool mbNum; OUString maFormula; ColorScaleRuleModelEntry(): @@ -83,7 +84,8 @@ struct ColorScaleRuleModelEntry mbMin(false), mbMax(false), mbPercent(false), - mbPercentile(false) {} + mbPercentile(false), + mbNum(false) {} }; class ColorScaleRule : public WorksheetHelper @@ -125,9 +127,10 @@ private: class IconSetRule : public WorksheetHelper { public: - IconSetRule( const CondFormat& rFormat ); + IconSetRule( const WorksheetHelper& rParent ); void importCfvo( const AttributeList& rAttribs ); void importAttribs( const AttributeList& rAttribs ); + void importFormula(const OUString& rFormula); void SetData( ScIconSetFormat* pFormat, ScDocument* pDoc, const ScAddress& rAddr ); @@ -135,6 +138,7 @@ private: std::vector< ColorScaleRuleModelEntry > maEntries; std::unique_ptr<ScIconSetFormatData> mxFormatData; OUString maIconSetType; + bool mbCustom; }; /** Represents a single rule in a conditional formatting. */ diff --git a/sc/source/filter/inc/condformatcontext.hxx b/sc/source/filter/inc/condformatcontext.hxx index 4606bde4c683..ff85e1832ab8 100644 --- a/sc/source/filter/inc/condformatcontext.hxx +++ b/sc/source/filter/inc/condformatcontext.hxx @@ -23,6 +23,8 @@ #include "condformatbuffer.hxx" #include "excelhandlers.hxx" +class IconSetRule; + namespace oox { namespace xls { @@ -55,12 +57,16 @@ private: class IconSetContext : public WorksheetContextBase { public: - explicit IconSetContext( CondFormatContext& rFormat, CondFormatRuleRef xRule ); + explicit IconSetContext( WorksheetContextBase& rParent, IconSetRule* pIconSet ); virtual oox::core::ContextHandlerRef onCreateContext( sal_Int32 nElement, const AttributeList& rAttribs ) SAL_OVERRIDE; virtual void onStartElement( const AttributeList& rAttribs ) SAL_OVERRIDE; + virtual void onCharacters(const OUString& rChars) SAL_OVERRIDE; + virtual void onEndElement() SAL_OVERRIDE; + private: - CondFormatRuleRef mxRule; + IconSetRule* mpIconSet; + OUString maChars; }; class CondFormatContext : public WorksheetContextBase diff --git a/sc/source/filter/inc/extlstcontext.hxx b/sc/source/filter/inc/extlstcontext.hxx index 43a4cacf7f6e..598adbd5f6e3 100644 --- a/sc/source/filter/inc/extlstcontext.hxx +++ b/sc/source/filter/inc/extlstcontext.hxx @@ -13,11 +13,16 @@ #include "excelhandlers.hxx" #include "worksheetfragment.hxx" +#include <boost/ptr_container/ptr_vector.hpp> + struct ScDataBarFormatData; +class ScFormatEntry; namespace oox { namespace xls { +class IconSetRule; + class ExtCfRuleContext : public WorksheetContextBase { public: @@ -32,6 +37,22 @@ private: bool mbFirstEntry; }; +class ExtConditionalFormattingContext : public WorksheetContextBase +{ +public: + explicit ExtConditionalFormattingContext(WorksheetContextBase& rFragment); + + virtual ::oox::core::ContextHandlerRef onCreateContext( sal_Int32 nElement, const AttributeList& rAttribs ) SAL_OVERRIDE; + virtual void onStartElement( const AttributeList& rAttribs ) SAL_OVERRIDE; + virtual void onCharacters(const OUString& rCharacters) SAL_OVERRIDE; + virtual void onEndElement() SAL_OVERRIDE; + +private: + OUString aChars; + boost::ptr_vector<ScFormatEntry> maEntries; + IconSetRule* mpCurrentRule; +}; + /** * Handle ExtLst entries in xlsx. These entries are a way to extend the standard * without actually changing it diff --git a/sc/source/filter/oox/condformatbuffer.cxx b/sc/source/filter/oox/condformatbuffer.cxx index 16946aa4b7ab..7483a06ac605 100644 --- a/sc/source/filter/oox/condformatbuffer.cxx +++ b/sc/source/filter/oox/condformatbuffer.cxx @@ -118,9 +118,10 @@ void SetCfvoData( ColorScaleRuleModelEntry* pEntry, const AttributeList& rAttrib double nVal = rAttribs.getDouble( XML_val, 0.0 ); pEntry->mnVal = nVal; } + if (aType == "num") { - // nothing to do + pEntry->mbNum = true; } else if( aType == "min" ) { @@ -235,6 +236,8 @@ ScColorScaleEntry* ConvertToModel( const ColorScaleRuleModelEntry& rEntry, ScDoc pEntry->SetType(COLORSCALE_PERCENT); if(rEntry.mbPercentile) pEntry->SetType(COLORSCALE_PERCENTILE); + if (rEntry.mbNum) + pEntry->SetType(COLORSCALE_VALUE); if(!rEntry.maFormula.isEmpty()) { @@ -327,9 +330,10 @@ void DataBarRule::SetData( ScDataBarFormat* pFormat, ScDocument* pDoc, const ScA pFormat->SetDataBarData(mxFormat.release()); } -IconSetRule::IconSetRule( const CondFormat& rFormat ): - WorksheetHelper( rFormat ), - mxFormatData( new ScIconSetFormatData ) +IconSetRule::IconSetRule( const WorksheetHelper& rParent ): + WorksheetHelper( rParent ), + mxFormatData( new ScIconSetFormatData ), + mbCustom(false) { } @@ -346,8 +350,24 @@ void IconSetRule::importAttribs( const AttributeList& rAttribs ) maIconSetType = rAttribs.getString( XML_iconSet, OUString("3TrafficLights1") ); mxFormatData->mbShowValue = rAttribs.getBool( XML_showValue, true ); mxFormatData->mbReverse = rAttribs.getBool( XML_reverse, false ); + mbCustom = rAttribs.getBool(XML_custom, false); +} + +void IconSetRule::importFormula(const OUString& rFormula) +{ + ColorScaleRuleModelEntry& rEntry = maEntries.back(); + if (rEntry.mbNum || + rEntry.mbPercent || + rEntry.mbPercentile) + { + double nVal = rFormula.toDouble(); + rEntry.mnVal = nVal; + } + else if (!rFormula.isEmpty()) + rEntry.maFormula = rFormula; } + void IconSetRule::SetData( ScIconSetFormat* pFormat, ScDocument* pDoc, const ScAddress& rPos ) { for(size_t i = 0; i < maEntries.size(); ++i) diff --git a/sc/source/filter/oox/condformatcontext.cxx b/sc/source/filter/oox/condformatcontext.cxx index 7153e1a6780b..08ce68b7ad75 100644 --- a/sc/source/filter/oox/condformatcontext.cxx +++ b/sc/source/filter/oox/condformatcontext.cxx @@ -20,6 +20,8 @@ #include "condformatcontext.hxx" #include "extlstcontext.hxx" +#include "condformatbuffer.hxx" + namespace oox { namespace xls { @@ -100,9 +102,9 @@ void DataBarContext::onStartElement( const AttributeList& rAttribs ) } } -IconSetContext::IconSetContext( CondFormatContext& rFragment, CondFormatRuleRef xRule ) : - WorksheetContextBase( rFragment ), - mxRule( xRule ) +IconSetContext::IconSetContext(WorksheetContextBase& rParent, IconSetRule* pIconSet) : + WorksheetContextBase(rParent), + mpIconSet(pIconSet) { } @@ -111,12 +113,19 @@ ContextHandlerRef IconSetContext::onCreateContext( sal_Int32 nElement, const Att switch( getCurrentElement() ) { case XLS_TOKEN( cfRule ): - return (nElement == XLS_TOKEN( iconSet )) ? this : 0; + case XLS14_TOKEN( cfRule ): + return (nElement == XLS_TOKEN( iconSet ) || nElement == XLS14_TOKEN(iconSet)) ? this : 0; case XLS_TOKEN( iconSet ): - if (nElement == XLS_TOKEN( cfvo )) + case XLS14_TOKEN(iconSet): + if (nElement == XLS_TOKEN( cfvo ) || + nElement == XLS14_TOKEN(cfvo) || + nElement == XLS14_TOKEN(cfIcon)) return this; else return 0; + case XLS14_TOKEN(cfvo): + if (nElement == XM_TOKEN(f)) + return this; } return 0; } @@ -126,10 +135,30 @@ void IconSetContext::onStartElement( const AttributeList& rAttribs ) switch( getCurrentElement() ) { case XLS_TOKEN( iconSet ): - mxRule->getIconSet()->importAttribs( rAttribs ); + case XLS14_TOKEN( iconSet ): + mpIconSet->importAttribs( rAttribs ); break; case XLS_TOKEN( cfvo ): - mxRule->getIconSet()->importCfvo( rAttribs ); + case XLS14_TOKEN( cfvo ): + mpIconSet->importCfvo( rAttribs ); + break; + case XLS14_TOKEN(cfIcon): + break; + } +} + +void IconSetContext::onCharacters(const OUString& rChars) +{ + maChars = rChars; +} + +void IconSetContext::onEndElement() +{ + switch(getCurrentElement()) + { + case XM_TOKEN(f): + mpIconSet->importFormula(maChars); + maChars = OUString(); break; } } @@ -153,7 +182,7 @@ ContextHandlerRef CondFormatContext::onCreateContext( sal_Int32 nElement, const else if (nElement == XLS_TOKEN( dataBar ) ) return new DataBarContext( *this, mxRule ); else if (nElement == XLS_TOKEN( iconSet ) ) - return new IconSetContext( *this, mxRule ); + return new IconSetContext(*this, mxRule->getIconSet()); else if (nElement == XLS_TOKEN( extLst ) ) return new ExtLstLocalContext( *this, mxRule->getDataBar()->getDataBarFormatData() ); else diff --git a/sc/source/filter/oox/extlstcontext.cxx b/sc/source/filter/oox/extlstcontext.cxx index 4f8f0ff10461..3d431cdb5e56 100644 --- a/sc/source/filter/oox/extlstcontext.cxx +++ b/sc/source/filter/oox/extlstcontext.cxx @@ -12,6 +12,10 @@ #include <oox/core/contexthandler.hxx> #include "colorscale.hxx" #include "condformatbuffer.hxx" +#include "condformatcontext.hxx" +#include "document.hxx" + +#include "rangeutl.hxx" using ::oox::core::ContextHandlerRef; @@ -34,25 +38,25 @@ void ExtCfRuleContext::onStartElement( const AttributeList& rAttribs ) { switch( getCurrentElement() ) { - case XLS_EXT_TOKEN( dataBar ): + case XLS14_TOKEN( dataBar ): { ExtCfRuleRef xRule = getCondFormats().createExtCfRule(mpTarget); xRule->importDataBar( rAttribs ); break; } - case XLS_EXT_TOKEN( negativeFillColor ): + case XLS14_TOKEN( negativeFillColor ): { ExtCfRuleRef xRule = getCondFormats().createExtCfRule(mpTarget); xRule->importNegativeFillColor( rAttribs ); break; } - case XLS_EXT_TOKEN( axisColor ): + case XLS14_TOKEN( axisColor ): { ExtCfRuleRef xRule = getCondFormats().createExtCfRule(mpTarget); xRule->importAxisColor( rAttribs ); break; } - case XLS_EXT_TOKEN( cfvo ): + case XLS14_TOKEN( cfvo ): { ExtCfRuleRef xRule = getCondFormats().createExtCfRule(mpTarget); xRule->importCfvo( rAttribs ); @@ -65,6 +69,143 @@ void ExtCfRuleContext::onStartElement( const AttributeList& rAttribs ) } } +ExtConditionalFormattingContext::ExtConditionalFormattingContext(WorksheetContextBase& rFragment): + WorksheetContextBase(rFragment), + mpCurrentRule(NULL) +{ +} + +ContextHandlerRef ExtConditionalFormattingContext::onCreateContext(sal_Int32 nElement, const AttributeList& rAttribs) +{ + if (mpCurrentRule) + { + ScFormatEntry& rFormat = *maEntries.rbegin(); + assert(rFormat.GetType() == condformat::ICONSET); + ScIconSetFormat& rIconSet = static_cast<ScIconSetFormat&>(rFormat); + ScDocument* pDoc = &getScDocument(); + SCTAB nTab = getCurrentSheetIndex(); + ScAddress aPos(0, 0, nTab); + mpCurrentRule->SetData(&rIconSet, pDoc, aPos); + delete mpCurrentRule; + mpCurrentRule = NULL; + } + if (nElement == XLS14_TOKEN(cfRule)) + { + OUString aType = rAttribs.getString(XML_type, OUString()); + OUString aId = rAttribs.getString(XML_id, OUString()); + if (aType == "dataBar") + { + // an ext entry does not need to have an existing corresponding entry + ExtLst::const_iterator aExt = getExtLst().find( aId ); + if(aExt == getExtLst().end()) + return NULL; + + ScDataBarFormatData* pInfo = aExt->second; + if (!pInfo) + { + return NULL; + } + return new ExtCfRuleContext( *this, pInfo ); + } + else if (aType == "iconSet") + { + ScDocument* pDoc = &getScDocument(); + mpCurrentRule = new IconSetRule(*this); + ScIconSetFormat* pIconSet = new ScIconSetFormat(pDoc); + maEntries.push_back(pIconSet); + return new IconSetContext(*this, mpCurrentRule); + } + else + { + SAL_WARN("sc", "unhandled XLS14_TOKEN(cfRule) with type: " << aType); + } + } + else if (nElement == XM_TOKEN(sqref)) + { + return this; + } + + return NULL; +} + +namespace { + +ScConditionalFormat* findFormatByRange(const ScRangeList& rRange, ScDocument* pDoc, SCTAB nTab) +{ + ScConditionalFormatList* pList = pDoc->GetCondFormList(nTab); + for (auto itr = pList->begin(); itr != pList->end(); ++itr) + { + if (itr->GetRange() == rRange) + { + return &(*itr); + } + } + + return NULL; +} + +} + +void ExtConditionalFormattingContext::onStartElement(const AttributeList& /*rAttribs*/) +{ + switch (getCurrentElement()) + { + case XM_TOKEN(sqref): + { + } + break; + } +} + +void ExtConditionalFormattingContext::onCharacters(const OUString& rCharacters) +{ + aChars = rCharacters; +} + +void ExtConditionalFormattingContext::onEndElement() +{ + switch (getCurrentElement()) + { + case XM_TOKEN(sqref): + { + if (maEntries.empty()) + break; + + ScDocument* pDoc = &getScDocument(); + assert(pDoc); + SCTAB nTab = getCurrentSheetIndex(); + ScRangeList aRange; + bool bSuccess = ScRangeStringConverter::GetRangeListFromString(aRange, aChars, pDoc, formula::FormulaGrammar::CONV_XL_OOX); + if (!bSuccess) + break; + + ScConditionalFormat* pFormat = findFormatByRange(aRange, pDoc, nTab); + if (!pFormat) + { + // create new conditional format and insert it + pFormat = new ScConditionalFormat(1, pDoc); + pFormat->SetRange(aRange); + sal_uLong nKey = pDoc->AddCondFormat(pFormat, nTab); + pDoc->AddCondFormatData(aRange, nTab, nKey); + } + + for (auto itr = maEntries.begin(), itrEnd = maEntries.end(); + itr != itrEnd; ++itr) + { + pFormat->AddEntry(itr->Clone(pDoc)); + } + } + break; + case XLS14_TOKEN(cfRule): + if (mpCurrentRule) + { + } + break; + default: + break; + } +} + ExtLstLocalContext::ExtLstLocalContext( WorksheetContextBase& rFragment, ScDataBarFormatData* pTarget ): WorksheetContextBase(rFragment), mpTarget(pTarget) @@ -82,7 +223,7 @@ ContextHandlerRef ExtLstLocalContext::onCreateContext( sal_Int32 nElement, const return 0; break; case XLS_TOKEN( ext ): - if (nElement == XLS_EXT_TOKEN( id )) + if (nElement == XLS14_TOKEN( id )) return this; else return 0; @@ -94,14 +235,14 @@ void ExtLstLocalContext::onStartElement( const AttributeList& ) { switch( getCurrentElement() ) { - case XLS_EXT_TOKEN( id ): + case XLS14_TOKEN( id ): break; } } void ExtLstLocalContext::onCharacters( const OUString& rChars ) { - if (getCurrentElement() == XLS_EXT_TOKEN( id )) + if (getCurrentElement() == XLS14_TOKEN( id )) { getExtLst().insert( std::pair< OUString, ScDataBarFormatData*>(rChars, mpTarget) ); } @@ -112,31 +253,12 @@ ExtGlobalContext::ExtGlobalContext( WorksheetContextBase& rFragment ): { } -ContextHandlerRef ExtGlobalContext::onCreateContext( sal_Int32 nElement, const AttributeList& rAttribs ) +ContextHandlerRef ExtGlobalContext::onCreateContext( sal_Int32 nElement, const AttributeList& /*rAttribs*/ ) { - if(!rAttribs.hasAttribute( XML_id)) - return this; - else - { - if(nElement == XLS_EXT_TOKEN( cfRule )) - { - OUString aId = rAttribs.getString( XML_id, OUString() ); + if (nElement == XLS14_TOKEN(conditionalFormatting)) + return new ExtConditionalFormattingContext(*this); - // an ext entrie does not need to have an existing corresponding entry - ExtLst::const_iterator aExt = getExtLst().find( aId ); - if(aExt == getExtLst().end()) - return NULL; - - ScDataBarFormatData* pInfo = aExt->second; - if (!pInfo) - { - return NULL; - } - return new ExtCfRuleContext( *this, pInfo ); - } - else - return this; - } + return this; } void ExtGlobalContext::onStartElement( const AttributeList& /*rAttribs*/ ) |