2

loadUI がロードされた、さまざまなウィジェットを持つ QMainWindow があります。これらのウィジェットの 1 つは、開始時に空の QGroupBox です (レイアウトもありません)。また、それ自体にさまざまなウィジェット (CustomWidget) を作成するカスタム ウィジェット (CustomWidgetContainer) もあります。いくつ、どれが実行時に決定されます。

問題は、CustomWidgetContainer にウィジェットを追加するための独自のレイアウトがあることです。ただし、CustomWidgetContainer が QMainWindow に追加されると、レイアウトは QMainWindow のペアレント レイアウトに置き換えられます (これは予期され、文書化された動作です)。

ただし、この CustomWidgetContainer が独自のレイアウト (self.layout()) を必要として、追加の CustomWidget を追加するか、すべての CustomWidget を削除する必要がある場合、self.layout() は None を返します。

親に既にレイアウトがあるかどうかを確認するためのあらゆる種類の回避策のチェックを想像できます(それを使用する、親にレイアウトを設定するなど)。しかし、私はこの悪い習慣を考えているので、私の子 (CustomWidgetContainer) クラスから私の親 (QMainWindow) で何もしたくありません。

スニペット: ScalarInputEdit == CustomWidget、InputsWidget == CustomWidgetContainer

class MainWindow(qt.QMainWindow):
    ....
    def connect(self, host, port):
        self._client = PymotClient(host, port)
        self.client.connect()        
        self._set_enabled_connected()
        self.log.info("Connected to %s:%d", host, port)

        self._inputswidget = InputsWidget(self, self.client)
        print "Layout Before:", self._inputswidget.layout()
        self.inputsBox.setLayout(self._inputswidget.layout())
        print "Layout After:", self._inputswidget.layout()
        self._inputswidget.append_inputs_from_client()

class InputsWidget(qt.QWidget):
    def __init__(self, parent, client):
        super(InputsWidget, self).__init__(parent)
        ....
        self.setLayout(qt.QGridLayout())

    def append_inputs_from_client(self):
        for inp in some_list:
           self.append_input(inp)

    def append_input(self, pbo):
        self.layout().addWidget(ScalarInputEdit(self, self.client, pbo))

    def remove_all_inputs(self):
        for child in self.layout().children():
            child.deleteLater()

出力:

Layout Before: <PyQt4.QtGui.QGridLayout object at 0x8880ecc> 
Layout After: None
Exception: 
  File    "...inputwidgets.py", line 134, in append_input
    self.layout().addWidget(ScalarInputEdit(self, self.client, pbo))
AttributeError: 'NoneType' object has no attribute 'addWidget'

これを行うための標準/グッドプラクティスは何ですか? 後の段階(__ init__の後)でlayout()が必要になることはよくあることです。しかし、一部の使用例では MY レイアウトを置き換えたり、さらに悪いことにそれを削除したりするように見えるため、追加/削除するレイアウトを確認するにはどうすればよいですか?

4

1 に答える 1

1

見積もり:

when the CustomWidgetContainer gets added to the QMainWindow, the layout is
replaced with the parenting layout of the QMainWindow (which is expected and
documented behaviour).

これは私には非常に不明確です。あなたが言及している文書化された動作は何ですか?

self._inputswidget = InputsWidget(self, self.client)
print "Layout Before:", self._inputswidget.layout()
self.inputsBox.setLayout(self._inputswidget.layout())

inputsBoxのレイアウトを のレイアウトに設定するのはなぜ_inputswidgetですか?

print "Layout After:", self._inputswidget.layout()

に転送したばかりなので、のレイアウトは_inputswidget自然にNone今のようになります。inputsBox

self._inputswidget.append_inputs_from_client()

のレイアウトを取り去り、_inputswidgetそれを置き換えていないため、明らかにこれは機能しません。

于 2012-11-13T17:28:00.120 に答える