aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEven Rouault <even.rouault@spatialys.com>2020-03-06 14:11:31 +0100
committerEven Rouault <even.rouault@spatialys.com>2020-03-06 14:11:31 +0100
commit6512ef2427ed6b303ae1c03b91907020cb5366d8 (patch)
tree2d6f318b8f1700ebcb35dbfd7791c038d7b2a212
parent2dbca196a0c73972a0cc70856a42f01765868145 (diff)
downloadPROJ-6512ef2427ed6b303ae1c03b91907020cb5366d8.tar.gz
PROJ-6512ef2427ed6b303ae1c03b91907020cb5366d8.zip
WKT import/export: add support for WKT1_ESRI VERTCS syntax
-rw-r--r--include/proj/internal/io_internal.hpp3
-rw-r--r--src/iso19111/crs.cpp19
-rw-r--r--src/iso19111/datum.cpp6
-rw-r--r--src/iso19111/io.cpp49
-rw-r--r--src/iso19111/static.cpp1
-rw-r--r--src/wkt1_generated_parser.c406
-rw-r--r--src/wkt1_generated_parser.h26
-rw-r--r--src/wkt1_grammar.y8
-rw-r--r--src/wkt1_parser.cpp7
-rw-r--r--test/unit/test_crs.cpp30
-rw-r--r--test/unit/test_io.cpp39
11 files changed, 378 insertions, 216 deletions
diff --git a/include/proj/internal/io_internal.hpp b/include/proj/internal/io_internal.hpp
index 1e2508cc..617dffab 100644
--- a/include/proj/internal/io_internal.hpp
+++ b/include/proj/internal/io_internal.hpp
@@ -62,6 +62,7 @@ class WKTConstants {
static const std::string PROJECTION;
static const std::string PARAMETER; // WKT2 too
static const std::string VERT_CS;
+ static const std::string VERTCS; // WKT1 ESRI
static const std::string VERT_DATUM;
static const std::string COMPD_CS;
static const std::string TOWGS84; // WKT1 only
@@ -95,7 +96,7 @@ class WKTConstants {
static const std::string CITATION;
static const std::string URI;
static const std::string VERTCRS;
- static const std::string VDATUM;
+ static const std::string VDATUM; // WKT2 and WKT1 ESRI
static const std::string COMPOUNDCRS;
static const std::string PARAMETERFILE;
static const std::string COORDINATEOPERATION;
diff --git a/src/iso19111/crs.cpp b/src/iso19111/crs.cpp
index 45e2309c..e1181d43 100644
--- a/src/iso19111/crs.cpp
+++ b/src/iso19111/crs.cpp
@@ -2548,12 +2548,29 @@ const cs::VerticalCSNNPtr VerticalCRS::coordinateSystem() const {
void VerticalCRS::_exportToWKT(io::WKTFormatter *formatter) const {
const bool isWKT2 = formatter->version() == io::WKTFormatter::Version::WKT2;
formatter->startNode(isWKT2 ? io::WKTConstants::VERTCRS
- : io::WKTConstants::VERT_CS,
+ : formatter->useESRIDialect()
+ ? io::WKTConstants::VERTCS
+ : io::WKTConstants::VERT_CS,
!identifiers().empty());
formatter->addQuotedString(nameStr());
exportDatumOrDatumEnsembleToWkt(formatter);
const auto &cs = SingleCRS::getPrivate()->coordinateSystem;
const auto &axisList = cs->axisList();
+
+ if (formatter->useESRIDialect()) {
+ // Seems to be a constant value...
+ formatter->startNode(io::WKTConstants::PARAMETER, false);
+ formatter->addQuotedString("Vertical_Shift");
+ formatter->add(0.0);
+ formatter->endNode();
+
+ formatter->startNode(io::WKTConstants::PARAMETER, false);
+ formatter->addQuotedString("Direction");
+ formatter->add(
+ axisList[0]->direction() == cs::AxisDirection::UP ? 1.0 : -1.0);
+ formatter->endNode();
+ }
+
if (!isWKT2) {
axisList[0]->unit()._exportToWKT(formatter);
}
diff --git a/src/iso19111/datum.cpp b/src/iso19111/datum.cpp
index d9d9c261..ad287e73 100644
--- a/src/iso19111/datum.cpp
+++ b/src/iso19111/datum.cpp
@@ -1846,7 +1846,9 @@ void VerticalReferenceFrame::_exportToWKT(
{
const bool isWKT2 = formatter->version() == io::WKTFormatter::Version::WKT2;
formatter->startNode(isWKT2 ? io::WKTConstants::VDATUM
- : io::WKTConstants::VERT_DATUM,
+ : formatter->useESRIDialect()
+ ? io::WKTConstants::VDATUM
+ : io::WKTConstants::VERT_DATUM,
!identifiers().empty());
const auto &l_name = nameStr();
if (!l_name.empty()) {
@@ -1856,7 +1858,7 @@ void VerticalReferenceFrame::_exportToWKT(
}
if (isWKT2) {
Datum::getPrivate()->exportAnchorDefinition(formatter);
- } else {
+ } else if (!formatter->useESRIDialect()) {
formatter->add(2005); // CS_VD_GeoidModelDerived from OGC 01-009
const auto &extension = formatter->getVDatumExtension();
if (!extension.empty()) {
diff --git a/src/iso19111/io.cpp b/src/iso19111/io.cpp
index 861aadbf..c57014d9 100644
--- a/src/iso19111/io.cpp
+++ b/src/iso19111/io.cpp
@@ -2463,18 +2463,57 @@ WKTParser::Private::buildCS(const WKTNodeNNPtr &node, /* maybe null */
return CartesianCS::createEastingNorthing(unit);
}
} else if (ci_equal(parentNodeName, WKTConstants::VERT_CS) ||
+ ci_equal(parentNodeName, WKTConstants::VERTCS) ||
ci_equal(parentNodeName, WKTConstants::BASEVERTCRS)) {
csTypeCStr = "vertical";
+
+ bool downDirection = false;
+ if (ci_equal(parentNodeName, WKTConstants::VERTCS)) // ESRI
+ {
+ for (const auto &childNode : parentNode->GP()->children()) {
+ const auto &childNodeChildren = childNode->GP()->children();
+ if (childNodeChildren.size() == 2 &&
+ ci_equal(childNode->GP()->value(),
+ WKTConstants::PARAMETER) &&
+ childNodeChildren[0]->GP()->value() ==
+ "\"Direction\"") {
+ const auto &paramValue =
+ childNodeChildren[1]->GP()->value();
+ try {
+ double val = asDouble(childNodeChildren[1]);
+ if (val == 1.0) {
+ // ok
+ } else if (val == -1.0) {
+ downDirection = true;
+ }
+ } catch (const std::exception &) {
+ throw ParsingException(
+ concat("unhandled parameter value type : ",
+ paramValue));
+ }
+ }
+ }
+ }
+
if (axisCount == 0) {
auto unit =
buildUnitInSubNode(parentNode, UnitOfMeasure::Type::LINEAR);
if (unit == UnitOfMeasure::NONE) {
- if (ci_equal(parentNodeName, WKTConstants::VERT_CS)) {
+ if (ci_equal(parentNodeName, WKTConstants::VERT_CS) ||
+ ci_equal(parentNodeName, WKTConstants::VERTCS)) {
ThrowParsingExceptionMissingUNIT();
} else {
unit = UnitOfMeasure::METRE;
}
}
+ if (downDirection) {
+ return VerticalCS::create(
+ util::PropertyMap(),
+ CoordinateSystemAxis::create(
+ util::PropertyMap().set(IdentifiedObject::NAME_KEY,
+ "depth"),
+ "D", AxisDirection::DOWN, unit));
+ }
return VerticalCS::createGravityRelatedHeight(unit);
}
} else if (ci_equal(parentNodeName, WKTConstants::LOCAL_CS)) {
@@ -3890,6 +3929,7 @@ CRSNNPtr WKTParser::Private::buildVerticalCRS(const WKTNodeNNPtr &node) {
auto &csNode = nodeP->lookForChild(WKTConstants::CS_);
const auto &nodeValue = nodeP->value();
if (isNull(csNode) && !ci_equal(nodeValue, WKTConstants::VERT_CS) &&
+ !ci_equal(nodeValue, WKTConstants::VERTCS) &&
!ci_equal(nodeValue, WKTConstants::BASEVERTCRS)) {
ThrowMissing(WKTConstants::CS_);
}
@@ -3905,7 +3945,8 @@ CRSNNPtr WKTParser::Private::buildVerticalCRS(const WKTNodeNNPtr &node) {
// following conventions from
// https://pubs.usgs.gov/tm/11b4/pdf/tm11-B4.pdf
// page 9
- if (ci_equal(nodeValue, WKTConstants::VERT_CS)) {
+ if (ci_equal(nodeValue, WKTConstants::VERT_CS) ||
+ ci_equal(nodeValue, WKTConstants::VERTCS)) {
std::string name;
if (props.getStringValue(IdentifiedObject::NAME_KEY, name)) {
std::string geoidName;
@@ -4404,6 +4445,7 @@ CRSPtr WKTParser::Private::buildCRS(const WKTNodeNNPtr &node) {
}
if (ci_equal(name, WKTConstants::VERT_CS) ||
+ ci_equal(name, WKTConstants::VERTCS) ||
ci_equal(name, WKTConstants::VERTCRS) ||
ci_equal(name, WKTConstants::VERTICALCRS)) {
if (!isNull(nodeP->lookForChild(WKTConstants::BASEVERTCRS))) {
@@ -6165,6 +6207,9 @@ WKTParser::attachDatabaseContext(const DatabaseContextPtr &dbContext) {
*/
WKTParser::WKTGuessedDialect
WKTParser::guessDialect(const std::string &wkt) noexcept {
+ if (ci_starts_with(wkt, WKTConstants::VERTCS)) {
+ return WKTGuessedDialect::WKT1_ESRI;
+ }
const std::string *const wkt1_keywords[] = {
&WKTConstants::GEOCCS, &WKTConstants::GEOGCS, &WKTConstants::COMPD_CS,
&WKTConstants::PROJCS, &WKTConstants::VERT_CS, &WKTConstants::LOCAL_CS};
diff --git a/src/iso19111/static.cpp b/src/iso19111/static.cpp
index da399288..11306e35 100644
--- a/src/iso19111/static.cpp
+++ b/src/iso19111/static.cpp
@@ -204,6 +204,7 @@ DEFINE_WKT_CONSTANT(PROJCS);
DEFINE_WKT_CONSTANT(PROJECTION);
DEFINE_WKT_CONSTANT(PARAMETER);
DEFINE_WKT_CONSTANT(VERT_CS);
+DEFINE_WKT_CONSTANT(VERTCS);
DEFINE_WKT_CONSTANT(VERT_DATUM);
DEFINE_WKT_CONSTANT(COMPD_CS);
DEFINE_WKT_CONSTANT(TOWGS84);
diff --git a/src/wkt1_generated_parser.c b/src/wkt1_generated_parser.c
index 7a590f80..2785ec9f 100644
--- a/src/wkt1_generated_parser.c
+++ b/src/wkt1_generated_parser.c
@@ -150,18 +150,20 @@ extern int pj_wkt1_debug;
T_GEOCCS = 269,
T_AUTHORITY = 270,
T_VERT_CS = 271,
- T_VERT_DATUM = 272,
- T_COMPD_CS = 273,
- T_AXIS = 274,
- T_TOWGS84 = 275,
- T_FITTED_CS = 276,
- T_LOCAL_CS = 277,
- T_LOCAL_DATUM = 278,
- T_PARAMETER = 279,
- T_EXTENSION = 280,
- T_STRING = 281,
- T_NUMBER = 282,
- T_IDENTIFIER = 283
+ T_VERTCS = 272,
+ T_VERT_DATUM = 273,
+ T_VDATUM = 274,
+ T_COMPD_CS = 275,
+ T_AXIS = 276,
+ T_TOWGS84 = 277,
+ T_FITTED_CS = 278,
+ T_LOCAL_CS = 279,
+ T_LOCAL_DATUM = 280,
+ T_PARAMETER = 281,
+ T_EXTENSION = 282,
+ T_STRING = 283,
+ T_NUMBER = 284,
+ T_IDENTIFIER = 285
};
#endif
@@ -420,23 +422,23 @@ union yyalloc
#endif /* !YYCOPY_NEEDED */
/* YYFINAL -- State number of the termination state. */
-#define YYFINAL 28
+#define YYFINAL 30
/* YYLAST -- Last index in YYTABLE. */
-#define YYLAST 215
+#define YYLAST 222
/* YYNTOKENS -- Number of terminals. */
-#define YYNTOKENS 34
+#define YYNTOKENS 36
/* YYNNTS -- Number of nonterminals. */
-#define YYNNTS 66
+#define YYNNTS 67
/* YYNRULES -- Number of rules. */
-#define YYNRULES 99
+#define YYNRULES 101
/* YYNSTATES -- Number of states. */
-#define YYNSTATES 257
+#define YYNSTATES 267
/* YYTRANSLATE[YYX] -- Symbol number corresponding to YYX as returned
by yylex, with out-of-bounds checking. */
#define YYUNDEFTOK 2
-#define YYMAXUTOK 283
+#define YYMAXUTOK 285
#define YYTRANSLATE(YYX) \
((unsigned int) (YYX) <= YYMAXUTOK ? yytranslate[YYX] : YYUNDEFTOK)
@@ -449,12 +451,12 @@ static const yytype_uint8 yytranslate[] =
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
- 30, 32, 2, 2, 33, 2, 2, 2, 2, 2,
+ 32, 34, 2, 2, 35, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
- 2, 29, 2, 31, 2, 2, 2, 2, 2, 2,
+ 2, 31, 2, 33, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
@@ -473,23 +475,24 @@ static const yytype_uint8 yytranslate[] =
2, 2, 2, 2, 2, 2, 1, 2, 3, 4,
5, 6, 7, 8, 9, 10, 11, 12, 13, 14,
15, 16, 17, 18, 19, 20, 21, 22, 23, 24,
- 25, 26, 27, 28
+ 25, 26, 27, 28, 29, 30
};
#if YYDEBUG
/* YYRLINE[YYN] -- Source line where rule number YYN was defined. */
static const yytype_uint16 yyrline[] =
{
- 0, 76, 76, 88, 88, 91, 94, 94, 97, 97,
- 97, 97, 100, 103, 105, 106, 109, 111, 112, 115,
- 118, 122, 127, 127, 127, 127, 127, 127, 130, 130,
- 134, 138, 139, 142, 143, 145, 146, 147, 148, 150,
- 151, 154, 157, 160, 164, 166, 167, 168, 169, 172,
- 176, 179, 182, 185, 188, 191, 194, 197, 200, 203,
- 204, 205, 206, 209, 212, 215, 217, 218, 219, 222,
- 224, 225, 226, 229, 232, 235, 238, 240, 243, 248,
- 251, 253, 256, 259, 262, 265, 268, 271, 274, 277,
- 280, 283, 286, 289, 292, 294, 296, 297, 298, 301
+ 0, 80, 80, 92, 92, 95, 98, 98, 101, 101,
+ 101, 101, 104, 107, 109, 110, 113, 115, 116, 119,
+ 122, 126, 131, 131, 131, 131, 131, 131, 134, 134,
+ 138, 142, 143, 146, 147, 149, 150, 151, 152, 154,
+ 155, 158, 161, 164, 168, 170, 171, 172, 173, 176,
+ 180, 183, 186, 189, 192, 195, 198, 201, 204, 207,
+ 208, 209, 210, 213, 216, 219, 220, 222, 223, 224,
+ 227, 230, 232, 233, 234, 237, 240, 243, 246, 248,
+ 251, 256, 259, 261, 264, 267, 270, 273, 276, 279,
+ 282, 285, 288, 291, 294, 297, 300, 302, 304, 305,
+ 306, 309
};
#endif
@@ -502,25 +505,27 @@ static const char *const yytname[] =
"\"CONCAT_MT\"", "\"INVERSE_MT\"", "\"PASSTHROUGH_MT\"", "\"PROJCS\"",
"\"PROJECTION\"", "\"GEOGCS\"", "\"DATUM\"", "\"SPHEROID\"",
"\"PRIMEM\"", "\"UNIT\"", "\"GEOCCS\"", "\"AUTHORITY\"", "\"VERT_CS\"",
- "\"VERT_DATUM\"", "\"COMPD_CS\"", "\"AXIS\"", "\"TOWGS84\"",
- "\"FITTED_CS\"", "\"LOCAL_CS\"", "\"LOCAL_DATUM\"", "\"PARAMETER\"",
- "\"EXTENSION\"", "\"string\"", "\"number\"", "\"identifier\"", "'['",
- "'('", "']'", "')'", "','", "$accept", "input", "begin_node",
- "begin_node_name", "end_node", "math_transform", "param_mt", "parameter",
- "opt_parameter_list", "concat_mt", "opt_math_transform_list", "inv_mt",
- "passthrough_mt", "integer", "coordinate_system", "horz_cs",
- "projected_cs", "opt_parameter_list_linear_unit",
- "parameter_list_linear_unit", "opt_twin_axis_extension_authority",
- "opt_authority", "extension", "projection", "geographic_cs", "datum",
+ "\"VERTCS\"", "\"VERT_DATUM\"", "\"VDATUM\"", "\"COMPD_CS\"", "\"AXIS\"",
+ "\"TOWGS84\"", "\"FITTED_CS\"", "\"LOCAL_CS\"", "\"LOCAL_DATUM\"",
+ "\"PARAMETER\"", "\"EXTENSION\"", "\"string\"", "\"number\"",
+ "\"identifier\"", "'['", "'('", "']'", "')'", "','", "$accept", "input",
+ "begin_node", "begin_node_name", "end_node", "math_transform",
+ "param_mt", "parameter", "opt_parameter_list", "concat_mt",
+ "opt_math_transform_list", "inv_mt", "passthrough_mt", "integer",
+ "coordinate_system", "horz_cs", "projected_cs",
+ "opt_parameter_list_linear_unit", "parameter_list_linear_unit",
+ "opt_twin_axis_extension_authority", "opt_authority", "extension",
+ "projection", "geographic_cs", "datum",
"opt_towgs84_authority_extension", "spheroid", "semi_major_axis",
"inverse_flattening", "prime_meridian", "longitude", "angular_unit",
"linear_unit", "unit", "conversion_factor", "geocentric_cs",
"opt_three_axis_extension_authority", "three_axis", "authority",
- "vert_cs", "opt_axis_authority", "vert_datum", "opt_extension_authority",
- "datum_type", "compd_cs", "head_cs", "tail_cs", "twin_axis", "axis",
- "towgs84", "towgs84_parameters", "three_parameters", "seven_parameters",
- "dx", "dy", "dz", "ex", "ey", "ez", "ppm", "fitted_cs", "to_base",
- "base_cs", "local_cs", "opt_axis_list_authority", "local_datum", YY_NULLPTR
+ "vert_cs", "opt_axis_authority", "vert_datum", "vdatum",
+ "opt_extension_authority", "datum_type", "compd_cs", "head_cs",
+ "tail_cs", "twin_axis", "axis", "towgs84", "towgs84_parameters",
+ "three_parameters", "seven_parameters", "dx", "dy", "dz", "ex", "ey",
+ "ez", "ppm", "fitted_cs", "to_base", "base_cs", "local_cs",
+ "opt_axis_list_authority", "local_datum", YY_NULLPTR
};
#endif
@@ -531,8 +536,8 @@ static const yytype_uint16 yytoknum[] =
{
0, 256, 257, 258, 259, 260, 261, 262, 263, 264,
265, 266, 267, 268, 269, 270, 271, 272, 273, 274,
- 275, 276, 277, 278, 279, 280, 281, 282, 283, 91,
- 40, 93, 41, 44
+ 275, 276, 277, 278, 279, 280, 281, 282, 283, 284,
+ 285, 91, 40, 93, 41, 44
};
# endif
@@ -550,32 +555,33 @@ static const yytype_uint16 yytoknum[] =
STATE-NUM. */
static const yytype_int16 yypact[] =
{
- 136, 2, 2, 2, 2, 2, 2, 2, 26, -127,
+ 125, 1, 1, 1, 1, 1, 1, 1, 1, 25,
-127, -127, -127, -127, -127, -127, -127, -127, -127, -127,
- 11, 5, 18, 32, 36, 40, 42, 53, -127, -127,
- 35, 66, 66, 61, 136, 85, -127, -127, 59, -127,
- 67, 2, 68, 69, 2, 70, -127, 72, 2, 2,
- 2, 2, -127, -127, -127, -127, -127, 76, 2, 77,
- 84, 79, 87, 87, 82, 105, 136, 88, 85, 85,
- 93, 136, 89, 105, 2, 90, 113, 2, 95, 96,
- 103, 2, 98, -127, -127, 99, 109, 25, 101, 25,
- -127, 107, -127, 25, 103, 111, 114, 1, 2, 115,
- 120, 105, 105, -127, 99, 122, 14, 25, 34, 25,
- 2, 88, -127, 85, 25, -127, 85, -127, 114, 119,
- 141, 25, 126, 127, -127, -127, 128, 15, 25, 135,
- 127, -127, 130, 25, 137, 2, 2, -127, 114, -127,
- 2, 114, -127, -127, 132, -127, 101, -127, 25, 25,
- 133, -127, -127, 1, 33, 25, 140, 2, 114, -127,
- 99, -127, -127, 114, 25, 33, 25, -127, -127, 114,
- 138, 139, -127, 142, -127, 143, -127, -127, -127, 14,
- 25, -127, -127, 114, -127, 99, 144, -127, -127, 145,
- 146, -127, -127, 25, -127, 114, 99, -127, 147, -127,
- 25, 148, 151, 150, 25, -127, 133, -127, -127, -127,
- 119, 154, -127, 25, -127, -127, 149, -127, -127, -127,
- 119, -127, 25, 25, 25, -127, -127, -127, -127, 114,
- -127, 156, 153, -127, -127, -127, 25, -127, 155, 119,
- -127, 157, -127, -127, 158, 160, -127, 159, 162, -127,
- 161, 163, -127, 164, 166, -127, -127
+ -127, 8, 9, 18, 28, 37, 46, 50, 51, 43,
+ -127, -127, 61, 77, 77, 71, 74, 125, 132, -127,
+ -127, 65, -127, 60, 1, 64, 66, 1, 67, 1,
+ 69, -127, 70, 1, 1, 1, 1, -127, -127, -127,
+ -127, -127, 72, 1, 76, 88, 83, 97, 97, 85,
+ 99, 33, -7, 125, 86, 132, 132, 95, 125, 90,
+ 99, 1, 91, 118, 1, 96, 108, 101, 1, 109,
+ -127, -127, 1, 112, 33, -127, -127, -127, 115, 126,
+ 33, 116, 33, -127, 119, -127, 33, 101, 120, 121,
+ -7, 1, 122, 123, 99, 99, -127, 115, 124, -3,
+ 33, 130, -7, -127, 0, 33, 86, -127, 132, 33,
+ -127, 132, -127, 121, 139, 146, 33, 131, 133, -1,
+ 33, 138, 131, -127, 134, 33, 141, 1, 1, -127,
+ 121, -127, 142, -127, -127, 1, 121, -127, -127, -127,
+ 116, -127, 33, 33, 137, -127, -127, 7, 33, 144,
+ 1, 121, -127, 115, -127, -127, 121, 33, 7, 33,
+ -127, -127, 121, 143, 145, -127, 33, 149, -127, -127,
+ -127, -127, -3, 33, 121, -127, 115, 150, -127, -127,
+ 151, 147, -127, -127, 33, -127, 121, 115, -127, 152,
+ -127, 33, 153, 158, -127, 161, -127, 137, -127, -127,
+ -127, 139, 148, -127, 33, -127, -127, 156, -127, -127,
+ -127, 139, -127, 33, 33, 33, -127, -127, -127, 121,
+ -127, 163, 159, -127, -127, -127, 33, -127, 160, 139,
+ -127, 164, -127, -127, 162, 167, -127, 165, 169, -127,
+ 166, 170, -127, 168, 173, -127, -127
};
/* YYDEFACT[STATE-NUM] -- Default reduction number in state STATE-NUM.
@@ -583,158 +589,163 @@ static const yytype_int16 yypact[] =
means the default is an error. */
static const yytype_uint8 yydefact[] =
{
- 0, 0, 0, 0, 0, 0, 0, 0, 0, 2,
- 22, 29, 28, 23, 24, 25, 26, 27, 3, 4,
- 0, 0, 0, 0, 0, 0, 0, 0, 1, 5,
- 0, 0, 0, 0, 0, 0, 6, 7, 0, 95,
- 0, 0, 0, 0, 0, 0, 75, 0, 0, 0,
- 0, 0, 92, 8, 9, 10, 11, 0, 0, 0,
- 0, 0, 0, 0, 0, 0, 0, 14, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
- 0, 0, 66, 55, 76, 70, 0, 0, 17, 0,
- 21, 0, 93, 0, 0, 0, 39, 0, 0, 45,
- 0, 0, 0, 73, 70, 0, 0, 0, 0, 0,
- 0, 14, 12, 0, 0, 19, 0, 91, 39, 0,
- 0, 0, 0, 35, 32, 31, 0, 0, 0, 0,
- 35, 54, 59, 0, 0, 0, 0, 68, 39, 65,
- 0, 39, 72, 74, 0, 15, 17, 16, 0, 0,
- 96, 40, 42, 0, 0, 0, 0, 0, 39, 48,
- 70, 44, 53, 39, 0, 0, 0, 69, 57, 39,
- 0, 0, 67, 0, 71, 0, 18, 20, 99, 0,
- 0, 33, 34, 39, 38, 70, 0, 30, 50, 0,
- 0, 47, 46, 0, 43, 39, 70, 62, 0, 58,
- 0, 0, 0, 0, 0, 97, 96, 94, 37, 36,
- 0, 0, 84, 0, 81, 80, 0, 52, 61, 60,
- 0, 56, 0, 0, 0, 13, 98, 77, 51, 39,
- 79, 0, 0, 64, 78, 41, 0, 85, 0, 0,
- 49, 0, 63, 86, 82, 0, 87, 0, 0, 88,
- 0, 0, 89, 0, 0, 90, 83
+ 2, 22, 29, 28, 23, 24, 25, 26, 27, 3,
+ 4, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 1, 5, 0, 0, 0, 0, 0, 0, 0, 6,
+ 7, 0, 97, 0, 0, 0, 0, 0, 0, 0,
+ 0, 77, 0, 0, 0, 0, 0, 94, 8, 9,
+ 10, 11, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 14, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 67,
+ 55, 71, 0, 0, 0, 32, 31, 78, 72, 0,
+ 0, 17, 0, 21, 0, 95, 0, 0, 0, 39,
+ 0, 0, 45, 0, 0, 0, 75, 72, 0, 0,
+ 0, 0, 0, 66, 0, 0, 14, 12, 0, 0,
+ 19, 0, 93, 39, 0, 0, 0, 35, 0, 0,
+ 0, 0, 35, 54, 59, 0, 0, 0, 0, 69,
+ 39, 65, 0, 33, 34, 0, 39, 74, 76, 15,
+ 17, 16, 0, 0, 98, 40, 42, 0, 0, 0,
+ 0, 39, 48, 72, 44, 53, 39, 0, 0, 0,
+ 70, 57, 39, 0, 0, 68, 0, 0, 73, 18,
+ 20, 101, 0, 0, 39, 38, 72, 0, 30, 50,
+ 0, 0, 47, 46, 0, 43, 39, 72, 62, 0,
+ 58, 0, 0, 0, 13, 0, 99, 98, 96, 37,
+ 36, 0, 0, 86, 0, 83, 82, 0, 52, 61,
+ 60, 0, 56, 0, 0, 0, 100, 79, 51, 39,
+ 81, 0, 0, 64, 80, 41, 0, 87, 0, 0,
+ 49, 0, 63, 88, 84, 0, 89, 0, 0, 90,
+ 0, 0, 91, 0, 0, 92, 85
};
/* YYPGOTO[NTERM-NUM]. */
static const yytype_int16 yypgoto[] =
{
- -127, -127, -46, 6, -87, -50, -127, 83, 57, -127,
- 49, -127, -127, -127, -11, -127, -127, -127, 43, 71,
- -44, -126, -127, 168, 167, -127, -127, -127, -127, 152,
- -127, -127, -81, -56, -127, -127, -127, -127, -84, -127,
- -127, -127, -89, 106, -127, -127, -127, -127, -112, -127,
+ -127, -127, -53, 35, -71, -67, -127, 75, 53, -127,
+ 44, -127, -127, -127, -26, -127, -127, 98, 84, 63,
+ -126, -64, -127, 175, 176, -127, -127, -127, -127, 154,
+ -127, -127, -60, -63, -127, -127, -127, -127, -119, -127,
+ -127, -127, -127, -113, 102, -127, -127, -127, -127, -121,
-127, -127, -127, -127, -127, -127, -127, -127, -127, -127,
- -127, -127, -127, -127, -4, -127
+ -127, -127, -127, -127, -127, -6, -127
};
/* YYDEFGOTO[NTERM-NUM]. */
static const yytype_int16 yydefgoto[] =
{
- -1, 8, 20, 21, 39, 52, 53, 122, 87, 54,
- 114, 55, 56, 91, 9, 10, 11, 123, 124, 155,
- 121, 141, 75, 12, 42, 128, 99, 189, 229, 78,
- 163, 130, 82, 83, 169, 13, 166, 196, 137, 14,
- 107, 45, 109, 104, 15, 47, 85, 185, 138, 160,
- 213, 214, 215, 216, 238, 244, 247, 250, 253, 256,
- 16, 57, 93, 17, 180, 59
+ -1, 9, 21, 22, 42, 57, 58, 93, 100, 59,
+ 129, 60, 61, 104, 10, 11, 12, 94, 95, 168,
+ 136, 156, 82, 13, 45, 140, 112, 200, 239, 85,
+ 176, 142, 96, 90, 182, 14, 179, 207, 149, 15,
+ 120, 48, 50, 125, 117, 16, 52, 98, 196, 150,
+ 173, 224, 225, 226, 227, 248, 254, 257, 260, 263,
+ 266, 17, 62, 106, 18, 193, 64
};
/* YYTABLE[YYPACT[STATE-NUM]] -- What to do in state STATE-NUM. If
positive, shift that token. If negative, reduce the rule whose
number is the opposite. If YYTABLE_NINF, syntax error. */
-static const yytype_uint8 yytable[] =
+static const yytype_uint16 yytable[] =
{
- 112, 158, 115, 68, 69, 70, 117, 150, 22, 23,
- 24, 25, 26, 27, 81, 133, 125, 95, 88, 89,
- 139, 132, 143, 46, 142, 110, 28, 147, 183, 135,
- 135, 18, 19, 136, 152, 157, 151, 29, 30, 195,
- 140, 161, 186, 159, 2, 131, 167, 61, 135, 135,
- 64, 31, 136, 198, 67, 84, 36, 37, 140, 140,
- 92, 177, 178, 146, 72, 32, 148, 206, 187, 33,
- 184, 192, 182, 34, 149, 35, 41, 194, 44, 199,
- 96, 197, 58, 100, 36, 37, 38, 105, 48, 49,
- 50, 51, 74, 207, 172, 205, 209, 174, 227, 77,
- 60, 62, 63, 65, 126, 66, 217, 219, 232, 71,
- 73, 190, 76, 221, 191, 80, 144, 225, 81, 193,
- 90, 86, 94, 97, 98, 200, 230, 242, 101, 102,
- 103, 106, 108, 110, 113, 233, 234, 235, 136, 208,
- 116, 170, 171, 1, 119, 2, 173, 120, 127, 240,
- 3, 218, 4, 129, 5, 134, 135, 6, 7, 153,
- 154, 156, 162, 165, 168, 175, 179, 188, 145, 111,
- 204, 201, 202, 212, 222, 203, 224, 210, 211, 223,
- 220, 228, 231, 237, 243, 236, 239, 246, 241, 249,
- 252, 245, 248, 255, 251, 176, 181, 254, 40, 43,
- 118, 164, 226, 0, 0, 0, 0, 0, 0, 0,
- 0, 0, 0, 0, 0, 79
+ 91, 75, 76, 77, 145, 157, 88, 163, 101, 102,
+ 89, 51, 147, 164, 147, 147, 165, 108, 148, 92,
+ 172, 170, 147, 123, 185, 30, 155, 155, 148, 127,
+ 188, 130, 19, 20, 155, 132, 31, 23, 24, 25,
+ 26, 27, 28, 29, 32, 202, 197, 97, 195, 151,
+ 204, 143, 105, 33, 158, 144, 211, 209, 161, 208,
+ 203, 160, 154, 34, 162, 166, 39, 40, 219, 174,
+ 2, 217, 35, 216, 180, 171, 39, 40, 41, 66,
+ 229, 36, 69, 220, 71, 37, 38, 44, 74, 47,
+ 63, 190, 191, 49, 230, 65, 81, 198, 79, 67,
+ 237, 68, 70, 194, 72, 73, 205, 78, 210, 84,
+ 242, 80, 88, 246, 206, 214, 109, 201, 83, 113,
+ 87, 99, 218, 118, 103, 107, 110, 121, 252, 111,
+ 116, 114, 1, 228, 2, 53, 54, 55, 56, 3,
+ 232, 4, 5, 115, 119, 6, 138, 122, 7, 8,
+ 124, 128, 92, 240, 131, 134, 135, 139, 141, 146,
+ 148, 147, 243, 244, 245, 152, 167, 175, 169, 178,
+ 181, 186, 192, 199, 126, 250, 223, 238, 212, 159,
+ 213, 233, 183, 184, 215, 221, 222, 231, 234, 235,
+ 187, 241, 247, 253, 249, 251, 256, 255, 259, 262,
+ 258, 261, 265, 264, 189, 177, 153, 43, 137, 133,
+ 46, 236, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 86
};
static const yytype_int16 yycheck[] =
{
- 87, 127, 89, 49, 50, 51, 93, 119, 2, 3,
- 4, 5, 6, 7, 13, 104, 97, 73, 68, 69,
- 107, 102, 109, 34, 108, 24, 0, 114, 154, 15,
- 15, 29, 30, 19, 121, 20, 120, 26, 33, 165,
- 25, 128, 154, 127, 9, 101, 133, 41, 15, 15,
- 44, 33, 19, 165, 48, 66, 31, 32, 25, 25,
- 71, 148, 149, 113, 58, 33, 116, 179, 155, 33,
- 154, 160, 153, 33, 118, 33, 10, 164, 17, 166,
- 74, 165, 23, 77, 31, 32, 33, 81, 3, 4,
- 5, 6, 8, 180, 138, 179, 185, 141, 210, 12,
- 33, 33, 33, 33, 98, 33, 193, 196, 220, 33,
- 33, 157, 33, 200, 158, 33, 110, 204, 13, 163,
- 27, 33, 33, 33, 11, 169, 213, 239, 33, 33,
- 27, 33, 33, 24, 33, 222, 223, 224, 19, 183,
- 33, 135, 136, 7, 33, 9, 140, 33, 33, 236,
- 14, 195, 16, 33, 18, 33, 15, 21, 22, 33,
- 33, 33, 27, 33, 27, 33, 33, 27, 111, 86,
- 27, 33, 33, 27, 26, 33, 26, 33, 33, 28,
- 33, 27, 33, 27, 27, 229, 33, 27, 33, 27,
- 27, 33, 33, 27, 33, 146, 153, 33, 30, 32,
- 94, 130, 206, -1, -1, -1, -1, -1, -1, -1,
- -1, -1, -1, -1, -1, 63
+ 71, 54, 55, 56, 117, 124, 13, 133, 75, 76,
+ 70, 37, 15, 134, 15, 15, 135, 80, 21, 26,
+ 139, 22, 15, 94, 150, 0, 27, 27, 21, 100,
+ 156, 102, 31, 32, 27, 106, 28, 2, 3, 4,
+ 5, 6, 7, 8, 35, 171, 167, 73, 167, 120,
+ 176, 114, 78, 35, 125, 115, 182, 178, 129, 178,
+ 173, 128, 122, 35, 131, 136, 33, 34, 194, 140,
+ 9, 192, 35, 192, 145, 139, 33, 34, 35, 44,
+ 206, 35, 47, 196, 49, 35, 35, 10, 53, 18,
+ 25, 162, 163, 19, 207, 35, 8, 168, 63, 35,
+ 221, 35, 35, 167, 35, 35, 177, 35, 179, 12,
+ 231, 35, 13, 239, 178, 186, 81, 170, 35, 84,
+ 35, 35, 193, 88, 29, 35, 35, 92, 249, 11,
+ 29, 35, 7, 204, 9, 3, 4, 5, 6, 14,
+ 211, 16, 17, 35, 35, 20, 111, 35, 23, 24,
+ 35, 35, 26, 224, 35, 35, 35, 35, 35, 35,
+ 21, 15, 233, 234, 235, 35, 35, 29, 35, 35,
+ 29, 29, 35, 29, 99, 246, 29, 29, 35, 126,
+ 35, 28, 147, 148, 35, 35, 35, 35, 30, 28,
+ 155, 35, 29, 29, 35, 35, 29, 35, 29, 29,
+ 35, 35, 29, 35, 160, 142, 122, 32, 110, 107,
+ 34, 217, -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, 68
};
/* YYSTOS[STATE-NUM] -- The (internal number of the) accessing
symbol of state STATE-NUM. */
static const yytype_uint8 yystos[] =
{
- 0, 7, 9, 14, 16, 18, 21, 22, 35, 48,
- 49, 50, 57, 69, 73, 78, 94, 97, 29, 30,
- 36, 37, 37, 37, 37, 37, 37, 37, 0, 26,
- 33, 33, 33, 33, 33, 33, 31, 32, 33, 38,
- 57, 10, 58, 58, 17, 75, 48, 79, 3, 4,
- 5, 6, 39, 40, 43, 45, 46, 95, 23, 99,
- 33, 37, 33, 33, 37, 33, 33, 37, 36, 36,
- 36, 33, 37, 33, 8, 56, 33, 12, 63, 63,
- 33, 13, 66, 67, 48, 80, 33, 42, 39, 39,
- 27, 47, 48, 96, 33, 67, 37, 33, 11, 60,
- 37, 33, 33, 27, 77, 37, 33, 74, 33, 76,
- 24, 41, 38, 33, 44, 38, 33, 38, 77, 33,
- 33, 54, 41, 51, 52, 66, 37, 33, 59, 33,
- 65, 67, 66, 76, 33, 15, 19, 72, 82, 38,
- 25, 55, 72, 38, 37, 42, 39, 38, 39, 54,
- 82, 72, 38, 33, 33, 53, 33, 20, 55, 72,
- 83, 38, 27, 64, 53, 33, 70, 38, 27, 68,
- 37, 37, 54, 37, 54, 33, 44, 38, 38, 33,
- 98, 52, 66, 55, 72, 81, 82, 38, 27, 61,
- 36, 54, 76, 54, 38, 55, 71, 72, 82, 38,
- 54, 33, 33, 33, 27, 72, 82, 38, 54, 76,
- 33, 33, 27, 84, 85, 86, 87, 38, 54, 76,
- 33, 38, 26, 28, 26, 38, 98, 82, 27, 62,
- 38, 33, 82, 38, 38, 38, 54, 27, 88, 33,
- 38, 33, 82, 27, 89, 33, 27, 90, 33, 27,
- 91, 33, 27, 92, 33, 27, 93
+ 0, 7, 9, 14, 16, 17, 20, 23, 24, 37,
+ 50, 51, 52, 59, 71, 75, 81, 97, 100, 31,
+ 32, 38, 39, 39, 39, 39, 39, 39, 39, 39,
+ 0, 28, 35, 35, 35, 35, 35, 35, 35, 33,
+ 34, 35, 40, 59, 10, 60, 60, 18, 77, 19,
+ 78, 50, 82, 3, 4, 5, 6, 41, 42, 45,
+ 47, 48, 98, 25, 102, 35, 39, 35, 35, 39,
+ 35, 39, 35, 35, 39, 38, 38, 38, 35, 39,
+ 35, 8, 58, 35, 12, 65, 65, 35, 13, 68,
+ 69, 40, 26, 43, 53, 54, 68, 50, 83, 35,
+ 44, 41, 41, 29, 49, 50, 99, 35, 69, 39,
+ 35, 11, 62, 39, 35, 35, 29, 80, 39, 35,
+ 76, 39, 35, 40, 35, 79, 43, 40, 35, 46,
+ 40, 35, 40, 80, 35, 35, 56, 53, 39, 35,
+ 61, 35, 67, 69, 68, 79, 35, 15, 21, 74,
+ 85, 40, 35, 54, 68, 27, 57, 74, 40, 44,
+ 41, 40, 41, 56, 85, 74, 40, 35, 55, 35,
+ 22, 57, 74, 86, 40, 29, 66, 55, 35, 72,
+ 40, 29, 70, 39, 39, 56, 29, 39, 56, 46,
+ 40, 40, 35, 101, 57, 74, 84, 85, 40, 29,
+ 63, 38, 56, 79, 56, 40, 57, 73, 74, 85,
+ 40, 56, 35, 35, 40, 35, 74, 85, 40, 56,
+ 79, 35, 35, 29, 87, 88, 89, 90, 40, 56,
+ 79, 35, 40, 28, 30, 28, 101, 85, 29, 64,
+ 40, 35, 85, 40, 40, 40, 56, 29, 91, 35,
+ 40, 35, 85, 29, 92, 35, 29, 93, 35, 29,
+ 94, 35, 29, 95, 35, 29, 96
};
/* YYR1[YYN] -- Symbol number of symbol that rule YYN derives. */
static const yytype_uint8 yyr1[] =
{
- 0, 34, 35, 36, 36, 37, 38, 38, 39, 39,
- 39, 39, 40, 41, 42, 42, 43, 44, 44, 45,
- 46, 47, 48, 48, 48, 48, 48, 48, 49, 49,
- 50, 51, 51, 52, 52, 53, 53, 53, 53, 54,
- 54, 55, 56, 57, 58, 59, 59, 59, 59, 60,
- 61, 62, 63, 64, 65, 66, 67, 68, 69, 70,
- 70, 70, 70, 71, 72, 73, 74, 74, 74, 75,
- 76, 76, 76, 77, 78, 79, 80, 81, 82, 83,
- 84, 84, 85, 86, 87, 88, 89, 90, 91, 92,
- 93, 94, 95, 96, 97, 97, 98, 98, 98, 99
+ 0, 36, 37, 38, 38, 39, 40, 40, 41, 41,
+ 41, 41, 42, 43, 44, 44, 45, 46, 46, 47,
+ 48, 49, 50, 50, 50, 50, 50, 50, 51, 51,
+ 52, 53, 53, 54, 54, 55, 55, 55, 55, 56,
+ 56, 57, 58, 59, 60, 61, 61, 61, 61, 62,
+ 63, 64, 65, 66, 67, 68, 69, 70, 71, 72,
+ 72, 72, 72, 73, 74, 75, 75, 76, 76, 76,
+ 77, 78, 79, 79, 79, 80, 81, 82, 83, 84,
+ 85, 86, 87, 87, 88, 89, 90, 91, 92, 93,
+ 94, 95, 96, 97, 98, 99, 100, 100, 101, 101,
+ 101, 102
};
/* YYR2[YYN] -- Number of symbols on the right hand side of rule YYN. */
@@ -746,10 +757,11 @@ static const yytype_uint8 yyr2[] =
10, 1, 1, 3, 3, 0, 3, 3, 2, 0,
2, 5, 4, 10, 6, 0, 3, 3, 2, 8,
1, 1, 6, 1, 1, 1, 6, 1, 10, 0,
- 3, 3, 2, 5, 5, 8, 0, 3, 2, 6,
- 0, 3, 2, 1, 8, 1, 1, 3, 5, 4,
- 1, 1, 5, 13, 1, 1, 1, 1, 1, 1,
- 1, 7, 1, 1, 10, 3, 0, 2, 3, 6
+ 3, 3, 2, 5, 5, 8, 7, 0, 3, 2,
+ 6, 3, 0, 3, 2, 1, 8, 1, 1, 3,
+ 5, 4, 1, 1, 5, 13, 1, 1, 1, 1,
+ 1, 1, 1, 7, 1, 1, 10, 3, 0, 2,
+ 3, 6
};
diff --git a/src/wkt1_generated_parser.h b/src/wkt1_generated_parser.h
index 989f1f32..53180dec 100644
--- a/src/wkt1_generated_parser.h
+++ b/src/wkt1_generated_parser.h
@@ -60,18 +60,20 @@ extern int pj_wkt1_debug;
T_GEOCCS = 269,
T_AUTHORITY = 270,
T_VERT_CS = 271,
- T_VERT_DATUM = 272,
- T_COMPD_CS = 273,
- T_AXIS = 274,
- T_TOWGS84 = 275,
- T_FITTED_CS = 276,
- T_LOCAL_CS = 277,
- T_LOCAL_DATUM = 278,
- T_PARAMETER = 279,
- T_EXTENSION = 280,
- T_STRING = 281,
- T_NUMBER = 282,
- T_IDENTIFIER = 283
+ T_VERTCS = 272,
+ T_VERT_DATUM = 273,
+ T_VDATUM = 274,
+ T_COMPD_CS = 275,
+ T_AXIS = 276,
+ T_TOWGS84 = 277,
+ T_FITTED_CS = 278,
+ T_LOCAL_CS = 279,
+ T_LOCAL_DATUM = 280,
+ T_PARAMETER = 281,
+ T_EXTENSION = 282,
+ T_STRING = 283,
+ T_NUMBER = 284,
+ T_IDENTIFIER = 285
};
#endif
diff --git a/src/wkt1_grammar.y b/src/wkt1_grammar.y
index 28ff7a6e..e17135c6 100644
--- a/src/wkt1_grammar.y
+++ b/src/wkt1_grammar.y
@@ -53,7 +53,11 @@
%token T_GEOCCS "GEOCCS"
%token T_AUTHORITY "AUTHORITY"
%token T_VERT_CS "VERT_CS"
+// ESRI variation
+%token T_VERTCS "VERTCS"
%token T_VERT_DATUM "VERT_DATUM"
+// ESRI variation
+%token T_VDATUM "VDATUM"
%token T_COMPD_CS "COMPD_CS"
%token T_AXIS "AXIS"
%token T_TOWGS84 "TOWGS84"
@@ -213,6 +217,7 @@ authority:
vert_cs:
T_VERT_CS begin_node_name ',' vert_datum ',' linear_unit opt_axis_authority end_node
+ | T_VERTCS begin_node_name ',' vdatum ',' opt_parameter_list_linear_unit end_node
opt_axis_authority:
| ',' axis opt_authority
@@ -221,6 +226,9 @@ opt_axis_authority:
vert_datum:
T_VERT_DATUM begin_node_name ',' datum_type opt_extension_authority end_node
+vdatum:
+ T_VDATUM begin_node_name end_node
+
opt_extension_authority:
| ',' extension opt_authority
| ',' authority
diff --git a/src/wkt1_parser.cpp b/src/wkt1_parser.cpp
index 9db7d4bd..5aa898b1 100644
--- a/src/wkt1_parser.cpp
+++ b/src/wkt1_parser.cpp
@@ -81,7 +81,12 @@ static const osr_cs_wkt_tokens tokens[] = {
PAIR(PROJCS), PAIR(PROJECTION), PAIR(GEOGCS), PAIR(DATUM),
PAIR(SPHEROID), PAIR(PRIMEM), PAIR(UNIT), PAIR(GEOCCS),
- PAIR(AUTHORITY), PAIR(VERT_CS), PAIR(VERT_DATUM), PAIR(COMPD_CS),
+ PAIR(AUTHORITY),
+ PAIR(VERT_CS),
+ PAIR(VERTCS),
+ PAIR(VERT_DATUM),
+ PAIR(VDATUM),
+ PAIR(COMPD_CS),
PAIR(AXIS), PAIR(TOWGS84), PAIR(FITTED_CS), PAIR(LOCAL_CS),
PAIR(LOCAL_DATUM),
diff --git a/test/unit/test_crs.cpp b/test/unit/test_crs.cpp
index c988080b..6ab60270 100644
--- a/test/unit/test_crs.cpp
+++ b/test/unit/test_crs.cpp
@@ -3157,6 +3157,36 @@ TEST(crs, verticalCRS_as_WKT1_GDAL) {
// ---------------------------------------------------------------------------
+TEST(crs, verticalCRS_as_WKT1_ESRI) {
+ auto crs = createVerticalCRS();
+ auto expected = "VERTCS[\"ODN height\",VDATUM[\"Ordnance Datum Newlyn\"],"
+ "PARAMETER[\"Vertical_Shift\",0.0],"
+ "PARAMETER[\"Direction\",1.0],"
+ "UNIT[\"Meter\",1.0]]";
+
+ EXPECT_EQ(
+ crs->exportToWKT(
+ WKTFormatter::create(WKTFormatter::Convention::WKT1_ESRI).get()),
+ expected);
+}
+// ---------------------------------------------------------------------------
+
+TEST(crs, verticalCRS_down_as_WKT1_ESRI) {
+ auto wkt = "VERTCS[\"Caspian\",VDATUM[\"Caspian_Sea\"],"
+ "PARAMETER[\"Vertical_Shift\",0.0],"
+ "PARAMETER[\"Direction\",-1.0],UNIT[\"Meter\",1.0]]";
+
+ auto obj = WKTParser().createFromWKT(wkt);
+ auto crs = nn_dynamic_pointer_cast<VerticalCRS>(obj);
+ ASSERT_TRUE(crs != nullptr);
+ EXPECT_EQ(
+ crs->exportToWKT(
+ WKTFormatter::create(WKTFormatter::Convention::WKT1_ESRI).get()),
+ wkt);
+}
+
+// ---------------------------------------------------------------------------
+
TEST(crs, verticalCRS_identify_db) {
auto dbContext = DatabaseContext::create();
auto factory = AuthorityFactory::create(dbContext, "EPSG");
diff --git a/test/unit/test_io.cpp b/test/unit/test_io.cpp
index 581083b3..767c39e9 100644
--- a/test/unit/test_io.cpp
+++ b/test/unit/test_io.cpp
@@ -2061,6 +2061,45 @@ TEST(wkt_parse, vertcrs_WKT1_GDAL_minimum) {
// ---------------------------------------------------------------------------
+TEST(wkt_parse, VERTCS_WKT1_ESRI) {
+ auto wkt = "VERTCS[\"EGM2008_Geoid\",VDATUM[\"EGM2008_Geoid\"],"
+ "PARAMETER[\"Vertical_Shift\",0.0],"
+ "PARAMETER[\"Direction\",1.0],UNIT[\"Meter\",1.0]]";
+
+ auto obj = WKTParser().createFromWKT(wkt);
+ auto crs = nn_dynamic_pointer_cast<VerticalCRS>(obj);
+ ASSERT_TRUE(crs != nullptr);
+ EXPECT_EQ(crs->nameStr(), "EGM2008_Geoid");
+
+ auto datum = crs->datum();
+ EXPECT_EQ(datum->nameStr(), "EGM2008_Geoid");
+
+ auto cs = crs->coordinateSystem();
+ ASSERT_EQ(cs->axisList().size(), 1U);
+ EXPECT_EQ(cs->axisList()[0]->direction(), AxisDirection::UP);
+
+ EXPECT_EQ(WKTParser().guessDialect(wkt),
+ WKTParser::WKTGuessedDialect::WKT1_ESRI);
+}
+
+// ---------------------------------------------------------------------------
+
+TEST(wkt_parse, VERTCS_WKT1_ESRI_down) {
+ auto wkt = "VERTCS[\"Caspian\",VDATUM[\"Caspian_Sea\"],"
+ "PARAMETER[\"Vertical_Shift\",0.0],"
+ "PARAMETER[\"Direction\",-1.0],UNIT[\"Meter\",1.0]]";
+
+ auto obj = WKTParser().createFromWKT(wkt);
+ auto crs = nn_dynamic_pointer_cast<VerticalCRS>(obj);
+ ASSERT_TRUE(crs != nullptr);
+
+ auto cs = crs->coordinateSystem();
+ ASSERT_EQ(cs->axisList().size(), 1U);
+ EXPECT_EQ(cs->axisList()[0]->direction(), AxisDirection::DOWN);
+}
+
+// ---------------------------------------------------------------------------
+
TEST(wkt_parse, vertcrs_WKT1_LAS_ftUS) {
auto wkt = "VERT_CS[\"NAVD88 - Geoid03 (Feet)\","
" VERT_DATUM[\"unknown\",2005],"