Coverage Report

Created: 2026-08-14 10:22

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/libreoffice/sc/inc/dbdata.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 "scdllapi.h"
23
#include "refreshtimer.hxx"
24
#include "address.hxx"
25
#include "global.hxx"
26
#include "rangelst.hxx"
27
28
#include <svl/listener.hxx>
29
#include <svl/poolitem.hxx>
30
31
#include <memory>
32
#include <set>
33
#include <vector>
34
35
class ScDocument;
36
struct ScSortParam;
37
struct ScQueryParam;
38
struct ScSubTotalParam;
39
class ScTokenArray;
40
41
class SC_DLLPUBLIC ScDatabaseSettingItem final : public SfxPoolItem
42
{
43
    bool mbHeaderRow;
44
    bool mbTotalRow;
45
    bool mbFirstCol;
46
    bool mbLastCol;
47
    bool mbStripedRows;
48
    bool mbStripedCols;
49
    bool mbShowFilters;
50
    OUString maStyleID;
51
52
public:
53
    static SfxPoolItem* CreateDefault();
54
    DECLARE_ITEM_TYPE_FUNCTION(ScDatabaseSettingItem)
55
    ScDatabaseSettingItem();
56
    ScDatabaseSettingItem(bool bHeaderRow, bool bTotalRow, bool bFirstCol, bool bLastCol,
57
                          bool bStripedRows, bool bStripedCols, bool bShowFilter,
58
                          const OUString& aStyleID);
59
    ScDatabaseSettingItem( const ScDatabaseSettingItem& rItem );
60
    virtual ~ScDatabaseSettingItem() override;
61
62
    virtual bool            QueryValue( css::uno::Any& rVal, sal_uInt8 nMemberId = 0 ) const override;
63
    virtual bool            PutValue( const css::uno::Any& rVal, sal_uInt8 nMemberId ) override;
64
65
    ScDatabaseSettingItem& operator=( const ScDatabaseSettingItem& rItem );
66
    virtual bool operator==( const SfxPoolItem& ) const override;
67
    virtual ScDatabaseSettingItem* Clone( SfxItemPool *pPool = nullptr ) const override;
68
69
    bool HasHeaderRow() const;
70
    bool HasTotalRow() const;
71
    bool HasFirstCol() const;
72
    bool HasLastCol() const;
73
    bool HasStripedRows() const;
74
    bool HasStripedCols() const;
75
    bool HasShowFilters() const;
76
    const OUString& GetStyleID() const;
77
};
78
79
/** Enum used to indicate which portion of the DBArea is to be considered. */
80
enum class ScDBDataPortion
81
{
82
    TOP_LEFT,   ///< top left cell of area
83
    AREA        ///< entire area
84
};
85
86
// TODO: this can be merged with struct TableColumnModel
87
struct TableColumnAttributes
88
{
89
    std::optional<OUString> maTotalsRowLabel = std::nullopt;
90
    std::optional<OUString> maTotalsFunction = std::nullopt;
91
    std::optional<OUString> maCustomFunction = std::nullopt;
92
};
93
94
// xmlColumnPr attributes
95
struct XmlColumnPrModel
96
{
97
    sal_uInt32          mnMapId;
98
    OUString            msXpath;
99
    OUString            msXmlDataType;
100
    bool                mbDenormalized;
101
102
    explicit            XmlColumnPrModel();
103
};
104
105
struct TableColumnModel
106
{
107
    typedef std::unique_ptr<XmlColumnPrModel> XmlColumnPrModelPtr;
108
    XmlColumnPrModelPtr mxXmlColumnPr; // Special settings for XML Column Properties.
109
    XmlColumnPrModel&   createXmlColumnPr();
110
111
    OUString            maUniqueName; // unique name of the <tableColumn>
112
113
    explicit            TableColumnModel();
114
};
115
116
/** Container base class to provide selected access for ScDBData. */
117
class ScDBDataContainerBase
118
{
119
public:
120
134k
    ScDBDataContainerBase( ScDocument& rDoc ) : mrDoc(rDoc) {}
121
134k
    virtual ~ScDBDataContainerBase() {}
122
    ScDocument& GetDocument() const;
123
    ScRangeList& GetDirtyTableColumnNames();
124
125
protected:
126
    ScDocument& mrDoc;
127
    ScRangeList maDirtyTableColumnNames;
128
};
129
130
131
struct SAL_DLLPUBLIC_RTTI ScTableStyleParam
132
{
133
    OUString maStyleID;
134
    bool mbRowStripes;
135
    bool mbColumnStripes;
136
    bool mbFirstColumn;
137
    bool mbLastColumn;
138
139
    SC_DLLPUBLIC ScTableStyleParam();
140
141
    bool operator== (const ScTableStyleParam& rData) const;
142
};
143
144
class SAL_DLLPUBLIC_RTTI ScDBData final : public SvtListener, public ScRefreshTimer
145
{
146
private:
147
    std::unique_ptr<ScSortParam> mpSortParam;
148
    std::unique_ptr<ScQueryParam> mpQueryParam;
149
    std::unique_ptr<ScSubTotalParam> mpSubTotal;
150
    std::unique_ptr<ScImportParam> mpImportParam;
151
    std::unique_ptr<ScTableStyleParam> mpTableStyles;
152
153
    ScDBDataContainerBase* mpContainer;
154
155
    /// DBParam
156
    const OUString aName;
157
    OUString aUpper;
158
    OUString        aTableType;
159
    SCTAB           nTable;
160
    SCCOL           nStartCol;
161
    SCROW           nStartRow;
162
    SCCOL           nEndCol;
163
    SCROW           nEndRow;
164
    bool            bByRow;
165
    bool            bHasHeader;
166
    bool            bHasTotals;
167
    bool            bDoSize;
168
    bool            bKeepFmt;
169
    bool            bStripData;
170
171
    /// QueryParam
172
    bool            bIsAdvanced;        ///< true if created by advanced filter
173
    ScRange         aAdvSource;         ///< source range
174
175
    bool            bDBSelection;       ///< not in Param: if selection, block update
176
177
    sal_uInt16      nIndex;             ///< unique index formulas
178
    bool            bAutoFilter;        ///< AutoFilter? (not saved)
179
    bool            bModified;          ///< is set/cleared for/by(?) UpdateReference
180
181
    ::std::vector< OUString > maTableColumnNames;   ///< names of table columns
182
    ::std::vector< TableColumnModel > maTableColumnModel;
183
    bool            mbTableColumnNamesDirty;
184
    SCSIZE          nFilteredRowCount;
185
186
    using ScRefreshTimer::operator==;
187
188
public:
189
    struct less
190
    {
191
        bool operator() (const std::unique_ptr<ScDBData>& left, const std::unique_ptr<ScDBData>& right) const;
192
    };
193
194
    SC_DLLPUBLIC ScDBData(const OUString& rName,
195
             SCTAB nTab,
196
             SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, bool bByR = true, bool bHasH = true, bool bTotals = false,
197
                          const OUString& rTableType = u""_ustr,
198
                          const OUString& rTableStyleID = u""_ustr);
199
    ScDBData(const ScDBData& rData);
200
    ScDBData(const OUString& rName, const ScDBData& rData);
201
    SC_DLLPUBLIC virtual ~ScDBData() override;
202
203
    virtual void Notify( const SfxHint& rHint ) override;
204
205
    ScDBData&   operator= (const ScDBData& rData) ;
206
207
    bool        operator== (const ScDBData& rData) const;
208
209
3.08k
    const OUString& GetName() const { return aName; }
210
38.7k
    const OUString& GetUpperName() const { return aUpper; }
211
270
    SCTAB       GetTab() const                  { return nTable; }
212
    void        GetArea(SCTAB& rTab, SCCOL& rCol1, SCROW& rRow1, SCCOL& rCol2, SCROW& rRow2) const;
213
    SC_DLLPUBLIC void GetArea(ScRange& rRange) const;
214
    void        SetArea(SCTAB nTab, SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2);
215
    void SetArea(ScRange const& rRange)
216
0
    {
217
0
        SetArea(rRange.aStart.Tab(), rRange.aStart.Col(), rRange.aStart.Row(),
218
0
                rRange.aEnd.Col(), rRange.aEnd.Row());
219
0
    }
220
    void        MoveTo(SCTAB nTab, SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2,
221
                       SCCOL nUpdateCol = -1);
222
0
    void        SetByRow(bool bByR)             { bByRow = bByR; }
223
1.11k
    bool        HasHeader() const               { return bHasHeader; }
224
973
    void        SetHeader(bool bHasH)           { bHasHeader = bHasH; }
225
256
    bool        HasTotals() const               { return bHasTotals; }
226
1.09k
    void        SetTotals(bool bTotals)         { bHasTotals = bTotals; }
227
258
    void        SetIndex(sal_uInt16 nInd)           { nIndex = nInd; }
228
4.04k
    sal_uInt16  GetIndex() const                { return nIndex; }
229
0
    bool        IsDoSize() const                { return bDoSize; }
230
0
    void        SetDoSize(bool bSet)            { bDoSize = bSet; }
231
0
    bool        IsKeepFmt() const               { return bKeepFmt; }
232
0
    void        SetKeepFmt(bool bSet)           { bKeepFmt = bSet; }
233
0
    bool        IsStripData() const             { return bStripData; }
234
0
    void        SetStripData(bool bSet)         { bStripData = bSet; }
235
238
    void        SetTableType(const OUString& sTableType) { aTableType = sTableType; }
236
0
    const OUString& GetTableType() const           { return aTableType; }
237
238
248
    void        SetContainer( ScDBDataContainerBase* pContainer ) { mpContainer = pContainer; }
239
    /** Returns header row range if has headers, else invalid range. */
240
    ScRange     GetHeaderArea() const;
241
    void        StartTableColumnNamesListener();
242
    void        EndTableColumnNamesListener();
243
    SC_DLLPUBLIC void SetTableColumnNames( ::std::vector< OUString >&& rNames );
244
0
    SC_DLLPUBLIC const ::std::vector< OUString >& GetTableColumnNames() const { return maTableColumnNames; }
245
    SC_DLLPUBLIC void SetTableColumnModel( TableColumnModel& rModel )
246
1.05k
    {
247
1.05k
        maTableColumnModel.push_back(std::move(rModel));
248
1.05k
    }
249
0
    SC_DLLPUBLIC const ::std::vector< TableColumnModel >& GetTableColumnModel() const { return maTableColumnModel; }
250
496
    bool        AreTableColumnNamesDirty() const { return mbTableColumnNamesDirty; }
251
252
    /** Refresh/update the column names with the header row's cell contents. */
253
    SC_DLLPUBLIC void RefreshTableColumnNames( ScDocument* pDoc );
254
255
    /** Refresh/update the column names with the header row's cell contents
256
        within the given range. */
257
    void RefreshTableColumnNames( ScDocument& rDoc, const ScRangeList& rRangeList );
258
259
    /** Finds the column named rName and returns the corresponding offset
260
        within the table.
261
        @returns -1 if not found.
262
263
        XXX NOTE: there is no refresh of names or anything implemented yet, use
264
        this only during document load time.
265
     */
266
    sal_Int32   GetColumnNameOffset( const OUString& rName ) const;
267
268
    /** Returns table column name if nCol is within column range and name
269
        is stored, else empty string. */
270
    const OUString & GetTableColumnName( SCCOL nCol ) const;
271
272
    OUString GetSourceString() const;
273
    OUString GetOperations() const;
274
275
    SC_DLLPUBLIC void GetSortParam(ScSortParam& rSortParam) const;
276
    SC_DLLPUBLIC void SetSortParam(const ScSortParam& rSortParam);
277
278
    /** Remember some more settings of ScSortParam, only to be called at
279
        anonymous DB ranges as it at least overwrites bHasHeader. */
280
    void        UpdateFromSortParam( const ScSortParam& rSortParam );
281
282
    SC_DLLPUBLIC void       GetQueryParam(ScQueryParam& rQueryParam) const;
283
    SC_DLLPUBLIC void       SetQueryParam(const ScQueryParam& rQueryParam);
284
    SC_DLLPUBLIC bool       GetAdvancedQuerySource(ScRange& rSource) const;
285
    SC_DLLPUBLIC void       SetAdvancedQuerySource(const ScRange* pSource);
286
287
    SC_DLLPUBLIC void       GetSubTotalParam(ScSubTotalParam& rSubTotalParam) const;
288
    SC_DLLPUBLIC void       SetSubTotalParam(const ScSubTotalParam& rSubTotalParam);
289
290
    // Total row param handling for Table Styles
291
    SC_DLLPUBLIC void       ImportTotalRowParam(ScSubTotalParam& rSubTotalParam,
292
                                                const std::vector<TableColumnAttributes>& rAttributesVector,
293
                                                formula::FormulaGrammar::Grammar eGrammar) const;
294
    SC_DLLPUBLIC void       CreateTotalRowParam(ScSubTotalParam& rSubTotalParam) const;
295
296
    SC_DLLPUBLIC std::vector<TableColumnAttributes>
297
                            GetTotalRowAttributes(formula::FormulaGrammar::Grammar eGrammar) const;
298
299
    OUString    GetSimpleSubTotalFunction(const ScTokenArray* pTokens, SCCOL nCol, SCROW nHeaderRow) const;
300
301
    void        GetImportParam(ScImportParam& rImportParam) const;
302
    void        SetImportParam(const ScImportParam& rImportParam);
303
304
    bool        IsDBAtCursor(SCCOL nCol, SCROW nRow, SCTAB nTab, ScDBDataPortion ePortion) const;
305
    bool        IsDBAtArea(SCTAB nTab, SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2) const;
306
307
    bool        HasImportParam() const;
308
    SC_DLLPUBLIC bool HasQueryParam() const;
309
    bool        HasSortParam() const;
310
    bool        HasSubTotalParam() const;
311
312
0
    bool        HasImportSelection() const      { return bDBSelection; }
313
0
    void        SetImportSelection(bool bSet)   { bDBSelection = bSet; }
314
315
6.27k
    bool        HasAutoFilter() const       { return bAutoFilter; }
316
466
    void        SetAutoFilter(bool bSet)    { bAutoFilter = bSet; }
317
318
0
    bool        IsModified() const          { return bModified; }
319
10
    void        SetModified(bool bMod)      { bModified = bMod; }
320
321
    void    UpdateMoveTab( SCTAB nOldPos, SCTAB nNewPos );
322
    bool    UpdateReference(const ScDocument& rDoc, UpdateRefMode eUpdateRefMode, SCCOL nCol1,
323
                            SCROW nRow1, SCTAB nTab1, SCCOL nCol2, SCROW nRow2, SCTAB nTab2,
324
                            SCCOL nDx, SCROW nDy, SCTAB nDz);
325
326
    void ExtendDataArea(const ScDocument& rDoc);
327
    void CalcSaveFilteredCount(SCSIZE nNonFilteredRowCount);
328
    void GetFilterSelCount(SCSIZE& nSelected, SCSIZE& nTotal);
329
330
    SC_DLLPUBLIC void SetTableStyleInfo(const ScTableStyleParam& rParams);
331
    SC_DLLPUBLIC const ScTableStyleParam* GetTableStyleInfo() const;
332
333
    static ScSubTotalFunc GetSubTotalFuncFromString(std::u16string_view sFunction);
334
    static OUString GetStringFromSubTotalFunc(ScSubTotalFunc eFunc);
335
336
private:
337
338
    void AdjustTableColumnNames( UpdateRefMode eUpdateRefMode, SCCOL nDx, SCCOL nCol1,
339
            SCCOL nOldCol1, SCCOL nOldCol2, SCCOL nNewCol1, SCCOL nNewCol2 );
340
    void InvalidateTableColumnNames( bool bSwapToEmptyNames );
341
};
342
343
class ScDBCollection
344
{
345
public:
346
    enum RangeType { GlobalNamed, GlobalAnonymous, SheetAnonymous };
347
348
    /**
349
     * Stores global named database ranges.
350
     */
351
    class SC_DLLPUBLIC NamedDBs final : public ScDBDataContainerBase
352
    {
353
        friend class ScDBCollection;
354
355
        typedef ::std::set<std::unique_ptr<ScDBData>, ScDBData::less> DBsType;
356
        DBsType m_DBs;
357
        ScDBCollection& mrParent;
358
        NamedDBs(ScDBCollection& rParent, ScDocument& rDoc);
359
        NamedDBs(const NamedDBs& r, ScDBCollection& rParent);
360
        NamedDBs(const NamedDBs&) = delete;
361
        virtual ~NamedDBs() override;
362
        NamedDBs & operator=(NamedDBs const&) = delete;
363
        void initInserted( ScDBData* p );
364
365
    public:
366
        typedef DBsType::iterator iterator;
367
        typedef DBsType::const_iterator const_iterator;
368
369
        iterator begin();
370
        iterator end();
371
        const_iterator begin() const;
372
        const_iterator end() const;
373
        ScDBData* findByIndex(sal_uInt16 nIndex);
374
        ScDBData* findByUpperName(const OUString& rName);
375
        iterator findByUpperName2(const OUString& rName);
376
        iterator findByPointer(const ScDBData* p);
377
        ScDBData* findByName(const OUString& rName);
378
379
        /** Takes ownership of p and attempts to insert it into the collection.
380
            Deletes p if it could not be inserted, i.e. duplicate name.
381
            @return <TRUE/> if inserted, else <FALSE/>.
382
         */
383
        bool insert(std::unique_ptr<ScDBData> p);
384
385
        iterator erase(const iterator& itr);
386
        bool empty() const;
387
        size_t size() const;
388
        bool operator== (const NamedDBs& r) const;
389
    };
390
391
    /**
392
     * Stores global anonymous database ranges.
393
     */
394
    class AnonDBs
395
    {
396
        typedef ::std::vector<std::unique_ptr<ScDBData>> DBsType;
397
        DBsType m_DBs;
398
399
        AnonDBs& operator=(AnonDBs const&) = delete;
400
401
    public:
402
        AnonDBs();
403
        AnonDBs(AnonDBs const&);
404
405
        typedef DBsType::iterator iterator;
406
        typedef DBsType::const_iterator const_iterator;
407
408
        iterator begin();
409
        iterator end();
410
        const_iterator begin() const;
411
        const_iterator end() const;
412
        const ScDBData* findAtCursor(SCCOL nCol, SCROW nRow, SCTAB nTab, ScDBDataPortion ePortion) const;
413
        const ScDBData* findByRange(const ScRange& rRange) const;
414
        void deleteOnTab(SCTAB nTab);
415
        ScDBData* getByRange(const ScRange& rRange);
416
        void insert(ScDBData* p);
417
        iterator erase(const iterator& itr);
418
        bool empty() const;
419
        bool has( const ScDBData* p ) const;
420
        bool operator== (const AnonDBs& r) const;
421
    };
422
423
private:
424
    Link<Timer *, void> aRefreshHandler;
425
    ScDocument& rDoc;
426
    sal_uInt16 nEntryIndex;         ///< counter for unique indices
427
    NamedDBs maNamedDBs;
428
    AnonDBs maAnonDBs;
429
430
public:
431
    ScDBCollection(ScDocument& rDocument);
432
    ScDBCollection(const ScDBCollection& r);
433
434
2.23M
    NamedDBs& getNamedDBs() { return maNamedDBs;}
435
1.95k
    const NamedDBs& getNamedDBs() const { return maNamedDBs;}
436
437
0
    AnonDBs& getAnonDBs() { return maAnonDBs;}
438
0
    const AnonDBs& getAnonDBs() const { return maAnonDBs;}
439
440
    const ScDBData* GetTableDBAtCursor(SCCOL nCol, SCROW nRow, SCTAB nTab, ScDBDataPortion ePortion) const;
441
    ScDBData* GetTableDBAtCursor(SCCOL nCol, SCROW nRow, SCTAB nTab, ScDBDataPortion ePortion);
442
    const ScDBData* GetDBAtCursor(SCCOL nCol, SCROW nRow, SCTAB nTab, ScDBDataPortion ePortion) const;
443
    ScDBData* GetDBAtCursor(SCCOL nCol, SCROW nRow, SCTAB nTab, ScDBDataPortion ePortion);
444
    const ScDBData* GetDBAtArea(SCTAB nTab, SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2) const;
445
    SC_DLLPUBLIC ScDBData* GetDBAtArea(SCTAB nTab, SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2);
446
    SC_DLLPUBLIC ScDBData* GetDBNearCursor(SCCOL nCol, SCROW nRow, SCTAB nTab );
447
    SC_DLLPUBLIC std::vector<ScDBData*> GetAllDBsFromTab(SCTAB nTab);
448
    std::vector<const ScDBData*> GetAllNamedDBsInArea(SCCOL nCol1, SCROW nRow1, SCCOL nCol2,
449
                                                      SCROW nRow2, SCTAB nTab) const;
450
451
    void RefreshDirtyTableColumnNames();
452
453
    void    DeleteOnTab( SCTAB nTab );
454
    void    UpdateReference(UpdateRefMode eUpdateRefMode,
455
                                SCCOL nCol1, SCROW nRow1, SCTAB nTab1,
456
                                SCCOL nCol2, SCROW nRow2, SCTAB nTab2,
457
                                SCCOL nDx, SCROW nDy, SCTAB nDz);
458
    void    UpdateMoveTab( SCTAB nOldPos, SCTAB nNewPos );
459
    void    CopyToTable(SCTAB nOldPos, SCTAB nNewPos);
460
461
    void            SetRefreshHandler( const Link<Timer *, void>& rLink )
462
28.2k
                        { aRefreshHandler = rLink; }
463
0
    const Link<Timer *, void>& GetRefreshHandler() const { return aRefreshHandler; }
464
465
    SC_DLLPUBLIC bool empty() const;
466
    bool operator== (const ScDBCollection& r) const;
467
};
468
469
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */