Browse Source

Merge pull request #7758 from DonLakeFlyer/DirectionArrows

More work on direction arrows
QGC4.4
Don Gagne 6 years ago committed by GitHub
parent
commit
6ce4d6cf33
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 7
      src/FlightMap/MapItems/MissionLineView.qml
  2. 6
      src/MissionManager/MapLineArrow.qml
  3. 38
      src/MissionManager/MissionController.cc
  4. 5
      src/MissionManager/MissionController.h
  5. 11
      src/PlanView/PlanView.qml
  6. 8
      src/PlanView/TransectStyleMapVisuals.qml

7
src/FlightMap/MapItems/MissionLineView.qml

@ -17,8 +17,6 @@ import QGroundControl.Palette 1.0
/// The MissionLineView control is used to add lines between mission items /// The MissionLineView control is used to add lines between mission items
MapItemView { MapItemView {
id: _root
property bool homePositionValid: true ///< true: show home position, false: don't show home position property bool homePositionValid: true ///< true: show home position, false: don't show home position
delegate: MapPolyline { delegate: MapPolyline {
@ -26,9 +24,6 @@ MapItemView {
line.color: "#be781c" // Hack, can't get palette to work in here line.color: "#be781c" // Hack, can't get palette to work in here
z: QGroundControl.zOrderWaypointLines z: QGroundControl.zOrderWaypointLines
path: object ? [ path: object ? [ object.coordinate1, object.coordinate2 ] : [ ]
object.coordinate1,
object.coordinate2,
] : []
} }
} }

6
src/MissionManager/MapLineArrow.qml

@ -22,17 +22,17 @@ MapQuickItem {
property color arrowColor: "white" property color arrowColor: "white"
property var fromCoord: QtPositioning.coordinate() property var fromCoord: QtPositioning.coordinate()
property var toCoord: QtPositioning.coordinate() property var toCoord: QtPositioning.coordinate()
property bool exitPosition: false property int arrowPosition: 1 ///< 1: first quarter, 2: halfway, 3: last quarter
property var _map: parent property var _map: parent
property real _arrowSize: 20 property real _arrowSize: 15
property real _arrowHeading: 0 property real _arrowHeading: 0
function _updateArrowDetails() { function _updateArrowDetails() {
if (fromCoord && fromCoord.isValid && toCoord && toCoord.isValid) { if (fromCoord && fromCoord.isValid && toCoord && toCoord.isValid) {
_arrowHeading = fromCoord.azimuthTo(toCoord) _arrowHeading = fromCoord.azimuthTo(toCoord)
var lineDistanceQuarter = fromCoord.distanceTo(toCoord) / 4 var lineDistanceQuarter = fromCoord.distanceTo(toCoord) / 4
coordinate = fromCoord.atDistanceAndAzimuth(lineDistanceQuarter * (exitPosition ? 3 : 1), _arrowHeading) coordinate = fromCoord.atDistanceAndAzimuth(lineDistanceQuarter * arrowPosition, _arrowHeading)
} else { } else {
coordinate = QtPositioning.coordinate() coordinate = QtPositioning.coordinate()
_arrowHeading = 0 _arrowHeading = 0

38
src/MissionManager/MissionController.cc

@ -1070,30 +1070,36 @@ double MissionController::_calcDistanceToHome(VisualMissionItem* currentItem, Vi
return distanceOk ? homeCoord.distanceTo(currentCoord) : 0.0; return distanceOk ? homeCoord.distanceTo(currentCoord) : 0.0;
} }
void MissionController::_addWaypointLineSegment(CoordVectHashTable& prevItemPairHashTable, VisualItemPair& pair) CoordinateVector* MissionController::_addWaypointLineSegment(CoordVectHashTable& prevItemPairHashTable, VisualItemPair& pair)
{ {
CoordinateVector* coordVector = nullptr;
if (prevItemPairHashTable.contains(pair)) { if (prevItemPairHashTable.contains(pair)) {
// Pair already exists and connected, just re-use // Pair already exists and connected, just re-use
_linesTable[pair] = prevItemPairHashTable.take(pair); _linesTable[pair] = coordVector = prevItemPairHashTable.take(pair);
} else { } else {
// Create a new segment and wire update notifiers // Create a new segment and wire update notifiers
auto linevect = new CoordinateVector(pair.first->isSimpleItem() ? pair.first->coordinate() : pair.first->exitCoordinate(), pair.second->coordinate(), this); coordVector = new CoordinateVector(pair.first->isSimpleItem() ? pair.first->coordinate() : pair.first->exitCoordinate(), pair.second->coordinate(), this);
auto originNotifier = pair.first->isSimpleItem() ? &VisualMissionItem::coordinateChanged : &VisualMissionItem::exitCoordinateChanged; auto originNotifier = pair.first->isSimpleItem() ? &VisualMissionItem::coordinateChanged : &VisualMissionItem::exitCoordinateChanged;
auto endNotifier = &VisualMissionItem::coordinateChanged; auto endNotifier = &VisualMissionItem::coordinateChanged;
// Use signals/slots to update the coordinate endpoints // Use signals/slots to update the coordinate endpoints
connect(pair.first, originNotifier, linevect, &CoordinateVector::setCoordinate1); connect(pair.first, originNotifier, coordVector, &CoordinateVector::setCoordinate1);
connect(pair.second, endNotifier, linevect, &CoordinateVector::setCoordinate2); connect(pair.second, endNotifier, coordVector, &CoordinateVector::setCoordinate2);
// FIXME: We should ideally have signals for 2D position change, alt change, and 3D position change // FIXME: We should ideally have signals for 2D position change, alt change, and 3D position change
// Not optimal, but still pretty fast, do a full update of range/bearing/altitudes // Not optimal, but still pretty fast, do a full update of range/bearing/altitudes
connect(pair.second, &VisualMissionItem::coordinateChanged, this, &MissionController::_recalcMissionFlightStatus); connect(pair.second, &VisualMissionItem::coordinateChanged, this, &MissionController::_recalcMissionFlightStatus);
_linesTable[pair] = linevect; _linesTable[pair] = coordVector;
} }
return coordVector;
} }
void MissionController::_recalcWaypointLines(void) void MissionController::_recalcWaypointLines(void)
{ {
int segmentCount = 0;
CoordinateVector* lastCoordVector = nullptr;
bool firstCoordinateItem = true; bool firstCoordinateItem = true;
VisualMissionItem* lastCoordinateItem = qobject_cast<VisualMissionItem*>(_visualItems->get(0)); VisualMissionItem* lastCoordinateItem = qobject_cast<VisualMissionItem*>(_visualItems->get(0));
@ -1105,6 +1111,7 @@ void MissionController::_recalcWaypointLines(void)
_linesTable.clear(); _linesTable.clear();
_waypointLines.clear(); _waypointLines.clear();
_waypointPath.clear(); _waypointPath.clear();
_directionArrows.clear();
bool linkEndToHome; bool linkEndToHome;
SimpleMissionItem* lastItem = _visualItems->value<SimpleMissionItem*>(_visualItems->count() - 1); SimpleMissionItem* lastItem = _visualItems->value<SimpleMissionItem*>(_visualItems->count() - 1);
@ -1128,13 +1135,20 @@ void MissionController::_recalcWaypointLines(void)
} }
if (item->specifiesCoordinate() && !item->isStandaloneCoordinate()) { if (item->specifiesCoordinate() && !item->isStandaloneCoordinate()) {
firstCoordinateItem = false;
if (lastCoordinateItem != _settingsItem || (homePositionValid && linkStartToHome)) { if (lastCoordinateItem != _settingsItem || (homePositionValid && linkStartToHome)) {
if (!_flyView) { if (!_flyView) {
VisualItemPair pair(lastCoordinateItem, item); VisualItemPair pair(lastCoordinateItem, item);
_addWaypointLineSegment(old_table, pair); lastCoordVector = _addWaypointLineSegment(old_table, pair);
segmentCount++;
if (firstCoordinateItem || !lastCoordinateItem->isSimpleItem() || !item->isSimpleItem()) {
_directionArrows.append(lastCoordVector);
} else if (segmentCount > 5) {
segmentCount = 0;
_directionArrows.append(lastCoordVector);
}
} }
} }
firstCoordinateItem = false;
_waypointPath.append(QVariant::fromValue(item->coordinate())); _waypointPath.append(QVariant::fromValue(item->coordinate()));
lastCoordinateItem = item; lastCoordinateItem = item;
} }
@ -1147,7 +1161,7 @@ void MissionController::_recalcWaypointLines(void)
if (linkEndToHome && lastCoordinateItem != _settingsItem && homePositionValid) { if (linkEndToHome && lastCoordinateItem != _settingsItem && homePositionValid) {
if (!_flyView) { if (!_flyView) {
VisualItemPair pair(lastCoordinateItem, _settingsItem); VisualItemPair pair(lastCoordinateItem, _settingsItem);
_addWaypointLineSegment(old_table, pair); lastCoordVector = _addWaypointLineSegment(old_table, pair);
} else { } else {
_waypointPath.append(QVariant::fromValue(_settingsItem->coordinate())); _waypointPath.append(QVariant::fromValue(_settingsItem->coordinate()));
} }
@ -1168,10 +1182,14 @@ void MissionController::_recalcWaypointLines(void)
// Anything left in the old table is an obsolete line object that can go // Anything left in the old table is an obsolete line object that can go
qDeleteAll(old_table); qDeleteAll(old_table);
if (lastCoordVector) {
_directionArrows.append(lastCoordVector);
}
_recalcMissionFlightStatus(); _recalcMissionFlightStatus();
if (_waypointPath.count() == 0) { if (_waypointPath.count() == 0) {
// MapPolyLine has a bug where if you can from a path which has elements to an empty path the line drawn // MapPolyLine has a bug where if you change from a path which has elements to an empty path the line drawn
// is not cleared from the map. This hack works around that since it causes the previous lines to be remove // is not cleared from the map. This hack works around that since it causes the previous lines to be remove
// as then doesn't draw anything on the map. // as then doesn't draw anything on the map.
_waypointPath.append(QVariant::fromValue(QGeoCoordinate(0, 0))); _waypointPath.append(QVariant::fromValue(QGeoCoordinate(0, 0)));

5
src/MissionManager/MissionController.h

@ -70,6 +70,7 @@ public:
Q_PROPERTY(QmlObjectListModel* visualItems READ visualItems NOTIFY visualItemsChanged) Q_PROPERTY(QmlObjectListModel* visualItems READ visualItems NOTIFY visualItemsChanged)
Q_PROPERTY(QmlObjectListModel* waypointLines READ waypointLines NOTIFY waypointLinesChanged) ///< Used by Plan view only for interactive editing Q_PROPERTY(QmlObjectListModel* waypointLines READ waypointLines NOTIFY waypointLinesChanged) ///< Used by Plan view only for interactive editing
Q_PROPERTY(QVariantList waypointPath READ waypointPath NOTIFY waypointPathChanged) ///< Used by Fly view only for static display Q_PROPERTY(QVariantList waypointPath READ waypointPath NOTIFY waypointPathChanged) ///< Used by Fly view only for static display
Q_PROPERTY(QmlObjectListModel* directionArrows READ directionArrows CONSTANT)
Q_PROPERTY(QStringList complexMissionItemNames READ complexMissionItemNames NOTIFY complexMissionItemNamesChanged) Q_PROPERTY(QStringList complexMissionItemNames READ complexMissionItemNames NOTIFY complexMissionItemNamesChanged)
Q_PROPERTY(QGeoCoordinate plannedHomePosition READ plannedHomePosition NOTIFY plannedHomePositionChanged) Q_PROPERTY(QGeoCoordinate plannedHomePosition READ plannedHomePosition NOTIFY plannedHomePositionChanged)
@ -169,6 +170,7 @@ public:
QmlObjectListModel* visualItems (void) { return _visualItems; } QmlObjectListModel* visualItems (void) { return _visualItems; }
QmlObjectListModel* waypointLines (void) { return &_waypointLines; } QmlObjectListModel* waypointLines (void) { return &_waypointLines; }
QmlObjectListModel* directionArrows (void) { return &_directionArrows; }
QVariantList waypointPath (void) { return _waypointPath; } QVariantList waypointPath (void) { return _waypointPath; }
QStringList complexMissionItemNames (void) const; QStringList complexMissionItemNames (void) const;
QGeoCoordinate plannedHomePosition (void) const; QGeoCoordinate plannedHomePosition (void) const;
@ -273,7 +275,7 @@ private:
void _updateBatteryInfo(int waypointIndex); void _updateBatteryInfo(int waypointIndex);
bool _loadItemsFromJson(const QJsonObject& json, QmlObjectListModel* visualItems, QString& errorString); bool _loadItemsFromJson(const QJsonObject& json, QmlObjectListModel* visualItems, QString& errorString);
void _initLoadedVisualItems(QmlObjectListModel* loadedVisualItems); void _initLoadedVisualItems(QmlObjectListModel* loadedVisualItems);
void _addWaypointLineSegment(CoordVectHashTable& prevItemPairHashTable, VisualItemPair& pair); CoordinateVector* _addWaypointLineSegment(CoordVectHashTable& prevItemPairHashTable, VisualItemPair& pair);
void _addTimeDistance(bool vtolInHover, double hoverTime, double cruiseTime, double extraTime, double distance, int seqNum); void _addTimeDistance(bool vtolInHover, double hoverTime, double cruiseTime, double extraTime, double distance, int seqNum);
int _insertComplexMissionItemWorker(ComplexMissionItem* complexItem, int i); int _insertComplexMissionItemWorker(ComplexMissionItem* complexItem, int i);
void _warnIfTerrainFrameUsed(void); void _warnIfTerrainFrameUsed(void);
@ -285,6 +287,7 @@ private:
MissionSettingsItem* _settingsItem; MissionSettingsItem* _settingsItem;
QmlObjectListModel _waypointLines; QmlObjectListModel _waypointLines;
QVariantList _waypointPath; QVariantList _waypointPath;
QmlObjectListModel _directionArrows;
CoordVectHashTable _linesTable; CoordVectHashTable _linesTable;
bool _firstItemsFromVehicle; bool _firstItemsFromVehicle;
bool _itemsRequested; bool _itemsRequested;

11
src/PlanView/PlanView.qml

@ -472,6 +472,17 @@ Item {
model: _editingLayer == _layerMission ? _missionController.waypointLines : undefined model: _editingLayer == _layerMission ? _missionController.waypointLines : undefined
} }
MapItemView {
model: _editingLayer == _layerMission ? _missionController.directionArrows : undefined
delegate: MapLineArrow {
fromCoord: object ? object.coordinate1 : undefined
toCoord: object ? object.coordinate2 : undefined
arrowPosition: 2
z: QGroundControl.zOrderWaypointLines
}
}
// Add the vehicles to the map // Add the vehicles to the map
MapItemView { MapItemView {
model: QGroundControl.multiVehicleManager.vehicles model: QGroundControl.multiVehicleManager.vehicles

8
src/PlanView/TransectStyleMapVisuals.qml

@ -138,7 +138,7 @@ Item {
MapLineArrow { MapLineArrow {
fromCoord: _transectPoints[_firstTrueTransectIndex] fromCoord: _transectPoints[_firstTrueTransectIndex]
toCoord: _transectPoints[_firstTrueTransectIndex + 1] toCoord: _transectPoints[_firstTrueTransectIndex + 1]
exitPosition: false arrowPosition: 1
visible: _currentItem visible: _currentItem
} }
} }
@ -149,7 +149,7 @@ Item {
MapLineArrow { MapLineArrow {
fromCoord: _transectPoints[nextTrueTransectIndex] fromCoord: _transectPoints[nextTrueTransectIndex]
toCoord: _transectPoints[nextTrueTransectIndex + 1] toCoord: _transectPoints[nextTrueTransectIndex + 1]
exitPosition: false arrowPosition: 1
visible: _currentItem && _transectCount > 3 visible: _currentItem && _transectCount > 3
property int nextTrueTransectIndex: _firstTrueTransectIndex + (_hasTurnaround ? 4 : 2) property int nextTrueTransectIndex: _firstTrueTransectIndex + (_hasTurnaround ? 4 : 2)
@ -162,7 +162,7 @@ Item {
MapLineArrow { MapLineArrow {
fromCoord: _transectPoints[_lastTrueTransectIndex - 1] fromCoord: _transectPoints[_lastTrueTransectIndex - 1]
toCoord: _transectPoints[_lastTrueTransectIndex] toCoord: _transectPoints[_lastTrueTransectIndex]
exitPosition: true arrowPosition: 3
visible: _currentItem visible: _currentItem
} }
} }
@ -173,7 +173,7 @@ Item {
MapLineArrow { MapLineArrow {
fromCoord: _transectPoints[prevTrueTransectIndex - 1] fromCoord: _transectPoints[prevTrueTransectIndex - 1]
toCoord: _transectPoints[prevTrueTransectIndex] toCoord: _transectPoints[prevTrueTransectIndex]
exitPosition: true arrowPosition: 13
visible: _currentItem && _transectCount > 3 visible: _currentItem && _transectCount > 3
property int prevTrueTransectIndex: _lastTrueTransectIndex - (_hasTurnaround ? 4 : 2) property int prevTrueTransectIndex: _lastTrueTransectIndex - (_hasTurnaround ? 4 : 2)

Loading…
Cancel
Save