LibreOffice Module sw (master)  1
htmlflywriter.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 <com/sun/star/text/HoriOrientation.hpp>
21 #include <com/sun/star/text/VertOrientation.hpp>
22 #include <com/sun/star/text/RelOrientation.hpp>
23 #include <com/sun/star/beans/XPropertySet.hpp>
24 #include <hintids.hxx>
25 #include <tools/fract.hxx>
26 #include <svl/urihelper.hxx>
27 #include <vcl/svapp.hxx>
28 #include <sfx2/event.hxx>
29 #include <svtools/htmlkywd.hxx>
30 #include <svtools/htmlout.hxx>
31 #include <svtools/htmltokn.h>
32 #include <vcl/imap.hxx>
33 #include <vcl/imapobj.hxx>
34 #include <svtools/htmlcfg.hxx>
35 #include <svtools/HtmlWriter.hxx>
36 #include <svx/svdouno.hxx>
37 #include <svx/xoutbmp.hxx>
38 #include <editeng/boxitem.hxx>
39 #include <editeng/lrspitem.hxx>
40 #include <editeng/ulspitem.hxx>
41 #include <editeng/brushitem.hxx>
42 #include <sal/log.hxx>
43 #include <osl/diagnose.h>
44 
45 #include <fmtanchr.hxx>
46 #include <fmtornt.hxx>
47 #include <fmturl.hxx>
48 #include <fmtfsize.hxx>
49 #include <fmtclds.hxx>
50 #include <fmtcntnt.hxx>
51 #include <fmtsrnd.hxx>
52 #include <fmtinfmt.hxx>
53 #include <txtinet.hxx>
54 #include <frmatr.hxx>
55 #include <grfatr.hxx>
56 #include <flypos.hxx>
57 #include <ndgrf.hxx>
58 
59 #include <doc.hxx>
60 #include <ndtxt.hxx>
61 #include <pam.hxx>
62 #include <swerror.h>
63 #include <frmfmt.hxx>
64 #include "wrthtml.hxx"
65 #include "htmlatr.hxx"
66 #include "htmlfly.hxx"
67 #include "htmlreqifreader.hxx"
68 
69 using namespace css;
70 
88 
100 
107 
114 
122 
130 
131 static Writer& OutHTML_FrameFormatTableNode( Writer& rWrt, const SwFrameFormat& rFrameFormat );
132 static Writer& OutHTML_FrameFormatAsMulticol( Writer& rWrt, const SwFrameFormat& rFormat,
133  bool bInCntnr );
134 static Writer& OutHTML_FrameFormatAsSpacer( Writer& rWrt, const SwFrameFormat& rFormat );
136  const SwFrameFormat& rFrameFormat, bool bSpan );
137 static Writer& OutHTML_FrameFormatAsImage( Writer& rWrt, const SwFrameFormat& rFormat );
138 
139 static Writer& OutHTML_FrameFormatGrfNode( Writer& rWrt, const SwFrameFormat& rFormat,
140  bool bInCntnr );
141 
142 static Writer& OutHTML_FrameFormatAsMarquee( Writer& rWrt, const SwFrameFormat& rFrameFormat,
143  const SdrObject& rSdrObj );
144 
146 {
147  { OOO_STRING_SVTOOLS_HTML_O_SDonload, OOO_STRING_SVTOOLS_HTML_O_onload, SvMacroItemId::OnImageLoadDone },
148  { OOO_STRING_SVTOOLS_HTML_O_SDonabort, OOO_STRING_SVTOOLS_HTML_O_onabort, SvMacroItemId::OnImageLoadCancel },
149  { OOO_STRING_SVTOOLS_HTML_O_SDonerror, OOO_STRING_SVTOOLS_HTML_O_onerror, SvMacroItemId::OnImageLoadError },
150  { nullptr, nullptr, SvMacroItemId::NONE }
151 };
152 
154 {
157  { nullptr, nullptr, SvMacroItemId::NONE }
158 };
159 
160 sal_uInt16 SwHTMLWriter::GuessFrameType( const SwFrameFormat& rFrameFormat,
161  const SdrObject*& rpSdrObj )
162 {
164 
165  if( RES_DRAWFRMFMT == rFrameFormat.Which() )
166  {
167  // use an arbitrary draw object as the default value
168  eType = HTML_FRMTYPE_DRAW;
169 
170  const SdrObject *pObj =
171  SwHTMLWriter::GetMarqueeTextObj( static_cast<const SwDrawFrameFormat &>(rFrameFormat) );
172  if( pObj )
173  {
174  // scrolling text
175  rpSdrObj = pObj;
176  eType = HTML_FRMTYPE_MARQUEE;
177  }
178  else
179  {
180  pObj = GetHTMLControl( static_cast<const SwDrawFrameFormat &>(rFrameFormat) );
181 
182  if( pObj )
183  {
184  // Form control
185  rpSdrObj = pObj;
186  eType = HTML_FRMTYPE_CONTROL;
187  }
188  }
189  }
190  else
191  {
192  // use a text frame as the default value
193  eType = HTML_FRMTYPE_TEXT;
194 
195  const SwFormatContent& rFlyContent = rFrameFormat.GetContent();
196  sal_uLong nStt = rFlyContent.GetContentIdx()->GetIndex()+1;
197  const SwNode* pNd = m_pDoc->GetNodes()[ nStt ];
198 
199  if( pNd->IsGrfNode() )
200  {
201  // graphic node
202  eType = HTML_FRMTYPE_GRF;
203  }
204  else if( pNd->IsOLENode() )
205  {
206  // applet, plugin, floating frame
207  eType = static_cast<SwHTMLFrameType>(GuessOLENodeFrameType( *pNd ));
208  }
209  else
210  {
211  sal_uLong nEnd = m_pDoc->GetNodes()[nStt-1]->EndOfSectionIndex();
212 
213  const SfxPoolItem* pItem;
214  const SfxItemSet& rItemSet = rFrameFormat.GetAttrSet();
215  if( SfxItemState::SET == rItemSet.GetItemState( RES_COL,
216  true, &pItem ) &&
217  static_cast<const SwFormatCol *>(pItem)->GetNumCols() > 1 )
218  {
219  // frame with columns
220  eType = HTML_FRMTYPE_MULTICOL;
221  }
222  else if( pNd->IsTableNode() )
223  {
224  const SwTableNode *pTableNd = pNd->GetTableNode();
225  sal_uLong nTableEnd = pTableNd->EndOfSectionIndex();
226 
227  if( nTableEnd+1 == nEnd )
228  {
229  // table
230  eType = HTML_FRMTYPE_TABLE;
231  }
232  else if( nTableEnd+2 == nEnd )
233  {
234  // table with caption
235  eType = HTML_FRMTYPE_TABLE_CAP;
236  }
237  }
238  else if( pNd->IsTextNode() )
239  {
240  const SwTextNode *pTextNd = pNd->GetTextNode();
241 
242  bool bEmpty = false;
243  if( nStt==nEnd-1 && !pTextNd->Len() )
244  {
245  // empty frame? Only if no frame is
246  // anchored to the text or start node.
247  bEmpty = true;
248  if( m_pHTMLPosFlyFrames )
249  {
250  for( auto & pHTMLPosFlyFrame : *m_pHTMLPosFlyFrames )
251  {
252  sal_uLong nIdx = pHTMLPosFlyFrame->GetNdIndex().GetIndex();
253  bEmpty = (nIdx != nStt) && (nIdx != nStt-1);
254  if( !bEmpty || nIdx > nStt )
255  break;
256  }
257  }
258  }
259  if( bEmpty )
260  {
261  std::unique_ptr<SvxBrushItem> aBrush = rFrameFormat.makeBackgroundBrushItem();
264  if( aBrush &&
265  (GPOS_NONE != aBrush->GetGraphicPos() ||
266  aBrush->GetColor() != COL_TRANSPARENT ))
267  {
268  bEmpty = false;
269  }
270  }
271  if( bEmpty )
272  {
273  // empty frame
274  eType = HTML_FRMTYPE_EMPTY;
275  }
276  else if( m_pDoc->GetNodes()[nStt+1]->IsTableNode() )
277  {
278  const SwTableNode *pTableNd =
279  m_pDoc->GetNodes()[nStt+1]->GetTableNode();
280  if( pTableNd->EndOfSectionIndex()+1 == nEnd )
281  {
282  // table with heading
283  eType = HTML_FRMTYPE_TABLE_CAP;
284  }
285  }
286  }
287  }
288  }
289 
290  return static_cast< sal_uInt16 >(eType);
291 }
292 
294 {
295  OSL_ENSURE( HTML_CFG_MAX+1 == MAX_BROWSERS,
296  "number of browser configurations has changed" );
297 
298  SwPosFlyFrames aFlyPos(
299  m_pDoc->GetAllFlyFormats(m_bWriteAll ? nullptr : m_pCurrentPam.get(), true));
300 
301  for(const auto& rpItem : aFlyPos)
302  {
303  const SwFrameFormat& rFrameFormat = rpItem->GetFormat();
304  const SdrObject *pSdrObj = nullptr;
305  const SwPosition *pAPos;
306  const SwContentNode *pACNd;
307  SwHTMLFrameType eType = static_cast<SwHTMLFrameType>(GuessFrameType( rFrameFormat, pSdrObj ));
308 
309  AllHtmlFlags nMode;
310  const SwFormatAnchor& rAnchor = rFrameFormat.GetAnchor();
311  sal_Int16 eHoriRel = rFrameFormat.GetHoriOrient().GetRelationOrient();
312  switch( rAnchor.GetAnchorId() )
313  {
314  case RndStdIds::FLY_AT_PAGE:
315  case RndStdIds::FLY_AT_FLY:
316  nMode = aHTMLOutFramePageFlyTable[eType][m_nExportMode];
317  break;
318 
319  case RndStdIds::FLY_AT_PARA:
320  // frames that are anchored to a paragraph are only placed
321  // before the paragraph, if the paragraph has a
322  // spacing.
323  if( text::RelOrientation::FRAME == eHoriRel &&
324  (pAPos = rAnchor.GetContentAnchor()) != nullptr &&
325  (pACNd = pAPos->nNode.GetNode().GetContentNode()) != nullptr )
326  {
327  const SvxLRSpaceItem& rLRItem =
328  static_cast<const SvxLRSpaceItem&>(pACNd->GetAttr(RES_LR_SPACE));
329  if( rLRItem.GetTextLeft() || rLRItem.GetRight() )
330  {
331  nMode = aHTMLOutFrameParaFrameTable[eType][m_nExportMode];
332  break;
333  }
334  }
335  nMode = aHTMLOutFrameParaPrtAreaTable[eType][m_nExportMode];
336  break;
337 
338  case RndStdIds::FLY_AT_CHAR:
339  if( text::RelOrientation::FRAME == eHoriRel || text::RelOrientation::PRINT_AREA == eHoriRel )
340  nMode = aHTMLOutFrameParaPrtAreaTable[eType][m_nExportMode];
341  else
342  nMode = aHTMLOutFrameParaOtherTable[eType][m_nExportMode];
343  break;
344 
345  default:
346  nMode = aHTMLOutFrameParaPrtAreaTable[eType][m_nExportMode];
347  break;
348  }
349 
350  if( !m_pHTMLPosFlyFrames )
351  m_pHTMLPosFlyFrames.reset(new SwHTMLPosFlyFrames);
352 
353  m_pHTMLPosFlyFrames->insert( std::make_unique<SwHTMLPosFlyFrame>(*rpItem, pSdrObj, nMode) );
354  }
355 }
356 
357 bool SwHTMLWriter::OutFlyFrame( sal_uLong nNdIdx, sal_Int32 nContentIdx, HtmlPosition nPos,
358  HTMLOutContext *pContext )
359 {
360  bool bFlysLeft = false; // Are there still Flys left at the current node position?
361 
362  // OutFlyFrame can be called recursively. Thus, sometimes it is
363  // necessary to start over after a Fly was returned.
364  bool bRestart = true;
365  while( m_pHTMLPosFlyFrames && bRestart )
366  {
367  bFlysLeft = bRestart = false;
368 
369  // search for the beginning of the FlyFrames
370  size_t i {0};
371 
372  for( ; i < m_pHTMLPosFlyFrames->size() &&
373  (*m_pHTMLPosFlyFrames)[i]->GetNdIndex().GetIndex() < nNdIdx; i++ )
374  ;
375  for( ; !bRestart && i < m_pHTMLPosFlyFrames->size() &&
376  (*m_pHTMLPosFlyFrames)[i]->GetNdIndex().GetIndex() == nNdIdx; i++ )
377  {
378  SwHTMLPosFlyFrame *pPosFly = (*m_pHTMLPosFlyFrames)[i].get();
379  if( ( HtmlPosition::Any == nPos ||
380  pPosFly->GetOutPos() == nPos ) &&
381  pPosFly->GetContentIndex() == nContentIdx )
382  {
383  // It is important to remove it first, because additional
384  // elements or the whole array could be deleted on
385  // deeper recursion levels.
386  std::unique_ptr<SwHTMLPosFlyFrame> flyHolder = m_pHTMLPosFlyFrames->erase_extract(i);
387  i--;
388  if( m_pHTMLPosFlyFrames->empty() )
389  {
390  m_pHTMLPosFlyFrames.reset();
391  bRestart = true; // not really, only exit the loop
392  }
393 
394  if( pContext )
395  {
396  HTMLOutFuncs::FlushToAscii(Strm(), *pContext );
397  pContext = nullptr; // one time only
398  }
399 
400  OutFrameFormat( pPosFly->GetOutMode(), pPosFly->GetFormat(),
401  pPosFly->GetSdrObject() );
402  switch( pPosFly->GetOutFn() )
403  {
404  case HtmlOut::Div:
405  case HtmlOut::Span:
406  case HtmlOut::MultiCol:
407  case HtmlOut::TableNode:
408  bRestart = true; // It could become recursive here
409  break;
410  default: break;
411  }
412  }
413  else
414  {
415  bFlysLeft = true;
416  }
417  }
418  }
419 
420  return bFlysLeft;
421 }
422 
423 void SwHTMLWriter::OutFrameFormat( AllHtmlFlags nMode, const SwFrameFormat& rFrameFormat,
424  const SdrObject *pSdrObject )
425 {
426  HtmlContainerFlags nCntnrMode = nMode.nContainer;
427  HtmlOut nOutMode = nMode.nOut;
428  OString aContainerStr;
429  if( HtmlContainerFlags::NONE != nCntnrMode )
430  {
431 
432  if( m_bLFPossible && HtmlContainerFlags::Div == nCntnrMode )
433  OutNewLine();
434 
435  OStringBuffer sOut;
436  aContainerStr = (HtmlContainerFlags::Div == nCntnrMode)
439  sOut.append('<').append(GetNamespace() + aContainerStr).append(' ')
440  .append(OOO_STRING_SVTOOLS_HTML_O_class).append("=\"")
441  .append("sd-abs-pos").append('\"');
442  Strm().WriteOString( sOut.makeStringAndClear() );
443 
444  // Output a width for non-draw objects
445  HtmlFrmOpts nFrameFlags = HTML_FRMOPTS_CNTNR;
446 
447  // For frames with columns we can also output the background
448  if( HtmlOut::MultiCol == nOutMode )
450 
451  if( IsHTMLMode( HTMLMODE_BORDER_NONE ) )
452  nFrameFlags |= HtmlFrmOpts::SNoBorder;
453  OutCSS1_FrameFormatOptions( rFrameFormat, nFrameFlags, pSdrObject );
454  Strm().WriteChar( '>' );
455 
456  if( HtmlContainerFlags::Div == nCntnrMode )
457  {
458  IncIndentLevel();
459  m_bLFPossible = true;
460  }
461  }
462 
463  switch( nOutMode )
464  {
465  case HtmlOut::TableNode: // OK
466  OSL_ENSURE( aContainerStr.isEmpty(), "Table: Container is not supposed to be here" );
467  OutHTML_FrameFormatTableNode( *this, rFrameFormat );
468  break;
469  case HtmlOut::GraphicNode: // OK
470  OutHTML_FrameFormatGrfNode( *this, rFrameFormat, !aContainerStr.isEmpty() );
471  break;
472  case HtmlOut::OleNode: // OK
473  OutHTML_FrameFormatOLENode( *this, rFrameFormat, !aContainerStr.isEmpty() );
474  break;
475  case HtmlOut::OleGraphic: // OK
476  OutHTML_FrameFormatOLENodeGrf( *this, rFrameFormat, !aContainerStr.isEmpty() );
477  break;
478  case HtmlOut::Div:
479  case HtmlOut::Span:
480  OSL_ENSURE( aContainerStr.isEmpty(), "Div: Container is not supposed to be here" );
481  OutHTML_FrameFormatAsDivOrSpan( *this, rFrameFormat, HtmlOut::Span==nOutMode );
482  break;
483  case HtmlOut::MultiCol: // OK
484  OutHTML_FrameFormatAsMulticol( *this, rFrameFormat, !aContainerStr.isEmpty() );
485  break;
486  case HtmlOut::Spacer: // OK
487  OSL_ENSURE( aContainerStr.isEmpty(), "Spacer: Container is not supposed to be here" );
488  OutHTML_FrameFormatAsSpacer( *this, rFrameFormat );
489  break;
490  case HtmlOut::Control: // OK
492  static_cast<const SwDrawFrameFormat &>(rFrameFormat), dynamic_cast<const SdrUnoObj&>(*pSdrObject),
493  !aContainerStr.isEmpty() );
494  break;
495  case HtmlOut::AMarquee:
496  OutHTML_FrameFormatAsMarquee( *this, rFrameFormat, *pSdrObject );
497  break;
498  case HtmlOut::Marquee:
499  OSL_ENSURE( aContainerStr.isEmpty(), "Marquee: Container is not supposed to be here" );
501  static_cast<const SwDrawFrameFormat &>(rFrameFormat), *pSdrObject );
502  break;
504  OutHTML_FrameFormatAsImage( *this, rFrameFormat );
505  break;
506  }
507 
508  if( HtmlContainerFlags::Div == nCntnrMode )
509  {
510  DecIndentLevel();
511  if( m_bLFPossible )
512  OutNewLine();
513  HTMLOutFuncs::Out_AsciiTag( Strm(), GetNamespace() + OOO_STRING_SVTOOLS_HTML_division, false );
514  m_bLFPossible = true;
515  }
516  else if( HtmlContainerFlags::Span == nCntnrMode )
517  HTMLOutFuncs::Out_AsciiTag( Strm(), GetNamespace() + OOO_STRING_SVTOOLS_HTML_span, false );
518 }
519 
521  const OUString& rAlternateText,
522  HtmlFrmOpts nFrameOpts )
523 {
524  OString sRetEndTags;
525  OStringBuffer sOut;
526  const SfxPoolItem* pItem;
527  const SfxItemSet& rItemSet = rFrameFormat.GetAttrSet();
528 
529  // Name
530  if( (nFrameOpts & (HtmlFrmOpts::Id|HtmlFrmOpts::Name)) &&
531  !rFrameFormat.GetName().isEmpty() )
532  {
533  const char *pStr =
535  sOut.append(' ').append(pStr).
536  append("=\"");
537  Strm().WriteOString( sOut.makeStringAndClear() );
538  HTMLOutFuncs::Out_String( Strm(), rFrameFormat.GetName(), m_eDestEnc, &m_aNonConvertableCharacters );
539  sOut.append('\"');
540  }
541 
542  // Name
543  if( nFrameOpts & HtmlFrmOpts::Dir )
544  {
545  SvxFrameDirection nDir = GetHTMLDirection( rItemSet );
546  Strm().WriteOString( sOut.makeStringAndClear() );
547  OutDirection( nDir );
548  }
549 
550  // ALT
551  if( (nFrameOpts & HtmlFrmOpts::Alt) && !rAlternateText.isEmpty() )
552  {
553  sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_alt).
554  append("=\"");
555  Strm().WriteOString( sOut.makeStringAndClear() );
556  HTMLOutFuncs::Out_String( Strm(), rAlternateText, m_eDestEnc, &m_aNonConvertableCharacters );
557  sOut.append('\"');
558  }
559 
560  // ALIGN
561  const char *pStr = nullptr;
562  RndStdIds eAnchorId = rFrameFormat.GetAnchor().GetAnchorId();
563  if( (nFrameOpts & HtmlFrmOpts::Align) &&
564  ((RndStdIds::FLY_AT_PARA == eAnchorId) || (RndStdIds::FLY_AT_CHAR == eAnchorId)) )
565  {
566  // MIB 12.3.98: Wouldn't it be more clever to left-align frames that
567  // are anchored to a paragraph if necessary, instead of inserting them
568  // as being anchored to characters?
569  const SwFormatHoriOrient& rHoriOri = rFrameFormat.GetHoriOrient();
570  if( !(nFrameOpts & HtmlFrmOpts::SAlign) ||
571  text::RelOrientation::FRAME == rHoriOri.GetRelationOrient() ||
572  text::RelOrientation::PRINT_AREA == rHoriOri.GetRelationOrient() )
573  {
574  pStr = text::HoriOrientation::RIGHT == rHoriOri.GetHoriOrient()
577  }
578  }
579  if( (nFrameOpts & HtmlFrmOpts::Align) && !pStr &&
580  ( !(nFrameOpts & HtmlFrmOpts::SAlign) ||
581  (RndStdIds::FLY_AS_CHAR == eAnchorId) ) &&
582  SfxItemState::SET == rItemSet.GetItemState( RES_VERT_ORIENT, true, &pItem ))
583  {
584  switch( static_cast<const SwFormatVertOrient*>(pItem)->GetVertOrient() )
585  {
586  case text::VertOrientation::LINE_TOP: pStr = OOO_STRING_SVTOOLS_HTML_VA_top; break;
587  case text::VertOrientation::CHAR_TOP:
588  case text::VertOrientation::BOTTOM: pStr = OOO_STRING_SVTOOLS_HTML_VA_texttop; break; // not possible
589  case text::VertOrientation::LINE_CENTER:
590  case text::VertOrientation::CHAR_CENTER: pStr = OOO_STRING_SVTOOLS_HTML_VA_absmiddle; break; // not possible
591  case text::VertOrientation::CENTER: pStr = OOO_STRING_SVTOOLS_HTML_VA_middle; break;
592  case text::VertOrientation::LINE_BOTTOM:
593  case text::VertOrientation::CHAR_BOTTOM: pStr = OOO_STRING_SVTOOLS_HTML_VA_absbottom; break; // not possible
594  case text::VertOrientation::TOP: pStr = OOO_STRING_SVTOOLS_HTML_VA_bottom; break;
595  case text::VertOrientation::NONE: break;
596  }
597  }
598  if( pStr )
599  {
600  sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_align).append("=\"").
601  append(pStr).append("\"");
602  }
603 
604  // HSPACE and VSPACE
605  Size aTwipSpc( 0, 0 );
606  if( (nFrameOpts & (HtmlFrmOpts::Space|HtmlFrmOpts::MarginSize)) &&
607  SfxItemState::SET == rItemSet.GetItemState( RES_LR_SPACE, true, &pItem ))
608  {
609  aTwipSpc.setWidth(
610  ( static_cast<const SvxLRSpaceItem*>(pItem)->GetLeft() +
611  static_cast<const SvxLRSpaceItem*>(pItem)->GetRight() ) / 2 );
612  m_nDfltLeftMargin = m_nDfltRightMargin = aTwipSpc.Width();
613  }
614  if( (nFrameOpts & (HtmlFrmOpts::Space|HtmlFrmOpts::MarginSize)) &&
615  SfxItemState::SET == rItemSet.GetItemState( RES_UL_SPACE, true, &pItem ))
616  {
617  aTwipSpc.setHeight(
618  ( static_cast<const SvxULSpaceItem*>(pItem)->GetUpper() +
619  static_cast<const SvxULSpaceItem*>(pItem)->GetLower() ) / 2 );
620  m_nDfltTopMargin = m_nDfltBottomMargin = static_cast<sal_uInt16>(aTwipSpc.Height());
621  }
622 
623  if( (nFrameOpts & HtmlFrmOpts::Space) &&
624  (aTwipSpc.Width() || aTwipSpc.Height()) &&
626  {
627  Size aPixelSpc =
629  MapMode(MapUnit::MapTwip) );
630  if( !aPixelSpc.Width() && aTwipSpc.Width() )
631  aPixelSpc.setWidth( 1 );
632  if( !aPixelSpc.Height() && aTwipSpc.Height() )
633  aPixelSpc.setHeight( 1 );
634 
635  if( aPixelSpc.Width() )
636  {
637  sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_hspace).
638  append("=\"").append(static_cast<sal_Int32>(aPixelSpc.Width())).append("\"");
639  }
640 
641  if( aPixelSpc.Height() )
642  {
643  sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_vspace).
644  append("=\"").append(static_cast<sal_Int32>(aPixelSpc.Height())).append("\"");
645  }
646  }
647 
648  // The spacing must be considered for the size, if the corresponding flag
649  // is set.
650  if( nFrameOpts & HtmlFrmOpts::MarginSize )
651  {
652  aTwipSpc.setWidth( aTwipSpc.Width() * -2 );
653  aTwipSpc.setHeight( aTwipSpc.Height() * -2 );
654  }
655  else
656  {
657  aTwipSpc.setWidth( 0 );
658  aTwipSpc.setHeight( 0 );
659  }
660 
661  if( !(nFrameOpts & HtmlFrmOpts::AbsSize) &&
662  SfxItemState::SET == rItemSet.GetItemState( RES_BOX, true, &pItem ))
663  {
664  const SvxBoxItem* pBoxItem = static_cast<const SvxBoxItem*>(pItem);
665 
666  aTwipSpc.AdjustWidth(pBoxItem->CalcLineSpace( SvxBoxItemLine::LEFT ) );
667  aTwipSpc.AdjustWidth(pBoxItem->CalcLineSpace( SvxBoxItemLine::RIGHT ) );
668  aTwipSpc.AdjustHeight(pBoxItem->CalcLineSpace( SvxBoxItemLine::TOP ) );
669  aTwipSpc.AdjustHeight(pBoxItem->CalcLineSpace( SvxBoxItemLine::BOTTOM ) );
670  }
671 
672  // WIDTH and/or HEIGHT
673  // Output SwFrameSize::Variable/SwFrameSize::Minimum only, if ANYSIZE is set
674  if( (nFrameOpts & HtmlFrmOpts::Size) &&
675  SfxItemState::SET == rItemSet.GetItemState( RES_FRM_SIZE, true, &pItem ) &&
676  ( (nFrameOpts & HtmlFrmOpts::AnySize) ||
677  SwFrameSize::Fixed == static_cast<const SwFormatFrameSize *>(pItem)->GetHeightSizeType()) )
678  {
679  const SwFormatFrameSize *pFSItem = static_cast<const SwFormatFrameSize *>(pItem);
680  sal_uInt8 nPercentWidth = pFSItem->GetWidthPercent();
681  sal_uInt8 nPercentHeight = pFSItem->GetHeightPercent();
682 
683  // Size of the object in Twips without margins
684  Size aTwipSz( (nPercentWidth ? 0
685  : pFSItem->GetWidth()-aTwipSpc.Width()),
686  (nPercentHeight ? 0
687  : pFSItem->GetHeight()-aTwipSpc.Height()) );
688 
689  OSL_ENSURE( !aTwipSz.IsEmpty(), "Frame size minus spacing < 0!!!???" );
690  if( aTwipSz.Width() < 0 )
691  aTwipSz.setWidth( 0 );
692  if( aTwipSz.Height() < 0 )
693  aTwipSz.setHeight( 0 );
694 
695  Size aPixelSz( 0, 0 );
696  if( (aTwipSz.Width() || aTwipSz.Height()) &&
698  {
699  aPixelSz =
701  MapMode(MapUnit::MapTwip) );
702  if( !aPixelSz.Width() && aTwipSz.Width() )
703  aPixelSz.setWidth( 1 );
704  if( !aPixelSz.Height() && aTwipSz.Height() )
705  aPixelSz.setHeight( 1 );
706  }
707 
708  if( (nFrameOpts & HtmlFrmOpts::Width) &&
709  ((nPercentWidth && nPercentWidth!=255) || aPixelSz.Width()) )
710  {
711  sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_width).
712  append("=\"");
713  if( nPercentWidth )
714  sOut.append(static_cast<sal_Int32>(nPercentWidth)).append('%');
715  else
716  sOut.append(static_cast<sal_Int32>(aPixelSz.Width()));
717  sOut.append("\"");
718  }
719 
720  if( (nFrameOpts & HtmlFrmOpts::Height) &&
721  ((nPercentHeight && nPercentHeight!=255) || aPixelSz.Height()) )
722  {
723  sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_height).
724  append("=\"");
725  if( nPercentHeight )
726  sOut.append(static_cast<sal_Int32>(nPercentHeight)).append('%');
727  else
728  sOut.append(static_cast<sal_Int32>(aPixelSz.Height()));
729  sOut.append("\"");
730  }
731  }
732 
733  if (!sOut.isEmpty())
734  Strm().WriteOString( sOut.makeStringAndClear() );
735 
736  // Insert wrap for graphics that are anchored to a paragraph as
737  // <BR CLEAR=...> in the string
738  if( (nFrameOpts & HtmlFrmOpts::BrClear) &&
739  ((RndStdIds::FLY_AT_PARA == rFrameFormat.GetAnchor().GetAnchorId()) ||
740  (RndStdIds::FLY_AT_CHAR == rFrameFormat.GetAnchor().GetAnchorId())) &&
741  SfxItemState::SET == rItemSet.GetItemState( RES_SURROUND, true, &pItem ))
742  {
743  const SwFormatSurround* pSurround = static_cast<const SwFormatSurround*>(pItem);
744  sal_Int16 eHoriOri = rFrameFormat.GetHoriOrient().GetHoriOrient();
745  pStr = nullptr;
746  css::text::WrapTextMode eSurround = pSurround->GetSurround();
747  bool bAnchorOnly = pSurround->IsAnchorOnly();
748  switch( eHoriOri )
749  {
750  case text::HoriOrientation::RIGHT:
751  {
752  switch( eSurround )
753  {
754  case css::text::WrapTextMode_NONE:
755  case css::text::WrapTextMode_RIGHT:
757  break;
758  case css::text::WrapTextMode_LEFT:
759  case css::text::WrapTextMode_PARALLEL:
760  if( bAnchorOnly )
761  m_bClearRight = true;
762  break;
763  default:
764  ;
765  }
766  }
767  break;
768 
769  default:
770  // If a frame is centered, it gets left aligned. This
771  // should be taken into account here, too.
772  {
773  switch( eSurround )
774  {
775  case css::text::WrapTextMode_NONE:
776  case css::text::WrapTextMode_LEFT:
778  break;
779  case css::text::WrapTextMode_RIGHT:
780  case css::text::WrapTextMode_PARALLEL:
781  if( bAnchorOnly )
782  m_bClearLeft = true;
783  break;
784  default:
785  ;
786  }
787  }
788  break;
789 
790  }
791 
792  if( pStr )
793  {
794  sOut.append('<').append(OOO_STRING_SVTOOLS_HTML_linebreak).
795  append(' ').append(OOO_STRING_SVTOOLS_HTML_O_clear).
796  append("=\"").append(pStr).append("\">");
797  sRetEndTags = sOut.makeStringAndClear();
798  }
799  }
800  return sRetEndTags;
801 }
802 
803 void SwHTMLWriter::writeFrameFormatOptions(HtmlWriter& aHtml, const SwFrameFormat& rFrameFormat, std::u16string_view rAlternateText, HtmlFrmOpts nFrameOptions)
804 {
805  bool bReplacement = (nFrameOptions & HtmlFrmOpts::Replacement) || mbReqIF;
806  const SfxPoolItem* pItem;
807  const SfxItemSet& rItemSet = rFrameFormat.GetAttrSet();
808 
809  // Name
810  if( (nFrameOptions & (HtmlFrmOpts::Id|HtmlFrmOpts::Name)) &&
811  !rFrameFormat.GetName().isEmpty() && !bReplacement)
812  {
813  const char* pAttributeName = (nFrameOptions & HtmlFrmOpts::Id) ? OOO_STRING_SVTOOLS_HTML_O_id : OOO_STRING_SVTOOLS_HTML_O_name;
814  aHtml.attribute(pAttributeName, rFrameFormat.GetName());
815  }
816 
817  // Name
818  if (nFrameOptions & HtmlFrmOpts::Dir)
819  {
820  SvxFrameDirection nCurrentDirection = GetHTMLDirection(rItemSet);
821  OString sDirection = convertDirection(nCurrentDirection);
822  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_dir, sDirection);
823  }
824 
825  // alt
826  if( (nFrameOptions & HtmlFrmOpts::Alt) && !rAlternateText.empty() && !bReplacement )
827  {
828  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_alt, rAlternateText);
829  }
830 
831  // align
832  const char* pAlignString = nullptr;
833  RndStdIds eAnchorId = rFrameFormat.GetAnchor().GetAnchorId();
834  if( (nFrameOptions & HtmlFrmOpts::Align) &&
835  ((RndStdIds::FLY_AT_PARA == eAnchorId) || (RndStdIds::FLY_AT_CHAR == eAnchorId)) && !bReplacement)
836  {
837  const SwFormatHoriOrient& rHoriOri = rFrameFormat.GetHoriOrient();
838  if( !(nFrameOptions & HtmlFrmOpts::SAlign) ||
839  text::RelOrientation::FRAME == rHoriOri.GetRelationOrient() ||
840  text::RelOrientation::PRINT_AREA == rHoriOri.GetRelationOrient() )
841  {
842  pAlignString = text::HoriOrientation::RIGHT == rHoriOri.GetHoriOrient()
845  }
846  }
847  if( (nFrameOptions & HtmlFrmOpts::Align) && !pAlignString &&
848  ( !(nFrameOptions & HtmlFrmOpts::SAlign) ||
849  (RndStdIds::FLY_AS_CHAR == eAnchorId) ) &&
850  SfxItemState::SET == rItemSet.GetItemState( RES_VERT_ORIENT, true, &pItem ))
851  {
852  switch( static_cast<const SwFormatVertOrient*>(pItem)->GetVertOrient() )
853  {
854  case text::VertOrientation::LINE_TOP: pAlignString = OOO_STRING_SVTOOLS_HTML_VA_top; break;
855  case text::VertOrientation::CHAR_TOP:
856  case text::VertOrientation::BOTTOM: pAlignString = OOO_STRING_SVTOOLS_HTML_VA_texttop; break;
857  case text::VertOrientation::LINE_CENTER:
858  case text::VertOrientation::CHAR_CENTER: pAlignString = OOO_STRING_SVTOOLS_HTML_VA_absmiddle; break;
859  case text::VertOrientation::CENTER: pAlignString = OOO_STRING_SVTOOLS_HTML_VA_middle; break;
860  case text::VertOrientation::LINE_BOTTOM:
861  case text::VertOrientation::CHAR_BOTTOM: pAlignString = OOO_STRING_SVTOOLS_HTML_VA_absbottom; break;
862  case text::VertOrientation::TOP: pAlignString = OOO_STRING_SVTOOLS_HTML_VA_bottom; break;
863  case text::VertOrientation::NONE: break;
864  }
865  }
866  if (pAlignString && !bReplacement)
867  {
868  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_align, pAlignString);
869  }
870 
871  // hspace and vspace
872  Size aTwipSpc( 0, 0 );
873  if( (nFrameOptions & (HtmlFrmOpts::Space | HtmlFrmOpts::MarginSize)) &&
874  SfxItemState::SET == rItemSet.GetItemState( RES_LR_SPACE, true, &pItem ))
875  {
876  aTwipSpc.setWidth(
877  ( static_cast<const SvxLRSpaceItem*>(pItem)->GetLeft() +
878  static_cast<const SvxLRSpaceItem*>(pItem)->GetRight() ) / 2 );
879  m_nDfltLeftMargin = m_nDfltRightMargin = aTwipSpc.Width();
880  }
881  if( (nFrameOptions & (HtmlFrmOpts::Space|HtmlFrmOpts::MarginSize)) &&
882  SfxItemState::SET == rItemSet.GetItemState( RES_UL_SPACE, true, &pItem ))
883  {
884  aTwipSpc.setHeight(
885  ( static_cast<const SvxULSpaceItem*>(pItem)->GetUpper() +
886  static_cast<const SvxULSpaceItem*>(pItem)->GetLower() ) / 2 );
887  m_nDfltTopMargin = m_nDfltBottomMargin = static_cast<sal_uInt16>(aTwipSpc.Height());
888  }
889 
890  if( (nFrameOptions & HtmlFrmOpts::Space) &&
891  (aTwipSpc.Width() || aTwipSpc.Height()) &&
893  {
894  Size aPixelSpc =
896  MapMode(MapUnit::MapTwip) );
897  if( !aPixelSpc.Width() && aTwipSpc.Width() )
898  aPixelSpc.setWidth( 1 );
899  if( !aPixelSpc.Height() && aTwipSpc.Height() )
900  aPixelSpc.setHeight( 1 );
901 
902  if (aPixelSpc.Width())
903  {
904  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_hspace, static_cast<sal_Int32>(aPixelSpc.Width()));
905  }
906 
907  if (aPixelSpc.Height())
908  {
909  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_vspace, static_cast<sal_Int32>(aPixelSpc.Height()));
910  }
911  }
912 
913  // The spacing must be considered for the size, if the corresponding flag
914  // is set.
915  if( nFrameOptions & HtmlFrmOpts::MarginSize )
916  {
917  aTwipSpc.setWidth( aTwipSpc.Width() * -2 );
918  aTwipSpc.setHeight( aTwipSpc.Height() * -2 );
919  }
920  else
921  {
922  aTwipSpc.setWidth( 0 );
923  aTwipSpc.setHeight( 0 );
924  }
925 
926  if( !(nFrameOptions & HtmlFrmOpts::AbsSize) &&
927  SfxItemState::SET == rItemSet.GetItemState( RES_BOX, true, &pItem ))
928  {
929  const SvxBoxItem* pBoxItem = static_cast<const SvxBoxItem*>(pItem);
930 
931  aTwipSpc.AdjustWidth(pBoxItem->CalcLineSpace( SvxBoxItemLine::LEFT ) );
932  aTwipSpc.AdjustWidth(pBoxItem->CalcLineSpace( SvxBoxItemLine::RIGHT ) );
933  aTwipSpc.AdjustHeight(pBoxItem->CalcLineSpace( SvxBoxItemLine::TOP ) );
934  aTwipSpc.AdjustHeight(pBoxItem->CalcLineSpace( SvxBoxItemLine::BOTTOM ) );
935  }
936 
937  // "width" and/or "height"
938  // Only output SwFrameSize::Variable/SwFrameSize::Minimum if ANYSIZE is set
939  if( (nFrameOptions & HtmlFrmOpts::Size) &&
940  SfxItemState::SET == rItemSet.GetItemState( RES_FRM_SIZE, true, &pItem ) &&
941  ( (nFrameOptions & HtmlFrmOpts::AnySize) ||
942  SwFrameSize::Fixed == static_cast<const SwFormatFrameSize *>(pItem)->GetHeightSizeType()) )
943  {
944  const SwFormatFrameSize *pFSItem = static_cast<const SwFormatFrameSize *>(pItem);
945  sal_uInt8 nPercentWidth = pFSItem->GetWidthPercent();
946  sal_uInt8 nPercentHeight = pFSItem->GetHeightPercent();
947 
948  // Size of the object in Twips without margins
949  Size aTwipSz( (nPercentWidth ? 0
950  : pFSItem->GetWidth()-aTwipSpc.Width()),
951  (nPercentHeight ? 0
952  : pFSItem->GetHeight()-aTwipSpc.Height()) );
953 
954  OSL_ENSURE( !aTwipSz.IsEmpty(), "Frame size minus spacing < 0!!!???" );
955  if( aTwipSz.Width() < 0 )
956  aTwipSz.setWidth( 0 );
957  if( aTwipSz.Height() < 0 )
958  aTwipSz.setHeight( 0 );
959 
960  Size aPixelSz( 0, 0 );
961  if( (aTwipSz.Width() || aTwipSz.Height()) &&
963  {
964  aPixelSz =
966  MapMode(MapUnit::MapTwip) );
967  if( !aPixelSz.Width() && aTwipSz.Width() )
968  aPixelSz.setWidth( 1 );
969  if( !aPixelSz.Height() && aTwipSz.Height() )
970  aPixelSz.setHeight( 1 );
971  }
972 
973  if( (nFrameOptions & HtmlFrmOpts::Width) &&
974  ((nPercentWidth && nPercentWidth!=255) || aPixelSz.Width()) )
975  {
976  OString sWidth;
977  if (nPercentWidth)
978  sWidth = OString::number(static_cast<sal_Int32>(nPercentWidth)) + "%";
979  else
980  sWidth = OString::number(static_cast<sal_Int32>(aPixelSz.Width()));
982  }
983 
984  if( (nFrameOptions & HtmlFrmOpts::Height) &&
985  ((nPercentHeight && nPercentHeight!=255) || aPixelSz.Height()) )
986  {
987  OString sHeight;
988  if (nPercentHeight)
989  sHeight = OString::number(static_cast<sal_Int32>(nPercentHeight)) + "%";
990  else
991  sHeight = OString::number(static_cast<sal_Int32>(aPixelSz.Height()));
993  }
994  }
995 
996  // Insert wrap for graphics that are anchored to a paragraph as
997  // <BR CLEAR=...> in the string
998 
999  if( !((nFrameOptions & HtmlFrmOpts::BrClear) &&
1000  ((RndStdIds::FLY_AT_PARA == rFrameFormat.GetAnchor().GetAnchorId()) ||
1001  (RndStdIds::FLY_AT_CHAR == rFrameFormat.GetAnchor().GetAnchorId())) &&
1002  SfxItemState::SET == rItemSet.GetItemState( RES_SURROUND, true, &pItem )))
1003  return;
1004 
1005  const char* pSurroundString = nullptr;
1006 
1007  const SwFormatSurround* pSurround = static_cast<const SwFormatSurround*>(pItem);
1008  sal_Int16 eHoriOri = rFrameFormat.GetHoriOrient().GetHoriOrient();
1009  css::text::WrapTextMode eSurround = pSurround->GetSurround();
1010  bool bAnchorOnly = pSurround->IsAnchorOnly();
1011  switch( eHoriOri )
1012  {
1013  case text::HoriOrientation::RIGHT:
1014  {
1015  switch( eSurround )
1016  {
1017  case css::text::WrapTextMode_NONE:
1018  case css::text::WrapTextMode_RIGHT:
1019  pSurroundString = OOO_STRING_SVTOOLS_HTML_AL_right;
1020  break;
1021  case css::text::WrapTextMode_LEFT:
1022  case css::text::WrapTextMode_PARALLEL:
1023  if( bAnchorOnly )
1024  m_bClearRight = true;
1025  break;
1026  default:
1027  ;
1028  }
1029  }
1030  break;
1031 
1032  default:
1033  // If a frame is centered, it gets left aligned. This
1034  // should be taken into account here, too.
1035  {
1036  switch( eSurround )
1037  {
1038  case css::text::WrapTextMode_NONE:
1039  case css::text::WrapTextMode_LEFT:
1040  pSurroundString = OOO_STRING_SVTOOLS_HTML_AL_left;
1041  break;
1042  case css::text::WrapTextMode_RIGHT:
1043  case css::text::WrapTextMode_PARALLEL:
1044  if( bAnchorOnly )
1045  m_bClearLeft = true;
1046  break;
1047  default:
1048  break;
1049  }
1050  }
1051  break;
1052  }
1053 
1054  if (pSurroundString)
1055  {
1057  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_clear, pSurroundString);
1058  aHtml.end();
1059  }
1060 }
1061 
1062 namespace
1063 {
1064 
1065 OUString lclWriteOutImap(SwHTMLWriter& rHTMLWrt, const SfxItemSet& rItemSet, const SwFrameFormat& rFrameFormat,
1066  const Size& rRealSize, const ImageMap* pAltImgMap, const SwFormatURL*& pURLItem)
1067 {
1068  OUString aIMapName;
1069 
1070  const SfxPoolItem* pItem;
1071 
1072  // Only consider the URL attribute if no ImageMap was supplied
1073  if (!pAltImgMap && SfxItemState::SET == rItemSet.GetItemState( RES_URL, true, &pItem))
1074  {
1075  pURLItem = static_cast<const SwFormatURL*>( pItem);
1076  }
1077 
1078  // write ImageMap
1079  const ImageMap* pIMap = pAltImgMap;
1080  if( !pIMap && pURLItem )
1081  {
1082  pIMap = pURLItem->GetMap();
1083  }
1084 
1085  if (pIMap)
1086  {
1087  // make the name unique
1088  aIMapName = pIMap->GetName();
1089  OUString aNameBase;
1090  if (!aIMapName.isEmpty())
1091  aNameBase = aIMapName;
1092  else
1093  aNameBase = OOO_STRING_SVTOOLS_HTML_map;
1094 
1095  if (aIMapName.isEmpty())
1096  aIMapName = aNameBase + OUString::number(rHTMLWrt.m_nImgMapCnt);
1097 
1098  bool bFound;
1099  do
1100  {
1101  bFound = false;
1102  for (const OUString & rImgMapName : rHTMLWrt.m_aImgMapNames)
1103  {
1104  // TODO: Unicode: Comparison is case insensitive for ASCII
1105  // characters only now!
1106  if (aIMapName.equalsIgnoreAsciiCase(rImgMapName))
1107  {
1108  bFound = true;
1109  break;
1110  }
1111  }
1112  if (bFound)
1113  {
1114  rHTMLWrt.m_nImgMapCnt++;
1115  aIMapName = aNameBase + OUString::number( rHTMLWrt.m_nImgMapCnt );
1116  }
1117  } while (bFound);
1118 
1119  bool bScale = false;
1120  Fraction aScaleX(1, 1);
1121  Fraction aScaleY(1, 1);
1122 
1123  const SwFormatFrameSize& rFrameSize = rFrameFormat.GetFrameSize();
1124  const SvxBoxItem& rBox = rFrameFormat.GetBox();
1125 
1126  if (!rFrameSize.GetWidthPercent() && rRealSize.Width())
1127  {
1128  SwTwips nWidth = rFrameSize.GetWidth();
1129  nWidth -= rBox.CalcLineSpace(SvxBoxItemLine::LEFT) + rBox.CalcLineSpace(SvxBoxItemLine::RIGHT);
1130 
1131  OSL_ENSURE( nWidth > 0, "Are there any graphics that are 0 twip wide!?" );
1132  if (nWidth <= 0) // should not happen
1133  nWidth = 1;
1134 
1135  if (rRealSize.Width() != nWidth)
1136  {
1137  aScaleX = Fraction(nWidth, rRealSize.Width());
1138  bScale = true;
1139  }
1140  }
1141 
1142  if (!rFrameSize.GetHeightPercent() && rRealSize.Height())
1143  {
1144  SwTwips nHeight = rFrameSize.GetHeight();
1145 
1146  nHeight -= rBox.CalcLineSpace(SvxBoxItemLine::TOP) + rBox.CalcLineSpace(SvxBoxItemLine::BOTTOM);
1147 
1148  OSL_ENSURE( nHeight > 0, "Are there any graphics that are 0 twip high!?" );
1149  if (nHeight <= 0)
1150  nHeight = 1;
1151 
1152  if (rRealSize.Height() != nHeight)
1153  {
1154  aScaleY = Fraction(nHeight, rRealSize.Height());
1155  bScale = true;
1156  }
1157  }
1158 
1159  rHTMLWrt.m_aImgMapNames.push_back(aIMapName);
1160 
1161  OString aIndMap, aIndArea;
1162  const char *pIndArea = nullptr, *pIndMap = nullptr;
1163 
1164  if (rHTMLWrt.m_bLFPossible)
1165  {
1166  rHTMLWrt.OutNewLine( true );
1167  aIndMap = rHTMLWrt.GetIndentString();
1168  aIndArea = rHTMLWrt.GetIndentString(1);
1169  pIndArea = aIndArea.getStr();
1170  pIndMap = aIndMap.getStr();
1171  }
1172 
1173  if (bScale)
1174  {
1175  ImageMap aScaledIMap(*pIMap);
1176  aScaledIMap.Scale(aScaleX, aScaleY);
1177  HTMLOutFuncs::Out_ImageMap( rHTMLWrt.Strm(), rHTMLWrt.GetBaseURL(), aScaledIMap, aIMapName,
1179  rHTMLWrt.m_bCfgStarBasic,
1180  SAL_NEWLINE_STRING, pIndArea, pIndMap,
1181  rHTMLWrt.m_eDestEnc,
1182  &rHTMLWrt.m_aNonConvertableCharacters );
1183  }
1184  else
1185  {
1186  HTMLOutFuncs::Out_ImageMap( rHTMLWrt.Strm(), rHTMLWrt.GetBaseURL(), *pIMap, aIMapName,
1188  rHTMLWrt.m_bCfgStarBasic,
1189  SAL_NEWLINE_STRING, pIndArea, pIndMap,
1190  rHTMLWrt.m_eDestEnc,
1191  &rHTMLWrt.m_aNonConvertableCharacters );
1192  }
1193  }
1194  return aIMapName;
1195 }
1196 
1197 }
1198 
1199 Writer& OutHTML_Image( Writer& rWrt, const SwFrameFormat &rFrameFormat,
1200  const OUString& rGraphicURL,
1201  Graphic const & rGraphic, const OUString& rAlternateText,
1202  const Size &rRealSize, HtmlFrmOpts nFrameOpts,
1203  const char *pMarkType,
1204  const ImageMap *pAltImgMap,
1205  const OUString& rMimeType )
1206 {
1207  SwHTMLWriter& rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
1208  // <object data="..."> instead of <img src="...">
1209  bool bReplacement = (nFrameOpts & HtmlFrmOpts::Replacement) || rHTMLWrt.mbReqIF;
1210 
1211  if (rHTMLWrt.mbSkipImages)
1212  return rHTMLWrt;
1213 
1214  // if necessary, temporarily close an open attribute
1215  if( !rHTMLWrt.m_aINetFormats.empty() )
1216  {
1217  SwFormatINetFormat* pINetFormat = rHTMLWrt.m_aINetFormats.back();
1218  OutHTML_INetFormat( rWrt, *pINetFormat, false );
1219  }
1220 
1221  OUString aGraphicURL( rGraphicURL );
1222  if( !rHTMLWrt.mbEmbedImages && !HTMLOutFuncs::PrivateURLToInternalImg(aGraphicURL) && !rHTMLWrt.mpTempBaseURL )
1223  aGraphicURL = URIHelper::simpleNormalizedMakeRelative( rWrt.GetBaseURL(), aGraphicURL);
1224 
1225  const SfxPoolItem* pItem;
1226  const SfxItemSet& rItemSet = rFrameFormat.GetAttrSet();
1227 
1228  const SwFormatURL* pURLItem = nullptr;
1229  OUString aIMapName = lclWriteOutImap(rHTMLWrt, rItemSet, rFrameFormat, rRealSize, pAltImgMap, pURLItem);
1230 
1231  // put img into new line
1232  if( rHTMLWrt.m_bLFPossible )
1233  rHTMLWrt.OutNewLine( true );
1234 
1235  HtmlWriter aHtml(rWrt.Strm(), rHTMLWrt.maNamespace);
1236 
1237  // <a name=...></a>...<img ...>
1238  if( pMarkType && !rFrameFormat.GetName().isEmpty() )
1239  {
1240  rHTMLWrt.OutImplicitMark( rFrameFormat.GetName(), pMarkType );
1241  }
1242 
1243  // URL -> <a>...<img ... >...</a>
1244  const SvxMacroItem *pMacItem = nullptr;
1245  if (SfxItemState::SET == rItemSet.GetItemState(RES_FRMMACRO, true, &pItem))
1246  {
1247  pMacItem = static_cast<const SvxMacroItem *>(pItem);
1248  }
1249 
1250  if (pURLItem || pMacItem)
1251  {
1252  OUString aMapURL;
1253  OUString aName;
1254  OUString aTarget;
1255 
1256  if(pURLItem)
1257  {
1258  aMapURL = pURLItem->GetURL();
1259  aName = pURLItem->GetName();
1260  aTarget = pURLItem->GetTargetFrameName();
1261  }
1262 
1263  bool bEvents = pMacItem && !pMacItem->GetMacroTable().empty();
1264 
1265  if( !aMapURL.isEmpty() || !aName.isEmpty() || !aTarget.isEmpty() || bEvents )
1266  {
1267  aHtml.start(OOO_STRING_SVTOOLS_HTML_anchor);
1268 
1269  // Output "href" element if a link or macro exists
1270  if( !aMapURL.isEmpty() || bEvents )
1271  {
1272  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_href, OUStringToOString(rHTMLWrt.convertHyperlinkHRefValue(aMapURL), RTL_TEXTENCODING_UTF8));
1273  }
1274 
1275  if( !aName.isEmpty() )
1276  {
1277  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_name, OUStringToOString(aName, RTL_TEXTENCODING_UTF8));
1278  }
1279 
1280  if( !aTarget.isEmpty() )
1281  {
1282  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_target, OUStringToOString(aTarget, RTL_TEXTENCODING_UTF8));
1283  }
1284 
1285  if( pMacItem )
1286  {
1287  const SvxMacroTableDtor& rMacTable = pMacItem->GetMacroTable();
1288  if (!rMacTable.empty())
1289  {
1291  }
1292  }
1293  }
1294  }
1295 
1296  // <font color = ...>...<img ... >...</font>
1297  sal_uInt16 nBorderWidth = 0;
1298  if( (nFrameOpts & HtmlFrmOpts::Border) &&
1299  SfxItemState::SET == rItemSet.GetItemState( RES_BOX, true, &pItem ))
1300  {
1301  Size aTwipBorder( 0, 0 );
1302  const SvxBoxItem* pBoxItem = static_cast<const SvxBoxItem*>(pItem);
1303 
1304  const ::editeng::SvxBorderLine *pColBorderLine = nullptr;
1305  const ::editeng::SvxBorderLine *pBorderLine = pBoxItem->GetLeft();
1306  if( pBorderLine )
1307  {
1308  pColBorderLine = pBorderLine;
1309  aTwipBorder.AdjustWidth(pBorderLine->GetOutWidth() );
1310  }
1311 
1312  pBorderLine = pBoxItem->GetRight();
1313  if( pBorderLine )
1314  {
1315  pColBorderLine = pBorderLine;
1316  aTwipBorder.AdjustWidth(pBorderLine->GetOutWidth() );
1317  }
1318 
1319  pBorderLine = pBoxItem->GetTop();
1320  if( pBorderLine )
1321  {
1322  pColBorderLine = pBorderLine;
1323  aTwipBorder.AdjustHeight(pBorderLine->GetOutWidth() );
1324  }
1325 
1326  pBorderLine = pBoxItem->GetBottom();
1327  if( pBorderLine )
1328  {
1329  pColBorderLine = pBorderLine;
1330  aTwipBorder.AdjustHeight(pBorderLine->GetOutWidth() );
1331  }
1332 
1333  aTwipBorder.setWidth( aTwipBorder.Width() / 2 );
1334  aTwipBorder.setHeight( aTwipBorder.Height() / 2 );
1335 
1336  if( (aTwipBorder.Width() || aTwipBorder.Height()) &&
1338  {
1339  Size aPixelBorder =
1341  MapMode(MapUnit::MapTwip) );
1342  if( !aPixelBorder.Width() && aTwipBorder.Width() )
1343  aPixelBorder.setWidth( 1 );
1344  if( !aPixelBorder.Height() && aTwipBorder.Height() )
1345  aPixelBorder.setHeight( 1 );
1346 
1347  if( aPixelBorder.Width() )
1348  aPixelBorder.setHeight( 0 );
1349 
1350  nBorderWidth =
1351  static_cast<sal_uInt16>(aPixelBorder.Width() + aPixelBorder.Height());
1352  }
1353 
1354  if( pColBorderLine )
1355  {
1356  aHtml.start(OOO_STRING_SVTOOLS_HTML_font);
1357  HtmlWriterHelper::applyColor(aHtml, OOO_STRING_SVTOOLS_HTML_O_color, pColBorderLine->GetColor());
1358  }
1359  }
1360 
1361  OString aTag(OOO_STRING_SVTOOLS_HTML_image);
1362  if (bReplacement)
1363  // Write replacement graphic of OLE object as <object>.
1365  aHtml.start(aTag);
1366 
1367  OStringBuffer sBuffer;
1368  if(rHTMLWrt.mbEmbedImages)
1369  {
1370  OUString aGraphicInBase64;
1371  if (XOutBitmap::GraphicToBase64(rGraphic, aGraphicInBase64))
1372  {
1373  sBuffer.append(OOO_STRING_SVTOOLS_HTML_O_data);
1374  sBuffer.append(":");
1375  sBuffer.append(OUStringToOString(aGraphicInBase64, RTL_TEXTENCODING_UTF8));
1376  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_src, sBuffer.makeStringAndClear().getStr());
1377  }
1378  else
1379  rHTMLWrt.m_nWarn = WARN_SWG_POOR_LOAD;
1380  }
1381  else
1382  {
1383  sBuffer.append(OUStringToOString(aGraphicURL, RTL_TEXTENCODING_UTF8));
1384  OString aAttribute(OOO_STRING_SVTOOLS_HTML_O_src);
1385  if (bReplacement)
1386  aAttribute = OOO_STRING_SVTOOLS_HTML_O_data;
1387  aHtml.attribute(aAttribute, sBuffer.makeStringAndClear().getStr());
1388  }
1389 
1390  if (bReplacement)
1391  {
1392  // Handle XHTML type attribute for OLE replacement images.
1393  if (!rMimeType.isEmpty())
1394  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_type, rMimeType.toUtf8());
1395  }
1396 
1397  // Events
1398  if (SfxItemState::SET == rItemSet.GetItemState(RES_FRMMACRO, true, &pItem))
1399  {
1400  const SvxMacroTableDtor& rMacTable = static_cast<const SvxMacroItem *>(pItem)->GetMacroTable();
1401  if (!rMacTable.empty())
1402  {
1403  HtmlWriterHelper::applyEvents(aHtml, rMacTable, aImageEventTable, rHTMLWrt.m_bCfgStarBasic);
1404  }
1405  }
1406 
1407  // alt, align, width, height, hspace, vspace
1408  rHTMLWrt.writeFrameFormatOptions(aHtml, rFrameFormat, rAlternateText, nFrameOpts);
1409  if( rHTMLWrt.IsHTMLMode( HTMLMODE_ABS_POS_FLY ) )
1410  rHTMLWrt.OutCSS1_FrameFormatOptions( rFrameFormat, nFrameOpts );
1411 
1412  if ((nFrameOpts & HtmlFrmOpts::Border) && !bReplacement)
1413  {
1414  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_border, nBorderWidth);
1415  }
1416 
1417  if( pURLItem && pURLItem->IsServerMap() )
1418  {
1419  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_ismap);
1420  }
1421 
1422  if( !aIMapName.isEmpty() )
1423  {
1424  aHtml.attribute(OOO_STRING_SVTOOLS_HTML_O_usemap, OUString("#" + aIMapName));
1425  }
1426 
1427  if (bReplacement)
1428  {
1429  // XHTML object replacement image's alternate text doesn't use the
1430  // "alt" attribute.
1431  if (rAlternateText.isEmpty())
1432  // Empty alternate text is not valid.
1433  aHtml.characters(" ");
1434  else
1435  aHtml.characters(rAlternateText.toUtf8());
1436  }
1437 
1438  aHtml.flushStack();
1439 
1440  if( !rHTMLWrt.m_aINetFormats.empty() )
1441  {
1442  // There is still an attribute on the stack that has to be reopened
1443  SwFormatINetFormat *pINetFormat = rHTMLWrt.m_aINetFormats.back();
1444  OutHTML_INetFormat( rWrt, *pINetFormat, true );
1445  }
1446 
1447  return rHTMLWrt;
1448 }
1449 
1451  const char *pTag,
1452  const SvxBrushItem* pBrush,
1453  const OUString &rGraphicURL)
1454 {
1455  SwHTMLWriter & rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
1456 
1457  OUString aGraphicInBase64;
1458  OUString aLink;
1459  if( pBrush )
1460  {
1461  aLink = pBrush->GetGraphicLink();
1462  if(rHTMLWrt.mbEmbedImages || aLink.isEmpty())
1463  {
1464  const Graphic* pGrf = pBrush->GetGraphic();
1465  if( pGrf )
1466  {
1467  if( !XOutBitmap::GraphicToBase64(*pGrf, aGraphicInBase64) )
1468  {
1469  rHTMLWrt.m_nWarn = WARN_SWG_POOR_LOAD;
1470  }
1471  }
1472  }
1473  else if(!aLink.isEmpty())
1474  {
1475  if( rHTMLWrt.m_bCfgCpyLinkedGrfs )
1476  {
1477  rHTMLWrt.CopyLocalFileToINet( aLink );
1478  }
1479 
1480  }
1481  }
1482  else if(!rHTMLWrt.mbEmbedImages)
1483  {
1484  aLink = rGraphicURL;
1485  }
1486  if(!aLink.isEmpty())
1487  {
1489  aLink = URIHelper::simpleNormalizedMakeRelative( rWrt.GetBaseURL(), aLink);
1490  }
1491 
1492  OStringBuffer sOut;
1493  if( pTag )
1494  sOut.append('<').append(pTag);
1495 
1496  sOut.append(' ');
1497  sOut.append(OOO_STRING_SVTOOLS_HTML_O_style).append("=\"");
1498  if(!aLink.isEmpty())
1499  {
1500  sOut.append(OOO_STRING_SVTOOLS_HTML_O_src).append("=\"");
1501  rWrt.Strm().WriteOString( sOut.makeStringAndClear() );
1502  HTMLOutFuncs::Out_String( rWrt.Strm(), aLink, rHTMLWrt.m_eDestEnc, &rHTMLWrt.m_aNonConvertableCharacters );
1503  }
1504  else
1505  {
1506  sOut.append("list-style-image: ").append("url(").
1507  append(OOO_STRING_SVTOOLS_HTML_O_data).append(":");
1508  rWrt.Strm().WriteOString( sOut.makeStringAndClear() );
1509  HTMLOutFuncs::Out_String( rWrt.Strm(), aGraphicInBase64, rHTMLWrt.m_eDestEnc, &rHTMLWrt.m_aNonConvertableCharacters );
1510  sOut.append(");");
1511  }
1512  sOut.append('\"');
1513 
1514  if (pTag)
1515  sOut.append('>');
1516  rWrt.Strm().WriteOString( sOut.makeStringAndClear() );
1517 
1518  return rWrt;
1519 }
1520 
1521 static Writer& OutHTML_FrameFormatTableNode( Writer& rWrt, const SwFrameFormat& rFrameFormat )
1522 {
1523  SwHTMLWriter & rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
1524 
1525  const SwFormatContent& rFlyContent = rFrameFormat.GetContent();
1526  sal_uLong nStt = rFlyContent.GetContentIdx()->GetIndex()+1;
1527  sal_uLong nEnd = rHTMLWrt.m_pDoc->GetNodes()[nStt-1]->EndOfSectionIndex();
1528 
1529  OUString aCaption;
1530  bool bTopCaption = false;
1531 
1532  // Not const, because GetTable won't be const sometime later
1533  SwNode *pNd = rHTMLWrt.m_pDoc->GetNodes()[ nStt ];
1534  SwTableNode *pTableNd = pNd->GetTableNode();
1535  const SwTextNode *pTextNd = pNd->GetTextNode();
1536  if( !pTableNd && pTextNd )
1537  {
1538  // Table with heading
1539  bTopCaption = true;
1540  pTableNd = rHTMLWrt.m_pDoc->GetNodes()[nStt+1]->GetTableNode();
1541  }
1542  OSL_ENSURE( pTableNd, "Frame does not contain a table" );
1543  if( pTableNd )
1544  {
1545  sal_uLong nTableEnd = pTableNd->EndOfSectionIndex();
1546  OSL_ENSURE( nTableEnd == nEnd - 1 ||
1547  (nTableEnd == nEnd - 2 && !bTopCaption),
1548  "Invalid frame content for a table" );
1549 
1550  if( nTableEnd == nEnd - 2 )
1551  pTextNd = rHTMLWrt.m_pDoc->GetNodes()[nTableEnd+1]->GetTextNode();
1552  }
1553  if( pTextNd )
1554  aCaption = pTextNd->GetText();
1555 
1556  if( pTableNd )
1557  {
1558  HTMLSaveData aSaveData( rHTMLWrt, pTableNd->GetIndex()+1,
1559  pTableNd->EndOfSectionIndex(),
1560  true, &rFrameFormat );
1561  rHTMLWrt.m_bOutFlyFrame = true;
1562  OutHTML_SwTableNode( rHTMLWrt, *pTableNd, &rFrameFormat, &aCaption,
1563  bTopCaption );
1564  }
1565 
1566  return rWrt;
1567 }
1568 
1570  const SwFrameFormat& rFrameFormat,
1571  bool bInCntnr )
1572 {
1573  SwHTMLWriter & rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
1574 
1575  rHTMLWrt.ChangeParaToken( HtmlTokenId::NONE );
1576 
1577  // Close the current <DL>!
1578  rHTMLWrt.OutAndSetDefList( 0 );
1579 
1580  // output as Multicol
1581  if( rHTMLWrt.m_bLFPossible )
1582  rHTMLWrt.OutNewLine();
1583 
1584  OStringBuffer sOut;
1585  sOut.append('<').append(rHTMLWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_multicol);
1586 
1587  const SwFormatCol& rFormatCol = rFrameFormat.GetCol();
1588 
1589  // output the number of columns as COLS
1590  sal_uInt16 nCols = rFormatCol.GetNumCols();
1591  if( nCols )
1592  {
1593  sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_cols).
1594  append("=\"").append(static_cast<sal_Int32>(nCols)).append("\"");
1595  }
1596 
1597  // the Gutter width (minimum value) as GUTTER
1598  sal_uInt16 nGutter = rFormatCol.GetGutterWidth( true );
1599  if( nGutter!=USHRT_MAX )
1600  {
1601  if( nGutter && Application::GetDefaultDevice() )
1602  {
1603  nGutter = static_cast<sal_uInt16>(Application::GetDefaultDevice()
1604  ->LogicToPixel( Size(nGutter,0),
1605  MapMode(MapUnit::MapTwip) ).Width());
1606  }
1607  sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_gutter).
1608  append("=\"").append(static_cast<sal_Int32>(nGutter)).append("\"");
1609  }
1610 
1611  rWrt.Strm().WriteOString( sOut.makeStringAndClear() );
1612 
1613  // WIDTH
1614  HtmlFrmOpts nFrameFlags = HTML_FRMOPTS_MULTICOL;
1615  if( rHTMLWrt.IsHTMLMode( HTMLMODE_ABS_POS_FLY ) && !bInCntnr )
1616  nFrameFlags |= HTML_FRMOPTS_MULTICOL_CSS1;
1617  rHTMLWrt.OutFrameFormatOptions(rFrameFormat, OUString(), nFrameFlags);
1618  if( rHTMLWrt.IsHTMLMode( HTMLMODE_ABS_POS_FLY ) && !bInCntnr )
1619  rHTMLWrt.OutCSS1_FrameFormatOptions( rFrameFormat, nFrameFlags );
1620 
1621  rWrt.Strm().WriteChar( '>' );
1622 
1623  rHTMLWrt.m_bLFPossible = true;
1624  rHTMLWrt.IncIndentLevel(); // indent the content of Multicol
1625 
1626  const SwFormatContent& rFlyContent = rFrameFormat.GetContent();
1627  sal_uLong nStt = rFlyContent.GetContentIdx()->GetIndex();
1628  const SwStartNode* pSttNd = rWrt.m_pDoc->GetNodes()[nStt]->GetStartNode();
1629  OSL_ENSURE( pSttNd, "Where is the start node" );
1630 
1631  {
1632  // in a block, so that the old state can be restored in time
1633  // before the end
1634  HTMLSaveData aSaveData( rHTMLWrt, nStt+1,
1635  pSttNd->EndOfSectionIndex(),
1636  true, &rFrameFormat );
1637  rHTMLWrt.m_bOutFlyFrame = true;
1638  rHTMLWrt.Out_SwDoc( rWrt.m_pCurrentPam.get() );
1639  }
1640 
1641  rHTMLWrt.DecIndentLevel(); // indent the content of Multicol;
1642  if( rHTMLWrt.m_bLFPossible )
1643  rHTMLWrt.OutNewLine();
1645  rHTMLWrt.m_bLFPossible = true;
1646 
1647  return rWrt;
1648 }
1649 
1650 static Writer& OutHTML_FrameFormatAsSpacer( Writer& rWrt, const SwFrameFormat& rFrameFormat )
1651 {
1652  SwHTMLWriter & rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
1653 
1654  // if possible, output a line break before the graphic
1655  if( rHTMLWrt.m_bLFPossible )
1656  rHTMLWrt.OutNewLine( true );
1657 
1658  OString sOut =
1659  "<" + rHTMLWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_spacer " "
1662  rWrt.Strm().WriteOString( sOut );
1663 
1664  // ALIGN, WIDTH, HEIGHT
1665  OString aEndTags = rHTMLWrt.OutFrameFormatOptions(rFrameFormat, OUString(), HTML_FRMOPTS_SPACER);
1666 
1667  rWrt.Strm().WriteChar( '>' );
1668  if( !aEndTags.isEmpty() )
1669  rWrt.Strm().WriteOString( aEndTags );
1670 
1671  return rWrt;
1672 }
1673 
1675  const SwFrameFormat& rFrameFormat, bool bSpan)
1676 {
1677  SwHTMLWriter & rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
1678 
1679  OString aTag;
1680  if( !bSpan )
1681  {
1682  rHTMLWrt.ChangeParaToken( HtmlTokenId::NONE );
1683 
1684  // Close the current <DL>!
1685  rHTMLWrt.OutAndSetDefList( 0 );
1687  }
1688  else
1690 
1691  // output as DIV
1692  if( rHTMLWrt.m_bLFPossible )
1693  rHTMLWrt.OutNewLine();
1694 
1695  OStringBuffer sOut;
1696  sOut.append('<').append(rHTMLWrt.GetNamespace() + aTag);
1697 
1698  rWrt.Strm().WriteOString( sOut.makeStringAndClear() );
1699  HtmlFrmOpts nFrameFlags = HTML_FRMOPTS_DIV;
1700  if( rHTMLWrt.IsHTMLMode( HTMLMODE_BORDER_NONE ) )
1701  nFrameFlags |= HtmlFrmOpts::SNoBorder;
1702  OString aEndTags = rHTMLWrt.OutFrameFormatOptions(rFrameFormat, OUString(), nFrameFlags);
1703  rHTMLWrt.OutCSS1_FrameFormatOptions( rFrameFormat, nFrameFlags );
1704  rWrt.Strm().WriteChar( '>' );
1705 
1706  rHTMLWrt.IncIndentLevel(); // indent the content
1707  rHTMLWrt.m_bLFPossible = true;
1708 
1709  const SwFormatContent& rFlyContent = rFrameFormat.GetContent();
1710  sal_uLong nStt = rFlyContent.GetContentIdx()->GetIndex();
1711 
1712  // Output frame-anchored frames that are anchored to the start node
1713  rHTMLWrt.OutFlyFrame( nStt, 0, HtmlPosition::Any );
1714 
1715  const SwStartNode* pSttNd = rWrt.m_pDoc->GetNodes()[nStt]->GetStartNode();
1716  OSL_ENSURE( pSttNd, "Where is the start node" );
1717 
1718  {
1719  // in a block, so that the old state can be restored in time
1720  // before the end
1721  HTMLSaveData aSaveData( rHTMLWrt, nStt+1,
1722  pSttNd->EndOfSectionIndex(),
1723  true, &rFrameFormat );
1724  rHTMLWrt.m_bOutFlyFrame = true;
1725  rHTMLWrt.Out_SwDoc( rWrt.m_pCurrentPam.get() );
1726  }
1727 
1728  rHTMLWrt.DecIndentLevel(); // indent the content of Multicol;
1729  if( rHTMLWrt.m_bLFPossible )
1730  rHTMLWrt.OutNewLine();
1731  HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), rHTMLWrt.GetNamespace() + aTag, false );
1732 
1733  if( !aEndTags.isEmpty() )
1734  rWrt.Strm().WriteOString( aEndTags );
1735 
1736  return rWrt;
1737 }
1738 
1739 static Writer & OutHTML_FrameFormatAsImage( Writer& rWrt, const SwFrameFormat& rFrameFormat )
1740 {
1741  SwHTMLWriter& rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
1742 
1743  if (rHTMLWrt.mbSkipImages)
1744  return rWrt;
1745 
1746  ImageMap aIMap;
1747  Graphic aGraphic( const_cast<SwFrameFormat &>(rFrameFormat).MakeGraphic( &aIMap ) );
1748  Size aSz( 0, 0 );
1749  OUString GraphicURL;
1750  if(!rHTMLWrt.mbEmbedImages)
1751  {
1752  if( rHTMLWrt.GetOrigFileName() )
1753  GraphicURL = *rHTMLWrt.GetOrigFileName();
1754  if( aGraphic.GetType() == GraphicType::NONE ||
1755  XOutBitmap::WriteGraphic( aGraphic, GraphicURL,
1756  "JPG",
1757  (XOutFlags::UseGifIfPossible|
1758  XOutFlags::UseNativeIfPossible) ) != ERRCODE_NONE )
1759  {
1760  // empty or incorrect, because there is nothing to output
1761  rHTMLWrt.m_nWarn = WARN_SWG_POOR_LOAD;
1762  return rWrt;
1763  }
1764 
1765  GraphicURL = URIHelper::SmartRel2Abs(
1766  INetURLObject(rWrt.GetBaseURL()), GraphicURL,
1768 
1769  }
1770  OutHTML_Image( rWrt, rFrameFormat, GraphicURL, aGraphic, rFrameFormat.GetName(), aSz,
1771  HtmlFrmOpts::GenImgMask, "frame",
1772  aIMap.GetIMapObjectCount() ? &aIMap : nullptr );
1773 
1774  return rWrt;
1775 }
1776 
1777 static Writer& OutHTML_FrameFormatGrfNode( Writer& rWrt, const SwFrameFormat& rFrameFormat,
1778  bool bInCntnr )
1779 {
1780  SwHTMLWriter& rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
1781 
1782  if (rHTMLWrt.mbSkipImages)
1783  return rWrt;
1784 
1785  const SwFormatContent& rFlyContent = rFrameFormat.GetContent();
1786  sal_uLong nStt = rFlyContent.GetContentIdx()->GetIndex()+1;
1787  SwGrfNode *pGrfNd = rHTMLWrt.m_pDoc->GetNodes()[ nStt ]->GetGrfNode();
1788  OSL_ENSURE( pGrfNd, "Grf node expected" );
1789  if( !pGrfNd )
1790  return rWrt;
1791 
1792  HtmlFrmOpts nFrameFlags = bInCntnr ? HTML_FRMOPTS_IMG_CNTNR : HTML_FRMOPTS_IMG;
1793  if( rHTMLWrt.IsHTMLMode( HTMLMODE_ABS_POS_FLY ) && !bInCntnr )
1794  nFrameFlags |= HTML_FRMOPTS_IMG_CSS1;
1795 
1796  Graphic aGraphic = pGrfNd->GetGraphic();
1797  OUString aGraphicURL;
1798  OUString aMimeType;
1799  if(!rHTMLWrt.mbEmbedImages)
1800  {
1801  const SwMirrorGrf& rMirror = pGrfNd->GetSwAttrSet().GetMirrorGrf();
1802 
1803  if( !pGrfNd->IsLinkedFile() || MirrorGraph::Dont != rMirror.GetValue() )
1804  {
1805  // create a (mirrored) jpeg file
1806  if( rHTMLWrt.GetOrigFileName() )
1807  aGraphicURL = *rHTMLWrt.GetOrigFileName();
1808  else
1809  aGraphicURL = rHTMLWrt.GetBaseURL();
1810  pGrfNd->GetGrf( true );
1811 
1812  XOutFlags nFlags = XOutFlags::UseGifIfSensible |
1813  XOutFlags::UseNativeIfPossible;
1814  switch( rMirror.GetValue() )
1815  {
1816  case MirrorGraph::Vertical: nFlags = XOutFlags::MirrorHorz; break;
1817  case MirrorGraph::Horizontal: nFlags = XOutFlags::MirrorVert; break;
1818  case MirrorGraph::Both:
1819  nFlags = XOutFlags::MirrorVert | XOutFlags::MirrorHorz;
1820  break;
1821  default: break;
1822  }
1823 
1824  Size aMM100Size;
1825  const SwFormatFrameSize& rSize = rFrameFormat.GetFrameSize();
1826  aMM100Size = OutputDevice::LogicToLogic( rSize.GetSize(),
1827  MapMode( MapUnit::MapTwip ), MapMode( MapUnit::Map100thMM ));
1828 
1829  OUString aFilterName("");
1830 
1831  if (rHTMLWrt.mbReqIF)
1832  {
1833  // Writing image without fallback PNG in ReqIF mode: force PNG
1834  // output.
1835  aFilterName = "PNG";
1836  nFlags &= ~XOutFlags::UseNativeIfPossible;
1837  nFlags &= ~XOutFlags::UseGifIfSensible;
1838  aMimeType = "image/png";
1839  }
1840 
1841  const Graphic& rGraphic = pGrfNd->GetGrf();
1842 
1843  // So that Graphic::IsTransparent() can report true.
1844  if (!rGraphic.isAvailable())
1845  const_cast<Graphic&>(rGraphic).makeAvailable();
1846 
1847  ErrCode nErr = XOutBitmap::WriteGraphic( rGraphic, aGraphicURL,
1848  aFilterName, nFlags, &aMM100Size );
1849  if( nErr )
1850  {
1851  rHTMLWrt.m_nWarn = WARN_SWG_POOR_LOAD;
1852  return rWrt;
1853  }
1854  aGraphicURL = URIHelper::SmartRel2Abs(
1855  INetURLObject(rWrt.GetBaseURL()), aGraphicURL,
1857  }
1858  else
1859  {
1860  pGrfNd->GetFileFilterNms( &aGraphicURL, nullptr );
1861  if( rHTMLWrt.m_bCfgCpyLinkedGrfs )
1862  rWrt.CopyLocalFileToINet( aGraphicURL );
1863  }
1864 
1865  }
1866  uno::Reference<beans::XPropertySet> xGraphic(aGraphic.GetXGraphic(), uno::UNO_QUERY);
1867  if (xGraphic.is() && aMimeType.isEmpty())
1868  xGraphic->getPropertyValue("MimeType") >>= aMimeType;
1869 
1870  if (rHTMLWrt.mbReqIF)
1871  {
1872  // Write the original image as an RTF fragment.
1873  OUString aFileName;
1874  if (rHTMLWrt.GetOrigFileName())
1875  aFileName = *rHTMLWrt.GetOrigFileName();
1876  INetURLObject aURL(aFileName);
1877  OUString aName = aURL.getBase() + "_" +
1878  aURL.getExtension() + "_" +
1879  OUString::number(aGraphic.GetChecksum(), 16);
1880  aURL.setBase(aName);
1881  aURL.setExtension("ole");
1883 
1884  SvFileStream aOutStream(aFileName, StreamMode::WRITE);
1885  if (!SwReqIfReader::WrapGraphicInRtf(aGraphic, pGrfNd->GetTwipSize(), aOutStream))
1886  SAL_WARN("sw.html", "SwReqIfReader::WrapGraphicInRtf() failed");
1887 
1888  // Refer to this data.
1889  aFileName = URIHelper::simpleNormalizedMakeRelative(rWrt.GetBaseURL(), aFileName);
1890  rWrt.Strm().WriteOString("<" + rHTMLWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_object);
1891  rWrt.Strm().WriteOString(" data=\"" + aFileName.toUtf8() + "\"");
1892  rWrt.Strm().WriteOString(" type=\"text/rtf\"");
1893  rWrt.Strm().WriteOString(">");
1894  rHTMLWrt.OutNewLine();
1895  }
1896 
1897  OutHTML_Image( rWrt, rFrameFormat, aGraphicURL, aGraphic, pGrfNd->GetTitle(),
1898  pGrfNd->GetTwipSize(), nFrameFlags, "graphic", nullptr, aMimeType );
1899 
1900  if (rHTMLWrt.mbReqIF)
1901  rWrt.Strm().WriteOString("</" + rHTMLWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_object ">");
1902 
1903  return rWrt;
1904 }
1905 
1906 static Writer& OutHTML_FrameFormatAsMarquee( Writer& rWrt, const SwFrameFormat& rFrameFormat,
1907  const SdrObject& rSdrObj )
1908 {
1909  SwHTMLWriter & rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
1910 
1911  // get the edit engine attributes of the object as SW attributes and
1912  // sort them as Hints
1913  const SfxItemSet& rFormatItemSet = rFrameFormat.GetAttrSet();
1914  SfxItemSet aItemSet( *rFormatItemSet.GetPool(), svl::Items<RES_CHRATR_BEGIN,
1915  RES_CHRATR_END>{} );
1916  SwHTMLWriter::GetEEAttrsFromDrwObj( aItemSet, &rSdrObj );
1917  bool bCfgOutStylesOld = rHTMLWrt.m_bCfgOutStyles;
1918  rHTMLWrt.m_bCfgOutStyles = false;
1919  rHTMLWrt.m_bTextAttr = true;
1920  rHTMLWrt.m_bTagOn = true;
1921  Out_SfxItemSet( aHTMLAttrFnTab, rWrt, aItemSet, false );
1922  rHTMLWrt.m_bTextAttr = false;
1923 
1925  static_cast<const SwDrawFrameFormat &>(rFrameFormat),
1926  rSdrObj );
1927  rHTMLWrt.m_bTextAttr = true;
1928  rHTMLWrt.m_bTagOn = false;
1929  Out_SfxItemSet( aHTMLAttrFnTab, rWrt, aItemSet, false );
1930  rHTMLWrt.m_bTextAttr = false;
1931  rHTMLWrt.m_bCfgOutStyles = bCfgOutStylesOld;
1932 
1933  return rWrt;
1934 }
1935 
1936 Writer& OutHTML_HeaderFooter( Writer& rWrt, const SwFrameFormat& rFrameFormat,
1937  bool bHeader )
1938 {
1939  SwHTMLWriter & rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
1940 
1941  // output as Multicol
1942  rHTMLWrt.OutNewLine();
1943  OStringBuffer sOut;
1944  sOut.append(OOO_STRING_SVTOOLS_HTML_division).append(' ')
1945  .append(OOO_STRING_SVTOOLS_HTML_O_title).append("=\"")
1946  .append( bHeader ? "header" : "footer" ).append("\"");
1947  HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), rHTMLWrt.GetNamespace() + sOut.makeStringAndClear().getStr() );
1948 
1949  rHTMLWrt.IncIndentLevel(); // indent the content of Multicol;
1950 
1951  // Piece a spacer for the spacing together. Because the
1952  // <DL> or </DL> always produces a space between paragraphs, it is
1953  // subtracted if necessary.
1954  const SvxULSpaceItem& rULSpace = rFrameFormat.GetULSpace();
1955  sal_uInt16 nSize = bHeader ? rULSpace.GetLower() : rULSpace.GetUpper();
1956  rHTMLWrt.m_nHeaderFooterSpace = nSize;
1957 
1958  OString aSpacer;
1959  if( rHTMLWrt.IsHTMLMode(HTMLMODE_VERT_SPACER) &&
1961  {
1962  nSize -= HTML_PARSPACE;
1963  nSize = static_cast<sal_Int16>(Application::GetDefaultDevice()
1964  ->LogicToPixel( Size(nSize,0), MapMode(MapUnit::MapTwip) ).Width());
1965 
1966  aSpacer = OStringBuffer(OOO_STRING_SVTOOLS_HTML_spacer).
1967  append(' ').append(OOO_STRING_SVTOOLS_HTML_O_type).
1968  append("=\"").append(OOO_STRING_SVTOOLS_HTML_SPTYPE_vertical).append("\"").
1969  append(' ').append(OOO_STRING_SVTOOLS_HTML_O_size).
1970  append("=\"").append(static_cast<sal_Int32>(nSize)).append("\"").
1971  makeStringAndClear();
1972  }
1973 
1974  const SwFormatContent& rFlyContent = rFrameFormat.GetContent();
1975  sal_uLong nStt = rFlyContent.GetContentIdx()->GetIndex();
1976  const SwStartNode* pSttNd = rWrt.m_pDoc->GetNodes()[nStt]->GetStartNode();
1977  OSL_ENSURE( pSttNd, "Where is the start node" );
1978 
1979  if( !bHeader && !aSpacer.isEmpty() )
1980  {
1981  rHTMLWrt.OutNewLine();
1982  HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), rHTMLWrt.GetNamespace() + aSpacer.getStr() );
1983  }
1984 
1985  {
1986  // in a block, so that the old state can be restored in time
1987  // before the end. pFlyFormat doesn't need to be set here, because
1988  // PageDesc attributes cannot occur here
1989  HTMLSaveData aSaveData( rHTMLWrt, nStt+1,
1990  pSttNd->EndOfSectionIndex() );
1991 
1992  if( bHeader )
1993  rHTMLWrt.m_bOutHeader = true;
1994  else
1995  rHTMLWrt.m_bOutFooter = true;
1996 
1997  rHTMLWrt.Out_SwDoc( rWrt.m_pCurrentPam.get() );
1998  }
1999 
2000  if( bHeader && !aSpacer.isEmpty() )
2001  {
2002  rHTMLWrt.OutNewLine();
2003  HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), rHTMLWrt.GetNamespace() + aSpacer.getStr() );
2004  }
2005 
2006  rHTMLWrt.DecIndentLevel(); // indent the content of Multicol;
2007  rHTMLWrt.OutNewLine();
2009 
2010  rHTMLWrt.m_nHeaderFooterSpace = 0;
2011 
2012  return rWrt;
2013 }
2014 
2015 void SwHTMLWriter::AddLinkTarget( const OUString& rURL )
2016 {
2017  if( rURL.isEmpty() || rURL[0] != '#' )
2018  return;
2019 
2020  // There might be a '|' as delimiter (if the link has been inserted
2021  // freshly) or a '%7c' or a '%7C' if the document has been saved and
2022  // loaded already.
2023  sal_Int32 nPos = rURL.getLength();
2024  bool bFound = false, bEncoded = false;
2025  while( !bFound && nPos > 0 )
2026  {
2027  sal_Unicode c = rURL[ --nPos ];
2028  switch( c )
2029  {
2030  case cMarkSeparator:
2031  bFound = true;
2032  break;
2033  case '%':
2034  bFound = (rURL.getLength() - nPos) >=3 && rURL[ nPos+1 ] == '7';
2035  if(bFound)
2036  {
2037  c = rURL[ nPos+2 ];
2038  bFound = (c == 'C' || c == 'c');
2039  }
2040  if( bFound )
2041  bEncoded = true;
2042  }
2043  }
2044  if( !bFound || nPos < 2 ) // at least "#a|..."
2045  return;
2046 
2047  OUString aURL( rURL.copy( 1 ) );
2048 
2049  // nPos-1+1/3 (-1 because of Erase)
2050  OUString sCmp = aURL.copy(bEncoded ? nPos+2 : nPos).replaceAll(" ","");
2051  if( sCmp.isEmpty() )
2052  return;
2053 
2054  sCmp = sCmp.toAsciiLowerCase();
2055 
2056  if( sCmp == "region" ||
2057  sCmp == "frame" ||
2058  sCmp == "graphic" ||
2059  sCmp == "ole" ||
2060  sCmp == "table" )
2061  {
2062  // Just remember it in a sorted array
2063  if( bEncoded )
2064  {
2065  aURL = aURL.replaceAt( nPos - 1, 3, OUString(cMarkSeparator) );
2066  }
2067  m_aImplicitMarks.insert( aURL );
2068  }
2069  else if( sCmp == "outline" )
2070  {
2071  // Here, we need position and name. That's why we sort a
2072  // sal_uInt16 and a string array ourselves.
2073  OUString aOutline( aURL.copy( 0, nPos-1 ) );
2074  SwPosition aPos( *m_pCurrentPam->GetPoint() );
2075  if( m_pDoc->GotoOutline( aPos, aOutline ) )
2076  {
2077  sal_uInt32 nIdx = aPos.nNode.GetIndex();
2078 
2079  decltype(m_aOutlineMarkPoss)::size_type nIns=0;
2080  while( nIns < m_aOutlineMarkPoss.size() &&
2081  m_aOutlineMarkPoss[nIns] < nIdx )
2082  nIns++;
2083 
2084  m_aOutlineMarkPoss.insert( m_aOutlineMarkPoss.begin()+nIns, nIdx );
2085  if( bEncoded )
2086  {
2087  aURL = aURL.replaceAt( nPos - 1, 3, OUString(cMarkSeparator) );
2088  }
2089  m_aOutlineMarks.insert( m_aOutlineMarks.begin()+nIns, aURL );
2090  }
2091  }
2092 }
2093 
2095 {
2096  const SwTextINetFormat* pTextAttr;
2097 
2098  for (const SfxPoolItem* pItem : m_pDoc->GetAttrPool().GetItemSurrogates(RES_TXTATR_INETFMT))
2099  {
2100  auto pINetFormat = dynamic_cast<const SwFormatINetFormat*>(pItem);
2101  const SwTextNode* pTextNd;
2102 
2103  if( pINetFormat &&
2104  nullptr != ( pTextAttr = pINetFormat->GetTextINetFormat()) &&
2105  nullptr != ( pTextNd = pTextAttr->GetpTextNode() ) &&
2106  pTextNd->GetNodes().IsDocNodes() )
2107  {
2108  AddLinkTarget( pINetFormat->GetValue() );
2109  }
2110  }
2111 
2112  for (const SfxPoolItem* pItem : m_pDoc->GetAttrPool().GetItemSurrogates(RES_URL))
2113  {
2114  auto pURL = dynamic_cast<const SwFormatURL*>(pItem);
2115  if( pURL )
2116  {
2117  AddLinkTarget( pURL->GetURL() );
2118  const ImageMap *pIMap = pURL->GetMap();
2119  if( pIMap )
2120  {
2121  for( size_t i=0; i<pIMap->GetIMapObjectCount(); ++i )
2122  {
2123  const IMapObject* pObj = pIMap->GetIMapObject( i );
2124  if( pObj )
2125  {
2126  AddLinkTarget( pObj->GetURL() );
2127  }
2128  }
2129  }
2130  }
2131  }
2132 }
2133 
2134 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
const HtmlFrmOpts HTML_FRMOPTS_SPACER
#define OOO_STRING_SVTOOLS_HTML_O_src
Graphic GetGraphic() const
Definition: ndnotxt.cxx:229
Starts a section of nodes in the document model.
Definition: node.hxx:312
static SVT_DLLPUBLIC void applyEvents(HtmlWriter &rHtmlWriter, const SvxMacroTableDtor &rMacroTable, const HTMLOutEvent *pEventTable, bool bOutStarBasic)
#define OOO_STRING_SVTOOLS_HTML_O_vspace
#define OOO_STRING_SVTOOLS_HTML_O_onload
std::set< SwPosFlyFramePtr, SwPosFlyFrameCmp > SwPosFlyFrames
Definition: flypos.hxx:51
bool m_bCfgCpyLinkedGrfs
Definition: wrthtml.hxx:344
tools::Long GetWidth() const
static const SdrObject * GetMarqueeTextObj(const SwDrawFrameFormat &rFormat)
constexpr TypedWhichId< SwFormatSurround > RES_SURROUND(101)
URL aURL
sal_uInt16 GuessFrameType(const SwFrameFormat &rFrameFormat, const SdrObject *&rpStrObj)
sal_uLong GetIndex() const
Definition: node.hxx:291
const OUString & GetBaseURL() const
Definition: shellio.hxx:439
#define OOO_STRING_SVTOOLS_HTML_VA_texttop
static Writer & OutHTML_FrameFormatAsSpacer(Writer &rWrt, const SwFrameFormat &rFormat)
const SwFormatCol & GetCol(bool=true) const
Definition: fmtclds.hxx:168
#define OOO_STRING_SVTOOLS_HTML_O_clear
#define OOO_STRING_SVTOOLS_HTML_VA_bottom
Marks a position in the document model.
Definition: pam.hxx:35
std::vector< OUString > m_aImgMapNames
Definition: wrthtml.hxx:280
bool IsGrfNode() const
Definition: node.hxx:660
#define OOO_STRING_SVTOOLS_HTML_SPTYPE_vertical
HtmlContainerFlags nContainer
Definition: htmlfly.hxx:88
HtmlOut nOut
Definition: htmlfly.hxx:86
sal_uInt16 GetLower() const
static SVT_DLLPUBLIC SvStream & Out_String(SvStream &, const OUString &, rtl_TextEncoding eDestEnc, OUString *pNonConvertableChars=nullptr)
static SVT_DLLPUBLIC void applyColor(HtmlWriter &rHtmlWriter, const OString &aAttributeName, const Color &rColor)
void setWidth(tools::Long nWidth)
const OUString & GetText() const
Definition: ndtxt.hxx:210
static bool GraphicToBase64(const Graphic &rGraphic, OUString &rOUString, bool bAddPrefix=true, ConvertDataFormat aTargetFormat=ConvertDataFormat::Unknown)
#define OOO_STRING_SVTOOLS_HTML_O_title
static Writer & OutHTML_FrameFormatAsMulticol(Writer &rWrt, const SwFrameFormat &rFormat, bool bInCntnr)
Point LogicToLogic(const Point &rPtSource, const MapMode *pMapModeSource, const MapMode *pMapModeDest) const
constexpr TypedWhichId< SwFormatCol > RES_COL(109)
#define OOO_STRING_SVTOOLS_HTML_O_ismap
#define OOO_STRING_SVTOOLS_HTML_VA_absmiddle
SwNodeIndex nNode
Definition: pam.hxx:37
GPOS_NONE
constexpr TypedWhichId< SwFormatFrameSize > RES_FRM_SIZE(89)
BitmapChecksum GetChecksum() const
OUString getBase(sal_Int32 nIndex=LAST_SEGMENT, bool bIgnoreFinalSlash=true, DecodeMechanism eMechanism=DecodeMechanism::ToIUri, rtl_TextEncoding eCharset=RTL_TEXTENCODING_UTF8) const
sal_Int32 GetContentIndex() const
Definition: htmlfly.hxx:118
#define OOO_STRING_SVTOOLS_HTML_O_SDonmouseover
const OUString & GetName() const
#define HTMLMODE_BORDER_NONE
Definition: wrthtml.hxx:125
Writer & OutHTML_FrameFormatOLENodeGrf(Writer &rWrt, const SwFrameFormat &rFrameFormat, bool bInCntnr)
Definition: htmlplug.cxx:1449
virtual sal_Int32 Len() const override
Definition: ndtxt.cxx:276
sal_uIntPtr sal_uLong
tools::Long GetRight() const
constexpr::Color COL_TRANSPARENT(ColorTransparency, 0xFF, 0xFF, 0xFF, 0xFF)
HtmlContainerFlags
Definition: htmlfly.hxx:73
AllHtmlFlags const aHTMLOutFrameParaFrameTable[MAX_FRMTYPES][MAX_BROWSERS]
Definition: htmlflyt.cxx:120
#define OOO_STRING_SVTOOLS_HTML_O_dir
void DecIndentLevel()
Definition: wrthtml.hxx:501
OUString m_aNonConvertableCharacters
Definition: wrthtml.hxx:294
bool IsLinkedFile() const
Definition: ndgrf.hxx:164
#define OOO_STRING_SVTOOLS_HTML_map
void OutFrameFormat(AllHtmlFlags nType, const SwFrameFormat &rFormat, const SdrObject *pSdrObj)
SwNode & GetNode() const
Definition: ndindex.hxx:119
static SVT_DLLPUBLIC SvStream & Out_ImageMap(SvStream &, const OUString &, const ImageMap &, const OUString &, const HTMLOutEvent *pEventTable, bool bOutStarBasic, const char *pDelim, const char *pIndentArea, const char *pIndentMap, rtl_TextEncoding eDestEnc=RTL_TEXTENCODING_MS_1252, OUString *pNonConvertableChars=nullptr)
#define OOO_STRING_SVTOOLS_HTML_O_gutter
Content, content of frame (header, footer, fly).
Definition: fmtcntnt.hxx:31
SvxFrameDirection
SvStream & WriteOString(const OString &rStr)
#define OOO_STRING_SVTOOLS_HTML_O_id
size_t GetIMapObjectCount() const
const editeng::SvxBorderLine * GetRight() const
HTMLOutEvent const aImageEventTable[]
AllHtmlFlags const aHTMLOutFrameParaPrtAreaTable[MAX_FRMTYPES][MAX_BROWSERS]
Definition: htmlflyt.cxx:217
SVL_DLLPUBLIC OUString simpleNormalizedMakeRelative(OUString const &baseUriReference, OUString const &uriReference)
OString maNamespace
XML namespace, in case of XHTML.
Definition: wrthtml.hxx:397
css::uno::Reference< css::graphic::XGraphic > GetXGraphic() const
const HtmlFrmOpts HTML_FRMOPTS_IMG_CSS1
HtmlPosition GetOutPos() const
Definition: htmlfly.hxx:121
ErrCode m_nWarn
Definition: wrthtml.hxx:307
#define OOO_STRING_SVTOOLS_HTML_O_alt
const SvxBoxItem & GetBox(bool=true) const
Definition: frmatr.hxx:84
#define OOO_STRING_SVTOOLS_HTML_O_usemap
Writer & Out_SfxItemSet(const SwAttrFnTab, Writer &, const SfxItemSet &, bool bDeep)
Definition: wrt_fn.cxx:42
static OutputDevice * GetDefaultDevice()
#define OOO_STRING_SVTOOLS_HTML_O_onmouseout
constexpr tools::Long Width() const
void OutNewLine(bool bCheck=false)
Definition: wrthtml.cxx:1432
constexpr TypedWhichId< SwFormatVertOrient > RES_VERT_ORIENT(102)
sal_uInt16 sal_Unicode
const sal_uInt16 MAX_BROWSERS
Definition: htmlfly.hxx:83
bool m_bLFPossible
Definition: wrthtml.hxx:380
std::unique_ptr< SvxBrushItem > makeBackgroundBrushItem(bool=true) const
Definition: format.cxx:742
#define OOO_STRING_SVTOOLS_HTML_O_size
static SVT_DLLPUBLIC SvStream & Out_AsciiTag(SvStream &, const OString &rStr, bool bOn=true)
SwTableNode * GetTableNode()
Definition: node.hxx:603
bool mbReqIF
If the ReqIF subset of XHTML should be written.
Definition: wrthtml.hxx:399
#define OOO_STRING_SVTOOLS_HTML_O_height
constexpr TypedWhichId< SwDrawFrameFormat > RES_DRAWFRMFMT(159)
SwAttrFnTab aHTMLAttrFnTab
Definition: htmlatr.cxx:3205
bool setExtension(OUString const &rTheExtension, sal_Int32 nIndex=LAST_SEGMENT, bool bIgnoreFinalSlash=true, rtl_TextEncoding eCharset=RTL_TEXTENCODING_UTF8)
#define OOO_STRING_SVTOOLS_HTML_O_href
#define WARN_SWG_POOR_LOAD
Definition: swerror.h:40
#define OOO_STRING_SVTOOLS_HTML_O_SDonabort
const OUString & GetName() const
Definition: format.hxx:115
void end()
sal_uLong GetIndex() const
Definition: ndindex.hxx:152
bool IsAnchorOnly() const
Definition: fmtsrnd.hxx:52
OString GetIndentString(sal_uInt16 nIncLvl=0)
Definition: wrthtml.cxx:1415
#define OOO_STRING_SVTOOLS_HTML_O_onabort
static ErrCode WriteGraphic(const Graphic &rGraphic, OUString &rFileName, const OUString &rFilterName, const XOutFlags nFlags, const Size *pMtfSize_100TH_MM=nullptr, const css::uno::Sequence< css::beans::PropertyValue > *pFilterData=nullptr)
#define OOO_STRING_SVTOOLS_HTML_VA_top
std::unique_ptr< utl::TempFile > mpTempBaseURL
Temporary base URL for paste of images.
Definition: wrthtml.hxx:393
bool isAvailable() const
const Graphic * GetGraphic(OUString const &referer=OUString()) const
OString OUStringToOString(std::u16string_view str, ConnectionSettings const *settings)
bool GetFileFilterNms(OUString *pFileNm, OUString *pFilterNm) const
Definition: ndgrf.cxx:494
bool IsHTMLMode(sal_uInt32 nMode) const
Definition: wrthtml.hxx:570
#define OOO_STRING_SVTOOLS_HTML_O_hspace
const OUString & GetName() const
Definition: fmturl.hxx:71
std::vector< SwFormatINetFormat * > m_aINetFormats
Definition: wrthtml.hxx:290
constexpr TypedWhichId< SwFormatINetFormat > RES_TXTATR_INETFMT(51)
void ChangeParaToken(HtmlTokenId nNew)
Definition: htmlatr.cxx:157
bool IsOLENode() const
Definition: node.hxx:656
#define OOO_STRING_SVTOOLS_HTML_O_data
DocumentType eType
bool WrapGraphicInRtf(const Graphic &rGraphic, const Size &rLogicSize, SvStream &rRtf)
Wraps an image in an RTF fragment.
#define OOO_STRING_SVTOOLS_HTML_O_class
#define OOO_STRING_SVTOOLS_HTML_font
void OutImplicitMark(std::u16string_view rMark, const char *pMarkType)
Definition: wrthtml.cxx:1224
#define HTML_PARSPACE
Definition: wrthtml.hxx:69
const SwFrameFormat & GetFormat() const
Definition: htmlfly.hxx:115
const editeng::SvxBorderLine * GetTop() const
bool empty() const
tools::Long GetTextLeft() const
#define OOO_STRING_SVTOOLS_HTML_O_SDonerror
Style of a layout element.
Definition: frmfmt.hxx:58
The graphic frame is a replacement image of an OLE object.
bool m_bCfgStarBasic
Definition: wrthtml.hxx:343
rtl_TextEncoding m_eDestEnc
Definition: wrthtml.hxx:335
#define HTML_CFG_MAX
#define OOO_STRING_SVTOOLS_HTML_O_onerror
bool IsEmpty() const
const editeng::SvxBorderLine * GetLeft() const
SfxItemState GetItemState(sal_uInt16 nWhich, bool bSrchInParent=true, const SfxPoolItem **ppItem=nullptr) const
const SwFormatAnchor & GetAnchor(bool=true) const
Definition: fmtanchr.hxx:81
int i
const HtmlFrmOpts HTML_FRMOPTS_IMG
#define OOO_STRING_SVTOOLS_HTML_O_border
void attribute(const OString &aAttribute, const char *aValue)
GraphicType GetType() const
static Writer & OutHTML_FrameFormatAsImage(Writer &rWrt, const SwFrameFormat &rFormat)
sal_uInt16 m_nHeaderFooterSpace
Definition: wrthtml.hxx:327
Writer & OutHTML_SwTableNode(Writer &rWrt, SwTableNode &rNode, const SwFrameFormat *pFlyFrameFormat, const OUString *pCaption, bool bTopCaption)
Definition: htmltabw.cxx:870
RndStdIds GetAnchorId() const
Definition: fmtanchr.hxx:65
static Writer & OutHTML_FrameFormatAsMarquee(Writer &rWrt, const SwFrameFormat &rFrameFormat, const SdrObject &rSdrObj)
const SwFormatHoriOrient & GetHoriOrient(bool=true) const
Definition: fmtornt.hxx:108
SVL_DLLPUBLIC Link< OUString *, bool > const & GetMaybeFileHdl()
constexpr TypedWhichId< SvxMacroItem > RES_FRMMACRO(108)
const SwPosition * GetContentAnchor() const
Definition: fmtanchr.hxx:67
bool OutFlyFrame(sal_uLong nNdIdx, sal_Int32 nContentIdx, HtmlPosition nPos, HTMLOutContext *pContext=nullptr)
constexpr TypedWhichId< SwFormatURL > RES_URL(111)
static SVT_DLLPUBLIC SvStream & FlushToAscii(SvStream &, HTMLOutContext &rContext)
sal_uInt16 GetGutterWidth(bool bMin=false) const
Definition: atrfrm.cxx:911
SwContentNode * GetContentNode()
Definition: node.hxx:619
FlyAnchors.
Definition: fmtanchr.hxx:34
HtmlOut GetOutFn() const
Definition: htmlfly.hxx:120
sal_uInt8 GetHeightPercent() const
Definition: fmtfsize.hxx:88
static Writer & OutHTML_FrameFormatGrfNode(Writer &rWrt, const SwFrameFormat &rFormat, bool bInCntnr)
const char *const aMimeType[]
static SVT_DLLPUBLIC bool PrivateURLToInternalImg(OUString &rURL)
#define OOO_STRING_SVTOOLS_HTML_AL_left
#define OOO_STRING_SVTOOLS_HTML_O_onmouseover
#define OOO_STRING_SVTOOLS_HTML_O_name
sal_Int16 GetHoriOrient() const
Definition: fmtornt.hxx:87
css::text::WrapTextMode GetSurround() const
Definition: fmtsrnd.hxx:51
AllHtmlFlags const aHTMLOutFramePageFlyTable[MAX_FRMTYPES][MAX_BROWSERS]
Definition: htmlflyt.cxx:24
SwNodes & GetNodes()
Node is in which nodes-array/doc?
Definition: node.hxx:697
bool mbEmbedImages
Definition: wrthtml.hxx:391
#define OOO_STRING_SVTOOLS_HTML_VA_middle
AllHtmlFlags const & GetOutMode() const
Definition: htmlfly.hxx:119
sal_uInt8 GetWidthPercent() const
Definition: fmtfsize.hxx:91
const SwTextNode * GetpTextNode() const
Definition: txtinet.hxx:45
bool m_bOutFooter
Definition: wrthtml.hxx:364
tools::Long GetHeight() const
#define OOO_STRING_SVTOOLS_HTML_multicol
const sal_Unicode cMarkSeparator
Definition: swtypes.hxx:129
Writer & OutHTML_DrawFrameFormatAsMarquee(Writer &rWrt, const SwDrawFrameFormat &rFormat, const SdrObject &rSdrObject)
SfxItemPool * GetPool() const
Writer & OutHTML_Image(Writer &rWrt, const SwFrameFormat &rFrameFormat, const OUString &rGraphicURL, Graphic const &rGraphic, const OUString &rAlternateText, const Size &rRealSize, HtmlFrmOpts nFrameOpts, const char *pMarkType, const ImageMap *pAltImgMap, const OUString &rMimeType)
SwHTMLFrameType
Definition: htmlfly.hxx:33
void Out_SwDoc(SwPaM *)
Definition: wrthtml.cxx:805
Frame cannot be moved in Var-direction.
tools::Long SwTwips
Definition: swtypes.hxx:49
static Writer & OutHTML_FrameFormatAsDivOrSpan(Writer &rWrt, const SwFrameFormat &rFrameFormat, bool bSpan)
virtual Size GetTwipSize() const override
Definition: ndgrf.cxx:432
bool setBase(OUString const &rTheBase, sal_Int32 nIndex=LAST_SEGMENT, EncodeMechanism eMechanism=EncodeMechanism::WasEncoded, rtl_TextEncoding eCharset=RTL_TEXTENCODING_UTF8)
const HtmlFrmOpts HTML_FRMOPTS_MULTICOL
const SwNodeIndex * GetContentIdx() const
Definition: fmtcntnt.hxx:46
Point LogicToPixel(const Point &rLogicPt) const
bool m_bTagOn
Definition: wrthtml.hxx:349
const ImageMap * GetMap() const
Definition: fmturl.hxx:68
const OUString & GetGraphicLink() const
#define OOO_STRING_SVTOOLS_HTML_SPTYPE_block
OUString GetMainURL(DecodeMechanism eMechanism, rtl_TextEncoding eCharset=RTL_TEXTENCODING_UTF8) const
HtmlFrmOpts
Definition: wrthtml.hxx:75
const SwMirrorGrf & GetMirrorGrf(bool=true) const
Definition: grfatr.hxx:282
sal_uInt16 Which() const
for Querying of Writer-functions.
Definition: format.hxx:82
#define OOO_STRING_SVTOOLS_HTML_O_align
#define OOO_STRING_SVTOOLS_HTML_division
AllHtmlFlags const aHTMLOutFrameParaOtherTable[MAX_FRMTYPES][MAX_BROWSERS]
Definition: htmlflyt.cxx:313
const HtmlFrmOpts HTML_FRMOPTS_CNTNR
#define OOO_STRING_SVTOOLS_HTML_linebreak
sal_uLong EndOfSectionIndex() const
Definition: node.hxx:681
SwTextNode is a paragraph in the document model.
Definition: ndtxt.hxx:79
const SvxULSpaceItem & GetULSpace(bool=true) const
Definition: frmatr.hxx:76
const SvxMacroTableDtor & GetMacroTable() const
XOutFlags
constexpr sal_uInt16 RES_CHRATR_BEGIN(HINT_BEGIN)
Writer & OutHTML_DrawFrameFormatAsControl(Writer &rWrt, const SwDrawFrameFormat &rFormat, const SdrUnoObj &rFormObj, bool bInCntnr)
Definition: htmlforw.cxx:679
#define HTMLMODE_ABS_POS_FLY
Definition: wrthtml.hxx:122
#define OOO_STRING_SVTOOLS_HTML_AL_right
bool m_bOutHeader
Definition: wrthtml.hxx:363
sal_Int16 GetRelationOrient() const
Definition: fmtornt.hxx:88
static Writer & OutHTML_FrameFormatTableNode(Writer &rWrt, const SwFrameFormat &rFrameFormat)
void start(const OString &aElement)
#define OOO_STRING_SVTOOLS_HTML_O_style
#define ERRCODE_NONE
constexpr tools::Long Height() const
unsigned char sal_uInt8
const HtmlFrmOpts HTML_FRMOPTS_IMG_CNTNR
OUString GetTitle() const
Definition: ndnotxt.cxx:258
const SdrObject * GetSdrObject() const
Definition: htmlfly.hxx:116
#define OOO_STRING_SVTOOLS_HTML_O_cols
#define OOO_STRING_SVTOOLS_HTML_O_target
const o3tl::enumarray< SvxAdjust, unsigned short > aSvxToUnoAdjust USHRT_MAX
Definition: unosett.cxx:254
const OUString & GetTargetFrameName() const
Definition: fmturl.hxx:65
void IncIndentLevel()
Definition: wrthtml.hxx:497
void CollectFlyFrames()
void writeFrameFormatOptions(HtmlWriter &aHtml, const SwFrameFormat &rFrameFormat, std::u16string_view rAltText, HtmlFrmOpts nFrameOpts)
OUString aName
const OUString * GetOrigFileName() const
Definition: shellio.hxx:434
SwNodes & GetNodes()
Definition: doc.hxx:408
const HtmlFrmOpts HTML_FRMOPTS_DIV
tools::Long AdjustWidth(tools::Long n)
#define HTMLMODE_VERT_SPACER
Definition: wrthtml.hxx:117
HTMLOutEvent const aIMapEventTable[]
OString GetNamespace() const
Determines the prefix string needed to respect the requested namespace alias.
Definition: wrthtml.cxx:1481
#define OOO_STRING_SVTOOLS_HTML_spacer
const HtmlFrmOpts HTML_FRMOPTS_IMG_ALL
bool makeAvailable()
Writer & OutHTML_HeaderFooter(Writer &rWrt, const SwFrameFormat &rFrameFormat, bool bHeader)
constexpr TypedWhichId< SvxLRSpaceItem > RES_LR_SPACE(91)
#define OOO_STRING_SVTOOLS_HTML_image
SvStream & WriteChar(char nChar)
tools::Long AdjustHeight(tools::Long n)
constexpr sal_uInt16 RES_CHRATR_END(46)
constexpr TypedWhichId< SvxBoxItem > RES_BOX(106)
HtmlOut
Definition: htmlfly.hxx:51
const SwFormatFrameSize & GetFrameSize(bool=true) const
Definition: fmtfsize.hxx:104
const SwAttrSet & GetSwAttrSet() const
Does node has already its own auto-attributes? Access to SwAttrSet.
Definition: node.hxx:718
const SwFormatContent & GetContent(bool=true) const
Definition: fmtcntnt.hxx:55
#define OOO_STRING_SVTOOLS_HTML_O_SDonmouseout
sal_uInt16 CalcLineSpace(SvxBoxItemLine nLine, bool bEvenIfNoLine=false) const
std::shared_ptr< SwUnoCursor > m_pCurrentPam
Definition: shellio.hxx:405
const HtmlFrmOpts HTML_FRMOPTS_MULTICOL_CSS1
sal_uInt16 m_nImgMapCnt
Definition: wrthtml.hxx:312
void setHeight(tools::Long nHeight)
void AddLinkTarget(const OUString &rURL)
SvStream & Strm()
Definition: writer.cxx:215
#define OOO_STRING_SVTOOLS_HTML_O_type
sal_uInt16 GetNumCols() const
Definition: fmtclds.hxx:114
#define OOO_STRING_SVTOOLS_HTML_O_SDonload
#define OOO_STRING_SVTOOLS_HTML_O_color
void CollectLinkTargets()
#define SAL_WARN(area, stream)
bool IsDocNodes() const
Is the NodesArray the regular one of Doc? (and not the UndoNds, ...) Implementation in doc...
Definition: nodes.cxx:2329
RndStdIds
static void GetEEAttrsFromDrwObj(SfxItemSet &rItemSet, const SdrObject *pObj)
bool IsTableNode() const
Definition: node.hxx:644
bool m_bTextAttr
Definition: wrthtml.hxx:358
#define OOO_STRING_SVTOOLS_HTML_VA_absbottom
if(!pCandidateA->getEnd().equal(pCandidateB->getStart()))
HtmlPosition
Definition: htmlfly.hxx:66
HTMLOutEvent const aAnchorEventTable[]
Definition: htmlatr.cxx:85
const SwAttrSet & GetAttrSet() const
For querying the attribute array.
Definition: format.hxx:120
bool m_bCfgOutStyles
Definition: wrthtml.hxx:340
#define OOO_STRING_SVTOOLS_HTML_object
const SfxPoolItem & GetAttr(sal_uInt16 nWhich, bool bInParent=true) const
SS for PoolItems: hard attributation.
Definition: node.hxx:725
void OutAndSetDefList(sal_uInt16 nNewLvl)
Definition: htmlatr.cxx:119
OUString convertHyperlinkHRefValue(const OUString &rURL)
Definition: wrthtml.cxx:1237
Writer & OutHTML_INetFormat(Writer &rWrt, const SwFormatINetFormat &rINetFormat, bool bOn)
Definition: htmlatr.cxx:2935
bool IsServerMap() const
Definition: fmturl.hxx:67
#define OOO_STRING_SVTOOLS_HTML_span
bool IsTextNode() const
Definition: node.hxx:640
bool mbSkipImages
Definition: wrthtml.hxx:388
Reference< XGraphic > xGraphic
const editeng::SvxBorderLine * GetBottom() const
const OUString & GetURL() const
#define OOO_STRING_SVTOOLS_HTML_anchor
constexpr TypedWhichId< SvxULSpaceItem > RES_UL_SPACE(92)
#define OOO_STRING_SVTOOLS_HTML_O_width
const Graphic & GetGrf(bool bWait=false) const
Definition: ndgrf.cxx:373
#define SAL_NEWLINE_STRING
SwDoc * m_pDoc
Definition: shellio.hxx:403
const Size & GetSize() const
sal_uInt16 nPos
OString OutFrameFormatOptions(const SwFrameFormat &rFrameFormat, const OUString &rAltText, HtmlFrmOpts nFrameOpts)
bool m_bOutFlyFrame
Definition: wrthtml.hxx:365
bool CopyLocalFileToINet(OUString &rFileNm)
Definition: writer.cxx:300
SwTextNode * GetTextNode()
Inline methods from Node.hxx.
Definition: ndtxt.hxx:845
OUString getExtension(sal_Int32 nIndex=LAST_SEGMENT, bool bIgnoreFinalSlash=true, DecodeMechanism eMechanism=DecodeMechanism::ToIUri, rtl_TextEncoding eCharset=RTL_TEXTENCODING_UTF8) const
Writer & OutHTML_FrameFormatOLENode(Writer &rWrt, const SwFrameFormat &rFrameFormat, bool bInCntnr)
Definition: htmlplug.cxx:1181
sal_uInt16 GetUpper() const
Writer & OutHTML_BulletImage(Writer &rWrt, const char *pTag, const SvxBrushItem *pBrush, const OUString &rGraphicURL)
const OUString & GetURL() const
Definition: fmturl.hxx:66
SVL_DLLPUBLIC OUString SmartRel2Abs(INetURLObject const &rTheBaseURIRef, OUString const &rTheRelURIRef, Link< OUString *, bool > const &rMaybeFileHdl=Link< OUString *, bool >(), bool bCheckFileExists=true, bool bIgnoreFragment=false, INetURLObject::EncodeMechanism eEncodeMechanism=INetURLObject::EncodeMechanism::WasEncoded, INetURLObject::DecodeMechanism eDecodeMechanism=INetURLObject::DecodeMechanism::ToIUri, rtl_TextEncoding eCharset=RTL_TEXTENCODING_UTF8, FSysStyle eStyle=FSysStyle::Detect)
void OutCSS1_FrameFormatOptions(const SwFrameFormat &rFrameFormat, HtmlFrmOpts nFrameOpts, const SdrObject *pSdrObj=nullptr, const SfxItemSet *pItemSet=nullptr)
Definition: css1atr.cxx:1848
EnumT GetValue() const
Base class of the Writer document model elements.
Definition: node.hxx:80