4

I created a table view like this:

enter image description here

I have a create button to create new rows and as you can see I defined a button for each row to delete that row by this code:

int i = 0;
QPushButton *viewButton;
QStandardItemModel *model;
void MainWindow::on_pushButton_clicked()
{
    model->appendRow(new QStandardItem(QString("")));
    viewButton = new QPushButton();
    viewButton->setText("Delete " + QString::number(i));
    ui->tableView->setIndexWidget(model->index(i , 7), viewButton);
    connect(viewButton , SIGNAL(clicked()) , this , SLOT(button_clicked()));
    i++;
}

and I created a slot for each button clicked for remove a row:

void MainWindow::button_clicked()
{
//   by this line I can get the sender of signal
    QPushButton *pb = qobject_cast<QPushButton *>(QObject::sender());
}

as you can see I know witch button sends signal and now I need to delete that row. here is my question: how can I get the row of sender button in table view to remove that row? I searched everywhere and I didn’t realise how to get the row and column of an item.

Cœur
  • 37,241
  • 25
  • 195
  • 267
HMD
  • 2,202
  • 6
  • 24
  • 37

1 Answers1

2

On workaround is to use QObject::setObjectName and set some names to the buttons you add :

viewButton.setObjectName(QString("%1").arg(i));

And in button_clicked slot you can retrieve the row number using the object name :

void MainWindow::button_clicked()
{
//   by this line I can get the sender of signal
    QPushButton *pb = qobject_cast<QPushButton *>(QObject::sender());

    int row = pb->objectName().toInt();
}

Note that you should update object names after a row is removed.

Another way is to use the QSignalMapper class which collects a set of parameterless signals, and re-emits them with integer, string or widget parameters corresponding to the object that sent the signal. So you can have one like:

QSignalMapper * mapper = new QSignalMapper(this);
QObject::connect(mapper,SIGNAL(mapped(int)),this,SLOT(button_clicked(int)));

When adding your buttons in each row of table view, you can connect the clicked() signal of the button to the map() slot of QSignalMapper and add a mapping using setMapping so that when clicked() is signaled from a button, the signal mapped(int) is emitted:

viewButton = new QPushButton();
viewButton->setText("Delete " + QString::number(i));
ui->tableView->setIndexWidget(model->index(i , 7), viewButton);

QObject::connect(viewButton, SIGNAL(clicked()),mapper,SLOT(map()));
mapper->setMapping(but, i);

This way whenever you click a button in a row, the mapped(int) signal of the mapper is emitted containing the row number and consequently button_clicked is called with a parameter containing the row number.

Also here you should update the mappings in button_clicked slot since the row is removed when you click an item.

Nejat
  • 31,784
  • 12
  • 106
  • 138
  • thank for your answer dear nejat. but I have some issues with your answer. after using remove function rows will sort again. and row indexes will change. but in your code button's indexes are kind of static. am I right? – HMD Feb 21 '15 at 11:35
  • sorry but still I think object name doesn't show the row after some remove. if there is a way that I can resort buttons after each delete that would be great! but if I missed something in your answer please tell me. – HMD Feb 21 '15 at 12:05
  • @ATN You should update object names or mapping after each remove. I can't think of anything else. – Nejat Feb 21 '15 at 12:35