]> git.cworth.org Git - vogl/commitdiff
UI: Fix issue #20: Search in the editor really slow
authorPeterLValve <peterl@valvesoftware.com>
Tue, 18 Mar 2014 22:24:24 +0000 (15:24 -0700)
committerCarl Worth <cworth@cworth.org>
Tue, 1 Apr 2014 19:37:29 +0000 (12:37 -0700)
* Instead of selecting all the rows which match the search string,
  the tree view now highlights those rows which match and are visible.
* If the user presses [enter], the first matching row (if one exists) will
  be scrolled into view and selected.
* Continually pressing enter will cycle through each match, in the same way
  that clicking the "Next" button works.
* If there are no matching items when the user presses [enter], the background to the search textbox will turn red.
  It will restore to its previous color when the user next edits the text.

src/vogleditor/vogleditor.cpp
src/vogleditor/vogleditor.h
src/vogleditor/vogleditor_qapicalltreemodel.cpp
src/vogleditor/vogleditor_qapicalltreemodel.h

index a7c199cabdca2e3ffd166e834d2471076bdeeb89..ea33ffa184714fef249f3354ad2075b11131ad2a 100644 (file)
@@ -132,6 +132,9 @@ VoglEditor::VoglEditor(QWidget *parent) :
    m_statusLabel->setBaseSize(150, 12);
    ui->statusBar->addWidget(m_statusLabel, 1);
 
    m_statusLabel->setBaseSize(150, 12);
    ui->statusBar->addWidget(m_statusLabel, 1);
 
+   // cache the original background color of the search text box
+   m_searchTextboxBackgroundColor = ui->searchTextBox->palette().base().color();
+
    // setup framebuffer tab
    QGridLayout* framebufferTab_layout = new QGridLayout;
    m_framebufferExplorer = new vogleditor_QFramebufferExplorer(ui->framebufferTab);
    // setup framebuffer tab
    QGridLayout* framebufferTab_layout = new QGridLayout;
    m_framebufferExplorer = new vogleditor_QFramebufferExplorer(ui->framebufferTab);
@@ -348,7 +351,6 @@ void VoglEditor::close_trace_file()
       m_openFilename.clear();
       m_backtraceToJsonMap.clear();
       m_backtraceDoc.clear();
       m_openFilename.clear();
       m_backtraceToJsonMap.clear();
       m_backtraceDoc.clear();
-      m_searchApicallResults.clear();
 
       reset_tracefile_ui();
 
 
       reset_tracefile_ui();
 
@@ -1632,71 +1634,23 @@ void VoglEditor::selectApicallModelIndex(QModelIndex index, bool scrollTo, bool
     {
         ui->treeView->setCurrentIndex(index);
     }
     {
         ui->treeView->setCurrentIndex(index);
     }
-
-    if (m_searchApicallResults.size() > 0 && !ui->searchTextBox->text().isEmpty())
-    {
-        QItemSelectionModel* pSelection = ui->treeView->selectionModel();
-        for (int i = 0; i < m_searchApicallResults.size(); i++)
-        {
-            pSelection->select(m_searchApicallResults[i], QItemSelectionModel::Select | QItemSelectionModel::Rows);
-        }
-        ui->treeView->setSelectionModel(pSelection);
-    }
 }
 
 void VoglEditor::on_searchTextBox_textChanged(const QString &searchText)
 {
 }
 
 void VoglEditor::on_searchTextBox_textChanged(const QString &searchText)
 {
-    QModelIndex curSearchIndex = ui->treeView->currentIndex();
-    if (curSearchIndex.isValid() == false)
-    {
-        return;
-    }
-
-    // store original background color of the search text box so that it can be turned to red and later restored.
-    static const QColor sOriginalTextBoxBackground = ui->searchTextBox->palette().base().color();
-
-    // clear previous items
-    QItemSelectionModel* pSelection = ui->treeView->selectionModel();
-    if (pSelection != NULL)
-    {
-        for (int i = 0; i < m_searchApicallResults.size(); i++)
-        {
-            pSelection->select(m_searchApicallResults[i], QItemSelectionModel::Clear | QItemSelectionModel::Rows);
-        }
-        ui->treeView->setSelectionModel(pSelection);
-    }
+    QPalette palette(ui->searchTextBox->palette());
+    palette.setColor(QPalette::Base, m_searchTextboxBackgroundColor);
+    ui->searchTextBox->setPalette(palette);
 
 
-    // find new matches
-    m_searchApicallResults.clear();
     if (m_pApicallTreeModel != NULL)
     {
     if (m_pApicallTreeModel != NULL)
     {
-        m_searchApicallResults = m_pApicallTreeModel->find_search_matches(searchText);
+        m_pApicallTreeModel->set_highlight_search_string(searchText);
     }
 
     }
 
-    // if there are matches, restore the textbox background to its original color
-    if (m_searchApicallResults.size() > 0)
-    {
-        QPalette palette(ui->searchTextBox->palette());
-        palette.setColor(QPalette::Base, sOriginalTextBoxBackground);
-        ui->searchTextBox->setPalette(palette);
-    }
-
-    // select new items
-    if (!searchText.isEmpty())
-    {
-        if (m_searchApicallResults.size() > 0)
-        {
-            // scroll to the first result, but don't select it
-            selectApicallModelIndex(m_searchApicallResults[0], true, false);
-        }
-        else
-        {
-            // no items were found, so set the textbox background to red
-            QPalette palette(ui->searchTextBox->palette());
-            palette.setColor(QPalette::Base, Qt::red);
-            ui->searchTextBox->setPalette(palette);
-        }
-    }
+    // need to briefly give the treeview focus so that it properly redraws and highlights the matching rows
+    // then return focus to the search textbox so that typed keys are not lost
+    ui->treeView->setFocus();
+    ui->searchTextBox->setFocus();
 }
 
 void VoglEditor::on_searchNextButton_clicked()
 }
 
 void VoglEditor::on_searchNextButton_clicked()
@@ -1704,7 +1658,11 @@ void VoglEditor::on_searchNextButton_clicked()
     if (m_pApicallTreeModel != NULL)
     {
         QModelIndex index = m_pApicallTreeModel->find_next_search_result(m_pCurrentCallTreeItem, ui->searchTextBox->text());
     if (m_pApicallTreeModel != NULL)
     {
         QModelIndex index = m_pApicallTreeModel->find_next_search_result(m_pCurrentCallTreeItem, ui->searchTextBox->text());
-        selectApicallModelIndex(index, true, true);
+        if (index.isValid())
+        {
+            selectApicallModelIndex(index, true, true);
+            ui->treeView->setFocus();
+        }
     }
 }
 
     }
 }
 
@@ -1713,7 +1671,11 @@ void VoglEditor::on_searchPrevButton_clicked()
     if (m_pApicallTreeModel != NULL)
     {
         QModelIndex index = m_pApicallTreeModel->find_prev_search_result(m_pCurrentCallTreeItem, ui->searchTextBox->text());
     if (m_pApicallTreeModel != NULL)
     {
         QModelIndex index = m_pApicallTreeModel->find_prev_search_result(m_pCurrentCallTreeItem, ui->searchTextBox->text());
-        selectApicallModelIndex(index, true, true);
+        if (index.isValid())
+        {
+            selectApicallModelIndex(index, true, true);
+            ui->treeView->setFocus();
+        }
     }
 }
 
     }
 }
 
@@ -1722,8 +1684,11 @@ void VoglEditor::on_prevSnapshotButton_clicked()
     if (m_pApicallTreeModel != NULL)
     {
         vogleditor_apiCallTreeItem* pPrevItemWithSnapshot = m_pApicallTreeModel->find_prev_snapshot(m_pCurrentCallTreeItem);
     if (m_pApicallTreeModel != NULL)
     {
         vogleditor_apiCallTreeItem* pPrevItemWithSnapshot = m_pApicallTreeModel->find_prev_snapshot(m_pCurrentCallTreeItem);
-        selectApicallModelIndex(m_pApicallTreeModel->indexOf(pPrevItemWithSnapshot), true, true);
-        ui->treeView->setFocus();
+        if (pPrevItemWithSnapshot != NULL)
+        {
+            selectApicallModelIndex(m_pApicallTreeModel->indexOf(pPrevItemWithSnapshot), true, true);
+            ui->treeView->setFocus();
+        }
     }
 }
 
     }
 }
 
@@ -1732,8 +1697,11 @@ void VoglEditor::on_nextSnapshotButton_clicked()
     if (m_pApicallTreeModel != NULL)
     {
         vogleditor_apiCallTreeItem* pNextItemWithSnapshot = m_pApicallTreeModel->find_next_snapshot(m_pCurrentCallTreeItem);
     if (m_pApicallTreeModel != NULL)
     {
         vogleditor_apiCallTreeItem* pNextItemWithSnapshot = m_pApicallTreeModel->find_next_snapshot(m_pCurrentCallTreeItem);
-        selectApicallModelIndex(m_pApicallTreeModel->indexOf(pNextItemWithSnapshot), true, true);
-        ui->treeView->setFocus();
+        if (pNextItemWithSnapshot != NULL)
+        {
+            selectApicallModelIndex(m_pApicallTreeModel->indexOf(pNextItemWithSnapshot), true, true);
+            ui->treeView->setFocus();
+        }
     }
 }
 
     }
 }
 
@@ -1742,8 +1710,11 @@ void VoglEditor::on_prevDrawcallButton_clicked()
     if (m_pApicallTreeModel != NULL)
     {
         vogleditor_apiCallTreeItem* pPrevItem = m_pApicallTreeModel->find_prev_drawcall(m_pCurrentCallTreeItem);
     if (m_pApicallTreeModel != NULL)
     {
         vogleditor_apiCallTreeItem* pPrevItem = m_pApicallTreeModel->find_prev_drawcall(m_pCurrentCallTreeItem);
-        selectApicallModelIndex(m_pApicallTreeModel->indexOf(pPrevItem), true, true);
-        ui->treeView->setFocus();
+        if (pPrevItem != NULL)
+        {
+            selectApicallModelIndex(m_pApicallTreeModel->indexOf(pPrevItem), true, true);
+            ui->treeView->setFocus();
+        }
     }
 }
 
     }
 }
 
@@ -1752,12 +1723,14 @@ void VoglEditor::on_nextDrawcallButton_clicked()
     if (m_pApicallTreeModel != NULL)
     {
         vogleditor_apiCallTreeItem* pNextItem = m_pApicallTreeModel->find_next_drawcall(m_pCurrentCallTreeItem);
     if (m_pApicallTreeModel != NULL)
     {
         vogleditor_apiCallTreeItem* pNextItem = m_pApicallTreeModel->find_next_drawcall(m_pCurrentCallTreeItem);
-        selectApicallModelIndex(m_pApicallTreeModel->indexOf(pNextItem), true, true);
-        ui->treeView->setFocus();
+        if (pNextItem != NULL)
+        {
+            selectApicallModelIndex(m_pApicallTreeModel->indexOf(pNextItem), true, true);
+            ui->treeView->setFocus();
+        }
     }
 }
 
     }
 }
 
-
 void VoglEditor::on_program_edited(vogl_program_state* pNewProgramState)
 {
     VOGL_NOTE_UNUSED(pNewProgramState);
 void VoglEditor::on_program_edited(vogl_program_state* pNewProgramState)
 {
     VOGL_NOTE_UNUSED(pNewProgramState);
@@ -1841,3 +1814,23 @@ void VoglEditor::on_actionOpen_Session_triggered()
 
     setCursor(origCursor);
 }
 
     setCursor(origCursor);
 }
+
+void VoglEditor::on_searchTextBox_returnPressed()
+{
+    if (m_pApicallTreeModel != NULL)
+    {
+        QModelIndex index = m_pApicallTreeModel->find_next_search_result(m_pCurrentCallTreeItem, ui->searchTextBox->text());
+        if (index.isValid())
+        {
+            // a valid item was found, scroll to it and select it
+            selectApicallModelIndex(index, true, true);
+        }
+        else
+        {
+            // no items were found, so set the textbox background to red (it will get cleared to the original color if the user edits the search text)
+            QPalette palette(ui->searchTextBox->palette());
+            palette.setColor(QPalette::Base, Qt::red);
+            ui->searchTextBox->setPalette(palette);
+        }
+    }
+}
index ad007e2ba8b65c0f3382350f010cf88b473486e4..30ffd589952341b47ccda95708829d227989bf9e 100644 (file)
@@ -110,6 +110,8 @@ private slots:
 
    void on_actionOpen_Session_triggered();
 
 
    void on_actionOpen_Session_triggered();
 
+   void on_searchTextBox_returnPressed();
+
 private:
    Ui::VoglEditor* ui;
 
 private:
    Ui::VoglEditor* ui;
 
@@ -166,8 +168,7 @@ private:
    vogleditor_apiCallTimelineModel* m_pTimelineModel;
 
    vogleditor_QApiCallTreeModel* m_pApicallTreeModel;
    vogleditor_apiCallTimelineModel* m_pTimelineModel;
 
    vogleditor_QApiCallTreeModel* m_pApicallTreeModel;
-
-   QModelIndexList m_searchApicallResults;
+   QColor m_searchTextboxBackgroundColor;
 };
 
 #endif // VOGLEDITOR_H
 };
 
 #endif // VOGLEDITOR_H
index e34cc5b531611290f6f33ca173cc4c298d9600ee..e661f1cdd8fd217e0b5397711dfea99e49643c96 100644 (file)
@@ -312,9 +312,23 @@ QVariant vogleditor_QApiCallTreeModel::data(const QModelIndex &index, int role)
     if (!index.isValid())
         return QVariant();
 
     if (!index.isValid())
         return QVariant();
 
-    vogleditor_apiCallTreeItem *item = static_cast<vogleditor_apiCallTreeItem*>(index.internalPointer());
+    vogleditor_apiCallTreeItem* pItem = static_cast<vogleditor_apiCallTreeItem*>(index.internalPointer());
 
 
-    return item->columnData(index.column(), role);
+    // highlight the API call cell if it has a substring which matches the searchString
+    if (role == Qt::BackgroundRole && index.column() == VOGL_ACTC_APICALL)
+    {
+        if (!m_searchString.isEmpty())
+        {
+            QVariant data = pItem->columnData(VOGL_ACTC_APICALL, Qt::DisplayRole);
+            QString string = data.toString();
+            if (string.contains(m_searchString, Qt::CaseInsensitive))
+            {
+                return QColor(Qt::yellow);
+            }
+        }
+    }
+
+    return pItem->columnData(index.column(), role);
 }
 
 Qt::ItemFlags vogleditor_QApiCallTreeModel::flags(const QModelIndex &index) const
 }
 
 Qt::ItemFlags vogleditor_QApiCallTreeModel::flags(const QModelIndex &index) const
@@ -334,44 +348,35 @@ QVariant vogleditor_QApiCallTreeModel::headerData(int section, Qt::Orientation o
     return QVariant();
 }
 
     return QVariant();
 }
 
-QModelIndexList vogleditor_QApiCallTreeModel::find_search_matches(const QString searchText)
+void vogleditor_QApiCallTreeModel::set_highlight_search_string(const QString searchString)
+{
+    m_searchString = searchString;
+}
+
+QModelIndex vogleditor_QApiCallTreeModel::find_prev_search_result(vogleditor_apiCallTreeItem* start, const QString searchText)
 {
     QLinkedListIterator<vogleditor_apiCallTreeItem*> iter(m_itemList);
 
 {
     QLinkedListIterator<vogleditor_apiCallTreeItem*> iter(m_itemList);
 
-    QModelIndexList matches;
-    // iterate through all items and find matching text
-    while (iter.hasNext())
+    if (start != NULL)
     {
     {
-        vogleditor_apiCallTreeItem* pItem = iter.peekNext();
-        QVariant data = pItem->columnData(VOGL_ACTC_APICALL, Qt::DisplayRole);
-        QString string = data.toString();
-        if (string.contains(searchText, Qt::CaseInsensitive))
+        if (iter.findNext(start) == false)
         {
         {
-            matches.push_back(indexOf(pItem));
+            // the object wasn't found in the list, so return a default (invalid) item
+            return QModelIndex();
         }
 
         }
 
-        iter.next();
+        // need to back up past the current item
+        iter.previous();
     }
     }
-
-    return matches;
-}
-
-QModelIndex vogleditor_QApiCallTreeModel::find_prev_search_result(vogleditor_apiCallTreeItem* start, const QString searchText)
-{
-    QLinkedListIterator<vogleditor_apiCallTreeItem*> iter(m_itemList);
-
-    if (iter.findNext(start) == false)
+    else
     {
     {
-        // the object wasn't found in the list, so just return the same item
-        return indexOf(start);
+        // set the iterator to the back so that searching starts from the end of the list
+        iter.toBack();
     }
 
     }
 
-    // need to back up past the current item
-    iter.previous();
-
     // now the iterator is pointing to the desired start object in the list,
     // continually check the prev item and find one with a snapshot
     // now the iterator is pointing to the desired start object in the list,
     // continually check the prev item and find one with a snapshot
-    vogleditor_apiCallTreeItem* pFound = start;
+    vogleditor_apiCallTreeItem* pFound = NULL;
     while (iter.hasPrevious())
     {
         vogleditor_apiCallTreeItem* pItem = iter.peekPrevious();
     while (iter.hasPrevious())
     {
         vogleditor_apiCallTreeItem* pItem = iter.peekPrevious();
@@ -391,18 +396,20 @@ QModelIndex vogleditor_QApiCallTreeModel::find_prev_search_result(vogleditor_api
 
 QModelIndex vogleditor_QApiCallTreeModel::find_next_search_result(vogleditor_apiCallTreeItem* start, const QString searchText)
 {
 
 QModelIndex vogleditor_QApiCallTreeModel::find_next_search_result(vogleditor_apiCallTreeItem* start, const QString searchText)
 {
-
     QLinkedListIterator<vogleditor_apiCallTreeItem*> iter(m_itemList);
 
     QLinkedListIterator<vogleditor_apiCallTreeItem*> iter(m_itemList);
 
-    if (iter.findNext(start) == false)
+    if (start != NULL)
     {
     {
-        // the object wasn't found in the list, so just return the same item
-        return indexOf(start);
+        if (iter.findNext(start) == false)
+        {
+            // the object wasn't found in the list, so return a default (invalid) item
+            return QModelIndex();
+        }
     }
 
     // now the iterator is pointing to the desired start object in the list,
     // continually check the next item and find one with a snapshot
     }
 
     // now the iterator is pointing to the desired start object in the list,
     // continually check the next item and find one with a snapshot
-    vogleditor_apiCallTreeItem* pFound = start;
+    vogleditor_apiCallTreeItem* pFound = NULL;
     while (iter.hasNext())
     {
         vogleditor_apiCallTreeItem* pItem = iter.peekNext();
     while (iter.hasNext())
     {
         vogleditor_apiCallTreeItem* pItem = iter.peekNext();
@@ -424,18 +431,26 @@ vogleditor_apiCallTreeItem* vogleditor_QApiCallTreeModel::find_prev_snapshot(vog
 {
     QLinkedListIterator<vogleditor_apiCallTreeItem*> iter(m_itemList);
 
 {
     QLinkedListIterator<vogleditor_apiCallTreeItem*> iter(m_itemList);
 
-    if (iter.findNext(start) == false)
+    if (start != NULL)
     {
     {
-        // the object wasn't found in the list, so just return the same item
-        return start;
-    }
+        if (iter.findNext(start) == false)
+        {
+            // the object wasn't found in the list
+            return NULL;
+        }
 
 
-    // need to back up past the current item
-    iter.previous();
+        // need to back up past the current item
+        iter.previous();
+    }
+    else
+    {
+        // set the iterator to the back so that searching starts from the end of the list
+        iter.toBack();
+    }
 
     // now the iterator is pointing to the desired start object in the list,
     // continually check the prev item and find one with a snapshot
 
     // now the iterator is pointing to the desired start object in the list,
     // continually check the prev item and find one with a snapshot
-    vogleditor_apiCallTreeItem* pFound = start;
+    vogleditor_apiCallTreeItem* pFound = NULL;
     while (iter.hasPrevious())
     {
         if (iter.peekPrevious()->has_snapshot())
     while (iter.hasPrevious())
     {
         if (iter.peekPrevious()->has_snapshot())
@@ -459,14 +474,14 @@ vogleditor_apiCallTreeItem* vogleditor_QApiCallTreeModel::find_next_snapshot(vog
     {
         if (iter.findNext(start) == false)
         {
     {
         if (iter.findNext(start) == false)
         {
-            // the object wasn't found in the list, so just return the same item
-            return start;
+            // the object wasn't found in the list
+            return NULL;
         }
     }
 
     // now the iterator is pointing to the desired start object in the list,
     // continually check the next item and find one with a snapshot
         }
     }
 
     // now the iterator is pointing to the desired start object in the list,
     // continually check the next item and find one with a snapshot
-    vogleditor_apiCallTreeItem* pFound = start;
+    vogleditor_apiCallTreeItem* pFound = NULL;
     while (iter.hasNext())
     {
         if (iter.peekNext()->has_snapshot())
     while (iter.hasNext())
     {
         if (iter.peekNext()->has_snapshot())
@@ -486,18 +501,26 @@ vogleditor_apiCallTreeItem *vogleditor_QApiCallTreeModel::find_prev_drawcall(vog
 {
     QLinkedListIterator<vogleditor_apiCallTreeItem*> iter(m_itemList);
 
 {
     QLinkedListIterator<vogleditor_apiCallTreeItem*> iter(m_itemList);
 
-    if (iter.findNext(start) == false)
+    if (start != NULL)
     {
     {
-        // the object wasn't found in the list, so just return the same item
-        return start;
-    }
+        if (iter.findNext(start) == false)
+        {
+            // the object wasn't found in the list
+            return NULL;
+        }
 
 
-    // need to back up past the current item
-    iter.previous();
+        // need to back up past the current item
+        iter.previous();
+    }
+    else
+    {
+        // set the iterator to the back so that searching starts from the end of the list
+        iter.toBack();
+    }
 
     // now the iterator is pointing to the desired start object in the list,
     // continually check the prev item and find one with a snapshot
 
     // now the iterator is pointing to the desired start object in the list,
     // continually check the prev item and find one with a snapshot
-    vogleditor_apiCallTreeItem* pFound = start;
+    vogleditor_apiCallTreeItem* pFound = NULL;
     while (iter.hasPrevious())
     {
         vogleditor_apiCallTreeItem* pItem = iter.peekPrevious();
     while (iter.hasPrevious())
     {
         vogleditor_apiCallTreeItem* pItem = iter.peekPrevious();
@@ -524,13 +547,13 @@ vogleditor_apiCallTreeItem *vogleditor_QApiCallTreeModel::find_next_drawcall(vog
 
     if (iter.findNext(start) == false)
     {
 
     if (iter.findNext(start) == false)
     {
-        // the object wasn't found in the list, so just return the same item
-        return start;
+        // the object wasn't found in the list
+        return NULL;
     }
 
     // now the iterator is pointing to the desired start object in the list,
     // continually check the next item and find one with a snapshot
     }
 
     // now the iterator is pointing to the desired start object in the list,
     // continually check the next item and find one with a snapshot
-    vogleditor_apiCallTreeItem* pFound = start;
+    vogleditor_apiCallTreeItem* pFound = NULL;
     while (iter.hasNext())
     {
         vogleditor_apiCallTreeItem* pItem = iter.peekNext();
     while (iter.hasNext())
     {
         vogleditor_apiCallTreeItem* pItem = iter.peekNext();
index 91305c86661a4ff3014b43f69774c185485ee5a0..dab3da9100f3703a98d726d0f82ebb91c94a9a12 100644 (file)
@@ -61,7 +61,7 @@ public:
       return m_rootItem;
    }
 
       return m_rootItem;
    }
 
-   QModelIndexList find_search_matches(const QString searchText);
+   void set_highlight_search_string(const QString searchString);
    QModelIndex find_prev_search_result(vogleditor_apiCallTreeItem* start, const QString searchText);
    QModelIndex find_next_search_result(vogleditor_apiCallTreeItem* start, const QString searchText);
 
    QModelIndex find_prev_search_result(vogleditor_apiCallTreeItem* start, const QString searchText);
    QModelIndex find_next_search_result(vogleditor_apiCallTreeItem* start, const QString searchText);
 
@@ -82,6 +82,7 @@ private:
    vogleditor_apiCallTreeItem* m_rootItem;
    vogl_ctypes m_trace_ctypes;
    QLinkedList<vogleditor_apiCallTreeItem*> m_itemList;
    vogleditor_apiCallTreeItem* m_rootItem;
    vogl_ctypes m_trace_ctypes;
    QLinkedList<vogleditor_apiCallTreeItem*> m_itemList;
+   QString m_searchString;
 
    void setupModelData(vogl_trace_file_reader* pTrace_reader, vogleditor_apiCallTreeItem* parent);
 
 
    void setupModelData(vogl_trace_file_reader* pTrace_reader, vogleditor_apiCallTreeItem* parent);