commit ac275a66b5d34e211ba6e63ea9a2d02efce7eb72
Author: Juergen Spitzmueller <sp...@lyx.org>
Date:   Sun Sep 17 19:17:12 2023 +0200

    Get rid of unnecessary flickering when clicking in outliner
    
    No need to collapse and re-expand the node where the currently selected
    item is in.
---
 src/frontends/qt/TocWidget.cpp |   72 ++++++++++++++++++++++++++++++++++++---
 src/frontends/qt/TocWidget.h   |    8 ++++-
 2 files changed, 73 insertions(+), 7 deletions(-)

diff --git a/src/frontends/qt/TocWidget.cpp b/src/frontends/qt/TocWidget.cpp
index e3d857b..c5c2ea4 100644
--- a/src/frontends/qt/TocWidget.cpp
+++ b/src/frontends/qt/TocWidget.cpp
@@ -334,16 +334,20 @@ void TocWidget::on_depthSL_valueChanged(int depth)
 }
 
 
-void TocWidget::setTreeDepth(int depth)
+void TocWidget::setTreeDepth(int depth, bool const maintain_current)
 {
        depth_ = depth;
        if (!tocTV->model())
                return;
 
-       if (depth == 0)
-               tocTV->collapseAll();
-       else
-               tocTV->expandToDepth(depth - 1);
+       if (maintain_current)
+               collapseAllOthers(depth);
+       else {
+               if (depth == 0)
+                       tocTV->collapseAll();
+               else
+                       tocTV->expandToDepth(depth - 1);
+       }
 }
 
 
@@ -518,7 +522,7 @@ void TocWidget::finishUpdateView()
        // and outweighted by TocModels::reset() anyway.
        if (canNavigate()) {
                if (!persistent_ && !keep_expanded_)
-                       setTreeDepth(depth_);
+                       setTreeDepth(depth_, true);
                keep_expanded_ = false;
                persistentCB->setChecked(persistent_);
                // select the item at current cursor location
@@ -573,6 +577,62 @@ void TocWidget::filterContents()
 }
 
 
+bool TocWidget::isAncestor(QModelIndex const & ancestor,
+                          QModelIndex const & descendant) const
+{
+       QModelIndex mi = descendant;
+       while (true) {
+               if (ancestor == mi.parent())
+                       return true;
+               if (mi == QModelIndex())
+                       return false;
+               mi = mi.parent();
+       }
+       return false;
+}
+
+
+QModelIndex TocWidget::getAncestor(QModelIndex const & descendant) const
+{
+       QModelIndex mi = descendant;
+       while (true) {
+               if (mi.parent() == QModelIndex())
+                       return mi;
+               mi = mi.parent();
+       }
+       return mi;
+}
+
+
+void TocWidget::collapseAllOthers(int const depth)
+{
+       if (!tocTV->model())
+               return;
+
+       QModelIndexList indices = tocTV->model()->match(
+               tocTV->model()->index(0, 0),
+               Qt::DisplayRole, ".*", -1,
+#if QT_VERSION >= QT_VERSION_CHECK(5, 15, 0)
+               Qt::MatchFlags(Qt::MatchRegularExpression|Qt::MatchRecursive));
+#else
+               // deprecated in Qt 5.15.
+               Qt::MatchFlags(Qt::MatchRegExp|Qt::MatchRecursive));
+#endif
+
+       int size = indices.size();
+       // collapse parents which are not in our ancestry line
+       for (int i = size - 1; i >= 0; i--) {
+               QModelIndex index = indices[i];
+               if (tocTV->isExpanded(index)
+                   && !isAncestor(index, tocTV->currentIndex())) {
+                       tocTV->collapse(index);
+                       if (depth > 0 && index.parent() == QModelIndex())
+                               tocTV->expandRecursively(index, depth - 1);
+               }
+       }
+}
+
+
 static QString decodeType(QString const & str)
 {
        QString type = str;
diff --git a/src/frontends/qt/TocWidget.h b/src/frontends/qt/TocWidget.h
index 079fd24..50c1089 100644
--- a/src/frontends/qt/TocWidget.h
+++ b/src/frontends/qt/TocWidget.h
@@ -102,8 +102,14 @@ private:
        ///
        bool isSortable()
                { return current_type_ != "tableofcontents"; }
+       /// \returns the top-most ancestor of \p descendant
+       QModelIndex getAncestor(QModelIndex const & descendant) const;
+       /// \returns \c true if \p ancestor is an ancestor (parent, 
grandparent, etc.) of \p descendant
+       bool isAncestor(QModelIndex const & ancestor, QModelIndex const & 
descendant) const;
+       /// collapse all nodes to \c depth except for the branch of the 
currently active item
+       void collapseAllOthers(int const depth);
        ///
-       void setTreeDepth(int depth);
+       void setTreeDepth(int depth, bool const maintain_current = false);
        ///
        void outline(FuncCode func_code);
        /// finds the inset that is connected to the current item,
-- 
lyx-cvs mailing list
lyx-cvs@lists.lyx.org
http://lists.lyx.org/mailman/listinfo/lyx-cvs

Reply via email to