QSqlTableModel: last checkstate change doesn't reflect on database

250 views Asked by At

I have MySQL database, QSqlTableModel and QTableView with few checkbox columns. It works, but the last click on checkbox does not cause changes in database. It means that if I launch a program, click on some checkbox once and close program, no changes in database will be made. If I'll change the state of several checkboxes, the last change will not be shown in database. Maybe there's something wrong in my setData method?

bool PartyModel::setData(const QModelIndex &index, const QVariant &value, int role)
{
    QString h=headerData(index.column(),Qt::Horizontal).toString();
    QVariant v=value;
    switch(role)
    {
    case Qt::CheckStateRole:
        if(h=="One" || h=="Two" || h=="Three" || h=="Four")
        {
            if(value.toInt()==Qt::Unchecked) v=0;
            else v=1;
            bool ret = QSqlTableModel::setData(index,v,Qt::EditRole);
            if(ret) emit dataChanged(index,index);
            return ret;
        }
        break;
    case Qt::DisplayRole:
    case Qt::EditRole:
        .......
        break;
    default:
        break;
    }
    return QSqlTableModel::setData(index,v,role);
}

QVariant PartyModel::data(const QModelIndex &idx, int role) const
{
    QString h=headerData(idx.column(),Qt::Horizontal).toString();
    QVariant v=QSqlTableModel::data(idx,role);
    switch(role)
    {
    case Qt::CheckStateRole:
        if(h=="One" || h=="Two" || h=="Three" || h=="Four")
            v = (QSqlTableModel::data(idx,Qt::DisplayRole).toInt()==0 ? Qt::Unchecked : Qt::Checked);
        break;
    case Qt::DisplayRole:
        if(h=="One" || h=="Two" || h=="Three" || h=="Four")
            v="";
        break;
    default:
        break;
    }
    return v;
}

Qt::ItemFlags PartyModel::flags(const QModelIndex &index) const
{
    QString h=headerData(index.column(),Qt::Horizontal).toString();
    Qt::ItemFlags f=QSqlQueryModel::flags(index);
    if(h=="One" || h=="Two" || h=="Three" || h=="Four")
    {
        f |= Qt::ItemIsUserCheckable;
        f &= ~Qt::ItemIsEditable;
    }
    return f;
}
1

There are 1 answers

0
E4z9 On BEST ANSWER

The default "edit strategy" of QSqlTabelModel is OnRowChange, which means that changes are only submitted, as the name suggests, when the selected row changes. To submit changes to the database at other times, you need to either change the edit strategy to OnFieldChange, or manually call submit() or submitAll() at appropriate times.