/src/libreoffice/sc/inc/dptabres.hxx
Line | Count | Source |
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 | | #pragma once |
21 | | |
22 | | #include "global.hxx" |
23 | | #include "dpfilteredcache.hxx" |
24 | | #include "calcmacros.hxx" |
25 | | #include "dpitemdata.hxx" |
26 | | #include "subtotal.hxx" |
27 | | |
28 | | #include <com/sun/star/sheet/DataPilotFieldOrientation.hpp> |
29 | | #include <com/sun/star/sheet/DataPilotFieldReference.hpp> |
30 | | |
31 | | #include <map> |
32 | | #include <unordered_map> |
33 | | #include <unordered_set> |
34 | | #include <memory> |
35 | | #include <vector> |
36 | | |
37 | | namespace com::sun::star::sheet { struct DataResult; } |
38 | | namespace com::sun::star::sheet { struct MemberResult; } |
39 | | namespace com::sun::star::uno { template <typename > class Sequence; } |
40 | | |
41 | | class ScDPSource; |
42 | | class ScDPDimension; |
43 | | class ScDPLevel; |
44 | | class ScDPMember; |
45 | | class ScDPResultMember; |
46 | | class ScDPResultVisibilityData; |
47 | | class ScTokenArray; |
48 | | |
49 | | struct ScDPValue; |
50 | | struct ScDPResultFilterContext; |
51 | | |
52 | | /** |
53 | | * Member names that are being processed for InitFrom/LateInitFrom (needed |
54 | | * for initialization of grouped items). |
55 | | */ |
56 | | class ScDPInitState |
57 | | { |
58 | | public: |
59 | | struct Member |
60 | | { |
61 | | tools::Long mnSrcIndex; |
62 | | SCROW mnNameIndex; |
63 | | |
64 | | Member(tools::Long nSrcIndex, SCROW nNameIndex); |
65 | | }; |
66 | | |
67 | | void AddMember(tools::Long nSourceIndex, SCROW nMember); |
68 | | void RemoveMember(); |
69 | | |
70 | 30 | const std::vector<Member>& GetMembers() const { return maMembers; } |
71 | | |
72 | | private: |
73 | | std::vector<Member> maMembers; |
74 | | }; |
75 | | |
76 | | typedef ::std::vector<sal_Int32> ScMemberSortOrder; |
77 | | |
78 | | /** |
79 | | * Select subtotal information, passed down the dimensions. |
80 | | */ |
81 | | struct ScDPSubTotalState |
82 | | { |
83 | | ScSubTotalFunc eColForce; |
84 | | ScSubTotalFunc eRowForce; |
85 | | tools::Long nColSubTotalFunc; |
86 | | tools::Long nRowSubTotalFunc; |
87 | | |
88 | | ScDPSubTotalState() : |
89 | 75.5M | eColForce( SUBTOTAL_FUNC_NONE ), |
90 | 75.5M | eRowForce( SUBTOTAL_FUNC_NONE ), |
91 | 75.5M | nColSubTotalFunc( -1 ), |
92 | 75.5M | nRowSubTotalFunc( -1 ) |
93 | 75.5M | {} |
94 | | }; |
95 | | |
96 | | /** |
97 | | * indexes when calculating running totals |
98 | | * |
99 | | * Col/RowVisible: simple counts from 0 - without sort order applied |
100 | | * - visible index (only used for running total / relative index) |
101 | | * |
102 | | * Col/RowSorted: with sort order applied - member index (used otherwise - |
103 | | * so other members' children can be accessed). |
104 | | */ |
105 | | class ScDPRunningTotalState |
106 | | { |
107 | | public: |
108 | | typedef std::vector<sal_Int32> IndexArray; /// array of sal_Int32 terminated by -1. |
109 | | |
110 | | ScDPRunningTotalState( ScDPResultMember* pColRoot, ScDPResultMember* pRowRoot ); |
111 | | |
112 | 0 | ScDPResultMember* GetColResRoot() const { return pColResRoot; } |
113 | 0 | ScDPResultMember* GetRowResRoot() const { return pRowResRoot; } |
114 | | |
115 | 0 | const IndexArray& GetColVisible() const { return maColVisible;} |
116 | 0 | const IndexArray& GetColSorted() const { return maColSorted;} |
117 | 0 | const IndexArray& GetRowVisible() const { return maRowVisible;} |
118 | 0 | const IndexArray& GetRowSorted() const { return maRowSorted;} |
119 | | |
120 | | void AddColIndex( sal_Int32 nVisible, tools::Long nSorted ); |
121 | | void AddRowIndex( sal_Int32 nVisible, tools::Long nSorted ); |
122 | | void RemoveColIndex(); |
123 | | void RemoveRowIndex(); |
124 | | |
125 | | private: |
126 | | ScDPResultMember* pColResRoot; |
127 | | ScDPResultMember* pRowResRoot; |
128 | | |
129 | | mutable IndexArray maColVisible; |
130 | | mutable IndexArray maColSorted; |
131 | | mutable IndexArray maRowVisible; |
132 | | mutable IndexArray maRowSorted; |
133 | | }; |
134 | | |
135 | | struct ScDPRelativePos |
136 | | { |
137 | | tools::Long nBasePos; // simple count, without sort order applied |
138 | | tools::Long nDirection; |
139 | | |
140 | | ScDPRelativePos( tools::Long nBase, tools::Long nDir ); |
141 | | }; |
142 | | |
143 | | // aggregated data |
144 | | //! separate header file? |
145 | | |
146 | | // Possible values for the nCount member: |
147 | | // (greater than 0 counts the collected values) |
148 | | const sal_Int64 SC_DPAGG_EMPTY = 0; // empty during data collection |
149 | | const sal_Int64 SC_DPAGG_DATA_ERROR = -1; // error during data collection |
150 | | const sal_Int64 SC_DPAGG_RESULT_EMPTY = -2; // empty result calculated |
151 | | const sal_Int64 SC_DPAGG_RESULT_VALID = -3; // valid result calculated |
152 | | const sal_Int64 SC_DPAGG_RESULT_ERROR = -4; // error in calculated result |
153 | | |
154 | | class ScDPAggData |
155 | | { |
156 | | private: |
157 | | WelfordRunner maWelford; |
158 | | double fVal; |
159 | | double fAux; |
160 | | sal_Int64 nCount; |
161 | | std::unique_ptr<ScDPAggData> pChild; |
162 | | std::vector<double> mSortedValues; |
163 | | |
164 | | public: |
165 | 10.1k | ScDPAggData() : fVal(0.0), fAux(0.0), nCount(SC_DPAGG_EMPTY) {} |
166 | | |
167 | | void Update( const ScDPValue& rNext, ScSubTotalFunc eFunc, const ScDPSubTotalState& rSubState ); |
168 | | void Calculate( ScSubTotalFunc eFunc, const ScDPSubTotalState& rSubState ); |
169 | | bool IsCalculated() const; |
170 | | |
171 | | double GetResult() const; |
172 | | bool HasError() const; |
173 | | bool HasData() const; |
174 | | |
175 | | void SetResult( double fNew ); |
176 | | void SetCalculatedResult( double fNew ); |
177 | | void SetEmpty( bool bSet ); |
178 | | void SetError(); |
179 | | |
180 | | double GetAuxiliary() const; |
181 | | void SetAuxiliary( double fNew ); |
182 | | |
183 | | void Reset(); // also deletes children |
184 | | |
185 | 998 | const ScDPAggData* GetExistingChild() const { return pChild.get(); } |
186 | | ScDPAggData* GetChild(); |
187 | | |
188 | | #if DUMP_PIVOT_TABLE |
189 | | void Dump(int nIndent) const; |
190 | | #endif |
191 | | }; |
192 | | |
193 | | // Row and grand total state, passed down (column total is at result member) |
194 | | |
195 | | class ScDPRowTotals |
196 | | { |
197 | | ScDPAggData aRowTotal; |
198 | | ScDPAggData aGrandTotal; |
199 | | bool bIsInColRoot; |
200 | | |
201 | | public: |
202 | | ScDPRowTotals(); |
203 | | ~ScDPRowTotals(); |
204 | | |
205 | | ScDPAggData* GetRowTotal( tools::Long nMeasure ); |
206 | | ScDPAggData* GetGrandTotal( tools::Long nMeasure ); |
207 | | |
208 | 90 | bool IsInColRoot() const { return bIsInColRoot; } |
209 | 1.34k | void SetInColRoot(bool bSet) { bIsInColRoot = bSet; } |
210 | | }; |
211 | | |
212 | | // results for a hierarchy dimension |
213 | | |
214 | | class ScDPResultDimension; |
215 | | class ScDPDataDimension; |
216 | | class ScDPDataMember; |
217 | | |
218 | 57.3k | #define SC_DPMEASURE_ALL -1 |
219 | 1.14k | #define SC_DPMEASURE_ANY -2 |
220 | | |
221 | | struct ScDPParentDimData |
222 | | { |
223 | | const SCROW mnOrder; //! Ref |
224 | | const ScDPDimension* mpParentDim; //! Ref |
225 | | const ScDPLevel* mpParentLevel; //! Ref |
226 | | const ScDPMember* mpMemberDesc; //! Ref |
227 | | |
228 | | ScDPParentDimData(); |
229 | | ScDPParentDimData(SCROW nIndex, const ScDPDimension* pDim, const ScDPLevel* pLev, const ScDPMember* pMember); |
230 | | }; |
231 | | |
232 | | class ResultMembers final |
233 | | { |
234 | | std::unordered_map<SCROW, ScDPParentDimData> maMemberHash; |
235 | | bool mbHasHideDetailsMember; |
236 | | public: |
237 | | const ScDPParentDimData* FindMember( SCROW nIndex ) const; |
238 | | void InsertMember( ScDPParentDimData const & rNew ); |
239 | 2.12M | bool IsHasHideDetailsMembers() const { return mbHasHideDetailsMember; } |
240 | 2.12M | void SetHasHideDetailsMembers( bool b ) { mbHasHideDetailsMember = b; } |
241 | | ResultMembers(); |
242 | | ~ResultMembers(); |
243 | | }; |
244 | | |
245 | | class LateInitParams |
246 | | { |
247 | | private: |
248 | | const ::std::vector<ScDPDimension*>& mppDim; |
249 | | const ::std::vector<ScDPLevel*>& mppLev; |
250 | | |
251 | | bool mbRow:1; |
252 | | bool mbInitChild:1; |
253 | | bool mbAllChildren:1; |
254 | | public: |
255 | | LateInitParams( const ::std::vector<ScDPDimension*>& ppDim, const ::std::vector<ScDPLevel*>& ppLev, |
256 | | bool bRow); |
257 | | |
258 | 146M | void SetInitChild( bool b ) { mbInitChild = b; } |
259 | 146M | void SetInitAllChildren( bool b ) { mbAllChildren = b; } |
260 | | |
261 | 2.12M | ScDPDimension* GetDim( size_t nPos ) const { return mppDim[nPos];} |
262 | 2.12M | ScDPLevel* GetLevel( size_t nPos ) const { return mppLev[nPos];} |
263 | | |
264 | 2.12M | bool GetInitChild() const {return mbInitChild; } |
265 | 2.12M | bool GetInitAllChild() const { return mbAllChildren; } |
266 | 2.12M | bool IsRow() const { return mbRow; } |
267 | | bool IsEnd( size_t nPos ) const ; |
268 | | }; |
269 | | |
270 | | /** |
271 | | * The term 'measure' here roughly equals "data dimension" ? |
272 | | */ |
273 | | class ScDPResultData |
274 | | { |
275 | | ScDPSource& mrSource; |
276 | | //! keep things like measure lists here |
277 | | |
278 | | std::vector<ScSubTotalFunc> maMeasureFuncs; |
279 | | std::vector<css::sheet::DataPilotFieldReference> maMeasureRefs; |
280 | | std::vector<css::sheet::DataPilotFieldOrientation> maMeasureRefOrients; |
281 | | std::vector<OUString> maMeasureNames; |
282 | | std::vector<sal_Int32> maMeasureIndexes; |
283 | | |
284 | | tools::Long mnVisibleMeasureCount; |
285 | | |
286 | | bool bLateInit:1; |
287 | | bool bDataAtCol:1; |
288 | | bool bDataAtRow:1; |
289 | | |
290 | | //! add "displayed values" settings |
291 | | mutable std::vector<std::unique_ptr<ResultMembers>> maDimMembers; |
292 | | public: |
293 | | ScDPResultData( ScDPSource& rSrc ); |
294 | | ~ScDPResultData(); |
295 | | |
296 | | void SetMeasureData( |
297 | | std::vector<ScSubTotalFunc>& rFunctions, |
298 | | std::vector<css::sheet::DataPilotFieldReference>& rRefs, |
299 | | std::vector<css::sheet::DataPilotFieldOrientation>& rRefOrient, |
300 | | std::vector<OUString>& rNames, std::vector<sal_Int32>& rIndexes, |
301 | | tools::Long nVisibleMeasureCount ); |
302 | | |
303 | | void SetDataLayoutOrientation( css::sheet::DataPilotFieldOrientation nOrient ); |
304 | | void SetLateInit( bool bSet ); |
305 | | |
306 | 324 | tools::Long GetMeasureCount() const { return maMeasureFuncs.size(); } |
307 | | ScSubTotalFunc GetMeasureFunction(tools::Long nMeasure) const; |
308 | | OUString GetMeasureString(tools::Long nMeasure, bool bForce, ScSubTotalFunc eForceFunc, bool& rbTotalResult) const; |
309 | | OUString GetMeasureDimensionName(tools::Long nMeasure) const; |
310 | | const ScTokenArray* GetMeasureDimensionCalculationToken(tools::Long nMeasure) const; |
311 | | const css::sheet::DataPilotFieldReference& GetMeasureRefVal(tools::Long nMeasure) const; |
312 | | css::sheet::DataPilotFieldOrientation GetMeasureRefOrient(tools::Long nMeasure) const; |
313 | | |
314 | 224M | bool IsLateInit() const { return bLateInit; } |
315 | | |
316 | | tools::Long GetColStartMeasure() const; |
317 | | tools::Long GetRowStartMeasure() const; |
318 | | |
319 | 20.2k | tools::Long GetCountForMeasure( tools::Long nMeas ) const { return (nMeas == SC_DPMEASURE_ALL) ? maMeasureFuncs.size() : 1; } |
320 | | |
321 | | bool IsBaseForGroup( tools::Long nDim ) const; // any group |
322 | | tools::Long GetGroupBase( tools::Long nGroupDim ) const; |
323 | | bool IsNumOrDateGroup( tools::Long nDim ) const; |
324 | | bool IsInGroup( SCROW nGroupDataId, tools::Long nGroupIndex, |
325 | | const ScDPItemData& rBaseData, tools::Long nBaseIndex ) const; |
326 | | bool HasCommonElement( SCROW nFirstDataId, tools::Long nFirstIndex, |
327 | | const ScDPItemData& rSecondData, tools::Long nSecondIndex ) const; |
328 | | |
329 | | ResultMembers& GetDimResultMembers(tools::Long nDim, const ScDPDimension* pDim, ScDPLevel* pLevel) const; |
330 | | |
331 | 11.3k | const ScDPSource& GetSource() const { return mrSource;} |
332 | 0 | const std::vector<OUString>& GetMeasureNames() const { return maMeasureNames; } |
333 | | }; |
334 | | |
335 | | class ScDPResultMember |
336 | | { |
337 | | private: |
338 | | const ScDPResultData* pResultData; |
339 | | ScDPParentDimData aParentDimData; |
340 | | std::unique_ptr<ScDPResultDimension> pChildDimension; |
341 | | std::unique_ptr<ScDPDataMember> pDataRoot; |
342 | | std::unique_ptr<ScDPAggData> pColTotal; // to store column totals |
343 | | sal_uInt16 nMemberStep; // step to show details |
344 | | bool bHasElements:1; |
345 | | bool bForceSubTotal:1; |
346 | | bool bHasHiddenDetails:1; |
347 | | bool bInitialized:1; |
348 | | bool bAutoHidden:1; |
349 | | |
350 | | public: |
351 | | ScDPResultMember( |
352 | | const ScDPResultData* pData, const ScDPParentDimData& rParentDimData ); //! Ref |
353 | | ScDPResultMember( const ScDPResultData* pData, bool bForceSub ); |
354 | | ~ScDPResultMember(); |
355 | | |
356 | | void InitFrom( const ::std::vector<ScDPDimension*>& ppDim, |
357 | | const ::std::vector<ScDPLevel*>& ppLev, |
358 | | size_t nPos, |
359 | | ScDPInitState& rInitState, |
360 | | bool bInitChild = true ); |
361 | | void LateInitFrom( |
362 | | LateInitParams& rParams, |
363 | | const ::std::vector< SCROW >& pItemData, |
364 | | size_t nPos, |
365 | | ScDPInitState& rInitState); |
366 | | void CheckShowEmpty( bool bShow = false ); |
367 | | OUString GetName() const; |
368 | | OUString GetDisplayName( bool bLocaleIndependent ) const; |
369 | | |
370 | | ScDPItemData FillItemData() const; |
371 | | bool IsValid() const; |
372 | | bool IsVisible() const; |
373 | | tools::Long GetSize(tools::Long nMeasure) const; |
374 | | // bHasHiddenDetails is set only if the "show details" flag is off, |
375 | | // and there was a child dimension to skip |
376 | 0 | bool HasHiddenDetails() const { return bHasHiddenDetails; } |
377 | | bool IsSubTotalInTitle(tools::Long nMeasure) const; |
378 | | |
379 | | tools::Long GetSubTotalCount( tools::Long* pUserSubStart = nullptr ) const; |
380 | | |
381 | | bool IsNamedItem( SCROW nIndex ) const; |
382 | | bool IsValidEntry( const ::std::vector< SCROW >& aMembers ) const; |
383 | | |
384 | 75.5M | void SetHasElements() { bHasElements = true; } |
385 | 0 | void SetAutoHidden() { bAutoHidden = true; } |
386 | | |
387 | | void ProcessData( const ::std::vector<SCROW>& aChildMembers, |
388 | | const ScDPResultDimension* pDataDim, |
389 | | const ::std::vector<SCROW>& aDataMembers, |
390 | | const ::std::vector<ScDPValue>& aValues ); |
391 | | void FillMemberResults( |
392 | | css::uno::Sequence< css::sheet::MemberResult>* pSequences, |
393 | | tools::Long& rPos, tools::Long nMeasure, bool bRoot, const OUString* pMemberName, const OUString* pMemberCaption ); |
394 | | |
395 | | void FillDataResults( |
396 | | const ScDPResultMember* pRefMember, |
397 | | ScDPResultFilterContext& rFilterCxt, |
398 | | css::uno::Sequence< css::uno::Sequence< css::sheet::DataResult> >& rSequence, |
399 | | tools::Long nMeasure) const; |
400 | | |
401 | | void UpdateDataResults( const ScDPResultMember* pRefMember, tools::Long nMeasure ) const; |
402 | | void UpdateRunningTotals( ScDPResultMember* pRefMember, tools::Long nMeasure, |
403 | | ScDPRunningTotalState& rRunning, ScDPRowTotals& rTotals ) const; |
404 | | |
405 | | void SortMembers( ScDPResultMember* pRefMember ); |
406 | | void DoAutoShow( ScDPResultMember* pRefMember ); |
407 | | |
408 | | void ResetResults(); |
409 | | |
410 | | #if DUMP_PIVOT_TABLE |
411 | | void DumpState( const ScDPResultMember* pRefMember, ScDocument* pDoc, ScAddress& rPos ) const; |
412 | | |
413 | | void Dump(int nIndent) const; |
414 | | #endif |
415 | | |
416 | | //! this will be removed! |
417 | 2.15M | const ScDPResultDimension* GetChildDimension() const { return pChildDimension.get(); } |
418 | 295M | ScDPResultDimension* GetChildDimension() { return pChildDimension.get(); } |
419 | | |
420 | 8 | ScDPDataMember* GetDataRoot() const { return pDataRoot.get(); } |
421 | | |
422 | 1.76k | const ScDPDimension* GetParentDim() const { return aParentDimData.mpParentDim; } //! Ref |
423 | 151M | const ScDPLevel* GetParentLevel() const { return aParentDimData.mpParentLevel; } //! Ref |
424 | 12.8M | const ScDPMember* GetDPMember()const { return aParentDimData.mpMemberDesc; } //! Ref |
425 | 30 | SCROW GetOrder() const { return aParentDimData.mnOrder; } //! Ref |
426 | 2.63k | bool IsRoot() const { return GetParentLevel() == nullptr; } |
427 | | SCROW GetDataId( ) const ; |
428 | | ScDPAggData* GetColTotal( tools::Long nMeasure ); |
429 | | |
430 | | void FillVisibilityData(ScDPResultVisibilityData& rData) const; |
431 | | }; |
432 | | |
433 | | class ScDPDataMember |
434 | | { |
435 | | private: |
436 | | const ScDPResultData* pResultData; |
437 | | const ScDPResultMember* pResultMember; //! Ref? |
438 | | std::unique_ptr<ScDPDataDimension> |
439 | | pChildDimension; |
440 | | ScDPAggData aAggregate; |
441 | | |
442 | | void UpdateValues( const ::std::vector<ScDPValue>& aValues, const ScDPSubTotalState& rSubState ); |
443 | | |
444 | | public: |
445 | | ScDPDataMember( const ScDPResultData* pData, const ScDPResultMember* pRes ); |
446 | | ~ScDPDataMember(); |
447 | | |
448 | | void InitFrom( const ScDPResultDimension* pDim ); |
449 | | |
450 | | OUString GetName() const; |
451 | | bool IsVisible() const; |
452 | | bool HasData( tools::Long nMeasure, const ScDPSubTotalState& rSubState ) const; |
453 | | |
454 | | bool IsNamedItem( SCROW nRow ) const; |
455 | | bool HasHiddenDetails() const; |
456 | | |
457 | | void ProcessData( const ::std::vector< SCROW >& aChildMembers, const ::std::vector<ScDPValue>& aValues, |
458 | | const ScDPSubTotalState& rSubState ); |
459 | | bool HasError( tools::Long nMeasure, const ScDPSubTotalState& rSubState ) const; |
460 | | double GetAggregate( tools::Long nMeasure, const ScDPSubTotalState& rSubState ) const; |
461 | | const ScDPAggData* GetConstAggData( tools::Long nMeasure, const ScDPSubTotalState& rSubState ) const; |
462 | | ScDPAggData* GetAggData( tools::Long nMeasure, const ScDPSubTotalState& rSubState ); |
463 | | |
464 | | void FillDataRow( |
465 | | const ScDPResultMember* pRefMember, |
466 | | ScDPResultFilterContext& rFilterCxt, |
467 | | css::uno::Sequence<css::sheet::DataResult>& rSequence, |
468 | | tools::Long nMeasure, bool bIsSubTotalRow, |
469 | | const ScDPSubTotalState& rSubState) const; |
470 | | |
471 | | void UpdateDataRow( const ScDPResultMember* pRefMember, tools::Long nMeasure, bool bIsSubTotalRow, |
472 | | const ScDPSubTotalState& rSubState ); |
473 | | void UpdateRunningTotals( ScDPResultMember* pRefMember, tools::Long nMeasure, bool bIsSubTotalRow, |
474 | | const ScDPSubTotalState& rSubState, ScDPRunningTotalState& rRunning, |
475 | | ScDPRowTotals& rTotals, const ScDPResultMember& rRowParent ); |
476 | | |
477 | | void SortMembers( ScDPResultMember* pRefMember ); |
478 | | void DoAutoShow( ScDPResultMember* pRefMember ); |
479 | | |
480 | | void ResetResults(); |
481 | | |
482 | | // function resolver |
483 | | static tools::Long FindMeasureIndex(const std::vector<OUString>& rNames, const OUString& rName); |
484 | | std::unique_ptr<ScTokenArray> ReplaceTokenMeasuresWithValues(const ScTokenArray* pArray, |
485 | | const ScDPSubTotalState& rSubState, std::unordered_set<tools::Long>& rRecStack); |
486 | | |
487 | | #if DUMP_PIVOT_TABLE |
488 | | void DumpState( const ScDPResultMember* pRefMember, ScDocument* pDoc, ScAddress& rPos ) const; |
489 | | void Dump(int nIndent) const; |
490 | | #endif |
491 | | |
492 | | //! this will be removed! |
493 | 4.97k | const ScDPDataDimension* GetChildDimension() const { return pChildDimension.get(); } |
494 | 11.7k | ScDPDataDimension* GetChildDimension() { return pChildDimension.get(); } |
495 | | }; |
496 | | |
497 | | // result dimension contains only members |
498 | | |
499 | | class ScDPResultDimension |
500 | | { |
501 | | public: |
502 | | typedef std::vector<std::unique_ptr<ScDPResultMember>> MemberArray; |
503 | | typedef std::unordered_map<SCROW, ScDPResultMember*> MemberHash; |
504 | | private: |
505 | | const ScDPResultData* pResultData; |
506 | | MemberArray maMemberArray; |
507 | | MemberHash maMemberHash; |
508 | | OUString aDimensionName; //! or ptr to IntDimension? |
509 | | tools::Long nSortMeasure; |
510 | | ScMemberSortOrder aMemberOrder; // used when sorted by measure |
511 | | bool bIsDataLayout:1; //! or ptr to IntDimension? |
512 | | bool bSortByData:1; |
513 | | bool bSortAscending:1; |
514 | | bool bAutoShow:1; |
515 | | bool bAutoTopItems:1; |
516 | | bool bInitialized:1; |
517 | | tools::Long nAutoMeasure; |
518 | | tools::Long nAutoCount; |
519 | | |
520 | | ScDPResultMember* FindMember( SCROW iData ) const; |
521 | | ScDPResultMember* AddMember( const ScDPParentDimData& aData ); |
522 | | ScDPResultMember* InsertMember( const ScDPParentDimData* pMemberData ); |
523 | | void InitWithMembers( LateInitParams& rParams, |
524 | | const ::std::vector< SCROW >& pItemData, |
525 | | size_t nPos, |
526 | | ScDPInitState& rInitState ); |
527 | | public: |
528 | | ScDPResultDimension( const ScDPResultData* pData ); |
529 | | ~ScDPResultDimension(); |
530 | | |
531 | | // allocates new members |
532 | | void InitFrom( |
533 | | const ::std::vector<ScDPDimension*>& ppDim, const ::std::vector<ScDPLevel*>& ppLev, |
534 | | size_t nPos, ScDPInitState& rInitState, bool bInitChild = true ); |
535 | | void LateInitFrom( LateInitParams& rParams, |
536 | | const ::std::vector< SCROW >& pItemData, |
537 | | size_t nPos, |
538 | | ScDPInitState& rInitState ); |
539 | | void CheckShowEmpty( bool bShow = false ); |
540 | | |
541 | | tools::Long GetSize(tools::Long nMeasure) const; |
542 | | |
543 | | bool IsValidEntry( const ::std::vector<SCROW>& aMembers ) const; |
544 | | |
545 | | // modifies existing members, allocates data dimensions |
546 | | void ProcessData( const ::std::vector<SCROW>& aMembers, |
547 | | const ScDPResultDimension* pDataDim, |
548 | | const ::std::vector<SCROW>& aDataMembers, |
549 | | const ::std::vector<ScDPValue>& aValues ) const; //! Test |
550 | | void FillMemberResults( css::uno::Sequence< |
551 | | css::sheet::MemberResult>* pSequences, |
552 | | tools::Long nStart, tools::Long nMeasure ); |
553 | | |
554 | | void FillDataResults( |
555 | | const ScDPResultMember* pRefMember, |
556 | | ScDPResultFilterContext& rFilterCxt, |
557 | | css::uno::Sequence< |
558 | | css::uno::Sequence< |
559 | | css::sheet::DataResult> >& rSequence, |
560 | | tools::Long nMeasure) const; |
561 | | |
562 | | void UpdateDataResults( const ScDPResultMember* pRefMember, tools::Long nMeasure ) const; |
563 | | void UpdateRunningTotals( ScDPResultMember* pRefMember, tools::Long nMeasure, |
564 | | ScDPRunningTotalState& rRunning, ScDPRowTotals& rTotals ) const; |
565 | | |
566 | | void SortMembers( ScDPResultMember* pRefMember ); |
567 | | tools::Long GetSortedIndex( tools::Long nUnsorted ) const; |
568 | | |
569 | | void DoAutoShow( ScDPResultMember* pRefMember ); |
570 | | |
571 | | void ResetResults(); |
572 | | |
573 | | // called for the reference dimension |
574 | | ScDPDataMember* GetRowReferenceMember( |
575 | | const ScDPRelativePos* pMemberPos, const OUString* pName, |
576 | | const sal_Int32* pRowIndexes, const sal_Int32* pColIndexes ) const; |
577 | | |
578 | | // uses row root member from ScDPRunningTotalState |
579 | | static ScDPDataMember* GetColReferenceMember( |
580 | | const ScDPRelativePos* pMemberPos, const OUString* pName, |
581 | | sal_Int32 nRefDimPos, const ScDPRunningTotalState& rRunning ); |
582 | | |
583 | | #if DUMP_PIVOT_TABLE |
584 | | void DumpState( const ScDPResultMember* pRefMember, ScDocument* pDoc, ScAddress& rPos ) const; |
585 | | void Dump(int nIndent) const; |
586 | | #endif |
587 | | |
588 | | // for ScDPDataDimension::InitFrom |
589 | | tools::Long GetMemberCount() const; |
590 | | const ScDPResultMember* GetMember(tools::Long n) const; |
591 | | ScDPResultMember* GetMember(tools::Long n); |
592 | | |
593 | 745 | const ScMemberSortOrder& GetMemberOrder() const { return aMemberOrder; } |
594 | 4.16k | ScMemberSortOrder& GetMemberOrder() { return aMemberOrder; } |
595 | | |
596 | 1.51k | bool IsDataLayout() const { return bIsDataLayout; } |
597 | 975 | const OUString& GetName() const { return aDimensionName; } |
598 | | |
599 | 98 | bool IsSortByData() const { return bSortByData; } |
600 | 0 | bool IsSortAscending() const { return bSortAscending; } |
601 | 0 | tools::Long GetSortMeasure() const { return nSortMeasure; } |
602 | | |
603 | 0 | bool IsAutoShow() const { return bAutoShow; } |
604 | 0 | bool IsAutoTopItems() const { return bAutoTopItems; } |
605 | 0 | tools::Long GetAutoMeasure() const { return nAutoMeasure; } |
606 | 0 | tools::Long GetAutoCount() const { return nAutoCount; } |
607 | | |
608 | | ScDPResultDimension* GetFirstChildDimension() const; |
609 | | |
610 | | void FillVisibilityData(ScDPResultVisibilityData& rData) const; |
611 | | }; |
612 | | |
613 | | class ScDPDataDimension |
614 | | { |
615 | | private: |
616 | | const ScDPResultData* pResultData; |
617 | | const ScDPResultDimension* pResultDimension; // column |
618 | | std::vector<std::unique_ptr<ScDPDataMember>> maMembers; |
619 | | bool bIsDataLayout; //! or ptr to IntDimension? |
620 | | |
621 | | public: |
622 | | ScDPDataDimension( const ScDPResultData* pData ); |
623 | | ~ScDPDataDimension(); |
624 | | |
625 | | void InitFrom( const ScDPResultDimension* pDim ); // recursive |
626 | | void ProcessData( const ::std::vector< SCROW >& aDataMembers, const ::std::vector<ScDPValue>& aValues, |
627 | | const ScDPSubTotalState& rSubState ); |
628 | | void FillDataRow( |
629 | | const ScDPResultDimension* pRefDim, |
630 | | ScDPResultFilterContext& rFilterCxt, |
631 | | css::uno::Sequence<css::sheet::DataResult>& rSequence, |
632 | | tools::Long nMeasure, bool bIsSubTotalRow, const ScDPSubTotalState& rSubState) const; |
633 | | |
634 | | void UpdateDataRow( const ScDPResultDimension* pRefDim, tools::Long nMeasure, bool bIsSubTotalRow, |
635 | | const ScDPSubTotalState& rSubState ) const; |
636 | | void UpdateRunningTotals( ScDPResultDimension* pRefDim, tools::Long nMeasure, bool bIsSubTotalRow, |
637 | | const ScDPSubTotalState& rSubState, ScDPRunningTotalState& rRunning, |
638 | | ScDPRowTotals& rTotals, const ScDPResultMember& rRowParent ) const; |
639 | | |
640 | | void SortMembers( ScDPResultDimension* pRefDim ); |
641 | | tools::Long GetSortedIndex( tools::Long nUnsorted ) const; |
642 | | |
643 | | void DoAutoShow( ScDPResultDimension* pRefDim ); |
644 | | |
645 | | void ResetResults(); |
646 | | |
647 | | #if DUMP_PIVOT_TABLE |
648 | | void DumpState( const ScDPResultDimension* pRefDim, ScDocument* pDoc, ScAddress& rPos ) const; |
649 | | void Dump(int nIndent) const; |
650 | | #endif |
651 | | |
652 | | tools::Long GetMemberCount() const; |
653 | | const ScDPDataMember* GetMember(tools::Long n) const; |
654 | | ScDPDataMember* GetMember(tools::Long n); |
655 | | }; |
656 | | |
657 | | /** |
658 | | * This class collects visible members of each dimension and uses that |
659 | | * information to create filtering criteria (e.g. for drill-down data). |
660 | | */ |
661 | | class ScDPResultVisibilityData |
662 | | { |
663 | | public: |
664 | | ScDPResultVisibilityData( ScDPSource* pSource); |
665 | | ~ScDPResultVisibilityData(); |
666 | | |
667 | | void addVisibleMember(const OUString& rDimName, const ScDPItemData& rMemberItem); |
668 | | void fillFieldFilters(::std::vector<ScDPFilteredCache::Criterion>& rFilters) const; |
669 | | |
670 | | private: |
671 | | struct MemberHash |
672 | | { |
673 | | size_t operator()(const ScDPItemData& r) const; |
674 | | }; |
675 | | typedef std::unordered_set<ScDPItemData, MemberHash> VisibleMemberType; |
676 | | typedef std::unordered_map<OUString, VisibleMemberType> DimMemberType; |
677 | | DimMemberType maDimensions; |
678 | | |
679 | | ScDPSource* mpSource; |
680 | | }; |
681 | | |
682 | | /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ |