LibreOffice Module xmloff (master)  1
txtftne.cxx
Go to the documentation of this file.
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3  * This file is part of the LibreOffice project.
4  *
5  * This Source Code Form is subject to the terms of the Mozilla Public
6  * License, v. 2.0. If a copy of the MPL was not distributed with this
7  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8  *
9  * This file incorporates work covered by the following license notice:
10  *
11  * Licensed to the Apache Software Foundation (ASF) under one or more
12  * contributor license agreements. See the NOTICE file distributed
13  * with this work for additional information regarding copyright
14  * ownership. The ASF licenses this file to you under the Apache
15  * License, Version 2.0 (the "License"); you may not use this file
16  * except in compliance with the License. You may obtain a copy of
17  * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18  */
19 
20 
30 #include <sal/config.h>
31 #include <sal/log.hxx>
32 
33 #include <o3tl/any.hxx>
34 #include <rtl/ustrbuf.hxx>
35 #include <com/sun/star/lang/XServiceInfo.hpp>
36 #include <com/sun/star/beans/XPropertySet.hpp>
37 #include <com/sun/star/beans/XPropertyState.hpp>
38 #include <com/sun/star/text/XTextDocument.hpp>
39 #include <com/sun/star/text/XText.hpp>
40 #include <com/sun/star/text/XFootnote.hpp>
41 #include <com/sun/star/text/XFootnotesSupplier.hpp>
42 #include <com/sun/star/text/XEndnotesSupplier.hpp>
43 #include <com/sun/star/text/FootnoteNumbering.hpp>
44 #include <com/sun/star/container/XNameReplace.hpp>
45 #include <xmloff/xmltoken.hxx>
46 #include <xmloff/xmlnmspe.hxx>
47 #include <xmloff/xmluconv.hxx>
48 #include <xmloff/xmlexp.hxx>
49 #include <xmloff/families.hxx>
52 #include <xmloff/txtparae.hxx>
53 
54 
55 using namespace ::com::sun::star;
56 using namespace ::com::sun::star::uno;
57 using namespace ::com::sun::star::lang;
58 using namespace ::com::sun::star::beans;
59 using namespace ::com::sun::star::text;
60 using namespace ::com::sun::star::container;
61 using namespace ::xmloff::token;
62 
63 
65  const Reference<XPropertySet> & rPropSet,
66  const OUString& rText,
67  bool bAutoStyles, bool bIsProgress )
68 {
69  // get footnote and associated text
70  Any aAny = rPropSet->getPropertyValue(gsFootnote);
71  Reference<XFootnote> xFootnote;
72  aAny >>= xFootnote;
73  Reference<XText> xText(xFootnote, UNO_QUERY);
74 
75  // are we an endnote?
76  Reference<XServiceInfo> xServiceInfo( xFootnote, UNO_QUERY );
77  bool bIsEndnote = xServiceInfo->supportsService(gsTextEndnoteService);
78 
79  if (bAutoStyles)
80  {
81  // handle formatting of citation mark
82  Add( XmlStyleFamily::TEXT_TEXT, rPropSet );
83 
84  // handle formatting within footnote
85  exportTextFootnoteHelper(xFootnote, xText, rText,
86  bAutoStyles, bIsEndnote, bIsProgress );
87  }
88  else
89  {
90  // create span (for citation mark) if necessary; footnote content
91  // will be handled via exportTextFootnoteHelper, exportText
92  bool bHasHyperlink;
93  bool bIsUICharStyle = false;
94  bool bHasAutoStyle = false;
95 
96  OUString sStyle = FindTextStyleAndHyperlink( rPropSet, bHasHyperlink,
97  bIsUICharStyle, bHasAutoStyle );
98 
99  // export hyperlink (if we have one)
100  Reference < XPropertySetInfo > xPropSetInfo;
101  if( bHasHyperlink )
102  {
103  Reference<XPropertyState> xPropState( rPropSet, UNO_QUERY );
104  xPropSetInfo = rPropSet->getPropertySetInfo();
105  bHasHyperlink =
106  addHyperlinkAttributes( rPropSet, xPropState, xPropSetInfo );
107  }
108  SvXMLElementExport aHyperlink( GetExport(), bHasHyperlink,
110  false, false );
111 
112  if( bHasHyperlink )
113  {
114  // export events (if supported)
115  OUString sHyperLinkEvents("HyperLinkEvents");
116  if (xPropSetInfo->hasPropertyByName(sHyperLinkEvents))
117  {
118  Any a = rPropSet->getPropertyValue(sHyperLinkEvents);
119  Reference<XNameReplace> xName;
120  a >>= xName;
121  GetExport().GetEventExport().Export(xName, false);
122  }
123  }
124 
125  {
126  XMLTextCharStyleNamesElementExport aCharStylesExport(
127  GetExport(), bIsUICharStyle &&
129  rPropSet ), bHasAutoStyle,
130  rPropSet, gsCharStyleNames );
131  if( !sStyle.isEmpty() )
132  {
134  GetExport().EncodeStyleName( sStyle ) );
136  XML_SPAN, false, false );
137  exportTextFootnoteHelper(xFootnote, xText, rText,
138  bAutoStyles, bIsEndnote, bIsProgress );
139  }
140  else
141  {
142  exportTextFootnoteHelper(xFootnote, xText, rText,
143  bAutoStyles, bIsEndnote, bIsProgress );
144  }
145  }
146  }
147 }
148 
149 
151  const Reference<XFootnote> & rFootnote,
152  const Reference<XText> & rText,
153  const OUString& rTextString,
154  bool bAutoStyles,
155  bool bIsEndnote,
156  bool bIsProgress )
157 {
158  if (bAutoStyles)
159  {
160  exportText(rText, bAutoStyles, bIsProgress, true );
161  }
162  else
163  {
164  // export reference Id (for reference fields)
165  Reference<XPropertySet> xPropSet(rFootnote, UNO_QUERY);
166  Any aAny = xPropSet->getPropertyValue(gsReferenceId);
167  sal_Int32 nNumber = 0;
168  aAny >>= nNumber;
170  "ftn" + OUString::number(nNumber));
172  GetXMLToken( bIsEndnote ? XML_ENDNOTE
173  : XML_FOOTNOTE ) );
174 
176  XML_NOTE, false, false);
177  {
178  // handle label vs. automatic numbering
179  OUString sLabel = rFootnote->getLabel();
180  if (!sLabel.isEmpty())
181  {
183  sLabel);
184  }
185  // else: automatic numbering -> no attribute
186 
188  XML_NOTE_CITATION, false, false);
189  GetExport().Characters(rTextString);
190  }
191 
192  {
194  XML_NOTE_BODY, false, false);
195  exportText(rText, bAutoStyles, bIsProgress, true );
196  }
197  }
198 }
199 
200 
202 {
203  // footnote settings
204  Reference<XFootnotesSupplier> aFootnotesSupplier(GetExport().GetModel(),
205  UNO_QUERY);
206  Reference<XPropertySet> aFootnoteConfiguration(
207  aFootnotesSupplier->getFootnoteSettings());
208  exportTextFootnoteConfigurationHelper(aFootnoteConfiguration, false);
209 
210  // endnote settings
211  Reference<XEndnotesSupplier> aEndnotesSupplier(GetExport().GetModel(),
212  UNO_QUERY);
213  Reference<XPropertySet> aEndnoteConfiguration(
214  aEndnotesSupplier->getEndnoteSettings());
215  exportTextFootnoteConfigurationHelper(aEndnoteConfiguration, true);
216 }
217 
218 
219 static void lcl_exportString(
221  const Reference<XPropertySet> & rPropSet,
222  const OUString& sProperty,
223  sal_uInt16 nPrefix,
224  enum XMLTokenEnum eElement,
225  bool bEncodeName)
226 {
227  SAL_WARN_IF( eElement == XML_TOKEN_INVALID, "xmloff", "need element token");
228 
229  Any aAny = rPropSet->getPropertyValue(sProperty);
230  OUString sTmp;
231  aAny >>= sTmp;
232  if (!sTmp.isEmpty())
233  {
234  if( bEncodeName )
235  sTmp = rExport.EncodeStyleName( sTmp );
236  rExport.AddAttribute(nPrefix, eElement, sTmp);
237  }
238 }
239 
241  const Reference<XPropertySet> & rFootnoteConfig,
242  bool bIsEndnote)
243 {
245  GetXMLToken( bIsEndnote ? XML_ENDNOTE
246  : XML_FOOTNOTE ) );
247  // default/paragraph style
248  lcl_exportString( GetExport(), rFootnoteConfig,
251  true);
252 
253  // citation style
254  lcl_exportString( GetExport(), rFootnoteConfig,
257  true);
258 
259  // citation body style
260  lcl_exportString( GetExport(), rFootnoteConfig,
263  true);
264 
265  // page style
266  lcl_exportString( GetExport(), rFootnoteConfig,
269  true );
270 
271  // prefix
272  lcl_exportString( GetExport(), rFootnoteConfig, gsPrefix,
274 
275  // suffix
276  lcl_exportString( GetExport(), rFootnoteConfig, gsSuffix,
278 
279 
280  Any aAny;
281 
282  // numbering style
283  OUStringBuffer sBuffer;
284  aAny = rFootnoteConfig->getPropertyValue(gsNumberingType);
285  sal_Int16 nNumbering = 0;
286  aAny >>= nNumbering;
287  GetExport().GetMM100UnitConverter().convertNumFormat( sBuffer, nNumbering);
289  sBuffer.makeStringAndClear() );
290  SvXMLUnitConverter::convertNumLetterSync( sBuffer, nNumbering);
291  if (!sBuffer.isEmpty() )
292  {
294  sBuffer.makeStringAndClear());
295  }
296 
297  // StartAt / start-value
298  aAny = rFootnoteConfig->getPropertyValue(gsStartAt);
299  sal_Int16 nOffset = 0;
300  aAny >>= nOffset;
302  OUString::number(nOffset));
303 
304  // some properties are for footnotes only
305  if (!bIsEndnote)
306  {
307  // footnotes position
308  aAny = rFootnoteConfig->getPropertyValue(
311  ( (*o3tl::doAccess<bool>(aAny)) ?
312  XML_DOCUMENT : XML_PAGE ) );
313 
314  aAny = rFootnoteConfig->getPropertyValue(gsFootnoteCounting);
315  sal_Int16 nTmp = 0;
316  aAny >>= nTmp;
317  enum XMLTokenEnum eElement;
318  switch (nTmp)
319  {
320  case FootnoteNumbering::PER_PAGE:
321  eElement = XML_PAGE;
322  break;
323  case FootnoteNumbering::PER_CHAPTER:
324  eElement = XML_CHAPTER;
325  break;
326  case FootnoteNumbering::PER_DOCUMENT:
327  default:
328  eElement = XML_DOCUMENT;
329  break;
330  }
332  XML_START_NUMBERING_AT, eElement);
333  }
334 
335  // element
336  SvXMLElementExport aFootnoteConfigElement(
339  true, true);
340 
341  // two element for footnote content
342  if (!bIsEndnote)
343  {
344  OUString sTmp;
345 
346  // end notice / quo vadis
347  aAny = rFootnoteConfig->getPropertyValue(gsEndNotice);
348  aAny >>= sTmp;
349 
350  if (!sTmp.isEmpty())
351  {
354  true, false);
355  GetExport().Characters(sTmp);
356  }
357 
358  // begin notice / ergo sum
359  aAny = rFootnoteConfig->getPropertyValue(gsBeginNotice);
360  aAny >>= sTmp;
361 
362  if (!sTmp.isEmpty())
363  {
366  true, false);
367  GetExport().Characters(sTmp);
368  }
369  }
370 }
371 
372 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
constexpr sal_uInt16 XML_NAMESPACE_STYLE
Definition: xmlnmspe.hxx:30
static const OUStringLiteral gsCharStyleNames
Definition: txtparae.hxx:137
static const OUStringLiteral gsSuffix
Definition: txtparae.hxx:149
static const OUStringLiteral gsFootnote
Definition: txtparae.hxx:139
bool convertNumFormat(sal_Int16 &rType, const OUString &rNumFormat, const OUString &rNumLetterSync, bool bNumberNone=false) const
convert num-format and num-letter-sync values to NumberingType
Definition: xmluconv.cxx:574
const SvXMLUnitConverter & GetMM100UnitConverter() const
Definition: xmlexp.hxx:395
static const OUStringLiteral gsPositionEndOfDoc
Definition: txtparae.hxx:145
constexpr sal_uInt16 XML_NAMESPACE_TEXT
Definition: xmlnmspe.hxx:31
static const OUStringLiteral gsTextEndnoteService
Definition: txtparae.hxx:150
SvXMLExport & GetExport()
Definition: styleexp.hxx:59
void AddAttribute(sal_uInt16 nPrefix, const char *pName, const OUString &rValue)
Definition: xmlexp.cxx:926
bool hasProperty(const css::uno::Reference< css::beans::XPropertySet > &rPropSet, css::uno::Reference< css::beans::XPropertySetInfo > &rPropSetInfo)
XMLTokenEnum
The enumeration of all XML tokens.
Definition: xmltoken.hxx:47
static const OUStringLiteral gsPrefix
Definition: txtparae.hxx:146
static const OUStringLiteral gsAnchorCharStyleName
Definition: txtparae.hxx:133
static const OUStringLiteral gsNumberingType
Definition: txtparae.hxx:141
uno_Any a
XMLEventExport & GetEventExport()
get Event export, with handlers for script types "None" and "StarBasic" already registered; other han...
Definition: xmlexp.cxx:2014
static const OUStringLiteral gsReferenceId
Definition: txtparae.hxx:147
void exportTextFootnoteConfigurationHelper(const css::uno::Reference< css::beans::XPropertySet > &rFootnoteSupplier, bool bIsEndnote)
Definition: txtftne.cxx:240
static const OUStringLiteral gsCharStyleName
Definition: txtparae.hxx:136
static const OUStringLiteral gsEndNotice
Definition: txtparae.hxx:138
void Add(XmlStyleFamily nFamily, MultiPropertySetHelper &rPropSetHelper, const css::uno::Reference< css::beans::XPropertySet > &rPropSet)
add autostyle for specified family
static const OUStringLiteral gsPageStyleName
Definition: txtparae.hxx:143
bool addHyperlinkAttributes(const css::uno::Reference< css::beans::XPropertySet > &rPropSet, const css::uno::Reference< css::beans::XPropertyState > &rPropState, const css::uno::Reference< css::beans::XPropertySetInfo > &rPropSetInfo)
Definition: txtparae.cxx:3301
static void lcl_exportString(SvXMLExport &rExport, const Reference< XPropertySet > &rPropSet, const OUString &sProperty, sal_uInt16 nPrefix, enum XMLTokenEnum eElement, bool bEncodeName)
Definition: txtftne.cxx:219
OUString EncodeStyleName(const OUString &rName, bool *pEncoded=nullptr) const
Definition: xmlexp.cxx:1959
static void convertNumLetterSync(OUStringBuffer &rBuffer, sal_Int16 nType)
Definition: xmluconv.cxx:671
void exportTextFootnoteConfiguration()
export footnote and endnote configuration elements
Definition: txtftne.cxx:201
static const OUStringLiteral gsParaStyleName
Definition: txtparae.hxx:144
#define SAL_WARN_IF(condition, area, stream)
const OUString & GetXMLToken(enum XMLTokenEnum eToken)
return the OUString representation for eToken
Definition: xmltoken.cxx:3366
Handling of tokens in XML:
static const OUStringLiteral gsFootnoteCounting
Definition: txtparae.hxx:140
static const OUStringLiteral gsBeginNotice
Definition: txtparae.hxx:134
void Characters(const OUString &rChars)
Definition: xmlexp.cxx:2163
void exportTextFootnote(const css::uno::Reference< css::beans::XPropertySet > &rPropSet, const OUString &sString, bool bAutoStyles, bool bProgress)
export a footnote and styles
Definition: txtftne.cxx:64
void exportTextFootnoteHelper(const css::uno::Reference< css::text::XFootnote > &rPropSet, const css::uno::Reference< css::text::XText > &rText, const OUString &sString, bool bAutoStyles, bool bIsEndnote, bool bProgress)
helper for exportTextFootnote
Definition: txtftne.cxx:150
static const OUStringLiteral gsStartAt
Definition: txtparae.hxx:148
OUString FindTextStyleAndHyperlink(const css::uno::Reference< css::beans::XPropertySet > &rPropSet, bool &rbHyperlink, bool &rbHasCharStyle, bool &rbHasAutoStyle, const XMLPropertyState **pAddState=nullptr) const
Definition: txtparae.cxx:801
SinglePropertySetInfoCache aCharStyleNamesPropInfoCache
Definition: txtparae.hxx:155
css::uno::Any const SvXMLExport & rExport
Definition: ImageStyle.hxx:38
void exportText(const css::uno::Reference< css::text::XText > &rText, bool bAutoStyles, bool bProgress, bool bExportParagraph, TextPNS eExtensionNS=TextPNS::ODF)
void Export(css::uno::Reference< css::document::XEventsSupplier > const &xAccess, bool bUseWhitespace=true)
export the events (calls EventExport::Export(Reference) )