示例#1
0
def get_spherical_harmonics_coefficients(dwi, bvals, bvecs, sh_order=8, smooth=0.006, first=False, mean_centering=True):
    """ Compute coefficients of the spherical harmonics basis.

    Parameters
    -----------
    dwi : `nibabel.NiftiImage` object
        Diffusion signal as weighted images (4D).
    bvals : ndarray shape (N,)
        B-values used with each direction.
    bvecs : ndarray shape (N, 3)
        Directions of the diffusion signal. Directions are
        assumed to be only on the hemisphere.
    sh_order : int, optional
        SH order. Default: 8
    smooth : float, optional
        Lambda-regularization in the SH fit. Default: 0.006.
    mean_centering : bool
        If True, signal will have zero mean in each direction for all nonzero voxels

    Returns
    -------
    sh_coeffs : ndarray of shape (X, Y, Z, #coeffs)
        Spherical harmonics coefficients at every voxel. The actual number of
        coeffs depends on `sh_order`.
    """
    bvals = np.asarray(bvals)
    bvecs = np.asarray(bvecs)
    dwi_weights = dwi.get_data().astype("float32")

    # Exract the averaged b0.
    b0_idx = bvals == 0
    b0 = dwi_weights[..., b0_idx].mean(axis=3)

    # Extract diffusion weights and normalize by the b0.
    bvecs = bvecs[np.logical_not(b0_idx)]
    weights = dwi_weights[..., np.logical_not(b0_idx)]
    weights = normalize_dwi(weights, b0)

    # Assuming all directions are on the hemisphere.
    raw_sphere = HemiSphere(xyz=bvecs)

    # Fit SH to signal
    sph_harm_basis = sph_harm_lookup.get('mrtrix')
    Ba, m, n = sph_harm_basis(sh_order, raw_sphere.theta, raw_sphere.phi)
    L = -n * (n + 1)
    invB = smooth_pinv(Ba, np.sqrt(smooth) * L)
    data_sh = np.dot(weights, invB.T)

    if mean_centering:
        # Normalization in each direction (zero mean)
        idx = data_sh.sum(axis=-1).nonzero()
        means = data_sh[idx].mean(axis=0)
        data_sh[idx] -= means

    return data_sh
示例#2
0
def displaySphericalHist(odf, pts, minmax=False):
    # assumes pts and odf are hemisphere
    fullsphere = HemiSphere(xyz=pts).mirror()
    fullodf = np.concatenate((odf, odf), axis=0)

    r = fvtk.ren()
    if minmax:
        a = fvtk.sphere_funcs(fullodf - fullodf.min(), fullsphere)
    else:
        a = fvtk.sphere_funcs(fullodf, fullsphere)
    fvtk.add(r, a)
    fvtk.show(r)
def create_repulsion_sphere(n_points, n_iter):
    """ Create a sphere using electrostatic repulsion.
	params:
	npoints: number of points in the electrostatic repulsion
        n_iter: number of iterations to optimise energy
	return: HemiSphere object with n points vertices
	"""
    theta = np.pi * np.random.rand(n_points)
    phi = 2 * np.pi * np.random.rand(n_points)
    hsph_initial = HemiSphere(theta=theta, phi=phi)
    hsph_updated, energy = disperse_charges(hsph_initial, iters=n_iter)
    sph = hsph_updated
    return sph
def create_symmetric_repulsion_sphere(n_points, n_iter):
    """
	Create a full Sphere object using electrostatic repulsion.
	params:
	npoints: number of points in the electrostatic repulsion
	n_iter: number of iterations to optimise energy
	return: Sphere object with 2*npoints vertices
	"""
    theta = np.pi * np.random.rand(n_points)
    phi = 2 * np.pi * np.random.rand(n_points)
    hsph_initial = HemiSphere(theta=theta, phi=phi)
    hsph_updated, energy = disperse_charges(hsph_initial, iters=n_iter)
    sph = Sphere(xyz=np.vstack((hsph_updated.vertices,
                                -hsph_updated.vertices)))
    return sph
    def get_spherical_harmonics_coefficients(self,
                                             dwi_weights,
                                             bvals,
                                             bvecs,
                                             sh_order=8,
                                             smooth=0.006):
        """ Compute coefficients of the spherical harmonics basis.
        Parameters
        -----------
        dwi_weights : `nibabel.NiftiImage` object
            Diffusion signal as weighted images (4D).
        bvals : ndarray shape (N,)
            B-values used with each direction.
        bvecs : ndarray shape (N, 3)
            Directions of the diffusion signal. Directions are
            assumed to be only on the hemisphere.
        sh_order : int, optional
            SH order. Default: 8
        smooth : float, optional
            Lambda-regularization in the SH fit. Default: 0.006.
        Returns
        -------
        sh_coeffs : ndarray of shape (X, Y, Z, #coeffs)
            Spherical harmonics coefficients at every voxel. The actual number of
            coeffs depends on `sh_order`.
        """

        # Exract the averaged b0.
        b0_idx = bvals == 0
        b0 = dwi_weights[..., b0_idx].mean(axis=3) + 1e-10

        # Extract diffusion weights and normalize by the b0.
        bvecs = bvecs[np.logical_not(b0_idx)]
        weights = dwi_weights[..., np.logical_not(b0_idx)]
        weights = self.normalize_dwi(weights, b0)

        # Assuming all directions are on the hemisphere.
        raw_sphere = HemiSphere(xyz=bvecs)

        # Fit SH to signal
        sph_harm_basis = sph_harm_lookup.get("tournier07")
        Ba, m, n = sph_harm_basis(sh_order, raw_sphere.theta, raw_sphere.phi)
        L = -n * (n + 1)
        invB = smooth_pinv(Ba, np.sqrt(smooth) * L)
        data_sh = np.dot(weights, invB.T)
        return data_sh