1 /**************************************************************
2 *
3 * Licensed to the Apache Software Foundation (ASF) under one
4 * or more contributor license agreements. See the NOTICE file
5 * distributed with this work for additional information
6 * regarding copyright ownership. The ASF licenses this file
7 * to you under the Apache License, Version 2.0 (the
8 * "License"); you may not use this file except in compliance
9 * with the License. You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing,
14 * software distributed under the License is distributed on an
15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16 * KIND, either express or implied. See the License for the
17 * specific language governing permissions and limitations
18 * under the License.
19 *
20 *************************************************************/
21
22
23
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_xmloff.hxx"
26 #include "PageMasterExportPropMapper.hxx"
27 #include <xmloff/xmltoken.hxx>
28 #include <comphelper/types.hxx>
29 #include <com/sun/star/table/BorderLine.hpp>
30 #include <xmloff/PageMasterStyleMap.hxx>
31 #include <tools/debug.hxx>
32 #include <rtl/ustrbuf.hxx>
33 #include <comphelper/extract.hxx>
34
35 using namespace ::com::sun::star;
36 using namespace ::com::sun::star::uno;
37 using namespace ::com::sun::star::beans;
38 using namespace ::comphelper;
39 using namespace ::xmloff::token;
40
41
42 //______________________________________________________________________________
43
lcl_HasSameLineWidth(const table::BorderLine & rLine1,const table::BorderLine & rLine2)44 inline sal_Bool lcl_HasSameLineWidth( const table::BorderLine& rLine1, const table::BorderLine& rLine2 )
45 {
46 return (rLine1.InnerLineWidth == rLine2.InnerLineWidth) &&
47 (rLine1.OuterLineWidth == rLine2.OuterLineWidth) &&
48 (rLine1.LineDistance == rLine2.LineDistance);
49 }
50
operator ==(const table::BorderLine & rLine1,const table::BorderLine & rLine2)51 inline sal_Bool operator==( const table::BorderLine& rLine1, const table::BorderLine& rLine2 )
52 {
53 return (rLine1.Color == rLine2.Color) &&
54 lcl_HasSameLineWidth( rLine1, rLine2 );
55 }
56
lcl_RemoveState(XMLPropertyState * pState)57 inline void lcl_RemoveState( XMLPropertyState* pState )
58 {
59 pState->mnIndex = -1;
60 pState->maValue.clear();
61 }
62
lcl_RemoveStateIfZero16(XMLPropertyState * pState)63 void lcl_RemoveStateIfZero16( XMLPropertyState* pState )
64 {
65 sal_Int16 nValue = sal_Int16();
66 if( (pState->maValue >>= nValue) && !nValue )
67 lcl_RemoveState( pState );
68 }
69
lcl_AddState(::std::vector<XMLPropertyState> & rPropState,sal_Int32 nIndex,const rtl::OUString & rProperty,uno::Reference<beans::XPropertySet> & xProps)70 void lcl_AddState(::std::vector< XMLPropertyState >& rPropState, sal_Int32 nIndex, const rtl::OUString& rProperty, uno::Reference< beans::XPropertySet >& xProps)
71 {
72 if(::cppu::any2bool(xProps->getPropertyValue(rProperty)))
73 rPropState.push_back(XMLPropertyState (nIndex, cppu::bool2any(sal_True)));
74 }
75
76 //______________________________________________________________________________
77 // helper struct to handle equal XMLPropertyState's for page, header and footer
78
79 struct XMLPropertyStateBuffer
80 {
81 XMLPropertyState* pPMMarginAll;
82 XMLPropertyState* pPMMarginTop;
83 XMLPropertyState* pPMMarginBottom;
84 XMLPropertyState* pPMMarginLeft;
85 XMLPropertyState* pPMMarginRight;
86
87 XMLPropertyState* pPMBorderAll;
88 XMLPropertyState* pPMBorderTop;
89 XMLPropertyState* pPMBorderBottom;
90 XMLPropertyState* pPMBorderLeft;
91 XMLPropertyState* pPMBorderRight;
92
93 XMLPropertyState* pPMBorderWidthAll;
94 XMLPropertyState* pPMBorderWidthTop;
95 XMLPropertyState* pPMBorderWidthBottom;
96 XMLPropertyState* pPMBorderWidthLeft;
97 XMLPropertyState* pPMBorderWidthRight;
98
99 XMLPropertyState* pPMPaddingAll;
100 XMLPropertyState* pPMPaddingTop;
101 XMLPropertyState* pPMPaddingBottom;
102 XMLPropertyState* pPMPaddingLeft;
103 XMLPropertyState* pPMPaddingRight;
104
105 XMLPropertyStateBuffer();
106 void ContextFilter( ::std::vector< XMLPropertyState >& rPropState );
107 };
108
XMLPropertyStateBuffer()109 XMLPropertyStateBuffer::XMLPropertyStateBuffer()
110 : pPMMarginAll( NULL )
111 , pPMMarginTop( NULL )
112 , pPMMarginBottom( NULL )
113 , pPMMarginLeft( NULL )
114 , pPMMarginRight( NULL )
115 ,
116 pPMBorderAll( NULL ),
117 pPMBorderTop( NULL ),
118 pPMBorderBottom( NULL ),
119 pPMBorderLeft( NULL ),
120 pPMBorderRight( NULL ),
121
122 pPMBorderWidthAll( NULL ),
123 pPMBorderWidthTop( NULL ),
124 pPMBorderWidthBottom( NULL ),
125 pPMBorderWidthLeft( NULL ),
126 pPMBorderWidthRight( NULL ),
127
128 pPMPaddingAll( NULL ),
129 pPMPaddingTop( NULL ),
130 pPMPaddingBottom( NULL ),
131 pPMPaddingLeft( NULL ),
132 pPMPaddingRight( NULL )
133 {
134 }
135
ContextFilter(::std::vector<XMLPropertyState> &)136 void XMLPropertyStateBuffer::ContextFilter( ::std::vector< XMLPropertyState >& )
137 {
138 if (pPMMarginAll)
139 {
140 lcl_RemoveState(pPMMarginAll); // #i117696# do not write fo:margin
141 }
142
143 if( pPMBorderAll )
144 {
145 if( pPMBorderTop && pPMBorderBottom && pPMBorderLeft && pPMBorderRight )
146 {
147 table::BorderLine aLineTop, aLineBottom, aLineLeft, aLineRight;
148
149 pPMBorderTop->maValue >>= aLineTop;
150 pPMBorderBottom->maValue >>= aLineBottom;
151 pPMBorderLeft->maValue >>= aLineLeft;
152 pPMBorderRight->maValue >>= aLineRight;
153
154 if( (aLineTop == aLineBottom) && (aLineBottom == aLineLeft) && (aLineLeft == aLineRight) )
155 {
156 lcl_RemoveState( pPMBorderTop );
157 lcl_RemoveState( pPMBorderBottom );
158 lcl_RemoveState( pPMBorderLeft );
159 lcl_RemoveState( pPMBorderRight );
160 }
161 else
162 lcl_RemoveState( pPMBorderAll );
163 }
164 else
165 lcl_RemoveState( pPMBorderAll );
166 }
167
168 if( pPMBorderWidthAll )
169 {
170 if( pPMBorderWidthTop && pPMBorderWidthBottom && pPMBorderWidthLeft && pPMBorderWidthRight )
171 {
172 table::BorderLine aLineTop, aLineBottom, aLineLeft, aLineRight;
173
174 pPMBorderWidthTop->maValue >>= aLineTop;
175 pPMBorderWidthBottom->maValue >>= aLineBottom;
176 pPMBorderWidthLeft->maValue >>= aLineLeft;
177 pPMBorderWidthRight->maValue >>= aLineRight;
178
179 if( lcl_HasSameLineWidth( aLineTop, aLineBottom ) &&
180 lcl_HasSameLineWidth( aLineBottom, aLineLeft ) &&
181 lcl_HasSameLineWidth( aLineLeft, aLineRight ) )
182 {
183 lcl_RemoveState( pPMBorderWidthTop );
184 lcl_RemoveState( pPMBorderWidthBottom );
185 lcl_RemoveState( pPMBorderWidthLeft );
186 lcl_RemoveState( pPMBorderWidthRight );
187 }
188 else
189 lcl_RemoveState( pPMBorderWidthAll );
190 }
191 else
192 lcl_RemoveState( pPMBorderWidthAll );
193 }
194
195 if( pPMPaddingAll )
196 {
197 if( pPMPaddingTop && pPMPaddingBottom && pPMPaddingLeft && pPMPaddingRight )
198 {
199 sal_Int32 nTop = 0, nBottom = 0, nLeft = 0, nRight = 0;
200
201 pPMPaddingTop->maValue >>= nTop;
202 pPMPaddingBottom->maValue >>= nBottom;
203 pPMPaddingLeft->maValue >>= nLeft;
204 pPMPaddingRight->maValue >>= nRight;
205
206 if( (nTop == nBottom) && (nBottom == nLeft) && (nLeft == nRight) )
207 {
208 lcl_RemoveState( pPMPaddingTop );
209 lcl_RemoveState( pPMPaddingBottom );
210 lcl_RemoveState( pPMPaddingLeft );
211 lcl_RemoveState( pPMPaddingRight );
212 }
213 else
214 lcl_RemoveState( pPMPaddingAll );
215 }
216 else
217 lcl_RemoveState( pPMPaddingAll );
218 }
219 }
220
221 //______________________________________________________________________________
222
XMLPageMasterExportPropMapper(const UniReference<XMLPropertySetMapper> & rMapper,SvXMLExport & rExport)223 XMLPageMasterExportPropMapper::XMLPageMasterExportPropMapper(
224 const UniReference< XMLPropertySetMapper >& rMapper,
225 SvXMLExport& rExport ) :
226 SvXMLExportPropertyMapper( rMapper ),
227 aBackgroundImageExport( rExport ),
228 aTextColumnsExport( rExport ),
229 aFootnoteSeparatorExport( rExport )
230 {
231 }
232
~XMLPageMasterExportPropMapper()233 XMLPageMasterExportPropMapper::~XMLPageMasterExportPropMapper()
234 {
235 }
236
handleElementItem(SvXMLExport &,const XMLPropertyState & rProperty,sal_uInt16,const::std::vector<XMLPropertyState> * pProperties,sal_uInt32 nIdx) const237 void XMLPageMasterExportPropMapper::handleElementItem(
238 SvXMLExport&,
239 const XMLPropertyState& rProperty,
240 sal_uInt16 /*nFlags*/,
241 const ::std::vector< XMLPropertyState >* pProperties,
242 sal_uInt32 nIdx ) const
243 {
244 XMLPageMasterExportPropMapper* pThis = (XMLPageMasterExportPropMapper*) this;
245
246 sal_uInt32 nContextId = getPropertySetMapper()->GetEntryContextId( rProperty.mnIndex );
247 switch( nContextId )
248 {
249 case CTF_PM_GRAPHICURL:
250 case CTF_PM_HEADERGRAPHICURL:
251 case CTF_PM_FOOTERGRAPHICURL:
252 {
253 DBG_ASSERT( pProperties && (nIdx >= 2), "property vector missing" );
254 sal_Int32 nPos;
255 sal_Int32 nFilter;
256 switch( nContextId )
257 {
258 case CTF_PM_GRAPHICURL:
259 nPos = CTF_PM_GRAPHICPOSITION;
260 nFilter = CTF_PM_GRAPHICFILTER;
261 break;
262 case CTF_PM_HEADERGRAPHICURL:
263 nPos = CTF_PM_HEADERGRAPHICPOSITION;
264 nFilter = CTF_PM_HEADERGRAPHICFILTER;
265 break;
266 case CTF_PM_FOOTERGRAPHICURL:
267 nPos = CTF_PM_FOOTERGRAPHICPOSITION;
268 nFilter = CTF_PM_FOOTERGRAPHICFILTER;
269 break;
270 default:
271 nPos = 0; // TODO What values should this be?
272 nFilter = 0;
273 }
274 const Any* pPos = NULL;
275 const Any* pFilter = NULL;
276 if( pProperties && (nIdx >= 2) )
277 {
278 const XMLPropertyState& rPos = (*pProperties)[nIdx - 2];
279 DBG_ASSERT( getPropertySetMapper()->GetEntryContextId( rPos.mnIndex ) == nPos,
280 "invalid property map: pos expected" );
281 if( getPropertySetMapper()->GetEntryContextId( rPos.mnIndex ) == nPos )
282 pPos = &rPos.maValue;
283
284 const XMLPropertyState& rFilter = (*pProperties)[nIdx - 1];
285 DBG_ASSERT( getPropertySetMapper()->GetEntryContextId( rFilter.mnIndex ) == nFilter,
286 "invalid property map: filter expected" );
287 if( getPropertySetMapper()->GetEntryContextId( rFilter.mnIndex ) == nFilter )
288 pFilter = &rFilter.maValue;
289 }
290 sal_uInt32 nPropIndex = rProperty.mnIndex;
291 pThis->aBackgroundImageExport.exportXML( rProperty.maValue, pPos, pFilter, NULL,
292 getPropertySetMapper()->GetEntryNameSpace( nPropIndex ),
293 getPropertySetMapper()->GetEntryXMLName( nPropIndex ) );
294 }
295 break;
296 case CTF_PM_TEXTCOLUMNS:
297 pThis->aTextColumnsExport.exportXML( rProperty.maValue );
298 break;
299 case CTF_PM_FTN_LINE_WEIGTH:
300 pThis->aFootnoteSeparatorExport.exportXML( pProperties, nIdx,
301 getPropertySetMapper());
302 break;
303 }
304 }
305
handleSpecialItem(SvXMLAttributeList &,const XMLPropertyState &,const SvXMLUnitConverter &,const SvXMLNamespaceMap &,const::std::vector<XMLPropertyState> *,sal_uInt32) const306 void XMLPageMasterExportPropMapper::handleSpecialItem(
307 SvXMLAttributeList&,
308 const XMLPropertyState&,
309 const SvXMLUnitConverter&,
310 const SvXMLNamespaceMap&,
311 const ::std::vector< XMLPropertyState >*,
312 sal_uInt32 /*nIdx*/) const
313 {
314 }
315
ContextFilter(::std::vector<XMLPropertyState> & rPropState,Reference<XPropertySet> rPropSet) const316 void XMLPageMasterExportPropMapper::ContextFilter(
317 ::std::vector< XMLPropertyState >& rPropState,
318 Reference< XPropertySet > rPropSet ) const
319 {
320 XMLPropertyStateBuffer aPageBuffer;
321 XMLPropertyStateBuffer aHeaderBuffer;
322 XMLPropertyStateBuffer aFooterBuffer;
323
324 XMLPropertyState* pPMHeaderHeight = NULL;
325 XMLPropertyState* pPMHeaderMinHeight = NULL;
326 XMLPropertyState* pPMHeaderDynamic = NULL;
327
328 XMLPropertyState* pPMFooterHeight = NULL;
329 XMLPropertyState* pPMFooterMinHeight = NULL;
330 XMLPropertyState* pPMFooterDynamic = NULL;
331
332 XMLPropertyState* pPMScaleTo = NULL;
333 XMLPropertyState* pPMScaleToPages = NULL;
334 XMLPropertyState* pPMScaleToX = NULL;
335 XMLPropertyState* pPMScaleToY = NULL;
336 XMLPropertyState* pPMStandardMode = NULL;
337 XMLPropertyState* pPMGridBaseWidth = NULL;
338 XMLPropertyState* pPMGridSnapToChars = NULL;
339
340 XMLPropertyState* pPrint = NULL;
341
342 UniReference < XMLPropertySetMapper > aPropMapper(getPropertySetMapper());
343
344 for( ::std::vector< XMLPropertyState >::iterator aIter = rPropState.begin(); aIter != rPropState.end(); ++aIter )
345 {
346 XMLPropertyState *pProp = &(*aIter);
347 sal_Int16 nContextId = aPropMapper->GetEntryContextId( pProp->mnIndex );
348 sal_Int16 nFlag = nContextId & CTF_PM_FLAGMASK;
349 sal_Int16 nSimpleId = nContextId & (~CTF_PM_FLAGMASK | XML_PM_CTF_START);
350 sal_Int16 nPrintId = nContextId & CTF_PM_PRINTMASK;
351
352 XMLPropertyStateBuffer* pBuffer;
353 switch( nFlag )
354 {
355 case CTF_PM_HEADERFLAG: pBuffer = &aHeaderBuffer; break;
356 case CTF_PM_FOOTERFLAG: pBuffer = &aFooterBuffer; break;
357 default: pBuffer = &aPageBuffer; break;
358 }
359
360 switch( nSimpleId )
361 {
362 case CTF_PM_MARGINALL: pBuffer->pPMMarginAll = pProp; break;
363 case CTF_PM_MARGINTOP: pBuffer->pPMMarginTop = pProp; break;
364 case CTF_PM_MARGINBOTTOM: pBuffer->pPMMarginBottom = pProp; break;
365 case CTF_PM_MARGINLEFT: pBuffer->pPMMarginLeft = pProp; break;
366 case CTF_PM_MARGINRIGHT: pBuffer->pPMMarginRight = pProp; break;
367 case CTF_PM_BORDERALL: pBuffer->pPMBorderAll = pProp; break;
368 case CTF_PM_BORDERTOP: pBuffer->pPMBorderTop = pProp; break;
369 case CTF_PM_BORDERBOTTOM: pBuffer->pPMBorderBottom = pProp; break;
370 case CTF_PM_BORDERLEFT: pBuffer->pPMBorderLeft = pProp; break;
371 case CTF_PM_BORDERRIGHT: pBuffer->pPMBorderRight = pProp; break;
372 case CTF_PM_BORDERWIDTHALL: pBuffer->pPMBorderWidthAll = pProp; break;
373 case CTF_PM_BORDERWIDTHTOP: pBuffer->pPMBorderWidthTop = pProp; break;
374 case CTF_PM_BORDERWIDTHBOTTOM: pBuffer->pPMBorderWidthBottom = pProp; break;
375 case CTF_PM_BORDERWIDTHLEFT: pBuffer->pPMBorderWidthLeft = pProp; break;
376 case CTF_PM_BORDERWIDTHRIGHT: pBuffer->pPMBorderWidthRight = pProp; break;
377 case CTF_PM_PADDINGALL: pBuffer->pPMPaddingAll = pProp; break;
378 case CTF_PM_PADDINGTOP: pBuffer->pPMPaddingTop = pProp; break;
379 case CTF_PM_PADDINGBOTTOM: pBuffer->pPMPaddingBottom = pProp; break;
380 case CTF_PM_PADDINGLEFT: pBuffer->pPMPaddingLeft = pProp; break;
381 case CTF_PM_PADDINGRIGHT: pBuffer->pPMPaddingRight = pProp; break;
382 }
383
384 switch( nContextId )
385 {
386 case CTF_PM_HEADERHEIGHT: pPMHeaderHeight = pProp; break;
387 case CTF_PM_HEADERMINHEIGHT: pPMHeaderMinHeight = pProp; break;
388 case CTF_PM_HEADERDYNAMIC: pPMHeaderDynamic = pProp; break;
389 case CTF_PM_FOOTERHEIGHT: pPMFooterHeight = pProp; break;
390 case CTF_PM_FOOTERMINHEIGHT: pPMFooterMinHeight = pProp; break;
391 case CTF_PM_FOOTERDYNAMIC: pPMFooterDynamic = pProp; break;
392 case CTF_PM_SCALETO: pPMScaleTo = pProp; break;
393 case CTF_PM_SCALETOPAGES: pPMScaleToPages = pProp; break;
394 case CTF_PM_SCALETOX: pPMScaleToX = pProp; break;
395 case CTF_PM_SCALETOY: pPMScaleToY = pProp; break;
396 case CTF_PM_STANDARD_MODE: pPMStandardMode = pProp; break;
397 case CTP_PM_GRID_BASE_WIDTH: pPMGridBaseWidth = pProp; break;
398 case CTP_PM_GRID_SNAP_TO_CHARS: pPMGridSnapToChars = pProp; break;
399 }
400 if (nPrintId == CTF_PM_PRINTMASK)
401 {
402 pPrint = pProp;
403 lcl_RemoveState(pPrint);
404 }
405 }
406
407 if( pPMStandardMode && !getBOOL(pPMStandardMode->maValue) )
408 {
409 lcl_RemoveState(pPMStandardMode);
410 if( pPMGridBaseWidth )
411 lcl_RemoveState(pPMGridBaseWidth);
412 if( pPMGridSnapToChars )
413 lcl_RemoveState(pPMGridSnapToChars);
414 }
415
416 if( pPMGridBaseWidth && pPMStandardMode )
417 lcl_RemoveState(pPMStandardMode);
418
419 aPageBuffer.ContextFilter( rPropState );
420 aHeaderBuffer.ContextFilter( rPropState );
421 aFooterBuffer.ContextFilter( rPropState );
422
423 if( pPMHeaderHeight && (!pPMHeaderDynamic || (pPMHeaderDynamic && getBOOL( pPMHeaderDynamic->maValue ))) )
424 lcl_RemoveState( pPMHeaderHeight );
425 if( pPMHeaderMinHeight && pPMHeaderDynamic && !getBOOL( pPMHeaderDynamic->maValue ) )
426 lcl_RemoveState( pPMHeaderMinHeight );
427 if( pPMHeaderDynamic )
428 lcl_RemoveState( pPMHeaderDynamic );
429
430 if( pPMFooterHeight && (!pPMFooterDynamic || (pPMFooterDynamic && getBOOL( pPMFooterDynamic->maValue ))) )
431 lcl_RemoveState( pPMFooterHeight );
432 if( pPMFooterMinHeight && pPMFooterDynamic && !getBOOL( pPMFooterDynamic->maValue ) )
433 lcl_RemoveState( pPMFooterMinHeight );
434 if( pPMFooterDynamic )
435 lcl_RemoveState( pPMFooterDynamic );
436
437 if( pPMScaleTo )
438 lcl_RemoveStateIfZero16( pPMScaleTo );
439 if( pPMScaleToPages )
440 lcl_RemoveStateIfZero16( pPMScaleToPages );
441 if( pPMScaleToX )
442 lcl_RemoveStateIfZero16( pPMScaleToX );
443 if( pPMScaleToY )
444 lcl_RemoveStateIfZero16( pPMScaleToY );
445
446 if (pPrint)
447 {
448 lcl_AddState(rPropState, aPropMapper->FindEntryIndex(CTF_PM_PRINT_ANNOTATIONS), rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("PrintAnnotations")), rPropSet);
449 lcl_AddState(rPropState, aPropMapper->FindEntryIndex(CTF_PM_PRINT_CHARTS), rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("PrintCharts")), rPropSet);
450 lcl_AddState(rPropState, aPropMapper->FindEntryIndex(CTF_PM_PRINT_DRAWING), rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("PrintDrawing")), rPropSet);
451 lcl_AddState(rPropState, aPropMapper->FindEntryIndex(CTF_PM_PRINT_FORMULAS), rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("PrintFormulas")), rPropSet);
452 lcl_AddState(rPropState, aPropMapper->FindEntryIndex(CTF_PM_PRINT_GRID), rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("PrintGrid")), rPropSet);
453 lcl_AddState(rPropState, aPropMapper->FindEntryIndex(CTF_PM_PRINT_HEADERS), rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("PrintHeaders")), rPropSet);
454 lcl_AddState(rPropState, aPropMapper->FindEntryIndex(CTF_PM_PRINT_OBJECTS), rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("PrintObjects")), rPropSet);
455 lcl_AddState(rPropState, aPropMapper->FindEntryIndex(CTF_PM_PRINT_ZEROVALUES), rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("PrintZeroValues")), rPropSet);
456 }
457
458 SvXMLExportPropertyMapper::ContextFilter(rPropState,rPropSet);
459 }
460
461