void Rast3d_retile(void *map, const char *nameOut, int tileX, int tileY, int tileZ) { void *map2; double value; int x, y, z, saveType; int rows, cols, depths, typeIntern; int xTile, yTile, zTile; int xOffs, yOffs, zOffs, prev; int tileXsave, tileYsave, tileZsave; RASTER3D_Region region; if (!Rast3d_tile_use_cache_map(map)) { retileNocache(map, nameOut, tileX, tileY, tileZ); return; } saveType = Rast3d_get_file_type(); Rast3d_set_file_type(Rast3d_file_type_map(map)); Rast3d_get_tile_dimension(&tileXsave, &tileYsave, &tileZsave); Rast3d_set_tile_dimension(tileX, tileY, tileZ); typeIntern = Rast3d_tile_type_map(map); Rast3d_get_region_struct_map(map, ®ion); map2 = Rast3d_open_cell_new(nameOut, typeIntern, RASTER3D_USE_CACHE_DEFAULT, ®ion); if (map2 == NULL) Rast3d_fatal_error("Rast3d_retile: error in Rast3d_open_cell_new"); Rast3d_set_file_type(saveType); Rast3d_set_tile_dimension(tileXsave, tileYsave, tileZsave); Rast3d_coord2tile_coord(map2, 0, 0, 0, &xTile, &yTile, &zTile, &xOffs, &yOffs, &zOffs); prev = zTile; x = 0; y = 0; Rast3d_get_coords_map(map, &rows, &cols, &depths); for (z = 0; z < depths; z++) { G_percent(z, depths, 1); Rast3d_coord2tile_coord(map2, x, y, z, &xTile, &yTile, &zTile, &xOffs, &yOffs, &zOffs); if (zTile > prev) { if (!Rast3d_flush_all_tiles(map2)) Rast3d_fatal_error("Rast3d_retile: error in Rast3d_flush_all_tiles"); prev++; } for (y = 0; y < rows; y++) for (x = 0; x < cols; x++) { Rast3d_get_value_region(map, x, y, z, &value, typeIntern); if (!Rast3d_put_value(map2, x, y, z, &value, typeIntern)) Rast3d_fatal_error("Rast3d_retile: error in Rast3d_put_value"); } } G_percent(1, 1, 1); if (!Rast3d_flush_all_tiles(map2)) Rast3d_fatal_error("Rast3d_retile: error in Rast3d_flush_all_tiles"); if (!Rast3d_close(map2)) Rast3d_fatal_error("Rast3d_retile: error in Rast3d_close"); }
static void makeMask(char *name, d_Mask * maskRules) { void *map, *mask; RASTER3D_Region region; int tileX, tileY, tileZ, x, y, z, cacheSize; double value; float floatNull; cacheSize = Rast3d_cache_size_encode(RASTER3D_USE_CACHE_XY, 1); if (NULL == G_find_raster3d(name, "")) Rast3d_fatal_error(_("3D raster map <%s> not found"), name); map = Rast3d_open_cell_old(name, G_mapset(), RASTER3D_DEFAULT_WINDOW, DCELL_TYPE, cacheSize); if (map == NULL) Rast3d_fatal_error(_("Unable to open 3D raster map <%s>"), name); Rast3d_get_region_struct_map(map, ®ion); Rast3d_get_tile_dimensions_map(map, &tileX, &tileY, &tileZ); mask = Rast3d_open_new_param(Rast3d_mask_file(), FCELL_TYPE, cacheSize, ®ion, FCELL_TYPE, RASTER3D_COMPRESSION, 0, tileX, tileY, tileZ); if (mask == NULL) Rast3d_fatal_error(_("Unable to open 3D raster mask file")); Rast3d_min_unlocked(map, RASTER3D_USE_CACHE_X); Rast3d_autolock_on(map); Rast3d_unlock_all(map); Rast3d_min_unlocked(mask, RASTER3D_USE_CACHE_X); Rast3d_autolock_on(mask); Rast3d_unlock_all(mask); Rast3d_set_null_value(&floatNull, 1, FCELL_TYPE); for (z = 0; z < region.depths; z++) { if ((z % tileZ) == 0) { Rast3d_unlock_all(map); Rast3d_unlock_all(mask); } for (y = 0; y < region.rows; y++) /* We count from north to south in the cube coordinate system */ for (x = 0; x < region.cols; x++) { value = Rast3d_get_double_region(map, x, y, z); if (Rast3d_mask_d_select((DCELL *) & value, maskRules)) Rast3d_put_float(mask, x, y, z, (float)floatNull); /* mask-out value */ else Rast3d_put_float(mask, x, y, z, (float)0.0); /* not mask-out value */ } if ((z % tileZ) == 0) { if (!Rast3d_flush_tiles_in_cube (mask, 0, 0, MAX(0, z - tileZ), region.rows - 1, region.cols - 1, z)) Rast3d_fatal_error(_("makeMask: error flushing tiles in cube")); } } if (!Rast3d_flush_all_tiles(mask)) Rast3d_fatal_error(_("makeMask: error flushing all tiles")); Rast3d_autolock_off(map); Rast3d_unlock_all(map); Rast3d_autolock_off(mask); Rast3d_unlock_all(mask); if (!Rast3d_close(mask)) Rast3d_fatal_error(_("Unable to close 3D raster mask file")); if (!Rast3d_close(map)) Rast3d_fatal_error(_("Unable to close raster map <%s>"), name); }
int main(int argc, char **argv) { RASTER3D_Map *input; RASTER3D_Map *output; RASTER3D_Region region; struct GModule *module; stat_func *method_fn; double quantile; int x, y, z; /* Initialize GRASS */ G_gisinit(argv[0]); module = G_define_module(); G_add_keyword(_("raster3d")); G_add_keyword(_("neighbor")); G_add_keyword(_("aggregation")); G_add_keyword(_("statistics")); G_add_keyword(_("filter")); module->description = _("Makes each voxel value a " "function of the values assigned to the voxels " "around it, and stores new voxel values in an output 3D raster map"); /* Get parameters from user */ set_params(); if (G_parser(argc, argv)) exit(EXIT_FAILURE); if (NULL == G_find_raster3d(param.input->answer, "")) Rast3d_fatal_error(_("3D raster map <%s> not found"), param.input->answer); Rast3d_init_defaults(); Rast3d_get_window(®ion); nx = region.cols; ny = region.rows; nz = region.depths; /* Size fo the moving window */ x_size = atoi(param.window->answers[0]); y_size = atoi(param.window->answers[1]); z_size = atoi(param.window->answers[2]); /* Distances in all directions */ x_dist = x_size / 2; y_dist = y_size / 2; z_dist = z_size / 2; /* Maximum size of the buffer */ size = x_size * y_size * z_size; /* Set the computation method */ method_fn = menu[find_method(param.method->answer)].method; if (param.quantile->answer) quantile = atof(param.quantile->answer); else quantile = 0.0; input = Rast3d_open_cell_old(param.input->answer, G_find_raster3d(param.input->answer, ""), ®ion, RASTER3D_TILE_SAME_AS_FILE, RASTER3D_USE_CACHE_DEFAULT); if (input == NULL) Rast3d_fatal_error(_("Unable to open 3D raster map <%s>"), param.input->answer); output = Rast3d_open_new_opt_tile_size(param.output->answer, RASTER3D_USE_CACHE_X, ®ion, DCELL_TYPE, 32); if (output == NULL) Rast3d_fatal_error(_("Unable to open 3D raster map <%s>"), param.output->answer); Rast3d_min_unlocked(output, RASTER3D_USE_CACHE_X); Rast3d_autolock_on(output); Rast3d_unlock_all(output); DCELL *buff = NULL, value; buff = (DCELL *) calloc(size, sizeof(DCELL)); if (buff == NULL) Rast3d_fatal_error(_("Unable to allocate buffer")); for (z = 0; z < nz; z++) { for (y = 0; y < ny; y++) { for (x = 0; x < nx; x++) { /* Gather values in moving window */ int num = gather_values(input, buff, x, y, z); /* Compute the resulting value */ if (num > 0) (*method_fn) (&value, buff, num, &quantile); else Rast_set_d_null_value(&value, 1); /* Write the value */ Rast3d_put_double(output, x, y, z, value); } } } free(buff); if (!Rast3d_flush_all_tiles(output)) G_fatal_error(_("Error flushing tiles")); Rast3d_autolock_off(output); Rast3d_unlock_all(output); Rast3d_close(input); Rast3d_close(output); return 0; }
static void bin_to_raster3d(char *null, int map_type, int is_integer, int is_signed, int bytes, int byte_swap, int row_swap, int depth_swap) { int x, y, z; int col, row, depth; DCELL value; FCELL fvalue; DCELL null_value; int tileX, tileY, tileZ; if (null) null_value = atof(null); Rast3d_get_tile_dimensions_map(map, &tileX, &tileY, &tileZ); Rast3d_min_unlocked(map, RASTER3D_USE_CACHE_X); Rast3d_autolock_on(map); Rast3d_unlock_all(map); G_message(_("Loading %s data with %i bytes ... (%dx%dx%d)"), (is_integer? "integer":"floating point "), bytes, region.cols, region.rows, region.depths); for (z = 0; z < region.depths; z++) { G_percent(z, region.depths, 1); if ((z % tileZ) == 0) Rast3d_unlock_all(map); for (y = 0; y < region.rows; y++) {/* go south to north */ for (x = 0; x < region.cols; x++) { /* From west to east */ col = x; /* The default is to read rows from north to south */ row = y; /* From bottom to the top */ depth = z; /* Read rows as from south to north */ if (row_swap) row = region.rows - y - 1; /* Read XY layer from top to bottom */ if (depth_swap) depth = region.depths - z - 1; /* Read value from binary file */ read_cell(&value, is_integer, is_signed, bytes, byte_swap); /* Write value to the 3D raster map */ if (map_type == DCELL_TYPE) { if (null && value == null_value) Rast3d_set_null_value(&value, 1, DCELL_TYPE); Rast3d_put_double(map, col, row, depth, value); } else { fvalue = (FCELL) value; if (null && value == null_value) Rast3d_set_null_value(&fvalue, 1, FCELL_TYPE); Rast3d_put_double(map, col, row, depth, fvalue); } } } } if (!Rast3d_flush_all_tiles(map)) G_fatal_error(_("Error flushing tiles")); Rast3d_autolock_off(map); Rast3d_unlock_all(map); G_percent(1, 1, 1); }
void asciiToG3d(FILE * fp, RASTER3D_Region * region, int convertNull, char *nullValue) { int x, y, z; int col, row, depth; double value; char buff[256]; int tileX, tileY, tileZ; Rast3d_get_tile_dimensions_map(map, &tileX, &tileY, &tileZ); Rast3d_min_unlocked(map, RASTER3D_USE_CACHE_X); Rast3d_autolock_on(map); Rast3d_unlock_all(map); G_message(_("Loading data ... (%dx%dx%d)"), region->cols, region->rows, region->depths); G_debug(3, "asciiToG3d: writing the 3D raster map, with rows %i cols %i depths %i", region->rows, region->cols, region->depths); for (z = 0; z < region->depths; z++) { G_percent(z, region->depths, 1); if ((z % tileZ) == 0) Rast3d_unlock_all(map); for (y = 0; y < region->rows; y++) /* go south to north */ for (x = 0; x < region->cols; x++) { /* From west to east */ col = x; /* The default is to read rows from north to south */ row = y; /* From bottom to the top */ depth = z; /* Read rows as from south to north */ if (rowOrder == ROW_ORDER_SOUTH_TO_NORTH) row = region->rows - y - 1; /* Read XY layer from top to bottom */ if (depthOrder == DEPTH_ORDER_TOP_TO_BOTTOM) depth = region->depths - z - 1; if (fscanf(fp, "%s", buff) != 1) { if (feof(fp)) G_warning(_("End of file reached while still loading data.")); G_debug(3, "missing data at col=%d row=%d depth=%d last_value=[%.4f]", x + 1, y + 1, z + 1, value); fatalError("asciiToG3d: read failed"); } /* Check for null value */ if (convertNull && strncmp(buff, nullValue, strlen(nullValue)) == 0) { Rast3d_set_null_value(&value, 1, DCELL_TYPE); } else { if (sscanf(buff, "%lf", &value) != 1) { G_warning(_("Invalid value detected")); G_debug(1, "invalid value at col=%d row=%d depth=%d last_value=[%s]", x + 1, y + 1, z + 1, buff); fatalError("asciiToG3d: read failed"); } } /* Write the data */ Rast3d_put_double(map, col, row, depth, value); } } if (fscanf(fp, "%lf", &value) == 1) { G_warning(_("Data exists in input file after fully importing " "expected data. [%.4f ...]"), value); } if (!Rast3d_flush_all_tiles(map)) fatalError("asciiTog3d: error flushing tiles"); Rast3d_autolock_off(map); Rast3d_unlock_all(map); G_percent(1, 1, 1); }
int test_large_file_sparse_random(int depths, int rows, int cols, int tile_size) { int sum = 0; int x, y, z, i; DCELL value, random_value; DCELL *random_value_vector = G_calloc(RAND_VALUE_VECTOR_SIZE, sizeof(DCELL)); G_message("Testing DCELL put function for large files filled with sparse random values"); RASTER3D_Region region; RASTER3D_Map *map = NULL; /* We need to set up a specific region for the new raster3d map. * First we safe the default region. */ Rast3d_get_window(®ion); region.bottom = -365.5; region.top = 365.5; region.south = -90; region.north = 90; region.west = -180; region.east = 180; region.rows = rows; region.cols = cols; region.depths = depths; Rast3d_adjust_region(®ion); G_message("Creating 3D raster map filled with sparse random values"); map = Rast3d_open_new_opt_tile_size("test_put_get_value_dcell_large_sparse_random", RASTER3D_USE_CACHE_XY, ®ion, DCELL_TYPE, tile_size); /* The window is the same as the map region ... of course */ Rast3d_set_window_map(map, ®ion); srand(1); /* We fill the random value vector */ for(i = 0; i < RAND_VALUE_VECTOR_SIZE; i++) { /* Put the counter as cell value */ value = (DCELL)rand(); value /= RAND_MAX; if(value <= 0.7) value = 0.0; else if(value <= 0.8) value = 1.0; else if(value <= 0.9) value = 2.0; else if(value <= 1.0) value = 3.0; else value = 4.0; random_value_vector[i] = value; } i = 0; for(z = 0; z < region.depths; z++) { G_percent(z, region.depths, 1); for(y = 0; y < region.rows; y++) { for(x = 0; x < region.cols; x++) { /* Put the counter as cell value */ value = random_value_vector[i]; Rast3d_put_value(map, x, y, z, &value, DCELL_TYPE); i++; if(i == RAND_VALUE_VECTOR_SIZE) i = 0; } } } G_percent(1, 1, 1); /* Write everything to the disk */ Rast3d_flush_all_tiles(map); Rast3d_close(map); G_message("Verifying 3D raster map filled with sparse random values"); map = Rast3d_open_cell_old("test_put_get_value_dcell_large_sparse_random", G_mapset(), ®ion, DCELL_TYPE, RASTER3D_USE_CACHE_XY); i = 0; for(z = 0; z < region.depths; z++) { G_percent(z, region.depths, 1); for(y = 0; y < region.rows; y++) { for(x = 0; x < region.cols; x++) { /* Check the counter as cell value */ Rast3d_get_value(map, x, y, z, &value, DCELL_TYPE); if(fabs(value - random_value_vector[i]) > EPSILON) { G_message("At: z %i y %i x %i -- value %.14lf != %.14lf\n", z, y, x, value, random_value); sum++; } i++; if(i == RAND_VALUE_VECTOR_SIZE) i = 0; } } } G_percent(1, 1, 1); Rast3d_close(map); G_free(random_value_vector); G_remove("grid3", "test_put_get_value_dcell_large_sparse_random"); return sum; }
int test_large_file_zeros(int depths, int rows, int cols, int tile_size) { int sum = 0; int x, y, z; DCELL value; G_message("Testing DCELL put function for large files filled with zeros"); RASTER3D_Region region; RASTER3D_Map *map = NULL; /* We need to set up a specific region for the new raster3d map. * First we safe the default region. */ Rast3d_get_window(®ion); region.bottom = -365.5; region.top = 365.5; region.south = -90; region.north = 90; region.west = -180; region.east = 180; region.rows = rows; region.cols = cols; region.depths = depths; Rast3d_adjust_region(®ion); G_message("Creating 3D raster map filled with zeros"); map = Rast3d_open_new_opt_tile_size("test_put_get_value_dcell_large_zeros", RASTER3D_USE_CACHE_XY, ®ion, DCELL_TYPE, tile_size); /* The window is the same as the map region ... of course */ Rast3d_set_window_map(map, ®ion); for(z = 0; z < region.depths; z++) { G_percent(z, region.depths, 1); for(y = 0; y < region.rows; y++) { for(x = 0; x < region.cols; x++) { /* Put the counter as cell value */ value = 0.0; Rast3d_put_value(map, x, y, z, &value, DCELL_TYPE); } } } G_percent(1, 1, 1); /* Write everything to the disk */ Rast3d_flush_all_tiles(map); Rast3d_close(map); G_message("Verifying 3D raster map filled with zeros"); map = Rast3d_open_cell_old("test_put_get_value_dcell_large_zeros", G_mapset(), ®ion, DCELL_TYPE, RASTER3D_USE_CACHE_XY); for(z = 0; z < region.depths; z++) { G_percent(z, region.depths, 1); for(y = 0; y < region.rows; y++) { for(x = 0; x < region.cols; x++) { /* Check the counter as cell value */ Rast3d_get_value(map, x, y, z, &value, DCELL_TYPE); if(value > EPSILON) { G_message("At: z %i y %i x %i -- value %.14lf != 0.0\n", z, y, x, value); sum++; } } } } G_percent(1, 1, 1); Rast3d_close(map); G_remove("grid3", "test_put_get_value_dcell_large_zeros"); return sum; }
static void modifyNull(char *name, d_Mask * maskRules, int changeNull, double newNullVal) { void *map, *mapOut; RASTER3D_Region region; int tileX, tileY, tileZ, x, y, z; double value; int doCompress, doLzw, doRle, precision; int cacheSize; cacheSize = Rast3d_cache_size_encode(RASTER3D_USE_CACHE_XY, 1); if (NULL == G_find_raster3d(name, "")) Rast3d_fatal_error(_("3D raster map <%s> not found"), name); fprintf(stderr, "name %s Mapset %s \n", name, G_mapset()); map = Rast3d_open_cell_old(name, G_mapset(), RASTER3D_DEFAULT_WINDOW, DCELL_TYPE, cacheSize); if (map == NULL) Rast3d_fatal_error(_("Unable to open 3D raster map <%s>"), name); Rast3d_get_region_struct_map(map, ®ion); Rast3d_get_tile_dimensions_map(map, &tileX, &tileY, &tileZ); Rast3d_get_compression_mode(&doCompress, &doLzw, &doRle, &precision); mapOut = Rast3d_open_new_param(name, DCELL_TYPE, RASTER3D_USE_CACHE_XY, ®ion, Rast3d_file_type_map(map), doLzw, doRle, Rast3d_tile_precision_map(map), tileX, tileY, tileZ); if (mapOut == NULL) Rast3d_fatal_error(_("modifyNull: error opening tmp file")); Rast3d_min_unlocked(map, RASTER3D_USE_CACHE_X); Rast3d_autolock_on(map); Rast3d_unlock_all(map); Rast3d_min_unlocked(mapOut, RASTER3D_USE_CACHE_X); Rast3d_autolock_on(mapOut); Rast3d_unlock_all(mapOut); for (z = 0; z < region.depths; z++) { if ((z % tileZ) == 0) { Rast3d_unlock_all(map); Rast3d_unlock_all(mapOut); } for (y = 0; y < region.rows; y++) for (x = 0; x < region.cols; x++) { value = Rast3d_get_double_region(map, x, y, z); if (Rast3d_is_null_value_num(&value, DCELL_TYPE)) { if (changeNull) { value = newNullVal; } } else if (Rast3d_mask_d_select((DCELL *) & value, maskRules)) { Rast3d_set_null_value(&value, 1, DCELL_TYPE); } Rast3d_put_double(mapOut, x, y, z, value); } if ((z % tileZ) == 0) { if (!Rast3d_flush_tiles_in_cube (mapOut, 0, 0, MAX(0, z - tileZ), region.rows - 1, region.cols - 1, z)) Rast3d_fatal_error(_("modifyNull: error flushing tiles in cube")); } } if (!Rast3d_flush_all_tiles(mapOut)) Rast3d_fatal_error(_("modifyNull: error flushing all tiles")); Rast3d_autolock_off(map); Rast3d_unlock_all(map); Rast3d_autolock_off(mapOut); Rast3d_unlock_all(mapOut); if (!Rast3d_close(map)) Rast3d_fatal_error(_("Unable to close raster map")); if (!Rast3d_close(mapOut)) Rast3d_fatal_error(_("modifyNull: Unable to close tmp file")); }
static int close_new(RASTER3D_Map * map) { char path[GPATH_MAX]; struct Categories cats; struct History hist; Rast3d_remove_color(map->fileName); /* create empty cats file */ Rast_init_cats(NULL, &cats); Rast3d_write_cats(map->fileName, &cats); Rast_free_cats(&cats); /*generate the history file, use the normal G_ functions */ Rast_short_history(map->fileName, "raster3d", &hist); Rast_command_history(&hist); /*Use the G3d function to write the history file, * otherwise the path is wrong */ if (Rast3d_write_history(map->fileName, &hist) < 0) { G_warning(_("Unable to write history for 3D raster map <%s>"), map->fileName); } Rast3d_range_write(map); close(map->data_fd); /* finally move tempfile to data file */ Rast3d_filename(path, RASTER3D_CELL_ELEMENT, map->fileName, map->mapset); #ifdef __MINGW32__ if (CopyFile(map->tempName, path, FALSE) == 0) { #else if (link(map->tempName, path) < 0) { #endif if (rename(map->tempName, path)) { G_warning(_("Unable to move temp raster map <%s> to 3D raster map <%s>"), map->tempName, path); return 0; } } else remove(map->tempName); return 1; } static int close_cell_new(RASTER3D_Map * map) { long ltmp; if (map->useCache) if (!Rast3d_flush_all_tiles(map)) { G_warning(_("Unable to flush all tiles")); return 0; } if (!Rast3d_flush_index(map)) { G_warning(_("Unable to flush index")); return 0; } /* write the header info which was filled with dummy values at the */ /* opening time */ if (lseek(map->data_fd, (long)(map->offset - sizeof(int) - sizeof(long)), SEEK_SET) == -1) { G_warning(_("Unable to position file")); return 0; } if (!Rast3d_write_ints(map->data_fd, map->useXdr, &(map->indexNbytesUsed), 1)) { G_warning(_("Unable to write header for 3D raster map <%s>"), map->fileName); return 0; } Rast3d_long_encode(&(map->indexOffset), (unsigned char *)<mp, 1); if (write(map->data_fd, <mp, sizeof(long)) != sizeof(long)) { G_warning(_("Unable to write header for 3D raster map <%s>"), map->fileName); return 0; } if (!close_new(map) != 0) { G_warning(_("Unable to create 3D raster map <%s>"), map->fileName); return 0; } return 1; }