Rangefinder as only altitude source

Hello,

I am trying to connect a custom distance sensor to my copter facing downwards to measure altitude. So far I have succesfully connected a Raspberry Pi companion computer via MAVROS and I am able to read out the transfered distance_sensor_msg in the QGC’s MAVLINK inspector.

My goal is to have the copter solely rely on the data from the distance sensor to prove it’s capabilities. This means I would like the copter to ignore barometer as well as GPS altidude data.

To test this I fly the copter in position mode (altitude mode should also be fine) on a stable height (let’s say 1 m), then manuver it over a box (0.5 m). My expectation would be that since the distance to the ground decreases, the copter will fly up (to 1.5 m over floor which is 1 m over the box) to try to maintain it’s previous distance to the ground.

In my current tests the copter did not rise any further when directly over the box. I was able to see that the distance_sensor_msg changes as expected but the Vehicle_AltitudeRelative remained the same. Because of that I assume that PX4 eighter ignores the distance sensor completely, or it fuses altitude data from other sensors as well as IMU and thinks the distance sensor gives faulty readings, again ignoring it.

I wonder if there is a parameter that would allow me to achieve my goal, here is what I have tried so far:

  • EKF2_RNG_CTRL: 2 (Enabled) - Always read rangefinder data
    1 (Enabled, Conditional mode) - Read rangefinder at low speed
  • EKF2_HGT_REF: 2 (Range sensor) - Use rangefinder as primary source of height
  • MPC_ALT_MODE: 1 (Terrain following) - Adjust height to rangefinder reading, both when hovering and moving

After these basic settings I tried to manually deactivate other height sources, in that case GPS and Barometer:

  • EKF2_BARO_CTRL: 0 (Disabled) - Do not read barometer data
  • EKF2_GPS_CTRL: 5 - Bitmask (Position, 3D Velocity)
    7 - Bitmask (Position, 3D Velocity, Altitude)

In case of the barometer according to this post Distance sensor as only source of altitude - #4 by AlexandreBorowczyk I tried to increase it’s noise to have the EKF igrnore the baro:

  • EKF2_BARO_NOISE: 3 m → 15 m

I also played around with the time delay of the rangefinder (since it actually has a noticiable delay between the publishing of the ROS message and the readout of the distance_sensor_msg in QGC)

  • EKF2_RNG_DELAY: 5 ms → 300 ms

None of these options has achieved my goal, yet.

I was also thinking that it might be a vibration problem that could be solved by tuning the copter. I would be happy if anyone could give me a clue on what to try next or where to find out how the altitude is processed in PX4.

I might be missing something here, so please take this as a “thinking out loud” / debugging angle rather than a definitive answer :grinning_face:

From what I’ve seen, the main confusion with “rangefinder as the only altitude source” is that in PX4/EKF2 that phrase can map to slightly different semantics, and it’s easy for us to talk past each other.

In EKF2 there are (at least) two layers that get conflated:

  1. Height reference preference (EKF2_HGT_REF)
    This is more like “what EKF2 would like to anchor height to”, but it doesn’t necessarily mean other sources won’t still influence things (depending on the aiding path / constraints).

  2. Range height fusion + gating (EKF2_RNG_CTRL + range gates like EKF2_RNG_A_VMAX/HMAX)
    Even with a healthy rangefinder, fusion can be conditionally enabled/disabled based on speed/height/quality. So you can end up with behavior that feels like “range is the only source” in hover / low speed, but it quietly drops out once conditions change.

Also (and this is the part I’m least confident about without logs), the controller side may not interpret “altitude” the same way you do in that setup — depending on mode and MPC_ALT_MODE / terrain-following logic, it might be tracking local z vs HAGL (dist_bottom). So two setups can both be “using range” but still produce different altitude-hold behavior.

If your goal is “closed-loop altitude hold should be driven by range/HAGL as the primary truth”, I think the quickest sanity check is a log looking at:

  • whether range height fusion is actually active (e.g. estimator_aid_src_rng_hgt.fused, innovation/test_ratio), and

  • which signal the controller is really using in that mode (z vs dist_bottom / terrain estimate).

I’ve been trying to untangle this exact “semantic/priority” mismatch (especially around when range should dominate vs when it gets gated), but I’m definitely not 100% sure yet. I wrote up what I found + the relevant code paths / questions in this GitHub issue, in case it helps keep the deep dive in one place:
https://github.com/PX4/PX4-Autopilot/issues/26226

If you have a short log + your key params (EKF2_HGT_REF, EKF2_RNG_CTRL, EKF2_RNG_A_VMAX/HMAX, MPC_ALT_MODE), I’m happy to compare notes there — and we can circle back here once we have something concrete.


hello there, i too am doing the same thing with the tf02 rangefinder as the primary height source and also did the same parameter setup in px4 version 1.16.1rc
EKF2_RNG_CTRL=Enabled [ Always accept rangefinder data]
EKF2_HGT_REF= Range sensor[Take height ref from the rangefinder]
MPC_ALT_MODE= Terrain following
EKF2_BARO_CTRL: Disabled
EKF2_EV_CTRL=13 [Neglects the vertical from the openvins (vio)]
EKF2_RNG_DELAY=5ms
here are the following params that i changed
EKF2_BARO_CTRL 0
EKF2_EV_CTRL 13
EKF2_EV_DELAY 75.0
EKF2_GPS_CTRL 0
EKF2_HGT_REF 2
EKF2_MAG_TYPE 0
EKF2_MIN_RNG 0.24
EKF2_MULTI_IMU 3
EKF2_OF_CTRL 0
EKF2_REQ_NSATS 0
EKF2_RNG_A_HMAX 10.000
EKF2_RNG_A_VMAX 1.500
EKF2_RNG_CTRL 1
EKF2_RNG_FOG 0.5
EKF2_RNG_GATE 10.0
EKF2_RNG_NOISE 0.50
EKF2_RNG_QLTY_T 0.100
MIS_TAKEOFF_ALT 1.5

MPC_ALT_MODE 1
MPC_VEL_MANUAL 1.0
MPC_XY_CRUISE 1.0
MPC_XY_VEL_MAX 1.0
MPC_Z_VEL_MAX_UP 0.6
MPC_Z_V_AUTO_DN 0.5
MPC_Z_V_AUTO_UP 0.6
SYS_HAS_GPS 0
SYS_HAS_MAG 0
SENS_BOARD_X_OFF 2.148
SENS_BOARD_Y_OFF -3.491
SENS_IMU_MODE 0
SENS_TFMINI_CFG 103

if i check in the mavlink inspector in the distance sensor the values are good and changing accordingly …
these are the following updates we made in our system
Pixhawk 6C port usage described by user:

this is my current status:
In mavlink console:
listener distance_sensor
listener vehicle_local_position

Output:
current_distance: 0.14 m
min_distance: 0.40 m
signal_quality: 0
dist_bottom_valid: False

what i interpreted:
TF02 was detected correctly

  1. But measurement < min_distance (0.4 m) → PX4 rejects it

  2. Result:
    dist_bottom_valid=false
    No height fusion at low altitude
    Rangefinder was not the problem, but **operating below valid range caused rejection

    If it was intialized above te valid range

current_distance: ~1.0 m
min_distance: 0.40 m
max_distance: 12.0 m
signal_quality: -1

listener estimator_aid_src_rng_hgt

observation: ~0.988 m
innovation: ~0.001 m
test_ratio: 0.0
innovation_rejected: False
fused: True

listener estimator_status_flags

cs_rng_hgt: True
cs_rng_fault: False
cs_rng_kin_consistent: True
reject_hagl: False

what im thinking :
Rangefinder Fusion WORKING
fused=true

  • No innovation rejection

  • Innovation ~0 → very accurate

EKF2 is **accepting and trusting TF02 height
**
From vehicle_local_position
z_valid: True
v_z_valid: True
height estimation is stable

after all this things also I am not able to achieve the correct stable altitude reading when i see in the home page in the qgc where there shows the vertical,horizontal velocities ,altitude,compass[heading].

PLEASE help me with this guys im trying too much on this , if no fix suggest me some better alternatives please ! !
here are the flight logs of my fight which was in manual mode with the rangefinder