aboutsummaryrefslogtreecommitdiff
path: root/src/4D_api.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/4D_api.cpp')
-rw-r--r--src/4D_api.cpp146
1 files changed, 87 insertions, 59 deletions
diff --git a/src/4D_api.cpp b/src/4D_api.cpp
index ba292262..710b59e3 100644
--- a/src/4D_api.cpp
+++ b/src/4D_api.cpp
@@ -27,6 +27,8 @@
* DEALINGS IN THE SOFTWARE.
*****************************************************************************/
+#define FROM_PROJ_CPP
+
#include <errno.h>
#include <stddef.h>
#include <stdio.h>
@@ -44,7 +46,9 @@
#include "proj/common.hpp"
#include "proj/coordinateoperation.hpp"
+#include "proj/internal/internal.hpp"
+using namespace NS_PROJ::internal;
/* Initialize PJ_COORD struct */
PJ_COORD proj_coord (double x, double y, double z, double t) {
@@ -726,6 +730,20 @@ int proj_context_get_use_proj4_init_rules(PJ_CONTEXT *ctx, int from_legacy_code_
return from_legacy_code_path;
}
+/** Adds a " +type=crs" suffix to a PROJ string (if it is a PROJ string) */
+std::string pj_add_type_crs_if_needed(const std::string& str)
+{
+ std::string ret(str);
+ if( (starts_with(str, "proj=") ||
+ starts_with(str, "+proj=") ||
+ starts_with(str, "+init=") ||
+ starts_with(str, "+title=")) &&
+ str.find("type=crs") == std::string::npos )
+ {
+ ret += " +type=crs";
+ }
+ return ret;
+}
/*****************************************************************************/
PJ *proj_create_crs_to_crs (PJ_CONTEXT *ctx, const char *source_crs, const char *target_crs, PJ_AREA *area) {
@@ -763,79 +781,89 @@ PJ *proj_create_crs_to_crs (PJ_CONTEXT *ctx, const char *source_crs, const char
const char* const* optionsImportCRS =
proj_context_get_use_proj4_init_rules(ctx, FALSE) ? optionsProj4Mode : nullptr;
- auto src = proj_create_from_user_input(ctx, source_crs, optionsImportCRS);
- if( !src ) {
- proj_context_log_debug(ctx, "Cannot instantiate source_crs");
- return nullptr;
- }
+ try
+ {
+ std::string source_crs_modified(pj_add_type_crs_if_needed(source_crs));
+ std::string target_crs_modified(pj_add_type_crs_if_needed(target_crs));
- auto dst = proj_create_from_user_input(ctx, target_crs, optionsImportCRS);
- if( !dst ) {
- proj_context_log_debug(ctx, "Cannot instantiate target_crs");
- proj_destroy(src);
- return nullptr;
- }
+ auto src = proj_create_from_user_input(ctx, source_crs_modified.c_str(), optionsImportCRS);
+ if( !src ) {
+ proj_context_log_debug(ctx, "Cannot instantiate source_crs");
+ return nullptr;
+ }
- auto operation_ctx = proj_create_operation_factory_context(ctx, nullptr);
- if( !operation_ctx ) {
- proj_destroy(src);
- proj_destroy(dst);
- return nullptr;
- }
+ auto dst = proj_create_from_user_input(ctx, target_crs_modified.c_str(), optionsImportCRS);
+ if( !dst ) {
+ proj_context_log_debug(ctx, "Cannot instantiate target_crs");
+ proj_destroy(src);
+ return nullptr;
+ }
- if( area && area->bbox_set ) {
- proj_operation_factory_context_set_area_of_interest(
- ctx,
- operation_ctx,
- area->west_lon_degree,
- area->south_lat_degree,
- area->east_lon_degree,
- area->north_lat_degree);
- }
+ auto operation_ctx = proj_create_operation_factory_context(ctx, nullptr);
+ if( !operation_ctx ) {
+ proj_destroy(src);
+ proj_destroy(dst);
+ return nullptr;
+ }
- proj_operation_factory_context_set_grid_availability_use(
- ctx, operation_ctx, PROJ_GRID_AVAILABILITY_DISCARD_OPERATION_IF_MISSING_GRID);
+ if( area && area->bbox_set ) {
+ proj_operation_factory_context_set_area_of_interest(
+ ctx,
+ operation_ctx,
+ area->west_lon_degree,
+ area->south_lat_degree,
+ area->east_lon_degree,
+ area->north_lat_degree);
+ }
- auto op_list = proj_create_operations(ctx, src, dst, operation_ctx);
+ proj_operation_factory_context_set_grid_availability_use(
+ ctx, operation_ctx, PROJ_GRID_AVAILABILITY_DISCARD_OPERATION_IF_MISSING_GRID);
- proj_operation_factory_context_destroy(operation_ctx);
- proj_destroy(src);
- proj_destroy(dst);
+ auto op_list = proj_create_operations(ctx, src, dst, operation_ctx);
- if( !op_list ) {
- return nullptr;
- }
+ proj_operation_factory_context_destroy(operation_ctx);
+ proj_destroy(src);
+ proj_destroy(dst);
- if( proj_list_get_count(op_list) == 0 ) {
+ if( !op_list ) {
+ return nullptr;
+ }
+
+ if( proj_list_get_count(op_list) == 0 ) {
+ proj_list_destroy(op_list);
+ proj_context_log_debug(ctx, "No operation found matching criteria");
+ return nullptr;
+ }
+
+ auto op = proj_list_get(ctx, op_list, 0);
proj_list_destroy(op_list);
- proj_context_log_debug(ctx, "No operation found matching criteria");
- return nullptr;
- }
+ if( !op ) {
+ return nullptr;
+ }
- auto op = proj_list_get(ctx, op_list, 0);
- proj_list_destroy(op_list);
- if( !op ) {
- return nullptr;
- }
+ proj_string = proj_as_proj_string(ctx, op, PJ_PROJ_5, nullptr);
+ if( !proj_string) {
+ proj_destroy(op);
+ proj_context_log_debug(ctx, "Cannot export operation as a PROJ string");
+ return nullptr;
+ }
+
+ PJ* P;
+ if( proj_string[0] == '\0' ) {
+ /* Null transform ? */
+ P = proj_create(ctx, "proj=affine");
+ } else {
+ P = proj_create(ctx, proj_string);
+ }
- proj_string = proj_as_proj_string(ctx, op, PJ_PROJ_5, nullptr);
- if( !proj_string) {
proj_destroy(op);
- proj_context_log_debug(ctx, "Cannot export operation as a PROJ string");
- return nullptr;
- }
- PJ* P;
- if( proj_string[0] == '\0' ) {
- /* Null transform ? */
- P = proj_create(ctx, "proj=affine");
- } else {
- P = proj_create(ctx, proj_string);
+ return P;
+ }
+ catch( const std::exception& )
+ {
+ return nullptr;
}
-
- proj_destroy(op);
-
- return P;
}
PJ *proj_destroy (PJ *P) {