QTreeWidget from my QMap<int, QTreeWidgetItem*> populate only once



  • Hi.
    I have a QMap<int, QTreeWidgetItem*> where i have my items.
    Also i have a QTabWidget, when i insert a tab (on_btnMyTree_clicked()) QTreeWidget populate good. But when i delete a tab and insert a tab again QTreeWidget is empty.

    //create items

    for (int i = 0; i < treeList.size(); i++) {
        ForTree &temp = treeList[i];
        auto item = new QTreeWidgetItem(QStringList() << temp.Name);
        item->setCheckState(0, Qt::Unchecked);
        item->setWhatsThis(0, QString::number(temp.ParentUID));
        globalall->tree[temp.UID] = item;
    }
    

    //insert tab from MainWindow

    void MainWindow::on_btnMyTree_clicked()
    {
        if (wdgTemplate) {
            ui->tabWidget->setCurrentWidget(wdgTemplate);
            return;
        }
    
        wdgTemplate = new MainWidget(this);
        ui->tabWidget->addTab(wdgTemplate, "შაბლონები");
        ui->tabWidget->setCurrentWidget(wdgTemplate);
    }
    

    //MainWidget constructor

    MainWidget::MainWidget(QWidget *parent) :
        QWidget(parent),
        ui(new Ui::MainWidget)
    {
        ui->setupUi(this);
    
        objTree = new wdgTree(this);
    
        ui->bgTree->addWidget(objTree);
    }
    

    //wdgTree

    #include "wdgtree.h"
    #include "ui_wdgtree.h"
    
    wdgTree::wdgTree(QWidget *parent) :
        QWidget(parent),
        ui(new Ui::wdgTree)
    {
        ui->setupUi(this);
    
        ui->treeWidget->setColumnCount(1);
        ui->treeWidget->setColumnWidth(0, ui->treeWidget->width() - 30);
        ui->treeWidget->setContextMenuPolicy(Qt::CustomContextMenu);
        ui->treeWidget->setHeaderLabels(QStringList() << "შაბლონები");
        ui->treeWidget->header()->setFixedHeight(25);
    
        QMap<int, QTreeWidgetItem*> &items = globalall->tree;
    
        for (auto it = items.begin(); it != items.end(); it++) {
            ui->treeWidget->addTopLevelItem(it.value());
            it.value()->setExpanded(true);
        }
    }
    


  • Documantation says:

    QTreeWidget::~QTreeWidget()
    
    Destroys the tree widget and all its items.
    

    I think, when treeWidget is deleted, my items in my QMap are destroyed...

    But

        for (auto it = items.begin(); it != items.end(); it++) {
            ui->treeWidget->addTopLevelItem(it.value());
            it.value()->setExpanded(true);
            qDebug() << it.value()->whatThis(0);
        }
    

    its printed My items...
    What happend?


  • Moderators

    @Taz742 Did you delete the tree widget before printing the items?



  • @jsulm never


  • Moderators

    @Taz742 Then it's fine, right? Or do I misunderstand something? If ~QTreeWidget() isn't called then it does not delete anything.



  • @jsulm said in QTreeWidget from my QMap<int, QTreeWidgetItem*> populate only once:

    Then it's fine, right?

    Yes.

    @jsulm said in QTreeWidget from my QMap<int, QTreeWidgetItem*> populate only once:

    If ~QTreeWidget() isn't called then it does not delete anything.

    I also dont know what happend..


  • Moderators

    @Taz742 "its printed My items...
    What happend" - to be honest I don't understand what you mean. What happened and what were you expecting to happen?



  • @jsulm
    when I click on the button I can see treewidgetitems, then I close tab and click on this button again but this treewidgetitems is not shown.


  • Moderators

    @Taz742 said in QTreeWidget from my QMap<int, QTreeWidgetItem*> populate only once:

    then I close tab

    I guess if you close the tab then the tab and its content (tree view) are deleted?



  • @jsulm
    First click on my button
    alt text

    Result is good, i have 2 treeitem:
    alt text

    now close this tab and click again my button and insert tab, result is:
    alt text


  • Moderators

    @Taz742 You should debug your app to see what happens.



  • @jsulm
    Of course i tryed...

        for (auto it = items.begin(); it != items.end(); it++) {
            ui->treeWidget->addTopLevelItem(it.value());
            it.value()->setExpanded(true);
        }
    

    Its entered in my loop, everything is done without a problem but i can't see my treeitems.
    Also i tryed

    qDebug() << ui->treeWidget->topLevelItemsCount();
    

    after end loop, and result is 0.



  • Here are you sure your wdgTemplate is nullptr after closing it ? or when close is activated are you sure you handled to not delete the closed tab and its data ?

     if (wdgTemplate) {
            ui->tabWidget->setCurrentWidget(wdgTemplate);
            return;
        }
    


  • @GeekOwL said in QTreeWidget from my QMap<int, QTreeWidgetItem*> populate only once:

    Here are you sure your wdgTemplate is nullptr after closing it ?

    Yes.

        QObject::connect(this->ui->tabWidget, &QTabWidget::tabCloseRequested, this, [=](int index) {
            if (index != ui->tabWidget->indexOf(dlg)) {
                if(ui->tabWidget->widget(index) == dlgRep) {
                    ui->tabWidget->removeTab(index);
                    dlgRep = NULL;
                } else if (ui->tabWidget->widget(index) == wdgTemplate) {
                    ui->tabWidget->removeTab(index);
                    wdgTemplate = NULL;
                }
            }
        });
    

    @GeekOwL said in QTreeWidget from my QMap<int, QTreeWidgetItem*> populate only once:

    or when close is activated are you sure you handled to not delete the closed tab and its data

    I dont know... I have no answer to this question.



  • I replace my code, i create QtreeWidgetItem only constructor, i have a following code and its work fine:

    QMap<int, ForTree> &items = globalall->tree;
    auto it = items.begin();
    auto &&topItem = new MyTree(it.value().Name, it.value().UID, it.value().Pause);
    topItem->setExpanded(true);
    ui->treeWidget->addTopLevelItem(topItem);
    this->mpTree[it.key()] = topItem;
    
    it++;
    for (; it != items.end(); it++) {
        MyTree *m_item = new MyTree(it.value().Name, it.value().UID, it.value().Pause);
        m_item->setExpanded(true);
        this->mpTree[it.value().ParentUID]->addChild(m_item);
        this->mpTree[it.key()] = m_item;
    }
    

    MyTree is a my class, sub class of QTreeWidgetItem:

    MyTree::MyTree(QVariant value, int UID, bool checked, QTreeWidgetItem *parent) : QTreeWidgetItem(parent)
    {
        this->m_value = value;
        this->m_parent = static_cast<MyTree*>(parent);
        this->m_UID = UID;
        this->m_checked = checked;
    
        this->setData(0, Qt::EditRole, value);
        this->setIcon(0, QIcon(":/SMSicons/folder.png"));
        this->setCheckState(0, (checked ^ 1) ? Qt::Checked : Qt::Unchecked);
    }
    
    • But I still wonder what was the problem?

    • If my treeItems were destroyed with the tree, why i have items in my QMap<> ?


  • Moderators

    @Taz742 said in QTreeWidget from my QMap<int, QTreeWidgetItem*> populate only once:

    MyTree *m_item = new MyTree(it.value().Name, it.value().UID, it.value().Pause);

    You don't provide a parent and I'm not sure the QTreeWidget takes the ownership of the children if you add them. If not then it would explain why they are still there.



  • @jsulm
    Please leave it for a while.
    Think about the problem only, because if i use QTreeWidgetItem and not MyTree i have the same problem..


  • Qt Champions 2017

    Hi
    I was thinking:

    If the TreeWidget didnt not take ownership of the items, then any normal use case would leak.
    So if the treewidget is deleted, it will delete its items too.

    If you have a QMap with pointers to the items.
    You map will still have the items * pointer but now they point to deleted QtreeWidgetItem (child)
    if used once/given to a TreeWidget and this TreeWidget gets deleted.



  • @mrjj
    Yes supposedly.


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.