changeset 298:226cb289bdf4

* Layer tree view updating when visibility / audibility changed (and layers updating when they are changed in view) -- still some problems when a model is loaded while the tree is visible * FFTW_MEASURE throughout -- it does turn out to make an appreciable difference sometimes
author Chris Cannam
date Thu, 16 Aug 2007 16:47:07 +0000
parents 860f9ada4327
children 5c59c433b358
files view/View.cpp view/View.h widgets/LayerTree.cpp widgets/LayerTree.h widgets/PropertyStack.cpp
diffstat 5 files changed, 171 insertions(+), 6 deletions(-) [+]
line wrap: on
line diff
--- a/view/View.cpp	Tue Aug 14 19:37:10 2007 +0000
+++ b/view/View.cpp	Thu Aug 16 16:47:07 2007 +0000
@@ -259,6 +259,8 @@
     } else {
 	m_haveSelectedLayer = false;
     }
+
+    emit propertyContainerSelected(pc);
 }
 
 void
--- a/view/View.h	Tue Aug 14 19:37:10 2007 +0000
+++ b/view/View.h	Thu Aug 16 16:47:07 2007 +0000
@@ -258,6 +258,7 @@
     void propertyContainerPropertyChanged(PropertyContainer *pc);
     void propertyContainerPropertyRangeChanged(PropertyContainer *pc);
     void propertyContainerNameChanged(PropertyContainer *pc);
+    void propertyContainerSelected(PropertyContainer *pc);
     void propertyChanged(PropertyContainer::PropertyName);
 
     void centreFrameChanged(unsigned long frame,
--- a/widgets/LayerTree.cpp	Tue Aug 14 19:37:10 2007 +0000
+++ b/widgets/LayerTree.cpp	Thu Aug 16 16:47:07 2007 +0000
@@ -17,6 +17,7 @@
 #include "LayerTree.h"
 #include "view/PaneStack.h"
 
+#include "base/PlayParameters.h"
 #include "view/Pane.h"
 #include "layer/Layer.h"
 #include "data/model/Model.h"
@@ -31,12 +32,98 @@
 {
     connect(stack, SIGNAL(paneAdded()), this, SIGNAL(layoutChanged()));
     connect(stack, SIGNAL(paneDeleted()), this, SIGNAL(layoutChanged()));
+
+    for (int i = 0; i < stack->getPaneCount(); ++i) {
+        Pane *pane = stack->getPane(i);
+        if (!pane) continue;
+        connect(pane, SIGNAL(propertyContainerAdded(PropertyContainer *)),
+                this, SLOT(propertyContainerAdded(PropertyContainer *)));
+        connect(pane, SIGNAL(propertyContainerRemoved(PropertyContainer *)),
+                this, SLOT(propertyContainerRemoved(PropertyContainer *)));
+        connect(pane, SIGNAL(propertyContainerSelected(PropertyContainer *)),
+                this, SLOT(propertyContainerSelected(PropertyContainer *)));
+        connect(pane, SIGNAL(propertyContainerPropertyChanged(PropertyContainer *)),
+                this, SLOT(propertyContainerPropertyChanged(PropertyContainer *)));
+        connect(pane, SIGNAL(propertyContainerNameChanged(PropertyContainer *)),
+                this, SLOT(propertyContainerPropertyChanged(PropertyContainer *)));
+        for (int j = 0; j < pane->getLayerCount(); ++j) {
+            Layer *layer = pane->getLayer(j);
+            if (!layer) continue;
+            PlayParameters *params = layer->getPlayParameters();
+            if (!params) continue;
+            connect(params, SIGNAL(playAudibleChanged(bool)),
+                    this, SLOT(playParametersAudibilityChanged(bool)));
+        }
+    }
 }
 
 LayerTreeModel::~LayerTreeModel()
 {
 }
 
+void
+LayerTreeModel::propertyContainerAdded(PropertyContainer *)
+{
+    emit layoutChanged();
+}
+
+void
+LayerTreeModel::propertyContainerRemoved(PropertyContainer *)
+{
+    emit layoutChanged();
+}
+
+void
+LayerTreeModel::propertyContainerSelected(PropertyContainer *)
+{
+    emit layoutChanged();
+}
+
+void
+LayerTreeModel::propertyContainerPropertyChanged(PropertyContainer *pc)
+{
+    for (int i = 0; i < m_stack->getPaneCount(); ++i) {
+        Pane *pane = m_stack->getPane(i);
+        if (!pane) continue;
+        for (int j = 0; j < pane->getLayerCount(); ++j) {
+            if (pane->getLayer(j) == pc) {
+                emit dataChanged(createIndex(pane->getLayerCount() - j - 1,
+                                             0, pane),
+                                 createIndex(pane->getLayerCount() - j - 1,
+                                             3, pane));
+            }
+        }
+    }
+}
+
+void
+LayerTreeModel::playParametersAudibilityChanged(bool a)
+{
+    PlayParameters *params = dynamic_cast<PlayParameters *>(sender());
+    if (!params) return;
+
+    std::cerr << "LayerTreeModel::playParametersAudibilityChanged("
+              << params << "," << a << ")" << std::endl;
+
+    for (int i = 0; i < m_stack->getPaneCount(); ++i) {
+        Pane *pane = m_stack->getPane(i);
+        if (!pane) continue;
+        for (int j = 0; j < pane->getLayerCount(); ++j) {
+            Layer *layer = pane->getLayer(j);
+            if (!layer) continue;
+            if (layer->getPlayParameters() == params) {
+                std::cerr << "LayerTreeModel::playParametersAudibilityChanged("
+                          << params << "," << a << "): row " << pane->getLayerCount() - j - 1 << ", col " << 2 << std::endl;
+
+                emit dataChanged(createIndex(pane->getLayerCount() - j - 1,
+                                             2, pane),
+                                 createIndex(pane->getLayerCount() - j - 1,
+                                             2, pane));
+            }
+        }
+    }
+}
+
 QVariant
 LayerTreeModel::data(const QModelIndex &index, int role) const
 {
@@ -59,7 +146,7 @@
     }
 
     if (pane && pane->getLayerCount() > row) {
-        Layer *layer = pane->getLayer(row);
+        Layer *layer = pane->getLayer(pane->getLayerCount() - row - 1);
         if (layer) {
             if (col == 0) {
                 switch (role) {
@@ -72,6 +159,22 @@
                 default: break;
                 }
             } else if (col == 1) {
+                if (role == Qt::CheckStateRole) {
+                    return QVariant(layer->isLayerDormant(pane) ?
+                                    Qt::Unchecked : Qt::Checked);
+                } else if (role == Qt::TextAlignmentRole) {
+                    return QVariant(Qt::AlignHCenter);
+                }
+            } else if (col == 2) {
+                if (role == Qt::CheckStateRole) {
+                    PlayParameters *params = layer->getPlayParameters();
+                    if (params) return QVariant(params->isPlayMuted() ?
+                                                Qt::Unchecked : Qt::Checked);
+                    else return QVariant();
+                } else if (role == Qt::TextAlignmentRole) {
+                    return QVariant(Qt::AlignHCenter);
+                }
+            } else if (col == 3) {
                 Model *model = layer->getModel();
                 if (model && role == Qt::DisplayRole) {
                     return QVariant(model->objectName());
@@ -83,11 +186,53 @@
     return QVariant();
 }
 
+bool
+LayerTreeModel::setData(const QModelIndex &index, const QVariant &value, int role)
+{
+    if (!index.isValid()) return false;
+
+    QObject *obj = static_cast<QObject *>(index.internalPointer());
+    int row = index.row(), col = index.column();
+
+    Pane *pane = dynamic_cast<Pane *>(obj);
+    if (!pane || pane->getLayerCount() <= row) return false;
+
+    Layer *layer = pane->getLayer(pane->getLayerCount() - row - 1);
+    if (!layer) return false;
+
+    if (col == 1) {
+        if (role == Qt::CheckStateRole) {
+            layer->showLayer(pane, value.toInt() == Qt::Checked);
+            emit dataChanged(index, index);
+            return true;
+        }
+    } else if (col == 2) {
+        if (role == Qt::CheckStateRole) {
+            PlayParameters *params = layer->getPlayParameters();
+            if (params) {
+                params->setPlayMuted(value.toInt() == Qt::Unchecked);
+                emit dataChanged(index, index);
+                return true;
+            }
+        }
+    }
+
+    return false;
+}
+
 Qt::ItemFlags
 LayerTreeModel::flags(const QModelIndex &index) const
 {
-    if (!index.isValid()) return Qt::ItemIsEnabled;
-    return Qt::ItemIsEnabled | Qt::ItemIsSelectable;
+    Qt::ItemFlags flags = Qt::ItemIsEnabled;
+    if (!index.isValid()) return flags;
+
+    if (index.column() == 1 || index.column() == 2) {
+        flags |= Qt::ItemIsUserCheckable;
+    } else if (index.column() == 0) {
+        flags |= Qt::ItemIsSelectable;
+    }
+
+    return flags;
 }
 
 QVariant
@@ -97,7 +242,9 @@
 {
     if (orientation == Qt::Horizontal && role == Qt::DisplayRole) {
 	if (section == 0) return QVariant(tr("Layer"));
-	else if (section == 1) return QVariant(tr("Model"));
+        else if (section == 1) return QVariant(tr("Shown"));
+        else if (section == 2) return QVariant(tr("Played"));
+	else if (section == 3) return QVariant(tr("Model"));
     }
 
     return QVariant();
@@ -161,10 +308,10 @@
 int
 LayerTreeModel::columnCount(const QModelIndex &parent) const
 {
-    if (!parent.isValid()) return 2;
+    if (!parent.isValid()) return 4;
 
     QObject *obj = static_cast<QObject *>(parent.internalPointer());
-    if (obj == m_stack) return 2;
+    if (obj == m_stack) return 4; // row for a layer
 
     return 1;
 }
--- a/widgets/LayerTree.h	Tue Aug 14 19:37:10 2007 +0000
+++ b/widgets/LayerTree.h	Thu Aug 16 16:47:07 2007 +0000
@@ -22,6 +22,7 @@
 class PaneStack;
 class View;
 class Layer;
+class PropertyContainer;
 
 class LayerTreeModel : public QAbstractItemModel
 {
@@ -33,6 +34,8 @@
 
     QVariant data(const QModelIndex &index, int role) const;
 
+    bool setData(const QModelIndex &index, const QVariant &value, int role);
+
     Qt::ItemFlags flags(const QModelIndex &index) const;
 
     QVariant headerData(int section, Qt::Orientation orientation,
@@ -48,6 +51,13 @@
 
 protected:
     PaneStack *m_stack;
+
+protected slots:
+    void propertyContainerAdded(PropertyContainer *);
+    void propertyContainerRemoved(PropertyContainer *);
+    void propertyContainerSelected(PropertyContainer *);
+    void propertyContainerPropertyChanged(PropertyContainer *);
+    void playParametersAudibilityChanged(bool);
 };
 
 #endif
--- a/widgets/PropertyStack.cpp	Tue Aug 14 19:37:10 2007 +0000
+++ b/widgets/PropertyStack.cpp	Thu Aug 16 16:47:07 2007 +0000
@@ -182,9 +182,14 @@
 void
 PropertyStack::propertyContainerPropertyChanged(PropertyContainer *pc)
 {
+    Layer *layer = dynamic_cast<Layer *>(pc);
     for (unsigned int i = 0; i < m_boxes.size(); ++i) {
 	if (pc == m_boxes[i]->getContainer()) {
 	    m_boxes[i]->propertyContainerPropertyChanged(pc);
+            if (layer) {
+                m_boxes[i]->layerVisibilityChanged
+                    (!layer->isLayerDormant(m_client));
+            }
 	}
     }
 }