aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/PJ_pipeline.c135
-rw-r--r--src/pj_internal.c15
-rw-r--r--src/proj_4D_api.c1
-rw-r--r--src/proj_internal.h2
-rw-r--r--src/projects.h1
5 files changed, 38 insertions, 116 deletions
diff --git a/src/PJ_pipeline.c b/src/PJ_pipeline.c
index b60105bf..73e15174 100644
--- a/src/PJ_pipeline.c
+++ b/src/PJ_pipeline.c
@@ -107,22 +107,17 @@ Thomas Knudsen, thokn@sdfe.dk, 2016-05-20
PROJ_HEAD(pipeline, "Transformation pipeline manager");
/* Projection specific elements for the PJ object */
-#define PIPELINE_STACK_SIZE 100
struct pj_opaque {
int reversible;
int steps;
- int depth;
int verbose;
- int *reverse_step;
- int *omit_forward;
- int *omit_inverse;
char **argv;
char **current_argv;
- PJ_OBS stack[PIPELINE_STACK_SIZE];
PJ **pipeline;
};
+
static PJ_OBS pipeline_forward_obs (PJ_OBS, PJ *P);
static PJ_OBS pipeline_reverse_obs (PJ_OBS, PJ *P);
static XYZ pipeline_forward_3d (LPZ lpz, PJ *P);
@@ -185,50 +180,23 @@ static PJ_OBS pipeline_forward_obs (PJ_OBS point, PJ *P) {
first_step = 1;
last_step = P->opaque->steps + 1;
- for (i = first_step; i != last_step; i++) {
- proj_log_trace (P, "In[%2.2d]: %20.15g %20.15g %20.15g - %20.20s",
- i-first_step, point.coo.xyz.x, point.coo.xyz.y, point.coo.xyz.z,
- P->opaque->pipeline[i]->descr
- );
+ for (i = first_step; i != last_step; i++)
+ point = proj_trans_obs (P->opaque->pipeline[i], 1, point);
- if (P->opaque->omit_forward[i])
- continue;
- if (P->opaque->reverse_step[i])
- point = proj_trans_obs (P->opaque->pipeline[i], PJ_INV, point);
- else
- point = proj_trans_obs (P->opaque->pipeline[i], PJ_FWD, point);
- if (P->opaque->depth < PIPELINE_STACK_SIZE)
- P->opaque->stack[P->opaque->depth++] = point;
- }
- proj_log_trace (P, "Out[ ]: %20.15g %20.15g %20.15g", point.coo.xyz.x, point.coo.xyz.y, point.coo.xyz.z);
-
- P->opaque->depth = 0; /* Clear the stack */
return point;
}
+
static PJ_OBS pipeline_reverse_obs (PJ_OBS point, PJ *P) {
int i, first_step, last_step;
first_step = P->opaque->steps;
last_step = 0;
- for (i = first_step; i != last_step; i--) {
- proj_log_trace (P, "In[%2.2d]: %20.15g %20.15g %20.15g - %.4f %.4f",
- i - 1, point.coo.xyz.x, point.coo.xyz.y, point.coo.xyz.z,
- P->opaque->pipeline[i]->a, P->opaque->pipeline[i]->rf
- );
- if (P->opaque->omit_inverse[i])
- continue;
- if (P->opaque->reverse_step[i])
- point = proj_trans_obs (P->opaque->pipeline[i], PJ_FWD, point);
- else
- point = proj_trans_obs (P->opaque->pipeline[i], PJ_INV, point);
- if (P->opaque->depth < PIPELINE_STACK_SIZE)
- P->opaque->stack[P->opaque->depth++] = point;
- }
- proj_log_trace (P, "Out[ ]: %20.15g %20.15g %20.15g", point.coo.xyz.x, point.coo.xyz.y, point.coo.xyz.z);
- P->opaque->depth = 0; /* Clear the stack */
+ for (i = first_step; i != last_step; i--)
+ point = proj_trans_obs (P->opaque->pipeline[i], -1, point);
+
return point;
}
@@ -279,9 +247,6 @@ static void *destructor (PJ *P, int errlev) {
P->opaque->pipeline[i+1]->destructor (P->opaque->pipeline[i+1], errlev);
pj_dealloc (P->opaque->pipeline);
- pj_dealloc (P->opaque->reverse_step);
- pj_dealloc (P->opaque->omit_forward);
- pj_dealloc (P->opaque->omit_inverse);
pj_dealloc (P->opaque->argv);
pj_dealloc (P->opaque->current_argv);
@@ -298,18 +263,6 @@ static PJ *pj_create_pipeline (PJ *P, size_t steps) {
P->opaque->steps = (int)steps;
- P->opaque->reverse_step = pj_calloc (steps + 2, sizeof(int));
- if (0==P->opaque->reverse_step)
- return 0;
-
- P->opaque->omit_forward = pj_calloc (steps + 2, sizeof(int));
- if (0==P->opaque->omit_forward)
- return 0;
-
- P->opaque->omit_inverse = pj_calloc (steps + 2, sizeof(int));
- if (0==P->opaque->omit_inverse)
- return 0;
-
return P;
}
@@ -339,6 +292,7 @@ static char **argv_params (paralist *params, size_t argc) {
}
+
PJ *PROJECTION(pipeline) {
int i, nsteps = 0, argc;
int i_pipeline = -1, i_first_step = -1, i_current_step;
@@ -418,84 +372,35 @@ PJ *PROJECTION(pipeline) {
for (j = i_pipeline + 1; 0 != strcmp ("step", argv[j]); j++)
current_argv[current_argc++] = argv[j];
- /* Finally handle non-symmetric steps and inverted steps */
- for (j = 0; j < current_argc; j++) {
- if (0==strcmp("omit_inv", current_argv[j])) {
- P->opaque->omit_inverse[i+1] = 1;
- P->opaque->omit_forward[i+1] = 0;
- }
- if (0==strcmp("omit_fwd", current_argv[j])) {
- P->opaque->omit_inverse[i+1] = 0;
- P->opaque->omit_forward[i+1] = 1;
- }
- if (0==strcmp("inv", current_argv[j]))
- P->opaque->reverse_step[i+1] = 1;
- }
-
proj_log_trace (P, "Pipeline: init - %s, %d", current_argv[0], current_argc);
for (j = 1; j < current_argc; j++)
proj_log_trace (P, " %s", current_argv[j]);
next_step = pj_init_ctx (P->ctx, current_argc, current_argv);
+
proj_log_trace (P, "Pipeline: Step %d at %p", i, next_step);
if (0==next_step) {
proj_log_error (P, "Pipeline: Bad step definition: %s", current_argv[0]);
return destructor (P, PJD_ERR_MALFORMED_PIPELINE); /* ERROR: bad pipeline def */
}
+
+ /* Is this step inverted? */
+ for (j = 0; j < current_argc; j++)
+ if (0==strcmp("inv", current_argv[j]))
+ next_step->inverted = 1;
+
P->opaque->pipeline[i+1] = next_step;
+
proj_log_trace (P, "Pipeline: step done");
}
proj_log_trace (P, "Pipeline: %d steps built. Determining i/o characteristics", nsteps);
/* Determine forward input (= reverse output) data type */
-
- /* First locate the first forward-active pipeline step */
- for (i = 0; i < nsteps; i++)
- if (0==P->opaque->omit_forward[i+1])
- break;
- if (i==nsteps) {
- proj_log_error (P, "Pipeline: No forward steps");
- return destructor (P, PJD_ERR_MALFORMED_PIPELINE);
- }
-
- if (P->opaque->reverse_step[i + 1])
- P->left = P->opaque->pipeline[i + 1]->right;
- else
- P->left = P->opaque->pipeline[i + 1]->left;
-
- if (P->left==PJ_IO_UNITS_CLASSIC) {
- if (P->opaque->reverse_step[i + 1])
- P->left = PJ_IO_UNITS_METERS;
- else
- P->left = PJ_IO_UNITS_RADIANS;
- }
+ P->left = pj_left (P->opaque->pipeline[1]);
/* Now, correspondingly determine forward output (= reverse input) data type */
-
- /* First locate the last reverse-active pipeline step */
- for (i = nsteps - 1; i >= 0; i--)
- if (0==P->opaque->omit_inverse[i+1])
- break;
- if (i==-1) {
- proj_log_error (P, "Pipeline: No reverse steps");
- return destructor (P, PJD_ERR_MALFORMED_PIPELINE);
- }
-
- if (P->opaque->reverse_step[i + 1])
- P->right = P->opaque->pipeline[i + 1]->left;
- else
- P->right = P->opaque->pipeline[i + 1]->right;
-
- if (P->right==PJ_IO_UNITS_CLASSIC) {
- if (P->opaque->reverse_step[i + 1])
- P->right = PJ_IO_UNITS_RADIANS;
- else
- P->right = PJ_IO_UNITS_METERS;
- }
- proj_log_trace (P, "Pipeline: Units - left: [%s], right: [%s]\n",
- P->left ==PJ_IO_UNITS_RADIANS? "angular": "linear",
- P->right==PJ_IO_UNITS_RADIANS? "angular": "linear");
+ P->right = pj_right (P->opaque->pipeline[nsteps]);
return P;
}
@@ -512,14 +417,14 @@ int pj_pipeline_selftest (void) {
double dist;
/* forward-reverse geo->utm->geo */
- P = proj_create (PJ_DEFAULT_CTX, "+proj=pipeline +zone=32 +step +proj=utm +ellps=GRS80 +step +proj=utm +ellps=GRS80 +inv");
+ P = proj_create (PJ_DEFAULT_CTX, "+proj=pipeline +zone=32 +step +proj=utm +ellps=GRS80 +step +proj=utm +ellps=GRS80 +inv");
if (0==P)
return 1000;
/* zero initialize everything, then set (longitude, latitude, height) to (12, 55, 0) */
a = b = proj_obs_null;
a.coo.lpz.lam = PJ_TORAD(12);
a.coo.lpz.phi = PJ_TORAD(55);
- a.coo.lpz.z = 0;
+ a.coo.lpz.z = 10;
/* Forward projection */
b = proj_trans_obs (P, PJ_FWD, a);
diff --git a/src/pj_internal.c b/src/pj_internal.c
index 5eb98afb..19dd6409 100644
--- a/src/pj_internal.c
+++ b/src/pj_internal.c
@@ -66,13 +66,28 @@ PJ_OBS proj_obs (double x, double y, double z, double t) {
+enum pj_io_units pj_left (PJ *P) {
+ enum pj_io_units u = P->inverted? P->right: P->left;
+ if (u==PJ_IO_UNITS_RADIANS)
+ return PJ_IO_UNITS_RADIANS;
+ return PJ_IO_UNITS_METERS;
+}
+enum pj_io_units pj_right (PJ *P) {
+ enum pj_io_units u = P->inverted? P->left: P->right;
+ if (u==PJ_IO_UNITS_RADIANS)
+ return PJ_IO_UNITS_RADIANS;
+ return PJ_IO_UNITS_METERS;
+}
/* Apply the transformation P to the coordinate coo */
PJ_OBS proj_trans_obs (PJ *P, PJ_DIRECTION direction, PJ_OBS obs) {
if (0==P)
return obs;
+ if (P->inverted)
+ direction = -direction;
+
switch (direction) {
case PJ_FWD:
return pj_fwdobs (obs, P);
diff --git a/src/proj_4D_api.c b/src/proj_4D_api.c
index 5484b650..4b8fd854 100644
--- a/src/proj_4D_api.c
+++ b/src/proj_4D_api.c
@@ -45,7 +45,6 @@ PJ_COORD proj_coord (double x, double y, double z, double t) {
}
-
/* Geodesic distance (in meter) between two points with angular 2D coordinates */
double proj_lp_dist (const PJ *P, LP a, LP b) {
double s12, azi1, azi2;
diff --git a/src/proj_internal.h b/src/proj_internal.h
index ba542dea..36ff5767 100644
--- a/src/proj_internal.h
+++ b/src/proj_internal.h
@@ -64,6 +64,8 @@ typedef struct PJ_OBS PJ_OBS;
#endif
+enum pj_io_units pj_left (PJ *P);
+enum pj_io_units pj_right (PJ *P);
PJ_OBS proj_obs (double x, double y, double z, double t);
PJ_OBS proj_trans_obs (PJ *P, PJ_DIRECTION direction, PJ_OBS obs);
diff --git a/src/projects.h b/src/projects.h
index 6ea0c914..a7763dd1 100644
--- a/src/projects.h
+++ b/src/projects.h
@@ -231,6 +231,7 @@ struct PJconsts {
paralist *params; /* Parameter list */
struct geod_geodesic *geod; /* For geodesic computations */
struct pj_opaque *opaque; /* Projection specific parameters, Defined in PJ_*.c */
+ int inverted; /* Tell high level API functions to swap inv/fwd */
/*************************************************************************************