问题
from PySide2 import QtWidgets
class Widget(QtWidgets.QWidget):
def __init__(self, parent=None):
super().__init__(parent)
self.lineEdit = QtWidgets.QLineEdit()
self.lineEdit.setText("1")
self.lineEdit.editingFinished.connect(self.check)
self.lineEdit2 = QtWidgets.QLineEdit()
vlay = QtWidgets.QVBoxLayout(self)
vlay.addWidget(self.lineEdit)
vlay.addWidget(self.lineEdit2)
def check(self):
if self.lineEdit.text() == "1":
popup = QtWidgets.QMessageBox(self)
popup.setWindowTitle("why")
popup.show()
print("test")
if __name__ == "__main__":
import sys
app = QtWidgets.QApplication(sys.argv)
w = Widget()
w.show()
sys.exit(app.exec_())
So in this script if you press "Enter" while editing "lineEdit", the "check" slot is called two times. But if you click on "lineEdit2", the slot will be called only one time, as it should be. This happens because of QMessageBox, but why?
回答1:
If you check the docs:
void QLineEdit::editingFinished()
This signal is emitted when the Return or Enter key is pressed or the line edit loses focus. Note that if there is a validator() or inputMask() set on the line edit and enter/return is pressed, the editingFinished() signal will only be emitted if the input follows the inputMask() and the validator() returns QValidator::Acceptable.
(emphasis mine)
In your case the first print is given when you press Enter and the second print is given when the QLineEdit loses focus since the QMessageBox obtains it.
If you want to avoid this behavior, you can block the emittion of QLineEdit events a moment before the QMessageBox is displayed until a moment after it is displayed:
self.lineEdit.blockSignals(True)
popup = QtWidgets.QMessageBox(self)
popup.setWindowTitle("why")
QtCore.QTimer.singleShot(100, lambda: self.lineEdit.blockSignals(True))
popup.show()
print("test")
来源:https://stackoverflow.com/questions/58783280/why-does-editingfinished-signal-generates-two-times-when-qmessagebox-is-being-sh