繁体   English   中英

如何重新初始化python pyqt5 gui

[英]How do I re-initialize a python pyqt5 gui

我有一个由两个QWidget组成的简单程序。 一个是输入窗口,另一个是输出窗口。 输入窗口具有QlineEdit,一旦我使用信号和插槽按下Apply,该值便传递到输出窗口QlineEdit。 我当前的程序是什么样的:

在此处输入图片说明

到目前为止,一切正常。 我想要实现的是,根据我在输入中输入的数字,应该在输出窗口中出现类似数量的“ Entry options”(新的QlineEdits)。 我要实现的目标:

在此处输入图片说明

我希望我要实现的目标很明确。 在下面,您会发现我的工作代码如图1所示。我刚刚开始编程,因此在此阶段,一些小的代码示例为我提供的帮助不仅仅包括手册。

from PyQt5.QtWidgets import QLabel, QHBoxLayout, QWidget, QLineEdit, QPushButton, QGridLayout, QApplication
from PyQt5.QtCore import pyqtSignal, pyqtSlot
import sys


class Input(QWidget):

    dataChanged = pyqtSignal(str)

    def __init__(self):
        super().__init__()

        self.init_ui()

    def init_ui(self):

        self.input_label = QLabel('Entries:', self)
        self.input_cell = QLineEdit()
        self.apply_button = QPushButton('Apply')
        self.apply_button.setEnabled(False)

        self.hboxLayout = QHBoxLayout(self)

        self.hboxLayout.addWidget(self.input_label)
        self.hboxLayout.addWidget(self.input_cell)
        self.hboxLayout.addWidget(self.apply_button)

        self.setLayout(self.hboxLayout)

        self.input_cell.textChanged.connect(self.apply_change)

        self.setWindowTitle("Input window")
        self.show()

    def apply_change(self, value):
        self.apply_button.setEnabled(True)
        self.send_this = value
        self.apply_button.clicked.connect(self.send_value)

    def send_value(self, value):
        if value is False:
            self.dataChanged.emit(self.send_this)
            self.apply_button.setEnabled(False)


class Output(QWidget):
    def __init__(self):
        super().__init__()

        self.init_ui()

    def init_ui(self):
        self.setWindowTitle('Output window')

        self.content()

        self.show()

    def content(self):
        layout = QGridLayout()
        output_label = QLabel('Nr. of entries:', self)
        self.output_cell = QLineEdit()

        entry_label_1 = QLabel('Entry1:', self)
        entry_cell_1 = QLineEdit()
        layout.addWidget(entry_label_1, 2, 0)
        layout.addWidget(entry_cell_1, 2, 2)
        entry_label_2 = QLabel('Entry2:', self)
        entry_cell_2 = QLineEdit()
        layout.addWidget(entry_label_2, 4, 0)
        layout.addWidget(entry_cell_2, 4, 2)

        layout.addWidget(output_label, 0, 0)
        layout.addWidget(self.output_cell, 0, 2)

        layout.setSpacing(10)
        self.setLayout(layout)

    def make_connection(self, input_object):
        input_object.dataChanged.connect(self.get_input_value)

    @pyqtSlot(str)
    def get_input_value(self, val):
        self.output_cell.setText(val)


if __name__ == '__main__':
    app = QApplication(sys.argv)
    inp = Input()
    out = Output()
    # Making the connection
    out.make_connection(inp)
    sys.exit(app.exec_())

好消息是,您的问题中有一半很容易解决。 为此,请替换代码并执行以查看结果。

def content(self):
    layout = QGridLayout()
    output_label = QLabel('Nr. of entries:', self)
    self.output_cell = QLineEdit()

    for x in range(3):
        entry_label_1 = QLabel('Entry'+str(x)+':', self)
        entry_cell_1 = QLineEdit()
        layout.addWidget(entry_label_1, x+1, 0)
        layout.addWidget(entry_cell_1, x+1, 2)

    layout.addWidget(output_label, 0, 0)
    layout.addWidget(self.output_cell, 0, 2)
    layout.setSpacing(10)
    self.setLayout(layout)

在我的示例中,我使用range(3)作为循环示例,以告诉程序创建3个文本框。 如果将其更改为range(10)...好吧,请猜测。

现在最棘手的部分是,您只需要捕获输入数据并用int(self.output_cell.text())替换range(3)就可以了。 但是,有很多方法可以实现这一目标。 您选择使用信号,而我大多数时候在程序上使用全局变量,因此我不完全了解它对您如何工作。 当我找到一种简便的方法时,将更新此答案。

@saelyth的答案很有趣,但是由于每次更改数字都会创建布局,因此使用内存的方式不正确,我的解决方案不会创建更多的布局,而是会重用它们。

为此,我们必须进行一些更改以创建更稳定的代码:

  1. QIntValidator设置为QLineEdit以便强制用户仅放置数字:

self.input_cell.setValidator(QIntValidator(0, 1000, self))
  1. 将QGridLayout更改为QFormLayout,因为它已优化为在另一个小部件旁边有一个标签。

layout = QFormLayout(self)
  1. 我们必须使用addRow()添加项目,并使用removeRow()删除项目:

@pyqtSlot(str)
def get_input_value(self, val):

    self.output_cell.setText(val)
    val_int = int(val)

    if val_int > (self.layout().rowCount() - 1):
        [self.hboxLayout.addRow('Entry '+str(i), QLineEdit(self)) for i in range(self.layout().rowCount(), val_int+1)]

    elif val_int < (self.layout().rowCount() - 1):
        for i in range(self.layout().rowCount(), val_int, -1):
            child = self.hboxLayout.removeRow(i)

完整的代码:

class Input(QWidget):

    dataChanged = pyqtSignal(str)

    def __init__(self):
        super().__init__()

        self.init_ui()

    def init_ui(self):

        self.input_label = QLabel('Entries:', self)
        self.input_cell = QLineEdit(self)
        self.input_cell.setValidator(QIntValidator(0, 1000, self))
        self.apply_button = QPushButton('Apply')
        self.apply_button.setEnabled(False)

        self.hboxLayout = QHBoxLayout(self)

        self.hboxLayout.addWidget(self.input_label)
        self.hboxLayout.addWidget(self.input_cell)
        self.hboxLayout.addWidget(self.apply_button)

        self.setLayout(self.hboxLayout)

        self.input_cell.textChanged.connect(self.apply_change)
        self.apply_button.clicked.connect(self.send_value)

        self.setWindowTitle("Input window")
        self.show()

    def apply_change(self, value):
        self.apply_button.setEnabled(True)

    def send_value(self, value):
        if value is False:
            self.dataChanged.emit(self.input_cell.text())
            self.apply_button.setEnabled(False)


class Output(QWidget):
    def __init__(self):
        super().__init__()

        self.init_ui()

    def init_ui(self):
        self.setWindowTitle('Output window')
        self.content()
        self.show()

    def content(self):
        layout = QFormLayout(self)
        self.output_cell = QLineEdit(self)
        layout.addRow('Nr. of entries:', self.output_cell)
        layout.setSpacing(10)

    def make_connection(self, input_object):
        input_object.dataChanged.connect(self.get_input_value)

    @pyqtSlot(str)
    def get_input_value(self, val):

        self.output_cell.setText(val)
        val_int = int(val)

        if val_int > (self.layout().rowCount() - 1):
            [self.layout().addRow('Entry '+str(i), QLineEdit(self)) for i in range(self.layout().rowCount(), val_int+1)]

        elif val_int < (self.layout().rowCount() - 1):
            for i in range(self.layout().rowCount(), val_int, -1):
                child = self.layout().removeRow(i)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM