Esempio n. 1
0
    def __init__(self, parent=None):
        QOpenGLWidget.__init__(self, parent)
        QOpenGLFunctions.__init__(self)

        self.core = "--coreprofile" in QCoreApplication.arguments()
        self.xRot = 0
        self.yRot = 0
        self.zRot = 0
        self.lastPos = 0
        self.logo = Logo()
        self.vao = QOpenGLVertexArrayObject()
        self.logoVbo = QOpenGLBuffer()
        self.program = QOpenGLShaderProgram()
        self.projMatrixLoc = 0
        self.mvMatrixLoc = 0
        self.normalMatrixLoc = 0
        self.lightPosLoc = 0
        self.proj = QMatrix4x4()
        self.camera = QMatrix4x4()
        self.world = QMatrix4x4()
        self.transparent = "--transparent" in QCoreApplication.arguments()
        if self.transparent:
            fmt = self.format()
            fmt.setAlphaBufferSize(8)
            self.setFormat(fmt)
Esempio n. 2
0
    def __init__(self):
        qDebug('RendererHelper::__init__()')
        super().__init__()
        self.__m_vtkFboItem = None
        self.gl = QOpenGLFunctions()

        self.__m_mouseLeftButton: QMouseEvent = None
        self.__m_mouseEvent: QMouseEvent = None
        self.__m_moveEvent: QMouseEvent = None
        self.__m_wheelEvent: QWheelEvent = None

        self.__m_firstRender: bool = True

        self.renderWindow: vtk.vtkGenericOpenGLRenderWindow = vtk.vtkGenericOpenGLRenderWindow(
        )
        self.renderer: vtk.vtkRenderer = vtk.vtkRenderer()
        self.renderWindow.AddRenderer(self.renderer)

        # * Interactor
        self.interactor: vtk.vtkGenericRenderWindowInteractor = vtk.vtkGenericRenderWindowInteractor(
        )
        self.interactor.EnableRenderOff()
        self.renderWindow.SetInteractor(self.interactor)

        # * Initialize the OpenGL context for the renderer
        self.renderWindow.OpenGLInitContext()

        # * Interactor Style
        style = vtk.vtkInteractorStyleTrackballCamera()
        style.SetDefaultRenderer(self.renderer)
        style.SetMotionFactor(10.0)
        self.interactor.SetInteractorStyle(style)
Esempio n. 3
0
    def __init__(self, window, project):
        super(View, self).__init__(window)
        QOpenGLFunctions.__init__(self)

        self.setFocusPolicy(Qt.StrongFocus)
        self.aspectRatio = 0.0
        self.shiftKey = False
        self.ctrlKey = False
        self.lastMousePos = QPoint()

        self.project = project
        self.project.redraw.connect(self.update, type=Qt.QueuedConnection)
        self.project.aspectRatio.connect(self.setAspectRatio,
                                         type=Qt.QueuedConnection)
        self.cameraMode.connect(self.project.setCameraMode,
                                type=Qt.QueuedConnection)
        self.cameraOrigin.connect(self.project.setCameraAtOrigin,
                                  type=Qt.QueuedConnection)
        self.cameraMove.connect(self.project.moveCamera,
                                type=Qt.QueuedConnection)
        self.cameraOrient.connect(self.project.orientCamera,
                                  type=Qt.QueuedConnection)
        self.cameraZoom.connect(self.project.zoomCamera,
                                type=Qt.QueuedConnection)
        self.cameraView.connect(self.project.setCameraView,
                                type=Qt.QueuedConnection)
        self.displayRatio.connect(self.project.setDisplayRatio,
                                  type=Qt.QueuedConnection)
        self.togglePicture.connect(self.project.togglePicture,
                                   type=Qt.QueuedConnection)
        self.removeView.connect(self.project.removeCurrentView,
                                type=Qt.QueuedConnection)
        self.selected.connect(self.project.select, type=Qt.QueuedConnection)
Esempio n. 4
0
    def __init__(self, parent=None):
        QOpenGLWidget.__init__(self, parent)
        QOpenGLFunctions.__init__(self)

        self.core = "--coreprofile" in QCoreApplication.arguments()
        self.xRot = 0
        self.yRot = 0
        self.zRot = 0
        self.lastPos = 0
        self.logo = Logo()
        self.vao = QOpenGLVertexArrayObject()
        self.logoVbo = QOpenGLBuffer()
        self.program = QOpenGLShaderProgram()
        self.projMatrixLoc = 0
        self.mvMatrixLoc = 0
        self.normalMatrixLoc = 0
        self.lightPosLoc = 0
        self.proj = QMatrix4x4()
        self.camera = QMatrix4x4()
        self.world = QMatrix4x4()
        self.transparent = "--transparent" in QCoreApplication.arguments()
        if self.transparent:
            fmt = self.format()
            fmt.setAlphaBufferSize(8)
            self.setFormat(fmt)
    def initilize(self):
        self._glFunc = QOpenGLFunctions()  # used in all OpenGL systems
        self._renderWindow = vtk.vtkGenericOpenGLRenderWindow(
        )  # Can not Resize
        # self._renderWindow = vtk.vtkExternalOpenGLRenderWindow()  # Recommend; vtk-8.1.2-py3-none-any.whl
        self._renderer: vtk.vtkRenderer = vtk.vtkRenderer()
        self._renderWindow.AddRenderer(self._renderer)

        # * Interactor
        self._rwInteractor = vtk.vtkGenericRenderWindowInteractor()
        self._rwInteractor.EnableRenderOff()
        self._rwInteractor.SetRenderWindow(self._renderWindow)

        # * Initialize the OpenGL context for the renderer
        self._renderWindow.OpenGLInitContext()

        # * Interactor Style
        style = vtk.vtkInteractorStyleTrackballCamera()
        style.SetDefaultRenderer(self._renderer)
        style.SetMotionFactor(10.0)
        self._rwInteractor.SetInteractorStyle(style)

        self.__m_mouseLeftButton: QMouseEvent = None
        self.__m_mouseEvent: QMouseEvent = None
        self.__m_moveEvent: QMouseEvent = None
        self.__m_wheelEvent: QWheelEvent = None
        self.__fboItem: "QmlVTKRenderWindowInteractor" = None
        self.__firstRender = True
        self.jointPose = np.array([0, 0, 0, 0, 0, 0])
        self._axis = [[0, 0, 1], [0, 1, 0], [0, 1, 0], [0, 1, 0], [0, 0, 1],
                      [0, 1, 0]]
        self.__jointPoseChanged = False
Esempio n. 6
0
    def __init__(self, render_window, interactor, *args, **kwargs):
        self.gl = QOpenGLFunctions()
        QQuickFramebufferObject.Renderer.__init__(self)
        QObject.__init__(self)
        self.__fbo = None

        self.__m_mouseLeftButton: QMouseEvent = None
        self.__m_mouseEvent: QMouseEvent = None
        self.__m_moveEvent: QMouseEvent = None
        self.__m_wheelEvent: QWheelEvent = None

        self.__m_firstRender: bool = True

        # self._render_window: vtk.vtkGenericOpenGLRenderWindow = vtk.vtkGenericOpenGLRenderWindow()
        self._renderer = [RendererOPENGL(parent=self, **kwargs)]
        self._renderer[0].AutomaticLightCreationOn()
        self._renderer_index = 0

        self._render_window = render_window
        self._render_window.OpenGLInitContext()
        self._interactor = interactor

        self.render_signal.connect(self._render)
        self.dump_ren_win.connect(self._dump_ren_win)
        self.__m_vtkFboItem = None
        self.__image_data = None
Esempio n. 7
0
    def __init__(self, parent=None):
        QOpenGLWidget.__init__(self, parent)
        QOpenGLFunctions.__init__(self)
        self.setMinimumSize(32, 32)

        self.info = ""
        self._supported_images = [
            "TGA", "PNG", "JPG", "JPEG", "TIF", "TIFF", "BMP", "DDS"
        ]

        # indices
        indices = [0, 1, 3, 1, 2, 3]
        self._indices = array('I', indices)

        # vertices
        # 3 position | 2 texture coord
        vertex = [
            1.0,
            1.0,
            0.0,
            1.0,
            1.0,  # top right
            1.0,
            -1.0,
            0.0,
            1.0,
            0.0,  # bottom right
            -1.0,
            -1.0,
            0.0,
            0.0,
            0.0,  # bottom left
            -1.0,
            1.0,
            0.0,
            0.0,
            1.0  # top left
        ]
        self._vertex = array('f', vertex)

        # opengl data related
        self._program = QOpenGLShaderProgram()
        self._program_bg = QOpenGLShaderProgram()
        self._vao = QOpenGLVertexArrayObject()
        self._vbo = QOpenGLBuffer(QOpenGLBuffer.VertexBuffer)
        self._texture = None
        self._texture_size = (1, 1)
        self._location = ()

        self._colors_default = (QColor.fromRgbF(0.65, 0.65, 0.65, 1.0),
                                QColor.fromRgbF(0.90, 0.90, 0.90, 1.0))
        self._u_colors = self._colors_default
        self._height = QVector4D(0, self.height(), 0, 0)

        self._u_channels = QMatrix4x4(1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0,
                                      0, 0)
    def __init__(self):
        super(QmlVTKOpenGLRenderWindowInteractor, self).__init__()

        self._glFunc = QOpenGLFunctions()

        self._RenderWindow = vtk.vtkGenericOpenGLRenderWindow()
        self._Iren = vtk.vtkGenericRenderWindowInteractor()
        self._ren = vtk.vtkRenderer()
        self._RenderWindow.AddRenderer(self._ren)
        self._Iren.SetRenderWindow(self._RenderWindow)
        self._RenderWindow.OpenGLInitContext()
Esempio n. 9
0
class RendererHelper(QObject):
    def __init__(self):
        qDebug('RendererHelper::__init__()')
        super().__init__()
        self.__m_vtkFboItem = None
        self.gl = QOpenGLFunctions()

        self.__m_mouseLeftButton: QMouseEvent = None
        self.__m_mouseEvent: QMouseEvent = None
        self.__m_moveEvent: QMouseEvent = None
        self.__m_wheelEvent: QWheelEvent = None

        self.__m_firstRender: bool = True

        self.renderWindow: vtk.vtkGenericOpenGLRenderWindow = vtk.vtkGenericOpenGLRenderWindow(
        )
        self.renderer: vtk.vtkRenderer = vtk.vtkRenderer()
        self.renderWindow.AddRenderer(self.renderer)

        # * Interactor
        self.interactor: vtk.vtkGenericRenderWindowInteractor = vtk.vtkGenericRenderWindowInteractor(
        )
        self.interactor.EnableRenderOff()
        self.renderWindow.SetInteractor(self.interactor)

        # * Initialize the OpenGL context for the renderer
        self.renderWindow.OpenGLInitContext()

        # * Interactor Style
        style = vtk.vtkInteractorStyleTrackballCamera()
        style.SetDefaultRenderer(self.renderer)
        style.SetMotionFactor(10.0)
        self.interactor.SetInteractorStyle(style)

    def setVtkFboItem(self, vtkFboItem):
        self.__m_vtkFboItem = vtkFboItem

    def synchronize(self, item: QQuickFramebufferObject):
        rendererSize = self.renderWindow.GetSize()
        if self.__m_vtkFboItem.width() != rendererSize[
                0] or self.__m_vtkFboItem.height() != rendererSize[1]:
            self.renderWindow.SetSize(int(self.__m_vtkFboItem.width()),
                                      int(self.__m_vtkFboItem.height()))

        # * Copy mouse events
        print(self.__m_vtkFboItem.getLastMouseButton().isAccepted())
        if not self.__m_vtkFboItem.getLastMouseButton().isAccepted():
            self.__m_mouseEvent = self.__m_vtkFboItem.getLastMouseButton()

        if not self.__m_vtkFboItem.getLastMoveEvent().isAccepted():
            self.__m_moveEvent = self.__m_vtkFboItem.getLastMoveEvent()

        if self.__m_vtkFboItem.getLastWheelEvent(
        ) and not self.__m_vtkFboItem.getLastWheelEvent().isAccepted():
            self.__m_wheelEvent = self.__m_vtkFboItem.getLastWheelEvent()

    def render(self):
        self.renderWindow.PushState()
        self.openGLInitState()
        self.renderWindow.Start()

        if self.__m_firstRender:
            self.renderWindow.SetOffScreenRendering(True)
            sceneHelper = SceneHelper(self.renderer)
            sceneHelper.initScene()
            self.resetCamera()
            self.__m_firstRender = False

        # * Process camera related commands
        if self.__m_mouseEvent and not self.__m_mouseEvent.isAccepted():
            self.interactor.SetEventInformationFlipY(
                self.__m_mouseEvent.x(), self.__m_mouseEvent.y(), 1 if
                (self.__m_mouseEvent.modifiers() & Qt.ControlModifier) > 0 else
                0, 1 if
                (self.__m_mouseEvent.modifiers() & Qt.ShiftModifier) > 0 else
                0, '0', 1 if self.__m_mouseEvent.type()
                == QEvent.MouseButtonDblClick else 0)

            if self.__m_mouseEvent.type() == QEvent.MouseButtonPress:
                self.interactor.InvokeEvent(
                    vtk.vtkCommand.LeftButtonPressEvent)
            elif self.__m_mouseEvent.type() == QEvent.MouseButtonRelease:
                self.interactor.InvokeEvent(
                    vtk.vtkCommand.LeftButtonReleaseEvent)

            self.__m_mouseEvent.accept()

        # * Process move event
        if self.__m_moveEvent and not self.__m_moveEvent.isAccepted():
            if self.__m_moveEvent.type(
            ) == QEvent.MouseMove and self.__m_moveEvent.buttons() & (
                    Qt.RightButton | Qt.LeftButton):
                self.interactor.SetEventInformationFlipY(
                    self.__m_moveEvent.x(), self.__m_moveEvent.y(), 1 if
                    (self.__m_moveEvent.modifiers() & Qt.ControlModifier) > 0
                    else 0, 1 if
                    (self.__m_moveEvent.modifiers() & Qt.ShiftModifier) > 0
                    else 0, '0', 1 if self.__m_moveEvent.type()
                    == QEvent.MouseButtonDblClick else 0)

                self.interactor.InvokeEvent(vtk.vtkCommand.MouseMoveEvent)

            self.__m_moveEvent.accept()

        # * Process wheel event
        if self.__m_wheelEvent and not self.__m_wheelEvent.isAccepted():
            self.interactor.SetEventInformationFlipY(
                self.__m_wheelEvent.x(), self.__m_wheelEvent.y(), 1 if
                (self.__m_wheelEvent.modifiers() & Qt.ControlModifier) > 0 else
                0, 1 if
                (self.__m_wheelEvent.modifiers() & Qt.ShiftModifier) > 0 else
                0, '0', 1 if self.__m_wheelEvent.type()
                == QEvent.MouseButtonDblClick else 0)

            if self.__m_wheelEvent.delta() > 0:
                self.interactor.InvokeEvent(
                    vtk.vtkCommand.MouseWheelForwardEvent)
            elif self.__m_wheelEvent.delta() < 0:
                self.interactor.InvokeEvent(
                    vtk.vtkCommand.MouseWheelBackwardEvent)

            self.__m_wheelEvent.accept()

        # Render
        self.renderWindow.Render()
        self.renderWindow.PopState()
        self.__m_vtkFboItem.window().resetOpenGLState()

    def openGLInitState(self):
        self.renderWindow.OpenGLInitState()
        self.renderWindow.MakeCurrent()
        self.gl.initializeOpenGLFunctions()

    def createFramebufferObject(self, size: QSize) -> QOpenGLFramebufferObject:
        format = QOpenGLFramebufferObjectFormat()
        format.setAttachment(QOpenGLFramebufferObject.Depth)
        framebufferObject = QOpenGLFramebufferObject(size, format)
        framebufferObject.release()
        return framebufferObject

    def addModel(self, fileName):
        reader = vtk.vtkSTLReader()
        url = QUrl(fileName)
        reader.SetFileName(url.path())
        reader.Update()

        transform = vtk.vtkTransform()
        transform.Scale((.5, .5, .5))

        transformFilter = vtk.vtkTransformPolyDataFilter()
        transformFilter.SetInputConnection(reader.GetOutputPort())
        transformFilter.SetTransform(transform)
        transformFilter.Update()

        mapper = vtk.vtkPolyDataMapper()
        mapper.SetInputConnection(transformFilter.GetOutputPort())

        actor = vtk.vtkActor()
        actor.SetMapper(mapper)
        self.renderer.AddActor(actor)

        print(f"Added...{url.path()}")

    def plot(self, plot_type: str):
        print(plot_type)
        (w, h) = self.renderWindow.GetSize()
        w = int(w / 10)
        h = int(h / 10)
        radius = 10
        if plot_type == 'sphere':
            polyDataSource = vtk.vtkSphereSource()
            polyDataSource.SetRadius(radius)
            polyDataSource.SetPhiResolution(50)
            polyDataSource.SetThetaResolution(50)
            polyDataSource.SetCenter([
                random.randint(-w, w),
                random.randint(-h, h),
                random.randint(radius, h)
            ])
        else:
            polyDataSource = vtk.vtkConeSource()
        mapper = vtk.vtkPolyDataMapper()
        mapper.SetInputConnection(polyDataSource.GetOutputPort())
        actor = vtk.vtkActor()
        actor.SetMapper(mapper)

        actor.GetProperty().SetColor(
            [random.random(),
             random.random(),
             random.random()])
        # actor.GetProperty().SetOpacity(random.random())

        self.renderer.AddActor(actor)

    def addActors(self, actors):
        for actor in actors:
            self.renderer.AddActor(actor)

    def resetCamera(self):
        # * Seting the clipping range here messes with the opacity of the actors prior to moving the camera
        m_camPositionX = -10
        m_camPositionY = -20
        m_camPositionZ = 10
        self.renderer.GetActiveCamera().SetPosition(m_camPositionX,
                                                    m_camPositionY,
                                                    m_camPositionZ)
        self.renderer.GetActiveCamera().SetFocalPoint(0.0, 0.0, 0.0)
        self.renderer.GetActiveCamera().SetViewUp(0.0, 0.0, 1.0)
        self.renderer.ResetCameraClippingRange()

    def getCamera(self):
        return self.renderer.GetActiveCamera()

    def setFocalPoint(self, point):
        self.renderer.GetActiveCamera().SetFocalPoint(*point)
        self.renderer.GetActiveCamera().SetViewUp(0.0, 0.0, 1.0)
        self.renderer.ResetCameraClippingRange()
Esempio n. 10
0
class RendererHelper(QObject):
    def __init__(self):
        qDebug('RendererHelper::__init__()')
        super().__init__()
        self.__m_vtkFboItem = None
        self.gl = QOpenGLFunctions()

        self.devicePixelRatio = 1
        self.__m_mouseLeftButton: QMouseEvent = None
        self.__m_mouseEvent: QMouseEvent = None
        self.__m_moveEvent: QMouseEvent = None
        self.__m_wheelEvent: QWheelEvent = None

        self.__m_firstRender: bool = True

        self.renderWindow: vtk.vtkGenericOpenGLRenderWindow = vtk.vtkGenericOpenGLRenderWindow(
        )
        self.renderer: vtk.vtkRenderer = vtk.vtkRenderer()
        self.renderWindow.AddRenderer(self.renderer)

        # * Interactor
        self.interactor: vtk.vtkGenericRenderWindowInteractor = vtk.vtkGenericRenderWindowInteractor(
        )
        self.interactor.EnableRenderOff()
        self.renderWindow.SetInteractor(self.interactor)

        # * Initialize the OpenGL context for the renderer
        self.renderWindow.OpenGLInitContext()

        # * Interactor Style
        style = vtk.vtkInteractorStyleTrackballCamera()
        style.SetDefaultRenderer(self.renderer)
        style.SetMotionFactor(10.0)
        self.interactor.SetInteractorStyle(style)

    def setVtkFboItem(self, vtkFboItem):
        self.__m_vtkFboItem = vtkFboItem

    def synchronize(self, item: QQuickFramebufferObject):
        qDebug('SYNC')
        rendererSize = self.renderWindow.GetSize()
        if self.__m_vtkFboItem.width() * self.devicePixelRatio != rendererSize[
                0] or self.__m_vtkFboItem.height(
                ) * self.devicePixelRatio != rendererSize[1]:
            self.renderWindow.SetSize(
                int(self.__m_vtkFboItem.width() * self.devicePixelRatio),
                int(self.__m_vtkFboItem.height() * self.devicePixelRatio))

        # * Copy mouse events
        qDebug(
            f'Mouse : {self.__m_vtkFboItem.getLastMouseButton().isAccepted()}')
        if not self.__m_vtkFboItem.getLastMouseButton().isAccepted():
            self.__m_mouseEvent = self.__m_vtkFboItem.getLastMouseButton()

        if not self.__m_vtkFboItem.getLastMoveEvent().isAccepted():
            self.__m_moveEvent = self.__m_vtkFboItem.getLastMoveEvent()

        if self.__m_vtkFboItem.getLastWheelEvent(
        ) and not self.__m_vtkFboItem.getLastWheelEvent().isAccepted():
            self.__m_wheelEvent = self.__m_vtkFboItem.getLastWheelEvent()

    def render(self):
        qDebug('RENDER!')
        self.renderWindow.PushState()
        self.openGLInitState()
        self.renderWindow.Start()

        if self.__m_firstRender:
            self.renderWindow.SetOffScreenRendering(True)
            sceneHelper = SceneHelper(self.renderer)
            sceneHelper.initScene()
            self.resetCamera()
            self.__m_firstRender = False

        # * Process camera related commands
        if self.__m_mouseEvent and not self.__m_mouseEvent.isAccepted():
            self.interactor.SetEventInformationFlipY(
                self.__m_mouseEvent.x(), self.__m_mouseEvent.y(), 1 if
                (self.__m_mouseEvent.modifiers() & Qt.ControlModifier) > 0 else
                0, 1 if
                (self.__m_mouseEvent.modifiers() & Qt.ShiftModifier) > 0 else
                0, '0', 1 if self.__m_mouseEvent.type()
                == QEvent.MouseButtonDblClick else 0)

            if self.__m_mouseEvent.type() == QEvent.MouseButtonPress:
                self.interactor.InvokeEvent(
                    vtk.vtkCommand.LeftButtonPressEvent)
            elif self.__m_mouseEvent.type() == QEvent.MouseButtonRelease:
                self.interactor.InvokeEvent(
                    vtk.vtkCommand.LeftButtonReleaseEvent)

            self.__m_mouseEvent.accept()

        # * Process move event
        if self.__m_moveEvent and not self.__m_moveEvent.isAccepted():
            if self.__m_moveEvent.type(
            ) == QEvent.MouseMove and self.__m_moveEvent.buttons() & (
                    Qt.RightButton | Qt.LeftButton):
                self.interactor.SetEventInformationFlipY(
                    self.__m_moveEvent.x(), self.__m_moveEvent.y(), 1 if
                    (self.__m_moveEvent.modifiers() & Qt.ControlModifier) > 0
                    else 0, 1 if
                    (self.__m_moveEvent.modifiers() & Qt.ShiftModifier) > 0
                    else 0, '0', 1 if self.__m_moveEvent.type()
                    == QEvent.MouseButtonDblClick else 0)

                self.interactor.InvokeEvent(vtk.vtkCommand.MouseMoveEvent)

            self.__m_moveEvent.accept()

        # * Process wheel event
        if self.__m_wheelEvent and not self.__m_wheelEvent.isAccepted():
            self.interactor.SetEventInformationFlipY(
                self.__m_wheelEvent.x(), self.__m_wheelEvent.y(), 1 if
                (self.__m_wheelEvent.modifiers() & Qt.ControlModifier) > 0 else
                0, 1 if
                (self.__m_wheelEvent.modifiers() & Qt.ShiftModifier) > 0 else
                0, '0', 1 if self.__m_wheelEvent.type()
                == QEvent.MouseButtonDblClick else 0)

            if self.__m_wheelEvent.delta() > 0:
                self.interactor.InvokeEvent(
                    vtk.vtkCommand.MouseWheelForwardEvent)
            elif self.__m_wheelEvent.delta() < 0:
                self.interactor.InvokeEvent(
                    vtk.vtkCommand.MouseWheelBackwardEvent)

            self.__m_wheelEvent.accept()

        # Render
        self.renderWindow.Render()
        self.renderWindow.PopState()
        self.__m_vtkFboItem.window().resetOpenGLState()

    def openGLInitState(self):
        self.renderWindow.OpenGLInitState()
        self.renderWindow.MakeCurrent()
        self.gl.initializeOpenGLFunctions()

    def createFramebufferObject(self, size: QSize) -> QOpenGLFramebufferObject:
        format = QOpenGLFramebufferObjectFormat()
        format.setAttachment(QOpenGLFramebufferObject.Depth)
        framebufferObject = QOpenGLFramebufferObject(size, format)
        framebufferObject.release()
        return framebufferObject

    def addActors(self, actors):
        for actor in actors:
            self.renderer.AddActor(actor)

    def resetCamera(self):
        # * Seting the clipping range here messes with the opacity of the actors prior to moving the camera
        m_camPositionX = -10
        m_camPositionY = -20
        m_camPositionZ = 10
        self.renderer.GetActiveCamera().SetPosition(m_camPositionX,
                                                    m_camPositionY,
                                                    m_camPositionZ)
        self.renderer.GetActiveCamera().SetFocalPoint(0.0, 0.0, 0.0)
        self.renderer.GetActiveCamera().SetViewUp(0.0, 0.0, 1.0)
        self.renderer.ResetCameraClippingRange()

    def getCamera(self):
        return self.renderer.GetActiveCamera()

    def setFocalPoint(self, point):
        self.renderer.GetActiveCamera().SetFocalPoint(*point)
        self.renderer.GetActiveCamera().SetViewUp(0.0, 0.0, 1.0)
        self.renderer.ResetCameraClippingRange()
class QmlVTKOpenGLRenderWindowInteractor(QQuickFramebufferObject.Renderer):
    def __init__(self):
        super(QmlVTKOpenGLRenderWindowInteractor, self).__init__()

        self._glFunc = QOpenGLFunctions()

        self._RenderWindow = vtk.vtkGenericOpenGLRenderWindow()
        self._Iren = vtk.vtkGenericRenderWindowInteractor()
        self._ren = vtk.vtkRenderer()
        self._RenderWindow.AddRenderer(self._ren)
        self._Iren.SetRenderWindow(self._RenderWindow)
        self._RenderWindow.OpenGLInitContext()

    def createFramebufferObject(self, size: QSize) -> QOpenGLFramebufferObject:
        print("createFramebufferobj")
        gl_format = QOpenGLFramebufferObjectFormat()
        gl_format.setAttachment(QOpenGLFramebufferObject.Depth)
        frame_buffer_object = QOpenGLFramebufferObject(size, gl_format)
        self.__fbo = frame_buffer_object
        return self.__fbo

    def synchronize(self, item: QQuickFramebufferObject):
        print("synchronize")
        pass

    def render(self):
        self.openGLInitState()

        # cylinderActor = self.__get_polydata_actor()
        # self._ren.AddActor(cylinderActor)
        # self._ren.SetBackground(0.1, 0.2, 0.4)
        ironPortVolume = self.__get_volumedata_actor()
        self._ren.AddVolume(ironPortVolume)
        self._ren.SetBackground(1, 1, 1)
        self._RenderWindow.SetSize(150, 150)

        self._Iren.Initialize()
        self._ren.ResetCamera()
        self._ren.GetActiveCamera().Zoom(1.5)
        self._RenderWindow.Render()
        print("Start rendering")
        self._Iren.Start()

    def __get_polydata_actor(self):
        cylinder = vtk.vtkCylinderSource()
        cylinder.SetResolution(8)
        cylinderMapper = vtk.vtkPolyDataMapper()
        cylinderMapper.SetInputConnection(cylinder.GetOutputPort())
        cylinderActor = vtk.vtkActor()
        cylinderActor.SetMapper(cylinderMapper)
        cylinderActor.GetProperty().SetColor(tomato)
        cylinderActor.RotateX(30.0)
        cylinderActor.RotateY(-45.0)
        return cylinderActor

    def __get_volumedata_actor(self):
        # Create the reader for the data
        reader = vtk.vtkStructuredPointsReader()
        file_path = os.path.join(const.RC_FILE_DIR, "ironProt.vtk")
        reader.SetFileName(file_path)

        # Create transfer mapping scalar value to opacity
        opacityTransferFunction = vtk.vtkPiecewiseFunction()
        opacityTransferFunction.AddPoint(20, 0.0)
        opacityTransferFunction.AddPoint(255, 0.2)

        # Create transfer mapping scalar value to color
        colorTransferFunction = vtk.vtkColorTransferFunction()
        colorTransferFunction.AddRGBPoint(0.0, 0.0, 0.0, 0.0)
        colorTransferFunction.AddRGBPoint(64.0, 1.0, 0.0, 0.0)
        colorTransferFunction.AddRGBPoint(128.0, 0.0, 0.0, 1.0)
        colorTransferFunction.AddRGBPoint(192.0, 0.0, 1.0, 0.0)
        colorTransferFunction.AddRGBPoint(255.0, 0.0, 0.2, 0.0)

        # The property describes how the data will look
        volumeProperty = vtk.vtkVolumeProperty()
        volumeProperty.SetColor(colorTransferFunction)
        volumeProperty.SetScalarOpacity(opacityTransferFunction)
        volumeProperty.ShadeOn()
        volumeProperty.SetInterpolationTypeToLinear()

        # The mapper / ray cast function know how to render the data
        volumeMapper = vtk.vtkGPUVolumeRayCastMapper()
        # volumeMapper = vtk.vtkFixedPointVolumeRayCastMapper()
        volumeMapper.SetBlendModeToComposite()
        volumeMapper.SetInputConnection(reader.GetOutputPort())

        # The volume holds the mapper and the property and
        # can be used to position/orient the volume
        volume = vtk.vtkVolume()
        volume.SetMapper(volumeMapper)
        volume.SetProperty(volumeProperty)
        return volume

    def openGLInitState(self):
        self._RenderWindow.OpenGLInitState()
        self._RenderWindow.MakeCurrent()
        self._glFunc.initializeOpenGLFunctions()
        self._glFunc.glUseProgram(0)
class RendererHelper(QObject):
    def initilize(self):
        self._glFunc = QOpenGLFunctions()  # used in all OpenGL systems
        self._renderWindow = vtk.vtkGenericOpenGLRenderWindow(
        )  # Can not Resize
        # self._renderWindow = vtk.vtkExternalOpenGLRenderWindow()  # Recommend; vtk-8.1.2-py3-none-any.whl
        self._renderer: vtk.vtkRenderer = vtk.vtkRenderer()
        self._renderWindow.AddRenderer(self._renderer)

        # * Interactor
        self._rwInteractor = vtk.vtkGenericRenderWindowInteractor()
        self._rwInteractor.EnableRenderOff()
        self._rwInteractor.SetRenderWindow(self._renderWindow)

        # * Initialize the OpenGL context for the renderer
        self._renderWindow.OpenGLInitContext()

        # * Interactor Style
        style = vtk.vtkInteractorStyleTrackballCamera()
        style.SetDefaultRenderer(self._renderer)
        style.SetMotionFactor(10.0)
        self._rwInteractor.SetInteractorStyle(style)

        self.__m_mouseLeftButton: QMouseEvent = None
        self.__m_mouseEvent: QMouseEvent = None
        self.__m_moveEvent: QMouseEvent = None
        self.__m_wheelEvent: QWheelEvent = None
        self.__fboItem: "QmlVTKRenderWindowInteractor" = None
        self.__firstRender = True
        self.jointPose = np.array([0, 0, 0, 0, 0, 0])
        self._axis = [[0, 0, 1], [0, 1, 0], [0, 1, 0], [0, 1, 0], [0, 0, 1],
                      [0, 1, 0]]
        self.__jointPoseChanged = False

    def __init__(self):
        #        qDebug("Creating FbItemRenderer")
        super().__init__()
        self.initilize()

    def synchronize(self, item: QQuickFramebufferObject):
        #        qDebug("Synchronizing")
        if not self.__fboItem:
            self.__fboItem = item
        rendererSize = self._renderWindow.GetSize()
        if self.__fboItem.width() != rendererSize[0] or self.__fboItem.height(
        ) != rendererSize[1]:
            self._renderWindow.SetSize(int(self.__fboItem.width()),
                                       int(self.__fboItem.height()))

        #* Copy mouse events
        # print(self.__fboItem.getLastMouseButton().isAccepted())
        if not self.__fboItem.getLastMouseButton().isAccepted():
            self.__m_mouseEvent = self.__fboItem.getLastMouseButton()

        if not self.__fboItem.getLastMoveEvent().isAccepted():
            self.__m_moveEvent = self.__fboItem.getLastMoveEvent()

        if self.__fboItem.getLastWheelEvent(
        ) and not self.__fboItem.getLastWheelEvent().isAccepted():
            self.__m_wheelEvent = self.__fboItem.getLastWheelEvent()

    def createFramebufferObject(self, size: QSize) -> QOpenGLFramebufferObject:
        #        qDebug("Creating FrameBufferObject")
        format = QOpenGLFramebufferObjectFormat()
        format.setAttachment(
            QOpenGLFramebufferObject.Depth
        )  # or QOpenGLFramebufferObject.CombinedDepthStencil
        self.__openGLFbo = QOpenGLFramebufferObject(size, format)
        # self.__openGLFbo.release()
        return self.__openGLFbo

    def openGLInitState(self):
        self._renderWindow.OpenGLInitState()
        self._renderWindow.MakeCurrent()
        self._glFunc.initializeOpenGLFunctions()
        # self._glFunc.glUseProgram(0)

    def update_robot_state(self, pose):
        if self.__firstRender:
            return
#        self.deltaJoint = np.array(pose) - self.jointPose
#        print(np.round(self.deltaJoint,2))
        self.jointPose = np.array(pose)
        self.__jointPoseChanged = True

    def render(self):
        self._renderWindow.PushState()
        self.openGLInitState()
        self._renderWindow.Start()

        # the first time to Render, add all model. after that, use self.update
        if self.__firstRender:
            # self.renderWindow.SetOffScreenRendering(True)
            self.sceneur = URVtk()
            # time.sleep(0.1)
            # print(sceneur.ur_assembly)
            self._renderer.AddActor(self.sceneur.ur_assembly[0])
            self._renderer.AddActor(self.sceneur.groundSence)
            self._renderer.AddActor(self.sceneur.axesSence)
            self.resetCamera()
            self.__firstRender = False
        else:
            if self.__jointPoseChanged:
                self.sceneur.ur_assembly[1].SetOrientation(
                    0, 0, self.jointPose[0])
                self.sceneur.ur_assembly[2].SetOrientation(
                    0, 90 + self.jointPose[1], 0)
                self.sceneur.ur_assembly[3].SetOrientation(
                    0, self.jointPose[2], 0)
                self.sceneur.ur_assembly[4].SetOrientation(
                    0, 90 + self.jointPose[3], 0)
                self.sceneur.ur_assembly[5].SetOrientation(
                    0, 0, self.jointPose[4])
                self.sceneur.ur_assembly[6].SetOrientation(
                    0, self.jointPose[5], 0)
                self.__jointPoseChanged = False

        #* Process camera related commands
        if self.__m_mouseEvent and not self.__m_mouseEvent.isAccepted():
            self._rwInteractor.SetEventInformationFlipY(
                self.__m_mouseEvent.x(), self.__m_mouseEvent.y(), 1 if
                (self.__m_mouseEvent.modifiers() & Qt.ControlModifier) > 0 else
                0, 1 if
                (self.__m_mouseEvent.modifiers() & Qt.ShiftModifier) > 0 else
                0, '0', 1 if self.__m_mouseEvent.type()
                == QEvent.MouseButtonDblClick else 0, None)
            if self.__m_mouseEvent.type() == QEvent.MouseButtonPress:
                if self.__m_mouseEvent.button() == Qt.LeftButton:
                    self._rwInteractor.LeftButtonPressEvent()
                elif self.__m_mouseEvent.button() == Qt.RightButton:
                    self._rwInteractor.RightButtonPressEvent()
                elif self.__m_mouseEvent.button() == Qt.MidButton:
                    self._rwInteractor.MiddleButtonPressEvent()
                # self._rwInteractor.InvokeEvent(vtk.vtkCommand.LeftButtonPressEvent)
            elif self.__m_mouseEvent.type() == QEvent.MouseButtonRelease:
                if self.__m_mouseEvent.button() == Qt.LeftButton:
                    self._rwInteractor.LeftButtonReleaseEvent()
                elif self.__m_mouseEvent.button() == Qt.RightButton:
                    self._rwInteractor.RightButtonReleaseEvent()
                elif self.__m_mouseEvent.button() == Qt.MidButton:
                    self._rwInteractor.MiddleButtonReleaseEvent()
                # self._rwInteractor.InvokeEvent(vtk.vtkCommand.LeftButtonReleaseEvent)
            self.__m_mouseEvent.accept()

        #* Process move event
        if self.__m_moveEvent and not self.__m_moveEvent.isAccepted():
            if self.__m_moveEvent.type(
            ) == QEvent.MouseMove and self.__m_moveEvent.buttons() & (
                    Qt.RightButton | Qt.LeftButton | Qt.MidButton):
                self._rwInteractor.SetEventInformationFlipY(
                    self.__m_moveEvent.x(), self.__m_moveEvent.y(), 1 if
                    (self.__m_moveEvent.modifiers() & Qt.ControlModifier) > 0
                    else 0, 1 if
                    (self.__m_moveEvent.modifiers() & Qt.ShiftModifier) > 0
                    else 0, '0', 1 if self.__m_moveEvent.type()
                    == QEvent.MouseButtonDblClick else 0)
                self._rwInteractor.InvokeEvent(vtk.vtkCommand.MouseMoveEvent)

            self.__m_moveEvent.accept()

        #* Process wheel event
        if self.__m_wheelEvent and not self.__m_wheelEvent.isAccepted():
            self._rwInteractor.SetEventInformationFlipY(
                self.__m_wheelEvent.x(), self.__m_wheelEvent.y(), 1 if
                (self.__m_wheelEvent.modifiers() & Qt.ControlModifier) > 0 else
                0, 1 if
                (self.__m_wheelEvent.modifiers() & Qt.ShiftModifier) > 0 else
                0, '0', 1 if self.__m_wheelEvent.type()
                == QEvent.MouseButtonDblClick else 0)
            if self.__m_wheelEvent.delta() > 0:
                self._rwInteractor.InvokeEvent(
                    vtk.vtkCommand.MouseWheelForwardEvent)
            elif self.__m_wheelEvent.delta() < 0:
                self._rwInteractor.InvokeEvent(
                    vtk.vtkCommand.MouseWheelBackwardEvent)

            self.__m_wheelEvent.accept()

        # Render
        self._renderWindow.Render()
        self._renderWindow.PopState()
        self.__fboItem.window().resetOpenGLState()

    def addModel(self, fileName):
        reader = vtk.vtkSTLReader()
        url = QUrl(fileName)
        reader.SetFileName(url.path())
        reader.Update()

        transform = vtk.vtkTransform()
        transform.Scale((.5, .5, .5))

        transformFilter = vtk.vtkTransformPolyDataFilter()
        transformFilter.SetInputConnection(reader.GetOutputPort())
        transformFilter.SetTransform(transform)
        transformFilter.Update()

        mapper = vtk.vtkPolyDataMapper()
        mapper.SetInputConnection(transformFilter.GetOutputPort())

        actor = vtk.vtkActor()
        actor.SetMapper(mapper)
        self.renderer.AddActor(actor)

        print(f"Added...{url.path()}")

    def resetCamera(self):
        self._renderer.SetBackground(1.0, 1.0, 1.0)
        self._renderer.SetBackground2(0.529, 0.8078, 0.92157)
        # self._renderer.SetBackground2(0.67, 0.67, 0.67)
        self._renderer.GradientBackgroundOn()
        #  设置相机参数
        # Seting the clipping range here messes with the opacity of the actors prior to moving the camera
        # self._ren.GetActiveCamera().Yaw(90)  #鼠标向左转动,顺时针
        # self._ren.GetActiveCamera().Pitch(25)  #鼠标向上转动,顺时针
        # self._ren.GetActiveCamera().Roll(-90) #垂直于屏幕的方向
        # self._ren.ResetCamera()
        m_camPositionX = -2
        m_camPositionY = -2
        m_camPositionZ = 2
        self._renderer.GetActiveCamera().SetPosition(m_camPositionX,
                                                     m_camPositionY,
                                                     m_camPositionZ)
        self._renderer.GetActiveCamera().SetFocalPoint(0.2, 0.2, 0.0)
        self._renderer.GetActiveCamera().SetViewUp(0.0, 0.0, 1.0)
        self._renderer.ResetCameraClippingRange()
    def __init__(self):
        qDebug('RendererHelper::__init__()')
        super().__init__()
        self.__m_vtkFboItem = None
        self.gl = QOpenGLFunctions()
        self.__m_processingEngine: ProcessingEngine = None

        self.__m_selectedModel: Model = None
        self.__m_selectedActor: vtk.vtkActor = None
        self.__m_isModelSelected: bool = False

        self.__m_selectedModelPositionX: float = 0.0
        self.__m_selectedModelPositionY: float = 0.0

        self.__m_mouseLeftButton: QMouseEvent = None
        self.__m_mouseEvent: QMouseEvent = None
        self.__m_moveEvent: QMouseEvent = None
        self.__m_wheelEvent: QWheelEvent = None

        self.__m_platformModel: vtk.vtkCubeSource = None
        self.__m_platformGrid: vtk.vtkPolyData = None
        self.__m_platformModelActor: vtk.vtkActor = None
        self.__m_platformGridActor: vtk.vtkActor = None

        self.__m_platformWidth: float = 200.0
        self.__m_platformDepth: float = 200.0
        # self.__m_platformHeight:float = 200.0
        self.__m_platformThickness: float = 2.0
        self.__m_gridBottomHeight: float = 0.15
        self.__m_gridSize: np.uint16 = 10

        # self.__m_camPositionX:float = 0.0
        # self.__m_camPositionY:float = 0.0
        # self.__m_camPositionZ:float = 0.0

        self.__m_clickPositionZ: float = 0.0

        self.__m_firstRender: bool = True

        self.__m_modelsRepresentationOption: int = 0
        self.__m_modelsOpacity: float = 1.0
        self.__m_modelsGouraudInterpolation: bool = False

        #* Renderer
        #* https://vtk.org/doc/nightly/html/classQVTKOpenGLNativeWidget.html#details
        # QSurfaceFormat.setDefaultFormat(QVTKOpenGLNativeWidget.defaultFormat()) # from vtk 8.2.0
        # QSurfaceFormat.setDefaultFormat(fmt)
        self.__m_vtkRenderWindow: vtk.vtkGenericOpenGLRenderWindow = vtk.vtkGenericOpenGLRenderWindow(
        )
        self.__m_renderer: vtk.vtkRenderer = vtk.vtkRenderer()
        self.__m_vtkRenderWindow.AddRenderer(self.__m_renderer)

        #* Interactor
        self.__m_vtkRenderWindowInteractor: vtk.vtkGenericRenderWindowInteractor = vtk.vtkGenericRenderWindowInteractor(
        )
        self.__m_vtkRenderWindowInteractor.EnableRenderOff()
        self.__m_vtkRenderWindow.SetInteractor(
            self.__m_vtkRenderWindowInteractor)

        #* Initialize the OpenGL context for the renderer
        self.__m_vtkRenderWindow.OpenGLInitContext()

        #* Interactor Style
        style = vtk.vtkInteractorStyleTrackballCamera()
        style.SetDefaultRenderer(self.__m_renderer)
        style.SetMotionFactor(10.0)
        self.__m_vtkRenderWindowInteractor.SetInteractorStyle(style)

        #* Picker
        self.__m_picker: vtk.vtkCellPicker = vtk.vtkCellPicker()
        self.__m_picker.SetTolerance(0.0)
class RendererHelper(QObject):
    isModelSelectedChanged = Signal(bool)
    selectedModelPositionXChanged = Signal(float)
    selectedModelPositionYChanged = Signal(float)

    def __init__(self):
        qDebug('RendererHelper::__init__()')
        super().__init__()
        self.__m_vtkFboItem = None
        self.gl = QOpenGLFunctions()
        self.__m_processingEngine: ProcessingEngine = None

        self.__m_selectedModel: Model = None
        self.__m_selectedActor: vtk.vtkActor = None
        self.__m_isModelSelected: bool = False

        self.__m_selectedModelPositionX: float = 0.0
        self.__m_selectedModelPositionY: float = 0.0

        self.__m_mouseLeftButton: QMouseEvent = None
        self.__m_mouseEvent: QMouseEvent = None
        self.__m_moveEvent: QMouseEvent = None
        self.__m_wheelEvent: QWheelEvent = None

        self.__m_platformModel: vtk.vtkCubeSource = None
        self.__m_platformGrid: vtk.vtkPolyData = None
        self.__m_platformModelActor: vtk.vtkActor = None
        self.__m_platformGridActor: vtk.vtkActor = None

        self.__m_platformWidth: float = 200.0
        self.__m_platformDepth: float = 200.0
        # self.__m_platformHeight:float = 200.0
        self.__m_platformThickness: float = 2.0
        self.__m_gridBottomHeight: float = 0.15
        self.__m_gridSize: np.uint16 = 10

        # self.__m_camPositionX:float = 0.0
        # self.__m_camPositionY:float = 0.0
        # self.__m_camPositionZ:float = 0.0

        self.__m_clickPositionZ: float = 0.0

        self.__m_firstRender: bool = True

        self.__m_modelsRepresentationOption: int = 0
        self.__m_modelsOpacity: float = 1.0
        self.__m_modelsGouraudInterpolation: bool = False

        #* Renderer
        #* https://vtk.org/doc/nightly/html/classQVTKOpenGLNativeWidget.html#details
        # QSurfaceFormat.setDefaultFormat(QVTKOpenGLNativeWidget.defaultFormat()) # from vtk 8.2.0
        # QSurfaceFormat.setDefaultFormat(fmt)
        self.__m_vtkRenderWindow: vtk.vtkGenericOpenGLRenderWindow = vtk.vtkGenericOpenGLRenderWindow(
        )
        self.__m_renderer: vtk.vtkRenderer = vtk.vtkRenderer()
        self.__m_vtkRenderWindow.AddRenderer(self.__m_renderer)

        #* Interactor
        self.__m_vtkRenderWindowInteractor: vtk.vtkGenericRenderWindowInteractor = vtk.vtkGenericRenderWindowInteractor(
        )
        self.__m_vtkRenderWindowInteractor.EnableRenderOff()
        self.__m_vtkRenderWindow.SetInteractor(
            self.__m_vtkRenderWindowInteractor)

        #* Initialize the OpenGL context for the renderer
        self.__m_vtkRenderWindow.OpenGLInitContext()

        #* Interactor Style
        style = vtk.vtkInteractorStyleTrackballCamera()
        style.SetDefaultRenderer(self.__m_renderer)
        style.SetMotionFactor(10.0)
        self.__m_vtkRenderWindowInteractor.SetInteractorStyle(style)

        #* Picker
        self.__m_picker: vtk.vtkCellPicker = vtk.vtkCellPicker()
        self.__m_picker.SetTolerance(0.0)

    def setVtkFboItem(self, vtkFboItem):
        qDebug('RendererHelper::setVtkFboItem()')
        self.__m_vtkFboItem = vtkFboItem

    def setProcessingEngine(self, processingEngine: ProcessingEngine):
        qDebug('RendererHelper::setProcessingEngine()')
        self.__m_processingEngine = processingEngine

    def synchronize(self, item: QQuickFramebufferObject):
        # qDebug('RendererHelper::synchronize()')
        #* the first synchronize
        # if not self.__m_vtkFboItem:
        #     from QVTKFramebufferObjectItem import QVTKFramebufferObjectItem
        #     self.__m_vtkFboItem = (QVTKFramebufferObjectItem)(item)

        # if not self.__m_vtkFboItem.isInitialized():
        #     self.__m_vtkFboItem.setVtkRendererHelper(self)
        #     self.__m_vtkFboItem.rendererInitialized.emit()

        rendererSize = self.__m_vtkRenderWindow.GetSize()
        if self.__m_vtkFboItem.width() != rendererSize[
                0] or self.__m_vtkFboItem.height() != rendererSize[1]:
            self.__m_vtkRenderWindow.SetSize(int(self.__m_vtkFboItem.width()),
                                             int(self.__m_vtkFboItem.height()))

        #* Copy mouse events
        if not self.__m_vtkFboItem.getLastMouseLeftButton(
                clone=False).isAccepted():
            self.__m_mouseLeftButton = self.__m_vtkFboItem.getLastMouseLeftButton(
            )
            self.__m_vtkFboItem.getLastMouseLeftButton(clone=False).accept()

        if not self.__m_vtkFboItem.getLastMouseButton(
                clone=False).isAccepted():
            self.__m_mouseEvent = self.__m_vtkFboItem.getLastMouseButton()
            self.__m_vtkFboItem.getLastMouseButton(clone=False).accept()

        if not self.__m_vtkFboItem.getLastMoveEvent(clone=False).isAccepted():
            self.__m_moveEvent = self.__m_vtkFboItem.getLastMoveEvent()
            self.__m_vtkFboItem.getLastMoveEvent(clone=False).accept()

        if self.__m_vtkFboItem.getLastWheelEvent(
        ) and not self.__m_vtkFboItem.getLastWheelEvent().isAccepted():
            self.__m_wheelEvent = self.__m_vtkFboItem.getLastWheelEvent()

        #* Get extra data
        self.__m_modelsRepresentationOption = self.__m_vtkFboItem.getModelsRepresentation(
        )
        self.__m_modelsOpacity = self.__m_vtkFboItem.getModelsOpacity()
        self.__m_modelsGouraudInterpolation = self.__m_vtkFboItem.getGourauInterpolation(
        )
        setSelectedModelColor(
            QColor(self.__m_vtkFboItem.getModelColorR(),
                   self.__m_vtkFboItem.getModelColorG(),
                   self.__m_vtkFboItem.getModelColorB()))

    def render(self):
        self.__m_vtkRenderWindow.PushState()
        self.openGLInitState()
        self.__m_vtkRenderWindow.Start()

        if self.__m_firstRender:
            self.initScene()
            self.__m_firstRender = False

        #* Process camera related commands

        #* Process mouse event
        if self.__m_mouseEvent and not self.__m_mouseEvent.isAccepted():
            self.__m_vtkRenderWindowInteractor.SetEventInformationFlipY(
                self.__m_mouseEvent.x(), self.__m_mouseEvent.y(), 1 if
                (self.__m_mouseEvent.modifiers() & Qt.ControlModifier) > 0 else
                0, 1 if
                (self.__m_mouseEvent.modifiers() & Qt.ShiftModifier) > 0 else
                0, '0', 1 if self.__m_mouseEvent.type()
                == QEvent.MouseButtonDblClick else 0)

            if self.__m_mouseEvent.type() == QEvent.MouseButtonPress:
                self.__m_vtkRenderWindowInteractor.InvokeEvent(
                    vtk.vtkCommand.LeftButtonPressEvent)
            elif self.__m_mouseEvent.type() == QEvent.MouseButtonRelease:
                self.__m_vtkRenderWindowInteractor.InvokeEvent(
                    vtk.vtkCommand.LeftButtonReleaseEvent)

            self.__m_mouseEvent.accept()

        #* Process move event
        if self.__m_moveEvent and not self.__m_moveEvent.isAccepted():
            if self.__m_moveEvent.type(
            ) == QEvent.MouseMove and self.__m_moveEvent.buttons():
                self.__m_vtkRenderWindowInteractor.SetEventInformationFlipY(
                    self.__m_moveEvent.x(), self.__m_moveEvent.y(), 1 if
                    (self.__m_moveEvent.modifiers() & Qt.ControlModifier) > 0
                    else 0, 1 if
                    (self.__m_moveEvent.modifiers() & Qt.ShiftModifier) > 0
                    else 0, '0', 1 if self.__m_moveEvent.type()
                    == QEvent.MouseButtonDblClick else 0)

                self.__m_vtkRenderWindowInteractor.InvokeEvent(
                    vtk.vtkCommand.MouseMoveEvent)

            self.__m_moveEvent.accept()

        #* Process wheel event
        if self.__m_wheelEvent and not self.__m_wheelEvent.isAccepted():
            self.__m_vtkRenderWindowInteractor.SetEventInformationFlipY(
                self.__m_wheelEvent.x(), self.__m_wheelEvent.y(), 1 if
                (self.__m_wheelEvent.modifiers() & Qt.ControlModifier) > 0 else
                0, 1 if
                (self.__m_wheelEvent.modifiers() & Qt.ShiftModifier) > 0 else
                0, '0', 1 if self.__m_wheelEvent.type()
                == QEvent.MouseButtonDblClick else 0)

            if self.__m_wheelEvent.delta() > 0:
                self.__m_vtkRenderWindowInteractor.InvokeEvent(
                    vtk.vtkCommand.MouseWheelForwardEvent)
            elif self.__m_wheelEvent.delta() < 0:
                self.__m_vtkRenderWindowInteractor.InvokeEvent(
                    vtk.vtkCommand.MouseWheelBackwardEvent)

            self.__m_wheelEvent.accept()

        #* Process model related commands

        #* Select model
        if self.__m_mouseLeftButton and not self.__m_mouseLeftButton.isAccepted(
        ):
            self.__selectModel(self.__m_mouseLeftButton.x(),
                               self.__m_mouseLeftButton.y())
            self.__m_mouseLeftButton.accept()

        #* Model transformations

        command = None  # CommandModel
        while not self.__m_vtkFboItem.isCommandsQueueEmpty():
            self.__m_vtkFboItem.lockCommandsQueueMutex()

            command = self.__m_vtkFboItem.getCommandsQueueFront()
            if not command.isReady():
                self.__m_vtkFboItem.unlockCommandsQueueMutex()
                break
            self.__m_vtkFboItem.commandsQueuePop()

            self.__m_vtkFboItem.unlockCommandsQueueMutex()

            command.execute()

        #* Reset the view-up vector. self improves the interaction of the camera with the plate.
        self.__m_renderer.GetActiveCamera().SetViewUp(0.0, 0.0, 1.0)

        #* Extra actions
        self.__m_processingEngine.setModelsRepresentation(
            self.__m_modelsRepresentationOption)
        self.__m_processingEngine.setModelsOpacity(self.__m_modelsOpacity)
        self.__m_processingEngine.setModelsGouraudInterpolation(
            self.__m_modelsGouraudInterpolation)
        self.__m_processingEngine.updateModelsColor()

        #* Render
        self.__m_vtkRenderWindow.Render()
        self.__m_vtkRenderWindow.PopState()

        self.__m_vtkFboItem.window().resetOpenGLState()

    def openGLInitState(self):
        self.__m_vtkRenderWindow.OpenGLInitState()
        self.__m_vtkRenderWindow.MakeCurrent()
        self.gl.initializeOpenGLFunctions()
        self.gl.glUseProgram(0)

    def createFramebufferObject(self, size: QSize) -> QOpenGLFramebufferObject:
        qDebug('RendererHelper::createFramebufferObject()')
        macSize = QSize(size.width() / 2, size.height() / 2)

        format = QOpenGLFramebufferObjectFormat()
        format.setAttachment(QOpenGLFramebufferObject.Depth)

        # ifdef Q_OS_MAC
        #     std::unique_ptr<QOpenGLFramebufferObject> framebufferObject(new QOpenGLFramebufferObject(macSize, format))
        # else
        framebufferObject = QOpenGLFramebufferObject(size, format)
        # endif
        self.__m_vtkRenderWindow.SetBackLeftBuffer(GL.GL_COLOR_ATTACHMENT0)
        self.__m_vtkRenderWindow.SetFrontLeftBuffer(GL.GL_COLOR_ATTACHMENT0)
        self.__m_vtkRenderWindow.SetBackBuffer(GL.GL_COLOR_ATTACHMENT0)
        self.__m_vtkRenderWindow.SetFrontBuffer(GL.GL_COLOR_ATTACHMENT0)
        self.__m_vtkRenderWindow.SetSize(framebufferObject.size().width(),
                                         framebufferObject.size().height())
        self.__m_vtkRenderWindow.SetOffScreenRendering(True)
        self.__m_vtkRenderWindow.Modified()
        framebufferObject.release()
        return framebufferObject

    def initScene(self):
        qDebug('RendererHelper::initScene()')

        self.__m_vtkRenderWindow.SetOffScreenRendering(True)

        #* Top background color
        r2 = 245.0 / 255.0
        g2 = 245.0 / 255.0
        b2 = 245.0 / 255.0

        #* Bottom background color
        r1 = 170.0 / 255.0
        g1 = 170.0 / 255.0
        b1 = 170.0 / 255.0

        self.__m_renderer.SetBackground(r2, g2, b2)
        self.__m_renderer.SetBackground2(r1, g1, b1)
        self.__m_renderer.GradientBackgroundOn()

        # #* Axes
        axes = vtk.vtkAxesActor()
        axes_length = 20.0
        axes_label_font_size = np.int16(20)
        axes.SetTotalLength(axes_length, axes_length, axes_length)
        axes.SetCylinderRadius(0.02)
        axes.SetShaftTypeToCylinder()
        axes.GetXAxisCaptionActor2D().GetTextActor().SetTextScaleModeToNone()
        axes.GetYAxisCaptionActor2D().GetTextActor().SetTextScaleModeToNone()
        axes.GetZAxisCaptionActor2D().GetTextActor().SetTextScaleModeToNone()
        axes.GetXAxisCaptionActor2D().GetCaptionTextProperty().SetFontSize(
            axes_label_font_size)
        axes.GetYAxisCaptionActor2D().GetCaptionTextProperty().SetFontSize(
            axes_label_font_size)
        axes.GetZAxisCaptionActor2D().GetCaptionTextProperty().SetFontSize(
            axes_label_font_size)
        self.__m_renderer.AddActor(axes)

        # #* Platform
        self.__generatePlatform()

        #* Initial camera position
        self.resetCamera()

    def __generatePlatform(self):
        qDebug('RendererHelper::__generatePlatform()')

        #* Platform Model
        platformModelMapper = vtk.vtkPolyDataMapper()

        self.__m_platformModel = vtk.vtkCubeSource()
        platformModelMapper.SetInputConnection(
            self.__m_platformModel.GetOutputPort())

        self.__m_platformModelActor = vtk.vtkActor()
        self.__m_platformModelActor.SetMapper(platformModelMapper)
        self.__m_platformModelActor.GetProperty().SetColor(1, 1, 1)
        self.__m_platformModelActor.GetProperty().LightingOn()
        self.__m_platformModelActor.GetProperty().SetOpacity(1)
        self.__m_platformModelActor.GetProperty().SetAmbient(0.45)
        self.__m_platformModelActor.GetProperty().SetDiffuse(0.4)

        self.__m_platformModelActor.PickableOff()
        self.__m_renderer.AddActor(self.__m_platformModelActor)

        #* Platform Grid
        self.__m_platformGrid = vtk.vtkPolyData()

        platformGridMapper = vtk.vtkPolyDataMapper()
        platformGridMapper.SetInputData(self.__m_platformGrid)

        self.__m_platformGridActor = vtk.vtkActor()
        self.__m_platformGridActor.SetMapper(platformGridMapper)
        self.__m_platformGridActor.GetProperty().LightingOff()
        self.__m_platformGridActor.GetProperty().SetColor(0.45, 0.45, 0.45)
        self.__m_platformGridActor.GetProperty().SetOpacity(1)
        self.__m_platformGridActor.PickableOff()
        self.__m_renderer.AddActor(self.__m_platformGridActor)

        self.__updatePlatform()

    def __updatePlatform(self):
        qDebug('RendererHelper::__updatePlatform()')

        #* Platform Model

        if self.__m_platformModel:
            self.__m_platformModel.SetXLength(self.__m_platformWidth)
            self.__m_platformModel.SetYLength(self.__m_platformDepth)
            self.__m_platformModel.SetZLength(self.__m_platformThickness)
            self.__m_platformModel.SetCenter(0.0, 0.0,
                                             -self.__m_platformThickness / 2)

        #* Platform Grid
        gridPoints = vtk.vtkPoints()
        gridCells = vtk.vtkCellArray()

        i = -self.__m_platformWidth / 2
        while i <= self.__m_platformWidth / 2:
            self.__createLine(i, -self.__m_platformDepth / 2,
                              self.__m_gridBottomHeight, i,
                              self.__m_platformDepth / 2,
                              self.__m_gridBottomHeight, gridPoints, gridCells)
            i += self.__m_gridSize

        i = -self.__m_platformDepth / 2
        while i <= self.__m_platformDepth / 2:
            self.__createLine(-self.__m_platformWidth / 2, i,
                              self.__m_gridBottomHeight,
                              self.__m_platformWidth / 2, i,
                              self.__m_gridBottomHeight, gridPoints, gridCells)
            i += self.__m_gridSize

        self.__m_platformGrid.SetPoints(gridPoints)
        self.__m_platformGrid.SetLines(gridCells)

    def __createLine(self, x1: float, y1: float, z1: float, x2: float,
                     y2: float, z2: float, points: vtk.vtkPoints,
                     cells: vtk.vtkCellArray):
        line = vtk.vtkPolyLine()
        line.GetPointIds().SetNumberOfIds(2)

        id_1 = points.InsertNextPoint(x1, y1, z1)  # vtkIdType
        id_2 = points.InsertNextPoint(x2, y2, z2)  # vtkIdType

        line.GetPointIds().SetId(0, id_1)
        line.GetPointIds().SetId(1, id_2)

        cells.InsertNextCell(line)

    def addModelActor(self, model: Model):
        self.__m_renderer.AddActor(model.getModelActor())
        # qDebug(f'RendererHelper::addModelActor(): Model added {model}')

    def __selectModel(self, x: np.int16, y: np.int16):
        qDebug('RendererHelper::__selectModel()')

        #*  the y-axis flip for the pickin:
        self.__m_picker.Pick(x,
                             self.__m_renderer.GetSize()[1] - y, 0,
                             self.__m_renderer)

        #* Get pick position
        # clickPosition = [0.0, 0.0, 0.0]
        # self.__m_picker.GetPickPosition(clickPosition)
        clickPosition = self.__m_picker.GetPickPosition()
        self.__m_clickPositionZ = clickPosition[2]

        if self.__m_selectedActor == self.__m_picker.GetActor():
            if self.__m_selectedModel:
                self.__m_selectedModel.setMouseDeltaXY(
                    clickPosition[0] - self.__m_selectedModel.getPositionX(),
                    clickPosition[1] - self.__m_selectedModel.getPositionY())
            return

        #* Disconnect signals
        if self.__m_selectedModel:
            self.__clearSelectedModel()

        #* Pick the new actor
        self.__m_selectedActor = self.__m_picker.GetActor()

        self.__m_selectedModel = self.__getSelectedModelNoLock()

        if self.__m_selectedActor:
            # qDebug(f'RendererHelper::__selectModel(): picked actor {self.__m_selectedActor}')

            self.__m_selectedModel.setSelected(True)

            #* Connect signals
            self.__m_selectedModel.positionXChanged.connect(
                self.setSelectedModelPositionX)
            self.__m_selectedModel.positionYChanged.connect(
                self.setSelectedModelPositionY)

            self.setSelectedModelPositionX(
                self.__m_selectedModel.getPositionX())
            self.setSelectedModelPositionY(
                self.__m_selectedModel.getPositionY())

            self.__setIsModelSelected(True)

            #* Set mouse click delta from center position
            self.__m_selectedModel.setMouseDeltaXY(
                clickPosition[0] - self.__m_selectedModel.getPositionX(),
                clickPosition[1] - self.__m_selectedModel.getPositionY())
        else:
            self.__setIsModelSelected(False)

        qDebug('RendererHelper::__selectModel() end')

    def __clearSelectedModel(self):
        self.__m_selectedModel.setSelected(False)

        self.__m_selectedModel.positionXChanged.disconnect(
            self.setSelectedModelPositionX)
        self.__m_selectedModel.positionYChanged.disconnect(
            self.setSelectedModelPositionY)

        self.__m_selectedModel = None
        self.__m_selectedActor = None

    def __setIsModelSelected(self, isModelSelected: bool):
        if self.__m_isModelSelected != isModelSelected:
            qDebug(
                f'RendererHelper::__setIsModelSelected(): {isModelSelected}')
            self.__m_isModelSelected = isModelSelected
            self.isModelSelectedChanged.emit(isModelSelected)

    def isModelSelected(self) -> bool:
        return self.__m_isModelSelected

    def getSelectedModel(self) -> Model:
        selectedModel = self.__getSelectedModelNoLock()
        return selectedModel

    def __getSelectedModelNoLock(self) -> Model:
        return self.__m_processingEngine.getModelFromActor(
            self.__m_selectedActor)

    def setSelectedModelPositionX(self, positionX: float):
        if self.__m_selectedModelPositionX != positionX:
            self.__m_selectedModelPositionX = positionX
            self.selectedModelPositionXChanged.emit(positionX)

    def setSelectedModelPositionY(self, positionY: float):
        if self.__m_selectedModelPositionY != positionY:
            self.__m_selectedModelPositionY = positionY
            self.selectedModelPositionYChanged.emit(positionY)

    def getSelectedModelPositionX(self) -> float:
        return self.__m_selectedModelPositionX

    def getSelectedModelPositionY(self) -> float:
        return self.__m_selectedModelPositionY

    def screenToWorld(self, screenX: np.int16, screenY: np.int16,
                      worldPos: list) -> bool:  # list of float
        #* Create  planes for projection plan:
        boundingPlanes = list(vtk.vtkPlane() for i in range(0, 4))

        boundingPlanes[0].SetOrigin(0.0, 1000.0, 0.0)
        boundingPlanes[0].SetNormal(0.0, -1.0, 0.0)

        boundingPlanes[1].SetOrigin(0.0, -1000.0, 0.0)
        boundingPlanes[1].SetNormal(0.0, 1.0, 0.0)

        boundingPlanes[2].SetOrigin(1000.0, 0.0, 0.0)
        boundingPlanes[2].SetNormal(-1.0, 0.0, 0.0)

        boundingPlanes[3].SetOrigin(-1000.0, 0.0, 0.0)
        boundingPlanes[3].SetNormal(1.0, 0.0, 0.0)

        #* Create projection plane parallel platform and Z coordinate from clicked position in model
        plane = vtk.vtkPlane()
        plane.SetOrigin(0.0, 0.0, self.__m_clickPositionZ)
        plane.SetNormal(0.0, 0.0, 1.0)

        #* Set projection and bounding planes to placer
        placer = vtk.vtkBoundedPlanePointPlacer()
        placer.SetObliquePlane(plane)
        placer.SetProjectionNormalToOblique()

        placer.AddBoundingPlane(boundingPlanes[0])
        placer.AddBoundingPlane(boundingPlanes[1])
        placer.AddBoundingPlane(boundingPlanes[2])
        placer.AddBoundingPlane(boundingPlanes[3])

        screenPos = list(0.0 for i in range(0, 2))  # 2 items
        worldOrient = list(0.0 for i in range(0, 9))  # 9 items

        screenPos[0] = screenX
        #*  the y-axis flip for the pickin:
        screenPos[1] = self.__m_renderer.GetSize()[1] - screenY

        withinBounds = placer.ComputeWorldPosition(self.__m_renderer,
                                                   screenPos, worldPos,
                                                   worldOrient)  # int16_t

        return withinBounds

    def resetCamera(self):
        #* Seting the clipping range here messes with the opacity of the actors prior to moving the camera
        m_camPositionX = -237.885
        m_camPositionY = -392.348
        m_camPositionZ = 369.477
        self.__m_renderer.GetActiveCamera().SetPosition(
            m_camPositionX, m_camPositionY, m_camPositionZ)
        self.__m_renderer.GetActiveCamera().SetFocalPoint(0.0, 0.0, 0.0)
        self.__m_renderer.GetActiveCamera().SetViewUp(0.0, 0.0, 1.0)
        self.__m_renderer.ResetCameraClippingRange()
Esempio n. 15
0
class FboRenderer(QObject, QQuickFramebufferObject.Renderer):

    render_signal = Signal()
    dump_ren_win = Signal()

    def __init__(self, render_window, interactor, *args, **kwargs):
        self.gl = QOpenGLFunctions()
        QQuickFramebufferObject.Renderer.__init__(self)
        QObject.__init__(self)
        self.__fbo = None

        self.__m_mouseLeftButton: QMouseEvent = None
        self.__m_mouseEvent: QMouseEvent = None
        self.__m_moveEvent: QMouseEvent = None
        self.__m_wheelEvent: QWheelEvent = None

        self.__m_firstRender: bool = True

        # self._render_window: vtk.vtkGenericOpenGLRenderWindow = vtk.vtkGenericOpenGLRenderWindow()
        self._renderer = [RendererOPENGL(parent=self, **kwargs)]
        self._renderer[0].AutomaticLightCreationOn()
        self._renderer_index = 0

        self._render_window = render_window
        self._render_window.OpenGLInitContext()
        self._interactor = interactor

        self.render_signal.connect(self._render)
        self.dump_ren_win.connect(self._dump_ren_win)
        self.__m_vtkFboItem = None
        self.__image_data = None

    @property
    def _scalar_bar_mappers(self):
        if self.__m_vtkFboItem is not None:
            return self.__m_vtkFboItem._scalar_bar_mappers

    @_scalar_bar_mappers.setter
    def _scalar_bar_mappers(self, value):
        if self.__m_vtkFboItem is not None:
            self.__m_vtkFboItem._scalar_bar_mappers = value

    @property
    def _scalar_bar_ranges(self):
        if self.__m_vtkFboItem is not None:
            return self.__m_vtkFboItem._scalar_bar_ranges

    @_scalar_bar_ranges.setter
    def _scalar_bar_ranges(self, value):
        if self.__m_vtkFboItem is not None:
            self.__m_vtkFboItem._scalar_bar_ranges = value

    @property
    def remove_actor(self):
        if self.__m_vtkFboItem is not None:
            return self.__m_vtkFboItem.remove_actor

    @property
    def _scalar_bar_slot_lookup(self):
        if self.__m_vtkFboItem is not None:
            return self.__m_vtkFboItem._scalar_bar_slot_lookup

    @_scalar_bar_slot_lookup.setter
    def _scalar_bar_slot_lookup(self, value):
        if self.__m_vtkFboItem is not None:
            self.__m_vtkFboItem._scalar_bar_slot_lookup = value

    @property
    def _scalar_bar_slots(self):
        if self.__m_vtkFboItem is not None:
            return self.__m_vtkFboItem._scalar_bar_slots

    @_scalar_bar_slots.setter
    def _scalar_bar_slots(self, value):
        if self.__m_vtkFboItem is not None:
            self.__m_vtkFboItem._scalar_bar_slots = value

    @property
    def renderers(self) -> List[Renderer]:
        return self._renderer

    @renderers.setter
    def renderers(self, value: List[Renderer]):
        self._renderer = value

    @property
    def renderer_index(self) -> int:
        return self._renderer_index

    @renderer_index.setter
    def renderer_index(self, value: int):
        self._renderer_index = value

    @property
    def renderer(self) -> Renderer:
        return self._renderer[self.renderer_index]

    def create_renderer(self, *args, **kwargs) -> Renderer:
        return RendererOPENGL(parent=self, **kwargs)

    def setVtkFboItem(self, vtkFboItem):
        self.__m_vtkFboItem = vtkFboItem

    def _render(self, *args: Any, **kwargs: Any):
        """Wrap ``BasePlotter.render``."""
        return FboRenderer.render_this_thread(self, *args, **kwargs)

    def _dump_ren_win(self, *args, **kwargs):
        return FboRenderer._dump_ren_win(self, *args, **kwargs)

    def render(self) -> None:
        """Override the ``render`` method to handle threading issues."""
        return self.render_signal.emit()

    def image(self):
        return self.dump_ren_win.emit()

    @property
    def iren(self):
        return self._interactor

    def render_this_thread(self):
        qDebug('ObjectRenderer: RENDER')
        self._render_window.PushState()
        self.openGLInitState()
        self._render_window.Start()

        # * Process camera related commands
        if self.__m_mouseEvent and not self.__m_mouseEvent.isAccepted():
            # qDebug('A')
            self._interactor.SetEventInformationFlipY(
                self.__m_mouseEvent.x(), self.__m_mouseEvent.y(), 1 if
                (self.__m_mouseEvent.modifiers() & Qt.ControlModifier) > 0 else
                0, 1 if
                (self.__m_mouseEvent.modifiers() & Qt.ShiftModifier) > 0 else
                0, '0', 1 if self.__m_mouseEvent.type()
                == QEvent.MouseButtonDblClick else 0)

            if self.__m_mouseEvent.type() == QEvent.MouseButtonPress:
                # qDebug('B')
                self._interactor.InvokeEvent(
                    vtk.vtkCommand.LeftButtonPressEvent)
            elif self.__m_mouseEvent.type() == QEvent.MouseButtonRelease:
                # qDebug('C')
                self._interactor.InvokeEvent(
                    vtk.vtkCommand.LeftButtonReleaseEvent)

            self.__m_mouseEvent.accept()

        # * Process move event
        if self.__m_moveEvent and not self.__m_moveEvent.isAccepted():
            # qDebug('D')
            if self.__m_moveEvent.type(
            ) == QEvent.MouseMove and self.__m_moveEvent.buttons() & (
                    Qt.RightButton | Qt.LeftButton):
                # qDebug('E')
                self._interactor.SetEventInformationFlipY(
                    self.__m_moveEvent.x(), self.__m_moveEvent.y(), 1 if
                    (self.__m_moveEvent.modifiers() & Qt.ControlModifier) > 0
                    else 0, 1 if
                    (self.__m_moveEvent.modifiers() & Qt.ShiftModifier) > 0
                    else 0, '0', 1 if self.__m_moveEvent.type()
                    == QEvent.MouseButtonDblClick else 0)

                self._interactor.InvokeEvent(vtk.vtkCommand.MouseMoveEvent)

            self.__m_moveEvent.accept()

        # * Process wheel event
        if self.__m_wheelEvent and not self.__m_wheelEvent.isAccepted():
            # qDebug('F')
            self._interactor.SetEventInformationFlipY(
                self.__m_wheelEvent.x(), self.__m_wheelEvent.y(), 1 if
                (self.__m_wheelEvent.modifiers() & Qt.ControlModifier) > 0 else
                0, 1 if
                (self.__m_wheelEvent.modifiers() & Qt.ShiftModifier) > 0 else
                0, '0', 1 if self.__m_wheelEvent.type()
                == QEvent.MouseButtonDblClick else 0)

            if self.__m_wheelEvent.delta() > 0:
                self._interactor.InvokeEvent(
                    vtk.vtkCommand.MouseWheelForwardEvent)
            elif self.__m_wheelEvent.delta() < 0:
                self._interactor.InvokeEvent(
                    vtk.vtkCommand.MouseWheelBackwardEvent)

            self.__m_wheelEvent.accept()

        # Render
        self._render_window.Render()
        self._render_window.PopState()
        self.__m_vtkFboItem.window().resetOpenGLState()

    def _dump_ren_win(self):
        qDebug('ObjectRenderer: DUMPING RENDER')
        self._render_window.PushState()
        self.openGLInitState()
        self._render_window.Start()
        # Render
        self._render_window.Render()

        width, height = self._render_window.GetSize()
        arr = vtk.vtkUnsignedCharArray()
        self.ren_win.GetRGBACharPixelData(0, 0, width - 1, height - 1, 0, arr)
        data = vtk_to_numpy(arr).reshape(height, width, -1)[::-1]
        self._render_window.PopState()
        self.__m_vtkFboItem.window().resetOpenGLState()
        return data

    def synchronize(self, item: QQuickFramebufferObject):
        qDebug('ObjectRenderer: SYNC')
        rendererSize = self._render_window.GetSize()
        if self.__m_vtkFboItem.width() != rendererSize[
                0] or self.__m_vtkFboItem.height() != rendererSize[1]:
            self._render_window.SetSize(int(self.__m_vtkFboItem.width()),
                                        int(self.__m_vtkFboItem.height()))

        # * Copy mouse events
        print(self.__m_vtkFboItem.getLastMouseButton().isAccepted())
        if not self.__m_vtkFboItem.getLastMouseButton().isAccepted():
            self.__m_mouseEvent = self.__m_vtkFboItem.getLastMouseButton()

        if not self.__m_vtkFboItem.getLastMoveEvent().isAccepted():
            self.__m_moveEvent = self.__m_vtkFboItem.getLastMoveEvent()

        if self.__m_vtkFboItem.getLastWheelEvent(
        ) and not self.__m_vtkFboItem.getLastWheelEvent().isAccepted():
            self.__m_wheelEvent = self.__m_vtkFboItem.getLastWheelEvent()

    def createFramebufferObject(self, size):
        qDebug('ObjectRenderer: Created OpenGLFBO')
        fmt = QOpenGLFramebufferObjectFormat()
        fmt.setAttachment(QOpenGLFramebufferObject.Depth)
        fbo = QOpenGLFramebufferObject(size, fmt)
        fbo.release()
        self.__fbo = fbo
        return self.__fbo

    def openGLInitState(self):
        self._render_window.OpenGLInitState()
        self._render_window.MakeCurrent()
        # When called from a pyvista function this fails....
        self.gl.initializeOpenGLFunctions()