Пример #1
0
 def run(self, iterations):
     self.fn = getFilterFile(self.fd, self.pg, iterations, self.rg, self.osz)
     if os.path.exists(self.fn):
         flt = np.load(self.fn)
         self.v[:] = self.customFBP(flt)
         return
     nd = self.nd
     if self.osz:
         nds = self.osz
     else:
         nds = nd
     na = len(self.ang)
     pgc = astra.create_proj_geom('parallel',1.0,nd,self.ang)
     vgc = astra.create_vol_geom((nds,nds))
     pidc = astra.create_projector('strip',pgc,vgc)
     x = np.zeros((nds,nds))
     xs = np.zeros((nds,nds))
     sf = np.zeros((na,nd))
     vid = astra.data2d.create('-vol',vgc)
     sid = astra.data2d.create('-sino',pgc)
     cfg = astra.astra_dict('FP')
     cfg['ProjectorId']=pidc
     cfg['ProjectionDataId']=sid
     cfg['VolumeDataId']=vid
     fpid = astra.algorithm.create(cfg)
     cfg = astra.astra_dict('BP')
     cfg['ProjectorId']=pidc
     cfg['ProjectionDataId']=sid
     cfg['ReconstructionDataId']=vid
     bpid = astra.algorithm.create(cfg)
     vc = astra.data2d.get_shared(vid)
     sc = astra.data2d.get_shared(sid)
     x[nds//2,nds//2]=1
     alp = 1./(na*nds)
     if self.rg:
         if self.rg*alp >=0.1:
             alp = 0.1/self.rg
     astra.log.info('Computing filter...')
     for i in range(iterations):
         if i%10==0: astra.log.info('{:.2f} % done'.format(100*float(i)/iterations))
         xs+=x
         vc[:] = x
         astra.algorithm.run(fpid)
         astra.algorithm.run(bpid)
         if self.rg:
             dx = x[:-1,:] - x[1:,:]
             dy = x[:,:-1] - x[:,1:]
             x[:-1,:] -= self.rg*dx*alp
             x[1:,:] += self.rg*dx*alp
             x[:,:-1] -= self.rg*dy*alp
             x[:,1:] += self.rg*dy*alp
         x -= vc*alp
     vc[:] = xs
     astra.algorithm.run(fpid)
     flt = sc.copy()*alp
     astra.algorithm.delete([fpid,bpid])
     astra.algorithm.delete([vid,sid])
     np.save(self.fn,flt)
     self.v[:] = self.customFBP(flt)
     astra.projector.delete(pidc)
Пример #2
0
    def cgls2D(self, sinogram, iterations):
        """perform CGLS reconstruction"""
        rec_id = astra.data2d.create('-vol', self.vol_geom)
        # Create a data object to hold the sinogram data
        sinogram_id = astra.data2d.create('-sino', self.proj_geom, sinogram)

        if self.device == 1:
            cfg = astra.astra_dict('CGLS')
            cfg['ProjectorId'] = self.proj_id
        else:
            cfg = astra.astra_dict('CGLS_CUDA')
        cfg['ReconstructionDataId'] = rec_id
        cfg['ProjectionDataId'] = sinogram_id

        # Create and run the algorithm object from the configuration structure
        alg_id = astra.algorithm.create(cfg)
        astra.algorithm.run(alg_id, iterations)
        # Get the result
        recCGLS = astra.data2d.get(rec_id)

        astra.algorithm.delete(alg_id)
        astra.data2d.delete(rec_id)
        astra.data2d.delete(sinogram_id)
        astra.data2d.delete(self.proj_id)
        return recCGLS
Пример #3
0
 def init(self, volume_data=1, projection_data=1):
     # Create volume geometry
     self.volume_geom = astra.create_vol_geom(self.num_voxel)
 
     # Create projection geometry
     self.projection_geom = astra.create_proj_geom(self.geometry_type,
                                        self.detector_spacing_x, self.detector_spacing_y,
                                        self.det_row_count, self.det_col_count,
                                        self.angles,
                                        self.source_origin, self.origin_detector)
 
     # Allocate and store volume data in ASTRA memory
     self.volume_id = astra.data3d.create('-vol', self.volume_geom, volume_data)
 
     # Allocate and store projection data in ASTRA memeory
     self.projection_id = astra.data3d.create('-sino', self.projection_geom, projection_data)
     
     # Create algorithm object: forward projector
     cfg = astra.astra_dict('FP3D_CUDA')
     cfg['option'] = {'GPUindex': self.gpu_index}
     cfg['ProjectionDataId'] = self.projection_id
     cfg['VolumeDataId'] = self.volume_id
     self.forward_alg_id = astra.algorithm.create(cfg)
     
     # Create algorithm object: backward projector
     cfg = astra.astra_dict('BP3D_CUDA')
     cfg['option'] = {'GPUindex': self.gpu_index}
     cfg['ProjectionDataId'] = self.projection_id
     cfg['ReconstructionDataId'] = self.volume_id
     self.backward_alg_id = astra.algorithm.create(cfg)
Пример #4
0
def astrarecon(tilt_data,tilt_angles,iterations=1,geometry='parallel3d',SO_dist=1.0,OD_dist=1.0):
    proj_shape = np.shape(tilt_data)
    recon_shape = (proj_shape[2],proj_shape[2],proj_shape[1])
    
    vol_geom = astra.create_vol_geom(recon_shape)

    angles = np.pi*tilt_angles/180
    
    if geometry == 'parallel3d':
        proj_geom = astra.create_proj_geom(geometry, 1.0, 1.0, proj_shape[1], proj_shape[2], angles)
        cfg = astra.astra_dict('SIRT3D_CUDA')
    elif geometry == 'cone':
        proj_geom = astra.create_proj_geom(geometry, 1.0, 1.0, proj_shape[1], proj_shape[2], angles, SO_dist, OD_dist)
        cfg = astra.astra_dict('FDK_CUDA')
        
    proj_id = astra.data3d.create('-proj3d', proj_geom, np.swapaxes(tilt_data,0,1))
    
    rec_id = astra.data3d.create('-vol', vol_geom)
    
    cfg['ReconstructionDataId'] = rec_id
    cfg['ProjectionDataId'] = proj_id
    
    alg_id = astra.algorithm.create(cfg)
    
    astra.algorithm.run(alg_id, iterations)
    
    rec = astra.data3d.get(rec_id)
    
    astra.algorithm.delete(alg_id)
    astra.data3d.delete(rec_id)
    astra.data3d.delete(proj_id)
    
    return(rec)
Пример #5
0
    def fbp2D(self, sinogram):
        """perform FBP reconstruction"""
        rec_id = astra.data2d.create('-vol', self.vol_geom)
        # Create a data object to hold the sinogram data
        sinogram_id = astra.data2d.create('-sino', self.proj_geom, sinogram)

        if self.device == 1:
            cfg = astra.astra_dict('FBP')
            cfg['ProjectorId'] = self.proj_id
        else:
            cfg = astra.astra_dict('FBP_CUDA')
        cfg['ReconstructionDataId'] = rec_id
        cfg['ProjectionDataId'] = sinogram_id
        cfg['FilterType'] = 'Ram-Lak'

        # Create and run the algorithm object from the configuration structure
        alg_id = astra.algorithm.create(cfg)
        astra.algorithm.run(alg_id)
        # Get the result
        recFBP = astra.data2d.get(rec_id)

        astra.algorithm.delete(alg_id)
        astra.data2d.delete(rec_id)
        astra.data2d.delete(sinogram_id)
        astra.data2d.delete(self.proj_id)
        return recFBP
Пример #6
0
    def init(self, volume_data=1, projection_data=1):
        # Create volume geometry
        self.volume_geom = astra.create_vol_geom(self.num_voxel)

        # Create projection geometry
        self.projection_geom = astra.create_proj_geom(
            self.geometry_type, self.detector_spacing_x,
            self.detector_spacing_y, self.det_row_count, self.det_col_count,
            self.angles, self.source_origin, self.origin_detector)

        # Allocate and store volume data in ASTRA memory
        self.volume_id = astra.data3d.create('-vol', self.volume_geom,
                                             volume_data)

        # Allocate and store projection data in ASTRA memeory
        self.projection_id = astra.data3d.create('-sino', self.projection_geom,
                                                 projection_data)

        # Create algorithm object: forward projector
        cfg = astra.astra_dict('FP3D_CUDA')
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.projection_id
        cfg['VolumeDataId'] = self.volume_id
        self.forward_alg_id = astra.algorithm.create(cfg)

        # Create algorithm object: backward projector
        cfg = astra.astra_dict('BP3D_CUDA')
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.projection_id
        cfg['ReconstructionDataId'] = self.volume_id
        self.backward_alg_id = astra.algorithm.create(cfg)
Пример #7
0
    def __init__(self, geometry_type='cone',
                 num_voxel=(100, 100, 100),
                 det_row_count=100, det_col_count=100,
                 angles=np.linspace(0, 2 * np.pi, 180, endpoint=False),
                 det_col_spacing=1.0, det_row_spacing=1.0,
                 source_origin=100.0, origin_detector=10.0,
                 volume_data=1, projection_data=1,
                 gpu_index=0):
        self.geometry_type = geometry_type
        self.num_voxel = num_voxel
        self.detector_spacing_x = det_col_spacing
        self.detector_spacing_y = det_row_spacing
        self.det_row_count = det_row_count
        self.det_col_count = det_col_count
        self.angles = angles
        self.source_origin = source_origin
        self.origin_detector = origin_detector
        self.volume_data = volume_data
        self.projection_data = projection_data
        self.gpu_index = gpu_index

        # Create volume geometry
        self.volume_geom = astra.create_vol_geom(self.num_voxel)

        # Create projection geometry
        self.projection_geom = astra.create_proj_geom(
            self.geometry_type,
            self.detector_spacing_x, self.detector_spacing_y,
            self.det_row_count, self.det_col_count,
            self.angles,
            self.source_origin, self.origin_detector)

        # Allocate and store volume data in ASTRA memory
        self.volume_id = astra.data3d.create(
            '-vol',
            self.volume_geom,
            self.volume_data)

        # Allocate and store projection data in ASTRA memory
        self.projection_id = astra.data3d.create(
            '-sino',
            self.projection_geom,
            self.projection_data)

        # Create algorithm object: forward projector
        cfg = astra.astra_dict('FP3D_CUDA')
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.projection_id
        cfg['VolumeDataId'] = self.volume_id
        self.forward_alg_id = astra.algorithm.create(cfg)

        # Create algorithm object: backward projector
        cfg = astra.astra_dict('BP3D_CUDA')
        # classmethod?
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.projection_id
        cfg['ReconstructionDataId'] = self.volume_id
        self.backward_alg_id = astra.algorithm.create(cfg)
Пример #8
0
    def __init__(self,
                 geometry_type='cone',
                 num_voxel=(100, 100, 100),
                 det_row_count=100,
                 det_col_count=100,
                 angles=np.linspace(0, 2 * np.pi, 180, endpoint=False),
                 det_col_spacing=1.0,
                 det_row_spacing=1.0,
                 source_origin=100.0,
                 origin_detector=10.0,
                 volume_data=1,
                 projection_data=1,
                 gpu_index=0):
        self.geometry_type = geometry_type
        self.num_voxel = num_voxel
        self.detector_spacing_x = det_col_spacing
        self.detector_spacing_y = det_row_spacing
        self.det_row_count = det_row_count
        self.det_col_count = det_col_count
        self.angles = angles
        self.source_origin = source_origin
        self.origin_detector = origin_detector
        self.volume_data = volume_data
        self.projection_data = projection_data
        self.gpu_index = gpu_index

        # Create volume geometry
        self.volume_geom = astra.create_vol_geom(self.num_voxel)

        # Create projection geometry
        self.projection_geom = astra.create_proj_geom(
            self.geometry_type, self.detector_spacing_x,
            self.detector_spacing_y, self.det_row_count, self.det_col_count,
            self.angles, self.source_origin, self.origin_detector)

        # Allocate and store volume data in ASTRA memory
        self.volume_id = astra.data3d.create('-vol', self.volume_geom,
                                             self.volume_data)

        # Allocate and store projection data in ASTRA memory
        self.projection_id = astra.data3d.create('-sino', self.projection_geom,
                                                 self.projection_data)

        # Create algorithm object: forward projector
        cfg = astra.astra_dict('FP3D_CUDA')
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.projection_id
        cfg['VolumeDataId'] = self.volume_id
        self.forward_alg_id = astra.algorithm.create(cfg)

        # Create algorithm object: backward projector
        cfg = astra.astra_dict('BP3D_CUDA')
        # classmethod?
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.projection_id
        cfg['ReconstructionDataId'] = self.volume_id
        self.backward_alg_id = astra.algorithm.create(cfg)
Пример #9
0
    def _fp_id(self):
        """Create algorithms object of forward projection."""

        geom_type = self.geom.geom_type.lower()
        cfg = None

        if geom_type in self.type2d:
            cfg = astra.astra_dict('FP_CUDA')
        elif geom_type in self.type3d:
            cfg = astra.astra_dict('FP3D_CUDA')
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.proj_id
        cfg['VolumeDataId'] = self.vol_id

        return astra.algorithm.create(cfg)
Пример #10
0
    def _fp_id(self):
        """Create algorithms object of forward projection."""

        geom_type = self.geom.geom_type.lower()
        cfg = None

        if geom_type in self.type2d:
            cfg = astra.astra_dict('FP_CUDA')
        elif geom_type in self.type3d:
            cfg = astra.astra_dict('FP3D_CUDA')
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.proj_id
        cfg['VolumeDataId'] = self.vol_id

        return astra.algorithm.create(cfg)
Пример #11
0
def main():
    parser = argparse.ArgumentParser()
    parser.add_argument('--width', type=int, required=True)
    parser.add_argument('--num-projections', type=int, required=True)
    parser.add_argument('--num-slices', type=int, required=True)

    args = parser.parse_args()
    angles = np.linspace(0,
                         np.pi,
                         args.num_projections,
                         False,
                         dtype=np.float64)

    vol_geom = astra.create_vol_geom(args.width, args.width, args.num_slices)
    proj_geom = astra.create_proj_geom('parallel3d', 1.0, 1.0, args.num_slices,
                                       args.width, angles)

    vid = astra.data3d.create('-vol', vol_geom)
    pid = astra.data3d.create('-proj3d', proj_geom, 0.0)

    config = astra.astra_dict('BP3D_CUDA')
    config['ProjectionDataId'] = pid
    config['ReconstructionDataId'] = vid

    aid = astra.algorithm.create(config)
    astra.algorithm.run(aid)
Пример #12
0
def SIRT2D_cpu(sinogram, Niter, proj_geom, vol_geom):
    # Create a data object for the reconstruction
    rec_id = astra.data2d.create('-vol', vol_geom)
    proj_id = astra.create_projector('strip',proj_geom,vol_geom)
    
    sinogram_id = astra.data2d.create('-sino', proj_geom, sinogram)
    # Set up the parameters for a reconstruction algorithm using the CPU
    cfg = astra.astra_dict('SIRT')
    cfg['ReconstructionDataId'] = rec_id
    cfg['ProjectionDataId'] = sinogram_id
    cfg['ProjectorId'] = proj_id
    cfg['option']={}
    cfg['option']['MinConstraint'] = 0

    # Create the algorithm object from the configuration structure
    alg_id = astra.algorithm.create(cfg)

    astra.algorithm.run(alg_id, Niter)

    # Get the result
    rec = astra.data2d.get(rec_id)

    # Clean up.
    astra.algorithm.delete(alg_id)
    astra.data2d.delete(rec_id)
    astra.data2d.delete(sinogram_id)
    astra.projector.delete(proj_id)
    
    return rec;
Пример #13
0
    def single_sino(sino: np.ndarray,
                    cor: ScalarCoR,
                    proj_angles: ProjectionAngles,
                    recon_params: ReconstructionParameters,
                    progress: Optional[Progress] = None) -> np.ndarray:
        assert sino.ndim == 2, "Sinogram must be a 2D image"

        sino = BaseRecon.prepare_sinogram(sino, recon_params)
        image_width = sino.shape[1]

        if astra_mutex.locked():
            LOG.warning("Astra recon already in progress. Waiting")
        with astra_mutex:
            vectors = vec_geom_init2d(proj_angles, 1.0,
                                      cor.to_vec(image_width).value)
            vol_geom = astra.create_vol_geom((image_width, image_width))
            proj_geom = astra.create_proj_geom('parallel_vec', image_width,
                                               vectors)
            cfg = astra.astra_dict(recon_params.algorithm)
            cfg['FilterType'] = recon_params.filter_name

            with _managed_recon(sino, cfg, proj_geom,
                                vol_geom) as (alg_id, rec_id):
                astra.algorithm.run(alg_id, iterations=recon_params.num_iter)
                return astra.data2d.get(rec_id)
Пример #14
0
    def backward(self, proj_vector=None):
        """Backprojection."""

        # Store projection data in ASTRA memory
        if proj_vector is None:
            astra.data3d.store(self.proj_id,
                               self.proj.data.reshape(
                                   self.geom.det_row_count,
                                   self.geom.angles.size,
                                   self.geom.det_col_count))
        else:
            astra.data3d.store(self.proj_id,
                               proj_vector.data.reshape(
                                   self.geom.det_row_count,
                                   self.geom.angles.size,
                                   self.geom.det_col_count))

        # Create algorithm object
        cfg = astra.astra_dict('BP3D_CUDA')
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.proj_id
        cfg['ReconstructionDataId'] = self.volume_id
        self.bp_id = astra.algorithm.create(cfg)

        # Run algorithms
        astra.algorithm.run(self.bp_id)

        # Retrieve projection from ASTRA memory
        self.vol.data[:] = np.ravel(astra.data3d.get(self.volume_id))
Пример #15
0
def fbp_cpu(sinogram, proj_id):

    # Get projection geometry from projector
    proj_geom = astra.projector.projection_geometry(proj_id)
    vol_geom = astra.projector.volume_geometry(proj_id)

    # Create a data object for the reconstruction
    rec_id = astra.data2d.create('-vol', vol_geom)

    # Create a data object to hold the sinogram data
    sinogram_id = astra.data2d.create('-sino', proj_geom, sinogram)

    # Create configuration for reconstruction algorithm
    cfg = astra.astra_dict('FBP')
    cfg['ReconstructionDataId'] = rec_id
    cfg['ProjectionDataId'] = sinogram_id
    cfg['ProjectorId'] = proj_id

    # Create and run the algorithm object from the configuration structure
    alg_id = astra.algorithm.create(cfg)
    astra.algorithm.run(alg_id)

    # Get the result
    rec = astra.data2d.get(rec_id)

    # Clean up.
    astra.algorithm.delete(alg_id)
    astra.data2d.delete(rec_id)
    astra.data2d.delete(sinogram_id)

    return rec
Пример #16
0
def astra_rec_cuda(tomo, center, recon, theta, vol_geom, niter, proj_type,
                   gpu_index, opts):
    # Lazy import ASTRA
    import astra as astra_mod
    nslices, nang, ndet = tomo.shape
    cfg = astra_mod.astra_dict(opts['method'])
    if 'extra_options' in opts:
        # NOTE: we are modifying 'extra_options' and so need to make a copy
        cfg['option'] = copy.deepcopy(opts['extra_options'])
    else:
        cfg['option'] = {}
    if gpu_index is not None:
        cfg['option']['GPUindex'] = gpu_index
    oc = None
    const_theta = np.ones(nang)
    proj_geom = astra_mod.create_proj_geom('parallel', 1.0, ndet,
                                           theta.astype(np.float64))
    for i in range(nslices):
        if center[i] != oc:
            oc = center[i]
            proj_geom['option'] = {
                'ExtraDetectorOffset': (center[i] - ndet / 2.) * const_theta
            }
        pid = astra_mod.create_projector(proj_type, proj_geom, vol_geom)
        cfg['ProjectorId'] = pid
        sid = astra_mod.data2d.link('-sino', proj_geom, tomo[i])
        cfg['ProjectionDataId'] = sid
        vid = astra_mod.data2d.link('-vol', vol_geom, recon[i])
        cfg['ReconstructionDataId'] = vid
        alg_id = astra_mod.algorithm.create(cfg)
        astra_mod.algorithm.run(alg_id, niter)
        astra_mod.algorithm.delete(alg_id)
        astra_mod.data2d.delete(vid)
        astra_mod.data2d.delete(sid)
        astra_mod.projector.delete(pid)
Пример #17
0
    def reconstruct(self, data, algo="SIRT3D_CUDA", iterations=25, pars={}):
        if self.data_id is None:
            self.data_id = astra.data3d.create("-sino", self.proj_geom, data)
        else:
            astra.data3d.store(self.data_id, data)

        if self.vol_id is None:
            self.vol_id = astra.data3d.create("-vol", self.vol_geom, 0)
        else:
            astra.data3d.store(self.vol_id, 0)

        cfg = astra.astra_dict(algo)
        cfg["ProjectorId"] = self.projector_id
        cfg["ProjectionDataId"] = self.data_id
        cfg["ReconstructionDataId"] = self.vol_id
        if self.gpu_index is not None:
            cfg["options"] = {"GPUindex": self.gpu_index}
        else:
            cfg["options"] = {}
        if "lower_limit" in pars:
            cfg["options"]["UseMinConstraint"] = True
            cfg["options"]["MinConstraintValue"] = pars["lower_limit"]
        if "upper_limit" in pars:
            cfg["options"]["UseMaxConstraint"] = True
            cfg["options"]["MaxConstraintValue"] = pars["upper_limit"]

        self.algo_id = astra.algorithm.create(cfg)
        astra.algorithm.run(self.algo_id, iterations)
        astra.algorithm.delete(self.algo_id)
        self.algo_id = None

        return astra.data3d.get(self.vol_id)
Пример #18
0
def reconstruct(s, alg, iterations, rnge=np.pi):
    # Create reconstruction.
    # s is the sinogram to reconstruct
    # alg is the algorithm to use (string) eg 'SIRT' or 'FBP'
    # iterations is number of iterations
    # rnge is the range of angles used (if not set the default is pi)...
    # ... r should be >=pi for an accurate reconstruction
    if alg == 'FBP':
        iterations = 1
    vol_geom, projector_id, proj_geom = geom_setup(s.shape[1], rnge, s.shape[0])
    
    # create an astratoolbox id for the projections(sinogram)
    projections_id = astra.data2d.create('-sino', proj_geom, s)
    
    # set up reconstruction
    reconstruction_id = astra.data2d.create('-vol', vol_geom)
    cfg = astra.astra_dict(alg)
    cfg['ReconstructionDataId'] = reconstruction_id
    cfg['ProjectionDataId'] = projections_id 
    cfg['ProjectorId'] = projector_id
    cfg['option'] = {}
    cfg['option']['MinConstraint'] = 0.  # Force solution to be nonnegative.
    algorithm_id = astra.algorithm.create(cfg)
    astra.algorithm.run(algorithm_id, iterations) 
    
    return astra.data2d.get(reconstruction_id)
Пример #19
0
def astra_rec_cuda(tomo, center, recon, theta, vol_geom, niter, proj_type, gpu_index, opts):
    # Lazy import ASTRA
    import astra as astra_mod
    nslices, nang, ndet = tomo.shape
    cfg = astra_mod.astra_dict(opts['method'])
    if 'extra_options' in opts:
        # NOTE: we are modifying 'extra_options' and so need to make a copy
        cfg['option'] = copy.deepcopy(opts['extra_options'])
    else:
        cfg['option'] = {}
    if gpu_index is not None:
        cfg['option']['GPUindex'] = gpu_index
    oc = None
    const_theta = np.ones(nang)
    proj_geom = astra_mod.create_proj_geom(
        'parallel', 1.0, ndet, theta.astype(np.float64))
    for i in range(nslices):
        if center[i] != oc:
            oc = center[i]
            proj_geom['option'] = {
                'ExtraDetectorOffset':
                (center[i] - ndet / 2.) * const_theta}
        pid = astra_mod.create_projector(proj_type, proj_geom, vol_geom)
        cfg['ProjectorId'] = pid
        sid = astra_mod.data2d.link('-sino', proj_geom, tomo[i])
        cfg['ProjectionDataId'] = sid
        vid = astra_mod.data2d.link('-vol', vol_geom, recon[i])
        cfg['ReconstructionDataId'] = vid
        alg_id = astra_mod.algorithm.create(cfg)
        astra_mod.algorithm.run(alg_id, niter)
        astra_mod.algorithm.delete(alg_id)
        astra_mod.data2d.delete(vid)
        astra_mod.data2d.delete(sid)
        astra_mod.projector.delete(pid)
Пример #20
0
def fbp(sinogram, geo):
    vol_geom = astra.create_vol_geom(geo["nVoxelY"], geo["nVoxelX"],
                                     -1 * geo["sVoxelY"] / 2,
                                     geo["sVoxelY"] / 2,
                                     -1 * geo["sVoxelX"] / 2,
                                     geo["sVoxelX"] / 2)
    proj_geom = astra.create_proj_geom(
        geo["mode"], geo["dDetecU"], geo["nDetecU"],
        np.linspace(geo["start_angle"], geo["end_angle"], geo["sino_views"],
                    False), geo["DSO"], geo["DOD"])
    if geo["mode"] is "parallel":
        proj_id = astra.create_projector("linear", proj_geom, vol_geom)
    elif geo["mode"] is "fanflat":
        proj_id = astra.create_projector("line_fanflat", proj_geom_full,
                                         vol_geom)

    rec_id = astra.data2d.create('-vol', vol_geom)
    sinogram_id = astra.data2d.create('-sino', proj_geom, sinogram)

    cfg = astra.astra_dict('FBP')
    cfg['ProjectorId'] = proj_id
    cfg["FilterType"] = "Ram-Lak"
    cfg['ReconstructionDataId'] = rec_id
    cfg['ProjectionDataId'] = sinogram_id

    alg_id = astra.algorithm.create(cfg)
    astra.algorithm.run(alg_id)

    image_recon = astra.data2d.get(rec_id)
    astra.algorithm.delete(alg_id)
    astra.data2d.delete(rec_id)
    astra.data2d.delete(sinogram_id)

    return image_recon
Пример #21
0
    def backward(self, proj_vector=None):
        """Backprojection."""

        # Store projection data in ASTRA memory
        if proj_vector is None:
            astra.data3d.store(
                self.proj_id,
                self.proj.data.reshape(self.geom.det_row_count,
                                       self.geom.angles.size,
                                       self.geom.det_col_count))
        else:
            astra.data3d.store(
                self.proj_id,
                proj_vector.data.reshape(self.geom.det_row_count,
                                         self.geom.angles.size,
                                         self.geom.det_col_count))

        # Create algorithm object
        cfg = astra.astra_dict('BP3D_CUDA')
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.proj_id
        cfg['ReconstructionDataId'] = self.volume_id
        self.bp_id = astra.algorithm.create(cfg)

        # Run algorithms
        astra.algorithm.run(self.bp_id)

        # Retrieve projection from ASTRA memory
        self.vol.data[:] = np.ravel(astra.data3d.get(self.volume_id))
Пример #22
0
def FBP_reconstruction(projections, scanner_params, proj_vecs, voxel_size=.1, rec_shape=501, vol_center=0, **kwargs):

    astra.astra.set_gpu_index(globals().get('GPU_ID', kwargs.get('gpu_id', -1)))

    # from [proj_slc,rows,cols] to [rows,proj_slc,cols]
    projections = np.transpose(projections, (1,0,2))
    proj_geom = astra.create_proj_geom('cone_vec', *scanner_params.detector_effective_size, proj_vecs)    
    projections_id = astra.data3d.create('-sino', proj_geom, projections)

    # [z,x,y] to [y,x,z] axis transposition
    vol_center = tuple([vol_center[i] for i in [2,1,0]]) if isinstance(vol_center, tuple) else (vol_center,) *3
    reconstructed_shape = tuple([rec_shape[i] for i in [2,1,0]]) if isinstance(rec_shape, tuple) else (rec_shape,) *3
    
    vol_geom = astra.creators.create_vol_geom(*reconstructed_shape,
        *[center+sign*size/2*voxel_size for center, size in zip(vol_center, reconstructed_shape) for sign in [-1, 1]]
    )
    reconstruction_id = astra.data3d.create('-vol', vol_geom, data=0)

    alg_cfg = astra.astra_dict('BP3D_CUDA')
    alg_cfg['ProjectionDataId'] = projections_id
    alg_cfg['ReconstructionDataId'] = reconstruction_id
    algorithm_id = astra.algorithm.create(alg_cfg)

    astra.algorithm.run(algorithm_id)
    reconstruction = astra.data3d.get(reconstruction_id)

    # Free ressources
    astra.algorithm.delete(algorithm_id)
    astra.data3d.delete([projections_id, reconstruction_id])

    return reconstruction
Пример #23
0
def full_reconstruct(p):
    # Create geometries and projector.
    vol_geom = astra.create_vol_geom(128, 128)
    angles = np.linspace(0, np.pi, 180, endpoint=False)
    proj_geom = astra.create_proj_geom('parallel', 1., 128, angles)
    projector_id = astra.create_projector('linear', proj_geom, vol_geom)
     
    # Create sinogram.
    sinogram_id, sinogram = astra.create_sino(p, projector_id)
     
    # Create reconstruction.
    reconstruction_id = astra.data2d.create('-vol', vol_geom)
    cfg = astra.astra_dict('FBP')
    cfg['ReconstructionDataId'] = reconstruction_id
    cfg['ProjectionDataId'] = sinogram_id
    cfg['ProjectorId'] = projector_id
    cfg['option'] = {}
    cfg['option']['MinConstraint'] = 0.  # Force solution to be nonnegative.
    algorithm_id = astra.algorithm.create(cfg)
    astra.algorithm.run(algorithm_id, 100)  # 100 iterations.
    reconstruction = astra.data2d.get(reconstruction_id)
    return reconstruction
    
    # Cleanup.
    astra.algorithm.delete(algorithm_id)
    astra.data2d.delete(reconstruction_id)
    astra.data2d.delete(sinogram_id)
    astra.projector.delete(projector_id)
Пример #24
0
def astra_fp_3d(volume, proj_geom):
    """
    :param proj_geom:
    :param volume:
    :return:3D sinogram
    """
    detector_size = volume.shape[1]
    slices_number = volume.shape[0]
    rec_size = detector_size

    vol_geom = build_volume_geometry_3d(rec_size, slices_number)

    sinogram_id = astra.data3d.create('-sino', proj_geom)
    # Create a data object for the reconstruction
    rec_id = astra.data3d.create('-vol', vol_geom, data=volume)

    # Set up the parameters for a reconstruction algorithm using the GPU
    cfg = astra.astra_dict('FP3D_CUDA')
    cfg['VolumeDataId'] = rec_id
    cfg['ProjectionDataId'] = sinogram_id
    cfg['option'] = {}

    alg_id = astra.algorithm.create(cfg)
    astra.algorithm.run(alg_id, 1)
    res_sino = astra.data3d.get(sinogram_id)

    # Clean up. Note that GPU memory is tied up in the algorithm object,
    # and main RAM in the data objects.
    astra.algorithm.delete(alg_id)
    astra.data3d.delete(rec_id)
    astra.data3d.delete(sinogram_id)
    astra.clear()
    return res_sino
Пример #25
0
 def performBP(self, proj_id, rec_id):
     cfg = astra.astra_dict('BP3D_CUDA')
     cfg['ProjectionDataId'] = proj_id
     cfg['ReconstructionDataId'] = rec_id
     alg_id = astra.algorithm.create(cfg)
     astra.algorithm.run(alg_id)
     astra.algorithm.delete(alg_id)
Пример #26
0
def astra_rec_cpu(tomo, center, recon, theta, vol_geom, niter, proj_type, opts):
    # Lazy import ASTRA
    import astra as astra_mod
    nslices, nang, ndet = tomo.shape
    cfg = astra_mod.astra_dict(opts['method'])
    if 'extra_options' in opts:
        cfg['option'] = opts['extra_options']
    proj_geom = astra_mod.create_proj_geom('parallel', 1.0, ndet, theta.astype(np.float64))
    pid = astra_mod.create_projector(proj_type, proj_geom, vol_geom)
    sino = np.zeros((nang, ndet), dtype=np.float32)
    sid = astra_mod.data2d.link('-sino', proj_geom, sino)
    cfg['ProjectorId'] = pid
    cfg['ProjectionDataId'] = sid
    for i in range(nslices):
        shft = int(np.round(ndet / 2. - center[i]))
        if not shft == 0:
            sino[:] = np.roll(tomo[i], shft)
            l = shft
            r = ndet + shft
            if l < 0:
                l = 0
            if r > ndet:
                r = ndet
            sino[:, :l] = 0
            sino[:,  r:] = 0
        else:
            sino[:] = tomo[i]
        vid = astra_mod.data2d.link('-vol', vol_geom, recon[i])
        cfg['ReconstructionDataId'] = vid
        alg_id = astra_mod.algorithm.create(cfg)
        astra_mod.algorithm.run(alg_id, niter)
        astra_mod.algorithm.delete(alg_id)
        astra_mod.data2d.delete(vid)
    astra_mod.data2d.delete(sid)
    astra_mod.projector.delete(pid)
Пример #27
0
def fbp(g, theta, n, filter='ram-lak'):
    '''
    Computes the filtered backprojection of the given numpy.ndarray g with the
    desired filter.
    '''
    vol_geom = astra.create_vol_geom(n)
    proj_geom = astra.create_proj_geom('parallel', 1.0, 367, theta)

    f_id = astra.data2d.create('-vol', vol_geom)
    g_id = astra.data2d.create('-sino', proj_geom, g)

    cfg = astra.astra_dict("FBP_CUDA")
    cfg["ProjectionDataId"] = g_id
    cfg["ReconstructionDataId"] = f_id
    cfg['option'] = {}
    cfg['option']["FilterType"] = filter

    alg_id = astra.algorithm.create(cfg)
    astra.algorithm.run(alg_id)
    rec_data = astra.data2d.get(f_id)
    astra.algorithm.delete(alg_id)
    astra.data2d.delete(f_id)
    astra.data2d.delete(g_id)

    return rec_data
Пример #28
0
 def cfg_setup(self):
     cfg = astra.astra_dict(self.name)
     cfg['ReconstructionDataId'] = self.rec_id
     cfg['ProjectionDataId'] = self.sino_id
     if 'CUDA' in self.name:
         cfg['option'] = {'GPUindex': self.parameters['GPU_index']}
     return cfg
Пример #29
0
    def _backproject(self,
                     y,
                     algorithm='FDK_CUDA',
                     iterations=1,
                     min_constraint=None,
                     short_scan=False):

        cfg = astra.astra_dict(algorithm)
        cfg['option'] = {'ShortScan': short_scan}
        if (min_constraint is not None):
            cfg['option']['MinConstraint'] = min_constraint

        output = numpy.zeros(astra.functions.geom_size(self.vol_geom),
                             dtype=numpy.float32)
        rec_id = astra.data3d.link('-vol', self.vol_geom, output)
        sinogram_id = astra.data3d.link('-sino', self.proj_geom, y)

        cfg['ReconstructionDataId'] = rec_id
        cfg['ProjectionDataId'] = sinogram_id
        #print(cfg['option'])
        alg_id = astra.algorithm.create(cfg)

        #astra.data3d.store(self.sinogram_id, y)
        astra.algorithm.run(alg_id, iterations)

        astra.algorithm.delete(alg_id)

        astra.data3d.delete([rec_id, sinogram_id])

        return output  #astra.data3d.get(self.rec_id)
    def Kadj(sino: np.array) -> np.array:
        # Create objects for the reconstruction
        rec_id = astra.data2d.create('-vol', vol_geom)
        sino_id = astra.data2d.create('-sino', proj_geom, sino)
        proj_id = astra.create_projector(proj_type, proj_geom, vol_geom)

        # Set up the parameters for the backpropagation reconstruction.
        cfg = astra.astra_dict(alg)
        cfg['ReconstructionDataId'] = rec_id
        cfg['ProjectionDataId'] = sino_id
        cfg['ProjectorId'] = proj_id

        # Create the algorithm object from the configuration structure
        alg_id = astra.algorithm.create(cfg)

        # Run algorithm.
        astra.algorithm.run(alg_id)

        # Get the result
        rec = astra.data2d.get(rec_id)

        # Clean up and return result.
        astra.algorithm.delete(alg_id)
        astra.data2d.delete(rec_id)
        astra.data2d.delete(sino_id)
        astra.projector.delete(proj_id)
        return rec
Пример #31
0
    def backward(self, proj_vector):
        """Backprojection."""

        if self.geom.vol_ndim == 2:

            # Store projection data in ASTRA memory
            astra.data2d.store(
                self.proj_id,
                proj_vector.data.reshape(self.geom.angles.size,
                                         self.geom.det_col_count))

            # Create algorithm object
            cfg = astra.astra_dict('BP_CUDA')
            cfg['option'] = {'GPUindex': self.gpu_index}
            cfg['ProjectionDataId'] = self.proj_id
            cfg['ReconstructionDataId'] = self.volume_id
            self.bp_id = astra.algorithm.create(cfg)

            # Run algorithms
            astra.algorithm.run(self.bp_id)

            # Retrieve projection from ASTRA memory
            return self.vol_space.element(
                self.scal_fac * np.ravel(astra.data2d.get(self.volume_id)))

        elif self.geom.vol_ndim == 3:

            # Store projection data in ASTRA memory
            astra.data3d.store(
                self.proj_id,
                proj_vector.data.reshape(self.geom.det_row_count,
                                         self.geom.angles.size,
                                         self.geom.det_col_count))

            # Create algorithm object
            cfg = astra.astra_dict('BP3D_CUDA')
            cfg['option'] = {'GPUindex': self.gpu_index}
            cfg['ProjectionDataId'] = self.proj_id
            cfg['ReconstructionDataId'] = self.volume_id
            self.bp_id = astra.algorithm.create(cfg)

            # Run algorithms
            astra.algorithm.run(self.bp_id)

            # Retrieve projection from ASTRA memory
            return self.vol_space.element(
                self.scal_fac * np.ravel(astra.data3d.get(self.volume_id)))
Пример #32
0
def FDK_reconstruction(projections,
                       scanner_params,
                       proj_vecs,
                       voxel_size=.1,
                       rec_shape=501,
                       **kwargs):
    """Uses FDK method to reconstruct CT volume from CB projections
        
        Args:
        -----
            projections (np.ndarray): [proj_slc, rows, cols] CBCT projections
            scanner_params (class): class containing scanner data
            proj_vecs (np.ndarray): vects describing the scanning used for reconstruction
            voxel_size (float): size of the voxels in the reconstructed volume
            rec_shape (int/tuple): shape of the reconstructed volume tuple with 3 dims [z,x,y] or int if isotropic

            --optional--
            gpu_id (int): GPU for astra to use if not set globaly, defaults to -1
            
        Returns:
        --------
            reconstruction (np.ndarray): [z,x,y] recontructed CT volume
    """

    astra.astra.set_gpu_index(globals().get('GPU_ID', kwargs.get('gpu_id',
                                                                 -1)))

    # from [proj_slc,rows,cols] to [rows,proj_slc,cols]
    projections = np.transpose(projections, (1, 0, 2))
    proj_geom = astra.create_proj_geom('cone_vec',
                                       *scanner_params.detector_binned_size,
                                       proj_vecs)
    projections_id = astra.data3d.create('-sino', proj_geom, projections)

    # [z,x,y] to [y,x,z] axis transposition
    reconstructed_shape = tuple([rec_shape[i]
                                 for i in [2, 1, 0]]) if isinstance(
                                     rec_shape, tuple) else (rec_shape, ) * 3
    vol_geom = astra.creators.create_vol_geom(
        *reconstructed_shape, *[
            sign * size / 2 * voxel_size for size in reconstructed_shape
            for sign in [-1, 1]
        ])
    reconstruction_id = astra.data3d.create('-vol', vol_geom, data=0)

    alg_cfg = astra.astra_dict('FDK_CUDA')
    alg_cfg['ProjectionDataId'] = projections_id
    alg_cfg['ReconstructionDataId'] = reconstruction_id
    alg_cfg['option'] = {'ShortScan': False}
    algorithm_id = astra.algorithm.create(alg_cfg)

    astra.algorithm.run(algorithm_id)
    reconstruction = astra.data3d.get(reconstruction_id)

    # Free ressources
    astra.algorithm.delete(algorithm_id)
    astra.data3d.delete([projections_id, reconstruction_id])

    return reconstruction
Пример #33
0
    def single_test(self, geom_type, proj_type, alg, iters, vss, dss):
        if alg == 'FBP' and 'fanflat' in geom_type:
            self.skipTest('CPU FBP is parallel-beam only')
        is3D = (geom_type in ['parallel3d', 'cone'])
        for vg in VolumeGeometries(is3D, 'FDK' not in alg):
            for pg in ProjectionGeometries(geom_type):
                if not is3D:
                    vol = np.zeros((128, 128), dtype=np.float32)
                    vol[50:70, 50:70] = 1
                else:
                    vol = np.zeros((64, 64, 64), dtype=np.float32)
                    vol[25:35, 25:35, 25:35] = 1
                options = {}
                if vss > 1:
                    options["VoxelSuperSampling"] = vss
                if dss > 1:
                    options["DetectorSuperSampling"] = vss
                proj_id = astra.create_projector(proj_type,
                                                 pg,
                                                 vg,
                                                 options=options)
                if not is3D:
                    sino_id, sinogram = astra.create_sino(vol, proj_id)
                else:
                    sino_id, sinogram = astra.create_sino3d_gpu(vol, pg, vg)
                if not is3D:
                    DATA = astra.data2d
                else:
                    DATA = astra.data3d

                rec_id = DATA.create('-vol', vg,
                                     0.0 if 'EM' not in alg else 1.0)

                cfg = astra.astra_dict(alg)
                cfg['ReconstructionDataId'] = rec_id
                cfg['ProjectionDataId'] = sino_id
                cfg['ProjectorId'] = proj_id
                alg_id = astra.algorithm.create(cfg)

                for i in range(iters):
                    astra.algorithm.run(alg_id, 1)
                rec = DATA.get(rec_id)
                astra.astra.delete([sino_id, alg_id, alg_id, proj_id])
                if not is3D:
                    val = np.sum(rec[55:65, 55:65]) / 100.
                else:
                    val = np.sum(rec[27:32, 27:32, 27:32]) / 125.
                TOL = 5e-2
                if DISPLAY and abs(val - 1.0) >= TOL:
                    print(geom_type, proj_type, alg, vg, pg)
                    print(val)
                    pylab.gray()
                    if not is3D:
                        pylab.imshow(rec)
                    else:
                        pylab.imshow(rec[:, 32, :])
                    pylab.show()
                self.assertTrue(abs(val - 1.0) < TOL)
Пример #34
0
    def backward(self, proj_vector):
        """Backprojection."""

        if self.geom.vol_ndim == 2:

            # Store projection data in ASTRA memory
            astra.data2d.store(self.proj_id, proj_vector.data.reshape(
                self.geom.angles.size, self.geom.det_col_count))

            # Create algorithm object
            cfg = astra.astra_dict('BP_CUDA')
            cfg['option'] = {'GPUindex': self.gpu_index}
            cfg['ProjectionDataId'] = self.proj_id
            cfg['ReconstructionDataId'] = self.volume_id
            self.bp_id = astra.algorithm.create(cfg)

            # Run algorithms
            astra.algorithm.run(self.bp_id)

            # Retrieve projection from ASTRA memory
            return self.vol_space.element(self.scal_fac * np.ravel(
                astra.data2d.get(self.volume_id)))

        elif self.geom.vol_ndim == 3:

            # Store projection data in ASTRA memory
            astra.data3d.store(self.proj_id,
                               proj_vector.data.reshape(
                                   self.geom.det_row_count,
                                   self.geom.angles.size,
                                   self.geom.det_col_count))

            # Create algorithm object
            cfg = astra.astra_dict('BP3D_CUDA')
            cfg['option'] = {'GPUindex': self.gpu_index}
            cfg['ProjectionDataId'] = self.proj_id
            cfg['ReconstructionDataId'] = self.volume_id
            self.bp_id = astra.algorithm.create(cfg)

            # Run algorithms
            astra.algorithm.run(self.bp_id)

            # Retrieve projection from ASTRA memory
            return self.vol_space.element(self.scal_fac * np.ravel(
                astra.data3d.get(self.volume_id)))
Пример #35
0
    def reconstruct(self, sinogram, centre_of_rotation, angles, shape, center):

        ctr = centre_of_rotation
        width = sinogram.shape[1]
        pad = 50

        sino = np.nan_to_num(sinogram)

        # pad the array so that the centre of rotation is in the middle
        alen = ctr
        blen = width - ctr
        mid = width / 2.0

        if (ctr > mid):
            plow = pad
            phigh = (alen - blen) + pad
        else:
            plow = (blen - alen) + pad
            phigh = pad

        logdata = np.log(sino+1)
        sinogram = np.pad(logdata, ((0, 0), (int(plow), int(phigh))),
                          mode='reflect')

        width = sinogram.shape[1]

        vol_geom = astra.create_vol_geom(shape[0], shape[1])
        proj_geom = astra.create_proj_geom('parallel', 1.0, width,
                                           np.deg2rad(angles))

        sinogram_id = astra.data2d.create("-sino", proj_geom, sinogram)

        # Create a data object for the reconstruction
        rec_id = astra.data2d.create('-vol', vol_geom)

        proj_id = astra.create_projector('strip', proj_geom, vol_geom)

        cfg = astra.astra_dict(self.parameters['reconstruction_type'])
        cfg['ReconstructionDataId'] = rec_id
        cfg['ProjectionDataId'] = sinogram_id
        cfg['ProjectorId'] = proj_id

        # Create the algorithm object from the configuration structure
        alg_id = astra.algorithm.create(cfg)
        # Run 20 iterations of the algorithm
        itterations = int(self.parameters['number_of_iterations'])
        # This will have a runtime in the order of 10 seconds.
        astra.algorithm.run(alg_id, itterations)
        # Get the result
        rec = astra.data2d.get(rec_id)

        # Clean up.
        astra.algorithm.delete(alg_id)
        astra.data2d.delete(rec_id)
        astra.data2d.delete(sinogram_id)

        return rec
Пример #36
0
def check_recon(folder, alg, iterations, bin_num):

    raw_data = np.load(os.path.join(directory, folder, 'Data',
                                    'data_corr.npy'))[:, :, :, 6]
    raw_data = np.transpose(raw_data,
                            axes=(1, 0,
                                  2))  # Transpose to (rows, angles, columns)

    # Change if isocentre is not directly in the center of the detector
    # raw_data = np.roll(raw_data, -2, axis=2)

    # Create a 3D projection geometry with our cone-beam data
    # Parameters: 'acquisition type', number of detector rows, number of detector columns, data ndarray
    proj_geom = astra.create_proj_geom('cone', pixel_pitch, pixel_pitch,
                                       det_row_count, det_col_count, angles,
                                       source_origin, origin_det)
    proj_id = astra.data3d.create('-proj3d', proj_geom, raw_data)

    # Create a 3D volume geometry.
    # Parameter order: rows, columns, slices (y, x, z)
    vol_geom = astra.create_vol_geom(det_col_count, det_col_count,
                                     det_row_count)

    # Create a data object for the reconstruction
    if alg == 'FDK_CUDA':
        recon_id = astra.data3d.create('-vol', vol_geom)
    else:
        ct_data = np.load(os.path.join(directory, folder, 'CT', 'FDK_CT.npy'))
        recon_id = astra.data3d.create('-vol', vol_geom, data=ct_data)

    # Set up the parameters for a reconstruction algorithm using the GPU
    cfg = astra.astra_dict(alg)
    cfg['ReconstructionDataId'] = recon_id
    cfg['ProjectionDataId'] = proj_id

    # Create the algorithm object from the configuration structure
    alg_id = astra.algorithm.create(cfg)

    # Run the specified number of iterations of the algorithm
    rec_data = np.zeros((iterations // 5, 576, 576))
    for i in range(0, iterations, 5):
        astra.algorithm.run(alg_id, 5)

        # Get the result
        rec = astra.data3d.get(recon_id)[11]
        print(alg[0:4] + f': {i + 5} Iterations')
        rec_data[i // 5] = rec

    np.save(
        os.path.join(directory, folder, 'CT',
                     alg[0:4] + '_iteration_check.npy'), rec_data)

    # Clean up. Note that GPU memory is tied up in the algorithm object,
    # and main RAM in the data objects.
    astra.algorithm.delete(alg_id)
    astra.data3d.delete(recon_id)
    astra.data3d.delete(proj_id)
Пример #37
0
    def forward(self, vol_space_vector):
        """Forward projection."""

        if self.geom.vol_ndim == 2:

            # Store volume data in ASTRA memory
            astra.data2d.store(
                self.volume_id,
                vol_space_vector.data.reshape(self.geom.vol_shape))

            # Create algorithm object
            cfg = astra.astra_dict('FP_CUDA')
            cfg['option'] = {'GPUindex': self.gpu_index}
            cfg['ProjectionDataId'] = self.proj_id
            cfg['VolumeDataId'] = self.volume_id
            self.fp_id = astra.algorithm.create(cfg)

            # Run algorithm
            astra.algorithm.run(self.fp_id)

            # Retrieve projection data from ASTRA memory
            return self.proj_space.element(
                self.scal_fac * np.ravel(astra.data2d.get(self.proj_id)))

        elif self.geom.vol_ndim == 3:

            # Store volume data in ASTRA memory
            astra.data3d.store(
                self.volume_id,
                vol_space_vector.data.reshape(self.geom.vol_shape))

            # Create algorithm object
            cfg = astra.astra_dict('FP3D_CUDA')
            cfg['option'] = {'GPUindex': self.gpu_index}
            cfg['ProjectionDataId'] = self.proj_id
            cfg['VolumeDataId'] = self.volume_id
            self.fp_id = astra.algorithm.create(cfg)

            # Run algorithm
            astra.algorithm.run(self.fp_id)

            # Retrieve projection data from ASTRA memory
            return self.proj_space.element(
                self.scal_fac * np.ravel(astra.data3d.get(self.proj_id)))
Пример #38
0
    def forward(self, vol_space_vector):
        """Forward projection."""

        if self.geom.vol_ndim == 2:

            # Store volume data in ASTRA memory
            astra.data2d.store(self.volume_id,
                               vol_space_vector.data.reshape(
                                   self.geom.vol_shape))

            # Create algorithm object
            cfg = astra.astra_dict('FP_CUDA')
            cfg['option'] = {'GPUindex': self.gpu_index}
            cfg['ProjectionDataId'] = self.proj_id
            cfg['VolumeDataId'] = self.volume_id
            self.fp_id = astra.algorithm.create(cfg)

            # Run algorithm
            astra.algorithm.run(self.fp_id)

            # Retrieve projection data from ASTRA memory
            return self.proj_space.element(self.scal_fac * np.ravel(
                astra.data2d.get(self.proj_id)))

        elif self.geom.vol_ndim == 3:

            # Store volume data in ASTRA memory
            astra.data3d.store(self.volume_id,
                               vol_space_vector.data.reshape(
                                   self.geom.vol_shape))

            # Create algorithm object
            cfg = astra.astra_dict('FP3D_CUDA')
            cfg['option'] = {'GPUindex': self.gpu_index}
            cfg['ProjectionDataId'] = self.proj_id
            cfg['VolumeDataId'] = self.volume_id
            self.fp_id = astra.algorithm.create(cfg)

            # Run algorithm
            astra.algorithm.run(self.fp_id)

            # Retrieve projection data from ASTRA memory
            return self.proj_space.element(self.scal_fac * np.ravel(
                astra.data3d.get(self.proj_id)))
Пример #39
0
    def _fbp_id(self):
        """Create algorithms object of back-projection."""

        geom_type = self.geom.geom_type.lower()

        if geom_type == 'parallel3d':
            return None

        cfg = None

        if geom_type in self.type2d:
            cfg = astra.astra_dict('FBP_CUDA')
        elif geom_type == 'cone':
            cfg = astra.astra_dict('FDK_CUDA')

        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.proj_id
        cfg['ReconstructionDataId'] = self.vol_id

        return astra.algorithm.create(cfg)
Пример #40
0
    def _fbp_id(self):
        """Create algorithms object of back-projection."""

        geom_type = self.geom.geom_type.lower()

        if geom_type == 'parallel3d':
            return None

        cfg = None

        if geom_type in self.type2d:
            cfg = astra.astra_dict('FBP_CUDA')
        elif geom_type == 'cone':
            cfg = astra.astra_dict('FDK_CUDA')

        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.proj_id
        cfg['ReconstructionDataId'] = self.vol_id

        return astra.algorithm.create(cfg)
Пример #41
0
 def set_config(self, rec_id, sino_id, proj_geom, vol_geom):
     cfg = astra.astra_dict(self.alg)
     cfg['ReconstructionDataId'] = rec_id
     cfg['ProjectionDataId'] = sino_id
     if 'FBP' in self.alg:
         cfg['FilterType'] = self.parameters['FBP_filter']
     if 'projector' in self.parameters.keys():
         proj_id = astra.create_projector(self.parameters['projector'],
                                          proj_geom, vol_geom)
         cfg['ProjectorId'] = proj_id
     cfg = self.set_options(cfg)
     return cfg
Пример #42
0
def do_AGD(meta, vecs, sc, g, niter):
    start = time.time()
    ang, u, v = g.shape
    g_vec = np.transpose(g.copy(), (2, 0, 1))
    vox = 1024 // sc
    pix_size = meta['pix_size'] * sc
    src_rad = meta['s2o']
    det_rad = meta['o2d']
    magn = src_rad / (src_rad + det_rad)
    bounds = vox * pix_size * magn / 2
    vol_geom = astra.create_vol_geom(vox, vox, vox, -bounds, bounds, -bounds,
                                     bounds, -bounds, bounds)

    proj_geom = astra.create_proj_geom('cone_vec', v, u, vecs)

    rec = np.zeros(astra.geom_size(vol_geom), dtype=np.float32)
    rec_id = astra.data3d.link('-vol', vol_geom, rec)
    # %%
    projector_id = astra.create_projector('cuda3d', proj_geom, vol_geom)

    #    rec_id = astra.data3d.create('-vol', vol_geom)

    proj_id = astra.data3d.create('-proj3d', proj_geom, g_vec)

    astra.plugin.register(NesterovGradient.AcceleratedGradientPlugin)
    cfg_agd = astra.astra_dict('AGD-PLUGIN')
    cfg_agd['ProjectionDataId'] = proj_id
    cfg_agd['ReconstructionDataId'] = rec_id
    cfg_agd['ProjectorId'] = projector_id
    cfg_agd['option'] = {}
    cfg_agd['option']['MinConstraint'] = 0
    alg_id = astra.algorithm.create(cfg_agd)

    # Run Nesterov Accelerated Gradient Descent algorithm with 'nb_iter' iterations

    astra.algorithm.run(alg_id, niter)
    rec = np.transpose(rec, (2, 1, 0))
    # %%
    pylab.figure()
    pylab.imshow(rec[vox // 2, :, :])
    pylab.figure()
    pylab.imshow(rec[:, vox // 2, :])
    pylab.figure()
    pylab.imshow(rec[:, :, vox // 2])

    # release memory allocated by ASTRA structures
    astra.algorithm.delete(alg_id)
    astra.data3d.delete(proj_id)
    astra.data3d.delete(rec_id)
    print((time.time() - start), 'Finished AGD 50 reconstructionn')
    return rec
Пример #43
0
 def set_config(self, rec_id, sino_id, proj_geom, vol_geom):
     cfg = astra.astra_dict(self.alg)
     cfg['ReconstructionDataId'] = rec_id
     cfg['ProjectionDataId'] = sino_id
     if 'FBP' in self.alg:
         fbp_filter = self.parameters['FBP_filter'] if 'FBP_filter' in \
             self.parameters.keys() else 'none'
         cfg['FilterType'] = fbp_filter
     if 'projector' in self.parameters.keys():
         proj_id = astra.create_projector(
             self.parameters['projector'], proj_geom, vol_geom)
         cfg['ProjectorId'] = proj_id
     cfg = self.set_options(cfg)
     return cfg
Пример #44
0
 def run_algorithm(self, alg, n_it, data):
     rec_id = astra.data2d.create('-vol', self.vol_geom)
     sino_id = astra.data2d.create('-sino', self.proj_geom, data)
     cfg = astra.astra_dict(alg)
     cfg['ReconstructionDataId'] = rec_id
     cfg['ProjectionDataId'] = sino_id
     alg_id = astra.algorithm.create(cfg)
     print("Running %s" %alg)
     astra.algorithm.run(alg_id, n_it)
     rec = astra.data2d.get(rec_id)
     astra.algorithm.delete(alg_id)
     astra.data2d.delete(rec_id)
     astra.data2d.delete(sino_id)
     return rec
Пример #45
0
def cg_alg(proj_id, sid, vid):
    # CG algorithm
    cfg = astra.astra_dict('CG')
    cfg['ProjectorId'] = proj_id
    cfg['ProjectionDataId'] = sid
    cfg['ReconstructionDataId'] = vid
    cfg['option'] = {}
    alg_id = astra.algorithm.create(cfg)
    astra.algorithm.run(alg_id, 100)
    rec = astra.data2d.get(vid)
    rec = np.flipud(rec)
    plt.imsave('rec_cg.png', rec, cmap = plt.cm.gray)
    save_one_image(rec, 'reconstruct', 'rec_cg_.png')

    astra.algorithm.delete(alg_id)
    return rec
Пример #46
0
 def set_config(self, rec_id, sino_id, proj_geom, vol_geom):
     cfg = astra.astra_dict(self.alg)
     cfg['ReconstructionDataId'] = rec_id
     cfg['ProjectionDataId'] = sino_id
     if 'FBP' in self.alg:
         cfg['FilterType'] = self.parameters['FBP_filter']
     if 'projector' in self.parameters.keys():
         proj_id = astra.create_projector(
             self.parameters['projector'], proj_geom, vol_geom)
         cfg['ProjectorId'] = proj_id
     # mask not currently working correctly for SIRT or SART algorithms
     sirt_or_sart = [a for a in ['SIRT', 'SART'] if a in self.alg]
     if self.mask_id and not sirt_or_sart:
         cfg['option'] = {}
         cfg['option']['ReconstructionMaskId'] = self.mask_id
     cfg = self.set_options(cfg)
     return cfg
Пример #47
0
def cp_alg(proj_id, sid, vid):
    # CP algorithm
    cfg = astra.astra_dict('CP')
    cfg['ProjectorId'] = proj_id
    cfg['ProjectionDataId'] = sid
    cfg['ReconstructionDataId'] = vid
    cfg['option'] = {}
    cfg['option']['its_PM'] = 150
    cfg['option']['Lambda'] = 10000.0
    alg_id = astra.algorithm.create(cfg)
    astra.algorithm.run(alg_id, 100)
    rec = astra.data2d.get(vid)
    rec = np.flipud(rec)
    rec = rec.astype('float32')
    plt.imsave('rec_cp.png', rec, cmap = plt.cm.gray)
    save_one_image(rec, 'reconstruct', 'rec_cp_.png')

    astra.algorithm.delete(alg_id)
    return rec
Пример #48
0
    def reconstruct3D(self, sinogram, angles, shape, depth, alg_name, iterations):
        
        det_rows = sinogram.shape[0]
        det_cols = sinogram.shape[2]

#        sinogram = np.transpose(sinogram, (2,1,0))
                      
        vol_geom = astra.create_vol_geom(shape[0], depth, shape[1])
        
        proj_geom = astra.create_proj_geom('parallel3d', 1.0, 1.0, det_cols, \
                                            det_rows, np.deg2rad(angles))
                                            
        sinogram_id = astra.data3d.create("-sino", proj_geom, sinogram)

        # Create a data object for the reconstruction
        rec_id = astra.data3d.create('-vol', vol_geom)
                
        cfg = astra.astra_dict(alg_name)
        cfg['ReconstructionDataId'] = rec_id
        cfg['ProjectionDataId'] = sinogram_id
         
        # Create the algorithm object from the configuration structure
        alg_id = astra.algorithm.create(cfg)
        
        # This will have a runtime in the order of 10 seconds.
        astra.algorithm.run(alg_id, iterations)
        
        
        #if "CUDA" in params[0] and "FBP" not in params[0]:
        #self.res += astra.algorithm.get_res_norm(alg_id)**2
        #print math.sqrt(self.res)
        
        # Get the result
        rec = astra.data3d.get(rec_id)

        astra.algorithm.delete(alg_id)
        astra.data3d.delete(rec_id)
        astra.data3d.delete(sinogram_id)

        rec = rec[:160,:160,1]                

        return rec
Пример #49
0
    def forward(self, vol_vector=None):
        """Forward projection."""
        # Store volume data in ASTRA memory
        if vol_vector is None:
            astra.data3d.store(self.volume_id,
                               self.vol.data.reshape(self.geom.vol_shape))
        else:
            astra.data3d.store(self.volume_id,
                               vol_vector.data.reshape(self.geom.vol_shape))

        # Create algorithm object
        cfg = astra.astra_dict('FP3D_CUDA')
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = self.proj_id
        cfg['VolumeDataId'] = self.volume_id
        self.fp_id = astra.algorithm.create(cfg)

        # Run algorithm
        astra.algorithm.run(self.fp_id)

        # Retrieve projection data from ASTRA memory
        self.proj.data[:] = np.ravel(astra.data3d.get(self.proj_id))
Пример #50
0
def run_all_experiment(proj_id, sid, vid, sino):
    cfg = astra.astra_dict('CP')
    cfg['ProjectorId'] = proj_id
    cfg['ProjectionDataId'] = sid
    cfg['ReconstructionDataId'] = vid
    cfg['option'] = {}
    cfg['option']['its_PM'] = 100

    for i in np.arange(1.0, 1.01, 0.1):
        cfg['option']['Lambda'] = i
        alg_id = astra.algorithm.create(cfg)
        astra.algorithm.run(alg_id, 100)
        rec = astra.data2d.get(vid)
        rec = np.flipud(rec)
        rec = rec.astype('float32')
        tv, l2 = calculate_error(proj_id, rec, sino)
        print 'tv rec: ', tv, 'l2 norm rec: ', l2
        astra.algorithm.delete(alg_id)
    
        plt.imsave('rec_cp_Lamda_' + str(i) + '.png', rec, cmap = plt.cm.gray)
        save_one_image(rec, 'reconstruct', 'rec_cp_Lamda_' + str(i) + '_.png')
    return
Пример #51
0
    def reconstruct2D(self, sinogram, angles, shape, alg_name, iterations):
        
        vol_geom = astra.create_vol_geom(shape[0], shape[1])
        
        proj_geom = astra.create_proj_geom('parallel', 1.0, sinogram.shape[1],
                                           np.deg2rad(angles))

        sinogram_id = astra.data2d.create("-sino", proj_geom, sinogram)

        # Create a data object for the reconstruction
        rec_id = astra.data2d.create('-vol', vol_geom)
        
        cfg = astra.astra_dict(alg_name)
        cfg['ReconstructionDataId'] = rec_id
        cfg['ProjectionDataId'] = sinogram_id
        
        if not "CUDA" in alg_name:
            proj_id = astra.create_projector('strip', proj_geom, vol_geom)
            cfg['ProjectorId'] = proj_id
         
        # Create the algorithm object from the configuration structure
        alg_id = astra.algorithm.create(cfg)
        
        # This will have a runtime in the order of 10 seconds.
        astra.algorithm.run(alg_id, iterations)
        
        if "CUDA" in alg_name and "FBP" not in alg_name:
                self.res += astra.algorithm.get_res_norm(alg_id)**2
                print math.sqrt(self.res)
        
        # Get the result
        rec = astra.data2d.get(rec_id)

        astra.algorithm.delete(alg_id)
        astra.data2d.delete(rec_id)
        astra.data2d.delete(sinogram_id)
        
        return rec
def recon_multi_part(algon,proj_data,proj_data_low,det_move,angles,x_sub_boundaries,y_sub_boundaries,z_sub_boundaries,vol_size,det_spacing_x,det_spacing_y,x_subvol_width,y_subvol_width,z_subvol_width,n_x,n_y,n_z,nr_iterations_high,source_origin, origin_det,relaxation):
    # this part performs the reconstruction of the subvolume.
    pro_proj = proj_data - proj_data_low  # we only want to have the projection data that comes from the sub volume
    det_row_count= pro_proj.shape[0]
    det_col_count=pro_proj.shape[2]

    vectors_ROI = np.zeros((len(angles), 12)) # this vector will contain the information of the source and detector position.
    move_x,move_y,move_z=how_to_move(x_sub_boundaries,y_sub_boundaries,z_sub_boundaries,vol_size,x_subvol_width,y_subvol_width,z_subvol_width,n_x,n_y,n_z)
    for i in range(0,len(angles)):
        # source
        vectors_ROI[i,0] = np.sin(angles[i]) * (source_origin) +move_x 
        vectors_ROI[i,1] = -np.cos(angles[i]) * (source_origin) + move_y
        vectors_ROI[i,2] = move_z
        # center of detector
        vectors_ROI[i,3] = -np.sin(angles[i]) * (origin_det) + move_x 
        vectors_ROI[i,4] = np.cos(angles[i]) * (origin_det)  + move_y
        vectors_ROI[i,5] = move_z +det_move
        # vector from detector pixel 0 to 1
        vectors_ROI[i,6] = np.cos(angles[i]) *det_spacing_x    
        vectors_ROI[i,7] = np.sin(angles[i])*det_spacing_x
        vectors_ROI[i,8] = 0

        # vector from detector pixel (0,0) to (1,0)
        vectors_ROI[i,9] = 0
        vectors_ROI[i,10] = 0
        vectors_ROI[i,11] = det_spacing_y
    
            #ROI=cube[:,:,z_sub_boundaries[n_z,0]:z_sub_boundaries[n_z+1,0]]
            # mlab.figure()
            # mlab.contour3d(ROI)
    width_z=z_sub_boundaries[n_z+1,2]-z_sub_boundaries[n_z,1]
    width_y=y_sub_boundaries[n_y+1,2]-y_sub_boundaries[n_y,1]
    width_x=x_sub_boundaries[n_x+1,2]-x_sub_boundaries[n_x,1]
    
    vol_geom_ROI= astra.create_vol_geom(width_y.astype(int), width_z.astype(int), width_x.astype(int))
    proj_geom_ROI = astra.create_proj_geom('cone_vec', det_row_count, det_col_count, vectors_ROI)

    if algon[0:4] != 'EGEN':

        # Create a data object for the reconstruction


        rec_id_ROI = astra.data3d.create('-vol', vol_geom_ROI)
        sinogram_id_ROI = astra.data3d.create('-proj3d', proj_geom_ROI, pro_proj)
        if algon=='SIRT':
            algon='SIRT3D_CUDA'
        elif algon=='CGLS':
            algon='CGLS3D_CUDA'

        # Set up the parameters for a reconstruction algorithm using the GPU
        cfg = astra.astra_dict(algon)   
        cfg['ReconstructionDataId'] = rec_id_ROI
        cfg['ProjectionDataId'] = sinogram_id_ROI
        cfg['option']={}
        cfg['option']['MinConstraint'] = 0 #attenuation coefficient can't be negative
        #cfg['option']['VoxelSuperSampling'] = np.round(float(det_spacing_x)/vol_size,decimals=2)
        alg_id = astra.algorithm.create(cfg)

    print "startar algo"
    if algon == 'SIRT3D_CUDA' or algon=='CGLS3D_CUDA':
        astra.algorithm.run(alg_id,nr_iterations_high)

            
    elif algon=='EGEN_SART':

        rec_volume=(width_x.astype(int), width_y.astype(int), width_z.astype(int))
        rec_volume=np.zeros(rec_volume,dtype= np.float16)
        
        sides=[rec_volume.shape[0],rec_volume.shape[1],rec_volume.shape[2]]
        max_side=np.max(sides)
        print max_side
        h=relaxation*float(1)/(max_side)#0.00001 change to max size of y o z


        vectors=np.matrix('0 0 0 0 0 0 0 0 0 0 0 0',dtype= np.float16)
        for ii in range(0,nr_iterations_high):
            angles_ind = np.linspace(0, len(angles), len(angles),False)
            np.random.shuffle(angles_ind) #shuffle the projection angles to get faster convergence
            
            for jj in angles_ind:
                
                #proj_geom = astra.create_proj_geom('cone', det_spacing, det_spacing, det_size[1], det_size[1], angles[jj], source_to_origin_pixels,origin_to_detector_pixels)
                vectors[:,:]=vectors_ROI[jj,:]
                proj_geom_SART = astra.create_proj_geom('cone_vec', det_row_count, det_col_count, vectors)
                sinogram_id, proj_it = astra.create_sino3d_gpu(rec_volume, proj_geom_SART,vol_geom_ROI)

                proj_it=proj_it[:,0,:]


                residual=np.zeros((det_row_count,1,det_col_count))
                residual[:,0,:]=proj_it-pro_proj[:,jj,:]

                astra.data3d.store(sinogram_id, residual)

                #h=0.001
                [id, rec_volume_it] = astra.create_backprojection3d_gpu(residual, proj_geom_SART, vol_geom_ROI)
                rec_volume= rec_volume -h*rec_volume_it
                rec_volume=rec_volume*(rec_volume>0)
                astra.data3d.delete(id)
                astra.data3d.delete(sinogram_id)  
                
            

    else:
        print"algorithm is not supported"

    print "s**t algo"
    if algon[0:4] != 'EGEN':
        # Get the result
        
        rec_sub_vol=astra.data3d.get(rec_id_ROI)
    
        # Clean up. Note that GPU memory is tied up in the algorithm object,
        # and main RAM in the data objects.
        astra.algorithm.delete(alg_id)
        astra.data3d.delete(rec_id_ROI)
        astra.data3d.delete(sinogram_id_ROI)
        return rec_sub_vol
    else:
        return rec_volume
Пример #53
0
def astra(*args):
    """
    Reconstruct object using the ASTRA toolbox

    Extra options
    ----------
    method : str
        ASTRA reconstruction method to use.
    num_iter : int, optional
        Number of algorithm iterations performed.
    proj_type : str, optional
        ASTRA projector type to use: 'line', 'linear', or 'strip' (CPU only).
    extra_options : dict, optional
        Extra options for the ASTRA config (i.e. those in cfg['option'])

    Warning
    -------
    When using CUDA, only 1 CPU core can be used.

    Example
    -------
    >>> import tomopy
    >>> obj = tomopy.shepp3d() # Generate an object.
    >>> ang = tomopy.angles(180) # Generate uniformly spaced tilt angles.
    >>> sim = tomopy.project(obj, ang) # Calculate projections.
    >>>
    >>> # Reconstruct object:
    >>> rec = tomopy.recon(sim, ang, algorithm=tomopy.astra,
    >>>       options={'method':'SART', 'num_iter':10*180, 'proj_type':'linear',
    >>>       'extra_options':{'MinConstraint':0}})
    >>>
    >>> # Show 64th slice of the reconstructed object.
    >>> import pylab
    >>> pylab.imshow(rec[64], cmap='gray')
    >>> pylab.show()
    """
    # Lazy import ASTRA
    import astra as astra_mod

    # Get shared arrays
    tomo = mproc.SHARED_TOMO
    recon = mproc.SHARED_ARRAY

    # Unpack arguments
    nang = args[0]
    nslices = args[1]
    ndet = args[2]
    centers = args[3]
    angles = args[4]
    num_gridx = args[5]['num_gridx']
    num_gridy = args[5]['num_gridy']
    opts = args[5]['options']
    istart = args[6]
    iend = args[7]

    # Check options
    for o in needed_options['astra']:
        if not o in opts:
            logger.error("Option %s needed for ASTRA reconstruction." % (o,))
            raise ValueError()
    for o in default_options['astra']:
        if not o in opts:
            opts[o] = default_options['astra'][o]

    # Create ASTRA geometries
    vol_geom = astra_mod.create_vol_geom((num_gridx,num_gridy))
    proj_geom = astra_mod.create_proj_geom('parallel',1.0,ndet,angles.astype(np.float64))

    # Create ASTRA data id
    sino = np.zeros((nang, ndet), dtype=np.float32)

    # Create ASTRA config
    cfg = astra_mod.astra_dict(opts['method'])

    if opts['proj_type']!='cuda':
        pi = astra_mod.create_projector(opts['proj_type'], proj_geom, vol_geom)
        sid = astra_mod.data2d.link('-sino', proj_geom, sino)
        cfg['ProjectorId'] = pi
        cfg['ProjectionDataId'] = sid
        use_cuda=False
    else:
        use_cuda=True

    if 'extra_options' in opts:
        cfg['option'] = opts['extra_options']
    else:
        cfg['option'] = {}

    # Perform reconstruction
    for i in xrange(istart, iend):
        sino[:] = tomo[:,i,:]

        cfg['option']['z_id']=i

        # Fix center of rotation
        if use_cuda:
            proj_geom['option'] = {'ExtraDetectorOffset': (centers[i]-ndet/2.)*np.ones(nang)}
            sid = astra_mod.data2d.link('-sino', proj_geom, sino)
            cfg['ProjectionDataId'] = sid
            pi = astra_mod.create_projector(opts['proj_type'], proj_geom, vol_geom)
            cfg['ProjectorId'] = pi
        else:
            # Temporary workaround, will be fixed in later ASTRA version
            shft = int(np.round(ndet/2.-centers[i]))
            sino[:] = np.roll(sino,shft)
            l = shft
            r = sino.shape[1]+shft
            if l<0: l=0
            if r>sino.shape[1]: r=sino.shape[1]
            sino[:,0:l]=0
            sino[:,r:sino.shape[1]]=0

        vid = astra_mod.data2d.link('-vol', vol_geom, recon[i])
        cfg['ReconstructionDataId'] = vid
        alg_id = astra_mod.algorithm.create(cfg)
        astra_mod.algorithm.run(alg_id, opts['num_iter'])
        astra_mod.algorithm.delete(alg_id)
        astra_mod.data2d.delete(vid)
        if use_cuda:
            astra_mod.projector.delete(pi)
            astra_mod.data2d.delete(sid)

    # Clean up
    if not use_cuda:
        astra_mod.projector.delete(pi)
        astra_mod.data2d.delete(sid)
Пример #54
0
proj_id = astra.create_projector('line',proj_geom,vol_geom)
sinogram_id, sinogram = astra.create_sino(P, proj_id,useCUDA=True)

pylab.figure(2)
pylab.imshow(P)
pylab.figure(3)
pylab.imshow(sinogram)

# Create a data object for the reconstruction
rec_id = astra.data2d.create('-vol', vol_geom)

# Create a data object for the mask
mask_id = astra.data2d.create('-vol', vol_geom, mask)

# Set up the parameters for a reconstruction algorithm using the GPU
cfg = astra.astra_dict('SIRT_CUDA')
cfg['ReconstructionDataId'] = rec_id
cfg['ProjectionDataId'] = sinogram_id
cfg['option'] = {}
cfg['option']['ReconstructionMaskId'] = mask_id

# Create the algorithm object from the configuration structure
alg_id = astra.algorithm.create(cfg)

# Run 150 iterations of the algorithm
astra.algorithm.run(alg_id, 150)

# Get the result
rec = astra.data2d.get(rec_id)

pylab.figure(4)
Пример #55
0
    def _apply(self, projections, volume):
        """ Apply back projector.

        Parameters
        ----------

        projections : RNVector

              RNVector of dimension self.range.n which contains the
              projection data (sinogram).

        volume_data : RNVector

              RNVector of dimension self.domain.n onto which the projection
              will be projected back.


        Examples
        --------
        >>> num_voxel = (100, 100, 100)
        >>> det_row_count = 100
        >>> det_col_count = 100
        >>> angles = np.linspace(0, 2 * np.pi, 180, endpoint=False)
        >>> phantom = Cuboid(shape=num_voxel).data

        # <class 'RL.space.euclidean.RN'>
        >>> rn = Rn(phantom.size)

        # <class 'RL.space.euclidean.Vector'>
        >>> rn_phantom = rn.element(phantom.ravel())

        # <class 'astra.ForwardProjector'>
        >>> fp = ForwardProjector(num_voxel=num_voxel, \
        det_row_count=det_row_count, det_col_count=det_col_count, \
        angles=angles)

        # <class 'RL.space.euclidean.Vector'>
        >>> rn_proj = fp(rn_phantom)

        >>> bp = BackwardProjector(num_voxel=num_voxel,\
        det_row_count=det_row_count, det_col_count=det_col_count, \
        angles=angles)

        >>> type(bp)
        <class 'pyastra.BackwardProjector'>

        # <class 'RL.space.euclidean.Vector'>
        >>> rn_rec = bp(rn_proj)

        >>> rec = np.reshape(rn_rec.data, num_voxel)
        >>> rec.shape
        (100, 100, 100)
        """

        # Create volume geometry
        vol_geom = astra.create_vol_geom(self.num_voxel)

        # Create projection geometry
        proj_geom = astra.create_proj_geom(
            self.geometry_type,
            self.detector_spacing_x, self.detector_spacing_y,
            self.det_row_count, self.det_col_count,
            self.angles,
            self.source_origin, self.origin_detector)

        # Allocate ASTRA memeory and store projection data in it
        proj_id = astra.data3d.create(
            '-sino',
            proj_geom,
            projections.data.reshape(
                self.det_row_count,
                self.angles.size,
                self.det_col_count))

        # proj_data = np.reshape(
        #     np.ravel(projections.data),
        #     (self.det_row_count, self.angles.size, self.det_col_count))
        # proj_id = astra.data3d.create('-sino', proj_geom, proj_data)

        # Allocate ASTRA memory for volume data
        volume_id = astra.data3d.create('-vol', vol_geom, 0)

        # Create algorithm object
        cfg = astra.astra_dict(self.alg_string)
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = proj_id
        cfg['ReconstructionDataId'] = volume_id
        alg_id = astra.algorithm.create(cfg)

        # Run algorithms
        # with(Timer("Projection")):
        astra.algorithm.run(alg_id)

        # Retrieve projection from ASTRA memory
        volume.data[:] = np.ravel(astra.data3d.get(volume_id))

        # Free ASTRA memory
        astra.data3d.delete(volume_id)
        astra.data3d.delete(proj_id)
        astra.algorithm.delete(alg_id)
Пример #56
0
    import s018_plugin
    # Then, we register the plugin class with ASTRA
    astra.plugin.register(s018_plugin.LandweberPlugin)

    # Get a list of registered plugins
    six.print_(astra.plugin.get_registered())

    # To get help on a registered plugin, use get_help
    six.print_(astra.plugin.get_help('LANDWEBER-PLUGIN'))

    # Create data structures
    sid = astra.data2d.create('-sino', proj_geom, sinogram)
    vid = astra.data2d.create('-vol', vol_geom)

    # Create config using plugin name
    cfg = astra.astra_dict('LANDWEBER-PLUGIN')
    cfg['ProjectorId'] = proj_id
    cfg['ProjectionDataId'] = sid
    cfg['ReconstructionDataId'] = vid

    # Create algorithm object
    alg_id = astra.algorithm.create(cfg)

    # Run algorithm for 100 iterations
    astra.algorithm.run(alg_id, 100)

    # Get reconstruction
    rec = astra.data2d.get(vid)

    # Options for the plugin go in cfg['option']
    cfg = astra.astra_dict('LANDWEBER-PLUGIN')
def make_reconsruction(proj_data,number_of_projections,vol_size_ratio,det_size,rec_volume,source_to_origin_pixels,origin_to_detector_pixels,nr_iterations,algo,relaxation,initializer):

    vol_geom = astra.create_vol_geom(rec_volume)
    
    angles = np.linspace(0, 2*np.pi, number_of_projections, False)
    det_spacing=np.round((float(det_size[0])/det_size[1])/vol_size_ratio,decimals=3)

    proj_geom = astra.create_proj_geom('cone', det_spacing, det_spacing, det_size[1], det_size[1], angles, source_to_origin_pixels,origin_to_detector_pixels)

    #np.round(float(rec_volume[0])/new_size[0],decimals=2)
    if algo[0:4] != 'EGEN':
        # Create projection data from this
        proj_id=4

        # Create a data object for the reconstruction
        rec_id = astra.data3d.create('-vol', vol_geom,initializer)
        sinogram_id = astra.data3d.create('-proj3d', proj_geom, proj_data)
        #Set up the parameters for a reconstruction algorithm using the GPU
        cfg = astra.astra_dict(algo)
        cfg['ReconstructionDataId'] = rec_id
        cfg['ProjectionDataId'] = sinogram_id
        cfg['option']={}
        cfg['option']['MinConstraint'] = 0 #attenuation coefficient can't be negative
 
        # Create the algorithm object from the configuration structure
        alg_id = astra.algorithm.create(cfg)

    print "startar algo"
    if algo == 'SIRT3D_CUDA' or algo=='CGLS3D_CUDA':
        astra.algorithm.run(alg_id,nr_iterations)
    elif algo=='FDK_CUDA':
        astra.algorithm.run(alg_id)
    elif algo=='EGEN_SIRT':
        if isinstance( initializer, ( int, long ) ):
            rec_volume=np.zeros(rec_volume,dtype= np.float16)
        else:
            rec_volume=initializer
        for ii in range(0,nr_iterations):

            sinogram_id, proj_it = astra.create_sino3d_gpu(rec_volume, proj_geom,vol_geom)
            residual=proj_it-proj_data

            h=relaxation*float(1)/(rec_volume.shape[0]*number_of_projections)
            [id, rec_volume_it] = astra.create_backprojection3d_gpu(residual, proj_geom, vol_geom)
            rec_volume= rec_volume -h*rec_volume_it
            rec_volume=rec_volume*(rec_volume>0)
            astra.data3d.delete(id)
            astra.data3d.delete(sinogram_id)
            
    elif algo=='EGEN_SART':
        if isinstance( initializer, ( int, long ) ):
            rec_volume=np.zeros(rec_volume,dtype= np.float16)
        else:
            rec_volume=initializer
        #print rec_volume.shape[0]
        
        for ii in range(0,nr_iterations):
            angles_ind = np.linspace(0, number_of_projections, number_of_projections,False)
            np.random.shuffle(angles_ind)

            for jj in angles_ind:
                proj_geom = astra.create_proj_geom('cone', det_spacing, det_spacing, det_size[1], det_size[1], angles[jj], source_to_origin_pixels,origin_to_detector_pixels)
            #print np.min(sub_volume_high)
                sinogram_id, proj_it = astra.create_sino3d_gpu(rec_volume, proj_geom,vol_geom)
                proj_it=proj_it[:,0,:]
                residual=np.zeros((det_size[1],1,det_size[1]))
                residual[:,0,:]=proj_it-proj_data[:,jj,:]
                #print np.shape(proj_it),np.shape(residual),np.shape(proj_data[:,jj,:])
                #astra.data3d.store(sinogram_id, residual)
                
                h=relaxation*float(1)/(rec_volume.shape[0])#0.00001
                [id, rec_volume_it] = astra.create_backprojection3d_gpu(residual, proj_geom, vol_geom)
                rec_volume= rec_volume -h*rec_volume_it
                rec_volume=rec_volume*(rec_volume>0)
                astra.data3d.delete(id)
                astra.data3d.delete(sinogram_id)    
#             pylab.figure()
#             pylab.gray()
#             pylab.imshow(rec_volume[:,:,128])
            

    else:
        print"algorithm is not supported"
        
        
    print "s**t algo"
    if algo[0:4] != 'EGEN':
        # Get the result
        rec = astra.data3d.get(rec_id)
    
        # Clean up. Note that GPU memory is tied up in the algorithm object,
        # and main RAM in the data objects.
        astra.algorithm.delete(alg_id)
        astra.data3d.delete(rec_id)
        astra.data3d.delete(proj_id)
        astra.data3d.delete(sinogram_id)
        return rec
    else:
        return rec_volume
Пример #58
0
    def _apply(self, volume, projections):
        """Apply forward projector.

        Parameters
        ----------

        volume_data : RNVector
              RNVector of dimension self.domain.n which contains the data be
              projected.

        projections : RNVector
              RNVector of dimension self.range.n the projections are written
              to.


        Examples
        --------
        >>> num_voxel = (100, 100, 100)

        #>>> phantom = Cuboid(shape=num_voxel).data
        >>> phantom = np.zeros(num_voxel)

        # <class 'RL.space.euclidean.RN'>
        >>> rn = Rn(phantom.size)

        # <class 'RL.space.euclidean.Vector'>
        >>> rn_phantom = rn.element(phantom.flatten())

        # <class 'astra.ForwardProjector'>
        >>> fp = ForwardProjector(num_voxel=num_voxel)

        # <class 'RL.space.euclidean.Vector'>
        >>> rn_proj = fp(rn_phantom)

        >>> proj = np.reshape(rn_proj.data, (100, 180, 100))
        >>> proj.shape
        (100, 180, 100)
        """

        # Create volume geometry
        vol_geom = astra.create_vol_geom(self.num_voxel)

        # Create projection geometry
        proj_geom = astra.create_proj_geom(
            self.geometry_type,
            self.detector_spacing_x, self.detector_spacing_y,
            self.det_row_count, self.det_col_count,
            self.angles,
            self.source_origin, self.origin_detector)

        # Allocate and store volume data in ASTRA memory
        volume_id = astra.data3d.create(
            '-vol',
            vol_geom,
            volume.data.reshape(self.num_voxel))

        # Allocate ASTRA memeory for projection data
        proj_id = astra.data3d.create('-sino', proj_geom, 0)

        # Create algorithm object
        cfg = astra.astra_dict(self.alg_string)
        cfg['option'] = {'GPUindex': self.gpu_index}
        cfg['ProjectionDataId'] = proj_id
        cfg['VolumeDataId'] = volume_id
        alg_id = astra.algorithm.create(cfg)

        # Run algorithms
        # with(Timer("Projection")):
        astra.algorithm.run(alg_id)

        # Retrieve projection from ASTRA memory
        projections.data[:] = np.ravel(astra.data3d.get(proj_id))

        # Free ASTRA memory
        astra.data3d.delete(volume_id)
        astra.data3d.delete(proj_id)
        astra.algorithm.delete(alg_id)
Пример #59
0
def conebeam_test(data_obj=ctdata.Data(), alg_type='fdk', num_iterations=10, padding=None, scale_factor=1,
                  vol_init=None,
                  gpu_index=0,
                  num_voxel=None):
    """Test conebeam reconstruction of ASTRA.

    conebeam_sim()
    """

    t = time.time()

    # Default arguments
    if not num_voxel:
        num_voxel = [100, 100, 100]

    if not padding:
        padding = 0

    if scale_factor:
        pass

    # Extract paramaters from data class
    detector_spacing_x = 1
    detector_spacing_y = 1
    det_row_count = data_obj.shape[0]
    det_col_count = data_obj.shape[2] + 2 * padding
    angles_rad = data_obj.angles__rad
    source_origin = data_obj.distance_source_origin__mm
    source_det = data_obj.distance_source_detector__mm

    # Create volume geometry
    vol_geom = astra.create_vol_geom(*num_voxel)

    # Create projection geometry
    proj_geom = astra.create_proj_geom('cone',
                                       detector_spacing_x, detector_spacing_y,
                                       det_row_count, det_col_count,
                                       angles_rad,
                                       source_origin, source_det)

    # Create a sinogram from phantom
    sinogram = np.pad(data_obj.projections, ((0, 0), (0, 0), (padding, padding)), mode='edge')
    sino_id = astra.data3d.create('-sino', proj_geom, sinogram)

    # Set up the parameters for a reconstruction algorithm using the GPU
    rec_id = astra.data3d.create('-vol', vol_geom, vol_init)
    alg_type += '_CUDA'
    alg_type = alg_type.upper()
    cfg = astra.astra_dict(alg_type)
    cfg['ReconstructionDataId'] = rec_id
    cfg['ProjectionDataId'] = sino_id

    # Use GPU
    cfg['option'] = {}
    cfg['option']['GPUindex'] = gpu_index

    # Iterate algorithm
    alg_id = astra.algorithm.create(cfg)
    astra.algorithm.run(alg_id, num_iterations)
    rec_vol = astra.data3d.get(rec_id)

    print("Algorithm: %s" % cfg['type'])
    print("Elapsed time: %g s" % (time.time() - t))

    # Clean up.
    astra.algorithm.delete(alg_id)
    astra.data3d.delete(rec_id)
    astra.data3d.delete(sino_id)

    return rec_vol, sinogram