PyQt如何理解我们的班级是从某种事物继承而来的?

时间:2019-04-17 08:35:10

标签: python pyqt pyqt5

我最近在PyQt上进行了很多挖掘工作,并为此做了一些工作,但是突然意识到,我不了解我正在做的一些基本工作。假设从QGraphicsView继承的类如何变为QGraphicsView本身或如何变为QWidget?据我了解,当您从某事物继承时,类只是从您继承的类中获取所有方法。这是下面的一些代码:

import PyQt5.QtWidgets as QtWidgets
import PyQt5.QtCore as QtCore


class First(QtWidgets.QGraphicsView):
    def __init__(self, parent=None):
        super(First, self).__init__(parent)
        print('hello')

class Window(QtWidgets.QDialog):
    def __init__(self, parent=None):
        super(Window, self).__init__(parent)

        self.window = 'test'
        self.title = 'test'
        self.size = (1000, 650)
        self.create()

    def create(self):
        self.setWindowTitle(self.title)
        self.resize(QtCore.QSize(*self.size))
        self.graphicsWidget = First(self)

        self.mainLayout = QtWidgets.QVBoxLayout( )
        self.mainLayout.addWidget(self.graphicsWidget)
        self.setLayout(self.mainLayout)

if __name__ == '__main__':
    import sys

    app = QtWidgets.QApplication(sys.argv)
    window = Window( )
    window.setGeometry(500, 300, 800, 600)
    window.show( )
    sys.exit(app.exec_( ))

例如,在这段代码中,我创建了一个名为“ First”的类,该类继承自QtWidgets.QGraphicsView,然后将其作为小部件添加到Window类中的 mainLayout 中。到现在为止,我一直认为它是理所当然的,并没有考虑太多,但是有人可以向我解释我只接受QWidgets的mainLayout.addWidget()是如何理解在他面前是QWidget吗?因为如果您执行print(type(First)),它将为<class 'sip.wrappertype'>提供一个小部件。谢谢

2 个答案:

答案 0 :(得分:2)

继承是针对类的专业化的,也就是说,继承的类必须具有从其继承的类的特定特征。


QGraphicsView是一个QWidget,因为如果您执行QGraphicsView固有图:

┌--------------┐   ┌--------------┐ 
|   QObject    |   | QPaintDevice |
└------┬-------┘   └-------┬------┘ 
       |                   |
       └---------┬---------┘
                 |
          ┌------┴------┐
          |   QWidget   |
          └------┬------┘
                 |
          ┌------┴------┐
          |   QFrame    |
          └------┬------┘
                 |
       ┌---------┴---------┐
       |QAbstractScrollArea|
       └---------┬---------┘
                 |
       ┌---------┴---------┐
       |   QGraphicsView   |
       └-------------------┘

由此得出结论:

  • QGraphicsView是一个QAbstractScrollArea。
  • QGraphicsView是一个QFrame。
  • QGraphicsView是一个QWidget。
  • QGraphicsView是一个QObject。
  • QGraphicsView是一个QPaintDevice。

为什么print(type(First))返回<class 'sip.wrappertype'>

如果对docs进行了审核:

  

[...]
SIP实现了两个超类型sip.simplewrapper和   sip.wrapper和一个元类型sip.wrappertype。

     

sip.simplewrapper是sip.wrapper的超类型。的超类型   sip.simplewrapper是对象。

     

sip.wrappertype是sip.simplewrapper和   sip.wrapper。 sip.wrappertype的超类型是type。

     

sip.wrapper支持对象所有权的概念,在   对象的所有权,默认情况下是所有所有者的超类型   SIP生成的类型。
  [...]

由此得出sip.wrappertype是QObject的元类。这就是您要执行的操作,因为type(FooClass)返回FooClass的元类。

如果要打印类,则必须使用该对象:

print(type(self.graphicsWidget))

输出:

<class '__main__.First'>

要确定对象属于某个类(或其父类),可以使用以下方法,例如,如果它是QWidget:

1。

if isinstance(obj, QtWidgets.QWidget):
    print("is QWidget")

2。。如果它是QObject

2.1

if qobject.inherits("QWidget"):
    print("is QWidget")

2.2

if qobject.isWidgetType():
    print("is QWidget")

答案 1 :(得分:1)

First()实例也是QtWidgets.QGraphicsView的实例,正是因为您这样说,即您使类继承自QtWidgets.QGraphicsView。您可以检查以下内容:

f = First()
isinstance(f, QtWidgets.QGraphicsView)  # True

由于QtWidgets.QGraphicsView依次继承自QtWidgets.QWidget,因此以下内容也适用:

isinstance(f, PyQt5.QtWidgets.QWidget)

因此,addWidget愉快地将实例接受为QWidget。 (请注意,addWidget不必对其接收到的实例进行显式类型检查。代码可以仅由于实例“像鸭子一样嘎嘎叫”(即它具有适当的QWidget方法)而起作用。