How do I delete all items from a QStandardItemModel
Asked Answered
R

2

6

I am having some trouble with my QStandardItemModel. What I want to do is add a list to my model, and when the list is updated, I pass the new list in the parameter, clear the old model and add the new list. This sounds simple enough but i'm coming across a bug that i can't figure out. When i add the first list to the model there is no problem, but when i add the second one, the first one is successfully deleted (I can see that in the console) but then the application crashes.

Here is my code :

void MyModel::updateList(QList<QStandardItem*> list)
{

    // Delete current model

    int rows = rowCount();
    for (int i = 0 ; i < rows ; i++)
    {
        if(item(0)->hasChildren())
        {
            int children = item(0)->rowCount();
            for (int j = 0 ; j < children ; j++)
            {
                QString name = item(0)->child(0)->accessibleText();
                qDebug()<<(name + QLatin1String("\tremoved"));
                item(0)->removeRow(0);
            }
        }
        QString itemRemoved = item(0)->accessibleText();
        qDebug()<<(itemRemoved + QLatin1String("\tremoved"));
        removeRow(0);
    }


    // Add new list to model

    for(int j=0 ; j<list.count() ; j++)
    {
        appendRow(list[j]);
        qDebug()<< (list[j]->accessibleText() + tr(" ADDED"));
    }

    printf("List UPDATED \n");
}

Obviously i have tried using the method clear(); instead of deleting row by row but it has the same result.

I don't understand why this code doesn't work.

If somebody can shed some light on the matter i would be very grateful.

Ridgeling answered 24/4, 2014 at 13:7 Comment(9)
Where exactly (and with what message) does it crash? Also, you should avoid using C-style output (printf) in C++ ;)Opinionated
There is no message, it just crashes at the first appendRow() in the for loop that adds the new list. I actually found that out by placing one printf before and one after this line and realising that only the first was printed to the consoleRidgeling
How you items hierarchy looks like? You remove sub items, but add only top level items.Bespoke
It's worth noting that using clear(); does exactly the same thing that you are doing manually (well, it also sets the rowcount and colcount to 0, which you don't), so using it is not what causes the problem. Can you show how do you fill in the model for the first time?Opinionated
Yes that is true. That is because the list in the parameter is of QStandardItem. Whilst constructing this new list, i append subitems to top level items, hence, when i add them to the model, i only need to add the top level items and the subitems are added automatically (i know this works because the first list I add is constructed this way and works fine, it is only after i delete the first list and try to add the second that i have a problem)Ridgeling
@Opinionated I have tried using clear(); but it crashes in exactly the same place. This is how I fill the model the first time, i send a list in the parameter and it is added.Ridgeling
Well, your code looks ok as it is. It's most likely that after you clear the model, it's internal state is somehow messed up (i.e. not really fully cleared), so adding new items causes it to crash. What if you try to append to invisibleRootItem() instead of the model itself?Opinionated
No, unfortunately i have already tried this and obtained the same result :(Ridgeling
This is another case in point why you absolutely, positively need an SSCCE. We'll be going in circles until you post a minimal example that actually compiles.Brelje
R
0

The problem was coming from the fact that i was adding the items from the input list directly to the new list. As the input list was created in a different class the parent of the items in it was different and when trying to delete them from the new list it made the application crash.

I resolved the issue by creating the new list from new items and just taking the text() of the old list :

void MyModel::updateList(QList<QStandardItem*> list)
{
    clear();

    for(int i=0 ; i<list.count() ; i++)
    {
        QStandardItem *l_item = new QStandardItem(list[i]->text());
        l_item->setEditable(false);
        l_item->setCheckable(true);
        appendRow(l_item);
        for (int j = 0 ; j<list[i]->rowCount() ; j++)
        {
            QStandardItem *l_subItem = new QStandardItem(list[i]->child(j)->text());
            l_subItem->setEditable(false);
            l_subItem->setCheckable(true);
            l_item->appendRow(l_subItem);
        }
    }
}

This meant that i had to run through the list of children in the input list as pointed out in one of the previous comments because by creating new items i needed to re-append them.

Thanks for all the help

Ridgeling answered 28/4, 2014 at 12:38 Comment(0)
I
8

The following code is in PyQt, however it's very similar to what you need:

model.removeRows( 0, model.rowCount() )
Intisar answered 24/11, 2015 at 14:39 Comment(0)
R
0

The problem was coming from the fact that i was adding the items from the input list directly to the new list. As the input list was created in a different class the parent of the items in it was different and when trying to delete them from the new list it made the application crash.

I resolved the issue by creating the new list from new items and just taking the text() of the old list :

void MyModel::updateList(QList<QStandardItem*> list)
{
    clear();

    for(int i=0 ; i<list.count() ; i++)
    {
        QStandardItem *l_item = new QStandardItem(list[i]->text());
        l_item->setEditable(false);
        l_item->setCheckable(true);
        appendRow(l_item);
        for (int j = 0 ; j<list[i]->rowCount() ; j++)
        {
            QStandardItem *l_subItem = new QStandardItem(list[i]->child(j)->text());
            l_subItem->setEditable(false);
            l_subItem->setCheckable(true);
            l_item->appendRow(l_subItem);
        }
    }
}

This meant that i had to run through the list of children in the input list as pointed out in one of the previous comments because by creating new items i needed to re-append them.

Thanks for all the help

Ridgeling answered 28/4, 2014 at 12:38 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.