1*b1cdbd2cSJim Jagielski /**************************************************************
2*b1cdbd2cSJim Jagielski  *
3*b1cdbd2cSJim Jagielski  * Licensed to the Apache Software Foundation (ASF) under one
4*b1cdbd2cSJim Jagielski  * or more contributor license agreements.  See the NOTICE file
5*b1cdbd2cSJim Jagielski  * distributed with this work for additional information
6*b1cdbd2cSJim Jagielski  * regarding copyright ownership.  The ASF licenses this file
7*b1cdbd2cSJim Jagielski  * to you under the Apache License, Version 2.0 (the
8*b1cdbd2cSJim Jagielski  * "License"); you may not use this file except in compliance
9*b1cdbd2cSJim Jagielski  * with the License.  You may obtain a copy of the License at
10*b1cdbd2cSJim Jagielski  *
11*b1cdbd2cSJim Jagielski  *   http://www.apache.org/licenses/LICENSE-2.0
12*b1cdbd2cSJim Jagielski  *
13*b1cdbd2cSJim Jagielski  * Unless required by applicable law or agreed to in writing,
14*b1cdbd2cSJim Jagielski  * software distributed under the License is distributed on an
15*b1cdbd2cSJim Jagielski  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*b1cdbd2cSJim Jagielski  * KIND, either express or implied.  See the License for the
17*b1cdbd2cSJim Jagielski  * specific language governing permissions and limitations
18*b1cdbd2cSJim Jagielski  * under the License.
19*b1cdbd2cSJim Jagielski  *
20*b1cdbd2cSJim Jagielski  *************************************************************/
21*b1cdbd2cSJim Jagielski 
22*b1cdbd2cSJim Jagielski 
23*b1cdbd2cSJim Jagielski 
24*b1cdbd2cSJim Jagielski #ifndef _SVX_TABLE_TABLELAYOUTER_HXX_
25*b1cdbd2cSJim Jagielski #define _SVX_TABLE_TABLELAYOUTER_HXX_
26*b1cdbd2cSJim Jagielski 
27*b1cdbd2cSJim Jagielski #include <com/sun/star/container/XIndexAccess.hpp>
28*b1cdbd2cSJim Jagielski #include <com/sun/star/text/WritingMode.hpp>
29*b1cdbd2cSJim Jagielski #include <com/sun/star/table/XTable.hpp>
30*b1cdbd2cSJim Jagielski #include <basegfx/range/b2irectangle.hxx>
31*b1cdbd2cSJim Jagielski #include <basegfx/tuple/b2ituple.hxx>
32*b1cdbd2cSJim Jagielski #include <tools/gen.hxx>
33*b1cdbd2cSJim Jagielski #include <boost/shared_ptr.hpp>
34*b1cdbd2cSJim Jagielski #include <vector>
35*b1cdbd2cSJim Jagielski #include <map>
36*b1cdbd2cSJim Jagielski 
37*b1cdbd2cSJim Jagielski #include "svx/svdotable.hxx"
38*b1cdbd2cSJim Jagielski 
39*b1cdbd2cSJim Jagielski // -----------------------------------------------------------------------------
40*b1cdbd2cSJim Jagielski 
41*b1cdbd2cSJim Jagielski class SvxBorderLine;
42*b1cdbd2cSJim Jagielski 
43*b1cdbd2cSJim Jagielski namespace sdr { namespace table {
44*b1cdbd2cSJim Jagielski 
45*b1cdbd2cSJim Jagielski /** returns true if the cell(nMergedCol,nMergedRow) is merged with other cells.
46*b1cdbd2cSJim Jagielski 	the returned cell( rOriginCol, rOriginRow ) is the origin( top left cell ) of the merge.
47*b1cdbd2cSJim Jagielski */
48*b1cdbd2cSJim Jagielski bool findMergeOrigin( const TableModelRef& xTable, sal_Int32 nMergedCol, sal_Int32 nMergedRow, sal_Int32& rOriginCol, sal_Int32& rOriginRow );
49*b1cdbd2cSJim Jagielski 
50*b1cdbd2cSJim Jagielski typedef std::vector< SvxBorderLine* > BorderLineVector;
51*b1cdbd2cSJim Jagielski typedef std::vector< BorderLineVector > BorderLineMap;
52*b1cdbd2cSJim Jagielski 
53*b1cdbd2cSJim Jagielski // -----------------------------------------------------------------------------
54*b1cdbd2cSJim Jagielski // TableModel
55*b1cdbd2cSJim Jagielski // -----------------------------------------------------------------------------
56*b1cdbd2cSJim Jagielski 
57*b1cdbd2cSJim Jagielski class TableLayouter
58*b1cdbd2cSJim Jagielski {
59*b1cdbd2cSJim Jagielski public:
60*b1cdbd2cSJim Jagielski 	TableLayouter( const TableModelRef& xTableModel );
61*b1cdbd2cSJim Jagielski 	virtual ~TableLayouter();
62*b1cdbd2cSJim Jagielski 
63*b1cdbd2cSJim Jagielski 	/** this checks if new rows are inserted or old rows where removed.
64*b1cdbd2cSJim Jagielski 		This can be used to grow or shrink the table shape in this case.
65*b1cdbd2cSJim Jagielski 		@returns
66*b1cdbd2cSJim Jagielski 			the height difference
67*b1cdbd2cSJim Jagielski 	sal_Int32 detectInsertedOrRemovedRows();
68*b1cdbd2cSJim Jagielski 	*/
69*b1cdbd2cSJim Jagielski 
70*b1cdbd2cSJim Jagielski 	/** try to fit the table into the given rectangle.
71*b1cdbd2cSJim Jagielski 		If the rectangle is to small, it will be grown to fit the table.
72*b1cdbd2cSJim Jagielski 
73*b1cdbd2cSJim Jagielski 		if bFitWidth or bFitHeight is set, the layouter tries to scale
74*b1cdbd2cSJim Jagielski 		the rows and/or columns to the given area. The result my be bigger
75*b1cdbd2cSJim Jagielski 		to fullfill constrains.
76*b1cdbd2cSJim Jagielski 
77*b1cdbd2cSJim Jagielski 		if bFitWidth or bFitHeight is set, the model is changed.
78*b1cdbd2cSJim Jagielski 	*/
79*b1cdbd2cSJim Jagielski 	void LayoutTable( ::Rectangle& rRectangle, bool bFitWidth, bool bFitHeight );
80*b1cdbd2cSJim Jagielski 
81*b1cdbd2cSJim Jagielski 	/** after a call to LayoutTable, this method can be used to set the new
82*b1cdbd2cSJim Jagielski 		column and row sizes back to the model. */
83*b1cdbd2cSJim Jagielski //	void SetLayoutToModel();
84*b1cdbd2cSJim Jagielski 
85*b1cdbd2cSJim Jagielski 	void UpdateBorderLayout();
86*b1cdbd2cSJim Jagielski 
87*b1cdbd2cSJim Jagielski 	basegfx::B2ITuple getCellSize( const CellPos& rPos ) const;
88*b1cdbd2cSJim Jagielski 	bool getCellArea( const CellRef& xCell, basegfx::B2IRectangle& rArea ) const;
89*b1cdbd2cSJim Jagielski 	bool getCellArea( const CellPos& rPos, basegfx::B2IRectangle& rArea ) const;
90*b1cdbd2cSJim Jagielski 
getRowCount() const91*b1cdbd2cSJim Jagielski 	::sal_Int32 getRowCount() const { return static_cast< ::sal_Int32 >( maRows.size() ); }
getColumnCount() const92*b1cdbd2cSJim Jagielski 	::sal_Int32 getColumnCount() const { return static_cast< ::sal_Int32 >( maColumns.size() ); }
93*b1cdbd2cSJim Jagielski 
94*b1cdbd2cSJim Jagielski 	sal_Int32 getRowHeight( sal_Int32 nRow );
95*b1cdbd2cSJim Jagielski 
96*b1cdbd2cSJim Jagielski 	// sets the layout height of the given row hard, LayoutTable must be called directly after calling this method! */
97*b1cdbd2cSJim Jagielski 	void setRowHeight( sal_Int32 nRow, sal_Int32 nHeight );
98*b1cdbd2cSJim Jagielski 
99*b1cdbd2cSJim Jagielski 	sal_Int32 getColumnWidth( sal_Int32 nColumn );
100*b1cdbd2cSJim Jagielski 
101*b1cdbd2cSJim Jagielski 	// sets the layout width of the given column hard, LayoutTable must be called directly after calling this method! */
102*b1cdbd2cSJim Jagielski 	void setColumnWidth( sal_Int32 nColumn, sal_Int32 nWidth );
103*b1cdbd2cSJim Jagielski 
104*b1cdbd2cSJim Jagielski 	sal_Int32 getMinimumColumnWidth( sal_Int32 nColumn );
105*b1cdbd2cSJim Jagielski 
106*b1cdbd2cSJim Jagielski 	sal_Int32 getColumnStart( sal_Int32 nColumn ) const;
107*b1cdbd2cSJim Jagielski 	sal_Int32 getRowStart( sal_Int32 nRow ) const;
108*b1cdbd2cSJim Jagielski 
109*b1cdbd2cSJim Jagielski 	/** checks if the given edge is visible.
110*b1cdbd2cSJim Jagielski 		Edges between merged cells are not visible.
111*b1cdbd2cSJim Jagielski 	*/
112*b1cdbd2cSJim Jagielski 	bool isEdgeVisible( sal_Int32 nEdgeX, sal_Int32 nEdgeY, bool bHorizontal ) const;
113*b1cdbd2cSJim Jagielski 
114*b1cdbd2cSJim Jagielski 	/** returns the requested borderline in rpBorderLine or a null pointer if there is no border at this edge */
115*b1cdbd2cSJim Jagielski 	SvxBorderLine* getBorderLine( sal_Int32 nEdgeX, sal_Int32 nEdgeY, bool bHorizontal )const;
116*b1cdbd2cSJim Jagielski 
117*b1cdbd2cSJim Jagielski 	void updateCells( ::Rectangle& rRectangle );
118*b1cdbd2cSJim Jagielski 
119*b1cdbd2cSJim Jagielski 	sal_Int32 getHorizontalEdge( int nEdgeY, sal_Int32* pnMin = 0, sal_Int32* pnMax = 0 );
120*b1cdbd2cSJim Jagielski 	sal_Int32 getVerticalEdge( int nEdgeX , sal_Int32* pnMin = 0, sal_Int32* pnMax = 0);
121*b1cdbd2cSJim Jagielski 
122*b1cdbd2cSJim Jagielski 	void DistributeColumns( ::Rectangle& rArea, sal_Int32 nFirstCol, sal_Int32 nLastCol );
123*b1cdbd2cSJim Jagielski 	void DistributeRows( ::Rectangle& rArea, sal_Int32 nFirstRow, sal_Int32 nLastRow );
124*b1cdbd2cSJim Jagielski 
GetWritingMode() const125*b1cdbd2cSJim Jagielski 	com::sun::star::text::WritingMode GetWritingMode() const { return meWritingMode; }
126*b1cdbd2cSJim Jagielski 	void SetWritingMode( com::sun::star::text::WritingMode eWritingMode );
127*b1cdbd2cSJim Jagielski 
128*b1cdbd2cSJim Jagielski private:
129*b1cdbd2cSJim Jagielski 	CellRef getCell( const CellPos& rPos ) const;
130*b1cdbd2cSJim Jagielski 
131*b1cdbd2cSJim Jagielski 	void LayoutTableWidth( ::Rectangle& rArea, bool bFit );
132*b1cdbd2cSJim Jagielski 	void LayoutTableHeight( ::Rectangle& rArea, bool bFit );
133*b1cdbd2cSJim Jagielski 
isValidColumn(sal_Int32 nColumn) const134*b1cdbd2cSJim Jagielski 	inline bool isValidColumn( sal_Int32 nColumn ) const { return (nColumn >= 0) && (nColumn < static_cast<sal_Int32>( maColumns.size())); }
isValidRow(sal_Int32 nRow) const135*b1cdbd2cSJim Jagielski 	inline bool isValidRow( sal_Int32 nRow ) const { return (nRow >= 0) && (nRow < static_cast<sal_Int32>( maRows.size())); }
isValid(const CellPos & rPos) const136*b1cdbd2cSJim Jagielski 	inline bool isValid( const CellPos& rPos ) const { return isValidColumn( rPos.mnCol ) && isValidRow( rPos.mnRow ); }
137*b1cdbd2cSJim Jagielski 
138*b1cdbd2cSJim Jagielski 	void ClearBorderLayout();
139*b1cdbd2cSJim Jagielski 	void ClearBorderLayout(BorderLineMap& rMap);
140*b1cdbd2cSJim Jagielski 	void ResizeBorderLayout();
141*b1cdbd2cSJim Jagielski 	void ResizeBorderLayout( BorderLineMap& rMap );
142*b1cdbd2cSJim Jagielski 
143*b1cdbd2cSJim Jagielski 	void SetBorder( sal_Int32 nCol, sal_Int32 nRow, bool bHorizontal, const SvxBorderLine* pLine );
144*b1cdbd2cSJim Jagielski 
145*b1cdbd2cSJim Jagielski 	static bool HasPriority( const SvxBorderLine* pThis, const SvxBorderLine* pOther );
146*b1cdbd2cSJim Jagielski 
147*b1cdbd2cSJim Jagielski 	struct Layout
148*b1cdbd2cSJim Jagielski 	{
149*b1cdbd2cSJim Jagielski 		sal_Int32 mnPos;
150*b1cdbd2cSJim Jagielski 		sal_Int32 mnSize;
151*b1cdbd2cSJim Jagielski 		sal_Int32 mnMinSize;
152*b1cdbd2cSJim Jagielski 
Layoutsdr::table::TableLayouter::Layout153*b1cdbd2cSJim Jagielski 		Layout() : mnPos( 0 ), mnSize( 0 ), mnMinSize( 0 ) {}
clearsdr::table::TableLayouter::Layout154*b1cdbd2cSJim Jagielski 		void clear() { mnPos = 0; mnSize = 0; mnMinSize = 0; }
155*b1cdbd2cSJim Jagielski 	};
156*b1cdbd2cSJim Jagielski 	typedef std::vector< Layout > LayoutVector;
157*b1cdbd2cSJim Jagielski 
158*b1cdbd2cSJim Jagielski 	sal_Int32 distribute( LayoutVector& rLayouts, sal_Int32 nDistribute );
159*b1cdbd2cSJim Jagielski 
160*b1cdbd2cSJim Jagielski 	TableModelRef mxTable;
161*b1cdbd2cSJim Jagielski 	LayoutVector maRows;
162*b1cdbd2cSJim Jagielski 	LayoutVector maColumns;
163*b1cdbd2cSJim Jagielski 
164*b1cdbd2cSJim Jagielski 	BorderLineMap maHorizontalBorders;
165*b1cdbd2cSJim Jagielski 	BorderLineMap maVerticalBorders;
166*b1cdbd2cSJim Jagielski 
167*b1cdbd2cSJim Jagielski 	com::sun::star::text::WritingMode	meWritingMode;
168*b1cdbd2cSJim Jagielski 
169*b1cdbd2cSJim Jagielski 	const rtl::OUString msSize;
170*b1cdbd2cSJim Jagielski };
171*b1cdbd2cSJim Jagielski 
172*b1cdbd2cSJim Jagielski } }
173*b1cdbd2cSJim Jagielski 
174*b1cdbd2cSJim Jagielski #endif
175