2017-08-27 24 views
0

Ich machte diesen einfachen Dialog, um das Problem zu zeigen, das ich habe, der Dialog ist nur ein QTableView und QSqlRelationalTableModel. Das Problem ist, dass ich die Ansicht nicht speichern kann, auch wenn die geänderten Daten keine der zugehörigen Tabellen waren. Aber wenn ich die Beziehungen wie im folgenden Code auskommentiere, kann ich ohne Probleme aktualisieren. Gibt es einen zusätzlichen Schritt zum Speichern von Informationen, wenn Fremdschlüssel im Spiel sind?Aktualisieren einer relationalen Tabellenansicht

PS. Nur für den Fall ist wichtig, ich betreibe einen MySql Server über das Netzwerk.

#include "xtest.h" 
#include "ui_xtest.h" 

XTest::XTest(QWidget *parent) : QDialog(parent), ui(new Ui::XTest) 
{ 
    ui->setupUi(this); 
    modelSuppliers=new QSqlRelationalTableModel(this); 
    modelSuppliers->setTable("supplier"); 
    modelSuppliers->setEditStrategy(QSqlTableModel::OnManualSubmit); 
    modelSuppliers->setHeaderData(0,Qt::Horizontal,"ID"); 
    modelSuppliers->setHeaderData(1,Qt::Horizontal,"Name"); 
    modelSuppliers->setHeaderData(2,Qt::Horizontal,"Address"); 
    modelSuppliers->setHeaderData(3,Qt::Horizontal,"Address1"); 
    modelSuppliers->setHeaderData(4,Qt::Horizontal,"City"); 
    modelSuppliers->setHeaderData(5,Qt::Horizontal,"User"); 
    modelSuppliers->setHeaderData(6,Qt::Horizontal,"Country"); 
    modelSuppliers->setHeaderData(7,Qt::Horizontal,"Sta/Reg"); 
    modelSuppliers->setHeaderData(8,Qt::Horizontal,"Active"); 
// modelSuppliers->setRelation(5,QSqlRelation("user","iduser","email")); 
// modelSuppliers->setRelation(6,QSqlRelation("country","idcountry","name")); 
// modelSuppliers->setRelation(7,QSqlRelation("sta_reg","idsta_reg","name")); 
    modelSuppliers->select(); 

    ui->suppliers->setModel(modelSuppliers); 
    ui->suppliers->resizeColumnsToContents(); 
    ui->suppliers->resizeRowsToContents(); 
    ui->suppliers->setItemDelegate(new QSqlRelationalDelegate(ui->suppliers)); 
    ui->suppliers->show(); 
} 

XTest::~XTest() 
{ 
    delete ui; 
} 

void XTest::on_save_clicked() 
{ 
    modelSuppliers->submitAll(); 
} 

Ich habe damit eine Weile gespielt und ich habe etwas entdeckt, das verwandt sein könnte. Ich habe das Signal beforeUpdate des Modells mit einer Funktion verbunden, die die Zeile und QSqlRecord anzeigt. Ich habe zwei Läufe gemacht, eine mit der Beziehung "Benutzer" aktiv und eine andere mit keiner von ihnen aktiv. In Zeile 5 scheint mir, dass das Modell versucht, den Datensatz mit der Beschreibung der zugehörigen Tabelle und nicht mit dem Schlüssel zu aktualisieren. Der zweite Lauf, der aktualisiert wird, hat den Schlüssel an dieser Position. Ist das ein Fehler bei QT?

2 
QSqlRecord(9) 
0: QSqlField("idsupplier", int, length: 11, precision: 0, required: yes, generated: no, typeID: 3, autoValue: true, readOnly: false) "4" 
1: QSqlField("name", QString, length: 180, precision: 0, required: no, generated: no, typeID: 253, autoValue: false, readOnly: false) "Other" 
2: QSqlField("address", QString, length: 180, precision: 0, required: no, generated: no, typeID: 253, autoValue: false, readOnly: false) "Direccion" 
3: QSqlField("address1", QString, length: 180, precision: 0, required: no, generated: yes, typeID: 253, autoValue: false, readOnly: false) "dddd" 
4: QSqlField("city", QString, length: 180, precision: 0, required: no, generated: no, typeID: 253, autoValue: false, readOnly: false) "Santiago" 
5: QSqlField("iduser", int, length: 11, precision: 0, required: yes, generated: no, typeID: 3, autoValue: false, readOnly: false) "N/A" 
6: QSqlField("idcountry", int, length: 11, precision: 0, required: yes, generated: no, typeID: 3, autoValue: false, readOnly: false) "2" 
7: QSqlField("idsta_reg", int, length: 11, precision: 0, required: yes, generated: no, typeID: 3, autoValue: false, readOnly: false) "5" 
8: QSqlField("active", char, length: 4, precision: 0, required: no, generated: no, typeID: 1, autoValue: false, readOnly: false) "1" 
"" 

. 
    2 
    QSqlRecord(9) 
    0: QSqlField("idsupplier", int, length: 11, precision: 0, required: yes, generated: no, typeID: 3, autoValue: true, readOnly: false) "4" 
    1: QSqlField("name", QString, length: 180, precision: 0, required: no, generated: no, typeID: 253, autoValue: false, readOnly: false) "Other" 
    2: QSqlField("address", QString, length: 180, precision: 0, required: no, generated: no, typeID: 253, autoValue: false, readOnly: false) "Direccion" 
    3: QSqlField("address1", QString, length: 180, precision: 0, required: no, generated: yes, typeID: 253, autoValue: false, readOnly: false) "dddd" 
    4: QSqlField("city", QString, length: 180, precision: 0, required: no, generated: no, typeID: 253, autoValue: false, readOnly: false) "Santiago" 
    5: QSqlField("iduser", int, length: 11, precision: 0, required: yes, generated: no, typeID: 3, autoValue: false, readOnly: false) "1" 
    6: QSqlField("idcountry", int, length: 11, precision: 0, required: yes, generated: no, typeID: 3, autoValue: false, readOnly: false) "2" 
    7: QSqlField("idsta_reg", int, length: 11, precision: 0, required: yes, generated: no, typeID: 3, autoValue: false, readOnly: false) "5" 
    8: QSqlField("active", char, length: 4, precision: 0, required: no, generated: no, typeID: 1, autoValue: false, readOnly: false) "1" 

Antwort

-1

Können Sie auch Ihre Tabellendefinitionen angeben? Hier ist ein minimales Arbeitsbeispiel für SQLITE.

mainwindow.cpp:

#include "mainwindow.hpp" 
#include "ui_mainwindow.h" 

#include <QSqlDatabase> 
#include <QSqlRelationalTableModel> 
#include <QSqlRelationalDelegate> 
#include <QSqlQuery> 
#include <QSqlError> 
#include <QFile> 
#include <QMessageBox> 

MainWindow::MainWindow(QWidget *parent) : 
    QMainWindow(parent), 
    ui(new Ui::MainWindow) 
{ 
    ui->setupUi(this); 

    QString fileName = "test.sqlite"; 
    QSqlDatabase db = QSqlDatabase::addDatabase("QSQLITE"); 
    db.setDatabaseName(fileName); 
    // This part is just to have sample data ... 
    if (!QFile(fileName).exists()) { 
     db.open(); 

     QSqlQuery query; 
     query.exec("DROP TABLE SUPPLIER"); 
     query.exec("DROP TABLE USER"); 

     query.exec("CREATE TABLE USER(id INTEGER PRIMARY KEY AUTOINCREMENT, name VARCHAR(40) NOT NULL)"); 
     query.exec("CREATE TABLE SUPPLIER(id INTEGER PRIMARY KEY AUTOINCREMENT, name VARCHAR(40) NOT NULL, userId INTEGER NOT NULL, FOREIGN KEY (userId) REFERENCES USER)"); 

     query.exec("INSERT INTO USER(name) VALUES('USER_1'), ('USER_2'), ('USER_3')"); 
     query.exec("INSERT INTO SUPPLIER(name, userId) VALUES('SUPPLIER_1', 1), ('SUPPLIER_2', 2), ('SUPPLIER_3', 3)"); 

     db.close(); 
    } 
    // End of part for sample data. 

    QSqlRelationalTableModel *model = new QSqlRelationalTableModel(this); 
    model->setTable("SUPPLIER"); 
    model->setEditStrategy(QSqlTableModel::OnManualSubmit); 
    model->setHeaderData(0,Qt::Horizontal,"ID"); 
    model->setHeaderData(1,Qt::Horizontal,"NAME"); 
    model->setRelation(2,QSqlRelation("USER", "id", "name")); 
    model->select(); 

    ui->tableView->setModel(model); 
    ui->tableView->setItemDelegate(new QSqlRelationalDelegate(this)); 

    connect(ui->pushButton, &QPushButton::clicked, [=]() { 
     model->submitAll(); 
    }); 
} 

MainWindow::~MainWindow() 
{ 
    delete ui; 
} 

mainwindow.ui:

<?xml version="1.0" encoding="UTF-8"?> 
<ui version="4.0"> 
<class>MainWindow</class> 
<widget class="QMainWindow" name="MainWindow"> 
    <property name="geometry"> 
    <rect> 
    <x>0</x> 
    <y>0</y> 
    <width>400</width> 
    <height>300</height> 
    </rect> 
    </property> 
    <property name="windowTitle"> 
    <string>MainWindow</string> 
    </property> 
    <widget class="QWidget" name="centralWidget"> 
    <layout class="QVBoxLayout" name="verticalLayout"> 
    <item> 
    <widget class="QTableView" name="tableView"/> 
    </item> 
    <item> 
    <widget class="QPushButton" name="pushButton"> 
     <property name="text"> 
     <string>Commit</string> 
     </property> 
    </widget> 
    </item> 
    </layout> 
    </widget> 
    <widget class="QMenuBar" name="menuBar"> 
    <property name="geometry"> 
    <rect> 
    <x>0</x> 
    <y>0</y> 
    <width>400</width> 
    <height>22</height> 
    </rect> 
    </property> 
    </widget> 
    <widget class="QToolBar" name="mainToolBar"> 
    <attribute name="toolBarArea"> 
    <enum>TopToolBarArea</enum> 
    </attribute> 
    <attribute name="toolBarBreak"> 
    <bool>false</bool> 
    </attribute> 
    </widget> 
    <widget class="QStatusBar" name="statusBar"/> 
</widget> 
<layoutdefault spacing="6" margin="11"/> 
<resources/> 
<connections/> 
</ui> 

Hoffnung, das hilft!

freundlichen Grüßen

+0

zeigen die .ui Datei nicht erforderlich ist, wird der OP zu reden, wie es zu tun mit QSqlRelationalTableModel, QSqlQuery verwendet, ist eine altmodische Art und Weise, es zu tun, da es Tausende von Zeilen nehmen statt ein paar zehn, wenn Sie QSqlRelationalTableModel korrekt verwenden. – eyllanesc

+0

Bitte lesen Sie das Folgende, um Ihre Antworten zu verbessern. [Wie schreibe ich eine gute Antwort?] (Https://stackoverflow.com/help/how-to-answer) – eyllanesc

+0

Die Datenbank wurde direkt auf MySql mit dem Model tool.'supplier erstellt, es hat nur einen Primärschlüssel mit 3 Fremdschlüsseln, die auf die im OP auskommentierten Tabellen verweisen. – Dan3460

Verwandte Themen