PostGIS  2.1.10dev-r@@SVN_REVISION@@
rt_errorstate rt_raster_iterator ( rt_iterator  itrset,
uint16_t  itrcount,
rt_extenttype  extenttype,
rt_raster  customextent,
rt_pixtype  pixtype,
uint8_t  hasnodata,
double  nodataval,
uint16_t  distancex,
uint16_t  distancey,
void *  userarg,
int(*)(rt_iterator_arg arg, void *userarg, double *value, int *nodata)  callback,
rt_raster rtnraster 
)

n-raster iterator.

Returns a raster with one band. The raster returned should be freed by the caller

Parameters
itrset: set of rt_iterator objects.
itrcount: number of objects in itrset.
extenttype: type of extent for the output raster.
customextent: raster specifying custom extent. is only used if extenttype is ET_CUSTOM.
pixtype: the desired pixel type of the output raster's band.
hasnodata: indicates if the band has nodata value
nodataval: the nodata value, will be appropriately truncated to fit the pixtype size.
distancex: the number of pixels around the specified pixel along the X axis
distancey: the number of pixels around the specified pixel along the Y axis
*userarg: pointer to any argument that is passed as-is to callback.
*callback: callback function for actual processing of pixel values.
*rtnraster: return one band raster from iterator process

The callback function must have the following signature.

int FNAME(rt_iterator_arg arg, void *userarg, double *value, int *nodata)

The callback function must return zero (error) or non-zero (success) indicating whether the function ran successfully. The parameters passed to the callback function are as follows.

  • rt_iterator_arg arg : struct containing pixel values, NODATA flags and metadata
  • void *userarg : NULL or calling function provides to rt_raster_iterator() for use by callback function
  • double *value : value of pixel to be burned by rt_raster_iterator()
  • int *nodata : flag (0 or 1) indicating that pixel to be burned is NODATA
Returns
ES_NONE on success, ES_ERROR on error

The raster returned should be freed by the caller

Parameters
itrset: set of rt_iterator objects.
itrcount: number of objects in itrset.
extenttype: type of extent for the output raster.
customextent: raster specifying custom extent. is only used if extenttype is ET_CUSTOM.
pixtype: the desired pixel type of the output raster's band.
hasnodata: indicates if the band has nodata value
nodataval: the nodata value, will be appropriately truncated to fit the pixtype size.
distancex: the number of pixels around the specified pixel along the X axis
distancey: the number of pixels around the specified pixel along the Y axis
userarg: pointer to any argument that is passed as-is to callback.
callback: callback function for actual processing of pixel values.
*rtnraster: return one band raster from iterator process

The callback function must have the following signature.

int FNAME(rt_iterator_arg arg, void *userarg, double *value, int *nodata)

The callback function must return zero (error) or non-zero (success) indicating whether the function ran successfully. The parameters passed to the callback function are as follows.

  • rt_iterator_arg arg: struct containing pixel values, NODATA flags and metadata
  • void *userarg: NULL or calling function provides to rt_raster_iterator() for use by callback function
  • double *value: value of pixel to be burned by rt_raster_iterator()
  • int *nodata: flag (0 or 1) indicating that pixel to be burned is NODATA
Returns
ES_NONE on success, ES_ERROR on error

Definition at line 13927 of file rt_api.c.

References _rti_iterator_arg_callback_clean(), _rti_iterator_arg_callback_init(), _rti_iterator_arg_destroy(), _rti_iterator_arg_empty_init(), _rti_iterator_arg_init(), _rti_iterator_arg_populate(), _rti_iterator_arg_t::arg, _rti_iterator_arg_t::band, rt_raster_t::bands, rt_iterator_arg_t::dst_pixel, _rti_iterator_arg_t::empty, ES_ERROR, ES_NONE, ET_CUSTOM, ET_FIRST, ET_INTERSECTION, ET_LAST, ET_SECOND, ET_UNION, _rti_iterator_arg_t::hasnodata, _rti_iterator_arg_t::isempty, _rti_iterator_arg_t::isnodata, _rti_iterator_arg_t::minval, rt_iterator_t::nbnodata, rt_pixel_t::nodata, rt_iterator_arg_t::nodata, _rti_iterator_arg_t::nodata, _rti_iterator_arg_t::nodataval, rt_raster_t::numBands, _rti_iterator_arg_t::offset, PT_END, rtpixdump::rast, _rti_iterator_arg_t::raster, RASTER_DEBUG, RASTER_DEBUGF, rt_band_destroy(), rt_band_get_min_value(), rt_band_get_nearest_pixel(), rt_band_get_pixel(), rt_band_set_pixel(), rt_pixel_set_to_array(), rt_raster_destroy(), rt_raster_from_two_rasters(), rt_raster_generate_new_band(), rt_raster_get_band(), rt_raster_get_height(), rt_raster_get_srid(), rt_raster_get_width(), rt_raster_get_x_offset(), rt_raster_get_x_scale(), rt_raster_get_x_skew(), rt_raster_get_y_offset(), rt_raster_get_y_scale(), rt_raster_get_y_skew(), rt_raster_is_empty(), rt_raster_new(), rt_raster_same_alignment(), rt_raster_set_scale(), rtalloc(), _rti_iterator_arg_t::rtband, rtdealloc(), rterror(), rtinfo(), rtrealloc(), rt_iterator_arg_t::src_pixel, genraster::value, rt_pixel_t::value, rt_iterator_arg_t::values, _rti_iterator_arg_t::values, pixval::x, rt_pixel_t::x, pixval::y, and rt_pixel_t::y.

Referenced by RASTER_clip(), RASTER_nMapAlgebra(), RASTER_nMapAlgebraExpr(), RASTER_setPixelValuesGeomval(), RASTER_union_finalfn(), RASTER_union_transfn(), and test_raster_iterator().

13941  {
13942  /* output raster */
13943  rt_raster rtnrast = NULL;
13944  /* output raster's band */
13945  rt_band rtnband = NULL;
13946 
13947  /* working raster */
13948  rt_raster rast = NULL;
13949 
13950  _rti_iterator_arg _param = NULL;
13951  int allnull = 0;
13952  int allempty = 0;
13953  int aligned = 0;
13954  double offset[4] = {0.};
13955  rt_pixel npixels;
13956 
13957  int i = 0;
13958  int status = 0;
13959  int inextent = 0;
13960  int x = 0;
13961  int y = 0;
13962  int _x = 0;
13963  int _y = 0;
13964 
13965  int _width = 0;
13966  int _height = 0;
13967 
13968  double minval;
13969  double value;
13970  int isnodata;
13971  int nodata;
13972 
13973  RASTER_DEBUG(3, "Starting...");
13974 
13975  assert(itrset != NULL && itrcount > 0);
13976  assert(rtnraster != NULL);
13977 
13978  /* init rtnraster to NULL */
13979  *rtnraster = NULL;
13980 
13981  /* check that callback function is not NULL */
13982  if (callback == NULL) {
13983  rterror("rt_raster_iterator: Callback function not provided");
13984  return ES_ERROR;
13985  }
13986 
13987  /* check that custom extent is provided if extenttype = ET_CUSTOM */
13988  if (extenttype == ET_CUSTOM && rt_raster_is_empty(customextent)) {
13989  rterror("rt_raster_iterator: Custom extent cannot be empty if extent type is ET_CUSTOM");
13990  return ES_ERROR;
13991  }
13992 
13993  /* check that pixtype != PT_END */
13994  if (pixtype == PT_END) {
13995  rterror("rt_raster_iterator: Pixel type cannot be PT_END");
13996  return ES_ERROR;
13997  }
13998 
13999  /* initialize _param */
14000  if ((_param = _rti_iterator_arg_init()) == NULL) {
14001  rterror("rt_raster_iterator: Could not initialize internal variables");
14002  return ES_ERROR;
14003  }
14004 
14005  /* fill _param */
14006  if (!_rti_iterator_arg_populate(_param, itrset, itrcount, distancex, distancey, &allnull, &allempty)) {
14007  rterror("rt_raster_iterator: Could not populate for internal variables");
14008  _rti_iterator_arg_destroy(_param);
14009  return ES_ERROR;
14010  }
14011 
14012  /* shortcut if all null, return NULL */
14013  if (allnull == itrcount) {
14014  RASTER_DEBUG(3, "all rasters are NULL, returning NULL");
14015 
14016  _rti_iterator_arg_destroy(_param);
14017 
14018  return ES_NONE;
14019  }
14020  /* shortcut if all empty, return empty raster */
14021  else if (allempty == itrcount) {
14022  RASTER_DEBUG(3, "all rasters are empty, returning empty raster");
14023 
14024  _rti_iterator_arg_destroy(_param);
14025 
14026  rtnrast = rt_raster_new(0, 0);
14027  if (rtnrast == NULL) {
14028  rterror("rt_raster_iterator: Could not create empty raster");
14029  return ES_ERROR;
14030  }
14031  rt_raster_set_scale(rtnrast, 0, 0);
14032 
14033  *rtnraster = rtnrast;
14034  return ES_NONE;
14035  }
14036 
14037  /* check that all rasters are aligned */
14038  RASTER_DEBUG(3, "checking alignment of all rasters");
14039  rast = NULL;
14040 
14041  /* find raster to use as reference */
14042  /* use custom if provided */
14043  if (extenttype == ET_CUSTOM) {
14044  RASTER_DEBUG(4, "using custom extent as reference raster");
14045  rast = customextent;
14046  }
14047  /* use first valid one in _param->raster */
14048  else {
14049  for (i = 0; i < itrcount; i++) {
14050  if (!_param->isempty[i]) {
14051  RASTER_DEBUGF(4, "using raster at index %d as reference raster", i);
14052  rast = _param->raster[i];
14053  break;
14054  }
14055  }
14056  }
14057 
14058  /* no rasters found, SHOULD NEVER BE HERE! */
14059  if (rast == NULL) {
14060  rterror("rt_raster_iterator: Could not find reference raster to use for alignment tests");
14061 
14062  _rti_iterator_arg_destroy(_param);
14063 
14064  return ES_ERROR;
14065  }
14066 
14067  do {
14068  aligned = 1;
14069 
14070  /* check custom first if set. also skip if rasters are the same */
14071  if (extenttype == ET_CUSTOM && rast != customextent) {
14072  if (rt_raster_same_alignment(rast, customextent, &aligned, NULL) != ES_NONE) {
14073  rterror("rt_raster_iterator: Could not test for alignment between reference raster and custom extent");
14074 
14075  _rti_iterator_arg_destroy(_param);
14076 
14077  return ES_ERROR;
14078  }
14079 
14080  RASTER_DEBUGF(5, "custom extent alignment: %d", aligned);
14081  if (!aligned)
14082  break;
14083  }
14084 
14085  for (i = 0; i < itrcount; i++) {
14086  /* skip NULL rasters and if rasters are the same */
14087  if (_param->isempty[i] || rast == _param->raster[i])
14088  continue;
14089 
14090  if (rt_raster_same_alignment(rast, _param->raster[i], &aligned, NULL) != ES_NONE) {
14091  rterror("rt_raster_iterator: Could not test for alignment between reference raster and raster %d", i);
14092 
14093  _rti_iterator_arg_destroy(_param);
14094 
14095  return ES_ERROR;
14096  }
14097  RASTER_DEBUGF(5, "raster at index %d alignment: %d", i, aligned);
14098 
14099  /* abort checking since a raster isn't aligned */
14100  if (!aligned)
14101  break;
14102  }
14103  }
14104  while (0);
14105 
14106  /* not aligned, error */
14107  if (!aligned) {
14108  rterror("rt_raster_iterator: The set of rasters provided (custom extent included, if appropriate) do not have the same alignment");
14109 
14110  _rti_iterator_arg_destroy(_param);
14111 
14112  return ES_ERROR;
14113  }
14114 
14115  /* use extenttype to build output raster (no bands though) */
14116  i = -1;
14117  switch (extenttype) {
14118  case ET_INTERSECTION:
14119  case ET_UNION:
14120  /* make copy of first "real" raster */
14121  rtnrast = rtalloc(sizeof(struct rt_raster_t));
14122  if (rtnrast == NULL) {
14123  rterror("rt_raster_iterator: Could not allocate memory for output raster");
14124 
14125  _rti_iterator_arg_destroy(_param);
14126 
14127  return ES_ERROR;
14128  }
14129 
14130  for (i = 0; i < itrcount; i++) {
14131  if (!_param->isempty[i]) {
14132  memcpy(rtnrast, _param->raster[i], sizeof(struct rt_raster_serialized_t));
14133  break;
14134  }
14135  }
14136  rtnrast->numBands = 0;
14137  rtnrast->bands = NULL;
14138 
14139  /* get extent of output raster */
14140  rast = NULL;
14141  for (i = i + 1; i < itrcount; i++) {
14142  if (_param->isempty[i])
14143  continue;
14144 
14145  status = rt_raster_from_two_rasters(rtnrast, _param->raster[i], extenttype, &rast, NULL);
14146  rtdealloc(rtnrast);
14147 
14148  if (rast == NULL || status != ES_NONE) {
14149  rterror("rt_raster_iterator: Could not compute %s extent of rasters",
14150  extenttype == ET_UNION ? "union" : "intersection"
14151  );
14152 
14153  _rti_iterator_arg_destroy(_param);
14154 
14155  return ES_ERROR;
14156  }
14157  else if (rt_raster_is_empty(rast)) {
14158  rtinfo("rt_raster_iterator: Computed raster for %s extent is empty",
14159  extenttype == ET_UNION ? "union" : "intersection"
14160  );
14161 
14162  _rti_iterator_arg_destroy(_param);
14163 
14164  *rtnraster = rast;
14165  return ES_NONE;
14166  }
14167 
14168  rtnrast = rast;
14169  rast = NULL;
14170  }
14171 
14172  break;
14173  /*
14174  first, second and last have similar checks
14175  and continue into custom
14176  */
14177  case ET_FIRST:
14178  i = 0;
14179  case ET_SECOND:
14180  if (i < 0) {
14181  if (itrcount < 2)
14182  i = 0;
14183  else
14184  i = 1;
14185  }
14186  case ET_LAST:
14187  if (i < 0) i = itrcount - 1;
14188 
14189  /* input raster is null, return NULL */
14190  if (_param->raster[i] == NULL) {
14191  RASTER_DEBUGF(3, "returning NULL as %s raster is NULL and extent type is ET_%s",
14192  (i == 0 ? "first" : (i == 1 ? "second" : "last")),
14193  (i == 0 ? "FIRST" : (i == 1 ? "SECOND" : "LAST"))
14194  );
14195 
14196  _rti_iterator_arg_destroy(_param);
14197 
14198  return ES_NONE;
14199  }
14200  /* input raster is empty, return empty raster */
14201  else if (_param->isempty[i]) {
14202  RASTER_DEBUGF(3, "returning empty raster as %s raster is empty and extent type is ET_%s",
14203  (i == 0 ? "first" : (i == 1 ? "second" : "last")),
14204  (i == 0 ? "FIRST" : (i == 1 ? "SECOND" : "LAST"))
14205  );
14206 
14207  _rti_iterator_arg_destroy(_param);
14208 
14209  rtnrast = rt_raster_new(0, 0);
14210  if (rtnrast == NULL) {
14211  rterror("rt_raster_iterator: Could not create empty raster");
14212  return ES_ERROR;
14213  }
14214  rt_raster_set_scale(rtnrast, 0, 0);
14215 
14216  *rtnraster = rtnrast;
14217  return ES_NONE;
14218  }
14219  /* copy the custom extent raster */
14220  case ET_CUSTOM:
14221  rtnrast = rtalloc(sizeof(struct rt_raster_t));
14222  if (rtnrast == NULL) {
14223  rterror("rt_raster_iterator: Could not allocate memory for output raster");
14224 
14225  _rti_iterator_arg_destroy(_param);
14226 
14227  return ES_ERROR;
14228  }
14229 
14230  switch (extenttype) {
14231  case ET_CUSTOM:
14232  memcpy(rtnrast, customextent, sizeof(struct rt_raster_serialized_t));
14233  break;
14234  /* first, second, last */
14235  default:
14236  memcpy(rtnrast, _param->raster[i], sizeof(struct rt_raster_serialized_t));
14237  break;
14238  }
14239  rtnrast->numBands = 0;
14240  rtnrast->bands = NULL;
14241  break;
14242  }
14243 
14244  _width = rt_raster_get_width(rtnrast);
14245  _height = rt_raster_get_height(rtnrast);
14246 
14247  RASTER_DEBUGF(4, "rtnrast (width, height, ulx, uly, scalex, scaley, skewx, skewy, srid) = (%d, %d, %f, %f, %f, %f, %f, %f, %d)",
14248  _width,
14249  _height,
14250  rt_raster_get_x_offset(rtnrast),
14251  rt_raster_get_y_offset(rtnrast),
14252  rt_raster_get_x_scale(rtnrast),
14253  rt_raster_get_y_scale(rtnrast),
14254  rt_raster_get_x_skew(rtnrast),
14255  rt_raster_get_y_skew(rtnrast),
14256  rt_raster_get_srid(rtnrast)
14257  );
14258 
14259  /* init values and NODATA for use with empty rasters */
14260  if (!_rti_iterator_arg_empty_init(_param)) {
14261  rterror("rt_raster_iterator: Could not initialize empty values and NODATA");
14262 
14263  _rti_iterator_arg_destroy(_param);
14264  rt_raster_destroy(rtnrast);
14265 
14266  return ES_ERROR;
14267  }
14268 
14269  /* create output band */
14271  rtnrast,
14272  pixtype,
14273  nodataval,
14274  hasnodata, nodataval,
14275  0
14276  ) < 0) {
14277  rterror("rt_raster_iterator: Could not add new band to output raster");
14278 
14279  _rti_iterator_arg_destroy(_param);
14280  rt_raster_destroy(rtnrast);
14281 
14282  return ES_ERROR;
14283  }
14284 
14285  /* get output band */
14286  rtnband = rt_raster_get_band(rtnrast, 0);
14287  if (rtnband == NULL) {
14288  rterror("rt_raster_iterator: Could not get new band from output raster");
14289 
14290  _rti_iterator_arg_destroy(_param);
14291  rt_raster_destroy(rtnrast);
14292 
14293  return ES_ERROR;
14294  }
14295 
14296  /* output band's minimum value */
14297  minval = rt_band_get_min_value(rtnband);
14298 
14299  /* initialize argument for callback function */
14300  if (!_rti_iterator_arg_callback_init(_param)) {
14301  rterror("rt_raster_iterator: Could not initialize callback function argument");
14302 
14303  _rti_iterator_arg_destroy(_param);
14304  rt_band_destroy(rtnband);
14305  rt_raster_destroy(rtnrast);
14306 
14307  return ES_ERROR;
14308  }
14309 
14310  /* fill _param->offset */
14311  for (i = 0; i < itrcount; i++) {
14312  if (_param->isempty[i])
14313  continue;
14314 
14315  status = rt_raster_from_two_rasters(rtnrast, _param->raster[i], ET_FIRST, &rast, offset);
14316  rtdealloc(rast);
14317  if (status != ES_NONE) {
14318  rterror("rt_raster_iterator: Could not compute raster offsets");
14319 
14320  _rti_iterator_arg_destroy(_param);
14321  rt_band_destroy(rtnband);
14322  rt_raster_destroy(rtnrast);
14323 
14324  return ES_ERROR;
14325  }
14326 
14327  _param->offset[i][0] = offset[2];
14328  _param->offset[i][1] = offset[3];
14329  RASTER_DEBUGF(4, "rast %d offset: %f %f", i, offset[2], offset[3]);
14330  }
14331 
14332  /* loop over each pixel (POI) of output raster */
14333  /* _x,_y are for output raster */
14334  /* x,y are for input raster */
14335  for (_y = 0; _y < _height; _y++) {
14336  for (_x = 0; _x < _width; _x++) {
14337  RASTER_DEBUGF(4, "iterating output pixel (x, y) = (%d, %d)", _x, _y);
14338  _param->arg->dst_pixel[0] = _x;
14339  _param->arg->dst_pixel[1] = _y;
14340 
14341  /* loop through each input raster */
14342  for (i = 0; i < itrcount; i++) {
14343  RASTER_DEBUGF(4, "raster %d", i);
14344 
14345  /*
14346  empty raster
14347  OR band does not exist and flag set to use NODATA
14348  OR band is NODATA
14349  */
14350  if (
14351  _param->isempty[i] ||
14352  (_param->band.rtband[i] == NULL && itrset[i].nbnodata) ||
14353  _param->band.isnodata[i]
14354  ) {
14355  RASTER_DEBUG(4, "empty raster, band does not exist or band is NODATA. using empty values and NODATA");
14356 
14357  x = _x;
14358  y = _y;
14359 
14360  _param->arg->values[i] = _param->empty.values;
14361  _param->arg->nodata[i] = _param->empty.nodata;
14362 
14363  continue;
14364  }
14365 
14366  /* input raster's X,Y */
14367  x = _x - (int) _param->offset[i][0];
14368  y = _y - (int) _param->offset[i][1];
14369  RASTER_DEBUGF(4, "source pixel (x, y) = (%d, %d)", x, y);
14370 
14371  _param->arg->src_pixel[i][0] = x;
14372  _param->arg->src_pixel[i][1] = y;
14373 
14374  /* neighborhood */
14375  npixels = NULL;
14376  status = 0;
14377  if (distancex > 0 && distancey > 0) {
14378  RASTER_DEBUG(4, "getting neighborhood");
14379 
14380  status = rt_band_get_nearest_pixel(
14381  _param->band.rtband[i],
14382  x, y,
14383  distancex, distancey,
14384  1,
14385  &npixels
14386  );
14387  if (status < 0) {
14388  rterror("rt_raster_iterator: Could not get pixel neighborhood");
14389 
14390  _rti_iterator_arg_destroy(_param);
14391  rt_band_destroy(rtnband);
14392  rt_raster_destroy(rtnrast);
14393 
14394  return ES_ERROR;
14395  }
14396  }
14397 
14398  /* get value of POI */
14399  /* get pixel's value */
14400  if (
14401  (x >= 0 && x < _param->width[i]) &&
14402  (y >= 0 && y < _param->height[i])
14403  ) {
14404  RASTER_DEBUG(4, "getting value of POI");
14405  if (rt_band_get_pixel(
14406  _param->band.rtband[i],
14407  x, y,
14408  &value,
14409  &isnodata
14410  ) != ES_NONE) {
14411  rterror("rt_raster_iterator: Could not get the pixel value of band");
14412 
14413  _rti_iterator_arg_destroy(_param);
14414  rt_band_destroy(rtnband);
14415  rt_raster_destroy(rtnrast);
14416 
14417  return ES_ERROR;
14418  }
14419  inextent = 1;
14420  }
14421  /* outside band extent, set to NODATA */
14422  else {
14423  RASTER_DEBUG(4, "Outside band extent, setting value to NODATA");
14424  /* has NODATA, use NODATA */
14425  if (_param->band.hasnodata[i])
14426  value = _param->band.nodataval[i];
14427  /* no NODATA, use min possible value */
14428  else
14429  value = _param->band.minval[i];
14430 
14431  inextent = 0;
14432  isnodata = 1;
14433  }
14434 
14435  /* add pixel to neighborhood */
14436  status++;
14437  if (status > 1)
14438  npixels = (rt_pixel) rtrealloc(npixels, sizeof(struct rt_pixel_t) * status);
14439  else
14440  npixels = (rt_pixel) rtalloc(sizeof(struct rt_pixel_t));
14441 
14442  if (npixels == NULL) {
14443  rterror("rt_raster_iterator: Could not reallocate memory for neighborhood");
14444 
14445  _rti_iterator_arg_destroy(_param);
14446  rt_band_destroy(rtnband);
14447  rt_raster_destroy(rtnrast);
14448 
14449  return ES_ERROR;
14450  }
14451 
14452  npixels[status - 1].x = x;
14453  npixels[status - 1].y = y;
14454  npixels[status - 1].nodata = 1;
14455  npixels[status - 1].value = value;
14456 
14457  /* set nodata flag */
14458  if ((!_param->band.hasnodata[i] && inextent) || !isnodata) {
14459  npixels[status - 1].nodata = 0;
14460  }
14461  RASTER_DEBUGF(4, "value, nodata: %f, %d", value, npixels[status - 1].nodata);
14462 
14463  /* convert set of rt_pixel to 2D array */
14464  status = rt_pixel_set_to_array(
14465  npixels, status,
14466  x, y,
14467  distancex, distancey,
14468  &(_param->arg->values[i]),
14469  &(_param->arg->nodata[i]),
14470  NULL, NULL
14471  );
14472  rtdealloc(npixels);
14473  if (status != ES_NONE) {
14474  rterror("rt_raster_iterator: Could not create 2D array of neighborhood");
14475 
14476  _rti_iterator_arg_destroy(_param);
14477  rt_band_destroy(rtnband);
14478  rt_raster_destroy(rtnrast);
14479 
14480  return ES_ERROR;
14481  }
14482  }
14483 
14484  /* callback */
14485  RASTER_DEBUG(4, "calling callback function");
14486  value = 0;
14487  nodata = 0;
14488  status = callback(_param->arg, userarg, &value, &nodata);
14489 
14490  /* free memory from callback */
14492 
14493  /* handle callback status */
14494  if (status == 0) {
14495  rterror("rt_raster_iterator: Callback function returned an error");
14496 
14497  _rti_iterator_arg_destroy(_param);
14498  rt_band_destroy(rtnband);
14499  rt_raster_destroy(rtnrast);
14500 
14501  return ES_ERROR;
14502  }
14503 
14504  /* burn value to pixel */
14505  status = 0;
14506  if (!nodata) {
14507  status = rt_band_set_pixel(rtnband, _x, _y, value, NULL);
14508  RASTER_DEBUGF(4, "burning pixel (%d, %d) with value: %f", _x, _y, value);
14509  }
14510  else if (!hasnodata) {
14511  status = rt_band_set_pixel(rtnband, _x, _y, minval, NULL);
14512  RASTER_DEBUGF(4, "burning pixel (%d, %d) with minval: %f", _x, _y, minval);
14513  }
14514  else {
14515  RASTER_DEBUGF(4, "NOT burning pixel (%d, %d)", _x, _y);
14516  }
14517  if (status != ES_NONE) {
14518  rterror("rt_raster_iterator: Could not set pixel value");
14519 
14520  _rti_iterator_arg_destroy(_param);
14521  rt_band_destroy(rtnband);
14522  rt_raster_destroy(rtnrast);
14523 
14524  return ES_ERROR;
14525  }
14526  }
14527  }
14528 
14529  /* lots of cleanup */
14530  _rti_iterator_arg_destroy(_param);
14531 
14532  *rtnraster = rtnrast;
14533  return ES_NONE;
14534 }
rt_errorstate rt_pixel_set_to_array(rt_pixel npixel, int count, int x, int y, uint16_t distancex, uint16_t distancey, double ***value, int ***nodata, int *dimx, int *dimy)
Definition: rt_api.c:1341
rt_band * rtband
Definition: rt_api.c:13512
void rtdealloc(void *mem)
Definition: rt_api.c:882
double rt_raster_get_y_offset(rt_raster raster)
Get raster y offset, in projection units.
Definition: rt_api.c:5527
void rt_raster_destroy(rt_raster raster)
Release memory associated to a raster.
Definition: rt_api.c:5387
uint16_t numBands
Definition: rt_api.h:2215
int ** src_pixel
Definition: rt_api.h:2381
rt_raster * raster
Definition: rt_api.c:13505
Definition: rt_api.h:184
int rt_band_get_nearest_pixel(rt_band band, int x, int y, uint16_t distancex, uint16_t distancey, int exclude_nodata_value, rt_pixel *npixels)
Get nearest pixel(s) with value (not NODATA) to specified pixel.
Definition: rt_api.c:2702
double rt_raster_get_x_skew(rt_raster raster)
Get skew about the X axis.
Definition: rt_api.c:5486
rt_iterator_arg arg
Definition: rt_api.c:13534
tuple rast
Definition: rtpixdump.py:62
double rt_raster_get_y_skew(rt_raster raster)
Get skew about the Y axis.
Definition: rt_api.c:5495
double value
Definition: rt_api.h:2263
double rt_raster_get_x_offset(rt_raster raster)
Get raster x offset, in projection units.
Definition: rt_api.c:5518
rt_errorstate rt_raster_from_two_rasters(rt_raster rast1, rt_raster rast2, rt_extenttype extenttype, rt_raster *rtnraster, double *offset)
Definition: rt_api.c:12876
int32_t rt_raster_get_srid(rt_raster raster)
Get raster's SRID.
Definition: rt_api.c:5661
struct rt_pixel_t * rt_pixel
Definition: rt_api.h:135
static int _rti_iterator_arg_empty_init(_rti_iterator_arg _param)
Definition: rt_api.c:13786
void rtinfo(const char *fmt,...)
Definition: rt_api.c:907
#define RASTER_DEBUG(level, msg)
Definition: rt_api.h:281
void rt_raster_set_scale(rt_raster raster, double scaleX, double scaleY)
Set scale in projection units.
Definition: rt_api.c:5442
double ** values
Definition: rt_api.c:13530
#define RASTER_DEBUGF(level, msg,...)
Definition: rt_api.h:285
struct _rti_iterator_arg_t::@13 empty
double rt_band_get_min_value(rt_band band)
Returns the minimal possible value for the band according to the pixel type.
Definition: rt_api.c:3073
rt_errorstate rt_band_get_pixel(rt_band band, int x, int y, double *value, int *nodata)
Get pixel value.
Definition: rt_api.c:2549
double * nodataval
Definition: rt_api.c:13515
struct _rti_iterator_arg_t::@10 band
double rt_raster_get_x_scale(rt_raster raster)
Get scale X in projection units.
Definition: rt_api.c:5455
double ** offset
Definition: rt_api.c:13507
uint8_t nodata
Definition: rt_api.h:2262
tuple x
Definition: pixval.py:53
void rt_band_destroy(rt_band band)
Destroy a raster band.
Definition: rt_api.c:1650
uint16_t rt_raster_get_height(rt_raster raster)
Definition: rt_api.c:5434
void * rtalloc(size_t size)
Raster core memory management functions.
Definition: rt_api.c:867
void rterror(const char *fmt,...)
Raster core error and info handlers.
Definition: rt_api.c:895
double *** values
Definition: rt_api.h:2376
rt_band rt_raster_get_band(rt_raster raster, int n)
Return Nth band, or NULL if unavailable.
Definition: rt_api.c:5686
uint8_t nbnodata
Definition: rt_api.h:2362
Struct definitions.
Definition: rt_api.h:2175
rt_band * bands
Definition: rt_api.h:2228
int rt_raster_is_empty(rt_raster raster)
Return TRUE if the raster is empty.
Definition: rt_api.c:8550
double rt_raster_get_y_scale(rt_raster raster)
Get scale Y in projection units.
Definition: rt_api.c:5464
rt_raster rt_raster_new(uint32_t width, uint32_t height)
Construct a raster with given dimensions.
Definition: rt_api.c:5353
int *** nodata
Definition: rt_api.h:2378
rt_errorstate rt_raster_same_alignment(rt_raster rast1, rt_raster rast2, int *aligned, char **reason)
Definition: rt_api.c:12774
static void _rti_iterator_arg_callback_clean(_rti_iterator_arg _param)
Definition: rt_api.c:13862
static _rti_iterator_arg _rti_iterator_arg_init()
Definition: rt_api.c:13538
int dst_pixel[2]
Definition: rt_api.h:2384
tuple y
Definition: pixval.py:54
static int _rti_iterator_arg_callback_init(_rti_iterator_arg _param)
Definition: rt_api.c:13816
uint16_t rt_raster_get_width(rt_raster raster)
Definition: rt_api.c:5426
static void _rti_iterator_arg_destroy(_rti_iterator_arg _param)
Definition: rt_api.c:13576
int rt_raster_generate_new_band(rt_raster raster, rt_pixtype pixtype, double initialvalue, uint32_t hasnodata, double nodatavalue, int index)
Generate a new inline band and add it to a raster.
Definition: rt_api.c:5784
rt_errorstate rt_band_set_pixel(rt_band band, int x, int y, double val, int *converted)
Set single pixel's value.
Definition: rt_api.c:2302
static int _rti_iterator_arg_populate(_rti_iterator_arg _param, rt_iterator itrset, uint16_t itrcount, uint16_t distancex, uint16_t distancey, int *allnull, int *allempty)
Definition: rt_api.c:13647
void * rtrealloc(void *mem, size_t size)
Definition: rt_api.c:875

Here is the call graph for this function:

Here is the caller graph for this function: