Ben,
the general plan if we wanted to introduce support for
DerivedProjectedCRS in the database is sound, but I still don't think
that using that concept for polyhedral projections with a face
identifier is ISO-19111 compliant. AFAICS, there is no Coordinate System
subclass that allows mixing linear axis (X,Y) and an ordinal one (face
number). In particular a Cartesian CS is "a coordinate system in
Euclidean space which gives the position of points relative to n
mutually perpendicular straight axes all having the same unit of measure".
Even
Le 27/03/2026 à 12:13, Ben Griffin via PROJ a écrit :
Hi all,
Following the earlier thread on face/octant coordinates and the UTM zone
analogy, I've been investigating whether DERIVEDPROJCRS could be used to
formally express planar net projections as derived from intermediate
octahedral ProjectedCRS.
In doing so I found that the C++ side is already largely in place — the object
model, WKT parser, and operation factory all handle DerivedProjectedCRS
correctly.
The operation factory catches via the DerivedCRS* cast and routes through
createOperationsDerivedTo, so WGS84 → ProjectedCRS → derivedProjectedCRS chains
already work when the CRS is constructed programmatically or from inline WKT.
The gap, as I understand it, is purely in the database layer:
1. There is no derived_projected_crs table in proj.db / user.db
2. crs_view has no entry for this type, so authority-code lookup fails
3. createCoordinateReferenceSystem() has no dispatch for the type
4. createProjectedCRSEnd() throws a generic error if text_definition contains a
DERIVEDPROJCRS WKT
I my thought is to offer a fix that is additive and non-breaking:
A new derived_projected_crs table (FK to projected_crs as base, consistent with
ISO 19111's restriction that the base must be a ProjectedCRS);
A new type “derived projected” in crs_view;
A new createDerivedProjectedCRS() factory method;
And a clearer error message, with the existing text_definition path pointing
users to the new derived_projected_crs table.
Use Cases (there may be others)
* Polyhedral projections, where a face index is a necessary part of the
coordinate — analogous to a UTM zone number.
The intermediate ProjectedCRS could carry the ellipsoid relationship and the
face identifier; the DerivedProjectedCRS consumes both and produces a globally
unambiguous planar coordinate. PROJ already includes several polyhedral
projections (ISEA, HEALPix) where this two-layer architecture might be the
correct formal expression. Any future polyhedral work (such as my own project!)
would benefit from the same foundation.
* Datum-agnostic net/tile projections — a butterfly net derived from an
octahedral CRS that is itself derived from ED50 rather than WGS84 is just a
different base ProjectedCRS. The net definition doesn't change. Currently we
are expected to register a separate CRS for each datum combination.
* Rotated or recentred projections — a Transverse Mercator variant recentred on
a local origin, expressed as derived from a standard TM ProjectedCRS, rather
than as a fresh projection from the ellipsoid. The datum relationship is
inherited, not repeated.
In brief, and as I understand it, the ISO 19111:2019 defines
DerivedProjectedCRS as a first-class CRS type, and PROJ's C++ object model
reflects this faithfully. However without database registration support, the
type cannot be used in the authority-code workflows that most users depend on —
making it effectively unavailable in practice.
I have started to compose a PR against master in order to close this gap, but I
felt it wise to check in: is there anything architecturally that would make
this unwelcome, or any prior discussion I should be aware of, or does the plan
sound reasonable?
=== Affected files ===
** SQL (data/sql)
proj_db_table_defs.sql : derived_projected_crs table; extend crs_view.
consistency_checks_triggers.sql : Duplicate preventions (2) on crs_view, insert
rejections (coordinate_system not found, base_crs not found)
** src/iso19111/factory.cpp
Add #define DERIVED_PROJECTED "derived projected”
Add functions to support DerivedProjectedCRS
Modify createCoordinateReferenceSystem, createObject, createProjectedCRSEnd to
support DerivedProjectedCRS
** Public API
include/proj/io.hpp
public `createDerivedProjectedCRS(const std::string &code)` on
`AuthorityFactory`
** C API
src/iso19111/c_api.cpp
Wire authority-code lookup in `proj_create_derived_projected_crs()` to use
`createDerivedProjectedCRS()`
** Tests
test/unit/test_factory.cpp createDerivedProjectedCRS,
createCoordinateReferenceSystem,
`text_definition` : `projected_crs` containing `DERIVEDPROJCRS` WKT gives
directed error
`text_definition` in `derived_projected_crs` round-trips correctly
`cs2cs`-equivalent pipeline resolves end-to-end for a registered
`DerivedProjectedCRS`
** No change
No need to modify the wkt2 grammar/parser, iso19111 io, operations, crs, or
their test frameworks.
Best regards
-Ben
_______________________________________________
PROJ mailing list
[email protected]
https://lists.osgeo.org/mailman/listinfo/proj
--
http://www.spatialys.com
My software is free, but my time generally not.
_______________________________________________
PROJ mailing list
[email protected]
https://lists.osgeo.org/mailman/listinfo/proj