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 #ifndef INCLUDED_SW_INC_SWTABLE_HXX
20 #define INCLUDED_SW_INC_SWTABLE_HXX
21 
22 #include <tools/solar.h>
23 #include <tools/ref.hxx>
24 #include "tblenum.hxx"
25 #include "swtypes.hxx"
26 #include "calbck.hxx"
27 #include "swrect.hxx"
28 #include "swtblfmt.hxx"
29 
30 #include <memory>
31 #include <vector>
32 #include <algorithm>
33 #include <o3tl/sorted_vector.hxx>
34 
35 class SwStartNode;
36 class SwFormat;
37 class Color;
38 class SwHTMLTableLayout;
39 class SwTableLine;
40 class SwTableBox;
41 class SwTableNode;
42 class SwTabCols;
43 class SwDoc;
44 class SwSelBoxes;
45 class SwTableCalcPara;
46 struct SwPosition;
47 class SwNodeIndex;
48 class SwNode;
49 class SfxPoolItem;
50 class SwUndoTableMerge;
51 class SwUndo;
52 class SwPaM;
53 class SwUndoTableCpyTable;
54 class SwBoxSelection;
55 struct SwSaveRowSpan;
56 struct Parm;
57 class SwServerObject;
58 
59 void sw_GetTableBoxColStr( sal_uInt16 nCol, OUString& rNm );
60 
61 class SwTableLines
62 {
63     std::vector<SwTableLine*> m_vLines;
64 
65 public:
66     typedef std::vector<SwTableLine*>::size_type size_type;
67     typedef std::vector<SwTableLine*>::iterator iterator;
68     typedef std::vector<SwTableLine*>::const_iterator const_iterator;
69 
70     // free's any remaining child objects
71     ~SwTableLines();
72 
empty() const73     bool empty() const { return m_vLines.empty(); }
size() const74     size_type size() const { return m_vLines.size(); }
begin()75     iterator begin() { return m_vLines.begin(); }
begin() const76     const_iterator begin() const { return m_vLines.begin(); }
end()77     iterator end() { return m_vLines.end(); }
end() const78     const_iterator end() const { return m_vLines.end(); }
front() const79     SwTableLine* front() const { return m_vLines.front(); }
back() const80     SwTableLine* back() const { return m_vLines.back(); }
clear()81     void clear() { m_vLines.clear(); }
erase(iterator aIt)82     iterator erase( iterator aIt ) { return m_vLines.erase( aIt ); }
erase(iterator aFirst,iterator aLast)83     iterator erase( iterator aFirst, iterator aLast ) { return m_vLines.erase( aFirst, aLast ); }
insert(iterator aIt,SwTableLine * pLine)84     iterator insert( iterator aIt, SwTableLine* pLine ) { return m_vLines.insert( aIt, pLine ); }
85     template<typename TInputIterator>
insert(iterator aIt,TInputIterator aFirst,TInputIterator aLast)86     void insert( iterator aIt, TInputIterator aFirst, TInputIterator aLast )
87     {
88         m_vLines.insert( aIt, aFirst, aLast );
89     }
push_back(SwTableLine * pLine)90     void push_back( SwTableLine* pLine ) { m_vLines.push_back( pLine ); }
reserve(size_type nSize)91     void reserve( size_type nSize ) { m_vLines.reserve( nSize ); }
operator [](size_type nPos)92     SwTableLine*& operator[]( size_type nPos ) { return m_vLines[ nPos ]; }
operator [](size_type nPos) const93     SwTableLine* operator[]( size_type nPos ) const { return m_vLines[ nPos ]; }
94 
95     // return USHRT_MAX if not found, else index of position
GetPos(const SwTableLine * pBox) const96     sal_uInt16 GetPos(const SwTableLine* pBox) const
97     {
98         const_iterator it = std::find(begin(), end(), pBox);
99         return it == end() ? USHRT_MAX : it - begin();
100     }
101 };
102 
103 using SwTableBoxes = std::vector<SwTableBox*>;
104 
105 // Save content-bearing box-pointers additionally in a sorted array
106 // (for calculation in table).
107 class SwTableSortBoxes : public o3tl::sorted_vector<SwTableBox*> {};
108 
109 /// SwTable is one table in the document model, containing rows (which contain cells).
110 class SW_DLLPUBLIC SwTable: public SwClient          //Client of FrameFormat.
111 {
112 
113 protected:
114     SwTableLines m_aLines;
115     SwTableSortBoxes m_TabSortContentBoxes;
116     tools::SvRef<SwServerObject> m_xRefObj;   // In case DataServer -> pointer is set.
117 
118     std::shared_ptr<SwHTMLTableLayout> m_xHTMLLayout;
119 
120     // Usually, the table node of a SwTable can be accessed by getting a box
121     // out of m_TabSortContentBoxes, which know their SwStartNode. But in some rare
122     // cases, we need to know the table node of a SwTable, before the table
123     // boxes have been build (SwTableNode::MakeCopy with tables in tables).
124     SwTableNode* m_pTableNode;
125 
126     // Should that be adjustable for every table?
127     TableChgMode  m_eTableChgMode;
128 
129     sal_uInt16      m_nGraphicsThatResize;    // Count of Grfs that initiate a resize of table
130                                         // at HTML-import.
131     sal_uInt16      m_nRowsToRepeat;      // Number of rows to repeat on every page.
132 
133     /// Name of the table style to be applied on this table.
134     OUString maTableStyleName;
135 
136     bool        m_bModifyLocked   :1;
137     bool        m_bNewModel       :1; // false: old SubTableModel; true: new RowSpanModel
138 
139     virtual void Modify( const SfxPoolItem* pOld, const SfxPoolItem* pNew ) override;
140 
141 public:
142     enum SearchType
143     {
144         SEARCH_NONE, // Default: expand to rectangle
145         SEARCH_ROW, // row selection
146         SEARCH_COL  // column selection
147     };
148 
149 
150     explicit SwTable();
151     virtual ~SwTable() override;
152 
153     // @@@ public copy ctor, but no copy assignment?
154     SwTable( const SwTable& rTable );       // no copy of the lines !!
155 private:
156     // @@@ public copy ctor, but no copy assignment?
157     SwTable & operator= (const SwTable &) = delete;
158     bool OldMerge( SwDoc*, const SwSelBoxes&, SwTableBox*, SwUndoTableMerge* );
159     bool OldSplitRow( SwDoc*, const SwSelBoxes&, sal_uInt16, bool );
160     bool NewMerge( SwDoc*, const SwSelBoxes&, const SwSelBoxes& rMerged,
161                    SwUndoTableMerge* );
162     bool NewSplitRow( SwDoc*, const SwSelBoxes&, sal_uInt16, bool );
163     std::unique_ptr<SwBoxSelection> CollectBoxSelection( const SwPaM& rPam ) const;
164     void InsertSpannedRow( SwDoc* pDoc, sal_uInt16 nIdx, sal_uInt16 nCnt );
165     bool InsertRow_( SwDoc*, const SwSelBoxes&, sal_uInt16 nCnt, bool bBehind );
166     bool NewInsertCol( SwDoc*, const SwSelBoxes& rBoxes, sal_uInt16 nCnt, bool );
167     void FindSuperfluousRows_( SwSelBoxes& rBoxes, SwTableLine*, SwTableLine* );
168     void AdjustWidths( const long nOld, const long nNew );
169     void NewSetTabCols( Parm &rP, const SwTabCols &rNew, const SwTabCols &rOld,
170                         const SwTableBox *pStart, bool bCurRowOnly );
171 
172 public:
173 
GetHTMLTableLayout()174     SwHTMLTableLayout *GetHTMLTableLayout() { return m_xHTMLLayout.get(); }
GetHTMLTableLayout() const175     const SwHTMLTableLayout *GetHTMLTableLayout() const { return m_xHTMLLayout.get(); }
176     void SetHTMLTableLayout(std::shared_ptr<SwHTMLTableLayout> const& r);    //Change of property!
177 
IncGrfsThatResize()178     sal_uInt16 IncGrfsThatResize() { return ++m_nGraphicsThatResize; }
DecGrfsThatResize()179     sal_uInt16 DecGrfsThatResize() { return m_nGraphicsThatResize ? --m_nGraphicsThatResize : 0; }
180 
LockModify()181     void LockModify()   { m_bModifyLocked = true; }   // Must be used always
UnlockModify()182     void UnlockModify() { m_bModifyLocked = false;}   // in pairs!
183 
SetTableModel(bool bNew)184     void SetTableModel( bool bNew ){ m_bNewModel = bNew; }
IsNewModel() const185     bool IsNewModel() const { return m_bNewModel; }
186 
187     /// Return the table style name of this table.
GetTableStyleName() const188     const OUString& GetTableStyleName() const { return maTableStyleName; }
189 
190     /// Set the new table style name for this table.
SetTableStyleName(const OUString & rName)191     void SetTableStyleName(const OUString& rName) { maTableStyleName = rName; }
192 
GetRowsToRepeat() const193     sal_uInt16 GetRowsToRepeat() const { return std::min( static_cast<sal_uInt16>(GetTabLines().size()), m_nRowsToRepeat ); }
SetRowsToRepeat(sal_uInt16 nNumOfRows)194     void SetRowsToRepeat( sal_uInt16 nNumOfRows ) { m_nRowsToRepeat = nNumOfRows; }
195 
196     bool IsHeadline( const SwTableLine& rLine ) const;
197 
GetTabLines()198           SwTableLines &GetTabLines() { return m_aLines; }
GetTabLines() const199     const SwTableLines &GetTabLines() const { return m_aLines; }
200 
GetFrameFormat()201     SwTableFormat* GetFrameFormat()       { return static_cast<SwTableFormat*>(GetRegisteredIn()); }
GetFrameFormat() const202     SwTableFormat* GetFrameFormat() const { return const_cast<SwTableFormat*>(static_cast<const SwTableFormat*>(GetRegisteredIn())); }
203 
204     void GetTabCols( SwTabCols &rToFill, const SwTableBox *pStart,
205                      bool bHidden = false, bool bCurRowOnly = false ) const;
206     void SetTabCols( const SwTabCols &rNew, const SwTabCols &rOld,
207                      const SwTableBox *pStart, bool bCurRowOnly );
208 
209 // The following functions are for new table model only...
210     void CreateSelection(  const SwPaM& rPam, SwSelBoxes& rBoxes,
211         const SearchType eSearchType, bool bProtect ) const;
212     void CreateSelection( const SwNode* pStart, const SwNode* pEnd,
213         SwSelBoxes& rBoxes, const SearchType eSearchType, bool bProtect ) const;
214     void ExpandSelection( SwSelBoxes& rBoxes ) const;
215     // When a table is split into two tables, the row spans which overlaps
216     // the split have to be corrected and stored for undo
217     // SwSavRowSpan is the structure needed by Undo to undo the split operation
218     // CleanUpRowSpan corrects the (top of the) second table and delivers the structure
219     // for Undo
220     std::unique_ptr<SwSaveRowSpan> CleanUpTopRowSpan( sal_uInt16 nSplitLine );
221     // RestoreRowSpan is called by Undo to restore the old row span values
222     void RestoreRowSpan( const SwSaveRowSpan& );
223     // CleanUpBottomRowSpan corrects the overhanging row spans at the end of the first table
224     void CleanUpBottomRowSpan( sal_uInt16 nDelLines );
225 
226 // The following functions are "pseudo-virtual", i.e. they are different for old and new table model
227 // It's not allowed to change the table model after the first call of one of these functions.
228 
Merge(SwDoc * pDoc,const SwSelBoxes & rBoxes,const SwSelBoxes & rMerged,SwTableBox * pMergeBox,SwUndoTableMerge * pUndo)229     bool Merge( SwDoc* pDoc, const SwSelBoxes& rBoxes, const SwSelBoxes& rMerged,
230                 SwTableBox* pMergeBox, SwUndoTableMerge* pUndo )
231     {
232         return m_bNewModel ? NewMerge( pDoc, rBoxes, rMerged, pUndo ) :
233                              OldMerge( pDoc, rBoxes, pMergeBox, pUndo );
234     }
SplitRow(SwDoc * pDoc,const SwSelBoxes & rBoxes,sal_uInt16 nCnt,bool bSameHeight)235     bool SplitRow( SwDoc* pDoc, const SwSelBoxes& rBoxes, sal_uInt16 nCnt,
236                    bool bSameHeight )
237     {
238         return m_bNewModel ? NewSplitRow( pDoc, rBoxes, nCnt, bSameHeight ) :
239                            OldSplitRow( pDoc, rBoxes, nCnt, bSameHeight );
240     }
241     bool PrepareMerge( const SwPaM& rPam, SwSelBoxes& rBoxes,
242         SwSelBoxes& rMerged, SwTableBox** ppMergeBox, SwUndoTableMerge* pUndo );
243     void ExpandColumnSelection( SwSelBoxes& rBoxes, long &rMin, long &rMax ) const;
244     void PrepareDeleteCol( long nMin, long nMax );
245 
246     bool InsertCol( SwDoc*, const SwSelBoxes& rBoxes,
247                     sal_uInt16 nCnt, bool bBehind );
248     bool InsertRow( SwDoc*, const SwSelBoxes& rBoxes,
249                     sal_uInt16 nCnt, bool bBehind );
250     void PrepareDelBoxes( const SwSelBoxes& rBoxes );
251     bool DeleteSel( SwDoc*, const SwSelBoxes& rBoxes, const SwSelBoxes* pMerged,
252         SwUndo* pUndo, const bool bDelMakeFrames, const bool bCorrBorder );
253     bool SplitCol( SwDoc* pDoc, const SwSelBoxes& rBoxes, sal_uInt16 nCnt );
254 
FindSuperfluousRows(SwSelBoxes & rBoxes)255     void FindSuperfluousRows( SwSelBoxes& rBoxes )
256         { FindSuperfluousRows_( rBoxes, nullptr, nullptr ); }
257     void CheckRowSpan( SwTableLine* &rpLine, bool bUp ) const;
258 
GetTabSortBoxes()259           SwTableSortBoxes& GetTabSortBoxes()       { return m_TabSortContentBoxes; }
GetTabSortBoxes() const260     const SwTableSortBoxes& GetTabSortBoxes() const { return m_TabSortContentBoxes; }
261 
262     // Read 1st number and delete it from string (used by GetTableBox and SwTableField).
263 
264     // #i80314#
265     // add 3rd parameter in order to control validation check on <rStr>
266     static sal_uInt16 GetBoxNum( OUString& rStr,
267                               bool bFirst = false,
268                               const bool bPerformValidCheck = false );
269 
270     // Search content-bearing box with that name.
271 
272     // #i80314#
273     // add 2nd parameter in order to control validation check in called method
274     // <GetBoxNum(..)>
275     const SwTableBox* GetTableBox( const OUString& rName,
276                                  const bool bPerformValidCheck = false ) const;
277     // Copy selected boxes to another document.
278     bool MakeCopy( SwDoc*, const SwPosition&, const SwSelBoxes&,
279                     bool bCpyName = false ) const;
280     // Copy table in this
281     bool InsTable( const SwTable& rCpyTable, const SwNodeIndex&,
282                     SwUndoTableCpyTable* pUndo );
283     bool InsTable( const SwTable& rCpyTable, const SwSelBoxes&,
284                     SwUndoTableCpyTable* pUndo );
285     bool InsNewTable( const SwTable& rCpyTable, const SwSelBoxes&,
286                       SwUndoTableCpyTable* pUndo );
287     // Copy headline of table (with content!) into another one.
288     void CopyHeadlineIntoTable( SwTableNode& rTableNd );
289 
290     // Get box, whose start index is set on nBoxStt.
291           SwTableBox* GetTableBox( sal_uLong nSttIdx );
GetTableBox(sal_uLong nSttIdx) const292     const SwTableBox* GetTableBox( sal_uLong nSttIdx ) const
293                         {   return const_cast<SwTable*>(this)->GetTableBox( nSttIdx );  }
294 
295     // Returns true if table contains nestings.
296     bool IsTableComplex() const;
297 
298     // Returns true if table or selection is balanced.
299     bool IsTableComplexForChart( const OUString& rSel ) const;
300 
301     // Search all content-bearing boxes of the base line on which this box stands.
302     // rBoxes as a return value for immediate use.
303     // bToTop = true -> up to base line, false-> else only line of box.
304     static SwSelBoxes& SelLineFromBox( const SwTableBox* pBox,
305                             SwSelBoxes& rBoxes, bool bToTop = true );
306 
307     // Get information from client.
308     virtual bool GetInfo( SfxPoolItem& ) const override;
309 
310     // Search in format for registered table.
311     static SwTable * FindTable( SwFrameFormat const*const pFormat );
312 
313     // Clean up structure a bit.
314     void GCLines();
315 
316     // Returns the table node via m_TabSortContentBoxes or pTableNode.
317     SwTableNode* GetTableNode() const;
SetTableNode(SwTableNode * pNode)318     void SetTableNode( SwTableNode* pNode ) { m_pTableNode = pNode; }
319 
320     // Data server methods.
321     void SetRefObject( SwServerObject* );
GetObject() const322     const SwServerObject* GetObject() const     {  return m_xRefObj.get(); }
GetObject()323           SwServerObject* GetObject()           {  return m_xRefObj.get(); }
324 
325     // Fill data for chart.
326     void UpdateCharts() const;
327 
GetTableChgMode() const328     TableChgMode GetTableChgMode() const        { return m_eTableChgMode; }
SetTableChgMode(TableChgMode eMode)329     void SetTableChgMode( TableChgMode eMode )  { m_eTableChgMode = eMode; }
330 
331     bool SetColWidth( SwTableBox& rCurrentBox, TableChgWidthHeightType eType,
332                         SwTwips nAbsDiff, SwTwips nRelDiff, std::unique_ptr<SwUndo>* ppUndo );
333     bool SetRowHeight( SwTableBox& rCurrentBox, TableChgWidthHeightType eType,
334                         SwTwips nAbsDiff, SwTwips nRelDiff, std::unique_ptr<SwUndo>* ppUndo );
335     void RegisterToFormat( SwFormat& rFormat );
336 #ifdef DBG_UTIL
337     void CheckConsistency() const;
338 #endif
339 
340     bool HasLayout() const;
341 };
342 
343 /// SwTableLine is one table row in the document model.
344 class SW_DLLPUBLIC SwTableLine: public SwClient     // Client of FrameFormat.
345 {
346     SwTableBoxes m_aBoxes;
347     SwTableBox *m_pUpper;
348 
349 public:
350 
351     SwTableLine( SwTableLineFormat*, sal_uInt16 nBoxes, SwTableBox *pUp );
352     virtual ~SwTableLine() override;
353 
GetTabBoxes()354           SwTableBoxes &GetTabBoxes() { return m_aBoxes; }
GetTabBoxes() const355     const SwTableBoxes &GetTabBoxes() const { return m_aBoxes; }
GetBoxPos(const SwTableBox * pBox) const356     sal_uInt16 GetBoxPos(const SwTableBox* pBox) const
357     {
358         SwTableBoxes::const_iterator it = std::find(m_aBoxes.begin(), m_aBoxes.end(), pBox);
359         return it == m_aBoxes.end() ? USHRT_MAX : it - m_aBoxes.begin();
360     }
361 
GetUpper()362           SwTableBox *GetUpper() { return m_pUpper; }
GetUpper() const363     const SwTableBox *GetUpper() const { return m_pUpper; }
SetUpper(SwTableBox * pNew)364     void SetUpper( SwTableBox *pNew ) { m_pUpper = pNew; }
365 
GetFrameFormat()366     SwFrameFormat* GetFrameFormat()       { return static_cast<SwFrameFormat*>(GetRegisteredIn()); }
GetFrameFormat() const367     SwFrameFormat* GetFrameFormat() const { return const_cast<SwFrameFormat*>(static_cast<const SwFrameFormat*>(GetRegisteredIn())); }
368 
369     // Creates an own FrameFormat if more lines depend on it.
370     SwFrameFormat* ClaimFrameFormat();
371     void ChgFrameFormat( SwTableLineFormat* pNewFormat );
372 
373     // Search next/previous box with content.
374     SwTableBox* FindNextBox( const SwTable&, const SwTableBox* =nullptr,
375                             bool bOvrTableLns=true ) const;
376     SwTableBox* FindPreviousBox( const SwTable&, const SwTableBox* =nullptr,
377                             bool bOvrTableLns=true ) const;
378 
379     SwTwips GetTableLineHeight( bool& bLayoutAvailable ) const;
380 
381     bool hasSoftPageBreak() const;
382     void RegisterToFormat( SwFormat& rFormat );
383 };
384 
385 /// SwTableBox is one table cell in the document model.
386 class SW_DLLPUBLIC SwTableBox: public SwClient      //Client of FrameFormat.
387 {
388     friend class SwNodes;           // Transpose index.
389     friend void DelBoxNode(SwTableSortBoxes const &);  // Delete StartNode* !
390     friend class SwXMLTableContext;
391 
392     SwTableBox( const SwTableBox & ) = delete;
393     SwTableBox &operator=( const SwTableBox &) = delete;
394 
395     SwTableLines m_aLines;
396     const SwStartNode * m_pStartNode;
397     SwTableLine *m_pUpper;
398 
399     std::unique_ptr<Color> mpUserColor;
400     std::unique_ptr<Color> mpNumFormatColor;
401     long mnRowSpan;
402     bool mbDummyFlag;
403 
404     /// Do we contain any direct formatting?
405     bool mbDirectFormatting;
406 
407     // In case Format contains formulas/values already,
408     // a new one must be created for the new box.
409     static SwTableBoxFormat* CheckBoxFormat( SwTableBoxFormat* );
410 
411 public:
412 
413     SwTableBox( SwTableBoxFormat*, sal_uInt16 nLines, SwTableLine *pUp );
414     SwTableBox( SwTableBoxFormat*, const SwStartNode&, SwTableLine *pUp );
415     SwTableBox( SwTableBoxFormat*, const SwNodeIndex&, SwTableLine *pUp );
416     virtual ~SwTableBox() override;
417 
GetTabLines()418           SwTableLines &GetTabLines() { return m_aLines; }
GetTabLines() const419     const SwTableLines &GetTabLines() const { return m_aLines; }
420 
GetUpper()421           SwTableLine *GetUpper() { return m_pUpper; }
GetUpper() const422     const SwTableLine *GetUpper() const { return m_pUpper; }
SetUpper(SwTableLine * pNew)423     void SetUpper( SwTableLine *pNew ) { m_pUpper = pNew; }
424 
GetFrameFormat()425     SwFrameFormat* GetFrameFormat()       { return static_cast<SwFrameFormat*>(GetRegisteredIn()); }
GetFrameFormat() const426     SwFrameFormat* GetFrameFormat() const { return const_cast<SwFrameFormat*>(static_cast<const SwFrameFormat*>(GetRegisteredIn())); }
427 
428     /// Set that this table box contains formatting that is not set by the table style.
SetDirectFormatting(bool bDirect)429     void SetDirectFormatting(bool bDirect) { mbDirectFormatting = bDirect; }
430 
431     /// Do we contain any direct formatting (ie. something not affected by the table style)?
HasDirectFormatting() const432     bool HasDirectFormatting() const { return mbDirectFormatting; }
433 
434     // Creates its own FrameFormat if more boxes depend on it.
435     SwFrameFormat* ClaimFrameFormat();
436     void ChgFrameFormat( SwTableBoxFormat *pNewFormat, bool bNeedToReregister = true );
437 
438     void RemoveFromTable();
GetSttNd() const439     const SwStartNode *GetSttNd() const { return m_pStartNode; }
440     sal_uLong GetSttIdx() const;
441 
442     // Search next/previous box with content.
443     SwTableBox* FindNextBox( const SwTable&, const SwTableBox*,
444                             bool bOvrTableLns=true ) const;
445     SwTableBox* FindPreviousBox( const SwTable&, const SwTableBox* ) const;
446     // Return name of this box. It is determined dynamically and
447     // is calculated from the position in the lines/boxes/table.
448     OUString GetName() const;
449     // Return "value" of box (for calculating in table).
450     double GetValue( SwTableCalcPara& rPara ) const;
451 
452     // Computes "coordinates" of a box, used to computed selection
453     // width or height when inserting cols or rows
454     Point GetCoordinates() const;
455 
456     bool IsInHeadline( const SwTable* pTable ) const;
457 
458     // Contains box contents, that can be formatted as a number?
459     bool HasNumContent( double& rNum, sal_uInt32& rFormatIndex,
460                     bool& rIsEmptyTextNd ) const;
461     sal_uLong IsValidNumTextNd( bool bCheckAttr = true ) const;
462     // If a table formula is set, test if box contents is congruent with number.
463     // (For Redo of change of NumFormat!).
464     bool IsNumberChanged() const;
465 
466     // Is that a formula box or a box with numeric contents (AutoSum)?
467     // What it is indicated by the return value - the WhichId of the attribute.
468     // Empty boxes have the return value USHRT_MAX !!
469     sal_uInt16 IsFormulaOrValueBox() const;
470 
471     // Loading of a document requires an actualization of cells with values
472     void ActualiseValueBox();
473 
474     // Access on internal data - currently used for the NumFormatter.
475     inline const Color* GetSaveUserColor()  const;
476     inline const Color* GetSaveNumFormatColor() const;
477     inline void SetSaveUserColor(const Color* p );
478     inline void SetSaveNumFormatColor( const Color* p );
479 
480     long getRowSpan() const;
481     void setRowSpan( long nNewRowSpan );
482     bool getDummyFlag() const;
483     void setDummyFlag( bool bDummy );
484 
485     SwTableBox& FindStartOfRowSpan( const SwTable&, sal_uInt16 nMaxStep = USHRT_MAX );
FindStartOfRowSpan(const SwTable & rTable,sal_uInt16 nMaxStep=USHRT_MAX) const486     const SwTableBox& FindStartOfRowSpan( const SwTable& rTable,
487         sal_uInt16 nMaxStep = USHRT_MAX ) const
488         { return const_cast<SwTableBox*>(this)->FindStartOfRowSpan( rTable, nMaxStep ); }
489 
490     SwTableBox& FindEndOfRowSpan( const SwTable&, sal_uInt16 nMaxStep );
FindEndOfRowSpan(const SwTable & rTable,sal_uInt16 nMaxStep) const491     const SwTableBox& FindEndOfRowSpan( const SwTable& rTable,
492         sal_uInt16 nMaxStep ) const
493         { return const_cast<SwTableBox*>(this)->FindEndOfRowSpan( rTable, nMaxStep ); }
494     void RegisterToFormat( SwFormat& rFormat ) ;
495 };
496 
497 class SwCellFrame;
498 class SW_DLLPUBLIC SwTableCellInfo
499 {
500     struct Impl;
501     std::unique_ptr<Impl> m_pImpl;
502 
503     const SwCellFrame * getCellFrame() const;
504 
505     SwTableCellInfo(SwTableCellInfo const&) = delete;
506     SwTableCellInfo& operator=(SwTableCellInfo const&) = delete;
507 
508 public:
509     SwTableCellInfo(const SwTable * pTable);
510     ~SwTableCellInfo();
511 
512     bool getNext();
513     SwRect getRect() const;
514     const SwTableBox * getTableBox() const;
515 };
516 
517 #endif // INCLUDED_SW_INC_SWTABLE_HXX
518 
519 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
520