QDataWidgetMapper и изменение foregn key |
Здравствуйте, гость ( Вход | Регистрация )
QDataWidgetMapper и изменение foregn key |
Begemot |
28.5.2010, 17:44
Сообщение
#1
|
Студент Группа: Новичок Сообщений: 13 Регистрация: 15.5.2010 Пользователь №: 1718 Спасибо сказали: 0 раз(а) Репутация: 0 |
Случилось тут проблема, и уже больше суток не могу решить, пробовал разные подходы все или вообще не работает или работает но через раз (не шучу).
Есть MySqlRelationalTableModel, у нее одно из полей внешний ключ (fkey) ну и соответвенно связанная таблица ID, Name. Все поля таблицы привязаны к виджетам на форме через QDataWidgetMapper, fkey привязан к QLineEdit. Отображается все отлично, вместо значения ключа я вижу соответвующий Name из связанной таблицы. Вопрос как правильно програмно изменить это значение. Для юзера это выглядит так - QLineEdit read only, по щелчку на нему - открывается диалог, в котором список Name - пользователь выбирает нужное или _вводит новое_, я получаю строку которую он выбрал\ввел. Как мне теперь правильно изменить значение в главной модели и все это сохранить в бд? |
|
|
Litkevich Yuriy |
28.5.2010, 18:59
Сообщение
#2
|
разработчик РЭА Группа: Сомодератор Сообщений: 9669 Регистрация: 9.1.2008 Из: Тюмень Пользователь №: 64 Спасибо сказали: 807 раз(а) Репутация: 94 |
setModelData и submitAll
|
|
|
Begemot |
29.5.2010, 7:39
Сообщение
#3
|
Студент Группа: Новичок Сообщений: 13 Регистрация: 15.5.2010 Пользователь №: 1718 Спасибо сказали: 0 раз(а) Репутация: 0 |
setModelData и submitAll Я так полагаю что речь идет о делегате, потому как setModelData есть только у наследников QAbstractItemDelegate. Но из контрола (наследник QLineEdit) к делегату доступ получить вроде нельзя (не передавая его руками)? да это и не важно, в принципе, setModelData вызовется автоматически при потере контролом фокуса, использую setEditStrategy(QSqlTableModel::OnFieldChange); Сейчас работа идет так, в классе наследнике QEditLine перехватывается щелчек мыши, показывается диалог - пользователь выбирает строку, эта строка записывается в наш QLineEdit, дальше ждем потери фокуса, для автоматического сохранения. У меня есть свой делегат (изначально писался для обслуживания комбобоксов), для этого поля добавляю туда такой код CODE void DogDelegate::setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const { switch(index.column()) { ...... case Animals_Breed: QString text = editor->property("text").toString(); qDebug()<<"save Animals_Breed " << text; // --- get relation table and try to find our string QSqlTableModel * rm = ((QSqlRelationalTableModel *)model)->relationModel(Animals_Breed); QModelIndexList indexList = rm->match(rm->index(0, Breeds_Breed), Qt::DisplayRole, text, 1, Qt::MatchExactly); int id = 0; if (!indexList.isEmpty()) id = rm->data(rm->index(indexList.first().row(), Breeds_Id)).toInt(); else { // there is no such string - we should add it QSqlRecord record(rm->record()); record.setValue(Breeds_Breed, text); rm->insertRecord(0, record); rm->submit(); // --- Get id for new added string QModelIndexList indexList = rm->match(rm->index(0, Breeds_Breed), Qt::DisplayRole, text, 1, Qt::MatchExactly); if (!indexList.isEmpty()) id = rm->data(rm->index(indexList.first().row(), Breeds_Id)).toInt(); else Q_ASSERT(0); } model->setData(index, id); ((QSqlRelationalTableModel*) model)->submitAll(); return; } QItemDelegate::setModelData(editor, model, index); } Если маппер пытается сабмитить это поле, я получаю в rm таблицу связанную с внешним ключем, и пытаюсь в соответвуюшей колонке найти значение которое у нас в лайнэдите. Если значение есть - все отлично, беру соответсвующий id из внешней таблицы и пишу его в главную таблицу. Если там такого значения нет, значит пользователь ввел новую породу - я добавляю ее в связанную таблицу, сабмичу ее, дальше получаю id и пишу в главную. Этот подход работает если пользователь просто выбирает из списка строку (которая уже есть в таблице). Если же он вводит новую строку - я получаю проблемы 1. Строка добавляется в бд. 2. В едит бокс попадает соответвующее значение (уже прочитанное из бд, а не то что я руками поставил) 3. дальше пользователь ставит фокус в другой контрол, и потом когда фокус переходит в третий контрол - уходит из второго, значение в едит боксе и в базе данных сбрасывается в предыдущее, и так в 66% случаях. submitAll не помогает видимо проблема в том что при изменении\сабмите связаной таблицы, то ли главная модель не обновляется то ли еще что - но оно "забывает" изменения в 2 их 3 случаях. Что делать ума не приложу, как-то ресетить модель? заново перезагружать? что-то еще? Или это просто еще 1 баг |
|
|
Текстовая версия | Сейчас: 25.11.2024, 13:49 |