LibreOffice Module sw (master)  1
rtfattributeoutput.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 #include "rtfattributeoutput.hxx"
21 #include <memory>
22 #include <cstring>
23 #include "rtfsdrexport.hxx"
24 #include "writerwordglue.hxx"
25 #include "ww8par.hxx"
26 #include <fmtcntnt.hxx>
27 #include <rtl/tencinfo.h>
28 #include <sal/log.hxx>
29 #include <sot/exchange.hxx>
30 #include <svtools/rtfkeywd.hxx>
31 #include <editeng/fontitem.hxx>
32 #include <editeng/tstpitem.hxx>
33 #include <editeng/adjustitem.hxx>
34 #include <editeng/spltitem.hxx>
35 #include <editeng/widwitem.hxx>
36 #include <editeng/postitem.hxx>
37 #include <editeng/wghtitem.hxx>
38 #include <editeng/kernitem.hxx>
40 #include <editeng/cmapitem.hxx>
41 #include <editeng/wrlmitem.hxx>
42 #include <editeng/udlnitem.hxx>
43 #include <editeng/langitem.hxx>
45 #include <editeng/fhgtitem.hxx>
46 #include <editeng/colritem.hxx>
48 #include <editeng/contouritem.hxx>
49 #include <editeng/shdditem.hxx>
50 #include <editeng/autokernitem.hxx>
52 #include <editeng/twolinesitem.hxx>
57 #include <editeng/blinkitem.hxx>
59 #include <editeng/boxitem.hxx>
60 #include <editeng/brushitem.hxx>
61 #include <editeng/ulspitem.hxx>
62 #include <editeng/shaditem.hxx>
63 #include <editeng/keepitem.hxx>
64 #include <editeng/frmdiritem.hxx>
65 #include <editeng/opaqitem.hxx>
66 #include <svx/svdouno.hxx>
68 #include <sfx2/sfxbasemodel.hxx>
69 #include <svx/xflgrit.hxx>
70 #include <docufld.hxx>
71 #include <fmtclds.hxx>
72 #include <fmtrowsplt.hxx>
73 #include <fmtline.hxx>
74 #include <fmtanchr.hxx>
75 #include <ftninfo.hxx>
76 #include <htmltbl.hxx>
77 #include <ndgrf.hxx>
78 #include <pagedesc.hxx>
79 #include <swmodule.hxx>
80 #include <txtftn.hxx>
81 #include <txtinet.hxx>
82 #include <grfatr.hxx>
83 #include <ndole.hxx>
84 #include <lineinfo.hxx>
85 #include <rtf.hxx>
87 #include <vcl/cvtgrf.hxx>
88 #include <oox/mathml/export.hxx>
89 #include <com/sun/star/i18n/ScriptType.hpp>
90 #include <svl/grabbagitem.hxx>
91 #include <frmatr.hxx>
92 #include <swtable.hxx>
93 #include "rtfexport.hxx"
94 
95 using namespace ::com::sun::star;
96 using namespace sw::util;
97 
98 static OString OutTBLBorderLine(RtfExport const& rExport, const editeng::SvxBorderLine* pLine,
99  const sal_Char* pStr)
100 {
101  OStringBuffer aRet;
102  if (!pLine->isEmpty())
103  {
104  aRet.append(pStr);
105  // single line
106  switch (pLine->GetBorderLineStyle())
107  {
108  case SvxBorderLineStyle::SOLID:
109  {
110  if (DEF_LINE_WIDTH_0 == pLine->GetWidth())
111  aRet.append(OOO_STRING_SVTOOLS_RTF_BRDRHAIR);
112  else
113  aRet.append(OOO_STRING_SVTOOLS_RTF_BRDRS);
114  }
115  break;
116  case SvxBorderLineStyle::DOTTED:
117  aRet.append(OOO_STRING_SVTOOLS_RTF_BRDRDOT);
118  break;
119  case SvxBorderLineStyle::DASHED:
120  aRet.append(OOO_STRING_SVTOOLS_RTF_BRDRDASH);
121  break;
122  case SvxBorderLineStyle::DOUBLE:
123  case SvxBorderLineStyle::DOUBLE_THIN:
124  aRet.append(OOO_STRING_SVTOOLS_RTF_BRDRDB);
125  break;
126  case SvxBorderLineStyle::THINTHICK_SMALLGAP:
128  break;
129  case SvxBorderLineStyle::THINTHICK_MEDIUMGAP:
131  break;
132  case SvxBorderLineStyle::THINTHICK_LARGEGAP:
134  break;
135  case SvxBorderLineStyle::THICKTHIN_SMALLGAP:
137  break;
138  case SvxBorderLineStyle::THICKTHIN_MEDIUMGAP:
140  break;
141  case SvxBorderLineStyle::THICKTHIN_LARGEGAP:
143  break;
144  case SvxBorderLineStyle::EMBOSSED:
146  break;
147  case SvxBorderLineStyle::ENGRAVED:
149  break;
150  case SvxBorderLineStyle::OUTSET:
152  break;
153  case SvxBorderLineStyle::INSET:
155  break;
156  case SvxBorderLineStyle::FINE_DASHED:
158  break;
159  case SvxBorderLineStyle::DASH_DOT:
161  break;
162  case SvxBorderLineStyle::DASH_DOT_DOT:
164  break;
165  case SvxBorderLineStyle::NONE:
166  default:
167  aRet.append(OOO_STRING_SVTOOLS_RTF_BRDRNONE);
168  break;
169  }
170 
171  double const fConverted(
173  if (255 >= pLine->GetWidth()) // That value comes from RTF specs
174  {
175  aRet.append(OOO_STRING_SVTOOLS_RTF_BRDRW).append(static_cast<sal_Int32>(fConverted));
176  }
177  else
178  {
179  // use \brdrth to double the value range...
181  aRet.append(static_cast<sal_Int32>(fConverted) / 2);
182  }
183 
184  aRet.append(OOO_STRING_SVTOOLS_RTF_BRDRCF);
185  aRet.append(static_cast<sal_Int32>(rExport.GetColor(pLine->GetColor())));
186  }
187  return aRet.makeStringAndClear();
188 }
189 
190 static OString OutBorderLine(RtfExport const& rExport, const editeng::SvxBorderLine* pLine,
191  const sal_Char* pStr, sal_uInt16 nDist,
192  SvxShadowLocation eShadowLocation = SvxShadowLocation::NONE)
193 {
194  OStringBuffer aRet;
195  aRet.append(OutTBLBorderLine(rExport, pLine, pStr));
196  aRet.append(OOO_STRING_SVTOOLS_RTF_BRSP);
197  aRet.append(static_cast<sal_Int32>(nDist));
198  if (eShadowLocation == SvxShadowLocation::BottomRight)
199  aRet.append(LO_STRING_SVTOOLS_RTF_BRDRSH);
200  return aRet.makeStringAndClear();
201 }
202 
203 void RtfAttributeOutput::RTLAndCJKState(bool bIsRTL, sal_uInt16 nScript)
204 {
205  /*
206  You would have thought that
207  m_rExport.Strm() << (bIsRTL ? OOO_STRING_SVTOOLS_RTF_RTLCH : OOO_STRING_SVTOOLS_RTF_LTRCH); would be sufficient here ,
208  but looks like word needs to see the other directional token to be
209  satisfied that all is kosher, otherwise it seems in ver 2003 to go and
210  semi-randomly stick strike through about the place. Perhaps
211  strikethrough is some ms developers "something is wrong signal" debugging
212  code that we're triggering ?
213  */
214  if (bIsRTL)
215  {
216  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_LTRCH);
217  m_aStylesEnd.append(' ');
218  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_RTLCH);
219  }
220  else
221  {
222  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_RTLCH);
223  m_aStylesEnd.append(' ');
224  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_LTRCH);
225  }
226 
227  switch (nScript)
228  {
229  case i18n::ScriptType::LATIN:
230  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_LOCH);
231  break;
232  case i18n::ScriptType::ASIAN:
233  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_DBCH);
234  break;
235  case i18n::ScriptType::COMPLEX:
236  /* noop */
237  break;
238  default:
239  /* should not happen? */
240  break;
241  }
242 }
243 
245 {
246  if (m_bIsBeforeFirstParagraph && m_rExport.m_nTextTyp != TXT_HDFT)
247  m_bIsBeforeFirstParagraph = false;
248 
249  // Output table/table row/table cell starts if needed
250  if (pTextNodeInfo)
251  {
252  sal_uInt32 nRow = pTextNodeInfo->getRow();
253  sal_uInt32 nCell = pTextNodeInfo->getCell();
254 
255  // New cell/row?
256  if (m_nTableDepth > 0 && !m_bTableCellOpen)
257  {
259  pTextNodeInfo->getInnerForDepth(m_nTableDepth));
260  OSL_ENSURE(pDeepInner, "TableNodeInfoInner not found");
261  // Make sure we always start a row between ending one and starting a cell.
262  // In case of subtables, we may not get the first cell.
263  if (pDeepInner && (pDeepInner->getCell() == 0 || m_bTableRowEnded))
264  {
265  StartTableRow(pDeepInner);
266  }
267 
268  StartTableCell();
269  }
270 
271  // Again, if depth was incremented, start a new table even if we skipped the first cell.
272  if ((nRow == 0 && nCell == 0) || (m_nTableDepth == 0 && pTextNodeInfo->getDepth()))
273  {
274  // Do we have to start the table?
275  // [If we are at the right depth already, it means that we
276  // continue the table cell]
277  sal_uInt32 nCurrentDepth = pTextNodeInfo->getDepth();
278 
279  if (nCurrentDepth > m_nTableDepth)
280  {
281  // Start all the tables that begin here
282  for (sal_uInt32 nDepth = m_nTableDepth + 1; nDepth <= pTextNodeInfo->getDepth();
283  ++nDepth)
284  {
286  pTextNodeInfo->getInnerForDepth(nDepth));
287 
288  m_bLastTable = (nDepth == pTextNodeInfo->getDepth());
289  StartTable();
290  StartTableRow(pInner);
291  StartTableCell();
292  }
293 
294  m_nTableDepth = nCurrentDepth;
295  }
296  }
297  }
298 
299  OSL_ENSURE(m_aRun.getLength() == 0, "m_aRun is not empty");
300 }
301 
303 {
304  bool bLastPara = false;
305  if (m_rExport.m_nTextTyp == TXT_FTN || m_rExport.m_nTextTyp == TXT_EDN
306  || m_rExport.m_pDoc->IsClipBoard())
307  {
308  // We're ending a paragraph that is the last paragraph of a footnote or endnote, or of clipboard.
309  bLastPara
310  = m_rExport.GetCurrentNodeIndex()
311  && m_rExport.GetCurrentNodeIndex() == m_rExport.m_pCurPam->End()->nNode.GetIndex();
312  }
313 
314  FinishTableRowCell(pTextNodeInfoInner);
315 
316  RtfStringBuffer aParagraph;
317 
318  aParagraph.appendAndClear(m_aRun);
319  aParagraph->append(m_aAfterRuns.makeStringAndClear());
320  if (m_bTableAfterCell)
321  m_bTableAfterCell = false;
322  else
323  {
324  aParagraph->append(SAL_NEWLINE_STRING);
325  // RTF_PAR at the end of the footnote or clipboard, would cause an additional empty paragraph.
326  if (!bLastPara)
327  {
328  aParagraph->append(OOO_STRING_SVTOOLS_RTF_PAR);
329  aParagraph->append(' ');
330  }
331  }
332  if (m_nColBreakNeeded)
333  {
335  m_nColBreakNeeded = false;
336  }
337 
338  if (!m_bBufferSectionHeaders)
339  aParagraph.makeStringAndClear(this);
340  else
341  m_aSectionHeaders.append(aParagraph.makeStringAndClear());
342 }
343 
345 {
346  m_rExport.Strm()
347  .WriteCharPtr(SAL_NEWLINE_STRING)
348  .WriteCharPtr(OOO_STRING_SVTOOLS_RTF_PAR)
349  .WriteChar(' ');
350 }
351 
353 {
354  SwNodeIndex aNextIndex(rNode, 1);
355  if (rNode.IsTextNode())
356  {
357  OSL_ENSURE(m_aStyles.getLength() == 0, "m_aStyles is not empty");
358 
359  // output page/section breaks
360  m_rExport.Strm().WriteCharPtr(m_aSectionBreaks.makeStringAndClear().getStr());
361  m_bBufferSectionBreaks = true;
362 
363  // output section headers / footers
364  if (!m_bBufferSectionHeaders)
365  m_rExport.Strm().WriteCharPtr(m_aSectionHeaders.makeStringAndClear().getStr());
366 
367  if (aNextIndex.GetNode().IsTextNode())
368  {
369  const SwTextNode* pTextNode = static_cast<SwTextNode*>(&aNextIndex.GetNode());
370  m_rExport.OutputSectionBreaks(pTextNode->GetpSwAttrSet(), *pTextNode);
371  // Save the current page description for now, so later we will be able to access the previous one.
372  m_pPrevPageDesc = pTextNode->FindPageDesc();
373  }
374  else if (aNextIndex.GetNode().IsTableNode())
375  {
376  const SwTableNode* pTableNode = static_cast<SwTableNode*>(&aNextIndex.GetNode());
377  const SwFrameFormat* pFormat = pTableNode->GetTable().GetFrameFormat();
378  m_rExport.OutputSectionBreaks(&(pFormat->GetAttrSet()), *pTableNode);
379  }
380  m_bBufferSectionBreaks = false;
381  }
382  else if (rNode.IsEndNode())
383  {
384  // End of something: make sure that it's the end of a table.
385  assert(rNode.StartOfSectionNode()->IsTableNode());
386  if (aNextIndex.GetNode().IsTextNode())
387  {
388  // Handle section break between a table and a text node following it.
389  const SwTextNode* pTextNode = aNextIndex.GetNode().GetTextNode();
390  m_rExport.OutputSectionBreaks(pTextNode->GetpSwAttrSet(), *pTextNode);
391  }
392  }
393 }
394 
396 {
397  OStringBuffer aPar;
398  if (!m_rExport.GetRTFFlySyntax())
399  {
400  aPar.append(OOO_STRING_SVTOOLS_RTF_PARD);
401  aPar.append(OOO_STRING_SVTOOLS_RTF_PLAIN);
402  aPar.append(' ');
403  }
404  if (!m_bBufferSectionHeaders)
405  m_rExport.Strm().WriteCharPtr(aPar.makeStringAndClear().getStr());
406  else
407  m_aSectionHeaders.append(aPar.makeStringAndClear());
408 }
409 
411  const SfxItemSet& /*rParagraphMarkerProperties*/, const SwRedlineData* /*pRedlineData*/,
412  const SwRedlineData* /*pRedlineParagraphMarkerDeleted*/,
413  const SwRedlineData* /*pRedlineParagraphMarkerInserted*/)
414 {
415  m_aStyles.append(m_aStylesEnd.makeStringAndClear());
416  m_rExport.Strm().WriteCharPtr(m_aStyles.makeStringAndClear().getStr());
417 }
418 
419 void RtfAttributeOutput::StartRun(const SwRedlineData* pRedlineData, sal_Int32 /*nPos*/,
420  bool bSingleEmptyRun)
421 {
422  SAL_INFO("sw.rtf", OSL_THIS_FUNC << ", bSingleEmptyRun: " << bSingleEmptyRun);
423 
424  m_bInRun = true;
425  m_bSingleEmptyRun = bSingleEmptyRun;
426  if (!m_bSingleEmptyRun)
427  m_aRun->append('{');
428 
429  // if there is some redlining in the document, output it
430  Redline(pRedlineData);
431 
432  OSL_ENSURE(m_aRunText.getLength() == 0, "m_aRunText is not empty");
433 }
434 
435 void RtfAttributeOutput::EndRun(const SwTextNode* /*pNode*/, sal_Int32 /*nPos*/, bool /*bLastRun*/)
436 {
437  m_aRun->append(SAL_NEWLINE_STRING);
438  m_aRun.appendAndClear(m_aRunText);
439  if (!m_bSingleEmptyRun && m_bInRun)
440  m_aRun->append('}');
441  m_bInRun = false;
442 }
443 
445 {
446  OSL_ENSURE(m_aStyles.getLength() == 0, "m_aStyles is not empty");
447 }
448 
450 {
451  m_aStyles.append(m_aStylesEnd.makeStringAndClear());
452  m_aRun->append(m_aStyles.makeStringAndClear());
453 }
454 
455 void RtfAttributeOutput::RunText(const OUString& rText, rtl_TextEncoding /*eCharSet*/)
456 {
457  SAL_INFO("sw.rtf", OSL_THIS_FUNC << ", rText: " << rText);
458  RawText(rText, m_rExport.GetCurrentEncoding());
459 }
460 
461 OStringBuffer& RtfAttributeOutput::RunText() { return m_aRunText.getLastBuffer(); }
462 
463 OStringBuffer& RtfAttributeOutput::StylesEnd() { return m_aStylesEnd; }
464 
465 void RtfAttributeOutput::RawText(const OUString& rText, rtl_TextEncoding eCharSet)
466 {
467  m_aRunText->append(msfilter::rtfutil::OutString(rText, eCharSet));
468 }
469 
470 void RtfAttributeOutput::StartRuby(const SwTextNode& rNode, sal_Int32 nPos,
471  const SwFormatRuby& rRuby)
472 {
473  WW8Ruby aWW8Ruby(rNode, rRuby, GetExport());
474  OUString aStr(FieldString(ww::eEQ));
475  aStr += "\\* jc";
476  aStr += OUString::number(aWW8Ruby.GetJC());
477 
478  aStr += " \\* \"Font:";
479  aStr += aWW8Ruby.GetFontFamily();
480  aStr += "\" \\* hps";
481  aStr += OUString::number((aWW8Ruby.GetRubyHeight() + 5) / 10);
482  aStr += " \\o";
483  if (aWW8Ruby.GetDirective())
484  {
485  aStr += "\\a" + OUString(aWW8Ruby.GetDirective());
486  }
487  aStr += "(\\s\\up ";
488 
489  aStr += OUString::number((aWW8Ruby.GetBaseHeight() + 10) / 20 - 1);
490  aStr += "(";
491  EndRun(&rNode, nPos);
492  m_rExport.OutputField(nullptr, ww::eEQ, aStr, FieldFlags::Start | FieldFlags::CmdStart);
493  aStr = rRuby.GetText();
494  aStr += ")";
495  aStr += ",";
496  m_rExport.OutputField(nullptr, ww::eEQ, aStr, FieldFlags::NONE);
497 }
498 
499 void RtfAttributeOutput::EndRuby(const SwTextNode& rNode, sal_Int32 nPos)
500 {
501  m_rExport.OutputField(nullptr, ww::eEQ, ")", FieldFlags::End | FieldFlags::Close);
502  EndRun(&rNode, nPos);
503 }
504 
505 bool RtfAttributeOutput::StartURL(const OUString& rUrl, const OUString& rTarget)
506 {
507  m_sURL = rUrl;
508  // Ignore hyperlink without a URL.
509  if (!rUrl.isEmpty())
510  {
511  m_aRun->append('{');
512  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FIELD);
513  m_aRun->append('{');
514  m_aRun->append(OOO_STRING_SVTOOLS_RTF_IGNORE);
515  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FLDINST);
516  m_aRun->append(" HYPERLINK ");
517 
518  m_aRun->append("\"");
519  m_aRun->append(msfilter::rtfutil::OutString(rUrl, m_rExport.GetCurrentEncoding()));
520  m_aRun->append("\" ");
521 
522  if (!rTarget.isEmpty())
523  {
524  m_aRun->append("\\\\t \"");
525  m_aRun->append(msfilter::rtfutil::OutString(rTarget, m_rExport.GetCurrentEncoding()));
526  m_aRun->append("\" ");
527  }
528 
529  m_aRun->append("}");
530  m_aRun->append("{" OOO_STRING_SVTOOLS_RTF_FLDRSLT " {");
531  }
532  return true;
533 }
534 
535 bool RtfAttributeOutput::EndURL(bool const isAtEndOfParagraph)
536 {
537  if (!m_sURL.isEmpty())
538  {
539  // UGLY: usually EndRun is called earlier, but there is an extra
540  // call to OutAttrWithRange() when at the end of the paragraph,
541  // so in that special case the output needs to be appended to the
542  // new run's text instead of the previous run
543  if (isAtEndOfParagraph)
544  {
545  // close the fldrslt group
546  m_aRunText->append("}}");
547  // close the field group
548  m_aRunText->append('}');
549  }
550  else
551  {
552  // close the fldrslt group
553  m_aRun->append("}}");
554  // close the field group
555  m_aRun->append('}');
556  }
557  m_sURL.clear();
558  }
559  return true;
560 }
561 
562 void RtfAttributeOutput::FieldVanish(const OUString& /*rText*/, ww::eField /*eType*/)
563 {
564  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
565 }
566 
568 {
569  if (!pRedline)
570  return;
571 
572  if (pRedline->GetType() == nsRedlineType_t::REDLINE_INSERT)
573  {
574  m_aRun->append(OOO_STRING_SVTOOLS_RTF_REVISED);
575  m_aRun->append(OOO_STRING_SVTOOLS_RTF_REVAUTH);
576  m_aRun->append(static_cast<sal_Int32>(
577  m_rExport.GetRedline(SW_MOD()->GetRedlineAuthor(pRedline->GetAuthor()))));
578  m_aRun->append(OOO_STRING_SVTOOLS_RTF_REVDTTM);
579  }
580  else if (pRedline->GetType() == nsRedlineType_t::REDLINE_DELETE)
581  {
582  m_aRun->append(OOO_STRING_SVTOOLS_RTF_DELETED);
583  m_aRun->append(OOO_STRING_SVTOOLS_RTF_REVAUTHDEL);
584  m_aRun->append(static_cast<sal_Int32>(
585  m_rExport.GetRedline(SW_MOD()->GetRedlineAuthor(pRedline->GetAuthor()))));
586  m_aRun->append(OOO_STRING_SVTOOLS_RTF_REVDTTMDEL);
587  }
588  m_aRun->append(static_cast<sal_Int32>(sw::ms::DateTime2DTTM(pRedline->GetTimeStamp())));
589  m_aRun->append(' ');
590 }
591 
593  const SwFormatDrop& /*rSwFormatDrop*/, sal_uInt16 /*nStyle*/,
594  ww8::WW8TableNodeInfo::Pointer_t /*pTextNodeInfo*/,
595  ww8::WW8TableNodeInfoInner::Pointer_t /*pTextNodeInfoInner*/)
596 {
597  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
598 }
599 
600 void RtfAttributeOutput::ParagraphStyle(sal_uInt16 nStyle)
601 {
602  OString* pStyle = m_rExport.GetStyle(nStyle);
603  OStringBuffer aStyle;
604  aStyle.append(OOO_STRING_SVTOOLS_RTF_S);
605  aStyle.append(static_cast<sal_Int32>(nStyle));
606  if (pStyle)
607  aStyle.append(pStyle->getStr());
608  if (!m_bBufferSectionHeaders)
609  m_rExport.Strm().WriteCharPtr(aStyle.makeStringAndClear().getStr());
610  else
611  m_aSectionHeaders.append(aStyle.makeStringAndClear());
612 }
613 
615  ww8::WW8TableNodeInfoInner::Pointer_t /*pTableTextNodeInfoInner*/)
616 {
617  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_INTBL);
618  if (m_nTableDepth > 1)
619  {
620  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ITAP);
621  m_aStyles.append(static_cast<sal_Int32>(m_nTableDepth));
622  }
623  m_bWroteCellInfo = true;
624 }
625 
627 {
628  /* noop */
629 }
630 
632  ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner)
633 {
634  InitTableHelper(pTableTextNodeInfoInner);
635 
636  const SwTable* pTable = pTableTextNodeInfoInner->getTable();
637  SwFrameFormat* pFormat = pTable->GetFrameFormat();
638 
639  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_TROWD);
640  TableOrientation(pTableTextNodeInfoInner);
641  TableBidi(pTableTextNodeInfoInner);
642  TableHeight(pTableTextNodeInfoInner);
643  TableCanSplit(pTableTextNodeInfoInner);
644 
645  // Cell margins
646  const SvxBoxItem& rBox = pFormat->GetBox();
647  static const SvxBoxItemLine aBorders[] = { SvxBoxItemLine::TOP, SvxBoxItemLine::LEFT,
648  SvxBoxItemLine::BOTTOM, SvxBoxItemLine::RIGHT };
649 
650  static const char* aRowPadNames[]
653 
654  static const char* aRowPadUnits[]
657 
658  for (int i = 0; i < 4; ++i)
659  {
660  m_aRowDefs.append(aRowPadUnits[i]);
661  m_aRowDefs.append(sal_Int32(3));
662  m_aRowDefs.append(aRowPadNames[i]);
663  m_aRowDefs.append(static_cast<sal_Int32>(rBox.GetDistance(aBorders[i])));
664  }
665 
666  // The cell-dependent properties
667  const double fWidthRatio = m_pTableWrt->GetAbsWidthRatio();
668  const SwWriteTableRows& aRows = m_pTableWrt->GetRows();
669  SwWriteTableRow* pRow = aRows[pTableTextNodeInfoInner->getRow()].get();
670  SwTwips nSz = 0;
671 
672  // Not using m_nTableDepth, which is not yet incremented here.
673  sal_uInt32 nCurrentDepth = pTableTextNodeInfoInner->getDepth();
674  m_aCells[nCurrentDepth] = pRow->GetCells().size();
675  for (sal_uInt32 i = 0; i < m_aCells[nCurrentDepth]; i++)
676  {
677  const SwWriteTableCell* const pCell = pRow->GetCells()[i].get();
678  const SwFrameFormat* pCellFormat = pCell->GetBox()->GetFrameFormat();
679 
680  pTableTextNodeInfoInner->setCell(i);
681  TableCellProperties(pTableTextNodeInfoInner);
682 
683  // Right boundary: this can't be in TableCellProperties as the old
684  // value of nSz is needed.
685  nSz += pCellFormat->GetFrameSize().GetWidth();
686  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_CELLX);
687  m_aRowDefs.append(static_cast<sal_Int32>(pFormat->GetLRSpace().GetLeft()
688  + rtl::math::round(nSz * fWidthRatio)));
689  }
690 }
691 
693  ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner)
694 {
695  /*
696  * The function name is a bit misleading: given that we write borders
697  * before each row, we just have borders, not default ones. Additionally,
698  * this function actually writes borders for a specific cell only and is
699  * called for each cell.
700  */
701 
702  const SwWriteTableRows& aRows = m_pTableWrt->GetRows();
703  SwWriteTableRow* pRow = aRows[pTableTextNodeInfoInner->getRow()].get();
704  const SwWriteTableCell* const pCell
705  = pRow->GetCells()[pTableTextNodeInfoInner->getCell()].get();
706  const SwFrameFormat* pCellFormat = pCell->GetBox()->GetFrameFormat();
707  const SfxPoolItem* pItem;
708  if (pCellFormat->GetAttrSet().HasItem(RES_BOX, &pItem))
709  {
710  auto& rBox = static_cast<const SvxBoxItem&>(*pItem);
711  static const SvxBoxItemLine aBorders[] = { SvxBoxItemLine::TOP, SvxBoxItemLine::LEFT,
712  SvxBoxItemLine::BOTTOM, SvxBoxItemLine::RIGHT };
713  static const char* aBorderNames[]
716  //Yes left and top are swapped with each other for cell padding! Because
717  //that's what the thundering annoying rtf export/import word xp does.
718  static const char* aCellPadNames[]
721  static const char* aCellPadUnits[]
724  for (int i = 0; i < 4; ++i)
725  {
726  if (const editeng::SvxBorderLine* pLn = rBox.GetLine(aBorders[i]))
727  m_aRowDefs.append(OutTBLBorderLine(m_rExport, pLn, aBorderNames[i]));
728  if (rBox.GetDistance(aBorders[i]))
729  {
730  m_aRowDefs.append(aCellPadUnits[i]);
731  m_aRowDefs.append(sal_Int32(3));
732  m_aRowDefs.append(aCellPadNames[i]);
733  m_aRowDefs.append(static_cast<sal_Int32>(rBox.GetDistance(aBorders[i])));
734  }
735  }
736  }
737 }
738 
740  ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner)
741 {
742  const SwTable* pTable = pTableTextNodeInfoInner->getTable();
743  const SwTableBox* pTableBox = pTableTextNodeInfoInner->getTableBox();
744  const SwTableLine* pTableLine = pTableBox->GetUpper();
745 
746  Color aColor = COL_AUTO;
747  auto pTableColorProp
749  if (pTableColorProp)
750  aColor = pTableColorProp->GetColor();
751 
752  auto pRowColorProp
754  if (pRowColorProp && pRowColorProp->GetColor() != COL_AUTO)
755  aColor = pRowColorProp->GetColor();
756 
757  const SwWriteTableRows& aRows = m_pTableWrt->GetRows();
758  SwWriteTableRow* pRow = aRows[pTableTextNodeInfoInner->getRow()].get();
759  const SwWriteTableCell* const pCell
760  = pRow->GetCells()[pTableTextNodeInfoInner->getCell()].get();
761  const SwFrameFormat* pCellFormat = pCell->GetBox()->GetFrameFormat();
762  const SfxPoolItem* pItem;
763  if (pCellFormat->GetAttrSet().HasItem(RES_BACKGROUND, &pItem))
764  {
765  auto& rBack = static_cast<const SvxBrushItem&>(*pItem);
766  if (rBack.GetColor() != COL_AUTO)
767  aColor = rBack.GetColor();
768  }
769 
770  if (!aColor.GetTransparency())
771  {
772  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_CLCBPAT);
773  m_aRowDefs.append(static_cast<sal_Int32>(m_rExport.GetColor(aColor)));
774  }
775 }
776 
778  ww8::WW8TableNodeInfoInner::Pointer_t /*pTableTextNodeInfoInner*/)
779 {
780 }
781 
783  ww8::WW8TableNodeInfoInner::Pointer_t /*pTableTextNodeInfoInner*/)
784 {
785 }
786 
788 {
789  const SwTableBox* pTabBox = pTableTextNodeInfoInner->getTableBox();
790  const SwTableLine* pTabLine = pTabBox->GetUpper();
791  const SwFrameFormat* pLineFormat = pTabLine->GetFrameFormat();
792  const SwFormatFrameSize& rLSz = pLineFormat->GetFrameSize();
793 
794  if (ATT_VAR_SIZE != rLSz.GetHeightSizeType() && rLSz.GetHeight())
795  {
796  sal_Int32 nHeight = 0;
797 
798  switch (rLSz.GetHeightSizeType())
799  {
800  case ATT_FIX_SIZE:
801  nHeight = -rLSz.GetHeight();
802  break;
803  case ATT_MIN_SIZE:
804  nHeight = rLSz.GetHeight();
805  break;
806  default:
807  break;
808  }
809 
810  if (nHeight)
811  {
812  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_TRRH);
813  m_aRowDefs.append(nHeight);
814  }
815  }
816 }
817 
819  ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner)
820 {
821  const SwTableBox* pTabBox = pTableTextNodeInfoInner->getTableBox();
822  const SwTableLine* pTabLine = pTabBox->GetUpper();
823  const SwFrameFormat* pLineFormat = pTabLine->GetFrameFormat();
824  const SwFormatRowSplit& rSplittable = pLineFormat->GetRowSplit();
825 
826  // The rtf default is to allow a row to break
827  if (!rSplittable.GetValue())
828  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_TRKEEP);
829 }
830 
832 {
833  const SwTable* pTable = pTableTextNodeInfoInner->getTable();
834  const SwFrameFormat* pFrameFormat = pTable->GetFrameFormat();
835 
836  if (m_rExport.TrueFrameDirection(*pFrameFormat) != SvxFrameDirection::Horizontal_RL_TB)
837  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_LTRROW);
838  else
839  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_RTLROW);
840 }
841 
843  ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner)
844 {
845  const SwWriteTableRows& aRows = m_pTableWrt->GetRows();
846  SwWriteTableRow* pRow = aRows[pTableTextNodeInfoInner->getRow()].get();
847  const SwWriteTableCell* const pCell
848  = pRow->GetCells()[pTableTextNodeInfoInner->getCell()].get();
849  const SwFrameFormat* pCellFormat = pCell->GetBox()->GetFrameFormat();
850 
851  // Text direction.
852  if (SvxFrameDirection::Vertical_RL_TB == m_rExport.TrueFrameDirection(*pCellFormat))
853  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_CLTXTBRL);
854  else if (SvxFrameDirection::Vertical_LR_BT == m_rExport.TrueFrameDirection(*pCellFormat))
855  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_CLTXBTLR);
856 
857  const SfxPoolItem* pItem;
858 
859  // vertical merges
860  if (pCell->GetRowSpan() > 1)
861  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_CLVMGF);
862  else if (pCell->GetRowSpan() == 0)
863  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_CLVMRG);
864 
865  // vertical alignment
866  if (pCellFormat->GetAttrSet().HasItem(RES_VERT_ORIENT, &pItem))
867  switch (static_cast<const SwFormatVertOrient*>(pItem)->GetVertOrient())
868  {
869  case text::VertOrientation::CENTER:
870  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_CLVERTALC);
871  break;
873  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_CLVERTALB);
874  break;
875  default:
876  m_aRowDefs.append(OOO_STRING_SVTOOLS_RTF_CLVERTALT);
877  break;
878  }
879 }
880 
882 {
883  // This is called when the nested table ends in a cell, and there's no
884  // paragraph behind that; so we must check for the ends of cell, rows,
885  // and tables
886  FinishTableRowCell(pNodeInfoInner);
887 }
888 
890  ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner)
891 {
892  const SwTable* pTable = pTableTextNodeInfoInner->getTable();
893  SwFrameFormat* pFormat = pTable->GetFrameFormat();
894 
895  OStringBuffer aTableAdjust(OOO_STRING_SVTOOLS_RTF_TRQL);
896  switch (pFormat->GetHoriOrient().GetHoriOrient())
897  {
898  case text::HoriOrientation::CENTER:
899  aTableAdjust.setLength(0);
900  aTableAdjust.append(OOO_STRING_SVTOOLS_RTF_TRQC);
901  break;
903  aTableAdjust.setLength(0);
904  aTableAdjust.append(OOO_STRING_SVTOOLS_RTF_TRQR);
905  break;
907  case text::HoriOrientation::LEFT_AND_WIDTH:
908  aTableAdjust.append(OOO_STRING_SVTOOLS_RTF_TRLEFT);
909  aTableAdjust.append(static_cast<sal_Int32>(pFormat->GetLRSpace().GetLeft()));
910  break;
911  default:
912  break;
913  }
914 
915  m_aRowDefs.append(aTableAdjust.makeStringAndClear());
916 }
917 
919  ww8::WW8TableNodeInfoInner::Pointer_t /*pTableTextNodeInfoInner*/)
920 {
921  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
922 }
923 
924 void RtfAttributeOutput::TableRowEnd(sal_uInt32 /*nDepth*/) { /* noop, see EndTableRow() */}
925 
926 /*
927  * Our private table methods.
928  */
929 
931  const ww8::WW8TableNodeInfoInner::Pointer_t& pTableTextNodeInfoInner)
932 {
933  const SwTable* pTable = pTableTextNodeInfoInner->getTable();
934  if (m_pTableWrt && pTable == m_pTableWrt->GetTable())
935  return;
936 
937  long nPageSize = 0;
938  bool bRelBoxSize = false;
939 
940  // Create the SwWriteTable instance to use col spans
941  GetTablePageSize(pTableTextNodeInfoInner.get(), nPageSize, bRelBoxSize);
942 
943  const SwFrameFormat* pFormat = pTable->GetFrameFormat();
944  const sal_uInt32 nTableSz = pFormat->GetFrameSize().GetWidth();
945 
946  const SwHTMLTableLayout* pLayout = pTable->GetHTMLTableLayout();
947  if (pLayout && pLayout->IsExportable())
948  m_pTableWrt = std::make_unique<SwWriteTable>(pTable, pLayout);
949  else
950  m_pTableWrt = std::make_unique<SwWriteTable>(pTable, pTable->GetTabLines(), nPageSize,
951  nTableSz, false);
952 }
953 
955 {
956  // To trigger calling InitTableHelper()
957  m_pTableWrt.reset();
958 }
959 
961  const ww8::WW8TableNodeInfoInner::Pointer_t& pTableTextNodeInfoInner)
962 {
963  sal_uInt32 nCurrentDepth = pTableTextNodeInfoInner->getDepth();
964  SAL_INFO("sw.rtf", OSL_THIS_FUNC << ", (depth is " << nCurrentDepth << ")");
965  m_bTableRowEnded = false;
966 
967  TableDefinition(pTableTextNodeInfoInner);
968 
969  if (!m_bLastTable)
970  m_aTables.push_back(m_aRowDefs.makeStringAndClear());
971 
972  // We'll write the table definition for nested tables later
973  if (nCurrentDepth > 1)
974  return;
975  // Empty the previous row closing buffer before starting the new one,
976  // necessary for subtables.
977  m_rExport.Strm().WriteCharPtr(m_aAfterRuns.makeStringAndClear().getStr());
978  m_rExport.Strm().WriteCharPtr(m_aRowDefs.makeStringAndClear().getStr());
979 }
980 
981 void RtfAttributeOutput::StartTableCell() { m_bTableCellOpen = true; }
982 
984  const ww8::WW8TableNodeInfoInner::Pointer_t& pTableTextNodeInfoInner)
985 {
986  TableDefaultBorders(pTableTextNodeInfoInner);
987  TableBackgrounds(pTableTextNodeInfoInner);
988  TableVerticalCell(pTableTextNodeInfoInner);
989 }
990 
992 {
993  SAL_INFO("sw.rtf", OSL_THIS_FUNC << ", (depth is " << m_nTableDepth << ")");
994 
995  if (!m_bWroteCellInfo)
996  {
997  m_aAfterRuns.append(OOO_STRING_SVTOOLS_RTF_INTBL);
998  m_aAfterRuns.append(OOO_STRING_SVTOOLS_RTF_ITAP);
999  m_aAfterRuns.append(static_cast<sal_Int32>(m_nTableDepth));
1000  }
1001  if (m_nTableDepth > 1)
1002  m_aAfterRuns.append(OOO_STRING_SVTOOLS_RTF_NESTCELL);
1003  else
1004  m_aAfterRuns.append(OOO_STRING_SVTOOLS_RTF_CELL);
1005 
1006  m_bTableCellOpen = false;
1007  m_bTableAfterCell = true;
1008  m_bWroteCellInfo = false;
1009  if (m_aCells[m_nTableDepth] > 0)
1010  m_aCells[m_nTableDepth]--;
1011 }
1012 
1014 {
1015  SAL_INFO("sw.rtf", OSL_THIS_FUNC << ", (depth is " << m_nTableDepth << ")");
1016 
1017  // Trying to end the row without writing the required number of cells? Fill with empty ones.
1018  for (sal_uInt32 i = 0; i < m_aCells[m_nTableDepth]; i++)
1019  m_aAfterRuns.append(OOO_STRING_SVTOOLS_RTF_CELL);
1020 
1021  if (m_nTableDepth > 1)
1022  {
1023  m_aAfterRuns.append(
1025  if (!m_aRowDefs.isEmpty())
1026  m_aAfterRuns.append(m_aRowDefs.makeStringAndClear());
1027  else if (!m_aTables.empty())
1028  {
1029  m_aAfterRuns.append(m_aTables.back());
1030  m_aTables.pop_back();
1031  }
1032  m_aAfterRuns.append(OOO_STRING_SVTOOLS_RTF_NESTROW
1033  "}"
1035  }
1036  else
1037  {
1038  if (!m_aTables.empty())
1039  {
1040  m_aAfterRuns.append(m_aTables.back());
1041  m_aTables.pop_back();
1042  }
1043  m_aAfterRuns.append(OOO_STRING_SVTOOLS_RTF_ROW).append(OOO_STRING_SVTOOLS_RTF_PARD);
1044  }
1045  m_bTableRowEnded = true;
1046 }
1047 
1049 {
1050  if (m_nTableDepth > 0)
1051  {
1052  m_nTableDepth--;
1053  m_pTableWrt.reset();
1054  }
1055 
1056  // We closed the table; if it is a nested table, the cell that contains it
1057  // still continues
1058  m_bTableCellOpen = true;
1059 
1060  // Cleans the table helper
1061  m_pTableWrt.reset();
1062 }
1063 
1065 {
1066  if (pInner)
1067  {
1068  // Where are we in the table
1069  sal_uInt32 nRow = pInner->getRow();
1070 
1071  const SwTable* pTable = pInner->getTable();
1072  const SwTableLines& rLines = pTable->GetTabLines();
1073  sal_uInt16 nLinesCount = rLines.size();
1074 
1075  if (pInner->isEndOfCell())
1076  EndTableCell();
1077 
1078  // This is a line end
1079  if (pInner->isEndOfLine())
1080  EndTableRow();
1081 
1082  // This is the end of the table
1083  if (pInner->isEndOfLine() && (nRow + 1) == nLinesCount)
1084  EndTable();
1085  }
1086 }
1087 
1089 {
1090  m_rExport.Strm()
1091  .WriteCharPtr(SAL_NEWLINE_STRING)
1092  .WriteChar('{')
1093  .WriteCharPtr(OOO_STRING_SVTOOLS_RTF_COLORTBL);
1094  m_rExport.OutColorTable();
1095  OSL_ENSURE(m_aStylesheet.getLength() == 0, "m_aStylesheet is not empty");
1096  m_aStylesheet.append(SAL_NEWLINE_STRING);
1097  m_aStylesheet.append('{');
1098  m_aStylesheet.append(OOO_STRING_SVTOOLS_RTF_STYLESHEET);
1099 }
1100 
1101 void RtfAttributeOutput::EndStyles(sal_uInt16 /*nNumberOfStyles*/)
1102 {
1103  m_rExport.Strm().WriteChar('}');
1104  m_rExport.Strm().WriteCharPtr(m_aStylesheet.makeStringAndClear().getStr());
1105  m_rExport.Strm().WriteChar('}');
1106 }
1107 
1108 void RtfAttributeOutput::DefaultStyle() { /* noop, the default style is always 0 in RTF */}
1109 
1110 void RtfAttributeOutput::StartStyle(const OUString& rName, StyleType eType, sal_uInt16 nBase,
1111  sal_uInt16 nNext, sal_uInt16 /*nWwId*/, sal_uInt16 nId,
1112  bool bAutoUpdate)
1113 {
1114  SAL_INFO("sw.rtf", OSL_THIS_FUNC << ", rName = '" << rName << "'");
1115 
1116  m_aStylesheet.append('{');
1117  if (eType == STYLE_TYPE_PARA)
1118  m_aStylesheet.append(OOO_STRING_SVTOOLS_RTF_S);
1119  else
1121  m_aStylesheet.append(static_cast<sal_Int32>(nId));
1122 
1123  if (nBase != 0x0FFF)
1124  {
1125  m_aStylesheet.append(OOO_STRING_SVTOOLS_RTF_SBASEDON);
1126  m_aStylesheet.append(static_cast<sal_Int32>(nBase));
1127  }
1128 
1129  m_aStylesheet.append(OOO_STRING_SVTOOLS_RTF_SNEXT);
1130  m_aStylesheet.append(static_cast<sal_Int32>(nNext));
1131 
1132  if (bAutoUpdate)
1133  m_aStylesheet.append(OOO_STRING_SVTOOLS_RTF_SAUTOUPD);
1134 
1135  m_rStyleName = rName;
1136  m_nStyleId = nId;
1137 }
1138 
1140 {
1141  m_aStyles.append(m_aStylesEnd.makeStringAndClear());
1142  OString aStyles = m_aStyles.makeStringAndClear();
1143  m_rExport.InsStyle(m_nStyleId, aStyles);
1144  m_aStylesheet.append(aStyles);
1145  m_aStylesheet.append(' ');
1146  m_aStylesheet.append(
1147  msfilter::rtfutil::OutString(m_rStyleName, m_rExport.GetCurrentEncoding()));
1148  m_aStylesheet.append(";}");
1149  m_aStylesheet.append(SAL_NEWLINE_STRING);
1150 }
1151 
1152 void RtfAttributeOutput::StartStyleProperties(bool /*bParProp*/, sal_uInt16 /*nStyle*/)
1153 {
1154  /* noop */
1155 }
1156 
1157 void RtfAttributeOutput::EndStyleProperties(bool /*bParProp*/) { /* noop */}
1158 
1160 {
1161  if (nLvl >= WW8ListManager::nMaxLevel)
1162  nLvl = WW8ListManager::nMaxLevel - 1;
1163 
1164  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ILVL);
1165  m_aStyles.append(static_cast<sal_Int32>(nLvl));
1166  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_OUTLINELEVEL);
1167  m_aStyles.append(static_cast<sal_Int32>(nLvl));
1168 }
1169 
1171 {
1172  if (bBreak)
1173  {
1174  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_PAGEBB);
1175  }
1176 }
1177 
1179 {
1180  switch (nC)
1181  {
1182  case msword::ColumnBreak:
1183  m_nColBreakNeeded = true;
1184  break;
1185  case msword::PageBreak:
1186  if (pSectionInfo)
1187  m_rExport.SectionProperties(*pSectionInfo);
1188  break;
1189  }
1190 }
1191 
1193 {
1194  if (m_bIsBeforeFirstParagraph)
1195  return;
1196 
1198  if (!m_bBufferSectionBreaks)
1199  m_rExport.Strm().WriteCharPtr(m_aSectionBreaks.makeStringAndClear().getStr());
1200 }
1201 
1203 {
1204  /*
1205  * noop, \sect must go to StartSection or Word won't notice multiple
1206  * columns...
1207  */
1208 }
1209 
1211 {
1212  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_SECTUNLOCKED);
1213  m_aSectionBreaks.append(static_cast<sal_Int32>(!bProtected));
1214 }
1215 
1217  const SwLineNumberInfo& rLnNumInfo)
1218 {
1219  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LINEMOD);
1220  m_rExport.OutLong(rLnNumInfo.GetCountBy());
1221  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LINEX);
1222  m_rExport.OutLong(rLnNumInfo.GetPosFromLeft());
1223  if (!rLnNumInfo.IsRestartEachPage())
1224  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LINECONT);
1225 
1226  if (nRestartNo > 0)
1227  {
1228  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LINESTARTS);
1229  m_rExport.OutLong(nRestartNo);
1230  }
1231 }
1232 
1234 {
1235  /*
1236  * noop, handled in RtfExport::WriteHeaderFooter()
1237  */
1238 }
1239 
1241  const SwFrameFormat* /*pFirstPageFormat*/)
1242 {
1243  const SvxBoxItem& rBox = pFormat->GetBox();
1244  const editeng::SvxBorderLine* pLine = rBox.GetTop();
1245  if (pLine)
1246  m_aSectionBreaks.append(OutBorderLine(m_rExport, pLine, OOO_STRING_SVTOOLS_RTF_PGBRDRT,
1247  rBox.GetDistance(SvxBoxItemLine::TOP)));
1248  pLine = rBox.GetBottom();
1249  if (pLine)
1250  m_aSectionBreaks.append(OutBorderLine(m_rExport, pLine, OOO_STRING_SVTOOLS_RTF_PGBRDRB,
1251  rBox.GetDistance(SvxBoxItemLine::BOTTOM)));
1252  pLine = rBox.GetLeft();
1253  if (pLine)
1254  m_aSectionBreaks.append(OutBorderLine(m_rExport, pLine, OOO_STRING_SVTOOLS_RTF_PGBRDRL,
1255  rBox.GetDistance(SvxBoxItemLine::LEFT)));
1256  pLine = rBox.GetRight();
1257  if (pLine)
1258  m_aSectionBreaks.append(OutBorderLine(m_rExport, pLine, OOO_STRING_SVTOOLS_RTF_PGBRDRR,
1259  rBox.GetDistance(SvxBoxItemLine::RIGHT)));
1260 }
1261 
1263 {
1264  m_rExport.Strm().WriteCharPtr(bBiDi ? OOO_STRING_SVTOOLS_RTF_RTLSECT
1266 }
1267 
1269  sal_uInt16 nNumType, const ::boost::optional<sal_uInt16>& oPageRestartNumber)
1270 {
1271  if (oPageRestartNumber)
1272  {
1273  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_PGNSTARTS);
1274  m_aSectionBreaks.append(static_cast<sal_Int32>(oPageRestartNumber.get()));
1275  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_PGNRESTART);
1276  }
1277 
1278  const char* pStr = nullptr;
1279  switch (nNumType)
1280  {
1284  break;
1288  break;
1289  case SVX_NUM_ROMAN_UPPER:
1291  break;
1292  case SVX_NUM_ROMAN_LOWER:
1294  break;
1295 
1296  case SVX_NUM_ARABIC:
1298  break;
1299  }
1300  if (pStr)
1301  m_aSectionBreaks.append(pStr);
1302 }
1303 
1305 {
1306  SAL_INFO("sw.rtf", OSL_THIS_FUNC << ", nBreakCode = " << int(nBreakCode));
1307 
1308  /*
1309  * break code: 0 No break, 1 New column
1310  * 2 New page, 3 Even page, 4 Odd page
1311  */
1312  const char* sType = nullptr;
1313  switch (nBreakCode)
1314  {
1315  case 1:
1317  break;
1318  case 2:
1320  break;
1321  case 3:
1323  break;
1324  case 4:
1326  break;
1327  default:
1329  break;
1330  }
1331  m_aSectionBreaks.append(sType);
1332  if (!m_bBufferSectionBreaks)
1333  m_rExport.Strm().WriteCharPtr(m_aSectionBreaks.makeStringAndClear().getStr());
1334 }
1335 
1336 void RtfAttributeOutput::NumberingDefinition(sal_uInt16 nId, const SwNumRule& /*rRule*/)
1337 {
1338  m_rExport.Strm().WriteChar('{').WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LISTOVERRIDE);
1339  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LISTID);
1340  m_rExport.OutULong(nId);
1341  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LISTOVERRIDECOUNT).WriteChar('0');
1342  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LS);
1343  m_rExport.OutULong(nId).WriteChar('}');
1344 }
1345 
1347 {
1348  m_rExport.Strm()
1349  .WriteChar('{')
1350  .WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LIST)
1352  m_rExport.OutULong(nId);
1353  m_nListId = nId;
1354 }
1355 
1357 {
1358  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LISTID);
1359  m_rExport.OutULong(m_nListId).WriteChar('}').WriteCharPtr(SAL_NEWLINE_STRING);
1360 }
1361 
1362 void RtfAttributeOutput::NumberingLevel(sal_uInt8 nLevel, sal_uInt16 nStart,
1363  sal_uInt16 nNumberingType, SvxAdjust eAdjust,
1364  const sal_uInt8* pNumLvlPos, sal_uInt8 nFollow,
1365  const wwFont* pFont, const SfxItemSet* pOutSet,
1366  sal_Int16 nIndentAt, sal_Int16 nFirstLineIndex,
1367  sal_Int16 /*nListTabPos*/, const OUString& rNumberingString,
1368  const SvxBrushItem* pBrush)
1369 {
1370  m_rExport.Strm().WriteCharPtr(SAL_NEWLINE_STRING);
1371  if (nLevel > 8) // RTF knows only 9 levels
1372  m_rExport.Strm()
1373  .WriteCharPtr(OOO_STRING_SVTOOLS_RTF_IGNORE)
1374  .WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SOUTLVL);
1375 
1376  m_rExport.Strm().WriteChar('{').WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LISTLEVEL);
1377 
1378  sal_uInt16 nVal = 0;
1379  switch (nNumberingType)
1380  {
1381  case SVX_NUM_ROMAN_UPPER:
1382  nVal = 1;
1383  break;
1384  case SVX_NUM_ROMAN_LOWER:
1385  nVal = 2;
1386  break;
1389  nVal = 3;
1390  break;
1393  nVal = 4;
1394  break;
1396  nVal = 14;
1397  break;
1398  case SVX_NUM_CIRCLE_NUMBER:
1399  nVal = 18;
1400  break;
1402  nVal = 35;
1403  if (pOutSet)
1404  {
1405  const SvxLanguageItem& rLang = pOutSet->Get(RES_CHRATR_CJK_LANGUAGE);
1407  {
1408  nVal = 39;
1409  }
1410  }
1411  break;
1413  nVal = 38;
1414  break;
1416  nVal = 34;
1417  break;
1418  case SVX_NUM_TIAN_GAN_ZH:
1419  nVal = 30;
1420  break;
1421  case SVX_NUM_DI_ZI_ZH:
1422  nVal = 31;
1423  break;
1425  nVal = 16;
1426  break;
1428  nVal = 20;
1429  break;
1431  nVal = 12;
1432  break;
1434  nVal = 21;
1435  break;
1437  nVal = 13;
1438  break;
1439  case style::NumberingType::HANGUL_SYLLABLE_KO:
1440  nVal = 24;
1441  break; // ganada
1442  case style::NumberingType::HANGUL_JAMO_KO:
1443  nVal = 25;
1444  break; // chosung
1445  case style::NumberingType::HANGUL_CIRCLED_SYLLABLE_KO:
1446  nVal = 24;
1447  break;
1448  case style::NumberingType::HANGUL_CIRCLED_JAMO_KO:
1449  nVal = 25;
1450  break;
1451  case style::NumberingType::NUMBER_HANGUL_KO:
1452  nVal = 41;
1453  break;
1454  case style::NumberingType::NUMBER_UPPER_KO:
1455  nVal = 44;
1456  break;
1457 
1458  case SVX_NUM_BITMAP:
1459  case SVX_NUM_CHAR_SPECIAL:
1460  nVal = 23;
1461  break;
1462  case SVX_NUM_NUMBER_NONE:
1463  nVal = 255;
1464  break;
1465  }
1466  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LEVELNFC);
1467  m_rExport.OutULong(nVal);
1468 
1469  switch (eAdjust)
1470  {
1471  case SvxAdjust::Center:
1472  nVal = 1;
1473  break;
1474  case SvxAdjust::Right:
1475  nVal = 2;
1476  break;
1477  default:
1478  nVal = 0;
1479  break;
1480  }
1481  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LEVELJC);
1482  m_rExport.OutULong(nVal);
1483 
1484  // bullet
1485  if (nNumberingType == SVX_NUM_BITMAP && pBrush)
1486  {
1487  int nIndex = m_rExport.GetGrfIndex(*pBrush);
1488  if (nIndex != -1)
1489  {
1490  m_rExport.Strm().WriteCharPtr(LO_STRING_SVTOOLS_RTF_LEVELPICTURE);
1491  m_rExport.OutULong(nIndex);
1492  }
1493  }
1494 
1495  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LEVELSTARTAT);
1496  m_rExport.OutULong(nStart);
1497 
1498  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LEVELFOLLOW);
1499  m_rExport.OutULong(nFollow);
1500 
1501  // leveltext group
1502  m_rExport.Strm().WriteChar('{').WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LEVELTEXT).WriteChar(' ');
1503 
1504  if (SVX_NUM_CHAR_SPECIAL == nNumberingType || SVX_NUM_BITMAP == nNumberingType)
1505  {
1506  m_rExport.Strm().WriteCharPtr("\\'01");
1507  sal_Unicode cChar = rNumberingString[0];
1508  m_rExport.Strm().WriteCharPtr("\\u");
1509  m_rExport.OutULong(cChar);
1510  m_rExport.Strm().WriteCharPtr(" ?");
1511  }
1512  else
1513  {
1514  m_rExport.Strm().WriteCharPtr("\\'").WriteCharPtr(
1515  msfilter::rtfutil::OutHex(rNumberingString.getLength(), 2).getStr());
1516  m_rExport.Strm().WriteCharPtr(msfilter::rtfutil::OutString(rNumberingString,
1517  m_rExport.GetDefaultEncoding(),
1518  /*bUnicode =*/false)
1519  .getStr());
1520  }
1521 
1522  m_rExport.Strm().WriteCharPtr(";}");
1523 
1524  // write the levelnumbers
1525  m_rExport.Strm().WriteCharPtr("{").WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LEVELNUMBERS);
1526  for (sal_uInt8 i = 0; i <= nLevel && pNumLvlPos[i]; ++i)
1527  {
1528  m_rExport.Strm().WriteCharPtr("\\'").WriteCharPtr(
1529  msfilter::rtfutil::OutHex(pNumLvlPos[i], 2).getStr());
1530  }
1531  m_rExport.Strm().WriteCharPtr(";}");
1532 
1533  if (pOutSet)
1534  {
1535  if (pFont)
1536  {
1537  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_F);
1538  m_rExport.OutULong(m_rExport.m_aFontHelper.GetId(*pFont));
1539  }
1540  m_rExport.OutputItemSet(*pOutSet, false, true, i18n::ScriptType::LATIN,
1541  m_rExport.m_bExportModeRTF);
1542  m_aStyles.append(m_aStylesEnd.makeStringAndClear());
1543  m_rExport.Strm().WriteCharPtr(m_aStyles.makeStringAndClear().getStr());
1544  }
1545 
1546  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_FI);
1547  m_rExport.OutLong(nFirstLineIndex).WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LI);
1548  m_rExport.OutLong(nIndentAt);
1549 
1550  m_rExport.Strm().WriteChar('}');
1551  if (nLevel > 8)
1552  m_rExport.Strm().WriteChar('}');
1553 }
1554 
1556  const OUString& rFieldCmd, FieldFlags nMode)
1557 {
1558  // If there are no field instructions, don't export it as a field.
1559  bool bHasInstructions = !rFieldCmd.isEmpty();
1560  if (FieldFlags::All == nMode)
1561  {
1562  if (bHasInstructions)
1563  {
1564  m_aRunText->append("{" OOO_STRING_SVTOOLS_RTF_FIELD);
1566  " ");
1567  m_aRunText->append(
1568  msfilter::rtfutil::OutString(rFieldCmd, m_rExport.GetCurrentEncoding()));
1569  m_aRunText->append("}{" OOO_STRING_SVTOOLS_RTF_FLDRSLT " ");
1570  }
1571  if (pField)
1572  m_aRunText->append(msfilter::rtfutil::OutString(pField->ExpandField(true, nullptr),
1573  m_rExport.GetDefaultEncoding()));
1574  if (bHasInstructions)
1575  m_aRunText->append("}}");
1576  }
1577  else if (eType == ww::eEQ)
1578  {
1579  if (FieldFlags::Start & nMode)
1580  {
1581  m_aRunText->append("{" OOO_STRING_SVTOOLS_RTF_FIELD);
1583  " ");
1584  }
1585  if (bHasInstructions)
1586  m_aRunText->append(
1587  msfilter::rtfutil::OutString(rFieldCmd, m_rExport.GetCurrentEncoding()));
1588  if (FieldFlags::End & nMode)
1589  {
1590  m_aRunText->append("}{" OOO_STRING_SVTOOLS_RTF_FLDRSLT " ");
1591  m_aRunText->append("}}");
1592  }
1593  }
1594 }
1595 
1596 void RtfAttributeOutput::WriteBookmarks_Impl(std::vector<OUString>& rStarts,
1597  std::vector<OUString>& rEnds)
1598 {
1599  for (const auto& rStart : rStarts)
1600  {
1602  m_aRun->append(msfilter::rtfutil::OutString(rStart, m_rExport.GetCurrentEncoding()));
1603  m_aRun->append('}');
1604  }
1605  rStarts.clear();
1606 
1607  for (const auto& rEnd : rEnds)
1608  {
1610  m_aRun->append(msfilter::rtfutil::OutString(rEnd, m_rExport.GetCurrentEncoding()));
1611  m_aRun->append('}');
1612  }
1613  rEnds.clear();
1614 }
1615 
1616 void RtfAttributeOutput::WriteAnnotationMarks_Impl(std::vector<OUString>& rStarts,
1617  std::vector<OUString>& rEnds)
1618 {
1619  for (const auto& rStart : rStarts)
1620  {
1621  OString rName = OUStringToOString(rStart, RTL_TEXTENCODING_UTF8);
1622 
1623  // Output the annotation mark
1624  const sal_Int32 nId = m_nNextAnnotationMarkId++;
1625  m_rOpenedAnnotationMarksIds[rName] = nId;
1627  m_aRun->append(OString::number(nId).getStr());
1628  m_aRun->append('}');
1629  }
1630  rStarts.clear();
1631 
1632  for (const auto& rEnd : rEnds)
1633  {
1634  OString rName = OUStringToOString(rEnd, RTL_TEXTENCODING_UTF8);
1635 
1636  // Get the id of the annotation mark
1637  auto it = m_rOpenedAnnotationMarksIds.find(rName);
1638  if (it != m_rOpenedAnnotationMarksIds.end())
1639  {
1640  const sal_Int32 nId = it->second;
1642  m_aRun->append(OString::number(nId).getStr());
1643  m_aRun->append('}');
1644  m_rOpenedAnnotationMarksIds.erase(rName);
1645 
1646  if (m_aPostitFields.find(nId) != m_aPostitFields.end())
1647  {
1648  m_aRunText->append("{");
1649  m_nCurrentAnnotationMarkId = nId;
1650  PostitField(m_aPostitFields[nId]);
1651  m_nCurrentAnnotationMarkId = -1;
1652  m_aRunText->append("}");
1653  }
1654  }
1655  }
1656  rEnds.clear();
1657 }
1658 
1660  const sal_Char* pStr, bool bTitlepg)
1661 {
1662  OStringBuffer aSectionBreaks = m_aSectionBreaks;
1663  m_aSectionBreaks.setLength(0);
1664  RtfStringBuffer aRun = m_aRun;
1665  m_aRun.clear();
1666 
1667  m_aSectionHeaders.append(bHeader ? OOO_STRING_SVTOOLS_RTF_HEADERY
1669  m_aSectionHeaders.append(
1670  static_cast<sal_Int32>(m_rExport.m_pCurrentPageDesc->GetMaster().GetULSpace().GetUpper()));
1671  if (bTitlepg)
1672  m_aSectionHeaders.append(OOO_STRING_SVTOOLS_RTF_TITLEPG);
1673  m_aSectionHeaders.append('{');
1674  m_aSectionHeaders.append(pStr);
1675  m_bBufferSectionHeaders = true;
1676  m_rExport.WriteHeaderFooterText(rFormat, bHeader);
1677  m_bBufferSectionHeaders = false;
1678  m_aSectionHeaders.append('}');
1679 
1680  m_aSectionBreaks = aSectionBreaks;
1681  m_aRun = aRun;
1682 }
1683 
1684 namespace
1685 {
1686 void lcl_TextFrameShadow(std::vector<std::pair<OString, OString>>& rFlyProperties,
1687  const SwFrameFormat& rFrameFormat)
1688 {
1689  const SvxShadowItem& aShadowItem = rFrameFormat.GetShadow();
1690  if (aShadowItem.GetLocation() == SvxShadowLocation::NONE)
1691  return;
1692 
1693  rFlyProperties.push_back(std::make_pair<OString, OString>("fShadow", OString::number(1)));
1694 
1695  const Color& rColor = aShadowItem.GetColor();
1696  // We in fact need RGB to BGR, but the transformation is symmetric.
1697  rFlyProperties.push_back(std::make_pair<OString, OString>(
1698  "shadowColor", OString::number(wwUtility::RGBToBGR(rColor))));
1699 
1700  // Twips -> points -> EMUs -- hacky, the intermediate step hides rounding errors on roundtrip.
1701  OString aShadowWidth = OString::number(sal_Int32(aShadowItem.GetWidth() / 20) * 12700);
1702  OString aOffsetX;
1703  OString aOffsetY;
1704  switch (aShadowItem.GetLocation())
1705  {
1706  case SvxShadowLocation::TopLeft:
1707  aOffsetX = "-" + aShadowWidth;
1708  aOffsetY = "-" + aShadowWidth;
1709  break;
1710  case SvxShadowLocation::TopRight:
1711  aOffsetX = aShadowWidth;
1712  aOffsetY = "-" + aShadowWidth;
1713  break;
1714  case SvxShadowLocation::BottomLeft:
1715  aOffsetX = "-" + aShadowWidth;
1716  aOffsetY = aShadowWidth;
1717  break;
1718  case SvxShadowLocation::BottomRight:
1719  aOffsetX = aShadowWidth;
1720  aOffsetY = aShadowWidth;
1721  break;
1722  case SvxShadowLocation::NONE:
1723  case SvxShadowLocation::End:
1724  break;
1725  }
1726  if (!aOffsetX.isEmpty())
1727  rFlyProperties.emplace_back("shadowOffsetX", aOffsetX);
1728  if (!aOffsetY.isEmpty())
1729  rFlyProperties.emplace_back("shadowOffsetY", aOffsetY);
1730 }
1731 
1732 void lcl_TextFrameRelativeSize(std::vector<std::pair<OString, OString>>& rFlyProperties,
1733  const SwFrameFormat& rFrameFormat)
1734 {
1735  const SwFormatFrameSize& rSize = rFrameFormat.GetFrameSize();
1736 
1737  // Relative size of the Text Frame.
1738  const sal_uInt8 nWidthPercent = rSize.GetWidthPercent();
1739  if (nWidthPercent && nWidthPercent != SwFormatFrameSize::SYNCED)
1740  {
1741  rFlyProperties.push_back(
1742  std::make_pair<OString, OString>("pctHoriz", OString::number(nWidthPercent * 10)));
1743 
1744  OString aRelation;
1745  switch (rSize.GetWidthPercentRelation())
1746  {
1747  case text::RelOrientation::PAGE_FRAME:
1748  aRelation = "1"; // page
1749  break;
1750  default:
1751  aRelation = "0"; // margin
1752  break;
1753  }
1754  rFlyProperties.emplace_back(std::make_pair("sizerelh", aRelation));
1755  }
1756  const sal_uInt8 nHeightPercent = rSize.GetHeightPercent();
1757  if (nHeightPercent && nHeightPercent != SwFormatFrameSize::SYNCED)
1758  {
1759  rFlyProperties.push_back(
1760  std::make_pair<OString, OString>("pctVert", OString::number(nHeightPercent * 10)));
1761 
1762  OString aRelation;
1763  switch (rSize.GetHeightPercentRelation())
1764  {
1765  case text::RelOrientation::PAGE_FRAME:
1766  aRelation = "1"; // page
1767  break;
1768  default:
1769  aRelation = "0"; // margin
1770  break;
1771  }
1772  rFlyProperties.emplace_back(std::make_pair("sizerelv", aRelation));
1773  }
1774 }
1775 }
1776 
1777 void RtfAttributeOutput::writeTextFrame(const ww8::Frame& rFrame, bool bTextBox)
1778 {
1779  RtfStringBuffer aRunText;
1780  if (bTextBox)
1781  {
1782  m_rExport.setStream();
1783  aRunText = m_aRunText;
1784  m_aRunText.clear();
1785  }
1786 
1787  m_rExport.Strm().WriteCharPtr("{" OOO_STRING_SVTOOLS_RTF_SHPTXT);
1788 
1789  {
1790  // Save table state, in case the inner text also contains a table.
1791  ww8::WW8TableInfo::Pointer_t pTableInfoOrig = m_rExport.m_pTableInfo;
1792  m_rExport.m_pTableInfo = std::make_shared<ww8::WW8TableInfo>();
1793  std::unique_ptr<SwWriteTable> pTableWrt(std::move(m_pTableWrt));
1794  sal_uInt32 nTableDepth = m_nTableDepth;
1795 
1796  m_nTableDepth = 0;
1797  /*
1798  * Save m_aRun as we should not lose the opening brace.
1799  * OTOH, just drop the contents of m_aRunText in case something
1800  * would be there, causing a problem later.
1801  */
1802  OString aSave = m_aRun.makeStringAndClear();
1803  // Also back m_bInRun and m_bSingleEmptyRun up.
1804  bool bInRunOrig = m_bInRun;
1805  m_bInRun = false;
1806  bool bSingleEmptyRunOrig = m_bSingleEmptyRun;
1807  m_bSingleEmptyRun = false;
1808  m_rExport.SetRTFFlySyntax(true);
1809 
1810  const SwFrameFormat& rFrameFormat = rFrame.GetFrameFormat();
1811  const SwNodeIndex* pNodeIndex = rFrameFormat.GetContent().GetContentIdx();
1812  sal_uLong nStt = pNodeIndex ? pNodeIndex->GetIndex() + 1 : 0;
1813  sal_uLong nEnd = pNodeIndex ? pNodeIndex->GetNode().EndOfSectionIndex() : 0;
1814  m_rExport.SaveData(nStt, nEnd);
1815  m_rExport.m_pParentFrame = &rFrame;
1816  m_rExport.WriteText();
1817  m_rExport.RestoreData();
1818 
1819  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_PARD);
1820  m_rExport.SetRTFFlySyntax(false);
1821  m_aRun->append(aSave);
1822  m_aRunText.clear();
1823  m_bInRun = bInRunOrig;
1824  m_bSingleEmptyRun = bSingleEmptyRunOrig;
1825 
1826  // Restore table state.
1827  m_rExport.m_pTableInfo = pTableInfoOrig;
1828  m_pTableWrt = std::move(pTableWrt);
1829  m_nTableDepth = nTableDepth;
1830  }
1831 
1832  m_rExport.m_pParentFrame = nullptr;
1833 
1834  m_rExport.Strm().WriteChar('}'); // shptxt
1835 
1836  if (bTextBox)
1837  {
1838  m_aRunText = aRunText;
1839  m_aRunText->append(m_rExport.getStream());
1840  m_rExport.resetStream();
1841  }
1842 }
1843 
1844 void RtfAttributeOutput::OutputFlyFrame_Impl(const ww8::Frame& rFrame, const Point& /*rNdTopLeft*/)
1845 {
1846  const SwNode* pNode = rFrame.GetContent();
1847  const SwGrfNode* pGrfNode = pNode ? pNode->GetGrfNode() : nullptr;
1848 
1849  switch (rFrame.GetWriterType())
1850  {
1851  case ww8::Frame::eTextBox:
1852  {
1853  // If this is a TextBox of a shape, then ignore: it's handled in RtfSdrExport::StartShape().
1855  break;
1856 
1857  OSL_ENSURE(m_aRunText.getLength() == 0, "m_aRunText is not empty");
1858  m_rExport.m_pParentFrame = &rFrame;
1859 
1860  m_rExport.Strm().WriteCharPtr("{" OOO_STRING_SVTOOLS_RTF_SHP);
1861  m_rExport.Strm().WriteCharPtr(
1863 
1864  // Shape properties.
1865  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
1866  "shapeType", OString::number(ESCHER_ShpInst_TextBox)));
1867 
1868  // When a frame has some low height, but automatically expanded due
1869  // to lots of contents, this size contains the real size.
1870  const Size aSize = rFrame.GetSize();
1871  m_pFlyFrameSize = &aSize;
1872 
1873  m_rExport.m_bOutFlyFrameAttrs = true;
1874  m_rExport.SetRTFFlySyntax(true);
1875  m_rExport.OutputFormat(rFrame.GetFrameFormat(), false, false, true);
1876 
1877  // Write ZOrder.
1878  if (const SdrObject* pObject = rFrame.GetFrameFormat().FindRealSdrObject())
1879  {
1880  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPZ);
1881  m_rExport.OutULong(pObject->GetOrdNum());
1882  }
1883 
1884  m_rExport.Strm().WriteCharPtr(m_aRunText.makeStringAndClear().getStr());
1885  m_rExport.Strm().WriteCharPtr(m_aStyles.makeStringAndClear().getStr());
1886  m_rExport.m_bOutFlyFrameAttrs = false;
1887  m_rExport.SetRTFFlySyntax(false);
1888  m_pFlyFrameSize = nullptr;
1889 
1890  const SwFrameFormat& rFrameFormat = rFrame.GetFrameFormat();
1891  lcl_TextFrameShadow(m_aFlyProperties, rFrameFormat);
1892  lcl_TextFrameRelativeSize(m_aFlyProperties, rFrameFormat);
1893 
1894  for (std::pair<OString, OString>& rPair : m_aFlyProperties)
1895  {
1896  m_rExport.Strm().WriteCharPtr("{" OOO_STRING_SVTOOLS_RTF_SP "{");
1897  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SN " ");
1898  m_rExport.Strm().WriteCharPtr(rPair.first.getStr());
1899  m_rExport.Strm().WriteCharPtr("}{" OOO_STRING_SVTOOLS_RTF_SV " ");
1900  m_rExport.Strm().WriteCharPtr(rPair.second.getStr());
1901  m_rExport.Strm().WriteCharPtr("}}");
1902  }
1903  m_aFlyProperties.clear();
1904 
1905  writeTextFrame(rFrame);
1906 
1907  m_rExport.Strm().WriteChar('}'); // shpinst
1908  m_rExport.Strm().WriteChar('}'); // shp
1909 
1910  m_rExport.Strm().WriteCharPtr(SAL_NEWLINE_STRING);
1911  }
1912  break;
1913  case ww8::Frame::eGraphic:
1914  if (!rFrame.IsInline())
1915  {
1916  m_rExport.m_pParentFrame = &rFrame;
1917  m_rExport.SetRTFFlySyntax(true);
1918  m_rExport.OutputFormat(rFrame.GetFrameFormat(), false, false, true);
1919  m_rExport.SetRTFFlySyntax(false);
1920  m_aRunText->append("{" OOO_STRING_SVTOOLS_RTF_IGNORE);
1921  m_rExport.OutputFormat(rFrame.GetFrameFormat(), false, false, true);
1922  m_aRunText->append('}');
1923  m_rExport.m_pParentFrame = nullptr;
1924  }
1925 
1926  if (pGrfNode)
1927  m_aRunText.append(dynamic_cast<const SwFlyFrameFormat*>(&rFrame.GetFrameFormat()),
1928  pGrfNode);
1929  break;
1930  case ww8::Frame::eDrawing:
1931  {
1932  const SdrObject* pSdrObj = rFrame.GetFrameFormat().FindRealSdrObject();
1933  if (pSdrObj)
1934  {
1935  m_aRunText->append("{" OOO_STRING_SVTOOLS_RTF_FIELD "{");
1936  m_aRunText->append(OOO_STRING_SVTOOLS_RTF_IGNORE);
1937  m_aRunText->append(OOO_STRING_SVTOOLS_RTF_FLDINST);
1938  m_aRunText->append(" SHAPE ");
1939  m_aRunText->append("}"
1941 
1942  m_rExport.SdrExporter().AddSdrObject(*pSdrObj);
1943 
1944  m_aRunText->append('}');
1945  m_aRunText->append('}');
1946  }
1947  }
1948  break;
1950  {
1951  const SwFrameFormat& rFrameFormat = rFrame.GetFrameFormat();
1952  const SdrObject* pObject = rFrameFormat.FindRealSdrObject();
1953 
1954  m_aRun->append("{" OOO_STRING_SVTOOLS_RTF_FIELD);
1956 
1957  if (pObject && pObject->GetObjInventor() == SdrInventor::FmForm)
1958  {
1959  if (auto pFormObj = dynamic_cast<const SdrUnoObj*>(pObject))
1960  {
1961  const uno::Reference<awt::XControlModel>& xControlModel
1962  = pFormObj->GetUnoControlModel();
1963  uno::Reference<lang::XServiceInfo> xInfo(xControlModel, uno::UNO_QUERY);
1964  if (xInfo.is())
1965  {
1966  uno::Reference<beans::XPropertySet> xPropSet(xControlModel, uno::UNO_QUERY);
1967  uno::Reference<beans::XPropertySetInfo> xPropSetInfo
1968  = xPropSet->getPropertySetInfo();
1969  OUString sName;
1970  if (xInfo->supportsService("com.sun.star.form.component.CheckBox"))
1971  {
1973  m_rExport.GetCurrentEncoding()));
1974  m_aRun->append(
1976  "{");
1977  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFTYPE "1"); // 1 = checkbox
1978  // checkbox size in half points, this seems to be always 20
1979  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFHPS "20");
1980 
1981  OUString aStr;
1982  sName = "Name";
1983  if (xPropSetInfo->hasPropertyByName(sName))
1984  {
1985  xPropSet->getPropertyValue(sName) >>= aStr;
1986  m_aRun->append(
1988  " ");
1989  m_aRun->append(
1990  OUStringToOString(aStr, m_rExport.GetCurrentEncoding()));
1991  m_aRun->append('}');
1992  }
1993 
1994  sName = "HelpText";
1995  if (xPropSetInfo->hasPropertyByName(sName))
1996  {
1997  xPropSet->getPropertyValue(sName) >>= aStr;
1998  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFOWNHELP);
1999  m_aRun->append("{" OOO_STRING_SVTOOLS_RTF_IGNORE
2001  m_aRun->append(
2002  OUStringToOString(aStr, m_rExport.GetCurrentEncoding()));
2003  m_aRun->append('}');
2004  }
2005 
2006  sName = "HelpF1Text";
2007  if (xPropSetInfo->hasPropertyByName(sName))
2008  {
2009  xPropSet->getPropertyValue(sName) >>= aStr;
2010  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFOWNSTAT);
2011  m_aRun->append("{" OOO_STRING_SVTOOLS_RTF_IGNORE
2013  m_aRun->append(
2014  OUStringToOString(aStr, m_rExport.GetCurrentEncoding()));
2015  m_aRun->append('}');
2016  }
2017 
2018  sal_Int16 nTemp = 0;
2019  xPropSet->getPropertyValue("DefaultState") >>= nTemp;
2020  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFDEFRES);
2021  m_aRun->append(static_cast<sal_Int32>(nTemp));
2022  xPropSet->getPropertyValue("State") >>= nTemp;
2023  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFRES);
2024  m_aRun->append(static_cast<sal_Int32>(nTemp));
2025 
2026  m_aRun->append("}}");
2027 
2028  // field result is empty, ffres already contains the form result
2029  m_aRun->append("}{" OOO_STRING_SVTOOLS_RTF_FLDRSLT " ");
2030  }
2031  else if (xInfo->supportsService("com.sun.star.form.component.TextField"))
2032  {
2033  OStringBuffer aBuf;
2034  OString aStr;
2035  OUString aTmp;
2036  const sal_Char* pStr;
2037 
2039  m_rExport.GetCurrentEncoding()));
2040  m_aRun->append(
2042  " ");
2043  for (int i = 0; i < 8; i++)
2044  aBuf.append(sal_Char(0x00));
2045  xPropSet->getPropertyValue("Name") >>= aTmp;
2046  aStr = OUStringToOString(aTmp, m_rExport.GetCurrentEncoding());
2047  aBuf.append(static_cast<sal_Char>(aStr.getLength()));
2048  aBuf.append(aStr);
2049  aBuf.append(sal_Char(0x00));
2050  xPropSet->getPropertyValue("DefaultText") >>= aTmp;
2051  aStr = OUStringToOString(aTmp, m_rExport.GetCurrentEncoding());
2052  aBuf.append(static_cast<sal_Char>(aStr.getLength()));
2053  aBuf.append(aStr);
2054  for (int i = 0; i < 11; i++)
2055  aBuf.append(sal_Char(0x00));
2056  aStr = aBuf.makeStringAndClear();
2057  pStr = aStr.getStr();
2058  for (int i = 0; i < aStr.getLength(); i++, pStr++)
2059  m_aRun->append(msfilter::rtfutil::OutHex(*pStr, 2));
2060  m_aRun->append('}');
2061  m_aRun->append("}{" OOO_STRING_SVTOOLS_RTF_FLDRSLT " ");
2062  xPropSet->getPropertyValue("Text") >>= aTmp;
2063  m_aRun->append(OUStringToOString(aTmp, m_rExport.GetCurrentEncoding()));
2064  m_aRun->append('}');
2065  m_aRun->append(
2067  "{");
2068  sName = "HelpText";
2069  if (xPropSetInfo->hasPropertyByName(sName))
2070  {
2071  xPropSet->getPropertyValue(sName) >>= aTmp;
2072  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFOWNHELP);
2073  m_aRun->append("{" OOO_STRING_SVTOOLS_RTF_IGNORE
2075  m_aRun->append(
2076  OUStringToOString(aTmp, m_rExport.GetCurrentEncoding()));
2077  m_aRun->append('}');
2078  }
2079 
2080  sName = "HelpF1Text";
2081  if (xPropSetInfo->hasPropertyByName(sName))
2082  {
2083  xPropSet->getPropertyValue(sName) >>= aTmp;
2084  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFOWNSTAT);
2085  m_aRun->append("{" OOO_STRING_SVTOOLS_RTF_IGNORE
2087  m_aRun->append(
2088  OUStringToOString(aTmp, m_rExport.GetCurrentEncoding()));
2089  m_aRun->append('}');
2090  }
2091  m_aRun->append("}");
2092  }
2093  else if (xInfo->supportsService("com.sun.star.form.component.ListBox"))
2094  {
2095  OUString aStr;
2096  uno::Sequence<sal_Int16> aIntSeq;
2097  uno::Sequence<OUString> aStrSeq;
2098 
2100  m_rExport.GetCurrentEncoding()));
2101  m_aRun->append(
2103  "{");
2104  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFTYPE "2"); // 2 = list
2105  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFHASLISTBOX);
2106 
2107  xPropSet->getPropertyValue("DefaultSelection") >>= aIntSeq;
2108  if (aIntSeq.hasElements())
2109  {
2110  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFDEFRES);
2111  // a dropdown list can have only one 'selected item by default'
2112  m_aRun->append(static_cast<sal_Int32>(aIntSeq[0]));
2113  }
2114 
2115  xPropSet->getPropertyValue("SelectedItems") >>= aIntSeq;
2116  if (aIntSeq.hasElements())
2117  {
2118  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFRES);
2119  // a dropdown list can have only one 'currently selected item'
2120  m_aRun->append(static_cast<sal_Int32>(aIntSeq[0]));
2121  }
2122 
2123  sName = "Name";
2124  if (xPropSetInfo->hasPropertyByName(sName))
2125  {
2126  xPropSet->getPropertyValue(sName) >>= aStr;
2127  m_aRun->append(
2129  " ");
2130  m_aRun->append(
2131  OUStringToOString(aStr, m_rExport.GetCurrentEncoding()));
2132  m_aRun->append('}');
2133  }
2134 
2135  sName = "HelpText";
2136  if (xPropSetInfo->hasPropertyByName(sName))
2137  {
2138  xPropSet->getPropertyValue(sName) >>= aStr;
2139  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFOWNHELP);
2140  m_aRun->append("{" OOO_STRING_SVTOOLS_RTF_IGNORE
2142  m_aRun->append(
2143  OUStringToOString(aStr, m_rExport.GetCurrentEncoding()));
2144  m_aRun->append('}');
2145  }
2146 
2147  sName = "HelpF1Text";
2148  if (xPropSetInfo->hasPropertyByName(sName))
2149  {
2150  xPropSet->getPropertyValue(sName) >>= aStr;
2151  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FFOWNSTAT);
2152  m_aRun->append("{" OOO_STRING_SVTOOLS_RTF_IGNORE
2154  m_aRun->append(
2155  OUStringToOString(aStr, m_rExport.GetCurrentEncoding()));
2156  m_aRun->append('}');
2157  }
2158 
2159  xPropSet->getPropertyValue("StringItemList") >>= aStrSeq;
2160  sal_uInt32 nListItems = aStrSeq.getLength();
2161  for (sal_uInt32 i = 0; i < nListItems; i++)
2162  m_aRun
2163  ->append(
2165  " ")
2166  .append(OUStringToOString(aStrSeq[i],
2167  m_rExport.GetCurrentEncoding()))
2168  .append('}');
2169 
2170  m_aRun->append("}}");
2171 
2172  // field result is empty, ffres already contains the form result
2173  m_aRun->append("}{" OOO_STRING_SVTOOLS_RTF_FLDRSLT " ");
2174  }
2175  else
2176  SAL_INFO("sw.rtf", OSL_THIS_FUNC << " unhandled form control: '"
2177  << xInfo->getImplementationName()
2178  << "'");
2179  m_aRun->append('}');
2180  }
2181  }
2182  }
2183 
2184  m_aRun->append('}');
2185  }
2186  break;
2187  case ww8::Frame::eOle:
2188  {
2189  const SwFrameFormat& rFrameFormat = rFrame.GetFrameFormat();
2190  const SdrObject* pSdrObj = rFrameFormat.FindRealSdrObject();
2191  if (pSdrObj)
2192  {
2193  SwNodeIndex aIdx(*rFrameFormat.GetContent().GetContentIdx(), 1);
2194  SwOLENode& rOLENd = *aIdx.GetNode().GetOLENode();
2195  FlyFrameOLE(dynamic_cast<const SwFlyFrameFormat*>(&rFrameFormat), rOLENd,
2196  rFrame.GetLayoutSize());
2197  }
2198  }
2199  break;
2200  default:
2201  SAL_INFO("sw.rtf", OSL_THIS_FUNC << ": unknown type ("
2202  << static_cast<int>(rFrame.GetWriterType()) << ")");
2203  break;
2204  }
2205 }
2206 
2208 {
2209  switch (rCaseMap.GetValue())
2210  {
2211  case SvxCaseMap::SmallCaps:
2212  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SCAPS);
2213  break;
2214  case SvxCaseMap::Uppercase:
2215  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_CAPS);
2216  break;
2217  default: // Something that rtf does not support
2218  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SCAPS);
2219  m_aStyles.append(sal_Int32(0));
2220  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_CAPS);
2221  m_aStyles.append(sal_Int32(0));
2222  break;
2223  }
2224 }
2225 
2227 {
2228  const Color aColor(rColor.GetValue());
2229 
2230  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_CF);
2231  m_aStyles.append(static_cast<sal_Int32>(m_rExport.GetColor(aColor)));
2232 }
2233 
2235 {
2236  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_OUTL);
2237  if (!rContour.GetValue())
2238  m_aStyles.append(sal_Int32(0));
2239 }
2240 
2242 {
2243  switch (rCrossedOut.GetStrikeout())
2244  {
2245  case STRIKEOUT_NONE:
2246  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_STRIKE);
2247  m_aStyles.append(sal_Int32(0));
2248  break;
2249  case STRIKEOUT_DOUBLE:
2250  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_STRIKED);
2251  m_aStyles.append(sal_Int32(1));
2252  break;
2253  default:
2254  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_STRIKE);
2255  break;
2256  }
2257 }
2258 
2260 {
2261  short nEsc = rEscapement.GetEsc();
2262  if (rEscapement.GetProportionalHeight() == DFLT_ESC_PROP)
2263  {
2264  if (DFLT_ESC_SUB == nEsc || DFLT_ESC_AUTO_SUB == nEsc)
2265  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SUB);
2266  else if (DFLT_ESC_SUPER == nEsc || DFLT_ESC_AUTO_SUPER == nEsc)
2267  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SUPER);
2268  return;
2269  }
2270 
2271  const char* pUpDn;
2272 
2273  SwTwips nH = m_rExport.GetItem(RES_CHRATR_FONTSIZE).GetHeight();
2274 
2275  if (0 < rEscapement.GetEsc())
2276  pUpDn = OOO_STRING_SVTOOLS_RTF_UP;
2277  else if (0 > rEscapement.GetEsc())
2278  {
2279  pUpDn = OOO_STRING_SVTOOLS_RTF_DN;
2280  nH = -nH;
2281  }
2282  else
2283  return;
2284 
2285  short nProp = rEscapement.GetProportionalHeight() * 100;
2286  if (DFLT_ESC_AUTO_SUPER == nEsc)
2287  {
2288  nEsc = 100 - rEscapement.GetProportionalHeight();
2289  ++nProp;
2290  }
2291  else if (DFLT_ESC_AUTO_SUB == nEsc)
2292  {
2293  nEsc = -100 + rEscapement.GetProportionalHeight();
2294  ++nProp;
2295  }
2296 
2297  m_aStyles.append('{');
2298  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_IGNORE);
2299  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_UPDNPROP);
2300  m_aStyles.append(static_cast<sal_Int32>(nProp));
2301  m_aStyles.append('}');
2302  m_aStyles.append(pUpDn);
2303 
2304  /*
2305  * Calculate the act. FontSize and the percentage of the displacement;
2306  * RTF file expects half points, while internally it's in twips.
2307  * Formally : (FontSize * 1/20 ) pts x * 2
2308  * ----------------------- = ------------
2309  * 100% Escapement
2310  */
2311 
2312  m_aStyles.append(static_cast<sal_Int32>((long(nEsc) * nH) + 500) / 1000);
2313  // 500 to round !!
2314 }
2315 
2317 {
2318  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_LOCH);
2319  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_F);
2320  m_aStylesEnd.append(static_cast<sal_Int32>(m_rExport.m_aFontHelper.GetId(rFont)));
2321 
2322  if (!m_rExport.HasItem(RES_CHRATR_CJK_FONT) && !m_rExport.HasItem(RES_CHRATR_CTL_FONT))
2323  {
2324  // Be explicit about that the given font should be used everywhere, not
2325  // just for the loch range.
2326  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_HICH);
2327  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_AF);
2328  m_aStylesEnd.append(static_cast<sal_Int32>(m_rExport.m_aFontHelper.GetId(rFont)));
2329  }
2330 
2331  // FIXME: this may be a tad expensive... but the charset needs to be
2332  // consistent with what wwFont::WriteRtf() does
2333  sw::util::FontMapExport aTmp(rFont.GetFamilyName());
2335  aTmp.msPrimary, aTmp.msSecondary, rFont.GetCharSet());
2336  m_rExport.SetCurrentEncoding(rtl_getTextEncodingFromWindowsCharset(nWindowsCharset));
2337  if (m_rExport.GetCurrentEncoding() == RTL_TEXTENCODING_DONTKNOW)
2338  m_rExport.SetCurrentEncoding(m_rExport.GetDefaultEncoding());
2339 }
2340 
2342 {
2343  switch (rFontSize.Which())
2344  {
2345  case RES_CHRATR_FONTSIZE:
2346  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_FS);
2347  m_aStylesEnd.append(static_cast<sal_Int32>(rFontSize.GetHeight() / 10));
2348  break;
2350  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_FS);
2351  m_aStyles.append(static_cast<sal_Int32>(rFontSize.GetHeight() / 10));
2352  break;
2354  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_AFS);
2355  m_aStyles.append(static_cast<sal_Int32>(rFontSize.GetHeight() / 10));
2356  break;
2357  }
2358 }
2359 
2361 {
2362  // in quarter points then in twips
2363  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_EXPND);
2364  m_aStyles.append(static_cast<sal_Int32>(rKerning.GetValue() / 5));
2365  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_EXPNDTW);
2366  m_aStyles.append(static_cast<sal_Int32>(rKerning.GetValue()));
2367 }
2368 
2370 {
2371  switch (rLanguage.Which())
2372  {
2373  case RES_CHRATR_LANGUAGE:
2374  m_aStylesEnd.append(OOO_STRING_SVTOOLS_RTF_LANG);
2375  m_aStylesEnd.append(
2376  static_cast<sal_Int32>(static_cast<sal_uInt16>(rLanguage.GetLanguage())));
2377  break;
2379  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_LANGFE);
2380  m_aStyles.append(
2381  static_cast<sal_Int32>(static_cast<sal_uInt16>(rLanguage.GetLanguage())));
2382  break;
2384  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ALANG);
2385  m_aStyles.append(
2386  static_cast<sal_Int32>(static_cast<sal_uInt16>(rLanguage.GetLanguage())));
2387  break;
2388  }
2389 }
2390 
2392 {
2393  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_I);
2394  if (rPosture.GetPosture() == ITALIC_NONE)
2395  m_aStyles.append(sal_Int32(0));
2396 }
2397 
2399 {
2400  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SHAD);
2401  if (!rShadow.GetValue())
2402  m_aStyles.append(sal_Int32(0));
2403 }
2404 
2406 {
2407  const char* pStr = nullptr;
2408  const SfxPoolItem* pItem = m_rExport.HasItem(RES_CHRATR_WORDLINEMODE);
2409  bool bWord = false;
2410  if (pItem)
2411  bWord = static_cast<const SvxWordLineModeItem*>(pItem)->GetValue();
2412  switch (rUnderline.GetLineStyle())
2413  {
2414  case LINESTYLE_SINGLE:
2416  break;
2417  case LINESTYLE_DOUBLE:
2419  break;
2420  case LINESTYLE_NONE:
2422  break;
2423  case LINESTYLE_DOTTED:
2425  break;
2426  case LINESTYLE_DASH:
2428  break;
2429  case LINESTYLE_DASHDOT:
2431  break;
2432  case LINESTYLE_DASHDOTDOT:
2434  break;
2435  case LINESTYLE_BOLD:
2437  break;
2438  case LINESTYLE_WAVE:
2440  break;
2441  case LINESTYLE_BOLDDOTTED:
2443  break;
2444  case LINESTYLE_BOLDDASH:
2446  break;
2447  case LINESTYLE_LONGDASH:
2449  break;
2452  break;
2453  case LINESTYLE_BOLDDASHDOT:
2455  break;
2458  break;
2459  case LINESTYLE_BOLDWAVE:
2461  break;
2462  case LINESTYLE_DOUBLEWAVE:
2464  break;
2465  default:
2466  break;
2467  }
2468 
2469  if (pStr)
2470  {
2471  m_aStyles.append(pStr);
2472  // NEEDSWORK looks like here rUnderline.GetColor() is always black,
2473  // even if the color in the odt is for example green...
2474  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ULC);
2475  m_aStyles.append(static_cast<sal_Int32>(m_rExport.GetColor(rUnderline.GetColor())));
2476  }
2477 }
2478 
2480 {
2481  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_B);
2482  if (rWeight.GetWeight() != WEIGHT_BOLD)
2483  m_aStyles.append(sal_Int32(0));
2484 }
2485 
2487 {
2488  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_KERNING);
2489  m_aStyles.append(static_cast<sal_Int32>(rAutoKern.GetValue() ? 1 : 0));
2490 }
2491 
2493 {
2494  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ANIMTEXT);
2495  m_aStyles.append(static_cast<sal_Int32>(rBlink.GetValue() ? 2 : 0));
2496 }
2497 
2499 {
2500  if (!rBrush.GetColor().GetTransparency())
2501  {
2502  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_CHCBPAT);
2503  m_aStyles.append(static_cast<sal_Int32>(m_rExport.GetColor(rBrush.GetColor())));
2504  }
2505 }
2506 
2508 {
2509  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_DBCH);
2510  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_AF);
2511  m_aStyles.append(static_cast<sal_Int32>(m_rExport.m_aFontHelper.GetId(rFont)));
2512 }
2513 
2515 {
2516  CharFontSize(rFontSize);
2517 }
2518 
2520 {
2521  CharLanguage(rLanguageItem);
2522 }
2523 
2525 {
2526  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_I);
2527  if (rPosture.GetPosture() == ITALIC_NONE)
2528  m_aStyles.append(sal_Int32(0));
2529 }
2530 
2532 {
2533  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_B);
2534  if (rWeight.GetWeight() != WEIGHT_BOLD)
2535  m_aStyles.append(sal_Int32(0));
2536 }
2537 
2539 {
2540  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_DBCH);
2541  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_AF);
2542  m_aStyles.append(static_cast<sal_Int32>(m_rExport.m_aFontHelper.GetId(rFont)));
2543 }
2544 
2546 {
2547  CharFontSize(rFontSize);
2548 }
2549 
2551 {
2552  CharLanguage(rLanguageItem);
2553 }
2554 
2556 {
2557  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_AI);
2558  if (rPosture.GetPosture() == ITALIC_NONE)
2559  m_aStyles.append(sal_Int32(0));
2560 }
2561 
2563 {
2564  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_AB);
2565  if (rWeight.GetWeight() != WEIGHT_BOLD)
2566  m_aStyles.append(sal_Int32(0));
2567 }
2568 
2570 
2572 
2574 {
2575  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_HORZVERT);
2576  m_aStyles.append(static_cast<sal_Int32>(rRotate.IsFitToLine() ? 1 : 0));
2577 }
2578 
2580 {
2581  FontEmphasisMark v = rEmphasisMark.GetEmphasisMark();
2582  if (v == FontEmphasisMark::NONE)
2583  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ACCNONE);
2584  else if (v == (FontEmphasisMark::Dot | FontEmphasisMark::PosAbove))
2585  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ACCDOT);
2586  else if (v == (FontEmphasisMark::Accent | FontEmphasisMark::PosAbove))
2587  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ACCCOMMA);
2588  else if (v == (FontEmphasisMark::Circle | FontEmphasisMark::PosAbove))
2589  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ACCCIRCLE);
2590  else if (v == (FontEmphasisMark::Dot | FontEmphasisMark::PosBelow))
2591  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ACCUNDERDOT);
2592 }
2593 
2595 {
2596  if (rTwoLines.GetValue())
2597  {
2598  sal_Unicode cStart = rTwoLines.GetStartBracket();
2599  sal_Unicode cEnd = rTwoLines.GetEndBracket();
2600 
2601  sal_uInt16 nType;
2602  if (!cStart && !cEnd)
2603  nType = 0;
2604  else if ('{' == cStart || '}' == cEnd)
2605  nType = 4;
2606  else if ('<' == cStart || '>' == cEnd)
2607  nType = 3;
2608  else if ('[' == cStart || ']' == cEnd)
2609  nType = 2;
2610  else // all other kind of brackets
2611  nType = 1;
2612 
2613  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_TWOINONE);
2614  m_aStyles.append(static_cast<sal_Int32>(nType));
2615  }
2616 }
2617 
2619 {
2620  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_CHARSCALEX);
2621  m_aStyles.append(static_cast<sal_Int32>(rScaleWidth.GetValue()));
2622 }
2623 
2625 {
2626  const sal_Char* pStr;
2627  switch (rRelief.GetValue())
2628  {
2629  case FontRelief::Embossed:
2631  break;
2632  case FontRelief::Engraved:
2634  break;
2635  default:
2636  pStr = nullptr;
2637  break;
2638  }
2639 
2640  if (pStr)
2641  m_aStyles.append(pStr);
2642 }
2643 
2645 {
2646  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_V);
2647  if (!rHidden.GetValue())
2648  m_aStyles.append(sal_Int32(0));
2649 }
2650 
2652  const sal_uInt16 nDist, const bool bShadow)
2653 {
2654  m_aStyles.append(
2655  OutBorderLine(m_rExport, pAllBorder, OOO_STRING_SVTOOLS_RTF_CHBRDR, nDist,
2656  bShadow ? SvxShadowLocation::BottomRight : SvxShadowLocation::NONE));
2657 }
2658 
2660 {
2661  if (!rBrush.GetColor().GetTransparency())
2662  {
2663  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_HIGHLIGHT);
2664  m_aStyles.append(static_cast<sal_Int32>(msfilter::util::TransColToIco(rBrush.GetColor())));
2665  }
2666 }
2667 
2669 {
2670  if (!rURL.GetValue().isEmpty())
2671  {
2672  const SwCharFormat* pFormat;
2673  const SwTextINetFormat* pTextAtr = rURL.GetTextINetFormat();
2674 
2675  if (pTextAtr && nullptr != (pFormat = pTextAtr->GetCharFormat()))
2676  {
2677  sal_uInt16 nStyle = m_rExport.GetId(pFormat);
2678  OString* pString = m_rExport.GetStyle(nStyle);
2679  if (pString)
2680  m_aStyles.append(*pString);
2681  }
2682  }
2683 }
2684 
2686 {
2687  sal_uInt16 nStyle = m_rExport.GetId(rCharFormat.GetCharFormat());
2688  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_CS);
2689  m_aStyles.append(static_cast<sal_Int32>(nStyle));
2690  OString* pString = m_rExport.GetStyle(nStyle);
2691  if (pString)
2692  m_aStyles.append(*pString);
2693 }
2694 
2696 {
2697  if (rFootnote.GetNumStr().isEmpty())
2698  m_aRun->append(OOO_STRING_SVTOOLS_RTF_CHFTN);
2699  else
2700  m_aRun->append(
2701  msfilter::rtfutil::OutString(rFootnote.GetNumStr(), m_rExport.GetCurrentEncoding()));
2702 }
2703 
2705 {
2706  SAL_INFO("sw.rtf", OSL_THIS_FUNC << " start");
2707 
2708  m_aRun->append("{" OOO_STRING_SVTOOLS_RTF_SUPER " ");
2709  EndRunProperties(nullptr);
2710  m_aRun->append(' ');
2711  WriteTextFootnoteNumStr(rFootnote);
2713  if (rFootnote.IsEndNote() || m_rExport.m_pDoc->GetFootnoteInfo().ePos == FTNPOS_CHAPTER)
2714  m_aRun->append(OOO_STRING_SVTOOLS_RTF_FTNALT);
2715  m_aRun->append(' ');
2716  WriteTextFootnoteNumStr(rFootnote);
2717 
2718  /*
2719  * The footnote contains a whole paragraph, so we have to:
2720  * 1) Reset, then later restore the contents of our run buffer and run state.
2721  * 2) Buffer the output of the whole paragraph, as we do so for section headers already.
2722  */
2723  const SwNodeIndex* pIndex = rFootnote.GetTextFootnote()->GetStartNode();
2724  RtfStringBuffer aRun = m_aRun;
2725  m_aRun.clear();
2726  bool bInRunOrig = m_bInRun;
2727  m_bInRun = false;
2728  bool bSingleEmptyRunOrig = m_bSingleEmptyRun;
2729  m_bSingleEmptyRun = false;
2730  m_bBufferSectionHeaders = true;
2731  m_rExport.WriteSpecialText(pIndex->GetIndex() + 1, pIndex->GetNode().EndOfSectionIndex(),
2732  !rFootnote.IsEndNote() ? TXT_FTN : TXT_EDN);
2733  m_bBufferSectionHeaders = false;
2734  m_bInRun = bInRunOrig;
2735  m_bSingleEmptyRun = bSingleEmptyRunOrig;
2736  m_aRun = aRun;
2737  m_aRun->append(m_aSectionHeaders.makeStringAndClear());
2738 
2739  m_aRun->append("}");
2740  m_aRun->append("}");
2741 
2742  SAL_INFO("sw.rtf", OSL_THIS_FUNC << " end");
2743 }
2744 
2745 void RtfAttributeOutput::ParaLineSpacing_Impl(short nSpace, short nMulti)
2746 {
2747  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SL);
2748  m_aStyles.append(static_cast<sal_Int32>(nSpace));
2749  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SLMULT);
2750  m_aStyles.append(static_cast<sal_Int32>(nMulti));
2751 }
2752 
2754 {
2755  switch (rAdjust.GetAdjust())
2756  {
2757  case SvxAdjust::Left:
2758  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_QL);
2759  break;
2760  case SvxAdjust::Right:
2761  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_QR);
2762  break;
2763  case SvxAdjust::BlockLine:
2764  case SvxAdjust::Block:
2765  if (rAdjust.GetLastBlock() == SvxAdjust::Block)
2766  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_QD);
2767  else
2768  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_QJ);
2769  break;
2770  case SvxAdjust::Center:
2771  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_QC);
2772  break;
2773  default:
2774  break;
2775  }
2776 }
2777 
2779 {
2780  if (!rSplit.GetValue())
2781  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_KEEP);
2782 }
2783 
2785 {
2786  if (rWidows.GetValue())
2787  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_WIDCTLPAR);
2788  else
2789  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_NOWIDCTLPAR);
2790 }
2791 
2793 {
2794  long nOffset = 0;
2795  // Tabs are absolute by default.
2796  if (m_rExport.m_pDoc->getIDocumentSettingAccess().get(
2798  nOffset = m_rExport.GetItem(RES_LR_SPACE).GetTextLeft();
2799 
2800  for (sal_uInt16 n = 0; n < rTabStop.Count(); n++)
2801  {
2802  const SvxTabStop& rTS = rTabStop[n];
2803  if (SvxTabAdjust::Default != rTS.GetAdjustment())
2804  {
2805  const char* pFill = nullptr;
2806  switch (rTS.GetFill())
2807  {
2808  case cDfltFillChar:
2809  break;
2810 
2811  case '.':
2813  break;
2814  case '_':
2816  break;
2817  case '-':
2819  break;
2820  case '=':
2822  break;
2823  default:
2824  break;
2825  }
2826  if (pFill)
2827  m_aStyles.append(pFill);
2828 
2829  const sal_Char* pAdjStr = nullptr;
2830  switch (rTS.GetAdjustment())
2831  {
2832  case SvxTabAdjust::Right:
2833  pAdjStr = OOO_STRING_SVTOOLS_RTF_TQR;
2834  break;
2835  case SvxTabAdjust::Decimal:
2836  pAdjStr = OOO_STRING_SVTOOLS_RTF_TQDEC;
2837  break;
2838  case SvxTabAdjust::Center:
2839  pAdjStr = OOO_STRING_SVTOOLS_RTF_TQC;
2840  break;
2841  default:
2842  break;
2843  }
2844  if (pAdjStr)
2845  m_aStyles.append(pAdjStr);
2846  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_TX);
2847  m_aStyles.append(static_cast<sal_Int32>(rTS.GetTabPos() + nOffset));
2848  }
2849  else
2850  {
2851  m_aTabStop.append(OOO_STRING_SVTOOLS_RTF_DEFTAB);
2852  m_aTabStop.append(rTabStop[0].GetTabPos());
2853  }
2854  }
2855 }
2856 
2858 {
2859  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_HYPHPAR);
2860  m_aStyles.append(sal_Int32(rHyphenZone.IsHyphen()));
2861 }
2862 
2863 void RtfAttributeOutput::ParaNumRule_Impl(const SwTextNode* pTextNd, sal_Int32 nLvl,
2864  sal_Int32 nNumId)
2865 {
2866  if (USHRT_MAX == nNumId || 0 == nNumId || nullptr == pTextNd)
2867  return;
2868 
2869  const SwNumRule* pRule = pTextNd->GetNumRule();
2870 
2871  if (!pRule || !pTextNd->IsInList())
2872  return;
2873 
2874  SAL_WARN_IF(pTextNd->GetActualListLevel() < 0 || pTextNd->GetActualListLevel() >= MAXLEVEL,
2875  "sw.rtf", "text node does not have valid list level");
2876 
2877  const SwNumFormat* pFormat = pRule->GetNumFormat(nLvl);
2878  if (!pFormat)
2879  pFormat = &pRule->Get(nLvl);
2880 
2881  const SfxItemSet& rNdSet = pTextNd->GetSwAttrSet();
2882 
2883  m_aStyles.append('{');
2884  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_LISTTEXT);
2885  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_PARD);
2886  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_PLAIN);
2887  m_aStyles.append(' ');
2888 
2889  SvxLRSpaceItem aLR(rNdSet.Get(RES_LR_SPACE));
2890  aLR.SetTextLeft(aLR.GetTextLeft() + pFormat->GetIndentAt());
2891  aLR.SetTextFirstLineOfst(pFormat->GetFirstLineOffset()); //TODO: overflow
2892 
2893  sal_uInt16 nStyle = m_rExport.GetId(pFormat->GetCharFormat());
2894  OString* pString = m_rExport.GetStyle(nStyle);
2895  if (pString)
2896  m_aStyles.append(*pString);
2897 
2898  {
2899  OUString sText;
2900  if (SVX_NUM_CHAR_SPECIAL == pFormat->GetNumberingType()
2901  || SVX_NUM_BITMAP == pFormat->GetNumberingType())
2902  sText = OUString(pFormat->GetBulletChar());
2903  else
2904  sText = pTextNd->GetNumString();
2905 
2906  if (!sText.isEmpty())
2907  {
2908  m_aStyles.append(' ');
2909  m_aStyles.append(msfilter::rtfutil::OutString(sText, m_rExport.GetDefaultEncoding()));
2910  }
2911 
2912  if (OUTLINE_RULE != pRule->GetRuleType())
2913  {
2914  if (!sText.isEmpty())
2915  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_TAB);
2916  m_aStyles.append('}');
2917  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ILVL);
2918  if (nLvl > 8) // RTF knows only 9 levels
2919  {
2920  m_aStyles.append(sal_Int32(8));
2922  m_aStyles.append(nLvl);
2923  m_aStyles.append('}');
2924  }
2925  else
2926  m_aStyles.append(nLvl);
2927  }
2928  else
2929  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_TAB "}");
2930  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_LS);
2931  m_aStyles.append(static_cast<sal_Int32>(m_rExport.GetId(*pRule)) + 1);
2932  m_aStyles.append(' ');
2933  }
2934  FormatLRSpace(aLR);
2935 }
2936 
2938 {
2939  if (!rScriptSpace.GetValue())
2940  return;
2941 
2942  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_ASPALPHA);
2943 }
2944 
2946 {
2947  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
2948 }
2949 
2951 {
2952  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
2953 }
2954 
2956 {
2957  const char* pStr;
2958  switch (rAlign.GetValue())
2959  {
2962  break;
2965  break;
2968  break;
2971  break;
2972 
2973  default:
2975  break;
2976  }
2977  m_aStyles.append(pStr);
2978 }
2979 
2981 {
2982  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
2983 }
2984 
2986 {
2987  if (m_rExport.m_bOutPageDescs)
2988  {
2989  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_PGWSXN);
2990  m_aSectionBreaks.append(static_cast<sal_Int32>(rSize.GetWidth()));
2991  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_PGHSXN);
2992  m_aSectionBreaks.append(static_cast<sal_Int32>(rSize.GetHeight()));
2993  if (!m_bBufferSectionBreaks)
2994  m_rExport.Strm().WriteCharPtr(m_aSectionBreaks.makeStringAndClear().getStr());
2995  }
2996 }
2997 
2999 {
3000  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
3001 }
3002 
3004 {
3005  if (!m_rExport.m_bOutFlyFrameAttrs)
3006  {
3007  if (m_rExport.m_bOutPageDescs)
3008  {
3009  if (rLRSpace.GetLeft())
3010  {
3011  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_MARGLSXN);
3012  m_aSectionBreaks.append(static_cast<sal_Int32>(rLRSpace.GetLeft()));
3013  }
3014  if (rLRSpace.GetRight())
3015  {
3016  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_MARGRSXN);
3017  m_aSectionBreaks.append(static_cast<sal_Int32>(rLRSpace.GetRight()));
3018  }
3019  if (!m_bBufferSectionBreaks)
3020  m_rExport.Strm().WriteCharPtr(m_aSectionBreaks.makeStringAndClear().getStr());
3021  }
3022  else
3023  {
3024  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_LI);
3025  m_aStyles.append(static_cast<sal_Int32>(rLRSpace.GetTextLeft()));
3026  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_RI);
3027  m_aStyles.append(static_cast<sal_Int32>(rLRSpace.GetRight()));
3028  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_LIN);
3029  m_aStyles.append(static_cast<sal_Int32>(rLRSpace.GetTextLeft()));
3030  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_RIN);
3031  m_aStyles.append(static_cast<sal_Int32>(rLRSpace.GetRight()));
3032  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_FI);
3033  m_aStyles.append(static_cast<sal_Int32>(rLRSpace.GetTextFirstLineOfst()));
3034  }
3035  }
3036  else if (m_rExport.GetRTFFlySyntax())
3037  {
3038  // Wrap: top and bottom spacing, convert from twips to EMUs.
3039  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3040  "dxWrapDistLeft", OString::number(rLRSpace.GetLeft() * 635)));
3041  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3042  "dxWrapDistRight", OString::number(rLRSpace.GetRight() * 635)));
3043  }
3044 }
3045 
3047 {
3048  if (!m_rExport.m_bOutFlyFrameAttrs)
3049  {
3050  if (m_rExport.m_bOutPageDescs)
3051  {
3052  OSL_ENSURE(m_rExport.GetCurItemSet(), "Impossible");
3053  if (!m_rExport.GetCurItemSet())
3054  return;
3055 
3056  // If we export a follow page format, then our doc model has
3057  // separate header/footer distances for the first page and the
3058  // follow pages, but Word can have only a single distance. In case
3059  // the two values differ, work with the value from the first page
3060  // format to be in sync with the import.
3061  sw::util::HdFtDistanceGlue aDistances(m_rExport.GetFirstPageItemSet()
3062  ? *m_rExport.GetFirstPageItemSet()
3063  : *m_rExport.GetCurItemSet());
3064 
3065  if (aDistances.dyaTop)
3066  {
3067  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_MARGTSXN);
3068  m_aSectionBreaks.append(static_cast<sal_Int32>(aDistances.dyaTop));
3069  }
3070  if (aDistances.HasHeader())
3071  {
3072  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_HEADERY);
3073  m_aSectionBreaks.append(static_cast<sal_Int32>(aDistances.dyaHdrTop));
3074  }
3075 
3076  if (aDistances.dyaBottom)
3077  {
3078  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_MARGBSXN);
3079  m_aSectionBreaks.append(static_cast<sal_Int32>(aDistances.dyaBottom));
3080  }
3081  if (aDistances.HasFooter())
3082  {
3083  m_aSectionBreaks.append(OOO_STRING_SVTOOLS_RTF_FOOTERY);
3084  m_aSectionBreaks.append(static_cast<sal_Int32>(aDistances.dyaHdrBottom));
3085  }
3086  if (!m_bBufferSectionBreaks)
3087  m_rExport.Strm().WriteCharPtr(m_aSectionBreaks.makeStringAndClear().getStr());
3088  }
3089  else
3090  {
3091  // Spacing before.
3092  if (m_bParaBeforeAutoSpacing && m_nParaBeforeSpacing == rULSpace.GetUpper())
3093  m_aStyles.append(LO_STRING_SVTOOLS_RTF_SBAUTO "1");
3094  else if (m_bParaBeforeAutoSpacing && m_nParaBeforeSpacing == -1)
3095  {
3096  m_aStyles.append(LO_STRING_SVTOOLS_RTF_SBAUTO "0");
3097  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SB);
3098  m_aStyles.append(static_cast<sal_Int32>(rULSpace.GetUpper()));
3099  }
3100  else
3101  {
3102  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SB);
3103  m_aStyles.append(static_cast<sal_Int32>(rULSpace.GetUpper()));
3104  }
3105  m_bParaBeforeAutoSpacing = false;
3106 
3107  // Spacing after.
3108  if (m_bParaAfterAutoSpacing && m_nParaAfterSpacing == rULSpace.GetLower())
3109  m_aStyles.append(LO_STRING_SVTOOLS_RTF_SAAUTO "1");
3110  else if (m_bParaAfterAutoSpacing && m_nParaAfterSpacing == -1)
3111  {
3112  m_aStyles.append(LO_STRING_SVTOOLS_RTF_SAAUTO "0");
3113  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SA);
3114  m_aStyles.append(static_cast<sal_Int32>(rULSpace.GetLower()));
3115  }
3116  else
3117  {
3118  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_SA);
3119  m_aStyles.append(static_cast<sal_Int32>(rULSpace.GetLower()));
3120  }
3121  m_bParaAfterAutoSpacing = false;
3122 
3123  // Contextual spacing.
3124  if (rULSpace.GetContext())
3125  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_CONTEXTUALSPACE);
3126  }
3127  }
3128  else if (m_rExport.GetRTFFlySyntax())
3129  {
3130  // Wrap: top and bottom spacing, convert from twips to EMUs.
3131  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3132  "dyWrapDistTop", OString::number(rULSpace.GetUpper() * 635)));
3133  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3134  "dyWrapDistBottom", OString::number(rULSpace.GetLower() * 635)));
3135  }
3136 }
3137 
3139 {
3140  if (m_rExport.m_bOutFlyFrameAttrs && !m_rExport.GetRTFFlySyntax())
3141  {
3142  css::text::WrapTextMode eSurround = rSurround.GetSurround();
3143  bool bGold = css::text::WrapTextMode_DYNAMIC == eSurround;
3144  if (bGold)
3145  eSurround = css::text::WrapTextMode_PARALLEL;
3146  RTFSurround aMC(bGold, static_cast<sal_uInt8>(eSurround));
3147  m_aRunText->append(OOO_STRING_SVTOOLS_RTF_FLYMAINCNT);
3148  m_aRunText->append(static_cast<sal_Int32>(aMC.GetValue()));
3149  }
3150  else if (m_rExport.m_bOutFlyFrameAttrs && m_rExport.GetRTFFlySyntax())
3151  {
3152  // See DocxSdrExport::startDMLAnchorInline() for SwFormatSurround -> WR / WRK mappings.
3153  sal_Int32 nWr = -1;
3155  switch (rSurround.GetValue())
3156  {
3157  case css::text::WrapTextMode_NONE:
3158  nWr = 1; // top and bottom
3159  break;
3160  case css::text::WrapTextMode_THROUGH:
3161  nWr = 3; // none
3162  break;
3163  case css::text::WrapTextMode_PARALLEL:
3164  nWr = 2; // around
3165  oWrk = 0; // both sides
3166  break;
3167  case css::text::WrapTextMode_DYNAMIC:
3168  default:
3169  nWr = 2; // around
3170  oWrk = 3; // largest
3171  break;
3172  }
3173 
3174  if (rSurround.IsContour())
3175  nWr = 4; // tight
3176 
3177  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPWR);
3178  m_rExport.OutLong(nWr);
3179  if (oWrk)
3180  {
3181  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPWRK);
3182  m_rExport.OutLong(*oWrk);
3183  }
3184  }
3185 }
3186 
3188 {
3189  if (m_rExport.m_bOutFlyFrameAttrs && m_rExport.GetRTFFlySyntax())
3190  {
3191  switch (rFlyVert.GetRelationOrient())
3192  {
3193  case text::RelOrientation::PAGE_FRAME:
3194  m_aFlyProperties.push_back(
3195  std::make_pair<OString, OString>("posrelv", OString::number(1)));
3196  break;
3197  default:
3198  m_aFlyProperties.push_back(
3199  std::make_pair<OString, OString>("posrelv", OString::number(2)));
3200  m_rExport.Strm()
3201  .WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPBYPARA)
3202  .WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPBYIGNORE);
3203  break;
3204  }
3205 
3206  switch (rFlyVert.GetVertOrient())
3207  {
3209  case text::VertOrientation::LINE_TOP:
3210  m_aFlyProperties.push_back(
3211  std::make_pair<OString, OString>("posv", OString::number(1)));
3212  break;
3214  case text::VertOrientation::LINE_BOTTOM:
3215  m_aFlyProperties.push_back(
3216  std::make_pair<OString, OString>("posv", OString::number(3)));
3217  break;
3218  case text::VertOrientation::CENTER:
3219  case text::VertOrientation::LINE_CENTER:
3220  m_aFlyProperties.push_back(
3221  std::make_pair<OString, OString>("posv", OString::number(2)));
3222  break;
3223  default:
3224  break;
3225  }
3226 
3227  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPTOP);
3228  m_rExport.OutLong(rFlyVert.GetPos());
3229  if (m_pFlyFrameSize)
3230  {
3231  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPBOTTOM);
3232  m_rExport.OutLong(rFlyVert.GetPos() + m_pFlyFrameSize->Height());
3233  }
3234  }
3235 }
3236 
3238 {
3239  if (m_rExport.m_bOutFlyFrameAttrs && m_rExport.GetRTFFlySyntax())
3240  {
3241  switch (rFlyHori.GetRelationOrient())
3242  {
3243  case text::RelOrientation::PAGE_FRAME:
3244  m_aFlyProperties.push_back(
3245  std::make_pair<OString, OString>("posrelh", OString::number(1)));
3246  break;
3247  default:
3248  m_aFlyProperties.push_back(
3249  std::make_pair<OString, OString>("posrelh", OString::number(2)));
3250  m_rExport.Strm()
3251  .WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPBXCOLUMN)
3252  .WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPBXIGNORE);
3253  break;
3254  }
3255 
3256  switch (rFlyHori.GetHoriOrient())
3257  {
3259  m_aFlyProperties.push_back(
3260  std::make_pair<OString, OString>("posh", OString::number(1)));
3261  break;
3262  case text::HoriOrientation::CENTER:
3263  m_aFlyProperties.push_back(
3264  std::make_pair<OString, OString>("posh", OString::number(2)));
3265  break;
3267  m_aFlyProperties.push_back(
3268  std::make_pair<OString, OString>("posh", OString::number(3)));
3269  break;
3270  default:
3271  break;
3272  }
3273 
3274  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPLEFT);
3275  m_rExport.OutLong(rFlyHori.GetPos());
3276  if (m_pFlyFrameSize)
3277  {
3278  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_SHPRIGHT);
3279  m_rExport.OutLong(rFlyHori.GetPos() + m_pFlyFrameSize->Width());
3280  }
3281  }
3282 }
3283 
3285 {
3286  if (!m_rExport.GetRTFFlySyntax())
3287  {
3288  RndStdIds eId = rAnchor.GetAnchorId();
3289  m_aRunText->append(OOO_STRING_SVTOOLS_RTF_FLYANCHOR);
3290  m_aRunText->append(static_cast<sal_Int32>(eId));
3291  switch (eId)
3292  {
3293  case RndStdIds::FLY_AT_PAGE:
3294  m_aRunText->append(OOO_STRING_SVTOOLS_RTF_FLYPAGE);
3295  m_aRunText->append(static_cast<sal_Int32>(rAnchor.GetPageNum()));
3296  break;
3297  case RndStdIds::FLY_AT_PARA:
3298  case RndStdIds::FLY_AS_CHAR:
3299  m_aRunText->append(OOO_STRING_SVTOOLS_RTF_FLYCNTNT);
3300  break;
3301  default:
3302  break;
3303  }
3304  }
3305 }
3306 
3308 {
3309  if (m_rExport.GetRTFFlySyntax())
3310  {
3311  const Color& rColor = rBrush.GetColor();
3312  // We in fact need RGB to BGR, but the transformation is symmetric.
3313  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3314  "fillColor", OString::number(wwUtility::RGBToBGR(rColor))));
3315  }
3316  else if (!rBrush.GetColor().GetTransparency())
3317  {
3318  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_CBPAT);
3319  m_aStyles.append(static_cast<sal_Int32>(m_rExport.GetColor(rBrush.GetColor())));
3320  }
3321 }
3322 
3324 {
3325  m_oFillStyle.reset(rFillStyle.GetValue());
3326 }
3327 
3329 {
3330  if (*m_oFillStyle == drawing::FillStyle_GRADIENT)
3331  {
3332  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3333  "fillType", OString::number(7))); // Shade using the fillAngle
3334 
3335  const XGradient& rGradient = rFillGradient.GetGradientValue();
3336  const Color& rStartColor = rGradient.GetStartColor();
3337  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3338  "fillBackColor", OString::number(wwUtility::RGBToBGR(rStartColor))));
3339 
3340  const Color& rEndColor = rGradient.GetEndColor();
3341  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3342  "fillColor", OString::number(wwUtility::RGBToBGR(rEndColor))));
3343 
3344  switch (rGradient.GetGradientStyle())
3345  {
3346  case css::awt::GradientStyle_LINEAR:
3347  break;
3348  case css::awt::GradientStyle_AXIAL:
3349  m_aFlyProperties.push_back(
3350  std::make_pair<OString, OString>("fillFocus", OString::number(50)));
3351  break;
3352  case css::awt::GradientStyle_RADIAL:
3353  break;
3354  case css::awt::GradientStyle_ELLIPTICAL:
3355  break;
3356  case css::awt::GradientStyle_SQUARE:
3357  break;
3358  case css::awt::GradientStyle_RECT:
3359  break;
3360  default:
3361  break;
3362  }
3363  }
3364 }
3365 
3367 {
3368  static const SvxBoxItemLine aBorders[] = { SvxBoxItemLine::TOP, SvxBoxItemLine::LEFT,
3369  SvxBoxItemLine::BOTTOM, SvxBoxItemLine::RIGHT };
3370  static const sal_Char* aBorderNames[]
3373 
3374  sal_uInt16 const nDist = rBox.GetSmallestDistance();
3375 
3376  if (m_rExport.GetRTFFlySyntax())
3377  {
3378  // Borders: spacing to contents, convert from twips to EMUs.
3379  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3380  "dxTextLeft", OString::number(rBox.GetDistance(SvxBoxItemLine::LEFT) * 635)));
3381  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3382  "dyTextTop", OString::number(rBox.GetDistance(SvxBoxItemLine::TOP) * 635)));
3383  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3384  "dxTextRight", OString::number(rBox.GetDistance(SvxBoxItemLine::RIGHT) * 635)));
3385  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3386  "dyTextBottom", OString::number(rBox.GetDistance(SvxBoxItemLine::BOTTOM) * 635)));
3387 
3388  const editeng::SvxBorderLine* pLeft = rBox.GetLine(SvxBoxItemLine::LEFT);
3389  const editeng::SvxBorderLine* pRight = rBox.GetLine(SvxBoxItemLine::RIGHT);
3390  const editeng::SvxBorderLine* pTop = rBox.GetLine(SvxBoxItemLine::TOP);
3391  const editeng::SvxBorderLine* pBottom = rBox.GetLine(SvxBoxItemLine::BOTTOM);
3392  if (pLeft && pRight && pTop && pBottom && *pLeft == *pRight && *pLeft == *pTop
3393  && *pLeft == *pBottom)
3394  {
3395  const Color& rColor = pTop->GetColor();
3396  // We in fact need RGB to BGR, but the transformation is symmetric.
3397  m_aFlyProperties.push_back(std::make_pair<OString, OString>(
3398  "lineColor", OString::number(wwUtility::RGBToBGR(rColor))));
3399 
3400  if (pTop->GetBorderLineStyle() != SvxBorderLineStyle::NONE)
3401  {
3402  double const fConverted(editeng::ConvertBorderWidthToWord(
3403  pTop->GetBorderLineStyle(), pTop->GetWidth()));
3404  sal_Int32 nWidth = fConverted * 635; // Twips -> EMUs
3405  m_aFlyProperties.push_back(
3406  std::make_pair<OString, OString>("lineWidth", OString::number(nWidth)));
3407  }
3408  else
3409  // No border: no line.
3410  m_aFlyProperties.push_back(std::make_pair<OString, OString>("fLine", "0"));
3411  }
3412 
3413  return;
3414  }
3415 
3416  if (rBox.GetTop() && rBox.GetBottom() && rBox.GetLeft() && rBox.GetRight()
3417  && *rBox.GetTop() == *rBox.GetBottom() && *rBox.GetTop() == *rBox.GetLeft()
3418  && *rBox.GetTop() == *rBox.GetRight() && nDist == rBox.GetDistance(SvxBoxItemLine::TOP)
3419  && nDist == rBox.GetDistance(SvxBoxItemLine::LEFT)
3420  && nDist == rBox.GetDistance(SvxBoxItemLine::BOTTOM)
3421  && nDist == rBox.GetDistance(SvxBoxItemLine::RIGHT))
3422  m_aSectionBreaks.append(
3423  OutBorderLine(m_rExport, rBox.GetTop(), OOO_STRING_SVTOOLS_RTF_BOX, nDist));
3424  else
3425  {
3426  SvxShadowLocation eShadowLocation = SvxShadowLocation::NONE;
3427  if (const SfxPoolItem* pItem = GetExport().HasItem(RES_SHADOW))
3428  eShadowLocation = static_cast<const SvxShadowItem*>(pItem)->GetLocation();
3429 
3430  const SvxBoxItemLine* pBrd = aBorders;
3431  const sal_Char** pBrdNms = aBorderNames;
3432  for (int i = 0; i < 4; ++i, ++pBrd, ++pBrdNms)
3433  {
3434  if (const editeng::SvxBorderLine* pLn = rBox.GetLine(*pBrd))
3435  {
3436  m_aSectionBreaks.append(OutBorderLine(m_rExport, pLn, *pBrdNms,
3437  rBox.GetDistance(*pBrd), eShadowLocation));
3438  }
3439  }
3440  }
3441 
3442  if (!m_bBufferSectionBreaks)
3443  m_aStyles.append(m_aSectionBreaks.makeStringAndClear());
3444 }
3445 
3446 void RtfAttributeOutput::FormatColumns_Impl(sal_uInt16 nCols, const SwFormatCol& rCol, bool bEven,
3447  SwTwips nPageSize)
3448 {
3449  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_COLS);
3450  m_rExport.OutLong(nCols);
3451 
3452  if (rCol.GetLineAdj() != COLADJ_NONE)
3453  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_LINEBETCOL);
3454 
3455  if (bEven)
3456  {
3457  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_COLSX);
3458  m_rExport.OutLong(rCol.GetGutterWidth(true));
3459  }
3460  else
3461  {
3462  const SwColumns& rColumns = rCol.GetColumns();
3463  for (sal_uInt16 n = 0; n < nCols;)
3464  {
3465  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_COLNO);
3466  m_rExport.OutLong(n + 1);
3467 
3468  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_COLW);
3469  m_rExport.OutLong(rCol.CalcPrtColWidth(n, nPageSize));
3470 
3471  if (++n != nCols)
3472  {
3473  m_rExport.Strm().WriteCharPtr(OOO_STRING_SVTOOLS_RTF_COLSR);
3474  m_rExport.OutLong(rColumns[n - 1].GetRight() + rColumns[n].GetLeft());
3475  }
3476  }
3477  }
3478 }
3479 
3481 {
3482  if (rItem.GetValue())
3483  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_KEEPN);
3484 }
3485 
3487 {
3488  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
3489 }
3490 
3492 {
3493  if (!rNumbering.IsCount())
3494  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_NOLINE);
3495 }
3496 
3498 {
3499  if (!m_rExport.m_bOutPageDescs)
3500  {
3501  SvxFrameDirection nDir = rDirection.GetValue();
3502  if (nDir == SvxFrameDirection::Environment)
3503  nDir = GetExport().GetDefaultFrameDirection();
3504 
3505  if (nDir == SvxFrameDirection::Horizontal_RL_TB)
3506  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_RTLPAR);
3507  else
3508  m_aStyles.append(OOO_STRING_SVTOOLS_RTF_LTRPAR);
3509  }
3510 }
3511 
3513 {
3514  const std::map<OUString, css::uno::Any>& rMap = rItem.GetGrabBag();
3515  for (const auto& rValue : rMap)
3516  {
3517  if (rValue.first == "ParaTopMarginBeforeAutoSpacing")
3518  {
3519  m_bParaBeforeAutoSpacing = true;
3520  rValue.second >>= m_nParaBeforeSpacing;
3521  m_nParaBeforeSpacing = convertMm100ToTwip(m_nParaBeforeSpacing);
3522  }
3523  else if (rValue.first == "ParaBottomMarginAfterAutoSpacing")
3524  {
3525  m_bParaAfterAutoSpacing = true;
3526  rValue.second >>= m_nParaAfterSpacing;
3527  m_nParaAfterSpacing = convertMm100ToTwip(m_nParaAfterSpacing);
3528  }
3529  }
3530 }
3531 
3533 
3535 
3537 {
3538  OUString sCmd; // for optional Parameters
3539  switch (pField->GetTyp()->Which())
3540  {
3541  //#i119803# Export user field for RTF filter
3542  case SwFieldIds::User:
3543  sCmd = pField->GetTyp()->GetName();
3544  m_rExport.OutputField(pField, ww::eNONE, sCmd);
3545  break;
3546  default:
3547  m_rExport.OutputField(pField, ww::eUNKNOWN, sCmd);
3548  break;
3549  }
3550 }
3551 
3552 void RtfAttributeOutput::RefField(const SwField& /*rField*/, const OUString& /*rRef*/)
3553 {
3554  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
3555 }
3556 
3558 {
3559  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
3560 }
3561 
3562 void RtfAttributeOutput::SetField(const SwField& /*rField*/, ww::eField /*eType*/,
3563  const OUString& /*rCmd*/)
3564 {
3565  SAL_INFO("sw.rtf", "TODO: " << OSL_THIS_FUNC);
3566 }
3567 
3569 {
3570  const SwPostItField& rPField = *static_cast<const SwPostItField*>(pField);
3571 
3572  OString aName = OUStringToOString(rPField.GetName(), RTL_TEXTENCODING_UTF8);
3573  auto it = m_rOpenedAnnotationMarksIds.find(aName);
3574  if (it != m_rOpenedAnnotationMarksIds.end())
3575  {
3576  // In case this field is inside annotation marks, we want to write the
3577  // annotation itself after the annotation mark is closed, not here.
3578  m_aPostitFields[it->second] = &rPField;
3579  return;
3580  }
3581 
3582  m_aRunText->append("{" OOO_STRING_SVTOOLS_RTF_IGNORE OOO_STRING_SVTOOLS_RTF_ATNID " ");
3583  m_aRunText->append(OUStringToOString(rPField.GetInitials(), m_rExport.GetCurrentEncoding()));
3584  m_aRunText->append("}");
3586  m_aRunText->append(OUStringToOString(rPField.GetPar1(), m_rExport.GetCurrentEncoding()));
3587  m_aRunText->append("}");
3588  m_aRunText->append(OOO_STRING_SVTOOLS_RTF_CHATN);
3589 
3591 
3592  if (m_nCurrentAnnotationMarkId != -1)
3593  {
3595  m_aRunText->append(m_nCurrentAnnotationMarkId);
3596  m_aRunText->append('}');
3597  }
3599  m_aRunText->append(static_cast<sal_Int32>(sw::ms::DateTime2DTTM(rPField.GetDateTime())));
3600  m_aRunText->append('}');
3601  if (const OutlinerParaObject* pObject = rPField.GetTextObject())
3602  m_rExport.SdrExporter().WriteOutliner(*pObject, TXT_ATN);
3603  m_aRunText->append('}');
3604 }
3605 
3607 {
3608  // this is handled in OutputFlyFrame_Impl()
3609  return true;
3610 }
3611 
3613 {
3614  m_aRunText->append("{" OOO_STRING_SVTOOLS_RTF_FIELD
3616  " MACROBUTTON None ");
3617  RunText(pField->GetPar1());
3618  m_aRunText->append("}}");
3619  return false; // do not expand
3620 }
3621 
3623  : m_rExport(rExport)
3624  , m_pPrevPageDesc(nullptr)
3625  , m_nStyleId(0)
3626  , m_nListId(0)
3627  , m_nNextAnnotationMarkId(0)
3628  , m_nCurrentAnnotationMarkId(-1)
3629  , m_bTableCellOpen(false)
3630  , m_nTableDepth(0)
3631  , m_bTableAfterCell(false)
3632  , m_nColBreakNeeded(false)
3633  , m_bBufferSectionBreaks(false)
3634  , m_bBufferSectionHeaders(false)
3635  , m_bLastTable(true)
3636  , m_bWroteCellInfo(false)
3637  , m_bTableRowEnded(false)
3638  , m_bIsBeforeFirstParagraph(true)
3639  , m_bSingleEmptyRun(false)
3640  , m_bInRun(false)
3641  , m_pFlyFrameSize(nullptr)
3642  , m_bParaBeforeAutoSpacing(false)
3643  , m_nParaBeforeSpacing(0)
3644  , m_bParaAfterAutoSpacing(false)
3645  , m_nParaAfterSpacing(0)
3646 {
3647 }
3648 
3650 
3652 
3653 // These are used by wwFont::WriteRtf()
3654 
3656 void RtfAttributeOutput::StartFont(const OUString& rFamilyName) const
3657 {
3658  // write the font name hex-encoded, but without Unicode - Word at least
3659  // cannot read *both* Unicode and fallback as written by OutString
3661  msfilter::rtfutil::OutString(rFamilyName, m_rExport.GetCurrentEncoding(), false).getStr());
3662 }
3663 
3666 {
3667  m_rExport.Strm().WriteCharPtr(";}");
3669 }
3670 
3672 void RtfAttributeOutput::FontAlternateName(const OUString& rName) const
3673 {
3674  m_rExport.Strm()
3675  .WriteChar('{')
3678  .WriteChar(' ');
3679  // write the font name hex-encoded, but without Unicode - Word at least
3680  // cannot read *both* Unicode and fallback as written by OutString
3681  m_rExport.Strm()
3682  .WriteCharPtr(
3683  msfilter::rtfutil::OutString(rName, m_rExport.GetCurrentEncoding(), false).getStr())
3684  .WriteChar('}');
3685 }
3686 
3689 {
3691  m_rExport.OutULong(nCharSet);
3692  m_rExport.Strm().WriteChar(' ');
3693  m_rExport.SetCurrentEncoding(rtl_getTextEncodingFromWindowsCharset(nCharSet));
3694 }
3695 
3697 void RtfAttributeOutput::FontFamilyType(FontFamily eFamily, const wwFont& rFont) const
3698 {
3700 
3701  const char* pStr = OOO_STRING_SVTOOLS_RTF_FNIL;
3702  switch (eFamily)
3703  {
3704  case FAMILY_ROMAN:
3706  break;
3707  case FAMILY_SWISS:
3709  break;
3710  case FAMILY_MODERN:
3712  break;
3713  case FAMILY_SCRIPT:
3715  break;
3716  case FAMILY_DECORATIVE:
3718  break;
3719  default:
3720  break;
3721  }
3722  m_rExport.OutULong(m_rExport.m_aFontHelper.GetId(rFont)).WriteCharPtr(pStr);
3723 }
3724 
3727 {
3729 
3730  sal_uInt16 nVal = 0;
3731  switch (ePitch)
3732  {
3733  case PITCH_FIXED:
3734  nVal = 1;
3735  break;
3736  case PITCH_VARIABLE:
3737  nVal = 2;
3738  break;
3739  default:
3740  break;
3741  }
3742  m_rExport.OutULong(nVal);
3743 }
3744 
3745 static void lcl_AppendSP(OStringBuffer& rBuffer, const char cName[], const OUString& rValue,
3746  const RtfExport& rExport)
3747 {
3748  rBuffer.append("{" OOO_STRING_SVTOOLS_RTF_SP "{"); // "{\sp{"
3749  rBuffer.append(OOO_STRING_SVTOOLS_RTF_SN " "); //" \sn "
3750  rBuffer.append(cName); //"PropName"
3751  rBuffer.append("}{" OOO_STRING_SVTOOLS_RTF_SV " ");
3752  // "}{ \sv "
3753  rBuffer.append(msfilter::rtfutil::OutString(rValue, rExport.GetCurrentEncoding()));
3754  rBuffer.append("}}");
3755 }
3756 
3757 static OString ExportPICT(const SwFlyFrameFormat* pFlyFrameFormat, const Size& rOrig,
3758  const Size& rRendered, const Size& rMapped, const SwCropGrf& rCr,
3759  const char* pBLIPType, const sal_uInt8* pGraphicAry, sal_uInt64 nSize,
3760  const RtfExport& rExport, SvStream* pStream = nullptr,
3761  bool bWritePicProp = true, const SwAttrSet* pAttrSet = nullptr)
3762 {
3763  OStringBuffer aRet;
3764  if (pBLIPType && nSize && pGraphicAry)
3765  {
3766  bool bIsWMF = std::strcmp(pBLIPType, OOO_STRING_SVTOOLS_RTF_WMETAFILE) == 0;
3767 
3768  aRet.append("{" OOO_STRING_SVTOOLS_RTF_PICT);
3769 
3770  if (pFlyFrameFormat && bWritePicProp)
3771  {
3772  OUString sDescription = pFlyFrameFormat->GetObjDescription();
3773  //write picture properties - wzDescription at first
3774  //looks like: "{\*\picprop{\sp{\sn PropertyName}{\sv PropertyValue}}}"
3775  aRet.append(
3777  lcl_AppendSP(aRet, "wzDescription", sDescription, rExport);
3778  OUString sName = pFlyFrameFormat->GetObjTitle();
3779  lcl_AppendSP(aRet, "wzName", sName, rExport);
3780 
3781  if (pAttrSet)
3782  {
3783  MirrorGraph eMirror = pAttrSet->Get(RES_GRFATR_MIRRORGRF).GetValue();
3784  if (eMirror == MirrorGraph::Vertical || eMirror == MirrorGraph::Both)
3785  // Mirror on the vertical axis is a horizontal flip.
3786  lcl_AppendSP(aRet, "fFlipH", "1", rExport);
3787  }
3788 
3789  aRet.append("}"); //"}"
3790  }
3791 
3792  long nXCroppedSize = rOrig.Width() - (rCr.GetLeft() + rCr.GetRight());
3793  long nYCroppedSize = rOrig.Height() - (rCr.GetTop() + rCr.GetBottom());
3794  /* Graphic with a zero height or width, typically copied from webpages, caused crashes. */
3795  if (!nXCroppedSize)
3796  nXCroppedSize = 100;
3797  if (!nYCroppedSize)
3798  nYCroppedSize = 100;
3799 
3800  //Given the original size and taking cropping into account
3801  //first, how much has the original been scaled to get the
3802  //final rendered size
3803  aRet.append(OOO_STRING_SVTOOLS_RTF_PICSCALEX);
3804  aRet.append(static_cast<sal_Int32>((100 * rRendered.Width()) / nXCroppedSize));
3805  aRet.append(OOO_STRING_SVTOOLS_RTF_PICSCALEY);
3806  aRet.append(static_cast<sal_Int32>((100 * rRendered.Height()) / nYCroppedSize));
3807 
3808  aRet.append(OOO_STRING_SVTOOLS_RTF_PICCROPL);
3809  aRet.append(rCr.GetLeft());
3810  aRet.append(OOO_STRING_SVTOOLS_RTF_PICCROPR);
3811  aRet.append(rCr.GetRight());
3812  aRet.append(OOO_STRING_SVTOOLS_RTF_PICCROPT);
3813  aRet.append(rCr.GetTop());
3814  aRet.append(OOO_STRING_SVTOOLS_RTF_PICCROPB);
3815  aRet.append(rCr.GetBottom());
3816 
3817  aRet.append(OOO_STRING_SVTOOLS_RTF_PICW);
3818  aRet.append(static_cast<sal_Int32>(rMapped.Width()));
3819  aRet.append(OOO_STRING_SVTOOLS_RTF_PICH);
3820  aRet.append(static_cast<sal_Int32>(rMapped.Height()));
3821 
3822  aRet.append(OOO_STRING_SVTOOLS_RTF_PICWGOAL);
3823  aRet.append(static_cast<sal_Int32>(rOrig.Width()));
3824  aRet.append(OOO_STRING_SVTOOLS_RTF_PICHGOAL);
3825  aRet.append(static_cast<sal_Int32>(rOrig.Height()));
3826 
3827  aRet.append(pBLIPType);
3828  if (bIsWMF)
3829  {
3830  aRet.append(sal_Int32(8));
3831  msfilter::rtfutil::StripMetafileHeader(pGraphicAry, nSize);
3832  }
3833  aRet.append(SAL_NEWLINE_STRING);
3834  if (pStream)
3835  pStream->WriteCharPtr(aRet.makeStringAndClear().getStr());
3836  if (pStream)
3837  msfilter::rtfutil::WriteHex(pGraphicAry, nSize, pStream);
3838  else
3839  aRet.append(msfilter::rtfutil::WriteHex(pGraphicAry, nSize));
3840  aRet.append('}');
3841  if (pStream)
3842  pStream->WriteCharPtr(aRet.makeStringAndClear().getStr());
3843  }
3844  return aRet.makeStringAndClear();
3845 }
3846 
3848  SwOLENode& rOLENode, const Size& rSize)
3849 {
3851  Size aSize(rOLENode.GetTwipSize());
3852  Size aRendered(aSize);
3853  aRendered.setWidth(rSize.Width());
3854  aRendered.setHeight(rSize.Height());
3855  const Graphic* pGraphic = rOLENode.GetGraphic();
3856  Size aMapped(pGraphic->GetPrefSize());
3857  auto& rCr = static_cast<const SwCropGrf&>(rOLENode.GetAttr(RES_GRFATR_CROPGRF));
3858  const sal_Char* pBLIPType = OOO_STRING_SVTOOLS_RTF_PNGBLIP;
3859  const sal_uInt8* pGraphicAry = nullptr;
3860  SvMemoryStream aStream;
3861  if (GraphicConverter::Export(aStream, *pGraphic, ConvertDataFormat::PNG) != ERRCODE_NONE)
3862  SAL_WARN("sw.rtf", "failed to export the graphic");
3863  sal_uInt32 nSize = aStream.TellEnd();
3864  pGraphicAry = static_cast<sal_uInt8 const*>(aStream.GetData());
3865  m_aRunText->append(ExportPICT(pFlyFrameFormat, aSize, aRendered, aMapped, rCr, pBLIPType,
3866  pGraphicAry, nSize, m_rExport));
3867  m_aRunText->append("}"); // shppict
3870  SvMemoryStream aWmfStream;
3871  if (GraphicConverter::Export(aWmfStream, *pGraphic, ConvertDataFormat::WMF) != ERRCODE_NONE)
3872  SAL_WARN("sw.rtf", "failed to export the graphic");
3873  nSize = aWmfStream.TellEnd();
3874  pGraphicAry = static_cast<sal_uInt8 const*>(aWmfStream.GetData());
3875  m_aRunText->append(ExportPICT(pFlyFrameFormat, aSize, aRendered, aMapped, rCr, pBLIPType,
3876  pGraphicAry, nSize, m_rExport));
3877  m_aRunText->append("}"); // nonshppict
3878 }
3879 
3881  SwOLENode& rOLENode, const Size& rSize)
3882 {
3883  uno::Reference<embed::XEmbeddedObject> xObj(rOLENode.GetOLEObj().GetOleRef());
3884  sal_Int64 nAspect = rOLENode.GetAspect();
3885  svt::EmbeddedObjectRef aObjRef(xObj, nAspect);
3886  SvGlobalName aObjName(aObjRef->getClassID());
3887 
3888  if (!SotExchange::IsMath(aObjName))
3889  return false;
3890 
3892  uno::Reference<util::XCloseable> xClosable(xObj->getComponent(), uno::UNO_QUERY);
3893  if (!xClosable.is())
3894  return false;
3895  // gcc4.4 (and 4.3 and possibly older) have a problem with dynamic_cast directly to the target class,
3896  // so help it with an intermediate cast. I'm not sure what exactly the problem is, seems to be unrelated
3897  // to RTLD_GLOBAL, so most probably a gcc bug.
3898  auto pBase
3899  = dynamic_cast<oox::FormulaExportBase*>(dynamic_cast<SfxBaseModel*>(xClosable.get()));
3900  assert(pBase != nullptr);
3901  OStringBuffer aBuf;
3902  if (pBase)
3903  pBase->writeFormulaRtf(aBuf, m_rExport.GetCurrentEncoding());
3904  m_aRunText->append(aBuf.makeStringAndClear());
3905  // Replacement graphic.
3907  FlyFrameOLEReplacement(pFlyFrameFormat, rOLENode, rSize);
3908  m_aRunText->append("}"); // mmathPict
3909  m_aRunText->append("}"); // mmath
3910 
3911  return true;
3912 }
3913 
3914 void RtfAttributeOutput::FlyFrameOLE(const SwFlyFrameFormat* pFlyFrameFormat, SwOLENode& rOLENode,
3915  const Size& rSize)
3916 {
3917  if (FlyFrameOLEMath(pFlyFrameFormat, rOLENode, rSize))
3918  return;
3919 
3920  FlyFrameOLEReplacement(pFlyFrameFormat, rOLENode, rSize);
3921 }
3922 
3924  const SwGrfNode* pGrfNode)
3925 {
3926  SvMemoryStream aStream;
3927  const sal_uInt8* pGraphicAry = nullptr;
3928  sal_uInt32 nSize = 0;
3929 
3930  const Graphic& rGraphic(pGrfNode->GetGrf());
3931 
3932  // If there is no graphic there is not much point in parsing it
3933  if (rGraphic.GetType() == GraphicType::NONE)
3934  return;
3935 
3936  ConvertDataFormat aConvertDestinationFormat = ConvertDataFormat::WMF;
3937  const sal_Char* pConvertDestinationBLIPType = OOO_STRING_SVTOOLS_RTF_WMETAFILE;
3938 
3939  GfxLink aGraphicLink;
3940  const sal_Char* pBLIPType = nullptr;
3941  if (rGraphic.IsGfxLink())
3942  {
3943  aGraphicLink = rGraphic.GetGfxLink();
3944  nSize = aGraphicLink.GetDataSize();
3945  pGraphicAry = aGraphicLink.GetData();
3946  switch (aGraphicLink.GetType())
3947  {
3948  // #i15508# trying to add BMP type for better exports, need to check if this works
3949  // checked, does not work. Also need to reset pGraphicAry to NULL to force conversion
3950  // to PNG, else the BMP array will be used.
3951  // It may work using direct DIB data, but that needs to be checked eventually
3952  //
3953  // #i15508# before GfxLinkType::NativeBmp was added the graphic data
3954  // (to be hold in pGraphicAry) was not available; thus for now to stay
3955  // compatible, keep it that way by assigning NULL value to pGraphicAry
3956  case GfxLinkType::NativeBmp:
3957  // pBLIPType = OOO_STRING_SVTOOLS_RTF_WBITMAP;
3958  pGraphicAry = nullptr;
3959  break;
3960 
3961  case GfxLinkType::NativeJpg:
3962  pBLIPType = OOO_STRING_SVTOOLS_RTF_JPEGBLIP;
3963  break;
3964  case GfxLinkType::NativePng:
3965  pBLIPType = OOO_STRING_SVTOOLS_RTF_PNGBLIP;
3966  break;
3967  case GfxLinkType::NativeWmf:
3968  pBLIPType = aGraphicLink.IsEMF() ? OOO_STRING_SVTOOLS_RTF_EMFBLIP
3970  break;
3971  case GfxLinkType::NativeGif:
3972  // GIF is not supported by RTF, but we override default conversion to WMF, PNG seems fits better here.
3973  aConvertDestinationFormat = ConvertDataFormat::PNG;
3974  pConvertDestinationBLIPType = OOO_STRING_SVTOOLS_RTF_PNGBLIP;
3975  break;
3976  default:
3977  break;
3978  }
3979  }
3980 
3981  GraphicType eGraphicType = rGraphic.GetType();
3982  if (!pGraphicAry)
3983  {
3984  if (ERRCODE_NONE
3985  == GraphicConverter::Export(aStream, rGraphic,
3986  (eGraphicType == GraphicType::Bitmap)
3987  ? ConvertDataFormat::PNG
3988  : ConvertDataFormat::WMF))
3989  {
3990  pBLIPType = (eGraphicType == GraphicType::Bitmap) ? OOO_STRING_SVTOOLS_RTF_PNGBLIP
3992  nSize = aStream.TellEnd();
3993  pGraphicAry = static_cast<sal_uInt8 const*>(aStream.GetData());
3994  }
3995  }
3996 
3997  Size aMapped(eGraphicType == GraphicType::Bitmap ? rGraphic.GetSizePixel()
3998  : rGraphic.GetPrefSize());
3999 
4000  auto& rCr = static_cast<const SwCropGrf&>(pGrfNode->GetAttr(RES_GRFATR_CROPGRF));
4001 
4002  //Get original size in twips
4003  Size aSize(pGrfNode->GetTwipSize());
4004  Size aRendered(aSize);
4005 
4006  const SwFormatFrameSize& rS = pFlyFrameFormat->GetFrameSize();
4007  aRendered.setWidth(rS.GetWidth());
4008  aRendered.setHeight(rS.GetHeight());
4009 
4010  ww8::Frame* pFrame = nullptr;
4011  for (auto& rFrame : m_rExport.m_aFrames)
4012  {
4013  if (pFlyFrameFormat == &rFrame.GetFrameFormat())
4014  {
4015  pFrame = &rFrame;
4016  break;
4017  }
4018  }
4019 
4020  /*
4021  If the graphic is not of type WMF then we will have to store two
4022  graphics, one in the native format wrapped in shppict, and the other in
4023  the wmf format wrapped in nonshppict, so as to keep wordpad happy. If its
4024  a wmf already then we don't need any such wrapping
4025  */
4026  bool bIsWMF = pBLIPType && std::strcmp(pBLIPType, OOO_STRING_SVTOOLS_RTF_WMETAFILE) == 0;
4027  const SwAttrSet* pAttrSet = pGrfNode->GetpSwAttrSet();
4028  if (!pFrame || pFrame->IsInline())
4029  {
4030  if (!bIsWMF)
4033  }
4034  else
4035  {
4039  m_pFlyFrameSize = &aRendered;
4040  m_rExport.m_pParentFrame = pFrame;
4042  m_rExport.SetRTFFlySyntax(true);
4043  m_rExport.OutputFormat(pFrame->GetFrameFormat(), false, false, true);
4045  m_rExport.SetRTFFlySyntax(false);
4046  m_rExport.m_pParentFrame = nullptr;
4047  m_pFlyFrameSize = nullptr;
4048 
4049  std::vector<std::pair<OString, OString>> aFlyProperties;
4050  aFlyProperties.push_back(std::make_pair<OString, OString>(
4051  "shapeType", OString::number(ESCHER_ShpInst_PictureFrame)));
4052  aFlyProperties.push_back(std::make_pair<OString, OString>(
4053  "wzDescription", msfilter::rtfutil::OutString(pFlyFrameFormat->GetObjDescription(),
4055  aFlyProperties.push_back(std::make_pair<OString, OString>(
4056  "wzName", msfilter::rtfutil::OutString(pFlyFrameFormat->GetObjTitle(),
4058 
4059  // If we have a wrap polygon, then handle that here.
4060  if (pFlyFrameFormat->GetSurround().IsContour())
4061  {
4062  if (const SwNoTextNode* pNd
4063  = sw::util::GetNoTextNodeFromSwFrameFormat(*pFlyFrameFormat))
4064  {
4065  const tools::PolyPolygon* pPolyPoly = pNd->HasContour();
4066  if (pPolyPoly && pPolyPoly->Count())
4067  {
4068  tools::Polygon aPoly
4069  = sw::util::CorrectWordWrapPolygonForExport(*pPolyPoly, pNd);
4070  OStringBuffer aVerticies;
4071  for (sal_uInt16 i = 0; i < aPoly.GetSize(); ++i)
4072  aVerticies.append(";(")
4073  .append(aPoly[i].X())
4074  .append(",")
4075  .append(aPoly[i].Y())
4076  .append(")");
4077  aFlyProperties.push_back(std::make_pair<OString, OString>(
4078  "pWrapPolygonVertices",
4079  "8;" + OString::number(aPoly.GetSize()) + aVerticies.makeStringAndClear()));
4080  }
4081  }
4082  }
4083 
4084  // Below text, behind document, opaque: they all refer to the same thing.
4085  if (!pFlyFrameFormat->GetOpaque().GetValue())
4086  aFlyProperties.push_back(std::make_pair<OString, OString>("fBehindDocument", "1"));
4087 
4088  if (pAttrSet)
4089  {
4090  if (sal_Int32 nRot = pAttrSet->Get(RES_GRFATR_ROTATION).GetValue())
4091  {
4092  // See writerfilter::rtftok::RTFSdrImport::applyProperty(),
4093  // positive rotation angles are clockwise in RTF, we have them
4094  // as counter-clockwise.
4095  // Additionally, RTF type is 0..360*2^16, our is 0..360*10.
4096  nRot = nRot * -1 * RTF_MULTIPLIER / 10;
4097  aFlyProperties.emplace_back("rotation", OString::number(nRot));
4098  }
4099  }
4100 
4101  for (std::pair<OString, OString>& rPair : aFlyProperties)
4102  {
4105  m_rExport.Strm().WriteCharPtr(rPair.first.getStr());
4107  m_rExport.Strm().WriteCharPtr(rPair.second.getStr());
4108  m_rExport.Strm().WriteCharPtr("}}");
4109  }
4111  " pib"
4112  "}{" OOO_STRING_SVTOOLS_RTF_SV " ");
4113  }
4114 
4115  bool bWritePicProp = !pFrame || pFrame->IsInline();
4116  if (pBLIPType)
4117  ExportPICT(pFlyFrameFormat, aSize, aRendered, aMapped, rCr, pBLIPType, pGraphicAry, nSize,
4118  m_rExport, &m_rExport.Strm(), bWritePicProp, pAttrSet);
4119  else
4120  {
4121  aStream.Seek(0);
4122  if (GraphicConverter::Export(aStream, rGraphic, aConvertDestinationFormat) != ERRCODE_NONE)
4123  SAL_WARN("sw.rtf", "failed to export the graphic");
4124  pBLIPType = pConvertDestinationBLIPType;
4125  nSize = aStream.TellEnd();
4126  pGraphicAry = static_cast<sal_uInt8 const*>(aStream.GetData());
4127 
4128  ExportPICT(pFlyFrameFormat, aSize, aRendered, aMapped, rCr, pBLIPType, pGraphicAry, nSize,
4129  m_rExport, &m_rExport.Strm(), bWritePicProp, pAttrSet);
4130  }
4131 
4132  if (!pFrame || pFrame->IsInline())
4133  {
4134  if (!bIsWMF)
4135  {
4138 
4139  aStream.Seek(0);
4140  if (GraphicConverter::Export(aStream, rGraphic, ConvertDataFormat::WMF) != ERRCODE_NONE)
4141  SAL_WARN("sw.rtf", "failed to export the graphic");
4143  nSize = aStream.TellEnd();
4144  pGraphicAry = static_cast<sal_uInt8 const*>(aStream.GetData());
4145 
4146  ExportPICT(pFlyFrameFormat, aSize, aRendered, aMapped, rCr, pBLIPType, pGraphicAry,
4147  nSize, m_rExport, &m_rExport.Strm());
4148 
4149  m_rExport.Strm().WriteChar('}');
4150  }
4151  }
4152  else
4153  m_rExport.Strm().WriteCharPtr("}}}}"); // Close SV, SP, SHPINST and SHP.
4154 
4156 }
4157 
4158 void RtfAttributeOutput::BulletDefinition(int /*nId*/, const Graphic& rGraphic, Size aSize)
4159 {
4162 
4164  m_rExport.OutULong(aSize.Width());
4166  m_rExport.OutULong(aSize.Height());
4167 
4169  const sal_uInt8* pGraphicAry = nullptr;
4170  SvMemoryStream aStream;
4171  if (GraphicConverter::Export(aStream, rGraphic, ConvertDataFormat::PNG) != ERRCODE_NONE)
4172  SAL_WARN("sw.rtf", "failed to export the numbering picture bullet");
4173  sal_uInt32 nSize = aStream.TellEnd();
4174  pGraphicAry = static_cast<sal_uInt8 const*>(aStream.GetData());
4175  msfilter::rtfutil::WriteHex(pGraphicAry, nSize, &m_rExport.Strm());
4176  m_rExport.Strm().WriteCharPtr("}}"); // pict, shppict
4177 }
4178 
4179 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
#define OOO_STRING_SVTOOLS_RTF_SNEXT
#define OOO_STRING_SVTOOLS_RTF_ULW
sal_uInt16 Count() const
long GetLeft() const
void FormatBackground(const SvxBrushItem &rBrush) override
Sfx item RES_BACKGROUND.
void FormatTextGrid(const SwTextGridItem &rItem) override
Sfx item RES_TEXTGRID.
bool GetValue() const
long Width() const
bool IsContour() const
Definition: fmtsrnd.hxx:53
SvStream & OutULong(sal_uLong nVal)
Definition: rtfexport.cxx:1087
void CharFontCTL(const SvxFontItem &rFont) override
Sfx item RES_CHRATR_CTL_FONT.
#define OOO_STRING_SVTOOLS_RTF_QL
void StartRun(const SwRedlineData *pRedlineData, sal_Int32 nPos, bool bSingleEmptyRun=false) override
Start of the text run.
Wrapper around OStringBuffers, so less hexdump of graphics have to be kept in memory during RTF expor...
bool EndURL(bool isAtEndOfParagraph) override
Output URL end.
void TableHeight(ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner) override
#define OOO_STRING_SVTOOLS_RTF_CONTEXTUALSPACE
#define OOO_STRING_SVTOOLS_RTF_LTRSECT
#define OOO_STRING_SVTOOLS_RTF_ACCCOMMA
SVX_NUM_CHARS_UPPER_LETTER_N
void CharGrabBag(const SfxGrabBagItem &rItem) override
Sfx item RES_CHRATR_GRABBAG.
void Redline(const SwRedlineData *pRedline) override
Output redlining.
SwNoTextNode * GetNoTextNodeFromSwFrameFormat(const SwFrameFormat &rFormat)
Get the SwNoTextNode associated with a SwFrameFormat if here is one.
sal_Int64 GetAspect() const
Definition: ndole.hxx:132
void TableSpacing(ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner) override
#define OOO_STRING_SVTOOLS_RTF_WIDCTLPAR
#define OOO_STRING_SVTOOLS_RTF_SHPRIGHT
void TextINetFormat(const SwFormatINetFormat &rURL) override
Sfx item RES_TXTATR_INETFMT.
OStringBuffer & StylesEnd()
SwCharFormat * GetCharFormat()
Definition: txtatr2.cxx:113
void FormatULSpace(const SvxULSpaceItem &rULSpace) override
Sfx item RES_UL_SPACE.
void FormatColumns_Impl(sal_uInt16 nCols, const SwFormatCol &rCol, bool bEven, SwTwips nPageSize) override
Sfx item RES_COL.
#define OOO_STRING_SVTOOLS_RTF_QR
#define OOO_STRING_SVTOOLS_RTF_ANIMTEXT
#define OOO_STRING_SVTOOLS_RTF_ULTHDASHD
sal_uInt16 GetRowSpan() const
Definition: wrtswtbl.hxx:78
#define OOO_STRING_SVTOOLS_RTF_ALANG
#define OOO_STRING_SVTOOLS_RTF_BRDRINSET
#define OOO_STRING_SVTOOLS_RTF_COLNO
sal_uInt16 Count() const
sal_Int32 GetLeft() const
std::vector< SwColumn > SwColumns
Definition: fmtclds.hxx:57
void FormatKeep(const SvxFormatKeepItem &rItem) override
Sfx item RES_KEEP.
#define OOO_STRING_SVTOOLS_RTF_FSWISS
#define RES_CHRATR_CJK_LANGUAGE
Definition: hintids.hxx:92
FAMILY_SCRIPT
void EndRuby(const SwTextNode &rNode, sal_Int32 nPos) override
Output ruby end.
#define OOO_STRING_SVTOOLS_RTF_SN
void FieldVanish(const OUString &rText, ww::eField eType) override
OUString GetObjDescription() const
Definition: atrfrm.cxx:3138
void CharKerning(const SvxKerningItem &rKerning) override
Sfx item RES_CHRATR_KERNING.
#define OOO_STRING_SVTOOLS_RTF_ULHWAVE
sal_uInt16 GetLower() const
SvxAdjust GetAdjust() const
#define OOO_STRING_SVTOOLS_RTF_PNGBLIP
sal_Char GetDirective()
#define RES_CHRATR_FONTSIZE
Definition: hintids.hxx:76
SwOLENode * GetOLENode()
Inline methods from Node.hxx.
Definition: ndole.hxx:157
void ParaSnapToGrid(const SvxParaGridItem &rItem) override
Sfx item RES_PARATR_SNAPTOGRID.
#define OOO_STRING_SVTOOLS_RTF_CLVMGF
void CharBidiRTL(const SfxPoolItem &rItem) override
Sfx item RES_CHRATR_BidiRTL.
void WriteBookmarks_Impl(std::vector< OUString > &rStarts, std::vector< OUString > &rEnds)
bool GetValue() const
#define RES_CHRATR_LANGUAGE
Definition: hintids.hxx:78
const SwOLEObj & GetOLEObj() const
Definition: ndole.hxx:110
double ConvertBorderWidthToWord(SvxBorderLineStyle, double)
void EndRun(const SwTextNode *pNode, sal_Int32 nPos, bool bLastRun=false) override
End of the text run.
#define OOO_STRING_SVTOOLS_RTF_SUB
void StartTableRow(const ww8::WW8TableNodeInfoInner::Pointer_t &pTableTextNodeInfoInner)
FAMILY_MODERN
#define OOO_STRING_SVTOOLS_RTF_EXPNDTW
RtfAttributeOutput(RtfExport &rExport)
#define OOO_STRING_SVTOOLS_RTF_FTNALT
#define OOO_STRING_SVTOOLS_RTF_BRDRENGRAVE
SVX_NUM_FULL_WIDTH_ARABIC
sal_Unicode GetStartBracket() const
std::string GetValue
#define OOO_STRING_SVTOOLS_RTF_FMODERN
rtl_TextEncoding GetCurrentEncoding() const
Definition: rtfexport.hxx:176
void CharBackground(const SvxBrushItem &rBrush) override
Sfx item RES_CHRATR_BACKGROUND.
short GetTextFirstLineOfst() const
#define OOO_STRING_SVTOOLS_RTF_SBASEDON
void FormatVertOrientation(const SwFormatVertOrient &rFlyVert) override
Sfx item RES_VERT_ORIENT.
#define OOO_STRING_SVTOOLS_RTF_ULDASH
sal_uInt16 GetCountBy() const
Definition: lineinfo.hxx:75
long Height() const
#define OOO_STRING_SVTOOLS_RTF_S
void PostitField(const SwField *pField) override
#define OOO_STRING_SVTOOLS_RTF_CLBRDRR
const SwNumFormat * GetNumFormat(sal_uInt16 i) const
Definition: number.cxx:93
#define OOO_STRING_SVTOOLS_RTF_SLMULT
#define OOO_STRING_SVTOOLS_RTF_LI
#define OOO_STRING_SVTOOLS_RTF_PICCROPT
#define OOO_STRING_SVTOOLS_RTF_LEVELFOLLOW
long GetWidth() const
std::size_t GetAuthor() const
Definition: redline.hxx:145
#define OOO_STRING_SVTOOLS_RTF_FOOTNOTE
#define OOO_STRING_SVTOOLS_RTF_FROMAN
#define RES_SHADOW
Definition: hintids.hxx:212
#define RES_CHRATR_WORDLINEMODE
Definition: hintids.hxx:84
#define OOO_STRING_SVTOOLS_RTF_FFTYPE
LINESTYLE_BOLD
#define OOO_STRING_SVTOOLS_RTF_TLUL
#define OOO_STRING_SVTOOLS_RTF_FOOTERY
SVX_NUM_NUMBER_NONE
sal_uInt16 GetPageNum() const
Definition: fmtanchr.hxx:66
#define OOO_STRING_SVTOOLS_RTF_FFOWNSTAT
#define OOO_STRING_SVTOOLS_RTF_TQDEC
sal_uInt8 GetTransparency() const
sal_uInt8 TransColToIco(const Color &rCol)
#define OOO_STRING_SVTOOLS_RTF_ULDASHD
static OString OutBorderLine(RtfExport const &rExport, const editeng::SvxBorderLine *pLine, const sal_Char *pStr, sal_uInt16 nDist, SvxShadowLocation eShadowLocation=SvxShadowLocation::NONE)
SwTwips GetPos() const
Definition: fmtornt.hxx:92
sal_uIntPtr sal_uLong
void CharHighlight(const SvxBrushItem &rBrush) override
Sfx item RES_CHRATR_HIGHLIGHT.
void FormatDrop(const SwTextNode &rNode, const SwFormatDrop &rSwFormatDrop, sal_uInt16 nStyle, ww8::WW8TableNodeInfo::Pointer_t pTextNodeInfo, ww8::WW8TableNodeInfoInner::Pointer_t pTextNodeInfoInner) override
#define OOO_STRING_SVTOOLS_RTF_CLPADFR
sal_uInt8 & GetProportionalHeight()
#define OOO_STRING_SVTOOLS_RTF_TRPADDB
#define OOO_STRING_SVTOOLS_RTF_ASPALPHA
#define OOO_STRING_SVTOOLS_RTF_NESTTABLEPROPRS
bool FlyFrameOLEMath(const SwFlyFrameFormat *pFlyFrameFormat, SwOLENode &rOLENode, const Size &rSize)
Math export.
FontEmphasisMark
#define OOO_STRING_SVTOOLS_RTF_ULTHLDASH
#define OOO_STRING_SVTOOLS_RTF_UP
Base class of all fields.
Definition: fldbas.hxx:279
const SwPageDesc * FindPageDesc(size_t *pPgDescNdIdx=nullptr) const
Search PageDesc with which this node is formatted.
Definition: node.cxx:466
#define OOO_STRING_SVTOOLS_RTF_PICCROPL
#define OOO_STRING_SVTOOLS_RTF_RIN
void ParaHangingPunctuation(const SfxBoolItem &rItem) override
Sfx item RES_PARATR_HANGINGPUNCTUATION.
SVX_NUM_CHARS_UPPER_LETTER
#define LO_STRING_SVTOOLS_RTF_LEVELPICTURE
css::uno::Reference< css::embed::XEmbeddedObject > const & GetOleRef()
Definition: ndole.cxx:900
#define OOO_STRING_SVTOOLS_RTF_FORMFIELD
SvStream & Strm()
Definition: rtfexport.cxx:1065
static OString OutTBLBorderLine(RtfExport const &rExport, const editeng::SvxBorderLine *pLine, const sal_Char *pStr)
GraphicType
#define OOO_STRING_SVTOOLS_RTF_AF
#define OOO_STRING_SVTOOLS_RTF_FFNAME
#define OOO_STRING_SVTOOLS_RTF_LISTLEVEL
void ParaNumRule_Impl(const SwTextNode *pTextNd, sal_Int32 nLvl, sal_Int32 nNumId) override
Sfx item RES_PARATR_NUMRULE.
#define OOO_STRING_SVTOOLS_RTF_ATNREF
#define OOO_STRING_SVTOOLS_RTF_SHPBXCOLUMN
SVX_NUM_CIRCLE_NUMBER
#define OOO_STRING_SVTOOLS_RTF_SL
void ParaSplit(const SvxFormatSplitItem &rSplit) override
Sfx item RES_PARATR_SPLIT.
void StartFont(const OUString &rFamilyName) const
Start the font.
aBuf
void CharFontCJK(const SvxFontItem &rFont) override
Sfx item RES_CHRATR_CJK_FONT.
LINESTYLE_BOLDWAVE
sal_Int16 nId
sal_uInt16 GetDistance(SvxBoxItemLine nLine) const
void FlyFrameGraphic(const SwFlyFrameFormat *pFlyFrameFormat, const SwGrfNode *pGrfNode)
Output graphic fly frames.
#define OOO_STRING_SVTOOLS_RTF_PICT
void clear()
Similar to ->setLength(0), but for all buffers.
void TableInfoCell(ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner) override
virtual OUString GetPar1() const override
Author.
Definition: docufld.cxx:1787
sal_uInt64 Seek(sal_uInt64 nPos)
void ParaWidows(const SvxWidowsItem &rWidows) override
Sfx item RES_PARATR_WIDOWS.
#define cDfltFillChar
#define OOO_STRING_SVTOOLS_RTF_FIELD
SwTableLine is one table row in the document model.
Definition: swtable.hxx:344
#define OOO_STRING_SVTOOLS_RTF_KEEPN
#define OOO_STRING_SVTOOLS_RTF_ULDB
#define OOO_STRING_SVTOOLS_RTF_SAUTOUPD
#define OOO_STRING_SVTOOLS_RTF_SHPWRK
void FormatSurround(const SwFormatSurround &rSurround) override
Sfx item RES_SURROUND.
void SetTextLeft(const long nL, const sal_uInt16 nProp=100)
SwNode & GetNode() const
Definition: ndindex.hxx:118
#define OOO_STRING_SVTOOLS_RTF_PICSCALEY
MirrorGraph
Definition: grfatr.hxx:31
long SwTwips
Definition: swtypes.hxx:49
void EndStyles(sal_uInt16 nNumberOfStyles) override
End of the styles table.
#define LO_STRING_SVTOOLS_RTF_MMATH
#define LO_STRING_SVTOOLS_RTF_MMATHPICT
void RefField(const SwField &rField, const OUString &rRef) override
#define OOO_STRING_SVTOOLS_RTF_INTBL
SvxFrameDirection
#define OOO_STRING_SVTOOLS_RTF_CLTXTBRL
#define OOO_STRING_SVTOOLS_RTF_SOUTLVL
#define OOO_STRING_SVTOOLS_RTF_BKMKEND
void CharLanguage(const SvxLanguageItem &rLanguage) override
Sfx item RES_CHRATR_LANGUAGE.
#define OOO_STRING_SVTOOLS_RTF_OUTLINELEVEL
#define OOO_STRING_SVTOOLS_RTF_FLYANCHOR
#define OOO_STRING_SVTOOLS_RTF_FSCRIPT
void StartAbstractNumbering(sal_uInt16 nId) override
Start of the abstract numbering definition instance.
#define OOO_STRING_SVTOOLS_RTF_CLVMRG
#define OOO_STRING_SVTOOLS_RTF_RTLPAR
bool IsEndNote() const
Definition: fmtftn.hxx:73
#define DFLT_ESC_AUTO_SUB
#define OOO_STRING_SVTOOLS_RTF_LEVELSTARTAT
#define OOO_STRING_SVTOOLS_RTF_FLDRSLT
void StartStyles() override
Start of the styles table.
void FormatFrameSize(const SwFormatFrameSize &rSize) override
Sfx item RES_FRM_SIZE.
#define RES_CHRATR_CJK_FONT
Definition: hintids.hxx:90
FAMILY_ROMAN
void SectionTitlePage() override
Has different headers/footers for the title page.
tools::Polygon CorrectWordWrapPolygonForExport(const tools::PolyPolygon &rPolyPoly, const SwNoTextNode *pNd)
Undo all scaling / move tricks of the wrap polygon done during import.
void CharPostureCTL(const SvxPostureItem &rPosture) override
Sfx item RES_CHRATR_CTL_POSTURE.
#define OOO_STRING_SVTOOLS_RTF_ACCUNDERDOT
#define RES_CHRATR_CJK_FONTSIZE
Definition: hintids.hxx:91
void FlyFrameOLE(const SwFlyFrameFormat *pFlyFrameFormat, SwOLENode &rOLENode, const Size &rSize)
#define OOO_STRING_SVTOOLS_RTF_LTRCH
const sal_uInt8 ColumnBreak
void SectionBiDi(bool bBiDi) override
Columns populated from right/numbers on the right side?
const editeng::SvxBorderLine * GetRight() const
#define OOO_STRING_SVTOOLS_RTF_SBKNONE
void CharCaseMap(const SvxCaseMapItem &rCaseMap) override
Sfx item Sfx item RES_CHRATR_CASEMAP.
sal_Int16 GetRelationOrient() const
Definition: fmtornt.hxx:55
#define OOO_STRING_SVTOOLS_RTF_CLVERTALB
#define OOO_STRING_SVTOOLS_RTF_PICH
Frame cannot be moved in Var-direction.
Definition: fmtfsize.hxx:38
rtl_TextEncoding GetDefaultEncoding() const
Definition: rtfexport.hxx:171
#define OOO_STRING_SVTOOLS_RTF_MARGRSXN
#define OOO_STRING_SVTOOLS_RTF_RTLROW
OUString FieldString(ww::eField eIndex)
Definition: ww8atr.cxx:2579
SvStream & WriteCharPtr(const char *pBuf)
#define OOO_STRING_SVTOOLS_RTF_HIGHLIGHT
#define OOO_STRING_SVTOOLS_RTF_SHPPICT
#define OOO_STRING_SVTOOLS_RTF_FAROMAN
int GetActualListLevel() const
Returns the actual list level of this text node, when it is a list item.
Definition: ndtxt.cxx:4097
SwTableFormat * GetFrameFormat()
Definition: swtable.hxx:201
void StartSection() override
Start of the section properties.
void TableBidi(ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner) override
void CharWeight(const SvxWeightItem &rWeight) override
Sfx item RES_CHRATR_WEIGHT.
void TableBackgrounds(ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner) override
size_type size() const
Definition: swtable.hxx:74
FontItalic GetPosture() const
#define OOO_STRING_SVTOOLS_RTF_LINECONT
#define OOO_STRING_SVTOOLS_RTF_CLPADFB
#define OOO_STRING_SVTOOLS_RTF_CHBRDR
#define RES_GRFATR_MIRRORGRF
Definition: hintids.hxx:239
static bool isTextBox(const SwFrameFormat &rFrameFormat)
Is this a standalone TextFrame, or used as a TextBox of a shape?
const SvxBoxItem & GetBox(bool=true) const
Definition: frmatr.hxx:84
virtual sal_uInt64 TellEnd() override
const SwTextINetFormat * GetTextINetFormat() const
Definition: fmtinfmt.hxx:70
#define OOO_STRING_SVTOOLS_RTF_FLYPAGE
LINESTYLE_DASH
void NumberingDefinition(sal_uInt16 nId, const SwNumRule &rRule) override
Definition of a numbering instance.
#define OOO_STRING_SVTOOLS_RTF_CLPADFL
WEIGHT_BOLD
#define OOO_STRING_SVTOOLS_RTF_FAHANG
const Color & GetStartColor() const
#define OOO_STRING_SVTOOLS_RTF_HICH
void TableDefinition(ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner) override
const SwTableBox * GetBox() const
Definition: wrtswtbl.hxx:73
void WriteExpand(const SwField *pField) override
Write the expanded field.
#define OOO_STRING_SVTOOLS_RTF_ACCDOT
virtual OUString GetPar1() const
Definition: fldbas.cxx:271
#define OOO_STRING_SVTOOLS_RTF_CLPADFT
#define OOO_STRING_SVTOOLS_RTF_DELETED
constexpr::Color COL_AUTO(0xFF, 0xFF, 0xFF, 0xFF)
void CharBorder(const ::editeng::SvxBorderLine *pAllBorder, sal_uInt16 nDist, bool bShadow) override
Sfx item RES_CHRATR_BOX.
#define OOO_STRING_SVTOOLS_RTF_SBKEVEN
bool StripMetafileHeader(const sal_uInt8 *&rpGraphicAry, sal_uInt64 &rSize)
LINESTYLE_DASHDOT
void ParaAdjust(const SvxAdjustItem &rAdjust) override
Sfx item RES_PARATR_ADJUST.
const SwTextFootnote * GetTextFootnote() const
Definition: fmtftn.hxx:85
sal_uInt16 sal_Unicode
const OUString & GetValue() const
Definition: fmtinfmt.hxx:75
bool IsRestartEachPage() const
Definition: lineinfo.hxx:90
const Color & GetColor() const
sal_Unicode GetEndBracket() const
#define OOO_STRING_SVTOOLS_RTF_PGNLCLTR
LINESTYLE_BOLDDASHDOTDOT
FieldFlags
Definition: wrtww8.hxx:147
#define OOO_STRING_SVTOOLS_RTF_BRDRTH
Value in Var-direction gives minimum (can be exceeded but not be less).
Definition: fmtfsize.hxx:39
#define OOO_STRING_SVTOOLS_RTF_BRDRCF
#define OOO_STRING_SVTOOLS_RTF_ACCCIRCLE
SvxShadowLocation GetLocation() const
#define OOO_STRING_SVTOOLS_RTF_ATNAUTHOR
#define OOO_STRING_SVTOOLS_RTF_BRDRDASHDD
void FontCharset(sal_uInt8 nCharSet) const
Font charset.
#define OOO_STRING_SVTOOLS_RTF_MARGBSXN
void FontPitchType(FontPitch ePitch) const
Font pitch.
FUNC_TYPE const nType
void CharScaleWidth(const SvxCharScaleWidthItem &rScaleWidth) override
Sfx item RES_CHRATR_SCALEW.
The class that does all the actual RTF export-related work.
Definition: rtfexport.hxx:36
#define OOO_STRING_SVTOOLS_RTF_ULTH
#define OOO_STRING_SVTOOLS_RTF_TRPADDFL
LINESTYLE_NONE
#define RES_CHRATR_CTL_FONTSIZE
Definition: hintids.hxx:96
#define OOO_STRING_SVTOOLS_RTF_LISTTEMPLATEID
void ParaForbiddenRules(const SfxBoolItem &rItem) override
Sfx item RES_PARATR_FORBIDDEN_RULES.
#define OOO_STRING_SVTOOLS_RTF_TITLEPG
void EndParagraphProperties(const SfxItemSet &rParagraphMarkerProperties, const SwRedlineData *pRedlineData, const SwRedlineData *pRedlineParagraphMarkerDeleted, const SwRedlineData *pRedlineParagraphMarkerInserted) override
Called after we end outputting the attributes.
#define OOO_STRING_SVTOOLS_RTF_I
#define OOO_STRING_SVTOOLS_RTF_SHPZ
#define OOO_STRING_SVTOOLS_RTF_NESTROW
void ParaScriptSpace(const SfxBoolItem &rScriptSpace) override
Sfx item RES_PARATR_SCRIPTSPACE.
#define X
void OutputFormat(const SwFormat &rFormat, bool bPapFormat, bool bChpFormat, bool bFlyFormat=false)
Output attributes.
Definition: ww8atr.cxx:753
rtl_TextEncoding GetCharSet() const
#define OOO_STRING_SVTOOLS_RTF_BRDRTNTHSG
void PageBreakBefore(bool bBreak) override
Page break As a paragraph property - the paragraph should be on the next page.
#define OOO_STRING_SVTOOLS_RTF_SBKODD
char sal_Char
StyleType
sal_uLong GetIndex() const
Definition: ndindex.hxx:151
sal_Int32 & GetTabPos()
const Size & GetLayoutSize() const
The layout size of the contained element.
void TableVerticalCell(ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner) override
SVX_NUM_ARABIC
#define OOO_STRING_SVTOOLS_RTF_QJ
eField
Definition: fields.hxx:26
const sal_uInt8 MAXLEVEL
Definition: swtypes.hxx:95
#define OOO_STRING_SVTOOLS_RTF_LANG
#define OOO_STRING_SVTOOLS_RTF_MARGLSXN
const SwWriteTableCells & GetCells() const
Definition: wrtswtbl.hxx:135
void FormatFillGradient(const XFillGradientItem &rFillGradient) override
Sfx item RES_FILL_GRADIENT.
SVX_NUM_ROMAN_UPPER
sal_uInt32 RGBToBGR(::Color nColour)
Definition: ww8struc.hxx:1082
#define DFLT_ESC_AUTO_SUPER
FontEmphasisMark GetEmphasisMark() const
#define OOO_STRING_SVTOOLS_RTF_LISTOVERRIDECOUNT
const SwTable & GetTable() const
Definition: node.hxx:497
const SwFormatSurround & GetSurround(bool=true) const
Definition: fmtsrnd.hxx:66
SVX_NUM_ROMAN_LOWER
#define OOO_STRING_SVTOOLS_RTF_HEADERY
SVX_NUM_IROHA_FULLWIDTH_JA
const editeng::SvxBorderLine * GetLine(SvxBoxItemLine nLine) const
OUString GetObjTitle() const
Definition: atrfrm.cxx:3101
const OUString & GetNumStr() const
Definition: fmtftn.hxx:70
#define OOO_STRING_SVTOOLS_RTF_PGBRDRL
void ParaVerticalAlign(const SvxParaVertAlignItem &rAlign) override
Sfx item RES_PARATR_VERTALIGN.
PITCH_VARIABLE
void FontAlternateName(const OUString &rName) const
Alternate name for the font.