如何运行 在处理完QT QWidget 启动中的信号和事件后立即编码?
How to run code just after signals and events in QT QWidget initiation are processed?
import sys
from PyQt5.Qt import *
app = QApplication([])
class MyDialog(QDialog):
def __init__(self):
super().__init__()
layout = QVBoxLayout(self)
self.list_widget = QListWidget()
layout.addWidget(self.list_widget)
self.list_widget.currentRowChanged.connect(self.on_cur_row_changed)
self.list_widget.addItems(['apple', 'orange'])
# code block A # start #
self.clear_qt_currentRow()
# code block A # end #
print('End of MyDialog.__init__')
def on_cur_row_changed(self, row):
print('Current row changed to: ', row)
def clear_qt_currentRow(self):
print('Clear Qt currentRow')
self.list_widget.selectionModel().clear()
dialog = MyDialog()
dialog.show()
sys.exit(app.exec())
如上面的代码,我不喜欢 QT 将列表小部件的 currentRow 属性 设置为 0(第一行)。我想 运行 clear_qt_currentRow()里面的代码,在QT QWidget发起的信号和事件处理之后(在这种情况下,将currentRow 属性设置为None) 但是[=代码块 A 运行 中的 31=]() 太早(在 QT 更改 currentRow 之前)。结果显示为:
Clear Qt currentRow
End of MyDialog.__init__
Current row changed to: 0
然后,我尝试了以下两种代码块 A 的替代方案,但仍然没有足够晚地 self.clear_qt_currentRow() 到 运行。
# alternative 1
app.processEvents()
self.clear_qt_currentRow()
# result:
# Clear Qt currentRow
# End of MyDialog.__init__
# Current row changed to: 0
# alternative 2
QTimer.singleShot(0, self.clear_qt_currentRow)
# result:
# End of MyDialog.__init__
# Clear Qt currentRow
# Current row changed to: 0
我知道 QTimer.singleShot(10000, self.clear_qt_currentRow) 可以做到。但这不可能是 "real" 解决方案,因为用户可能拥有不同规格的计算机。
对我有什么建议吗?
编辑:用粗体文本添加我想做的事情。
编辑:在@zariii9003 的帮助下,我更改为以下代码,它在 class.
中完成工作
import sys
from PyQt5.Qt import *
app = QApplication([])
class MyDialog(QDialog):
def __init__(self):
super().__init__()
layout = QVBoxLayout(self)
self.list_widget = QListWidget()
layout.addWidget(self.list_widget)
self.list_widget.currentRowChanged.connect(self.on_cur_row_changed)
self.list_widget.addItems(['apple', 'orange'])
# code block A # start #
QTimer.singleShot(0, self.clear_qt_currentRow)
# code block A # end #
print('End of MyDialog.__init__')
def on_cur_row_changed(self, row):
print('Current row changed to: ', row)
def clear_qt_currentRow(self):
print('Process events')
# add here
app.processEvents()
print('Clear Qt currentRow')
self.list_widget.selectionModel().clear()
dialog = MyDialog()
dialog.show()
sys.exit(app.exec())
你可以看看 Spyder,一个用 Qt 实现的 IDE:
如果你看here:
# Main window
main = MainWindow(options)
main.show()
main.post_visible_setup()
他们首先初始化 MainWindow,然后调用 show()
,然后执行 post_visible_setup()
。
对于你的情况,这个:
dialog = MyDialog()
dialog.show()
app.processEvents()
dialog.clear_qt_currentRow()
sys.exit(app.exec())
结果
End of MyDialog.__init__
Current row changed to: 0
Clear Qt currentRow
Current row changed to: -1
import sys
from PyQt5.Qt import *
app = QApplication([])
class MyDialog(QDialog):
def __init__(self):
super().__init__()
layout = QVBoxLayout(self)
self.list_widget = QListWidget()
layout.addWidget(self.list_widget)
self.list_widget.currentRowChanged.connect(self.on_cur_row_changed)
self.list_widget.addItems(['apple', 'orange'])
# code block A # start #
self.clear_qt_currentRow()
# code block A # end #
print('End of MyDialog.__init__')
def on_cur_row_changed(self, row):
print('Current row changed to: ', row)
def clear_qt_currentRow(self):
print('Clear Qt currentRow')
self.list_widget.selectionModel().clear()
dialog = MyDialog()
dialog.show()
sys.exit(app.exec())
如上面的代码,我不喜欢 QT 将列表小部件的 currentRow 属性 设置为 0(第一行)。我想 运行 clear_qt_currentRow()里面的代码,在QT QWidget发起的信号和事件处理之后(在这种情况下,将currentRow 属性设置为None) 但是[=代码块 A 运行 中的 31=]() 太早(在 QT 更改 currentRow 之前)。结果显示为:
Clear Qt currentRow
End of MyDialog.__init__
Current row changed to: 0
然后,我尝试了以下两种代码块 A 的替代方案,但仍然没有足够晚地 self.clear_qt_currentRow() 到 运行。
# alternative 1
app.processEvents()
self.clear_qt_currentRow()
# result:
# Clear Qt currentRow
# End of MyDialog.__init__
# Current row changed to: 0
# alternative 2
QTimer.singleShot(0, self.clear_qt_currentRow)
# result:
# End of MyDialog.__init__
# Clear Qt currentRow
# Current row changed to: 0
我知道 QTimer.singleShot(10000, self.clear_qt_currentRow) 可以做到。但这不可能是 "real" 解决方案,因为用户可能拥有不同规格的计算机。
对我有什么建议吗?
编辑:用粗体文本添加我想做的事情。
编辑:在@zariii9003 的帮助下,我更改为以下代码,它在 class.
中完成工作import sys
from PyQt5.Qt import *
app = QApplication([])
class MyDialog(QDialog):
def __init__(self):
super().__init__()
layout = QVBoxLayout(self)
self.list_widget = QListWidget()
layout.addWidget(self.list_widget)
self.list_widget.currentRowChanged.connect(self.on_cur_row_changed)
self.list_widget.addItems(['apple', 'orange'])
# code block A # start #
QTimer.singleShot(0, self.clear_qt_currentRow)
# code block A # end #
print('End of MyDialog.__init__')
def on_cur_row_changed(self, row):
print('Current row changed to: ', row)
def clear_qt_currentRow(self):
print('Process events')
# add here
app.processEvents()
print('Clear Qt currentRow')
self.list_widget.selectionModel().clear()
dialog = MyDialog()
dialog.show()
sys.exit(app.exec())
你可以看看 Spyder,一个用 Qt 实现的 IDE:
如果你看here:
# Main window
main = MainWindow(options)
main.show()
main.post_visible_setup()
他们首先初始化 MainWindow,然后调用 show()
,然后执行 post_visible_setup()
。
对于你的情况,这个:
dialog = MyDialog()
dialog.show()
app.processEvents()
dialog.clear_qt_currentRow()
sys.exit(app.exec())
结果
End of MyDialog.__init__
Current row changed to: 0
Clear Qt currentRow
Current row changed to: -1