merge the formfield patch from ooo-build
[ooovba.git] / xmloff / source / style / prstylei.cxx
blob4f666b4fc3c5181772eedf3e71b5c06930724b9b
1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: prstylei.cxx,v $
10 * $Revision: 1.20 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_xmloff.hxx"
35 #include <tools/debug.hxx>
36 #ifndef __SGI_STL_SET
37 #include <set>
38 #endif
39 #include "xmlnmspe.hxx"
40 #include <xmloff/xmltoken.hxx>
41 #include <xmloff/xmlprcon.hxx>
42 #include <com/sun/star/style/XStyle.hpp>
43 #include <com/sun/star/style/XAutoStyleFamily.hpp>
44 #include <com/sun/star/container/XNameContainer.hpp>
45 #include <com/sun/star/beans/XPropertySet.hpp>
46 #include <com/sun/star/beans/XPropertyState.hpp>
47 #include <com/sun/star/beans/XMultiPropertyStates.hpp>
48 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
49 #include <xmloff/xmlimp.hxx>
51 #ifndef _XMLOFF_PRSTYLEI_HXX
52 #include <xmloff/prstylei.hxx>
53 #endif
54 #include <xmloff/attrlist.hxx>
55 #include "xmlerror.hxx"
57 using ::rtl::OUString;
58 using ::rtl::OUStringBuffer;
60 using namespace ::com::sun::star;
61 using namespace ::com::sun::star::uno;
62 using namespace ::com::sun::star::xml::sax;
63 using namespace ::com::sun::star::style;
64 using namespace ::com::sun::star::container;
65 using namespace ::com::sun::star::beans;
66 using namespace ::com::sun::star::lang;
67 using namespace ::xmloff::token;
70 void XMLPropStyleContext::SetAttribute( sal_uInt16 nPrefixKey,
71 const OUString& rLocalName,
72 const OUString& rValue )
74 if( XML_NAMESPACE_STYLE == nPrefixKey && IsXMLToken( rLocalName, XML_FAMILY ) )
76 DBG_ASSERT( GetFamily() == ((SvXMLStylesContext *)&mxStyles)->GetFamily( rValue ), "unexpected style family" );
78 else
80 SvXMLStyleContext::SetAttribute( nPrefixKey, rLocalName, rValue );
84 TYPEINIT1( XMLPropStyleContext, SvXMLStyleContext );
86 XMLPropStyleContext::XMLPropStyleContext( SvXMLImport& rImport,
87 sal_uInt16 nPrfx, const OUString& rLName,
88 const Reference< XAttributeList > & xAttrList,
89 SvXMLStylesContext& rStyles, sal_uInt16 nFamily,
90 sal_Bool bDefault )
91 : SvXMLStyleContext( rImport, nPrfx, rLName, xAttrList, nFamily, bDefault )
92 , msIsPhysical( RTL_CONSTASCII_USTRINGPARAM( "IsPhysical" ) )
93 , msFollowStyle( RTL_CONSTASCII_USTRINGPARAM( "FollowStyle" ) )
94 , mxStyles( &rStyles )
98 XMLPropStyleContext::~XMLPropStyleContext()
102 SvXMLImportContext *XMLPropStyleContext::CreateChildContext(
103 sal_uInt16 nPrefix,
104 const OUString& rLocalName,
105 const Reference< XAttributeList > & xAttrList )
107 SvXMLImportContext *pContext = 0;
109 sal_uInt32 nFamily = 0;
110 if( XML_NAMESPACE_STYLE == nPrefix )
112 if( IsXMLToken( rLocalName, XML_GRAPHIC_PROPERTIES ) )
113 nFamily = XML_TYPE_PROP_GRAPHIC;
114 else if( IsXMLToken( rLocalName, XML_DRAWING_PAGE_PROPERTIES ) )
115 nFamily = XML_TYPE_PROP_DRAWING_PAGE;
116 else if( IsXMLToken( rLocalName, XML_TEXT_PROPERTIES ) )
117 nFamily = XML_TYPE_PROP_TEXT;
118 else if( IsXMLToken( rLocalName, XML_PARAGRAPH_PROPERTIES ) )
119 nFamily = XML_TYPE_PROP_PARAGRAPH;
120 else if( IsXMLToken( rLocalName, XML_RUBY_PROPERTIES ) )
121 nFamily = XML_TYPE_PROP_RUBY;
122 else if( IsXMLToken( rLocalName, XML_SECTION_PROPERTIES ) )
123 nFamily = XML_TYPE_PROP_SECTION;
124 else if( IsXMLToken( rLocalName, XML_TABLE_PROPERTIES ) )
125 nFamily = XML_TYPE_PROP_TABLE;
126 else if( IsXMLToken( rLocalName, XML_TABLE_COLUMN_PROPERTIES ) )
127 nFamily = XML_TYPE_PROP_TABLE_COLUMN;
128 else if( IsXMLToken( rLocalName, XML_TABLE_ROW_PROPERTIES ) )
129 nFamily = XML_TYPE_PROP_TABLE_ROW;
130 else if( IsXMLToken( rLocalName, XML_TABLE_CELL_PROPERTIES ) )
131 nFamily = XML_TYPE_PROP_TABLE_CELL;
132 else if( IsXMLToken( rLocalName, XML_CHART_PROPERTIES ) )
133 nFamily = XML_TYPE_PROP_CHART;
135 if( nFamily )
137 UniReference < SvXMLImportPropertyMapper > xImpPrMap =
138 ((SvXMLStylesContext *)&mxStyles)->GetImportPropertyMapper(
139 GetFamily() );
140 if( xImpPrMap.is() )
141 pContext = new SvXMLPropertySetContext( GetImport(), nPrefix,
142 rLocalName, xAttrList,
143 nFamily,
144 maProperties,
145 xImpPrMap );
148 if( !pContext )
149 pContext = SvXMLStyleContext::CreateChildContext( nPrefix, rLocalName,
150 xAttrList );
152 return pContext;
155 void XMLPropStyleContext::FillPropertySet(
156 const Reference< XPropertySet > & rPropSet )
158 UniReference < SvXMLImportPropertyMapper > xImpPrMap =
159 ((SvXMLStylesContext *)&mxStyles)->GetImportPropertyMapper(
160 GetFamily() );
161 DBG_ASSERT( xImpPrMap.is(), "There is the import prop mapper" );
162 if( xImpPrMap.is() )
163 xImpPrMap->FillPropertySet( maProperties, rPropSet );
166 void XMLPropStyleContext::SetDefaults()
170 Reference < XStyle > XMLPropStyleContext::Create()
172 Reference < XStyle > xNewStyle;
174 OUString sServiceName(
175 ((SvXMLStylesContext *)&mxStyles)->GetServiceName( GetFamily() ) );
176 if( sServiceName.getLength() )
178 Reference< XMultiServiceFactory > xFactory( GetImport().GetModel(),
179 UNO_QUERY );
180 if( xFactory.is() )
182 Reference < XInterface > xIfc =
183 xFactory->createInstance( sServiceName );
184 if( xIfc.is() )
185 xNewStyle = Reference < XStyle >( xIfc, UNO_QUERY );
189 return xNewStyle;
192 typedef ::std::set < OUString, ::comphelper::UStringLess > PropertyNameSet;
194 void XMLPropStyleContext::CreateAndInsert( sal_Bool bOverwrite )
196 if( ((SvXMLStylesContext *)&mxStyles)->IsAutomaticStyle()
197 && ( GetFamily() == XML_STYLE_FAMILY_TEXT_TEXT || GetFamily() == XML_STYLE_FAMILY_TEXT_PARAGRAPH ) )
199 Reference < XAutoStyleFamily > xAutoFamily =
200 ((SvXMLStylesContext *)&mxStyles)->GetAutoStyles( GetFamily() );
201 if( !xAutoFamily.is() )
202 return;
203 UniReference < SvXMLImportPropertyMapper > xImpPrMap =
204 ((SvXMLStylesContext *)&mxStyles)->GetImportPropertyMapper( GetFamily() );
205 DBG_ASSERT( xImpPrMap.is(), "There is no import prop mapper" );
206 if( xImpPrMap.is() )
208 Sequence< PropertyValue > aValues;
209 xImpPrMap->FillPropertySequence( maProperties, aValues );
211 sal_Int32 nLen = aValues.getLength();
212 if( nLen )
214 if( GetFamily() == XML_STYLE_FAMILY_TEXT_PARAGRAPH )
216 aValues.realloc( nLen + 2 );
217 PropertyValue *pProps = aValues.getArray() + nLen;
218 pProps->Name = rtl::OUString::createFromAscii("ParaStyleName");
219 OUString sParent( GetParentName() );
220 if( sParent.getLength() )
221 sParent = GetImport().GetStyleDisplayName( GetFamily(), sParent );
222 else
223 sParent = rtl::OUString::createFromAscii("Standard");
224 pProps->Value <<= sParent;
225 ++pProps;
226 pProps->Name = rtl::OUString::createFromAscii("ParaConditionalStyleName");
227 pProps->Value <<= sParent;
230 Reference < XAutoStyle > xAutoStyle = xAutoFamily->insertStyle( aValues );
231 if( xAutoStyle.is() )
233 Sequence< OUString > aPropNames(1);
234 aPropNames[0] = GetFamily() == XML_STYLE_FAMILY_TEXT_PARAGRAPH ?
235 rtl::OUString::createFromAscii("ParaAutoStyleName") :
236 rtl::OUString::createFromAscii("CharAutoStyleName");
237 Sequence< Any > aAny = xAutoStyle->getPropertyValues( aPropNames );
238 if( aAny.hasElements() )
240 OUString aName;
241 aAny[0] >>= aName;
242 SetAutoName( aName );
248 else
250 const OUString& rName = GetDisplayName();
251 if( 0 == rName.getLength() || IsDefaultStyle() )
252 return;
254 Reference < XNameContainer > xFamilies =
255 ((SvXMLStylesContext *)&mxStyles)->GetStylesContainer( GetFamily() );
256 if( !xFamilies.is() )
257 return;
259 sal_Bool bNew = sal_False;
260 if( xFamilies->hasByName( rName ) )
262 Any aAny = xFamilies->getByName( rName );
263 aAny >>= mxStyle;
265 else
267 mxStyle = Create();
268 if( !mxStyle.is() )
269 return;
271 Any aAny;
272 aAny <<= mxStyle;
273 xFamilies->insertByName( rName, aAny );
274 bNew = sal_True;
277 Reference < XPropertySet > xPropSet( mxStyle, UNO_QUERY );
278 Reference< XPropertySetInfo > xPropSetInfo =
279 xPropSet->getPropertySetInfo();
280 if( !bNew && xPropSetInfo->hasPropertyByName( msIsPhysical ) )
282 Any aAny = xPropSet->getPropertyValue( msIsPhysical );
283 bNew = !*(sal_Bool *)aAny.getValue();
285 SetNew( bNew );
286 if( rName != GetName() )
287 GetImport().AddStyleDisplayName( GetFamily(), GetName(), rName );
289 if( bOverwrite || bNew )
291 Reference< XPropertyState > xPropState( xPropSet, uno::UNO_QUERY );
293 UniReference < XMLPropertySetMapper > xPrMap;
294 UniReference < SvXMLImportPropertyMapper > xImpPrMap =
295 ((SvXMLStylesContext *)&mxStyles)->GetImportPropertyMapper(
296 GetFamily() );
297 DBG_ASSERT( xImpPrMap.is(), "There is the import prop mapper" );
298 if( xImpPrMap.is() )
299 xPrMap = xImpPrMap->getPropertySetMapper();
300 if( xPrMap.is() )
302 Reference < XMultiPropertyStates > xMultiStates( xPropSet,
303 UNO_QUERY );
304 if( xMultiStates.is() )
306 xMultiStates->setAllPropertiesToDefault();
308 else
310 PropertyNameSet aNameSet;
311 sal_Int32 nCount = xPrMap->GetEntryCount();
312 sal_Int32 i;
313 for( i = 0; i < nCount; i++ )
315 const OUString& rPrName = xPrMap->GetEntryAPIName( i );
316 if( xPropSetInfo->hasPropertyByName( rPrName ) )
317 aNameSet.insert( rPrName );
320 nCount = aNameSet.size();
321 Sequence < OUString > aNames( nCount );
322 OUString *pNames = aNames.getArray();
323 PropertyNameSet::iterator aIter = aNameSet.begin();
324 while( aIter != aNameSet.end() )
325 *pNames++ = *aIter++;
327 Sequence < PropertyState > aStates(
328 xPropState->getPropertyStates( aNames ) );
329 const PropertyState *pStates = aStates.getConstArray();
330 pNames = aNames.getArray();
332 for( i = 0; i < nCount; i++ )
334 if( PropertyState_DIRECT_VALUE == *pStates++ )
335 xPropState->setPropertyToDefault( pNames[i] );
340 if (mxStyle.is())
341 mxStyle->setParentStyle(OUString());
343 FillPropertySet( xPropSet );
345 else
347 SetValid( sal_False );
352 void XMLPropStyleContext::Finish( sal_Bool bOverwrite )
354 if( mxStyle.is() && (IsNew() || bOverwrite) )
356 // The families cintaner must exist
357 Reference < XNameContainer > xFamilies =
358 ((SvXMLStylesContext *)&mxStyles)->GetStylesContainer( GetFamily() );
359 DBG_ASSERT( xFamilies.is(), "Families lost" );
360 if( !xFamilies.is() )
361 return;
363 // connect parent
364 OUString sParent( GetParentName() );
365 if( sParent.getLength() )
366 sParent = GetImport().GetStyleDisplayName( GetFamily(), sParent );
367 if( sParent.getLength() && !xFamilies->hasByName( sParent ) )
368 sParent = OUString();
370 if( sParent != mxStyle->getParentStyle() )
372 // this may except if setting the parent style forms a
373 // circle in the style depencies; especially if the parent
374 // style is the same as the current style
377 mxStyle->setParentStyle( sParent );
379 catch( uno::Exception e )
381 // according to the API definition, I would expect a
382 // container::NoSuchElementException. But it throws an
383 // uno::RuntimeException instead. I catch
384 // uno::Exception in order to process both of them.
386 // We can't set the parent style. For a proper
387 // Error-Message, we should pass in the name of the
388 // style, as well as the desired parent style.
389 Sequence<OUString> aSequence(2);
391 // getName() throws no non-Runtime exception:
392 aSequence[0] = mxStyle->getName();
393 aSequence[1] = sParent;
395 GetImport().SetError(
396 XMLERROR_FLAG_ERROR | XMLERROR_PARENT_STYLE_NOT_ALLOWED,
397 aSequence, e.Message, NULL );
401 // connect follow
402 OUString sFollow( GetFollow() );
403 if( sFollow.getLength() )
404 sFollow = GetImport().GetStyleDisplayName( GetFamily(), sFollow );
405 if( !sFollow.getLength() || !xFamilies->hasByName( sFollow ) )
406 sFollow = mxStyle->getName();
408 Reference < XPropertySet > xPropSet( mxStyle, UNO_QUERY );
409 Reference< XPropertySetInfo > xPropSetInfo =
410 xPropSet->getPropertySetInfo();
411 if( xPropSetInfo->hasPropertyByName( msFollowStyle ) )
413 Any aAny = xPropSet->getPropertyValue( msFollowStyle );
414 OUString sCurrFollow;
415 aAny >>= sCurrFollow;
416 if( sCurrFollow != sFollow )
418 aAny <<= sFollow;
419 xPropSet->setPropertyValue( msFollowStyle, aAny );