Форум сайта python.su
http://python.su/forum/topic/24662/?page=2#post-130903
Офлайн
Переписал по Вашему примеру.
import time from PyQt5 import QtCore from PyQt5.QtCore import Qt from PyQt5.QtWidgets import QApplication, QWidget, QPushButton, QMessageBox, QDesktopWidget from PyQt5.QtWidgets import QMainWindow, QLabel, QLineEdit, QGridLayout, QCheckBox from PyQt5.QtCore import QCoreApplication from PyQt5.QtGui import QPixmap,QImage #from threading import Thread #Потоки class Main_Window(QMainWindow): def __init__(self): super(Main_Window,self).__init__() self.initUI() self.t = MyThread() QtCore.QObject.connect(self.t, QtCore.SIGNAL("message(str)"), self.setStatusBar) self.t.start() def initUI(self): self.statusBar().showMessage('Ready') #Отображаем текст в статусбаре def setStatusBar(self,text): self.statusBar().showMessage(str(text)) class Main_Widget(QWidget): def __init__(self): super(Main_Widget,self).__init__() class MyThread(QtCore.QThread): def __init__(self): QtCore.QThread.__init__(self) def run(self): time.sleep(2) i = 0 while True: text = str(i) i = i+1 #Тут надо как-то вызвать смену текста статусбара self.emit(QtCore.SIGNAL("message(str)"), text) time.sleep(2) if __name__ == '__main__': import sys app = QApplication(sys.argv) window = Main_Window() widget = Main_Widget() window.setCentralWidget(widget) window.show() #window.connect(QtCore.pyqtSignal("message()"),window.setStatusBar) sys.exit(app.exec_())
Traceback (most recent call last): File "<string>", line 420, in run_nodebug File "D:\MyFiles\tests\1.py", line 58, in <module> window = Main_Window() File "D:\MyFiles\tests\1.py", line 26, in __init__ QtCore.QObject.connect(self.t, QtCore.SIGNAL("message(str)"), self.setStatusBar) AttributeError: type object 'QObject' has no attribute 'connect'
Traceback (most recent call last): File "D:\MyFiles\tests\1.py", line 52, in run self.emit(QtCore.SIGNAL("message(str)"), text) AttributeError: 'MyThread' object has no attribute 'emit'
Отредактировано admiral (Май 11, 2015 15:27:26)
Офлайн
Блина, да что же это за система такая…
Даже просто сменить строку статусбара из другого потока не получается…
Офлайн
# coding: utf-8 import sys import PySide.QtGui as QtGui import PySide.QtCore as QtCore class Main_Window(QtGui.QMainWindow): def __init__(self): QtGui.QMainWindow.__init__(self) self.statusBar().showMessage('Ready') self.t = MyThread() self.connect(self.t, QtCore.SIGNAL("message(PyObject)"), self.setStatusText) self.t.start() def setStatusText(self, text): self.statusBar().showMessage(text) class MyThread(QtCore.QThread): def __init__(self): QtCore.QThread.__init__(self) def run(self): QtCore.QThread.msleep(2000) i = 0 while True: text = str(i) i = i+1 #Тут надо как-то вызвать смену текста статусбара self.emit(QtCore.SIGNAL("message(PyObject)"), text) QtCore.QThread.msleep(2000) if __name__ == '__main__': app = QtGui.QApplication(sys.argv) window = Main_Window() window.show() sys.exit(app.exec_())
Отредактировано Rodegast (Май 11, 2015 16:01:28)
Офлайн
Спасибо. PySide у меня не установлен. И, как я понял, для PyQt5 не подходит код. Все равно ругается.
Но наконец-то я нашел внятное объяснение как делать сигналы вот тут.
Оказывается нужно сделать отдельный класс с наследованием от QObject, в нем прописать сигнал. И только потом уже можно к этому сигналу делать connect.
Вот в каком случае у меня заработало:
import time from PyQt5 import QtCore from PyQt5.QtCore import Qt, QObject, pyqtSignal from PyQt5.QtWidgets import QApplication, QWidget, QPushButton, QMessageBox, QDesktopWidget from PyQt5.QtWidgets import QMainWindow, QLabel, QLineEdit, QGridLayout, QCheckBox from PyQt5.QtCore import QCoreApplication from PyQt5.QtGui import QPixmap,QImage from threading import Thread #Потоки class Main_Window(QMainWindow): def __init__(self): super(Main_Window,self).__init__() self.initUI() def initUI(self): self.statusBar().showMessage('Ready') #Отображаем текст в статусбаре def setStatusBar(self,text): self.statusBar().showMessage(str(text)) class Main_Widget(QWidget): def __init__(self): super(Main_Widget,self).__init__() class MyThread(Thread): def __init__(self,f): Thread.__init__(self) self.f = f def run(self): time.sleep(2) i = 0 while True: text = str(i) i = i+1 #Тут надо как-то вызвать смену текста статусбара self.f.message.emit(text) time.sleep(2) class foo(QObject): message = pyqtSignal(str) if __name__ == '__main__': import sys app = QApplication(sys.argv) window = Main_Window() widget = Main_Widget() window.setCentralWidget(widget) window.show() f=foo() f.message.connect(window.setStatusBar) t = MyThread(f) t.start() sys.exit(app.exec_())
Офлайн
Вот заготовка, которая работает для PyQt4
#!/usr/bin/env python3 from PyQt4 import QtGui, QtCore import sys import time class MainWindow(QtGui.QMainWindow): def __init__(self): super().__init__() self.init_ui() def init_ui(self): self.thread = Thread(self) self.thread.message[str].connect(self.change_status) self.thread.start() self.statusBar().showMessage('Ready') self.show() def change_status(self, text): self.statusBar().showMessage(text) class Thread(QtCore.QThread): message = QtCore.pyqtSignal(str) def run(self): while True: n = int(time.time()) % 10 self.message.emit(str(n)) time.sleep(1) def main(): app = QtGui.QApplication(sys.argv) ex = MainWindow() sys.exit(app.exec_()) if __name__ == '__main__': main()
class Thread(QtCore.QThread, QtCore.QObject):
admiralСлот у тебя неправильно написан. Приходит текст, то есть уже строка, а ты строку снова делаешь строкой.
Вот в каком случае у меня заработало:
Отредактировано py.user.next (Май 12, 2015 02:47:47)
Офлайн
py.user.nextЭто я для надежности. А то в питоне с переменной можно делать все что угодно, а статусбар только строку может принимать. Ничего же страшного? Или стоит убрать преобразование в строку?
Слот у тебя неправильно написан. Приходит текст, то есть уже строка, а ты строку снова делаешь строкой.
Офлайн
Блина, буду наверное кодить на PyQT4, а то каждый раз какие-то проблемы, а в инете большинство примеров для PyQT4 и, как оказалось, не так-то просто их переделать.
Офлайн
admiralОна должна выпасть, если что-то не то подаётся.
А то в питоне с переменной можно делать все что угодно
admiralСнаружи нужно преобразовывать.
Или стоит убрать преобразование в строку?
admiralФункция становится надёжнее тогда, когда она не делает ничего лишнего - занимается только своим делом. (Функциональная прочность модуля.)
Это я для надежности. :)
Отредактировано py.user.next (Май 12, 2015 08:38:51)
Офлайн
py.user.nextПоставил PyQT4 - заработала без проблем и ошибок. И без лишних созданий классов. Спасибо.
Вот заготовка, которая работает для PyQt4
Офлайн