PostGIS  2.1.10dev-r@@SVN_REVISION@@
LWMLINE* lwmline_measured_from_lwmline ( const LWMLINE lwmline,
double  m_start,
double  m_end 
)

Re-write the measure ordinate (or add one, if it isn't already there) interpolating the measure between the supplied start and end values.

Definition at line 43 of file lwmline.c.

References LWMLINE::flags, FLAGS_GET_Z, LWMLINE::geoms, if(), lwalloc(), lwcollection_construct(), lwcollection_construct_empty(), lwerror(), lwgeom_is_empty(), lwline_measured_from_lwline(), MULTILINETYPE, LWMLINE::ngeoms, POINTARRAY::npoints, LWLINE::points, ptarray_length_2d(), LWMLINE::srid, and LWMLINE::type.

Referenced by ST_AddMeasure().

44 {
45  int i = 0;
46  int hasm = 0, hasz = 0;
47  double length = 0.0, length_so_far = 0.0;
48  double m_range = m_end - m_start;
49  LWGEOM **geoms = NULL;
50 
51  if ( lwmline->type != MULTILINETYPE )
52  {
53  lwerror("lwmline_measured_from_lmwline: only multiline types supported");
54  return NULL;
55  }
56 
57  hasz = FLAGS_GET_Z(lwmline->flags);
58  hasm = 1;
59 
60  /* Calculate the total length of the mline */
61  for ( i = 0; i < lwmline->ngeoms; i++ )
62  {
63  LWLINE *lwline = (LWLINE*)lwmline->geoms[i];
64  if ( lwline->points && lwline->points->npoints > 1 )
65  {
66  length += ptarray_length_2d(lwline->points);
67  }
68  }
69 
70  if ( lwgeom_is_empty((LWGEOM*)lwmline) )
71  {
72  return (LWMLINE*)lwcollection_construct_empty(MULTILINETYPE, lwmline->srid, hasz, hasm);
73  }
74 
75  geoms = lwalloc(sizeof(LWGEOM*) * lwmline->ngeoms);
76 
77  for ( i = 0; i < lwmline->ngeoms; i++ )
78  {
79  double sub_m_start, sub_m_end;
80  double sub_length = 0.0;
81  LWLINE *lwline = (LWLINE*)lwmline->geoms[i];
82 
83  if ( lwline->points && lwline->points->npoints > 1 )
84  {
85  sub_length = ptarray_length_2d(lwline->points);
86  }
87 
88  sub_m_start = (m_start + m_range * length_so_far / length);
89  sub_m_end = (m_start + m_range * (length_so_far + sub_length) / length);
90 
91  geoms[i] = (LWGEOM*)lwline_measured_from_lwline(lwline, sub_m_start, sub_m_end);
92 
93  length_so_far += sub_length;
94  }
95 
96  return (LWMLINE*)lwcollection_construct(lwmline->type, lwmline->srid, NULL, lwmline->ngeoms, geoms);
97 }
LWLINE * lwline_measured_from_lwline(const LWLINE *lwline, double m_start, double m_end)
Add a measure dimension to a line, interpolating linearly from the start to the end value...
Definition: lwline.c:366
uint8_t type
Definition: liblwgeom.h:433
LWCOLLECTION * lwcollection_construct(uint8_t type, int srid, GBOX *bbox, uint32_t ngeoms, LWGEOM **geoms)
Definition: lwcollection.c:30
int npoints
Definition: liblwgeom.h:327
double ptarray_length_2d(const POINTARRAY *pts)
Find the 2d length of the given POINTARRAY (even if it's 3d)
Definition: ptarray.c:1586
int ngeoms
Definition: liblwgeom.h:437
void lwerror(const char *fmt,...)
Write a notice out to the error handler.
Definition: lwutil.c:67
uint8_t flags
Definition: liblwgeom.h:434
#define FLAGS_GET_Z(flags)
Macros for manipulating the 'flags' byte.
Definition: liblwgeom.h:106
LWLINE ** geoms
Definition: liblwgeom.h:439
void * lwalloc(size_t size)
Definition: lwutil.c:175
int lwgeom_is_empty(const LWGEOM *geom)
Return true or false depending on whether a geometry is an "empty" geometry (no vertices members) ...
Definition: lwgeom.c:1229
#define MULTILINETYPE
Definition: liblwgeom.h:64
LWCOLLECTION * lwcollection_construct_empty(uint8_t type, int srid, char hasz, char hasm)
Definition: lwcollection.c:81
if(!(yy_init))
Definition: lwin_wkt_lex.c:860
int32_t srid
Definition: liblwgeom.h:436
POINTARRAY * points
Definition: liblwgeom.h:378

Here is the call graph for this function:

Here is the caller graph for this function: