def topple(self, point, J, cage, Bpoint, method='function', **kwargs): # eq.Bpoint == point calculated method (slow) # sf.Bpoint == spline interpolated method (fast) x = {'cl': {'r': cage.coil_loop[:, 0], 'z': cage.coil_loop[:, 2]}} if 'streamfunction' in Bpoint.__str__(): topright = Bpoint((np.max(x['cl']['r']), np.max(x['cl']['z'])), check_bounds=True) bottomleft = Bpoint((np.max(x['cl']['r']), np.max(x['cl']['z'])), check_bounds=True) if not (topright and bottomleft): errtxt = 'TF coil extends outside Bpoint interpolation grid\n' errtxt = 'extend sf grid\n' raise ValueError(errtxt) if method == 'function': # calculate tf feild as fitted 1/r function i = np.argmax(x['cl']['z']) ro, zo = x['cl']['r'][i], x['cl']['z'][i] bm = ro * cage.point((ro, 0, zo), variable='feild')[1] # TF moment elif method != 'BS': # raise error if method not 'function' or 'BS' errtxt = 'invalid tf feild method {}\n'.format(method) errtxt += 'select method from \'function\' or \'BS\'\n' raise ValueError(errtxt) if method == 'function': b = np.zeros(3) b[2] = -bm / point[ 0] # TF feild (fast version / only good for TF cl) elif method == 'BS': # calculate tf feild with full Biot-Savart b = cage.point(point, variable='feild') # (slow / correct) theta = np.arctan2(point[1], point[0]) pf_point = np.dot(geom.rotate(-theta, 'z'), point) # rotate to PF plane pf_b = Bpoint([pf_point[0], pf_point[2]]) # PF feild (sf-fast, eq-slow) b += np.dot(geom.rotate(theta, 'z'), [pf_b[0], 0, pf_b[1]]) # add PF Fbody = np.cross(J, b) # body force return Fbody
def point(self, s, variable='ripple'): # s==3D point vector B = np.zeros(2) n = np.array([0, 1, 0]) if variable == 'ripple': planes = [0, np.pi / self.nTF] # rotate (inline, ingap) elif variable == 'feild': planes = [0] else: errtxt = '\n' errtxt += 'point variable error, require \'ripple\' or \'feild\'\n' raise ValueError(errtxt) for j, theta in enumerate(planes): sr = np.dot(s, geom.rotate(theta)) nr = np.dot(n, geom.rotate(theta)) Bo = np.zeros(3) for tcoil in self.Tcoil: for dy in self.dYwp: # wp pattern for dr in self.dRwp: # wp radial pattern Bo += self.Iturn*cc.mu_o*\ self.gfl.B(sr,theta=tcoil,dy=dy,dr=dr)/(self.ny*self.nr) B[j] = np.dot(nr, Bo) if variable == 'ripple': ripple = 1e2 * (B[0] - B[1]) / np.sum(B) return ripple else: return Bo
def rotate_cp(self, name, dof, theta, axis): self.check_cp_rotation(dof, self.mpc[name]['neq']) R = geom.rotate(theta, axis=axis) # 3x3 rotation matrix self.mpc[name]['Cr'] = np.zeros( (self.mpc[name]['neq'], self.mpc[name]['neq'])) self.mpc[name]['Cr'][:3, :3] = R if self.mpc[name]['neq'] == 6: self.mpc[name]['Cr'][3:, 3:] = R
def point(self, s, variable='ripple'): # s==3D point vector B = np.zeros(2) n = np.array([0, 1, 0]) if variable == 'ripple': planes = [0, np.pi / self.nTF] # rotate (inline, ingap) elif variable == 'feild': planes = [0] else: errtxt = '\n' errtxt += 'point variable error, require \'ripple\' or \'feild\'\n' raise ValueError(errtxt) for j, theta in enumerate(planes): sr = np.dot(s, geom.rotate(theta)) nr = np.dot(n, geom.rotate(theta)) Bo = np.zeros(3) for tcoil in np.linspace(0, 2 * np.pi, self.nTF, endpoint=False): Bo += cc.mu_o * self.gfl.B(sr, theta=tcoil) B[j] = np.dot(nr, Bo) if variable == 'ripple': ripple = 1e2 * (B[0] - B[1]) / np.sum(B) return ripple else: return Bo
def plot_3D(self, ms=5, bb=12, pattern=0): fig = pl.figure(figsize=(8, 8)) ax = fig.gca(projection='3d') Theta = np.linspace(0, 2 * np.pi, pattern, endpoint=False) for t in Theta: R = geom.rotate(t, axis='y') #X = np.dot(self.X,R) #ax.plot(X[:,0],X[:,2],X[:,1],'o',markersize=ms,color=0.75*np.ones(3)) for i, (part, c) in enumerate(zip(self.part, color)): D = np.dot(self.part[part]['D'], R) ax.plot(D[:, 0], D[:, 2], D[:, 1], color=c) ax.set_xlim(-bb, bb) ax.set_ylim(-bb, bb) ax.set_zlim(-bb, bb) ax.axis('off')
def rotateX_(self,theta): self.X_ = np.dot(self.X,geom.rotate(theta)) self.dX_ = np.dot(self.dX,geom.rotate(theta))