Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Treeview remove row
QtWS25 Last Chance

Treeview remove row

Scheduled Pinned Locked Moved Solved General and Desktop
treeviewtreeview modeltreeitem
11 Posts 3 Posters 1.6k Views
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • A Offline
    A Offline
    AlexandruToma
    wrote on last edited by VRonin
    #1

    Tree model

    TreeModel::TreeModel(Context & aContext, QObject * parent)
      : QAbstractItemModel(parent)
      , mContext(aContext)
    
    {
    }
    
    TreeModel::~TreeModel()
    {
    }
    
    int TreeModel::rowCount(const QModelIndex & parent) const
    {
      const auto parentItem = getItem(parent);
    
      return parentItem ? static_cast<int>(parentItem->GetChildrenSize()) : 0;
    }
    
    int TreeModel::columnCount(const QModelIndex & parent) const
    {
      Q_UNUSED(parent);
      return mContext.GetRootClass()->GetNumberOfData();
    }
    
    QVariant TreeModel::data(const QModelIndex & index, int role) const
    {
      if (!index.isValid())
        return QVariant();
    
      if (role != Qt::DisplayRole && role != Qt::EditRole)
        return QVariant();
    
      auto item = getItem(index);
    
      if (index.column() == 0)
      {
        return QString::fromStdString(item->GetName());
      }
      else
      {
        return item->GetNumberOfStudents();
      }
    }
    
    Qt::ItemFlags TreeModel::flags(const QModelIndex & index) const
    {
      if (!index.isValid())
        return Qt::NoItemFlags;
    
      return Qt::ItemIsEditable | QAbstractItemModel::flags(index);
    }
    
    QVariant TreeModel::headerData(int section, Qt::Orientation orientation, int role) const
    {
      if (role == Qt::DisplayRole && orientation == Qt::Horizontal)
      {
        if (section == 0)
        {
          return QString("Class Name");
        }
        else if (section == 1)
        {
          return QString("Students");
        }
      }
      return QVariant();
    }
    
    bool TreeModel::setData(const QModelIndex & index, const QVariant & aClassData, int role)
    {
      if (role != Qt::EditRole)
        return false;
    
      auto item = getItem(index);
    
      switch (index.column())
      {
      case 0:
        item->SetName(aClassData.toString().toStdString());
        break;
      case 1:
        item->SetNumberOfStudents(aClassData.toInt());
        break;
      }
    
      emit dataChanged(index, index, { Qt::DisplayRole, Qt::EditRole });
    
      return true;
    }
    
    QModelIndex TreeModel::index(int row, int column, const QModelIndex & parent) const
    {
      if (parent.isValid() && parent.column() != 0)
        return QModelIndex();
    
      auto parentItem = getItem(parent);
      if (!parentItem)
        return QModelIndex();
    
      auto childItem = parentItem->GetChild(row);
      if (childItem)
        return createIndex(row, column, childItem);
      return QModelIndex();
    }
    
    QModelIndex TreeModel::parent(const QModelIndex & index) const
    {
      if (!index.isValid())
        return QModelIndex();
    
      auto childItem  = getItem(index);
      auto parentItem = childItem->GetParent();
    
      if (parentItem == mContext.GetRootClass() || !parentItem)
        return QModelIndex();
    
      return createIndex(static_cast<int>(parentItem->GetChildrenSize()), 0, parentItem);
    }
    
    Group * TreeModel::getItem(const QModelIndex & index) const
    {
      if (index.isValid())
      {
        Group * item = static_cast<Group *>(index.internalPointer());
        if (item)
          return item;
      }
    
      return mContext.GetRootClass();
    }
    
    bool TreeModel::insertRows(int position, int rows, const QModelIndex & parent)
    {
      // insert one row at position
      auto parentItem = getItem(parent);
      if (!parentItem)
        return false;
    
      beginInsertRows(parent, position, position + rows - 1);
      parentItem->AppendChild(mContext.GenerateClassId());
      endInsertRows();
    
      return true;
    }
    
    bool TreeModel::removeRows(int position, int rows, const QModelIndex & parent)
    {
      auto parentItem = getItem(parent);
      if (!parentItem)
        return false;
    
      beginRemoveRows(parent, position, position + rows - 1);
      parentItem->RemoveChild(position);
      endRemoveRows();
    
      return true;
    }
    
    -------------------------------------------- group.cpp -> tree nodes
    
    Group::Group(string aName, int aNumber, int aId, Group * aParent)
      : mName(aName)
      , mNumberOfStudents(aNumber)
      , mId(aId)
      , mParent(aParent)
    
    {
    }
    
    void Group::SetNumberOfStudents(int aNrOfStudent)
    {
      mNumberOfStudents = aNrOfStudent;
    }
    
    int Group::GetNumberOfStudents()
    {
      return mNumberOfStudents;
    }
    
    void Group::SetName(string aName)
    {
      mName = aName;
    }
    
    string Group::GetName()
    {
      return mName;
    }
    
    int Group::GetId()
    {
      return mId;
    }
    
    bool Group::operator==(const Group & aClass)
    {
      return mId == aClass.mId;
    }
    
    Group & Group::operator=(const Group & aClass)
    {
      if (this != &aClass)
      {
        this->mName             = aClass.mName;
        this->mNumberOfStudents = aClass.mNumberOfStudents;
        this->mId               = aClass.mId;
      }
    
      return *this;
    }
    
    Group::~Group()
    {
    }
    
    Group * Group::GetChild(int nr)
    {
      if (nr < 0 || nr >= mChildren.size())
        return nullptr;
      return mChildren.at(nr).get();
    }
    
    size_t Group::GetChildrenSize()
    {
      return mChildren.size();
    }
    
    int Group::GetNumberOfData()
    {
      // class name and number of students
      return 2;
    }
    
    void Group::AppendChild(int id)
    {
      unique_ptr<Group> newClass = make_unique<Group>("name", 0, id, this);
    
      mChildren.push_back(move(newClass));
    }
    
    Group * Group::GetParent()
    {
      return mParent;
    }
    
    void Group::RemoveChild(int pos)
    {
      if (pos < 0 || pos >= mChildren.size())
        return;
    
      mChildren.erase(mChildren.begin() + pos);
    }
    
    

    What I m doing wrong in this model? Sometimes not showing some nodes after I add more nodes, the other shows up but empty like setData was not called for them. And sometimes works just fine.

    1 Reply Last reply
    0
    • VRoninV Offline
      VRoninV Offline
      VRonin
      wrote on last edited by
      #2

      The first step in diagnosing a model is passing it through the model test. It usually tells you what you are doing wrong

      "La mort n'est rien, mais vivre vaincu et sans gloire, c'est mourir tous les jours"
      ~Napoleon Bonaparte

      On a crusade to banish setIndexWidget() from the holy land of Qt

      1 Reply Last reply
      3
      • A Offline
        A Offline
        AlexandruToma
        wrote on last edited by
        #3

        Qt 5.11 or later

        1. Add the QtTest module to your pro file like: QT += testlib
          How do I add this module in visual studio? I am not using qt creator and when i try to #include <QAbstractItemModelTester> i get this error "cannot open source file QAbstractItemModelTester "
        1 Reply Last reply
        0
        • VRoninV Offline
          VRoninV Offline
          VRonin
          wrote on last edited by
          #4

          I assume you have the Qt Visual Studio extension installed, if so right click on your project, go to qt project settings and, in the modules tab, tick Qt Test (remember to remove it once you are done)

          "La mort n'est rien, mais vivre vaincu et sans gloire, c'est mourir tous les jours"
          ~Napoleon Bonaparte

          On a crusade to banish setIndexWidget() from the holy land of Qt

          1 Reply Last reply
          0
          • A Offline
            A Offline
            AlexandruToma
            wrote on last edited by AlexandruToma
            #5

            Thank you very much, sir. Now I need to debug the errors. I don't get it, beside I use a unique_ptr to store nodes, the model and tree nodes are the same as in the qt tree model example.. Maybe someone has encountered this errors
            Screenshot (316).png Screenshot (317).png

            1 Reply Last reply
            0
            • VRoninV Offline
              VRoninV Offline
              VRonin
              wrote on last edited by VRonin
              #6

              Use the debugger to see what problems are being reported.
              The first screenshot is telling you that either your index() or parent() method are wrong (it checks that model->parent(model->index(row,column,idx))==idx

              The second screenshot is telling you your index() method is wrong. Passing a row, column and parent within the rowCount(parent) and columnCount(parent) constraints returns an invalid index. This is likely caused by you ignoring the parent argument in TreeModel::columnCount

              "La mort n'est rien, mais vivre vaincu et sans gloire, c'est mourir tous les jours"
              ~Napoleon Bonaparte

              On a crusade to banish setIndexWidget() from the holy land of Qt

              1 Reply Last reply
              3
              • A Offline
                A Offline
                AlexandruToma
                wrote on last edited by
                #7

                Sir, do you have any link about qt debug in visual studio?

                jsulmJ 1 Reply Last reply
                0
                • A AlexandruToma

                  Sir, do you have any link about qt debug in visual studio?

                  jsulmJ Offline
                  jsulmJ Offline
                  jsulm
                  Lifetime Qt Champion
                  wrote on last edited by
                  #8

                  @AlexandruToma said in Treeview remove row:

                  Sir, do you have any link about qt debug in visual studio?

                  Simply debug in Visual Studio. There is no such thing as "qt debug".

                  https://forum.qt.io/topic/113070/qt-code-of-conduct

                  1 Reply Last reply
                  2
                  • A Offline
                    A Offline
                    AlexandruToma
                    wrote on last edited by
                    #9

                    I got the same problem as in this topic.

                    I changed columnCount function but the errors are still there

                    int TreeModel::columnCount(const QModelIndex &parent) const
                    {
                       return (!parent.isValid() || parent.column() == 0) ? rootItem->columnCount() : 0;
                    }
                    

                    I run tests on editable tree model in qt creator and I got the same error like in my project.

                    Here is the error.

                    // Common error test #3, the second column should NOT have the same children
                    // as the first column in a row.
                    // Usually the second column shouldn't have children.
                    if (model->hasIndex(0, 1)) {
                        QModelIndex topIndex1 = model->index(0, 1, QModelIndex());
                        MODELTESTER_VERIFY(topIndex1.isValid());
                        if (model->rowCount(topIndex) > 0 && model->rowCount(topIndex1) > 0) {
                            QModelIndex childIndex = model->index(0, 0, topIndex);
                            MODELTESTER_VERIFY(childIndex.isValid());
                            ***QModelIndex childIndex1 = model->index(0, 0, topIndex1);***
                            MODELTESTER_VERIFY(childIndex1.isValid());
                            MODELTESTER_VERIFY(childIndex != childIndex1);
                        }
                    }
                    
                    1 Reply Last reply
                    0
                    • VRoninV Offline
                      VRoninV Offline
                      VRonin
                      wrote on last edited by VRonin
                      #10

                      You are right, there is a bug in the example. I opened a ticket: https://bugreports.qt.io/browse/QTBUG-92178 the correct implementation should be:

                      int TreeModel::rowCount(const QModelIndex &parent) const
                      {
                          if(parent.isValid() && parent.column()>0)
                              return 0;
                          const TreeItem *parentItem = getItem(parent);
                          return parentItem ? parentItem->childCount() : 0;
                      }
                      

                      "La mort n'est rien, mais vivre vaincu et sans gloire, c'est mourir tous les jours"
                      ~Napoleon Bonaparte

                      On a crusade to banish setIndexWidget() from the holy land of Qt

                      1 Reply Last reply
                      3
                      • A Offline
                        A Offline
                        AlexandruToma
                        wrote on last edited by
                        #11

                        @VRonin said in Treeview remove row:

                        if(parent.isValid() && parent.column()>0)
                            return 0;
                        const TreeItem *parentItem = getItem(parent);
                        return parentItem ? parentItem->childCount() : 0;
                        

                        All good now. Thank you very much, sir.

                        1 Reply Last reply
                        0

                        • Login

                        • Login or register to search.
                        • First post
                          Last post
                        0
                        • Categories
                        • Recent
                        • Tags
                        • Popular
                        • Users
                        • Groups
                        • Search
                        • Get Qt Extensions
                        • Unsolved