def polydataBoolean(self,
                        polyData1,
                        polyData2,
                        operation,
                        triangleFilter=False,
                        loop=False,
                        clean=True):
        # Subtract/add polyData2 from polyData1
        if (not polyData1) or (not polyData2):
            return polyData1

        booleanFilter = vtk.vtkBooleanOperationPolyDataFilter()
        if loop:
            booleanFilter = vtk.vtkLoopBooleanPolyDataFilter()

        if operation == "difference" or operation == "subtract":
            booleanFilter.SetOperationToDifference()
        elif operation == "union" or operation == "addition":
            booleanFilter.SetOperationToUnion()
        elif operation == "intersection":
            booleanFilter.SetOperationToIntersection()
        else:
            return None

        if triangleFilter:
            triangleFilter1 = vtk.vtkTriangleFilter()
            triangleFilter1.SetInputData(polyData1)
            triangleFilter1.Update()

            triangleFilter2 = vtk.vtkTriangleFilter()
            triangleFilter2.SetInputData(polyData2)
            triangleFilter2.Update()

            booleanFilter.SetInputData(0, triangleFilter1.GetOutput())
            booleanFilter.SetInputData(1, triangleFilter2.GetOutput())
        else:
            booleanFilter.SetInputData(0, polyData1)
            booleanFilter.SetInputData(1, polyData2)

        booleanFilter.Update()

        if clean:
            cleanFilter = vtk.vtkCleanPolyData()
            cleanFilter.SetInputData(booleanFilter.GetOutput())
            cleanFilter.PointMergingOn()
            cleanFilter.Update()
            print("blah")
            return cleanFilter.GetOutput()
        else:
            return booleanFilter.GetOutput()
Ejemplo n.º 2
0
    def updateCurve(self):

        if self.controlPointsMarkupNode and self.curveModelNode:

            self.curvePoints.Reset()  # clear without deallocating memory
            lines = vtk.vtkCellArray()
            self.curvePoly.SetLines(lines)

            if self.controlPointsMarkupNode.GetNumberOfFiducials() >= 2:
                self.pointInterpolationFunction(self.controlPointsMarkupNode,
                                                self.curvePoints)
                nInterpolatedPoints = self.curvePoints.GetNumberOfPoints()
                lines.InsertNextCell(nInterpolatedPoints)
                for i in range(nInterpolatedPoints):
                    lines.InsertCellPoint(i)

            tubeFilter = vtk.vtkTubeFilter()
            tubeFilter.SetInputData(self.curvePoly)
            tubeFilter.SetRadius(self.tubeRadius)
            tubeFilter.SetNumberOfSides(self.tubeResolution)
            tubeFilter.SetCapping(not self.closed)

            # Triangulation is necessary to avoid discontinuous lines
            # in model/slice intersection display
            triangles = vtk.vtkTriangleFilter()
            triangles.SetInputConnection(tubeFilter.GetOutputPort())
            triangles.Update()

            self.curveModelNode.SetAndObservePolyData(triangles.GetOutput())
            self.curveModelNode.Modified()
Ejemplo n.º 3
0
  def applyFilters(self, state):

    surface = state.inputModelNode.GetPolyData()

    if state.decimation:
      triangle = vtk.vtkTriangleFilter()
      triangle.SetInput(surface)
      decimation = vtk.vtkDecimatePro()
      decimation.SetInput(triangle.GetOutput())
      decimation.SetTargetReduction(state.reduction)
      decimation.SetBoundaryVertexDeletion(state.boundaryDeletion)
      decimation.PreserveTopologyOn()
      decimation.Update()
      surface = decimation.GetOutput()

    if state.smoothing:
      if state.smoothingMethod == "Laplace":
        smoothing = vtk.vtkSmoothPolyDataFilter()
        smoothing.SetInput(surface)
        smoothing.SetBoundarySmoothing(state.boundarySmoothing)
        smoothing.SetNumberOfIterations(state.laplaceIterations)
        smoothing.SetRelaxationFactor(state.laplaceRelaxation)
        smoothing.Update()
        surface = smoothing.GetOutput()
      elif state.smoothingMethod == "Taubin":
        smoothing = vtk.vtkWindowedSincPolyDataFilter()
        smoothing.SetInput(surface)
        smoothing.SetBoundarySmoothing(state.boundarySmoothing)
        smoothing.SetNumberOfIterations(state.taubinIterations)
        smoothing.SetPassBand(state.taubinPassBand)
        smoothing.Update()
        surface = smoothing.GetOutput()

    if state.normals:
      normals = vtk.vtkPolyDataNormals()
      normals.SetInput(surface)
      normals.AutoOrientNormalsOn()
      normals.SetFlipNormals(state.flipNormals)
      normals.SetSplitting(state.splitting)
      normals.SetFeatureAngle(state.featureAngle)
      normals.ConsistencyOn()
      normals.Update()
      surface = normals.GetOutput()

    if state.cleaner:
      cleaner = vtk.vtkCleanPolyData()
      cleaner.SetInput(surface)
      cleaner.Update()
      surface = cleaner.GetOutput()

    if state.connectivity:
      connectivity = vtk.vtkPolyDataConnectivityFilter()
      connectivity.SetInput(surface)
      connectivity.SetExtractionModeToLargestRegion()
      connectivity.Update()
      surface = connectivity.GetOutput()

    state.outputModelNode.SetAndObservePolyData(surface)

    return True
Ejemplo n.º 4
0
  def applyFilters(self, state):

    surface = state.inputModelNode.GetPolyData()

    if state.decimation:
      triangle = vtk.vtkTriangleFilter()
      triangle.SetInput(surface)
      decimation = vtk.vtkDecimatePro()
      decimation.SetInput(triangle.GetOutput())
      decimation.SetTargetReduction(state.reduction)
      decimation.SetBoundaryVertexDeletion(state.boundaryDeletion)
      decimation.PreserveTopologyOn()
      decimation.Update()
      surface = decimation.GetOutput()

    if state.smoothing:
      if state.smoothingMethod == "Laplace":
        smoothing = vtk.vtkSmoothPolyDataFilter()
        smoothing.SetInput(surface)
        smoothing.SetBoundarySmoothing(state.boundarySmoothing)
        smoothing.SetNumberOfIterations(state.laplaceIterations)
        smoothing.SetRelaxationFactor(state.laplaceRelaxation)
        smoothing.Update()
        surface = smoothing.GetOutput()
      elif state.smoothingMethod == "Taubin":
        smoothing = vtk.vtkWindowedSincPolyDataFilter()
        smoothing.SetInput(surface)
        smoothing.SetBoundarySmoothing(state.boundarySmoothing)
        smoothing.SetNumberOfIterations(state.taubinIterations)
        smoothing.SetPassBand(state.taubinPassBand)
        smoothing.Update()
        surface = smoothing.GetOutput()

    if state.normals:
      normals = vtk.vtkPolyDataNormals()
      normals.SetInput(surface)
      normals.AutoOrientNormalsOn()
      normals.SetFlipNormals(state.flipNormals)
      normals.SetSplitting(state.splitting)
      normals.SetFeatureAngle(state.featureAngle)
      normals.ConsistencyOn()
      normals.Update()
      surface = normals.GetOutput()

    if state.cleaner:
      cleaner = vtk.vtkCleanPolyData()
      cleaner.SetInput(surface)
      cleaner.Update()
      surface = cleaner.GetOutput()

    if state.connectivity:
      connectivity = vtk.vtkPolyDataConnectivityFilter()
      connectivity.SetInput(surface)
      connectivity.SetExtractionModeToLargestRegion()
      connectivity.Update()
      surface = connectivity.GetOutput()

    state.outputModelNode.SetAndObservePolyData(surface)

    return True
  def runModelToLabelMap(self,image, modelNode, outputMask, refineRate):

    # Make sure all polygons are triangles
    triangle = vtk.vtkTriangleFilter()
    triangle.SetInput(modelNode.GetPolyData())
    triangle.Update()
    modelNode.SetAndObservePolyData(triangle.GetOutput())

    # Increase number of polygons in the mesh to avoid having holes
    # in contour, which confuse ModelToLabelMap when flooding
    # (flooding the whole labelmap if contour is not closed)
    refine = vtk.vtkLoopSubdivisionFilter()
    refine.SetInput(modelNode.GetPolyData())
    refine.SetNumberOfSubdivisions(refineRate)
    refine.Update()
    modelNode.SetAndObservePolyData(refine.GetOutput())

    # Set ModelToLabelMap parameters
    modelToLabelMapParameters["InputVolume"] = image.GetID()
    modelToLabelMapParameters["surface"] = modelNode.GetID()
    modelToLabelMapParameters["OutputVolume"] = outputMask.GetID()

    # Run ModelToLabelMap
    modelToLabelMapCLI = slicer.modules.modeltolabelmap
    slicer.cli.run(modelToLabelMapCLI, None, modelToLabelMapParameters, wait_for_completion=True)
def calculateSurfaceArea(polydata):
    triangleFilter = vtk.vtkTriangleFilter()
    triangleFilter.SetInputData(polydata)
    triangleFilter.SetPassLines(0)
    triangleFilter.Update()

    massProperties = vtk.vtkMassProperties()
    massProperties.SetInputData(triangleFilter.GetOutput())
    return massProperties.GetSurfaceArea()
    def prepareModel( self, polyData ):
        '''
        '''
        # import the vmtk libraries
        try:
            #from libvtkvmtkComputationalGeometryPython import *
            #from libvtkvmtkMiscPython import *
            import libvtkvmtkComputationalGeometryPython as cg
            import libvtkvmtkMiscPython as m
        except ImportError:
            print "FAILURE: Unable to import the SlicerVmtk libraries!"

        capDisplacement = 0.0

        surfaceCleaner = vtk.vtkCleanPolyData()
        surfaceCleaner.SetInput( polyData )
        surfaceCleaner.Update()

        surfaceTriangulator = vtk.vtkTriangleFilter()
        surfaceTriangulator.SetInput( surfaceCleaner.GetOutput() )
        surfaceTriangulator.PassLinesOff()
        surfaceTriangulator.PassVertsOff()
        surfaceTriangulator.Update()

        # new steps for preparation to avoid problems because of slim models (f.e. at stenosis)
        subdiv = vtk.vtkLinearSubdivisionFilter()
        subdiv.SetInput( surfaceTriangulator.GetOutput() )
        subdiv.SetNumberOfSubdivisions( 1 )
        subdiv.Update()

        smooth = vtk.vtkWindowedSincPolyDataFilter()
        smooth.SetInput( subdiv.GetOutput() )
        smooth.SetNumberOfIterations( 20 )
        smooth.SetPassBand( 0.1 )
        smooth.SetBoundarySmoothing( 1 )
        smooth.Update()

        normals = vtk.vtkPolyDataNormals()
        normals.SetInput( smooth.GetOutput() )
        normals.SetAutoOrientNormals( 1 )
        normals.SetFlipNormals( 0 )
        normals.SetConsistency( 1 )
        normals.SplittingOff()
        normals.Update()

        surfaceCapper = m.vtkvmtkCapPolyData()
        surfaceCapper.SetInput( normals.GetOutput() )
        surfaceCapper.SetDisplacement( capDisplacement )
        surfaceCapper.SetInPlaneDisplacement( capDisplacement )
        surfaceCapper.Update()

        outPolyData = vtk.vtkPolyData()
        outPolyData.DeepCopy( surfaceCapper.GetOutput() )
        outPolyData.Update()

        return outPolyData
def createBox(X, Y, Z, name):
    miterBox = slicer.mrmlScene.CreateNodeByClass('vtkMRMLModelNode')
    miterBox.SetName(slicer.mrmlScene.GetUniqueNameByString(name))
    slicer.mrmlScene.AddNode(miterBox)
    miterBox.CreateDefaultDisplayNodes()
    miterBoxSource = vtk.vtkCubeSource()
    miterBoxSource.SetXLength(X)
    miterBoxSource.SetYLength(Y)
    miterBoxSource.SetZLength(Z)
    triangleFilter = vtk.vtkTriangleFilter()
    triangleFilter.SetInputConnection(miterBoxSource.GetOutputPort())
    #triangleFilter.Update()
    miterBox.SetPolyDataConnection(triangleFilter.GetOutputPort())
    return miterBox
Ejemplo n.º 9
0
    def computeSurfaceBetweenLines(self):
        """
    Update model with a surface between base and margin lines.
    """

        numberOfBasePoints = self.baseLine.curvePoints.GetNumberOfPoints()
        numberOfMarginPoints = self.marginLine.curvePoints.GetNumberOfPoints()
        if numberOfBasePoints == 0 or numberOfMarginPoints == 0:
            self.surfaceModelNode.SetAndObservePolyData(None)
            return

        boundaryPoints = vtk.vtkPoints()
        boundaryPoints.DeepCopy(self.baseLine.curvePoints)
        boundaryPoints.InsertPoints(numberOfBasePoints, numberOfMarginPoints,
                                    0, self.marginLine.curvePoints)

        # Add a triangle strip between the base and margin lines
        strips = vtk.vtkCellArray()
        strips.InsertNextCell(numberOfBasePoints * 2)
        basePointToMarginPointScale = float(numberOfMarginPoints) / float(
            numberOfBasePoints)
        for basePointIndex in range(numberOfBasePoints):
            strips.InsertCellPoint(basePointIndex)
            strips.InsertCellPoint(
                int(numberOfBasePoints +
                    basePointIndex * basePointToMarginPointScale))

        clippingSurfacePolyData = vtk.vtkPolyData()
        clippingSurfacePolyData.SetPoints(boundaryPoints)
        clippingSurfacePolyData.SetStrips(strips)

        triangulator = vtk.vtkTriangleFilter()
        triangulator.SetInputData(clippingSurfacePolyData)
        triangulator.Update()

        clippingPolyData = triangulator.GetOutput()

        self.surfaceModelNode.SetAndObservePolyData(clippingPolyData)
Ejemplo n.º 10
0
    def decimateSurface( self, polyData ):
        '''
        '''

        decimationFilter = vtk.vtkDecimatePro()
        decimationFilter.SetInputData( polyData )
        decimationFilter.SetTargetReduction( 0.99 )
        decimationFilter.SetBoundaryVertexDeletion( 0 )
        decimationFilter.PreserveTopologyOn()
        decimationFilter.Update()

        cleaner = vtk.vtkCleanPolyData()
        cleaner.SetInputData( decimationFilter.GetOutput() )
        cleaner.Update()

        triangleFilter = vtk.vtkTriangleFilter()
        triangleFilter.SetInputData( cleaner.GetOutput() )
        triangleFilter.Update()

        outPolyData = vtk.vtkPolyData()
        outPolyData.DeepCopy( triangleFilter.GetOutput() )

        return outPolyData
Ejemplo n.º 11
0
    def updateRoi(self):
        if not self.roiModelNode:
            return

        numberOfContourPoints = 0
        annulusPoints = None
        planePosition = None
        planeNormal = None
        if self.annulusContourCurve:
            contourPoints = self.annulusContourCurve.curvePoints  # vtk.vtkPoints()
            numberOfContourPoints = contourPoints.GetNumberOfPoints()
            if numberOfContourPoints > 0:
                annulusPoints = self.annulusContourCurve.getInterpolatedPointsAsArray(
                )  # formerly contourPointsArray_Ras
                [planePosition,
                 planeNormal] = HeartValveLib.planeFit(annulusPoints)
        elif self.valveModel is not None and self.leafletSegmentId is not None:
            annulusPoints = self.getLeafletBoundary()
            if annulusPoints is not None:
                numberOfContourPoints = annulusPoints.shape[1]
                [planePosition,
                 planeNormal] = self.valveModel.getAnnulusContourPlane()

        if numberOfContourPoints <= 0:
            clippingPolyData = vtk.vtkPolyData()
            self.roiModelNode.SetAndObservePolyData(clippingPolyData)
            self.roiModelNode.Modified()
            return

        scale = float(self.roiModelNode.GetAttribute(self.PARAM_SCALE)) * 0.01
        topDistance = float(
            self.roiModelNode.GetAttribute(self.PARAM_TOP_DISTANCE))
        topScale = float(self.roiModelNode.GetAttribute(
            self.PARAM_TOP_SCALE)) * 0.01
        bottomDistance = float(
            self.roiModelNode.GetAttribute(self.PARAM_BOTTOM_DISTANCE))
        bottomScale = float(
            self.roiModelNode.GetAttribute(self.PARAM_BOTTOM_SCALE)) * 0.01

        transformPlaneToWorld = vtk.vtkTransform()
        transformWorldToPlaneMatrix = HeartValveLib.getTransformToPlane(
            planePosition, planeNormal)

        numberOfPoints = annulusPoints.shape[1]
        # Concatenate a 4th line containing 1s so that we can transform the positions using
        # a single matrix multiplication.
        annulusPoints_World = np.row_stack(
            (annulusPoints, np.ones(numberOfPoints)))
        # Point positions in the plane coordinate system:
        annulusPoints_Plane = np.dot(transformWorldToPlaneMatrix,
                                     annulusPoints_World)
        # remove the last row (all ones)
        annulusPoints_Plane = annulusPoints_Plane[0:3, :]

        # Add points for middle, top, and bottom planes
        clippingSurfacePoints = vtk.vtkPoints()
        clippingSurfacePoints.Allocate(
            3 * numberOfContourPoints
        )  # annulus contour + 2x shifted annulus contour
        # Middle plane
        annulusPoints_Plane[0, :] = (
            annulusPoints_Plane[0, :] - annulusPoints_Plane[0, :].mean()
        ) * scale + annulusPoints_Plane[0, :].mean()
        annulusPoints_Plane[1, :] = (
            annulusPoints_Plane[1, :] - annulusPoints_Plane[1, :].mean()
        ) * scale + annulusPoints_Plane[1, :].mean()
        for contourPoint in annulusPoints_Plane.T:
            clippingSurfacePoints.InsertNextPoint(contourPoint)
        meanPosZ = annulusPoints_Plane[:, 2].mean()
        # Top plane
        contourPointsArrayTop_Ras = np.copy(annulusPoints_Plane)
        contourPointsArrayTop_Ras[0, :] = (
            contourPointsArrayTop_Ras[0, :] - annulusPoints_Plane[0, :].mean()
        ) * topScale + annulusPoints_Plane[0, :].mean()
        contourPointsArrayTop_Ras[1, :] = (
            contourPointsArrayTop_Ras[1, :] - annulusPoints_Plane[1, :].mean()
        ) * topScale + annulusPoints_Plane[1, :].mean()
        contourPointsArrayTop_Ras[2, :] = topDistance  # make the plane planar
        for contourPoint in contourPointsArrayTop_Ras.T:
            clippingSurfacePoints.InsertNextPoint(contourPoint)
        # Bottom plane
        contourPointsArrayBottom_Ras = np.copy(annulusPoints_Plane)
        contourPointsArrayBottom_Ras[
            0, :] = (contourPointsArrayBottom_Ras[0, :] - annulusPoints_Plane[
                0, :].mean()) * bottomScale + annulusPoints_Plane[0, :].mean()
        contourPointsArrayBottom_Ras[
            1, :] = (contourPointsArrayBottom_Ras[1, :] - annulusPoints_Plane[
                1, :].mean()) * bottomScale + annulusPoints_Plane[1, :].mean()
        contourPointsArrayBottom_Ras[
            2, :] = -bottomDistance  # make the plane planar
        for contourPoint in contourPointsArrayBottom_Ras.T:
            clippingSurfacePoints.InsertNextPoint(contourPoint)

        # Add frustum surfaces
        strips = vtk.vtkCellArray()
        # Between middle and top
        strips.InsertNextCell(numberOfContourPoints * 2 + 2)
        firstTopPointIndex = numberOfContourPoints
        for i in range(numberOfContourPoints):
            strips.InsertCellPoint(i)
            strips.InsertCellPoint(i + firstTopPointIndex)
        strips.InsertCellPoint(0)
        strips.InsertCellPoint(firstTopPointIndex)
        # Between middle and bottom
        strips.InsertNextCell(numberOfContourPoints * 2 + 2)
        firstBottomPointIndex = numberOfContourPoints * 2
        for i in range(numberOfContourPoints):
            strips.InsertCellPoint(i)
            strips.InsertCellPoint(i + firstBottomPointIndex)
        strips.InsertCellPoint(0)
        strips.InsertCellPoint(firstBottomPointIndex)
        # Top and bottom caps
        polys = vtk.vtkCellArray()
        polys.InsertNextCell(numberOfContourPoints)
        for i in range(numberOfContourPoints, numberOfContourPoints * 2):
            polys.InsertCellPoint(i)
        polys.InsertNextCell(numberOfContourPoints)
        for i in range(numberOfContourPoints * 2, numberOfContourPoints * 3):
            polys.InsertCellPoint(i)

        clippingSurfacePolyData = vtk.vtkPolyData()
        clippingSurfacePolyData.SetPoints(clippingSurfacePoints)
        clippingSurfacePolyData.SetStrips(strips)
        clippingSurfacePolyData.SetPolys(polys)

        triangulator = vtk.vtkTriangleFilter()
        triangulator.SetInputData(clippingSurfacePolyData)

        transformPlaneToWorldMatrix = np.linalg.inv(
            transformWorldToPlaneMatrix)
        transformPlaneToWorldMatrixVtk = vtk.vtkMatrix4x4()
        for colIndex in range(4):
            for rowIndex in range(3):
                transformPlaneToWorldMatrixVtk.SetElement(
                    rowIndex, colIndex, transformPlaneToWorldMatrix[rowIndex,
                                                                    colIndex])
        transformPlaneToWorld.SetMatrix(transformPlaneToWorldMatrixVtk)
        polyTransformToWorld = vtk.vtkTransformPolyDataFilter()
        polyTransformToWorld.SetTransform(transformPlaneToWorld)
        polyTransformToWorld.SetInputConnection(triangulator.GetOutputPort())

        polyTransformToWorld.Update()
        clippingPolyData = polyTransformToWorld.GetOutput()

        self.roiModelNode.SetAndObservePolyData(clippingPolyData)
        self.roiModelNode.Modified()
Ejemplo n.º 12
0
# This module was tested on 3D Slicer version 4.3.1
Ejemplo n.º 13
0
    def run(self, inputModel, sModel, seedList):
        """
    Run the actual algorithm
    """

        self.delayDisplay('Running the aglorithm')

        tri = vtk.vtkDelaunay3D()
        tri.SetInputData(sModel.GetPolyData())

        elev = vtk.vtkElevationFilter()
        elev.SetInputConnection(tri.GetOutput())

        implicitDataSet = vtk.vtkImplicitDataSet()
        implicitDataSet.SetDataSet(elev.GetOutput())

        triangle = vtk.vtkTriangleFilter()
        triangle.SetInputData(inputModel.GetPolyData())
        triangle.Update()

        computeNormals = vtk.vtkPolyDataNormals()
        computeNormals.SetInputData(triangle.GetOutput())
        computeNormals.ComputeCellNormalsOn()
        computeNormals.Update()

        clip = vtk.vtkClipPolyData()
        clip.SetInputData(computeNormals.GetOutput())
        clip.SetClipFunction(implicitDataSet)
        clip.InsideOutOff()
        clip.Update()

        clean = vtk.vtkCleanPolyData()
        clean.SetInputData(clip.GetOutput())
        clean.Update()

        polydata = clean.GetOutput()

        cellData = polydata.GetCellData()
        normals = cellData.GetNormals()

        meanNormal = [0, 0, 0]
        nOfTuples = normals.GetNumberOfTuples()

        for cellIndex in range(0, nOfTuples):
            cellNormal = [0, 0, 0]
            cell = polydata.GetCell(cellIndex)

            normals.GetTuple(cellIndex, cellNormal)
            meanNormal[0] = meanNormal[0] + cellNormal[0]
            meanNormal[1] = meanNormal[1] + cellNormal[1]
            meanNormal[2] = meanNormal[2] + cellNormal[2]

        meanNormal[0] = meanNormal[0] / nOfTuples
        meanNormal[1] = meanNormal[1] / nOfTuples
        meanNormal[2] = meanNormal[2] / nOfTuples

        print("Normal: " + str(meanNormal))

        seed1 = [0, 0, 0]
        seedList.GetNthFiducialPosition(0, seed1)
        vector = [
            seed1[0] + 50 * meanNormal[0], seed1[1] + 50 * meanNormal[1],
            seed1[2] + 50 * meanNormal[2]
        ]
        seedList.AddFiducialFromArray(vector)

        # Calculate perpendicular vectors
        v1 = [0, 0, 0]
        v2 = [0, 0, 0]

        math = vtk.vtkMath()
        math.Perpendiculars(meanNormal, v2, v1, 0)

        # Normalize vectors
        math.Normalize(meanNormal)
        math.Normalize(v1)
        math.Normalize(v2)

        # create matrix4x4
        transform = slicer.mrmlScene.CreateNodeByClass(
            'vtkMRMLLinearTransformNode')
        slicer.mrmlScene.AddNode(transform)
        matrix = transform.GetMatrixTransformToParent()

        matrix.SetElement(0, 0, v1[0])
        matrix.SetElement(1, 0, v1[1])
        matrix.SetElement(2, 0, v1[2])
        matrix.SetElement(3, 0, 0.0)

        matrix.SetElement(0, 1, meanNormal[0])
        matrix.SetElement(1, 1, meanNormal[1])
        matrix.SetElement(2, 1, meanNormal[2])
        matrix.SetElement(3, 1, 0.0)

        matrix.SetElement(0, 2, v2[0])
        matrix.SetElement(1, 2, v2[1])
        matrix.SetElement(2, 2, v2[2])
        matrix.SetElement(3, 2, 0.0)

        matrix.SetElement(0, 3, seed1[0])
        matrix.SetElement(1, 3, seed1[1])
        matrix.SetElement(2, 3, seed1[2])
        matrix.SetElement(3, 3, 1.0)

        return True
  def run(self,inputModel,sModel,seedList):
    """
    Run the actual algorithm
    """

    self.delayDisplay('Running the aglorithm')

    tri = vtk.vtkDelaunay3D()
    tri.SetInputData(sModel.GetPolyData())

    elev = vtk.vtkElevationFilter()
    elev.SetInputConnection(tri.GetOutput())

    implicitDataSet = vtk.vtkImplicitDataSet()
    implicitDataSet.SetDataSet(elev.GetOutput())
    
    triangle = vtk.vtkTriangleFilter()
    triangle.SetInputData(inputModel.GetPolyData())
    triangle.Update()

    computeNormals = vtk.vtkPolyDataNormals()
    computeNormals.SetInputData(triangle.GetOutput())
    computeNormals.ComputeCellNormalsOn()
    computeNormals.Update()

    clip = vtk.vtkClipPolyData()
    clip.SetInputData(computeNormals.GetOutput())
    clip.SetClipFunction(implicitDataSet)
    clip.InsideOutOff()
    clip.Update()

    clean = vtk.vtkCleanPolyData()
    clean.SetInputData(clip.GetOutput())
    clean.Update()

    polydata = clean.GetOutput()

    cellData = polydata.GetCellData()
    normals = cellData.GetNormals()

    meanNormal = [0,0,0]
    nOfTuples = normals.GetNumberOfTuples()

    for cellIndex in range(0, nOfTuples):
      cellNormal = [0,0,0]
      cell = polydata.GetCell(cellIndex)
      
      normals.GetTuple(cellIndex, cellNormal)
      meanNormal[0] = meanNormal[0] + cellNormal[0]
      meanNormal[1] = meanNormal[1] + cellNormal[1]
      meanNormal[2] = meanNormal[2] + cellNormal[2]
        
    meanNormal[0] = meanNormal[0] / nOfTuples
    meanNormal[1] = meanNormal[1] / nOfTuples
    meanNormal[2] = meanNormal[2] / nOfTuples

    print("Normal: " + str(meanNormal))

    seed1 = [0,0,0]
    seedList.GetNthFiducialPosition(0,seed1)
    vector = [seed1[0]+50*meanNormal[0],
              seed1[1]+50*meanNormal[1],
              seed1[2]+50*meanNormal[2]]
    seedList.AddFiducialFromArray(vector)

    # Calculate perpendicular vectors
    v1 = [0,0,0]
    v2 = [0,0,0]

    math = vtk.vtkMath()
    math.Perpendiculars(meanNormal, v2, v1, 0)

    # Normalize vectors
    math.Normalize(meanNormal)
    math.Normalize(v1)
    math.Normalize(v2)

    # create matrix4x4
    transform = slicer.mrmlScene.CreateNodeByClass('vtkMRMLLinearTransformNode') 
    slicer.mrmlScene.AddNode(transform)
    matrix = transform.GetMatrixTransformToParent()
    
    matrix.SetElement(0,0,v1[0])
    matrix.SetElement(1,0,v1[1])
    matrix.SetElement(2,0,v1[2])
    matrix.SetElement(3,0,0.0)

    matrix.SetElement(0,1,meanNormal[0])
    matrix.SetElement(1,1,meanNormal[1])
    matrix.SetElement(2,1,meanNormal[2])
    matrix.SetElement(3,1,0.0)

    matrix.SetElement(0,2,v2[0])
    matrix.SetElement(1,2,v2[1])
    matrix.SetElement(2,2,v2[2])
    matrix.SetElement(3,2,0.0)

    matrix.SetElement(0,3,seed1[0])
    matrix.SetElement(1,3,seed1[1])
    matrix.SetElement(2,3,seed1[2])
    matrix.SetElement(3,3,1.0)


    return True
Ejemplo n.º 15
0
    def run(self, inputModel, spherePosition, sphereRadius, outputTransform):
        """
    Run the actual algorithm
    """

        if not self.isValidInputOutputData(inputModel, outputTransform):
            slicer.util.errorDisplay(
                'Input model is the same as sphere model. Choose a different input model.'
            )
            return False

        logging.info('Processing started')

        # Convert sphere model to an implicit dataset to clip input model with it
        sphere = vtk.vtkSphere()
        sphere.SetCenter(spherePosition)
        sphere.SetRadius(sphereRadius)

        # Clip and clean input model
        triangle = vtk.vtkTriangleFilter()
        triangle.SetInputData(inputModel.GetPolyData())
        triangle.Update()

        clip = vtk.vtkClipPolyData()
        clip.SetInputData(triangle.GetOutput())
        clip.SetClipFunction(sphere)
        clip.InsideOutOn()
        clip.Update()

        clean = vtk.vtkCleanPolyData()
        clean.SetInputConnection(clip.GetOutputPort())
        clean.Update()

        # Compute average normal
        clippedModel = clip.GetOutput()
        cellsNormal = clippedModel.GetPointData().GetNormals()

        averageNormal = [0.0, 0.0, 0.0]
        nOfNormals = 0

        for cellIndex in range(0, cellsNormal.GetNumberOfTuples()):
            cellNormal = [0.0, 0.0, 0.0]
            cellsNormal.GetTuple(cellIndex, cellNormal)

            if not (math.isnan(cellNormal[0]) or math.isnan(cellNormal[1])
                    or math.isnan(cellNormal[2])):
                averageNormal[0] = averageNormal[0] + cellNormal[0]
                averageNormal[1] = averageNormal[1] + cellNormal[1]
                averageNormal[2] = averageNormal[2] + cellNormal[2]
                nOfNormals = nOfNormals + 1

        # Compute perpendicular vectors
        v1 = [0.0, 0.0, 0.0]
        v2 = [0.0, 0.0, 0.0]

        vtkmath = vtk.vtkMath()
        #vtkmath.Perpendiculars(averageNormal, v2, v1, 0)
        self.calculatePerpendicularVectors(averageNormal, v2, v1)

        # Normalize vectors
        vtkmath.Normalize(averageNormal)
        vtkmath.Normalize(v1)
        vtkmath.Normalize(v2)

        # Create Matrix4x4
        outputMatrix = vtk.vtkMatrix4x4()

        outputMatrix.SetElement(0, 0, v1[0])
        outputMatrix.SetElement(1, 0, v1[1])
        outputMatrix.SetElement(2, 0, v1[2])
        outputMatrix.SetElement(3, 0, 0.0)

        outputMatrix.SetElement(0, 1, averageNormal[0])
        outputMatrix.SetElement(1, 1, averageNormal[1])
        outputMatrix.SetElement(2, 1, averageNormal[2])
        outputMatrix.SetElement(3, 1, 0.0)

        outputMatrix.SetElement(0, 2, v2[0])
        outputMatrix.SetElement(1, 2, v2[1])
        outputMatrix.SetElement(2, 2, v2[2])
        outputMatrix.SetElement(3, 2, 0.0)

        outputMatrix.SetElement(0, 3, spherePosition[0])
        outputMatrix.SetElement(1, 3, spherePosition[1])
        outputMatrix.SetElement(2, 3, spherePosition[2])
        outputMatrix.SetElement(3, 3, 1.0)

        outputTransform.SetMatrixTransformToParent(outputMatrix)

        logging.info('Processing completed')

        return True
Ejemplo n.º 16
0
  def PolyDataToImageData(self, inputPolydata_Ras, referenceVolumeNode_Ras, inVal=100, outVal=0):
    """ We take in an polydata and convert it to an new image data , withing the Reference Voulume node
        the reference volume node is cleared with a threshold because originally the volume may contain
        alot of noisy pixels 
        PARAM: inputPolydata_Ras: Polydata we are looking to conver       vtkPolydata()
        PARAM: refernceVolumeNode_Ras                                     vtkMRMLScalarVolumeNode()
        RETURN : vtkImageData
        """
    
    """ Transform the polydata from ras to ijk using the referenceVolumeNode """
    #inputPolydataTriangulated_Ijk=polyToImage.GetOutput()
    transformPolydataFilter=vtk.vtkTransformPolyDataFilter()
    rasToIjkMatrix=vtk.vtkMatrix4x4()
    referenceVolumeNode_Ras.GetRASToIJKMatrix(rasToIjkMatrix)
    rasToIjkTransform = vtk.vtkTransform()
    rasToIjkTransform.SetMatrix(rasToIjkMatrix)
    transformPolydataFilter.SetTransform(rasToIjkTransform)
    transformPolydataFilter.SetInputData(inputPolydata_Ras)
    transformPolydataFilter.Update()
    inputPolydata_Ijk=transformPolydataFilter.GetOutput()
    normalsFunction=vtk.vtkPolyDataNormals()
    normalsFunction.SetInputData(inputPolydata_Ijk)
    normalsFunction.ConsistencyOn()
    trigFilter=vtk.vtkTriangleFilter()
    trigFilter.SetInputConnection(normalsFunction.GetOutputPort())
    stripper=vtk.vtkStripper()
    stripper.SetInputConnection(trigFilter.GetOutputPort())
    stripper.Update()
    inputPolydataTriangulated_Ijk=stripper.GetOutput()
    
    # Clone reference image and clear it
    referenceImage_Ijk = referenceVolumeNode_Ras.GetImageData()
    
    # Fill image with outVal (there is no volume Fill filter in VTK, therefore we need to use threshold filter)
    thresh = vtk.vtkImageThreshold()
    thresh.ReplaceInOn()
    thresh.ReplaceOutOn()
    thresh.SetInValue(outVal)
    thresh.SetOutValue(outVal)
    #thresh.SetOutputScalarType (vtk.VTK_UNSIGNED_CHAR)
    thresh.SetInputData(referenceImage_Ijk)
    thresh.Update()
    whiteImage_Ijk = thresh.GetOutput()

    # Convert polydata to stencil
    polyToImage = vtk.vtkPolyDataToImageStencil()
    polyToImage.SetInputData(inputPolydataTriangulated_Ijk)
    polyToImage.SetOutputSpacing(whiteImage_Ijk.GetSpacing())
    polyToImage.SetOutputOrigin(whiteImage_Ijk.GetOrigin())
    polyToImage.SetOutputWholeExtent(whiteImage_Ijk.GetExtent())
    polyToImage.Update()
    imageStencil_Ijk=polyToImage.GetOutput()
    
    # Convert stencil to image
    imgstenc = vtk.vtkImageStencil()
    imgstenc.SetInputData(whiteImage_Ijk)
    imgstenc.SetStencilData(imageStencil_Ijk)
    imgstenc.ReverseStencilOn()
    imgstenc.SetBackgroundValue(inVal)
    imgstenc.Update()
    return imgstenc.GetOutput()
Ejemplo n.º 17
0
    def PolyDataToImageData(self,
                            inputPolydata_Ras,
                            referenceVolumeNode_Ras,
                            inVal=100,
                            outVal=0):
        """ We take in an polydata and convert it to an new image data , withing the Reference Voulume node
        the reference volume node is cleared with a threshold because originally the volume may contain
        alot of noisy pixels 
        PARAM: inputPolydata_Ras: Polydata we are looking to conver       vtkPolydata()
        PARAM: refernceVolumeNode_Ras                                     vtkMRMLScalarVolumeNode()
        RETURN : vtkImageData
        """
        """ Transform the polydata from ras to ijk using the referenceVolumeNode """
        #inputPolydataTriangulated_Ijk=polyToImage.GetOutput()
        transformPolydataFilter = vtk.vtkTransformPolyDataFilter()
        rasToIjkMatrix = vtk.vtkMatrix4x4()
        referenceVolumeNode_Ras.GetRASToIJKMatrix(rasToIjkMatrix)
        rasToIjkTransform = vtk.vtkTransform()
        rasToIjkTransform.SetMatrix(rasToIjkMatrix)
        transformPolydataFilter.SetTransform(rasToIjkTransform)
        transformPolydataFilter.SetInputData(inputPolydata_Ras)
        transformPolydataFilter.Update()
        inputPolydata_Ijk = transformPolydataFilter.GetOutput()
        normalsFunction = vtk.vtkPolyDataNormals()
        normalsFunction.SetInputData(inputPolydata_Ijk)
        normalsFunction.ConsistencyOn()
        trigFilter = vtk.vtkTriangleFilter()
        trigFilter.SetInputConnection(normalsFunction.GetOutputPort())
        stripper = vtk.vtkStripper()
        stripper.SetInputConnection(trigFilter.GetOutputPort())
        stripper.Update()
        inputPolydataTriangulated_Ijk = stripper.GetOutput()

        # Clone reference image and clear it
        referenceImage_Ijk = referenceVolumeNode_Ras.GetImageData()

        # Fill image with outVal (there is no volume Fill filter in VTK, therefore we need to use threshold filter)
        thresh = vtk.vtkImageThreshold()
        thresh.ReplaceInOn()
        thresh.ReplaceOutOn()
        thresh.SetInValue(outVal)
        thresh.SetOutValue(outVal)
        #thresh.SetOutputScalarType (vtk.VTK_UNSIGNED_CHAR)
        thresh.SetInputData(referenceImage_Ijk)
        thresh.Update()
        whiteImage_Ijk = thresh.GetOutput()

        # Convert polydata to stencil
        polyToImage = vtk.vtkPolyDataToImageStencil()
        polyToImage.SetInputData(inputPolydataTriangulated_Ijk)
        polyToImage.SetOutputSpacing(whiteImage_Ijk.GetSpacing())
        polyToImage.SetOutputOrigin(whiteImage_Ijk.GetOrigin())
        polyToImage.SetOutputWholeExtent(whiteImage_Ijk.GetExtent())
        polyToImage.Update()
        imageStencil_Ijk = polyToImage.GetOutput()

        # Convert stencil to image
        imgstenc = vtk.vtkImageStencil()
        imgstenc.SetInputData(whiteImage_Ijk)
        imgstenc.SetStencilData(imageStencil_Ijk)
        imgstenc.ReverseStencilOn()
        imgstenc.SetBackgroundValue(inVal)
        imgstenc.Update()
        return imgstenc.GetOutput()
Ejemplo n.º 18
0
    def vtk_to_obj_converter(self, node, radius=0.1, number_of_sides=3):

        qt.QApplication.setOverrideCursor(qt.Qt.WaitCursor)

        polydata = node.GetPolyData()
        tuber = vtk.vtkTubeFilter()
        tuber.SetNumberOfSides(int(number_of_sides))
        tuber.SetRadius(radius)
        tuber.SetInputData(polydata)
        tuber.Update()

        tubes = tuber.GetOutputDataObject(0)
        # scalars = tubes.GetPointData().GetArray(0)
        # scalars.SetName("scalars")

        triangles = vtk.vtkTriangleFilter()
        triangles.SetInputData(tubes)
        triangles.Update()

        tripolydata = vtk.vtkPolyData()
        tripolydata.ShallowCopy(triangles.GetOutput())

        # Decrease the number of triangle of 30% to reduce Blender loading costs
        decimate = vtk.vtkDecimatePro()
        decimate.SetInputData(tripolydata)
        decimate.SetTargetReduction(.30)
        decimate.Update()

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

        r = random.randrange(0, 256, 1)
        g = random.randrange(0, 256, 1)
        b = random.randrange(0, 256, 1)

        actor = vtk.vtkActor()
        actor.SetMapper(mapper)
        # actor.GetProperty().SetColor(0, 0, 0)  # Ka: ambient color of the material (r, g, b)
        actor.GetProperty().SetDiffuseColor(
            r, g, b)  # Kd: diffuse color of the material (r, g, b)
        # actor.GetProperty().SetSpecularColor(0, 0, 0)  # Ks: specular color of the material (r, g, b)

        renderer = vtk.vtkRenderer()
        renderer.AddActor(actor)

        window = vtk.vtkRenderWindow()
        window.AddRenderer(renderer)

        # Get output path
        storageNode = node.GetStorageNode()
        filepath = storageNode.GetFullNameFromFileName()
        filename = filepath.rsplit('.', 1)

        writer = vtk.vtkOBJExporter()
        writer.SetFilePrefix(filename[0])
        writer.SetInput(window)
        writer.Write()

        qt.QApplication.restoreOverrideCursor()

        if writer.Write() == 0:
            qt.QMessageBox.critical(None, "Conversion", "Conversion failed")
        else:
            qt.QMessageBox.information(None, "Conversion", "Conversion done")
  def run(self, inputModel, spherePosition, sphereRadius, outputTransform):
    """
    Run the actual algorithm
    """

    if not self.isValidInputOutputData(inputModel, outputTransform):
      slicer.util.errorDisplay('Input model is the same as sphere model. Choose a different input model.')
      return False

    logging.info('Processing started')

    # Convert sphere model to an implicit dataset to clip input model with it
    sphere = vtk.vtkSphere()
    sphere.SetCenter(spherePosition)
    sphere.SetRadius(sphereRadius)

    # Clip and clean input model
    triangle = vtk.vtkTriangleFilter()
    triangle.SetInputData(inputModel.GetPolyData())
    triangle.Update()

    clip = vtk.vtkClipPolyData()
    clip.SetInputData(triangle.GetOutput())
    clip.SetClipFunction(sphere)
    clip.InsideOutOn()
    clip.Update()

    clean = vtk.vtkCleanPolyData()
    clean.SetInputConnection(clip.GetOutputPort())
    clean.Update()

    # Compute average normal
    clippedModel = clip.GetOutput()
    cellsNormal = clippedModel.GetPointData().GetNormals()
    
    averageNormal = [0.0, 0.0, 0.0]
    nOfNormals = 0;

    for cellIndex in range(0, cellsNormal.GetNumberOfTuples()):
      cellNormal = [0.0, 0.0, 0.0]
      cellsNormal.GetTuple(cellIndex, cellNormal)
      
      if not(math.isnan(cellNormal[0]) or math.isnan(cellNormal[1]) or math.isnan(cellNormal[2])):
        averageNormal[0] = averageNormal[0] + cellNormal[0]
        averageNormal[1] = averageNormal[1] + cellNormal[1]
        averageNormal[2] = averageNormal[2] + cellNormal[2]
        nOfNormals = nOfNormals + 1

    # Compute perpendicular vectors
    v1 = [0.0, 0.0, 0.0]
    v2 = [0.0, 0.0, 0.0]
    
    vtkmath = vtk.vtkMath()
    #vtkmath.Perpendiculars(averageNormal, v2, v1, 0)
    self.calculatePerpendicularVectors(averageNormal, v2, v1)

    # Normalize vectors
    vtkmath.Normalize(averageNormal)
    vtkmath.Normalize(v1)
    vtkmath.Normalize(v2)
    
    # Create Matrix4x4
    outputMatrix = vtk.vtkMatrix4x4()
    
    outputMatrix.SetElement(0,0,v1[0])
    outputMatrix.SetElement(1,0,v1[1])
    outputMatrix.SetElement(2,0,v1[2])
    outputMatrix.SetElement(3,0,0.0)

    outputMatrix.SetElement(0,1,averageNormal[0])
    outputMatrix.SetElement(1,1,averageNormal[1])
    outputMatrix.SetElement(2,1,averageNormal[2])
    outputMatrix.SetElement(3,1,0.0)

    outputMatrix.SetElement(0,2,v2[0])
    outputMatrix.SetElement(1,2,v2[1])
    outputMatrix.SetElement(2,2,v2[2])
    outputMatrix.SetElement(3,2,0.0)

    outputMatrix.SetElement(0,3,spherePosition[0])
    outputMatrix.SetElement(1,3,spherePosition[1])
    outputMatrix.SetElement(2,3,spherePosition[2])
    outputMatrix.SetElement(3,3,1.0)

    outputTransform.SetMatrixTransformToParent(outputMatrix)

    logging.info('Processing completed')

    return True