PostGIS  2.2.7dev-r@@SVN_REVISION@@
static LWGEOM * lwline_split_by_line ( const LWLINE lwgeom_in,
const LWGEOM blade_in 
)
static

Definition at line 56 of file lwgeom_geos_split.c.

References COLLECTIONTYPE, LWLINE::flags, FLAGS_GET_Z, GEOS2LWGEOM(), LINETYPE, lwalloc(), lwcollection_construct(), lwerror(), LWGEOM2GEOS(), lwgeom_as_lwcollection(), lwgeom_geos_errmsg, lwgeom_geos_error(), lwgeom_set_srid(), MULTILINETYPE, MULTIPOLYGONTYPE, POLYGONTYPE, LWLINE::srid, LWGEOM::type, and LWCOLLECTION::type.

Referenced by lwline_split().

57 {
58  LWGEOM** components;
59  LWGEOM* diff;
60  LWCOLLECTION* out;
61  GEOSGeometry* gdiff; /* difference */
62  GEOSGeometry* g1;
63  GEOSGeometry* g2;
64  int ret;
65 
66  /* ASSERT blade_in is LINE or MULTILINE */
67  assert (blade_in->type == LINETYPE ||
68  blade_in->type == MULTILINETYPE ||
69  blade_in->type == POLYGONTYPE ||
70  blade_in->type == MULTIPOLYGONTYPE );
71 
72  /* Possible outcomes:
73  *
74  * 1. The lines do not cross or overlap
75  * -> Return a collection with single element
76  * 2. The lines cross
77  * -> Return a collection of all elements resulting from the split
78  */
79 
81 
82  g1 = LWGEOM2GEOS((LWGEOM*)lwline_in, 0);
83  if ( ! g1 )
84  {
85  lwerror("LWGEOM2GEOS: %s", lwgeom_geos_errmsg);
86  return NULL;
87  }
88  g2 = LWGEOM2GEOS(blade_in, 0);
89  if ( ! g2 )
90  {
91  GEOSGeom_destroy(g1);
92  lwerror("LWGEOM2GEOS: %s", lwgeom_geos_errmsg);
93  return NULL;
94  }
95 
96  /* If blade is a polygon, pick its boundary */
97  if ( blade_in->type == POLYGONTYPE || blade_in->type == MULTIPOLYGONTYPE )
98  {
99  gdiff = GEOSBoundary(g2);
100  GEOSGeom_destroy(g2);
101  if ( ! gdiff )
102  {
103  GEOSGeom_destroy(g1);
104  lwerror("GEOSBoundary: %s", lwgeom_geos_errmsg);
105  return NULL;
106  }
107  g2 = gdiff; gdiff = NULL;
108  }
109 
110  /* If interior intersecton is linear we can't split */
111  ret = GEOSRelatePattern(g1, g2, "1********");
112  if ( 2 == ret )
113  {
114  lwerror("GEOSRelatePattern: %s", lwgeom_geos_errmsg);
115  GEOSGeom_destroy(g1);
116  GEOSGeom_destroy(g2);
117  return NULL;
118  }
119  if ( ret )
120  {
121  GEOSGeom_destroy(g1);
122  GEOSGeom_destroy(g2);
123  lwerror("Splitter line has linear intersection with input");
124  return NULL;
125  }
126 
127 
128  gdiff = GEOSDifference(g1,g2);
129  GEOSGeom_destroy(g1);
130  GEOSGeom_destroy(g2);
131  if (gdiff == NULL)
132  {
133  lwerror("GEOSDifference: %s", lwgeom_geos_errmsg);
134  return NULL;
135  }
136 
137  diff = GEOS2LWGEOM(gdiff, FLAGS_GET_Z(lwline_in->flags));
138  GEOSGeom_destroy(gdiff);
139  if (NULL == diff)
140  {
141  lwerror("GEOS2LWGEOM: %s", lwgeom_geos_errmsg);
142  return NULL;
143  }
144 
145  out = lwgeom_as_lwcollection(diff);
146  if ( ! out )
147  {
148  components = lwalloc(sizeof(LWGEOM*)*1);
149  components[0] = diff;
150  out = lwcollection_construct(COLLECTIONTYPE, lwline_in->srid,
151  NULL, 1, components);
152  }
153  else
154  {
155  /* Set SRID */
156  lwgeom_set_srid((LWGEOM*)out, lwline_in->srid);
157  /* Force collection type */
158  out->type = COLLECTIONTYPE;
159  }
160 
161 
162  return (LWGEOM*)out;
163 }
#define LINETYPE
Definition: liblwgeom.h:71
LWCOLLECTION * lwcollection_construct(uint8_t type, int srid, GBOX *bbox, uint32_t ngeoms, LWGEOM **geoms)
Definition: lwcollection.c:30
uint8_t type
Definition: liblwgeom.h:487
#define POLYGONTYPE
Definition: liblwgeom.h:72
char lwgeom_geos_errmsg[LWGEOM_GEOS_ERRMSG_MAXSIZE]
void lwgeom_geos_error(const char *fmt,...)
int32_t srid
Definition: liblwgeom.h:490
#define FLAGS_GET_Z(flags)
Macros for manipulating the 'flags' byte.
Definition: liblwgeom.h:124
GEOSGeometry * LWGEOM2GEOS(const LWGEOM *lwgeom, int autofix)
#define MULTIPOLYGONTYPE
Definition: liblwgeom.h:75
LWCOLLECTION * lwgeom_as_lwcollection(const LWGEOM *lwgeom)
Definition: lwgeom.c:143
LWGEOM * GEOS2LWGEOM(const GEOSGeometry *geom, char want3d)
uint8_t type
Definition: liblwgeom.h:380
void lwgeom_set_srid(LWGEOM *geom, int srid)
Set the SRID on an LWGEOM For collections, only the parent gets an SRID, all the children get SRID_UN...
void * lwalloc(size_t size)
Definition: lwutil.c:199
#define MULTILINETYPE
Definition: liblwgeom.h:74
void lwerror(const char *fmt,...)
Write a notice out to the error handler.
Definition: lwutil.c:74
#define COLLECTIONTYPE
Definition: liblwgeom.h:76

Here is the call graph for this function:

Here is the caller graph for this function: