Commit 0778e3ba authored by Don Gagne's avatar Don Gagne

Add complex mission item exit coordinate support

Plus many load/save fixes
parent 2fcdda7f
...@@ -33,6 +33,7 @@ MapQuickItem { ...@@ -33,6 +33,7 @@ MapQuickItem {
id: _item id: _item
property var missionItem property var missionItem
property int sequenceNumber
signal clicked signal clicked
...@@ -43,10 +44,9 @@ MapQuickItem { ...@@ -43,10 +44,9 @@ MapQuickItem {
MissionItemIndexLabel { MissionItemIndexLabel {
id: _label id: _label
isCurrentItem: _isCurrentItem isCurrentItem: _isCurrentItem
label: _sequenceNumber == 0 ? "H" : missionItem.sequenceNumber label: sequenceNumber == 0 ? "H" : sequenceNumber
onClicked: _item.clicked() onClicked: _item.clicked()
property bool _isCurrentItem: missionItem ? missionItem.isCurrentItem : false property bool _isCurrentItem: missionItem ? missionItem.isCurrentItem : false
property bool _sequenceNumber: missionItem ? missionItem.sequenceNumber : 0
} }
} }
...@@ -41,6 +41,7 @@ MapItemView { ...@@ -41,6 +41,7 @@ MapItemView {
visible: object.specifiesCoordinate && (index != 0 || object.showHomePosition) visible: object.specifiesCoordinate && (index != 0 || object.showHomePosition)
z: QGroundControl.zOrderMapItems z: QGroundControl.zOrderMapItems
missionItem: object missionItem: object
sequenceNumber: object.sequenceNumber
// These are the non-coordinate child mission items attached to this item // These are the non-coordinate child mission items attached to this item
Row { Row {
......
...@@ -134,8 +134,6 @@ QGCFlickable { ...@@ -134,8 +134,6 @@ QGCFlickable {
width: barRow.width width: barRow.width
height: 1 height: 1
color: "red" color: "red"
Component.onCompleted: console.log(anchors.topMargin, xBar.height, _barBadValue, _barMaximum, _barMinimum)
} }
QGCLabel { QGCLabel {
......
...@@ -366,8 +366,42 @@ QGCView { ...@@ -366,8 +366,42 @@ QGCView {
// Add the simple mission items to the map // Add the simple mission items to the map
MapItemView { MapItemView {
model: controller.visualItems model: controller.visualItems
delegate: missionItemComponent delegate: missionItemComponent
}
// Add the complex mission items to the map
MapItemView {
model: controller.complexVisualItems
delegate: polygonItemComponent
}
Component {
id: polygonItemComponent
MapPolygon {
color: 'green'
path: object.polygonPath
opacity: 0.5
}
}
// Add the complex mission item exit coordinates
MapItemView {
model: controller.complexVisualItems
delegate: exitCoordinateComponent
}
Component {
id: exitCoordinateComponent
MissionItemIndicator {
coordinate: object.exitCoordinate
z: QGroundControl.zOrderMapItems
missionItem: object
sequenceNumber: object.lastSequenceNumber
visible: object.specifiesCoordinate
}
} }
Component { Component {
...@@ -379,18 +413,18 @@ QGCView { ...@@ -379,18 +413,18 @@ QGCView {
visible: object.specifiesCoordinate visible: object.specifiesCoordinate
z: QGroundControl.zOrderMapItems z: QGroundControl.zOrderMapItems
missionItem: object missionItem: object
sequenceNumber: object.sequenceNumber
onClicked: setCurrentItem(object.sequenceNumber) onClicked: setCurrentItem(object.sequenceNumber)
function updateItemIndicator() function updateItemIndicator()
{ {
if (object.isCurrentItem && itemIndicator.visible) { if (object.isCurrentItem && itemIndicator.visible &&
if (object.specifiesCoordinate) { object.specifiesCoordinate && object.isSimpleItem) {
// Setup our drag item // Setup our drag item
itemDragger.visible = true itemDragger.visible = true
itemDragger.missionItem = Qt.binding(function() { return object }) itemDragger.missionItem = Qt.binding(function() { return object })
itemDragger.missionItemIndicator = Qt.binding(function() { return itemIndicator }) itemDragger.missionItemIndicator = Qt.binding(function() { return itemIndicator })
}
} }
} }
...@@ -421,22 +455,6 @@ QGCView { ...@@ -421,22 +455,6 @@ QGCView {
} }
} }
// Add the complex mission items to the map
MapItemView {
model: controller.complexVisualItems
delegate: polygonItemComponent
}
Component {
id: polygonItemComponent
MapPolygon {
color: 'green'
path: object.polygonPath
opacity: 0.5
}
}
// Add lines between waypoints // Add lines between waypoints
MissionLineView { MissionLineView {
model: controller.waypointLines model: controller.waypointLines
......
...@@ -33,6 +33,7 @@ const char* ComplexMissionItem::_complexType = "survey"; ...@@ -33,6 +33,7 @@ const char* ComplexMissionItem::_complexType = "survey";
ComplexMissionItem::ComplexMissionItem(Vehicle* vehicle, QObject* parent) ComplexMissionItem::ComplexMissionItem(Vehicle* vehicle, QObject* parent)
: VisualMissionItem(vehicle, parent) : VisualMissionItem(vehicle, parent)
, _sequenceNumber(0)
, _dirty(false) , _dirty(false)
{ {
MissionItem missionItem; MissionItem missionItem;
...@@ -44,6 +45,7 @@ ComplexMissionItem::ComplexMissionItem(Vehicle* vehicle, QObject* parent) ...@@ -44,6 +45,7 @@ ComplexMissionItem::ComplexMissionItem(Vehicle* vehicle, QObject* parent)
ComplexMissionItem::ComplexMissionItem(const ComplexMissionItem& other, QObject* parent) ComplexMissionItem::ComplexMissionItem(const ComplexMissionItem& other, QObject* parent)
: VisualMissionItem(other, parent) : VisualMissionItem(other, parent)
, _sequenceNumber(other.sequenceNumber())
, _dirty(false) , _dirty(false)
{ {
...@@ -51,8 +53,18 @@ ComplexMissionItem::ComplexMissionItem(const ComplexMissionItem& other, QObject* ...@@ -51,8 +53,18 @@ ComplexMissionItem::ComplexMissionItem(const ComplexMissionItem& other, QObject*
void ComplexMissionItem::clearPolygon(void) void ComplexMissionItem::clearPolygon(void)
{ {
_polygonPath.clear(); // Bug workaround, see below
while (_polygonPath.count() > 1) {
_polygonPath.takeLast();
}
emit polygonPathChanged(); emit polygonPathChanged();
// Although this code should remove the polygon from the map it doesn't. There appears
// to be a bug in MapPolygon which causes it to not be redrawn if the list is empty. So
// we work around it by using the code above to remove all bu the last point which in turn
// will cause the polygon to go away.
_polygonPath.clear();
emit specifiesCoordinateChanged();
} }
void ComplexMissionItem::addPolygonCoordinate(const QGeoCoordinate coordinate) void ComplexMissionItem::addPolygonCoordinate(const QGeoCoordinate coordinate)
...@@ -60,15 +72,18 @@ void ComplexMissionItem::addPolygonCoordinate(const QGeoCoordinate coordinate) ...@@ -60,15 +72,18 @@ void ComplexMissionItem::addPolygonCoordinate(const QGeoCoordinate coordinate)
_polygonPath << QVariant::fromValue(coordinate); _polygonPath << QVariant::fromValue(coordinate);
emit polygonPathChanged(); emit polygonPathChanged();
// FIXME: Hack, first polygon point sets entry coordinate int pointCount = _polygonPath.count();
if (_polygonPath.count() == 1) { if (pointCount == 1) {
setCoordinate(coordinate); setCoordinate(coordinate);
} else if (pointCount == 3) {
emit specifiesCoordinateChanged();
} }
_setExitCoordinate(coordinate);
} }
int ComplexMissionItem::nextSequenceNumber(void) const int ComplexMissionItem::lastSequenceNumber(void) const
{ {
return _sequenceNumber + _missionItems.count(); return _sequenceNumber + _missionItems.count() - 1;
} }
void ComplexMissionItem::setCoordinate(const QGeoCoordinate& coordinate) void ComplexMissionItem::setCoordinate(const QGeoCoordinate& coordinate)
...@@ -126,11 +141,15 @@ void ComplexMissionItem::save(QJsonObject& saveObject) const ...@@ -126,11 +141,15 @@ void ComplexMissionItem::save(QJsonObject& saveObject) const
void ComplexMissionItem::setSequenceNumber(int sequenceNumber) void ComplexMissionItem::setSequenceNumber(int sequenceNumber)
{ {
VisualMissionItem::setSequenceNumber(sequenceNumber); if (_sequenceNumber != sequenceNumber) {
_sequenceNumber = sequenceNumber;
// Update internal mission items to new numbering // Update internal mission items to new numbering
for (int i=0; i<_missionItems.count(); i++) { for (int i=0; i<_missionItems.count(); i++) {
_missionItems[i]->setSequenceNumber(sequenceNumber++); _missionItems[i]->setSequenceNumber(sequenceNumber++);
}
emit sequenceNumberChanged(sequenceNumber);
} }
} }
...@@ -217,10 +236,12 @@ bool ComplexMissionItem::load(const QJsonObject& complexObject, QString& errorSt ...@@ -217,10 +236,12 @@ bool ComplexMissionItem::load(const QJsonObject& complexObject, QString& errorSt
int itemCount = _missionItems.count(); int itemCount = _missionItems.count();
if (itemCount > 0) { if (itemCount > 0) {
setCoordinate(_missionItems[0]->coordinate()); _coordinate = _missionItems[0]->coordinate();
_setExitCoordinate(_missionItems[itemCount - 1]->coordinate()); _exitCoordinate = _missionItems[itemCount - 1]->coordinate();
} }
qDebug() << coordinate() << exitCoordinate() << _missionItems[0]->coordinate() << _missionItems[1]->coordinate();
return true; return true;
} }
...@@ -236,3 +257,8 @@ void ComplexMissionItem::_setExitCoordinate(const QGeoCoordinate& coordinate) ...@@ -236,3 +257,8 @@ void ComplexMissionItem::_setExitCoordinate(const QGeoCoordinate& coordinate)
} }
} }
} }
bool ComplexMissionItem::specifiesCoordinate(void) const
{
return _polygonPath.count() > 2;
}
...@@ -35,7 +35,8 @@ public: ...@@ -35,7 +35,8 @@ public:
ComplexMissionItem(Vehicle* vehicle, QObject* parent = NULL); ComplexMissionItem(Vehicle* vehicle, QObject* parent = NULL);
ComplexMissionItem(const ComplexMissionItem& other, QObject* parent = NULL); ComplexMissionItem(const ComplexMissionItem& other, QObject* parent = NULL);
Q_PROPERTY(QVariantList polygonPath READ polygonPath NOTIFY polygonPathChanged) Q_PROPERTY(QVariantList polygonPath READ polygonPath NOTIFY polygonPathChanged)
Q_PROPERTY(int lastSequenceNumber READ lastSequenceNumber NOTIFY lastSequenceNumberChanged)
Q_INVOKABLE void clearPolygon(void); Q_INVOKABLE void clearPolygon(void);
Q_INVOKABLE void addPolygonCoordinate(const QGeoCoordinate coordinate); Q_INVOKABLE void addPolygonCoordinate(const QGeoCoordinate coordinate);
...@@ -44,8 +45,8 @@ public: ...@@ -44,8 +45,8 @@ public:
QList<MissionItem*>& missionItems(void) { return _missionItems; } QList<MissionItem*>& missionItems(void) { return _missionItems; }
/// @return The next sequence number to use after this item. Takes into account child items of the complex item /// @return The last sequence number used by this item. Takes into account child items of the complex item
int nextSequenceNumber(void) const; int lastSequenceNumber(void) const;
/// Load the complex mission item from Json /// Load the complex mission item from Json
/// @param complexObject Complex mission item json object /// @param complexObject Complex mission item json object
...@@ -58,11 +59,12 @@ public: ...@@ -58,11 +59,12 @@ public:
bool dirty (void) const final { return _dirty; } bool dirty (void) const final { return _dirty; }
bool isSimpleItem (void) const final { return false; } bool isSimpleItem (void) const final { return false; }
bool isStandaloneCoordinate (void) const final { return false; } bool isStandaloneCoordinate (void) const final { return false; }
bool specifiesCoordinate (void) const final { return true; } bool specifiesCoordinate (void) const final;
QString commandDescription (void) const final { return "Survey"; } QString commandDescription (void) const final { return "Survey"; }
QString commandName (void) const final { return "Survey"; } QString commandName (void) const final { return "Survey"; }
QGeoCoordinate coordinate (void) const final { return _coordinate; } QGeoCoordinate coordinate (void) const final { return _coordinate; }
QGeoCoordinate exitCoordinate (void) const final { return _exitCoordinate; } QGeoCoordinate exitCoordinate (void) const final { return _exitCoordinate; }
int sequenceNumber (void) const final { return _sequenceNumber; }
bool coordinateHasRelativeAltitude (void) const final { return true; } bool coordinateHasRelativeAltitude (void) const final { return true; }
bool exitCoordinateHasRelativeAltitude (void) const final { return true; } bool exitCoordinateHasRelativeAltitude (void) const final { return true; }
...@@ -75,11 +77,13 @@ public: ...@@ -75,11 +77,13 @@ public:
signals: signals:
void polygonPathChanged(void); void polygonPathChanged(void);
void lastSequenceNumberChanged(int lastSequenceNumber);
private: private:
void _clear(void); void _clear(void);
void _setExitCoordinate(const QGeoCoordinate& coordinate); void _setExitCoordinate(const QGeoCoordinate& coordinate);
int _sequenceNumber;
bool _dirty; bool _dirty;
QVariantList _polygonPath; QVariantList _polygonPath;
QList<MissionItem*> _missionItems; QList<MissionItem*> _missionItems;
......
This diff is collapsed.
...@@ -113,10 +113,11 @@ private: ...@@ -113,10 +113,11 @@ private:
void _addPlannedHomePosition(QmlObjectListModel* visualItems, bool addToCenter); void _addPlannedHomePosition(QmlObjectListModel* visualItems, bool addToCenter);
double _normalizeLat(double lat); double _normalizeLat(double lat);
double _normalizeLon(double lon); double _normalizeLon(double lon);
bool _loadJsonMissionFile(const QByteArray& bytes, QmlObjectListModel* visualItems, QString& errorString); bool _loadJsonMissionFile(const QByteArray& bytes, QmlObjectListModel* visualItems, QmlObjectListModel* complexItems, QString& errorString);
bool _loadTextMissionFile(QTextStream& stream, QmlObjectListModel* visualItems, QString& errorString); bool _loadTextMissionFile(QTextStream& stream, QmlObjectListModel* visualItems, QString& errorString);
void _loadMissionFromFile(const QString& file); void _loadMissionFromFile(const QString& file);
void _saveMissionToFile(const QString& file); void _saveMissionToFile(const QString& file);
int _nextSequenceNumber(void);
private: private:
bool _editMode; bool _editMode;
......
...@@ -190,6 +190,9 @@ void SimpleMissionItem::_connectSignals(void) ...@@ -190,6 +190,9 @@ void SimpleMissionItem::_connectSignals(void)
// These fact signals must alway signal out through SimpleMissionItem signals // These fact signals must alway signal out through SimpleMissionItem signals
connect(&_missionItem._commandFact, &Fact::valueChanged, this, &SimpleMissionItem::_sendCommandChanged); connect(&_missionItem._commandFact, &Fact::valueChanged, this, &SimpleMissionItem::_sendCommandChanged);
connect(&_missionItem._frameFact, &Fact::valueChanged, this, &SimpleMissionItem::_sendFrameChanged); connect(&_missionItem._frameFact, &Fact::valueChanged, this, &SimpleMissionItem::_sendFrameChanged);
// Sequence number is kept in mission iteem, so we need to propogate signal up as well
connect(&_missionItem, &MissionItem::sequenceNumberChanged, this, &SimpleMissionItem::sequenceNumberChanged);
} }
void SimpleMissionItem::_setupMetaData(void) void SimpleMissionItem::_setupMetaData(void)
...@@ -574,7 +577,6 @@ void SimpleMissionItem::setCommand(MavlinkQmlSingleton::Qml_MAV_CMD command) ...@@ -574,7 +577,6 @@ void SimpleMissionItem::setCommand(MavlinkQmlSingleton::Qml_MAV_CMD command)
void SimpleMissionItem::setCoordinate(const QGeoCoordinate& coordinate) void SimpleMissionItem::setCoordinate(const QGeoCoordinate& coordinate)
{ {
if (_missionItem.coordinate() != coordinate) { if (_missionItem.coordinate() != coordinate) {
qDebug() << _missionItem.coordinate() << coordinate;
_missionItem.setCoordinate(coordinate); _missionItem.setCoordinate(coordinate);
} }
} }
...@@ -582,5 +584,4 @@ void SimpleMissionItem::setCoordinate(const QGeoCoordinate& coordinate) ...@@ -582,5 +584,4 @@ void SimpleMissionItem::setCoordinate(const QGeoCoordinate& coordinate)
void SimpleMissionItem::setSequenceNumber(int sequenceNumber) void SimpleMissionItem::setSequenceNumber(int sequenceNumber)
{ {
_missionItem.setSequenceNumber(sequenceNumber); _missionItem.setSequenceNumber(sequenceNumber);
VisualMissionItem::setSequenceNumber(sequenceNumber);
} }
...@@ -101,6 +101,7 @@ public: ...@@ -101,6 +101,7 @@ public:
QString commandName (void) const final; QString commandName (void) const final;
QGeoCoordinate coordinate (void) const final { return _missionItem.coordinate(); } QGeoCoordinate coordinate (void) const final { return _missionItem.coordinate(); }
QGeoCoordinate exitCoordinate (void) const final { return coordinate(); } QGeoCoordinate exitCoordinate (void) const final { return coordinate(); }
int sequenceNumber (void) const final { return _missionItem.sequenceNumber(); }
bool coordinateHasRelativeAltitude (void) const final { return _missionItem.relativeAltitude(); } bool coordinateHasRelativeAltitude (void) const final { return _missionItem.relativeAltitude(); }
bool exitCoordinateHasRelativeAltitude (void) const final { return coordinateHasRelativeAltitude(); } bool exitCoordinateHasRelativeAltitude (void) const final { return coordinateHasRelativeAltitude(); }
......
...@@ -31,7 +31,6 @@ This file is part of the QGROUNDCONTROL project ...@@ -31,7 +31,6 @@ This file is part of the QGROUNDCONTROL project
VisualMissionItem::VisualMissionItem(Vehicle* vehicle, QObject* parent) VisualMissionItem::VisualMissionItem(Vehicle* vehicle, QObject* parent)
: QObject(parent) : QObject(parent)
, _vehicle(vehicle) , _vehicle(vehicle)
, _sequenceNumber(0)
, _isCurrentItem(false) , _isCurrentItem(false)
, _dirty(false) , _dirty(false)
, _altDifference(0.0) , _altDifference(0.0)
...@@ -45,7 +44,6 @@ VisualMissionItem::VisualMissionItem(Vehicle* vehicle, QObject* parent) ...@@ -45,7 +44,6 @@ VisualMissionItem::VisualMissionItem(Vehicle* vehicle, QObject* parent)
VisualMissionItem::VisualMissionItem(const VisualMissionItem& other, QObject* parent) VisualMissionItem::VisualMissionItem(const VisualMissionItem& other, QObject* parent)
: QObject(parent) : QObject(parent)
, _vehicle(NULL) , _vehicle(NULL)
, _sequenceNumber(0)
, _isCurrentItem(false) , _isCurrentItem(false)
, _dirty(false) , _dirty(false)
, _altDifference(0.0) , _altDifference(0.0)
...@@ -60,7 +58,6 @@ const VisualMissionItem& VisualMissionItem::operator=(const VisualMissionItem& o ...@@ -60,7 +58,6 @@ const VisualMissionItem& VisualMissionItem::operator=(const VisualMissionItem& o
{ {
_vehicle = other._vehicle; _vehicle = other._vehicle;
setSequenceNumber(other._sequenceNumber);
setIsCurrentItem(other._isCurrentItem); setIsCurrentItem(other._isCurrentItem);
setDirty(other._dirty); setDirty(other._dirty);
setAltDifference(other._altDifference); setAltDifference(other._altDifference);
...@@ -106,11 +103,3 @@ void VisualMissionItem::setAzimuth(double azimuth) ...@@ -106,11 +103,3 @@ void VisualMissionItem::setAzimuth(double azimuth)
_azimuth = azimuth; _azimuth = azimuth;
emit azimuthChanged(_azimuth); emit azimuthChanged(_azimuth);
} }
void VisualMissionItem::setSequenceNumber (int sequenceNumber)
{
if (_sequenceNumber != sequenceNumber) {
_sequenceNumber = sequenceNumber;
emit sequenceNumberChanged(_sequenceNumber);
}
}
...@@ -99,7 +99,6 @@ public: ...@@ -99,7 +99,6 @@ public:
double azimuth (void) const { return _azimuth; } double azimuth (void) const { return _azimuth; }
double distance (void) const { return _distance; } double distance (void) const { return _distance; }
bool isCurrentItem (void) const { return _isCurrentItem; } bool isCurrentItem (void) const { return _isCurrentItem; }
int sequenceNumber (void) const { return _sequenceNumber; }
QmlObjectListModel* childItems(void) { return &_childItems; } QmlObjectListModel* childItems(void) { return &_childItems; }
...@@ -111,10 +110,6 @@ public: ...@@ -111,10 +110,6 @@ public:
Vehicle* vehicle(void) { return _vehicle; } Vehicle* vehicle(void) { return _vehicle; }
// Virtuals which may be overriden by derived classes
virtual void setSequenceNumber(int sequenceNumber);
// Pure virtuals which must be provides by derived classes // Pure virtuals which must be provides by derived classes
virtual bool dirty (void) const = 0; virtual bool dirty (void) const = 0;
...@@ -125,6 +120,7 @@ public: ...@@ -125,6 +120,7 @@ public:
virtual QString commandName (void) const = 0; virtual QString commandName (void) const = 0;
virtual QGeoCoordinate coordinate (void) const = 0; virtual QGeoCoordinate coordinate (void) const = 0;
virtual QGeoCoordinate exitCoordinate (void) const = 0; virtual QGeoCoordinate exitCoordinate (void) const = 0;
virtual int sequenceNumber (void) const = 0;
virtual bool coordinateHasRelativeAltitude (void) const = 0; virtual bool coordinateHasRelativeAltitude (void) const = 0;
virtual bool exitCoordinateHasRelativeAltitude (void) const = 0; virtual bool exitCoordinateHasRelativeAltitude (void) const = 0;
...@@ -132,6 +128,7 @@ public: ...@@ -132,6 +128,7 @@ public:
virtual void setDirty (bool dirty) = 0; virtual void setDirty (bool dirty) = 0;
virtual void setCoordinate (const QGeoCoordinate& coordinate) = 0; virtual void setCoordinate (const QGeoCoordinate& coordinate) = 0;
virtual void setSequenceNumber (int sequenceNumber) = 0;
/// Save the item(s) in Json format /// Save the item(s) in Json format
/// @param saveObject Save the item to this json object /// @param saveObject Save the item to this json object
...@@ -159,7 +156,6 @@ signals: ...@@ -159,7 +156,6 @@ signals:
protected: protected:
Vehicle* _vehicle; Vehicle* _vehicle;
int _sequenceNumber;
bool _isCurrentItem; bool _isCurrentItem;
bool _dirty; bool _dirty;
double _altDifference; ///< Difference in altitude from previous waypoint double _altDifference; ///< Difference in altitude from previous waypoint
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment