空战博弈编程实现——2 初探JSBSIM

[原][JSBSIM]aircraft飞机xml脚本 - 南水之源 - 博客园 (cnblogs.com)

1 安装python版本 jsbsim

发布 ·JSBSim-Team/jsbsim ·GitHub

Jsbsim :: Anaconda.org

conda install -c conda-forge jsbsim

2 安装 jsbsim.exe

安装exe之后 使用命令符进入所在文件夹,查看相关信息

JSBSim 版本 1.1.11 [GitHub build 741/commit 10e077b486c42d38e76d1dd7f0aeb744f92d96a0] 2022 年 2 月 13 日 12:44:42

用法:jsbsim [脚本文件名] [输出文件名]

选项:
--help 返回此消息
--version 返回版本号
--outputlogfile= 设置(覆盖)数据输出文件的名称
--logdirectivefile= 指定数据记录指令文件的名称
(可以出现多次)
--root= 指定 JSBSim 根目录(飞机/、引擎/等所在的位置)
--aircraft= 指定要建模的飞机名称
--script= 指定要运行的脚本
--realtime 指定在实际的真实世界时间运行
--nice 指定以较低的 CPU 使用率运行
--nohighlight 指定控制台输出应该是纯文本(没有颜色)
--suspend 指定初始化后暂停模拟
--initfile= 指定一个初始化文件
--catalog 指定应打印此飞机模型的所有属性
(catalog=aircraftname 是可选格式)
--property=<name=value> 例如--property=simulation/integrator/rate/rotational=1
--simulation-rate=<rate (double)> 指定sim dT时间或频率
如果指定的速率小于 1,则将其解释为
时间步长,否则假定为以赫兹为单位的速率。
--end=<time (double)> 指定sim结束时间

注意:= 符号周围不能有空格
一个选项后跟一个文件名

将这个文件夹添加到环境变量中

gunplot 安装

这个好像没有用,不需要安装

(27条消息) WIN10下gnuplot 的安装_diantongqingjie的博客-CSDN博客_gnuplot安装

下载网站

gnuplot download | SourceForge.net

配置环境变量

验证

3 xml脚本解析

首先要进入文件夹中,运行737——test.xml

首先会加载aircraft/737.xml文件

模型作者及信息

aircraft/737.xml 第7行

<fileheader>
        <author> Dave Culp </author>
        <author> Aeromatic </author>
        <filecreationdate> 2006-01-04 </filecreationdate>
        <version>$Revision: 1.43 $</version>
        <description> Models a Boeing 737. </description>
        <license>
          <licenseName>GPL (General Public License)</licenseName>
          <licenseURL>http://www.gnu.org/licenses/gpl.html</licenseURL>
        </license>
        <note>
        This model was created using publicly available data, publicly available technical reports, textbooks, and guesses. It contains no proprietary or restricted data. If this model has been validated at all, it would be only to the extent that it seems to "fly right", and that it possibly complies with published, publicly known, performance data (maximum speed, endurance, etc.). Thus, this model is meant for educational and entertainment purposes only. This simulation model is not endorsed by the manufacturer. This model is not to be sold.
      </note>
    </fileheader>

Description : 描述

Model Author : 模型作者

Creation Data :创建时间

Version : 版本

Aircraft Metrics飞机指标

aircraft/737.xml 31行

 <metrics>
        <wingarea unit="FT2"> 1171.00 </wingarea>
        <wingspan unit="FT">    94.70 </wingspan>
        <chord unit="FT">       12.31 </chord>
        <htailarea unit="FT2"> 348.00 </htailarea>
        <htailarm unit="FT">    48.04 </htailarm>
        <vtailarea unit="FT2"> 297.00 </vtailarea>
        <vtailarm unit="FT">    44.50 </vtailarm>
        <location name="AERORP" unit="IN">
            <x> 625 </x>
            <y>   0 </y>
            <z>  24 </z>
        </location>
        <location name="EYEPOINT" unit="IN">
            <x>  80 </x>
            <y> -30 </y>
            <z>  70 </z>
        </location>
        <location name="VRP" unit="IN">
            <x> 0 </x>
            <y> 0 </y>
            <z> 0 </z>
        </location>
    </metrics>

Wing Area 机翼面积

WingSpan 翼展 翼层长度

Incidence 入射角

Chord 翼弦

AEROR ; aerodynamic Reference Point 气动中心

H. Tail Area: 水平尾翼面积 horizontal

H.Tail Arm : 水平尾翼力臂

V. Tail Area: 垂直尾翼面积

V.Tail Arm : 垂直尾翼力臂 vertical

EYEPOINT :飞行员眼点

Ref Pt : 参考点

Visual Ref Pt : Visual Reference Points (VRPs) for Flight Simulation 用于飞行模拟的视觉参考点

mass_balance 附加点质量(乘客,货物等)

aircraft/737.xml 56行

管理模型重量,平衡和转动惯量信息。 保持点质量的向量。 总结所有的信息,提供给FGPropagate。 加载的是飞机配置文件的<mass_balance>部分

<mass_balance negated_crossproduct_inertia="true">
        <ixx unit="SLUG*FT2">    562000 </ixx>
        <iyy unit="SLUG*FT2"> 1.473e+06 </iyy>
        <izz unit="SLUG*FT2"> 1.894e+06 </izz>
        <ixy unit="SLUG*FT2">         0 </ixy>
        <ixz unit="SLUG*FT2">      8000 </ixz>
        <iyz unit="SLUG*FT2">         0 </iyz>
        <emptywt unit="LBS">      83000 </emptywt>
        <location name="CG" unit="IN">
            <x> 639 </x>
            <y>   0 </y>
            <z> -40 </z>
        </location>
    </mass_balance>

CG: 重心

ground_reactions 起落架的位置和属性

aircraft/737.xml 71行

 <ground_reactions>
        <contact name="Nose Gear" type="BOGEY">
            <location unit="IN">
                <x> 158 </x>
                <y>   0 </y>
                <z> -84 </z>
            </location>
            <static_friction>  0.80 </static_friction>
            <dynamic_friction> 0.50 </dynamic_friction>
            <rolling_friction> 0.02 </rolling_friction>
            <spring_coeff unit="LBS/FT"> 90000 </spring_coeff>
            <damping_coeff unit="LBS/FT/SEC"> 4000 </damping_coeff>
            <damping_coeff_rebound unit="LBS/FT/SEC">8000</damping_coeff_rebound>

          <max_steer unit="DEG"> 35 </max_steer>
            <brake_group> NONE </brake_group>
            <retractable>1</retractable>
        </contact>
        <contact name="Left Main Gear" type="BOGEY">
            <location unit="IN">
                <x>  648 </x>
                <y> -100 </y>
                <z>  -84 </z>
            </location>
            <static_friction>  0.80 </static_friction>
            <dynamic_friction> 0.50 </dynamic_friction>
            <rolling_friction> 0.02 </rolling_friction>
            <spring_coeff unit="LBS/FT"> 120000 </spring_coeff>
            <damping_coeff unit="LBS/FT/SEC"> 10000 </damping_coeff>
            <damping_coeff_rebound unit="LBS/FT/SEC">20000</damping_coeff_rebound>

          <max_steer unit="DEG"> 0.0 </max_steer>
            <brake_group> LEFT </brake_group>
            <retractable>1</retractable>
        </contact>
        <contact name="Right Main Gear" type="BOGEY">
            <location unit="IN">
                <x> 648 </x>
                <y> 100 </y>
                <z> -84 </z>
            </location>
            <static_friction>  0.80 </static_friction>
            <dynamic_friction> 0.50 </dynamic_friction>
            <rolling_friction> 0.02 </rolling_friction>
            <spring_coeff unit="LBS/FT"> 120000 </spring_coeff>
            <damping_coeff unit="LBS/FT/SEC"> 10000 </damping_coeff>
            <damping_coeff_rebound unit="LBS/FT/SEC">20000</damping_coeff_rebound>
            
            <max_steer unit="DEG"> 0.0 </max_steer>
            <brake_group> RIGHT </brake_group>
            <retractable>1</retractable>
        </contact>
    </ground_reactions>

FGGroundFeactions类

管理与地面的接触。 维护起落架和地面接触点列表,FGLGear的所有实例。 计算他们的推力和时间片,提供给FGPropagate。 解析的是飞机配置文件的<ground_reactions>部分

Landing gear - Wikipedia

nose gear :前起落架

​ Location : 位置

​ Spring Constant: 弹簧常数
​ Damping Constant: 阻尼常数
​ Rebound Damping Constant 回弹阻尼常数
​ Dynanic Friction: 动态摩擦
​ Static Friction: 静态摩擦
​ Ro11ing Friction: Ro11ing 摩擦
​ Steering Type: 转向类型
​ Grouping: 分组
​ Max Steer Angle: 最大转向角度
​ Retractable: : 可伸缩

Left Main Gear : 左主起落架

Right Main Gear : 右主起落架

propulsion 推进系统(发动机,油箱和“推进器”)

aircraft/737.xml 124行

 <propulsion>
        <engine file="CFM56">
            <feed>0</feed>
            <feed>2</feed>
            <thruster file="direct">
                <location unit="IN">
                    <x>  540 </x>
                    <y> -193 </y>
                    <z>  -40 </z>
                </location>
                <orient unit="DEG">
                    <roll>  0 </roll>
                    <pitch> 0 </pitch>
                    <yaw>   0 </yaw>
                </orient>
            </thruster>
        </engine>
        <engine file="CFM56">
            <feed>1</feed>
            <feed>2</feed>
            <thruster file="direct">
                <location unit="IN">
                    <x> 540 </x>
                    <y> 193 </y>
                    <z> -40 </z>
                </location>
                <orient unit="DEG">
                    <roll>  0 </roll>
                    <pitch> 0 </pitch>
                    <yaw>   0 </yaw>
                </orient>
            </thruster>
        </engine>
        <tank type="FUEL"><!-- Left wing tank -->
            <location unit="IN">
                <x> 520 </x>
                <y> -80 </y>
                <z> -18 </z>
            </location>
            <type>JET-A</type>
            <capacity unit="LBS"> 10200 </capacity>
            <contents unit="LBS"> 10000 </contents>
        </tank>
        <tank type="FUEL"><!-- Right wing tank -->
            <location unit="IN">
                <x> 520 </x>
                <y>  80 </y>
                <z> -18 </z>
            </location>
            <type>JET-A</type>
            <capacity unit="LBS"> 10200 </capacity>
            <contents unit="LBS"> 10000 </contents>
        </tank>
        <tank type="FUEL"><!-- Center tank -->
            <location unit="IN">
                <x> 480 </x>
                <y>   0 </y>
                <z> -18 </z>
            </location>
            <type>JET-A</type>
            <capacity unit="LBS"> 15000 </capacity>
            <contents unit="LBS">  4000 </contents>
        </tank>
    </propulsion>

推进管理器 FGPropulsion

推进级是整个推进系统的容器,其由发动机engine和容器罐tank组成

这里的engine是engine/CFM56.XML文件

<?xml version="1.0"?>
<!--
  File:     CFM56_5.xml
  Author:   Aero-Matic v 0.8

  Inputs:
    name:           CFM56
    type:           turbine
    thrust:         20000 lb
    augmented?      no
    injected?       no
-->

<turbine_engine name="CFM56">
  <milthrust> 20000.0 </milthrust>
  <bypassratio>     5.9 </bypassratio>
  <tsfc>            0.657 </tsfc>
  <bleed>           0.04 </bleed>
  <idlen1>         30.0 </idlen1>
  <idlen2>         60.0 </idlen2>
  <maxn1>         100.0 </maxn1>
  <maxn2>         100.0 </maxn2>
  <augmented>         0 </augmented>
  <injected>          0 </injected>

  <function name="IdleThrust">
   <table>
    <independentVar lookup="row">velocities/mach</independentVar>
    <independentVar lookup="column">atmosphere/density-altitude</independentVar>
    <tableData>
         -10000     0     10000   20000   30000   40000   50000   60000
     0.0  0.0420  0.0436  0.0528  0.0694  0.0899  0.1183  0.1467  0.0
     0.2  0.0500  0.0501  0.0335  0.0544  0.0797  0.1049  0.1342  0.0
     0.4  0.0040  0.0047  0.0020  0.0272  0.0595  0.0891  0.1203  0.0
     0.6  0.0     0.0     0.0     0.0     0.0276  0.0718  0.1073  0.0
     0.8  0.0     0.0     0.0     0.0     0.0174  0.0468  0.0900  0.0
     1.0  0.0     0.0     0.0     0.0     0.0     0.0422  0.0700  0.0
    </tableData>
   </table>
  </function>

  <function name="MilThrust">
   <table>
    <independentVar lookup="row">velocities/mach</independentVar>
    <independentVar lookup="column">atmosphere/density-altitude</independentVar>
    <tableData>
          -10000       0   10000   20000   30000   40000   50000   60000
     0.0   1.2600  1.0000  0.7400  0.5340  0.3720  0.2410  0.1490  0.0
     0.2   1.1710  0.9340  0.6970  0.5060  0.3550  0.2310  0.1430  0.0
     0.4   1.1500  0.9210  0.6920  0.5060  0.3570  0.2330  0.1450  0.0
     0.6   1.1810  0.9510  0.7210  0.5320  0.3780  0.2480  0.1540  0.0
     0.8   1.2580  1.0200  0.7820  0.5820  0.4170  0.2750  0.1700  0.0
     1.0   1.3690  1.1200  0.8710  0.6510  0.4750  0.3150  0.1950  0.0
     1.2   0.0000  0.0000  0.0000  0.0000  0.0000  0.0000  0.0000  0.0
    </tableData>
   </table>
  </function>

</turbine_engine>

tableData是一个二维的表

row 行表示 velocities/mach 速度/马赫

column列 atmosphere/density-altitude大气/密度-高度

推进:
FUEL tark ho1ds 10200. 000000 1bs。

燃料目前为最大容量的 98. 039216%
坦克 1 位置 (X, Y, Z): 520.000000, -80。 0000,-18.000000
有效半径:0. 000000 英寸
初始温度:-9999。 000000 华氏度

优先级:1

milthrust - Maximum thrust, static, at sea level.

idle thrust: 慢车指发动机能够保持稳定工作的最小转速状态。慢车状态是涡扇发动机的一个重要工作状态,主要用于发动机起动后暖机、飞机在地面滑行、进近晚期和着陆阶段。 民用涡扇发动机有空中慢车和地面慢车两个状态。空中慢车时发动机转速比地面慢车时要大。当油门杆收到慢车状态时,在空中,发动机就会保持空中慢车转速;在地面,发动机则将保持地面慢车工作。

idlen1 - Fan rotor rpm (% of max) at idle
idlen2 - Core rotor rpm (% of max) at idle

FCS 飞行控制管理器

飞机的六个动作: Pitch Roll Yaw Flaps Landing Gear Flight Spoilers Ground Spoilers

aircraft/737.xml 189行

image-20220325102959417

<flight_control name="FCS: 737">

        <channel name="Pitch">

            <summer name="Pitch Trim Sum">
                <input>fcs/elevator-cmd-norm</input>
                <input>fcs/pitch-trim-cmd-norm</input>
                <clipto>
                    <min>-1</min>
                    <max> 1</max>
                </clipto>
            </summer>

            <aerosurface_scale name="Elevator Control">
                <input>fcs/pitch-trim-sum</input>
                <range>
                    <min>-0.3</min>
                    <max> 0.3</max>
                </range>
                <output>fcs/elevator-pos-rad</output>
            </aerosurface_scale>

            <aerosurface_scale name="Elevator Normalized">
                <input>fcs/elevator-pos-rad</input>
                <domain>
                    <min>-0.3</min>
                    <max> 0.3</max>
                </domain>
                <range>
                    <min>-1</min>
                    <max> 1</max>
                </range>
                <output>fcs/elevator-pos-norm</output>
            </aerosurface_scale>

        </channel>
        <channel name="Roll">

            <summer name="Roll Trim Sum">
                <input>fcs/aileron-cmd-norm</input>
                <input>fcs/roll-trim-cmd-norm</input>
                <clipto>
                    <min>-1</min>
                    <max> 1</max>
                </clipto>
            </summer>

            <aerosurface_scale name="Left Aileron Control">
                <input>fcs/roll-trim-sum</input>
                <range>
                    <min>-0.35</min>
                    <max> 0.35</max>
                </range>
                <output>fcs/left-aileron-pos-rad</output>
            </aerosurface_scale>

            <aerosurface_scale name="Right Aileron Control">
                <input>-fcs/roll-trim-sum</input>
                <range>
                    <min>-0.35</min>
                    <max> 0.35</max>
                </range>
                <output>fcs/right-aileron-pos-rad</output>
            </aerosurface_scale>

            <aerosurface_scale name="Left aileron Normalized">
                <input>fcs/left-aileron-pos-rad</input>
                <domain>
                    <min>-0.35</min>
                    <max> 0.35</max>
                </domain>
                <range>
                    <min>-1</min>
                    <max> 1</max>
                </range>
                <output>fcs/left-aileron-pos-norm</output>
            </aerosurface_scale>

            <aerosurface_scale name="Right aileron Normalized">
                <input>fcs/right-aileron-pos-rad</input>
                <domain>
                    <min>-0.35</min>
                    <max> 0.35</max>
                </domain>
                <range>
                    <min>-1</min>
                    <max> 1</max>
                </range>
                <output>fcs/right-aileron-pos-norm</output>
            </aerosurface_scale>

        </channel>
        <channel name="Yaw">

            <summer name="Rudder Command Sum">
                <input>fcs/rudder-cmd-norm</input>
                <input>fcs/yaw-trim-cmd-norm</input>
                <clipto>
                    <min>-1</min>
                    <max> 1</max>
                </clipto>
            </summer>

            <scheduled_gain name="Yaw Damper">
                <input>velocities/r-aero-rad_sec</input>
                <table>
                  <independentVar>velocities/mach</independentVar>
                    <tableData>
                        0.00	0.0
                        0.10	0.0
                        0.11	1.0
                    </tableData>
                </table>
            </scheduled_gain>

            <scheduled_gain name="Yaw Damper Final">
                <input>fcs/yaw-damper</input>
                <table>
                  <independentVar>velocities/mach</independentVar>
                    <tableData>
                        0.00	0.0
                        0.10	0.0
                        0.11	1.0
                    </tableData>
                </table>
            </scheduled_gain>

            <summer name="Rudder Sum">
                <input>fcs/rudder-command-sum</input>
                <input>fcs/yaw-damper-final</input>
                <clipto>
                    <min>-1</min>
                    <max> 1</max>
                </clipto>
            </summer>

            <aerosurface_scale name="Rudder Control">
                <input>fcs/rudder-sum</input>
                <range>
                    <min>-0.35</min>
                    <max> 0.35</max>
                </range>
                <output>fcs/rudder-pos-rad</output>
            </aerosurface_scale>

            <aerosurface_scale name="Rudder Normalized">
                <input>fcs/rudder-pos-rad</input>
                <domain>
                    <min>-0.35</min>
                    <max> 0.35</max>
                </domain>
                <range>
                    <min>-1</min>
                    <max> 1</max>
                </range>
                <output>fcs/rudder-pos-norm</output>
            </aerosurface_scale>

        </channel>
        <channel name="Flaps">

            <kinematic name="Flaps Control">
                <input>fcs/flap-cmd-norm</input>
                <traverse>
                    <setting>
                        <position>0</position>
                        <time>0</time>
                    </setting>
                    <setting>
                        <position>0.125</position>
                        <time>5</time>
                    </setting>
                    <setting>
                        <position>0.25</position>
                        <time>4</time>
                    </setting>
                    <setting>
                        <position>0.375</position>
                        <time>3</time>
                    </setting>
                    <setting>
                        <position>0.5</position>
                        <time>2</time>
                    </setting>
                    <setting>
                        <position>0.625</position>
                        <time>2</time>
                    </setting>
                    <setting>
                        <position>0.75</position>
                        <time>2</time>
                    </setting>
                    <setting>
                        <position>0.875</position>
                        <time>2</time>
                    </setting>
                    <setting>
                        <position>1</position>
                        <time>2</time>
                    </setting>
                </traverse>
                <output>fcs/flap-pos-norm</output>
            </kinematic>

        </channel>
        <channel name="Landing Gear">

            <kinematic name="Gear Control">
                <input>gear/gear-cmd-norm</input>
                <traverse>
                    <setting>
                        <position>0</position>
                        <time>0</time>
                    </setting>
                    <setting>
                        <position>1</position>
                        <time>5</time>
                    </setting>
                </traverse>
                <output>gear/gear-pos-norm</output>
            </kinematic>

        </channel>
        <channel name="Flight Spoilers">
          <!-- operated by the speedbrake handle and roll control -->
            <kinematic name="Flight Spoilers Control">
                <input>fcs/speedbrake-cmd-norm</input>
                <traverse>
                    <setting>
                        <position>0</position>
                        <time>0</time>
                    </setting>
                    <setting>
                        <position>1</position>
                        <time>0.6</time>
                    </setting>
                </traverse>
                <output>fcs/speedbrake-pos-norm</output>
            </kinematic>

        </channel>
        <channel name="Ground Spoilers">
          <!-- these only operate on the ground -->
            <kinematic name="Ground Spoilers Control">
                <input>fcs/spoiler-cmd-norm</input>
                <traverse>
                    <setting>
                        <position>0</position>
                        <time>0</time>
                    </setting>
                    <setting>
                        <position>1</position>
                        <time>0.6</time>
                    </setting>
                </traverse>
                <output>fcs/spoiler-pos-norm</output>
            </kinematic>

        </channel>

    </flight_control>

Roll, Pitch, and Yaw | How Things Fly (si.edu)

What is Pitch, Roll and Yaw ? - Emissary Drones

  • Pitch

Loading Component' Pitch Trim Sum" of type: SURAMER
Minimum 1imit: - 1. 000000
Maximum 1imit: 1. 000000
INPUTS:
e1 evator - cmd-norm
pi tch-trim-cnd-norm
OUTPUT: pi tch-trim- sum

Loading Component' E1evator Contro1" of type: AEROSURF ACE SCALE
INPUT: pi tch-trim- sum
GAIN: constant value 1. 000000
OUTPUT: elevator-pos-rad
OUTPUT: e1 evator- contro1
In/Out Mapping:
Input MIN: -1. 0000
Input MAX: 1. 0000
Output MIN: -0. 3000
Output MAX: 0. 3000
Loading Comp>onent" Elevator Normalized" of type: AEROSURF ACE_ SCALE
INPUT: elevator -pos-rad
GAIN: constant value 1. 000000
OUTPUT: elevator -pos-norm
OUTPUT: e1 eva tor -norma1i zed
In/Out Mapping:
Input MIN: -0. 3000
Input MAX: 0. 3000
Output MIN: - 1.0000
Output MAX: 1. 0000

  • Roll

    Channe1 Ro11
    Loading Component' Ro11 Trim Sum" of type: SUAMER
    Minimum limit: - 1.000000
    Maximum 1imit: 1. 00000
    INPUTS:
    ai 1 eron- cmd-norm
    ro11 -trim- cmd-norm
    OUTPUT: ro11- trim-sum

    Loading Component' Left Aileron Contro1" of type: AEROSURF ACE SCALE
    INPUT: rol1-trim-sum
    GAIN: constant value 1. 000000
    OUTPUT: 1eft-ai1eron-pos-rad
    OUTPUT: 1eft-aileron-contro1
    In/Out Mapping:
    Input MIN: -1. 0000
    Input MAX: 1. 0000
    Output MHIN: -0. 3500
    Output MAX: 0. 3500

    Loading Conponent Right Ai1eron Contro1”of type: AEROSURF ACE SCALE
    INPUT: -ro11 -trim-sum
    GAIN: constant value 1. 000000
    OUTPUT: right-ai1eron pos-rad
    OUTPUT: ri ght- aileron-contro1
    In/Out Mapping:
    Input MIN: -1. 0000
    Input MAX: 1. 0000
    Output MHIN: -0. 3500
    Output JIAX: 0. 3500

    Loading Component' Left aileron Normalized" of type: AEROSURF ACE SCALE
    INPUT: 1eft-aileron pos-rad
    GAIN: constant value 1. 000000
    OUTPUT: 1eft-ai1eron-pos-norm
    OUTPUT: 1eft-aileron-normalized
    In/Out ]lapping:
    Input MIN: -0. 3500
    Input MAX: 0. 3500
    Output MIN: - 1.0000
    Output MAX: 1. 0000

    Loading Component' Right aileron Normalized" of type: AEROSURFACE SCALE
    INPUT: ri ght-ai 1eron-pos-rad
    GAIN: constant. value 1. 000000
    OUTPUT: ri ght-ai1 eron-pos-norm
    OUTPUT: ri ght-ai1 eron-normalized
    In/Out ]lapping:
    Input MIN: -0. 3500
    Input MAX: 0. 3500
    Output MIN: - 1.0000
    Output MAX: 1. 0000

  • Yaw

    Channel Yaw
    Loading Component ' Rudder Command Sum" of type: SUKER
    Minimum limit: -1. 000000
    Maximum limit: 1. 000000
    INPUTS:
    rudder - cmd- norm
    yaw-tr i m- cnd-norm
    OUTPUT: rudder-command-sum

    Loading Component " Yaw Damper" of type: SCHEDULED GAIN
    1 dimensional tab1e with 3 rows.
    0.0000 0. 0000
    0.1000 0. 0000

    ​ 0.1100 1. 0000
    ​ INPUT: r-aero-rad_ sec
    ​ GAIN: constant value 1. 000000
    ​ OUTPUT: yaw-damper
    ​ Scheduled by tab1e:
    1 dimensional tab1e with 3 rows.
    ​ 0.0000 0. 0000

    ​ 0.1000 0.0000

    ​ 0.1100 1.0000

    Loading Component' Yaw Damper Final” of type: SCHEDULED GAIN
    1 di mensional table with 3 rows.
    0.0000 0. 0000
    0.1000 0.0000

    ​ 0.1100 1. 0000
    ​ INPUT: yaw-damper
    ​ GAIN: constant value 1. 000000
    ​ OUTPUT: yaw-danper-fina1
    ​ Scheduled by tab1e:
    1 dimensional tab1e with 3 rows.
    ​ 0.0000 0. 0000

    ​ 0.1000 0. 0000

    ​ 0.1100 1. 0000

    Loading Component' Rudder Sum" of type: SUMIMER

    ​ Minimum 1imit: -1. 00000
    ​ Maximum limit: 1. 000000
    ​ INPUTS:
    ​ rudder - command- sum
    ​ yaw- damper- fina1
    ​ OUTPUT: rudder -sum

    Loading Component "Rudder Contro1" of type: AEROSURF ACE SCALE
    INPUT: rudder-sum
    GAIN: constant value 1. 000000
    OUTPUT: rudder-pos rad
    OUTPUT: rudder -contro1
    In/0ut Mapping :
    Input MIN: -1. 0000
    Input MAX: 1. 0000
    Output MIN: -0. 3500
    Output MAX: 0. 3500

    Loading Component' Rudder Normalized" of type: AEROSURF ACE SCALE
    INPUT: rudder-pos-rad
    GAIN: constant value 1. 000000
    OUTPUT :rudder -pos -norm
    OUTPUT: rudder -normalized
    In/Out Mapping :
    Input MIN: -0. 3500
    Input MAX: 0. 3500
    Output MIN: - 1.0000
    Output MAX: 1. 0000

  • Flaps

    Channel F1aps
    Loading Component "F1aps Contro1"of type: KINEMATIC
    INPUT: f1 ap-cmd-norm
    DETENTS: 9

    ​ 0.0000 0.0000

    ​ 0.1250 5.0000

    ​ 0.2500 4.0000
    ​ 0.3750 3. 0000
    ​ 0.5000 2. 0000
    ​ 0.6250 2. 0000
    ​ 0.7500 2. 0000
    ​ 0.8750 2. 0000
    ​ 1.0000 2. 0000
    ​ OUTPUT: flap-pos-norm
    ​ OUTPUT: flaps-contro1

  • Landing Gear

    Channel Landing Gear

    Loading Component' Gear Contro1" of type: KINEMATIC
    INPUT: gear-cmd norm
    DETENTS: 2
    0.0000 0. 0000

    ​ 1.0000 5. 0000
    OUTPUT: gear -pos-norm
    OUTPUT: gear- contro1

  • Flight Spoilers

    Channel F1ight Spoilers

    Loading Component' F1ight Spoilers Contro1” of type: KINEMATIC
    INPUT: speedbrake-cmd-norm
    DETENTS: 2
    0.0000 0.0000
    1.0000 0.6000
    OUTPUT: speedbrake-pos -norm
    OUTPUT: flight-spoi1 ers-control

  • Ground Spoilers

    Channe1 Ground Spoilers

    Loading Component' Ground Spoilers Contro1" of type: KINEMATIC
    INPUT: spoi 1 er cmd-norm
    DETENTS: 2
    0.0000 0. 0000

    ​ 1.0000 0. 6000
    ​ OUTPUT: spoiler-pos-norm
    ​ OUTPUT: ground- spoil ers-control

    1 dimensional table wi th 10 rows.

    ​ 0.0000 0.0480
    ​ 0.1000 0.5150
    ​ 0.1500 0.6290
    ​ 0.2000 0.7090
    ​ 0.3000 0.8150

    ​ 0.4000 0.8820
    ​ 0.5000 0.9280
    ​ 0.6000 0.9620
    ​ 0.7000 0.9880
    ​ 0.8000 1.0000
    Function: aero/ functi on/ kCDge
    1 di mensional table with 13 rows.

    ​ 0.0000 1.2030
    ​ 0.1000 1.1270
    ​ 0.1500 1.0900

    ​ 0.2000 1.0730
    ​ 0.3000 1.0460
    ​ 0.4000 1.0280
    ​ 0.5000 1.0190
    ​ 0.6000 1.0130
    ​ 0.7000 1.0080
    ​ 0.8000 1.0060
    ​ 0.9000 1.0030
    ​ 1.0000 1.0020

    ​ 1.1000 1.0000
    Function: aero/ function/kCLge
    1 di mensional table with 2 rows.
    ​ 0.0000 1.0000
    ​ 0.1000 0.8500
    Function: aero/ functi on/kCLsb
    1 dimensional table with 2 rows.
    ​ 0.0000 1.0000

    ​ 0.1000 0.6000
    Function: aero/ functi on/kCLsp

Aerodynamics 空气动力学稳定性导数和系数

aircraft/737.xml 451行

image-20220325102900400

四个函数分别是 ,

        <function name="aero/function/kCDge">
            <description>Change_in_drag_due_to_ground_effect</description>
            <table>
                <independentVar>aero/h_b-mac-ft</independentVar>
                <tableData>
                    0.0000	0.0480
                    0.1000	0.5150
                    0.1500	0.6290
                    0.2000	0.7090
                    0.3000	0.8150
                    0.4000	0.8820
                    0.5000	0.9280
                    0.6000	0.9620
                    0.7000	0.9880
                    0.8000	1.0000
                </tableData>
            </table>
        </function>

        <function name="aero/function/kCLge">
            <description>Change_in_lift_due_to_ground_effect</description>
            <table>
                <independentVar>aero/h_b-mac-ft</independentVar>
                <tableData>
                    0.0000	1.2030
                    0.1000	1.1270
                    0.1500	1.0900
                    0.2000	1.0730
                    0.3000	1.0460
                    0.4000	1.0280
                    0.5000	1.0190
                    0.6000	1.0130
                    0.7000	1.0080
                    0.8000	1.0060
                    0.9000	1.0030
                    1.0000	1.0020
                    1.1000	1.0000
                </tableData>
            </table>
        </function>

        <function name="aero/function/kCLsb">
            <description>Change_in_lift_due_to_speed_brake</description>
            <table>
                <independentVar>fcs/speedbrake-pos-norm</independentVar>
                <tableData>
                    0.0000	1.0
                    0.1000	0.85
                </tableData>
            </table>
        </function>

        <function name="aero/function/kCLsp">
            <description>Change_in_lift_due_to_spoilers</description>
            <table>
                <independentVar>fcs/spoiler-pos-norm</independentVar>
                <tableData>
                    0.0000	1.0
                    0.1000	0.6
                </tableData>
            </table>
        </function>

Declared properties

xml 文件

<use aircraft="737" initialize="cruise_init"/>

结果:

Event

Event 0

对应的xml脚本内容:

 	<property value="0"> simulation/notify-time-trigger </property>

    <event name="Reset Initial Conditions"> 
      <condition> simulation/sim-time-sec ge 0 </condition>
      <set name="ic/h-sl-ft" value="30000"/>
      <set name="ic/mach"    value="0.78"/>
      <notify>
        <property caption="Altitude ASL">ic/h-sl-ft</property>
        <property caption="Mach .......">ic/mach</property>
      </notify>
    </event>

结果;

Event 1

对应的xml脚本内容:

<event name="Set engines running / raise gear">
      <condition> simulation/sim-time-sec ge 0 </condition>
      <set name="propulsion/engine[0]/set-running" value="1"/>
      <set name="propulsion/engine[1]/set-running" value="1"/>
      <set name="gear/gear-cmd-norm" value="0"/>
      <set name="gear/gear-pos-norm" value="0"/>
      <notify>
        <property caption="Eng[0] Thrust (lbs)">propulsion/engine[0]/thrust-lbs</property>
        <property caption="Eng[1] Thrust (lbs)">propulsion/engine[1]/thrust-lbs</property>
        <property caption="Gear Position .....">gear/gear-pos-norm</property>
      </notify>
    </event>

结果;

Event 2

对应的xml脚本内容:

<!--
      For "do_simple_trim" (Classic trim):
      0: Longitudinal
      1: Full
      2: Ground
      3: Pullup
      4: Custom
      5: Turn
      6: None
    -->
    
    <event name="Start Trim">
      <condition> gear/gear-pos-norm eq 0 </condition>
      <set name="simulation/do_simple_trim" value="0"/>
    </event>

结果;

Event 3

对应的xml脚本内容:

<event name="Repeating Notify" persistent="true">
      <description>Output message at 10 second intervals, starting after
                   trimming is completed.
      </description>
      <notify>
        <property>position/h-agl-ft</property>
        <property>velocities/mach</property>  
        <property>propulsion/engine[0]/n2</property>
        <property>propulsion/engine[1]/n2</property>
        <property>propulsion/engine[0]/thrust-lbs</property>
        <property>propulsion/engine[1]/thrust-lbs</property>
        <property>velocities/vc-kts</property>
        <property>velocities/vc-fps</property>
        <property>velocities/vt-fps</property>
        <property>attitude/theta-rad</property>
        <property>aero/alpha-deg</property>
        <property>simulation/frame</property>
      </notify>
      <condition logic="AND">
        simulation/sim-time-sec >= simulation/notify-time-trigger
        simulation/trim-completed eq 1
      </condition>
      <set name="simulation/notify-time-trigger" value="10" type="FG_DELTA"/>
    </event>

结果;

4 在Pyhton中调用JSBSim

demo 1

GitHub - JSBSim-Team/jsbsim: An open source flight dynamics & control software library

image-20220324085517548

import jsbsim

fdm = jsbsim.FGFDMExec(None)  # Use JSBSim default aircraft data.
fdm.load_script('scripts/c1723.xml')
fdm.run_ic()
fdm[]=1
while fdm.run():
  pass

demo2 -JSBSim.py

这个py文件的目的是使用JSBSim.py脚本 在命令行中运行

#! /usr/bin/python
#
# JSBSim.py
#
# Standalone version of JSBSim in Python language.
#
# Copyright (c) 2019 Bertrand Coconnier
#
# This program is free software; you can redistribute it and/or modify it under
# the terms of the GNU General Public License as published by the Free Software
# Foundation; either version 3 of the License, or (at your option) any later
# version.
#
# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
# FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
# details.
#
# You should have received a copy of the GNU General Public License along with
# this program; if not, see <http://www.gnu.org/licenses/>
#

import xml.etree.ElementTree as et
import argparse, sys, os
import jsbsim
import time

parser = argparse.ArgumentParser()
parser.add_argument("input", nargs='?', help="script file name")
parser.add_argument("--version", action="version",
                    version="%(prog)s {}".format(jsbsim.FGJSBBase().get_version()))
parser.add_argument("--outputlogfile", action="append", metavar="<filename>",
                    help="sets (overrides) the name of a data output file")
parser.add_argument("--logdirectivefile", action="append", metavar="<filename>",
                    help="specifies the name of a data logging directives file")
parser.add_argument("--root", default='.', metavar="<path>",
                    help="specifies the JSBSim root directory (where aircraft/, engine/, etc. reside)")
parser.add_argument("--aircraft", metavar="<filename>",
                    help="specifies the name of the aircraft to be modeled")
parser.add_argument("--script", metavar="<filename>",
                    help="specifies a script to run")
parser.add_argument("--initfile", metavar="<filename>",
                    help="specifies an initialization file")
parser.add_argument("--end", type=float, default=1E99, metavar="<time (double)>",
                    help="specifies the sim end time")
parser.add_argument("--realtime", default=False, action="store_true",
                    help="specifies to run in real world time")
parser.add_argument("--nice", default=False, action="store_true",
                    help="specifies to run at lower CPU usage")
args = parser.parse_args()

sleep_period = 0.01


def CheckXMLFile(f):
    # Is f a file ?
    if not os.path.isfile(f):
        return None

    # Is f an XML file ?
    try:
        tree = et.parse(f)
    except et.ParseError:
        return None

    return tree


if args.input:
    tree = CheckXMLFile(args.input)
    if not tree:
        print('The argument "{}" cannot be interpreted as a file name.'.format(args.input))
        sys.exit(1)

    root = tree.getroot()

    if root.tag == 'runscript':
        if args.script:
            print('Two script files are specified.')
            sys.exit(1)
        else:
            args.script = args.input

    if root.tag == 'output':
        if args.logdirectivefile:
            args.logdirectivefile += [args.input]
        else:
            args.logdirectivefile = [args.input]

    if root.tag == 'fdm_config':
        if args.aircraft:
            print('Two aircraft files are specified.')
            sys.exit(1)
        else:
            args.aircraft = args.input

fdm = jsbsim.FGFDMExec(args.root, None)

if args.script:
    fdm.load_script(args.script)
elif args.aircraft:
    fdm.load_model(args.aircraft, False)
    if args.initfile:
        fdm.load_ic(args.initfile, True)

if args.initfile and not args.aircraft:
    print("You must specify an initilization file with the aircraft name")
    sys.exit(1)

if args.logdirectivefile:
    for f in args.logdirectivefile:
        if not fdm.set_output_directive(f):
            print("Output directives not properly set in file {}".format(f))
            sys.exit(1)

if args.outputlogfile:
    for n, f in enumerate(args.outputlogfile):
        old_filename = fdm.get_output_filename(n)
        if not fdm.set_output_filename(n, f):
            print("Output filename could not be set")
        else:
            print("Output filename change from {} from aircraft configuration file to {} specified on command line.".format(old_filename, f))

fdm.run_ic()
fdm.print_simulation_configuration()
frame_duration = fdm.get_delta_t()
sleep_nseconds = (frame_duration if args.realtime else sleep_period) * 1E9
current_seconds = initial_seconds = time.time()
result = fdm.run()

while result and fdm.get_sim_time() <= args.end:
    if args.realtime:
        current_seconds = time.time()
        actual_elapsed_time = current_seconds - initial_seconds
        sim_lag_time = actual_elapsed_time - fdm.get_sim_time()

        for _ in range(int(sim_lag_time / frame_duration)):
            result = fdm.run()
            current_seconds = time.time()
    else:
        result = fdm.run()

        if args.nice:
            time.sleep(sleep_nseconds / 1000000.0)

demo2中使用到的函数解析

python之parser.add_argument()用法——命令行选项、参数和子命令解析器_夏普通的博客-CSDN博客_parser.add_argument(

效果测试:

首先使用Anconda进入相关环境 ,然后在命令行运行

demo3 PlotAoaVsCAS.py

jsbsim-master/examples/python/PlotAoaVsCAS.py


查看fdm对象的属性

FGFDMExec
root dir : ../..
aircraft path : ../../aircraft
engine path : ../../engine
systems path : ../../systems
output path : ../../.

5 解析源码

1 jsbsim.py/class FGFDMExec(FGJSBBase)

注释:

class FGFDMExec(FGJSBBase):
    """
    Encapsulates the JSBSim simulation executive.
    
           This class is the executive class through which all other simulation
           classes are instantiated, initialized, and run. When integrated with
           FlightGear (or other flight simulator) this class is typically
           instantiated by an interface class on the simulator side.
    
           At the time of simulation initialization, the interface class creates an
           instance of this executive class. The executive is subsequently directed
           to load the chosen aircraft specification file:
    
           .. code-block:: cpp
    
              fdmex = new FGFDMExec( ... );
              result = fdmex->LoadModel( ... );
    
           When an aircraft model is loaded, the config file is parsed and for each
           of the sections of the config file (propulsion, flight control, etc.)
           the corresponding Load() method is called (e.g. FGFCS::Load()).
    
           Subsequent to the creation of the executive and loading of the model,
           initialization is performed. Initialization involves copying control
           inputs into the appropriate JSBSim data storage locations, configuring
           it for the set of user supplied initial conditions, and then copying
           state variables from JSBSim. The state variables are used to drive the
           instrument displays and to place the vehicle model in world space for
           visual rendering:
    
           .. code-block:: cpp
    
              copy_to_JSBsim(); // copy control inputs to JSBSim
              fdmex->RunIC(); // loop JSBSim once w/o integrating
              copy_from_JSBsim(); // update the bus
    
           Once initialization is complete, cyclic execution proceeds:
    
           .. code-block:: cpp
    
              copy_to_JSBsim(); // copy control inputs to JSBSim
              fdmex->Run(); // execute JSBSim
              copy_from_JSBsim(); // update the bus
    
           JSBSim can be used in a standalone mode by creating a compact stub
           program that effectively performs the same progression of steps as
           outlined above for the integrated version, but with two exceptions.
           First, the copy_to_JSBSim() and copy_from_JSBSim() functions are not
           used because the control inputs are handled directly by the scripting
           facilities and outputs are handled by the output (data logging) class.
           Second, the name of a script file can be supplied to the stub program.
           Scripting (see FGScript) provides a way to supply command inputs to the
           simulation:
    
           .. code-block:: cpp
    
              FDMExec = new JSBSim::FGFDMExec();
              FDMExec->LoadScript( ScriptName ); // the script loads the aircraft and ICs
              result = FDMExec->Run();
              while (result) { // cyclic execution
                result = FDMExec->Run(); // execute JSBSim
              }
    
           The standalone mode has been useful for verifying changes before
           committing updates to the source code repository. It is also useful for
           running sets of tests that reveal some aspects of simulated aircraft
           performance, such as range, time-to-climb, takeoff distance, etc.
    
           .. rubric:: JSBSim Debugging Directives
    
           This describes to any interested entity the debug level requested by
           setting the JSBSIM_DEBUG environment variable. The bitmasked value
           choices are as follows:
    
           * **unset**: In this case (the default) JSBSim would only print out the
             normally expected messages, essentially echoing the config files as
             they are read. If the environment variable is not set, debug_lvl is
             set to 1 internally
           * **0**: This requests JSBSim not to output any messages whatsoever
           * **1**: This value explicity requests the normal JSBSim startup
             messages
           * **2**: This value asks for a message to be printed out when a class is
             instantiated
           * **4**: When this value is set, a message is displayed when a FGModel
             object executes its Run() method
           * **8**: When this value is set, various runtime state variables are
             printed out periodically
           * **16**: When set various parameters are sanity checked and a message
             is printed out when they go out of bounds
    
           .. rubric:: Properties
    
           * **simulator/do_trim** (write only) Can be set to the integer
             equivalent to one of tLongitudinal (0), tFull (1), tGround (2),
             tPullup (3), tCustom (4), tTurn (5). Setting this to a legal value
             (such as by a script) causes a trim to be performed. This property
             actually maps toa function call of DoTrim().
    """

翻译如下:

封装 JSBSim 仿真执行程序。

 这个类是执行类,通过它所有其他模拟
 类被实例化、初始化和运行。当与
 FlightGear(或其他飞行模拟器)这个类通常是
 由模拟器端的接口类实例化。

 在模拟初始化的时候,接口类创建一个
 这个行政级别的实例。行政人员随后被指示
 加载选择的飞机规格文件:

 .. 代码块:: cpp

    fdmex = 新 FGFDMExec( ... );
    结果 = fdmex->LoadModel( ... );

 加载飞机模型时,会解析配置文件并为每个
 配置文件的部分(推进、飞行控制等)
 调用相应的 Load() 方法(例如 FGFCS::Load())。

 在创建执行程序和加载模型之后,
 执行初始化。初始化涉及复制控制
 输入到适当的 JSBSim 数据存储位置,配置
 它为一组用户提供的初始条件,然后复制
 来自 JSBSim 的状态变量。状态变量用于驱动
 仪表显示并将车辆模型放置在世界空间中
 视觉渲染:

 .. 代码块:: cpp

    copy_to_JSBsim(); // 将控制输入复制到 JSBSim
    fdmex->RunIC(); // 循环 JSBSim 一次,无需积分
    copy_from_JSBsim(); //更新总线

 初始化完成后,循环执行继续:

 .. 代码块:: cpp

    copy_to_JSBsim(); // 将控制输入复制到 JSBSim
    fdmex->运行(); // 执行 JSBSim
    copy_from_JSBsim(); //更新总线

 JSBSim 可以通过创建一个紧凑的存根在独立模式下使用
 有效地执行与步骤相同的程序
 上面对集成版本进行了概述,但有两个例外。
 首先,copy_to_JSBSim() 和 copy_from_JSBSim() 函数不是
 使用,因为控制输入直接由脚本处理
 设施和输出由输出(数据记录)类处理。
 其次,脚本文件的名称可以提供给存根程序。
 脚本(参见 FGScript)提供了一种向
 模拟:

 .. 代码块:: cpp

    FDMExec = 新 JSBSim::FGFDMExec();
    FDMExec->LoadScript( ScriptName ); // 脚本加载飞行器和 IC
    结果 = FDMExec->运行();
    while (result) { // 循环执行
      结果 = FDMExec->运行(); // 执行 JSBSim
    }

 独立模式对于之前验证更改很有用
 提交对源代码存储库的更新。它也适用于
 运行一组测试,揭示模拟飞机的某些方面
 性能,例如航程、爬升时间、起飞距离等。

 .. rubric:: JSBSim 调试指令

 这向任何感兴趣的实体描述了所请求的调试级别
 设置 JSBSIM_DEBUG 环境变量。位掩码值
 选择如下:

     * **未设置**:在这种情况下(默认)JSBSim 只会打印出
       通常预期的消息,基本上将配置文件回显为
       他们被阅读。如果未设置环境变量,则 debug_lvl 为
       内部设置为 1
     * **0**:这要求 JSBSim 不输出任何消息
     * **1**:此值明确请求正常的 JSBSim 启动
       消息
     * **2**:该值要求在上课时打印一条消息
       实例化
     * **4**:设置此值时,FGModel 时会显示一条消息
       对象执行其 Run() 方法
     * **8**:设置此值时,各种运行时状态变量
       定期打印
     * **16**:设置各种参数时会检查是否正常并显示消息
       当它们超出范围时打印出来

     .. rubric:: 属性

     * **simulator/do_trim** (只写) 可以设置为整数
       相当于 tLongitudinal (0)、tFull (1)、tGround (2) 之一,
       tPullup (3)、tCustom (4)、tTurn (5)。将此设置为合法值
       (例如通过脚本)导致执行修剪。这个性质
       实际上映射到 DoTrim() 的函数调用。

"""

6 gym-JSBSim 环境配置

GitHub - Gor-Ren/gym-jsbsim: A reinforcement learning environment for aircraft control using the JSBSim flight dynamics model

posted @ 2024-03-24 18:43  英飞  阅读(677)  评论(0编辑  收藏  举报