merge the formfield patch from ooo-build
[ooovba.git] / xmloff / source / style / styleexp.cxx
blobfa1877b481d99e77087843f82ef059d60df83967
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: styleexp.cxx,v $
10 * $Revision: 1.25 $
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"
33 #include <tools/debug.hxx>
34 #ifndef _SVSTDARR_STRINGSSORTDTOR_DECL
35 #define _SVSTDARR_STRINGSSORTDTOR
36 #include <svtools/svstdarr.hxx>
37 #endif
38 #include <xmloff/nmspmap.hxx>
39 #include "xmlnmspe.hxx"
40 #include <xmloff/xmltoken.hxx>
41 #ifndef _XMLOFF_XMLITMAP_HXX
42 //#include "xmlitmap.hxx"
43 #endif
44 #include <xmloff/xmluconv.hxx>
45 #include "xmlkywd.hxx"
46 #include <xmloff/attrlist.hxx>
47 #include <xmloff/xmlprmap.hxx>
48 #include <xmloff/xmlexppr.hxx>
49 #include <com/sun/star/xml/sax/XExtendedDocumentHandler.hpp>
50 #include <com/sun/star/frame/XModel.hpp>
51 #include <com/sun/star/style/XStyleFamiliesSupplier.hpp>
52 #include <com/sun/star/style/XStyle.hpp>
53 #include <com/sun/star/container/XNameContainer.hpp>
54 #include <com/sun/star/beans/XPropertySet.hpp>
55 #include <com/sun/star/beans/XPropertyState.hpp>
56 #ifndef _COM_SUN_STAR_DOCUMENT_XEVENTSSUPPLIER_HPP
57 #include <com/sun/star/document/XEventsSupplier.hpp>
58 #endif
59 #include <com/sun/star/text/XChapterNumberingSupplier.hpp>
60 #include <xmloff/xmlaustp.hxx>
61 #ifndef _XMLOFF_STYLEEXP_HXX
62 #include <xmloff/styleexp.hxx>
63 #endif
64 #include <xmloff/xmlexp.hxx>
65 #include <xmloff/XMLEventExport.hxx>
67 using ::rtl::OUString;
68 using ::rtl::OUStringBuffer;
70 using namespace ::com::sun::star;
71 using namespace ::com::sun::star::uno;
72 using namespace ::com::sun::star::style;
73 using namespace ::com::sun::star::container;
74 using namespace ::com::sun::star::beans;
75 using namespace ::com::sun::star::text;
76 using namespace ::xmloff::token;
78 using ::com::sun::star::document::XEventsSupplier;
80 XMLStyleExport::XMLStyleExport(
81 SvXMLExport& rExp,
82 const ::rtl::OUString& rPoolStyleName,
83 SvXMLAutoStylePoolP *pAutoStyleP ) :
84 rExport( rExp ),
85 sIsPhysical( RTL_CONSTASCII_USTRINGPARAM( "IsPhysical" ) ),
86 sIsAutoUpdate( RTL_CONSTASCII_USTRINGPARAM( "IsAutoUpdate" ) ),
87 sFollowStyle( RTL_CONSTASCII_USTRINGPARAM( "FollowStyle" ) ),
88 sNumberingStyleName( RTL_CONSTASCII_USTRINGPARAM( "NumberingStyleName" ) ),
89 sOutlineLevel( RTL_CONSTASCII_USTRINGPARAM( "OutlineLevel" ) ),//#outline level,add by zhaojianwei
90 sPoolStyleName( rPoolStyleName ),
91 pAutoStylePool( pAutoStyleP )
95 XMLStyleExport::~XMLStyleExport()
99 void XMLStyleExport::exportStyleAttributes( const Reference< XStyle >& )
103 void XMLStyleExport::exportStyleContent( const Reference< XStyle >& )
107 sal_Bool XMLStyleExport::exportStyle(
108 const Reference< XStyle >& rStyle,
109 const OUString& rXMLFamily,
110 const UniReference < SvXMLExportPropertyMapper >& rPropMapper,
111 const Reference< XNameAccess >& xStyles, //#outline level,add by zhaojianwei
112 const OUString* pPrefix )
114 Reference< XPropertySet > xPropSet( rStyle, UNO_QUERY );
115 Reference< XPropertySetInfo > xPropSetInfo =
116 xPropSet->getPropertySetInfo();
117 Any aAny;
119 // Don't export styles that aren't existing really. This may be the
120 // case for StarOffice Writer's pool styles.
121 if( xPropSetInfo->hasPropertyByName( sIsPhysical ) )
123 aAny = xPropSet->getPropertyValue( sIsPhysical );
124 if( !*(sal_Bool *)aAny.getValue() )
125 return sal_False;
128 // <style:style ...>
129 GetExport().CheckAttrList();
131 // style:name="..."
132 OUString sName;
134 if(pPrefix)
135 sName = *pPrefix;
136 sName += rStyle->getName();
138 sal_Bool bEncoded = sal_False;
139 const OUString sEncodedStyleName(GetExport().EncodeStyleName( sName, &bEncoded ));
140 GetExport().AddAttribute( XML_NAMESPACE_STYLE, XML_NAME, sEncodedStyleName );
142 if( bEncoded )
143 GetExport().AddAttribute( XML_NAMESPACE_STYLE, XML_DISPLAY_NAME,
144 sName);
146 // style:family="..."
147 if( rXMLFamily.getLength() > 0 )
148 GetExport().AddAttribute( XML_NAMESPACE_STYLE, XML_FAMILY, rXMLFamily);
150 // style:parent-style-name="..."
151 OUString sParentString(rStyle->getParentStyle());
152 OUString sParent;
154 if(sParentString.getLength())
156 if(pPrefix)
157 sParent = *pPrefix;
158 sParent += sParentString;
160 else
161 sParent = sPoolStyleName;
163 if( sParent.getLength() )
164 GetExport().AddAttribute( XML_NAMESPACE_STYLE, XML_PARENT_STYLE_NAME,
165 GetExport().EncodeStyleName( sParent ) );
167 // style:next-style-name="..." (paragraph styles only)
168 if( xPropSetInfo->hasPropertyByName( sFollowStyle ) )
170 aAny = xPropSet->getPropertyValue( sFollowStyle );
171 OUString sNextName;
172 aAny >>= sNextName;
173 if( sName != sNextName )
175 GetExport().AddAttribute( XML_NAMESPACE_STYLE, XML_NEXT_STYLE_NAME,
176 GetExport().EncodeStyleName( sNextName ) );
180 // style:auto-update="..." (SW only)
181 if( xPropSetInfo->hasPropertyByName( sIsAutoUpdate ) )
183 aAny = xPropSet->getPropertyValue( sIsAutoUpdate );
184 if( *(sal_Bool *)aAny.getValue() )
185 GetExport().AddAttribute( XML_NAMESPACE_STYLE, XML_AUTO_UPDATE,
186 XML_TRUE );
189 // style:default-outline-level"..." //#outline level, add by zhaojianwei.0802
190 sal_Int32 nOutlineLevel = 0;
191 if( xPropSetInfo->hasPropertyByName( sOutlineLevel ) )
193 Reference< XPropertyState > xPropState( xPropSet, uno::UNO_QUERY );
194 if( PropertyState_DIRECT_VALUE == xPropState->getPropertyState( sOutlineLevel ) )
196 aAny = xPropSet->getPropertyValue( sOutlineLevel );
197 aAny >>= nOutlineLevel;
198 if( nOutlineLevel > 0 )
200 OUStringBuffer sTmp;
201 sTmp.append( static_cast<sal_Int32>(nOutlineLevel));
202 GetExport().AddAttribute( XML_NAMESPACE_STYLE,
203 XML_DEFAULT_OUTLINE_LEVEL,
204 sTmp.makeStringAndClear() );
206 else
208 GetExport().AddAttribute( XML_NAMESPACE_STYLE, XML_DEFAULT_OUTLINE_LEVEL,
209 OUString( RTL_CONSTASCII_USTRINGPARAM( "" )));
212 }//<-end,zhaojianwei
214 // style:list-style-name="..." (SW paragarph styles only)
215 if( xPropSetInfo->hasPropertyByName( sNumberingStyleName ) )
217 Reference< XPropertyState > xPropState( xPropSet, uno::UNO_QUERY );
218 if( PropertyState_DIRECT_VALUE ==
219 xPropState->getPropertyState( sNumberingStyleName ) )
221 aAny = xPropSet->getPropertyValue( sNumberingStyleName );
222 if( aAny.hasValue() )
224 OUString sListName;
225 aAny >>= sListName;
227 // --> OD 2006-09-21 #i69523#
228 // An direct set empty list style has to be written. Otherwise,
229 // this information is lost and causes an error, if the parent
230 // style has a list style set.
231 if ( !sListName.getLength() )
233 GetExport().AddAttribute( XML_NAMESPACE_STYLE,
234 XML_LIST_STYLE_NAME,
235 sListName /* empty string */);
237 else
239 // --> OD 2006-09-27 #i69627#
240 bool bSuppressListStyle( false );
242 if ( !GetExport().writeOutlineStyleAsNormalListStyle() )
244 Reference< XChapterNumberingSupplier > xCNSupplier
245 (GetExport().GetModel(), UNO_QUERY);
247 OUString sOutlineName;
248 if (xCNSupplier.is())
250 Reference< XIndexReplace > xNumRule
251 ( xCNSupplier->getChapterNumberingRules() );
252 DBG_ASSERT( xNumRule.is(), "no chapter numbering rules" );
254 if (xNumRule.is())
256 Reference< XPropertySet > xNumRulePropSet
257 (xNumRule, UNO_QUERY);
258 xNumRulePropSet->getPropertyValue(
259 OUString(RTL_CONSTASCII_USTRINGPARAM("Name")) )
260 >>= sOutlineName;
261 bSuppressListStyle = ( sListName == sOutlineName );
267 if ( sListName.getLength() && !bSuppressListStyle )
268 // <--
270 GetExport().AddAttribute( XML_NAMESPACE_STYLE,
271 XML_LIST_STYLE_NAME,
272 GetExport().EncodeStyleName( sListName ) );
275 // <--
278 //#outline level, add by zhaojianwei.0802
279 else if( nOutlineLevel > 0 )
282 bool bNoInheritedListStyle( true );
284 /////////////////////////////////////////////////
285 Reference<XStyle> xStyle( xPropState, UNO_QUERY );
286 while ( xStyle.is() )
288 OUString aParentStyle( xStyle->getParentStyle() );
289 if ( aParentStyle.getLength() == 0 ||
290 !xStyles->hasByName( aParentStyle ) )
292 break;
294 else
296 xPropState = Reference< XPropertyState >( xStyles->getByName( aParentStyle ), UNO_QUERY );
297 if ( !xPropState.is() )
299 break;
301 if ( xPropState->getPropertyState( sNumberingStyleName ) == PropertyState_DIRECT_VALUE )
303 bNoInheritedListStyle = false;
304 break;
306 else
308 xStyle = Reference<XStyle>( xPropState, UNO_QUERY );
312 /////////////////////////////////////////////////
313 if ( bNoInheritedListStyle )
314 GetExport().AddAttribute( XML_NAMESPACE_STYLE, XML_LIST_STYLE_NAME,
315 OUString( RTL_CONSTASCII_USTRINGPARAM( "" )));
317 //<-end,zhaojianwei
321 // style:pool-id="..." is not required any longer since we use
322 // english style names only
323 exportStyleAttributes( rStyle );
325 // TODO: style:help-file-name="..." and style:help-id="..." can neither
326 // be modified by UI nor by API and that for, have not to be exported
327 // currently.
330 // <style:style>
331 SvXMLElementExport aElem( GetExport(), XML_NAMESPACE_STYLE, XML_STYLE,
332 sal_True, sal_True );
334 rPropMapper->SetStyleName( sName );
336 // <style:properties>
337 ::std::vector< XMLPropertyState > xPropStates =
338 rPropMapper->Filter( xPropSet );
339 rPropMapper->exportXML( GetExport(), xPropStates,
340 XML_EXPORT_FLAG_IGN_WS );
342 rPropMapper->SetStyleName( OUString() );
344 exportStyleContent( rStyle );
346 // <script:events>, if they are supported by this style
347 Reference<XEventsSupplier> xEventsSupp(rStyle, UNO_QUERY);
348 GetExport().GetEventExport().Export(xEventsSupp);
350 return sal_True;
353 sal_Bool XMLStyleExport::exportDefaultStyle(
354 const Reference< XPropertySet >& xPropSet,
355 const OUString& rXMLFamily,
356 const UniReference < SvXMLExportPropertyMapper >& rPropMapper )
358 Reference< XPropertySetInfo > xPropSetInfo =
359 xPropSet->getPropertySetInfo();
361 Any aAny;
363 // <style:default-style ...>
364 GetExport().CheckAttrList();
367 // style:family="..."
368 if( rXMLFamily.getLength() > 0 )
369 GetExport().AddAttribute( XML_NAMESPACE_STYLE, XML_FAMILY,
370 rXMLFamily );
371 // <style:style>
372 SvXMLElementExport aElem( GetExport(), XML_NAMESPACE_STYLE,
373 XML_DEFAULT_STYLE,
374 sal_True, sal_True );
375 // <style:properties>
376 //::std::vector< XMLPropertyState > xPropStates =
377 // rPropMapper->FilterDefaults( xPropSet );
378 ::std::vector< XMLPropertyState > xPropStates =
379 rPropMapper->FilterDefaults( xPropSet );
380 rPropMapper->exportXML( GetExport(), xPropStates,
381 XML_EXPORT_FLAG_IGN_WS );
382 // exportStyleContent( rStyle );
384 return sal_True;
387 #if 0
388 void XMLStyleExport::exportStyleFamily(
389 const sal_Char *pFamily,
390 const OUString& rXMLFamily,
391 const UniReference < XMLPropertySetMapper >& rPropMapper,
392 sal_Bool bUsed, sal_uInt16 nFamily, const OUString* pPrefix)
394 const OUString sFamily(OUString::createFromAscii(pFamily ));
395 UniReference < SvXMLExportPropertyMapper > xExpPropMapper =
396 new SvXMLExportPropertyMapper( rPropMapper );
397 exportStyleFamily( sFamily, rXMLFamily, xExpPropMapper, bUsed, nFamily,
398 pPrefix);
401 void XMLStyleExport::exportStyleFamily(
402 const OUString& rFamily, const OUString& rXMLFamily,
403 const UniReference < XMLPropertySetMapper >& rPropMapper,
404 sal_Bool bUsed, sal_uInt16 nFamily, const OUString* pPrefix)
406 UniReference < SvXMLExportPropertyMapper > xExpPropMapper =
407 new SvXMLExportPropertyMapper( rPropMapper );
408 exportStyleFamily( rFamily, rXMLFamily, xExpPropMapper, bUsed, nFamily,
409 pPrefix);
411 #endif
413 void XMLStyleExport::exportStyleFamily(
414 const sal_Char *pFamily,
415 const OUString& rXMLFamily,
416 const UniReference < SvXMLExportPropertyMapper >& rPropMapper,
417 sal_Bool bUsed, sal_uInt16 nFamily, const OUString* pPrefix)
419 const OUString sFamily(OUString::createFromAscii(pFamily ));
420 exportStyleFamily( sFamily, rXMLFamily, rPropMapper, bUsed, nFamily,
421 pPrefix);
424 void XMLStyleExport::exportStyleFamily(
425 const OUString& rFamily, const OUString& rXMLFamily,
426 const UniReference < SvXMLExportPropertyMapper >& rPropMapper,
427 sal_Bool bUsed, sal_uInt16 nFamily, const OUString* pPrefix)
429 DBG_ASSERT( GetExport().GetModel().is(), "There is the model?" );
430 Reference< XStyleFamiliesSupplier > xFamiliesSupp( GetExport().GetModel(), UNO_QUERY );
431 if( !xFamiliesSupp.is() )
432 return; // family not available in current model
434 Reference< XNameAccess > xStyleCont;
436 Reference< XNameAccess > xFamilies( xFamiliesSupp->getStyleFamilies() );
437 if( xFamilies->hasByName( rFamily ) )
438 xFamilies->getByName( rFamily ) >>= xStyleCont;
440 if( !xStyleCont.is() )
441 return;
443 Reference< XNameAccess > xStyles( xStyleCont, UNO_QUERY );
444 // If next styles are supported and used styles should be exported only,
445 // the next style may be unused but has to be exported, too. In this case
446 // the names of all exported styles are remembered.
447 SvStringsSortDtor *pExportedStyles = 0;
448 sal_Bool bFirstStyle = sal_True;
450 const uno::Sequence< ::rtl::OUString> aSeq = xStyles->getElementNames();
451 const ::rtl::OUString* pIter = aSeq.getConstArray();
452 const ::rtl::OUString* pEnd = pIter + aSeq.getLength();
453 for(;pIter != pEnd;++pIter)
455 Reference< XStyle > xStyle;
458 xStyles->getByName( *pIter ) >>= xStyle;
460 catch( lang::IndexOutOfBoundsException )
462 // due to bugs in prior versions it is possible that
463 // a binary file is missing some critical styles.
464 // The only possible way to deal with this is to
465 // not export them here and remain silent.
466 continue;
469 DBG_ASSERT( xStyle.is(), "Style not found for export!" );
470 if( xStyle.is() )
472 if( !bUsed || xStyle->isInUse() )
474 BOOL bExported = exportStyle( xStyle, rXMLFamily, rPropMapper,
475 xStyles,pPrefix );
476 if( bUsed && bFirstStyle && bExported )
478 // If this is the first style, find out wether next styles
479 // are supported.
480 Reference< XPropertySet > xPropSet( xStyle, UNO_QUERY );
481 Reference< XPropertySetInfo > xPropSetInfo =
482 xPropSet->getPropertySetInfo();
484 if( xPropSetInfo->hasPropertyByName( sFollowStyle ) )
485 pExportedStyles = new SvStringsSortDtor;
486 bFirstStyle = sal_False;
489 if( pExportedStyles && bExported )
491 // If next styles are supported, remember this style's name.
492 String *pTmp = new String( xStyle->getName() );
493 if( !pExportedStyles->Insert( pTmp ) )
494 delete pTmp;
498 // if an auto style pool is given, remember this style's name as a
499 // style name that must not be used by automatic styles.
500 if( pAutoStylePool )
501 pAutoStylePool->RegisterName( nFamily, xStyle->getName() );
505 if( pExportedStyles )
507 // if next styles are supported, export all next styles that are
508 // unused and that for, haven't been exported in the first loop.
509 pIter = aSeq.getConstArray();
510 for(;pIter != pEnd;++pIter)
512 Reference< XStyle > xStyle;
513 xStyles->getByName( *pIter ) >>= xStyle;
515 DBG_ASSERT( xStyle.is(), "Style not found for export!" );
516 if( xStyle.is() )
518 Reference< XPropertySet > xPropSet( xStyle, UNO_QUERY );
519 Reference< XPropertySetInfo > xPropSetInfo( xPropSet->getPropertySetInfo() );
521 // styles that aren't existing realy are ignored.
522 if( xPropSetInfo->hasPropertyByName( sIsPhysical ) )
524 Any aAny( xPropSet->getPropertyValue( sIsPhysical ) );
525 if( !*(sal_Bool *)aAny.getValue() )
526 continue;
529 if( !xStyle->isInUse() )
530 continue;
532 if( !xPropSetInfo->hasPropertyByName( sFollowStyle ) )
534 DBG_ASSERT( 0==sFollowStyle.getLength(),
535 "no follow style???" );
536 continue;
539 OUString sNextName;
540 xPropSet->getPropertyValue( sFollowStyle ) >>= sNextName;
541 String sTmp( sNextName );
542 // if the next style hasn't been exported by now, export it now
543 // and remember its name.
544 if( xStyle->getName() != sNextName &&
545 !pExportedStyles->Seek_Entry( &sTmp ) )
547 xStyleCont->getByName( sNextName ) >>= xStyle;
548 DBG_ASSERT( xStyle.is(), "Style not found for export!" );
550 if( xStyle.is() && exportStyle( xStyle, rXMLFamily, rPropMapper, xStyles,pPrefix ) )
551 pExportedStyles->Insert( new String( sTmp ) );
557 delete pExportedStyles;