From c6e04990269a62d990941ca2a9ad3205363e9add Mon Sep 17 00:00:00 2001
From: dt <qtc-committer@nokia.com>
Date: Fri, 25 Mar 2011 16:48:18 +0100
Subject: [PATCH] Sessions: Store expand/collapsed state of project tree

Task-Nr: QTCREATORBUG-3161
And related to
Task-Nr: QTCREATORBUG-1796
---
 .../projectexplorer/projecttreewidget.cpp     | 52 ++++++++++++++++++-
 .../projectexplorer/projecttreewidget.h       |  7 +++
 src/plugins/projectexplorer/session.cpp       |  6 +--
 src/plugins/projectexplorer/session.h         |  1 +
 4 files changed, 62 insertions(+), 4 deletions(-)

diff --git a/src/plugins/projectexplorer/projecttreewidget.cpp b/src/plugins/projectexplorer/projecttreewidget.cpp
index 70530464774..ae536cd781e 100644
--- a/src/plugins/projectexplorer/projecttreewidget.cpp
+++ b/src/plugins/projectexplorer/projecttreewidget.cpp
@@ -101,6 +101,7 @@ ProjectTreeWidget::ProjectTreeWidget(QWidget *parent)
           m_model(0),
           m_filterProjectsAction(0),
           m_autoSync(false),
+          m_autoExpand(true),
           m_currentItemLocked(0)
 {
     m_model = new FlatModel(m_explorer->session()->sessionNode(), this);
@@ -150,6 +151,13 @@ ProjectTreeWidget::ProjectTreeWidget(QWidget *parent)
     connect(m_explorer->session(), SIGNAL(startupProjectChanged(ProjectExplorer::Project *)),
             this, SLOT(startupProjectChanged(ProjectExplorer::Project *)));
 
+    connect(m_explorer->session(), SIGNAL(aboutToLoadSession()),
+            this, SLOT(disableAutoExpand()));
+    connect(m_explorer->session(), SIGNAL(sessionLoaded()),
+            this, SLOT(loadExpandData()));
+    connect(m_explorer->session(), SIGNAL(aboutToSaveSession()),
+            this, SLOT(saveExpandData()));
+
     m_toggleSync = new QToolButton;
     m_toggleSync->setIcon(QIcon(QLatin1String(Core::Constants::ICON_LINK)));
     m_toggleSync->setCheckable(true);
@@ -160,6 +168,47 @@ ProjectTreeWidget::ProjectTreeWidget(QWidget *parent)
     setAutoSynchronization(true);
 }
 
+void ProjectTreeWidget::disableAutoExpand()
+{
+    m_autoExpand = false;
+}
+
+void ProjectTreeWidget::loadExpandData()
+{
+    m_autoExpand = true;
+    QStringList data = m_explorer->session()->value("ProjectTree.ExpandData").toStringList();
+    recursiveLoadExpandData(m_view->rootIndex(), data.toSet());
+}
+
+void ProjectTreeWidget::recursiveLoadExpandData(const QModelIndex &index, const QSet<QString> &data)
+{
+    if (data.contains(m_model->nodeForIndex(index)->path())) {
+        m_view->expand(index);
+        int count = m_model->rowCount(index);
+        for (int i = 0; i < count; ++i)
+            recursiveLoadExpandData(index.child(i, 0), data);
+    }
+}
+
+void ProjectTreeWidget::saveExpandData()
+{
+    QStringList data;
+    recursiveSaveExpandData(m_view->rootIndex(), &data);
+    // TODO if there are multiple ProjectTreeWidgets, the last one saves the data
+    m_explorer->session()->setValue("ProjectTree.ExpandData", data);
+}
+
+void ProjectTreeWidget::recursiveSaveExpandData(const QModelIndex &index, QStringList *data)
+{
+    Q_ASSERT(data);
+    if (m_view->isExpanded(index)) {
+        data->append(m_model->nodeForIndex(index)->path());
+        int count = m_model->rowCount(index);
+        for (int i = 0; i < count; ++i)
+            recursiveSaveExpandData(index.child(i, 0), data);
+    }
+}
+
 void ProjectTreeWidget::foldersAboutToBeRemoved(FolderNode *, const QList<FolderNode*> &list)
 {
     Node *n = m_explorer->currentNode();
@@ -284,7 +333,8 @@ void ProjectTreeWidget::handleProjectAdded(ProjectExplorer::Project *project)
 
     Node *node = project->rootProjectNode();
     QModelIndex idx = m_model->indexForNode(node);
-    m_view->setExpanded(idx, true);
+    if (m_autoExpand) // disabled while session restoring
+        m_view->setExpanded(idx, true);
     m_view->setCurrentIndex(idx);
 }
 
diff --git a/src/plugins/projectexplorer/projecttreewidget.h b/src/plugins/projectexplorer/projecttreewidget.h
index eee246de7f7..ea48bd8679f 100644
--- a/src/plugins/projectexplorer/projecttreewidget.h
+++ b/src/plugins/projectexplorer/projecttreewidget.h
@@ -84,7 +84,13 @@ private slots:
     void foldersAboutToBeRemoved(FolderNode *, const QList<FolderNode*> &);
     void filesAboutToBeRemoved(FolderNode *, const QList<FileNode*> &);
 
+    void loadExpandData();
+    void saveExpandData();
+    void disableAutoExpand();
+
 private:
+    void recursiveLoadExpandData(const QModelIndex &index, const QSet<QString> &data);
+    void recursiveSaveExpandData(const QModelIndex &index, QStringList *data);
     ProjectExplorerPlugin *m_explorer;
     QTreeView *m_view;
     FlatModel *m_model;
@@ -95,6 +101,7 @@ private:
     QModelIndex m_subIndex;
     QString m_modelId;
     bool m_autoSync;
+    bool m_autoExpand;
     Node *m_currentItemLocked;
     friend class ProjectTreeWidgetFactory;
 };
diff --git a/src/plugins/projectexplorer/session.cpp b/src/plugins/projectexplorer/session.cpp
index 0f11fe7b2ae..0c47df9542d 100644
--- a/src/plugins/projectexplorer/session.cpp
+++ b/src/plugins/projectexplorer/session.cpp
@@ -556,9 +556,6 @@ bool SessionManager::createImpl(const QString &fileName)
     if (debug)
         qDebug() << "SessionManager - creating new session returns " << success;
 
-    if (success)
-        emit sessionLoaded();
-
     return success;
 }
 
@@ -967,8 +964,10 @@ QString SessionManager::sessionNameToFileName(const QString &session) const
 
 void SessionManager::createAndLoadNewDefaultSession()
 {
+    emit aboutToLoadSession();
     updateName("default");
     createImpl(sessionNameToFileName(m_sessionName));
+    emit sessionLoaded();
 }
 
 bool SessionManager::createSession(const QString &session)
@@ -1025,6 +1024,7 @@ bool SessionManager::loadSession(const QString &session)
 
     if (!sessions().contains(session))
         return false;
+    emit aboutToLoadSession();
     QString fileName = sessionNameToFileName(session);
     if (QFileInfo(fileName).exists()) {
         if (loadImpl(fileName)) {
diff --git a/src/plugins/projectexplorer/session.h b/src/plugins/projectexplorer/session.h
index 53eee3cae13..bdfdb839ef1 100644
--- a/src/plugins/projectexplorer/session.h
+++ b/src/plugins/projectexplorer/session.h
@@ -150,6 +150,7 @@ signals:
 
     void startupProjectChanged(ProjectExplorer::Project *project);
 
+    void aboutToLoadSession();
     void sessionLoaded();
     void aboutToUnloadSession();
     void aboutToSaveSession();
-- 
GitLab