ITEM: Refactor ItemType
[LibreOffice.git] / sw / source / ui / vba / vbarows.cxx
blobe33f732e7638e6c1f6cbb7504b1be5dc5ad670fc
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
19 #include "vbarows.hxx"
20 #include "vbarow.hxx"
21 #include <com/sun/star/beans/XPropertySet.hpp>
22 #include <com/sun/star/text/HoriOrientation.hpp>
23 #include <com/sun/star/table/XCellRange.hpp>
24 #include <ooo/vba/word/WdRowAlignment.hpp>
25 #include <ooo/vba/word/WdConstants.hpp>
26 #include <ooo/vba/word/WdRulerStyle.hpp>
27 #include <basic/sberrors.hxx>
28 #include <utility>
29 #include "vbacolumns.hxx"
30 #include "vbatablehelper.hxx"
31 #include "wordvbahelper.hxx"
32 #include <unotxdoc.hxx>
34 using namespace ::ooo::vba;
35 using namespace ::ooo::vba::word;
36 using namespace ::com::sun::star;
38 namespace {
40 class RowsEnumWrapper : public EnumerationHelper_BASE
42 unotools::WeakReference< SwVbaRows > mxParent;
43 uno::Reference< uno::XComponentContext > mxContext;
44 uno::Reference< text::XTextTable > mxTextTable;
45 uno::Reference< container::XIndexAccess > mxIndexAccess;
46 sal_Int32 m_nIndex;
48 public:
49 RowsEnumWrapper( const rtl::Reference< SwVbaRows >& xParent, uno::Reference< uno::XComponentContext > xContext, uno::Reference< text::XTextTable > xTextTable ) : mxParent( xParent ), mxContext(std::move( xContext )), mxTextTable(std::move( xTextTable )), m_nIndex( 0 )
51 mxIndexAccess = mxTextTable->getRows();
53 virtual sal_Bool SAL_CALL hasMoreElements( ) override
55 return ( m_nIndex < mxIndexAccess->getCount() );
58 virtual uno::Any SAL_CALL nextElement( ) override
60 if( m_nIndex < mxIndexAccess->getCount() )
62 return uno::Any( uno::Reference< word::XRow > ( new SwVbaRow( mxParent.get(), mxContext, mxTextTable, m_nIndex++ ) ) );
64 throw container::NoSuchElementException();
70 SwVbaRows::SwVbaRows( const uno::Reference< XHelperInterface >& xParent, const uno::Reference< uno::XComponentContext > & xContext, uno::Reference< text::XTextTable > xTextTable, const uno::Reference< table::XTableRows >& xTableRows ) : SwVbaRows_BASE( xParent, xContext, uno::Reference< container::XIndexAccess >( xTableRows, uno::UNO_QUERY_THROW ) ), mxTextTable(std::move( xTextTable )), mxTableRows( xTableRows )
72 mnStartRowIndex = 0;
73 mnEndRowIndex = m_xIndexAccess->getCount() - 1;
76 SwVbaRows::SwVbaRows( const uno::Reference< XHelperInterface >& xParent, const uno::Reference< uno::XComponentContext > & xContext, uno::Reference< text::XTextTable > xTextTable, const uno::Reference< table::XTableRows >& xTableRows, sal_Int32 nStarIndex, sal_Int32 nEndIndex ) : SwVbaRows_BASE( xParent, xContext, uno::Reference< container::XIndexAccess >( xTableRows, uno::UNO_QUERY_THROW ) ), mxTextTable(std::move( xTextTable )), mxTableRows( xTableRows ), mnStartRowIndex( nStarIndex ), mnEndRowIndex( nEndIndex )
78 if( mnEndRowIndex < mnStartRowIndex )
79 throw uno::RuntimeException();
82 /**
83 * get the alignment of the rows: SO format com.sun.star.text.HoriOrientation
84 * is mapped to WdRowAlignment in Word
85 * @return the alignment
87 ::sal_Int32 SAL_CALL SwVbaRows::getAlignment()
89 sal_Int16 nAlignment = text::HoriOrientation::LEFT;
90 uno::Reference< beans::XPropertySet > xTableProps( mxTextTable, uno::UNO_QUERY_THROW );
91 xTableProps->getPropertyValue(u"HoriOrient"_ustr) >>= nAlignment;
92 sal_Int32 nRet = 0;
93 switch( nAlignment )
95 case text::HoriOrientation::CENTER:
97 nRet = word::WdRowAlignment::wdAlignRowCenter;
98 break;
100 case text::HoriOrientation::RIGHT:
102 nRet = word::WdRowAlignment::wdAlignRowRight;
103 break;
105 default:
107 nRet = word::WdRowAlignment::wdAlignRowLeft;
110 return nRet;
113 void SAL_CALL SwVbaRows::setAlignment( ::sal_Int32 _alignment )
115 sal_Int16 nAlignment = text::HoriOrientation::LEFT;
116 switch( _alignment )
118 case word::WdRowAlignment::wdAlignRowCenter:
120 nAlignment = text::HoriOrientation::CENTER;
121 break;
123 case word::WdRowAlignment::wdAlignRowRight:
125 nAlignment = text::HoriOrientation::RIGHT;
126 break;
128 default:
130 nAlignment = text::HoriOrientation::LEFT;
133 uno::Reference< beans::XPropertySet > xTableProps( mxTextTable, uno::UNO_QUERY_THROW );
134 xTableProps->setPropertyValue(u"HoriOrient"_ustr, uno::Any( nAlignment ) );
137 uno::Any SAL_CALL SwVbaRows::getAllowBreakAcrossPages()
139 bool bAllowBreak = false;
140 uno::Reference< container::XIndexAccess > xRowsAccess( mxTableRows, uno::UNO_QUERY_THROW );
141 for( sal_Int32 index = mnStartRowIndex; index <= mnEndRowIndex; ++index )
143 uno::Reference< beans::XPropertySet > xRowProps( xRowsAccess->getByIndex( index ), uno::UNO_QUERY_THROW );
144 bool bSplit = false;
145 xRowProps->getPropertyValue(u"IsSplitAllowed"_ustr) >>= bSplit;
146 if( index == 0 )
148 bAllowBreak = bSplit;
150 if( bSplit != bAllowBreak )
152 return uno::Any( sal_Int32(word::WdConstants::wdUndefined) );
155 return uno::Any( bAllowBreak );
158 void SAL_CALL SwVbaRows::setAllowBreakAcrossPages( const uno::Any& _allowbreakacrosspages )
160 bool bAllowBreak = false;
161 _allowbreakacrosspages >>= bAllowBreak;
162 uno::Reference< container::XIndexAccess > xRowsAccess( mxTableRows, uno::UNO_QUERY_THROW );
163 for( sal_Int32 index = mnStartRowIndex; index <= mnEndRowIndex; ++index )
165 uno::Reference< beans::XPropertySet > xRowProps( xRowsAccess->getByIndex( index ), uno::UNO_QUERY_THROW );
166 xRowProps->setPropertyValue(u"IsSplitAllowed"_ustr, uno::Any( bAllowBreak ) );
170 float SAL_CALL SwVbaRows::getSpaceBetweenColumns()
172 // just get the first spacing of the first cell
173 uno::Reference< table::XCellRange > xCellRange( mxTextTable, uno::UNO_QUERY_THROW );
174 uno::Reference< beans::XPropertySet > xCellProps( xCellRange->getCellByPosition( 0, mnStartRowIndex ), uno::UNO_QUERY_THROW );
175 sal_Int32 nLeftBorderDistance = 0;
176 sal_Int32 nRightBorderDistance = 0;
177 xCellProps->getPropertyValue(u"LeftBorderDistance"_ustr) >>= nLeftBorderDistance;
178 xCellProps->getPropertyValue(u"RightBorderDistance"_ustr) >>= nRightBorderDistance;
179 return static_cast< float >( Millimeter::getInPoints( nLeftBorderDistance + nRightBorderDistance ) );
182 void SAL_CALL SwVbaRows::setSpaceBetweenColumns( float _spacebetweencolumns )
184 sal_Int32 nSpace = Millimeter::getInHundredthsOfOneMillimeter( _spacebetweencolumns ) / 2;
185 uno::Reference< container::XIndexAccess > xColumnAccess( mxTextTable->getColumns(), uno::UNO_QUERY_THROW );
186 uno::Reference< table::XCellRange > xCellRange( mxTextTable, uno::UNO_QUERY_THROW );
187 SwVbaTableHelper aTableHelper( mxTextTable );
188 for( sal_Int32 row = mnStartRowIndex; row <= mnEndRowIndex; ++row )
190 sal_Int32 nColumns = aTableHelper.getTabColumnsCount( row );
191 for( sal_Int32 column = 0; column < nColumns; ++column )
193 uno::Reference< beans::XPropertySet > xCellProps( xCellRange->getCellByPosition( column, row ), uno::UNO_QUERY_THROW );
194 xCellProps->setPropertyValue(u"LeftBorderDistance"_ustr, uno::Any( nSpace ) );
195 xCellProps->setPropertyValue(u"RightBorderDistance"_ustr, uno::Any( nSpace ) );
200 void SAL_CALL SwVbaRows::Delete( )
202 mxTableRows->removeByIndex( mnStartRowIndex, getCount() );
205 void SAL_CALL SwVbaRows::SetLeftIndent( float LeftIndent, ::sal_Int32 RulerStyle )
207 uno::Reference< word::XColumns > xColumns( new SwVbaColumns( getParent(), mxContext, mxTextTable, mxTextTable->getColumns() ) );
208 sal_Int32 nIndent = static_cast<sal_Int32>(LeftIndent);
209 switch( RulerStyle )
211 case word::WdRulerStyle::wdAdjustFirstColumn:
213 setIndentWithAdjustFirstColumn( xColumns, nIndent );
214 break;
216 case word::WdRulerStyle::wdAdjustNone:
218 setIndentWithAdjustNone( nIndent );
219 break;
221 case word::WdRulerStyle::wdAdjustProportional:
223 setIndentWithAdjustProportional( xColumns, nIndent );
224 break;
226 case word::WdRulerStyle::wdAdjustSameWidth:
228 setIndentWithAdjustSameWidth( xColumns, nIndent );
229 break;
231 default:
233 DebugHelper::runtimeexception(ERRCODE_BASIC_BAD_ARGUMENT);
238 void SwVbaRows::setIndentWithAdjustNone( sal_Int32 indent )
240 uno::Reference< beans::XPropertySet > xTableProps( mxTextTable, uno::UNO_QUERY_THROW );
241 sal_Int32 nMargin = 0;
242 xTableProps->getPropertyValue(u"LeftMargin"_ustr) >>= nMargin;
243 nMargin += indent;
244 xTableProps->setPropertyValue(u"LeftMargin"_ustr, uno::Any( nMargin ) );
247 void SwVbaRows::setIndentWithAdjustFirstColumn( const uno::Reference< word::XColumns >& xColumns, sal_Int32 indent )
249 uno::Reference< XCollection > xCol( xColumns, uno::UNO_QUERY_THROW );
250 uno::Reference< word::XColumn > xColumn( xCol->Item( uno::Any( sal_Int32(1) ), uno::Any() ), uno::UNO_QUERY_THROW );
251 sal_Int32 nWidth = xColumn->getWidth();
252 nWidth -= indent;
253 xColumn->setWidth( nWidth );
254 setIndentWithAdjustNone( indent );
257 void SwVbaRows::setIndentWithAdjustProportional(
258 const uno::Reference< word::XColumns >& xColumns,
259 sal_Int32 indent
262 // calculate the new width and get the proportion between old and new
263 uno::Reference< beans::XPropertySet > xTableProps( mxTextTable, uno::UNO_QUERY_THROW );
264 sal_Int32 nWidth = 0;
265 xTableProps->getPropertyValue(u"Width"_ustr) >>= nWidth;
266 sal_Int32 nNewWidth = nWidth - indent;
267 if ((nNewWidth <= 0) || (nWidth <= 0))
269 throw uno::RuntimeException(
270 u"Pb with width, in SwVbaRows::setIndentWithAdjustProportional "
271 "(nNewWidth <= 0) || (nWidth <= 0)"_ustr
274 double propFactor = static_cast<double>(nNewWidth)/static_cast<double>(nWidth);
276 // get all columns, calculate and set the new width of the columns
277 uno::Reference< XCollection > xCol( xColumns, uno::UNO_QUERY_THROW );
278 sal_Int32 nColCount = xCol->getCount();
279 for( sal_Int32 i = 0; i < nColCount; i++ )
281 uno::Reference< word::XColumn > xColumn( xCol->Item( uno::Any( i ), uno::Any() ), uno::UNO_QUERY_THROW );
282 sal_Int32 nColWidth = xColumn->getWidth();
283 sal_Int32 nNewColWidth = static_cast<sal_Int32>( propFactor * nColWidth );
284 xColumn->setWidth( nNewColWidth );
287 // set the width and position of the table
288 setIndentWithAdjustNone( indent );
289 xTableProps->setPropertyValue(u"Width"_ustr, uno::Any( nNewWidth ) );
292 void SwVbaRows::setIndentWithAdjustSameWidth( const uno::Reference< word::XColumns >& xColumns, sal_Int32 indent )
294 // calculate the new width and get the width of all columns
295 uno::Reference< beans::XPropertySet > xTableProps( mxTextTable, uno::UNO_QUERY_THROW );
296 sal_Int32 nWidth = 0;
297 xTableProps->getPropertyValue(u"Width"_ustr) >>= nWidth;
298 sal_Int32 nNewWidth = nWidth - indent;
300 // get all columns, calculate and set the new width of the columns
301 uno::Reference< XCollection > xCol( xColumns, uno::UNO_QUERY_THROW );
302 sal_Int32 nColCount = xCol->getCount();
303 sal_Int32 nNewColWidth = static_cast<sal_Int32>( double( nNewWidth )/nColCount );
304 for( sal_Int32 i = 0; i < nColCount; i++ )
306 uno::Reference< word::XColumn > xColumn( xCol->Item( uno::Any( i ), uno::Any() ), uno::UNO_QUERY_THROW );
307 xColumn->setWidth( nNewColWidth );
310 // set the width and position of the table
311 setIndentWithAdjustNone( indent );
312 xTableProps->setPropertyValue(u"Width"_ustr, uno::Any( nNewWidth ) );
315 void SAL_CALL SwVbaRows::Select( )
317 SwVbaRow::SelectRow( getCurrentWordDoc(mxContext), mxTextTable, mnStartRowIndex, mnEndRowIndex );
320 ::sal_Int32 SAL_CALL SwVbaRows::getCount()
322 return ( mnEndRowIndex - mnStartRowIndex + 1 );
325 uno::Any SAL_CALL SwVbaRows::Item( const uno::Any& Index1, const uno::Any& /*not processed in this base class*/ )
327 sal_Int32 nIndex = 0;
328 if( Index1 >>= nIndex )
330 if( nIndex <= 0 || nIndex > getCount() )
332 throw lang::IndexOutOfBoundsException(u"Index out of bounds"_ustr );
334 return uno::Any( uno::Reference< word::XRow >( new SwVbaRow( this, mxContext, mxTextTable, nIndex - 1 ) ) );
336 throw uno::RuntimeException(u"Index out of bounds"_ustr );
339 // XEnumerationAccess
340 uno::Type
341 SwVbaRows::getElementType()
343 return cppu::UnoType<word::XRow>::get();
345 uno::Reference< container::XEnumeration >
346 SwVbaRows::createEnumeration()
348 return new RowsEnumWrapper( this, mxContext, mxTextTable );
351 uno::Any
352 SwVbaRows::createCollectionObject( const uno::Any& aSource )
354 return aSource;
357 OUString
358 SwVbaRows::getServiceImplName()
360 return u"SwVbaRows"_ustr;
363 uno::Sequence<OUString>
364 SwVbaRows::getServiceNames()
366 static uno::Sequence< OUString > const sNames
368 u"ooo.vba.word.Rows"_ustr
370 return sNames;
373 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */