diff options
Diffstat (limited to 'writerfilter')
-rw-r--r-- | writerfilter/source/dmapper/DomainMapperTableHandler.cxx | 79 | ||||
-rw-r--r-- | writerfilter/source/dmapper/DomainMapperTableHandler.hxx | 2 | ||||
-rw-r--r-- | writerfilter/source/dmapper/DomainMapper_Impl.cxx | 19 | ||||
-rw-r--r-- | writerfilter/source/dmapper/DomainMapper_Impl.hxx | 2 | ||||
-rw-r--r-- | writerfilter/source/dmapper/PropertyIds.cxx | 5 | ||||
-rw-r--r-- | writerfilter/source/dmapper/PropertyIds.hxx | 2 | ||||
-rw-r--r-- | writerfilter/source/dmapper/PropertyMap.cxx | 28 | ||||
-rw-r--r-- | writerfilter/source/dmapper/PropertyMap.hxx | 19 | ||||
-rw-r--r-- | writerfilter/source/dmapper/StyleSheetTable.cxx | 17 | ||||
-rw-r--r-- | writerfilter/source/dmapper/StyleSheetTable.hxx | 1 |
10 files changed, 135 insertions, 39 deletions
diff --git a/writerfilter/source/dmapper/DomainMapperTableHandler.cxx b/writerfilter/source/dmapper/DomainMapperTableHandler.cxx index a0b077282885..1391e47127bd 100644 --- a/writerfilter/source/dmapper/DomainMapperTableHandler.cxx +++ b/writerfilter/source/dmapper/DomainMapperTableHandler.cxx @@ -61,6 +61,7 @@ using namespace ::std; #define CNF_FIRST_ROW_FIRST_COLUMN 0x004 #define CNF_LAST_ROW_LAST_COLUMN 0x002 #define CNF_LAST_ROW_FIRST_COLUMN 0x001 +#define CNF_ALL 0xFFF DomainMapperTableHandler::DomainMapperTableHandler( css::uno::Reference<css::text::XTextAppendAndConvert> const& xText, @@ -226,6 +227,7 @@ struct TableInfo PropertyMapPtr pTableBorders; TableStyleSheetEntry* pTableStyle; css::beans::PropertyValues aTableProperties; + std::vector< PropertyIds > aTablePropertyIds; TableInfo() : nLeftBorderDistance(DEF_BORDER_DIST) @@ -636,6 +638,7 @@ TableStyleSheetEntry * DomainMapperTableHandler::endTableGetTableStyle(TableInfo } rInfo.aTableProperties = m_aTableProperties->GetPropertyValues(); + rInfo.aTablePropertyIds = m_aTableProperties->GetPropertyIds(); #ifdef DEBUG_WRITERFILTER TagLogger::getInstance().startElement("debug.tableprops"); @@ -810,9 +813,6 @@ CellPropertyValuesSeq_t DomainMapperTableHandler::endTableGetCellProperties(Tabl // Remove properties from style/row that aren't allowed in cells pAllCellProps->Erase( PROP_HEADER_ROW_COUNT ); pAllCellProps->Erase( PROP_TBL_HEADER ); - // Remove paragraph properties from style/row that paragraph style can overwrite - pAllCellProps->Erase( PROP_PARA_BOTTOM_MARGIN ); - pAllCellProps->Erase( PROP_PARA_LINE_SPACING ); // Then add the cell properties pAllCellProps->InsertProps(*aCellIterator); @@ -1018,29 +1018,59 @@ css::uno::Sequence<css::beans::PropertyValues> DomainMapperTableHandler::endTabl // table style has got bigger precedence than docDefault style, // but lower precedence than the paragraph styles and direct paragraph formatting -void DomainMapperTableHandler::ApplyParaProperty(css::beans::PropertyValues aTableProperties, PropertyIds eId) +void DomainMapperTableHandler::ApplyParagraphPropertiesFromTableStyle(TableInfo & rInfo) { - OUString sPropertyName = getPropertyName(eId); - auto pTableProp = std::find_if(aTableProperties.begin(), aTableProperties.end(), - [&](const beans::PropertyValue& rProp) { return rProp.Name == sPropertyName; }); - if (pTableProp != aTableProperties.end()) + for( auto const& eId : rInfo.aTablePropertyIds ) { - uno::Any aValue = pTableProp->Value; - for (const auto& rParaProp : m_rDMapper_Impl.m_aParagraphsToEndTable) + // apply paragraph and character properties of the table style on table paragraphs + if ( isParagraphProperty(eId) || isCharacterProperty(eId) ) { - // there is no direct paragraph formatting - if (!rParaProp.m_pPropertyMap->isSet(eId)) + // check all paragraphs of the table + for (const auto& rParaProp : m_rDMapper_Impl.m_aParagraphsToEndTable) { - OUString sParaStyleName; - rParaProp.m_rPropertySet->getPropertyValue("ParaStyleName") >>= sParaStyleName; - StyleSheetEntryPtr pEntry = m_rDMapper_Impl.GetStyleSheetTable()->FindStyleSheetByConvertedStyleName(sParaStyleName); - uno::Any aMargin = m_rDMapper_Impl.GetPropertyFromStyleSheet(eId, pEntry, true, true); - uno::Any aMarginDocDefault = m_rDMapper_Impl.GetPropertyFromStyleSheet(eId, nullptr, true, true); - // use table style only when 1) both values are empty (no docDefault and paragraph style definitions) or - // 2) both non-empty values are equal (docDefault paragraph properties are copied to the base paragraph style during import) - // TODO check the case, when two parent styles modify the docDefault and the last one set back the docDefault value - if (aMargin == aMarginDocDefault) - rParaProp.m_rPropertySet->setPropertyValue(sPropertyName, aValue); + // there is no direct paragraph formatting + if (!rParaProp.m_pPropertyMap->isSet(eId)) + { + bool bDocDefault; + OUString sParaStyleName; + rParaProp.m_rPropertySet->getPropertyValue("ParaStyleName") >>= sParaStyleName; + StyleSheetEntryPtr pEntry = m_rDMapper_Impl.GetStyleSheetTable()->FindStyleSheetByConvertedStyleName(sParaStyleName); + uno::Any aParaStyle = m_rDMapper_Impl.GetPropertyFromStyleSheet(eId, pEntry, true, true, &bDocDefault); + // use table style when a docDefault value is applied instead of it, + // and there is no associated TableStyleSheetEntry + // TODO: replace CNF_ALL with the actual mask + if ( (aParaStyle == uno::Any() || bDocDefault) && !rInfo.pTableStyle->GetProperties(CNF_ALL)->getProperty(eId) ) + { + OUString sPropertyName = getPropertyName(eId); + auto pTableProp = std::find_if(rInfo.aTableProperties.begin(), rInfo.aTableProperties.end(), + [&](const beans::PropertyValue& rProp) { return rProp.Name == sPropertyName; }); + if (pTableProp != rInfo.aTableProperties.end()) + { + try + { + rParaProp.m_rPropertySet->setPropertyValue( sPropertyName, pTableProp->Value ); + } + catch ( const uno::Exception & ) + { + SAL_WARN("writerfilter.dmapper", "Exception during table style correction"); + } + } + } + // table style can overwrite paragraph style, when the paragraph style property has a default value, restore it + // TODO remove the associated TableStyleSheetEntry styles, if needed + else if ( aParaStyle != uno::Any() && !bDocDefault ) + { + OUString sPropertyName = getPropertyName(eId); + try + { + rParaProp.m_rPropertySet->setPropertyValue( sPropertyName, aParaStyle ); + } + catch ( const uno::Exception & ) + { + SAL_WARN("writerfilter.dmapper", "Exception during table style correction"); + } + } + } } } } @@ -1144,9 +1174,8 @@ void DomainMapperTableHandler::endTable(unsigned int nestedTableLevel, bool bTab } } - // OOXML table style may container paragraph properties, apply these now. - ApplyParaProperty(aTableInfo.aTableProperties, PROP_PARA_BOTTOM_MARGIN); - ApplyParaProperty(aTableInfo.aTableProperties, PROP_PARA_LINE_SPACING); + // OOXML table style may contain paragraph properties, apply these now. + ApplyParagraphPropertiesFromTableStyle(aTableInfo); } } catch ( const lang::IllegalArgumentException &e ) diff --git a/writerfilter/source/dmapper/DomainMapperTableHandler.hxx b/writerfilter/source/dmapper/DomainMapperTableHandler.hxx index 16d2a0cc37cc..b454be94f563 100644 --- a/writerfilter/source/dmapper/DomainMapperTableHandler.hxx +++ b/writerfilter/source/dmapper/DomainMapperTableHandler.hxx @@ -91,7 +91,7 @@ public: */ void startTable(const TablePropertyMapPtr& pProps); - void ApplyParaProperty(css::beans::PropertyValues aTableProperties, PropertyIds eId); + void ApplyParagraphPropertiesFromTableStyle(TableInfo & rInfo); /// Handle end of table. void endTable(unsigned int nestedTableLevel, bool bTableStartsAtCellStart); diff --git a/writerfilter/source/dmapper/DomainMapper_Impl.cxx b/writerfilter/source/dmapper/DomainMapper_Impl.cxx index 2489f50ba94e..716c14e8a5bf 100644 --- a/writerfilter/source/dmapper/DomainMapper_Impl.cxx +++ b/writerfilter/source/dmapper/DomainMapper_Impl.cxx @@ -704,7 +704,7 @@ const OUString DomainMapper_Impl::GetDefaultParaStyleName() return m_sDefaultParaStyleName; } -uno::Any DomainMapper_Impl::GetPropertyFromStyleSheet(PropertyIds eId, StyleSheetEntryPtr pEntry, const bool bDocDefaults, const bool bPara) +uno::Any DomainMapper_Impl::GetPropertyFromStyleSheet(PropertyIds eId, StyleSheetEntryPtr pEntry, const bool bDocDefaults, const bool bPara, bool* pIsDocDefault) { while(pEntry.get( ) ) { @@ -714,6 +714,9 @@ uno::Any DomainMapper_Impl::GetPropertyFromStyleSheet(PropertyIds eId, StyleShee pEntry->pProperties->getProperty(eId); if( aProperty ) { + if (pIsDocDefault) + *pIsDocDefault = pEntry->pProperties->isDocDefault(eId); + return aProperty->second; } } @@ -737,7 +740,12 @@ uno::Any DomainMapper_Impl::GetPropertyFromStyleSheet(PropertyIds eId, StyleShee { boost::optional<PropertyMap::Property> aProperty = pDefaultParaProps->getProperty(eId); if ( aProperty ) + { + if (pIsDocDefault) + *pIsDocDefault = true; + return aProperty->second; + } } } if ( bDocDefaults && isCharacterProperty(eId) ) @@ -747,9 +755,18 @@ uno::Any DomainMapper_Impl::GetPropertyFromStyleSheet(PropertyIds eId, StyleShee { boost::optional<PropertyMap::Property> aProperty = pDefaultCharProps->getProperty(eId); if ( aProperty ) + { + if (pIsDocDefault) + *pIsDocDefault = true; + return aProperty->second; + } } } + + if (pIsDocDefault) + *pIsDocDefault = false; + return uno::Any(); } diff --git a/writerfilter/source/dmapper/DomainMapper_Impl.hxx b/writerfilter/source/dmapper/DomainMapper_Impl.hxx index cf681ea34deb..955d806e5bab 100644 --- a/writerfilter/source/dmapper/DomainMapper_Impl.hxx +++ b/writerfilter/source/dmapper/DomainMapper_Impl.hxx @@ -716,7 +716,7 @@ public: const OUString GetDefaultParaStyleName(); // specified style - including inherited properties. Indicate whether paragraph defaults should be checked. - css::uno::Any GetPropertyFromStyleSheet(PropertyIds eId, StyleSheetEntryPtr pEntry, const bool bDocDefaults, const bool bPara); + css::uno::Any GetPropertyFromStyleSheet(PropertyIds eId, StyleSheetEntryPtr pEntry, const bool bDocDefaults, const bool bPara, bool* bIsDocDefault = nullptr); // current paragraph style - including inherited properties css::uno::Any GetPropertyFromParaStyleSheet(PropertyIds eId); // context's character style - including inherited properties diff --git a/writerfilter/source/dmapper/PropertyIds.cxx b/writerfilter/source/dmapper/PropertyIds.cxx index 562f5f1795b1..35638f774c79 100644 --- a/writerfilter/source/dmapper/PropertyIds.cxx +++ b/writerfilter/source/dmapper/PropertyIds.cxx @@ -366,6 +366,11 @@ bool isCharacterProperty( const PropertyIds eId ) return eId > PROP_CHARACTER_STYLES && eId < PROP_CHARACTER_END; } +bool isParagraphProperty( const PropertyIds eId ) +{ + return eId >= PROP_PARA_ADJUST && eId <= PROP_PARA_WIDOWS; +} + } //namespace dmapper } //namespace writerfilter diff --git a/writerfilter/source/dmapper/PropertyIds.hxx b/writerfilter/source/dmapper/PropertyIds.hxx index 6b3136fe10a5..392c25e68b5a 100644 --- a/writerfilter/source/dmapper/PropertyIds.hxx +++ b/writerfilter/source/dmapper/PropertyIds.hxx @@ -363,6 +363,8 @@ OUString getPropertyName(PropertyIds eId); bool isCharacterProperty(const PropertyIds eId); +bool isParagraphProperty(const PropertyIds eId); + } //namespace dmapper } // namespace writerfilter #endif diff --git a/writerfilter/source/dmapper/PropertyMap.cxx b/writerfilter/source/dmapper/PropertyMap.cxx index 5d51a89e976a..f1448dbd4423 100644 --- a/writerfilter/source/dmapper/PropertyMap.cxx +++ b/writerfilter/source/dmapper/PropertyMap.cxx @@ -189,6 +189,14 @@ uno::Sequence< beans::PropertyValue > PropertyMap::GetPropertyValues( bool bChar return comphelper::containerToSequence( m_aValues ); } +std::vector< PropertyIds > PropertyMap::GetPropertyIds() +{ + std::vector< PropertyIds > aRet; + for ( const auto& rPropPair : m_vMap ) + aRet.push_back( rPropPair.first ); + return aRet; +} + #ifdef DEBUG_WRITERFILTER static void lcl_AnyToTag( const uno::Any& rAny ) { @@ -227,7 +235,7 @@ static void lcl_AnyToTag( const uno::Any& rAny ) } #endif -void PropertyMap::Insert( PropertyIds eId, const uno::Any& rAny, bool bOverwrite, GrabBagType i_GrabBagType ) +void PropertyMap::Insert( PropertyIds eId, const uno::Any& rAny, bool bOverwrite, GrabBagType i_GrabBagType, bool bDocDefault ) { #ifdef DEBUG_WRITERFILTER const OUString& rInsert = getPropertyName(eId); @@ -239,7 +247,7 @@ void PropertyMap::Insert( PropertyIds eId, const uno::Any& rAny, bool bOverwrite #endif if ( !bOverwrite ) - m_vMap.insert(std::make_pair(eId, PropValue(rAny, i_GrabBagType))); + m_vMap.insert(std::make_pair(eId, PropValue(rAny, i_GrabBagType, bDocDefault))); else m_vMap[eId] = PropValue(rAny, i_GrabBagType); @@ -268,6 +276,15 @@ bool PropertyMap::isSet( PropertyIds eId) const return m_vMap.find( eId ) != m_vMap.end(); } +bool PropertyMap::isDocDefault( PropertyIds eId ) const +{ + std::map< PropertyIds, PropValue >::const_iterator aIter = m_vMap.find( eId ); + if ( aIter == m_vMap.end() ) + return false; + else + return aIter->second.getIsDocDefault(); +} + #ifdef DEBUG_WRITERFILTER void PropertyMap::dumpXml() const { @@ -324,7 +341,12 @@ void PropertyMap::InsertProps( const PropertyMapPtr& rMap, const bool bOverwrite for ( const auto& rPropPair : rMap->m_vMap ) { if ( bOverwrite || !m_vMap.count(rPropPair.first) ) - m_vMap[rPropPair.first] = rPropPair.second; + { + if ( !bOverwrite && !rPropPair.second.getIsDocDefault() ) + m_vMap.insert(std::make_pair(rPropPair.first, PropValue(rPropPair.second.getValue(), rPropPair.second.getGrabBagType(), true))); + else + m_vMap[rPropPair.first] = rPropPair.second; + } } insertTableProperties( rMap.get(), bOverwrite ); diff --git a/writerfilter/source/dmapper/PropertyMap.hxx b/writerfilter/source/dmapper/PropertyMap.hxx index 6f16de26fe0a..9289534cc445 100644 --- a/writerfilter/source/dmapper/PropertyMap.hxx +++ b/writerfilter/source/dmapper/PropertyMap.hxx @@ -95,23 +95,35 @@ class PropValue private: css::uno::Any m_aValue; GrabBagType m_GrabBagType; + bool m_bIsDocDefault; public: + PropValue( const css::uno::Any& rValue, GrabBagType i_GrabBagType, bool bDocDefault ) + : m_aValue( rValue ) + , m_GrabBagType( i_GrabBagType ) + , m_bIsDocDefault( bDocDefault ) + { + } + PropValue( const css::uno::Any& rValue, GrabBagType i_GrabBagType ) : m_aValue( rValue ) , m_GrabBagType( i_GrabBagType ) + , m_bIsDocDefault( false ) { } PropValue() : m_aValue() , m_GrabBagType( NO_GRAB_BAG ) + , m_bIsDocDefault( false ) { } const css::uno::Any& getValue() const { return m_aValue; } GrabBagType getGrabBagType() const { return m_GrabBagType; } + + bool getIsDocDefault() const { return m_bIsDocDefault; } }; class PropertyMap : public virtual SvRefBase @@ -135,13 +147,15 @@ public: // the contained properties are their Value. css::uno::Sequence< css::beans::PropertyValue > GetPropertyValues( bool bCharGrabBag = true ); + std::vector< PropertyIds > GetPropertyIds(); + // Add property, optionally overwriting existing attributes - void Insert( PropertyIds eId, const css::uno::Any& rAny, bool bOverwrite = true, GrabBagType i_GrabBagType = NO_GRAB_BAG ); + void Insert( PropertyIds eId, const css::uno::Any& rAny, bool bOverwrite = true, GrabBagType i_GrabBagType = NO_GRAB_BAG, bool bDocDefault = false ); // Remove a named property from *this, does nothing if the property id has not been set void Erase( PropertyIds eId); - // Imports properties from pMap + // Imports properties from pMap (bOverwrite==false means m_bIsDocDefault=true setting) void InsertProps( const tools::SvRef< PropertyMap >& rMap, const bool bOverwrite = true ); // Returns a copy of the property if it exists, .first is its PropertyIds and .second is its Value (type css::uno::Any) @@ -149,6 +163,7 @@ public: // Has the property named been set (via Insert)? bool isSet( PropertyIds eId ) const; + bool isDocDefault( PropertyIds eId ) const; const css::uno::Reference< css::text::XFootnote >& GetFootnote() const { return m_xFootnote; } diff --git a/writerfilter/source/dmapper/StyleSheetTable.cxx b/writerfilter/source/dmapper/StyleSheetTable.cxx index 08145c98ad2f..31373d988611 100644 --- a/writerfilter/source/dmapper/StyleSheetTable.cxx +++ b/writerfilter/source/dmapper/StyleSheetTable.cxx @@ -397,6 +397,11 @@ StyleSheetTable::~StyleSheetTable() { } +void StyleSheetTable::SetDefaultParaProps(PropertyIds eId, const css::uno::Any& rAny) +{ + m_pImpl->m_pDefaultParaProps->Insert(eId, rAny, /*bOverwrite=*/false, NO_GRAB_BAG, /*bDocDefault=*/true); +} + PropertyMapPtr const & StyleSheetTable::GetDefaultParaProps() { return m_pImpl->m_pDefaultParaProps; @@ -692,7 +697,7 @@ void StyleSheetTable::lcl_sprm(Sprm & rSprm) if ( nSprmId == NS_ooxml::LN_CT_DocDefaults_pPrDefault && m_pImpl->m_pDefaultParaProps.get() && !m_pImpl->m_pDefaultParaProps->isSet( PROP_PARA_TOP_MARGIN ) ) { - m_pImpl->m_pDefaultParaProps->Insert( PROP_PARA_TOP_MARGIN, uno::makeAny( sal_Int32(0) ) ); + SetDefaultParaProps( PROP_PARA_TOP_MARGIN, uno::makeAny( sal_Int32(0) ) ); } m_pImpl->m_rDMapper.PopStyleSheetProperties(); applyDefaults( true ); @@ -999,7 +1004,7 @@ void StyleSheetTable::ApplyStyleSheets( const FontTablePtr& rFontTable ) else if( bParaStyle ) { // Paragraph styles that don't inherit from some parent need to apply the DocDefaults - pEntry->pProperties->InsertProps( m_pImpl->m_pDefaultParaProps, /*bAllowOverwrite=*/false ); + pEntry->pProperties->InsertProps( m_pImpl->m_pDefaultParaProps, /*bOverwrite=*/false ); //now it's time to set the default parameters - for paragraph styles //Fonts: Western first entry in font table @@ -1467,13 +1472,13 @@ void StyleSheetTable::applyDefaults(bool bParaProperties) if( bParaProperties && m_pImpl->m_pDefaultParaProps.get()) { // tdf#87533 LO will have different defaults here, depending on the locale. Import with documented defaults - m_pImpl->m_pDefaultParaProps->Insert(PROP_WRITING_MODE, uno::makeAny(sal_Int16(text::WritingMode_LR_TB)), /*bOverwrite=*/false); - m_pImpl->m_pDefaultParaProps->Insert(PROP_PARA_ADJUST, uno::makeAny(sal_Int16(style::ParagraphAdjust_LEFT)), false); + SetDefaultParaProps(PROP_WRITING_MODE, uno::makeAny(sal_Int16(text::WritingMode_LR_TB))); + SetDefaultParaProps(PROP_PARA_ADJUST, uno::makeAny(sal_Int16(style::ParagraphAdjust_LEFT))); // Widow/Orphan -> set both to two if not already set uno::Any aTwo = uno::makeAny(sal_Int8(2)); - m_pImpl->m_pDefaultParaProps->Insert(PROP_PARA_WIDOWS, aTwo, /*bOverwrite=*/false); - m_pImpl->m_pDefaultParaProps->Insert(PROP_PARA_ORPHANS, aTwo, false); + SetDefaultParaProps(PROP_PARA_WIDOWS, aTwo); + SetDefaultParaProps(PROP_PARA_ORPHANS, aTwo); uno::Reference<style::XStyleFamiliesSupplier> xStylesSupplier(m_pImpl->m_xTextDocument, uno::UNO_QUERY); uno::Reference<container::XNameAccess> xStyleFamilies = xStylesSupplier->getStyleFamilies(); diff --git a/writerfilter/source/dmapper/StyleSheetTable.hxx b/writerfilter/source/dmapper/StyleSheetTable.hxx index 686779acbd71..ee621093079e 100644 --- a/writerfilter/source/dmapper/StyleSheetTable.hxx +++ b/writerfilter/source/dmapper/StyleSheetTable.hxx @@ -102,6 +102,7 @@ public: OUString getOrCreateCharStyle( PropertyValueVector_t& rCharProperties, bool bAlwaysCreate ); + void SetDefaultParaProps(PropertyIds eId, const css::uno::Any& rAny); PropertyMapPtr const & GetDefaultParaProps(); /// Returns the default character properties. PropertyMapPtr const & GetDefaultCharProps(); |