[Kst] extragear/graphics/kst/src/libkst

Eli Fidler eli at staikos.net
Thu Feb 8 00:27:01 CET 2007


SVN commit 631420 by fidler:

added setUpdateDisplayTags(bool) to (en/dis)able display tag updates for
efficiency

use a QDict for the index instead of a QMap


 M  +90 -31    kstobjectcollection.h  


--- trunk/extragear/graphics/kst/src/libkst/kstobjectcollection.h #631419:631420
@@ -21,6 +21,7 @@
 // NAMEDEBUG: 0 for no debug, 1 for some debug, 2 for more debug, 3 for all debug
 #define NAMEDEBUG 0
 
+#include <qdict.h>
 #include <qintdict.h>
 
 #include "ksdebug.h"
@@ -37,7 +38,7 @@
 
 // Typedefs
 template <class T>
-class KstObjectNameIndex : public QMap<QString, QValueList<KstObjectTreeNode<T> *> > {
+class KstObjectNameIndex : public QDict<QValueList<KstObjectTreeNode<T> *> > {
 };
 
 
@@ -75,6 +76,8 @@
 template <class T>
 class KstObjectCollection {
   public:
+    KstObjectCollection();
+
     bool addObject(T *o);
     bool removeObject(T *o);
     void doRename(T *o, const KstObjectTag& newTag);
@@ -89,6 +92,8 @@
     // get the minimum number of tag components of in_tag necessary for a unique tag
     unsigned int componentsForUniqueTag(const KstObjectTag& in_tag) const;
 
+    void setUpdateDisplayTags(bool u);
+
     KstObjectTreeNode<T> *nameTreeRoot() { return &_root; }
 
     // QValueList compatibility
@@ -119,9 +124,12 @@
     void relatedNodesHelper(T *o, KstObjectTreeNode<T> *n, QIntDict<KstObjectTreeNode<T> >& nodes);
 
     // must be called AFTER the object is added to the index, while holding a write lock
-    void updateDisplayComponents(T *obj);
-    void updateDisplayComponents(QValueList<KstObjectTreeNode<T> *> nodes);
+    void updateAllDisplayTags();
+    void updateDisplayTag(T *obj);
+    void updateDisplayTags(QValueList<KstObjectTreeNode<T> *> nodes);
 
+    bool _updateDisplayTags;
+
     KstObjectTreeNode<T> _root;
     KstObjectNameIndex<T> _index;
     KstObjectList<KstSharedPtr<T> > _list; // owns the objects
@@ -238,7 +246,12 @@
       nextNode->_parent = currNode;
       currNode->_children[*i] = nextNode;
       if (index) {
-        (*index)[*i].append(nextNode);
+        QValueList<KstObjectTreeNode<T> *> *l;
+        if (!(l = index->take(*i))) {
+          l = new QValueList<KstObjectTreeNode<T> *>;
+        }
+        l->append(nextNode);
+        index->insert(*i, l);
       }
     }
     currNode = nextNode;
@@ -295,9 +308,10 @@
       kstdDebug() << "Removed naming tree node: \"" << currNode->fullTag().join(KstObjectTag::tagSeparator) << "\"" << endl;
 #endif
       if (index) {
-        (*index)[*i].remove(currNode);
-        if ((*index)[*i].isEmpty()) {
-          (*index).remove(*i);
+        QValueList<KstObjectTreeNode<T> *> *l = index->take(*i);
+        if (l) {
+          l->remove(currNode);
+          index->insert(*i, l);
         }
       }
       delete currNode;
@@ -324,7 +338,17 @@
 }
 
 
+/******************************************************************************/
+
+
 template <class T>
+KstObjectCollection<T>::KstObjectCollection() : _updateDisplayTags(true)
+{
+  _index.setAutoDelete(true);
+}
+
+
+template <class T>
 bool KstObjectCollection<T>::addObject(T *o) {
   if (!o) {
     return false;
@@ -332,13 +356,18 @@
 
   _list.append(o);
 
-  QValueList<KstObjectTreeNode<T> *> relNodes = relatedNodes(o);
+  QValueList<KstObjectTreeNode<T> *> relNodes;
+  if (_updateDisplayTags) {
+    relNodes = relatedNodes(o);
+  }
 
   KstObjectTreeNode<T> *n = _root.addDescendant(o, &_index);
 
   if (n) {
-    updateDisplayComponents(o);
-    updateDisplayComponents(relNodes);
+    if (_updateDisplayTags) {
+      updateDisplayTag(o);
+      updateDisplayTags(relNodes);
+    }
     return true;
   } else {
     // TODO: handle failed insert?
@@ -364,10 +393,13 @@
     kstdDebug() << "Removing object from the collection: " << o->tag().tagString() << endl;
 #endif
 
+    QValueList<KstObjectTreeNode<T> *> relNodes;
+    if (_updateDisplayTags) {
 #if NAMEDEBUG > 2
-    kstdDebug() << "  fetching related nodes" << endl;
+      kstdDebug() << "  fetching related nodes" << endl;
 #endif
-  QValueList<KstObjectTreeNode<T> *> relNodes = relatedNodes(o);
+      relNodes = relatedNodes(o);
+    }
 
 #if NAMEDEBUG > 2
     kstdDebug() << "  removing object from tree" << endl;
@@ -375,10 +407,12 @@
   bool ok = _root.removeDescendant(o, &_index);
 
   if (ok) {
+    if (_updateDisplayTags) {
 #if NAMEDEBUG > 2
-    kstdDebug() << "  updating display components" << endl;
+      kstdDebug() << "  updating display components" << endl;
 #endif
-    updateDisplayComponents(relNodes);
+      updateDisplayTags(relNodes);
+    }
 
 #if NAMEDEBUG > 2
     kstdDebug() << "  removing object from list" << endl;
@@ -400,16 +434,21 @@
     return;
   }
 
-  QValueList<KstObjectTreeNode<T> *> relNodes = relatedNodes(o);
+  QValueList<KstObjectTreeNode<T> *> relNodes;
+  if (_updateDisplayTags) {
+    relNodes = relatedNodes(o);
+  }
 
   _root.removeDescendant(o, &_index);
 
   o->KstObject::setTagName(newTag);
 
   if (_root.addDescendant(o, &_index)) {
-    relNodes += relatedNodes(o);  // TODO: remove duplicates
-    updateDisplayComponents(o);
-    updateDisplayComponents(relNodes);
+    if (_updateDisplayTags) {
+      relNodes += relatedNodes(o);  // TODO: remove duplicates
+      updateDisplayTag(o);
+      updateDisplayTags(relNodes);
+    }
   } else {
     // TODO: handle failed insert
   }
@@ -426,13 +465,13 @@
     return NULL;
   }
 
-  if (_index.contains(tag.first()) && _index[tag.first()].count() == 1) {
+  if (_index[tag.first()] && _index[tag.first()]->count() == 1) {
     // the first tag element is unique, so use the index
 #if NAMEDEBUG > 2
     kstdDebug() << "  first tag element (\"" << tag.first() << "\") is unique in index" << endl;
 #endif
 
-    KstObjectTreeNode<T> *n = _index[tag.first()].first();
+    KstObjectTreeNode<T> *n = _index[tag.first()]->first();
     if (n) {
       tag.pop_front();
       n = n->descendant(tag);
@@ -471,7 +510,7 @@
 
 template <class T>
 bool KstObjectCollection<T>::tagExists(const QString& tag) const {
-  return (_index.contains(tag) && _index[tag].count() > 0);
+  return (_index[tag] && _index[tag]->count() > 0);
 }
 
 template <class T>
@@ -494,7 +533,7 @@
   do {
     --it;
     out_tag.prepend(*it);
-    if (_index.contains(*it) && _index[*it].count() == 1) {
+    if (_index[*it] && _index[*it]->count() == 1) {
       // found unique tag
       break;
     }
@@ -518,7 +557,7 @@
   do {
     --it;
     components++;
-    if (_index.contains(*it) && _index[*it].count() == 1) {
+    if (_index[*it] && _index[*it]->count() == 1) {
       // found unique tag
       break;
     }
@@ -641,16 +680,37 @@
 }
 
 
+template <class T>
+void KstObjectCollection<T>::setUpdateDisplayTags(bool u) {
+  if (u && !_updateDisplayTags) {
+    // turning on _updateDisplayTags, so do an update
+    updateAllDisplayTags();
+  }
+
+  _updateDisplayTags = u;
+}
+
+
+// update the display tags for all the objects in the collection
+template <class T>
+void KstObjectCollection<T>::updateAllDisplayTags() {
+  Q_ASSERT(lock().myLockStatus() == KstRWLock::WRITELOCKED);
+
+  for (typename KstObjectList<KstSharedPtr<T> >::Iterator i = _list.begin(); i != _list.end(); ++i) {
+    updateDisplayTag(*i);
+  }
+}
+
 // must be called AFTER the object is added to the index, while holding a write lock
 template <class T>
-void KstObjectCollection<T>::updateDisplayComponents(T *obj) {
+void KstObjectCollection<T>::updateDisplayTag(T *obj) {
   if (!obj) {
     return;
   }
 
   KstObjectTag tag = obj->tag();
 
-  if (!_index.contains(tag.tag())) {
+  if (!_index[tag.tag()]) {
     return;
   }
 
@@ -659,15 +719,14 @@
 #if NAMEDEBUG > 2
     kstdDebug() << "Changing display components on \"" << tag.tagString() << "\" from " << tag.uniqueDisplayComponents() << " to " << nc << endl;
 #endif
-//    KstWriteLocker l(obj);
     obj->tag().setUniqueDisplayComponents(nc);
   }
 }
 
 template <class T>
-void KstObjectCollection<T>::updateDisplayComponents(QValueList<KstObjectTreeNode<T> *> nodes) {
+void KstObjectCollection<T>::updateDisplayTags(QValueList<KstObjectTreeNode<T> *> nodes) {
   for (typename QValueList<KstObjectTreeNode<T> *>::Iterator i = nodes.begin(); i != nodes.end(); ++i) {
-    updateDisplayComponents((*i)->object());
+    updateDisplayTag((*i)->object());
   }
 }
 
@@ -712,9 +771,9 @@
   QStringList ft = o->tag().fullTag();
 
   for (QStringList::ConstIterator i = ft.begin(); i != ft.end(); ++i) {
-    if (_index.contains(*i)) {
-      QValueList<KstObjectTreeNode<T> *> nodeList = _index[*i];
-      for (typename QValueList<KstObjectTreeNode<T> *>::ConstIterator i2 = nodeList.begin(); i2 != nodeList.end(); ++i2) {
+    if (_index[*i]) {
+      QValueList<KstObjectTreeNode<T> *> *nodeList = _index[*i];
+      for (typename QValueList<KstObjectTreeNode<T> *>::ConstIterator i2 = nodeList->begin(); i2 != nodeList->end(); ++i2) {
         relatedNodesHelper(o, *i2, nodes);
       }
     }


More information about the Kst mailing list