如何将数据从一个函数插入到 PyQt5 中的多个小部件
how to insert data from one function into multiple widgets in PyQt5
我有一个设备与我的界面相连,想将数据插入 QlineEdit
个小部件
此函数 def getdevice_data(self):
从设备接收数据并 returns 将其作为字符串
与self.get_output__button.clicked.connect(self.getdevice_data)
我"start"函数
并使用 self.custom_attribute.connect(self.device_input1.setText)
我将输出发送到 QLineEdit
小部件
如何保留函数 运行 并将函数中的新数据插入空行编辑小部件,而不添加多个按钮来一次又一次地启动该函数?
完整代码
import sys
from PyQt5 import QtWidgets as qtw
from PyQt5 import QtCore as qtc
from PyQt5 import QtGui as qtg
import serial
import time
class CustmClass(qtw.QWidget):
'''
description einfügen
'''
# Attribut Signal
custom_attribute = qtc.pyqtSignal(str)
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
# your code will go here
# Interface
self.resize(300, 210)
# button
self.get_output__button = qtw.QPushButton("start function ?")
# lineEdit
self.device_input1 = qtw.QLineEdit()
self.device_input2 = qtw.QLineEdit()
# Layout
vboxlaout = qtw.QVBoxLayout()
vboxlaout.addWidget(self.get_output__button)
vboxlaout.addWidget(self.device_input1)
vboxlaout.addWidget(self.device_input2)
self.setLayout(vboxlaout)
self.show()
# Funktionalität
self.get_output__button.clicked.connect(self.getdevice_data)
self.custom_attribute.connect(self.device_input1.setText)
# self.custom_attribute.connect(self.device_input2.setText)
def getdevice_data(self):
try:
# Serial() opens a serial port
my_serial = serial.Serial(port='COM6', baudrate=2400, bytesize=7,
parity=serial.PARITY_NONE, timeout=None, stopbits=1)
if my_serial.is_open:
print("port open")
# log einfügen
while my_serial.is_open:
data = my_serial.read() # wait forever till data arives
time.sleep(1) # delay
data_left = my_serial.inWaiting()
data += my_serial.read(data_left)
data = data.decode("utf-8", "strict")
if type(data) == str:
print(data)
return self.custom_attribute.emit(data)
else:
print("zu")
except serial.serialutil.SerialException:
print("not open")
# logger hinzufügen
if __name__ == '__main__':
app = qtw.QApplication(sys.argv)
w = CustmClass()
sys.exit(app.exec_())
你不应该在主线程中执行耗时或耗时的循环,因为它们会阻塞事件循环。您必须做的是在辅助线程上执行它并通过信号发送信息。要按顺序获取数据,您可以创建一个迭代器并通过 next() 函数访问每个元素
import sys
import threading
import time
import serial
from PyQt5 import QtWidgets as qtw
from PyQt5 import QtCore as qtc
from PyQt5 import QtGui as qtg
class SerialWorker(qtw.QObject):
dataChanged = qtw.pyqtSignal(str)
def start(self):
threading.Thread(target=self._execute, daemon=True).start()
def _execute(self):
try:
my_serial = serial.Serial(
port="COM6",
baudrate=2400,
bytesize=7,
parity=serial.PARITY_NONE,
timeout=None,
stopbits=1,
)
while my_serial.is_open:
data = my_serial.read() # wait forever till data arives
time.sleep(1) # delay
data_left = my_serial.inWaiting()
data += my_serial.read(data_left)
data = data.decode("utf-8", "strict")
print(data)
self.dataChanged.emit(data)
except serial.serialutil.SerialException:
print("not open")
class Widget(qtw.QWidget):
def __init__(self, parent=None):
super().__init__(parent)
self.resize(300, 210)
self.get_output__button = qtw.QPushButton("start function ?")
self.device_input1 = qtw.QLineEdit()
self.device_input2 = qtw.QLineEdit()
# Layout
vboxlaout = qtw.QVBoxLayout(self)
vboxlaout.addWidget(self.get_output__button)
vboxlaout.addWidget(self.device_input1)
vboxlaout.addWidget(self.device_input2)
self.serial_worker = SerialWorker()
self.device_iterator = iter([self.device_input1, self.device_input2])
self.get_output__button.clicked.connect(self.serial_worker.start)
self.serial_worker.dataChanged.connect(self.on_data_changed)
@qtw.pyqtSlot(str)
def on_data_changed(self, data):
try:
device = next(self.device_iterator)
device.setText(data)
except StopIteration:
pass
if __name__ == "__main__":
app = qtw.QApplication(sys.argv)
w = CustmClass()
w.show()
sys.exit(app.exec_())
我有一个设备与我的界面相连,想将数据插入 QlineEdit
个小部件
此函数 def getdevice_data(self):
从设备接收数据并 returns 将其作为字符串
与self.get_output__button.clicked.connect(self.getdevice_data)
我"start"函数
并使用 self.custom_attribute.connect(self.device_input1.setText)
我将输出发送到 QLineEdit
小部件
如何保留函数 运行 并将函数中的新数据插入空行编辑小部件,而不添加多个按钮来一次又一次地启动该函数?
完整代码
import sys
from PyQt5 import QtWidgets as qtw
from PyQt5 import QtCore as qtc
from PyQt5 import QtGui as qtg
import serial
import time
class CustmClass(qtw.QWidget):
'''
description einfügen
'''
# Attribut Signal
custom_attribute = qtc.pyqtSignal(str)
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
# your code will go here
# Interface
self.resize(300, 210)
# button
self.get_output__button = qtw.QPushButton("start function ?")
# lineEdit
self.device_input1 = qtw.QLineEdit()
self.device_input2 = qtw.QLineEdit()
# Layout
vboxlaout = qtw.QVBoxLayout()
vboxlaout.addWidget(self.get_output__button)
vboxlaout.addWidget(self.device_input1)
vboxlaout.addWidget(self.device_input2)
self.setLayout(vboxlaout)
self.show()
# Funktionalität
self.get_output__button.clicked.connect(self.getdevice_data)
self.custom_attribute.connect(self.device_input1.setText)
# self.custom_attribute.connect(self.device_input2.setText)
def getdevice_data(self):
try:
# Serial() opens a serial port
my_serial = serial.Serial(port='COM6', baudrate=2400, bytesize=7,
parity=serial.PARITY_NONE, timeout=None, stopbits=1)
if my_serial.is_open:
print("port open")
# log einfügen
while my_serial.is_open:
data = my_serial.read() # wait forever till data arives
time.sleep(1) # delay
data_left = my_serial.inWaiting()
data += my_serial.read(data_left)
data = data.decode("utf-8", "strict")
if type(data) == str:
print(data)
return self.custom_attribute.emit(data)
else:
print("zu")
except serial.serialutil.SerialException:
print("not open")
# logger hinzufügen
if __name__ == '__main__':
app = qtw.QApplication(sys.argv)
w = CustmClass()
sys.exit(app.exec_())
你不应该在主线程中执行耗时或耗时的循环,因为它们会阻塞事件循环。您必须做的是在辅助线程上执行它并通过信号发送信息。要按顺序获取数据,您可以创建一个迭代器并通过 next() 函数访问每个元素
import sys
import threading
import time
import serial
from PyQt5 import QtWidgets as qtw
from PyQt5 import QtCore as qtc
from PyQt5 import QtGui as qtg
class SerialWorker(qtw.QObject):
dataChanged = qtw.pyqtSignal(str)
def start(self):
threading.Thread(target=self._execute, daemon=True).start()
def _execute(self):
try:
my_serial = serial.Serial(
port="COM6",
baudrate=2400,
bytesize=7,
parity=serial.PARITY_NONE,
timeout=None,
stopbits=1,
)
while my_serial.is_open:
data = my_serial.read() # wait forever till data arives
time.sleep(1) # delay
data_left = my_serial.inWaiting()
data += my_serial.read(data_left)
data = data.decode("utf-8", "strict")
print(data)
self.dataChanged.emit(data)
except serial.serialutil.SerialException:
print("not open")
class Widget(qtw.QWidget):
def __init__(self, parent=None):
super().__init__(parent)
self.resize(300, 210)
self.get_output__button = qtw.QPushButton("start function ?")
self.device_input1 = qtw.QLineEdit()
self.device_input2 = qtw.QLineEdit()
# Layout
vboxlaout = qtw.QVBoxLayout(self)
vboxlaout.addWidget(self.get_output__button)
vboxlaout.addWidget(self.device_input1)
vboxlaout.addWidget(self.device_input2)
self.serial_worker = SerialWorker()
self.device_iterator = iter([self.device_input1, self.device_input2])
self.get_output__button.clicked.connect(self.serial_worker.start)
self.serial_worker.dataChanged.connect(self.on_data_changed)
@qtw.pyqtSlot(str)
def on_data_changed(self, data):
try:
device = next(self.device_iterator)
device.setText(data)
except StopIteration:
pass
if __name__ == "__main__":
app = qtw.QApplication(sys.argv)
w = CustmClass()
w.show()
sys.exit(app.exec_())