PostGIS  2.5.0dev-r@@SVN_REVISION@@
static rt_errorstate rt_raster_geos_spatial_relationship ( rt_raster  rast1,
int  nband1,
rt_raster  rast2,
int  nband2,
rt_geos_spatial_test  testtype,
int *  testresult 
)
static

Definition at line 137 of file rt_spatial_relationship.c.

References ES_ERROR, ES_NONE, GSR_CONTAINS, GSR_CONTAINSPROPERLY, GSR_COVEREDBY, GSR_COVERS, GSR_OVERLAPS, GSR_TOUCHES, LWGEOM2GEOS(), lwgeom_geos_error(), lwmpoly_as_lwgeom(), lwmpoly_free(), RASTER_DEBUG, rt_raster_get_num_bands(), rt_raster_get_srid(), rt_raster_surface(), rterror(), and rtinfo().

Referenced by rt_raster_contains(), rt_raster_contains_properly(), rt_raster_coveredby(), rt_raster_covers(), rt_raster_overlaps(), and rt_raster_touches().

142  {
143  LWMPOLY *surface1 = NULL;
144  LWMPOLY *surface2 = NULL;
145  GEOSGeometry *geom1 = NULL;
146  GEOSGeometry *geom2 = NULL;
147  int rtn = 0;
148  int flag = 0;
149 
150  RASTER_DEBUG(3, "Starting");
151 
152  assert(NULL != rast1);
153  assert(NULL != rast2);
154  assert(NULL != testresult);
155 
156  if (nband1 < 0 && nband2 < 0) {
157  nband1 = -1;
158  nband2 = -1;
159  }
160  else {
161  assert(nband1 >= 0 && nband1 < rt_raster_get_num_bands(rast1));
162  assert(nband2 >= 0 && nband2 < rt_raster_get_num_bands(rast2));
163  }
164 
165  /* initialize to zero, false result of spatial relationship test */
166  *testresult = 0;
167 
168  /* same srid */
169  if (rt_raster_get_srid(rast1) != rt_raster_get_srid(rast2)) {
170  rterror("rt_raster_geos_spatial_relationship: The two rasters provided have different SRIDs");
171  return ES_ERROR;
172  }
173 
174  initGEOS(rtinfo, lwgeom_geos_error);
175 
176  /* get LWMPOLY of each band */
177  if (rt_raster_surface(rast1, nband1, &surface1) != ES_NONE) {
178  rterror("rt_raster_geos_spatial_relationship: Could not get surface of the specified band from the first raster");
179  return ES_ERROR;
180  }
181  if (rt_raster_surface(rast2, nband2, &surface2) != ES_NONE) {
182  rterror("rt_raster_geos_spatial_relationship: Could not get surface of the specified band from the second raster");
183  lwmpoly_free(surface1);
184  return ES_ERROR;
185  }
186 
187  /* either surface is NULL, spatial relationship test is false */
188  if (surface1 == NULL || surface2 == NULL) {
189  if (surface1 != NULL) lwmpoly_free(surface1);
190  if (surface2 != NULL) lwmpoly_free(surface2);
191  return ES_NONE;
192  }
193 
194  /* convert LWMPOLY to GEOSGeometry */
195  geom1 = LWGEOM2GEOS(lwmpoly_as_lwgeom(surface1), 0);
196  lwmpoly_free(surface1);
197  if (geom1 == NULL) {
198  rterror("rt_raster_geos_spatial_relationship: Could not convert surface of the specified band from the first raster to a GEOSGeometry");
199  lwmpoly_free(surface2);
200  return ES_ERROR;
201  }
202 
203  geom2 = LWGEOM2GEOS(lwmpoly_as_lwgeom(surface2), 0);
204  lwmpoly_free(surface2);
205  if (geom2 == NULL) {
206  rterror("rt_raster_geos_spatial_relationship: Could not convert surface of the specified band from the second raster to a GEOSGeometry");
207  return ES_ERROR;
208  }
209 
210  flag = 0;
211  switch (testtype) {
212  case GSR_OVERLAPS:
213  rtn = GEOSOverlaps(geom1, geom2);
214  break;
215  case GSR_TOUCHES:
216  rtn = GEOSTouches(geom1, geom2);
217  break;
218  case GSR_CONTAINS:
219  rtn = GEOSContains(geom1, geom2);
220  break;
222  rtn = GEOSRelatePattern(geom1, geom2, "T**FF*FF*");
223  break;
224  case GSR_COVERS:
225  rtn = GEOSRelatePattern(geom1, geom2, "******FF*");
226  break;
227  case GSR_COVEREDBY:
228  rtn = GEOSRelatePattern(geom1, geom2, "**F**F***");
229  break;
230  default:
231  rterror("rt_raster_geos_spatial_relationship: Unknown or unsupported GEOS spatial relationship test");
232  flag = -1;
233  break;
234  }
235  GEOSGeom_destroy(geom1);
236  GEOSGeom_destroy(geom2);
237 
238  /* something happened in the spatial relationship test */
239  if (rtn == 2) {
240  rterror("rt_raster_geos_spatial_relationship: Could not run the appropriate GEOS spatial relationship test");
241  flag = ES_ERROR;
242  }
243  /* spatial relationship test ran fine */
244  else if (flag >= 0) {
245  if (rtn != 0)
246  *testresult = 1;
247  flag = ES_NONE;
248  }
249  /* flag < 0 for when testtype is unknown */
250  else
251  flag = ES_ERROR;
252 
253  return flag;
254 }
uint16_t rt_raster_get_num_bands(rt_raster raster)
Definition: rt_raster.c:372
void rterror(const char *fmt,...)
Wrappers used for reporting errors and info.
Definition: rt_context.c:199
rt_errorstate rt_raster_surface(rt_raster raster, int nband, LWMPOLY **surface)
Get a raster as a surface (multipolygon).
Definition: rt_geometry.c:355
void lwmpoly_free(LWMPOLY *mpoly)
Definition: lwmpoly.c:53
void lwgeom_geos_error(const char *fmt,...)
void rtinfo(const char *fmt,...)
Definition: rt_context.c:211
int32_t rt_raster_get_srid(rt_raster raster)
Get raster's SRID.
Definition: rt_raster.c:356
GEOSGeometry * LWGEOM2GEOS(const LWGEOM *lwgeom, int autofix)
#define RASTER_DEBUG(level, msg)
Definition: librtcore.h:295
LWGEOM * lwmpoly_as_lwgeom(const LWMPOLY *obj)
Definition: lwgeom.c:284

Here is the call graph for this function:

Here is the caller graph for this function: