Esempio n. 1
0
def join_process_surface(filenames, algorithm, smooth_iterations,
                         smooth_relaxation_factor, decimate_reduction,
                         keep_largest, fill_holes, options, msg_queue):
    def send_message(msg):
        try:
            msg_queue.put_nowait(msg)
        except queue.Full as e:
            print(e)

    send_message('Joining surfaces ...')
    polydata_append = vtk.vtkAppendPolyData()
    for f in filenames:
        reader = vtk.vtkXMLPolyDataReader()
        reader.SetFileName(f)
        reader.Update()

        polydata = reader.GetOutput()

        polydata_append.AddInputData(polydata)
        del reader
        del polydata

    polydata_append.Update()
    #  polydata_append.GetOutput().ReleaseDataFlagOn()
    polydata = polydata_append.GetOutput()
    #polydata.Register(None)
    #  polydata.SetSource(None)
    del polydata_append

    send_message('Cleaning surface ...')
    clean = vtk.vtkCleanPolyData()
    #  clean.ReleaseDataFlagOn()
    #  clean.GetOutput().ReleaseDataFlagOn()
    clean_ref = weakref.ref(clean)
    #  clean_ref().AddObserver("ProgressEvent", lambda obj,evt:
    #  UpdateProgress(clean_ref(), _("Creating 3D surface...")))
    clean.SetInputData(polydata)
    clean.PointMergingOn()
    clean.Update()

    del polydata
    polydata = clean.GetOutput()
    #  polydata.SetSource(None)
    del clean

    if algorithm == 'ca_smoothing':
        send_message('Calculating normals ...')
        normals = vtk.vtkPolyDataNormals()
        normals_ref = weakref.ref(normals)
        #  normals_ref().AddObserver("ProgressEvent", lambda obj,evt:
        #  UpdateProgress(normals_ref(), _("Creating 3D surface...")))
        normals.SetInputData(polydata)
        #  normals.ReleaseDataFlagOn()
        #normals.SetFeatureAngle(80)
        #normals.AutoOrientNormalsOn()
        normals.ComputeCellNormalsOn()
        #  normals.GetOutput().ReleaseDataFlagOn()
        normals.Update()
        del polydata
        polydata = normals.GetOutput()
        #  polydata.SetSource(None)
        del normals

        clean = vtk.vtkCleanPolyData()
        #  clean.ReleaseDataFlagOn()
        #  clean.GetOutput().ReleaseDataFlagOn()
        clean_ref = weakref.ref(clean)
        #  clean_ref().AddObserver("ProgressEvent", lambda obj,evt:
        #  UpdateProgress(clean_ref(), _("Creating 3D surface...")))
        clean.SetInputData(polydata)
        clean.PointMergingOn()
        clean.Update()

        del polydata
        polydata = clean.GetOutput()
        #  polydata.SetSource(None)
        del clean

        #  try:
        #  polydata.BuildLinks()
        #  except TypeError:
        #  polydata.BuildLinks(0)
        #  polydata = ca_smoothing.ca_smoothing(polydata, options['angle'],
        #  options['max distance'],
        #  options['min weight'],
        #  options['steps'])

        send_message('Context Aware smoothing ...')
        mesh = cy_mesh.Mesh(polydata)
        cy_mesh.ca_smoothing(mesh, options['angle'], options['max distance'],
                             options['min weight'], options['steps'])
        #  polydata = mesh.to_vtk()

        #  polydata.SetSource(None)
        #  polydata.DebugOn()
    else:
        #smoother = vtk.vtkWindowedSincPolyDataFilter()
        send_message('Smoothing ...')
        smoother = vtk.vtkSmoothPolyDataFilter()
        smoother_ref = weakref.ref(smoother)
        #  smoother_ref().AddObserver("ProgressEvent", lambda obj,evt:
        #  UpdateProgress(smoother_ref(), _("Creating 3D surface...")))
        smoother.SetInputData(polydata)
        smoother.SetNumberOfIterations(smooth_iterations)
        smoother.SetRelaxationFactor(smooth_relaxation_factor)
        smoother.SetFeatureAngle(80)
        #smoother.SetEdgeAngle(90.0)
        #smoother.SetPassBand(0.1)
        smoother.BoundarySmoothingOn()
        smoother.FeatureEdgeSmoothingOn()
        #smoother.NormalizeCoordinatesOn()
        #smoother.NonManifoldSmoothingOn()
        #  smoother.ReleaseDataFlagOn()
        #  smoother.GetOutput().ReleaseDataFlagOn()
        smoother.Update()
        del polydata
        polydata = smoother.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        del smoother

    if decimate_reduction:
        print("Decimating", decimate_reduction)
        send_message('Decimating ...')
        decimation = vtk.vtkQuadricDecimation()
        #  decimation.ReleaseDataFlagOn()
        decimation.SetInputData(polydata)
        decimation.SetTargetReduction(decimate_reduction)
        decimation_ref = weakref.ref(decimation)
        #  decimation_ref().AddObserver("ProgressEvent", lambda obj,evt:
        #  UpdateProgress(decimation_ref(), _("Creating 3D surface...")))
        #decimation.PreserveTopologyOn()
        #decimation.SplittingOff()
        #decimation.BoundaryVertexDeletionOff()
        #  decimation.GetOutput().ReleaseDataFlagOn()
        decimation.Update()
        del polydata
        polydata = decimation.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        del decimation

    #to_measure.Register(None)
    #  to_measure.SetSource(None)

    if keep_largest:
        send_message('Finding the largest ...')
        conn = vtk.vtkPolyDataConnectivityFilter()
        conn.SetInputData(polydata)
        conn.SetExtractionModeToLargestRegion()
        conn_ref = weakref.ref(conn)
        #  conn_ref().AddObserver("ProgressEvent", lambda obj,evt:
        #  UpdateProgress(conn_ref(), _("Creating 3D surface...")))
        conn.Update()
        #  conn.GetOutput().ReleaseDataFlagOn()
        del polydata
        polydata = conn.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        del conn

    #Filter used to detect and fill holes. Only fill boundary edges holes.
    #TODO: Hey! This piece of code is the same from
    #polydata_utils.FillSurfaceHole, we need to review this.
    if fill_holes:
        send_message('Filling holes ...')
        filled_polydata = vtk.vtkFillHolesFilter()
        #  filled_polydata.ReleaseDataFlagOn()
        filled_polydata.SetInputData(polydata)
        filled_polydata.SetHoleSize(300)
        filled_polydata_ref = weakref.ref(filled_polydata)
        #  filled_polydata_ref().AddObserver("ProgressEvent", lambda obj,evt:
        #  UpdateProgress(filled_polydata_ref(), _("Creating 3D surface...")))
        filled_polydata.Update()
        #  filled_polydata.GetOutput().ReleaseDataFlagOn()
        del polydata
        polydata = filled_polydata.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        #  polydata.DebugOn()
        del filled_polydata

    to_measure = polydata

    normals = vtk.vtkPolyDataNormals()
    #  normals.ReleaseDataFlagOn()
    #  normals_ref = weakref.ref(normals)
    #  normals_ref().AddObserver("ProgressEvent", lambda obj,evt:
    #  UpdateProgress(normals_ref(), _("Creating 3D surface...")))
    normals.SetInputData(polydata)
    #  normals.SetFeatureAngle(80)
    #  normals.SplittingOff()
    #  normals.AutoOrientNormalsOn()
    #  normals.GetOutput().ReleaseDataFlagOn()
    normals.Update()
    del polydata
    polydata = normals.GetOutput()
    #polydata.Register(None)
    #  polydata.SetSource(None)
    del normals

    # Improve performance
    stripper = vtk.vtkStripper()
    #  stripper.ReleaseDataFlagOn()
    #  stripper_ref = weakref.ref(stripper)
    #  stripper_ref().AddObserver("ProgressEvent", lambda obj,evt:
    #  UpdateProgress(stripper_ref(), _("Creating 3D surface...")))
    stripper.SetInputData(polydata)
    stripper.PassThroughCellIdsOn()
    stripper.PassThroughPointIdsOn()
    #  stripper.GetOutput().ReleaseDataFlagOn()
    stripper.Update()
    del polydata
    polydata = stripper.GetOutput()
    #polydata.Register(None)
    #  polydata.SetSource(None)
    del stripper

    send_message('Calculating area and volume ...')
    measured_polydata = vtk.vtkMassProperties()
    measured_polydata.SetInputData(to_measure)
    measured_polydata.Update()
    volume = float(measured_polydata.GetVolume())
    area = float(measured_polydata.GetSurfaceArea())
    del measured_polydata

    filename = tempfile.mktemp(suffix='_full.vtp')
    writer = vtk.vtkXMLPolyDataWriter()
    writer.SetInputData(polydata)
    writer.SetFileName(filename)
    writer.Write()
    del writer

    print("MY PID", os.getpid())
    return filename, {'volume': volume, 'area': area}
Esempio n. 2
0
    def AddNewActor(self, pubsub_evt):
        """
        Create surface actor, save into project and send it to viewer.
        """
        slice_, mask, surface_parameters = pubsub_evt.data
        matrix = slice_.matrix
        filename_img = slice_.matrix_filename
        spacing = slice_.spacing

        algorithm = surface_parameters['method']['algorithm']
        options = surface_parameters['method']['options']

        surface_name = surface_parameters['options']['name']
        quality = surface_parameters['options']['quality']
        fill_holes = surface_parameters['options']['fill']
        keep_largest = surface_parameters['options']['keep_largest']

        mode = 'CONTOUR' # 'GRAYSCALE'
        min_value, max_value = mask.threshold_range
        colour = mask.colour

        try:
            overwrite = surface_parameters['options']['overwrite']
        except KeyError:
            overwrite = False
        mask.matrix.flush()

        if quality in const.SURFACE_QUALITY.keys():
            imagedata_resolution = const.SURFACE_QUALITY[quality][0]
            smooth_iterations = const.SURFACE_QUALITY[quality][1]
            smooth_relaxation_factor = const.SURFACE_QUALITY[quality][2]
            decimate_reduction = const.SURFACE_QUALITY[quality][3]

        #if imagedata_resolution:
            #imagedata = iu.ResampleImage3D(imagedata, imagedata_resolution)

        pipeline_size = 4
        if decimate_reduction:
            pipeline_size += 1
        if (smooth_iterations and smooth_relaxation_factor):
            pipeline_size += 1
        if fill_holes:
            pipeline_size += 1
        if keep_largest:
            pipeline_size += 1

        ## Update progress value in GUI
        UpdateProgress = vu.ShowProgress(pipeline_size)
        UpdateProgress(0, _("Creating 3D surface..."))

        language = ses.Session().language

        if (prj.Project().original_orientation == const.CORONAL):
            flip_image = False
        else:
            flip_image = True

        n_processors = multiprocessing.cpu_count()

        pipe_in, pipe_out = multiprocessing.Pipe()
        o_piece = 1
        piece_size = 2000

        n_pieces = int(round(matrix.shape[0] / piece_size + 0.5, 0))

        q_in = multiprocessing.Queue()
        q_out = multiprocessing.Queue()

        p = []
        for i in xrange(n_processors):
            sp = surface_process.SurfaceProcess(pipe_in, filename_img,
                                                matrix.shape, matrix.dtype,
                                                mask.temp_file,
                                                mask.matrix.shape,
                                                mask.matrix.dtype,
                                                spacing,
                                                mode, min_value, max_value,
                                                decimate_reduction,
                                                smooth_relaxation_factor,
                                                smooth_iterations, language,
                                                flip_image, q_in, q_out,
                                                algorithm != 'Default',
                                                algorithm,
                                                imagedata_resolution)
            p.append(sp)
            sp.start()

        for i in xrange(n_pieces):
            init = i * piece_size
            end = init + piece_size + o_piece
            roi = slice(init, end)
            q_in.put(roi)
            print "new_piece", roi

        for i in p:
            q_in.put(None)

        none_count = 1
        while 1:
            msg = pipe_out.recv()
            if(msg is None):
                none_count += 1
            else:
                UpdateProgress(msg[0]/(n_pieces * pipeline_size), msg[1])

            if none_count > n_pieces:
                break

        polydata_append = vtk.vtkAppendPolyData()
        #  polydata_append.ReleaseDataFlagOn()
        t = n_pieces
        while t:
            filename_polydata = q_out.get()

            reader = vtk.vtkXMLPolyDataReader()
            reader.SetFileName(filename_polydata)
            #  reader.ReleaseDataFlagOn()
            reader.Update()
            #  reader.GetOutput().ReleaseDataFlagOn()

            polydata = reader.GetOutput()
            #  polydata.SetSource(None)

            polydata_append.AddInputData(polydata)
            del reader
            del polydata
            t -= 1

        polydata_append.Update()
        #  polydata_append.GetOutput().ReleaseDataFlagOn()
        polydata = polydata_append.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        del polydata_append

        if algorithm == 'ca_smoothing':
            normals = vtk.vtkPolyDataNormals()
            normals_ref = weakref.ref(normals)
            normals_ref().AddObserver("ProgressEvent", lambda obj,evt:
                                      UpdateProgress(normals_ref(), _("Creating 3D surface...")))
            normals.SetInputData(polydata)
            #  normals.ReleaseDataFlagOn()
            #normals.SetFeatureAngle(80)
            #normals.AutoOrientNormalsOn()
            normals.ComputeCellNormalsOn()
            #  normals.GetOutput().ReleaseDataFlagOn()
            normals.Update()
            del polydata
            polydata = normals.GetOutput()
            #  polydata.SetSource(None)
            del normals

            clean = vtk.vtkCleanPolyData()
            #  clean.ReleaseDataFlagOn()
            #  clean.GetOutput().ReleaseDataFlagOn()
            clean_ref = weakref.ref(clean)
            clean_ref().AddObserver("ProgressEvent", lambda obj,evt:
                            UpdateProgress(clean_ref(), _("Creating 3D surface...")))
            clean.SetInputData(polydata)
            clean.PointMergingOn()
            clean.Update()

            del polydata
            polydata = clean.GetOutput()
            #  polydata.SetSource(None)
            del clean

            #  try:
                #  polydata.BuildLinks()
            #  except TypeError:
                #  polydata.BuildLinks(0)
            #  polydata = ca_smoothing.ca_smoothing(polydata, options['angle'],
                                                 #  options['max distance'],
                                                 #  options['min weight'],
                                                 #  options['steps'])

            mesh = cy_mesh.Mesh(polydata)
            cy_mesh.ca_smoothing(mesh, options['angle'],
                                 options['max distance'],
                                 options['min weight'],
                                 options['steps'])
            #  polydata = mesh.to_vtk()

            #  polydata.SetSource(None)
            #  polydata.DebugOn()
            w = vtk.vtkPLYWriter()
            w.SetInputData(polydata)
            w.SetFileName('/tmp/ca_smoothing_inv.ply')
            w.Write()

        else:
            #smoother = vtk.vtkWindowedSincPolyDataFilter()
            smoother = vtk.vtkSmoothPolyDataFilter()
            smoother_ref = weakref.ref(smoother)
            smoother_ref().AddObserver("ProgressEvent", lambda obj,evt:
                            UpdateProgress(smoother_ref(), _("Creating 3D surface...")))
            smoother.SetInputData(polydata)
            smoother.SetNumberOfIterations(smooth_iterations)
            smoother.SetRelaxationFactor(smooth_relaxation_factor)
            smoother.SetFeatureAngle(80)
            #smoother.SetEdgeAngle(90.0)
            #smoother.SetPassBand(0.1)
            smoother.BoundarySmoothingOn()
            smoother.FeatureEdgeSmoothingOn()
            #smoother.NormalizeCoordinatesOn()
            #smoother.NonManifoldSmoothingOn()
            #  smoother.ReleaseDataFlagOn()
            #  smoother.GetOutput().ReleaseDataFlagOn()
            smoother.Update()
            del polydata
            polydata = smoother.GetOutput()
            #polydata.Register(None)
            #  polydata.SetSource(None)
            del smoother


        if decimate_reduction:
            print "Decimating", decimate_reduction
            decimation = vtk.vtkQuadricDecimation()
            #  decimation.ReleaseDataFlagOn()
            decimation.SetInputData(polydata)
            decimation.SetTargetReduction(decimate_reduction)
            decimation_ref = weakref.ref(decimation)
            decimation_ref().AddObserver("ProgressEvent", lambda obj,evt:
                            UpdateProgress(decimation_ref(), _("Creating 3D surface...")))
            #decimation.PreserveTopologyOn()
            #decimation.SplittingOff()
            #decimation.BoundaryVertexDeletionOff()
            #  decimation.GetOutput().ReleaseDataFlagOn()
            decimation.Update()
            del polydata
            polydata = decimation.GetOutput()
            #polydata.Register(None)
            #  polydata.SetSource(None)
            del decimation

        to_measure = polydata
        #to_measure.Register(None)
        #  to_measure.SetSource(None)

        if keep_largest:
            conn = vtk.vtkPolyDataConnectivityFilter()
            conn.SetInputData(polydata)
            conn.SetExtractionModeToLargestRegion()
            conn_ref = weakref.ref(conn)
            conn_ref().AddObserver("ProgressEvent", lambda obj,evt:
                    UpdateProgress(conn_ref(), _("Creating 3D surface...")))
            conn.Update()
            #  conn.GetOutput().ReleaseDataFlagOn()
            del polydata
            polydata = conn.GetOutput()
            #polydata.Register(None)
            #  polydata.SetSource(None)
            del conn

        #Filter used to detect and fill holes. Only fill boundary edges holes.
        #TODO: Hey! This piece of code is the same from
        #polydata_utils.FillSurfaceHole, we need to review this.
        if fill_holes:
            filled_polydata = vtk.vtkFillHolesFilter()
            #  filled_polydata.ReleaseDataFlagOn()
            filled_polydata.SetInputData(polydata)
            filled_polydata.SetHoleSize(300)
            filled_polydata_ref = weakref.ref(filled_polydata)
            filled_polydata_ref().AddObserver("ProgressEvent", lambda obj,evt:
                    UpdateProgress(filled_polydata_ref(), _("Creating 3D surface...")))
            filled_polydata.Update()
            #  filled_polydata.GetOutput().ReleaseDataFlagOn()
            del polydata
            polydata = filled_polydata.GetOutput()
            #polydata.Register(None)
            #  polydata.SetSource(None)
            #  polydata.DebugOn()
            del filled_polydata

        normals = vtk.vtkPolyDataNormals()
        #  normals.ReleaseDataFlagOn()
        normals_ref = weakref.ref(normals)
        normals_ref().AddObserver("ProgressEvent", lambda obj,evt:
                        UpdateProgress(normals_ref(), _("Creating 3D surface...")))
        normals.SetInputData(polydata)
        normals.SetFeatureAngle(80)
        normals.AutoOrientNormalsOn()
        #  normals.GetOutput().ReleaseDataFlagOn()
        normals.Update()
        del polydata
        polydata = normals.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        del normals

        # Improve performance
        stripper = vtk.vtkStripper()
        #  stripper.ReleaseDataFlagOn()
        stripper_ref = weakref.ref(stripper)
        stripper_ref().AddObserver("ProgressEvent", lambda obj,evt:
                        UpdateProgress(stripper_ref(), _("Creating 3D surface...")))
        stripper.SetInputData(polydata)
        stripper.PassThroughCellIdsOn()
        stripper.PassThroughPointIdsOn()
        #  stripper.GetOutput().ReleaseDataFlagOn()
        stripper.Update()
        del polydata
        polydata = stripper.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        del stripper

        # Map polygonal data (vtkPolyData) to graphics primitives.
        mapper = vtk.vtkPolyDataMapper()
        mapper.SetInputData(polydata)
        mapper.ScalarVisibilityOff()
        #  mapper.ReleaseDataFlagOn()
        mapper.ImmediateModeRenderingOn() # improve performance

        # Represent an object (geometry & properties) in the rendered scene
        actor = vtk.vtkActor()
        actor.SetMapper(mapper)
        del mapper
        #Create Surface instance
        if overwrite:
            surface = Surface(index = self.last_surface_index)
        else:
            surface = Surface(name=surface_name)
        surface.colour = colour
        surface.polydata = polydata
        del polydata

        # Set actor colour and transparency
        actor.GetProperty().SetColor(colour)
        actor.GetProperty().SetOpacity(1-surface.transparency)

        prop = actor.GetProperty()

        interpolation = int(ses.Session().surface_interpolation)

        prop.SetInterpolation(interpolation)

        proj = prj.Project()
        if overwrite:
            proj.ChangeSurface(surface)
        else:
            index = proj.AddSurface(surface)
            surface.index = index
            self.last_surface_index = index

        session = ses.Session()
        session.ChangeProject()

        # The following lines have to be here, otherwise all volumes disappear
        measured_polydata = vtk.vtkMassProperties()
        #  measured_polydata.ReleaseDataFlagOn()
        measured_polydata.SetInputData(to_measure)
        volume =  float(measured_polydata.GetVolume())
        area =  float(measured_polydata.GetSurfaceArea())
        surface.volume = volume
        surface.area = area
        self.last_surface_index = surface.index
        del measured_polydata
        del to_measure

        Publisher.sendMessage('Load surface actor into viewer', actor)

        # Send actor by pubsub to viewer's render
        if overwrite and self.actors_dict.keys():
            old_actor = self.actors_dict[self.last_surface_index]
            Publisher.sendMessage('Remove surface actor from viewer', old_actor)

        # Save actor for future management tasks
        self.actors_dict[surface.index] = actor

        Publisher.sendMessage('Update surface info in GUI',
                                    (surface.index, surface.name,
                                    surface.colour, surface.volume,
                                    surface.area,
                                    surface.transparency))

        #When you finalize the progress. The bar is cleaned.
        UpdateProgress = vu.ShowProgress(1)
        UpdateProgress(0, _("Ready"))
        Publisher.sendMessage('Update status text in GUI', _("Ready"))

        Publisher.sendMessage('End busy cursor')
        del actor
Esempio n. 3
0
    def AddNewActor(self, slice_, mask, surface_parameters):
        """
        Create surface actor, save into project and send it to viewer.
        """
        matrix = slice_.matrix
        filename_img = slice_.matrix_filename
        spacing = slice_.spacing

        algorithm = surface_parameters['method']['algorithm']
        options = surface_parameters['method']['options']

        surface_name = surface_parameters['options']['name']
        quality = surface_parameters['options']['quality']
        fill_holes = surface_parameters['options']['fill']
        keep_largest = surface_parameters['options']['keep_largest']

        mode = 'CONTOUR'  # 'GRAYSCALE'
        min_value, max_value = mask.threshold_range
        colour = mask.colour[:3]

        try:
            overwrite = surface_parameters['options']['overwrite']
        except KeyError:
            overwrite = False
        mask.matrix.flush()

        if quality in const.SURFACE_QUALITY.keys():
            imagedata_resolution = const.SURFACE_QUALITY[quality][0]
            smooth_iterations = const.SURFACE_QUALITY[quality][1]
            smooth_relaxation_factor = const.SURFACE_QUALITY[quality][2]
            decimate_reduction = const.SURFACE_QUALITY[quality][3]

        #if imagedata_resolution:
        #imagedata = iu.ResampleImage3D(imagedata, imagedata_resolution)

        pipeline_size = 4
        if decimate_reduction:
            pipeline_size += 1
        if (smooth_iterations and smooth_relaxation_factor):
            pipeline_size += 1
        if fill_holes:
            pipeline_size += 1
        if keep_largest:
            pipeline_size += 1

        ## Update progress value in GUI
        UpdateProgress = vu.ShowProgress(pipeline_size)
        UpdateProgress(0, _("Creating 3D surface..."))

        language = ses.Session().language

        if (prj.Project().original_orientation == const.CORONAL):
            flip_image = False
        else:
            flip_image = True

        n_processors = multiprocessing.cpu_count()

        pipe_in, pipe_out = multiprocessing.Pipe()
        o_piece = 1
        piece_size = 2000

        n_pieces = int(round(matrix.shape[0] / piece_size + 0.5, 0))

        q_in = multiprocessing.Queue()
        q_out = multiprocessing.Queue()

        p = []
        for i in range(n_processors):
            sp = surface_process.SurfaceProcess(
                pipe_in, filename_img, matrix.shape, matrix.dtype,
                mask.temp_file, mask.matrix.shape, mask.matrix.dtype, spacing,
                mode, min_value, max_value, decimate_reduction,
                smooth_relaxation_factor, smooth_iterations, language,
                flip_image, q_in, q_out, algorithm != 'Default', algorithm,
                imagedata_resolution)
            p.append(sp)
            sp.start()

        for i in range(n_pieces):
            init = i * piece_size
            end = init + piece_size + o_piece
            roi = slice(init, end)
            q_in.put(roi)
            print("new_piece", roi)

        for i in p:
            q_in.put(None)

        none_count = 1
        while 1:
            msg = pipe_out.recv()
            if (msg is None):
                none_count += 1
            else:
                UpdateProgress(msg[0] / (n_pieces * pipeline_size), msg[1])

            if none_count > n_pieces:
                break

        polydata_append = vtk.vtkAppendPolyData()
        #  polydata_append.ReleaseDataFlagOn()
        t = n_pieces
        while t:
            filename_polydata = q_out.get()

            reader = vtk.vtkXMLPolyDataReader()
            reader.SetFileName(filename_polydata)
            #  reader.ReleaseDataFlagOn()
            reader.Update()
            #  reader.GetOutput().ReleaseDataFlagOn()

            polydata = reader.GetOutput()
            #  polydata.SetSource(None)

            polydata_append.AddInputData(polydata)
            del reader
            del polydata
            t -= 1

        polydata_append.Update()
        #  polydata_append.GetOutput().ReleaseDataFlagOn()
        polydata = polydata_append.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        del polydata_append

        if algorithm == 'ca_smoothing':
            normals = vtk.vtkPolyDataNormals()
            normals_ref = weakref.ref(normals)
            normals_ref().AddObserver(
                "ProgressEvent", lambda obj, evt: UpdateProgress(
                    normals_ref(), _("Creating 3D surface...")))
            normals.SetInputData(polydata)
            #  normals.ReleaseDataFlagOn()
            #normals.SetFeatureAngle(80)
            #normals.AutoOrientNormalsOn()
            normals.ComputeCellNormalsOn()
            #  normals.GetOutput().ReleaseDataFlagOn()
            normals.Update()
            del polydata
            polydata = normals.GetOutput()
            #  polydata.SetSource(None)
            del normals

            clean = vtk.vtkCleanPolyData()
            #  clean.ReleaseDataFlagOn()
            #  clean.GetOutput().ReleaseDataFlagOn()
            clean_ref = weakref.ref(clean)
            clean_ref().AddObserver(
                "ProgressEvent", lambda obj, evt: UpdateProgress(
                    clean_ref(), _("Creating 3D surface...")))
            clean.SetInputData(polydata)
            clean.PointMergingOn()
            clean.Update()

            del polydata
            polydata = clean.GetOutput()
            #  polydata.SetSource(None)
            del clean

            #  try:
            #  polydata.BuildLinks()
            #  except TypeError:
            #  polydata.BuildLinks(0)
            #  polydata = ca_smoothing.ca_smoothing(polydata, options['angle'],
            #  options['max distance'],
            #  options['min weight'],
            #  options['steps'])

            mesh = cy_mesh.Mesh(polydata)
            cy_mesh.ca_smoothing(mesh, options['angle'],
                                 options['max distance'],
                                 options['min weight'], options['steps'])
            #  polydata = mesh.to_vtk()

            #  polydata.SetSource(None)
            #  polydata.DebugOn()
        else:
            #smoother = vtk.vtkWindowedSincPolyDataFilter()
            smoother = vtk.vtkSmoothPolyDataFilter()
            smoother_ref = weakref.ref(smoother)
            smoother_ref().AddObserver(
                "ProgressEvent", lambda obj, evt: UpdateProgress(
                    smoother_ref(), _("Creating 3D surface...")))
            smoother.SetInputData(polydata)
            smoother.SetNumberOfIterations(smooth_iterations)
            smoother.SetRelaxationFactor(smooth_relaxation_factor)
            smoother.SetFeatureAngle(80)
            #smoother.SetEdgeAngle(90.0)
            #smoother.SetPassBand(0.1)
            smoother.BoundarySmoothingOn()
            smoother.FeatureEdgeSmoothingOn()
            #smoother.NormalizeCoordinatesOn()
            #smoother.NonManifoldSmoothingOn()
            #  smoother.ReleaseDataFlagOn()
            #  smoother.GetOutput().ReleaseDataFlagOn()
            smoother.Update()
            del polydata
            polydata = smoother.GetOutput()
            #polydata.Register(None)
            #  polydata.SetSource(None)
            del smoother

        if decimate_reduction:
            print("Decimating", decimate_reduction)
            decimation = vtk.vtkQuadricDecimation()
            #  decimation.ReleaseDataFlagOn()
            decimation.SetInputData(polydata)
            decimation.SetTargetReduction(decimate_reduction)
            decimation_ref = weakref.ref(decimation)
            decimation_ref().AddObserver(
                "ProgressEvent", lambda obj, evt: UpdateProgress(
                    decimation_ref(), _("Creating 3D surface...")))
            #decimation.PreserveTopologyOn()
            #decimation.SplittingOff()
            #decimation.BoundaryVertexDeletionOff()
            #  decimation.GetOutput().ReleaseDataFlagOn()
            decimation.Update()
            del polydata
            polydata = decimation.GetOutput()
            #polydata.Register(None)
            #  polydata.SetSource(None)
            del decimation

        #to_measure.Register(None)
        #  to_measure.SetSource(None)

        if keep_largest:
            conn = vtk.vtkPolyDataConnectivityFilter()
            conn.SetInputData(polydata)
            conn.SetExtractionModeToLargestRegion()
            conn_ref = weakref.ref(conn)
            conn_ref().AddObserver(
                "ProgressEvent", lambda obj, evt: UpdateProgress(
                    conn_ref(), _("Creating 3D surface...")))
            conn.Update()
            #  conn.GetOutput().ReleaseDataFlagOn()
            del polydata
            polydata = conn.GetOutput()
            #polydata.Register(None)
            #  polydata.SetSource(None)
            del conn

        #Filter used to detect and fill holes. Only fill boundary edges holes.
        #TODO: Hey! This piece of code is the same from
        #polydata_utils.FillSurfaceHole, we need to review this.
        if fill_holes:
            filled_polydata = vtk.vtkFillHolesFilter()
            #  filled_polydata.ReleaseDataFlagOn()
            filled_polydata.SetInputData(polydata)
            filled_polydata.SetHoleSize(300)
            filled_polydata_ref = weakref.ref(filled_polydata)
            filled_polydata_ref().AddObserver(
                "ProgressEvent", lambda obj, evt: UpdateProgress(
                    filled_polydata_ref(), _("Creating 3D surface...")))
            filled_polydata.Update()
            #  filled_polydata.GetOutput().ReleaseDataFlagOn()
            del polydata
            polydata = filled_polydata.GetOutput()
            #polydata.Register(None)
            #  polydata.SetSource(None)
            #  polydata.DebugOn()
            del filled_polydata

        to_measure = polydata

        # If InVesalius is running without GUI
        if wx.GetApp() is None:
            proj = prj.Project()
            #Create Surface instance
            if overwrite:
                surface = Surface(index=self.last_surface_index)
                proj.ChangeSurface(surface)
            else:
                surface = Surface(name=surface_name)
                index = proj.AddSurface(surface)
                surface.index = index
                self.last_surface_index = index
            surface.colour = colour
            surface.polydata = polydata

        # With GUI
        else:
            normals = vtk.vtkPolyDataNormals()
            #  normals.ReleaseDataFlagOn()
            normals_ref = weakref.ref(normals)
            normals_ref().AddObserver(
                "ProgressEvent", lambda obj, evt: UpdateProgress(
                    normals_ref(), _("Creating 3D surface...")))
            normals.SetInputData(polydata)
            normals.SetFeatureAngle(80)
            normals.AutoOrientNormalsOn()
            #  normals.GetOutput().ReleaseDataFlagOn()
            normals.Update()
            del polydata
            polydata = normals.GetOutput()
            #polydata.Register(None)
            #  polydata.SetSource(None)
            del normals

            # Improve performance
            stripper = vtk.vtkStripper()
            #  stripper.ReleaseDataFlagOn()
            stripper_ref = weakref.ref(stripper)
            stripper_ref().AddObserver(
                "ProgressEvent", lambda obj, evt: UpdateProgress(
                    stripper_ref(), _("Creating 3D surface...")))
            stripper.SetInputData(polydata)
            stripper.PassThroughCellIdsOn()
            stripper.PassThroughPointIdsOn()
            #  stripper.GetOutput().ReleaseDataFlagOn()
            stripper.Update()
            del polydata
            polydata = stripper.GetOutput()
            #polydata.Register(None)
            #  polydata.SetSource(None)
            del stripper

            # Map polygonal data (vtkPolyData) to graphics primitives.
            mapper = vtk.vtkPolyDataMapper()
            mapper.SetInputData(polydata)
            mapper.ScalarVisibilityOff()
            #  mapper.ReleaseDataFlagOn()
            mapper.ImmediateModeRenderingOn()  # improve performance

            # Represent an object (geometry & properties) in the rendered scene
            actor = vtk.vtkActor()
            actor.SetMapper(mapper)
            del mapper
            #Create Surface instance
            if overwrite:
                surface = Surface(index=self.last_surface_index)
            else:
                surface = Surface(name=surface_name)
            surface.colour = colour
            surface.polydata = polydata
            del polydata

            # Set actor colour and transparency
            actor.GetProperty().SetColor(colour)
            actor.GetProperty().SetOpacity(1 - surface.transparency)

            prop = actor.GetProperty()

            interpolation = int(ses.Session().surface_interpolation)

            prop.SetInterpolation(interpolation)

            proj = prj.Project()
            if overwrite:
                proj.ChangeSurface(surface)
            else:
                index = proj.AddSurface(surface)
                surface.index = index
                self.last_surface_index = index

            session = ses.Session()
            session.ChangeProject()

            measured_polydata = vtk.vtkMassProperties()
            #  measured_polydata.ReleaseDataFlagOn()
            measured_polydata.SetInputData(to_measure)
            volume = float(measured_polydata.GetVolume())
            area = float(measured_polydata.GetSurfaceArea())
            surface.volume = volume
            surface.area = area
            self.last_surface_index = surface.index
            del measured_polydata
            del to_measure

            Publisher.sendMessage('Load surface actor into viewer',
                                  actor=actor)

            # Send actor by pubsub to viewer's render
            if overwrite and self.actors_dict.keys():
                old_actor = self.actors_dict[self.last_surface_index]
                Publisher.sendMessage('Remove surface actor from viewer',
                                      actor=old_actor)

            # Save actor for future management tasks
            self.actors_dict[surface.index] = actor

            Publisher.sendMessage('Update surface info in GUI',
                                  surface=surface)

            #When you finalize the progress. The bar is cleaned.
            UpdateProgress = vu.ShowProgress(1)
            UpdateProgress(0, _("Ready"))
            Publisher.sendMessage('Update status text in GUI',
                                  label=_("Ready"))

            Publisher.sendMessage('End busy cursor')
            del actor
Esempio n. 4
0
def join_process_surface(filenames, algorithm, smooth_iterations, smooth_relaxation_factor, decimate_reduction, keep_largest, fill_holes, options, msg_queue):
    def send_message(msg):
        try:
            msg_queue.put_nowait(msg)
        except queue.Full as e:
            print(e)

    log_path = tempfile.mktemp('vtkoutput.txt')
    fow = vtk.vtkFileOutputWindow()
    fow.SetFileName(log_path)
    ow = vtk.vtkOutputWindow()
    ow.SetInstance(fow)

    send_message('Joining surfaces ...')
    polydata_append = vtk.vtkAppendPolyData()
    for f in filenames:
        reader = vtk.vtkXMLPolyDataReader()
        reader.SetFileName(f)
        reader.Update()

        polydata = reader.GetOutput()

        polydata_append.AddInputData(polydata)
        del reader
        del polydata

    polydata_append.Update()
    #  polydata_append.GetOutput().ReleaseDataFlagOn()
    polydata = polydata_append.GetOutput()
    #polydata.Register(None)
    #  polydata.SetSource(None)
    del polydata_append

    send_message('Cleaning surface ...')
    clean = vtk.vtkCleanPolyData()
    #  clean.ReleaseDataFlagOn()
    #  clean.GetOutput().ReleaseDataFlagOn()
    clean_ref = weakref.ref(clean)
    #  clean_ref().AddObserver("ProgressEvent", lambda obj,evt:
                    #  UpdateProgress(clean_ref(), _("Creating 3D surface...")))
    clean.SetInputData(polydata)
    clean.PointMergingOn()
    clean.Update()

    del polydata
    polydata = clean.GetOutput()
    #  polydata.SetSource(None)
    del clean

    if algorithm == 'ca_smoothing':
        send_message('Calculating normals ...')
        normals = vtk.vtkPolyDataNormals()
        normals_ref = weakref.ref(normals)
        #  normals_ref().AddObserver("ProgressEvent", lambda obj,evt:
                                  #  UpdateProgress(normals_ref(), _("Creating 3D surface...")))
        normals.SetInputData(polydata)
        #  normals.ReleaseDataFlagOn()
        #normals.SetFeatureAngle(80)
        #normals.AutoOrientNormalsOn()
        normals.ComputeCellNormalsOn()
        #  normals.GetOutput().ReleaseDataFlagOn()
        normals.Update()
        del polydata
        polydata = normals.GetOutput()
        #  polydata.SetSource(None)
        del normals

        clean = vtk.vtkCleanPolyData()
        #  clean.ReleaseDataFlagOn()
        #  clean.GetOutput().ReleaseDataFlagOn()
        clean_ref = weakref.ref(clean)
        #  clean_ref().AddObserver("ProgressEvent", lambda obj,evt:
                        #  UpdateProgress(clean_ref(), _("Creating 3D surface...")))
        clean.SetInputData(polydata)
        clean.PointMergingOn()
        clean.Update()

        del polydata
        polydata = clean.GetOutput()
        #  polydata.SetSource(None)
        del clean

        #  try:
            #  polydata.BuildLinks()
        #  except TypeError:
            #  polydata.BuildLinks(0)
        #  polydata = ca_smoothing.ca_smoothing(polydata, options['angle'],
                                             #  options['max distance'],
                                             #  options['min weight'],
                                             #  options['steps'])

        send_message('Context Aware smoothing ...')
        mesh = cy_mesh.Mesh(polydata)
        cy_mesh.ca_smoothing(mesh, options['angle'],
                             options['max distance'],
                             options['min weight'],
                             options['steps'])
        #  polydata = mesh.to_vtk()

        #  polydata.SetSource(None)
        #  polydata.DebugOn()
    #  else:
        #  #smoother = vtk.vtkWindowedSincPolyDataFilter()
        #  send_message('Smoothing ...')
        #  smoother = vtk.vtkSmoothPolyDataFilter()
        #  smoother_ref = weakref.ref(smoother)
        #  #  smoother_ref().AddObserver("ProgressEvent", lambda obj,evt:
                        #  #  UpdateProgress(smoother_ref(), _("Creating 3D surface...")))
        #  smoother.SetInputData(polydata)
        #  smoother.SetNumberOfIterations(smooth_iterations)
        #  smoother.SetRelaxationFactor(smooth_relaxation_factor)
        #  smoother.SetFeatureAngle(80)
        #  #smoother.SetEdgeAngle(90.0)
        #  #smoother.SetPassBand(0.1)
        #  smoother.BoundarySmoothingOn()
        #  smoother.FeatureEdgeSmoothingOn()
        #  #smoother.NormalizeCoordinatesOn()
        #  #smoother.NonManifoldSmoothingOn()
        #  #  smoother.ReleaseDataFlagOn()
        #  #  smoother.GetOutput().ReleaseDataFlagOn()
        #  smoother.Update()
        #  del polydata
        #  polydata = smoother.GetOutput()
        #  #polydata.Register(None)
        #  #  polydata.SetSource(None)
        #  del smoother


    if not decimate_reduction:
        print("Decimating", decimate_reduction)
        send_message('Decimating ...')
        decimation = vtk.vtkQuadricDecimation()
        #  decimation.ReleaseDataFlagOn()
        decimation.SetInputData(polydata)
        decimation.SetTargetReduction(decimate_reduction)
        decimation_ref = weakref.ref(decimation)
        #  decimation_ref().AddObserver("ProgressEvent", lambda obj,evt:
                        #  UpdateProgress(decimation_ref(), _("Creating 3D surface...")))
        #decimation.PreserveTopologyOn()
        #decimation.SplittingOff()
        #decimation.BoundaryVertexDeletionOff()
        #  decimation.GetOutput().ReleaseDataFlagOn()
        decimation.Update()
        del polydata
        polydata = decimation.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        del decimation

    #to_measure.Register(None)
    #  to_measure.SetSource(None)

    if keep_largest:
        send_message('Finding the largest ...')
        conn = vtk.vtkPolyDataConnectivityFilter()
        conn.SetInputData(polydata)
        conn.SetExtractionModeToLargestRegion()
        conn_ref = weakref.ref(conn)
        #  conn_ref().AddObserver("ProgressEvent", lambda obj,evt:
                #  UpdateProgress(conn_ref(), _("Creating 3D surface...")))
        conn.Update()
        #  conn.GetOutput().ReleaseDataFlagOn()
        del polydata
        polydata = conn.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        del conn

    #Filter used to detect and fill holes. Only fill boundary edges holes.
    #TODO: Hey! This piece of code is the same from
    #polydata_utils.FillSurfaceHole, we need to review this.
    if fill_holes:
        send_message('Filling holes ...')
        filled_polydata = vtk.vtkFillHolesFilter()
        #  filled_polydata.ReleaseDataFlagOn()
        filled_polydata.SetInputData(polydata)
        filled_polydata.SetHoleSize(300)
        filled_polydata_ref = weakref.ref(filled_polydata)
        #  filled_polydata_ref().AddObserver("ProgressEvent", lambda obj,evt:
                #  UpdateProgress(filled_polydata_ref(), _("Creating 3D surface...")))
        filled_polydata.Update()
        #  filled_polydata.GetOutput().ReleaseDataFlagOn()
        del polydata
        polydata = filled_polydata.GetOutput()
        #polydata.Register(None)
        #  polydata.SetSource(None)
        #  polydata.DebugOn()
        del filled_polydata

    to_measure = polydata

    normals = vtk.vtkPolyDataNormals()
    #  normals.ReleaseDataFlagOn()
    #  normals_ref = weakref.ref(normals)
    #  normals_ref().AddObserver("ProgressEvent", lambda obj,evt:
                    #  UpdateProgress(normals_ref(), _("Creating 3D surface...")))
    normals.SetInputData(polydata)
    normals.SetFeatureAngle(80)
    normals.SplittingOn()
    normals.AutoOrientNormalsOn()
    normals.NonManifoldTraversalOn()
    normals.ComputeCellNormalsOn()
    #  normals.GetOutput().ReleaseDataFlagOn()
    normals.Update()
    del polydata
    polydata = normals.GetOutput()
    #polydata.Register(None)
    #  polydata.SetSource(None)
    del normals


    #  # Improve performance
    #  stripper = vtk.vtkStripper()
    #  #  stripper.ReleaseDataFlagOn()
    #  #  stripper_ref = weakref.ref(stripper)
    #  #  stripper_ref().AddObserver("ProgressEvent", lambda obj,evt:
                    #  #  UpdateProgress(stripper_ref(), _("Creating 3D surface...")))
    #  stripper.SetInputData(polydata)
    #  stripper.PassThroughCellIdsOn()
    #  stripper.PassThroughPointIdsOn()
    #  #  stripper.GetOutput().ReleaseDataFlagOn()
    #  stripper.Update()
    #  del polydata
    #  polydata = stripper.GetOutput()
    #  #polydata.Register(None)
    #  #  polydata.SetSource(None)
    #  del stripper

    send_message('Calculating area and volume ...')
    measured_polydata = vtk.vtkMassProperties()
    measured_polydata.SetInputData(to_measure)
    measured_polydata.Update()
    volume =  float(measured_polydata.GetVolume())
    area =  float(measured_polydata.GetSurfaceArea())
    del measured_polydata

    filename = tempfile.mktemp(suffix='_full.vtp')
    writer = vtk.vtkXMLPolyDataWriter()
    writer.SetInputData(polydata)
    writer.SetFileName(filename)
    writer.Write()
    del writer

    print("MY PID", os.getpid())
    return filename, {'volume': volume, 'area': area}