summaryrefslogtreecommitdiff
path: root/sc
diff options
context:
space:
mode:
authorSzymon Kłos <szymon.klos@collabora.com>2023-09-13 14:57:23 +0200
committerCaolán McNamara <caolan.mcnamara@collabora.com>2023-09-18 17:45:47 +0200
commitcea900fe9864bbc5314415cb369fc7b6111cd050 (patch)
treebd948b6ccbed62e446509e52aec3829a962bc63a /sc
parentd19fb1dd668473f2d4f8dbde8bac1fcb34042a6a (diff)
Schedule conditional formating repaint after filtering is completed
When we have sheet with lots of data with applied conditional formatting and that data is used with autofilter feature - filtering is very slow. That was caused by repaints synchronously called on every row show/hide. ScConditionalFormat::DoRepaint() called by ScFormulaListener callback ... ScDocument::Broadcast ScColumn::BroadcastRows ScTable::SetRowHidden ScTable::DBShowRows This patch schedules repaint in the Idle so we do that after all changes are already applied. Change-Id: If0876ada0f336a41b69560db6a581d6e24d7ac16 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/157016 Tested-by: Jenkins Reviewed-by: Caolán McNamara <caolan.mcnamara@collabora.com>
Diffstat (limited to 'sc')
-rw-r--r--sc/inc/conditio.hxx20
-rw-r--r--sc/qa/unit/subsequent_filters_test3.cxx5
-rw-r--r--sc/source/core/data/conditio.cxx15
3 files changed, 35 insertions, 5 deletions
diff --git a/sc/inc/conditio.hxx b/sc/inc/conditio.hxx
index 47f5fdb3addb..8e5af1dd3c3c 100644
--- a/sc/inc/conditio.hxx
+++ b/sc/inc/conditio.hxx
@@ -40,6 +40,7 @@
#include <memory>
#include <set>
+class RepaintInIdle;
class ScFormulaCell;
class ScTokenArray;
struct ScRefCellValue;
@@ -442,6 +443,8 @@ private:
};
mutable std::unique_ptr<ScConditionEntryCache> mpCache;
+
+ std::unique_ptr<RepaintInIdle> mpRepaintTask;
};
// single condition entry for conditional formatting
@@ -605,6 +608,23 @@ public:
void CalcAll();
};
+class RepaintInIdle final : public Idle
+{
+ ScConditionalFormat* mpCondFormat;
+
+public:
+ RepaintInIdle(ScConditionalFormat* pCondFormat)
+ : Idle("Contitional Format Repaint Idle")
+ , mpCondFormat(pCondFormat)
+ {}
+
+ void Invoke() override
+ {
+ if (mpCondFormat)
+ mpCondFormat->DoRepaint();
+ }
+};
+
struct CompareScConditionalFormat
{
using is_transparent = void;
diff --git a/sc/qa/unit/subsequent_filters_test3.cxx b/sc/qa/unit/subsequent_filters_test3.cxx
index ff19d3d55c3c..3a46b9926bf6 100644
--- a/sc/qa/unit/subsequent_filters_test3.cxx
+++ b/sc/qa/unit/subsequent_filters_test3.cxx
@@ -19,6 +19,7 @@
#include <svx/xflclit.hxx>
#include <svx/xflgrit.hxx>
#include <svx/xflhtit.hxx>
+#include <vcl/scheduler.hxx>
#include <editeng/borderline.hxx>
#include <editeng/lineitem.hxx>
#include <dbdata.hxx>
@@ -419,6 +420,8 @@ CPPUNIT_TEST_FIXTURE(ScFiltersTest3, testCondFormatFormulaListenerXLSX)
pDoc->SetDocVisible(true);
pDoc->SetValue(0, 0, 0, 2.0);
+ Scheduler::ProcessEventsToIdle();
+
CPPUNIT_ASSERT(aListener.mbCalled);
}
@@ -439,6 +442,8 @@ CPPUNIT_TEST_FIXTURE(ScFiltersTest3, testTdf131471)
pDoc->SetDocVisible(true);
pDoc->SetValue(0, 0, 0, 1.0);
+ Scheduler::ProcessEventsToIdle();
+
CPPUNIT_ASSERT(aListener.mbCalled);
}
diff --git a/sc/source/core/data/conditio.cxx b/sc/source/core/data/conditio.cxx
index b70f9579d0e8..93094e929bf4 100644
--- a/sc/source/core/data/conditio.cxx
+++ b/sc/source/core/data/conditio.cxx
@@ -160,12 +160,13 @@ void ScConditionEntry::StartListening()
if (!pCondFormat)
return;
+ mpRepaintTask = std::make_unique<RepaintInIdle>(pCondFormat);
const ScRangeList& rRanges = pCondFormat->GetRange();
mpListener->stopListening();
start_listen_to(*mpListener, pFormula1.get(), rRanges);
start_listen_to(*mpListener, pFormula2.get(), rRanges);
- mpListener->setCallback([&]() { pCondFormat->DoRepaint();});
+ mpListener->setCallback([&]() { mpRepaintTask->Start();});
}
void ScConditionEntry::SetParent(ScConditionalFormat* pParent)
@@ -195,7 +196,8 @@ ScConditionEntry::ScConditionEntry( const ScConditionEntry& r ) :
bFirstRun(true),
mpListener(new ScFormulaListener(*r.mpDoc)),
eConditionType( r.eConditionType ),
- pCondFormat(r.pCondFormat)
+ pCondFormat(r.pCondFormat),
+ mpRepaintTask()
{
// ScTokenArray copy ctor creates a flat copy
if (r.pFormula1)
@@ -228,7 +230,8 @@ ScConditionEntry::ScConditionEntry( ScDocument& rDocument, const ScConditionEntr
bFirstRun(true),
mpListener(new ScFormulaListener(rDocument)),
eConditionType( r.eConditionType),
- pCondFormat(r.pCondFormat)
+ pCondFormat(r.pCondFormat),
+ mpRepaintTask()
{
// Real copy of the formulas (for Ref Undo)
if (r.pFormula1)
@@ -262,7 +265,8 @@ ScConditionEntry::ScConditionEntry( ScConditionMode eOper,
bFirstRun(true),
mpListener(new ScFormulaListener(rDocument)),
eConditionType(eType),
- pCondFormat(nullptr)
+ pCondFormat(nullptr),
+ mpRepaintTask()
{
Compile( rExpr1, rExpr2, rExprNmsp1, rExprNmsp2, eGrammar1, eGrammar2, false );
@@ -287,7 +291,8 @@ ScConditionEntry::ScConditionEntry( ScConditionMode eOper,
bFirstRun(true),
mpListener(new ScFormulaListener(rDocument)),
eConditionType(ScFormatEntry::Type::Condition),
- pCondFormat(nullptr)
+ pCondFormat(nullptr),
+ mpRepaintTask()
{
if ( pArr1 )
{