diff --git a/src/MeasurementComplexItem/AreaData.cc b/src/MeasurementComplexItem/AreaData.cc index 1de851993e1cffc2b530d21190e6d44bf3f4892c..6d612ecc66bebed2c1c309e74a59b67373e70443 100644 --- a/src/MeasurementComplexItem/AreaData.cc +++ b/src/MeasurementComplexItem/AreaData.cc @@ -11,7 +11,7 @@ QGC_LOGGING_CATEGORY(AreaDataLog, "AreaDataLog") -const char *originJsonKey = "Origin"; +const char *originKey = "Origin"; const char *areaListKey = "AreaList"; const char *initializedKey = "Initialized"; @@ -304,7 +304,7 @@ bool AreaData::load(const QJsonObject &obj, QString &errorString) { if (JsonHelper::validateKeys(obj, keyInfo, e)) { this->clear(); // iterate over json array - for (const auto &jsonArea : obj[areaListKey]) { + for (const auto &jsonArea : obj[areaListKey].toArray()) { // check if area type key is present QList areaInfo = { {GeoArea::areaTypeKey, QJsonValue::String, true}, @@ -398,7 +398,7 @@ bool AreaData::save(QJsonObject &obj) { QJsonValue jsonOrigin; JsonHelper::saveGeoCoordinate(_origin, true, jsonOrigin); - temp[originJsonKey] = jsonOrigin; + temp[originKey] = jsonOrigin; temp[initializedKey] = _initialized; QJsonArray jsonAreaList; diff --git a/src/MeasurementComplexItem/CircularGenerator.cpp b/src/MeasurementComplexItem/CircularGenerator.cpp index e14c57c3b7206c4676b3063791b7470819aba771..e36852f4301f7a0c797cf173226cce6575d94eac 100644 --- a/src/MeasurementComplexItem/CircularGenerator.cpp +++ b/src/MeasurementComplexItem/CircularGenerator.cpp @@ -19,6 +19,13 @@ template <> inline auto get<0>(const IntPoint &p) { return p.X; } template <> inline auto get<1>(const IntPoint &p) { return p.Y; } namespace routing { +const QString generatorType = "CircularGenerator"; + +GeneratorBase *creator(QObject *parent) { + return new CircularGenerator(parent); +} + +REGISTER_GENERATOR(generatorType, creator) bool circularTransects(const snake::FPoint &reference, const snake::FPolygon &polygon, @@ -27,10 +34,10 @@ bool circularTransects(const snake::FPoint &reference, snake::Length minLength, snake::Transects &transects); const char *CircularGenerator::settingsGroup = "CircularGenerator"; -const char *CircularGenerator::distanceKey = "TransectDistance"; -const char *CircularGenerator::deltaAlphaKey = "DeltaAlpha"; -const char *CircularGenerator::minLengthKey = "MinLength"; -const char *CircularGenerator::referenceKey = "ReferencePoint"; +const char *distanceKey = "TransectDistance"; +const char *deltaAlphaKey = "DeltaAlpha"; +const char *minLengthKey = "MinLength"; +const char *referenceKey = "ReferencePoint"; CircularGenerator::CircularGenerator(QObject *parent) : CircularGenerator(nullptr, parent) {} @@ -51,6 +58,7 @@ CircularGenerator::CircularGenerator(GeneratorBase::Data d, QObject *parent) &GeneratorBase::generatorChanged); connect(this, &CircularGenerator::referenceChanged, this, &GeneratorBase::generatorChanged); + setName(tr("Circular Generator")); } QString CircularGenerator::editorQml() { @@ -61,11 +69,9 @@ QString CircularGenerator::mapVisualQml() { return QStringLiteral("CircularGeneratorMapVisual.qml"); } -QString CircularGenerator::name() { - return QStringLiteral("Circular Generator"); -} +QString CircularGenerator::abbreviation() { return tr("C. Gen."); } -QString CircularGenerator::abbreviation() { return QStringLiteral("C. Gen."); } +QString CircularGenerator::type() { return generatorType; } bool CircularGenerator::get(Generator &generator) { if (this->_d) { diff --git a/src/MeasurementComplexItem/CircularGenerator.h b/src/MeasurementComplexItem/CircularGenerator.h index eb3719c3d2e9d11bd51cf778f3061122f7f43236..225a5769812c7a123b907acc3d3377f8c8e120ff 100644 --- a/src/MeasurementComplexItem/CircularGenerator.h +++ b/src/MeasurementComplexItem/CircularGenerator.h @@ -23,8 +23,8 @@ public: virtual QString editorQml() override; virtual QString mapVisualQml() override; - virtual QString name() override; virtual QString abbreviation() override; + virtual QString type() override; virtual bool get(Generator &generator) override; @@ -66,5 +66,4 @@ private: SettingsFact _minLength; MeasurementArea *_measurementArea; }; - } // namespace routing diff --git a/src/MeasurementComplexItem/GeneratorBase.cc b/src/MeasurementComplexItem/GeneratorBase.cc index 212458d222b23e41800cc14a8a5ebbb895293c87..70381e5349917c171a244bf78e1e200013ea6d4b 100644 --- a/src/MeasurementComplexItem/GeneratorBase.cc +++ b/src/MeasurementComplexItem/GeneratorBase.cc @@ -1,7 +1,11 @@ #include "GeneratorBase.h" +#include "GenericSingelton.h" + namespace routing { +const char *GeneratorBase::typeKey = "GeneratorType"; + GeneratorBase::GeneratorBase(QObject *parent) : GeneratorBase(nullptr, parent) {} @@ -12,6 +16,15 @@ GeneratorBase::GeneratorBase(GeneratorBase::Data d, QObject *parent) GeneratorBase::~GeneratorBase() {} +QString GeneratorBase::name() { return _name; } + +void GeneratorBase::setName(const QString &name) { + if (_name != name) { + _name = name; + emit nameChanged(); + } +} + GeneratorBase::Data GeneratorBase::data() const { return _d; } void GeneratorBase::setData(Data d) { @@ -26,4 +39,71 @@ void GeneratorBase::setData(Data d) { void GeneratorBase::establishConnections() {} void GeneratorBase::deleteConnections() {} + +GeneratorFactory::GeneratorFactory() {} + +GeneratorFactory *GeneratorFactory::createInstance() { + return new GeneratorFactory(); +} + +GeneratorFactory::~GeneratorFactory() {} + +GeneratorFactory *GeneratorFactory::instance() { + return GenericSingelton::instance( + GeneratorFactory::createInstance); +} + +bool GeneratorFactory::registerGenerator(const QString &type, + GeneratorFactory::Creator creator) { + const auto pair = _creatorMap.insert(std::make_pair(type, creator)); + auto success = pair.second; + return success; +} + +bool GeneratorFactory::registered(const QString &type) { + return _creatorMap.end() != _creatorMap.find(type); +} + +void GeneratorFactory::unregisterGenerator(const QString &type) { + _creatorMap.erase(type); +} + +GeneratorBase *GeneratorFactory::create(const QString &type, QObject *parent) { + auto it = _creatorMap.find(type); + if (it != _creatorMap.end()) { + auto &creator = it->second; + return creator(parent); + } else { + return nullptr; + } +} + +GeneratorBase *GeneratorFactory::create(const QJsonObject &jsonGenerator, + QString &errorMessage, + QObject *parent) { + if (jsonGenerator.contains(GeneratorBase::typeKey) && + jsonGenerator[GeneratorBase::typeKey].isString()) { + auto gen = create(jsonGenerator[GeneratorBase::typeKey].toString(), parent); + if (gen != nullptr) { + QString e; + if (gen->load(jsonGenerator, e)) { + return gen; + } else { + gen->deleteLater(); + errorMessage.append(e); + return nullptr; + } + } else { + errorMessage.append(QObject::tr("Not able to create generator of type") + + " " + + jsonGenerator[GeneratorBase::typeKey].toString()); + return nullptr; + } + } else { + errorMessage.append(QObject::tr( + "Not able to load Generator. Impossible to determine type.")); + return nullptr; + } +} + } // namespace routing diff --git a/src/MeasurementComplexItem/GeneratorBase.h b/src/MeasurementComplexItem/GeneratorBase.h index 1f0bb22a580909d73cc2e99fce559f90e060fed7..c3900d55566b3becb7aaf7820926abc9c8ea5254 100644 --- a/src/MeasurementComplexItem/GeneratorBase.h +++ b/src/MeasurementComplexItem/GeneratorBase.h @@ -25,31 +25,67 @@ public: Q_PROPERTY(QString editorQml READ editorQml CONSTANT) Q_PROPERTY(QString mapVisualQml READ mapVisualQml CONSTANT) + Q_PROPERTY(QString name READ name WRITE setName NOTIFY nameChanged) virtual QString editorQml() = 0; virtual QString mapVisualQml() = 0; virtual bool save(QJsonObject &obj) const = 0; - virtual bool load(const QJsonObject &obj, QString &guiErrorMessage) = 0; + virtual bool load(const QJsonObject &obj, QString &errorString) = 0; - virtual QString name() = 0; + QString name(); + void setName(const QString &name); virtual QString abbreviation() = 0; + virtual QString type() = 0; virtual bool get(Generator &generator) = 0; Data data() const; void setData(Data d); + static const char *typeKey; + signals: void generatorChanged(); void dataChanged(); + void nameChanged(); protected: virtual void establishConnections(); virtual void deleteConnections(); Data _d; + QString _name; + +private: +}; + +class GeneratorFactory { + GeneratorFactory(); + GeneratorFactory(GeneratorFactory &other) = delete; + static GeneratorFactory *createInstance(); + +public: + typedef std::function Creator; + ~GeneratorFactory(); + static GeneratorFactory *instance(); + + bool registerGenerator(const QString &type, + Creator creator); // use REGISTER_GENERATOR to register + // a generator befor main() + bool registered(const QString &type); + void unregisterGenerator(const QString &type); + + GeneratorBase *create(const QString &type, QObject *parent = nullptr); + GeneratorBase *create(const QJsonObject &jsonGenerator, QString &errorMessage, + QObject *parent = nullptr); private: + std::map _creatorMap; }; +#define REGISTER_GENERATOR(type, creator) \ + namespace { \ + auto registered_##type = \ + GeneratorFactory::instance() -> registerGenerator(type, creator); \ + } } // namespace routing diff --git a/src/MeasurementComplexItem/LinearGenerator.cpp b/src/MeasurementComplexItem/LinearGenerator.cpp index ab4dc31731673021cf545a511832d45869bd8a3d..76d5b8e23e796114a8fecfe1912bfd50d3e0070e 100644 --- a/src/MeasurementComplexItem/LinearGenerator.cpp +++ b/src/MeasurementComplexItem/LinearGenerator.cpp @@ -1,7 +1,7 @@ #include "LinearGenerator.h" +#include "JsonHelper.h" #include "QGCLoggingCategory.h" -QGC_LOGGING_CATEGORY(LinearGeneratorLog, "LinearGeneratorLog") #define CLIPPER_SCALE 1000000 #include "geometry/MeasurementArea.h" @@ -12,6 +12,12 @@ QGC_LOGGING_CATEGORY(LinearGeneratorLog, "LinearGeneratorLog") #include "nemo_interface/SnakeTile.h" namespace routing { +const QString generatorType = "LinearGenerator"; + +GeneratorBase *creator(QObject *parent) { return new LinearGenerator(parent); } + +REGISTER_GENERATOR(generatorType, creator) +QGC_LOGGING_CATEGORY(LinearGeneratorLog, "LinearGeneratorLog") bool linearTransects(const snake::FPolygon &polygon, const std::vector &tiles, @@ -19,9 +25,9 @@ bool linearTransects(const snake::FPolygon &polygon, snake::Length minLength, snake::Transects &transects); const char *LinearGenerator::settingsGroup = "LinearGenerator"; -const char *LinearGenerator::distanceKey = "TransectDistance"; -const char *LinearGenerator::alphaKey = "Alpha"; -const char *LinearGenerator::minLenghKey = "MinLength"; +const char *distanceKey = "TransectDistance"; +const char *alphaKey = "Alpha"; +const char *minLengthKey = "MinLength"; LinearGenerator::LinearGenerator(QObject *parent) : LinearGenerator(nullptr, parent) {} @@ -32,7 +38,7 @@ LinearGenerator::LinearGenerator(GeneratorBase::Data d, QObject *parent) QStringLiteral(":/json/LinearGenerator.SettingsGroup.json"), this)), _distance(settingsGroup, _metaDataMap[distanceKey]), _alpha(settingsGroup, _metaDataMap[alphaKey]), - _minLength(settingsGroup, _metaDataMap[minLenghKey ), + _minLength(settingsGroup, _metaDataMap[minLengthKey]), _measurementArea(nullptr), _safeArea(nullptr) { connect(this->distance(), &Fact::rawValueChanged, this, &GeneratorBase::generatorChanged); @@ -42,6 +48,7 @@ LinearGenerator::LinearGenerator(GeneratorBase::Data d, QObject *parent) &GeneratorBase::generatorChanged); connect(this->_d, &AreaData::areaListChanged, this, &LinearGenerator::onAreaListChanged); + setName(tr("Linear Generator")); } QString LinearGenerator::editorQml() { @@ -50,10 +57,10 @@ QString LinearGenerator::editorQml() { QString LinearGenerator::mapVisualQml() { return QStringLiteral(""); } -QString LinearGenerator::name() { return QStringLiteral("Linear Generator"); } - QString LinearGenerator::abbreviation() { return QStringLiteral("L. Gen."); } +QString LinearGenerator::type() { return generatorType; } + bool LinearGenerator::get(Generator &generator) { if (_d) { if (this->_d->isCorrect()) { @@ -183,7 +190,7 @@ bool LinearGenerator::save(QJsonObject &obj) const { << variant.typeName(); return false; } else { - temp[minLenghKey = val; + temp[minLengthKey] = val; } obj = std::move(temp); diff --git a/src/MeasurementComplexItem/LinearGenerator.h b/src/MeasurementComplexItem/LinearGenerator.h index f0d300771ae3626923dd38afcc1b4b4d89c40269..0e5f2d0306f979329a3a34ed427036c2496c66fd 100644 --- a/src/MeasurementComplexItem/LinearGenerator.h +++ b/src/MeasurementComplexItem/LinearGenerator.h @@ -22,8 +22,8 @@ public: virtual QString editorQml() override; virtual QString mapVisualQml() override; - virtual QString name() override; virtual QString abbreviation() override; + virtual QString type() override; virtual bool get(Generator &generator) override;