LibreOffice Module sw (master)  1
docxsdrexport.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 
10 #include "docxsdrexport.hxx"
11 #include <com/sun/star/beans/XPropertySet.hpp>
12 #include <com/sun/star/drawing/PointSequenceSequence.hpp>
14 #include <editeng/lrspitem.hxx>
15 #include <editeng/ulspitem.hxx>
16 #include <editeng/shaditem.hxx>
17 #include <editeng/opaqitem.hxx>
18 #include <editeng/boxitem.hxx>
19 #include <svx/svdogrp.hxx>
20 #include <oox/token/namespaces.hxx>
21 #include <textboxhelper.hxx>
22 #include <fmtanchr.hxx>
23 #include <fmtsrnd.hxx>
24 #include <fmtcntnt.hxx>
25 #include <fmtornt.hxx>
26 #include <ndtxt.hxx>
27 #include <txatbase.hxx>
28 #include <fmtfsize.hxx>
29 #include <frmatr.hxx>
30 #include "docxattributeoutput.hxx"
31 #include "docxexportfilter.hxx"
32 #include <comphelper/sequence.hxx>
34 #include <sal/log.hxx>
35 
37 
38 using namespace com::sun::star;
39 using namespace oox;
40 
41 namespace
42 {
43 uno::Sequence<beans::PropertyValue> lclGetProperty(const uno::Reference<drawing::XShape>& rShape,
44  const OUString& rPropName)
45 {
46  uno::Sequence<beans::PropertyValue> aResult;
47  uno::Reference<beans::XPropertySet> xPropertySet(rShape, uno::UNO_QUERY);
48  uno::Reference<beans::XPropertySetInfo> xPropSetInfo;
49 
50  if (!xPropertySet.is())
51  return aResult;
52 
53  xPropSetInfo = xPropertySet->getPropertySetInfo();
54  if (xPropSetInfo.is() && xPropSetInfo->hasPropertyByName(rPropName))
55  {
56  xPropertySet->getPropertyValue(rPropName) >>= aResult;
57  }
58  return aResult;
59 }
60 
61 OUString lclGetAnchorIdFromGrabBag(const SdrObject* pObj)
62 {
63  OUString aResult;
64  uno::Reference<drawing::XShape> xShape(const_cast<SdrObject*>(pObj)->getUnoShape(),
65  uno::UNO_QUERY);
66  OUString aGrabBagName;
67  uno::Reference<lang::XServiceInfo> xServiceInfo(xShape, uno::UNO_QUERY);
68  if (xServiceInfo->supportsService("com.sun.star.text.TextFrame"))
69  aGrabBagName = "FrameInteropGrabBag";
70  else
71  aGrabBagName = "InteropGrabBag";
72  uno::Sequence<beans::PropertyValue> propList = lclGetProperty(xShape, aGrabBagName);
73  auto pProp
74  = std::find_if(propList.begin(), propList.end(),
75  [](const beans::PropertyValue& rProp) { return rProp.Name == "AnchorId"; });
76  if (pProp != propList.end())
77  pProp->Value >>= aResult;
78  return aResult;
79 }
80 
81 void lclMovePositionWithRotation(awt::Point& aPos, const Size& rSize, sal_Int64 nRotation)
82 {
83  // code from ImplEESdrWriter::ImplFlipBoundingBox (filter/source/msfilter/eschesdo.cxx)
84  // TODO: refactor
85 
86  if (nRotation == 0)
87  return;
88 
89  if (nRotation < 0)
90  nRotation = (36000 + nRotation) % 36000;
91  if (nRotation % 18000 == 0)
92  nRotation = 0;
93  while (nRotation > 9000)
94  nRotation = (18000 - (nRotation % 18000));
95 
96  double fVal = static_cast<double>(nRotation) * F_PI18000;
97  double fCos = cos(fVal);
98  double fSin = sin(fVal);
99 
100  double nWidthHalf = static_cast<double>(rSize.Width()) / 2;
101  double nHeightHalf = static_cast<double>(rSize.Height()) / 2;
102 
103  double nXDiff = fSin * nHeightHalf + fCos * nWidthHalf - nWidthHalf;
104  double nYDiff = fSin * nWidthHalf + fCos * nHeightHalf - nHeightHalf;
105 
106  aPos.X += nXDiff;
107  aPos.Y += nYDiff;
108 }
109 
111 bool IsAnchorTypeInsideParagraph(const ww8::Frame* pFrame)
112 {
113  const SwFormatAnchor& rAnchor = pFrame->GetFrameFormat().GetAttrSet().GetAnchor();
114  return rAnchor.GetAnchorId() != RndStdIds::FLY_AT_PAGE;
115 }
116 }
117 
119  ww8::Frame const* pParentFrame)
120  : m_rExport(rExport)
121 {
122  m_rExport.SaveData(nStt, nEnd);
123  m_rExport.m_pParentFrame = pParentFrame;
124 }
125 
127 
130 {
131 private:
140  OStringBuffer m_aTextFrameStyle;
153 
154 public:
156  oox::drawingml::DrawingML* pDrawingML)
157  : m_rExport(rExport)
158  , m_pSerializer(std::move(pSerializer))
159  , m_pDrawingML(pDrawingML)
160  , m_pFlyFrameSize(nullptr)
161  , m_bTextFrameSyntax(false)
162  , m_bDMLTextFrameSyntax(false)
163  , m_bDrawingOpen(false)
164  , m_bParagraphSdtOpen(false)
165  , m_bParagraphHasDrawing(false)
166  , m_bFlyFrameGraphic(false)
167  , m_pFlyWrapAttrList(nullptr)
168  , m_pBodyPrAttrList(nullptr)
169  , m_bDMLAndVMLDrawingOpen(false)
170  , m_nDMLandVMLTextFrameRotation(0)
171  {
172  }
173 
175 
176  void textFrameShadow(const SwFrameFormat& rFrameFormat);
177  static bool isSupportedDMLShape(const uno::Reference<drawing::XShape>& xShape);
178 
180  {
181  m_pSerializer = pSerializer;
182  }
183 
185 
186  void setFlyFrameSize(const Size* pFlyFrameSize) { m_pFlyFrameSize = pFlyFrameSize; }
187 
188  const Size* getFlyFrameSize() const { return m_pFlyFrameSize; }
189 
190  void setTextFrameSyntax(bool bTextFrameSyntax) { m_bTextFrameSyntax = bTextFrameSyntax; }
191 
192  bool getTextFrameSyntax() const { return m_bTextFrameSyntax; }
193 
194  void setDMLTextFrameSyntax(bool bDMLTextFrameSyntax)
195  {
196  m_bDMLTextFrameSyntax = bDMLTextFrameSyntax;
197  }
198 
200 
202  {
203  m_pFlyAttrList = pFlyAttrList;
204  }
205 
207 
208  void
210  {
211  m_pTextboxAttrList = pTextboxAttrList;
212  }
213 
215  {
216  return m_pTextboxAttrList;
217  }
218 
219  OStringBuffer& getTextFrameStyle() { return m_aTextFrameStyle; }
220 
221  void setDrawingOpen(bool bDrawingOpen) { m_bDrawingOpen = bDrawingOpen; }
222 
223  bool getDrawingOpen() { return m_bDrawingOpen; }
224 
225  void setParagraphSdtOpen(bool bParagraphSdtOpen) { m_bParagraphSdtOpen = bParagraphSdtOpen; }
226 
227  bool getParagraphSdtOpen() const { return m_bParagraphSdtOpen; }
228 
229  void setDMLAndVMLDrawingOpen(bool bDMLAndVMLDrawingOpen)
230  {
231  m_bDMLAndVMLDrawingOpen = bDMLAndVMLDrawingOpen;
232  }
233 
235 
236  void setParagraphHasDrawing(bool bParagraphHasDrawing)
237  {
238  m_bParagraphHasDrawing = bParagraphHasDrawing;
239  }
240 
242 
244  {
245  return m_pFlyFillAttrList;
246  }
247 
249  {
250  m_pFlyWrapAttrList = pFlyWrapAttrList;
251  }
252 
254 
256  {
257  m_pBodyPrAttrList = pBodyPrAttrList;
258  }
259 
261 
263  {
264  return m_pDashLineStyleAttr;
265  }
266 
267  void setFlyFrameGraphic(bool bFlyFrameGraphic) { m_bFlyFrameGraphic = bFlyFrameGraphic; }
268 
269  bool getFlyFrameGraphic() const { return m_bFlyFrameGraphic; }
270 
272 
273  DocxExport& getExport() const { return m_rExport; }
274 
275  void setDMLandVMLTextFrameRotation(sal_Int32 nDMLandVMLTextFrameRotation)
276  {
277  m_nDMLandVMLTextFrameRotation = nDMLandVMLTextFrameRotation;
278  }
279 
281 };
282 
284  oox::drawingml::DrawingML* pDrawingML)
285  : m_pImpl(std::make_unique<Impl>(rExport, pSerializer, pDrawingML))
286 {
287 }
288 
290 
292 {
293  m_pImpl->setSerializer(pSerializer);
294 }
295 
296 const Size* DocxSdrExport::getFlyFrameSize() { return m_pImpl->getFlyFrameSize(); }
297 
298 bool DocxSdrExport::getTextFrameSyntax() { return m_pImpl->getTextFrameSyntax(); }
299 
300 bool DocxSdrExport::getDMLTextFrameSyntax() { return m_pImpl->getDMLTextFrameSyntax(); }
301 
303 {
304  return m_pImpl->getFlyAttrList();
305 }
306 
308 {
309  return m_pImpl->getTextboxAttrList();
310 }
311 
312 OStringBuffer& DocxSdrExport::getTextFrameStyle() { return m_pImpl->getTextFrameStyle(); }
313 
314 bool DocxSdrExport::IsDrawingOpen() { return m_pImpl->getDrawingOpen(); }
315 
316 void DocxSdrExport::setParagraphSdtOpen(bool bParagraphSdtOpen)
317 {
318  m_pImpl->setParagraphSdtOpen(bParagraphSdtOpen);
319 }
320 
321 bool DocxSdrExport::IsDMLAndVMLDrawingOpen() { return m_pImpl->getDMLAndVMLDrawingOpen(); }
322 
323 bool DocxSdrExport::IsParagraphHasDrawing() { return m_pImpl->getParagraphHasDrawing(); }
324 
325 void DocxSdrExport::setParagraphHasDrawing(bool bParagraphHasDrawing)
326 {
327  m_pImpl->setParagraphHasDrawing(bParagraphHasDrawing);
328 }
329 
331 {
332  return m_pImpl->getFlyFillAttrList();
333 }
334 
336 {
337  return m_pImpl->getFlyWrapAttrList();
338 }
339 
341 {
342  return m_pImpl->getBodyPrAttrList();
343 }
344 
346 {
347  return m_pImpl->getDashLineStyleAttr();
348 }
349 
351 {
352  m_pImpl->setFlyWrapAttrList(pAttrList);
353 }
354 
355 void DocxSdrExport::startDMLAnchorInline(const SwFrameFormat* pFrameFormat, const Size& rSize)
356 {
357  m_pImpl->setDrawingOpen(true);
358  m_pImpl->setParagraphHasDrawing(true);
359  m_pImpl->getSerializer()->startElementNS(XML_w, XML_drawing);
360 
361  const SvxLRSpaceItem aLRSpaceItem = pFrameFormat->GetLRSpace(false);
362  const SvxULSpaceItem aULSpaceItem = pFrameFormat->GetULSpace(false);
363 
364  bool isAnchor;
365 
366  if (m_pImpl->getFlyFrameGraphic())
367  {
368  isAnchor = false; // make Graphic object inside DMLTextFrame & VMLTextFrame as Inline
369  }
370  else
371  {
372  isAnchor = pFrameFormat->GetAnchor().GetAnchorId() != RndStdIds::FLY_AS_CHAR;
373  }
374 
375  // Count effectExtent values, their value is needed before dist{T,B,L,R} is written.
376  SvxShadowItem aShadowItem = pFrameFormat->GetShadow();
377  sal_Int32 nLeftExt = 0;
378  sal_Int32 nRightExt = 0;
379  sal_Int32 nTopExt = 0;
380  sal_Int32 nBottomExt = 0;
381  if (aShadowItem.GetLocation() != SvxShadowLocation::NONE)
382  {
383  sal_Int32 nShadowWidth(TwipsToEMU(aShadowItem.GetWidth()));
384  switch (aShadowItem.GetLocation())
385  {
386  case SvxShadowLocation::TopLeft:
387  nTopExt = nLeftExt = nShadowWidth;
388  break;
389  case SvxShadowLocation::TopRight:
390  nTopExt = nRightExt = nShadowWidth;
391  break;
392  case SvxShadowLocation::BottomLeft:
393  nBottomExt = nLeftExt = nShadowWidth;
394  break;
395  case SvxShadowLocation::BottomRight:
396  nBottomExt = nRightExt = nShadowWidth;
397  break;
398  case SvxShadowLocation::NONE:
399  case SvxShadowLocation::End:
400  break;
401  }
402  }
403  else if (const SdrObject* pObject = pFrameFormat->FindRealSdrObject())
404  {
405  // No shadow, but we have an idea what was the original effectExtent.
406  uno::Any aAny;
407  pObject->GetGrabBagItem(aAny);
408  comphelper::SequenceAsHashMap aGrabBag(aAny);
409  auto it = aGrabBag.find("CT_EffectExtent");
410  if (it != aGrabBag.end())
411  {
412  comphelper::SequenceAsHashMap aEffectExtent(it->second);
413  for (std::pair<const OUString, uno::Any>& rDirection : aEffectExtent)
414  {
415  if (rDirection.first == "l" && rDirection.second.has<sal_Int32>())
416  nLeftExt = rDirection.second.get<sal_Int32>();
417  else if (rDirection.first == "t" && rDirection.second.has<sal_Int32>())
418  nTopExt = rDirection.second.get<sal_Int32>();
419  else if (rDirection.first == "r" && rDirection.second.has<sal_Int32>())
420  nRightExt = rDirection.second.get<sal_Int32>();
421  else if (rDirection.first == "b" && rDirection.second.has<sal_Int32>())
422  nBottomExt = rDirection.second.get<sal_Int32>();
423  }
424  }
425  }
426 
427  if (isAnchor)
428  {
431  bool bOpaque = pFrameFormat->GetOpaque().GetValue();
432  awt::Point aPos(pFrameFormat->GetHoriOrient().GetPos(),
433  pFrameFormat->GetVertOrient().GetPos());
434  const SdrObject* pObj = pFrameFormat->FindRealSdrObject();
435  long nRotation = 0;
436  if (pObj != nullptr)
437  {
438  // SdrObjects know their layer, consider that instead of the frame format.
439  bOpaque = pObj->GetLayer()
440  != pFrameFormat->GetDoc()->getIDocumentDrawModelAccess().GetHellId()
441  && pObj->GetLayer()
442  != pFrameFormat->GetDoc()
445 
446  nRotation = pObj->GetRotateAngle();
447  lclMovePositionWithRotation(aPos, rSize, nRotation);
448  }
449  attrList->add(XML_behindDoc, bOpaque ? "0" : "1");
450  // Extend distance with the effect extent if the shape is not rotated, which is the opposite
451  // of the mapping done at import time.
452  // The type of dist* attributes is unsigned, so make sure no negative value is written.
453  sal_Int64 nTopExtDist = nRotation ? 0 : nTopExt;
454  sal_Int64 nDistT = std::max(static_cast<sal_Int64>(0),
455  TwipsToEMU(aULSpaceItem.GetUpper()) - nTopExtDist);
456  attrList->add(XML_distT, OString::number(nDistT).getStr());
457  sal_Int64 nBottomExtDist = nRotation ? 0 : nBottomExt;
458  sal_Int64 nDistB = std::max(static_cast<sal_Int64>(0),
459  TwipsToEMU(aULSpaceItem.GetLower()) - nBottomExtDist);
460  attrList->add(XML_distB, OString::number(nDistB).getStr());
461  sal_Int64 nLeftExtDist = nRotation ? 0 : nLeftExt;
462  sal_Int64 nDistL = std::max(static_cast<sal_Int64>(0),
463  TwipsToEMU(aLRSpaceItem.GetLeft()) - nLeftExtDist);
464  attrList->add(XML_distL, OString::number(nDistL).getStr());
465  sal_Int64 nRightExtDist = nRotation ? 0 : nRightExt;
466  sal_Int64 nDistR = std::max(static_cast<sal_Int64>(0),
467  TwipsToEMU(aLRSpaceItem.GetRight()) - nRightExtDist);
468  attrList->add(XML_distR, OString::number(nDistR).getStr());
469  attrList->add(XML_simplePos, "0");
470  attrList->add(XML_locked, "0");
471  attrList->add(XML_layoutInCell, "1");
472  attrList->add(XML_allowOverlap, "1"); // TODO
473  if (pObj != nullptr)
474  // It seems 0 and 1 have special meaning: just start counting from 2 to avoid issues with that.
475  attrList->add(XML_relativeHeight, OString::number(pObj->GetOrdNum() + 2));
476  else
477  // relativeHeight is mandatory attribute, if value is not present, we must write default value
478  attrList->add(XML_relativeHeight, "0");
479  if (pObj != nullptr)
480  {
481  OUString sAnchorId = lclGetAnchorIdFromGrabBag(pObj);
482  if (!sAnchorId.isEmpty())
483  attrList->addNS(XML_wp14, XML_anchorId,
484  OUStringToOString(sAnchorId, RTL_TEXTENCODING_UTF8));
485  }
486  sax_fastparser::XFastAttributeListRef xAttrList(attrList);
487  m_pImpl->getSerializer()->startElementNS(XML_wp, XML_anchor, xAttrList);
488  m_pImpl->getSerializer()->singleElementNS(XML_wp, XML_simplePos, XML_x, "0", XML_y,
489  "0"); // required, unused
490  const char* relativeFromH;
491  const char* relativeFromV;
492  const char* alignH = nullptr;
493  const char* alignV = nullptr;
494  switch (pFrameFormat->GetVertOrient().GetRelationOrient())
495  {
496  case text::RelOrientation::PAGE_PRINT_AREA:
497  relativeFromV = "margin";
498  break;
499  case text::RelOrientation::PAGE_FRAME:
500  relativeFromV = "page";
501  break;
502  case text::RelOrientation::FRAME:
503  relativeFromV = "paragraph";
504  break;
505  case text::RelOrientation::TEXT_LINE:
506  default:
507  relativeFromV = "line";
508  break;
509  }
510  switch (pFrameFormat->GetVertOrient().GetVertOrient())
511  {
513  case text::VertOrientation::CHAR_TOP:
514  case text::VertOrientation::LINE_TOP:
515  if (pFrameFormat->GetVertOrient().GetRelationOrient()
516  == text::RelOrientation::TEXT_LINE)
517  alignV = "bottom";
518  else
519  alignV = "top";
520  break;
522  case text::VertOrientation::CHAR_BOTTOM:
523  case text::VertOrientation::LINE_BOTTOM:
524  if (pFrameFormat->GetVertOrient().GetRelationOrient()
525  == text::RelOrientation::TEXT_LINE)
526  alignV = "top";
527  else
528  alignV = "bottom";
529  break;
530  case text::VertOrientation::CENTER:
531  case text::VertOrientation::CHAR_CENTER:
532  case text::VertOrientation::LINE_CENTER:
533  alignV = "center";
534  break;
535  default:
536  break;
537  }
538  switch (pFrameFormat->GetHoriOrient().GetRelationOrient())
539  {
540  case text::RelOrientation::PAGE_PRINT_AREA:
541  relativeFromH = "margin";
542  break;
543  case text::RelOrientation::PAGE_FRAME:
544  relativeFromH = "page";
545  break;
546  case text::RelOrientation::CHAR:
547  relativeFromH = "character";
548  break;
549  case text::RelOrientation::PAGE_RIGHT:
550  relativeFromH = "rightMargin";
551  break;
552  case text::RelOrientation::PAGE_LEFT:
553  relativeFromH = "leftMargin";
554  break;
555  case text::RelOrientation::FRAME:
556  default:
557  relativeFromH = "column";
558  break;
559  }
560  switch (pFrameFormat->GetHoriOrient().GetHoriOrient())
561  {
563  alignH = "left";
564  break;
566  alignH = "right";
567  break;
568  case text::HoriOrientation::CENTER:
569  alignH = "center";
570  break;
571  case text::HoriOrientation::INSIDE:
572  alignH = "inside";
573  break;
574  case text::HoriOrientation::OUTSIDE:
575  alignH = "outside";
576  break;
577  default:
578  break;
579  }
580  m_pImpl->getSerializer()->startElementNS(XML_wp, XML_positionH, XML_relativeFrom,
581  relativeFromH);
587  const sal_Int64 MAX_INTEGER_VALUE = SAL_MAX_INT32;
588  const sal_Int64 MIN_INTEGER_VALUE = SAL_MIN_INT32;
589  if (alignH != nullptr)
590  {
591  m_pImpl->getSerializer()->startElementNS(XML_wp, XML_align);
592  m_pImpl->getSerializer()->write(alignH);
593  m_pImpl->getSerializer()->endElementNS(XML_wp, XML_align);
594  }
595  else
596  {
597  m_pImpl->getSerializer()->startElementNS(XML_wp, XML_posOffset);
598  sal_Int64 nPosXEMU = TwipsToEMU(aPos.X);
599 
600  /* Absolute Position Offset Value is of type Int. Hence it should not be greater than
601  * Maximum value for Int OR Less than the Minimum value for Int.
602  * - Maximum value for Int = 2147483647
603  * - Minimum value for Int = -2147483648
604  *
605  * As per ECMA Specification : ECMA-376, Second Edition,
606  * Part 1 - Fundamentals And Markup Language Reference[20.4.3.3 ST_PositionOffset (Absolute Position Offset Value)]
607  *
608  * Please refer : http://www.schemacentral.com/sc/xsd/t-xsd_int.html
609  */
610 
611  if (nPosXEMU > MAX_INTEGER_VALUE)
612  {
613  nPosXEMU = MAX_INTEGER_VALUE;
614  }
615  else if (nPosXEMU < MIN_INTEGER_VALUE)
616  {
617  nPosXEMU = MIN_INTEGER_VALUE;
618  }
619  m_pImpl->getSerializer()->write(nPosXEMU);
620  m_pImpl->getSerializer()->endElementNS(XML_wp, XML_posOffset);
621  }
622  m_pImpl->getSerializer()->endElementNS(XML_wp, XML_positionH);
623  m_pImpl->getSerializer()->startElementNS(XML_wp, XML_positionV, XML_relativeFrom,
624  relativeFromV);
625 
626  sal_Int64 nPosYEMU = TwipsToEMU(aPos.Y);
627 
628  // tdf#93675, 0 below line/paragraph and/or top line/paragraph with
629  // wrap top+bottom or other wraps is affecting the line directly
630  // above the anchor line, which seems odd, but a tiny adjustment
631  // here to bring the top down convinces msoffice to wrap like us
632  if (nPosYEMU == 0
633  && (strcmp(relativeFromV, "line") == 0 || strcmp(relativeFromV, "paragraph") == 0)
634  && (!alignV || strcmp(alignV, "top") == 0))
635  {
636  alignV = nullptr;
637  nPosYEMU = 635;
638  }
639 
640  if (alignV != nullptr)
641  {
642  m_pImpl->getSerializer()->startElementNS(XML_wp, XML_align);
643  m_pImpl->getSerializer()->write(alignV);
644  m_pImpl->getSerializer()->endElementNS(XML_wp, XML_align);
645  }
646  else
647  {
648  m_pImpl->getSerializer()->startElementNS(XML_wp, XML_posOffset);
649  if (nPosYEMU > MAX_INTEGER_VALUE)
650  {
651  nPosYEMU = MAX_INTEGER_VALUE;
652  }
653  else if (nPosYEMU < MIN_INTEGER_VALUE)
654  {
655  nPosYEMU = MIN_INTEGER_VALUE;
656  }
657  m_pImpl->getSerializer()->write(nPosYEMU);
658  m_pImpl->getSerializer()->endElementNS(XML_wp, XML_posOffset);
659  }
660  m_pImpl->getSerializer()->endElementNS(XML_wp, XML_positionV);
661  }
662  else
663  {
666  aAttrList->add(XML_distT, OString::number(TwipsToEMU(aULSpaceItem.GetUpper())).getStr());
667  aAttrList->add(XML_distB, OString::number(TwipsToEMU(aULSpaceItem.GetLower())).getStr());
668  aAttrList->add(XML_distL, OString::number(TwipsToEMU(aLRSpaceItem.GetLeft())).getStr());
669  aAttrList->add(XML_distR, OString::number(TwipsToEMU(aLRSpaceItem.GetRight())).getStr());
670  const SdrObject* pObj = pFrameFormat->FindRealSdrObject();
671  if (pObj != nullptr)
672  {
673  OUString sAnchorId = lclGetAnchorIdFromGrabBag(pObj);
674  if (!sAnchorId.isEmpty())
675  aAttrList->addNS(XML_wp14, XML_anchorId,
676  OUStringToOString(sAnchorId, RTL_TEXTENCODING_UTF8));
677  }
678  m_pImpl->getSerializer()->startElementNS(XML_wp, XML_inline, aAttrList);
679  }
680 
681  // now the common parts
682  // extent of the image
700  sal_uInt64 cx = TwipsToEMU(std::clamp(rSize.Width(), 0L, long(SAL_MAX_INT32)));
701  OString aWidth(OString::number(std::min(cx, sal_uInt64(SAL_MAX_INT32))));
702  sal_uInt64 cy = TwipsToEMU(std::clamp(rSize.Height(), 0L, long(SAL_MAX_INT32)));
703  OString aHeight(OString::number(std::min(cy, sal_uInt64(SAL_MAX_INT32))));
704 
705  m_pImpl->getSerializer()->singleElementNS(XML_wp, XML_extent, XML_cx, aWidth, XML_cy, aHeight);
706 
707  // effectExtent, extent including the effect (shadow only for now)
708  m_pImpl->getSerializer()->singleElementNS(
709  XML_wp, XML_effectExtent, XML_l, OString::number(nLeftExt), XML_t, OString::number(nTopExt),
710  XML_r, OString::number(nRightExt), XML_b, OString::number(nBottomExt));
711 
712  // See if we know the exact wrap type from grab-bag.
713  sal_Int32 nWrapToken = 0;
714  if (const SdrObject* pObject = pFrameFormat->FindRealSdrObject())
715  {
716  uno::Any aAny;
717  pObject->GetGrabBagItem(aAny);
718  comphelper::SequenceAsHashMap aGrabBag(aAny);
719  auto it = aGrabBag.find("EG_WrapType");
720  if (it != aGrabBag.end())
721  {
722  auto sType = it->second.get<OUString>();
723  if (sType == "wrapTight")
724  nWrapToken = XML_wrapTight;
725  else if (sType == "wrapThrough")
726  nWrapToken = XML_wrapThrough;
727  else
728  SAL_WARN("sw.ww8",
729  "DocxSdrExport::startDMLAnchorInline: unexpected EG_WrapType value");
730 
731  m_pImpl->getSerializer()->startElementNS(XML_wp, nWrapToken, XML_wrapText, "bothSides");
732 
733  it = aGrabBag.find("CT_WrapPath");
734  if (it != aGrabBag.end())
735  {
736  m_pImpl->getSerializer()->startElementNS(XML_wp, XML_wrapPolygon, XML_edited, "0");
737  auto aSeqSeq = it->second.get<drawing::PointSequenceSequence>();
738  auto aPoints(comphelper::sequenceToContainer<std::vector<awt::Point>>(aSeqSeq[0]));
739  for (auto i = aPoints.begin(); i != aPoints.end(); ++i)
740  {
741  awt::Point& rPoint = *i;
742  m_pImpl->getSerializer()->singleElementNS(
743  XML_wp, (i == aPoints.begin() ? XML_start : XML_lineTo), XML_x,
744  OString::number(rPoint.X), XML_y, OString::number(rPoint.Y));
745  }
746  m_pImpl->getSerializer()->endElementNS(XML_wp, XML_wrapPolygon);
747  }
748 
749  m_pImpl->getSerializer()->endElementNS(XML_wp, nWrapToken);
750  }
751  }
752 
753  // Or if we have a contour.
754  if (!nWrapToken && pFrameFormat->GetSurround().IsContour())
755  {
756  if (const SwNoTextNode* pNd = sw::util::GetNoTextNodeFromSwFrameFormat(*pFrameFormat))
757  {
758  const tools::PolyPolygon* pPolyPoly = pNd->HasContour();
759  if (pPolyPoly && pPolyPoly->Count())
760  {
761  nWrapToken = XML_wrapTight;
762  m_pImpl->getSerializer()->startElementNS(XML_wp, nWrapToken, XML_wrapText,
763  "bothSides");
764 
765  m_pImpl->getSerializer()->startElementNS(XML_wp, XML_wrapPolygon, XML_edited, "0");
767  for (sal_uInt16 i = 0; i < aPoly.GetSize(); ++i)
768  m_pImpl->getSerializer()->singleElementNS(
769  XML_wp, (i == 0 ? XML_start : XML_lineTo), XML_x,
770  OString::number(aPoly[i].X()), XML_y, OString::number(aPoly[i].Y()));
771  m_pImpl->getSerializer()->endElementNS(XML_wp, XML_wrapPolygon);
772 
773  m_pImpl->getSerializer()->endElementNS(XML_wp, nWrapToken);
774  }
775  }
776  }
777 
778  // No? Then just approximate based on what we have.
779  if (isAnchor && !nWrapToken)
780  {
781  switch (pFrameFormat->GetSurround().GetValue())
782  {
783  case css::text::WrapTextMode_NONE:
784  m_pImpl->getSerializer()->singleElementNS(XML_wp, XML_wrapTopAndBottom);
785  break;
786  case css::text::WrapTextMode_THROUGH:
787  m_pImpl->getSerializer()->singleElementNS(XML_wp, XML_wrapNone);
788  break;
789  case css::text::WrapTextMode_PARALLEL:
790  m_pImpl->getSerializer()->singleElementNS(XML_wp, XML_wrapSquare, XML_wrapText,
791  "bothSides");
792  break;
793  case css::text::WrapTextMode_DYNAMIC:
794  default:
795  m_pImpl->getSerializer()->singleElementNS(XML_wp, XML_wrapSquare, XML_wrapText,
796  "largest");
797  break;
798  }
799  }
800 }
801 
803 {
804  bool isAnchor;
805  if (m_pImpl->getFlyFrameGraphic())
806  {
807  isAnchor = false; // end Inline Graphic object inside DMLTextFrame
808  }
809  else
810  {
811  isAnchor = pFrameFormat->GetAnchor().GetAnchorId() != RndStdIds::FLY_AS_CHAR;
812  }
813  m_pImpl->getSerializer()->endElementNS(XML_wp, isAnchor ? XML_anchor : XML_inline);
814 
815  m_pImpl->getSerializer()->endElementNS(XML_w, XML_drawing);
816  m_pImpl->setDrawingOpen(false);
817 }
818 
819 void DocxSdrExport::writeVMLDrawing(const SdrObject* sdrObj, const SwFrameFormat& rFrameFormat)
820 {
821  m_pImpl->getSerializer()->startElementNS(XML_w, XML_pict);
822  m_pImpl->getDrawingML()->SetFS(m_pImpl->getSerializer());
823  // See WinwordAnchoring::SetAnchoring(), these are not part of the SdrObject, have to be passed around manually.
824 
825  const SwFormatHoriOrient& rHoriOri = rFrameFormat.GetHoriOrient();
826  const SwFormatVertOrient& rVertOri = rFrameFormat.GetVertOrient();
827  m_pImpl->getExport().VMLExporter().AddSdrObject(
828  *sdrObj, rHoriOri.GetHoriOrient(), rVertOri.GetVertOrient(), rHoriOri.GetRelationOrient(),
829  rVertOri.GetRelationOrient(), true);
830  m_pImpl->getSerializer()->endElementNS(XML_w, XML_pict);
831 }
832 
833 static bool lcl_isLockedCanvas(const uno::Reference<drawing::XShape>& xShape)
834 {
835  uno::Sequence<beans::PropertyValue> propList = lclGetProperty(xShape, "InteropGrabBag");
836  /*
837  * Export as Locked Canvas only if the property
838  * is in the PropertySet
839  */
840  return std::any_of(propList.begin(), propList.end(), [](const beans::PropertyValue& rProp) {
841  return rProp.Name == "LockedCanvas";
842  });
843 }
844 
845 void DocxSdrExport::writeDMLDrawing(const SdrObject* pSdrObject, const SwFrameFormat* pFrameFormat,
846  int nAnchorId)
847 {
848  uno::Reference<drawing::XShape> xShape(const_cast<SdrObject*>(pSdrObject)->getUnoShape(),
849  uno::UNO_QUERY_THROW);
850  if (!Impl::isSupportedDMLShape(xShape))
851  return;
852 
853  m_pImpl->getExport().DocxAttrOutput().GetSdtEndBefore(pSdrObject);
854 
855  sax_fastparser::FSHelperPtr pFS = m_pImpl->getSerializer();
856  Size aSize(pSdrObject->GetLogicRect().GetWidth(), pSdrObject->GetLogicRect().GetHeight());
857  startDMLAnchorInline(pFrameFormat, aSize);
858 
859  sax_fastparser::FastAttributeList* pDocPrAttrList
861  pDocPrAttrList->add(XML_id, OString::number(nAnchorId).getStr());
862  pDocPrAttrList->add(XML_name,
863  OUStringToOString(pSdrObject->GetName(), RTL_TEXTENCODING_UTF8).getStr());
864  if (!pSdrObject->GetTitle().isEmpty())
865  pDocPrAttrList->add(XML_title,
866  OUStringToOString(pSdrObject->GetTitle(), RTL_TEXTENCODING_UTF8));
867  if (!pSdrObject->GetDescription().isEmpty())
868  pDocPrAttrList->add(XML_descr,
869  OUStringToOString(pSdrObject->GetDescription(), RTL_TEXTENCODING_UTF8));
870  if (!pSdrObject->IsVisible()
871  && pFrameFormat->GetAnchor().GetAnchorId() != RndStdIds::FLY_AS_CHAR)
872 
873  pDocPrAttrList->add(XML_hidden, OString::number(1).getStr());
874  sax_fastparser::XFastAttributeListRef xDocPrAttrListRef(pDocPrAttrList);
875  pFS->singleElementNS(XML_wp, XML_docPr, xDocPrAttrListRef);
876 
877  uno::Reference<lang::XServiceInfo> xServiceInfo(xShape, uno::UNO_QUERY_THROW);
878  const char* pNamespace = "http://schemas.microsoft.com/office/word/2010/wordprocessingShape";
879  if (xServiceInfo->supportsService("com.sun.star.drawing.GroupShape"))
880  pNamespace = "http://schemas.microsoft.com/office/word/2010/wordprocessingGroup";
881  else if (xServiceInfo->supportsService("com.sun.star.drawing.GraphicObjectShape"))
882  pNamespace = "http://schemas.openxmlformats.org/drawingml/2006/picture";
883  pFS->startElementNS(XML_a, XML_graphic, FSNS(XML_xmlns, XML_a),
884  m_pImpl->getExport().GetFilter().getNamespaceURL(OOX_NS(dml)).toUtf8());
885  pFS->startElementNS(XML_a, XML_graphicData, XML_uri, pNamespace);
886 
887  bool bLockedCanvas = lcl_isLockedCanvas(xShape);
888  if (bLockedCanvas)
889  pFS->startElementNS(
890  XML_lc, XML_lockedCanvas, FSNS(XML_xmlns, XML_lc),
891  m_pImpl->getExport().GetFilter().getNamespaceURL(OOX_NS(dmlLockedCanvas)).toUtf8());
892 
893  m_pImpl->getExport().OutputDML(xShape);
894 
895  if (bLockedCanvas)
896  pFS->endElementNS(XML_lc, XML_lockedCanvas);
897  pFS->endElementNS(XML_a, XML_graphicData);
898  pFS->endElementNS(XML_a, XML_graphic);
899 
900  // Relative size of the drawing.
901  if (pSdrObject->GetRelativeWidth())
902  {
903  // At the moment drawinglayer objects are always relative from page.
904  pFS->startElementNS(XML_wp14, XML_sizeRelH, XML_relativeFrom,
905  (pSdrObject->GetRelativeWidthRelation() == text::RelOrientation::FRAME
906  ? "margin"
907  : "page"));
908  pFS->startElementNS(XML_wp14, XML_pctWidth);
909  pFS->writeEscaped(
910  OUString::number(*pSdrObject->GetRelativeWidth() * 100 * oox::drawingml::PER_PERCENT));
911  pFS->endElementNS(XML_wp14, XML_pctWidth);
912  pFS->endElementNS(XML_wp14, XML_sizeRelH);
913  }
914  if (pSdrObject->GetRelativeHeight())
915  {
916  pFS->startElementNS(XML_wp14, XML_sizeRelV, XML_relativeFrom,
917  (pSdrObject->GetRelativeHeightRelation() == text::RelOrientation::FRAME
918  ? "margin"
919  : "page"));
920  pFS->startElementNS(XML_wp14, XML_pctHeight);
921  pFS->writeEscaped(
922  OUString::number(*pSdrObject->GetRelativeHeight() * 100 * oox::drawingml::PER_PERCENT));
923  pFS->endElementNS(XML_wp14, XML_pctHeight);
924  pFS->endElementNS(XML_wp14, XML_sizeRelV);
925  }
926 
927  endDMLAnchorInline(pFrameFormat);
928 }
929 
931 {
932  const SvxShadowItem& aShadowItem = rFrameFormat.GetShadow();
933  if (aShadowItem.GetLocation() == SvxShadowLocation::NONE)
934  return;
935 
936  OString aShadowWidth(OString::number(double(aShadowItem.GetWidth()) / 20) + "pt");
937  OString aOffset;
938  switch (aShadowItem.GetLocation())
939  {
940  case SvxShadowLocation::TopLeft:
941  aOffset = "-" + aShadowWidth + ",-" + aShadowWidth;
942  break;
943  case SvxShadowLocation::TopRight:
944  aOffset = aShadowWidth + ",-" + aShadowWidth;
945  break;
946  case SvxShadowLocation::BottomLeft:
947  aOffset = "-" + aShadowWidth + "," + aShadowWidth;
948  break;
949  case SvxShadowLocation::BottomRight:
950  aOffset = aShadowWidth + "," + aShadowWidth;
951  break;
952  case SvxShadowLocation::NONE:
953  case SvxShadowLocation::End:
954  break;
955  }
956  if (aOffset.isEmpty())
957  return;
958 
959  OString aShadowColor = msfilter::util::ConvertColor(aShadowItem.GetColor());
960  m_pSerializer->singleElementNS(XML_v, XML_shadow, XML_on, "t", XML_color, "#" + aShadowColor,
961  XML_offset, aOffset);
962 }
963 
964 bool DocxSdrExport::Impl::isSupportedDMLShape(const uno::Reference<drawing::XShape>& xShape)
965 {
966  uno::Reference<lang::XServiceInfo> xServiceInfo(xShape, uno::UNO_QUERY_THROW);
967  if (xServiceInfo->supportsService("com.sun.star.drawing.PolyPolygonShape")
968  || xServiceInfo->supportsService("com.sun.star.drawing.PolyLineShape"))
969  return false;
970 
971  // For signature line shapes, we don't want DML, just the VML shape.
972  bool bIsSignatureLineShape = false;
973  if (xServiceInfo->supportsService("com.sun.star.drawing.GraphicObjectShape"))
974  {
975  uno::Reference<beans::XPropertySet> xShapeProperties(xShape, uno::UNO_QUERY);
976  xShapeProperties->getPropertyValue("IsSignatureLine") >>= bIsSignatureLineShape;
977  if (bIsSignatureLineShape)
978  return false;
979  }
980 
981  return true;
982 }
983 
985  const SwFrameFormat& rFrameFormat, int nAnchorId)
986 {
987  bool bDMLAndVMLDrawingOpen = m_pImpl->getDMLAndVMLDrawingOpen();
988  m_pImpl->setDMLAndVMLDrawingOpen(true);
989 
990  // Depending on the shape type, we actually don't write the shape as DML.
991  OUString sShapeType;
992  ShapeFlag nMirrorFlags = ShapeFlag::NONE;
993  uno::Reference<drawing::XShape> xShape(const_cast<SdrObject*>(sdrObj)->getUnoShape(),
994  uno::UNO_QUERY_THROW);
995 
996  // Locked canvas is OK inside DML.
997  if (lcl_isLockedCanvas(xShape))
998  bDMLAndVMLDrawingOpen = false;
999 
1000  MSO_SPT eShapeType
1001  = EscherPropertyContainer::GetCustomShapeType(xShape, nMirrorFlags, sShapeType);
1002 
1003  // In case we are already inside a DML block, then write the shape only as VML, turn out that's allowed to do.
1004  // A common service created in util to check for VML shapes which are allowed to have textbox in content
1006  && !bDMLAndVMLDrawingOpen)
1007  {
1008  m_pImpl->getSerializer()->startElementNS(XML_mc, XML_AlternateContent);
1009 
1010  auto pObjGroup = dynamic_cast<const SdrObjGroup*>(sdrObj);
1011  m_pImpl->getSerializer()->startElementNS(XML_mc, XML_Choice, XML_Requires,
1012  (pObjGroup ? "wpg" : "wps"));
1013  writeDMLDrawing(sdrObj, &rFrameFormat, nAnchorId);
1014  m_pImpl->getSerializer()->endElementNS(XML_mc, XML_Choice);
1015 
1016  m_pImpl->getSerializer()->startElementNS(XML_mc, XML_Fallback);
1017  writeVMLDrawing(sdrObj, rFrameFormat);
1018  m_pImpl->getSerializer()->endElementNS(XML_mc, XML_Fallback);
1019 
1020  m_pImpl->getSerializer()->endElementNS(XML_mc, XML_AlternateContent);
1021  }
1022  else
1023  writeVMLDrawing(sdrObj, rFrameFormat);
1024 
1025  m_pImpl->setDMLAndVMLDrawingOpen(false);
1026 }
1027 
1028 // Converts ARGB transparency (0..255) to drawingml alpha (opposite, and 0..100000)
1029 static OString lcl_ConvertTransparency(const Color& rColor)
1030 {
1031  if (rColor.GetTransparency() > 0)
1032  {
1033  sal_Int32 nTransparencyPercent = 100 - float(rColor.GetTransparency()) / 2.55;
1034  return OString::number(nTransparencyPercent * oox::drawingml::PER_PERCENT);
1035  }
1036 
1037  return OString();
1038 }
1039 
1041 {
1042  const SvxShadowItem& aShadowItem = rFrameFormat.GetShadow();
1043 
1044  // Output effects
1045  if (aShadowItem.GetLocation() == SvxShadowLocation::NONE)
1046  return;
1047 
1048  // Distance is measured diagonally from corner
1049  double nShadowDist
1050  = sqrt(static_cast<double>(aShadowItem.GetWidth()) * aShadowItem.GetWidth() * 2.0);
1051  OString aShadowDist(OString::number(TwipsToEMU(nShadowDist)));
1052  OString aShadowColor = msfilter::util::ConvertColor(aShadowItem.GetColor());
1053  OString aShadowAlpha = lcl_ConvertTransparency(aShadowItem.GetColor());
1054  sal_uInt32 nShadowDir = 0;
1055  switch (aShadowItem.GetLocation())
1056  {
1057  case SvxShadowLocation::TopLeft:
1058  nShadowDir = 13500000;
1059  break;
1060  case SvxShadowLocation::TopRight:
1061  nShadowDir = 18900000;
1062  break;
1063  case SvxShadowLocation::BottomLeft:
1064  nShadowDir = 8100000;
1065  break;
1066  case SvxShadowLocation::BottomRight:
1067  nShadowDir = 2700000;
1068  break;
1069  case SvxShadowLocation::NONE:
1070  case SvxShadowLocation::End:
1071  break;
1072  }
1073  OString aShadowDir(OString::number(nShadowDir));
1074 
1075  m_pImpl->getSerializer()->startElementNS(XML_a, XML_effectLst);
1076  m_pImpl->getSerializer()->startElementNS(XML_a, XML_outerShdw, XML_dist, aShadowDist, XML_dir,
1077  aShadowDir);
1078  if (aShadowAlpha.isEmpty())
1079  m_pImpl->getSerializer()->singleElementNS(XML_a, XML_srgbClr, XML_val, aShadowColor);
1080  else
1081  {
1082  m_pImpl->getSerializer()->startElementNS(XML_a, XML_srgbClr, XML_val, aShadowColor);
1083  m_pImpl->getSerializer()->singleElementNS(XML_a, XML_alpha, XML_val, aShadowAlpha);
1084  m_pImpl->getSerializer()->endElementNS(XML_a, XML_srgbClr);
1085  }
1086  m_pImpl->getSerializer()->endElementNS(XML_a, XML_outerShdw);
1087  m_pImpl->getSerializer()->endElementNS(XML_a, XML_effectLst);
1088 }
1089 
1090 void DocxSdrExport::writeDiagram(const SdrObject* sdrObject, const SwFrameFormat& rFrameFormat,
1091  int nDiagramId)
1092 {
1093  uno::Reference<drawing::XShape> xShape(const_cast<SdrObject*>(sdrObject)->getUnoShape(),
1094  uno::UNO_QUERY);
1095 
1096  // write necessary tags to document.xml
1097  Size aSize(sdrObject->GetSnapRect().GetWidth(), sdrObject->GetSnapRect().GetHeight());
1098  startDMLAnchorInline(&rFrameFormat, aSize);
1099 
1100  m_pImpl->getDrawingML()->WriteDiagram(xShape, nDiagramId);
1101 
1102  endDMLAnchorInline(&rFrameFormat);
1103 }
1104 
1106 {
1107  const SwFrameFormat& rFrameFormat = pParentFrame->GetFrameFormat();
1108  const SwNodeIndex* pNodeIndex = rFrameFormat.GetContent().GetContentIdx();
1109  sax_fastparser::FSHelperPtr pFS = m_pImpl->getSerializer();
1110 
1111  sal_uLong nStt = pNodeIndex ? pNodeIndex->GetIndex() + 1 : 0;
1112  sal_uLong nEnd = pNodeIndex ? pNodeIndex->GetNode().EndOfSectionIndex() : 0;
1113 
1114  //Save data here and restore when out of scope
1115  ExportDataSaveRestore aDataGuard(m_pImpl->getExport(), nStt, nEnd, pParentFrame);
1116 
1118  m_pImpl->setFlyFrameGraphic(true);
1119  m_pImpl->getExport().WriteText();
1120  m_pImpl->setFlyFrameGraphic(false);
1121 }
1122 
1124 {
1125  const editeng::SvxBorderLine* pBorderLine = nullptr;
1126 
1127  if (rBox.GetTop())
1128  {
1129  pBorderLine = rBox.GetTop();
1130  }
1131  else if (rBox.GetLeft())
1132  {
1133  pBorderLine = rBox.GetLeft();
1134  }
1135  else if (rBox.GetBottom())
1136  {
1137  pBorderLine = rBox.GetBottom();
1138  }
1139  else if (rBox.GetRight())
1140  {
1141  pBorderLine = rBox.GetRight();
1142  }
1143 
1144  if (!pBorderLine)
1145  {
1146  return;
1147  }
1148 
1149  sax_fastparser::FSHelperPtr pFS = m_pImpl->getSerializer();
1150  double fConverted(editeng::ConvertBorderWidthToWord(pBorderLine->GetBorderLineStyle(),
1151  pBorderLine->GetWidth()));
1152  OString sWidth(OString::number(TwipsToEMU(fConverted)));
1153  pFS->startElementNS(XML_a, XML_ln, XML_w, sWidth);
1154 
1155  pFS->startElementNS(XML_a, XML_solidFill);
1156  OString sColor(msfilter::util::ConvertColor(pBorderLine->GetColor()));
1157  pFS->singleElementNS(XML_a, XML_srgbClr, XML_val, sColor);
1158  pFS->endElementNS(XML_a, XML_solidFill);
1159 
1160  if (SvxBorderLineStyle::DASHED == pBorderLine->GetBorderLineStyle()) // Line Style is Dash type
1161  pFS->singleElementNS(XML_a, XML_prstDash, XML_val, "dash");
1162 
1163  pFS->endElementNS(XML_a, XML_ln);
1164 }
1165 
1166 void DocxSdrExport::writeDMLTextFrame(ww8::Frame const* pParentFrame, int nAnchorId,
1167  bool bTextBoxOnly)
1168 {
1169  bool bDMLAndVMLDrawingOpen = m_pImpl->getDMLAndVMLDrawingOpen();
1170  m_pImpl->setDMLAndVMLDrawingOpen(IsAnchorTypeInsideParagraph(pParentFrame));
1171 
1172  sax_fastparser::FSHelperPtr pFS = m_pImpl->getSerializer();
1173  const SwFrameFormat& rFrameFormat = pParentFrame->GetFrameFormat();
1174  const SwNodeIndex* pNodeIndex = rFrameFormat.GetContent().GetContentIdx();
1175 
1176  sal_uLong nStt = pNodeIndex ? pNodeIndex->GetIndex() + 1 : 0;
1177  sal_uLong nEnd = pNodeIndex ? pNodeIndex->GetNode().EndOfSectionIndex() : 0;
1178 
1179  //Save data here and restore when out of scope
1180  ExportDataSaveRestore aDataGuard(m_pImpl->getExport(), nStt, nEnd, pParentFrame);
1181 
1182  // When a frame has some low height, but automatically expanded due
1183  // to lots of contents, this size contains the real size.
1184  const Size aSize = pParentFrame->GetSize();
1185 
1186  uno::Reference<drawing::XShape> xShape;
1187  const SdrObject* pSdrObj = rFrameFormat.FindRealSdrObject();
1188  if (pSdrObj)
1189  xShape.set(const_cast<SdrObject*>(pSdrObj)->getUnoShape(), uno::UNO_QUERY);
1190  uno::Reference<beans::XPropertySet> xPropertySet(xShape, uno::UNO_QUERY);
1191  uno::Reference<beans::XPropertySetInfo> xPropSetInfo;
1192  if (xPropertySet.is())
1193  xPropSetInfo = xPropertySet->getPropertySetInfo();
1194 
1196  {
1197  drawing::TextVerticalAdjust eAdjust = drawing::TextVerticalAdjust_TOP;
1198  if (xPropSetInfo.is() && xPropSetInfo->hasPropertyByName("TextVerticalAdjust"))
1199  xPropertySet->getPropertyValue("TextVerticalAdjust") >>= eAdjust;
1200  m_pImpl->getBodyPrAttrList()->add(XML_anchor,
1202  }
1203 
1204  if (!bTextBoxOnly)
1205  {
1206  startDMLAnchorInline(&rFrameFormat, aSize);
1207 
1208  sax_fastparser::FastAttributeList* pDocPrAttrList
1210  pDocPrAttrList->add(XML_id, OString::number(nAnchorId).getStr());
1211  pDocPrAttrList->add(
1212  XML_name, OUStringToOString(rFrameFormat.GetName(), RTL_TEXTENCODING_UTF8).getStr());
1213  sax_fastparser::XFastAttributeListRef xDocPrAttrListRef(pDocPrAttrList);
1214  pFS->singleElementNS(XML_wp, XML_docPr, xDocPrAttrListRef);
1215 
1216  pFS->startElementNS(XML_a, XML_graphic, FSNS(XML_xmlns, XML_a),
1217  m_pImpl->getExport().GetFilter().getNamespaceURL(OOX_NS(dml)).toUtf8());
1218  pFS->startElementNS(XML_a, XML_graphicData, XML_uri,
1219  "http://schemas.microsoft.com/office/word/2010/wordprocessingShape");
1220  pFS->startElementNS(XML_wps, XML_wsp);
1221  pFS->singleElementNS(XML_wps, XML_cNvSpPr, XML_txBox, "1");
1222 
1223  uno::Any aRotation;
1224  m_pImpl->setDMLandVMLTextFrameRotation(0);
1225  if (xPropSetInfo.is() && xPropSetInfo->hasPropertyByName("FrameInteropGrabBag"))
1226  {
1227  uno::Sequence<beans::PropertyValue> propList;
1228  xPropertySet->getPropertyValue("FrameInteropGrabBag") >>= propList;
1229  auto pProp = std::find_if(propList.begin(), propList.end(),
1230  [](const beans::PropertyValue& rProp) {
1231  return rProp.Name == "mso-rotation-angle";
1232  });
1233  if (pProp != propList.end())
1234  aRotation = pProp->Value;
1235  }
1236  aRotation >>= m_pImpl->getDMLandVMLTextFrameRotation();
1237  OString sRotation(OString::number(
1238  oox::drawingml::ExportRotateClockwisify(m_pImpl->getDMLandVMLTextFrameRotation())));
1239  // Shape properties
1240  pFS->startElementNS(XML_wps, XML_spPr);
1241  if (m_pImpl->getDMLandVMLTextFrameRotation())
1242  {
1243  pFS->startElementNS(XML_a, XML_xfrm, XML_rot, sRotation);
1244  }
1245  else
1246  {
1247  pFS->startElementNS(XML_a, XML_xfrm);
1248  }
1249  pFS->singleElementNS(XML_a, XML_off, XML_x, "0", XML_y, "0");
1250  OString aWidth(OString::number(TwipsToEMU(aSize.Width())));
1251  OString aHeight(OString::number(TwipsToEMU(aSize.Height())));
1252  pFS->singleElementNS(XML_a, XML_ext, XML_cx, aWidth, XML_cy, aHeight);
1253  pFS->endElementNS(XML_a, XML_xfrm);
1254  OUString shapeType = "rect";
1255  if (xPropSetInfo.is() && xPropSetInfo->hasPropertyByName("FrameInteropGrabBag"))
1256  {
1257  uno::Sequence<beans::PropertyValue> propList;
1258  xPropertySet->getPropertyValue("FrameInteropGrabBag") >>= propList;
1259  auto pProp = std::find_if(propList.begin(), propList.end(),
1260  [](const beans::PropertyValue& rProp) {
1261  return rProp.Name == "mso-orig-shape-type";
1262  });
1263  if (pProp != propList.end())
1264  pProp->Value >>= shapeType;
1265  }
1266  //Empty shapeType will lead to corruption so to avoid that shapeType is set to default i.e. "rect"
1267  if (shapeType.isEmpty())
1268  shapeType = "rect";
1269 
1270  pFS->singleElementNS(XML_a, XML_prstGeom, XML_prst, shapeType.toUtf8());
1271  m_pImpl->setDMLTextFrameSyntax(true);
1272  m_pImpl->getExport().OutputFormat(pParentFrame->GetFrameFormat(), false, false, true);
1273  m_pImpl->setDMLTextFrameSyntax(false);
1274  writeDMLEffectLst(rFrameFormat);
1275  pFS->endElementNS(XML_wps, XML_spPr);
1276  }
1277 
1278  //first, loop through ALL of the chained textboxes to identify a unique ID for each chain, and sequence number for each textbox in that chain.
1279  if (!m_pImpl->getExport().m_bLinkedTextboxesHelperInitialized)
1280  {
1281  sal_Int32 nSeq = 0;
1282  for (auto& rEntry : m_pImpl->getExport().m_aLinkedTextboxesHelper)
1283  {
1284  //find the start of a textbox chain: has no PREVIOUS link, but does have NEXT link
1285  if (rEntry.second.sPrevChain.isEmpty() && !rEntry.second.sNextChain.isEmpty())
1286  {
1287  //assign this chain a unique ID and start a new sequence
1288  nSeq = 0;
1289  rEntry.second.nId = ++m_pImpl->getExport().m_nLinkedTextboxesChainId;
1290  rEntry.second.nSeq = nSeq;
1291 
1292  OUString sCheckForBrokenChains = rEntry.first;
1293 
1294  //follow the chain and assign the same id, and incremental sequence numbers.
1295  auto followChainIter
1296  = m_pImpl->getExport().m_aLinkedTextboxesHelper.find(rEntry.second.sNextChain);
1297  while (followChainIter != m_pImpl->getExport().m_aLinkedTextboxesHelper.end())
1298  {
1299  //verify that the NEXT textbox also points to me as the PREVIOUS.
1300  // A broken link indicates a leftover remnant that can be ignored.
1301  if (followChainIter->second.sPrevChain != sCheckForBrokenChains)
1302  break;
1303 
1304  followChainIter->second.nId = m_pImpl->getExport().m_nLinkedTextboxesChainId;
1305  followChainIter->second.nSeq = ++nSeq;
1306 
1307  //empty next chain indicates the end of the linked chain.
1308  if (followChainIter->second.sNextChain.isEmpty())
1309  break;
1310 
1311  sCheckForBrokenChains = followChainIter->first;
1312  followChainIter = m_pImpl->getExport().m_aLinkedTextboxesHelper.find(
1313  followChainIter->second.sNextChain);
1314  }
1315  }
1316  }
1317  m_pImpl->getExport().m_bLinkedTextboxesHelperInitialized = true;
1318  }
1319 
1320  m_pImpl->getExport().m_pParentFrame = nullptr;
1321  bool skipTxBxContent = false;
1322  bool isTxbxLinked = false;
1323 
1324  OUString sLinkChainName;
1325  if (xPropSetInfo.is())
1326  {
1327  if (xPropSetInfo->hasPropertyByName("LinkDisplayName"))
1328  xPropertySet->getPropertyValue("LinkDisplayName") >>= sLinkChainName;
1329  else if (xPropSetInfo->hasPropertyByName("ChainName"))
1330  xPropertySet->getPropertyValue("ChainName") >>= sLinkChainName;
1331  }
1332 
1333  // second, check if THIS textbox is linked and then decide whether to write the tag txbx or linkedTxbx
1334  auto linkedTextboxesIter = m_pImpl->getExport().m_aLinkedTextboxesHelper.find(sLinkChainName);
1335  if (linkedTextboxesIter != m_pImpl->getExport().m_aLinkedTextboxesHelper.end())
1336  {
1337  if ((linkedTextboxesIter->second.nId != 0) && (linkedTextboxesIter->second.nSeq != 0))
1338  {
1339  //not the first in the chain, so write the tag as linkedTxbx
1340  pFS->singleElementNS(XML_wps, XML_linkedTxbx, XML_id,
1341  OString::number(linkedTextboxesIter->second.nId), XML_seq,
1342  OString::number(linkedTextboxesIter->second.nSeq));
1343  /* no text content should be added to this tag,
1344  since the textbox is linked, the entire content
1345  is written in txbx block
1346  */
1347  skipTxBxContent = true;
1348  }
1349  else if ((linkedTextboxesIter->second.nId != 0) && (linkedTextboxesIter->second.nSeq == 0))
1350  {
1351  /* this is the first textbox in the chaining, we add the text content
1352  to this block*/
1353  //since the text box is linked, it needs an id.
1354  pFS->startElementNS(XML_wps, XML_txbx, XML_id,
1355  OString::number(linkedTextboxesIter->second.nId));
1356  isTxbxLinked = true;
1357  }
1358  }
1359 
1360  if (!skipTxBxContent)
1361  {
1362  if (!isTxbxLinked)
1363  pFS->startElementNS(XML_wps, XML_txbx); //text box is not linked, therefore no id.
1364 
1365  pFS->startElementNS(XML_w, XML_txbxContent);
1366 
1367  const SvxFrameDirectionItem& rDirection = rFrameFormat.GetFrameDir();
1368  if (rDirection.GetValue() == SvxFrameDirection::Vertical_RL_TB)
1369  m_pImpl->getBodyPrAttrList()->add(XML_vert, "vert");
1370 
1371  m_pImpl->setFlyFrameGraphic(true);
1372  m_pImpl->getExport().WriteText();
1373  if (m_pImpl->getParagraphSdtOpen())
1374  {
1375  m_pImpl->getExport().DocxAttrOutput().EndParaSdtBlock();
1376  m_pImpl->setParagraphSdtOpen(false);
1377  }
1378  m_pImpl->setFlyFrameGraphic(false);
1379 
1380  pFS->endElementNS(XML_w, XML_txbxContent);
1381  pFS->endElementNS(XML_wps, XML_txbx);
1382  }
1383 
1384  // We need to init padding to 0, if it's not set.
1385  // In LO the default is 0 and so ins attributes are not set when padding is 0
1386  // but in MSO the default is 254 / 127, so we need to set 0 padding explicitly
1387  if (!m_pImpl->getBodyPrAttrList()->hasAttribute(XML_lIns))
1388  m_pImpl->getBodyPrAttrList()->add(XML_lIns, OString::number(0));
1389  if (!m_pImpl->getBodyPrAttrList()->hasAttribute(XML_tIns))
1390  m_pImpl->getBodyPrAttrList()->add(XML_tIns, OString::number(0));
1391  if (!m_pImpl->getBodyPrAttrList()->hasAttribute(XML_rIns))
1392  m_pImpl->getBodyPrAttrList()->add(XML_rIns, OString::number(0));
1393  if (!m_pImpl->getBodyPrAttrList()->hasAttribute(XML_bIns))
1394  m_pImpl->getBodyPrAttrList()->add(XML_bIns, OString::number(0));
1395 
1396  sax_fastparser::XFastAttributeListRef xBodyPrAttrList(m_pImpl->getBodyPrAttrList());
1397  m_pImpl->setBodyPrAttrList(nullptr);
1398  if (!bTextBoxOnly)
1399  {
1400  pFS->startElementNS(XML_wps, XML_bodyPr, xBodyPrAttrList);
1401  // AutoSize of the Text Frame.
1402  const SwFormatFrameSize& rSize = rFrameFormat.GetFrameSize();
1403  pFS->singleElementNS(
1404  XML_a, (rSize.GetHeightSizeType() == ATT_VAR_SIZE ? XML_spAutoFit : XML_noAutofit));
1405  pFS->endElementNS(XML_wps, XML_bodyPr);
1406 
1407  pFS->endElementNS(XML_wps, XML_wsp);
1408  pFS->endElementNS(XML_a, XML_graphicData);
1409  pFS->endElementNS(XML_a, XML_graphic);
1410 
1411  // Relative size of the Text Frame.
1412  const sal_uInt8 nWidthPercent = rSize.GetWidthPercent();
1413  if (nWidthPercent && nWidthPercent != SwFormatFrameSize::SYNCED)
1414  {
1415  pFS->startElementNS(XML_wp14, XML_sizeRelH, XML_relativeFrom,
1416  (rSize.GetWidthPercentRelation() == text::RelOrientation::PAGE_FRAME
1417  ? "page"
1418  : "margin"));
1419  pFS->startElementNS(XML_wp14, XML_pctWidth);
1420  pFS->writeEscaped(OUString::number(nWidthPercent * oox::drawingml::PER_PERCENT));
1421  pFS->endElementNS(XML_wp14, XML_pctWidth);
1422  pFS->endElementNS(XML_wp14, XML_sizeRelH);
1423  }
1424  const sal_uInt8 nHeightPercent = rSize.GetHeightPercent();
1425  if (nHeightPercent && nHeightPercent != SwFormatFrameSize::SYNCED)
1426  {
1427  pFS->startElementNS(
1428  XML_wp14, XML_sizeRelV, XML_relativeFrom,
1429  (rSize.GetHeightPercentRelation() == text::RelOrientation::PAGE_FRAME ? "page"
1430  : "margin"));
1431  pFS->startElementNS(XML_wp14, XML_pctHeight);
1432  pFS->writeEscaped(OUString::number(nHeightPercent * oox::drawingml::PER_PERCENT));
1433  pFS->endElementNS(XML_wp14, XML_pctHeight);
1434  pFS->endElementNS(XML_wp14, XML_sizeRelV);
1435  }
1436 
1437  endDMLAnchorInline(&rFrameFormat);
1438  }
1439  m_pImpl->setDMLAndVMLDrawingOpen(bDMLAndVMLDrawingOpen);
1440 }
1441 
1442 void DocxSdrExport::writeVMLTextFrame(ww8::Frame const* pParentFrame, bool bTextBoxOnly)
1443 {
1444  bool bDMLAndVMLDrawingOpen = m_pImpl->getDMLAndVMLDrawingOpen();
1445  m_pImpl->setDMLAndVMLDrawingOpen(IsAnchorTypeInsideParagraph(pParentFrame));
1446 
1447  sax_fastparser::FSHelperPtr pFS = m_pImpl->getSerializer();
1448  const SwFrameFormat& rFrameFormat = pParentFrame->GetFrameFormat();
1449  const SwNodeIndex* pNodeIndex = rFrameFormat.GetContent().GetContentIdx();
1450 
1451  sal_uLong nStt = pNodeIndex ? pNodeIndex->GetIndex() + 1 : 0;
1452  sal_uLong nEnd = pNodeIndex ? pNodeIndex->GetNode().EndOfSectionIndex() : 0;
1453 
1454  //Save data here and restore when out of scope
1455  ExportDataSaveRestore aDataGuard(m_pImpl->getExport(), nStt, nEnd, pParentFrame);
1456 
1457  // When a frame has some low height, but automatically expanded due
1458  // to lots of contents, this size contains the real size.
1459  const Size aSize = pParentFrame->GetSize();
1460  m_pImpl->setFlyFrameSize(&aSize);
1461 
1462  m_pImpl->setTextFrameSyntax(true);
1465  m_pImpl->getTextFrameStyle() = "position:absolute";
1466  if (!bTextBoxOnly)
1467  {
1468  OString sRotation(OString::number(m_pImpl->getDMLandVMLTextFrameRotation() / -100));
1469  m_pImpl->getExport()
1470  .SdrExporter()
1471  .getTextFrameStyle()
1472  .append(";rotation:")
1473  .append(sRotation);
1474  }
1475  m_pImpl->getExport().OutputFormat(pParentFrame->GetFrameFormat(), false, false, true);
1476  m_pImpl->getFlyAttrList()->add(XML_style, m_pImpl->getTextFrameStyle().makeStringAndClear());
1477 
1478  const SdrObject* pObject = pParentFrame->GetFrameFormat().FindRealSdrObject();
1479  if (pObject != nullptr)
1480  {
1481  OUString sAnchorId = lclGetAnchorIdFromGrabBag(pObject);
1482  if (!sAnchorId.isEmpty())
1483  m_pImpl->getFlyAttrList()->addNS(XML_w14, XML_anchorId,
1484  OUStringToOString(sAnchorId, RTL_TEXTENCODING_UTF8));
1485  }
1486  sax_fastparser::XFastAttributeListRef xFlyAttrList(m_pImpl->getFlyAttrList().get());
1487  m_pImpl->getFlyAttrList().clear();
1488  sax_fastparser::XFastAttributeListRef xTextboxAttrList(m_pImpl->getTextboxAttrList().get());
1489  m_pImpl->getTextboxAttrList().clear();
1490  m_pImpl->setTextFrameSyntax(false);
1491  m_pImpl->setFlyFrameSize(nullptr);
1492  m_pImpl->getExport().m_pParentFrame = nullptr;
1493 
1494  if (!bTextBoxOnly)
1495  {
1496  pFS->startElementNS(XML_w, XML_pict);
1497  pFS->startElementNS(XML_v, XML_rect, xFlyAttrList);
1498  m_pImpl->textFrameShadow(rFrameFormat);
1499  if (m_pImpl->getFlyFillAttrList().is())
1500  {
1501  sax_fastparser::XFastAttributeListRef xFlyFillAttrList(
1502  m_pImpl->getFlyFillAttrList().get());
1503  m_pImpl->getFlyFillAttrList().clear();
1504  pFS->singleElementNS(XML_v, XML_fill, xFlyFillAttrList);
1505  }
1506  if (m_pImpl->getDashLineStyleAttr().is())
1507  {
1508  sax_fastparser::XFastAttributeListRef xDashLineStyleAttr(
1509  m_pImpl->getDashLineStyleAttr().get());
1510  m_pImpl->getDashLineStyleAttr().clear();
1511  pFS->singleElementNS(XML_v, XML_stroke, xDashLineStyleAttr);
1512  }
1513  pFS->startElementNS(XML_v, XML_textbox, xTextboxAttrList);
1514  }
1515  pFS->startElementNS(XML_w, XML_txbxContent);
1516  m_pImpl->setFlyFrameGraphic(true);
1517  m_pImpl->getExport().WriteText();
1518  if (m_pImpl->getParagraphSdtOpen())
1519  {
1520  m_pImpl->getExport().DocxAttrOutput().EndParaSdtBlock();
1521  m_pImpl->setParagraphSdtOpen(false);
1522  }
1523  m_pImpl->setFlyFrameGraphic(false);
1524  pFS->endElementNS(XML_w, XML_txbxContent);
1525  if (!bTextBoxOnly)
1526  {
1527  pFS->endElementNS(XML_v, XML_textbox);
1528 
1529  if (m_pImpl->getFlyWrapAttrList())
1530  {
1531  sax_fastparser::XFastAttributeListRef xFlyWrapAttrList(m_pImpl->getFlyWrapAttrList());
1532  m_pImpl->setFlyWrapAttrList(nullptr);
1533  pFS->singleElementNS(XML_w10, XML_wrap, xFlyWrapAttrList);
1534  }
1535 
1536  pFS->endElementNS(XML_v, XML_rect);
1537  pFS->endElementNS(XML_w, XML_pict);
1538  }
1539 
1540  m_pImpl->setDMLAndVMLDrawingOpen(bDMLAndVMLDrawingOpen);
1541 }
1542 
1543 bool DocxSdrExport::isTextBox(const SwFrameFormat& rFrameFormat)
1544 {
1545  return SwTextBoxHelper::isTextBox(&rFrameFormat, RES_FLYFRMFMT);
1546 }
1547 
1548 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
sal_uInt16 Count() const
long GetLeft() const
long Width() const
bool getTextFrameSyntax() const
bool IsContour() const
Definition: fmtsrnd.hxx:53
void writeDMLAndVMLDrawing(const SdrObject *sdrObj, const SwFrameFormat &rFrameFormat, int nAnchorId)
Writes shape in both DML and VML format.
sax_fastparser::FastAttributeList * getFlyWrapAttrList() const
long GetWidth() const
Helper class, so that the DocxExport::RestoreData() call will always happen.
SwNoTextNode * GetNoTextNodeFromSwFrameFormat(const SwFrameFormat &rFormat)
Get the SwNoTextNode associated with a SwFrameFormat if here is one.
static bool lcl_isLockedCanvas(const uno::Reference< drawing::XShape > &xShape)
sax_fastparser::FastAttributeList * m_pFlyWrapAttrList
bool getParagraphHasDrawing() const
long GetHeight() const
sal_uInt16 GetLower() const
sal_Int32 & getDMLandVMLTextFrameRotation()
const Size * m_pFlyFrameSize
static FastAttributeList * createAttrList()
double ConvertBorderWidthToWord(SvxBorderLineStyle, double)
std::unique_ptr< Impl > m_pImpl
TextVerticalAdjust GetTextVerticalAdjust(sal_Int32 nToken)
const sal_Int32 PER_PERCENT
void endDMLAnchorInline(const SwFrameFormat *pFrameFormat)
long Height() const
css::uno::Reference< css::xml::sax::XFastAttributeList > XFastAttributeListRef
const SwFormatVertOrient & GetVertOrient(bool=true) const
Definition: fmtornt.hxx:106
oox::drawingml::DrawingML * m_pDrawingML
#define FSNS(namespc, element)
rtl::Reference< sax_fastparser::FastAttributeList > & getFlyAttrList()
void setFlyFrameGraphic(bool bFlyFrameGraphic)
sal_uInt8 GetTransparency() const
SwTwips GetPos() const
Definition: fmtornt.hxx:92
sal_uIntPtr sal_uLong
virtual void SaveData(sal_uLong nStt, sal_uLong nEnd)
Remember some of the members so that we can recurse in WriteText().
Definition: wrtww8.cxx:1920
void writeDMLEffectLst(const SwFrameFormat &rFrameFormat)
Write , the effect list.
OUString GetDescription() const
void addNS(sal_Int32 nNamespaceToken, sal_Int32 nToken, const OString &rValue)
const SvxFrameDirectionItem & GetFrameDir(bool=true) const
Definition: frmatr.hxx:94
const SwFormatAnchor & GetAnchor(bool=true) const
Definition: fmtanchr.hxx:78
Holds data used by DocxSdrExport only.
DocxExport & m_rExport
void setFlyAttrList(const rtl::Reference< sax_fastparser::FastAttributeList > &pFlyAttrList)
SwNode & GetNode() const
Definition: ndindex.hxx:118
tools::Polygon CorrectWordWrapPolygonForExport(const tools::PolyPolygon &rPolyPoly, const SwNoTextNode *pNd)
Undo all scaling / move tricks of the wrap polygon done during import.
const editeng::SvxBorderLine * GetRight() const
sal_Int16 GetRelationOrient() const
Definition: fmtornt.hxx:55
The class that does all the actual DOCX export-related work.
Definition: docxexport.hxx:65
sax_fastparser::FastAttributeList * getBodyPrAttrList()
Attributes of , used during DML export of text frames.
bool getParagraphSdtOpen() const
void startDMLAnchorInline(const SwFrameFormat *pFrameFormat, const Size &rSize)
rtl::Reference< sax_fastparser::FastAttributeList > & getFlyFillAttrList()
void writeDiagram(const SdrObject *sdrObject, const SwFrameFormat &rFrameFormat, int nDiagramId)
Writes a diagram (smartart).
void setDMLAndVMLDrawingOpen(bool bDMLAndVMLDrawingOpen)
sal_Int32 m_nDMLandVMLTextFrameRotation
List of TextBoxes in this document: they are exported as part of their shape, never alone...
static bool isTextBox(const SwFrameFormat &rFrameFormat)
Is this a standalone TextFrame, or used as a TextBox of a shape?
IDocumentDrawModelAccess const & getIDocumentDrawModelAccess() const
Definition: doc.cxx:187
void writeDMLTextFrame(ww8::Frame const *pParentFrame, int nAnchorId, bool bTextBoxOnly=false)
Writes text frame in DML format.
virtual const tools::Rectangle & GetSnapRect() const
bool IsVisible() const
DstType sequenceToContainer(const css::uno::Sequence< SrcType > &i_Sequence)
bool getDMLAndVMLDrawingOpen() const
SvxShadowLocation GetLocation() const
MSO_SPT
#define X
bool getDMLTextFrameSyntax() const
const OUString & GetName() const
Definition: format.hxx:111
oox::drawingml::DrawingML * getDrawingML() const
sal_uLong GetIndex() const
Definition: ndindex.hxx:151
static bool isTextBox(const SwFrameFormat *pFormat, sal_uInt16 nType)
Is the frame format a text box?
const Size * getFlyFrameSize() const
const SwFormatSurround & GetSurround(bool=true) const
Definition: fmtsrnd.hxx:66
bool HasTextBoxContent(sal_uInt32 nShapeType)
bool getDMLTextFrameSyntax()
DocxSdrExport(DocxExport &rExport, const sax_fastparser::FSHelperPtr &pSerializer, oox::drawingml::DrawingML *pDrawingML)
void setParagraphSdtOpen(bool bParagraphSdtOpen)
const SwFrameFormat & GetFrameFormat() const
Get the writer SwFrameFormat that this object describes.
bool IsParagraphHasDrawing()
Impl(DocxExport &rExport, sax_fastparser::FSHelperPtr pSerializer, oox::drawingml::DrawingML *pDrawingML)
virtual SdrLayerID GetInvisibleHellId() const =0
#define RES_FLYFRMFMT
Definition: hintids.hxx:274
bool IsDMLAndVMLDrawingOpen()
ShapeFlag
void setParagraphHasDrawing(bool bParagraphHasDrawing)
const Color & GetColor() const
rtl::Reference< sax_fastparser::FastAttributeList > & getTextboxAttrList()
Attributes of the next v:textbox element.
const editeng::SvxBorderLine * GetTop() const
Style of a layout element.
Definition: frmfmt.hxx:57
#define SAL_MAX_INT32
rtl::Reference< sax_fastparser::FastAttributeList > m_pTextboxAttrList
void setFlyWrapAttrList(sax_fastparser::FastAttributeList *pFlyWrapAttrList)
virtual void RestoreData()
Restore what was saved in SaveData().
Definition: wrtww8.cxx:1952
bool m_bFlyFrameGraphic
Flag for checking drawing in a paragraph.
const editeng::SvxBorderLine * GetLeft() const
rtl::Reference< sax_fastparser::FastAttributeList > & getFlyAttrList()
const SwFormatAnchor & GetAnchor(bool=true) const
Definition: fmtanchr.hxx:81
OStringBuffer & getTextFrameStyle()
void setFlyFrameSize(const Size *pFlyFrameSize)
RndStdIds GetAnchorId() const
Definition: fmtanchr.hxx:65
const SwFormatHoriOrient & GetHoriOrient(bool=true) const
Definition: fmtornt.hxx:108
const Color & GetColor() const
ExportDataSaveRestore(DocxExport &rExport, sal_uLong nStt, sal_uLong nEnd, ww8::Frame const *pParentFrame)
int i
FlyAnchors.
Definition: fmtanchr.hxx:34
void setSerializer(const sax_fastparser::FSHelperPtr &pSerializer)
sal_uInt8 GetHeightPercent() const
Definition: fmtfsize.hxx:88
const ww8::Frame * m_pParentFrame
Definition: wrtww8.hxx:511
#define SAL_MIN_INT32
OUString GetTitle() const
sal_Int16 GetHoriOrient() const
Definition: fmtornt.hxx:87
Object Value
OStringBuffer & getTextFrameStyle()
OString ConvertColor(const Color &rColor)
sal_uInt16 GetSize() const
Marks a node in the document model.
Definition: ndindex.hxx:31
const SwDoc * GetDoc() const
The document is set in SwAttrPool now, therefore you always can access it.
Definition: format.hxx:119
sal_uInt8 GetWidthPercent() const
Definition: fmtfsize.hxx:91
rtl::Reference< sax_fastparser::FastAttributeList > & getFlyFillAttrList()
std::shared_ptr< FastSerializerHelper > FSHelperPtr
void textFrameShadow(const SwFrameFormat &rFrameFormat)
Writes wp wrapper code around an SdrObject, which itself is written using drawingML syntax...
rtl::Reference< sax_fastparser::FastAttributeList > m_pFlyAttrList
void setFlyWrapAttrList(sax_fastparser::FastAttributeList *pAttrList)
const double * GetRelativeWidth() const
sax_fastparser::FSHelperPtr m_pSerializer
sal_Int16 GetRelativeWidthRelation() const
OUString GetName() const
#define Y
sax_fastparser::FastAttributeList * m_pBodyPrAttrList
virtual SdrLayerID GetHellId() const =0
virtual SdrLayerID GetLayer() const
const Size * getFlyFrameSize()
When exporting fly frames, this holds the real size of the frame.
sal_Int16 GetHeightPercentRelation() const
Definition: fmtfsize.hxx:89
const SwNodeIndex * GetContentIdx() const
Definition: fmtcntnt.hxx:46
void setParagraphSdtOpen(bool bParagraphSdtOpen)
Set if paragraph sdt open in the current drawing.
OString OUStringToOString(const OUString &str, ConnectionSettings const *settings)
rtl::Reference< sax_fastparser::FastAttributeList > m_pDashLineStyleAttr
sal_uLong EndOfSectionIndex() const
Definition: node.hxx:677
const SvxULSpaceItem & GetULSpace(bool=true) const
Definition: frmatr.hxx:76
void writeVMLTextFrame(ww8::Frame const *pParentFrame, bool bTextBoxOnly=false)
Writes text frame in VML format.
rtl::Reference< sax_fastparser::FastAttributeList > & getDashLineStyle()
void setBodyPrAttrList(sax_fastparser::FastAttributeList *pBodyPrAttrList)
const SvxOpaqueItem & GetOpaque(bool=true) const
Definition: frmatr.hxx:80
iterator find(const OUString &rKey)
sal_Int16 GetRelationOrient() const
Definition: fmtornt.hxx:88
unsigned char sal_uInt8
void writeDMLDrawing(const SdrObject *pSdrObject, const SwFrameFormat *pFrameFormat, int nAnchorId)
Writes a drawing as DML.
Make exporting a Writer Frame easy.
rtl::Reference< sax_fastparser::FastAttributeList > m_pFlyFillAttrList
SwTwips GetPos() const
Definition: fmtornt.hxx:59
T ExportRotateClockwisify(T input)
void writeOnlyTextOfFrame(ww8::Frame const *pParentFrame)
Writes text from Textbox for
void setTextFrameSyntax(bool bTextFrameSyntax)
void setTextboxAttrList(const rtl::Reference< sax_fastparser::FastAttributeList > &pTextboxAttrList)
const Size & GetSize() const
The Size of the contained element.
static OString lcl_ConvertTransparency(const Color &rColor)
void add(sal_Int32 nToken, const sal_Char *pValue)
void writeBoxItemLine(const SvxBoxItem &rBox)
Writes the drawingML markup of a box item.
sal_Int16 GetVertOrient() const
Definition: fmtornt.hxx:54
sax_fastparser::FastAttributeList * getBodyPrAttrList() const
void setDMLTextFrameSyntax(bool bDMLTextFrameSyntax)
sax_fastparser::FastAttributeList * getFlyWrapAttrList()
const SwFormatFrameSize & GetFrameSize(bool=true) const
Definition: fmtfsize.hxx:104
const SwFormatContent & GetContent(bool=true) const
Definition: fmtcntnt.hxx:55
long GetRight() const
void setSerializer(const sax_fastparser::FSHelperPtr &pSerializer)
void writeVMLDrawing(const SdrObject *sdrObj, const SwFrameFormat &rFrameFormat)
Writes a drawing as VML data.
SvxBorderLineStyle GetBorderLineStyle() const
static bool isSupportedDMLShape(const uno::Reference< drawing::XShape > &xShape)
rtl::Reference< sax_fastparser::FastAttributeList > & getTextboxAttrList()
long GetWidth() const
sal_Int16 GetRelativeHeightRelation() const
#define SAL_WARN(area, stream)
virtual const tools::Rectangle & GetLogicRect() const
bool getFlyFrameGraphic() const
OStringBuffer m_aTextFrameStyle
const SwAttrSet & GetAttrSet() const
For querying the attribute array.
Definition: format.hxx:116
void setDrawingOpen(bool bDrawingOpen)
bool getTextFrameSyntax()
const sax_fastparser::FSHelperPtr & getSerializer()
void setParagraphHasDrawing(bool bParagraphHasDrawing)
void setDMLandVMLTextFrameRotation(sal_Int32 nDMLandVMLTextFrameRotation)
Frame is variable in Var-direction.
Definition: fmtfsize.hxx:37
const editeng::SvxBorderLine * GetBottom() const
sal_Int16 GetWidthPercentRelation() const
Definition: fmtfsize.hxx:92
static MSO_SPT GetCustomShapeType(const css::uno::Reference< css::drawing::XShape > &rXShape, ShapeFlag &nMirrorFlags, OUString &rShapeType, bool bOOXML=false)
SdrObject * FindRealSdrObject()
Definition: atrfrm.cxx:2686
const double * GetRelativeHeight() const
rtl::Reference< sax_fastparser::FastAttributeList > & getDashLineStyleAttr()
sal_uInt16 GetUpper() const
DocxExport & getExport() const
SwFrameSize GetHeightSizeType() const
Definition: fmtfsize.hxx:80
sal_uInt16 GetWidth() const
const SvxLRSpaceItem & GetLRSpace(bool=true) const
Definition: frmatr.hxx:74
EnumT GetValue() const
const SvxShadowItem & GetShadow(bool=true) const
Definition: frmatr.hxx:88