在QSqlTableModel中使用QSqlTableModel.OnFieldChange editStrategy时,如何知道数据库中的数据是否更新成功?
How to know if data updated successfully in database when using QSqlTableModel.OnFieldChange editStrategy in QSqlTableModel?
我正在使用 QSqlTableModel 和 QTableView 来表示我的数据库。我已成功将行插入到 tableModel:
self.tableView = QtWidgets.QTableView(self.verticalLayoutWidget)
self.table_model = QSqlTableModel(self.tableView, database)
self.table_model.select()
self.table_model.setEditStrategy(QSqlTableModel.OnFieldChange)
self.table_model.insertRows(count, 1)
现在,我想在数据库中更新行之后添加一些其他功能。我正在使用:self.table_model.setEditStrategy(QSqlTableModel.OnFieldChange)
.
它会自动更新所有更改,所以我不知道在哪里处理数据库更新的 return 状态。
我试图处理这个信号:https://doc.qt.io/qt-5/qsqltablemodel.html#primeInsert。但是,我找不到任何资源或如何使用它的示例。
完整代码:
class Ui_MainWindow(object):
# status new row in table
newRow = False
# status new copy row in table
copyRow = False
# Currently active persistent editors array
persistentEditorArray = []
def setupUi(self, MainWindow):
MainWindow.setObjectName("MainWindow")
MainWindow.resize(1049, 769)
MainWindow.setWindowFlags(Qt.Window | Qt.FramelessWindowHint)
MainWindow.setStyleSheet("background-color: rgb(106, 117, 202);")
MainWindow.setObjectName("centralwidget")
self.mdiArea = QtWidgets.QMdiArea(MainWindow)
self.mdiArea.setGeometry(QtCore.QRect(20, 10, 1021, 721))
self.mdiArea.setObjectName("mdiArea")
self.mdiArea.setTabsMovable(False)
self.subwindow = QtWidgets.QMdiSubWindow()
self.subwindow.setObjectName("subwindow")
self.subwindow.setGeometry(QtCore.QRect(0,0,self.mdiArea.width(),self.mdiArea.height()))
self.subwindow.setWindowFlags(Qt.Window | Qt.FramelessWindowHint)
self.mdiArea.addSubWindow( self.subwindow)
self.verticalLayoutWidget = QtWidgets.QWidget(self.subwindow)
self.verticalLayoutWidget.setGeometry(QtCore.QRect(0, 0, self.subwindow.width(), self.subwindow.height()))
self.verticalLayoutWidget.setObjectName("verticalLayoutWidget")
self.verticalLayout = QtWidgets.QVBoxLayout(self.verticalLayoutWidget)
self.verticalLayout.setContentsMargins(0, 0, 0, 0)
self.verticalLayout.setObjectName("verticalLayout")
self.createFrame()
self.createTable()
self.retranslateUi(MainWindow)
QtCore.QMetaObject.connectSlotsByName(MainWindow)
def retranslateUi(self, MainWindow):
_translate = QtCore.QCoreApplication.translate
MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow"))
MainWindow.setWindowTitle(_translate("Form", "Form"))
def createTable(self):
self.tableView = QtWidgets.QTableView(self.verticalLayoutWidget)
self.tableView.setGeometry(QtCore.QRect(20, 150, 1011, 601))
self.tableView.setObjectName("tableView")
self.tableView.horizontalHeader().setSortIndicatorShown(True)
self.tableView.verticalHeader().setVisible(False)
self.tableView.horizontalHeader()
self.tableView.setSelectionBehavior(QtWidgets.QTableView.SelectRows)
self.tableView.setSelectionMode(QtWidgets.QTableView.SingleSelection)
self.tableView.setFont(QFont('Gilroy', 12))
self.tableView.clicked.connect(self.enableButtons)
self.verticalLayout.addWidget(self.tableView)
database = QSqlDatabase.addDatabase('QPSQL')
database.setHostName('localhost')
database.setPort(0002)
database.setDatabaseName('example_db')
database.setUserName('username')
database.setPassword('password')
ok = database.open()
if not ok:
logging.debug(database.lastError().text())
# self.tableView.setRowCount(10)
# database.commit()
self.table_model = QSqlTableModel(self.tableView, database)
table_name = 'example_table'
self.table_model.setTable(table_name)
self.table_model.setEditStrategy(QSqlTableModel.OnFieldChange)
if not self.table_model.select():
logging.debug(self.table_model.lastError().text())
header_labels = ['id', 'Code', 'Name', 'Col1', 'Col3', 'Col2', 'Col4',
'Col5',
'Col6']
for i, label in enumerate(header_labels):
self.table_model.setHeaderData(i, QtCore.Qt.Horizontal, label, QtCore.Qt.DisplayRole)
if i != 2:
self.tableView.resizeColumnToContents(i)
self.tableView.setModel(self.table_model)
self.retranslateUiTable(self.tableView)
for i, _ in enumerate(header_labels):
if i != 2:
self.tableView.resizeColumnToContents(i)
self.tableView.horizontalHeader().setSectionResizeMode(i, QHeaderView.Fixed)
else:
self.tableView.horizontalHeader().setSectionResizeMode(i, QHeaderView.Stretch)
self.tableView.horizontalHeader().setSectionResizeMode(QHeaderView.Stretch)
self.tableView.setShowGrid(True)
def enableButtons(self):
if not self.table_model.isDirty():
self.button_add.setEnabled(True)
self.button_copy.setEnabled(True)
for persistentEditor in self.persistentEditorArray:
self.tableView.closePersistentEditor(persistentEditor)
def disableButtons(self):
self.button_add.setEnabled(False)
self.button_copy.setEnabled(False)
def addRow(self):
count = self.table_model.rowCount(QModelIndex())
self.table_model.insertRows(count, 1)
self.tableView.scrollToBottom()
self.table_model.setData(self.table_model.index(count, 0), count)
self.newRow = True
self.disableButtons()
def copyRow(self):
# if new Row adding process is not finished, revert all process stages and start copy Row process
if self.newRow:
self.table_model.revertAll()
select = self.tableView.selectionModel()
self.copyRow = True
self.disableButtons()
# if any row has not been selected, show a dialog with error message
if not select.hasSelection():
self.showDialog()
else:
rows = select.selectedRows()
for row in rows:
count = self.table_model.rowCount(QModelIndex())
self.table_model.insertRow(count)
self.table_model.setData(self.table_model.index(count, 0), count)
for i in range(self.table_model.columnCount()):
row_data = row.sibling(row.row(), i).data()
if i < 2:
if i == 1:
self.table_model.setData(self.table_model.index(count, i), row_data[0:2])
self.tableView.openPersistentEditor(self.table_model.index(count, 1))
self.persistentEditorArray.append(self.table_model.index(count, 1))
self.tableView.openPersistentEditor(self.table_model.index(count, 2))
self.persistentEditorArray.append(self.table_model.index(count, 2))
self.tableView.openPersistentEditor(self.table_model.index(count, 3))
self.persistentEditorArray.append(self.table_model.index(count, 3))
self.tableView.openPersistentEditor(self.table_model.index(count, 4))
self.persistentEditorArray.append(self.table_model.index(count, 4))
self.tableView.openPersistentEditor(self.table_model.index(count, 5))
self.persistentEditorArray.append(self.table_model.index(count, 5))
self.tableView.openPersistentEditor(self.table_model.index(count, 6))
self.persistentEditorArray.append(self.table_model.index(count, 6))
self.tableView.openPersistentEditor(self.table_model.index(count, 7))
self.persistentEditorArray.append(self.table_model.index(count, 7))
self.tableView.openPersistentEditor(self.table_model.index(count, 8))
self.persistentEditorArray.append(self.table_model.index(count, 8))
continue
self.table_model.setData(self.table_model.index(count, i), row_data)
self.tableView.scrollToBottom()
def createFrame(self):
self.frame = QtWidgets.QFrame(self.verticalLayoutWidget)
sizePolicy = QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Fixed, QtWidgets.QSizePolicy.Fixed)
sizePolicy.setHorizontalStretch(0)
sizePolicy.setVerticalStretch(0)
sizePolicy.setHeightForWidth(self.frame.sizePolicy().hasHeightForWidth())
self.frame.setSizePolicy(sizePolicy)
self.frame.setMinimumSize(QtCore.QSize(self.verticalLayoutWidget.width(), 75))
self.frame.setMaximumSize(QtCore.QSize(self.verticalLayoutWidget.width(), self.verticalLayoutWidget.height()))
self.frame.setStyleSheet("background-color: rgb(255, 255, 255);")
self.frame.setFrameShape(QtWidgets.QFrame.StyledPanel)
self.frame.setFrameShadow(QtWidgets.QFrame.Raised)
self.frame.setObjectName("frame")
self.frame.setStyleSheet(".QFrame{background-color: white; border: 1px; border-radius: 10px;}");
self.verticalLayout.addWidget(self.frame, 0, QtCore.Qt.AlignHCenter)
self.button_add = QPushButton(QIcon("../../static/img/036-add.png"), "", self.frame)
self.button_add.setGeometry(QtCore.QRect(40, 15, 50, 50))
self.button_add.setIconSize(self.button_add.size())
self.button_add.clicked.connect(self.addRow)
self.button_add.setFlat(True)
self.button_copy = QPushButton(QIcon("../../static/img/025-copy.png"), "", self.frame)
self.button_copy.setGeometry(QtCore.QRect(140, 15, 50, 50))
self.button_copy.setIconSize(self.button_copy.size())
self.button_copy.clicked.connect(self.copyRow)
self.button_copy.setFlat(True)
def showDialog(self):
msg = QMessageBox()
msg.setIcon(QMessageBox.Warning)
msg.setText("No rows has been selected")
msg.setInformativeText("Please select a row")
msg.setWindowTitle("Error")
msg.setStandardButtons(QMessageBox.Ok)
retval = msg.exec_()
print (retval)
def retranslateUiTable(self, Form):
_translate = QtCore.QCoreApplication.translate
Form.setItemDelegate(CenterTextDelegate(Form))
Form.setStyleSheet("QTableView {"
"selection-background-color : #7481EA;"
"font-weight: bolder;"
"font-style: normal;"
"background-color: white;"
"color: #193378;"
"}"
"QHeaderView { background-color: #E8ECF1;"
"color: #193378;"
" }"
"QScrollBar:vertical {"
" border: 1px solid #999999;"
" background:white;"
" width:10px; "
" margin: 0px 0px 0px 0px;"
"}"
"QScrollBar::handle:vertical {"
"background-color: #6A75CA;"
" min-height: 0px;"
"}"
"QScrollBar::add-line:vertical {"
" background: qlineargradient(x1:0, y1:0, x2:1, y2:0,"
" stop: 0 rgb(32, 47, 130), stop: 0.5 rgb(32, 47, 130), stop:1 rgb(32, 47, 130));"
" height: 0px;"
" subcontrol-position: bottom;"
" subcontrol-origin: margin;"
"}"
"QScrollBar::sub-line:vertical {"
" background: qlineargradient(x1:0, y1:0, x2:1, y2:0,"
" stop: 0 rgb(32, 47, 130), stop: 0.5 rgb(32, 47, 130), stop:1 rgb(32, 47, 130));"
" height: 0 px;"
" subcontrol-position: top;"
" subcontrol-origin: margin;"
"}"
"QLineEdit{"
"background-color:white;"
"border-style: inset;"
"border-width: 0.5px;"
"border-color: #6A75CA;"
"}")
Form.hideColumn(0)
您可以覆盖 bool QSqlTableModel::submit()
槽,当用户停止编辑当前行时,它由项目委托调用。
source
bool SqlTableModel::submit()
{
if (editStrategy() == QSqlTableModel::OnRowChange || editStrategy() == QSqlTableModel::OnFieldChange) {
bool res = submitAll();
// res is true on successfull query
return res;
}
return true;
}
我正在使用 QSqlTableModel 和 QTableView 来表示我的数据库。我已成功将行插入到 tableModel:
self.tableView = QtWidgets.QTableView(self.verticalLayoutWidget)
self.table_model = QSqlTableModel(self.tableView, database)
self.table_model.select()
self.table_model.setEditStrategy(QSqlTableModel.OnFieldChange)
self.table_model.insertRows(count, 1)
现在,我想在数据库中更新行之后添加一些其他功能。我正在使用:self.table_model.setEditStrategy(QSqlTableModel.OnFieldChange)
.
它会自动更新所有更改,所以我不知道在哪里处理数据库更新的 return 状态。
我试图处理这个信号:https://doc.qt.io/qt-5/qsqltablemodel.html#primeInsert。但是,我找不到任何资源或如何使用它的示例。
完整代码:
class Ui_MainWindow(object):
# status new row in table
newRow = False
# status new copy row in table
copyRow = False
# Currently active persistent editors array
persistentEditorArray = []
def setupUi(self, MainWindow):
MainWindow.setObjectName("MainWindow")
MainWindow.resize(1049, 769)
MainWindow.setWindowFlags(Qt.Window | Qt.FramelessWindowHint)
MainWindow.setStyleSheet("background-color: rgb(106, 117, 202);")
MainWindow.setObjectName("centralwidget")
self.mdiArea = QtWidgets.QMdiArea(MainWindow)
self.mdiArea.setGeometry(QtCore.QRect(20, 10, 1021, 721))
self.mdiArea.setObjectName("mdiArea")
self.mdiArea.setTabsMovable(False)
self.subwindow = QtWidgets.QMdiSubWindow()
self.subwindow.setObjectName("subwindow")
self.subwindow.setGeometry(QtCore.QRect(0,0,self.mdiArea.width(),self.mdiArea.height()))
self.subwindow.setWindowFlags(Qt.Window | Qt.FramelessWindowHint)
self.mdiArea.addSubWindow( self.subwindow)
self.verticalLayoutWidget = QtWidgets.QWidget(self.subwindow)
self.verticalLayoutWidget.setGeometry(QtCore.QRect(0, 0, self.subwindow.width(), self.subwindow.height()))
self.verticalLayoutWidget.setObjectName("verticalLayoutWidget")
self.verticalLayout = QtWidgets.QVBoxLayout(self.verticalLayoutWidget)
self.verticalLayout.setContentsMargins(0, 0, 0, 0)
self.verticalLayout.setObjectName("verticalLayout")
self.createFrame()
self.createTable()
self.retranslateUi(MainWindow)
QtCore.QMetaObject.connectSlotsByName(MainWindow)
def retranslateUi(self, MainWindow):
_translate = QtCore.QCoreApplication.translate
MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow"))
MainWindow.setWindowTitle(_translate("Form", "Form"))
def createTable(self):
self.tableView = QtWidgets.QTableView(self.verticalLayoutWidget)
self.tableView.setGeometry(QtCore.QRect(20, 150, 1011, 601))
self.tableView.setObjectName("tableView")
self.tableView.horizontalHeader().setSortIndicatorShown(True)
self.tableView.verticalHeader().setVisible(False)
self.tableView.horizontalHeader()
self.tableView.setSelectionBehavior(QtWidgets.QTableView.SelectRows)
self.tableView.setSelectionMode(QtWidgets.QTableView.SingleSelection)
self.tableView.setFont(QFont('Gilroy', 12))
self.tableView.clicked.connect(self.enableButtons)
self.verticalLayout.addWidget(self.tableView)
database = QSqlDatabase.addDatabase('QPSQL')
database.setHostName('localhost')
database.setPort(0002)
database.setDatabaseName('example_db')
database.setUserName('username')
database.setPassword('password')
ok = database.open()
if not ok:
logging.debug(database.lastError().text())
# self.tableView.setRowCount(10)
# database.commit()
self.table_model = QSqlTableModel(self.tableView, database)
table_name = 'example_table'
self.table_model.setTable(table_name)
self.table_model.setEditStrategy(QSqlTableModel.OnFieldChange)
if not self.table_model.select():
logging.debug(self.table_model.lastError().text())
header_labels = ['id', 'Code', 'Name', 'Col1', 'Col3', 'Col2', 'Col4',
'Col5',
'Col6']
for i, label in enumerate(header_labels):
self.table_model.setHeaderData(i, QtCore.Qt.Horizontal, label, QtCore.Qt.DisplayRole)
if i != 2:
self.tableView.resizeColumnToContents(i)
self.tableView.setModel(self.table_model)
self.retranslateUiTable(self.tableView)
for i, _ in enumerate(header_labels):
if i != 2:
self.tableView.resizeColumnToContents(i)
self.tableView.horizontalHeader().setSectionResizeMode(i, QHeaderView.Fixed)
else:
self.tableView.horizontalHeader().setSectionResizeMode(i, QHeaderView.Stretch)
self.tableView.horizontalHeader().setSectionResizeMode(QHeaderView.Stretch)
self.tableView.setShowGrid(True)
def enableButtons(self):
if not self.table_model.isDirty():
self.button_add.setEnabled(True)
self.button_copy.setEnabled(True)
for persistentEditor in self.persistentEditorArray:
self.tableView.closePersistentEditor(persistentEditor)
def disableButtons(self):
self.button_add.setEnabled(False)
self.button_copy.setEnabled(False)
def addRow(self):
count = self.table_model.rowCount(QModelIndex())
self.table_model.insertRows(count, 1)
self.tableView.scrollToBottom()
self.table_model.setData(self.table_model.index(count, 0), count)
self.newRow = True
self.disableButtons()
def copyRow(self):
# if new Row adding process is not finished, revert all process stages and start copy Row process
if self.newRow:
self.table_model.revertAll()
select = self.tableView.selectionModel()
self.copyRow = True
self.disableButtons()
# if any row has not been selected, show a dialog with error message
if not select.hasSelection():
self.showDialog()
else:
rows = select.selectedRows()
for row in rows:
count = self.table_model.rowCount(QModelIndex())
self.table_model.insertRow(count)
self.table_model.setData(self.table_model.index(count, 0), count)
for i in range(self.table_model.columnCount()):
row_data = row.sibling(row.row(), i).data()
if i < 2:
if i == 1:
self.table_model.setData(self.table_model.index(count, i), row_data[0:2])
self.tableView.openPersistentEditor(self.table_model.index(count, 1))
self.persistentEditorArray.append(self.table_model.index(count, 1))
self.tableView.openPersistentEditor(self.table_model.index(count, 2))
self.persistentEditorArray.append(self.table_model.index(count, 2))
self.tableView.openPersistentEditor(self.table_model.index(count, 3))
self.persistentEditorArray.append(self.table_model.index(count, 3))
self.tableView.openPersistentEditor(self.table_model.index(count, 4))
self.persistentEditorArray.append(self.table_model.index(count, 4))
self.tableView.openPersistentEditor(self.table_model.index(count, 5))
self.persistentEditorArray.append(self.table_model.index(count, 5))
self.tableView.openPersistentEditor(self.table_model.index(count, 6))
self.persistentEditorArray.append(self.table_model.index(count, 6))
self.tableView.openPersistentEditor(self.table_model.index(count, 7))
self.persistentEditorArray.append(self.table_model.index(count, 7))
self.tableView.openPersistentEditor(self.table_model.index(count, 8))
self.persistentEditorArray.append(self.table_model.index(count, 8))
continue
self.table_model.setData(self.table_model.index(count, i), row_data)
self.tableView.scrollToBottom()
def createFrame(self):
self.frame = QtWidgets.QFrame(self.verticalLayoutWidget)
sizePolicy = QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Fixed, QtWidgets.QSizePolicy.Fixed)
sizePolicy.setHorizontalStretch(0)
sizePolicy.setVerticalStretch(0)
sizePolicy.setHeightForWidth(self.frame.sizePolicy().hasHeightForWidth())
self.frame.setSizePolicy(sizePolicy)
self.frame.setMinimumSize(QtCore.QSize(self.verticalLayoutWidget.width(), 75))
self.frame.setMaximumSize(QtCore.QSize(self.verticalLayoutWidget.width(), self.verticalLayoutWidget.height()))
self.frame.setStyleSheet("background-color: rgb(255, 255, 255);")
self.frame.setFrameShape(QtWidgets.QFrame.StyledPanel)
self.frame.setFrameShadow(QtWidgets.QFrame.Raised)
self.frame.setObjectName("frame")
self.frame.setStyleSheet(".QFrame{background-color: white; border: 1px; border-radius: 10px;}");
self.verticalLayout.addWidget(self.frame, 0, QtCore.Qt.AlignHCenter)
self.button_add = QPushButton(QIcon("../../static/img/036-add.png"), "", self.frame)
self.button_add.setGeometry(QtCore.QRect(40, 15, 50, 50))
self.button_add.setIconSize(self.button_add.size())
self.button_add.clicked.connect(self.addRow)
self.button_add.setFlat(True)
self.button_copy = QPushButton(QIcon("../../static/img/025-copy.png"), "", self.frame)
self.button_copy.setGeometry(QtCore.QRect(140, 15, 50, 50))
self.button_copy.setIconSize(self.button_copy.size())
self.button_copy.clicked.connect(self.copyRow)
self.button_copy.setFlat(True)
def showDialog(self):
msg = QMessageBox()
msg.setIcon(QMessageBox.Warning)
msg.setText("No rows has been selected")
msg.setInformativeText("Please select a row")
msg.setWindowTitle("Error")
msg.setStandardButtons(QMessageBox.Ok)
retval = msg.exec_()
print (retval)
def retranslateUiTable(self, Form):
_translate = QtCore.QCoreApplication.translate
Form.setItemDelegate(CenterTextDelegate(Form))
Form.setStyleSheet("QTableView {"
"selection-background-color : #7481EA;"
"font-weight: bolder;"
"font-style: normal;"
"background-color: white;"
"color: #193378;"
"}"
"QHeaderView { background-color: #E8ECF1;"
"color: #193378;"
" }"
"QScrollBar:vertical {"
" border: 1px solid #999999;"
" background:white;"
" width:10px; "
" margin: 0px 0px 0px 0px;"
"}"
"QScrollBar::handle:vertical {"
"background-color: #6A75CA;"
" min-height: 0px;"
"}"
"QScrollBar::add-line:vertical {"
" background: qlineargradient(x1:0, y1:0, x2:1, y2:0,"
" stop: 0 rgb(32, 47, 130), stop: 0.5 rgb(32, 47, 130), stop:1 rgb(32, 47, 130));"
" height: 0px;"
" subcontrol-position: bottom;"
" subcontrol-origin: margin;"
"}"
"QScrollBar::sub-line:vertical {"
" background: qlineargradient(x1:0, y1:0, x2:1, y2:0,"
" stop: 0 rgb(32, 47, 130), stop: 0.5 rgb(32, 47, 130), stop:1 rgb(32, 47, 130));"
" height: 0 px;"
" subcontrol-position: top;"
" subcontrol-origin: margin;"
"}"
"QLineEdit{"
"background-color:white;"
"border-style: inset;"
"border-width: 0.5px;"
"border-color: #6A75CA;"
"}")
Form.hideColumn(0)
您可以覆盖 bool QSqlTableModel::submit()
槽,当用户停止编辑当前行时,它由项目委托调用。
source
bool SqlTableModel::submit()
{
if (editStrategy() == QSqlTableModel::OnRowChange || editStrategy() == QSqlTableModel::OnFieldChange) {
bool res = submitAll();
// res is true on successfull query
return res;
}
return true;
}