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. QtableView, need to clear selection index after removing a row
Forum Updated to NodeBB v4.3 + New Features

QtableView, need to clear selection index after removing a row

Scheduled Pinned Locked Moved Unsolved General and Desktop
16 Posts 5 Posters 5.1k Views 1 Watching
  • 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.
  • L lansing
    19 Jun 2020, 12:34

    I have a tableview with data and a remove button. When I selected a row and clicked on the button, the row was removed with no selection in the view. But when I clicked the button again, another row was removed without me selecting anything.

    This is the remove slot function in my main dialog.

    void MyDialog::slotRemoveData()
    {
        QModelIndex index = ui->myTableView->currentIndex();
        m_myModel->removeData(index);
    }
    

    myModel.cpp

    void MyModel::removeData(const QModelIndex &parent)
    {
        if (!parent.isValid())
            return;
    
        int row = parent.row();
    
        beginRemoveRows(QModelIndex(), row, row);
        m_myData.remove(row);
        endRemoveRows();
    }
    

    I think what happen was that the currentIndex was not cleared after the first remove call, so when I called remove again, it removed the new row that took place of the index.

    There's a clearSelection() in the document but it stated that the current index will not be changed. What is the correct way to deselect it after the first remove?

    J Online
    J Online
    JonB
    wrote on 19 Jun 2020, 12:56 last edited by
    #3

    @lansing
    Purely a guess: would ui->myTableView->setCurrentIndex(QIndex()) work for you?

    1 Reply Last reply
    0
    • G gde23
      19 Jun 2020, 12:52

      you can make the current index invalid after removing the row:

      void MyDialog::slotRemoveData()
      {
          QModelIndex index = ui->myTableView->currentIndex();
          m_myModel->removeData(index);
          setCurrentIndex(QModelIndex()); 
      }
      
      L Offline
      L Offline
      lansing
      wrote on 19 Jun 2020, 13:07 last edited by
      #4

      @gde23 @JonB

      Thanks guy this works. I also want to know why it works. What does QModelIndex means when passed into setCurrentIndex()?

      J 1 Reply Last reply 19 Jun 2020, 13:54
      0
      • V Offline
        V Offline
        VRonin
        wrote on 19 Jun 2020, 13:08 last edited by VRonin
        #5

        Don't use currentIndex(). That one record the last item that was "activated", it does not record selected indexes. You should use ui->myTableView->selectionModel()->selectedIndexes() instead

        "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

        L J 2 Replies Last reply 19 Jun 2020, 13:50
        2
        • V VRonin
          19 Jun 2020, 13:08

          Don't use currentIndex(). That one record the last item that was "activated", it does not record selected indexes. You should use ui->myTableView->selectionModel()->selectedIndexes() instead

          L Offline
          L Offline
          lansing
          wrote on 19 Jun 2020, 13:50 last edited by
          #6

          @VRonin

          Hi I just tested it, this still requires to set tableView's current index after remove.

          J 1 Reply Last reply 19 Jun 2020, 13:52
          0
          • V VRonin
            19 Jun 2020, 13:08

            Don't use currentIndex(). That one record the last item that was "activated", it does not record selected indexes. You should use ui->myTableView->selectionModel()->selectedIndexes() instead

            J Online
            J Online
            JonB
            wrote on 19 Jun 2020, 13:51 last edited by
            #7

            @VRonin said in QtableView, need to clear selection index after removing a row:

            That one record the last item that was "activated"

            Thanks! I had never understood that was the definition, I don't think the docs tell you that (that I came across?), they just seem to tell you it's the "current" one!

            1 Reply Last reply
            0
            • L lansing
              19 Jun 2020, 13:50

              @VRonin

              Hi I just tested it, this still requires to set tableView's current index after remove.

              J Offline
              J Offline
              JoeCFD
              wrote on 19 Jun 2020, 13:52 last edited by JoeCFD
              #8
              This post is deleted!
              L 1 Reply Last reply 19 Jun 2020, 14:01
              0
              • L lansing
                19 Jun 2020, 13:07

                @gde23 @JonB

                Thanks guy this works. I also want to know why it works. What does QModelIndex means when passed into setCurrentIndex()?

                J Online
                J Online
                JonB
                wrote on 19 Jun 2020, 13:54 last edited by JonB
                #9

                @lansing said in QtableView, need to clear selection index after removing a row:

                What does QModelIndex means when passed into setCurrentIndex()?

                QModelIndex() is the default-constructed one, https://doc.qt.io/qt-5/qmodelindex.html#QModelIndex

                Creates a new empty model index. This type of model index is used to indicate that the position in the model is invalid.

                In your MyModel::removeData() code it would hit your if (!parent.isValid()) return;.

                [BTW: Since you have a QTableView, not a QTreeView, I don't think you're doing yourself/myself any clarity favours by naming your parameter parent here? There is no parentage, plain const QModelIndex &index would not be misleading.]

                L 1 Reply Last reply 19 Jun 2020, 14:04
                0
                • J JoeCFD
                  19 Jun 2020, 13:52

                  This post is deleted!

                  L Offline
                  L Offline
                  lansing
                  wrote on 19 Jun 2020, 14:01 last edited by
                  #10

                  @VRonin This is the code I tested

                  QModelIndexList indexList= ui->myTableView->selectionModel()->selectedIndexes();
                  
                  if (!indexList.isEmpty()){
                      m_myModel->removeData(indexList.first());
                  }
                  

                  This still doesn't deselect the index after remove.

                  V 1 Reply Last reply 19 Jun 2020, 14:24
                  0
                  • J JonB
                    19 Jun 2020, 13:54

                    @lansing said in QtableView, need to clear selection index after removing a row:

                    What does QModelIndex means when passed into setCurrentIndex()?

                    QModelIndex() is the default-constructed one, https://doc.qt.io/qt-5/qmodelindex.html#QModelIndex

                    Creates a new empty model index. This type of model index is used to indicate that the position in the model is invalid.

                    In your MyModel::removeData() code it would hit your if (!parent.isValid()) return;.

                    [BTW: Since you have a QTableView, not a QTreeView, I don't think you're doing yourself/myself any clarity favours by naming your parameter parent here? There is no parentage, plain const QModelIndex &index would not be misleading.]

                    L Offline
                    L Offline
                    lansing
                    wrote on 19 Jun 2020, 14:04 last edited by
                    #11

                    @JonB

                    Those templates were created by Qt Creator, I was just going with them without knowing much.

                    1 Reply Last reply
                    0
                    • L lansing
                      19 Jun 2020, 14:01

                      @VRonin This is the code I tested

                      QModelIndexList indexList= ui->myTableView->selectionModel()->selectedIndexes();
                      
                      if (!indexList.isEmpty()){
                          m_myModel->removeData(indexList.first());
                      }
                      

                      This still doesn't deselect the index after remove.

                      V Offline
                      V Offline
                      VRonin
                      wrote on 19 Jun 2020, 14:24 last edited by VRonin
                      #12

                      @lansing

                      const QModelIndexList indexList= ui->myTableView->selectionModel()->selectedIndexes();
                      for(auto& i : indexList)
                          m_myModel->removeData(i);
                      ui->myTableView->selectionModel()->select(ui->myTableView->selectionModel()->selection(),QItemSelectionModel::Deselect);
                      

                      "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

                      L 1 Reply Last reply 19 Jun 2020, 14:49
                      2
                      • V VRonin
                        19 Jun 2020, 14:24

                        @lansing

                        const QModelIndexList indexList= ui->myTableView->selectionModel()->selectedIndexes();
                        for(auto& i : indexList)
                            m_myModel->removeData(i);
                        ui->myTableView->selectionModel()->select(ui->myTableView->selectionModel()->selection(),QItemSelectionModel::Deselect);
                        
                        L Offline
                        L Offline
                        lansing
                        wrote on 19 Jun 2020, 14:49 last edited by
                        #13

                        @VRonin

                        I use a vector in my model to hold the data, and for some reason this code is removing 3 rows at a time.

                        1 Reply Last reply
                        0
                        • L Offline
                          L Offline
                          lansing
                          wrote on 19 Jun 2020, 15:44 last edited by
                          #14

                          I solved my last problem with a check on empty indexList and removing only indexList.first().

                              const QModelIndexList indexList= ui->myTableView->selectionModel()->selectedIndexes();
                          
                              if (indexList.isEmpty()){
                                     return;
                                  }
                          
                              m_myModel->removeData(indexList.first());
                          
                              ui->myTableView->selectionModel()->select(
                                          ui->myTableView->selectionModel()->selection(),
                                          QItemSelectionModel::Deselect);
                          

                          Now I come into another problem trying to remove all. In my model I just called vector::clear() to clear my vector whose holding the data.

                          void MyModel::clearAll()
                          {
                              if (!m_myData.isEmpty()) {
                                  m_myData.clear();
                              }
                          }
                          

                          There are two problems, I don't know what signal I should be emitting. And my view doesn't update with the model.

                          myDialog.cpp

                          void MyDialog::slotRemoveAll()
                          {
                              m_myModel->clearAll();
                          }
                          

                          After calling this slot, all my data in the model were cleared, but the table grids still remained.

                          J 1 Reply Last reply 19 Jun 2020, 16:10
                          0
                          • L lansing
                            19 Jun 2020, 15:44

                            I solved my last problem with a check on empty indexList and removing only indexList.first().

                                const QModelIndexList indexList= ui->myTableView->selectionModel()->selectedIndexes();
                            
                                if (indexList.isEmpty()){
                                       return;
                                    }
                            
                                m_myModel->removeData(indexList.first());
                            
                                ui->myTableView->selectionModel()->select(
                                            ui->myTableView->selectionModel()->selection(),
                                            QItemSelectionModel::Deselect);
                            

                            Now I come into another problem trying to remove all. In my model I just called vector::clear() to clear my vector whose holding the data.

                            void MyModel::clearAll()
                            {
                                if (!m_myData.isEmpty()) {
                                    m_myData.clear();
                                }
                            }
                            

                            There are two problems, I don't know what signal I should be emitting. And my view doesn't update with the model.

                            myDialog.cpp

                            void MyDialog::slotRemoveAll()
                            {
                                m_myModel->clearAll();
                            }
                            

                            After calling this slot, all my data in the model were cleared, but the table grids still remained.

                            J Online
                            J Online
                            JonB
                            wrote on 19 Jun 2020, 16:10 last edited by JonB
                            #15

                            @lansing said in QtableView, need to clear selection index after removing a row:

                            There are two problems, I don't know what signal I should be emitting. And my view doesn't update with the model.

                            I think these are one problem :) When the model signal is right, the view should update. You have deleted all rows, so you need to emit QAbstractItemModel::rowsRemoved(const QModelIndex &parent, int first, int last), or do begin/endRemoveRows(), with the original number of rows. Or, I think you can do QAbstractItemModel::begin/endResetModel().

                            L 1 Reply Last reply 19 Jun 2020, 18:28
                            4
                            • J JonB
                              19 Jun 2020, 16:10

                              @lansing said in QtableView, need to clear selection index after removing a row:

                              There are two problems, I don't know what signal I should be emitting. And my view doesn't update with the model.

                              I think these are one problem :) When the model signal is right, the view should update. You have deleted all rows, so you need to emit QAbstractItemModel::rowsRemoved(const QModelIndex &parent, int first, int last), or do begin/endRemoveRows(), with the original number of rows. Or, I think you can do QAbstractItemModel::begin/endResetModel().

                              L Offline
                              L Offline
                              lansing
                              wrote on 19 Jun 2020, 18:28 last edited by
                              #16

                              @JonB

                              Thank you begin/endResetModel() solved it.

                              1 Reply Last reply
                              0

                              12/16

                              19 Jun 2020, 14:24

                              • Login

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