Skip to content

feat(waypoint radius): Add waypoint radius setting & map visual - #14579

Open
AhmWael wants to merge 2 commits into
mavlink:masterfrom
AhmWael:master
Open

feat(waypoint radius): Add waypoint radius setting & map visual#14579
AhmWael wants to merge 2 commits into
mavlink:masterfrom
AhmWael:master

Conversation

@AhmWael

@AhmWael AhmWael commented Jul 1, 2026

Copy link
Copy Markdown
Contributor

Introduce a Waypoint Radius Fact and UI/visual support.

Description

This pull request introduces a global Waypoint Radius setting and visual feedback in Plan Mode. Rather than being defined on a per-waypoint basis, the waypoint radius is managed as a global parameter that synchronizes bidirectionally with the flight controller's actual configuration (WP_RADIUS for ArduPilot Plane/Rover, WPNAV_RADIUS for ArduPilot Copter, or NAV_ACC_RAD for PX4).

Key Features:

  1. Offline Planning Support: The Waypoint Radius editor field is always visible and editable in Plan view, even if no vehicle is connected (defaulting to 50m).
  2. Auto-Synchronization with Connected Vehicle: When QGroundControl is online and a vehicle is connected, the local waypoint radius setting automatically synchronizes bidirectionally with the vehicle's parameters. Custom offline edits are preserved on connection.
  3. Plan File Serialization: The waypoint radius value is saved in the root object of the .plan JSON file and loaded back, fully preserving the mission plan setting across sessions.
  4. Explicit Parameter Upload: The updated waypoint radius value is sent to the vehicle's parameter list during a plan upload sequence.
  5. Interactive Map Circles: Every waypoint shows a circle representing the waypoint radius. Dragging the circle on the map modifies the global parameter value, updating the radius circles for all waypoints dynamically and seamlessly.

Type of Change

  • Bug fix (non-breaking change that fixes an issue)
  • New feature (non-breaking change that adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to change)
  • Documentation update
  • Refactoring (no functional changes)
  • CI/Build changes
  • Other

Testing

  • Tested locally
  • Added/updated unit tests
  • Tested with simulator (SITL)
  • Tested with hardware

Platforms Tested

  • Linux
  • Windows
  • macOS
  • Android
  • iOS

Flight Stacks Tested

  • PX4
  • ArduPilot

Checklist

  • I have read the Contribution Guidelines
  • I have read the Code of Conduct
  • My code follows the project's coding standards
  • I have added tests that prove my fix/feature works
  • New and existing unit tests pass locally

By submitting this pull request, I confirm that my contribution is made under the terms of the project's dual license (Apache 2.0 and GPL v3).

Introduce a Waypoint Radius Fact and UI/visual support. MissionSettingsItem gained a waypointRadius Fact (default 50 m) with metadata and sync logic to vehicle parameters (WP_RADIUS / WPNAV_RADIUS / NAV_ACC_RAD). MissionController now saves/loads waypointRadius in mission JSON. PlanMasterController writes the parameter to the vehicle during send. SimpleMissionItem exposes waypointRadius and triggers visual updates. QML editors (MissionDefaultsEditor, MissionSettingsEditor) and SimpleItemMapVisual add controls and an interactive map circle to view/edit radius. Unit test added to verify propagation.
Copilot AI lite review requested due to automatic review settings July 1, 2026 23:26

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR adds a global “Waypoint Radius” mission setting (Fact) with Plan View editors and map visualization, and persists it in .plan files while attempting to synchronize it with vehicle parameters.

Changes:

  • Introduces a waypointRadius Fact on MissionSettingsItem, serializes it to/from the root mission JSON, and surfaces it in Plan View editors.
  • Adds waypoint-radius circle visuals to each waypoint in SimpleItemMapVisual.qml, including interactive drag-to-edit behavior.
  • Wires SimpleMissionItem to expose the global waypoint radius and adds a unit test exercising the new API.

Reviewed changes

Copilot reviewed 11 out of 11 changed files in this pull request and generated 5 comments.

Show a summary per file
File Description
test/MissionManager/SimpleMissionItemTest.h Adds a new test slot for waypoint radius.
test/MissionManager/SimpleMissionItemTest.cc Adds a basic waypoint radius test and test setup changes.
src/PlanView/SimpleItemMapVisual.qml Adds loader/component to render/edit waypoint radius circles on the map.
src/PlanView/MissionSettingsEditor.qml Adds a waypoint radius editor field for mission settings.
src/PlanView/MissionDefaultsEditor.qml Adds a waypoint radius editor field in mission defaults UI.
src/MissionManager/SimpleMissionItem.h Exposes waypoint radius + visibility properties/signals to QML.
src/MissionManager/SimpleMissionItem.cc Implements lookup/notification for the global waypoint radius Fact.
src/MissionManager/PlanMasterController.cc Attempts to push waypoint radius into a vehicle parameter before mission upload.
src/MissionManager/MissionSettingsItem.h Adds waypoint radius Fact API and vehicle-sync slot/state.
src/MissionManager/MissionSettingsItem.cc Creates waypoint radius Fact metadata/default and implements vehicle parameter sync.
src/MissionManager/MissionController.cc Saves/loads waypointRadius in the mission root JSON.

Comment on lines +29 to 31
MissionSettingsItem* settingsItem = new MissionSettingsItem(planController(), false /* flyView */);
planController()->missionController()->visualItems()->append(settingsItem);
_simpleItem = new SimpleMissionItem(planController(), false /* flyView */, missionItem);
Comment on lines +274 to +278
static Vehicle* lastVehicle = nullptr;
if (lastVehicle != vehicle) {
if (lastVehicle && lastVehicle->parameterManager()) {
disconnect(lastVehicle->parameterManager(), &ParameterManager::parametersReadyChanged, this, &MissionSettingsItem::_syncWaypointRadiusWithVehicle);
disconnect(lastVehicle->parameterManager(), &ParameterManager::factAdded, this, &MissionSettingsItem::_syncWaypointRadiusWithVehicle);
Comment on lines +303 to +307
connect(&_waypointRadiusFact, &Fact::valueChanged, this, [paramFact](QVariant value){
if (paramFact->rawValue() != value) {
paramFact->setRawValue(value);
}
});
Comment on lines +297 to +301
if (_waypointRadiusFact.rawValue().toDouble() != 50.0) {
paramFact->setRawValue(_waypointRadiusFact.rawValue());
} else if (paramFact->rawValue().toDouble() > 0.0) {
_waypointRadiusFact.setRawValue(paramFact->rawValue());
}
Comment on lines +1162 to +1166
bool SimpleMissionItem::showWaypointRadius(void) const
{
Fact* fact = const_cast<SimpleMissionItem*>(this)->waypointRadius();
return command() == MAV_CMD_NAV_WAYPOINT && fact && fact->rawValue().toDouble() > 0.0;
}
@AhmWael

AhmWael commented Jul 4, 2026

Copy link
Copy Markdown
Contributor Author

@DonLakeFlyer Can you check this?

@DonLakeFlyer

Copy link
Copy Markdown
Contributor

We're in bug fix only more for 5.1 now. So this will have to wait for 5.2. First step is dealing with Copilot review.

@DonLakeFlyer DonLakeFlyer added this to the Release V5.1 milestone Jul 6, 2026
@DonLakeFlyer DonLakeFlyer modified the milestone: Release V5.2 Jul 27, 2026
Copilot AI review requested due to automatic review settings August 5, 2026 22:29

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 11 out of 11 changed files in this pull request and generated no new comments.

Suppressed comments (6)

src/MissionManager/MissionSettingsItem.cc:284

  • Using a function-local static lastVehicle makes vehicle tracking shared across all MissionSettingsItem instances and can become dangling if the previous Vehicle is deleted. Also, this code reconnects to a new vehicle but never disconnects the existing Fact<->param Fact connections, so switching controllerVehicle can leave multiple vehicles being kept in sync unintentionally.
    static Vehicle* lastVehicle = nullptr;
    if (lastVehicle != vehicle) {
        if (lastVehicle && lastVehicle->parameterManager()) {
            disconnect(lastVehicle->parameterManager(), &ParameterManager::parametersReadyChanged, this, &MissionSettingsItem::_syncWaypointRadiusWithVehicle);
            disconnect(lastVehicle->parameterManager(), &ParameterManager::factAdded, this, &MissionSettingsItem::_syncWaypointRadiusWithVehicle);
        }
        lastVehicle = vehicle;
        _vehicleWaypointRadiusConnected = false;
        connect(vehicle->parameterManager(), &ParameterManager::parametersReadyChanged, this, &MissionSettingsItem::_syncWaypointRadiusWithVehicle);
        connect(vehicle->parameterManager(), &ParameterManager::factAdded, this, &MissionSettingsItem::_syncWaypointRadiusWithVehicle);
    }

test/MissionManager/SimpleMissionItemTest.cc:30

  • SimpleMissionItem::waypointRadius() assumes MissionSettingsItem is at visualItems()[0]. The test currently appends the settings item, which would break if the list is non-empty (and diverges from production code which inserts at index 0).
    MissionSettingsItem* settingsItem = new MissionSettingsItem(planController(), false /* flyView */);
    planController()->missionController()->visualItems()->append(settingsItem);

src/MissionManager/MissionSettingsItem.cc:307

  • The lambda connected to _waypointRadiusFact captures paramFact while the receiver/context is this. If the vehicle disconnects and paramFact is destroyed, later offline edits to _waypointRadiusFact can dereference a stale pointer.
        connect(&_waypointRadiusFact, &Fact::valueChanged, this, [paramFact](QVariant value){
            if (paramFact->rawValue() != value) {
                paramFact->setRawValue(value);
            }
        });

src/MissionManager/SimpleMissionItem.cc:1187

  • showWaypointRadius depends on the mission command, but showWaypointRadiusChanged is only emitted when the waypointRadius Fact changes. If the command changes to/from MAV_CMD_NAV_WAYPOINT, QML bindings using showWaypointRadius may not update.
    if (fact && !_waypointRadiusConnected) {
        _waypointRadiusConnected = true;
        connect(fact, &Fact::valueChanged, this, [this](QVariant value){
            emit waypointRadiusChanged(value.toDouble());
            emit showWaypointRadiusChanged();
        });
    }

test/MissionManager/SimpleMissionItemTest.h:31

  • Typo in test slot name: “Propogation” → “Propagation”.
    void _testAltitudePropogation();
    void _testWaypointRadiusPropogation();

test/MissionManager/SimpleMissionItemTest.cc:334

  • Typo in test function name: “Propogation” → “Propagation” (should match the header slot declaration).
void SimpleMissionItemTest::_testWaypointRadiusPropogation()

@github-actions

github-actions Bot commented Aug 5, 2026

Copy link
Copy Markdown
Contributor

⚠️ Build results unavailable — artifact download from one or more platform workflows failed (likely artifact retention expiry or transient API error). The combined report cannot be generated for this run.

See the Build Results workflow run for details.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants