summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDennis Francis <dennis.francis@collabora.com>2020-05-05 01:55:37 +0530
committerDennis Francis <dennis.francis@collabora.com>2020-05-25 00:39:51 +0530
commitcced75dfbb8d48e855e3c110807d3c95393e94b1 (patch)
treebbf7174e22bb8230f34cef055ee62a18ba6a85d7
parent552db9165faaa8425f2b8cbf71bbef1438bb243a (diff)
Introduce ITiledRenderable::getSheetGeometryData()
ITiledRenderable::getSheetGeometryData(bool bColumns, bool bRows, bool bSizes, bool bHidden, bool bFiltered, bool bGroups) and implement it for the Calc derivation (ScModelObj). The aim is to use it actively in LOOL instead of the interface: ITiledRenderable::getRowColumnHeaders(const tools::Rectangle& /*rRectangle*/) This is used by the LOOL to fetch the sheet geometry data for just the current view-area in the clients, so LOOL queries this everytime some client's view-area changes. Like the existing interface, the new one will provide all 'kinds' of sheet geometry info [col/row sizes(twips), hidden/filtered and grouping]. But the difference is, it generates data for the whole sheet (not view-area specific). So the method need not be queried every time the view area changes in the LOOL clients, and more importantly it enables the clients to locate any cell at any zoom level without any further help from the core. This means core needn't send various client(zoom) specific positioning messages in pixel aligned twips. It just can send all positioning messages in print twips uniformly to all clients. Change-Id: Ib6aee9a0c92746b1576ed244e98cb54b572778c0
-rw-r--r--desktop/source/lib/init.cxx67
-rw-r--r--include/vcl/ITiledRenderable.hxx25
-rw-r--r--sc/inc/document.hxx19
-rw-r--r--sc/inc/docuno.hxx4
-rw-r--r--sc/inc/olinetab.hxx6
-rw-r--r--sc/inc/segmenttree.hxx7
-rw-r--r--sc/inc/table.hxx16
-rw-r--r--sc/source/core/data/document10.cxx9
-rw-r--r--sc/source/core/data/olinetab.cxx27
-rw-r--r--sc/source/core/data/segmenttree.cxx59
-rw-r--r--sc/source/core/data/table7.cxx105
-rw-r--r--sc/source/ui/inc/tabview.hxx4
-rw-r--r--sc/source/ui/unoobj/docuno.cxx15
-rw-r--r--sc/source/ui/view/tabview.cxx77
14 files changed, 440 insertions, 0 deletions
diff --git a/desktop/source/lib/init.cxx b/desktop/source/lib/init.cxx
index 373deb3c7c53..44f28454c8f8 100644
--- a/desktop/source/lib/init.cxx
+++ b/desktop/source/lib/init.cxx
@@ -4708,6 +4708,7 @@ static char* doc_getCommandValues(LibreOfficeKitDocument* pThis, const char* pCo
OString aCommand(pCommand);
static const OString aViewRowColumnHeaders(".uno:ViewRowColumnHeaders");
+ static const OString aSheetGeometryData(".uno:SheetGeometryData");
static const OString aCellCursor(".uno:CellCursor");
static const OString aFontSubset(".uno:FontSubset&name=");
@@ -4805,6 +4806,72 @@ static char* doc_getCommandValues(LibreOfficeKitDocument* pThis, const char* pCo
else
return convertOUString(aHeaders);
}
+ else if (aCommand.startsWith(aSheetGeometryData))
+ {
+ ITiledRenderable* pDoc = getTiledRenderable(pThis);
+ if (!pDoc)
+ {
+ SetLastExceptionMsg("Document doesn't support tiled rendering");
+ return nullptr;
+ }
+
+ bool bColumns = true;
+ bool bRows = true;
+ bool bSizes = true;
+ bool bHidden = true;
+ bool bFiltered = true;
+ bool bGroups = true;
+ if (aCommand.getLength() > aSheetGeometryData.getLength())
+ {
+ bColumns = bRows = bSizes = bHidden = bFiltered = bGroups = false;
+
+ OString aArguments = aCommand.copy(aSheetGeometryData.getLength() + 1);
+ sal_Int32 nParamIndex = 0;
+ do
+ {
+ OString aParamToken = aArguments.getToken(0, '&', nParamIndex);
+ sal_Int32 nIndex = 0;
+ OString aKey;
+ OString aValue;
+ do
+ {
+ OString aToken = aParamToken.getToken(0, '=', nIndex);
+ if (!aKey.getLength())
+ aKey = aToken;
+ else
+ aValue = aToken;
+
+ } while (nIndex >= 0);
+
+ bool bEnableFlag = aValue.isEmpty() ||
+ aValue.equalsIgnoreAsciiCase("true") || aValue.toInt32() > 0;
+ if (!bEnableFlag)
+ continue;
+
+ if (aKey == "columns")
+ bColumns = true;
+ else if (aKey == "rows")
+ bRows = true;
+ else if (aKey == "sizes")
+ bSizes = true;
+ else if (aKey == "hidden")
+ bHidden = true;
+ else if (aKey == "filtered")
+ bFiltered = true;
+ else if (aKey == "groups")
+ bGroups = true;
+
+ } while (nParamIndex >= 0);
+ }
+
+ OString aGeomDataStr
+ = pDoc->getSheetGeometryData(bColumns, bRows, bSizes, bHidden, bFiltered, bGroups);
+
+ if (aGeomDataStr.isEmpty())
+ return nullptr;
+
+ return convertOString(aGeomDataStr);
+ }
else if (aCommand.startsWith(aCellCursor))
{
ITiledRenderable* pDoc = getTiledRenderable(pThis);
diff --git a/include/vcl/ITiledRenderable.hxx b/include/vcl/ITiledRenderable.hxx
index 9e995216e573..2c716098630c 100644
--- a/include/vcl/ITiledRenderable.hxx
+++ b/include/vcl/ITiledRenderable.hxx
@@ -178,6 +178,31 @@ public:
}
/**
+ * Generates a serialization of the active (Calc document) sheet's geometry data.
+ *
+ * @param bColumns - if true, the column widths/hidden/filtered/groups data
+ * are included depending on the settings of the flags bSizes, bHidden,
+ * bFiltered and bGroups.
+ * @param bRows - if true, the row heights/hidden/filtered/groups data
+ * are included depending on the settings of the flags bSizes, bHidden,
+ * bFiltered and bGroups.
+ * @bSizes - if true, the column-widths and/or row-heights data (represented as a list of spans)
+ * are included depending on the settings of the flags bColumns and bRows.
+ * @bHidden - if true, the hidden columns and/or rows data (represented as a list of spans)
+ * are included depending on the settings of the flags bColumns and bRows.
+ * @bFiltered - if true, the filtered columns and/or rows data (represented as a list of spans)
+ * are included depending on the settings of the flags bColumns and bRows.
+ * @bGroups - if true, the column grouping and/or row grouping data
+ * are included depending on the settings of the flags bColumns and bRows.
+ * @return serialization of the active sheet's geometry data as OString.
+ */
+ virtual OString getSheetGeometryData(bool /*bColumns*/, bool /*bRows*/, bool /*bSizes*/,
+ bool /*bHidden*/, bool /*bFiltered*/, bool /*bGroups*/)
+ {
+ return "";
+ }
+
+ /**
* Get position and size of cell cursor in Calc - as JSON in the
* current' views' co-ordinate system.
* (This could maybe also be used for tables in Writer/Impress in future?)
diff --git a/sc/inc/document.hxx b/sc/inc/document.hxx
index 6e277f10a284..2376e3fdad4d 100644
--- a/sc/inc/document.hxx
+++ b/sc/inc/document.hxx
@@ -260,6 +260,15 @@ enum RangeNameScope
SHEET // with two scope on Manage Names dialog.
};
+/// Represents the type of sheet geometry data.
+enum class SheetGeomType
+{
+ SIZES, // Column widths or row heights.
+ HIDDEN, // Hidden columns/rows.
+ FILTERED, // Filtered columns/rows.
+ GROUPS // Grouping of columns/rows.
+};
+
struct ScDocStat
{
OUString aDocName;
@@ -2512,6 +2521,16 @@ public:
bool IsInDocShellRecalc() const { return mbDocShellRecalc; }
void SetDocShellRecalc(bool bSet) { mbDocShellRecalc = bSet; }
+ /**
+ * Serializes the specified sheet's geometry data.
+ *
+ * @param nTab is the index of the sheet to operate on.
+ * @param bColumns - if true it dumps the data for columns, else it does for rows.
+ * @param eGeomType indicates the type of data to be dumped for rows/columns.
+ * @return the serialization of the specified sheet's geometry data as an OString.
+ */
+ OString dumpSheetGeomData(SCTAB nTab, bool bColumns, SheetGeomType eGeomType);
+
private:
/**
diff --git a/sc/inc/docuno.hxx b/sc/inc/docuno.hxx
index 7c9c87a4f109..329571dfc056 100644
--- a/sc/inc/docuno.hxx
+++ b/sc/inc/docuno.hxx
@@ -368,6 +368,10 @@ public:
/// @see vcl::ITiledRenderable::getRowColumnHeaders().
virtual OUString getRowColumnHeaders(const tools::Rectangle& rRectangle) override;
+ /// @see vcl::ITiledRenderable::getSheetGeometryData().
+ virtual OString getSheetGeometryData(bool bColumns, bool bRows, bool bSizes, bool bHidden,
+ bool bFiltered, bool bGroups) override;
+
/// @see vcl::ITiledRenderable::getCellCursor().
virtual OString getCellCursor() override;
diff --git a/sc/inc/olinetab.hxx b/sc/inc/olinetab.hxx
index a25064d86c4e..cdaa74d19a93 100644
--- a/sc/inc/olinetab.hxx
+++ b/sc/inc/olinetab.hxx
@@ -59,6 +59,8 @@ public:
void SetPosSize( SCCOLROW nNewPos, SCSIZE nNewSize );
void SetHidden( bool bNewHidden );
void SetVisible( bool bNewVisible );
+
+ OString dumpAsString() const;
};
class ScOutlineCollection
@@ -83,6 +85,8 @@ public:
bool empty() const;
iterator FindStart(SCCOLROW nMinStart);
+
+ OString dumpAsString() const;
};
class SC_DLLPUBLIC ScOutlineArray
@@ -138,6 +142,8 @@ public:
void finalizeImport(const ScTable& rTable);
void RemoveAll();
+
+ OString dumpAsString() const;
};
class ScOutlineTable
diff --git a/sc/inc/segmenttree.hxx b/sc/inc/segmenttree.hxx
index 9d772a0b4b46..f37a3d3facd6 100644
--- a/sc/inc/segmenttree.hxx
+++ b/sc/inc/segmenttree.hxx
@@ -21,6 +21,7 @@
#define INCLUDED_SC_INC_SEGMENTTREE_HXX
#include "types.hxx"
+#include <rtl/string.hxx>
#include <memory>
@@ -76,6 +77,8 @@ public:
SCROW findLastTrue() const;
+ OString dumpAsString();
+
private:
::std::unique_ptr<ScFlatBoolSegmentsImpl> mpImpl;
};
@@ -99,6 +102,8 @@ public:
void removeSegment(SCCOL nCol1, SCCOL nCol2);
void insertSegment(SCCOL nCol, SCCOL nSize);
+ OString dumpAsString();
+
private:
::std::unique_ptr<ScFlatBoolSegmentsImpl> mpImpl;
};
@@ -147,6 +152,8 @@ public:
void enableTreeSearch(bool bEnable);
+ OString dumpAsString();
+
private:
::std::unique_ptr<ScFlatUInt16SegmentsImpl> mpImpl;
};
diff --git a/sc/inc/table.hxx b/sc/inc/table.hxx
index 12f8bb87bc89..5ffd70c77541 100644
--- a/sc/inc/table.hxx
+++ b/sc/inc/table.hxx
@@ -1081,6 +1081,15 @@ public:
SCCOL ClampToAllocatedColumns(SCCOL nCol) const { return std::min(nCol, static_cast<SCCOL>(aCol.size() - 1)); }
SCCOL GetAllocatedColumnsCount() const { return aCol.size(); }
+ /**
+ * Serializes the sheet's geometry data.
+ *
+ * @param bColumns - if true it dumps the data for columns, else it does for rows.
+ * @param eGeomType indicates the type of data to be dumped for rows/columns.
+ * @return the serialization of the sheet's geometry data as an OString.
+ */
+ OString dumpSheetGeomData(bool bColumns, SheetGeomType eGeomType);
+
private:
void FillFormulaVertical(
@@ -1240,6 +1249,13 @@ private:
void EndListeningGroup( sc::EndListeningContext& rCxt, const SCCOL nCol, SCROW nRow );
void SetNeedsListeningGroup( SCCOL nCol, SCROW nRow );
+ /// Returns list-of-spans representation of the column-widths/row-heights in twips encoded as an OString.
+ OString dumpColumnRowSizes(bool bColumns);
+ /// Returns list-of-spans representation of hidden/filtered states of columns/rows encoded as an OString.
+ OString dumpHiddenFiltered(bool bColumns, bool bHidden);
+ /// Returns list-of-spans representation of the column/row groupings encoded as an OString.
+ OString dumpColumnRowGroups(bool bColumns) const;
+
/**
* Use this to iterate through non-empty visible cells in a single column.
*/
diff --git a/sc/source/core/data/document10.cxx b/sc/source/core/data/document10.cxx
index b04ac76e06ab..f32e5f8a03f2 100644
--- a/sc/source/core/data/document10.cxx
+++ b/sc/source/core/data/document10.cxx
@@ -977,4 +977,13 @@ void ScDocument::RestoreTabFromCache(SCTAB nTab, SvStream& rStrm)
pTab->RestoreFromCache(rStrm);
}
+OString ScDocument::dumpSheetGeomData(SCTAB nTab, bool bColumns, SheetGeomType eGeomType)
+{
+ ScTable* pTab = FetchTable(nTab);
+ if (!pTab)
+ return "";
+
+ return pTab->dumpSheetGeomData(bColumns, eGeomType);
+}
+
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sc/source/core/data/olinetab.cxx b/sc/source/core/data/olinetab.cxx
index a7e66c8f8d55..19553c52cdbc 100644
--- a/sc/source/core/data/olinetab.cxx
+++ b/sc/source/core/data/olinetab.cxx
@@ -81,6 +81,13 @@ void ScOutlineEntry::SetVisible( bool bNewVisible )
bVisible = bNewVisible;
}
+OString ScOutlineEntry::dumpAsString() const
+{
+ const char* pSep = ":";
+ return OString::number(nStart) + pSep + OString::number(nSize) +
+ pSep + OString::number(bHidden) + pSep + OString::number(bVisible);
+}
+
ScOutlineCollection::ScOutlineCollection() {}
size_t ScOutlineCollection::size() const
@@ -134,6 +141,16 @@ ScOutlineCollection::iterator ScOutlineCollection::FindStart(SCCOLROW nMinStart)
return m_Entries.lower_bound(nMinStart);
}
+OString ScOutlineCollection::dumpAsString() const
+{
+ OString aOutput;
+ const char* pGroupEntrySep = ",";
+ for (const auto& rKeyValuePair : m_Entries)
+ aOutput += rKeyValuePair.second.dumpAsString() + pGroupEntrySep;
+
+ return aOutput;
+}
+
ScOutlineArray::ScOutlineArray() :
nDepth(0) {}
@@ -725,6 +742,16 @@ void ScOutlineArray::finalizeImport(const ScTable& rTable)
}
}
+OString ScOutlineArray::dumpAsString() const
+{
+ OString aOutput;
+ const char* pLevelSep = " ";
+ for (const auto& rCollection : aCollections)
+ aOutput += rCollection.dumpAsString() + pLevelSep;
+
+ return aOutput;
+}
+
ScOutlineTable::ScOutlineTable()
{
}
diff --git a/sc/source/core/data/segmenttree.cxx b/sc/source/core/data/segmenttree.cxx
index 254f0f875571..c33ff97e6b72 100644
--- a/sc/source/core/data/segmenttree.cxx
+++ b/sc/source/core/data/segmenttree.cxx
@@ -416,6 +416,27 @@ SCROW ScFlatBoolRowSegments::findLastTrue() const
return mpImpl->findLastTrue(false);
}
+OString ScFlatBoolRowSegments::dumpAsString()
+{
+ OString aOutput;
+ OString aSegment;
+ RangeData aRange;
+ SCROW nRow = 0;
+ while (getRangeData(nRow, aRange))
+ {
+ if (!nRow)
+ aSegment = OString::number(aRange.mbValue) + ":";
+ else
+ aSegment.clear();
+
+ aSegment += OString::number(aRange.mnRow2) + " ";
+ aOutput += aSegment;
+ nRow = aRange.mnRow2 + 1;
+ }
+
+ return aOutput;
+}
+
ScFlatBoolColSegments::ScFlatBoolColSegments(SCCOL nMaxCol) :
mpImpl(new ScFlatBoolSegmentsImpl(nMaxCol))
{
@@ -462,6 +483,27 @@ void ScFlatBoolColSegments::insertSegment(SCCOL nCol, SCCOL nSize)
mpImpl->insertSegment(static_cast<SCCOLROW>(nCol), static_cast<SCCOLROW>(nSize), true/*bSkipStartBoundary*/);
}
+OString ScFlatBoolColSegments::dumpAsString()
+{
+ OString aOutput;
+ OString aSegment;
+ RangeData aRange;
+ SCCOL nCol = 0;
+ while (getRangeData(nCol, aRange))
+ {
+ if (!nCol)
+ aSegment = OString::number(aRange.mbValue) + ":";
+ else
+ aSegment.clear();
+
+ aSegment += OString::number(aRange.mnCol2) + " ";
+ aOutput += aSegment;
+ nCol = aRange.mnCol2 + 1;
+ }
+
+ return aOutput;
+}
+
ScFlatUInt16RowSegments::ForwardIterator::ForwardIterator(ScFlatUInt16RowSegments& rSegs) :
mrSegs(rSegs), mnCurPos(0), mnLastPos(-1), mnCurValue(0)
{
@@ -554,4 +596,21 @@ void ScFlatUInt16RowSegments::setValueIf(SCROW nRow1, SCROW nRow2, sal_uInt16 nV
mpImpl->setValueIf(static_cast<SCCOLROW>(nRow1), static_cast<SCCOLROW>(nRow2), nValue, rPredicate);
}
+OString ScFlatUInt16RowSegments::dumpAsString()
+{
+ OString aOutput;
+ OString aSegment;
+ RangeData aRange;
+ SCROW nRow = 0;
+ while (getRangeData(nRow, aRange))
+ {
+ aSegment = OString::number(aRange.mnValue) + ":" +
+ OString::number(aRange.mnRow2) + " ";
+ aOutput += aSegment;
+ nRow = aRange.mnRow2 + 1;
+ }
+
+ return aOutput;
+}
+
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sc/source/core/data/table7.cxx b/sc/source/core/data/table7.cxx
index 38f1d02e3fd7..1e8721615821 100644
--- a/sc/source/core/data/table7.cxx
+++ b/sc/source/core/data/table7.cxx
@@ -479,4 +479,109 @@ void ScTable::RestoreFromCache(SvStream& rStrm)
}
}
+OString ScTable::dumpSheetGeomData(bool bColumns, SheetGeomType eGeomType)
+{
+ switch (eGeomType)
+ {
+ case SheetGeomType::SIZES:
+ // returns a non-empty space separated list of spans with trailing space.
+ // The format of the span is <size of any row/col in the span in print twips>:<last row/col of the span>
+ // Example (for columns with three spans if MAXCOL is 1023): "1280:3 1049:50 1280:1023"
+ return dumpColumnRowSizes(bColumns);
+ case SheetGeomType::HIDDEN:
+ // returns a non-empty space separated list of spans with trailing space.
+ // The format of the span is:
+ // 1) First span: <1 (span is hidden) / 0 (not hidden)>:<last row/col of the span>
+ // 2) Rest of the spans: <last row/col of the span>
+ // The hidden state of the spans after the first can be inferred from the first span's flag as no adjacent
+ // spans can have the same state by definition of span.
+ return dumpHiddenFiltered(bColumns, /*bHidden*/ true);
+ case SheetGeomType::FILTERED:
+ // has exactly the same format as 'hidden'.
+ return dumpHiddenFiltered(bColumns, /*bHidden*/ false);
+ case SheetGeomType::GROUPS:
+ // returns a space separated list of 'levels' with trailing space.
+ // A 'level' is a comma separated list of groups(outline entries) with trailing comma.
+ // format of a group is:
+ // <start row/col of group>:<number of rows/cols in the group>:<1/0(group is hidden?)>:<1/0(control is visible?)>
+ return dumpColumnRowGroups(bColumns);
+ default:
+ ;
+ }
+
+ return "";
+}
+
+OString ScTable::dumpColumnRowSizes(bool bColumns)
+{
+ // If the data-structures are not available, just report that all
+ // rows/cols have the default sizes.
+ static const OString aDefaultForCols
+ = OString::number(STD_COL_WIDTH) + ":" + OString::number(MAXCOL) + " ";
+ static const OString aDefaultForRows
+ = OString::number(ScGlobal::nStdRowHeight) + ":" + OString::number(MAXROW) + " ";
+
+ // ScCompressedArray is a template class and we don't want to impose
+ // the restriction that its value type should be string serializable,
+ // instead just operate on the specialized object.
+ typedef ScCompressedArray<SCCOL, sal_uInt16> ColWidthsType;
+ auto dumpColWidths = [](const ColWidthsType& rWidths) -> OString {
+ OString aOutput;
+ OString aSegment;
+ SCCOL nStartCol = 0;
+ const SCCOL nMaxCol = std::min(rWidths.GetLastPos(), MAXCOL);
+ size_t nDummy = 0;
+ while (nStartCol <= nMaxCol)
+ {
+ SCCOL nEndCol;
+ sal_uInt16 nWidth = rWidths.GetValue(nStartCol, nDummy, nEndCol);
+ // The last span nEndCol is always MAXCOL+1 for some reason, and we don't want that.
+ if (nEndCol > nMaxCol)
+ nEndCol = nMaxCol;
+ aSegment = OString::number(nWidth) + ":" + OString::number(nEndCol);
+ aSegment += " ";
+ aOutput += aSegment;
+ nStartCol = nEndCol + 1;
+ }
+
+ return aOutput;
+ };
+
+ if (bColumns)
+ return mpColWidth ? dumpColWidths(*mpColWidth) : aDefaultForCols;
+
+ return mpRowHeights ? mpRowHeights->dumpAsString() : aDefaultForRows;
+}
+
+OString ScTable::dumpHiddenFiltered(bool bColumns, bool bHidden)
+{
+ // defaults to no hidden/filtered row/cols.
+ static const OString aDefaultForCols = "0:" + OString::number(MAXCOL) + " ";
+ static const OString aDefaultForRows = "0:" + OString::number(MAXROW) + " ";
+
+ if (bHidden)
+ {
+ if (bColumns)
+ return mpHiddenCols ? mpHiddenCols->dumpAsString() : aDefaultForCols;
+
+ return mpHiddenRows ? mpHiddenRows->dumpAsString() : aDefaultForRows;
+ }
+
+ if (bColumns)
+ return mpFilteredCols ? mpFilteredCols->dumpAsString() : aDefaultForCols;
+
+ return mpFilteredRows ? mpFilteredRows->dumpAsString() : aDefaultForRows;
+}
+
+OString ScTable::dumpColumnRowGroups(bool bColumns) const
+{
+ if (!pOutlineTable)
+ return "";
+
+ if (bColumns)
+ return pOutlineTable->GetColArray().dumpAsString();
+
+ return pOutlineTable->GetRowArray().dumpAsString();
+}
+
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sc/source/ui/inc/tabview.hxx b/sc/source/ui/inc/tabview.hxx
index a46c76666145..873d05047e46 100644
--- a/sc/source/ui/inc/tabview.hxx
+++ b/sc/source/ui/inc/tabview.hxx
@@ -592,6 +592,10 @@ public:
void SetAutoSpellData( SCCOL nPosX, SCROW nPosY, const std::vector<editeng::MisspellRanges>* pRanges );
/// @see ScModelObj::getRowColumnHeaders().
OUString getRowColumnHeaders(const tools::Rectangle& rRectangle);
+ /// @see ScModelObj::getSheetGeometryData()
+ OString getSheetGeometryData(bool bColumns, bool bRows, bool bSizes, bool bHidden,
+ bool bFiltered, bool bGroups);
+
static void OnLOKNoteStateChanged(const ScPostIt* pNote);
SCROW GetLOKStartHeaderRow() const { return mnLOKStartHeaderRow; }
diff --git a/sc/source/ui/unoobj/docuno.cxx b/sc/source/ui/unoobj/docuno.cxx
index 2a4153756eb1..5d4fb17eb0fd 100644
--- a/sc/source/ui/unoobj/docuno.cxx
+++ b/sc/source/ui/unoobj/docuno.cxx
@@ -909,6 +909,21 @@ OUString ScModelObj::getRowColumnHeaders(const tools::Rectangle& rRectangle)
return pTabView->getRowColumnHeaders(rRectangle);
}
+OString ScModelObj::getSheetGeometryData(bool bColumns, bool bRows, bool bSizes, bool bHidden,
+ bool bFiltered, bool bGroups)
+{
+ ScViewData* pViewData = ScDocShell::GetViewData();
+
+ if (!pViewData)
+ return "";
+
+ ScTabView* pTabView = pViewData->GetView();
+ if (!pTabView)
+ return "";
+
+ return pTabView->getSheetGeometryData(bColumns, bRows, bSizes, bHidden, bFiltered, bGroups);
+}
+
OString ScModelObj::getCellCursor()
{
SolarMutexGuard aGuard;
diff --git a/sc/source/ui/view/tabview.cxx b/sc/source/ui/view/tabview.cxx
index d8bd7996f4ae..3e2f2fa3bdf5 100644
--- a/sc/source/ui/view/tabview.cxx
+++ b/sc/source/ui/view/tabview.cxx
@@ -49,6 +49,9 @@
#include <LibreOfficeKit/LibreOfficeKitEnums.h>
#include <sfx2/lokhelper.hxx>
+#include <boost/property_tree/ptree.hpp>
+#include <boost/property_tree/json_parser.hpp>
+
#include <com/sun/star/sheet/DataPilotFieldOrientation.hpp>
#include <algorithm>
@@ -2757,4 +2760,78 @@ OUString ScTabView::getRowColumnHeaders(const tools::Rectangle& rRectangle)
return sRet;
}
+OString ScTabView::getSheetGeometryData(bool bColumns, bool bRows, bool bSizes, bool bHidden,
+ bool bFiltered, bool bGroups)
+{
+ boost::property_tree::ptree aTree;
+ aTree.put("commandName", ".uno:SheetGeometryData");
+
+ auto getJSONString = [](const boost::property_tree::ptree& rTree) {
+ std::stringstream aStream;
+ boost::property_tree::write_json(aStream, rTree);
+ return aStream.str();
+ };
+
+ ScDocument* pDoc = aViewData.GetDocument();
+ if (!pDoc)
+ return getJSONString(aTree).c_str();
+
+ if ((!bSizes && !bHidden && !bFiltered && !bGroups) ||
+ (!bColumns && !bRows))
+ {
+ return getJSONString(aTree).c_str();
+ }
+
+ struct GeomEntry
+ {
+ SheetGeomType eType;
+ const char* pKey;
+ bool bEnabled;
+ };
+
+ const GeomEntry aGeomEntries[] = {
+ { SheetGeomType::SIZES, "sizes", bSizes },
+ { SheetGeomType::HIDDEN, "hidden", bHidden },
+ { SheetGeomType::FILTERED, "filtered", bFiltered },
+ { SheetGeomType::GROUPS, "groups", bGroups }
+ };
+
+ struct DimensionEntry
+ {
+ const char* pKey;
+ bool bDimIsCol;
+ bool bEnabled;
+ };
+
+ const DimensionEntry aDimEntries[] = {
+ { "columns", true, bColumns },
+ { "rows", false, bRows }
+ };
+
+ SCTAB nTab = aViewData.GetTabNo();
+
+ for (const auto& rDimEntry : aDimEntries)
+ {
+ if (!rDimEntry.bEnabled)
+ continue;
+
+ bool bDimIsCol = rDimEntry.bDimIsCol;
+
+ boost::property_tree::ptree aDimTree;
+ for (const auto& rGeomEntry : aGeomEntries)
+ {
+ if (!rGeomEntry.bEnabled)
+ continue;
+
+ OString aGeomDataEncoding = pDoc->dumpSheetGeomData(nTab, bDimIsCol, rGeomEntry.eType);
+ // TODO: Investigate if we can avoid the copy of the 'value' string in put().
+ aDimTree.put(rGeomEntry.pKey, aGeomDataEncoding.getStr());
+ }
+
+ aTree.add_child(rDimEntry.pKey, aDimTree);
+ }
+
+ return getJSONString(aTree).c_str();
+}
+
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */