3

I have a QTableView with 3 rows and 2 columns. (Here I am using a QStandardItemModel). I want to move up/move down a single row when a QPushButton is clicked. How can I move up/down a row in QTableView?

Thanks for your reply vahancho. I have already tried using QAbstractItemModel::moveRow, but it doesn't work:

   int currentRow = ui->tableView->currentIndex().row();
   QModelIndex sourceParent = ui->tableView->model()->index(ui->tableView->selectionModel()->currentIndex().row(),0);
   QModelIndex destinationParent = ui->tableView->model()->index(ui->tableView->selectionModel()->currentIndex().row()+1,0);
   ui->tableView->model()->moveRow(sourceParent,currentRow, destinationParent,destinationParent.row());
Emma Michelet
  • 197
  • 2
  • 6
New Moon
  • 787
  • 6
  • 21
  • 35
  • It doesn't work because it is a virtual function you have to implement it yourself. – eric Feb 22 '15 at 04:29
  • 2
    neuronet, thank you for your reply. So, are you saying that this function (`moveRow()`) does nothing if you do not implement it yourself? . So what is the idea of this function? – Angie Quijano Sep 04 '15 at 17:14

5 Answers5

6

Use Qt documentation for QStandartItemModel - QStandardItemModel Class

  1. takeRow
  2. insertRow
Angie Quijano
  • 4,167
  • 3
  • 25
  • 30
Dmitry Sazonov
  • 8,801
  • 1
  • 35
  • 61
  • i agree, `QStandardItemModel` is more convinient :) – Zaiborg Sep 12 '13 at 07:58
  • I posted solution to author, but he deleted my post. Problem was that TS didn't know about type casting and he couldn't cast QModelIndex::model() to QStandartItemModel. – Dmitry Sazonov Sep 12 '13 at 08:04
  • @SaZ who is TS, what do you mean he deleted the post, he can't do that with such low rep can he? – eric Feb 22 '15 at 04:30
  • TS == topic starter. He posted an answer, and i commented it. So he deleted his answer and my comment became invisible. – Dmitry Sazonov Feb 22 '15 at 17:46
3

If you use Qt5 you can take a look on this function:

bool QAbstractItemModel::moveRow(const QModelIndex & sourceParent, int sourceColumn, const QModelIndex & destinationParent, int destinationChild)

"On models that support this, moves sourceColumn from sourceParent to destinationChild under destinationParent. Returns true if the columns were successfully moved; otherwise returns false."

vahancho
  • 20,808
  • 3
  • 47
  • 55
3

Here is a short utility I use for moving the Qt::DisplayData of a row in QAbstractItemModel:

void CopyRowData( QAbstractItemModel * pModelDst, const QAbstractItemModel * pModelSrc, int nRowDst, int nRowSrc, const QModelIndex &parentDst /*= QModelIndex()*/, const QModelIndex &parentSrc /*= QModelIndex()*/, int nRole /*= Qt::DisplayRole*/ )
{
    if (parentSrc.isValid())
        assert(parentSrc.model() == pModelSrc);
    if (parentDst.isValid())
        assert(parentDst.model() == pModelDst);

    int nCols = pModelSrc->columnCount(parentSrc);

    for (int i = 0; i < nCols ; ++i)
        pModelDst->setData(pModelDst->index(nRowDst, i, parentDst), pModelSrc->index(nRowSrc, i, parentSrc).data(nRole), nRole);
}

bool MoveModelRows( QAbstractItemModel * pModel, int nSrcRow, int nDstRow, int nCount /*= 1*/, const QModelIndex &parent /*= QModelIndex()*/ )
{
    if (nSrcRow < 0 || nSrcRow >= pModel->rowCount(parent) ||
        nDstRow < 0 || nDstRow >= pModel->rowCount(parent))
        return false;

    if (nSrcRow == nDstRow)
        return true;

    int nDstRowNew = nSrcRow > nDstRow ? nDstRow : nDstRow + 1;

    if (!pModel->insertRows(nDstRowNew, nCount, parent))
        return false;

    int nSrcRowNew = nSrcRow > nDstRow ? nSrcRow + nCount : nSrcRow;

    for (int i = 0; i < nCount; ++i)
        CopyRowData(pModel, pModel, nDstRowNew + i, nSrcRowNew + i, parent, parent);

    pModel->removeRows(nSrcRowNew, nCount, parent);

    return true;
}
Uga Buga
  • 1,724
  • 3
  • 19
  • 38
0

Using the idea that SaZ said:

Use Qt documentation for QStandartItemModel - QStandardItemModel Class

  1. takeRow
  2. insertRow

This is the code I did for this purpose:

QModelIndexList selection = ui->tableView->selectionModel()->selectedRows();
int row = selection[0].row();
QList<QStandardItem*> itemList = ui->tableView->model()->takeRow(row);
ui->tableView->model()->insertRow(row-1,itemList);

I hope this help you.

Angie Quijano
  • 4,167
  • 3
  • 25
  • 30
-1

I think this would help:

for(int colId=0;colId<ui->tableWidget->columnCount();++colId)
{
    QTableWidgetItem *item1=new QTableWidgetItem( *ui->tableWidget->item(id_row1,colId) );
    QTableWidgetItem *item2=new QTableWidgetItem( *ui->tableWidget->item(id_row2,colId) );

    ui->tableWidget->setItem(id_row1,colId, item2 );
    ui->tableWidget->setItem(id_row2,colId, item1 );
}
OLS
  • 1