Index: framestack.h
===================================================================
RCS file: /home/kde/kdevelop/kdevelop/dbg/framestack.h,v
retrieving revision 1.1.2.2.2.1.4.1
diff -r1.1.2.2.2.1.4.1 framestack.h
21a22
> #include <qstringlist.h>
103a105,109
> #if QT_VERSION < 300
> private:
>   QListViewItem* findItemWhichBeginsWith(const QString& text) const;
> #endif
> 
107a114,115
>   QString           firstLineOfLastBacktrace_;
>   QStringList       threadList_;
Index: framestack.cpp
===================================================================
RCS file: /home/kde/kdevelop/kdevelop/dbg/framestack.cpp,v
retrieving revision 1.1.2.2.2.8.2.1
diff -r1.1.2.2.2.8.2.1 framestack.cpp
125c125
<   clear();
---
>   threadList_.clear();
133,141c133
<       ThreadStackItem* thread = new ThreadStackItem(this, threadDesc);
< 
<       // This indicates the current thread
<       if (*str == '*')
<       {
<         viewedThread_ = thread;
<         stoppedAtThread_ = thread;
<         thread->setOpen(true);
<       }
---
>       threadList_.append(threadDesc);
154,159c146,152
<   // If we don't have a thread program then clear the list.
<   if (!viewedThread_)
<     clear();
< 
<   while (char* end = strchr(str, '\n'))
<   {
---
>   // just find out what the first line of str is and store that in firstLine
>   // (store without the line number to enable comparison with firstLineOfLastBacktrace_)
>   QString firstLineLeft;
>   QString firstLine;
>   bool bBreak = false;
>   char* end = strchr(str, '\n');
>   while (!bBreak && end) {
162,164c155,192
<     if (*str == '#')                      // Don't bother with extra data
<       if (viewedThread_)
<         new FrameStackItem(viewedThread_, frameDesc);
---
>     if (*str == '#') {                     // Don't bother with extra data
>       firstLine = frameDesc;
>       int idx = frameDesc.findRev(':');
>       if (idx != -1) {
>         firstLineLeft = firstLine.left(idx);
>       }
>       bBreak = true;
>       str = end+1;                          // next string
>     }
>     else {
>       end = strchr(str, '\n');
>       str = end+1;                          // next string
>     }
>   }
> 
>   bool bRegenerateAll = false;
>   if (!threadList_.isEmpty() && threadList_.count() != (unsigned int)(childCount())) {
>      // a new thread came or some threads have gone
>      bRegenerateAll = true;
>   }
> 
>   // not always we have to remove all listview items, do some magic to find that out
>   if (bRegenerateAll || firstLineOfLastBacktrace_ != firstLineLeft) {
>     if (threadList_.isEmpty()) {
>       clear(); // non-threaded
>     }
>     else {
> // TODO: it aint safe because viewedThread_
> // and thread of the currently processed str can be different.
> // Hmm...we need to know which thread is meant with the call of this method
> //-----------------
>       // Since we just get the backtrace of a certain thread we must avoid removing all other possibly opened thread callstacks
>       if (!bRegenerateAll && viewedThread_) {
>         // just remove the listview items of the currently changed callstack
>         while (viewedThread_->childCount() > 0) {
>           viewedThread_->takeItem(viewedThread_->firstChild());
>         }
>       }
166,167c194,280
<         new FrameStackItem(this, frameDesc);
<     str = end+1;                          // next string
---
>         {
>         // rebuild everything
>         clear();
>         for (QStringList::Iterator it = threadList_.begin(); it != threadList_.end(); ++it) {
>           QString s = *it;
>           int idx = s.find(")");
>           if (idx != -1) {
>             s = s.left(idx+1);
>           }
>           ThreadStackItem* thread = new ThreadStackItem(this, s);
> 
>           // This indicates the current thread
>           if (s[0] == '*')
>           {
>             viewedThread_ = thread;
>             stoppedAtThread_ = thread;
>             thread->setOpen(true);
>           }
>         }
>       }
>     }
> 
>     // insert the first line
>     if (viewedThread_)
>       new FrameStackItem(viewedThread_, firstLine);
>     else
>       new FrameStackItem(this, firstLine);
> 
>     // insert the rest of the lines
>     while (char* end = strchr(str, '\n'))
>     {
>       *end = 0;                             // make it a string
>       QString frameDesc = QString(str);
>       if (*str == '#') {                     // Don't bother with extra data
>         if (viewedThread_)
>           new FrameStackItem(viewedThread_, frameDesc);
>         else
>           new FrameStackItem(this, frameDesc);
>       }
>       str = end+1;                          // next string
>     }
> 
>     firstLineOfLastBacktrace_ = firstLineLeft;
>   }
>   else {
>     // this is the optimized part, we do not have to rebuild the whole listview but only one item must be changed
> #if QT_VERSION < 300
>     QListViewItem* lvi = findItemWhichBeginsWith(firstLineLeft);
> #else
>     QListViewItem* lvi = findItem(firstLineLeft,0,Qt::BeginsWith);
> #endif
>     if (lvi) {
>       lvi->setText(0,firstLine);
>     }
>   }
> }
> 
> #if QT_VERSION < 300
> // this method is a slightly adapted downport of findItem of Qt-3.0.3,
> // just necessary because it doesn't exist in Qt-2.
> QListViewItem* FrameStack::findItemWhichBeginsWith(const QString& text) const
> {
>   if ( text.isEmpty() )
>      return 0;
> 
>   QString itmtxt;
>   QString comtxt = text;
>   comtxt = comtxt.lower();
> 
>   QListViewItem* curItem = currentItem();
>   if (!curItem)
>     curItem = viewedThread_;
>   QListViewItemIterator it(curItem);
>   QListViewItem* sentinel = 0;
>   QListViewItem* item;
> 
>   for (int pass = 0; pass < 2; pass++) {
>     while ((item = it.current()) != sentinel) {
>       itmtxt = item->text(0);
>       itmtxt = itmtxt.lower();
>       if ( itmtxt.startsWith(comtxt))
>         return item;
>       ++it;
>     }
> 
>     it = QListViewItemIterator(firstChild());
>     sentinel = curItem;
168a282
>   return 0;
169a284
> #endif
