diff options
| author | Even Rouault <even.rouault@spatialys.com> | 2020-06-08 13:40:31 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2020-06-08 13:40:31 +0200 |
| commit | dfa281a25d1f0fc5f3d919aa84f16b3b582a3f27 (patch) | |
| tree | 5224c776fc48ea4de68950ed383d500b7254e165 /src | |
| parent | 4e347f4710da2c5aa691ea3f3df942e0b25637ec (diff) | |
| parent | a24cf969aab61d950de916b48de88229b05a00f4 (diff) | |
| download | PROJ-dfa281a25d1f0fc5f3d919aa84f16b3b582a3f27.tar.gz PROJ-dfa281a25d1f0fc5f3d919aa84f16b3b582a3f27.zip | |
Merge pull request #2259 from rouault/slovakian_geoids
Register Slovakian geoid transformations with needed code changes
Diffstat (limited to 'src')
| -rw-r--r-- | src/iso19111/coordinateoperation.cpp | 91 | ||||
| -rw-r--r-- | src/iso19111/io.cpp | 20 |
2 files changed, 107 insertions, 4 deletions
diff --git a/src/iso19111/coordinateoperation.cpp b/src/iso19111/coordinateoperation.cpp index bdb2ad2e..ecc3df06 100644 --- a/src/iso19111/coordinateoperation.cpp +++ b/src/iso19111/coordinateoperation.cpp @@ -7822,9 +7822,34 @@ createPropertiesForInverse(const CoordinateOperation *op, bool derivedFrom, auto targetCRS = op->targetCRS(); std::string name; if (!forwardName.empty()) { - if (starts_with(forwardName, INVERSE_OF) || - forwardName.find(" + ") != std::string::npos) { - auto tokens = split(forwardName, " + "); + if (dynamic_cast<const Transformation *>(op) == nullptr && + dynamic_cast<const ConcatenatedOperation *>(op) == nullptr && + (starts_with(forwardName, INVERSE_OF) || + forwardName.find(" + ") != std::string::npos)) { + std::vector<std::string> tokens; + std::string curToken; + bool inString = false; + for (size_t i = 0; i < forwardName.size(); ++i) { + if (inString) { + curToken += forwardName[i]; + if (forwardName[i] == '\'') { + inString = false; + } + } else if (i + 3 < forwardName.size() && + memcmp(&forwardName[i], " + ", 3) == 0) { + tokens.push_back(curToken); + curToken.clear(); + i += 2; + } else if (forwardName[i] == '\'') { + inString = true; + curToken += forwardName[i]; + } else { + curToken += forwardName[i]; + } + } + if (!curToken.empty()) { + tokens.push_back(curToken); + } for (size_t i = tokens.size(); i > 0;) { i--; if (!name.empty()) { @@ -7841,7 +7866,11 @@ createPropertiesForInverse(const CoordinateOperation *op, bool derivedFrom, } } else if (!sourceCRS || !targetCRS || forwardName != buildOpName(opType, sourceCRS, targetCRS)) { - name = INVERSE_OF + forwardName; + if (forwardName.find(" + ") != std::string::npos) { + name = INVERSE_OF + '\'' + forwardName + '\''; + } else { + name = INVERSE_OF + forwardName; + } } } if (name.empty() && sourceCRS && targetCRS) { @@ -8662,6 +8691,7 @@ isGeographic3DToGravityRelatedHeight(const OperationMethodNNPtr &method, "9663", // Geographic3D to GravityRelatedHeight (OSGM-GB) "9664", // Geographic3D to GravityRelatedHeight (IGN1997) "9665", // Geographic3D to GravityRelatedHeight (US .gtx) + "9635", // Geog3D to Geog2D+GravityRelatedHeight (US .gtx) }; if (ci_find(methodName, "Geographic3D to GravityRelatedHeight") == 0) { @@ -9697,6 +9727,21 @@ void Transformation::_exportToPROJString( const auto &heightFilename = _getHeightToGeographic3DFilename(this, true); if (!heightFilename.empty()) { + auto targetCRSGeog = + extractGeographicCRSIfGeographicCRSOrEquivalent(targetCRS()); + if (!targetCRSGeog) { + throw io::FormattingException( + concat("Can apply ", methodName, " only to GeographicCRS")); + } + + if (!formatter->omitHorizontalConversionInVertTransformation()) { + formatter->startInversion(); + formatter->pushOmitZUnitConversion(); + targetCRSGeog->addAngularUnitConvertAndAxisSwap(formatter); + formatter->popOmitZUnitConversion(); + formatter->stopInversion(); + } + if (isMethodInverseOf) { formatter->startInversion(); } @@ -9706,6 +9751,13 @@ void Transformation::_exportToPROJString( if (isMethodInverseOf) { formatter->stopInversion(); } + + if (!formatter->omitHorizontalConversionInVertTransformation()) { + formatter->pushOmitZUnitConversion(); + targetCRSGeog->addAngularUnitConvertAndAxisSwap(formatter); + formatter->popOmitZUnitConversion(); + } + return; } @@ -9716,6 +9768,22 @@ void Transformation::_exportToPROJString( if (fileParameter && fileParameter->type() == ParameterValue::Type::FILENAME) { auto filename = fileParameter->valueFile(); + + auto sourceCRSGeog = + extractGeographicCRSIfGeographicCRSOrEquivalent(sourceCRS()); + if (!sourceCRSGeog) { + throw io::FormattingException( + concat("Can apply ", methodName, " only to GeographicCRS")); + } + + if (!formatter->omitHorizontalConversionInVertTransformation()) { + formatter->startInversion(); + formatter->pushOmitZUnitConversion(); + sourceCRSGeog->addAngularUnitConvertAndAxisSwap(formatter); + formatter->popOmitZUnitConversion(); + formatter->stopInversion(); + } + bool doInversion = isMethodInverseOf; // The EPSG Geog3DToHeight is the reverse convention of PROJ ! doInversion = !doInversion; @@ -9728,6 +9796,13 @@ void Transformation::_exportToPROJString( if (doInversion) { formatter->stopInversion(); } + + if (!formatter->omitHorizontalConversionInVertTransformation()) { + formatter->pushOmitZUnitConversion(); + sourceCRSGeog->addAngularUnitConvertAndAxisSwap(formatter); + formatter->popOmitZUnitConversion(); + } + return; } } @@ -12286,6 +12361,8 @@ createBallparkGeographicOffset(const crs::CRSNNPtr &sourceCRS, //! @cond Doxygen_Suppress +// --------------------------------------------------------------------------- + struct MyPROJStringExportableGeodToGeod final : public io::IPROJStringExportable { crs::GeodeticCRSPtr geodSrc{}; @@ -12332,14 +12409,18 @@ struct MyPROJStringExportableHorizVertical final _exportToPROJString(io::PROJStringFormatter *formatter) const override { formatter->pushOmitZUnitConversion(); + horizTransform->_exportToPROJString(formatter); formatter->startInversion(); geogDst->addAngularUnitConvertAndAxisSwap(formatter); formatter->stopInversion(); + formatter->popOmitZUnitConversion(); + formatter->pushOmitHorizontalConversionInVertTransformation(); verticalTransform->_exportToPROJString(formatter); + formatter->popOmitHorizontalConversionInVertTransformation(); formatter->pushOmitZUnitConversion(); geogDst->addAngularUnitConvertAndAxisSwap(formatter); @@ -12385,7 +12466,9 @@ struct MyPROJStringExportableHorizVerticalHorizPROJBased final formatter->popOmitZUnitConversion(); + formatter->pushOmitHorizontalConversionInVertTransformation(); verticalTransform->_exportToPROJString(formatter); + formatter->popOmitHorizontalConversionInVertTransformation(); formatter->pushOmitZUnitConversion(); diff --git a/src/iso19111/io.cpp b/src/iso19111/io.cpp index e7f8769c..38b407ee 100644 --- a/src/iso19111/io.cpp +++ b/src/iso19111/io.cpp @@ -6635,6 +6635,7 @@ struct PROJStringFormatter::Private { std::vector<InversionStackElt> inversionStack_{InversionStackElt()}; bool omitProjLongLatIfPossible_ = false; std::vector<bool> omitZUnitConversion_{false}; + std::vector<bool> omitHorizontalConversionInVertTransformation_{false}; DatabaseContextPtr dbContext_{}; bool useApproxTMerc_ = false; bool addNoDefs_ = true; @@ -7739,6 +7740,25 @@ bool PROJStringFormatter::omitZUnitConversion() const { // --------------------------------------------------------------------------- +void PROJStringFormatter::pushOmitHorizontalConversionInVertTransformation() { + d->omitHorizontalConversionInVertTransformation_.push_back(true); +} + +// --------------------------------------------------------------------------- + +void PROJStringFormatter::popOmitHorizontalConversionInVertTransformation() { + assert(d->omitHorizontalConversionInVertTransformation_.size() > 1); + d->omitHorizontalConversionInVertTransformation_.pop_back(); +} + +// --------------------------------------------------------------------------- + +bool PROJStringFormatter::omitHorizontalConversionInVertTransformation() const { + return d->omitHorizontalConversionInVertTransformation_.back(); +} + +// --------------------------------------------------------------------------- + void PROJStringFormatter::setLegacyCRSToCRSContext(bool legacyContext) { d->legacyCRSToCRSContext_ = legacyContext; } |
