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 INCLUDED_SC_INC_DPOBJECT_HXX
21 : #define INCLUDED_SC_INC_DPOBJECT_HXX
22 :
23 : #include "scdllapi.h"
24 : #include "global.hxx"
25 : #include "address.hxx"
26 : #include "dpoutput.hxx"
27 : #include "dptypes.hxx"
28 : #include "pivot.hxx"
29 : #include "calcmacros.hxx"
30 :
31 : #include <com/sun/star/sheet/XDimensionsSupplier.hpp>
32 :
33 : #include <set>
34 : #include <vector>
35 :
36 : #include <boost/ptr_container/ptr_list.hpp>
37 : #include <boost/ptr_container/ptr_vector.hpp>
38 : #include <boost/ptr_container/ptr_map.hpp>
39 : #include <boost/shared_ptr.hpp>
40 :
41 : namespace com { namespace sun { namespace star {
42 :
43 : namespace container {
44 : class XIndexAccess;
45 : }
46 :
47 : namespace sdbc {
48 : class XRowSet;
49 : }
50 :
51 : namespace sheet {
52 : struct DataPilotTablePositionData;
53 : struct DataPilotTableHeaderData;
54 : struct DataPilotFieldFilter;
55 : }
56 : }}}
57 :
58 : class Rectangle;
59 : class ScDPSaveData;
60 : class ScDPOutput;
61 : struct ScPivotParam;
62 : struct ScImportSourceDesc;
63 : class ScSheetSourceDesc;
64 : struct ScPivotField;
65 : class ScDPTableData;
66 : class ScDPDimensionSaveData;
67 : class ScRangeList;
68 :
69 0 : struct ScDPServiceDesc
70 : {
71 : OUString aServiceName;
72 : OUString aParSource;
73 : OUString aParName;
74 : OUString aParUser;
75 : OUString aParPass;
76 :
77 : ScDPServiceDesc( const OUString& rServ, const OUString& rSrc, const OUString& rNam,
78 : const OUString& rUser, const OUString& rPass );
79 :
80 : bool operator== ( const ScDPServiceDesc& rOther ) const;
81 : };
82 :
83 : class SC_DLLPUBLIC ScDPObject
84 : {
85 : private:
86 : ScDocument* pDoc;
87 : // settings
88 : ScDPSaveData* pSaveData;
89 : OUString aTableName;
90 : OUString aTableTag;
91 : ScRange aOutRange;
92 : ScSheetSourceDesc* pSheetDesc; // for sheet data
93 : ScImportSourceDesc* pImpDesc; // for database data
94 : ScDPServiceDesc* pServDesc; // for external service
95 : ::boost::shared_ptr<ScDPTableData> mpTableData;
96 : // cached data
97 : com::sun::star::uno::Reference<com::sun::star::sheet::XDimensionsSupplier> xSource;
98 : ScDPOutput* pOutput;
99 : sal_uInt16 mnAutoFormatIndex;
100 : long nHeaderRows; // page fields plus filter button
101 : bool mbHeaderLayout:1; // true : grid, false : standard
102 : bool bAllowMove:1;
103 : bool bSettingsChanged:1;
104 : bool mbEnableGetPivotData:1;
105 :
106 : SAL_DLLPRIVATE ScDPTableData* GetTableData();
107 : SAL_DLLPRIVATE void CreateObjects();
108 : SAL_DLLPRIVATE void CreateOutput();
109 : SAL_DLLPRIVATE void ClearSource();
110 : SAL_DLLPRIVATE bool FillLabelDataForDimension(
111 : const com::sun::star::uno::Reference<
112 : com::sun::star::container::XIndexAccess>& xDims,
113 : sal_Int32 nDim, ScDPLabelData& rLabelData);
114 :
115 : public:
116 : ScDPObject(ScDocument* pD);
117 : ScDPObject(const ScDPObject& r);
118 : ~ScDPObject();
119 :
120 : ScDPObject& operator= (const ScDPObject& r);
121 :
122 : void EnableGetPivotData(bool b);
123 :
124 : void SetAllowMove(bool bSet);
125 :
126 : void InvalidateData();
127 : void Clear();
128 : void ClearTableData();
129 : void ReloadGroupTableData();
130 :
131 : void Output( const ScAddress& rPos );
132 : ScRange GetNewOutputRange( bool& rOverflow );
133 :
134 : ScRange GetOutputRangeByType( sal_Int32 nType );
135 : ScRange GetOutputRangeByType( sal_Int32 nType ) const;
136 :
137 : void SetSaveData(const ScDPSaveData& rData);
138 582 : ScDPSaveData* GetSaveData() const { return pSaveData; }
139 :
140 : void SetOutRange(const ScRange& rRange);
141 : const ScRange& GetOutRange() const;
142 :
143 : void SetHeaderLayout(bool bUseGrid);
144 0 : bool GetHeaderLayout() const { return mbHeaderLayout;}
145 :
146 : void SetSheetDesc(const ScSheetSourceDesc& rDesc, bool bFromRefUpdate = false);
147 : void SetImportDesc(const ScImportSourceDesc& rDesc);
148 : void SetServiceData(const ScDPServiceDesc& rDesc);
149 :
150 : void WriteSourceDataTo( ScDPObject& rDest ) const;
151 : void WriteTempDataTo( ScDPObject& rDest ) const;
152 :
153 85 : const ScSheetSourceDesc* GetSheetDesc() const { return pSheetDesc; }
154 0 : const ScImportSourceDesc* GetImportSourceDesc() const { return pImpDesc; }
155 0 : const ScDPServiceDesc* GetDPServiceDesc() const { return pServDesc; }
156 :
157 : com::sun::star::uno::Reference<com::sun::star::sheet::XDimensionsSupplier> GetSource();
158 :
159 : bool IsSheetData() const;
160 0 : bool IsImportData() const { return(pImpDesc != NULL); }
161 0 : bool IsServiceData() const { return(pServDesc != NULL); }
162 :
163 : void SetName(const OUString& rNew);
164 1320 : const OUString& GetName() const { return aTableName; }
165 : void SetTag(const OUString& rNew);
166 23 : const OUString& GetTag() const { return aTableTag; }
167 :
168 : /**
169 : * Data description cell displays the description of a data dimension if
170 : * and only if there is only one data dimension. It's usually located at
171 : * the upper-left corner of the table output.
172 : */
173 : bool IsDataDescriptionCell(const ScAddress& rPos);
174 :
175 : bool IsDimNameInUse(const OUString& rName) const;
176 : OUString GetDimName( long nDim, bool& rIsDataLayout, sal_Int32* pFlags = NULL );
177 : bool IsDuplicated( long nDim );
178 : long GetDimCount();
179 : void GetHeaderPositionData(const ScAddress& rPos, ::com::sun::star::sheet::DataPilotTableHeaderData& rData);
180 : long GetHeaderDim( const ScAddress& rPos, sal_uInt16& rOrient );
181 : bool GetHeaderDrag( const ScAddress& rPos, bool bMouseLeft, bool bMouseTop,
182 : long nDragDim,
183 : Rectangle& rPosRect, sal_uInt16& rOrient, long& rDimPos );
184 : bool IsFilterButton( const ScAddress& rPos );
185 :
186 : double GetPivotData(
187 : const OUString& rDataFieldName,
188 : std::vector<com::sun::star::sheet::DataPilotFieldFilter>& rFilters);
189 :
190 : bool ParseFilters(
191 : OUString& rDataFieldName,
192 : std::vector<com::sun::star::sheet::DataPilotFieldFilter>& rFilters,
193 : std::vector<com::sun::star::sheet::GeneralFunction>& rFilterFuncs,
194 : const OUString& rFilterList );
195 :
196 : void GetMemberResultNames(ScDPUniqueStringSet& rNames, long nDimension);
197 :
198 : void ToggleDetails(const ::com::sun::star::sheet::DataPilotTableHeaderData& rElemDesc, ScDPObject* pDestObj);
199 :
200 : bool FillOldParam(ScPivotParam& rParam) const;
201 : bool FillLabelData(sal_Int32 nDim, ScDPLabelData& Labels);
202 : bool FillLabelData(ScPivotParam& rParam);
203 :
204 : bool GetHierarchiesNA( sal_Int32 nDim, com::sun::star::uno::Reference< com::sun::star::container::XNameAccess >& xHiers );
205 : bool GetHierarchies( sal_Int32 nDim, com::sun::star::uno::Sequence< OUString >& rHiers );
206 :
207 : sal_Int32 GetUsedHierarchy( sal_Int32 nDim );
208 :
209 : bool GetMembersNA( sal_Int32 nDim, com::sun::star::uno::Reference< com::sun::star::container::XNameAccess >& xMembers );
210 : bool GetMembersNA( sal_Int32 nDim, sal_Int32 nHier, com::sun::star::uno::Reference< com::sun::star::container::XNameAccess >& xMembers );
211 :
212 : bool GetMemberNames( sal_Int32 nDim, ::com::sun::star::uno::Sequence< OUString >& rNames );
213 : bool GetMembers( sal_Int32 nDim, sal_Int32 nHier, ::std::vector<ScDPLabelData::Member>& rMembers );
214 :
215 : void UpdateReference( UpdateRefMode eUpdateRefMode,
216 : const ScRange& r, SCsCOL nDx, SCsROW nDy, SCsTAB nDz );
217 : bool RefsEqual( const ScDPObject& r ) const;
218 : void WriteRefsTo( ScDPObject& r ) const;
219 :
220 : void GetPositionData(const ScAddress& rPos, ::com::sun::star::sheet::DataPilotTablePositionData& rPosData);
221 :
222 : bool GetDataFieldPositionData(const ScAddress& rPos,
223 : ::com::sun::star::uno::Sequence<
224 : ::com::sun::star::sheet::DataPilotFieldFilter >& rFilters);
225 :
226 : void GetDrillDownData(const ScAddress& rPos,
227 : ::com::sun::star::uno::Sequence<
228 : ::com::sun::star::uno::Sequence<
229 : ::com::sun::star::uno::Any > >& rTableData);
230 :
231 : // apply drop-down attribute, initialize nHeaderRows, without accessing the source
232 : // (button attribute must be present)
233 : void RefreshAfterLoad();
234 :
235 : void BuildAllDimensionMembers();
236 :
237 : /**
238 : * Remove in the save data entries for members that don't exist anymore.
239 : * This is called during pivot table refresh.
240 : */
241 : bool SyncAllDimensionMembers();
242 :
243 : static bool HasRegisteredSources();
244 : static com::sun::star::uno::Sequence<OUString> GetRegisteredSources();
245 : static com::sun::star::uno::Reference<com::sun::star::sheet::XDimensionsSupplier>
246 : CreateSource( const ScDPServiceDesc& rDesc );
247 :
248 : static void ConvertOrientation(
249 : ScDPSaveData& rSaveData,
250 : const ScPivotFieldVector& rFields, sal_uInt16 nOrient,
251 : const com::sun::star::uno::Reference<
252 : com::sun::star::sheet::XDimensionsSupplier>& xSource,
253 : const ScDPLabelDataVector& rLabels,
254 : const ScPivotFieldVector* pRefColFields = NULL,
255 : const ScPivotFieldVector* pRefRowFields = NULL,
256 : const ScPivotFieldVector* pRefPageFields = NULL );
257 :
258 : static bool IsOrientationAllowed( sal_uInt16 nOrient, sal_Int32 nDimFlags );
259 :
260 : #if DEBUG_PIVOT_TABLE
261 : void DumpCache() const;
262 : #endif
263 : };
264 :
265 : class ScDPCollection
266 : {
267 : friend class ScDPCache;
268 : public:
269 :
270 : /**
271 : * Stores and manages all caches from internal sheets.
272 : */
273 263 : class SheetCaches
274 : {
275 : friend class ScDPCollection;
276 : typedef boost::ptr_map<size_t, ScDPCache> CachesType;
277 : typedef std::vector<ScRange> RangeIndexType;
278 : CachesType maCaches;
279 : RangeIndexType maRanges;
280 : ScDocument* mpDoc;
281 : public:
282 : SheetCaches(ScDocument* pDoc);
283 : bool hasCache(const ScRange& rRange) const;
284 : const ScDPCache* getCache(const ScRange& rRange, const ScDPDimensionSaveData* pDimData);
285 : SC_DLLPUBLIC size_t size() const;
286 :
287 : void updateReference(
288 : UpdateRefMode eMode, const ScRange& r, SCsCOL nDx, SCsROW nDy, SCsTAB nDz);
289 :
290 : SC_DLLPUBLIC ScDPCache* getExistingCache(const ScRange& rRange);
291 : SC_DLLPUBLIC const ScDPCache* getExistingCache(const ScRange& rRange) const;
292 :
293 : void updateCache(const ScRange& rRange, std::set<ScDPObject*>& rRefs);
294 : bool remove(const ScDPCache* p);
295 :
296 : SC_DLLPUBLIC const std::vector<ScRange>& getAllRanges() const;
297 : };
298 :
299 : /**
300 : * Data caches for range name based source data.
301 : */
302 263 : class NameCaches
303 : {
304 : friend class ScDPCollection;
305 : typedef ::boost::ptr_map<OUString, ScDPCache> CachesType;
306 : CachesType maCaches;
307 : ScDocument* mpDoc;
308 : public:
309 : NameCaches(ScDocument* pDoc);
310 : bool hasCache(const OUString& rName) const;
311 : const ScDPCache* getCache(
312 : const OUString& rName, const ScRange& rRange, const ScDPDimensionSaveData* pDimData);
313 : size_t size() const;
314 : private:
315 : ScDPCache* getExistingCache(const OUString& rName);
316 :
317 : void updateCache(
318 : const OUString& rName, const ScRange& rRange, std::set<ScDPObject*>& rRefs);
319 : bool remove(const ScDPCache* p);
320 : };
321 :
322 : /**
323 : * Defines connection type to external data source. Used as a key to look
324 : * up database cache.
325 : */
326 0 : struct DBType
327 : {
328 : sal_Int32 mnSdbType;
329 : OUString maDBName;
330 : OUString maCommand;
331 : DBType(sal_Int32 nSdbType, const OUString& rDBName, const OUString& rCommand);
332 :
333 : struct less : public ::std::binary_function<DBType, DBType, bool>
334 : {
335 : bool operator() (const DBType& left, const DBType& right) const;
336 : };
337 : };
338 :
339 : /**
340 : * Data caches for external database sources.
341 : */
342 263 : class DBCaches
343 : {
344 : friend class ScDPCollection;
345 : typedef ::boost::ptr_map<DBType, ScDPCache, DBType::less> CachesType;
346 : CachesType maCaches;
347 : ScDocument* mpDoc;
348 : public:
349 : DBCaches(ScDocument* pDoc);
350 : bool hasCache(sal_Int32 nSdbType, const OUString& rDBName, const OUString& rCommand) const;
351 : const ScDPCache* getCache(
352 : sal_Int32 nSdbType, const OUString& rDBName, const OUString& rCommand,
353 : const ScDPDimensionSaveData* pDimData);
354 :
355 : private:
356 : ScDPCache* getExistingCache(
357 : sal_Int32 nSdbType, const OUString& rDBName, const OUString& rCommand);
358 :
359 : static com::sun::star::uno::Reference<com::sun::star::sdbc::XRowSet> createRowSet(
360 : sal_Int32 nSdbType, const OUString& rDBName, const OUString& rCommand);
361 :
362 : void updateCache(
363 : sal_Int32 nSdbType, const OUString& rDBName, const OUString& rCommand,
364 : std::set<ScDPObject*>& rRefs);
365 : bool remove(const ScDPCache* p);
366 : };
367 :
368 : ScDPCollection(ScDocument* pDocument);
369 : ScDPCollection(const ScDPCollection& r);
370 : ~ScDPCollection();
371 :
372 : sal_uLong ReloadCache(ScDPObject* pDPObj, std::set<ScDPObject*>& rRefs);
373 : bool ReloadGroupsInCache(ScDPObject* pDPObj, std::set<ScDPObject*>& rRefs);
374 :
375 : SC_DLLPUBLIC size_t GetCount() const;
376 : SC_DLLPUBLIC ScDPObject* operator[](size_t nIndex);
377 : SC_DLLPUBLIC const ScDPObject* operator[](size_t nIndex) const;
378 :
379 : const ScDPObject* GetByName(const OUString& rName) const;
380 :
381 : void DeleteOnTab( SCTAB nTab );
382 : void UpdateReference( UpdateRefMode eUpdateRefMode,
383 : const ScRange& r, SCsCOL nDx, SCsROW nDy, SCsTAB nDz );
384 : void CopyToTab( SCTAB nOld, SCTAB nNew );
385 : bool RefsEqual( const ScDPCollection& r ) const;
386 : void WriteRefsTo( ScDPCollection& r ) const;
387 :
388 : /**
389 : * Create a new name that's not yet used by any existing data pilot
390 : * objects. All data pilot names are 'DataPilot' + <num>, and the nMin
391 : * specifies the minimum number allowed.
392 : *
393 : * @param nMin minimum number allowed.
394 : *
395 : * @return new name for data pilot object.
396 : */
397 : OUString CreateNewName( sal_uInt16 nMin = 1 ) const;
398 :
399 : void FreeTable(ScDPObject* pDPObj);
400 : SC_DLLPUBLIC bool InsertNewTable(ScDPObject* pDPObj);
401 :
402 : SC_DLLPUBLIC SheetCaches& GetSheetCaches();
403 : SC_DLLPUBLIC const SheetCaches& GetSheetCaches() const;
404 : NameCaches& GetNameCaches();
405 : SC_DLLPUBLIC const NameCaches& GetNameCaches() const;
406 : DBCaches& GetDBCaches();
407 : SC_DLLPUBLIC const DBCaches& GetDBCaches() const;
408 :
409 : ScRangeList GetAllTableRanges( SCTAB nTab ) const;
410 : bool IntersectsTableByColumns( SCCOL nCol1, SCCOL nCol2, SCROW nRow, SCTAB nTab ) const;
411 : bool IntersectsTableByRows( SCCOL nCol, SCROW nRow1, SCROW nRow2, SCTAB nTab ) const;
412 : bool HasTable( const ScRange& rRange ) const;
413 :
414 : #if DEBUG_PIVOT_TABLE
415 : void DumpTables() const;
416 : #endif
417 :
418 : private:
419 : /** Only to be called from ScDPCache::RemoveReference(). */
420 : void RemoveCache(const ScDPCache* pCache);
421 :
422 : void GetAllTables(const ScRange& rSrcRange, std::set<ScDPObject*>& rRefs) const;
423 : void GetAllTables(const OUString& rSrcName, std::set<ScDPObject*>& rRefs) const;
424 : void GetAllTables(
425 : sal_Int32 nSdbType, const OUString& rDBName, const OUString& rCommand,
426 : std::set<ScDPObject*>& rRefs) const;
427 :
428 : private:
429 : typedef ::boost::ptr_vector<ScDPObject> TablesType;
430 :
431 : ScDocument* mpDoc;
432 : TablesType maTables;
433 : SheetCaches maSheetCaches;
434 : NameCaches maNameCaches;
435 : DBCaches maDBCaches;
436 : };
437 :
438 : bool operator<(const ScDPCollection::DBType& left, const ScDPCollection::DBType& right);
439 :
440 : #endif
441 :
442 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|