Solved QTableView move rows and update model
-
Hi all,
With the following code, I can move the position of the lines in my QTableViewvoid Gestione::show_item() { model = new QSqlTableModel(this); model->setTable("item"); model->setHeaderData(1, Qt::Horizontal, tr("Number")); model->setHeaderData(2, Qt::Horizontal, tr("Name")); model->setHeaderData(3, Qt::Horizontal, tr("Email")); if (model->select()) { ui->view_relatori->setModel(model); ui->view_relatori->resizeColumnsToContents(); ui->view_relatori->verticalHeader()->setSectionsMovable(true); ui->view_relatori->verticalHeader()->setDragDropOverwriteMode(true); ui->view_relatori->verticalHeader()->setDragEnabled(true); ui->view_relatori->verticalHeader()->setDragDropMode(QAbstractItemView::InternalMove); } }
Once I have ordered the list to my liking, I need to save the new order in the database table.
I tried to read the data with a for loop, but I read from the model and not from the viewvoid Gestione::read_data() { QStringList value_id; QStringList value_number; QVector<QStringList> current_order; current_order.clear(); for(int i = 0; i < model->rowCount(); i++) { QSqlRecord record = model->record(i); value_id.append(record.value(0).toString()); value_turno.append(record.value(1).toString()); row = ui->view->verticalHeader()->visualIndex(i); } current_order.append(value_id_rel); // 00 List id_rel[] current_order.append(value_turno); // 01 List Number[] }
I searched for a solution, but found nothing.
Is there a method to save the reordered view on the model?
Thank you in advance
blackout69 -
Hi,
Do you mean you want to be able to change the order of the database fields based on the visual changes you applied to the QTableView ?
-
@sgaist said in QTableView move rows and update model:
Do you mean you want to be able to change the order of the database fields based on the visual changes you applied to the QTableView ?
Hi,
Yes. The number field in the table serves as a "work shift". By changing the order in the view, I would like to update the table number field based on the new order. So that by applying a filter to the number field, I can always have the correct order in the view.blackout69
-
@blackout69
Since you are reordering via moving headers, you should perhaps read the answer in https://stackoverflow.com/questions/41807590/reading-qtableview-row-contents-with-the-same-order-as-are-seen-not-stored. Or, I think @VRonin's answer at https://forum.qt.io/topic/75393/reading-qtableview-row-contents-with-the-same-order-as-are-seen-not-stored/9 addresses your situation.Unless I am missing something (I am interested now), it does seems surprisingly complex to read table view row/columns in visual order instead of model order?
-
If you don't use the header to hide individual rows, you could try
QObject::connect(ui->view_relatori->verticalHeader(),&QHeaderView::sectionMoved,[=](int logicalIndex, int oldVisualIndex, int newVisualIndex)->void{ Q_ASSERT(logicalIndex==oldVisualIndex); const QModelIndex numberIndex =model->index(1,logicalIndex); /*I use 1 here because of model->setHeaderData(1, Qt::Horizontal, tr("Number")); it looks strange, however, you have nothing at index 0*/ Q_ASSERT(logicalIndex==numberIndex.data().toInt()); model->setData(numberIndex,newVisualIndex); });
-
@jonb
reading based on the view would be great, but I don't know how. Could you tell me how?
blackout69 -
I get this when I move a row
ASSERT: "logicalIndex==numberIndex.data().toInt()" in file gestione.cpp, line 843
Invalid parameter passed to C runtime function./I use 1 here because of model->setHeaderData(1, Qt::Horizontal, tr("Number")); it looks strange, however, you have nothing at index 0/
My index 0 is the table id
blackout69 -
@blackout69 said in QTableView move rows and update model:
My index 0 is the table id
could you
qDebug() << logicalIndex <<"!=" << numberIndex.data().toInt();
and post the result? -
QObject::connect(ui->view_relatori->verticalHeader(),&QHeaderView::sectionMoved,[=](int logicalIndex, int oldVisualIndex, int newVisualIndex)->void{ Q_ASSERT(logicalIndex == oldVisualIndex); const QModelIndex numberIndex = relatori_model->index(rel_id_rel,logicalIndex); /*I use 1 here because of model->setHeaderData(1, Qt::Horizontal, tr("Number")); it looks strange, however, you have nothing at index 0*/ qDebug() << logicalIndex <<"!=" << numberIndex.data().toInt(); Q_ASSERT(logicalIndex == numberIndex.data().toInt()); relatori_model->setData(numberIndex,newVisualIndex); });
5 != 0
ASSERT: "logicalIndex == numberIndex.data().toInt()" in file gestione.cpp, line 844
Invalid parameter passed to C runtime function.
Invalid parameter passed to C runtime function.blackout69
-
@blackout69 said in QTableView move rows and update model:
The number field in the table serves as a "work shift"
Looks like it contains a 0 though. what is in that column
-
@vronin said in QTableView move rows and update model:
Looks like it contains a 0 though. what is in that column
In that column there is the table id. So only integers starting from 1
The table is thus formed:
id_rel int(11)
turno decimal(3,1)
name varchar(40)
email varchar(60)blackout69
-
@vronin
Perfect so it works.
Thanks for your help.QObject::connect(ui->view_relatori->verticalHeader(), &QHeaderView::sectionMoved, [=](int logicalIndex, int oldVisualIndex, int newVisualIndex)->void{ Q_ASSERT(logicalIndex == oldVisualIndex); QModelIndex numberIndex = relatori_model->index(logicalIndex, rel_turno); Q_ASSERT(logicalIndex == numberIndex.data().toInt() - 1); relatori_model->setData(numberIndex, newVisualIndex + 1); relatori_model->submitAll(); });
blackout69