Hi Wes,
thanks for the detailed example.
The cct commands you provided use an explicit PROJ pipeline
(+proj=pipeline +step ...), which represents a transformation object
rather than a CRS definition. This works as expected in cct because it
directly creates and executes the pipeline via proj_create().
In contrast, las2las currently operates in a CRS-to-CRS model,
using CRS objects. Parameters like proj_string, proj_epsg, proj_wkt, and
proj_json are interpreted as CRS definitions, not executable
transformation pipelines. As a result, explicit pipeline steps such as
vgridshift with a manually specified grid cannot be expressed or
enforced through these interfaces.
This also explains the warning and error you get:
SERIOUS WARNING: The WKT representation could not be generated...
ERROR: Failed to create PROJ object for the transformation...
Internally, the PROJ C-API call proj_as_wkt(proj_ctx, proj_crs, ...)
fails because it expects a CRS object. A pipeline does not have a WKT
representation, and PROJ cannot serialize a transformation as a CRS.
Consequently, proj_create_crs_to_crs_from_pj() also fails, because it
requires proper CRS objects on both sides. EPSG- or CRS-based strings
work because they define actual CRS objects, allowing PROJ to resolve
transformations implicitly. Explicit pipeline control is outside the
current scope of LAStools PROJ integration, which is why such pipelines
cannot be mapped 1:1 to a proj_string.
We hope this helps you to understand the situation,
Cheers,
Jochen @rapidlasso