Ejemplo n.º 1
0
def creatCalibMatrix():
    """Generate and return symbolic expression of 4 x 4 affine rotation matrix from US probe reference frame to US image reference frame.

    Returns
    -------
    prTi : sympy.matrices.matrices.MutableMatrix 
        The matrix expression.
        
    syms : list
        List of ``sympy.core.symbol.Symbol`` symbol objects used to generate the expression. 
    
    """
    
    x1 = Symbol('x1')
    y1 = Symbol('y1')
    z1 = Symbol('z1')
    alpha1 = Symbol('alpha1')
    beta1 = Symbol('beta1')
    gamma1 = Symbol('gamma1')
    
    prTi = Matrix(([c(alpha1)*c(beta1), c(alpha1)*s(beta1)*s(gamma1)-s(alpha1)*c(gamma1), c(alpha1)*s(beta1)*c(gamma1)+s(alpha1)*s(gamma1), x1],\
                   [s(alpha1)*c(beta1), s(alpha1)*s(beta1)*s(gamma1)+c(alpha1)*c(gamma1), s(alpha1)*s(beta1)*c(gamma1)-c(alpha1)*s(gamma1), y1],\
                   [-s(beta1), c(beta1)*s(gamma1), c(beta1)*c(gamma1), z1],\
                   [0, 0, 0, 1]\
    ))
    
    syms = [x1, y1, z1, alpha1, beta1, gamma1]
    
    return prTi, syms
Ejemplo n.º 2
0
    def generate_het(self):
        """
        Generate heterogeneous terms for integrating the Z_i and I_i terms.

        Returns
        -------
        None.

        """

        self.hetx_list, self.hety_list = ([] for i in range(2))
        # get the general expression for h in z before plugging in g,z.

        # column vectors ax ay for use in matrix A = [ax ay]
        self.ax = Matrix([[0], [0]])
        self.ay = Matrix([[0], [0]])

        for j in range(1, self.trunc_gh + 1):
            p1 = lib.kProd(j, self.dx)
            p2 = kp(p1, sym.eye(2))

            d1 = lib.vec(lib.df(self.NIC1, self.x, j + 1))
            d2 = lib.vec(lib.df(self.NIC2, self.x, j + 1))

            self.ax += (1 / math.factorial(j)) * p2 * d1
            self.ay += (1 / math.factorial(j)) * p2 * d2

        self.A = sym.zeros(2, 2)

        self.A[:, 0] = self.ax
        self.A[:, 1] = self.ay

        self.z_expansion = Matrix([[self.zx], [self.zy]])
        het = self.A * self.z_expansion

        # expand all terms
        self.hetx = sym.expand(het[0].subs([(self.dx1, self.gx),
                                            (self.dx2, self.gy)]))
        self.hety = sym.expand(het[1].subs([(self.dx1, self.gx),
                                            (self.dx2, self.gy)]))

        # collect all psi terms into factors of pis^k
        self.hetx_powers = sym.collect(self.hetx, self.psi, evaluate=False)
        self.hety_powers = sym.collect(self.hety, self.psi, evaluate=False)

        self.hetx_list = []
        self.hety_list = []

        counter = 0
        while (counter <= self.trunc_g + 1):

            # save current term
            self.hetx_list.append(self.hetx_powers[self.psi**counter])
            self.hety_list.append(self.hety_powers[self.psi**counter])

            counter += 1

        # substitute limit cycle
        for i in range(len(self.ghx_list)):
            self.hetx_list[i] = self.hetx_list[i].subs({
                self.x1:
                sym.cos(2 * sym.pi * self.t),
                self.x2:
                sym.sin(2 * sym.pi * self.t),
                sym.Indexed('gx', 0):
                s(0),
                sym.Indexed('gy', 0):
                s(0)
            })
            self.hety_list[i] = self.hety_list[i].subs({
                self.x1:
                sym.cos(2 * sym.pi * self.t),
                self.x2:
                sym.sin(2 * sym.pi * self.t),
                sym.Indexed('gx', 0):
                s(0),
                sym.Indexed('gy', 0):
                s(0)
            })
Ejemplo n.º 3
0
    def generate_gh(self):
        """
        generate heterogeneous terms for the Floquet eigenfunctions g.

        Returns
        -------
        list of symbolic heterogeneous terms in self.ghx_list, self.ghy_list.

        """

        self.ghx_list = []
        self.ghy_list = []

        # get the general expression for h before plugging in g.
        self.hx = 0
        self.hy = 0

        for i in range(2, self.trunc_gh + 1):
            # all x1,x2 are evaluated on limit cycle x=cos(t), y=sin(t)
            p = lib.kProd(i, self.dx)
            d1 = lib.vec(lib.df(self.NIC1, self.x, i))
            d2 = lib.vec(lib.df(self.NIC2, self.x, i))

            self.hx += (1 / math.factorial(i)) * np.dot(p, d1)
            self.hy += (1 / math.factorial(i)) * np.dot(p, d2)

        self.hx = sym.Matrix(self.hx)
        self.hy = sym.Matrix(self.hy)

        # expand all terms
        self.hx = sym.expand(
            self.hx.subs([(self.dx1, self.gx), (self.dx2, self.gy)]))
        self.hy = sym.expand(
            self.hy.subs([(self.dx1, self.gx), (self.dx2, self.gy)]))

        # collect all psi terms into list of some kind
        self.tempx = sym.collect(self.hx[0], self.psi, evaluate=False)
        self.tempy = sym.collect(self.hy[0], self.psi, evaluate=False)

        counter = 0
        while (counter <= self.trunc_g + 1):
            # save current term
            self.ghx_list.append(self.tempx[self.psi**counter])
            self.ghy_list.append(self.tempy[self.psi**counter])

            counter += 1

        # substitute limit cycle. maybe move elsewhere.
        for i in range(len(self.ghx_list)):
            self.ghx_list[i] = self.ghx_list[i].subs({
                self.x1:
                sym.cos(2 * sym.pi * self.t),
                self.x2:
                sym.sin(2 * sym.pi * self.t),
                sym.Indexed('gx', 0):
                s(0),
                sym.Indexed('gy', 0):
                s(0)
            })
            self.ghy_list[i] = self.ghy_list[i].subs({
                self.x1:
                sym.cos(2 * sym.pi * self.t),
                self.x2:
                sym.sin(2 * sym.pi * self.t),
                sym.Indexed('gx', 0):
                s(0),
                sym.Indexed('gy', 0):
                s(0)
            })
Ejemplo n.º 4
0
		"Cd": 0.3, # unitless
		"p": 1.3, # Kg/m**3
		"A": 0.0042, # m**2
		"m": 0.145,# kg
		"g": -9.8, # m/s**2
	}

	# time without drag
	tf = sympy.solve(1+45*np.sin(np.deg2rad(35)*2)*t+0.5*(-9.8)*t**2,t)[1]
	# distance without drag
	xf = qd.e(45*np.cos(np.deg2rad(35.)*2)*t, {"t": tf})
	print "distance without drag:",  xf
	print "time without drag:",  tf

	# drag equation
	dfdt = lambda x, v: qd.e(M([0, s("g")]) + (s("-1/2*p*Cd*A")*v.norm()**2*v.normalized()), c)
	v = M(["vx", "vy"])
	print "acceleration:", qd.e(M([0, s("g")]) + (s("-1/2*p*Cd*A")*v.norm()**2*v.normalized()), c)
	# initial velocity matrix
	v0 = M([45.*np.cos(np.deg2rad(35.)*2), 45.*np.sin(np.deg2rad(35.)*2)])
	x0 = M([0, 1])
	c['dt'] = 0.1
	c['tol'] = 0# 0.001*xf # 0.1% of estimated range
	rData = qd.rk4(dfdt, x0, v0, lambda t, x, v: x[1] > 0, c)
	print 'rk45 complete'
	hData = qd.heun(dfdt, x0, v0, lambda t, x, v: x[1] > 0, c)
	print 'modeuler complete'
	eData = qd.euler(dfdt, x0, v0, lambda t, x, v: x[1] > 0, c)
	print 'fwdeuler complete'
	plt.plot(rData[0], rData[1], marker='o', label='RK4')
	plt.plot(hData[0], hData[1], marker='.', label='Heun')
Ejemplo n.º 5
0
def createCalibEquations():
    """Generate and return symbolic calibration equations (1) in [Ref2]_.
    
    Returns
    -------
    Pph : sympy.matrices.matrices.MutableMatrix
        3 x 1 matrix containing symbolic equations (1) in [Ref2]_.
    
    J : sympy.matrices.matrices.MutableMatrix*)
        3 x 14 matrix representing the Jacobian of equations ``Pph``.
    
    prTi : sympy.matrices.matrices.MutableMatrix*)
        4 x 4 affine rotation matrix from US probe reference frame to US image reference frame.
    
    syms : dict
        Dictionary of where keys are variable names and values are ``sympy.core.symbol.Symbol`` objects. 
        These symbols were used to create equations in ``Pph``, ``J``, ``prTi``.
    
    variables : list
        14-elem list of variable names (see ``process.Process.calibrateProbe()``).
    
    mus : list
        14-elem list of varables measurement units.
    
    """
    
    # Pi
    sx = Symbol('sx')
    sy = Symbol('sy')
    u = Symbol('u')
    v = Symbol('v')
    Pi = Matrix(([sx * u],\
                 [sy * v],\
                 [0],\
                 [1]\
    ))
    
    # prTi
    prTi, syms = creatCalibMatrix()
    [x1, y1, z1, alpha1, beta1, gamma1] = syms
    
    # wTpr
    #wTpr = Matrix(MatrixSymbol('wTpr', 4, 4))
    wTpr = MatrixOfMatrixSymbol('wTpr', 4, 4)
    wTpr[3, 0:4] = np.array([0,0,0,1])
    
    # phTw
    x2 = Symbol('x2')
    y2 = Symbol('y2')
    z2 = Symbol('z2')
    alpha2 = Symbol('alpha2')
    beta2 = Symbol('beta2')
    gamma2 = Symbol('gamma2')
    
    phTw = Matrix(([c(alpha2)*c(beta2), c(alpha2)*s(beta2)*s(gamma2)-s(alpha2)*c(gamma2), c(alpha2)*s(beta2)*c(gamma2)+s(alpha2)*s(gamma2), x2],\
                   [s(alpha2)*c(beta2), s(alpha2)*s(beta2)*s(gamma2)+c(alpha2)*c(gamma2), s(alpha2)*s(beta2)*c(gamma2)-c(alpha2)*s(gamma2), y2],\
                   [-s(beta2), c(beta2)*s(gamma2), c(beta2)*c(gamma2), z2],\
                   [0, 0, 0, 1]\
    ))
    
    # Calculate full equations
    Pph = phTw * wTpr * prTi * Pi
    Pph = Pph[0:3,:]
    
    # Calculate full Jacobians 
    x = Matrix([sx, sy, x1, y1, z1, alpha1, beta1, gamma1, x2, y2, z2, alpha2, beta2, gamma2])
    J = Pph.jacobian(x)
    
    # Create symbols dictionary
    syms = {}
    for expr in Pph:
        atoms = list(expr.atoms(Symbol))
        for i in xrange(0, len(atoms)):
            syms[atoms[i].name] = atoms[i]
    
    # Create list of variables and measurements units
    variables = ['sx', 'sy', 'x1', 'y1', 'z1', 'alpha1', 'beta1', 'gamma1', 'x2', 'y2', 'z2', 'alpha2', 'beta2', 'gamma2']
    mus = ['mm/px', 'mm/px', 'mm', 'mm', 'mm', 'rad', 'rad', 'rad', 'mm', 'mm', 'mm', 'rad', 'rad', 'rad']
        
    # Return data
    return Pph, J, prTi, syms, variables, mus
Ejemplo n.º 6
0
    
    # Set path for markers coordinates file
    p.setKineFiles(('test_baloon_2ang.c3d',))

    # Calculate pose from US probe to laboratory reference frame
    p.calculatePoseForUSProbe(mkrList=('Rigid_Body_1-Marker_1','Rigid_Body_1-Marker_2','Rigid_Body_1-Marker_3','Rigid_Body_1-Marker_4'))

    # Calculate pose from US images to laboratory reference frame
    p.calculatePoseForUSImages()

    # Reorient global reference frame to be approximately aligned with US scans direction 
    from sympy import Matrix, Symbol, cos as c, sin as s
    alpha = Symbol('alpha')
    beta = Symbol('beta')
    T1 = Matrix(([1,0,0,0],
                 [0,c(alpha),s(alpha),0],
                 [0,-s(alpha),c(alpha),0],
                 [0,0,0,1]
    ))
    T = T1.evalf(subs={'alpha':np.deg2rad(-10.)})
    T = np.array(T).astype(np.float)
    
    # Set time frames for images that can be cointaned in the voxel array
    p.setValidFramesForVoxelArray(voxFrames='auto')
    
    # Calculate convenient pose for the voxel array
    p.calculateConvPose(T)
    
    # Calculate scale factors
    #fxyz = 'auto_bounded_parallel_scans'
    fxyz = (1,10,1)