LibreOffice Module sw (master) 1
htmltabw.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 <hintids.hxx>
21#include <vcl/svapp.hxx>
22#include <svtools/htmlout.hxx>
23#include <svtools/htmltokn.h>
24#include <svtools/htmlkywd.hxx>
26#include <editeng/ulspitem.hxx>
27#include <editeng/lrspitem.hxx>
28#include <editeng/brushitem.hxx>
29#include <editeng/boxitem.hxx>
30#include <fmtornt.hxx>
31#include <frmfmt.hxx>
32#include <fmtfsize.hxx>
33#include <fmtsrnd.hxx>
34#include <frmatr.hxx>
35#include <doc.hxx>
37#include <pam.hxx>
38#include <ndtxt.hxx>
39#include <swrect.hxx>
40#include <cellatr.hxx>
41#include <poolfmt.hxx>
42#include <swtable.hxx>
43#include <htmltbl.hxx>
44#include "htmlnum.hxx"
45#include "wrthtml.hxx"
46#include <wrtswtbl.hxx>
47#ifdef DBG_UTIL
48#include <viewsh.hxx>
49#include <viewopt.hxx>
50#endif
51#include <rtl/strbuf.hxx>
52#include <sal/types.h>
53#include <osl/diagnose.h>
54
55#define MAX_DEPTH (3)
56
57using namespace ::com::sun::star;
58
59namespace {
60
61class SwHTMLWrtTable : public SwWriteTable
62{
63 static void Pixelize( sal_uInt16& rValue );
64 void PixelizeBorders();
65
66 void OutTableCell( SwHTMLWriter& rWrt, const SwWriteTableCell *pCell,
67 bool bOutVAlign ) const;
68
69 void OutTableCells( SwHTMLWriter& rWrt,
70 const SwWriteTableCells& rCells,
71 const SvxBrushItem *pBrushItem ) const;
72
73 virtual bool ShouldExpandSub( const SwTableBox *pBox,
74 bool bExpandedBefore, sal_uInt16 nDepth ) const override;
75
76 static bool HasTabBackground( const SwTableLine& rLine,
77 bool bTop, bool bBottom, bool bLeft, bool bRight );
78 static bool HasTabBackground( const SwTableBox& rBox,
79 bool bTop, bool bBottom, bool bLeft, bool bRight );
80
81public:
82 SwHTMLWrtTable( const SwTableLines& rLines, tools::Long nWidth, sal_uInt32 nBWidth,
83 bool bRel, sal_uInt16 nLeftSub, sal_uInt16 nRightSub,
84 sal_uInt16 nNumOfRowsToRepeat );
85 explicit SwHTMLWrtTable( const SwHTMLTableLayout *pLayoutInfo );
86
87 void Write( SwHTMLWriter& rWrt, sal_Int16 eAlign=text::HoriOrientation::NONE,
88 bool bTHead=false, const SwFrameFormat *pFrameFormat=nullptr,
89 const OUString *pCaption=nullptr, bool bTopCaption=false,
90 sal_uInt16 nHSpace=0, sal_uInt16 nVSpace=0 ) const;
91};
92
93}
94
95SwHTMLWrtTable::SwHTMLWrtTable( const SwTableLines& rLines, tools::Long nWidth,
96 sal_uInt32 nBWidth, bool bRel,
97 sal_uInt16 nLSub, sal_uInt16 nRSub,
98 sal_uInt16 nNumOfRowsToRepeat )
99 : SwWriteTable(nullptr, rLines, nWidth, nBWidth, bRel, MAX_DEPTH, nLSub, nRSub, nNumOfRowsToRepeat)
100{
101 PixelizeBorders();
102}
103
104SwHTMLWrtTable::SwHTMLWrtTable( const SwHTMLTableLayout *pLayoutInfo )
105 : SwWriteTable(nullptr, pLayoutInfo)
106{
107 // Adjust some Twip values to pixel limits
108 if( m_bCollectBorderWidth )
109 PixelizeBorders();
110}
111
112void SwHTMLWrtTable::Pixelize( sal_uInt16& rValue )
113{
114 if( rValue && Application::GetDefaultDevice() )
115 {
116 Size aSz( rValue, 0 );
117 aSz = Application::GetDefaultDevice()->LogicToPixel( aSz, MapMode(MapUnit::MapTwip) );
118 if( !aSz.Width() )
119 aSz.setWidth( 1 );
120 aSz = Application::GetDefaultDevice()->PixelToLogic( aSz, MapMode(MapUnit::MapTwip) );
121 rValue = o3tl::narrowing<sal_uInt16>(aSz.Width());
122 }
123}
124
125void SwHTMLWrtTable::PixelizeBorders()
126{
127 Pixelize( m_nBorder );
128 Pixelize( m_nCellSpacing );
129 Pixelize( m_nCellPadding );
130}
131
132bool SwHTMLWrtTable::HasTabBackground( const SwTableBox& rBox,
133 bool bTop, bool bBottom, bool bLeft, bool bRight )
134{
135 OSL_ENSURE( bTop || bBottom || bLeft || bRight,
136 "HasTabBackground: cannot be called" );
137
138 bool bRet = false;
139 if( rBox.GetSttNd() )
140 {
141 std::unique_ptr<SvxBrushItem> aBrushItem =
143
146 bRet = aBrushItem->GetColor() != COL_TRANSPARENT ||
147 !aBrushItem->GetGraphicLink().isEmpty() || aBrushItem->GetGraphic();
148 }
149 else
150 {
151 const SwTableLines& rLines = rBox.GetTabLines();
152 const SwTableLines::size_type nCount = rLines.size();
153 bool bLeftRight = bLeft || bRight;
154 for( SwTableLines::size_type i=0; !bRet && i<nCount; ++i )
155 {
156 bool bT = bTop && 0 == i;
157 bool bB = bBottom && nCount-1 == i;
158 if( bT || bB || bLeftRight )
159 bRet = HasTabBackground( *rLines[i], bT, bB, bLeft, bRight);
160 }
161 }
162
163 return bRet;
164}
165
166bool SwHTMLWrtTable::HasTabBackground( const SwTableLine& rLine,
167 bool bTop, bool bBottom, bool bLeft, bool bRight )
168{
169 OSL_ENSURE( bTop || bBottom || bLeft || bRight,
170 "HasTabBackground: cannot be called" );
171
172 std::unique_ptr<SvxBrushItem> aBrushItem = rLine.GetFrameFormat()->makeBackgroundBrushItem();
175 bool bRet = aBrushItem->GetColor() != COL_TRANSPARENT ||
176 !aBrushItem->GetGraphicLink().isEmpty() || aBrushItem->GetGraphic();
177
178 if( !bRet )
179 {
180 const SwTableBoxes& rBoxes = rLine.GetTabBoxes();
181 const SwTableBoxes::size_type nCount = rBoxes.size();
182 bool bTopBottom = bTop || bBottom;
183 for( SwTableBoxes::size_type i=0; !bRet && i<nCount; ++i )
184 {
185 bool bL = bLeft && 0 == i;
186 bool bR = bRight && nCount-1 == i;
187 if( bTopBottom || bL || bR )
188 bRet = HasTabBackground( *rBoxes[i], bTop, bBottom, bL, bR );
189 }
190 }
191
192 return bRet;
193}
194
195static bool lcl_TableLine_HasTabBorders( const SwTableLine* pLine, bool *pBorders );
196
197static bool lcl_TableBox_HasTabBorders( const SwTableBox* pBox, bool *pBorders )
198{
199 if( *pBorders )
200 return false;
201
202 if( !pBox->GetSttNd() )
203 {
204 for( const auto& rpLine : pBox->GetTabLines() )
205 {
206 if ( lcl_TableLine_HasTabBorders( rpLine, pBorders ) )
207 break;
208 }
209 }
210 else
211 {
212 const SvxBoxItem& rBoxItem =
214
215 *pBorders = rBoxItem.GetTop() || rBoxItem.GetBottom() ||
217 }
218
219 return !*pBorders;
220}
221
222static bool lcl_TableLine_HasTabBorders( const SwTableLine* pLine, bool *pBorders )
223{
224 if( *pBorders )
225 return false;
226
227 for( const auto& rpBox : pLine->GetTabBoxes() )
228 {
229 if ( lcl_TableBox_HasTabBorders( rpBox, pBorders ) )
230 break;
231 }
232 return !*pBorders;
233}
234
235bool SwHTMLWrtTable::ShouldExpandSub( const SwTableBox *pBox,
236 bool bExpandedBefore,
237 sal_uInt16 nDepth ) const
238{
239 bool bExpand = !pBox->GetSttNd() && nDepth>0;
240 if( bExpand && bExpandedBefore )
241 {
242 // MIB 30.6.97: If a box was already expanded, another one is only
243 // expanded when it has a border.
244 bool bBorders = false;
245 lcl_TableBox_HasTabBorders( pBox, &bBorders );
246 if( !bBorders )
247 bBorders = HasTabBackground( *pBox, true, true, true, true );
248 bExpand = bBorders;
249 }
250
251 return bExpand;
252}
253
254// Write a box as single cell
255void SwHTMLWrtTable::OutTableCell( SwHTMLWriter& rWrt,
256 const SwWriteTableCell *pCell,
257 bool bOutVAlign ) const
258{
259 const SwTableBox *pBox = pCell->GetBox();
260 sal_uInt16 nRow = pCell->GetRow();
261 sal_uInt16 nCol = pCell->GetCol();
262 sal_uInt16 nRowSpan = pCell->GetRowSpan();
263 sal_uInt16 nColSpan = pCell->GetColSpan();
264
265 if ( !nRowSpan )
266 return;
267
268 const SwStartNode* pSttNd = pBox->GetSttNd();
269 bool bHead = false;
270 if( pSttNd )
271 {
272 SwNodeOffset nNdPos = pSttNd->GetIndex()+1;
273
274 // determine the type of cell (TD/TH)
275 SwNode* pNd;
276 while( !( pNd = rWrt.m_pDoc->GetNodes()[nNdPos])->IsEndNode() )
277 {
278 if( pNd->IsTextNode() )
279 {
280 // The only paragraphs relevant for the distinction are those
281 // where the style is one of the two table related styles
282 // or inherits from one of these.
283 const SwFormat *pFormat = &static_cast<SwTextNode*>(pNd)->GetAnyFormatColl();
284 sal_uInt16 nPoolId = pFormat->GetPoolFormatId();
285 while( !pFormat->IsDefault() &&
286 RES_POOLCOLL_TABLE_HDLN!=nPoolId &&
287 RES_POOLCOLL_TABLE!=nPoolId )
288 {
289 pFormat = pFormat->DerivedFrom();
290 nPoolId = pFormat->GetPoolFormatId();
291 }
292
293 if( !pFormat->IsDefault() )
294 {
295 bHead = (RES_POOLCOLL_TABLE_HDLN==nPoolId);
296 break;
297 }
298 }
299 nNdPos++;
300 }
301 }
302
303 rWrt.OutNewLine(); // <TH>/<TD> in new line
304 OStringBuffer sOut;
305 sOut.append('<');
306 OString aTag(bHead ? OOO_STRING_SVTOOLS_HTML_tableheader : OOO_STRING_SVTOOLS_HTML_tabledata);
307 sOut.append(rWrt.GetNamespace() + aTag);
308
309 // output ROW- and COLSPAN
310 if( nRowSpan>1 )
311 {
312 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_rowspan
313 "=\"" + OString::number(nRowSpan) + "\"");
314 }
315 if( nColSpan > 1 )
316 {
317 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_colspan
318 "=\"" + OString::number(nColSpan) + "\"");
319 }
320
321 tools::Long nWidth = 0;
322 bool bOutWidth = true;
323 sal_uInt32 nPercentWidth = SAL_MAX_UINT32;
324
325 if( m_bLayoutExport )
326 {
327 if( pCell->HasPercentWidthOpt() )
328 {
329 nPercentWidth = pCell->GetWidthOpt();
330 }
331 else
332 {
333 nWidth = pCell->GetWidthOpt();
334 if( !nWidth )
335 bOutWidth = false;
336 }
337 }
338 else
339 {
340 if( HasRelWidths() )
341 nPercentWidth = GetPercentWidth(nCol, nColSpan);
342 else
343 nWidth = GetAbsWidth( nCol, nColSpan );
344 }
345
346 if (rWrt.mbReqIF)
347 // ReqIF implies strict XHTML: no width for <td>.
348 bOutWidth = false;
349
350 tools::Long nHeight = pCell->GetHeight() > 0
351 ? GetAbsHeight( pCell->GetHeight(), nRow, nRowSpan )
352 : 0;
353 Size aPixelSz( nWidth, nHeight );
354
355 // output WIDTH (Argh: only for Netscape)
356 if( (aPixelSz.Width() || aPixelSz.Height()) && Application::GetDefaultDevice() )
357 {
358 Size aOldSz( aPixelSz );
359 aPixelSz = Application::GetDefaultDevice()->LogicToPixel( aPixelSz,
360 MapMode(MapUnit::MapTwip) );
361 if( aOldSz.Width() && !aPixelSz.Width() )
362 aPixelSz.setWidth( 1 );
363 if( aOldSz.Height() && !aPixelSz.Height() )
364 aPixelSz.setHeight( 1 );
365 }
366
367 // output WIDTH: from layout or calculated
368 if( bOutWidth )
369 {
370 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_width "=\"");
371 if( nPercentWidth != SAL_MAX_UINT32 )
372 {
373 sOut.append(static_cast<sal_Int32>(nPercentWidth)).append('%');
374 }
375 else
376 {
377 sOut.append(static_cast<sal_Int32>(aPixelSz.Width()));
378 }
379 sOut.append("\"");
380 }
381
382 if (rWrt.mbReqIF)
383 {
384 // ReqIF implies strict XHTML: no height for <td>.
385 nHeight = 0;
386 }
387
388 if( nHeight )
389 {
390 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_height
391 "=\"" + OString::number(aPixelSz.Height()) + "\"");
392 }
393
394 const SfxItemSet& rItemSet = pBox->GetFrameFormat()->GetAttrSet();
395
396 // ALIGN is only outputted at the paragraphs from now on
397
398 // output VALIGN
399 if( bOutVAlign )
400 {
401 sal_Int16 eVertOri = pCell->GetVertOri();
402 if( text::VertOrientation::TOP==eVertOri || text::VertOrientation::BOTTOM==eVertOri )
403 {
404 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_valign
405 "=\"").append(text::VertOrientation::TOP==eVertOri ?
406 OOO_STRING_SVTOOLS_HTML_VA_top :
407 OOO_STRING_SVTOOLS_HTML_VA_bottom)
408 .append("\"");
409 }
410 }
411
412 rWrt.Strm().WriteOString( sOut );
413 sOut.setLength(0);
414
415 rWrt.m_bTextAttr = false;
416 rWrt.m_bOutOpts = true;
417 const SvxBrushItem *pBrushItem = rItemSet.GetItemIfSet( RES_BACKGROUND, false );
418 if( !pBrushItem )
419 pBrushItem = pCell->GetBackground();
420
421 if( pBrushItem )
422 {
423 // output background
424 if (!rWrt.mbReqIF)
425 // Avoid non-CSS version in the ReqIF case.
426 rWrt.OutBackground( pBrushItem, false );
427
428 if (!rWrt.m_bCfgOutStyles)
429 pBrushItem = nullptr;
430 }
431
432 // tdf#132739 with rWrt.m_bCfgOutStyles of true bundle the brush item css
433 // properties into the same "style" tag as the borders so there is only one
434 // style tag
435 rWrt.OutCSS1_TableCellBordersAndBG(*pBox->GetFrameFormat(), pBrushItem);
436
437 sal_uInt32 nNumFormat = 0;
438 double nValue = 0.0;
439 bool bNumFormat = false, bValue = false;
440 if( const SwTableBoxNumFormat* pItem = rItemSet.GetItemIfSet( RES_BOXATR_FORMAT, false ) )
441 {
442 nNumFormat = pItem->GetValue();
443 bNumFormat = true;
444 }
445 if( const SwTableBoxValue* pItem = rItemSet.GetItemIfSet( RES_BOXATR_VALUE, false ) )
446 {
447 nValue = pItem->GetValue();
448 bValue = true;
449 if( !bNumFormat )
450 nNumFormat = pBox->GetFrameFormat()->GetTableBoxNumFormat().GetValue();
451 }
452
453 if( bNumFormat || bValue )
454 {
455 sOut.append(HTMLOutFuncs::CreateTableDataOptionsValNum(bValue, nValue,
456 nNumFormat, *rWrt.m_pDoc->GetNumberFormatter()));
457 }
458 sOut.append('>');
459 rWrt.Strm().WriteOString( sOut );
460 sOut.setLength(0);
461 rWrt.m_bLFPossible = true;
462
463 rWrt.IncIndentLevel(); // indent the content of <TD>...</TD>
464
465 if( pSttNd )
466 {
467 HTMLSaveData aSaveData( rWrt, pSttNd->GetIndex()+1,
468 pSttNd->EndOfSectionIndex() );
469 rWrt.Out_SwDoc( rWrt.m_pCurrentPam.get() );
470 }
471 else
472 {
473 sal_uInt16 nTWidth;
474 sal_uInt32 nBWidth;
475 sal_uInt16 nLSub, nRSub;
476 if( HasRelWidths() )
477 {
478 nTWidth = 100;
479 nBWidth = GetRawWidth( nCol, nColSpan );
480 nLSub = 0;
481 nRSub = 0;
482 }
483 else
484 {
485 nTWidth = GetAbsWidth( nCol, nColSpan );
486 nBWidth = nTWidth;
487 nLSub = GetLeftSpace( nCol );
488 nRSub = GetRightSpace( nCol, nColSpan );
489 }
490
491 SwHTMLWrtTable aTableWrt( pBox->GetTabLines(), nTWidth,
492 nBWidth, HasRelWidths(), nLSub, nRSub, /*nNumOfRowsToRepeat*/0 );
493 aTableWrt.Write( rWrt );
494 }
495
496 rWrt.DecIndentLevel(); // indent the content of <TD>...</TD>
497
498 if( rWrt.m_bLFPossible )
499 rWrt.OutNewLine();
501 HTMLOutFuncs::Out_AsciiTag(rWrt.Strm(), Concat2View(rWrt.GetNamespace() + aTag), false);
502 rWrt.m_bLFPossible = true;
503}
504
505// output a line as lines
506void SwHTMLWrtTable::OutTableCells( SwHTMLWriter& rWrt,
507 const SwWriteTableCells& rCells,
508 const SvxBrushItem *pBrushItem ) const
509{
510 // If the line contains more the one cell and all cells have the same
511 // alignment, then output the VALIGN at the line instead of the cell.
512 sal_Int16 eRowVertOri = text::VertOrientation::NONE;
513 if( rCells.size() > 1 )
514 {
515 for (SwWriteTableCells::size_type nCell = 0; nCell < rCells.size(); ++nCell)
516 {
517 sal_Int16 eCellVertOri = rCells[nCell]->GetVertOri();
518 if( 0==nCell )
519 {
520 eRowVertOri = eCellVertOri;
521 }
522 else if( eRowVertOri != eCellVertOri )
523 {
524 eRowVertOri = text::VertOrientation::NONE;
525 break;
526 }
527 }
528 }
529
530 rWrt.OutNewLine(); // <TR> in new line
531 rWrt.Strm().WriteChar( '<' ).WriteOString( Concat2View(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_tablerow) );
532 if( pBrushItem )
533 {
534 if (!rWrt.mbXHTML)
535 {
536 rWrt.OutBackground(pBrushItem, false);
537 }
538
539 rWrt.m_bTextAttr = false;
540 rWrt.m_bOutOpts = true;
541 if (rWrt.m_bCfgOutStyles || rWrt.mbXHTML)
542 OutCSS1_TableBGStyleOpt( rWrt, *pBrushItem );
543 }
544
545 if( text::VertOrientation::TOP==eRowVertOri || text::VertOrientation::BOTTOM==eRowVertOri )
546 {
547 OStringBuffer sOut;
548 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_valign
549 "=\"").append(text::VertOrientation::TOP==eRowVertOri ? OOO_STRING_SVTOOLS_HTML_VA_top : OOO_STRING_SVTOOLS_HTML_VA_bottom)
550 .append("\"");
551 rWrt.Strm().WriteOString( sOut );
552 sOut.setLength(0);
553 }
554
555 rWrt.Strm().WriteChar( '>' );
556
557 rWrt.IncIndentLevel(); // indent content of <TR>...</TR>
558
559 for (const auto &rpCell : rCells)
560 {
561 OutTableCell(rWrt, rpCell.get(), text::VertOrientation::NONE == eRowVertOri);
562 }
563
564 rWrt.DecIndentLevel(); // indent content of <TR>...</TR>
565
566 rWrt.OutNewLine(); // </TR> in new line
567 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_tablerow), false );
568}
569
570void SwHTMLWrtTable::Write( SwHTMLWriter& rWrt, sal_Int16 eAlign,
571 bool bTHead, const SwFrameFormat *pFrameFormat,
572 const OUString *pCaption, bool bTopCaption,
573 sal_uInt16 nHSpace, sal_uInt16 nVSpace ) const
574{
575 // determine value of RULES
576 bool bRowsHaveBorder = false;
577 bool bRowsHaveBorderOnly = true;
578 SwWriteTableRow *pRow = m_aRows[0].get();
579 for( SwWriteTableRows::size_type nRow=1; nRow < m_aRows.size(); ++nRow )
580 {
581 SwWriteTableRow *pNextRow = m_aRows[nRow].get();
582 bool bBorder = ( pRow->m_bBottomBorder || pNextRow->m_bTopBorder );
583 bRowsHaveBorder |= bBorder;
584 bRowsHaveBorderOnly &= bBorder;
585
586 sal_uInt16 nBorder2 = pRow->m_bBottomBorder ? pRow->m_nBottomBorder : USHRT_MAX;
587 if( pNextRow->m_bTopBorder && pNextRow->m_nTopBorder < nBorder2 )
588 nBorder2 = pNextRow->m_nTopBorder;
589
590 pRow->m_bBottomBorder = bBorder;
591 pRow->m_nBottomBorder = nBorder2;
592
593 pNextRow->m_bTopBorder = bBorder;
594 pNextRow->m_nTopBorder = nBorder2;
595
596 pRow = pNextRow;
597 }
598
599 bool bColsHaveBorder = false;
600 bool bColsHaveBorderOnly = true;
601 SwWriteTableCol *pCol = m_aCols[0].get();
602 for( SwWriteTableCols::size_type nCol=1; nCol<m_aCols.size(); ++nCol )
603 {
604 SwWriteTableCol *pNextCol = m_aCols[nCol].get();
605 bool bBorder = ( pCol->m_bRightBorder || pNextCol->m_bLeftBorder );
606 bColsHaveBorder |= bBorder;
607 bColsHaveBorderOnly &= bBorder;
608 pCol->m_bRightBorder = bBorder;
609 pNextCol->m_bLeftBorder = bBorder;
610 pCol = pNextCol;
611 }
612
613 // close previous numbering, etc
614 rWrt.ChangeParaToken( HtmlTokenId::NONE );
615
616 if( rWrt.m_bLFPossible )
617 rWrt.OutNewLine(); // <TABLE> in new line
618 OStringBuffer sOut;
619 sOut.append('<').append(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_table);
620
621 const SvxFrameDirection nOldDirection = rWrt.m_nDirection;
622 if( pFrameFormat )
623 rWrt.m_nDirection = rWrt.GetHTMLDirection( pFrameFormat->GetAttrSet() );
624 if( rWrt.m_bOutFlyFrame || nOldDirection != rWrt.m_nDirection )
625 {
626 rWrt.Strm().WriteOString( sOut );
627 sOut.setLength(0);
628 rWrt.OutDirection( rWrt.m_nDirection );
629 }
630
631 // output ALIGN=
632 if( text::HoriOrientation::RIGHT == eAlign )
633 {
634 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_align
635 "=\"" OOO_STRING_SVTOOLS_HTML_AL_right "\"");
636 }
637 else if( text::HoriOrientation::CENTER == eAlign )
638 {
639 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_align
640 "=\"" OOO_STRING_SVTOOLS_HTML_AL_center "\"");
641 }
642 else if( text::HoriOrientation::LEFT == eAlign )
643 {
644 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_align
645 "=\"" OOO_STRING_SVTOOLS_HTML_AL_left "\"");
646 }
647
648 // output WIDTH: from layout or calculated
649 if( m_nTabWidth )
650 {
651 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_width "=\"");
652 if( HasRelWidths() )
653 sOut.append(static_cast<sal_Int32>(m_nTabWidth)).append('%');
655 {
656 sal_Int32 nPixWidth = Application::GetDefaultDevice()->LogicToPixel(
657 Size(m_nTabWidth,0), MapMode(MapUnit::MapTwip) ).Width();
658 if( !nPixWidth )
659 nPixWidth = 1;
660
661 sOut.append(nPixWidth);
662 }
663 else
664 {
665 OSL_ENSURE( Application::GetDefaultDevice(), "no Application-Window!?" );
666 sOut.append("100%");
667 }
668 sOut.append("\"");
669 }
670
671 if( (nHSpace || nVSpace) && Application::GetDefaultDevice() && !rWrt.mbReqIF)
672 {
673 Size aPixelSpc =
675 MapMode(MapUnit::MapTwip) );
676 if( !aPixelSpc.Width() && nHSpace )
677 aPixelSpc.setWidth( 1 );
678 if( !aPixelSpc.Height() && nVSpace )
679 aPixelSpc.setHeight( 1 );
680
681 if( aPixelSpc.Width() )
682 {
683 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_hspace
684 "=\"" + OString::number(aPixelSpc.Width()) + "\"");
685 }
686
687 if( aPixelSpc.Height() )
688 {
689 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_vspace
690 "=\"" + OString::number(aPixelSpc.Height()) + "\"");
691 }
692 }
693
694 // output CELLPADDING: from layout or calculated
695 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_cellpadding
696 "=\"" + OString::number(SwHTMLWriter::ToPixel(m_nCellPadding,false)) + "\"");
697
698 // output CELLSPACING: from layout or calculated
699 sOut.append(" " OOO_STRING_SVTOOLS_HTML_O_cellspacing
700 "=\"" + OString::number(SwHTMLWriter::ToPixel(m_nCellSpacing,false)) + "\"");
701
702 rWrt.Strm().WriteOString( sOut );
703 sOut.setLength(0);
704
705 // output background
706 if( pFrameFormat )
707 {
708 if (!rWrt.mbXHTML)
709 {
710 rWrt.OutBackground(pFrameFormat->GetAttrSet(), false);
711 }
712
713 if (rWrt.m_bCfgOutStyles || rWrt.mbXHTML)
714 {
715 rWrt.OutCSS1_TableFrameFormatOptions( *pFrameFormat );
716 }
717 }
718
719 sOut.append('>');
720 rWrt.Strm().WriteOString( sOut );
721 sOut.setLength(0);
722
723 rWrt.IncIndentLevel(); // indent content of table
724
725 // output caption
726 if( pCaption && !pCaption->isEmpty() )
727 {
728 rWrt.OutNewLine(); // <CAPTION> in new line
729 OStringBuffer sOutStr(OOO_STRING_SVTOOLS_HTML_caption);
730 sOutStr.append(" " OOO_STRING_SVTOOLS_HTML_O_align "=\"")
731 .append(bTopCaption ? OOO_STRING_SVTOOLS_HTML_VA_top : OOO_STRING_SVTOOLS_HTML_VA_bottom)
732 .append("\"");
733 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rWrt.GetNamespace() + sOutStr) );
734 HTMLOutFuncs::Out_String( rWrt.Strm(), *pCaption );
735 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_caption), false );
736 }
737
738 const SwWriteTableCols::size_type nCols = m_aCols.size();
739
740 // output <COLGRP>/<COL>: If exporting via layout only when during import
741 // some were there, otherwise always.
742 bool bColGroups = (bColsHaveBorder && !bColsHaveBorderOnly);
743 if( m_bColTags )
744 {
745 if( bColGroups )
746 {
747 rWrt.OutNewLine(); // <COLGRP> in new line
748 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_colgroup) );
749
750 rWrt.IncIndentLevel(); // indent content of <COLGRP>
751 }
752
753 for( SwWriteTableCols::size_type nCol=0; nCol<nCols; ++nCol )
754 {
755 rWrt.OutNewLine(); // </COL> in new line
756
757 const SwWriteTableCol *pColumn = m_aCols[nCol].get();
758
759 HtmlWriter html(rWrt.Strm(), rWrt.maNamespace);
760 html.start(OOO_STRING_SVTOOLS_HTML_col);
761
762 sal_uInt32 nWidth;
763 bool bRel;
764 if( m_bLayoutExport )
765 {
766 bRel = pColumn->HasRelWidthOpt();
767 nWidth = pColumn->GetWidthOpt();
768 }
769 else
770 {
771 bRel = HasRelWidths();
772 nWidth = bRel ? GetRelWidth(nCol,1) : GetAbsWidth(nCol,1);
773 }
774
775 if( bRel )
776 html.attribute(OOO_STRING_SVTOOLS_HTML_O_width, Concat2View(OString::number(nWidth) + "*"));
777 else
778 html.attribute(OOO_STRING_SVTOOLS_HTML_O_width, OString::number(SwHTMLWriter::ToPixel(nWidth,false)));
779 html.end();
780
781 if( bColGroups && pColumn->m_bRightBorder && nCol<nCols-1 )
782 {
783 rWrt.DecIndentLevel(); // indent content of <COLGRP>
784 rWrt.OutNewLine(); // </COLGRP> in new line
785 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_colgroup),
786 false );
787 rWrt.OutNewLine(); // <COLGRP> in new line
788 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_colgroup) );
789 rWrt.IncIndentLevel(); // indent content of <COLGRP>
790 }
791 }
792 if( bColGroups )
793 {
794 rWrt.DecIndentLevel(); // indent content of <COLGRP>
795
796 rWrt.OutNewLine(); // </COLGRP> in new line
797 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_colgroup),
798 false );
799 }
800 }
801
802 // output the lines as table lines
803
804 // Output <TBODY>?
805 bool bTSections = (bRowsHaveBorder && !bRowsHaveBorderOnly);
806 bool bTBody = bTSections;
807
808 // If sections must be outputted, then a THEAD around the first line only
809 // can be outputted if there is a line below the cell.
810 if( bTHead &&
811 (bTSections || bColGroups) &&
812 m_nHeadEndRow<m_aRows.size()-1 && !m_aRows[m_nHeadEndRow]->m_bBottomBorder )
813 bTHead = false;
814
815 // Output <TBODY> only if <THEAD> is outputted.
816 bTSections |= bTHead;
817
818 if( bTSections )
819 {
820 rWrt.OutNewLine(); // <THEAD>/<TDATA> in new line
822 HTMLOutFuncs::Out_AsciiTag(rWrt.Strm(), Concat2View(rWrt.GetNamespace() + aTag));
823
824 rWrt.IncIndentLevel(); // indent content of <THEAD>/<TDATA>
825 }
826
827 for( SwWriteTableRows::size_type nRow = 0; nRow < m_aRows.size(); ++nRow )
828 {
829 const SwWriteTableRow *pRow2 = m_aRows[nRow].get();
830
831 OutTableCells( rWrt, pRow2->GetCells(), pRow2->GetBackground() );
832 if( !m_nCellSpacing && nRow < m_aRows.size()-1 && pRow2->m_bBottomBorder &&
834 {
835 for( auto nCnt = (pRow2->m_nBottomBorder / SvxBorderLineWidth::Thin) - 1; nCnt; --nCnt )
836 {
837 rWrt.OutNewLine();
838 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_tablerow ));
839 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_tablerow),
840 false );
841 }
842 }
843 if( ( (bTHead && nRow==m_nHeadEndRow) ||
844 (bTBody && pRow2->m_bBottomBorder) ) &&
845 nRow < m_aRows.size()-1 )
846 {
847 rWrt.DecIndentLevel(); // indent content of <THEAD>/<TDATA>
848 rWrt.OutNewLine(); // </THEAD>/</TDATA> in new line
850 HTMLOutFuncs::Out_AsciiTag(rWrt.Strm(), Concat2View(rWrt.GetNamespace() + aTag), false);
851 rWrt.OutNewLine(); // <THEAD>/<TDATA> in new line
852
853 if( bTHead && nRow==m_nHeadEndRow )
854 bTHead = false;
855
857 HTMLOutFuncs::Out_AsciiTag(rWrt.Strm(), Concat2View(rWrt.GetNamespace() + aTag));
858 rWrt.IncIndentLevel(); // indent content of <THEAD>/<TDATA>
859 }
860 }
861
862 if( bTSections )
863 {
864 rWrt.DecIndentLevel(); // indent content of <THEAD>/<TDATA>
865
866 rWrt.OutNewLine(); // </THEAD>/</TDATA> in new line
868 HTMLOutFuncs::Out_AsciiTag(rWrt.Strm(), Concat2View(rWrt.GetNamespace() + aTag), false);
869 }
870
871 rWrt.DecIndentLevel(); // indent content of <TABLE>
872
873 rWrt.OutNewLine(); // </TABLE> in new line
874 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_table), false );
875
876 rWrt.m_nDirection = nOldDirection;
877}
878
880 const SwFrameFormat *pFlyFrameFormat,
881 const OUString *pCaption, bool bTopCaption )
882{
883
884 SwTable& rTable = rNode.GetTable();
885
886 SwHTMLWriter & rHTMLWrt = static_cast<SwHTMLWriter&>(rWrt);
887 rHTMLWrt.m_bOutTable = true;
888
889 // The horizontal alignment of the frame (if exists) has priority.
890 // NONE means that no horizontal alignment was outputted.
891 sal_Int16 eFlyHoriOri = text::HoriOrientation::NONE;
892 css::text::WrapTextMode eSurround = css::text::WrapTextMode_NONE;
893 sal_uInt8 nFlyPercentWidth = 0;
894 tools::Long nFlyWidth = 0;
895 sal_uInt16 nFlyHSpace = 0;
896 sal_uInt16 nFlyVSpace = 0;
897 if( pFlyFrameFormat )
898 {
899 eSurround = pFlyFrameFormat->GetSurround().GetSurround();
900 const SwFormatFrameSize& rFrameSize = pFlyFrameFormat->GetFrameSize();
901 nFlyPercentWidth = rFrameSize.GetWidthPercent();
902 nFlyWidth = rFrameSize.GetSize().Width();
903
904 eFlyHoriOri = pFlyFrameFormat->GetHoriOrient().GetHoriOrient();
905 if( text::HoriOrientation::NONE == eFlyHoriOri )
906 eFlyHoriOri = text::HoriOrientation::LEFT;
907
908 const SvxLRSpaceItem& rLRSpace = pFlyFrameFormat->GetLRSpace();
909 nFlyHSpace = static_cast< sal_uInt16 >((rLRSpace.GetLeft() + rLRSpace.GetRight()) / 2);
910
911 const SvxULSpaceItem& rULSpace = pFlyFrameFormat->GetULSpace();
912 nFlyVSpace = (rULSpace.GetUpper() + rULSpace.GetLower()) / 2;
913 }
914
915 // maybe open a FORM
916 bool bPreserveForm = false;
917 if( !rHTMLWrt.m_bPreserveForm )
918 {
919 rHTMLWrt.OutForm( true, &rNode );
920 bPreserveForm = rHTMLWrt.mxFormComps.is();
921 rHTMLWrt.m_bPreserveForm = bPreserveForm;
922 }
923
924 SwFrameFormat *pFormat = rTable.GetFrameFormat();
925
926 const SwFormatFrameSize& rFrameSize = pFormat->GetFrameSize();
927 tools::Long nWidth = rFrameSize.GetSize().Width();
928 sal_uInt8 nPercentWidth = rFrameSize.GetWidthPercent();
929 sal_uInt16 nBaseWidth = o3tl::narrowing<sal_uInt16>(nWidth);
930
931 sal_Int16 eTabHoriOri = pFormat->GetHoriOrient().GetHoriOrient();
932
933 // text::HoriOrientation::NONE and text::HoriOrientation::FULL tables need relative widths
934 sal_uInt16 nNewDefListLvl = 0;
935 bool bRelWidths = false;
936 bool bCheckDefList = false;
937 switch( eTabHoriOri )
938 {
939 case text::HoriOrientation::FULL:
940 // Tables with automatic alignment become tables with 100% width.
941 bRelWidths = true;
942 nWidth = 100;
943 eTabHoriOri = text::HoriOrientation::LEFT;
944 break;
946 {
947 const SvxLRSpaceItem& aLRItem = pFormat->GetLRSpace();
948 if( aLRItem.GetRight() )
949 {
950 // The table width is defined on the basis of the left and
951 // right margin. Therefore we try to define the actual
952 // width of the table. If that's not possible we transform
953 // it to a table with width 100%.
954 nWidth = pFormat->FindLayoutRect(true).Width();
955 if( !nWidth )
956 {
957 bRelWidths = true;
958 nWidth = 100;
959 }
960
961 }
962 else if( nPercentWidth )
963 {
964 // Without a right border the %-width is maintained.
965 nWidth = nPercentWidth;
966 bRelWidths = true;
967 }
968 else
969 {
970 // Without a right margin also an absolute width is maintained.
971 // We still try to define the actual width via the layout.
972 tools::Long nRealWidth = pFormat->FindLayoutRect(true).Width();
973 if( nRealWidth )
974 nWidth = nRealWidth;
975 }
976 bCheckDefList = true;
977 }
978 break;
979 case text::HoriOrientation::LEFT_AND_WIDTH:
980 eTabHoriOri = text::HoriOrientation::LEFT;
981 bCheckDefList = true;
982 [[fallthrough]];
983 default:
984 // In all other case it's possible to use directly an absolute
985 // or relative width.
986 if( nPercentWidth )
987 {
988 bRelWidths = true;
989 nWidth = nPercentWidth;
990 }
991 break;
992 }
993
994 if( bCheckDefList )
995 {
996 OSL_ENSURE( !rHTMLWrt.GetNumInfo().GetNumRule() ||
997 rHTMLWrt.GetNextNumInfo(),
998 "NumInfo for next paragraph is missing!" );
999 const SvxLRSpaceItem& aLRItem = pFormat->GetLRSpace();
1000 if( aLRItem.GetLeft() > 0 && rHTMLWrt.m_nDefListMargin > 0 &&
1001 ( !rHTMLWrt.GetNumInfo().GetNumRule() ||
1002 ( rHTMLWrt.GetNextNumInfo() &&
1003 (rHTMLWrt.GetNextNumInfo()->IsRestart() ||
1004 rHTMLWrt.GetNumInfo().GetNumRule() !=
1005 rHTMLWrt.GetNextNumInfo()->GetNumRule()) ) ) )
1006 {
1007 // If the paragraph before the table is not numbered or the
1008 // paragraph after the table starts with a new numbering or with
1009 // a different rule, we can maintain the indentation with a DL.
1010 // Otherwise we keep the indentation of the numbering.
1011 nNewDefListLvl = static_cast< sal_uInt16 >(
1012 (aLRItem.GetLeft() + (rHTMLWrt.m_nDefListMargin/2)) /
1013 rHTMLWrt.m_nDefListMargin );
1014 }
1015 }
1016
1017 if( !pFlyFrameFormat && nNewDefListLvl != rHTMLWrt.m_nDefListLvl )
1018 rHTMLWrt.OutAndSetDefList( nNewDefListLvl );
1019
1020 if( nNewDefListLvl )
1021 {
1022 if( rHTMLWrt.m_bLFPossible )
1023 rHTMLWrt.OutNewLine();
1024 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rHTMLWrt.GetNamespace() + OOO_STRING_SVTOOLS_HTML_dd) );
1025 }
1026
1027 // eFlyHoriOri and eTabHoriOri now only contain the values of
1028 // LEFT/CENTER and RIGHT!
1029 if( eFlyHoriOri!=text::HoriOrientation::NONE )
1030 {
1031 eTabHoriOri = eFlyHoriOri;
1032 // MIB 4.7.97: If the table has a relative width, then the width is
1033 // adjusted to the width of the frame, therefore we export its width.
1034 // If fixed width, the table width is relevant. Whoever puts tables with
1035 // relative width <100% into frames is to blame when the result looks bad.
1036 if( bRelWidths )
1037 {
1038 nWidth = nFlyPercentWidth ? nFlyPercentWidth : nFlyWidth;
1039 bRelWidths = nFlyPercentWidth > 0;
1040 }
1041 }
1042
1043 sal_Int16 eDivHoriOri = text::HoriOrientation::NONE;
1044 switch( eTabHoriOri )
1045 {
1046 case text::HoriOrientation::LEFT:
1047 // If a left-aligned table has no right sided flow, then we don't need
1048 // an ALIGN=LEFT in the table.
1049 if( eSurround==css::text::WrapTextMode_NONE || eSurround==css::text::WrapTextMode_LEFT )
1050 eTabHoriOri = text::HoriOrientation::NONE;
1051 break;
1052 case text::HoriOrientation::RIGHT:
1053 // Something like that also applies to right-aligned tables,
1054 // here we use a <DIV ALIGN=RIGHT> instead.
1055 if( eSurround==css::text::WrapTextMode_NONE || eSurround==css::text::WrapTextMode_RIGHT )
1056 {
1057 eDivHoriOri = text::HoriOrientation::RIGHT;
1058 eTabHoriOri = text::HoriOrientation::NONE;
1059 }
1060 break;
1061 case text::HoriOrientation::CENTER:
1062 // Almost nobody understands ALIGN=CENTER, therefore we abstain
1063 // from it and use a <CENTER>.
1064 eDivHoriOri = text::HoriOrientation::CENTER;
1065 eTabHoriOri = text::HoriOrientation::NONE;
1066 break;
1067 default:
1068 ;
1069 }
1070 if( text::HoriOrientation::NONE==eTabHoriOri )
1071 nFlyHSpace = nFlyVSpace = 0;
1072
1073 if( !pFormat->GetName().isEmpty() )
1074 rHTMLWrt.OutImplicitMark( pFormat->GetName(), "table" );
1075
1076 if( text::HoriOrientation::NONE!=eDivHoriOri )
1077 {
1078 if( rHTMLWrt.m_bLFPossible )
1079 rHTMLWrt.OutNewLine(); // <CENTER> in new line
1080 if( text::HoriOrientation::CENTER==eDivHoriOri )
1082 else
1083 {
1084 OStringLiteral sOut = OOO_STRING_SVTOOLS_HTML_division
1087 HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), Concat2View(rHTMLWrt.GetNamespace() + sOut) );
1088 }
1089 rHTMLWrt.IncIndentLevel(); // indent content of <CENTER>
1090 rHTMLWrt.m_bLFPossible = true;
1091 }
1092
1093 // If the table isn't in a frame, then you always can output a LF.
1094 if( text::HoriOrientation::NONE==eTabHoriOri )
1095 rHTMLWrt.m_bLFPossible = true;
1096
1097 const SwHTMLTableLayout *pLayout = rTable.GetHTMLTableLayout();
1098
1099#ifdef DBG_UTIL
1100 {
1102 if ( pSh && pSh->GetViewOptions()->IsTest1() )
1103 pLayout = nullptr;
1104 }
1105#endif
1106
1107 if( pLayout && pLayout->IsExportable() )
1108 {
1109 SwHTMLWrtTable aTableWrt( pLayout );
1110 aTableWrt.Write( rHTMLWrt, eTabHoriOri, rTable.GetRowsToRepeat() > 0,
1111 pFormat, pCaption, bTopCaption,
1112 nFlyHSpace, nFlyVSpace );
1113 }
1114 else
1115 {
1116 SwHTMLWrtTable aTableWrt( rTable.GetTabLines(), nWidth,
1117 nBaseWidth, bRelWidths, 0, 0, rTable.GetRowsToRepeat() );
1118 aTableWrt.Write( rHTMLWrt, eTabHoriOri, rTable.GetRowsToRepeat() > 0,
1119 pFormat, pCaption, bTopCaption,
1120 nFlyHSpace, nFlyVSpace );
1121 }
1122
1123 // If the table wasn't in a frame, then you always can output a LF.
1124 if( text::HoriOrientation::NONE==eTabHoriOri )
1125 rHTMLWrt.m_bLFPossible = true;
1126
1127 if( text::HoriOrientation::NONE!=eDivHoriOri )
1128 {
1129 rHTMLWrt.DecIndentLevel(); // indent content of <CENTER>
1130 rHTMLWrt.OutNewLine(); // </CENTER> in new line
1131 OString aTag = text::HoriOrientation::CENTER == eDivHoriOri
1134 HTMLOutFuncs::Out_AsciiTag(rWrt.Strm(), Concat2View(rHTMLWrt.GetNamespace() + aTag), false);
1135 rHTMLWrt.m_bLFPossible = true;
1136 }
1137
1138 // move Pam behind the table
1139 rHTMLWrt.m_pCurrentPam->GetPoint()->Assign( *rNode.EndOfSectionNode() );
1140
1141 if( bPreserveForm )
1142 {
1143 rHTMLWrt.m_bPreserveForm = false;
1144 rHTMLWrt.OutForm( false );
1145 }
1146
1147 rHTMLWrt.m_bOutTable = false;
1148
1149 if( rHTMLWrt.GetNextNumInfo() &&
1150 !rHTMLWrt.GetNextNumInfo()->IsRestart() &&
1151 rHTMLWrt.GetNextNumInfo()->GetNumRule() ==
1152 rHTMLWrt.GetNumInfo().GetNumRule() )
1153 {
1154 // If the paragraph after the table is numbered with the same rule as the
1155 // one before, then the NumInfo of the next paragraph holds the level of
1156 // paragraph before the table. Therefore NumInfo must be fetched again
1157 // to maybe close the Num list.
1158 rHTMLWrt.ClearNextNumInfo();
1159 rHTMLWrt.FillNextNumInfo();
1160 OutHTML_NumberBulletListEnd( rHTMLWrt, *rHTMLWrt.GetNextNumInfo() );
1161 }
1162 return rWrt;
1163}
1164
1165/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
static OutputDevice * GetDefaultDevice()
sal_uInt32 GetValue() const
virtual const SwViewShell * GetCurrentViewShell() const =0
Returns the layout set at the document.
SAL_WARN_UNUSED_RESULT Point PixelToLogic(const Point &rDevicePt) const
SAL_WARN_UNUSED_RESULT Point LogicToPixel(const Point &rLogicPt) const
const T * GetItemIfSet(TypedWhichId< T > nWhich, bool bSrchInParent=true) const
constexpr tools::Long Height() const
void setWidth(tools::Long nWidth)
void setHeight(tools::Long nHeight)
constexpr tools::Long Width() const
SvStream & WriteOString(std::string_view rStr)
SvStream & WriteChar(char nChar)
static const sal_Int16 Thin
const editeng::SvxBorderLine * GetTop() const
const editeng::SvxBorderLine * GetRight() const
const editeng::SvxBorderLine * GetLeft() const
const editeng::SvxBorderLine * GetBottom() const
tools::Long GetRight() const
tools::Long GetLeft() const
const Size & GetSize() const
sal_uInt16 GetUpper() const
sal_uInt16 GetLower() const
SwNodes & GetNodes()
Definition: doc.hxx:417
IDocumentLayoutAccess const & getIDocumentLayoutAccess() const
Definition: doc.cxx:411
SvNumberFormatter * GetNumberFormatter(bool bCreate=true)
Definition: doc.hxx:1418
sal_uInt8 GetWidthPercent() const
Definition: fmtfsize.hxx:91
sal_Int16 GetHoriOrient() const
Definition: fmtornt.hxx:94
css::text::WrapTextMode GetSurround() const
Definition: fmtsrnd.hxx:51
Base class for various Writer styles.
Definition: format.hxx:47
bool IsDefault() const
Definition: format.hxx:129
const SwTableBoxNumFormat & GetTableBoxNumFormat(bool=true) const
TableBox attributes - implemented in cellatr.hxx.
Definition: cellatr.hxx:105
sal_uInt16 GetPoolFormatId() const
Get and set Pool style IDs.
Definition: format.hxx:163
const SwFormatFrameSize & GetFrameSize(bool=true) const
Definition: fmtfsize.hxx:104
const SvxLRSpaceItem & GetLRSpace(bool=true) const
Definition: frmatr.hxx:74
const OUString & GetName() const
Definition: format.hxx:131
const SwAttrSet & GetAttrSet() const
For querying the attribute array.
Definition: format.hxx:136
const SwFormatSurround & GetSurround(bool=true) const
Definition: fmtsrnd.hxx:66
SwFormat * DerivedFrom() const
Definition: format.hxx:128
const SwFormatHoriOrient & GetHoriOrient(bool=true) const
Definition: fmtornt.hxx:115
const SfxPoolItem & GetFormatAttr(sal_uInt16 nWhich, bool bInParents=true) const
If bInParents is FALSE, search only in this format for attribute.
Definition: format.cxx:366
const SvxULSpaceItem & GetULSpace(bool=true) const
Definition: frmatr.hxx:76
std::unique_ptr< SvxBrushItem > makeBackgroundBrushItem(bool=true) const
Definition: format.cxx:736
Style of a layout element.
Definition: frmfmt.hxx:62
SwRect FindLayoutRect(const bool bPrtArea=false, const Point *pPoint=nullptr) const
Definition: atrfrm.cxx:2716
bool IsRestart() const
Definition: htmlnum.hxx:78
SwNumRule * GetNumRule()
Definition: htmlnum.hxx:69
bool IsExportable() const
Definition: htmltbl.hxx:333
bool m_bPreserveForm
Definition: wrthtml.hxx:399
bool mbXHTML
If XHTML markup should be written instead of HTML.
Definition: wrthtml.hxx:410
void OutAndSetDefList(sal_uInt16 nNewLvl)
Definition: htmlatr.cxx:120
bool m_bOutTable
Definition: wrthtml.hxx:377
void ChangeParaToken(HtmlTokenId nNew)
Definition: htmlatr.cxx:158
sal_Int32 m_nDefListMargin
Definition: wrthtml.hxx:342
void IncIndentLevel()
Definition: wrthtml.hxx:525
void OutDirection(SvxFrameDirection nDir)
Definition: wrthtml.cxx:1474
bool m_bLFPossible
Definition: wrthtml.hxx:395
css::uno::Reference< css::container::XIndexContainer > mxFormComps
Definition: wrthtml.hxx:313
bool m_bTextAttr
Definition: wrthtml.hxx:373
bool m_bOutOpts
Definition: wrthtml.hxx:375
bool m_bOutFlyFrame
Definition: wrthtml.hxx:380
void OutCSS1_TableFrameFormatOptions(const SwFrameFormat &rFrameFormat)
Writes the formatting for tables.
Definition: css1atr.cxx:2050
bool m_bCfgOutStyles
Definition: wrthtml.hxx:355
SvxFrameDirection m_nDirection
Definition: wrthtml.hxx:349
sal_uInt16 m_nDefListLvl
Definition: wrthtml.hxx:341
void DecIndentLevel()
Definition: wrthtml.hxx:529
OString GetNamespace() const
Determines the prefix string needed to respect the requested namespace alias.
Definition: wrthtml.cxx:1570
void Out_SwDoc(SwPaM *)
Definition: wrthtml.cxx:882
void FillNextNumInfo()
bool mbReqIF
If the ReqIF subset of XHTML should be written.
Definition: wrthtml.hxx:414
SwHTMLNumRuleInfo & GetNumInfo()
Definition: wrthtml.hxx:556
void OutNewLine(bool bCheck=false)
Definition: wrthtml.cxx:1521
static sal_uInt32 ToPixel(sal_uInt32 nVal, const bool bVert)
Definition: htmlatr.cxx:2605
OString maNamespace
XML namespace, in case of XHTML.
Definition: wrthtml.hxx:412
void ClearNextNumInfo()
SwHTMLNumRuleInfo * GetNextNumInfo()
Definition: wrthtml.hxx:560
SvxFrameDirection GetHTMLDirection(SvxFrameDirection nDir) const
Definition: wrthtml.cxx:1455
void OutForm(bool bTagOn=true, const SwStartNode *pStNd=nullptr)
Definition: htmlforw.cxx:225
void OutImplicitMark(std::u16string_view rMark, const char *pMarkType)
Definition: wrthtml.cxx:1314
void OutCSS1_TableCellBordersAndBG(const SwFrameFormat &rFrameFormat, const SvxBrushItem *pBrushItem)
Writes the borders and background for table cells.
Definition: css1atr.cxx:2071
void OutBackground(const SvxBrushItem *pBrushItem, bool bGraphic)
Definition: wrthtml.cxx:1362
Base class of the Writer document model elements.
Definition: node.hxx:98
SwNodeOffset GetIndex() const
Definition: node.hxx:312
bool IsTextNode() const
Definition: node.hxx:685
SwNodeOffset EndOfSectionIndex() const
Definition: node.hxx:726
const SwEndNode * EndOfSectionNode() const
Definition: node.hxx:731
void Width(tools::Long nNew)
Definition: swrect.hxx:189
Starts a section of nodes in the document model.
Definition: node.hxx:348
SwTableBox is one table cell in the document model.
Definition: swtable.hxx:426
SwFrameFormat * GetFrameFormat()
Definition: swtable.hxx:464
SwTableLines & GetTabLines()
Definition: swtable.hxx:457
const SwStartNode * GetSttNd() const
Definition: swtable.hxx:478
SwTableLine is one table row in the document model.
Definition: swtable.hxx:364
SwFrameFormat * GetFrameFormat()
Definition: swtable.hxx:386
SwTableBoxes & GetTabBoxes()
Definition: swtable.hxx:374
size_type size() const
Definition: swtable.hxx:76
std::vector< SwTableLine * >::size_type size_type
Definition: swtable.hxx:68
const SwTable & GetTable() const
Definition: node.hxx:542
SwTable is one table in the document model, containing rows (which contain cells).
Definition: swtable.hxx:113
SwTableLines & GetTabLines()
Definition: swtable.hxx:204
SwTableFormat * GetFrameFormat()
Definition: swtable.hxx:207
SwHTMLTableLayout * GetHTMLTableLayout()
Definition: swtable.hxx:180
sal_uInt16 GetRowsToRepeat() const
Definition: swtable.hxx:199
SwTextNode is a paragraph in the document model.
Definition: ndtxt.hxx:111
bool IsTest1() const
Definition: viewopt.hxx:602
const SwViewOption * GetViewOptions() const
Definition: viewsh.hxx:433
tools::Long GetHeight() const
Definition: wrtswtbl.hxx:81
sal_uInt32 GetWidthOpt() const
Definition: wrtswtbl.hxx:91
sal_uInt16 GetRowSpan() const
Definition: wrtswtbl.hxx:78
bool HasPercentWidthOpt() const
Definition: wrtswtbl.hxx:92
sal_Int16 GetVertOri() const
Definition: wrtswtbl.cxx:38
const SwTableBox * GetBox() const
Definition: wrtswtbl.hxx:73
const SvxBrushItem * GetBackground() const
Definition: wrtswtbl.hxx:84
sal_uInt16 GetRow() const
Definition: wrtswtbl.hxx:75
sal_uInt16 GetCol() const
Definition: wrtswtbl.hxx:76
sal_uInt16 GetColSpan() const
Definition: wrtswtbl.hxx:79
bool HasRelWidthOpt() const
Definition: wrtswtbl.hxx:186
sal_uInt32 GetWidthOpt() const
Definition: wrtswtbl.hxx:185
sal_uInt16 m_nBottomBorder
Definition: wrtswtbl.hxx:113
const SvxBrushItem * GetBackground() const
Definition: wrtswtbl.hxx:130
const SwWriteTableCells & GetCells() const
Definition: wrtswtbl.hxx:135
sal_uInt16 m_nTopBorder
Definition: wrtswtbl.hxx:112
bool m_bBottomBorder
Definition: wrtswtbl.hxx:116
virtual bool ShouldExpandSub(const SwTableBox *pBox, bool bExpandedBefore, sal_uInt16 nDepth) const
Definition: wrtswtbl.cxx:384
SvStream & Strm()
Definition: writer.cxx:214
SwDoc * m_pDoc
Definition: shellio.hxx:401
std::shared_ptr< SwUnoCursor > m_pCurrentPam
Definition: shellio.hxx:403
constexpr ::Color COL_TRANSPARENT(ColorTransparency, 0xFF, 0xFF, 0xFF, 0xFF)
Writer & OutCSS1_TableBGStyleOpt(Writer &rWrt, const SfxPoolItem &rHt)
Writes the background of table rows.
Definition: css1atr.cxx:1804
int nCount
sal_Int16 nValue
SvxFrameDirection
constexpr TypedWhichId< SwTableBoxValue > RES_BOXATR_VALUE(152)
constexpr TypedWhichId< SwTableBoxNumFormat > RES_BOXATR_FORMAT(RES_BOXATR_BEGIN)
constexpr TypedWhichId< SvxBoxItem > RES_BOX(106)
constexpr TypedWhichId< SvxBrushItem > RES_BACKGROUND(105)
#define OOO_STRING_SVTOOLS_HTML_O_align
#define OOO_STRING_SVTOOLS_HTML_tabledata
#define OOO_STRING_SVTOOLS_HTML_division
#define OOO_STRING_SVTOOLS_HTML_dd
#define OOO_STRING_SVTOOLS_HTML_tableheader
#define OOO_STRING_SVTOOLS_HTML_tbody
#define OOO_STRING_SVTOOLS_HTML_center
#define OOO_STRING_SVTOOLS_HTML_AL_right
#define OOO_STRING_SVTOOLS_HTML_thead
#define OOO_STRING_SVTOOLS_HTML_table
Writer & OutHTML_NumberBulletListEnd(SwHTMLWriter &rWrt, const SwHTMLNumRuleInfo &rNextInfo)
Writer & OutHTML_SwTableNode(Writer &rWrt, SwTableNode &rNode, const SwFrameFormat *pFlyFrameFormat, const OUString *pCaption, bool bTopCaption)
Definition: htmltabw.cxx:879
static bool lcl_TableBox_HasTabBorders(const SwTableBox *pBox, bool *pBorders)
Definition: htmltabw.cxx:197
#define MAX_DEPTH
Definition: htmltabw.cxx:55
static bool lcl_TableLine_HasTabBorders(const SwTableLine *pLine, bool *pBorders)
Definition: htmltabw.cxx:222
static void Write(std::u16string_view aString, SvStream &rStream)
Definition: ww8scan.cxx:6713
int i
long Long
@ RES_POOLCOLL_TABLE
Subgroup table.
Definition: poolfmt.hxx:341
@ RES_POOLCOLL_TABLE_HDLN
Table of Contents - heading.
Definition: poolfmt.hxx:342
static SVT_DLLPUBLIC SvStream & Out_AsciiTag(SvStream &, std::string_view rStr, bool bOn=true)
static SVT_DLLPUBLIC SvStream & Out_String(SvStream &, const OUString &, OUString *pNonConvertableChars=nullptr)
static SVT_DLLPUBLIC OString CreateTableDataOptionsValNum(bool bValue, double fVal, sal_uInt32 nFormat, SvNumberFormatter &rFormatter, OUString *pNonConvertableChars=nullptr)
std::vector< SwTableBox * > SwTableBoxes
Definition: swtable.hxx:105
SvxBoxItem & rBoxItem
unsigned char sal_uInt8
#define SAL_MAX_UINT32
std::vector< std::unique_ptr< SwWriteTableCell > > SwWriteTableCells
Definition: wrtswtbl.hxx:95