def discreteFiber(c, s, B=I3, ndiv=120, invert=False, csym=None, ssym=None): """ """ import symmetry as S ztol = 1.e-8 # arg handling for c if hasattr(c, '__len__'): if hasattr(c, 'shape'): assert c.shape[0] == 3, \ 'scattering vector must be 3-d; yours is %d-d' \ % (c.shape[0]) if len(c.shape) == 1: c = c.reshape(3, 1) elif len(c.shape) > 2: raise RuntimeError, \ 'incorrect arg shape; must be 1-d or 2-d, yours is %d-d' \ % (len(c.shape)) else: # convert list input to array and transpose if len(c) == 3 and isscalar(c[0]): c = asarray(c).reshape(3, 1) else: c = asarray(c).T else: raise RuntimeError, 'input must be array-like' # arg handling for s if hasattr(s, '__len__'): if hasattr(s, 'shape'): assert s.shape[0] == 3, \ 'scattering vector must be 3-d; yours is %d-d' \ % (s.shape[0]) if len(s.shape) == 1: s = s.reshape(3, 1) elif len(s.shape) > 2: raise RuntimeError, \ 'incorrect arg shape; must be 1-d or 2-d, yours is %d-d' \ % (len(s.shape)) else: # convert list input to array and transpose if len(s) == 3 and isscalar(s[0]): s = asarray(s).reshape(3, 1) else: s = asarray(s).T else: raise RuntimeError, 'input must be array-like' nptc = c.shape[1] npts = s.shape[1] c = unitVector(dot(B, c)) # turn c hkls into unit vector in crys frame s = unitVector(s) # convert s to unit vector in samp frame retval = [] for i_c in range(nptc): dupl_c = tile(c[:, i_c], (npts, 1)).T ax = s + dupl_c anrm = columnNorm(ax).squeeze() # should be 1-d okay = anrm > ztol nokay = okay.sum() if nokay == npts: ax = ax / tile(anrm, (3, 1)) else: nspace = nullSpace(c[:, i_c].reshape(3, 1)) hperp = nspace[:, 0].reshape(3, 1) if nokay == 0: ax = tile(hperp, (1, npts)) else: ax[:, okay] = ax[:, okay] / tile(anrm[okay], (3, 1)) ax[:, not okay] = tile(hperp, (1, npts - nokay)) q0 = vstack( [ zeros(npts), ax ] ) # find rotations # note: the following line fixes bug with use of arange with float increments phi = arange(0, ndiv) * (2*pi/float(ndiv)) qh = quatOfAngleAxis(phi, tile(c[:, i_c], (ndiv, 1)).T) # the fibers, arraged as (npts, 4, ndiv) qfib = dot( quatProductMatrix(qh, mult='right'), q0 ).transpose(2, 1, 0) if csym is not None: retval.append(S.toFundamentalRegion(qfib.squeeze(), crysSym=csym, sampSym=ssym)) else: retval.append(fixQuat(qfib).squeeze()) return retval
def discreteFiber(c, s, B=I3, ndiv=120, invert=False, csym=None, ssym=None): """ """ import symmetry as S ztol = 1.e-8 # arg handling for c if hasattr(c, '__len__'): if hasattr(c, 'shape'): assert c.shape[0] == 3, \ 'scattering vector must be 3-d; yours is %d-d' \ % (c.shape[0]) if len(c.shape) == 1: c = c.reshape(3, 1) elif len(c.shape) > 2: raise RuntimeError, \ 'incorrect arg shape; must be 1-d or 2-d, yours is %d-d' \ % (len(c.shape)) else: # convert list input to array and transpose if len(c) == 3 and isscalar(c[0]): c = asarray(c).reshape(3, 1) else: c = asarray(c).T else: raise RuntimeError, 'input must be array-like' # arg handling for s if hasattr(s, '__len__'): if hasattr(s, 'shape'): assert s.shape[0] == 3, \ 'scattering vector must be 3-d; yours is %d-d' \ % (s.shape[0]) if len(s.shape) == 1: s = s.reshape(3, 1) elif len(s.shape) > 2: raise RuntimeError, \ 'incorrect arg shape; must be 1-d or 2-d, yours is %d-d' \ % (len(s.shape)) else: # convert list input to array and transpose if len(s) == 3 and isscalar(s[0]): s = asarray(s).reshape(3, 1) else: s = asarray(s).T else: raise RuntimeError, 'input must be array-like' nptc = c.shape[1] npts = s.shape[1] c = unitVector(dot(B, c)) # turn c hkls into unit vector in crys frame s = unitVector(s) # convert s to unit vector in samp frame retval = [] for i_c in range(nptc): dupl_c = tile(c[:, i_c], (npts, 1)).T ax = s + dupl_c anrm = columnNorm(ax).squeeze() # should be 1-d okay = anrm > ztol nokay = okay.sum() if nokay == npts: ax = ax / tile(anrm, (3, 1)) else: nspace = nullSpace(c[:, i_c].reshape(3, 1)) hperp = nspace[:, 0].reshape(3, 1) if nokay == 0: ax = tile(hperp, (1, npts)) else: ax[:, okay] = ax[:, okay] / tile(anrm[okay], (3, 1)) ax[:, not okay] = tile(hperp, (1, npts - nokay)) q0 = vstack([zeros(npts), ax]) # find rotations # note: the following line fixes bug with use of arange with float increments phi = arange(0, ndiv) * (2 * pi / float(ndiv)) qh = quatOfAngleAxis(phi, tile(c[:, i_c], (ndiv, 1)).T) # the fibers, arraged as (npts, 4, ndiv) qfib = dot(quatProductMatrix(qh, mult='right'), q0).transpose(2, 1, 0) if csym is not None: retval.append( S.toFundamentalRegion(qfib.squeeze(), crysSym=csym, sampSym=ssym)) else: retval.append(fixQuat(qfib).squeeze()) return retval