Ejemplo n.º 1
0
def forceFromCoefficients(rocketState, environment, Cd, Cl, CMx, CMy, CMz,
                          CPLocation, refArea, refLength):
    ''' Initialize ForceMomentSystem from all aerodynamic coefficients '''
    q = AeroParameters.getDynamicPressure(rocketState, environment)
    if q == 0.0:
        # No force without dynamic pressure
        return ForceMomentSystem(Vector(0, 0, 0))
    nonDimConstant = q * refArea

    #### Drag ####
    localFrameAirVel = AeroParameters.getLocalFrameAirVel(
        rocketState, environment)
    dragDirection = localFrameAirVel.normalize()
    dragForce = dragDirection * Cd

    #### Lift ####
    # Find the lift force direction
    # Lift force will be in the same plane as the normalForceDirection & rocketFrameAirVel vectors
    # But, the lift force will be perpendicular to rocketFraeAirVel, whereas the normalForceDirection might form an acute angle with it
    # Rotate the normal force direction vector until it's perpendicular with rocketFrameAirVel
    normalForceDir = AeroParameters.getNormalAeroForceDirection(
        rocketState, environment)
    rotAxis = localFrameAirVel.crossProduct(normalForceDir)
    angle = math.pi / 2 - localFrameAirVel.angle(normalForceDir)
    rotatorQuat = Quaternion(rotAxis, angle)
    liftDirection = rotatorQuat.rotate(normalForceDir)
    liftForce = liftDirection * Cl

    # Combine and redimensionalize
    totalForce = (dragForce + liftForce) * nonDimConstant

    #### Moments ####
    moments = Vector(CMx, CMy, CMz) * nonDimConstant * refLength

    return ForceMomentSystem(totalForce, CPLocation, moments)
Ejemplo n.º 2
0
def forceFromCdCN(rocketState,
                  environment,
                  Cd,
                  CN,
                  CPLocation,
                  refArea,
                  moment=None):
    ''' 
        Convenience function for Barrowman Aero methods
        Initialize ForceMomentSystem from aerodynamic coefficients Cd and CN
        Cd should NOT already be adjusted for angle of attack 
        Moment should be a dimensional moment vector
    '''
    angleOfAttack = AeroParameters.getTotalAOA(rocketState, environment)
    q = AeroParameters.getDynamicPressure(rocketState, environment)

    #### Axial Force ####
    CA = getDragToAxialForceFactor(angleOfAttack) * Cd
    axialForce = Vector(0, 0, -CA)  #Axial force is in the negative Z-direction

    #### Normal Force ####
    normalForce = AeroParameters.getNormalAeroForceDirection(
        rocketState, environment) * CN

    totalForce = (axialForce + normalForce) * refArea * q
    return ForceMomentSystem(totalForce, CPLocation, moment)
Ejemplo n.º 3
0
    def test_getNormalAeroForceDirection(self):
        zeroAngVel = AngularVelocity(0,0,0)
        zeroPos = Vector(0,0,0)
        
        state1 = RigidBodyState(zeroPos, self.dummyVelocity1, self.dummyOrientation1, zeroAngVel)
        assertVectorsAlmostEqual(self, AeroParameters.getNormalAeroForceDirection(state1, self.currentConditions), Vector(0, -1, 0))

        state2 = RigidBodyState(zeroPos, self.dummyVelocity1, self.dummyOrientation2, zeroAngVel)
        assertVectorsAlmostEqual(self, AeroParameters.getNormalAeroForceDirection(state2, self.currentConditions), Vector(0, 1, 0))

        state3 = RigidBodyState(zeroPos, self.dummyVelocity1, self.dummyOrientation3, zeroAngVel)
        assertVectorsAlmostEqual(self, AeroParameters.getNormalAeroForceDirection(state3, self.currentConditions), Vector(1, 0, 0))

        state4 = RigidBodyState(zeroPos, self.dummyVelocity1, self.dummyOrientation4, zeroAngVel)
        assertVectorsAlmostEqual(self, AeroParameters.getNormalAeroForceDirection(state4, self.currentConditions), Vector(1, 0, 0))

        state5 = RigidBodyState(zeroPos, self.dummyVelocity1, self.dummyOrientation5, zeroAngVel)
        assertVectorsAlmostEqual(self, AeroParameters.getNormalAeroForceDirection(state5, self.currentConditions), Vector(0.707, -0.707, 0),3)

        assertVectorsAlmostEqual(self, AeroParameters.getNormalAeroForceDirection(self.rocketState8, self.currentConditions), Vector(-0.99999, 0.0022736, 0),3)

        # Prep rocket by calling getLocalFrameAirVel first to cache AOA result, then get cached result from getTotalAOA
        def testLocalFrameAirVelNormalForceDir(vel, orientation, expectedResult, precision=7):
            state = RigidBodyState(Vector(0,0,0), vel, orientation, AngularVelocity(0,0,0))
            assertVectorsAlmostEqual(self, AeroParameters.getNormalAeroForceDirection(state, self.currentConditions), expectedResult, precision)

        testLocalFrameAirVelNormalForceDir(self.dummyVelocity1, self.dummyOrientation1, Vector(0, -1, 0))
        testLocalFrameAirVelNormalForceDir(self.dummyVelocity1, self.dummyOrientation2, Vector(0, 1, 0))
        testLocalFrameAirVelNormalForceDir(self.dummyVelocity1, self.dummyOrientation3, Vector(1, 0, 0))
        testLocalFrameAirVelNormalForceDir(self.dummyVelocity1, self.dummyOrientation4, Vector(1, 0, 0))
        testLocalFrameAirVelNormalForceDir(self.dummyVelocity1, self.dummyOrientation5, Vector(0.707, -0.707, 0), 3)
        testLocalFrameAirVelNormalForceDir(self.rocketState8.velocity, self.rocketState8.orientation, Vector(-0.99999, 0.0022736, 0),3)
Ejemplo n.º 4
0
 def testLocalFrameAirVelNormalForceDir(vel, orientation, expectedResult, precision=7):
     state = RigidBodyState(Vector(0,0,0), vel, orientation, AngularVelocity(0,0,0))
     assertVectorsAlmostEqual(self, AeroParameters.getNormalAeroForceDirection(state, self.currentConditions), expectedResult, precision)