예제 #1
2
    def test_fuel_tanks_content(self):
        script_path = self.sandbox.path_to_jsbsim_file('scripts', 'J2460.xml')
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(script_path)
        fdm.run_ic()

        tree = et.parse(script_path)
        use_tag = tree.getroot().find('use')
        aircraft_name = use_tag.attrib['aircraft']
        aircraft_path = self.sandbox.path_to_jsbsim_file('aircraft',
                                                         aircraft_name)
        aircraft_tree = et.parse(os.path.join(aircraft_path,
                                              aircraft_name+'.xml'))

        total_fuel_quantity = 0.0
        total_oxidizer_quantity = 0.0
        for tank in aircraft_tree.findall('propulsion/tank'):
            contents = float(tank.find('contents').text)
            if tank.attrib['type'] == "FUEL":
                total_fuel_quantity += contents
            elif tank.attrib['type'] == 'OXIDIZER':
                total_oxidizer_quantity += contents

        self.assertAlmostEqual(fdm['propulsion/total-fuel-lbs'],
                               total_fuel_quantity)

        self.assertAlmostEqual(fdm['propulsion/total-oxidizer-lbs'],
                               total_oxidizer_quantity)
예제 #2
0
 def test_trim_on_ground(self):
     fdm = CreateFDM(self.sandbox)
     fdm.load_model('c172x')
     fdm['ic/theta-deg'] = 10.0
     fdm.run_ic()
     fdm['ic/theta-deg'] = 0.0
     fdm['simulation/do_simple_trim'] = 2
예제 #3
0
    def testDebugLvl(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(
            self.sandbox.path_to_jsbsim_file('scripts', 'ball_orbit.xml'))
        fdm.run_ic()

        ExecuteUntil(fdm, 1000.)

        ref = pd.read_csv('BallOut.csv', index_col=0)
        del fdm

        os.environ["JSBSIM_DEBUG"] = str(0)
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(
            self.sandbox.path_to_jsbsim_file('scripts', 'ball_orbit.xml'))
        fdm.run_ic()

        ExecuteUntil(fdm, 1000.)

        current = pd.read_csv('BallOut.csv', index_col=0)

        # Check the data are matching i.e. the time steps are the same between
        # the two data sets and that the output data are also the same.
        self.assertTrue(isDataMatching(ref, current))

        # Find all the data that are differing by more than 1E-8 between the
        # two data sets.
        diff = FindDifferences(ref, current, 1E-8)
        self.longMessage = True
        self.assertEqual(len(diff), 0, msg='\n' + diff.to_string())
예제 #4
0
    def test_hold_down_with_gnd_reactions(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(self.sandbox.path_to_jsbsim_file('scripts',
                                                         'c1721.xml'))
        fdm.run_ic()
        ExecuteUntil(fdm, 0.25)

        fdm['forces/hold-down'] = 1.0
        h0 = fdm['position/h-sl-ft']
        pitch = fdm['attitude/pitch-rad']
        roll = fdm['attitude/roll-rad']
        heading = fdm['attitude/heading-true-rad']

        while fdm['simulation/sim-time-sec'] < 2.0:
            fdm.run()
            self.assertAlmostEqual(fdm['accelerations/pdot-rad_sec2'], 0.0)
            self.assertAlmostEqual(fdm['accelerations/qdot-rad_sec2'], 0.0)
            self.assertAlmostEqual(fdm['accelerations/rdot-rad_sec2'], 0.0)
            self.assertAlmostEqual(fdm['accelerations/udot-ft_sec2'], 0.0)
            self.assertAlmostEqual(fdm['accelerations/vdot-ft_sec2'], 0.0)
            self.assertAlmostEqual(fdm['accelerations/wdot-ft_sec2'], 0.0)

        self.assertAlmostEqual(fdm['position/h-sl-ft'], h0, delta=1E-6)
        self.assertAlmostEqual(fdm['attitude/pitch-rad'], pitch)
        self.assertAlmostEqual(fdm['attitude/roll-rad'], roll)
        self.assertAlmostEqual(fdm['attitude/heading-true-rad'], heading)
예제 #5
0
    def test_output(self):
        tree = et.parse(self.script_path)
        output_tag = et.SubElement(tree.getroot(), 'output')
        output_tag.attrib['name'] = 'test.csv'
        output_tag.attrib['type'] = 'CSV'
        output_tag.attrib['rate'] = '10'
        property_tag = et.SubElement(output_tag, 'property')
        property_tag.text = 'position/vrp-radius-ft'
        tree.write('c1722_0.xml')

        fdm = CreateFDM(self.sandbox)
        fdm.load_script('c1722_0.xml')
        fdm.run_ic()
        ExecuteUntil(fdm, 10.)

        self.assertTrue(self.sandbox.exists(output_tag.attrib['name']),
                        msg="The file 'output.csv' has not been created")
        orig = pd.read_csv('JSBout172B.csv', index_col=0)
        test = pd.read_csv('test.csv', index_col=0)
        pname = '/fdm/jsbsim/' + property_tag.text
        ref = orig[pname]
        mod = test[pname]

        # Check the data are matching i.e. the time steps are the same between
        # the two data sets.
        self.assertTrue(isDataMatching(ref, mod))

        # Find all the data that are differing by more than 1E-8 between the
        # two data sets.
        delta = pd.concat([np.abs(ref - mod), ref, mod], axis=1)
        delta.columns = ['delta', 'ref value', 'value']
        diff = delta[delta['delta'] > 1E-8]
        self.longMessage = True
        self.assertEqual(len(diff), 0, msg='\n'+diff.to_string())
예제 #6
0
    def testDebugLvl(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(
            self.sandbox.path_to_jsbsim_file('scripts', 'ball_orbit.xml'))
        fdm.run_ic()

        ExecuteUntil(fdm, 1000.)

        ref, current = Table(), Table()
        ref.ReadCSV(self.sandbox('BallOut.csv'))
        del fdm

        os.environ["JSBSIM_DEBUG"] = str(0)
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(
            self.sandbox.path_to_jsbsim_file('scripts', 'ball_orbit.xml'))
        fdm.run_ic()

        ExecuteUntil(fdm, 1000.)

        current.ReadCSV(self.sandbox('BallOut.csv'))

        diff = ref.compare(current)
        self.longMessage = True
        self.assertTrue(diff.empty(), msg='\n' + repr(diff))
예제 #7
0
    def test_FG_reset(self):
        # This test reproduces how FlightGear resets. The important thing is
        # that the property manager is managed by FlightGear. So it is not
        # deleted when the JSBSim instance is killed.
        pm = jsbsim.FGPropertyManager(new_instance=True)

        self.assertFalse(pm.hasNode('fdm/jsbsim/ic/lat-geod-deg'))

        fdm = CreateFDM(self.sandbox, pm)
        fdm.load_model('ball')
        self.assertAlmostEqual(fdm['ic/lat-geod-deg'], 0.0)

        fdm['ic/lat-geod-deg'] = 45.0
        fdm.run_ic()

        del fdm

        # Check that the property ic/lat-geod-deg has survived the JSBSim
        # instance.
        self.assertTrue(pm.hasNode('fdm/jsbsim/ic/lat-geod-deg'))

        # Re-use the property manager just as FlightGear does.
        fdm = CreateFDM(self.sandbox, pm)
        self.assertAlmostEqual(fdm['ic/lat-geod-deg'], 45.0)

        del fdm
예제 #8
0
def SubProcessScriptExecution(sandbox, script_path):
    fdm = CreateFDM(sandbox)
    fdm.load_script(script_path)
    fdm.run_ic()

    while fdm.run():
        pass
예제 #9
0
    def Compare(self, section):
        # Rerun the script with the modified aircraft definition
        self.sandbox.delete_csv_files()
        fdm = CreateFDM(self.sandbox)
        # We need to tell JSBSim that the aircraft definition is located in the
        # directory build/.../aircraft
        fdm.set_aircraft_path('aircraft')
        fdm.set_output_directive(self.sandbox.path_to_jsbsim_file('tests',
                                                                  'output.xml'))
        fdm.load_script(self.script)
        fdm['simulation/randomseed'] = 0.0

        fdm.run_ic()
        ExecuteUntil(fdm, 50.0)

        mod = pd.read_csv('output.csv', index_col=0)

        # Check the data are matching i.e. the time steps are the same between
        # the two data sets and that the output data are also the same.
        self.assertTrue(isDataMatching(self.ref, mod))

        # Whether the data is read from the aircraft definition file or from an
        # external file, the results shall be exactly identical. Hence the
        # precision set to 0.0.
        diff = FindDifferences(self.ref, mod, 0.0)
        self.assertEqual(len(diff), 0,
                         msg='\nTesting section "'+section+'"\n'+diff.to_string())
예제 #10
0
    def testAircrafts(self):
        aircraft_path = self.sandbox.path_to_jsbsim_file('aircraft')
        for d in os.listdir(aircraft_path):
            fullpath = os.path.join(aircraft_path, d)

            # Is d a directory ?
            if not os.path.isdir(fullpath):
                continue

            f = os.path.join(aircraft_path, d, d + '.xml')

            # Is f an aircraft definition file ?
            if not CheckXMLFile(f, 'fdm_config'):
                continue

            if d in ('blank'):
                continue

            fdm = CreateFDM(self.sandbox)
            self.assertTrue(fdm.load_model(d),
                            msg='Failed to load aircraft %s' % (d, ))

            for f in os.listdir(fullpath):
                f = os.path.join(aircraft_path, d, f)
                if CheckXMLFile(f, 'initialize'):
                    self.assertTrue(
                        fdm.load_ic(f, False),
                        msg='Failed to load IC %s for aircraft %s' % (f, d))
                    try:
                        fdm.run_ic()
                    except RuntimeError:
                        self.fail('Failed to run IC %s for aircraft %s' %
                                  (f, d))

            del fdm
예제 #11
0
    def Compare(self, section):
        # Rerun the script with the modified aircraft definition
        self.sandbox.delete_csv_files()
        fdm = CreateFDM(self.sandbox)
        # We need to tell JSBSim that the aircraft definition is located in the
        # directory build/.../aircraft
        fdm.set_aircraft_path('aircraft')
        fdm.set_output_directive(
            self.sandbox.path_to_jsbsim_file('tests', 'output.xml'))
        fdm.load_script(self.script)
        fdm.set_property_value('simulation/randomseed', 0.0)

        fdm.run_ic()
        ExecuteUntil(fdm, 50.0)

        mod = Table()
        mod.ReadCSV(self.sandbox('output.csv'))

        # Whether the data is read from the aircraft definition file or from an
        # external file, the results shall be exactly identical. Hence the
        # precision set to 0.0.
        diff = self.ref.compare(mod, 0.0)
        self.assertTrue(diff.empty(),
                        msg='\nTesting section "' + section + '"\n' +
                        repr(diff))
예제 #12
0
    def test_fuel_tanks_content(self):
        script_path = self.sandbox.path_to_jsbsim_file('scripts', 'J2460.xml')
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(script_path)
        fdm.run_ic()

        tree = et.parse(script_path)
        use_tag = tree.getroot().find('use')
        aircraft_name = use_tag.attrib['aircraft']
        aircraft_path = self.sandbox.path_to_jsbsim_file(
            'aircraft', aircraft_name)
        aircraft_tree = et.parse(
            os.path.join(aircraft_path, aircraft_name + '.xml'))

        total_fuel_quantity = 0.0
        total_oxidizer_quantity = 0.0
        for tank in aircraft_tree.findall('propulsion/tank'):
            contents = float(tank.find('contents').text)
            if tank.attrib['type'] == "FUEL":
                total_fuel_quantity += contents
            elif tank.attrib['type'] == 'OXIDIZER':
                total_oxidizer_quantity += contents

        self.assertAlmostEqual(fdm['propulsion/total-fuel-lbs'],
                               total_fuel_quantity)

        self.assertAlmostEqual(fdm['propulsion/total-oxidizer-lbs'],
                               total_oxidizer_quantity)
예제 #13
0
    def testDebugLvl(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(self.sandbox.path_to_jsbsim_file('scripts',
                                                         'ball_orbit.xml'))
        fdm.run_ic()

        ExecuteUntil(fdm, 1000.)

        ref = pd.read_csv('BallOut.csv', index_col=0)
        del fdm

        os.environ["JSBSIM_DEBUG"] = str(0)
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(self.sandbox.path_to_jsbsim_file('scripts',
                                                         'ball_orbit.xml'))
        fdm.run_ic()

        ExecuteUntil(fdm, 1000.)

        current = pd.read_csv('BallOut.csv', index_col=0)

        # Check the data are matching i.e. the time steps are the same between
        # the two data sets and that the output data are also the same.
        self.assertTrue(isDataMatching(ref, current))

        # Find all the data that are differing by more than 1E-8 between the
        # two data sets.
        diff = FindDifferences(ref, current, 1E-8)
        self.longMessage = True
        self.assertEqual(len(diff), 0, msg='\n'+diff.to_string())
예제 #14
0
    def testOrbit(self):
        script_name = 'ball_orbit.xml'
        script_path = self.sandbox.path_to_jsbsim_file('scripts', script_name)
        self.AddAccelerometersToAircraft(script_path)

        # The time step is too small in ball_orbit so let's increase it to 0.1s
        # for a quicker run
        tree = et.parse(script_path)
        run_tag = tree.getroot().find('./run')
        run_tag.attrib['dt'] = '0.1'
        tree.write(script_name)

        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_script(script_name)
        # Switch the accel on
        fdm['fcs/accelerometer/on'] = 1.0
        fdm.run_ic()

        while fdm.run():
            self.assertAlmostEqual(fdm['fcs/accelerometer/X'], 0.0, delta=1E-8)
            self.assertAlmostEqual(fdm['fcs/accelerometer/Y'], 0.0, delta=1E-8)
            self.assertAlmostEqual(fdm['fcs/accelerometer/Z'], 0.0, delta=1E-8)
            self.assertAlmostEqual(fdm['accelerations/a-pilot-x-ft_sec2'],
                                   0.0,
                                   delta=1E-8)
            self.assertAlmostEqual(fdm['accelerations/a-pilot-y-ft_sec2'],
                                   0.0,
                                   delta=1E-8)
            self.assertAlmostEqual(fdm['accelerations/a-pilot-z-ft_sec2'],
                                   0.0,
                                   delta=1E-8)

        del fdm
예제 #15
0
    def test_humidity_parameters(self):
        # Table: Dew point (deg C), Vapor pressure (Pa), RH
        humidity_table = [
            (-40.0,   19.021201,     0.815452, 1.2040321),
            (-30.0,   51.168875,     2.193645, 1.2038877),
            (-20.0,  125.965126,    5.4002118, 1.2035517),
            (-10.0,  287.031031,   12.3052182, 1.2028282),
            (  0.0,  611.2,        26.2025655, 1.2013721),
            ( 10.0, 1226.030206,   52.5607604, 1.1986102),
            ( 20.0, 2332.5960221, 100.,        1.1936395)
        ]

        fdm = CreateFDM(self.sandbox)
        fdm.load_model('ball')
        fdm['atmosphere/delta-T'] = 5.0*self.K_to_R
        fdm.run_ic()

        Psat = fdm['atmosphere/saturated-vapor-pressure-psf']/self.Pa_to_psf

        self.assertAlmostEqual(Psat, humidity_table[-1][1])
        self.assertAlmostEqual(fdm['atmosphere/vapor-pressure-psf'], 0.0)
        self.assertAlmostEqual(fdm['atmosphere/RH'], 0.0)
        self.assertAlmostEqual(fdm['atmosphere/dew-point-R'], 54.054)

        for Tdp, Pv, RH, rho in humidity_table:
            fdm['atmosphere/dew-point-R'] = (Tdp+273.15)*self.K_to_R
            fdm.run_ic()
            self.assertAlmostEqual(fdm['atmosphere/vapor-pressure-psf'],
                                   Pv*self.Pa_to_psf)
            self.assertAlmostEqual(fdm['atmosphere/RH'], RH)
            self.assertAlmostEqual(fdm['atmosphere/rho-slugs_ft3']/(self.kg_to_slug*math.pow(0.3048,3)),
                                   rho)

        del fdm
예제 #16
0
    def test_direct_steer(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_model('c172r')
        aircraft_path = self.sandbox.path_to_jsbsim_file('aircraft')
        fdm.load_ic(os.path.join(aircraft_path, 'c172r', 'reset00'), False)
        fdm.run_ic()
        self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 0.0)
        self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 0.0)

        # Should be part of a unit test in C++ ?
        fpectl.turnon_sigfpe()

        grndreact = fdm.get_ground_reactions()
        for i in xrange(grndreact.get_num_gear_units()):
            gear = grndreact.get_gear_unit(i)
            self.assertEqual(gear.get_steer_norm(), 0.0)

        fpectl.turnoff_sigfpe()

        fdm['fcs/steer-pos-deg'] = 5.0
        self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 5.0)
        fdm.run()
        self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 0.0)
        fdm['fcs/steer-cmd-norm'] = 1.0
        self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
        fdm.run()
        self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
        self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 10.0)
예제 #17
0
    def LoadScript(self, tree, script_path, prop_output_to_CSV=[]):
        # Make a local copy of files referenced by the script.
        for element in list(tree.getroot()):
            if 'file' in element.keys():
                name = append_xml(element.attrib['file'])
                name_with_path = os.path.join(os.path.dirname(script_path),
                                              name)
                if os.path.exists(name_with_path):
                    shutil.copy(name_with_path, name)

        # Generate a CSV file to check that it is correctly initialized
        # with the initial values
        output_tag = et.SubElement(tree.getroot(), 'output')
        output_tag.attrib['name'] = 'check_csv_values.csv'
        output_tag.attrib['type'] = 'CSV'
        output_tag.attrib['rate'] = '10'
        position_tag = et.SubElement(output_tag, 'position')
        position_tag.text = 'ON'
        velocities_tag = et.SubElement(output_tag, 'velocities')
        velocities_tag.text = 'ON'
        for props in prop_output_to_CSV:
            property_tag = et.SubElement(output_tag, 'property')
            property_tag.text = props
        f = os.path.split(script_path)[-1]  # Script name
        tree.write(f)

        # Initialize the script
        fdm = CreateFDM(self.sandbox)
        self.assertTrue(fdm.load_script(f),
                        msg="Failed to load script %s" % (f, ))
        fdm.run_ic()

        return (f, fdm)
예제 #18
0
    def testOrbit(self):
        script_name = 'ball_orbit.xml'
        script_path = self.sandbox.path_to_jsbsim_file('scripts', script_name)
        self.AddAccelerometersToAircraft(script_path)

        # The time step is too small in ball_orbit so let's increase it to 0.1s
        # for a quicker run
        tree = et.parse(script_path)
        run_tag = tree.getroot().find('./run')
        run_tag.attrib['dt'] = '0.1'
        tree.write(script_name)

        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_script(script_name)
        # Switch the accel on
        fdm['fcs/accelerometer/on'] = 1.0
        fdm.run_ic()

        while fdm.run():
            self.assertAlmostEqual(fdm['fcs/accelerometer/X'], 0.0, delta=1E-8)
            self.assertAlmostEqual(fdm['fcs/accelerometer/Y'], 0.0, delta=1E-8)
            self.assertAlmostEqual(fdm['fcs/accelerometer/Z'], 0.0, delta=1E-8)
            self.assertAlmostEqual(fdm['accelerations/a-pilot-x-ft_sec2'], 0.0,
                                   delta=1E-8)
            self.assertAlmostEqual(fdm['accelerations/a-pilot-y-ft_sec2'], 0.0,
                                   delta=1E-8)
            self.assertAlmostEqual(fdm['accelerations/a-pilot-z-ft_sec2'], 0.0,
                                   delta=1E-8)

        del fdm
예제 #19
0
 def test_steer_with_fcs(self):
     fdm = CreateFDM(self.sandbox)
     fdm.load_model('L410')
     aircraft_path = self.sandbox.path_to_jsbsim_file('aircraft')
     fdm.load_ic(os.path.join(aircraft_path, 'L410', 'reset00'), False)
     fdm.run_ic()
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 0.0)
     self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 0.0)
     fdm['fcs/steer-cmd-norm'] = 1.0
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
     fdm.run()
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
     self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 5.0)
     fdm['/controls/switches/full-steering-sw'] = 1.0
     fdm.run()
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
     self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 0.0)
     fdm['/controls/switches/full-steering-sw'] = 2.0
     fdm.run()
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
     self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 45.0)
     fdm['fcs/steer-cmd-norm'] = -0.5
     fdm.run()
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], -0.5)
     self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], -22.5)
예제 #20
0
    def LoadScript(self, tree, script_path, prop_output_to_CSV=[]):
        # Make a local copy of files referenced by the script.
        for element in list(tree.getroot()):
            if 'file' in element.keys():
                name = append_xml(element.attrib['file'])
                name_with_path = os.path.join(os.path.dirname(script_path),
                                              name)
                if os.path.exists(name_with_path):
                    shutil.copy(name_with_path, name)

        # Generate a CSV file to check that it is correctly initialized
        # with the initial values
        output_tag = et.SubElement(tree.getroot(), 'output')
        output_tag.attrib['name'] = 'check_csv_values.csv'
        output_tag.attrib['type'] = 'CSV'
        output_tag.attrib['rate'] = '10'
        position_tag = et.SubElement(output_tag, 'position')
        position_tag.text = 'ON'
        velocities_tag = et.SubElement(output_tag, 'velocities')
        velocities_tag.text = 'ON'
        for props in prop_output_to_CSV:
            property_tag = et.SubElement(output_tag, 'property')
            property_tag.text = props
        f = os.path.split(script_path)[-1]  # Script name
        tree.write(f)

        # Initialize the script
        fdm = CreateFDM(self.sandbox)
        self.assertTrue(fdm.load_script(f),
                        msg="Failed to load script %s" % (f,))
        fdm.run_ic()

        return (f, fdm)
예제 #21
0
    def test_waypoint(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_model('c310')
        aircraft_path = self.sandbox.path_to_jsbsim_file('aircraft')
        fdm.load_ic(os.path.join(aircraft_path, 'c310', 'reset00'), False)

        slr = 20925646.32546  # Sea Level Radius
        TestCases = (
            (0.25 * math.pi, 0.5 * math.pi, 0.0, 0.0),
            (0.0, 0.5 * math.pi, math.pi, slr * 0.25 * math.pi),
            # North pole
            (0.5 * math.pi, 0.5 * math.pi, 0.0, slr * 0.25 * math.pi),
            # South pole
            (-0.5 * math.pi, 0.5 * math.pi, math.pi, slr * 0.75 * math.pi),
            (0.0, 0.0, 1.5 * math.pi, slr * 0.5 * math.pi),
            (0.0, math.pi, 0.5 * math.pi, slr * 0.5 * math.pi))

        fdm['ic/lat-gc-rad'] = TestCases[0][0]
        fdm['ic/long-gc-rad'] = TestCases[0][1]

        for case in TestCases:
            fdm['guidance/target_wp_latitude_rad'] = case[0]
            fdm['guidance/target_wp_longitude_rad'] = case[1]
            fdm.run_ic()
            self.assertAlmostEqual(fdm['guidance/wp-heading-rad'], case[2])
            self.assertAlmostEqual(fdm['guidance/wp-distance'], case[3])
예제 #22
0
    def test_output(self):
        tree = et.parse(self.script_path)
        output_tag = et.SubElement(tree.getroot(), 'output')
        output_tag.attrib['name'] = 'test.csv'
        output_tag.attrib['type'] = 'CSV'
        output_tag.attrib['rate'] = '10'
        property_tag = et.SubElement(output_tag, 'property')
        property_tag.text = 'position/vrp-radius-ft'
        tree.write('c1722_0.xml')

        fdm = CreateFDM(self.sandbox)
        fdm.load_script('c1722_0.xml')
        fdm.run_ic()
        ExecuteUntil(fdm, 10.)

        self.assertTrue(self.sandbox.exists(output_tag.attrib['name']),
                        msg="The file 'output.csv' has not been created")
        orig = pd.read_csv('JSBout172B.csv', index_col=0)
        test = pd.read_csv('test.csv', index_col=0)
        pname = '/fdm/jsbsim/' + property_tag.text
        ref = orig[pname]
        mod = test[pname]

        # Check the data are matching i.e. the time steps are the same between
        # the two data sets.
        self.assertTrue(isDataMatching(ref, mod))

        # Find all the data that are differing by more than 1E-8 between the
        # two data sets.
        delta = pd.concat([np.abs(ref - mod), ref, mod], axis=1)
        delta.columns = ['delta', 'ref value', 'value']
        diff = delta[delta['delta'] > 1E-8]
        self.longMessage = True
        self.assertEqual(len(diff), 0, msg='\n' + diff.to_string())
예제 #23
0
 def test_steer_with_fcs(self):
     fdm = CreateFDM(self.sandbox)
     fdm.load_model('L410')
     aircraft_path = self.sandbox.path_to_jsbsim_file('aircraft')
     fdm.load_ic(os.path.join(aircraft_path, 'L410', 'reset00'), False)
     fdm.run_ic()
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 0.0)
     self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 0.0)
     fdm['fcs/steer-cmd-norm'] = 1.0
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
     fdm.run()
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
     self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 5.0)
     fdm['/controls/switches/full-steering-sw'] = 1.0
     fdm.run()
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
     self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 0.0)
     fdm['/controls/switches/full-steering-sw'] = 2.0
     fdm.run()
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
     self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 45.0)
     fdm['fcs/steer-cmd-norm'] = -0.5
     fdm.run()
     self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], -0.5)
     self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], -22.5)
예제 #24
0
    def test_direct_steer(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_model('c172r')
        aircraft_path = self.sandbox.path_to_jsbsim_file('aircraft')
        fdm.load_ic(os.path.join(aircraft_path, 'c172r', 'reset00'), False)
        fdm.run_ic()
        self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 0.0)
        self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 0.0)

        # Should be part of a unit test in C++ ?
        fpectl.turnon_sigfpe()

        grndreact = fdm.get_ground_reactions()
        for i in xrange(grndreact.get_num_gear_units()):
            gear = grndreact.get_gear_unit(i)
            self.assertEqual(gear.get_steer_norm(), 0.0)

        fpectl.turnoff_sigfpe()

        fdm['fcs/steer-pos-deg'] = 5.0
        self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 5.0)
        fdm.run()
        self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 0.0)
        fdm['fcs/steer-cmd-norm'] = 1.0
        self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
        fdm.run()
        self.assertAlmostEqual(fdm['fcs/steer-cmd-norm'], 1.0)
        self.assertAlmostEqual(fdm['fcs/steer-pos-deg'], 10.0)
예제 #25
0
    def test_CAS_ic(self):
        script_name = 'Short_S23_3.xml'
        script_path = self.sandbox.path_to_jsbsim_file('scripts', script_name)

        # Add a Pitot angle to the Short S23
        tree, aircraft_name, path_to_jsbsim_aircrafts = CopyAircraftDef(script_path, self.sandbox)
        self.addPitotTube(tree.getroot(), 5.0)
        tree.write(self.sandbox('aircraft', aircraft_name,
                                aircraft_name+'.xml'))

        # Read the CAS specified in the IC file
        tree = et.parse(script_path)
        use_element = tree.getroot().find('use')
        IC_file = use_element.attrib['initialize']
        tree = et.parse(os.path.join(path_to_jsbsim_aircrafts,
                                     append_xml(IC_file)))
        vc_tag = tree.getroot().find('./vc')
        VCAS = float(vc_tag.text)
        if 'unit' in vc_tag.attrib and vc_tag.attrib['unit'] == 'FT/SEC':
            VCAS /= 1.68781  # Converts in kts

        # Run the IC and check that the model is initialized correctly
        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_script(script_path)
        fdm.run_ic()

        self.assertAlmostEqual(fdm['ic/vc-kts'], VCAS, delta=1E-7)
        self.assertAlmostEqual(fdm['velocities/vc-kts'], VCAS, delta=1E-7)
예제 #26
0
    def testAircrafts(self):
        aircraft_path = self.sandbox.path_to_jsbsim_file('aircraft')
        for d in os.listdir(aircraft_path):
            fullpath = os.path.join(aircraft_path, d)

            # Is d a directory ?
            if not os.path.isdir(fullpath):
                continue

            f = os.path.join(aircraft_path, d, d+'.xml')

            # Is f an aircraft definition file ?
            if not CheckXMLFile(f, 'fdm_config'):
                continue

            if d in ('blank'):
                continue

            fdm = CreateFDM(self.sandbox)
            self.assertTrue(fdm.load_model(d),
                            msg='Failed to load aircraft %s' % (d,))

            for f in os.listdir(fullpath):
                f = os.path.join(aircraft_path, d, f)
                if CheckXMLFile(f, 'initialize'):
                    self.assertTrue(fdm.load_ic(f, False),
                                    msg='Failed to load IC %s for aircraft %s' % (f, d))
                    try:
                        fdm.run_ic()
                    except RuntimeError:
                        self.fail('Failed to run IC %s for aircraft %s' % (f, d))

            del fdm
예제 #27
0
    def test_wind_frame(self):
        script_path = self.sandbox.path_to_jsbsim_file('scripts',
                                                       'ball_chute.xml')
        fdm = CreateFDM(self.sandbox)

        fdm.load_script(script_path)
        fdm.run_ic()

        self.assertAlmostEqual(
            fdm['external_reactions/parachute/location-x-in'], 12.0)
        self.assertAlmostEqual(
            fdm['external_reactions/parachute/location-y-in'], 0.0)
        self.assertAlmostEqual(
            fdm['external_reactions/parachute/location-z-in'], 0.0)
        self.assertAlmostEqual(fdm['external_reactions/parachute/x'], -1.0)
        self.assertAlmostEqual(fdm['external_reactions/parachute/y'], 0.0)
        self.assertAlmostEqual(fdm['external_reactions/parachute/z'], 0.0)

        while fdm.run():
            Tw2b = fdm.get_auxiliary().get_Tw2b()
            mag = fdm['aero/qbar-psf'] * fdm[
                'fcs/parachute_reef_pos_norm'] * 20.0
            f = Tw2b * np.mat([-1.0, 0.0, 0.0]).T * mag
            self.assertAlmostEqual(fdm['forces/fbx-external-lbs'], f[0, 0])
            self.assertAlmostEqual(fdm['forces/fby-external-lbs'], f[1, 0])
            self.assertAlmostEqual(fdm['forces/fbz-external-lbs'], f[2, 0])

            m = np.cross(self.getLeverArm(fdm, 'parachute'),
                         np.array([f[0, 0], f[1, 0], f[2, 0]]))
            self.assertAlmostEqual(fdm['moments/l-external-lbsft'], m[0])
            self.assertAlmostEqual(fdm['moments/m-external-lbsft'], m[1])
            self.assertAlmostEqual(fdm['moments/n-external-lbsft'], m[2])
예제 #28
0
    def Compare(self, section):
        # Rerun the script with the modified aircraft definition
        self.sandbox.delete_csv_files()
        fdm = CreateFDM(self.sandbox)
        # We need to tell JSBSim that the aircraft definition is located in the
        # directory build/.../aircraft
        fdm.set_aircraft_path('aircraft')
        fdm.set_output_directive(
            self.sandbox.path_to_jsbsim_file('tests', 'output.xml'))
        fdm.load_script(self.script)
        fdm['simulation/randomseed'] = 0.0

        fdm.run_ic()
        ExecuteUntil(fdm, 50.0)

        mod = pd.read_csv('output.csv', index_col=0)

        # Check the data are matching i.e. the time steps are the same between
        # the two data sets and that the output data are also the same.
        self.assertTrue(isDataMatching(self.ref, mod))

        # Whether the data is read from the aircraft definition file or from an
        # external file, the results shall be exactly identical. Hence the
        # precision set to 0.0.
        diff = FindDifferences(self.ref, mod, 0.0)
        self.assertEqual(len(diff),
                         0,
                         msg='\nTesting section "' + section + '"\n' +
                         diff.to_string())
예제 #29
0
    def test_pitot_angle(self):
        script_name = 'ball_chute.xml'
        script_path = self.sandbox.path_to_jsbsim_file('scripts', script_name)

        # Add a Pitot angle to the Cessna 172
        tree, aircraft_name, path_to_jsbsim_aircrafts = CopyAircraftDef(
            script_path, self.sandbox)
        root = tree.getroot()
        pitot_angle_deg = 5.0
        self.addPitotTube(root, 5.0)
        contact_tag = root.find('./ground_reactions/contact')
        contact_tag.attrib['type'] = 'STRUCTURE'
        tree.write(
            self.sandbox('aircraft', aircraft_name, aircraft_name + '.xml'))

        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_model('ball')
        pitot_angle = pitot_angle_deg * math.pi / 180.
        weight = fdm['inertia/weight-lbs']
        spring_tag = contact_tag.find('./spring_coeff')
        spring_coeff = float(spring_tag.text)
        print("Weight=%d Spring=%d" % (weight, spring_coeff))
        fdm['ic/h-sl-ft'] = weight / spring_coeff
        fdm['forces/hold-down'] = 1.0
        fdm.run_ic()

        ExecuteUntil(fdm, 10.)

        for i in range(36):
            for j in range(-9, 10):
                angle = math.pi * i / 18.0
                angle2 = math.pi * j / 18.0
                ca2 = math.cos(angle2)
                fdm['atmosphere/wind-north-fps'] = 10. * math.cos(angle) * ca2
                fdm['atmosphere/wind-east-fps'] = 10. * math.sin(angle) * ca2
                fdm['atmosphere/wind-down-fps'] = 10. * math.sin(angle2)
                fdm.run()

                vg = fdm['velocities/vg-fps']
                self.assertAlmostEqual(vg, 0.0, delta=1E-7)

                vt = fdm['velocities/vt-fps']
                self.assertAlmostEqual(vt, 10., delta=1E-7)

                mach = vt / fdm['atmosphere/a-fps']
                P = fdm['atmosphere/P-psf']
                pt = P * math.pow(1 + 0.2 * mach * mach, 3.5)
                psl = fdm['atmosphere/P-sl-psf']
                rhosl = fdm['atmosphere/rho-sl-slugs_ft3']
                A = math.pow((pt - P) / psl + 1.0, 1.0 / 3.5)
                alpha = fdm['aero/alpha-rad']
                beta = fdm['aero/beta-rad']
                vc = math.sqrt(
                    7.0 * psl / rhosl *
                    (A - 1.0)) * math.cos(alpha + pitot_angle) * math.cos(beta)

                self.assertAlmostEqual(fdm['velocities/vc-kts'],
                                       max(0.0, vc) / 1.68781,
                                       delta=1E-7)
예제 #30
0
    def testKinematicTiming(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_model('c172r')
        fdm.load_ic(self.sandbox.path_to_jsbsim_file('aircraft', 'c172r',
                                                     'reset00'), False)
        fdm.run_ic()
        self.assertEqual(fdm['fcs/flap-cmd-norm'], 0.0)
        self.assertEqual(fdm['fcs/flap-pos-deg'], 0.0)

        # Test the flap down sequence. The flap command is set to a value
        # higher than 1.0 to check that JSBSim clamps it to 1.0
        fdm['fcs/flap-cmd-norm'] = 1.5
        t = fdm['simulation/sim-time-sec']

        while t < 2.0:
            self.assertAlmostEqual(fdm['fcs/flap-pos-deg'], 5.*t)
            fdm.run()
            t = fdm['simulation/sim-time-sec']

        while t < 4.0:
            self.assertAlmostEqual(fdm['fcs/flap-pos-deg'], 10.*(t-1.))
            fdm.run()
            t = fdm['simulation/sim-time-sec']

        while t < 5.0:
            self.assertAlmostEqual(fdm['fcs/flap-pos-deg'], 30.)
            fdm.run()
            t = fdm['simulation/sim-time-sec']

        # Test the flap up sequence with an interruption at 7.5 deg
        fdm['fcs/flap-cmd-norm'] = 0.25

        while t < 7.0:
            self.assertAlmostEqual(fdm['fcs/flap-pos-deg'], 30.-10.*(t-5.))
            fdm.run()
            t = fdm['simulation/sim-time-sec']

        while t < 7.5:
            self.assertAlmostEqual(fdm['fcs/flap-pos-deg'], 10.-5.*(t-7.))
            fdm.run()
            t = fdm['simulation/sim-time-sec']

        while t < 8.0:
            self.assertAlmostEqual(fdm['fcs/flap-pos-deg'], 7.5)
            fdm.run()
            t = fdm['simulation/sim-time-sec']

        # Complete the flap up sequence. The flap command is set to a value
        # lower than 0.0 to check that JSBSim clamps it to 0.0
        fdm['fcs/flap-cmd-norm'] = -1.

        while t < 9.5:
            self.assertAlmostEqual(fdm['fcs/flap-pos-deg'], 10.-5.*(t-7.5))
            fdm.run()
            t = fdm['simulation/sim-time-sec']

        while t < 10.0:
            self.assertAlmostEqual(fdm['fcs/flap-pos-deg'], 0.0)
            fdm.run()
            t = fdm['simulation/sim-time-sec']
예제 #31
0
    def test_trim_doesnt_ignite_rockets(self):
        # Run a longitudinal trim with a rocket equipped with solid propellant
        # boosters (aka SRBs). The trim algorithm will try to reach a vertical
        # equilibrium by tweaking the throttle but since the rocket is nose up,
        # the trim cannot converge. As a result the algorithm will set full
        # throttle which will result in the SRBs ignition if the integration is
        # not suspended. This bug has been reported in FlightGear and this test
        # is checking that there is no regression.

        fdm = CreateFDM(self.sandbox)
        fdm.load_model('J246')
        fdm.load_ic(
            self.sandbox.path_to_jsbsim_file('aircraft', 'J246', 'LC39'),
            False)
        fdm.run_ic()

        # Check that the SRBs are not ignited
        self.assertEqual(fdm['propulsion/engine[0]/thrust-lbs'], 0.0)
        self.assertEqual(fdm['propulsion/engine[1]/thrust-lbs'], 0.0)

        try:
            fdm['simulation/do_simple_trim'] = 1
        except RuntimeError as e:
            # The trim cannot succeed. Just make sure that the raised exception
            # is due to the trim failure otherwise rethrow.
            if e.args[0] != 'Trim Failed':
                raise

        # Check that the trim did not ignite the SRBs
        self.assertEqual(fdm['propulsion/engine[0]/thrust-lbs'], 0.0)
        self.assertEqual(fdm['propulsion/engine[1]/thrust-lbs'], 0.0)
예제 #32
0
    def test_hold_down_with_gnd_reactions(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(
            self.sandbox.path_to_jsbsim_file('scripts', 'c1721.xml'))
        fdm.run_ic()
        ExecuteUntil(fdm, 0.25)

        fdm['forces/hold-down'] = 1.0
        h0 = fdm['position/h-sl-ft']
        pitch = fdm['attitude/pitch-rad']
        roll = fdm['attitude/roll-rad']
        heading = fdm['attitude/heading-true-rad']

        while fdm['simulation/sim-time-sec'] < 2.0:
            fdm.run()
            self.assertAlmostEqual(fdm['accelerations/pdot-rad_sec2'], 0.0)
            self.assertAlmostEqual(fdm['accelerations/qdot-rad_sec2'], 0.0)
            self.assertAlmostEqual(fdm['accelerations/rdot-rad_sec2'], 0.0)
            self.assertAlmostEqual(fdm['accelerations/udot-ft_sec2'], 0.0)
            self.assertAlmostEqual(fdm['accelerations/vdot-ft_sec2'], 0.0)
            self.assertAlmostEqual(fdm['accelerations/wdot-ft_sec2'], 0.0)

        self.assertAlmostEqual(fdm['position/h-sl-ft'], h0, delta=1E-6)
        self.assertAlmostEqual(fdm['attitude/pitch-rad'], pitch)
        self.assertAlmostEqual(fdm['attitude/roll-rad'], roll)
        self.assertAlmostEqual(fdm['attitude/heading-true-rad'], heading)
예제 #33
0
    def testFunctionWithIndexedProps(self):
        tree = et.parse(self.sandbox.path_to_jsbsim_file('engine',
                                                         'eng_PegasusXc.xml'))
        # Define the function starter-max-power-W as a 'post' function
        root = tree.getroot()
        startPowFunc_tag = root.find("function/[@name='propulsion/engine[#]/starter-max-power-W']")
        startPowFunc_tag.attrib['type']='post'
        tree.write('eng_PegasusXc.xml')

        # Copy the propeller file.
        shutil.copy(self.sandbox.path_to_jsbsim_file('engine', 'prop_deHavilland5000.xml'),
                    '.')
        fdm = CreateFDM(self.sandbox)
        fdm.set_engine_path('.')
        fdm.load_script(self.sandbox.path_to_jsbsim_file('scripts',
                                                         'Short_S23_1.xml'))
        fdm.run_ic()
        pm = fdm.get_property_manager()
        self.assertTrue(pm.hasNode('propulsion/engine[0]/starter-max-power-W'))
        self.assertTrue(pm.hasNode('propulsion/engine[1]/starter-max-power-W'))
        self.assertTrue(pm.hasNode('propulsion/engine[2]/starter-max-power-W'))
        self.assertTrue(pm.hasNode('propulsion/engine[3]/starter-max-power-W'))

        while fdm.run():
            rpm = [fdm['propulsion/engine[0]/engine-rpm'],
                   fdm['propulsion/engine[1]/engine-rpm'],
                   fdm['propulsion/engine[2]/engine-rpm'],
                   fdm['propulsion/engine[3]/engine-rpm']]
            for i in range(4):
                maxPower = max(0.0, 1.0-rpm[i]/400)*498.941*0.10471976*rpm[i]
                self.assertAlmostEqual(fdm['propulsion/engine[%d]/starter-max-power-W' % (i,)],
                                       maxPower)
예제 #34
0
    def test_gust_reset(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(self.sandbox.path_to_jsbsim_file('scripts',
                                                         'c172_cruise_8K.xml'))
        fdm['simulation/randomseed'] = 0.0
        fdm.set_output_directive(self.sandbox.path_to_jsbsim_file('tests', 'output.xml'))

        fdm.run_ic()
        ExecuteUntil(fdm, 15.5)

        ref = pd.read_csv('output.csv', index_col=0)

        fdm['simulation/randomseed'] = 0.0
        fdm.reset_to_initial_conditions(1)
        ExecuteUntil(fdm, 15.5)

        current = pd.read_csv('output_0.csv', index_col=0)

        # Check the data are matching i.e. the time steps are the same between
        # the two data sets and that the output data are also the same.
        self.assertTrue(isDataMatching(ref, current))

        # Find all the data that are differing by more than 1E-8 between the
        # two data sets.
        diff = FindDifferences(ref, current, 1E-8)
        self.longMessage = True
        self.assertEqual(len(diff), 0, msg='\n'+diff.to_string())
예제 #35
0
    def test_wind_frame(self):
        script_path = self.sandbox.path_to_jsbsim_file('scripts',
                                                       'ball_chute.xml')
        fdm = CreateFDM(self.sandbox)

        fdm.load_script(script_path)
        fdm.run_ic()

        self.assertAlmostEqual(fdm['external_reactions/parachute/location-x-in'],
                               12.0)
        self.assertAlmostEqual(fdm['external_reactions/parachute/location-y-in'],
                               0.0)
        self.assertAlmostEqual(fdm['external_reactions/parachute/location-z-in'],
                               0.0)
        self.assertAlmostEqual(fdm['external_reactions/parachute/x'], -1.0)
        self.assertAlmostEqual(fdm['external_reactions/parachute/y'], 0.0)
        self.assertAlmostEqual(fdm['external_reactions/parachute/z'], 0.0)

        while fdm.run():
            Tw2b = fdm.get_auxiliary().get_Tw2b()
            mag = fdm['aero/qbar-psf'] * fdm['fcs/parachute_reef_pos_norm']*20.0
            f = Tw2b * np.mat([-1.0, 0.0, 0.0]).T * mag
            self.assertAlmostEqual(fdm['forces/fbx-external-lbs'], f[0, 0])
            self.assertAlmostEqual(fdm['forces/fby-external-lbs'], f[1, 0])
            self.assertAlmostEqual(fdm['forces/fbz-external-lbs'], f[2, 0])

            m = np.cross(self.getLeverArm(fdm,'parachute'),
                         np.array([f[0,0], f[1,0], f[2, 0]]))
            self.assertAlmostEqual(fdm['moments/l-external-lbsft'], m[0])
            self.assertAlmostEqual(fdm['moments/m-external-lbsft'], m[1])
            self.assertAlmostEqual(fdm['moments/n-external-lbsft'], m[2])
예제 #36
0
파일: CheckTrim.py 프로젝트: Outerra/jsbsim
    def test_trim_doesnt_ignite_rockets(self):
        # Run a longitudinal trim with a rocket equipped with solid propellant
        # boosters (aka SRBs). The trim algorithm will try to reach a vertical
        # equilibrium by tweaking the throttle but since the rocket is nose up,
        # the trim cannot converge. As a result the algorithm will set full
        # throttle which will result in the SRBs ignition if the integration is
        # not suspended. This bug has been reported in FlightGear and this test
        # is checking that there is no regression.

        fdm = CreateFDM(self.sandbox)
        fdm.load_model('J246')
        fdm.load_ic(self.sandbox.path_to_jsbsim_file('aircraft', 'J246',
                                                     'LC39'), False)
        fdm.run_ic()

        # Check that the SRBs are not ignited
        self.assertEqual(fdm['propulsion/engine[0]/thrust-lbs'], 0.0)
        self.assertEqual(fdm['propulsion/engine[1]/thrust-lbs'], 0.0)

        try:
            fdm['simulation/do_simple_trim'] = 1
        except RuntimeError as e:
            # The trim cannot succeed. Just make sure that the raised exception
            # is due to the trim failure otherwise rethrow.
            if e.args[0] != 'Trim Failed':
                raise

        # Check that the trim did not ignite the SRBs
        self.assertEqual(fdm['propulsion/engine[0]/thrust-lbs'], 0.0)
        self.assertEqual(fdm['propulsion/engine[1]/thrust-lbs'], 0.0)
예제 #37
0
    def test_waypoint(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_model('c310')
        aircraft_path = self.sandbox.path_to_jsbsim_file('aircraft')
        fdm.load_ic(os.path.join(aircraft_path, 'c310', 'reset00'), False)

        slr = 20925646.32546  # Sea Level Radius
        TestCases = ((0.25*math.pi, 0.5*math.pi, 0.0, 0.0),
                     (0.0, 0.5*math.pi, math.pi, slr*0.25*math.pi),
                     # North pole
                     (0.5*math.pi, 0.5*math.pi, 0.0, slr*0.25*math.pi),
                     # South pole
                     (-0.5*math.pi, 0.5*math.pi, math.pi, slr*0.75*math.pi),
                     (0.0, 0.0, 1.5*math.pi, slr*0.5*math.pi),
                     (0.0, math.pi, 0.5*math.pi, slr*0.5*math.pi))

        fdm['ic/lat-gc-rad'] = TestCases[0][0]
        fdm['ic/long-gc-rad'] = TestCases[0][1]

        for case in TestCases:
            fdm['guidance/target_wp_latitude_rad'] = case[0]
            fdm['guidance/target_wp_longitude_rad'] = case[1]
            fdm.run_ic()
            self.assertAlmostEqual(fdm['guidance/wp-heading-rad'], case[2])
            self.assertAlmostEqual(fdm['guidance/wp-distance'], case[3])
예제 #38
0
    def test_fuel_tanks_inertia(self):
        script_path = self.sandbox.path_to_jsbsim_file('scripts', 'c1722.xml')

        # The aircraft c172x does not contain an <inertia_factor> tag so we
        # need to add one.
        tree, aircraft_name, b = CopyAircraftDef(script_path, self.sandbox)
        tank_tag = tree.getroot().find('propulsion/tank')
        inertia_factor = et.SubElement(tank_tag, 'inertia_factor')
        inertia_factor.text = '1.0'
        tree.write(self.sandbox('aircraft', aircraft_name,
                                aircraft_name+'.xml'))

        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_script(script_path)
        fdm.run_ic()

        contents0 = fdm['propulsion/tank/contents-lbs']
        ixx0 = fdm['propulsion/tank/local-ixx-slug_ft2']
        iyy0 = fdm['propulsion/tank/local-iyy-slug_ft2']
        izz0 = fdm['propulsion/tank/local-izz-slug_ft2']

        # Remove half of the tank contents and check that the inertias are
        # updated accordingly
        fdm['propulsion/tank/contents-lbs'] = 0.5*contents0
        contents = fdm['propulsion/tank/contents-lbs']
        ixx = fdm['propulsion/tank/local-ixx-slug_ft2']
        iyy = fdm['propulsion/tank/local-iyy-slug_ft2']
        izz = fdm['propulsion/tank/local-izz-slug_ft2']

        self.assertAlmostEqual(contents, 0.5*contents0, delta=1E-7,
                               msg="The tank content (%f lbs) should be %f lbs" % (contents, 0.5*contents0))
        self.assertAlmostEqual(ixx, 0.5*ixx0, delta=1E-7,
                               msg="The tank inertia Ixx (%f slug*ft^2) should be %f slug*ft^2" % (ixx, 0.5*ixx0))
        self.assertAlmostEqual(iyy, 0.5*iyy0, delta=1E-7,
                               msg="The tank inertia Iyy (%f slug*ft^2) should be %f slug*ft^2" % (iyy, 0.5*iyy0))
        self.assertAlmostEqual(izz, 0.5*izz0, delta=1E-7,
                               msg="The tank inertia Izz (%f slug*ft^2) should be %f slug*ft^2" % (izz, 0.5*izz0))

        # Execute the script and check that the fuel inertias have been updated
        # along with the consumption.
        ExecuteUntil(fdm, 200.0)

        contents = fdm['propulsion/tank/contents-lbs']
        ixx = fdm['propulsion/tank/local-ixx-slug_ft2']
        iyy = fdm['propulsion/tank/local-iyy-slug_ft2']
        izz = fdm['propulsion/tank/local-izz-slug_ft2']

        contents_ratio = contents / contents0
        ixx_ratio = ixx / ixx0
        iyy_ratio = iyy / iyy0
        izz_ratio = izz / izz0

        self.assertAlmostEqual(contents_ratio, ixx_ratio, delta=1E-7,
                               msg="Ixx does not vary as the tank content does\nIxx ratio=%f\nContents ratio=%f" % (ixx_ratio, contents_ratio))
        self.assertAlmostEqual(contents_ratio, iyy_ratio, delta=1E-7,
                               msg="Iyy does not vary as the tank content does\nIyy ratio=%f\nContents ratio=%f" % (iyy_ratio, contents_ratio))
        self.assertAlmostEqual(contents_ratio, izz_ratio, delta=1E-7,
                               msg="Izz does not vary as the tank content does\nIzz ratio=%f\nContents ratio=%f" % (izz_ratio, contents_ratio))
예제 #39
0
    def test_no_output(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(self.script_path)
        fdm.run_ic()
        ExecuteUntil(fdm, 10.)

        self.assertFalse(self.sandbox.exists('output.csv'),
                         msg="Results have unexpectedly been written to 'output.csv'")
예제 #40
0
    def test_no_input(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(self.script_path)
        fdm.run_ic()
        fdm.hold()

        with self.assertRaises(socket.error):
            TelnetInterface(fdm, 5., 1137)
예제 #41
0
    def testScripts(self):
        for s in self.script_list():
            fdm = CreateFDM(self.sandbox)
            self.assertTrue(fdm.load_script(s),
                            msg="Failed to load script %s" % (s,))
            fdm.run_ic()

            del fdm
예제 #42
0
    def test_no_input(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(self.script_path)
        fdm.run_ic()
        fdm.hold()

        with self.assertRaises(socket.error):
            TelnetInterface(fdm, 5., 1137)
예제 #43
0
    def test_fuel_tanks_inertia(self):
        script_path = self.sandbox.path_to_jsbsim_file('scripts', 'c1722.xml')

        # The aircraft c172x does not contain an <inertia_factor> tag so we need
        # to add one.
        tree, aircraft_name, b = CopyAircraftDef(script_path, self.sandbox)
        tank_tag = tree.getroot().find('./propulsion/tank')
        inertia_factor = et.SubElement(tank_tag, 'inertia_factor')
        inertia_factor.text = '1.0'
        tree.write(self.sandbox('aircraft', aircraft_name,  aircraft_name+'.xml'))

        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_script(script_path)
        fdm.run_ic()

        contents0 = fdm.get_property_value('propulsion/tank/contents-lbs')
        ixx0 = fdm.get_property_value('propulsion/tank/local-ixx-slug_ft2')
        iyy0 = fdm.get_property_value('propulsion/tank/local-iyy-slug_ft2')
        izz0 = fdm.get_property_value('propulsion/tank/local-izz-slug_ft2')

        # Remove half of the tank contents and check that the inertias are
        # updated accordingly
        fdm.set_property_value('propulsion/tank/contents-lbs', 0.5*contents0)
        contents = fdm.get_property_value('propulsion/tank/contents-lbs')
        ixx = fdm.get_property_value('propulsion/tank/local-ixx-slug_ft2')
        iyy = fdm.get_property_value('propulsion/tank/local-iyy-slug_ft2')
        izz = fdm.get_property_value('propulsion/tank/local-izz-slug_ft2')

        self.assertTrue(abs(contents-0.5*contents0) < 1E-7,
                        msg="The tank content (%f lbs) should be %f lbs" % (contents, 0.5*contents0))
        self.assertTrue(abs(ixx-0.5*ixx0) < 1E-7,
                        msg="The tank inertia Ixx (%f slug*ft^2) should be %f slug*ft^2" % (ixx, 0.5*ixx0))
        self.assertTrue(abs(iyy-0.5*iyy0) < 1E-7,
                        msg="The tank inertia Iyy (%f slug*ft^2) should be %f slug*ft^2" % (iyy, 0.5*iyy0))
        self.assertTrue(abs(izz-0.5*izz0) < 1E-7,
                        msg="The tank inertia Izz (%f slug*ft^2) should be %f slug*ft^2" % (izz, 0.5*izz0))

        # Execute the script and check that the fuel inertias have been updated
        # along with the consumption.
        ExecuteUntil(fdm, 200.0)

        contents = fdm.get_property_value('propulsion/tank/contents-lbs')
        ixx = fdm.get_property_value('propulsion/tank/local-ixx-slug_ft2')
        iyy = fdm.get_property_value('propulsion/tank/local-iyy-slug_ft2')
        izz = fdm.get_property_value('propulsion/tank/local-izz-slug_ft2')

        contents_ratio = contents / contents0
        ixx_ratio = ixx / ixx0
        iyy_ratio = iyy / iyy0
        izz_ratio = izz / izz0

        self.assertTrue(abs(contents_ratio - ixx_ratio) < 1E-7,
                        msg="Ixx does not vary as the tank content does\nIxx ratio=%f\nContents ratio=%f" % (ixx_ratio, contents_ratio))
        self.assertTrue(abs(contents_ratio - iyy_ratio) < 1E-7,
                        msg="Iyy does not vary as the tank content does\nIyy ratio=%f\nContents ratio=%f" % (iyy_ratio, contents_ratio))
        self.assertTrue(abs(contents_ratio - izz_ratio) < 1E-7,
                        msg="Izz does not vary as the tank content does\nIzz ratio=%f\nContents ratio=%f" % (izz_ratio, contents_ratio))
예제 #44
0
 def test_trim_on_ground(self):
     # Check that the trim is made with up to date initial conditions
     fdm = CreateFDM(self.sandbox)
     fdm.load_model('c172x')
     fdm['ic/theta-deg'] = 10.0
     fdm.run_ic()
     fdm['ic/theta-deg'] = 0.0
     # If the trim fails, it will raise an exception
     fdm['simulation/do_simple_trim'] = 2
예제 #45
0
    def test_pitot_angle(self):
        script_name = 'ball_chute.xml'
        script_path = self.sandbox.path_to_jsbsim_file('scripts', script_name)

        # Add a Pitot angle to the Cessna 172
        tree, aircraft_name, path_to_jsbsim_aircrafts = CopyAircraftDef(script_path, self.sandbox)
        root = tree.getroot()
        pitot_angle_deg = 5.0
        self.addPitotTube(root, 5.0)
        contact_tag = root.find('./ground_reactions/contact')
        contact_tag.attrib['type'] = 'STRUCTURE'
        tree.write(self.sandbox('aircraft', aircraft_name,
                                aircraft_name+'.xml'))

        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_model('ball')
        pitot_angle = pitot_angle_deg * math.pi / 180.
        weight = fdm['inertia/weight-lbs']
        spring_tag = contact_tag.find('./spring_coeff')
        spring_coeff = float(spring_tag.text)
        print "Weight=%d Spring=%d" % (weight, spring_coeff)
        fdm['ic/h-sl-ft'] = weight / spring_coeff
        fdm['forces/hold-down'] = 1.0
        fdm.run_ic()

        ExecuteUntil(fdm, 10.)

        for i in xrange(36):
            for j in xrange(-9, 10):
                angle = math.pi * i / 18.0
                angle2 = math.pi * j / 18.0
                ca2 = math.cos(angle2)
                fdm['atmosphere/wind-north-fps'] = 10. * math.cos(angle) * ca2
                fdm['atmosphere/wind-east-fps'] = 10. * math.sin(angle) * ca2
                fdm['atmosphere/wind-down-fps'] = 10. * math.sin(angle2)
                fdm.run()

                vg = fdm['velocities/vg-fps']
                self.assertAlmostEqual(vg, 0.0, delta=1E-7)

                vt = fdm['velocities/vt-fps']
                self.assertAlmostEqual(vt, 10., delta=1E-7)

                mach = vt / fdm['atmosphere/a-fps']
                P = fdm['atmosphere/P-psf']
                pt = P * math.pow(1+0.2*mach*mach, 3.5)
                psl = fdm['atmosphere/P-sl-psf']
                rhosl = fdm['atmosphere/rho-sl-slugs_ft3']
                A = math.pow((pt-P)/psl+1.0, 1.0/3.5)
                alpha = fdm['aero/alpha-rad']
                beta = fdm['aero/beta-rad']
                vc = math.sqrt(7.0*psl/rhosl*(A-1.0))*math.cos(alpha+pitot_angle)*math.cos(beta)

                self.assertAlmostEqual(fdm['velocities/vc-kts'],
                                       max(0.0, vc) / 1.68781, delta=1E-7)
예제 #46
0
    def testSteadyFlight(self):
        script_name = 'c1722.xml'
        script_path = self.sandbox.path_to_jsbsim_file('scripts', script_name)
        self.AddAccelerometersToAircraft(script_path)

        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_script(script_path)
        # Switch the accel on
        fdm['fcs/accelerometer/on'] = 1.0
        # Use the standard gravity (i.e. GM/r^2)
        fdm['simulation/gravity-model'] = 0
        # Select an orientation such that frame transformations simplify
        fdm['ic/psi-true-rad'] = 0.0
        fdm.run_ic()

        ExecuteUntil(fdm, 0.1)

        fdm['simulation/do_simple_trim'] = 1

        r = fdm['position/radius-to-vehicle-ft']
        pitch = fdm['attitude/theta-rad']
        roll = fdm['attitude/phi-rad']
        latitude = fdm['position/lat-gc-rad']
        g = fdm['accelerations/gravity-ft_sec2']
        omega = 0.00007292115  # Earth rotation rate in rad/sec
        fc = r * math.cos(latitude) * omega * omega  # Centrifugal force

        uvw = np.array(fdm.get_propagate().get_uvw().T)[0]
        Omega = omega * np.array([
            math.cos(pitch - latitude),
            math.sin(pitch - latitude) * math.sin(roll),
            math.sin(pitch - latitude) * math.cos(roll)
        ])

        # Compute the acceleration measured by the accelerometer as the sum of
        # the gravity and the centrifugal and Coriolis forces.
        fa_yz = (fc * math.cos(latitude - pitch) - g * math.cos(pitch))
        fa = np.array([(fc * math.sin(latitude - pitch) + g * math.sin(pitch)),
                       fa_yz * math.sin(roll), fa_yz * math.cos(roll)
                       ]) + np.cross(2.0 * Omega, uvw)

        # After the trim we are close to the equilibrium but there remains a
        # small residual that we have to take the bias into account
        fax = fa[0] + fdm['accelerations/udot-ft_sec2']
        fay = fa[1] + fdm['accelerations/vdot-ft_sec2']
        faz = fa[2] + fdm['accelerations/wdot-ft_sec2']

        # Deltas are relaxed because the tolerances of the trimming algorithm
        # are quite relaxed themselves.
        self.assertAlmostEqual(fdm['fcs/accelerometer/X'], fax, delta=1E-6)
        self.assertAlmostEqual(fdm['fcs/accelerometer/Y'], fay, delta=1E-4)
        self.assertAlmostEqual(fdm['fcs/accelerometer/Z'], faz, delta=1E-5)

        del fdm
예제 #47
0
    def testChannelRate(self):
        os.environ['JSBSIM_DEBUG'] = str(0)
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(
            self.sandbox.path_to_jsbsim_file('scripts',
                                             'systems-rate-test-0.xml'))
        fdm.run_ic()

        while fdm['simulation/sim-time-sec'] < 30:
            fdm.run()
            self.assertEqual(fdm['simulation/frame'], fdm['tests/rate-1'])
            self.assertEqual(int(fdm['simulation/frame'] / 4),
                             fdm['tests/rate-4'])
            self.assertEqual(fdm['simulation/sim-time-sec'],
                             fdm['tests/rate-1-dt-sum'])
            self.assertAlmostEqual(
                fdm['simulation/dt'] * fdm['tests/rate-4'] * 4,
                fdm['tests/rate-4-dt-sum'])

        self.assertEqual(fdm['simulation/dt'], fdm['tests/rate-1-dt'])
        self.assertEqual(fdm['simulation/dt'] * 4, fdm['tests/rate-4-dt'])

        try:
            fdm['simulation/do_simple_trim'] = 1
        except RuntimeError as e:
            # The trim cannot succeed. Just make sure that the raised exception
            # is due to the trim failure otherwise rethrow.
            if e.args[0] != 'Trim Failed':
                raise

        while fdm['simulation/sim-time-sec'] < 40:
            self.assertEqual(fdm['simulation/frame'], fdm['tests/rate-1'])
            self.assertEqual(int(fdm['simulation/frame'] / 4),
                             fdm['tests/rate-4'])
            self.assertEqual(fdm['simulation/sim-time-sec'],
                             fdm['tests/rate-1-dt-sum'])
            self.assertAlmostEqual(
                fdm['simulation/dt'] * fdm['tests/rate-4'] * 4,
                fdm['tests/rate-4-dt-sum'])
            fdm.run()

        fdm.reset_to_initial_conditions(1)
        tf = fdm['tests/rate-1-dt-sum']
        xtraFrames = fdm['simulation/frame'] % 4

        while fdm['simulation/sim-time-sec'] < 30:
            fdm.run()
            self.assertEqual(fdm['simulation/frame'], fdm['tests/rate-1'])
            self.assertEqual(int((fdm['simulation/frame'] - xtraFrames) / 4),
                             fdm['tests/rate-4'])
            self.assertAlmostEqual(fdm['simulation/sim-time-sec'],
                                   fdm['tests/rate-1-dt-sum'] - tf)
            self.assertAlmostEqual(
                fdm['simulation/dt'] * fdm['tests/rate-4'] * 4,
                fdm['tests/rate-4-dt-sum'])
예제 #48
0
    def testSteadyFlight(self):
        script_name = 'c1722.xml'
        script_path = self.sandbox.path_to_jsbsim_file('scripts', script_name)
        self.AddAccelerometersToAircraft(script_path)

        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_script(script_path)
        # Switch the accel on
        fdm['fcs/accelerometer/on'] = 1.0
        # Use the standard gravity (i.e. GM/r^2)
        fdm['simulation/gravity-model'] = 0
        # Select an orientation such that frame transformations simplify
        fdm['ic/psi-true-rad'] = 0.0
        fdm.run_ic()

        ExecuteUntil(fdm, 0.1)

        fdm['simulation/do_simple_trim'] = 1

        r = fdm['position/radius-to-vehicle-ft']
        pitch = fdm['attitude/theta-rad']
        roll = fdm['attitude/phi-rad']
        latitude = fdm['position/lat-gc-rad']
        g = fdm['accelerations/gravity-ft_sec2']
        omega = 0.00007292115  # Earth rotation rate in rad/sec
        fc = r * math.cos(latitude) * omega * omega  # Centrifugal force

        uvw = np.array(fdm.get_propagate().get_uvw().T)[0]
        Omega = omega * np.array([math.cos(pitch - latitude),
                                  math.sin(pitch - latitude) * math.sin(roll),
                                  math.sin(pitch - latitude) * math.cos(roll)])

        # Compute the acceleration measured by the accelerometer as the sum of
        # the gravity and the centrifugal and Coriolis forces.
        fa_yz = (fc * math.cos(latitude - pitch) - g * math.cos(pitch))
        fa = np.array([(fc * math.sin(latitude - pitch) + g * math.sin(pitch)),
                       fa_yz * math.sin(roll),
                       fa_yz * math.cos(roll)]) + np.cross(2.0*Omega, uvw)

        # After the trim we are close to the equilibrium but there remains a
        # small residual that we have to take the bias into account
        fax = fa[0] + fdm['accelerations/udot-ft_sec2']
        fay = fa[1] + fdm['accelerations/vdot-ft_sec2']
        faz = fa[2] + fdm['accelerations/wdot-ft_sec2']

        # Deltas are relaxed because the tolerances of the trimming algorithm
        # are quite relaxed themselves.
        self.assertAlmostEqual(fdm['fcs/accelerometer/X'], fax, delta=1E-6)
        self.assertAlmostEqual(fdm['fcs/accelerometer/Y'], fay, delta=1E-4)
        self.assertAlmostEqual(fdm['fcs/accelerometer/Z'], faz, delta=1E-5)

        del fdm
예제 #49
0
    def testEnginePowerVC(self):
        # Check that the same results are obtained whether the engine power
        # velocity correction is given in a <table> or <function>
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(self.sandbox.path_to_jsbsim_file('scripts',
                                                         'L4102.xml'))
        fdm.run_ic()

        while fdm.run():
            pass

        del fdm

        ref = pd.read_csv('L410.csv', index_col=0)

        tree = et.parse(self.sandbox.path_to_jsbsim_file('engine',
                                                         'engtm601.xml'))
        # Modify the engine definition to use a <function> rather than a
        # <table> component.
        root = tree.getroot()
        engPowVC_tag = root.find("table/[@name='EnginePowerVC']")
        root.remove(engPowVC_tag)
        del engPowVC_tag.attrib['name']
        func_engPowVC = et.SubElement(root, 'function')
        func_engPowVC.attrib['name'] = 'EnginePowerVC'
        func_engPowVC.append(engPowVC_tag)
        tree.write('engtm601.xml')

        # Copy the propeller file.
        shutil.copy(self.sandbox.path_to_jsbsim_file('engine', 'vrtule2.xml'),
                    '.')
        self.sandbox.delete_csv_files()

        fdm = CreateFDM(self.sandbox)
        fdm.set_engine_path('.')
        fdm.load_script(self.sandbox.path_to_jsbsim_file('scripts',
                                                         'L4102.xml'))
        fdm.run_ic()

        while fdm.run():
            pass

        current = pd.read_csv('L410.csv', index_col=0)

        # Check the data are matching i.e. the time steps are the same between
        # the two data sets and that the output data are also the same.
        self.assertTrue(isDataMatching(ref, current))

        # Find all the data that are differing by more than 1E-5 between the
        # two data sets.
        diff = FindDifferences(ref, current, 0.0)
        self.longMessage = True
        self.assertEqual(len(diff), 0, msg='\n'+diff.to_string())
예제 #50
0
 def initFDM(self):
     fdm = CreateFDM(self.sandbox)
     script_path = self.sandbox.path_to_jsbsim_file('scripts',
                                                    'cannonball.xml')
     fdm.load_script(script_path)
     fdm['simulation/integrator/rate/rotational'] = 5
     fdm['simulation/integrator/rate/translational'] = 5
     fdm['simulation/integrator/position/rotational'] = 5
     fdm['simulation/integrator/position/translational'] = 5
     fdm.run_ic()
     fdm.set_dt(0.05)
     return fdm
예제 #51
0
    def testEnginePowerVC(self):
        fdm = CreateFDM(self.sandbox)
        fdm.load_script(self.sandbox.path_to_jsbsim_file('scripts',
                                                         'L4102.xml'))
        fdm.run_ic()
        pm = fdm.get_property_manager()
        self.assertTrue(pm.hasNode('propulsion/engine[0]/EnginePowerVC'))
        self.assertTrue(pm.hasNode('propulsion/engine[1]/EnginePowerVC'))

        while fdm.run():
            self.assertAlmostEqual(fdm['propulsion/engine[0]/EnginePowerVC'],
                                   fdm['propulsion/engine[1]/EnginePowerVC'])
예제 #52
0
    def test_grain_tanks_content(self):
        script_path = self.sandbox.path_to_jsbsim_file('scripts', 'J2460.xml')
        tree, aircraft_name, b = CopyAircraftDef(script_path, self.sandbox)

        id = 0
        for tank in tree.getroot().findall('propulsion/tank'):
            grain_config = tank.find('grain_config')
            if grain_config and grain_config.attrib['type'] == 'CYLINDRICAL':
                break
            ++id

        capacity = float(tank.find('capacity').text)
        tank.find('contents').text = str(0.5*capacity)
        tree.write(self.sandbox('aircraft', aircraft_name,
                                aircraft_name+'.xml'))

        radius_tag = tank.find('radius')
        radius = float(radius_tag.text)
        if 'unit' in radius_tag.attrib and radius_tag.attrib['unit'] == 'IN':
            radius /= 12.0

        bore_diameter_tag = tank.find('grain_config/bore_diameter')
        bore_radius = 0.5*float(bore_diameter_tag.text)
        if 'unit' in bore_diameter_tag.attrib and bore_diameter_tag.attrib['unit'] == 'IN':
            bore_radius /= 12.0

        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_script(script_path)
        fdm.run_ic()

        tank_name = 'propulsion/tank[%g]' % (id,)

        self.assertAlmostEqual(fdm[tank_name+'/contents-lbs'], 0.5*capacity)
        fdm['propulsion/tank/contents-lbs'] = capacity
        mass = capacity / 32.174049  # Converting lbs to slugs
        ixx = 0.5 * mass * (radius * radius + bore_radius*bore_radius)
        self.assertAlmostEqual(fdm[tank_name+'local-ixx-slug_ft2'], ixx)

        del fdm

        tank.find('contents').text = '0.0'
        tree.write(self.sandbox('aircraft', aircraft_name,
                                aircraft_name+'.xml'))

        fdm = CreateFDM(self.sandbox)
        fdm.set_aircraft_path('aircraft')
        fdm.load_script(script_path)
        fdm.run_ic()

        self.assertAlmostEqual(fdm[tank_name+'/contents-lbs'], 0.0)
        fdm['propulsion/tank/contents-lbs'] = capacity
예제 #53
0
    def test_output_from_file(self):
        tree = et.parse(self.sandbox.elude(self.script_path))
        output_tag = et.SubElement(tree.getroot(), 'output')
        output_tag.attrib['file'] = self.sandbox.elude(self.sandbox.path_to_jsbsim_file('tests', 'output.xml'))
        tree.write(self.sandbox('c1722_0.xml'))

        fdm = CreateFDM(self.sandbox)
        fdm.load_script('c1722_0.xml')
        fdm.run_ic()
        ExecuteUntil(fdm, 10.)

        self.assertTrue(self.sandbox.exists('output.csv'),
                        msg="The file 'output.csv' has not been created")
예제 #54
0
    def test_script_input(self):
        tree = et.parse(self.sandbox.elude(self.script_path))
        input_tag = et.SubElement(tree.getroot(), 'input')
        input_tag.attrib['port'] = '1138'
        tree.write(self.sandbox('c1722_1.xml'))

        fdm = CreateFDM(self.sandbox)
        fdm.load_script('c1722_1.xml')
        fdm.run_ic()
        fdm.hold()

        tn = TelnetInterface(fdm, 5., 1138)
        self.sanityCheck(tn)