Branch data Line data Source code
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 : : #ifndef OOX_HELPER_CONTAINERHELPER_HXX
21 : : #define OOX_HELPER_CONTAINERHELPER_HXX
22 : :
23 : : #include <map>
24 : : #include <vector>
25 : : #include <com/sun/star/uno/Reference.h>
26 : : #include <com/sun/star/uno/Sequence.h>
27 : : #include "oox/dllapi.h"
28 : :
29 : : namespace rtl { class OUString; }
30 : :
31 : : namespace com { namespace sun { namespace star {
32 : : namespace container { class XIndexAccess; }
33 : : namespace container { class XIndexContainer; }
34 : : namespace container { class XNameAccess; }
35 : : namespace container { class XNameContainer; }
36 : : namespace uno { class XComponentContext; }
37 : : } } }
38 : :
39 : : namespace oox {
40 : :
41 : : // ============================================================================
42 : :
43 : : /** A range of signed 32-bit integer values. */
44 : : struct ValueRange
45 : : {
46 : : sal_Int32 mnFirst;
47 : : sal_Int32 mnLast;
48 : :
49 : 258 : inline explicit ValueRange( sal_Int32 nValue = 0 ) : mnFirst( nValue ), mnLast( nValue ) {}
50 : 381 : inline explicit ValueRange( sal_Int32 nFirst, sal_Int32 nLast ) : mnFirst( nFirst ), mnLast( nLast ) {}
51 : :
52 : : inline bool operator==( const ValueRange& rRange ) const { return (mnFirst == rRange.mnFirst) && (mnLast == rRange.mnLast); }
53 : : inline bool operator!=( const ValueRange& rRange ) const { return !(*this == rRange); }
54 : : inline bool contains( sal_Int32 nValue ) const { return (mnFirst <= nValue) && (nValue <= mnLast); }
55 [ # # ][ # # ]: 0 : inline bool contains( const ValueRange& rRange ) const { return (mnFirst <= rRange.mnFirst) && (rRange.mnLast <= mnLast); }
56 [ # # ][ # # ]: 0 : inline bool intersects( const ValueRange& rRange ) const { return (mnFirst <= rRange.mnLast) && (rRange.mnFirst <= mnLast); }
57 : : };
58 : :
59 : : // ----------------------------------------------------------------------------
60 : :
61 : : typedef ::std::vector< ValueRange > ValueRangeVector;
62 : :
63 : : // ----------------------------------------------------------------------------
64 : :
65 : : /** An ordered list of value ranges. The insertion operation will merge
66 : : consecutive value ranges.
67 : : */
68 : 1215 : class OOX_DLLPUBLIC ValueRangeSet
69 : : {
70 : : public:
71 : 417 : inline explicit ValueRangeSet() {}
72 : :
73 : : /** Inserts the passed value into the range list. */
74 : : inline void insert( sal_Int32 nValue ) { insert( ValueRange( nValue ) ); }
75 : : /** Inserts the passed value range into the range list. */
76 : : void insert( const ValueRange& rRange );
77 : :
78 : : /** Returns the ordered list of all value ranges. */
79 : 243 : inline const ValueRangeVector& getRanges() const { return maRanges; }
80 : :
81 : : private:
82 : : ValueRangeVector maRanges;
83 : : };
84 : :
85 : : // ============================================================================
86 : :
87 : : /** Template for a 2-dimensional array of objects.
88 : :
89 : : This class template provides a similar interface to the ::std::vector
90 : : template.
91 : : */
92 : : template< typename Type >
93 : 0 : class Matrix
94 : : {
95 : : public:
96 : : typedef ::std::vector< Type > container_type;
97 : : typedef typename container_type::value_type value_type;
98 : : typedef typename container_type::pointer pointer;
99 : : typedef typename container_type::reference reference;
100 : : typedef typename container_type::const_reference const_reference;
101 : : typedef typename container_type::size_type size_type;
102 : : typedef typename container_type::iterator iterator;
103 : : typedef typename container_type::const_iterator const_iterator;
104 : :
105 : 0 : inline explicit Matrix() : mnWidth( 0 ) {}
106 [ # # ]: 0 : inline explicit Matrix( size_type nWidth, size_type nHeight ) { this->resize( nWidth, nHeight ); }
107 [ # # ]: 0 : inline explicit Matrix( size_type nWidth, size_type nHeight, const_reference rData ) { this->resize( nWidth, nHeight, rData ); }
108 : :
109 : : inline size_type capacity() const { return maData.capacity(); }
110 : 0 : inline bool empty() const { return maData.empty(); }
111 : 0 : inline size_type size() const { return maData.size(); }
112 : 0 : inline size_type width() const { return mnWidth; }
113 [ # # ]: 0 : inline size_type height() const { return this->empty() ? 0 : (this->size() / this->width()); }
114 : : inline bool has( size_type nX, size_type nY ) const { return (nX < this->width()) && (nY < this->height()); }
115 : :
116 : : inline void reserve( size_type nWidth, size_type nHeight ) { maData.reserve( nWidth * nHeight ); }
117 : 0 : inline void clear() { this->resize( 0, 0 ); }
118 : 0 : inline void resize( size_type nWidth, size_type nHeight ) { mnWidth = nWidth; maData.resize( nWidth * nHeight ); }
119 : 0 : inline void resize( size_type nWidth, size_type nHeight, const_reference rData ) { mnWidth = nWidth; maData.resize( nWidth * nHeight, rData ); }
120 : :
121 : : inline iterator at( size_type nX, size_type nY ) { return maData.begin() + mnWidth * nY + nX; }
122 [ # # ][ # # ]: 0 : inline const_iterator at( size_type nX, size_type nY ) const { return maData.begin() + mnWidth * nY + nX; }
123 : :
124 : : inline reference operator()( size_type nX, size_type nY ) { return *this->at( nX, nY ); }
125 : 0 : inline const_reference operator()( size_type nX, size_type nY ) const { return *this->at( nX, nY ); }
126 : :
127 : 0 : inline iterator begin() { return maData.begin(); }
128 : : inline const_iterator begin() const { return maData.begin(); }
129 : 0 : inline iterator end() { return maData.end(); }
130 : : inline const_iterator end() const { return maData.end(); }
131 : :
132 : : inline reference front() { return maData.front(); }
133 : : inline const_reference front() const { return maData.front(); }
134 : : inline reference back() { return maData.back(); }
135 : : inline const_reference back() const { return maData.back(); }
136 : :
137 : : inline iterator row_begin( size_type nY ) { return this->at( 0, nY ); }
138 : 0 : inline const_iterator row_begin( size_type nY ) const { return this->at( 0, nY ); }
139 : : inline iterator row_end( size_type nY ) { return this->at( mnWidth, nY ); }
140 : 0 : inline const_iterator row_end( size_type nY ) const { return this->at( mnWidth, nY ); }
141 : :
142 : : inline reference row_front( size_type nY ) { return (*this)( 0, nY ); }
143 : 0 : inline const_reference row_front( size_type nY ) const { return (*this)( 0, nY ); }
144 : : inline reference row_back( size_type nY ) { return (*this)( mnWidth - 1, nY ); }
145 : : inline const_reference row_back( size_type nY ) const { return (*this)( mnWidth - 1, nY ); }
146 : :
147 : : inline void swap( Matrix& rMatrix ) { maData.swap( rMatrix.maData ); }
148 : :
149 : : private:
150 : : container_type maData;
151 : : size_type mnWidth;
152 : : };
153 : :
154 : : // ============================================================================
155 : :
156 : : /** Static helper functions for improved API container handling. */
157 : : class OOX_DLLPUBLIC ContainerHelper
158 : : {
159 : : public:
160 : : // com.sun.star.container.XIndexContainer ---------------------------------
161 : :
162 : : /** Creates a new index container object from scratch. */
163 : : static ::com::sun::star::uno::Reference< ::com::sun::star::container::XIndexContainer >
164 : : createIndexContainer( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XComponentContext >& rxContext );
165 : :
166 : : // com.sun.star.container.XNameContainer ----------------------------------
167 : :
168 : : /** Creates a new name container object from scratch. */
169 : : static ::com::sun::star::uno::Reference< ::com::sun::star::container::XNameContainer >
170 : : createNameContainer( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XComponentContext >& rxContext );
171 : :
172 : : /** Returns a name that is not used in the passed name container.
173 : :
174 : : @param rxNameAccess com.sun.star.container.XNameAccess interface of
175 : : the name container.
176 : :
177 : : @param rSuggestedName Suggested name for the object.
178 : :
179 : : @return An unused name. Will be equal to the suggested name, if not
180 : : contained, otherwise a numerical index will be appended.
181 : : */
182 : : static ::rtl::OUString getUnusedName(
183 : : const ::com::sun::star::uno::Reference< ::com::sun::star::container::XNameAccess >& rxNameAccess,
184 : : const ::rtl::OUString& rSuggestedName,
185 : : sal_Unicode cSeparator,
186 : : sal_Int32 nFirstIndexToAppend = 1 );
187 : :
188 : : /** Inserts an object into a name container.
189 : :
190 : : @param rxNameContainer com.sun.star.container.XNameContainer interface
191 : : of the name container.
192 : :
193 : : @param rName Exact name for the object.
194 : :
195 : : @param rObject The object to be inserted.
196 : :
197 : : @return True = object successfully inserted.
198 : : */
199 : : static bool insertByName(
200 : : const ::com::sun::star::uno::Reference< ::com::sun::star::container::XNameContainer >& rxNameContainer,
201 : : const ::rtl::OUString& rName,
202 : : const ::com::sun::star::uno::Any& rObject,
203 : : bool bReplaceOldExisting = true );
204 : :
205 : : /** Inserts an object into a name container.
206 : :
207 : : The function will use an unused name to insert the object, based on the
208 : : suggested object name. It is possible to specify whether the existing
209 : : object or the new inserted object will be renamed, if the container
210 : : already has an object with the name suggested for the new object.
211 : :
212 : : @param rxNameContainer com.sun.star.container.XNameContainer interface
213 : : of the name container.
214 : :
215 : : @param rSuggestedName Suggested name for the object.
216 : :
217 : : @param rObject The object to be inserted.
218 : :
219 : : @param bRenameOldExisting Specifies behaviour if an object with the
220 : : suggested name already exists. If false (default), the new object
221 : : will be inserted with a name not yet extant in the container (this
222 : : is done by appending a numerical index to the suggested name). If
223 : : true, the existing object will be removed and inserted with an
224 : : unused name, and the new object will be inserted with the suggested
225 : : name.
226 : :
227 : : @return The final name the object is inserted with. Will always be
228 : : equal to the suggested name, if parameter bRenameOldExisting is
229 : : true.
230 : : */
231 : : static ::rtl::OUString insertByUnusedName(
232 : : const ::com::sun::star::uno::Reference< ::com::sun::star::container::XNameContainer >& rxNameContainer,
233 : : const ::rtl::OUString& rSuggestedName,
234 : : sal_Unicode cSeparator,
235 : : const ::com::sun::star::uno::Any& rObject,
236 : : bool bRenameOldExisting = false );
237 : :
238 : : // std::vector and std::map element access --------------------------------
239 : :
240 : : /** Returns the pointer to an existing element of the passed vector, or a
241 : : null pointer, if the passed index is out of bounds. */
242 : : template< typename VectorType >
243 : : static const typename VectorType::value_type*
244 : : getVectorElement( const VectorType& rVector, sal_Int32 nIndex );
245 : :
246 : : /** Returns the pointer to an existing element of the passed vector, or a
247 : : null pointer, if the passed index is out of bounds. */
248 : : template< typename VectorType >
249 : : static typename VectorType::value_type*
250 : : getVectorElementAccess( VectorType& rVector, sal_Int32 nIndex );
251 : :
252 : : /** Returns the reference to an existing element of the passed vector, or
253 : : the passed default value, if the passed index is out of bounds. */
254 : : template< typename VectorType >
255 : : static const typename VectorType::value_type&
256 : : getVectorElement( const VectorType& rVector, sal_Int32 nIndex, const typename VectorType::value_type& rDefault );
257 : :
258 : : /** Returns the reference to an existing element of the passed vector, or
259 : : the passed default value, if the passed index is out of bounds. */
260 : : template< typename VectorType >
261 : : static typename VectorType::value_type&
262 : : getVectorElementAccess( VectorType& rVector, sal_Int32 nIndex, typename VectorType::value_type& rDefault );
263 : :
264 : : /** Returns the pointer to an existing element of the passed map, or a null
265 : : pointer, if an element with the passed key does not exist. */
266 : : template< typename MapType >
267 : : static const typename MapType::mapped_type*
268 : : getMapElement( const MapType& rMap, const typename MapType::key_type& rKey );
269 : :
270 : : /** Returns the pointer to an existing element of the passed map, or a null
271 : : pointer, if an element with the passed key does not exist. */
272 : : template< typename MapType >
273 : : static typename MapType::mapped_type*
274 : : getMapElementAccess( MapType& rMap, const typename MapType::key_type& rKey );
275 : :
276 : : /** Returns the reference to an existing element of the passed map, or the
277 : : passed default value, if an element with the passed key does not exist. */
278 : : template< typename MapType >
279 : : static const typename MapType::mapped_type&
280 : : getMapElement( const MapType& rMap, const typename MapType::key_type& rKey, const typename MapType::mapped_type& rDefault );
281 : :
282 : : /** Returns the reference to an existing element of the passed map, or the
283 : : passed default value, if an element with the passed key does not exist. */
284 : : template< typename MapType >
285 : : static typename MapType::mapped_type&
286 : : getMapElementAccess( MapType& rMap, const typename MapType::key_type& rKey, typename MapType::mapped_type& rDefault );
287 : :
288 : : // vector/map/matrix to UNO sequence --------------------------------------
289 : :
290 : : /** Creates a UNO sequence from a std::vector with copies of all elements.
291 : :
292 : : @param rVector The vector to be converted to a sequence.
293 : :
294 : : @return A com.sun.star.uno.Sequence object with copies of all objects
295 : : contained in the passed vector.
296 : : */
297 : : template< typename VectorType >
298 : : static ::com::sun::star::uno::Sequence< typename VectorType::value_type >
299 : : vectorToSequence( const VectorType& rVector );
300 : :
301 : : /** Creates a UNO sequence from a std::map with copies of all elements.
302 : :
303 : : @param rMap The map to be converted to a sequence.
304 : :
305 : : @return A com.sun.star.uno.Sequence object with copies of all objects
306 : : contained in the passed map.
307 : : */
308 : : template< typename MapType >
309 : : static ::com::sun::star::uno::Sequence< typename MapType::mapped_type >
310 : : mapToSequence( const MapType& rMap );
311 : :
312 : : /** Creates a UNO sequence of sequences from a matrix with copies of all elements.
313 : :
314 : : @param rMatrix The matrix to be converted to a sequence of sequences.
315 : :
316 : : @return A com.sun.star.uno.Sequence object containing
317 : : com.sun.star.uno.Sequence objects with copies of all objects
318 : : contained in the passed matrix.
319 : : */
320 : : template< typename MatrixType >
321 : : static ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Sequence< typename MatrixType::value_type > >
322 : : matrixToSequenceSequence( const MatrixType& rMatrix );
323 : : };
324 : :
325 : : // ----------------------------------------------------------------------------
326 : :
327 : : template< typename VectorType >
328 : 144 : /*static*/ const typename VectorType::value_type* ContainerHelper::getVectorElement( const VectorType& rVector, sal_Int32 nIndex )
329 : : {
330 [ + - ][ - + ]: 144 : return ((0 <= nIndex) && (static_cast< size_t >( nIndex ) < rVector.size())) ? &rVector[ static_cast< size_t >( nIndex ) ] : 0;
[ # # ][ # # ]
331 : : }
332 : :
333 : : template< typename VectorType >
334 : 0 : /*static*/ typename VectorType::value_type* ContainerHelper::getVectorElementAccess( VectorType& rVector, sal_Int32 nIndex )
335 : : {
336 [ # # ][ # # ]: 0 : return ((0 <= nIndex) && (static_cast< size_t >( nIndex ) < rVector.size())) ? &rVector[ static_cast< size_t >( nIndex ) ] : 0;
[ # # ][ # # ]
337 : : }
338 : :
339 : : template< typename VectorType >
340 : 6 : /*static*/ const typename VectorType::value_type& ContainerHelper::getVectorElement( const VectorType& rVector, sal_Int32 nIndex, const typename VectorType::value_type& rDefault )
341 : : {
342 [ + - ][ + - ]: 6 : return ((0 <= nIndex) && (static_cast< size_t >( nIndex ) < rVector.size())) ? rVector[ static_cast< size_t >( nIndex ) ] : rDefault;
343 : : }
344 : :
345 : : template< typename VectorType >
346 : : /*static*/ typename VectorType::value_type& ContainerHelper::getVectorElementAccess( VectorType& rVector, sal_Int32 nIndex, typename VectorType::value_type& rDefault )
347 : : {
348 : : return ((0 <= nIndex) && (static_cast< size_t >( nIndex ) < rVector.size())) ? rVector[ static_cast< size_t >( nIndex ) ] : rDefault;
349 : : }
350 : :
351 : : template< typename MapType >
352 : 4593 : /*static*/ const typename MapType::mapped_type* ContainerHelper::getMapElement( const MapType& rMap, const typename MapType::key_type& rKey )
353 : : {
354 [ + - ][ + - ]: 4593 : typename MapType::const_iterator aIt = rMap.find( rKey );
355 [ + + ][ + - ]: 4593 : return (aIt == rMap.end()) ? 0 : &aIt->second;
356 : : }
357 : :
358 : : template< typename MapType >
359 : : /*static*/ typename MapType::mapped_type* ContainerHelper::getMapElementAccess( MapType& rMap, const typename MapType::key_type& rKey )
360 : : {
361 : : typename MapType::iterator aIt = rMap.find( rKey );
362 : : return (aIt == rMap.end()) ? 0 : &aIt->second;
363 : : }
364 : :
365 : : template< typename MapType >
366 : 262 : /*static*/ const typename MapType::mapped_type& ContainerHelper::getMapElement( const MapType& rMap, const typename MapType::key_type& rKey, const typename MapType::mapped_type& rDefault )
367 : : {
368 [ + - ]: 262 : typename MapType::const_iterator aIt = rMap.find( rKey );
369 [ + - # ]: 262 : return (aIt == rMap.end()) ? rDefault : aIt->second;
[ - + ][ + - ]
370 : : }
371 : :
372 : : template< typename MapType >
373 : : /*static*/ typename MapType::mapped_type& ContainerHelper::getMapElementAccess( MapType& rMap, const typename MapType::key_type& rKey, typename MapType::mapped_type& rDefault )
374 : : {
375 : : typename MapType::iterator aIt = rMap.find( rKey );
376 : : return (aIt == rMap.end()) ? rDefault : aIt->second;
377 : : }
378 : :
379 : : template< typename VectorType >
380 : 947 : /*static*/ ::com::sun::star::uno::Sequence< typename VectorType::value_type > ContainerHelper::vectorToSequence( const VectorType& rVector )
381 : : {
382 : : typedef typename VectorType::value_type ValueType;
383 [ + + ][ - + ]: 947 : if( rVector.empty() )
384 : 337 : return ::com::sun::star::uno::Sequence< ValueType >();
385 : 947 : return ::com::sun::star::uno::Sequence< ValueType >( &rVector.front(), static_cast< sal_Int32 >( rVector.size() ) );
386 : : }
387 : :
388 : : template< typename MapType >
389 : : /*static*/ ::com::sun::star::uno::Sequence< typename MapType::mapped_type > ContainerHelper::mapToSequence( const MapType& rMap )
390 : : {
391 : : typedef typename MapType::mapped_type ValueType;
392 : : if( rMap.empty() )
393 : : return ::com::sun::star::uno::Sequence< ValueType >();
394 : : ::com::sun::star::uno::Sequence< ValueType > aSeq( static_cast< sal_Int32 >( rMap.size() ) );
395 : : sal_Int32 nIndex = 0;
396 : : for( typename MapType::const_iterator aIt = rMap.begin(), aEnd = rMap.end(); aIt != aEnd; ++aIt, ++nIndex )
397 : : aSeq[ nIndex ] = *aIt;
398 : : return aSeq;
399 : : }
400 : :
401 : : template< typename MatrixType >
402 : 0 : /*static*/ ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Sequence< typename MatrixType::value_type > > ContainerHelper::matrixToSequenceSequence( const MatrixType& rMatrix )
403 : : {
404 : : typedef typename MatrixType::value_type ValueType;
405 : 0 : ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Sequence< ValueType > > aSeq;
406 [ # # ]: 0 : if( !rMatrix.empty() )
407 : : {
408 [ # # ][ # # ]: 0 : aSeq.realloc( static_cast< sal_Int32 >( rMatrix.height() ) );
409 [ # # ][ # # ]: 0 : for( size_t nRow = 0, nHeight = rMatrix.height(); nRow < nHeight; ++nRow )
410 [ # # ][ # # ]: 0 : aSeq[ static_cast< sal_Int32 >( nRow ) ] =
[ # # ][ # # ]
[ # # ]
411 : : ::com::sun::star::uno::Sequence< ValueType >( &rMatrix.row_front( nRow ), static_cast< sal_Int32 >( rMatrix.width() ) );
412 : : }
413 : 0 : return aSeq;
414 : : }
415 : :
416 : : // ============================================================================
417 : :
418 : : } // namespace oox
419 : :
420 : : #endif
421 : :
422 : : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|