Repository navigation
XX-1 aircraft model in ArduPlane SITL #10
Mission-analyzer
started this conversation in
General
Replies: 0 comments
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Update (2 October 2026): the control-authority estimate in section 4 (step 7) and section 6 was corrected. The first version assumed that a full control deflection corresponds to 57.3 °/s at the scaling speed; the ArduPlane code gives 45 °/s, i.e. about 57 °/s at 47 m/s instead of 73 °/s. The model package attached in section 7 was rebuilt accordingly (
c_l_deltaaandc_m_deltaeare 21.5% lower); the figures are unchanged.A note on how to build a low-order model of a UAV for ArduPlane SITL from the data that are usually found in the
aircraft flight manual (FM), and how to refine the model parameters afterwards from the telemetry (tlog) of a test
flight. The example is the XX-1 aircraft.
1. Why a model is needed
ArduPlane SITL runs the same autopilot code as the aircraft itself (flight modes, TECS, navigation, command
handling), so missions, mode changes and autopilot logic can be tested without a real aircraft. The closer the
aircraft model is to the real vehicle, the more meaningful such a run is. This calls for a model of a specific
aircraft rather than a generic one.
2. Why the ArduPlane model and not X-Plane 12
Note that ArduPilot can work with X-Plane as well (SITL has a dedicated X-Plane back end) and with JSBSim. The
question is not compatibility but who computes the aircraft physics and what we pay for it.
ArduPlane.elfWhat is decisive for us: the goal is checking autopilot and mission logic, not a visually convincing flight.
For that it is enough for the model to reproduce speeds, the required throttle, climb and descent, control response and
stability, and such a model is easier and more reliable to fit to flight data when it boils down to a small number of
understandable numbers. Independence from a third-party commercial product is an additional argument.
X-Plane remains a good option for an independent cross-check: if you ever need to compare the behaviour of our
model with physics derived from geometry, it is suitable for that.
Low-order model
A low-order model (reduced-order model) is a simplified description of an object with a small number of state
variables and parameters. It reproduces only the dynamics that matter for the task at hand and deliberately neglects
the rest. The price of simplicity is a limited range of validity: the model is valid in the regimes its parameters
were fitted to.
Our XX-1 model is a low-order model. Comparison with an analogous model of the same aircraft in X-Plane 12:
Conclusion. In terms of rigid-body motion the models are of the same order (12 states). They differ in the order of
the description of aerodynamics and the propulsion system: about forty numbers for ours, tens of thousands of
properties for X-Plane. It is therefore correct to call our model a low-order model and the X-Plane model a detailed
(high-order) one.
The parameters of a low-order model can be estimated from a test flight. There are few unknowns and each has a
physical meaning, so they are determined from a small number of test regimes (system identification from flight data,
"grey-box": the structure and some of the parameters are physical, the rest are found from data). This is what we did:
geometry, mass and stall speed are given by documented data, and the rest was estimated from a real flight
(section 6):
Parameters for which the test flight has no suitable regimes remain calculated or are estimated only as bounds, so the
test-flight programme should be designed in advance around the missing parameters and include safe manoeuvres. This is
what makes a low-order model convenient: it can be refined after every new flight without rebuilding the model itself.
3. What source data are needed
The basis of the model is the characteristics of a specific aircraft, not typical values. Such data are usually found
in the aircraft flight manual (FM) or in the technical documentation of the vehicle.
Fig. 1. XX-1, top view: straight wing, two booms, pusher propeller, V-tail. The wingspan used in the calculation is
5.73 m (the diagram shows 5.80 m, measured over the wingtips).
The in-flight mass is 200–220 kg; the model uses the middle of the range, 210 kg.
4. How the model is built
The calculation is reproducible with the scripts in
tools/(Python,numpyrequired). All assumptions are collectedas constants at the top of
design.pyand marked as assumptions. The model package is attached to this post (seesection 7); paths in this note are relative to the unpacked package folder.
The aircraft is therefore scaled to 2 kg while keeping the wing loading and all speeds:
S_model = S_real · m_SITL / m_real. Speeds, angles and turn radii do not change as a result.CLmax = 2·m·g / (ρ·S·Vs²); the stall angle in the model is selected from it.source data do not cover; it is refined from flight data (section 6).
configured. For the autopilot throttle percentages to match the real ones, the throttle output is compressed with
the
SERVO3_MAXparameter: the cruise thrust falls at the throttle measured in flight. The thrust line and theengine location are not modelled in SITL (thrust acts along the aircraft axis through the centre of mass).
this is not an error. They are selected for target eigenmodes by computing the eigenvalues of the linearised
equations (the same formulas as in the SITL source): short-period mode 4.5 rad/s with damping 0.7, roll time
constant 0.25 s, Dutch roll 3.0 rad/s with damping 0.35, stable spiral mode.
-vtailmode). ArduPlane mixes the elevator command E and the rudder command Rinto the two tail halves: right = (E−R)·g, left = (E+R)·g, where g is
MIXING_GAIN. SITL decodes them back fromservo channels 2 and 4. Of the four possible servo layouts only one is correct (channel 2 — right half, reversed;
channel 4 — left half); the others swap the controls or flip a sign. This was verified by calculation using the
formulas of both sides (
tools/vtail_check.py). Becauseg = 0.5, the modelled control surface works at halfeffectiveness, so the control derivatives are doubled.
feed-forward output is
FF × rate[°/s] × scaler, wherescaler = SCALING_SPEED / V, and a full command correspondsto ±45° of surface travel. Hence with
RLL_RATE_FF = PTCH_RATE_FF = 1.0full deflection corresponds to 45 °/s atthe scaling speed of 37 m/s and to about 57 °/s at 47 m/s. We checked this relation on the stock SITL aircraft,
where the true roll authority is known: the code gives 278 °/s, the model physics 335 °/s (ratio 0.83). For roll the
estimate from flight (section 6) does not contradict the result; for pitch the relation is only an assumption,
because the pitch response is governed by the angle of attack and not by damping alone, and it is not yet confirmed.
xx1.json(coefficients) andxx1.parm(autopilot parameters: speeds, throttle, limits, TECS,controller gains, servo layout). They are generated by
tools/make_files.py.Launch: why the aircraft appears in the air
The real XX-1 is launched by a pyrotechnic (pyro) cartridge (about 45°): in the log of a real flight the acceleration to
37 m/s takes about 2 s, and an altitude of 30 m is reached at about 2.2 s. Of the source data only the angle of the
cartridge is known; the thrust and burn time were estimated from the log (about 5.0–5.7 kN and 2.0–2.2 s, impulse
about 11 kN·s).
The launch cannot be reproduced in SITL. The model's thrust at full throttle is 0.13 of its weight (it is tuned for
cruise), and on the ground SITL adds a drag of
0.3·v, so the acceleration ceiling is 4.2 m/s. SITL's built-inlaunchers (
-catapult,-bungee,-throw) give 24.5 / 19.3 / 9.9 m/s at the end of the launch against a stall speedof 30.2 m/s, i.e. the aircraft falls.
Therefore the Lua script
scripts/xx1_launch.luaplaces the aircraft in the air at arming in the "after launch"state (30 m, 38 m/s, flight path angle 9°, pitch 12°) and switches to AUTO. The method (
sim:set_pose) is taken fromArduPilot's official example
sim_arming_pos.lua. As in the developers' own tests,xx1.parmenablesSCR_ENABLE=1,AHRS_EKF_TYPE=10,EK3_ENABLE=0(otherwise the navigation filter sees a jump in position and velocity).Consequence: everything that happens after the launch can be tested (mission, modes, control); the acceleration
itself and launch failures are not reproduced.
5. Model limitations
comparison with the flight (section 6).
versus speed, fuel burn (the mass is constant), the launch itself (the aircraft is placed in the air, see above),
failures.
unknown).
AIRSPEED_MIN= 33 m/s is only 9% above the stall speed(30.2 m/s at 210 kg); at a 25° bank the margin drops to about 4%. This follows from the documented data.
6. How the model is refined from tlog
After a real flight we take what can be measured from the MAVLink telemetry log (tlog) and feed it back into the
constants of
design.py, then regenerate the model files. The analysis is done bytools/analyze_tlog.py; it takesthe servo parameters from the parameter dump recorded in the log itself.
What is determined reliably and has already been put into the model:
minutes airborne out of three hours of recording).
throttle (90% interval 72–79%), although
TRIM_THROTTLE= 65.SERVO3_MAXis set from this number.xx1.parmagainst the realconfiguration and to fix
THR_MIN(40 in flight).What is determined poorly, and why:
the throttle to gusts, which distorts the relation between throttle and climb. The assumed 10 lies within the
range. To narrow it, segments of climb and descent at constant throttle are needed.
47–56 °/s for full deflection (the model has 57 °/s, no contradiction), pitch at least 18–22 °/s (the model has
57 °/s, not confirmed). Safe segments with noticeable step commands in roll and pitch are needed.
Comparison of the model with the first flight:
The differences in climb and descent are caused by the model's linear thrust (see section 5).
Graphical comparison with the real flight.
Fig. 2. Pyro cartridge launch: the real log (dots) and the model (line; the band is the mass range 200–220 kg). The
thrust of 5.0 kN and the burn time of 2.2 s were fitted to the same data, so the figure shows how well a simple model
can reproduce the launch, but it is not an independent check. In the fit window the RMS error is: forward speed
2.6 m/s, vertical speed 2.5 m/s, altitude 1.7 m. After +3 s the aircraft is flown by the pilot while the model flies
without control, so the difference grows.
Fig. 3. Specific energy rate (climb rate at constant speed) versus throttle: 30 s windows from the straight segments
of the flight (dots), their means (diamonds) and the model line for L/D = 10 (the band is the L/D range of 9–17
allowed by the log). Only one regime is calibrated — level flight at 77% throttle; the climb and the descent are
predictions of the model.
The difference reaches 0.6 m/s and averages about 0.4 m/s. The model's linear thrust overestimates the climb at high
throttle (86–95%); at low throttle there are few data (three windows at 56%), so the conclusion there is preliminary.
Planned cross-check. The engine power and the propeller parameters (they are usually in the flight manual as well)
make it possible to estimate the thrust at operating speed and compare it with the drag found from the measured cruise
throttle. This gives an independent constraint on L/D that a single log cannot provide.
7. How to reproduce
The model package (
xx1.json,xx1.parm, the launch script and all analysis scripts) is attached to this post:[ATTACHMENT: drag
xx1_model_package.ziphere, then delete this line]It is distributed under GPL-3.0-or-later because it contains a Python port of ArduPilot SITL physics and files copied
from ArduPilot (see
NOTICE.mdinside the archive).To run, put
xx1.json,xx1.parmand thescriptsfolder (withxx1_launch.lua) into the SITL working folder nextto
ArduPlane.elfand start SITL with the arguments--model plane-vtail:xx1.json --defaults xx1.parm -w.8. Limitations of the estimates
preliminary; Fig. 2 and 3 are built from the same flight.
(stall, launch, ground) assumptions or the separate techniques described above are used.
All reactions