Exemple #1
0
int open_map(MAPS* rast) {
	
	int row, col;
	int fd;
	char* mapset;
	struct Cell_head cellhd;
	int bufsize;
	void* tmp_buf;
	
    mapset = (char*)G_find_raster2(rast->elevname, "");	
	
	    if (mapset == NULL)
		G_fatal_error(_("Raster map <%s> not found"), rast->elevname);
	
		rast->fd = Rast_open_old(rast->elevname, mapset);
		Rast_get_cellhd(rast->elevname, mapset, &cellhd);
		rast->raster_type = Rast_map_type(rast->elevname, mapset);

    if (window.ew_res < cellhd.ew_res || window.ns_res < cellhd.ns_res)
	G_warning(_("Region resolution shoudn't be lesser than map %s resolution. Run g.region rast=%s to set proper resolution"),
		      rast->elevname, rast->elevname);

		tmp_buf=Rast_allocate_buf(rast->raster_type);
		rast->elev = (FCELL**) G_malloc((row_buffer_size+1) * sizeof(FCELL*));
	
	for (row = 0; row < row_buffer_size+1; ++row) {
		rast->elev[row] = Rast_allocate_buf(FCELL_TYPE);
		Rast_get_row(rast->fd, tmp_buf,row, rast->raster_type);
				for (col=0;col<ncols;++col)
			get_cell(col, rast->elev[row], tmp_buf, rast->raster_type);
  } /* end elev */

G_free(tmp_buf);
return 0;
}
Exemple #2
0
static void rast_segment_load(SEGMENT * segment, int rowio,
                              RASTER_MAP_TYPE map_type)
{
    void *raster_row = Rast_allocate_input_buf(map_type);
    int row;

    for (row = 0; row < Rast_input_window_rows(); row++) {
        /* TODO: free mem */
        Rast_get_row(rowio, raster_row, row, map_type);
        Segment_put_row(segment, raster_row, row);
    }
}
Exemple #3
0
static int calc_mu(int *fds, double *mu, int bands)
{
    int i;
    int rows = Rast_window_rows();
    int cols = Rast_window_cols();
    void *rowbuf = NULL;

    for (i = 0; i < bands; i++) {
	RASTER_MAP_TYPE maptype;
	int row, col;
	double sum = 0.;

	maptype = Rast_get_map_type(fds[i]);

	/* don't assume each image is of the same type */
	if (rowbuf)
	    G_free(rowbuf);
	if ((rowbuf = Rast_allocate_buf(maptype)) == NULL)
	    G_fatal_error(_("Unable allocate memory for row buffer"));

	G_message(_("Computing means for band %d..."), i + 1);
	for (row = 0; row < rows; row++) {
	    void *ptr = rowbuf;

	    G_percent(row, rows - 1, 2);

	    Rast_get_row(fds[i], rowbuf, row, maptype);

	    for (col = 0; col < cols; col++) {
		/* skip null cells */
		if (Rast_is_null_value(ptr, maptype)) {
		    ptr = G_incr_void_ptr(ptr, Rast_cell_size(maptype));
		    continue;
		}

		sum += Rast_get_d_value(ptr, maptype);
		ptr = G_incr_void_ptr(ptr, Rast_cell_size(maptype));
	    }
	}

	mu[i] = sum / (double)(rows * cols);
    }

    if (rowbuf)
	G_free(rowbuf);

    return 0;
}
Exemple #4
0
void *read_raster(void *buf, const int fd, const RASTER_MAP_TYPE rtype)
{
    void *tmpbuf = buf;
    int rows = Rast_window_rows();
    int i;

    G_message(_("Reading raster map..."));

    for (i = 0; i < rows; i++) {
	G_percent(i + 1, rows, 10);

	Rast_get_row(fd, tmpbuf, i, rtype);
	tmpbuf =
	    G_incr_void_ptr(tmpbuf, Rast_cell_size(rtype) * Rast_window_cols());
    }

    return tmpbuf;
}
Exemple #5
0
int shift_buffers(int row)
{
int i;
int col;
void* tmp_buf;
FCELL* tmp_elev_buf, *slope_tmp, *aspect_tmp;

tmp_buf=Rast_allocate_buf(elevation.raster_type);
tmp_elev_buf=elevation.elev[0];
  
	for (i = 1; i < row_buffer_size+1; ++i)
elevation.elev[i - 1] = elevation.elev[i];

elevation.elev[row_buffer_size]=tmp_elev_buf;
Rast_get_row(elevation.fd, tmp_buf,row+row_radius_size+1, elevation.raster_type);

	for (col=0;col<ncols;++col)
get_cell(col, elevation.elev[row_buffer_size], tmp_buf, elevation.raster_type);

G_free(tmp_buf);
return 0;
}
Exemple #6
0
int read_row(void *buf)
{
    void *p;

    if (last_read)
	return (0);
    if (first_read) {
	blank_line(buf);
	first_read = 0;
    }
    else {
	if (row_count >= n_rows) {
	    last_read = 1;
	    blank_line(buf);
	}
	else {
	    /* The buf variable is a void pointer and thus */
	    /* points to anything. Therefore, it's size is */
	    /* unknown and thus, it cannot be used for pointer */
	    /* arithmetic (some compilers treat this as an error */
	    /* - SGI MIPSPro compiler for one). Make the */
	    /* assumption that data_size is the proper number of */
	    /* bytes and cast the buf variable to char * before */
	    /* incrementing */
	    p = ((char *)buf) + data_size;
	    Rast_get_row(input_fd, p, row_count++, data_type);
	    p = buf;
	    Rast_set_null_value(p, 1, data_type);

	    /* Again we need to cast p to char * under the */
	    /* assumption that the increment is the proper */
	    /* number of bytes. */
	    p = ((char *)p) + (row_length + 1) * data_size;
	    Rast_set_null_value(p, 1, data_type);
	}
    }
    return (row_length + 2);
}
Exemple #7
0
int main(int argc, char **argv)
{
    struct band B[3];
    int row;
    int next_row;
    int overlay;
    struct Cell_head window;
    struct GModule *module;
    struct Flag *flag_n;
    int i;

    G_gisinit(argv[0]);

    module = G_define_module();
    G_add_keyword(_("display"));
    G_add_keyword(_("graphics"));
    G_add_keyword(_("raster"));
    G_add_keyword("RGB");
    module->description =
	_("Displays three user-specified raster maps "
	  "as red, green, and blue overlays in the active graphics frame.");

    flag_n = G_define_flag();
    flag_n->key = 'n';
    flag_n->description = _("Make null cells opaque");
    flag_n->guisection = _("Null cells");
    
    for (i = 0; i < 3; i++) {
	char buff[80];

	sprintf(buff, _("Name of raster map to be used for <%s>"),
		color_names[i]);

	B[i].opt = G_define_standard_option(G_OPT_R_MAP);
	B[i].opt->key = G_store(color_names[i]);
	B[i].opt->description = G_store(buff);
    }

    if (G_parser(argc, argv))
	exit(EXIT_FAILURE);

    /* Do screen initializing stuff */
    D_open_driver();
    
    overlay = !flag_n->answer;

    D_setup(0);
    D_set_overlay_mode(overlay);

    for (i = 0; i < 3; i++) {
	/* Get name of layer to be used */
	char *name = B[i].opt->answer;

	/* Make sure map is available */
	B[i].file = Rast_open_old(name, "");

	B[i].type = Rast_get_map_type(B[i].file);

	/* Reading color lookup table */
	if (Rast_read_colors(name, "", &B[i].colors) == -1)
	    G_fatal_error(_("Color file for <%s> not available"), name);

	B[i].array = Rast_allocate_buf(B[i].type);
    }

    /* read in current window */
    G_get_window(&window);

    D_raster_draw_begin();

    next_row = 0;
    for (row = 0; row < window.rows;) {
	G_percent(row, window.rows, 5);

	for (i = 0; i < 3; i++)
	    Rast_get_row(B[i].file, B[i].array, row, B[i].type);

	if (row == next_row)
	    next_row = D_draw_raster_RGB(next_row,
					 B[0].array, B[1].array, B[2].array,
					 &B[0].colors, &B[1].colors,
					 &B[2].colors, B[0].type, B[1].type,
					 B[2].type);
	else if (next_row > 0)
	    row = next_row;
	else
	    break;
    }
    G_percent(window.rows, window.rows, 5);
    D_raster_draw_end();
    
    D_save_command(G_recreate_command());
    D_close_driver();

    /* Close the raster maps */
    for (i = 0; i < 3; i++)
	Rast_close(B[i].file);

    exit(EXIT_SUCCESS);
}
Exemple #8
0
/* ************************************************************************* */
void rast3d_cross_section(void *map,RASTER3D_Region region, int elevfd, int outfd)
{
    int col, row;
    int rows, cols, depths, typeIntern;
    FCELL *fcell = NULL;
    DCELL *dcell = NULL;
    void *elevrast;
    void *ptr;
    int intvalue;
    float fvalue;
    double dvalue;
    double elevation = 0;
    double north, east;
    struct Cell_head window;
 
    Rast_get_window(&window);
    
    rows = region.rows;
    cols = region.cols;
    depths = region.depths;
    
    /*Typ of the RASTER3D Tile */
    typeIntern = Rast3d_tile_type_map(map);

    /*Allocate mem for the output maps row */
    if (typeIntern == FCELL_TYPE)
        fcell = Rast_allocate_f_buf();
    else if (typeIntern == DCELL_TYPE)
        dcell = Rast_allocate_d_buf();

    /*Mem for the input map row */
    elevrast = Rast_allocate_buf(globalElevMapType);

    for (row = 0; row < rows; row++) {
        G_percent(row, rows - 1, 10);

        /*Read the input map row */
        Rast_get_row(elevfd, elevrast, row, globalElevMapType);

        for (col = 0, ptr = elevrast; col < cols; col++, ptr =
            G_incr_void_ptr(ptr, Rast_cell_size(globalElevMapType))) {

            if (Rast_is_null_value(ptr, globalElevMapType)) {
                if (typeIntern == FCELL_TYPE)
                    Rast_set_null_value(&fcell[col], 1, FCELL_TYPE);
                else if (typeIntern == DCELL_TYPE)
                    Rast_set_null_value(&dcell[col], 1, DCELL_TYPE);
                continue;
            }

            /*Read the elevation value */
            if (globalElevMapType == CELL_TYPE) {
                intvalue = *(CELL *) ptr;
                elevation = intvalue;
            } else if (globalElevMapType == FCELL_TYPE) {
                fvalue = *(FCELL *) ptr;
                elevation = fvalue;
            } else if (globalElevMapType == DCELL_TYPE) {
                dvalue = *(DCELL *) ptr;
                elevation = dvalue;
            }

            /* Compute the coordinates */
            north = Rast_row_to_northing((double)row + 0.5, &window);
            east = Rast_col_to_easting((double)col + 0.5, &window);

            /* Get the voxel value */
            if (typeIntern == FCELL_TYPE)
                Rast3d_get_region_value(map, north, east, elevation, &fcell[col], FCELL_TYPE);

            if (typeIntern == DCELL_TYPE)
                Rast3d_get_region_value(map, north, east, elevation, &dcell[col], DCELL_TYPE);
        }

        /*Write the data to the output map */
        if (typeIntern == FCELL_TYPE)
            Rast_put_f_row(outfd, fcell);

        if (typeIntern == DCELL_TYPE)
            Rast_put_d_row(outfd, dcell);
    }
    G_debug(3, "\nDone\n");

    /*Free the mem */
    if (elevrast)
        G_free(elevrast);
    if (dcell)
        G_free(dcell);
    if (fcell)
        G_free(fcell);
}
Exemple #9
0
static int calc_covariance(int *fds, double **covar, double *mu, int bands)
{
    int j, k;
    int rows = Rast_window_rows();
    int cols = Rast_window_cols();
    int row, col;

    for (j = 0; j < bands; j++) {
	RASTER_MAP_TYPE maptype = Rast_get_map_type(fds[j]);
	void *rowbuf1 = NULL;
	void *rowbuf2 = NULL;

	/* don't assume each image is of the same type */
	if (rowbuf1)
	    G_free(rowbuf1);
	if ((rowbuf1 = Rast_allocate_buf(maptype)) == NULL)
	    G_fatal_error(_("Unable allocate memory for row buffer"));

	G_message(_("Computing row %d (of %d) of covariance matrix..."),
		  j + 1, bands);
	for (row = 0; row < rows; row++) {
	    void *ptr1, *ptr2;

	    G_percent(row, rows - 1, 2);

	    Rast_get_row(fds[j], rowbuf1, row, maptype);

	    for (k = j; k < bands; k++) {
		RASTER_MAP_TYPE maptype2 = Rast_get_map_type(fds[k]);

		/* don't assume each image is of the same type */
		if (rowbuf2)
		    G_free(rowbuf2);
		if ((rowbuf2 = Rast_allocate_buf(maptype2)) == NULL)
		    G_fatal_error(_("Unable to allocate memory for row buffer"));

		Rast_get_row(fds[k], rowbuf2, row, maptype2);

		ptr1 = rowbuf1;
		ptr2 = rowbuf2;

		for (col = 0; col < cols; col++) {
		    /* skip null cells */
		    if (Rast_is_null_value(ptr1, maptype) ||
			Rast_is_null_value(ptr2, maptype2)) {
			ptr1 = G_incr_void_ptr(ptr1, Rast_cell_size(maptype));
			ptr2 = G_incr_void_ptr(ptr2, Rast_cell_size(maptype2));
			continue;
		    }

		    covar[j][k] +=
			((double)Rast_get_d_value(ptr1, maptype) -
			 mu[j]) * ((double)Rast_get_d_value(ptr2,
						   maptype2) - mu[k]);

		    ptr1 = G_incr_void_ptr(ptr1, Rast_cell_size(maptype));
		    ptr2 = G_incr_void_ptr(ptr2, Rast_cell_size(maptype2));
		}

		covar[k][j] = covar[j][k];
	    }
	}
    }

    return 0;
}
Exemple #10
0
int camera_angle(char *name)
{
    int row, col, nrows, ncols;
    double XC = group.XC;
    double YC = group.YC;
    double ZC = group.ZC;
    double c_angle, c_angle_min, c_alt, c_az, slope, aspect;
    double radians_to_degrees = 180.0 / M_PI;
    /* double degrees_to_radians = M_PI / 180.0; */
    DCELL e1, e2, e3, e4, e5, e6, e7, e8, e9;
    double factor, V, H, dx, dy, dz, key;
    double north, south, east, west, ns_med;
    FCELL *fbuf0, *fbuf1, *fbuf2, *tmpbuf, *outbuf;
    int elevfd, outfd;
    struct Cell_head cellhd;
    struct Colors colr;
    FCELL clr_min, clr_max;
    struct History hist;
    char *type;

    G_message(_("Calculating camera angle to local surface..."));
    
    select_target_env();
    
    /* align target window to elevation map, otherwise we get artefacts
     * like in r.slope.aspect -a */
     
    Rast_get_cellhd(elev_name, elev_mapset, &cellhd);

    Rast_align_window(&target_window, &cellhd);
    Rast_set_window(&target_window);
    
    elevfd = Rast_open_old(elev_name, elev_mapset);
    if (elevfd < 0) {
	G_fatal_error(_("Could not open elevation raster"));
	return 1;
    }

    nrows = target_window.rows;
    ncols = target_window.cols;
    
    outfd = Rast_open_new(name, FCELL_TYPE);
    fbuf0 = Rast_allocate_buf(FCELL_TYPE);
    fbuf1 = Rast_allocate_buf(FCELL_TYPE);
    fbuf2 = Rast_allocate_buf(FCELL_TYPE);
    outbuf = Rast_allocate_buf(FCELL_TYPE);
    
    /* give warning if location units are different from meters and zfactor=1 */
    factor = G_database_units_to_meters_factor();
    if (factor != 1.0)
	G_warning(_("Converting units to meters, factor=%.6f"), factor);

    G_begin_distance_calculations();
    north = Rast_row_to_northing(0.5, &target_window);
    ns_med = Rast_row_to_northing(1.5, &target_window);
    south = Rast_row_to_northing(2.5, &target_window);
    east = Rast_col_to_easting(2.5, &target_window);
    west = Rast_col_to_easting(0.5, &target_window);
    V = G_distance(east, north, east, south) * 4;
    H = G_distance(east, ns_med, west, ns_med) * 4;
    
    c_angle_min = 90;
    Rast_get_row(elevfd, fbuf1, 0, FCELL_TYPE);
    Rast_get_row(elevfd, fbuf2, 1, FCELL_TYPE);

    for (row = 0; row < nrows; row++) {
	G_percent(row, nrows, 2);
	
	Rast_set_null_value(outbuf, ncols, FCELL_TYPE);

	/* first and last row */
	if (row == 0 || row == nrows - 1) {
	    Rast_put_row(outfd, outbuf, FCELL_TYPE);
	    continue;
	}
	
	tmpbuf = fbuf0;
	fbuf0 = fbuf1;
	fbuf1 = fbuf2;
	fbuf2 = tmpbuf;
	
	Rast_get_row(elevfd, fbuf2, row + 1, FCELL_TYPE);

	north = Rast_row_to_northing(row + 0.5, &target_window);

	for (col = 1; col < ncols - 1; col++) {
	    
	    e1 = fbuf0[col - 1];
	    if (Rast_is_d_null_value(&e1))
		continue;
	    e2 = fbuf0[col];
	    if (Rast_is_d_null_value(&e2))
		continue;
	    e3 = fbuf0[col + 1];
	    if (Rast_is_d_null_value(&e3))
		continue;
	    e4 = fbuf1[col - 1];
	    if (Rast_is_d_null_value(&e4))
		continue;
	    e5 = fbuf1[col];
	    if (Rast_is_d_null_value(&e5))
		continue;
	    e6 = fbuf1[col + 1];
	    if (Rast_is_d_null_value(&e6))
		continue;
	    e7 = fbuf2[col - 1];
	    if (Rast_is_d_null_value(&e7))
		continue;
	    e8 = fbuf2[col];
	    if (Rast_is_d_null_value(&e8))
		continue;
	    e9 = fbuf2[col + 1];
	    if (Rast_is_d_null_value(&e9))
		continue;
	    
	    dx = ((e1 + e4 + e4 + e7) - (e3 + e6 + e6 + e9)) / H;
	    dy = ((e7 + e8 + e8 + e9) - (e1 + e2 + e2 + e3)) / V;
	    
	    /* compute topographic parameters */
	    key = dx * dx + dy * dy;
	    /* slope in radians */
	    slope = atan(sqrt(key));

	    /* aspect in radians */
	    if (key == 0.)
		aspect = 0.;
	    else if (dx == 0) {
		if (dy > 0)
		    aspect = M_PI / 2;
		else
		    aspect = 1.5 * M_PI;
	    }
	    else {
		aspect = atan2(dy, dx);
		if (aspect <= 0.)
		    aspect = 2 * M_PI + aspect;
	    }
	    
	    /* camera altitude angle in radians */
	    east = Rast_col_to_easting(col + 0.5, &target_window);
	    dx = east - XC;
	    dy = north - YC;
	    dz = ZC - e5;
	    c_alt = atan(sqrt(dx * dx + dy * dy) / dz);

	    /* camera azimuth angle in radians */
	    c_az = atan(dy / dx);
	    if (east < XC && north != YC)
		c_az += M_PI;
	    else if (north < YC && east > XC)
		c_az += 2 * M_PI;
		
	    /* camera angle to real ground */
	    /* orthogonal to ground: 90 degrees */
	    /* parallel to ground: 0 degrees */
	    c_angle = asin(cos(c_alt) * cos(slope) - sin(c_alt) * sin(slope) * cos(c_az - aspect));
	    
	    outbuf[col] = c_angle * radians_to_degrees;
	    if (c_angle_min > outbuf[col])
		c_angle_min = outbuf[col];
	}
	Rast_put_row(outfd, outbuf, FCELL_TYPE);
    }
    G_percent(row, nrows, 2);

    Rast_close(elevfd);
    Rast_close(outfd);
    G_free(fbuf0);
    G_free(fbuf1);
    G_free(fbuf2);
    G_free(outbuf);

    type = "raster";
    Rast_short_history(name, type, &hist);
    Rast_command_history(&hist);
    Rast_write_history(name, &hist);
    
    Rast_init_colors(&colr);
    if (c_angle_min < 0) {
	clr_min = (FCELL)((int)(c_angle_min / 10 - 1)) * 10;
	clr_max = 0;
	Rast_add_f_color_rule(&clr_min, 0, 0, 0, &clr_max, 0,
				  0, 0, &colr);
    }
    clr_min = 0;
    clr_max = 10;
    Rast_add_f_color_rule(&clr_min, 0, 0, 0, &clr_max, 255,
			      0, 0, &colr);
    clr_min = 10;
    clr_max = 40;
    Rast_add_f_color_rule(&clr_min, 255, 0, 0, &clr_max, 255,
			      255, 0, &colr);
    clr_min = 40;
    clr_max = 90;
    Rast_add_f_color_rule(&clr_min, 255, 255, 0, &clr_max, 0,
			      255, 0, &colr);

    Rast_write_colors(name, G_mapset(), &colr);

    select_current_env();

    return 1;
}
Exemple #11
0
int main(int argc, char *argv[])
{
    struct GModule *module;
    int infile;
    const char *mapset;
    size_t cell_size;
    int ytile, xtile, y, overlap;
    int *outfiles;
    void *inbuf;

    G_gisinit(argv[0]);

    module = G_define_module();
    G_add_keyword(_("raster"));
    G_add_keyword(_("tiling"));
    module->description =
	_("Splits a raster map into tiles.");

    parm.rastin = G_define_standard_option(G_OPT_R_INPUT);

    parm.rastout = G_define_option();
    parm.rastout->key = "output";
    parm.rastout->type = TYPE_STRING;
    parm.rastout->required = YES;
    parm.rastout->multiple = NO;
    parm.rastout->description = _("Output base name");

    parm.width = G_define_option();
    parm.width->key = "width";
    parm.width->type = TYPE_INTEGER;
    parm.width->required = YES;
    parm.width->multiple = NO;
    parm.width->description = _("Width of tiles (columns)");

    parm.height = G_define_option();
    parm.height->key = "height";
    parm.height->type = TYPE_INTEGER;
    parm.height->required = YES;
    parm.height->multiple = NO;
    parm.height->description = _("Height of tiles (rows)");

    parm.overlap = G_define_option();
    parm.overlap->key = "overlap";
    parm.overlap->type = TYPE_INTEGER;
    parm.overlap->required = NO;
    parm.overlap->multiple = NO;
    parm.overlap->description = _("Overlap of tiles");

    if (G_parser(argc, argv))
	exit(EXIT_FAILURE);

    G_get_set_window(&src_w);
    overlap = parm.overlap->answer ? atoi(parm.overlap->answer) : 0;

    mapset = G_find_raster2(parm.rastin->answer, "");
    if (mapset == NULL)
        G_fatal_error(_("Raster map <%s> not found"), parm.rastin->answer);

    /* set window to old map */
    Rast_get_cellhd(parm.rastin->answer, "", &src_w);
    dst_w = src_w;
    dst_w.cols = atoi(parm.width->answer);
    dst_w.rows = atoi(parm.height->answer);
    G_adjust_Cell_head(&dst_w, 1, 1);

    xtiles = (src_w.cols + dst_w.cols - 1) / dst_w.cols;
    ytiles = (src_w.rows + dst_w.rows - 1) / dst_w.rows;

    G_debug(1, "X: %d * %d, Y: %d * %d",
	    xtiles, dst_w.cols, ytiles, dst_w.rows);

    src_w.cols = xtiles * dst_w.cols + 2 * overlap;
    src_w.rows = ytiles * dst_w.rows + 2 * overlap;
    src_w.west = src_w.west - overlap * src_w.ew_res;
    src_w.east = src_w.west + (src_w.cols + 2 * overlap) * src_w.ew_res;
    src_w.north = src_w.north + overlap * src_w.ns_res;
    src_w.south = src_w.north - (src_w.rows + 2 * overlap) * src_w.ns_res;

    Rast_set_input_window(&src_w);

    /* set the output region */
    ovl_w = dst_w;
    ovl_w.cols = ovl_w.cols + 2 * overlap;
    ovl_w.rows = ovl_w.rows + 2 * overlap;

    G_adjust_Cell_head(&ovl_w, 1, 1);
    Rast_set_output_window(&ovl_w);

    infile = Rast_open_old(parm.rastin->answer, "");
    map_type = Rast_get_map_type(infile);
    cell_size = Rast_cell_size(map_type);

    inbuf = Rast_allocate_input_buf(map_type);

    outfiles = G_malloc(xtiles * sizeof(int));

    G_debug(1, "X: %d * %d, Y: %d * %d",
	    xtiles, dst_w.cols, ytiles, dst_w.rows);

    G_message(_("Generating %d x %d = %d tiles..."), xtiles, ytiles, xtiles * ytiles);
    for (ytile = 0; ytile < ytiles; ytile++) {
	G_debug(1, "reading y tile: %d", ytile);
	G_percent(ytile, ytiles, 2);
	for (xtile = 0; xtile < xtiles; xtile++) {
	    char name[GNAME_MAX];
	    sprintf(name, "%s-%03d-%03d", parm.rastout->answer, ytile, xtile);
	    outfiles[xtile] = Rast_open_new(name, map_type);
	}
	
	for (y = 0; y < ovl_w.rows; y++) {
	    int row = ytile * dst_w.rows + y;
	    G_debug(1, "reading row: %d", row);
	    Rast_get_row(infile, inbuf, row, map_type);
	    
	    for (xtile = 0; xtile < xtiles; xtile++) {
		int cells = xtile * dst_w.cols;
		void *ptr = G_incr_void_ptr(inbuf, cells * cell_size);
		Rast_put_row(outfiles[xtile], ptr, map_type);
	    }
	}

	for (xtile = 0; xtile < xtiles; xtile++) {
	    Rast_close(outfiles[xtile]);
	    write_support_files(xtile, ytile, overlap);
	}
    }

    Rast_close(infile);

    return EXIT_SUCCESS;
}
Exemple #12
0
int init_search(int depr_fd)
{
    int r, c, r_nbr, c_nbr, ct_dir;
    CELL *depr_buf, ele_value;
    int nextdr[8] = { 1, -1, 0, 0, -1, 1, 1, -1 };
    int nextdc[8] = { 0, 0, -1, 1, 1, -1, 1, -1 };
    char asp_value, is_null;
    WAT_ALT wa;
    ASP_FLAG af, af_nbr;
    GW_LARGE_INT n_depr_cells = 0;

    nxt_avail_pt = heap_size = 0;

    /* load edge cells and real depressions to A* heap */
    if (depr_fd >= 0)
	depr_buf = Rast_allocate_buf(CELL_TYPE);
    else
	depr_buf = NULL;

    G_message(_("Initializing A* search..."));
    for (r = 0; r < nrows; r++) {
	G_percent(r, nrows, 2);

	if (depr_fd >= 0) {
	    Rast_get_row(depr_fd, depr_buf, r, CELL_TYPE);
	}

	for (c = 0; c < ncols; c++) {

	    seg_get(&aspflag, (char *)&af, r, c);
	    is_null = FLAG_GET(af.flag, NULLFLAG);

	    if (is_null)
		continue;

	    asp_value = 0;
	    if (r == 0 || r == nrows - 1 || c == 0 || c == ncols - 1) {

		if (r == 0 && c == 0)
		    asp_value = -7;
		else if (r == 0 && c == ncols - 1)
		    asp_value = -5;
		else if (r == nrows - 1 && c == 0)
		    asp_value = -1;
		else if (r == nrows - 1 && c == ncols - 1)
		    asp_value = -3;
		else if (r == 0)
		    asp_value = -2;
		else if (c == 0)
		    asp_value = -4;
		else if (r == nrows - 1)
		    asp_value = -6;
		else if (c == ncols - 1)
		    asp_value = -8;

		seg_get(&watalt, (char *)&wa, r, c);
		ele_value = wa.ele;
		heap_add(r, c, ele_value);
		FLAG_SET(af.flag, INLISTFLAG);
		FLAG_SET(af.flag, EDGEFLAG);
		af.asp = asp_value;
		seg_put(&aspflag, (char *)&af, r, c);
		continue;
	    }

	    /* any neighbour NULL ? */
	    for (ct_dir = 0; ct_dir < sides; ct_dir++) {
		/* get r, c (r_nbr, c_nbr) for neighbours */
		r_nbr = r + nextdr[ct_dir];
		c_nbr = c + nextdc[ct_dir];

		seg_get(&aspflag, (char *)&af_nbr, r_nbr, c_nbr);
		is_null = FLAG_GET(af_nbr.flag, NULLFLAG);

		if (is_null) {
		    asp_value = -1 * drain[r - r_nbr + 1][c - c_nbr + 1];
		    seg_get(&watalt, (char *)&wa, r, c);
		    ele_value = wa.ele;
		    heap_add(r, c, ele_value);
		    FLAG_SET(af.flag, INLISTFLAG);
		    FLAG_SET(af.flag, EDGEFLAG);
		    af.asp = asp_value;
		    seg_put(&aspflag, (char *)&af, r, c);

		    break;
		}
	    }
	    if (asp_value) /* some neighbour was NULL, point added to list */
		continue;
	    
	    /* real depression ? */
	    if (depr_fd >= 0) {
		if (!Rast_is_c_null_value(&depr_buf[c]) && depr_buf[c] != 0) {
		    seg_get(&watalt, (char *)&wa, r, c);
		    ele_value = wa.ele;
		    heap_add(r, c, ele_value);
		    FLAG_SET(af.flag, INLISTFLAG);
		    FLAG_SET(af.flag, DEPRFLAG);
		    af.asp = asp_value;
		    seg_put(&aspflag, (char *)&af, r, c);
		    n_depr_cells++;
		}
	    }
	}
    }
    G_percent(nrows, nrows, 2);	/* finish it */

    if (depr_fd >= 0) {
	Rast_close(depr_fd);
	G_free(depr_buf);
    }

    G_debug(1, "%lld edge cells", heap_size - n_depr_cells);
    if (n_depr_cells)
	G_debug(1, "%lld cells in depressions", n_depr_cells);

    return 1;
}
Exemple #13
0
/* ************************************************************************* */
void write_vtk_points(input_maps * in, FILE * fp, RASTER3D_Region region, int dp,
                      int type, double scale)
{
    int x, y, z, percentage = 0;
    int rows, cols, depths;
    void *rast_top = NULL;
    void *rast_bottom = NULL;
    void *ptr_top = NULL;
    void *ptr_bottom = NULL;
    double topval = 0, bottomval = 0;
    double zcoor, ycoor, xcoor;
    double zcoor1, ycoor1, xcoor1;

    rows = region.rows;
    cols = region.cols;
    depths = region.depths;

    rast_top = Rast_allocate_buf(in->topMapType);
    rast_bottom = Rast_allocate_buf(in->bottomMapType);

    G_debug(3, _("write_vtk_points: Writing point coordinates"));

    for (z = 0; z < depths; z++) {

        for (y = 0; y < rows; y++) {
            G_percent(percentage, (rows * depths - 1), 10);
            percentage++;

            Rast_get_row(in->top, rast_top, y, in->topMapType);

            Rast_get_row(in->bottom, rast_bottom, y, in->bottomMapType);

            for (x = 0, ptr_top = rast_top, ptr_bottom = rast_bottom;
                    x < cols;
                    x++, ptr_top =
                        G_incr_void_ptr(ptr_top, Rast_cell_size(in->topMapType)),
                    ptr_bottom =
                        G_incr_void_ptr(ptr_bottom,
                                        Rast_cell_size(in->bottomMapType))) {

                /*Get the values */
                topval =
                    get_raster_value_as_double(in->topMapType, ptr_top, 0.0);
                bottomval =
                    get_raster_value_as_double(in->bottomMapType, ptr_bottom,
                                               0.0);

                if (type == 1) { /*Structured Grid */
                    /*Calculate the coordinates */
                    xcoor =
                        region.west + (region.ew_res / 2 +
                                       region.ew_res * (x));
                    /* Here the raster3d north->south coordinate system is used */
                    ycoor =
                        region.north - (region.ns_res / 2 +
                                        region.ns_res * (y));
                    zcoor =
                        (bottomval +
                         z * (topval - bottomval) / (depths - 1)) * scale;

                    xcoor -= x_extent;
                    ycoor -= y_extent;

                    fprintf(fp, "%.*f ", dp, xcoor);
                    fprintf(fp, "%.*f ", dp, ycoor);
                    fprintf(fp, "%.*f\n", dp, zcoor);
                } else { /*Unstructured Grid */
                    /*Write for every cell the coordinates for a hexahedron -> 8 points */
                    /*VTK Hexaeder */
                    /* bottom
                     * 3 --- 2
                     * |     |
                     * 0 --- 1

                     * top
                     * 7 --- 6
                     * |     |
                     * 4 --- 5

                     */
                    xcoor = region.west + (region.ew_res * (x)); /*0, 3, 4, 7 */
                    /* Here the raster3d north->south coordinate system is used */
                    ycoor = region.north - (region.ns_res * (y)); /*2, 3, 6, 7 */
                    zcoor = (bottomval + z * (topval - bottomval) / (depths)) * scale; /*0, 1, 2, 3 */

                    xcoor1 = region.west + (region.ew_res + region.ew_res * (x)); /*1, 2, 5, 6 */
                    /* Here the raster3d north->south coordinate system is used */
                    ycoor1 = region.north - (region.ns_res + region.ns_res * (y)); /*0, 1, 4, 5 */
                    zcoor1 = (bottomval + z * (topval - bottomval) / (depths) + (topval - bottomval) / (depths)) * scale; /*4, 5, ,6 ,7 */

                    xcoor -= x_extent;
                    ycoor -= y_extent;

                    xcoor1 -= x_extent;
                    ycoor1 -= y_extent;


                    /*0 */
                    fprintf(fp, "%.*f ", dp, xcoor);
                    fprintf(fp, "%.*f ", dp, ycoor1);
                    fprintf(fp, "%.*f\n", dp, zcoor);
                    /*1 */
                    fprintf(fp, "%.*f ", dp, xcoor1);
                    fprintf(fp, "%.*f ", dp, ycoor1);
                    fprintf(fp, "%.*f\n", dp, zcoor);
                    /*2 */
                    fprintf(fp, "%.*f ", dp, xcoor1);
                    fprintf(fp, "%.*f ", dp, ycoor);
                    fprintf(fp, "%.*f\n", dp, zcoor);
                    /*3 */
                    fprintf(fp, "%.*f ", dp, xcoor);
                    fprintf(fp, "%.*f ", dp, ycoor);
                    fprintf(fp, "%.*f\n", dp, zcoor);

                    /*4 */
                    fprintf(fp, "%.*f ", dp, xcoor);
                    fprintf(fp, "%.*f ", dp, ycoor1);
                    fprintf(fp, "%.*f\n", dp, zcoor1);
                    /*5 */
                    fprintf(fp, "%.*f ", dp, xcoor1);
                    fprintf(fp, "%.*f ", dp, ycoor1);
                    fprintf(fp, "%.*f\n", dp, zcoor1);
                    /*6 */
                    fprintf(fp, "%.*f ", dp, xcoor1);
                    fprintf(fp, "%.*f ", dp, ycoor);
                    fprintf(fp, "%.*f\n", dp, zcoor1);
                    /*7 */
                    fprintf(fp, "%.*f ", dp, xcoor);
                    fprintf(fp, "%.*f ", dp, ycoor);
                    fprintf(fp, "%.*f\n", dp, zcoor1);
                }
            }
        }
    }

    if (type == 1)
        fprintf(fp, "POINT_DATA %i\n", region.cols * region.rows * region.depths); /*We have pointdata */

    return;
}
Exemple #14
0
void process(void)
{

    /*--------------------------------------------------------------------------*/
    /*                              INITIALISE                                  */

    /*--------------------------------------------------------------------------*/


    DCELL *row_in,		/* Buffer large enough to hold `wsize'  */
     *row_out = NULL,		/* raster rows. When GRASS reads in a   */
	/* raster row, each element is of type  */
	/* DCELL        */
	*window_ptr,		/* Stores local terrain window.         */
	centre;			/* Elevation of central cell in window. */

    CELL *featrow_out = NULL;	/* store features in CELL */

    struct Cell_head region;	/* Structure to hold region information */

    int nrows,			/* Will store the current number of     */
      ncols,			/* rows and columns in the raster.      */
      row, col,			/* Counts through each row and column   */
	/* of the input raster.                 */
      wind_row,			/* Counts through each row and column   */
      wind_col,			/* of the local neighbourhood window.   */
     *index_ptr;		/* Row permutation vector for LU decomp. */

    double **normal_ptr,	/* Cross-products matrix.               */
     *obs_ptr,			/* Observed vector.                     */
      temp;			/* Unused */

    double *weight_ptr;		/* Weighting matrix for observed values. */


    /*--------------------------------------------------------------------------*/
    /*                     GET RASTER AND WINDOW DETAILS                        */

    /*--------------------------------------------------------------------------*/

    G_get_window(&region);	/* Fill out the region structure (the   */
    /* geographical limits etc.)            */

    nrows = Rast_window_rows();	/* Find out the number of rows and      */
    ncols = Rast_window_cols();	/* columns of the raster.               */


    if ((region.ew_res / region.ns_res >= 1.01) ||	/* If EW and NS resolns are    */
	(region.ns_res / region.ew_res >= 1.01)) {	/* >1% different, warn user.      */
	G_warning(_("E-W and N-S grid resolutions are different. Taking average."));
	resoln = (region.ns_res + region.ew_res) / 2;
    }
    else
	resoln = region.ns_res;


    /*--------------------------------------------------------------------------*/
    /*              RESERVE MEMORY TO HOLD Z VALUES AND MATRICES                */

    /*--------------------------------------------------------------------------*/

    row_in = (DCELL *) G_malloc(ncols * sizeof(DCELL) * wsize);
    /* Reserve `wsize' rows of memory.      */

    if (mparam != FEATURE)
	row_out = Rast_allocate_buf(DCELL_TYPE);	/* Initialise output row buffer.     */
    else
	featrow_out = Rast_allocate_buf(CELL_TYPE);	/* Initialise output row buffer.  */

    window_ptr = (DCELL *) G_malloc(SQR(wsize) * sizeof(DCELL));
    /* Reserve enough memory for local wind. */

    weight_ptr = (double *)G_malloc(SQR(wsize) * sizeof(double));
    /* Reserve enough memory weights matrix. */

    normal_ptr = dmatrix(0, 5, 0, 5);	/* Allocate memory for 6*6 matrix       */
    index_ptr = ivector(0, 5);	/* and for 1D vector holding indices    */
    obs_ptr = dvector(0, 5);	/* and for 1D vector holding observed z */


    /* ---------------------------------------------------------------- */
    /* -            CALCULATE LEAST SQUARES COEFFICIENTS              - */
    /* ---------------------------------------------------------------- */

    /*--- Calculate weighting matrix. ---*/

    find_weight(weight_ptr);

    /* Initial coefficients need only be found once since they are 
       constant for any given window size. The only element that 
       changes is the observed vector (RHS of normal equations). */

    /*--- Find normal equations in matrix form. ---*/

    find_normal(normal_ptr, weight_ptr);


    /*--- Apply LU decomposition to normal equations. ---*/

    if (constrained) {
	G_ludcmp(normal_ptr, 5, index_ptr, &temp);
	/* To constrain the quadtratic 
	   through the central cell, ignore 
	   the calculations involving the
	   coefficient f. Since these are 
	   all in the last row and column of
	   the matrix, simply redimension.   */
	/* disp_matrix(normal_ptr,obs_ptr,obs_ptr,5);
	 */
    }

    else {
	G_ludcmp(normal_ptr, 6, index_ptr, &temp);
	/* disp_matrix(normal_ptr,obs_ptr,obs_ptr,6);
	 */
    }


    /*--------------------------------------------------------------------------*/
    /*          PROCESS INPUT RASTER AND WRITE OUT RASTER LINE BY LINE          */

    /*--------------------------------------------------------------------------*/

    if (mparam != FEATURE)
	for (wind_row = 0; wind_row < EDGE; wind_row++)
	    Rast_put_row(fd_out, row_out, DCELL_TYPE);	/* Write out the edge cells as NULL.    */
    else
	for (wind_row = 0; wind_row < EDGE; wind_row++)
	    Rast_put_row(fd_out, featrow_out, CELL_TYPE);	/* Write out the edge cells as NULL.    */

    for (wind_row = 0; wind_row < wsize - 1; wind_row++)
	Rast_get_row(fd_in, row_in + (wind_row * ncols), wind_row,
			 DCELL_TYPE);
    /* Read in enough of the first rows to  */
    /* allow window to be examined.         */

    for (row = EDGE; row < (nrows - EDGE); row++) {
	G_percent(row + 1, nrows - EDGE, 2);

	Rast_get_row(fd_in, row_in + ((wsize - 1) * ncols), row + EDGE,
			 DCELL_TYPE);

	for (col = EDGE; col < (ncols - EDGE); col++) {
	    /* Find central z value */
	    centre = *(row_in + EDGE * ncols + col);

	    for (wind_row = 0; wind_row < wsize; wind_row++)
		for (wind_col = 0; wind_col < wsize; wind_col++)

		    /* Express all window values relative   */
		    /* to the central elevation.            */
		    *(window_ptr + (wind_row * wsize) + wind_col) =
			*(row_in + (wind_row * ncols) + col + wind_col -
			  EDGE) - centre;


	    /*--- Use LU back substitution to solve normal equations. ---*/
	    find_obs(window_ptr, obs_ptr, weight_ptr);

	    /*      disp_wind(window_ptr); 
	       disp_matrix(normal_ptr,obs_ptr,obs_ptr,6);
	     */

	    if (constrained) {
		G_lubksb(normal_ptr, 5, index_ptr, obs_ptr);
		/*
		   disp_matrix(normal_ptr,obs_ptr,obs_ptr,5);
		 */
	    }

	    else {
		G_lubksb(normal_ptr, 6, index_ptr, obs_ptr);
		/*      
		   disp_matrix(normal_ptr,obs_ptr,obs_ptr,6);
		 */

	    }

	    /*--- Calculate terrain parameter based on quad. coefficients. ---*/
	    if (mparam == FEATURE)
		*(featrow_out + col) = (CELL) feature(obs_ptr);
	    else
		*(row_out + col) = param(mparam, obs_ptr);

	    if (mparam == ELEV)
		*(row_out + col) += centre;	/* Add central elevation back */
	}

	if (mparam != FEATURE)
	    Rast_put_row(fd_out, row_out, DCELL_TYPE);	/* Write the row buffer to the output   */
	/* raster.                              */
	else			/* write FEATURE to CELL */
	    Rast_put_row(fd_out, featrow_out, CELL_TYPE);	/* Write the row buffer to the output       */
	/* raster.                              */

	/* 'Shuffle' rows down one, and read in */
	/*  one new row.                        */
	for (wind_row = 0; wind_row < wsize - 1; wind_row++)
	    for (col = 0; col < ncols; col++)
		*(row_in + (wind_row * ncols) + col) =
		    *(row_in + ((wind_row + 1) * ncols) + col);
    }

    for (wind_row = 0; wind_row < EDGE; wind_row++) {
	if (mparam != FEATURE)
	    Rast_put_row(fd_out, row_out, DCELL_TYPE);	/* Write out the edge cells as NULL. */
	else
	    Rast_put_row(fd_out, featrow_out, CELL_TYPE);	/* Write out the edge cells as NULL. */
    }

    /*--------------------------------------------------------------------------*/
    /*     FREE MEMORY USED TO STORE RASTER ROWS, LOCAL WINDOW AND MATRICES     */

    /*--------------------------------------------------------------------------*/

    G_free(row_in);
    if (mparam != FEATURE)
	G_free(row_out);
    else
	G_free(featrow_out);

    G_free(window_ptr);
    free_dmatrix(normal_ptr, 0, 5, 0, 5);
    free_dvector(obs_ptr, 0, 5);
    free_ivector(index_ptr, 0, 5);
}
Exemple #15
0
int zoom(struct Cell_head *window, const char *name, const char *mapset)
{
    int fd;
    void *raster, *rast_ptr;
    RASTER_MAP_TYPE map_type;
    int row, col;
    int nrows, ncols;
    int top, bottom, left, right, mark;
    double north, south, east, west;

    G_adjust_Cell_head3(window, 0, 0, 0);
    Rast_set_window(window);
    nrows = window->rows;
    ncols = window->cols;

    fd = Rast_open_old(name, mapset);
    map_type = Rast_get_map_type(fd);
    raster = Rast_allocate_buf(map_type);

    /* find first non-null row */
    top = nrows;
    bottom = -1;
    left = ncols;
    right = -1;
    for (row = 0; row < nrows; row++) {
	Rast_get_row(fd, rast_ptr = raster, row, map_type);
	for (col = 0; col < ncols; col++) {
	    if (!Rast_is_null_value(rast_ptr, map_type))
		break;
	    rast_ptr = G_incr_void_ptr(rast_ptr, Rast_cell_size(map_type));
	}
	if (col == ncols)
	    continue;
	if (row < top)
	    top = row;
	if (row > bottom)
	    bottom = row;
	if (col < left)
	    left = col;
	for (mark = col; col < ncols; col++) {
	    if (!Rast_is_null_value(rast_ptr, map_type))
		mark = col;
	    rast_ptr = G_incr_void_ptr(rast_ptr, Rast_cell_size(map_type));
	}
	if (mark > right)
	    right = mark;
    }
    Rast_close(fd);
    G_free(raster);

    /* no data everywhere? */
    if (bottom < 0)
	return 0;

    north = window->north - top * window->ns_res;
    south = window->north - (bottom + 1) * window->ns_res;
    west = window->west + left * window->ew_res;
    east = window->west + (right + 1) * window->ew_res;

    window->north = north;
    window->south = south;
    window->east = east;
    window->west = west;

    return 1;
}
Exemple #16
0
/* Process the raster and do atmospheric corrections.
   Params:
   * INPUT FILE
   ifd: input file descriptor
   iref: input file has radiance values (default is reflectance) ?
   iscale: input file's range (default is min = 0, max = 255)
   ialt_fd: height map file descriptor, negative if global value is used
   ivis_fd: visibility map file descriptor, negative if global value is used

   * OUTPUT FILE
   ofd: output file descriptor
   oflt: if true use FCELL_TYPE for output
   oscale: output file's range (default is min = 0, max = 255)
 */
static void process_raster(int ifd, InputMask imask, ScaleRange iscale,
			   int ialt_fd, int ivis_fd, int ofd, bool oint,
			   ScaleRange oscale)
{
    FCELL *buf;			/* buffer for the input values */
    FCELL *alt = NULL;		/* buffer for the elevation values */
    FCELL *vis = NULL;		/* buffer for the visibility values */
    FCELL prev_alt = -1.f;
    FCELL prev_vis = -1.f;
    int row, col, nrows, ncols;
    /* switch on optimization automatically if elevation and/or visibility map is given */
    bool optimize = (ialt_fd >= 0 || ivis_fd >= 0);
    
#ifdef _NO_OPTIMIZE_
    optimize = false;
#endif

    /* do initial computation with global elevation and visibility values */
    TransformInput ti;

    ti = compute();

    /* use a cache to increase computation speed when an elevation map 
     * and/or a visibility map is given */
    TICache ticache;

    /* allocate memory for buffers */
    buf = (FCELL *) Rast_allocate_buf(FCELL_TYPE);
    if (ialt_fd >= 0)
	alt = (FCELL *) Rast_allocate_buf(FCELL_TYPE);
    if (ivis_fd >= 0)
	vis = (FCELL *) Rast_allocate_buf(FCELL_TYPE);

    nrows = Rast_window_rows();
    ncols = Rast_window_cols();

    for (row = 0; row < nrows; row++) {
	G_percent(row, nrows, 1);	/* keep the user informed of our progress */

	/* read the next row */
	Rast_get_row(ifd, buf, row, FCELL_TYPE);

	/* read the next row of elevation values */
	if (ialt_fd >= 0)
	    Rast_get_row(ialt_fd, alt, row, FCELL_TYPE);

	/* read the next row of elevation values */
	if (ivis_fd >= 0)
	    Rast_get_row(ivis_fd, vis, row, FCELL_TYPE);

	/* loop over all the values in the row */
	for (col = 0; col < ncols; col++) {
	    if ((vis && Rast_is_f_null_value(&vis[col])) ||
		(alt && Rast_is_f_null_value(&alt[col])) ||
		Rast_is_f_null_value(&buf[col])) {
		Rast_set_f_null_value(&buf[col], 1);
		continue;
	    }
	    if (ialt_fd >= 0) {
		if (alt[col] < 0)
		    alt[col] = 0; /* on or below sea level, all the same for 6S */
		else
		    alt[col] /= 1000.0f;	/* converting to km from input which should be in meter */

		/* round to nearest altitude bin */
		/* rounding result: watch out for fp representation error */
		alt[col] = ((int) (alt[col] * BIN_ALT + 0.5)) / BIN_ALT;
	    }
	    if (ivis_fd >= 0) {
		if (vis[col] < 0)
		    vis[col] = 0; /* negative visibility is invalid, print a WARNING ? */

		/* round to nearest visibility bin */
		/* rounding result: watch out for fp representation error */
		vis[col] = ((int) (vis[col] + 0.5));
	    }

	    /* check if both maps are active and if whether any value has changed */
	    if ((ialt_fd >= 0) && (ivis_fd >= 0) &&
		((prev_vis != vis[col]) || (prev_alt != alt[col]))) {
		prev_alt = alt[col];	/* update new values */
		prev_vis = vis[col];
		if (optimize) {
		    int in_cache = ticache.search(alt[col], vis[col], &ti);

		    if (!in_cache) {
			pre_compute_hv(alt[col], vis[col]);	/* re-compute transformation inputs */
			ti = compute();	/* ... */

			ticache.add(ti, alt[col], vis[col]);
		    }
		}
		else {
		    pre_compute_hv(alt[col], vis[col]);	/* re-compute transformation inputs */
		    ti = compute();	/* ... */
		}
	    }
	    else {		/* only one of the maps is being used */

		if ((ivis_fd >= 0) && (prev_vis != vis[col])) {
		    prev_vis = vis[col];	/* keep track of previous visibility */

		    if (optimize) {
			int in_cache = ticache.search(0, vis[col], &ti);

			if (!in_cache) {
			    pre_compute_v(vis[col]);	/* re-compute transformation inputs */
			    ti = compute();	/* ... */

			    ticache.add(ti, 0, vis[col]);
			}
		    }
		    else {
			pre_compute_v(vis[col]);	/* re-compute transformation inputs */
			ti = compute();	/* ... */
		    }
		}

		if ((ialt_fd >= 0) && (prev_alt != alt[col])) {
		    prev_alt = alt[col];	/* keep track of previous altitude */

		    if (optimize) {
			int in_cache = ticache.search(alt[col], 0, &ti);

			if (!in_cache) {
			    pre_compute_h(alt[col]);	/* re-compute transformation inputs */
			    ti = compute();	/* ... */

			    ticache.add(ti, alt[col], 0);
			}
		    }
		    else {
			pre_compute_h(alt[col]);	/* re-compute transformation inputs */
			ti = compute();	/* ... */
		    }
		}
	    }
	    G_debug(3, "Computed r%d (%d), c%d (%d)", row, nrows, col, ncols);
	    /* transform from iscale.[min,max] to [0,1] */
	    buf[col] =
		(buf[col] - iscale.min) / ((float)iscale.max -
					   (float)iscale.min);
	    buf[col] = transform(ti, imask, buf[col]);
	    /* transform from [0,1] to oscale.[min,max] */
	    buf[col] =
		buf[col] * ((float)oscale.max - (float)oscale.min) +
		oscale.min;

	    if (oint && (buf[col] > (float)oscale.max))
		G_warning(_("The output data will overflow. Reflectance > 100%%"));
	}

	/* write output */
	if (oint)
	    write_fp_to_cell(ofd, buf);
	else
	    Rast_put_row(ofd, buf, FCELL_TYPE);
    }
    G_percent(1, 1, 1);

    /* free allocated memory */
    G_free(buf);
    if (ialt_fd >= 0)
	G_free(alt);
    if (ivis_fd >= 0)
	G_free(vis);
}
Exemple #17
0
int main(int argc, char *argv[])
{
    int out_fd, base_raster;
    char *infile, *outmap;
    int percent;
    double zrange_min, zrange_max, d_tmp;
    double irange_min, irange_max;
    unsigned long estimated_lines;

    RASTER_MAP_TYPE rtype, base_raster_data_type;
    struct History history;
    char title[64];
    SEGMENT base_segment;
    struct PointBinning point_binning;
    void *base_array;
    void *raster_row;
    struct Cell_head region;
    struct Cell_head input_region;
    int rows, last_rows, row0, cols;		/* scan box size */
    int row;		/* counters */

    int pass, npasses;
    unsigned long line, line_total;
    unsigned int counter;
    unsigned long n_invalid;
    char buff[BUFFSIZE];
    double x, y, z;
    double intensity;
    int arr_row, arr_col;
    unsigned long count, count_total;
    int point_class;

    double zscale = 1.0;
    double iscale = 1.0;
    double res = 0.0;

    struct BinIndex bin_index_nodes;
    bin_index_nodes.num_nodes = 0;
    bin_index_nodes.max_nodes = 0;
    bin_index_nodes.nodes = 0;

    struct GModule *module;
    struct Option *input_opt, *output_opt, *percent_opt, *type_opt, *filter_opt, *class_opt;
    struct Option *method_opt, *base_raster_opt;
    struct Option *zrange_opt, *zscale_opt;
    struct Option *irange_opt, *iscale_opt;
    struct Option *trim_opt, *pth_opt, *res_opt;
    struct Option *file_list_opt;
    struct Flag *print_flag, *scan_flag, *shell_style, *over_flag, *extents_flag;
    struct Flag *intens_flag, *intens_import_flag;
    struct Flag *set_region_flag;
    struct Flag *base_rast_res_flag;
    struct Flag *only_valid_flag;

    /* LAS */
    LASReaderH LAS_reader;
    LASHeaderH LAS_header;
    LASSRSH LAS_srs;
    LASPointH LAS_point;
    int return_filter;

    const char *projstr;
    struct Cell_head cellhd, loc_wind;

    unsigned int n_filtered;

    G_gisinit(argv[0]);

    module = G_define_module();
    G_add_keyword(_("raster"));
    G_add_keyword(_("import"));
    G_add_keyword(_("LIDAR"));
    G_add_keyword(_("statistics"));
    G_add_keyword(_("conversion"));
    G_add_keyword(_("aggregation"));
    G_add_keyword(_("binning"));
    module->description =
	_("Creates a raster map from LAS LiDAR points using univariate statistics.");

    input_opt = G_define_standard_option(G_OPT_F_BIN_INPUT);
    input_opt->required = NO;
    input_opt->label = _("LAS input file");
    input_opt->description = _("LiDAR input files in LAS format (*.las or *.laz)");
    input_opt->guisection = _("Input");

    output_opt = G_define_standard_option(G_OPT_R_OUTPUT);
    output_opt->required = NO;
    output_opt->guisection = _("Output");

    file_list_opt = G_define_standard_option(G_OPT_F_INPUT);
    file_list_opt->key = "file";
    file_list_opt->label = _("File containing names of LAS input files");
    file_list_opt->description = _("LiDAR input files in LAS format (*.las or *.laz)");
    file_list_opt->required = NO;
    file_list_opt->guisection = _("Input");

    method_opt = G_define_option();
    method_opt->key = "method";
    method_opt->type = TYPE_STRING;
    method_opt->required = NO;
    method_opt->description = _("Statistic to use for raster values");
    method_opt->options =
	"n,min,max,range,sum,mean,stddev,variance,coeff_var,median,percentile,skewness,trimmean";
    method_opt->answer = "mean";
    method_opt->guisection = _("Statistic");
    G_asprintf((char **)&(method_opt->descriptions),
               "n;%s;"
               "min;%s;"
               "max;%s;"
               "range;%s;"
               "sum;%s;"
               "mean;%s;"
               "stddev;%s;"
               "variance;%s;"
               "coeff_var;%s;"
               "median;%s;"
               "percentile;%s;"
               "skewness;%s;"
               "trimmean;%s",
               _("Number of points in cell"),
               _("Minimum value of point values in cell"),
               _("Maximum value of point values in cell"),
               _("Range of point values in cell"),
               _("Sum of point values in cell"),
               _("Mean (average) value of point values in cell"),
               _("Standard deviation of point values in cell"),
               _("Variance of point values in cell"),
               _("Coefficient of variance of point values in cell"),
               _("Median value of point values in cell"),
               _("pth (nth) percentile of point values in cell"),
               _("Skewness of point values in cell"),
               _("Trimmed mean of point values in cell"));

    type_opt = G_define_standard_option(G_OPT_R_TYPE);
    type_opt->required = NO;
    type_opt->answer = "FCELL";

    base_raster_opt = G_define_standard_option(G_OPT_R_INPUT);
    base_raster_opt->key = "base_raster";
    base_raster_opt->required = NO;
    base_raster_opt->label =
        _("Subtract raster values from the Z coordinates");
    base_raster_opt->description =
        _("The scale for Z is applied beforehand, the range filter for"
          " Z afterwards");
    base_raster_opt->guisection = _("Transform");

    zrange_opt = G_define_option();
    zrange_opt->key = "zrange";
    zrange_opt->type = TYPE_DOUBLE;
    zrange_opt->required = NO;
    zrange_opt->key_desc = "min,max";
    zrange_opt->description = _("Filter range for Z data (min,max)");
    zrange_opt->guisection = _("Selection");

    zscale_opt = G_define_option();
    zscale_opt->key = "zscale";
    zscale_opt->type = TYPE_DOUBLE;
    zscale_opt->required = NO;
    zscale_opt->answer = "1.0";
    zscale_opt->description = _("Scale to apply to Z data");
    zscale_opt->guisection = _("Transform");

    irange_opt = G_define_option();
    irange_opt->key = "intensity_range";
    irange_opt->type = TYPE_DOUBLE;
    irange_opt->required = NO;
    irange_opt->key_desc = "min,max";
    irange_opt->description = _("Filter range for intensity values (min,max)");
    irange_opt->guisection = _("Selection");

    iscale_opt = G_define_option();
    iscale_opt->key = "intensity_scale";
    iscale_opt->type = TYPE_DOUBLE;
    iscale_opt->required = NO;
    iscale_opt->answer = "1.0";
    iscale_opt->description = _("Scale to apply to intensity values");
    iscale_opt->guisection = _("Transform");

    percent_opt = G_define_option();
    percent_opt->key = "percent";
    percent_opt->type = TYPE_INTEGER;
    percent_opt->required = NO;
    percent_opt->answer = "100";
    percent_opt->options = "1-100";
    percent_opt->description = _("Percent of map to keep in memory");

    /* I would prefer to call the following "percentile", but that has too
     * much namespace overlap with the "percent" option above */
    pth_opt = G_define_option();
    pth_opt->key = "pth";
    pth_opt->type = TYPE_INTEGER;
    pth_opt->required = NO;
    pth_opt->options = "1-100";
    pth_opt->description = _("pth percentile of the values");
    pth_opt->guisection = _("Statistic");

    trim_opt = G_define_option();
    trim_opt->key = "trim";
    trim_opt->type = TYPE_DOUBLE;
    trim_opt->required = NO;
    trim_opt->options = "0-50";
    trim_opt->label = _("Discard given percentage of the smallest and largest values");
    trim_opt->description =
	_("Discard <trim> percent of the smallest and <trim> percent of the largest observations");
    trim_opt->guisection = _("Statistic");

    res_opt = G_define_option();
    res_opt->key = "resolution";
    res_opt->type = TYPE_DOUBLE;
    res_opt->required = NO;
    res_opt->description =
	_("Output raster resolution");
    res_opt->guisection = _("Output");

    filter_opt = G_define_option();
    filter_opt->key = "return_filter";
    filter_opt->type = TYPE_STRING;
    filter_opt->required = NO;
    filter_opt->label = _("Only import points of selected return type");
    filter_opt->description = _("If not specified, all points are imported");
    filter_opt->options = "first,last,mid";
    filter_opt->guisection = _("Selection");

    class_opt = G_define_option();
    class_opt->key = "class_filter";
    class_opt->type = TYPE_INTEGER;
    class_opt->multiple = YES;
    class_opt->required = NO;
    class_opt->label = _("Only import points of selected class(es)");
    class_opt->description = _("Input is comma separated integers. "
                               "If not specified, all points are imported.");
    class_opt->guisection = _("Selection");

    print_flag = G_define_flag();
    print_flag->key = 'p';
    print_flag->description =
	_("Print LAS file info and exit");

    extents_flag = G_define_flag();
    extents_flag->key = 'e';
    extents_flag->label =
        _("Use the extent of the input for the raster extent");
    extents_flag->description =
        _("Set internally computational region extents based on the"
          " point cloud");
    extents_flag->guisection = _("Output");

    set_region_flag = G_define_flag();
    set_region_flag->key = 'n';
    set_region_flag->label =
        _("Set computation region to match the new raster map");
    set_region_flag->description =
        _("Set computation region to match the 2D extent and resolution"
          " of the newly created new raster map");
    set_region_flag->guisection = _("Output");

    over_flag = G_define_flag();
    over_flag->key = 'o';
    over_flag->label =
	_("Override projection check (use current location's projection)");
    over_flag->description =
	_("Assume that the dataset has same projection as the current location");

    scan_flag = G_define_flag();
    scan_flag->key = 's';
    scan_flag->description = _("Scan data file for extent then exit");

    shell_style = G_define_flag();
    shell_style->key = 'g';
    shell_style->description =
	_("In scan mode, print using shell script style");

    intens_flag = G_define_flag();
    intens_flag->key = 'i';
    intens_flag->label =
        _("Use intensity values rather than Z values");
    intens_flag->description =
        _("Uses intensity values everywhere as if they would be Z"
          " coordinates");

    intens_import_flag = G_define_flag();
    intens_import_flag->key = 'j';
    intens_import_flag->description =
        _("Use Z values for filtering, but intensity values for statistics");

    base_rast_res_flag = G_define_flag();
    base_rast_res_flag->key = 'd';
    base_rast_res_flag->label =
        _("Use base raster resolution instead of computational region");
    base_rast_res_flag->description =
        _("For getting values from base raster, use its actual"
          " resolution instead of computational region resolution");

    only_valid_flag = G_define_flag();
    only_valid_flag->key = 'v';
    only_valid_flag->label = _("Use only valid points");
    only_valid_flag->description =
        _("Points invalid according to APSRS LAS specification will be"
          " filtered out");
    only_valid_flag->guisection = _("Selection");

    G_option_required(input_opt, file_list_opt, NULL);
    G_option_exclusive(input_opt, file_list_opt, NULL);
    G_option_required(output_opt, print_flag, scan_flag, shell_style, NULL);
    G_option_exclusive(intens_flag, intens_import_flag, NULL);
    G_option_requires(base_rast_res_flag, base_raster_opt, NULL);

    if (G_parser(argc, argv))
	exit(EXIT_FAILURE);

    int only_valid = FALSE;
    n_invalid = 0;
    if (only_valid_flag->answer)
        only_valid = TRUE;

    /* we could use rules but this gives more info and allows continuing */
    if (set_region_flag->answer && !(extents_flag->answer || res_opt->answer)) {
        G_warning(_("Flag %c makes sense only with %s option or -%c flag"),
                  set_region_flag->key, res_opt->key, extents_flag->key);
        /* avoid the call later on */
        set_region_flag->answer = '\0';
    }

    struct StringList infiles;

    if (file_list_opt->answer) {
        if (access(file_list_opt->answer, F_OK) != 0)
            G_fatal_error(_("File <%s> does not exist"), file_list_opt->answer);
        string_list_from_file(&infiles, file_list_opt->answer);
    }
    else {
        string_list_from_one_item(&infiles, input_opt->answer);
    }

    /* parse input values */
    outmap = output_opt->answer;

    if (shell_style->answer && !scan_flag->answer) {
	scan_flag->answer = 1; /* pointer not int, so set = shell_style->answer ? */
    }

    /* check zrange and extent relation */
    if (scan_flag->answer || extents_flag->answer) {
        if (zrange_opt->answer)
            G_warning(_("zrange will not be taken into account during scan"));
    }

    Rast_get_window(&region);
    /* G_get_window seems to be unreliable if the location has been changed */
    G_get_set_window(&loc_wind);        /* TODO: v.in.lidar uses G_get_default_window() */

    estimated_lines = 0;
    int i;
    for (i = 0; i < infiles.num_items; i++) {
        infile = infiles.items[i];
        /* don't if file not found */
        if (access(infile, F_OK) != 0)
            G_fatal_error(_("Input file <%s> does not exist"), infile);
        /* Open LAS file*/
        LAS_reader = LASReader_Create(infile);
        if (LAS_reader == NULL)
            G_fatal_error(_("Unable to open file <%s> as a LiDAR point cloud"),
                          infile);
        LAS_header = LASReader_GetHeader(LAS_reader);
        if  (LAS_header == NULL) {
            G_fatal_error(_("Unable to read LAS header of <%s>"), infile);
        }

        LAS_srs = LASHeader_GetSRS(LAS_header);

        /* print info or check projection if we are actually importing */
        if (print_flag->answer) {
            /* print filename when there is more than one file */
            if (infiles.num_items > 1)
                fprintf(stdout, "File: %s\n", infile);
            /* Print LAS header */
            print_lasinfo(LAS_header, LAS_srs);
        }
        else {
            /* report that we are checking more files */
            if (i == 1)
                G_message(_("First file's projection checked,"
                            " checking projection of the other files..."));
            /* Fetch input map projection in GRASS form. */
            projstr = LASSRS_GetWKT_CompoundOK(LAS_srs);
            /* we are printing the non-warning messages only for first file */
            projection_check_wkt(cellhd, loc_wind, projstr, over_flag->answer,
                                 shell_style->answer || i);
            /* if there is a problem in some other file, first OK message
             * is printed but than a warning, this is not ideal but hopefully
             * not so confusing when importing multiple files */
        }
        if (scan_flag->answer || extents_flag->answer) {
            /* we assign to the first one (i==0) but update for the rest */
            scan_bounds(LAS_reader, shell_style->answer, extents_flag->answer, i,
                        zscale, &region);
        }
        /* number of estimated point across all files */
        /* TODO: this should be ull which won't work with percent report */
        estimated_lines += LASHeader_GetPointRecordsCount(LAS_header);
        /* We are closing all again and we will be opening them later,
         * so we don't have to worry about limit for open files. */
        LASSRS_Destroy(LAS_srs);
        LASHeader_Destroy(LAS_header);
        LASReader_Destroy(LAS_reader);
    }
    /* if we are not importing, end */
    if (print_flag->answer || scan_flag->answer)
        exit(EXIT_SUCCESS);

    return_filter = LAS_ALL;
    if (filter_opt->answer) {
	if (strcmp(filter_opt->answer, "first") == 0)
	    return_filter = LAS_FIRST;
	else if (strcmp(filter_opt->answer, "last") == 0)
	    return_filter = LAS_LAST;
	else if (strcmp(filter_opt->answer, "mid") == 0)
	    return_filter = LAS_MID;
	else
	    G_fatal_error(_("Unknown filter option <%s>"), filter_opt->answer);
    }
    struct ReturnFilter return_filter_struct;
    return_filter_struct.filter = return_filter;
    struct ClassFilter class_filter;
    class_filter_create_from_strings(&class_filter, class_opt->answers);

    percent = atoi(percent_opt->answer);
    /* TODO: we already used zscale */
    /* TODO: we don't report intensity range */
    if (zscale_opt->answer)
        zscale = atof(zscale_opt->answer);
    if (iscale_opt->answer)
        iscale = atof(iscale_opt->answer);

    /* parse zrange */
    if (zrange_opt->answer != NULL) {
	if (zrange_opt->answers[0] == NULL)
	    G_fatal_error(_("Invalid zrange"));

	sscanf(zrange_opt->answers[0], "%lf", &zrange_min);
	sscanf(zrange_opt->answers[1], "%lf", &zrange_max);

	if (zrange_min > zrange_max) {
	    d_tmp = zrange_max;
	    zrange_max = zrange_min;
	    zrange_min = d_tmp;
	}
    }
    /* parse irange */
    if (irange_opt->answer != NULL) {
        if (irange_opt->answers[0] == NULL)
            G_fatal_error(_("Invalid %s"), irange_opt->key);

        sscanf(irange_opt->answers[0], "%lf", &irange_min);
        sscanf(irange_opt->answers[1], "%lf", &irange_max);

        if (irange_min > irange_max) {
            d_tmp = irange_max;
            irange_max = irange_min;
            irange_min = d_tmp;
        }
    }

    point_binning_set(&point_binning, method_opt->answer, pth_opt->answer,
                      trim_opt->answer, FALSE);

    base_array = NULL;

    if (strcmp("CELL", type_opt->answer) == 0)
	rtype = CELL_TYPE;
    else if (strcmp("DCELL", type_opt->answer) == 0)
	rtype = DCELL_TYPE;
    else
	rtype = FCELL_TYPE;

    if (point_binning.method == METHOD_N)
	rtype = CELL_TYPE;

    if (res_opt->answer) {
	/* align to resolution */
	res = atof(res_opt->answer);

	if (!G_scan_resolution(res_opt->answer, &res, region.proj))
	    G_fatal_error(_("Invalid input <%s=%s>"), res_opt->key, res_opt->answer);

	if (res <= 0)
	    G_fatal_error(_("Option '%s' must be > 0.0"), res_opt->key);
	
	region.ns_res = region.ew_res = res;

	region.north = ceil(region.north / res) * res;
	region.south = floor(region.south / res) * res;
	region.east = ceil(region.east / res) * res;
	region.west = floor(region.west / res) * res;

	G_adjust_Cell_head(&region, 0, 0);
    }
    else if (extents_flag->answer) {
	/* align to current region */
	Rast_align_window(&region, &loc_wind);
    }
    Rast_set_output_window(&region);

    rows = last_rows = region.rows;
    npasses = 1;
    if (percent < 100) {
	rows = (int)(region.rows * (percent / 100.0));
	npasses = region.rows / rows;
	last_rows = region.rows - npasses * rows;
	if (last_rows)
	    npasses++;
	else
	    last_rows = rows;

    }
    cols = region.cols;

    G_debug(2, "region.n=%f  region.s=%f  region.ns_res=%f", region.north,
	    region.south, region.ns_res);
    G_debug(2, "region.rows=%d  [box_rows=%d]  region.cols=%d", region.rows,
	    rows, region.cols);

    /* using row-based chunks (used for output) when input and output
     * region matches and using segment library when they don't */
    int use_segment = 0;
    int use_base_raster_res = 0;
    /* TODO: see if the input region extent is smaller than the raster
     * if yes, the we need to load the whole base raster if the -e
     * flag was defined (alternatively clip the regions) */
    if (base_rast_res_flag->answer)
        use_base_raster_res = 1;
    if (base_raster_opt->answer && (res_opt->answer || use_base_raster_res
                                    || extents_flag->answer))
        use_segment = 1;
    if (base_raster_opt->answer && !use_segment) {
        /* TODO: do we need to test existence first? mapset? */
        base_raster = Rast_open_old(base_raster_opt->answer, "");
        base_raster_data_type = Rast_get_map_type(base_raster);
        base_array = G_calloc((size_t)rows * (cols + 1), Rast_cell_size(base_raster_data_type));
    }
    if (base_raster_opt->answer && use_segment) {
        if (use_base_raster_res) {
            /* read raster actual extent and resolution */
            Rast_get_cellhd(base_raster_opt->answer, "", &input_region);
            /* TODO: make it only as small as the output is or points are */
            Rast_set_input_window(&input_region);  /* we have split window */
        } else {
            Rast_get_input_window(&input_region);
        }
        rast_segment_open(&base_segment, base_raster_opt->answer, &base_raster_data_type);
    }

    if (!scan_flag->answer) {
        if (!check_rows_cols_fit_to_size_t(rows, cols))
		G_fatal_error(_("Unable to process the hole map at once. "
                        "Please set the '%s' option to some value lower than 100."),
				percent_opt->key);
        point_binning_memory_test(&point_binning, rows, cols, rtype);
	}

    /* open output map */
    out_fd = Rast_open_new(outmap, rtype);

    /* allocate memory for a single row of output data */
    raster_row = Rast_allocate_output_buf(rtype);

    G_message(_("Reading data ..."));

    count_total = line_total = 0;

    /* main binning loop(s) */
    for (pass = 1; pass <= npasses; pass++) {

	if (npasses > 1)
	    G_message(_("Pass #%d (of %d) ..."), pass, npasses);

	/* figure out segmentation */
	row0 = (pass - 1) * rows;
	if (pass == npasses) {
	    rows = last_rows;
	}

        if (base_array) {
            G_debug(2, "filling base raster array");
            for (row = 0; row < rows; row++) {
                Rast_get_row(base_raster, base_array + ((size_t) row * cols * Rast_cell_size(base_raster_data_type)), row, base_raster_data_type);
            }
        }

	G_debug(2, "pass=%d/%d  rows=%d", pass, npasses, rows);

    point_binning_allocate(&point_binning, rows, cols, rtype);

	line = 0;
	count = 0;
	counter = 0;
	G_percent_reset();

        /* loop of input files */
        for (i = 0; i < infiles.num_items; i++) {
            infile = infiles.items[i];
            /* we already know file is there, so just do basic checks */
            LAS_reader = LASReader_Create(infile);
            if (LAS_reader == NULL)
                G_fatal_error(_("Unable to open file <%s>"), infile);

            while ((LAS_point = LASReader_GetNextPoint(LAS_reader)) != NULL) {
                line++;
                counter++;

                if (counter == 100000) {        /* speed */
                    if (line < estimated_lines)
                        G_percent(line, estimated_lines, 3);
                    counter = 0;
                }

                /* We always count them and report because behavior
                 * changed in between 7.0 and 7.2 from undefined (but skipping
                 * invalid points) to filtering them out only when requested. */
                if (!LASPoint_IsValid(LAS_point)) {
                    n_invalid++;
                    if (only_valid)
                        continue;
                }

                x = LASPoint_GetX(LAS_point);
                y = LASPoint_GetY(LAS_point);
                if (intens_flag->answer)
                    /* use intensity as z here to allow all filters (and
                     * modifications) below to be applied for intensity */
                    z = LASPoint_GetIntensity(LAS_point);
                else
                    z = LASPoint_GetZ(LAS_point);

                int return_n = LASPoint_GetReturnNumber(LAS_point);
                int n_returns = LASPoint_GetNumberOfReturns(LAS_point);
                if (return_filter_is_out(&return_filter_struct, return_n, n_returns)) {
                    n_filtered++;
                    continue;
                }
                point_class = (int) LASPoint_GetClassification(LAS_point);
                if (class_filter_is_out(&class_filter, point_class))
                    continue;

                if (y <= region.south || y > region.north) {
                    continue;
                }
                if (x < region.west || x >= region.east) {
                    continue;
                }

                /* find the bin in the current array box */
		arr_row = (int)((region.north - y) / region.ns_res) - row0;
		if (arr_row < 0 || arr_row >= rows)
		    continue;
                arr_col = (int)((x - region.west) / region.ew_res);

                z = z * zscale;

                if (base_array) {
                    double base_z;
                    if (row_array_get_value_row_col(base_array, arr_row, arr_col,
                                                    cols, base_raster_data_type,
                                                    &base_z))
                        z -= base_z;
                    else
                        continue;
                }
                else if (use_segment) {
                    double base_z;
                    if (rast_segment_get_value_xy(&base_segment, &input_region,
                                                  base_raster_data_type, x, y,
                                                  &base_z))
                        z -= base_z;
                    else
                        continue;
                }

                if (zrange_opt->answer) {
                    if (z < zrange_min || z > zrange_max) {
                        continue;
                    }
                }

                if (intens_import_flag->answer || irange_opt->answer) {
                    intensity = LASPoint_GetIntensity(LAS_point);
                    intensity *= iscale;
                    if (irange_opt->answer) {
                        if (intensity < irange_min || intensity > irange_max) {
                            continue;
                        }
                    }
                    /* use intensity for statistics */
                    if (intens_import_flag->answer)
                        z = intensity;
                }

                count++;
                /*          G_debug(5, "x: %f, y: %f, z: %f", x, y, z); */

                update_value(&point_binning, &bin_index_nodes, cols,
                             arr_row, arr_col, rtype, x, y, z);
            }                        /* while !EOF of one input file */
            /* close input LAS file */
            LASReader_Destroy(LAS_reader);
        }           /* end of loop for all input files files */

	G_percent(1, 1, 1);	/* flush */
	G_debug(2, "pass %d finished, %lu coordinates in box", pass, count);
	count_total += count;
	line_total += line;

	/* calc stats and output */
	G_message(_("Writing to map ..."));
	for (row = 0; row < rows; row++) {
        /* potentially vector writing can be independent on the binning */
        write_values(&point_binning, &bin_index_nodes, raster_row, row,
            cols, rtype, NULL);
	    /* write out line of raster data */
        Rast_put_row(out_fd, raster_row, rtype);
	}

	/* free memory */
	point_binning_free(&point_binning, &bin_index_nodes);
    }				/* passes loop */
    if (base_array)
        Rast_close(base_raster);
    if (use_segment)
        Segment_close(&base_segment);

    G_percent(1, 1, 1);		/* flush */
    G_free(raster_row);

    /* close raster file & write history */
    Rast_close(out_fd);

    sprintf(title, "Raw X,Y,Z data binned into a raster grid by cell %s",
            method_opt->answer);
    Rast_put_cell_title(outmap, title);

    Rast_short_history(outmap, "raster", &history);
    Rast_command_history(&history);
    Rast_set_history(&history, HIST_DATSRC_1, infile);
    Rast_write_history(outmap, &history);

    /* set computation region to the new raster map */
    /* TODO: should be in the done message */
    if (set_region_flag->answer)
        G_put_window(&region);

    if (n_invalid && only_valid)
        G_message(_("%lu input points were invalid and filtered out"),
                  n_invalid);
    if (n_invalid && !only_valid)
        G_message(_("%lu input points were invalid, use -%c flag to filter"
                    " them out"), n_invalid, only_valid_flag->key);
    if (infiles.num_items > 1) {
        sprintf(buff, _("Raster map <%s> created."
                        " %lu points from %d files found in region."),
                outmap, count_total, infiles.num_items);
    }
    else {
        sprintf(buff, _("Raster map <%s> created."
                        " %lu points found in region."),
                outmap, count_total);
    }

    G_done_msg("%s", buff);
    G_debug(1, "Processed %lu points.", line_total);

    string_list_free(&infiles);

    exit(EXIT_SUCCESS);

}
Exemple #18
0
int main(int argc, char *argv[])
{
    void *raster, *ptr;

    /*
       char  *null_row;
     */
    RASTER_MAP_TYPE out_type, map_type;
    char *outfile;
    char null_str[80];
    char cell_buf[300];
    int fd;
    int row, col;
    int nrows, ncols, dp;
    int do_stdout;
    FILE *fp;
    double cellsize;
    struct GModule *module;
    struct
    {
	struct Option *map;
	struct Option *output;
	struct Option *dp;
	struct Option *null;
    } parm;
    struct
    {
	struct Flag *noheader;
	struct Flag *singleline;
	struct Flag *ccenter;
    } flag;

    G_gisinit(argv[0]);

    module = G_define_module();
    G_add_keyword(_("raster"));
    G_add_keyword(_("export"));
    module->description =
	_("Converts a raster map layer into an ESRI ARCGRID file.");

    /* Define the different options */
    parm.map = G_define_standard_option(G_OPT_R_INPUT);

    parm.output = G_define_standard_option(G_OPT_R_OUTPUT);
    parm.output->gisprompt = "new_file,file,output";
    parm.output->description =
	_("Name of an output ARC-GRID map (use out=- for stdout)");

    parm.dp = G_define_option();
    parm.dp->key = "dp";
    parm.dp->type = TYPE_INTEGER;
    parm.dp->required = NO;
    parm.dp->answer = "8";
    parm.dp->description = _("Number of decimal places");

    flag.noheader = G_define_flag();
    flag.noheader->key = 'h';
    flag.noheader->description = _("Suppress printing of header information");

    /* Added to optionally produce a single line output.     -- emes -- 12.10.92 */
    flag.singleline = G_define_flag();
    flag.singleline->key = '1';
    flag.singleline->description =
	_("List one entry per line instead of full row");

    /* use cell center in header instead of cell corner */
    flag.ccenter = G_define_flag();
    flag.ccenter->key = 'c';
    flag.ccenter->description =
	_("Use cell center reference in header instead of cell corner");

    if (G_parser(argc, argv))
	exit(EXIT_FAILURE);


    sscanf(parm.dp->answer, "%d", &dp);
    if (dp > 20 || dp < 0)
	G_fatal_error("dp has to be from 0 to 20");

    outfile = parm.output->answer;
    if ((strcmp("-", outfile)) == 0)
	do_stdout = 1;
    else
	do_stdout = 0;

    sprintf(null_str, "-9999");

    fd = Rast_open_old(parm.map->answer, "");

    map_type = Rast_get_map_type(fd);
    out_type = map_type;

    /*
       null_row = Rast_allocate_null_buf();
     */
    raster = Rast_allocate_buf(out_type);

    nrows = Rast_window_rows();
    ncols = Rast_window_cols();

    /* open arc file for writing */
    if (do_stdout)
	fp = stdout;
    else if (NULL == (fp = fopen(outfile, "w")))
	G_fatal_error(_("Unable to open file <%s>"), outfile);

    if (!flag.noheader->answer) {
	struct Cell_head region;
	char buf[128];

	G_get_window(&region);
	fprintf(fp, "ncols %d\n", region.cols);
	fprintf(fp, "nrows %d\n", region.rows);
	cellsize = fabs(region.east - region.west) / region.cols;

	if (G_projection() != PROJECTION_LL) {	/* Is Projection != LL (3) */
	    if (!flag.ccenter->answer) {
		G_format_easting(region.west, buf, region.proj);
		fprintf(fp, "xllcorner %s\n", buf);
		G_format_northing(region.south, buf, region.proj);
		fprintf(fp, "yllcorner %s\n", buf);
	    }
	    else {
		G_format_easting(region.west + cellsize / 2., buf, region.proj);
		fprintf(fp, "xllcenter %s\n", buf);
		G_format_northing(region.south + cellsize / 2., buf, region.proj);
		fprintf(fp, "yllcenter %s\n", buf);
	    }
	}
	else {			/* yes, lat/long */
	    fprintf(fp, "xllcorner %f\n", region.west);
	    fprintf(fp, "yllcorner %f\n", region.south);
	}

	fprintf(fp, "cellsize %f\n", cellsize);
	fprintf(fp, "NODATA_value %s\n", null_str);
    }

    for (row = 0; row < nrows; row++) {
	G_percent(row, nrows, 2);
	Rast_get_row(fd, raster, row, out_type);
	/*
	   Rast_get_null_value_row(fd, null_row, row);
	 */
	for (col = 0, ptr = raster; col < ncols; col++,
	     ptr = G_incr_void_ptr(ptr, Rast_cell_size(out_type))) {
	    if (!Rast_is_null_value(ptr, out_type)) {
		if (out_type == CELL_TYPE)
		    fprintf(fp, "%d", *((CELL *) ptr));

		else if (out_type == FCELL_TYPE) {
		    sprintf(cell_buf, "%.*f", dp, *((FCELL *) ptr));
		    G_trim_decimal(cell_buf);
		    fprintf(fp, "%s", cell_buf);
		}
		else if (out_type == DCELL_TYPE) {
		    sprintf(cell_buf, "%.*f", dp, *((DCELL *) ptr));
		    G_trim_decimal(cell_buf);
		    fprintf(fp, "%s", cell_buf);
		}
	    }
	    else
		fprintf(fp, "%s", null_str);

	    if (!flag.singleline->answer)
		fprintf(fp, " ");
	    else
		fprintf(fp, "\n");
	}

	if (!flag.singleline->answer)
	    fprintf(fp, "\n");

	/*
	   for (col = 0; col < ncols; col++)
	   fprintf (fp,"%d ", null_row[col]);
	   fprintf (fp,"\n");
	 */
    }

    /* make sure it got to 100% */
    G_percent(1, 1, 2);

    Rast_close(fd);
    fclose(fp);

    exit(EXIT_SUCCESS);
}
Exemple #19
0
static int
write_pca(double **eigmat, int *inp_fd, char *out_basename,
	  int bands, int scale, int scale_min, int scale_max)
{
    int i, j;
    void *outbuf, *outptr;
    double min = 0.;
    double max = 0.;
    double old_range = 0.;
    double new_range = 0.;
    int rows = Rast_window_rows();
    int cols = Rast_window_cols();
    int cell_mapsiz = Rast_cell_size(CELL_TYPE);
    int dcell_mapsiz = Rast_cell_size(DCELL_TYPE);
    DCELL *d_buf;

    /* 2 passes for rescale.  1 pass for no rescale */
    int PASSES = (scale) ? 2 : 1;

    /* temporary row storage */
    d_buf = (DCELL *) G_malloc(cols * sizeof(double));

    /* allocate memory for output row buffer */
    outbuf = (scale) ? Rast_allocate_buf(CELL_TYPE) :
	Rast_allocate_buf(DCELL_TYPE);

    if (!outbuf)
	G_fatal_error(_("Unable to allocate memory for raster row"));

    for (i = 0; i < bands; i++) {
	char name[100];
	int out_fd;
	int pass;

	sprintf(name, "%s.%d", out_basename, i + 1);

	G_message(_("Transforming <%s>..."), name);

	/* open a new file for output */
	if (scale)
	    out_fd = Rast_open_c_new(name);
	else {
	    out_fd = Rast_open_fp_new(name);
	    Rast_set_fp_type(DCELL_TYPE);
	}

	for (pass = 1; pass <= PASSES; pass++) {
	    void *rowbuf = NULL;
	    int row, col;

	    if (scale && (pass == PASSES)) {
		G_message(_("Rescaling <%s> to range %d,%d..."),
			  name, scale_min, scale_max);

		old_range = max - min;
		new_range = (double)(scale_max - scale_min);
	    }

	    for (row = 0; row < rows; row++) {
		void *rowptr;

		G_percent(row, rows, 2);

		/* reset d_buf */
		for (col = 0; col < cols; col++)
		    d_buf[col] = 0.;

		for (j = 0; j < bands; j++) {
		    RASTER_MAP_TYPE maptype =
			Rast_get_map_type(inp_fd[j]);

		    /* don't assume each image is of the same type */
		    if (rowbuf)
			G_free(rowbuf);
		    if (!(rowbuf = Rast_allocate_buf(maptype)))
			G_fatal_error(_("Unable allocate memory for row buffer"));

		    Rast_get_row(inp_fd[j], rowbuf, row, maptype);

		    rowptr = rowbuf;
		    outptr = outbuf;

		    /* add into the output cell eigmat[i][j] * corresp cell 
		     * of j-th band for current j */
		    for (col = 0; col < cols; col++) {
			/* handle null cells */
			if (Rast_is_null_value(rowptr, maptype)) {
			    if (scale) {
				Rast_set_null_value(outptr, 1, CELL_TYPE);
				outptr = G_incr_void_ptr(outptr, cell_mapsiz);
			    }
			    else {
				Rast_set_null_value(outptr, 1, DCELL_TYPE);
				outptr =
				    G_incr_void_ptr(outptr, dcell_mapsiz);
			    }

			    rowptr =
				G_incr_void_ptr(rowptr,
						Rast_cell_size(maptype));
			    continue;
			}

			/* corresp. cell of j-th band */
			d_buf[col] +=
			    eigmat[i][j] * Rast_get_d_value(rowptr,
								maptype);

			/* the cell entry is complete */
			if (j == (bands - 1)) {
			    if (scale && (pass == 1)) {
				if ((row == 0) && (col == 0))
				    min = max = d_buf[0];

				if (d_buf[col] < min)
				    min = d_buf[col];

				if (d_buf[col] > max)
				    max = d_buf[col];
			    }
			    else if (scale) {

				if (min == max) {
				    Rast_set_c_value(outptr, 1,
							 CELL_TYPE);
				}
				else {
				    /* map data to 0, (new_range-1) and then adding new_min */
				    CELL tmpcell =
					round_c((new_range *
						 (d_buf[col] -
						  min) / old_range) +
						scale_min);

				    Rast_set_c_value(outptr, tmpcell,
							 CELL_TYPE);
				}
			    }
			    else {	/* (!scale) */

				Rast_set_d_value(outptr, d_buf[col],
						     DCELL_TYPE);
			    }
			}

			outptr = (scale) ?
			    G_incr_void_ptr(outptr, cell_mapsiz) :
			    G_incr_void_ptr(outptr, dcell_mapsiz);

			rowptr =
			    G_incr_void_ptr(rowptr, Rast_cell_size(maptype));
		    }
		}		/* for j = 0 to bands */

		if (pass == PASSES) {
		    if (scale)
			Rast_put_row(out_fd, outbuf, CELL_TYPE);
		    else
			Rast_put_row(out_fd, outbuf, DCELL_TYPE);
		}
	    }

	    G_percent(row, rows, 2);

	    /* close output file */
	    if (pass == PASSES)
		Rast_close(out_fd);
	}
    }

    if (d_buf)
	G_free(d_buf);
    if (outbuf)
	G_free(outbuf);

    return 0;
}
Exemple #20
0
void* raster2array(const char* name, struct Cell_head* header, int* rows,
		int* cols, RASTER_MAP_TYPE out_type) {
	// Open the raster map and load the dem
	// for simplicity sake, the dem will be an array of
	// doubles, converted from any possible GRASS CELL type.
	//ORG char* mapset = G_find_cell2(name, "");
	char* mapset = G_find_raster(name, "");
	if (mapset == NULL)
		G_fatal_error("Raster map <%s> not found", name);

	// Find out the cell type of the DEM
	//ORG RASTER_MAP_TYPE type = G_raster_map_type(name, mapset);
        RASTER_MAP_TYPE type = Rast_map_type(name, mapset);

	// Get a file descriptor for the DEM raster map
	int infd;
	//ORG if ((infd = G_open_cell_old(name, mapset)) < 0)
	if ((infd = Rast_open_old(name, mapset)) < 0)
		G_fatal_error("Unable to open raster map <%s>", name);

	// Get header info for the DEM raster map
	struct Cell_head cellhd;
	//ORG if (G_get_cellhd(name, mapset, &cellhd) < 0)
	//ORG 	G_fatal_error("Unable to open raster map <%s>", name);
        Rast_get_cellhd(name, mapset, &cellhd);

	// Create a GRASS buffer for the DEM raster
	//ORG void* inrast = G_allocate_raster_buf(type);
        void* inrast =  Rast_allocate_buf(type);

	// Get the max rows and max cols from the window information, since the 
	// header gives the values for the full raster
	//ORG const int maxr = G_window_rows();
	//ORG const int maxc = G_window_cols();
	const int maxr = Rast_window_rows();
	const int maxc = Rast_window_cols();

	// Read in the raster line by line, copying it into the double array
	// rast for return.
	void* rast;
	switch (out_type) {
	case CELL_TYPE:
		rast = (int*) calloc(maxr * maxc, sizeof(int));
		break;
	case FCELL_TYPE:
		rast = (float*) calloc(maxr * maxc, sizeof(float));
		break;
	case DCELL_TYPE:
		rast = (double*) calloc(maxr * maxc, sizeof(double));
		break;

	}

	if (rast == NULL) {
		G_fatal_error("Unable to allocate memory for raster map <%s>", name);
	}

	int row, col;
	for (row = 0; row < maxr; ++row) {
		//ORG if (G_get_raster_row(infd, inrast, row, type) < 0)
		//ORG 	G_fatal_error("Unable to read raster map <%s> row %d", name, row);
                Rast_get_row(infd, inrast, row, type);
                
		for (col = 0; col < maxc; ++col) {
			int index = col + row * maxc;

			if (out_type == CELL_TYPE) {
				switch (type) {
				case CELL_TYPE:
					((int*) rast)[index] = ((int *) inrast)[col];
					break;
				case FCELL_TYPE:
					((int*) rast)[index] = (int) ((float *) inrast)[col];
					break;
				case DCELL_TYPE:
					((int*) rast)[index] = (int) ((double *) inrast)[col];
					break;
				default:
					G_fatal_error("Unknown cell type");
					break;
				}
			}

			if (out_type == FCELL_TYPE) {
				switch (type) {
				case CELL_TYPE:
					((float*) rast)[index] = (float) ((int *) inrast)[col];
					break;
				case FCELL_TYPE:
					((float*) rast)[index] = ((float *) inrast)[col];
					break;
				case DCELL_TYPE:
					((float*) rast)[index] = (float) ((double *) inrast)[col];
					break;
				default:
					G_fatal_error("Unknown cell type");
					break;
				}
			}

			if (out_type == DCELL_TYPE) {
				switch (type) {
				case CELL_TYPE:
					((double*) rast)[index] = (double) ((int *) inrast)[col];
					break;
				case FCELL_TYPE:
					((double*) rast)[index] = (double) ((float *) inrast)[col];
					break;
				case DCELL_TYPE:
					((double*) rast)[index] = ((double *) inrast)[col];
					break;
				default:
					G_fatal_error("Unknown cell type");
					break;
				}
			}
		}
	}

	// Return cellhd, maxr, and maxc by pointer
	if (header != NULL)
		*header = cellhd;
	if (rows != NULL)
		*rows = maxr;
	if (cols != NULL)
		*cols = maxc;

	return rast;
}
Exemple #21
0
int execute_random(struct rr_state *theState)
{
    long nt;
    long nc;
    struct Cell_head window;
    int nrows, ncols, row, col;
    int infd, cinfd, outfd;
    struct Map_info Out;
    struct field_info *fi;
    dbTable *table;
    dbColumn *column;
    dbString sql;
    dbDriver *driver;
    struct line_pnts *Points;
    struct line_cats *Cats;
    int cat;
    RASTER_MAP_TYPE type;
    int do_check;

    G_get_window(&window);

    nrows = Rast_window_rows();
    ncols = Rast_window_cols();

    /* open the data files, input raster should be set-up already */
    if ((infd = theState->fd_old) < 0)
	G_fatal_error(_("Unable to open raster map <%s>"),
		      theState->inraster);
    if (theState->docover == TRUE) {
	if ((cinfd = theState->fd_cold) < 0)
	    G_fatal_error(_("Unable to open raster map <%s>"),
			  theState->inrcover);
    }

    if (theState->outraster != NULL) {
	if (theState->docover == TRUE)
	    type = theState->cover.type;
	else
	    type = theState->buf.type;
	outfd = Rast_open_new(theState->outraster, type);
	theState->fd_new = outfd;

    }

    if (theState->outvector) {
	if (Vect_open_new(&Out, theState->outvector, theState->z_geometry) < 0)
	    G_fatal_error(_("Unable to create vector map <%s>"),
			    theState->outvector);
	Vect_hist_command(&Out);

	fi = Vect_default_field_info(&Out, 1, NULL, GV_1TABLE);

	driver =
	    db_start_driver_open_database(fi->driver,
					  Vect_subst_var(fi->database, &Out));
	if (!driver)
	    G_fatal_error(_("Unable to open database <%s> by driver <%s>"),
			  Vect_subst_var(fi->database, &Out), fi->driver);
        db_set_error_handler_driver(driver);
        
	Vect_map_add_dblink(&Out, 1, NULL, fi->table, GV_KEY_COLUMN, fi->database,
			    fi->driver);

	if (theState->docover == TRUE)
	    table = db_alloc_table(3);
	else
	    table = db_alloc_table(2);
	db_set_table_name(table, fi->table);

	column = db_get_table_column(table, 0);
	db_set_column_name(column, GV_KEY_COLUMN);
	db_set_column_sqltype(column, DB_SQL_TYPE_INTEGER);

	column = db_get_table_column(table, 1);
	db_set_column_name(column, "value");
	db_set_column_sqltype(column, DB_SQL_TYPE_DOUBLE_PRECISION);

	if (theState->docover == TRUE) {
	    column = db_get_table_column(table, 2);
	    db_set_column_name(column, "covervalue");
	    db_set_column_sqltype(column, DB_SQL_TYPE_DOUBLE_PRECISION);
	}
	if (db_create_table(driver, table) != DB_OK)
	    G_warning(_("Cannot create new table"));

	db_begin_transaction(driver);

	Points = Vect_new_line_struct();
	Cats = Vect_new_cats_struct();
	db_init_string(&sql);
    }

    if (theState->outvector && theState->outraster)
	G_message(_("Writing raster map <%s> and vector map <%s> ..."),
		  theState->outraster, theState->outvector);
    else if (theState->outraster)
	G_message(_("Writing raster map <%s> ..."), theState->outraster);
    else if (theState->outvector)
	G_message(_("Writing vector map <%s> ..."), theState->outvector);

    G_percent(0, theState->nRand, 2);

    init_rand();
    nc = (theState->use_nulls) ? theState->nCells :
	theState->nCells - theState->nNulls;
    nt = theState->nRand;	/* Number of points to generate */
    cat = 1;

    /* Execute for loop for every row if nt>1 */
    for (row = 0; row < nrows && nt; row++) {
	Rast_get_row(infd, theState->buf.data.v, row, theState->buf.type);
	if (theState->docover == TRUE) {
	    Rast_get_row(cinfd, theState->cover.data.v, row,
			 theState->cover.type);
	}

	for (col = 0; col < ncols && nt; col++) {
	    do_check = 0;

	    if (theState->use_nulls || !is_null_value(theState->buf, col))
		do_check = 1;
	    if (do_check && theState->docover == TRUE) {	/* skip no data cover points */
		if (!theState->use_nulls &&
		    is_null_value(theState->cover, col))
		    do_check = 0;
	    }

	    if (do_check && make_rand() % nc < nt) {
		nt--;
		if (is_null_value(theState->buf, col))
		    cpvalue(&theState->nulls, 0, &theState->buf, col);
		if (theState->docover == TRUE) {
		    if (is_null_value(theState->cover, col))
			cpvalue(&theState->cnulls, 0, &theState->cover, col);
		}

		if (theState->outvector) {
		    double x, y, val, coverval;
		    char buf[500];

		    Vect_reset_line(Points);
		    Vect_reset_cats(Cats);

		    x = window.west + (col + .5) * window.ew_res;
		    y = window.north - (row + .5) * window.ns_res;

		    val = cell_as_dbl(&theState->buf, col);
		    if (theState->docover == 1)
			coverval = cell_as_dbl(&theState->cover, col);

		    if (theState->z_geometry)
			Vect_append_point(Points, x, y, val);
		    else
			Vect_append_point(Points, x, y, 0.0);
		    Vect_cat_set(Cats, 1, cat);

		    Vect_write_line(&Out, GV_POINT, Points, Cats);

		    if (theState->docover == 1)
			if (is_null_value(theState->cover, col))
			    sprintf(buf,
				    "insert into %s values ( %d, %f, NULL )",
				    fi->table, cat, val);
			else
			    sprintf(buf,
				    "insert into %s values ( %d, %f, %f )",
				    fi->table, cat, val, coverval);
		    else
			sprintf(buf, "insert into %s values ( %d, %f )",
				fi->table, cat, val);
		    db_set_string(&sql, buf);

		    if (db_execute_immediate(driver, &sql) != DB_OK)
			G_fatal_error(_("Cannot insert new record: %s"),
				      db_get_string(&sql));

		    cat++;
		}
		G_percent((theState->nRand - nt), theState->nRand, 2);
	    }
	    else {
		set_to_null(&theState->buf, col);
		if (theState->docover == 1)
		    set_to_null(&theState->cover, col);
	    }

	    if (do_check)
		nc--;
	}

	while (col < ncols) {
	    set_to_null(&theState->buf, col);
	    if (theState->docover == 1)
		set_to_null(&theState->cover, col);
	    col++;
	}

	if (theState->outraster) {
	    if (theState->docover == 1)
		Rast_put_row(outfd, theState->cover.data.v,
				 theState->cover.type);
	    else
		Rast_put_row(outfd, theState->buf.data.v,
				 theState->buf.type);
	}
    }

    /* Catch any remaining rows in the window */
    if (theState->outraster && row < nrows) {
	for (col = 0; col < ncols; col++) {
	    if (theState->docover == 1)
		set_to_null(&theState->cover, col);
	    else
		set_to_null(&theState->buf, col);
	}
	for (; row < nrows; row++) {
	    if (theState->docover == 1)
		Rast_put_row(outfd, theState->cover.data.v,
				 theState->cover.type);
	    else
		Rast_put_row(outfd, theState->buf.data.v,
				 theState->buf.type);
	}
    }

    if (nt > 0)
	G_warning(_("Only [%ld] random points created"),
		  theState->nRand - nt);

    /* close files */
    Rast_close(infd);
    if (theState->docover == TRUE)
	Rast_close(cinfd);
    if (theState->outvector) {
	db_commit_transaction(driver);
	if (db_create_index2(driver, fi->table, GV_KEY_COLUMN) != DB_OK)
	    G_warning(_("Unable to create index"));
	if (db_grant_on_table
	    (driver, fi->table, DB_PRIV_SELECT,
	     DB_GROUP | DB_PUBLIC) != DB_OK) {
	    G_fatal_error(_("Unable to grant privileges on table <%s>"),
			  fi->table);
	}
	db_close_database_shutdown_driver(driver);
	if (theState->notopol != 1)
	    Vect_build(&Out);
	Vect_close(&Out);
    }
    if (theState->outraster)
	Rast_close(outfd);

    return 0;
}				/* execute_random() */
Exemple #22
0
int main(int argc, char *argv[])
{

    int i, row, col;		/* counters */
    unsigned long filesize;

    int endianness;		/* 0=little, 1=big */
    int data_format;		/* 0=double  1=float  2=32bit signed int  5=8bit unsigned int (ie text) */
    int data_type;		/* 0=numbers  1=text */
    int format_block;		/* combo of endianness, 0, data_format, and type */
    int realflag = 0;		/* 0=only real values used */

    /* should type be specifically uint32 ??? */

    char array_name[32];	/* variable names must start with a letter (case 
				   sensitive) followed by letters, numbers, or 
				   underscores. 31 chars max. */
    int name_len;
    int mrows, ncols;		/* text/data/map array dimensions */

    int val_i;			/* for misc use */
    float val_f;		/* for misc use */
    double val_d;		/* for misc use */

    char *infile, *outfile, *maptitle, *basename;
    struct Cell_head region;
    void *raster, *ptr;
    RASTER_MAP_TYPE map_type;

    struct Option *inputfile, *outputfile;
    struct GModule *module;

    int fd;
    FILE *fp1;


    G_gisinit(argv[0]);

    module = G_define_module();
    G_add_keyword(_("raster"));
    G_add_keyword(_("export"));
    module->description = _("Exports a GRASS raster to a binary MAT-File.");

    /* Define the different options */

    inputfile = G_define_standard_option(G_OPT_R_INPUT);

    outputfile = G_define_option();
    outputfile->key = "output";
    outputfile->type = TYPE_STRING;
    outputfile->required = YES;
    outputfile->gisprompt = "new_file,file,output";
    outputfile->description = _("Name for the output binary MAT-File");

    if (G_parser(argc, argv))
	exit(EXIT_FAILURE);

    infile = inputfile->answer;
    basename = G_store(outputfile->answer);
    G_basename(basename, "mat");
    outfile = G_malloc(strlen(basename) + 5);
    sprintf(outfile, "%s.mat", basename);

    fd = Rast_open_old(infile, "");

    map_type = Rast_get_map_type(fd);

    /* open bin file for writing */
    fp1 = fopen(outfile, "wb");
    if (NULL == fp1)
	G_fatal_error(_("Unable to open output file <%s>"), outfile);


    /* Check Endian State of Host Computer */
    if (G_is_little_endian())
	endianness = 0;		/* ie little endian */
    else
	endianness = 1;		/* ie big endian */
    G_debug(1, "Machine is %s endian.\n", endianness ? "big" : "little");

    G_get_window(&region);


    /********** Write map **********/

    /** write text element (map name) **/
    strncpy(array_name, "map_name", 31);
    mrows = 1;
    ncols = strlen(infile);
    data_format = 5;		/* 0=double  1=float  2=32bit signed int  5=8bit unsigned int(text) */
    data_type = 1;		/* 0=numbers  1=text */

    G_verbose_message(_("Exporting <%s>"), infile);

    /* 4 byte data format */
    format_block = endianness * 1000 + data_format * 10 + data_type;
    fwrite(&format_block, sizeof(int), 1, fp1);
    /* fprintf(stderr, "name data format is [%04ld]\n", format_block); */

    /* 4 byte number of rows & columns */
    fwrite(&mrows, sizeof(int), 1, fp1);
    fwrite(&ncols, sizeof(int), 1, fp1);

    /* 4 byte real/imag flag   0=real vals only */
    fwrite(&realflag, sizeof(int), 1, fp1);

    /* length of array_name+1 */
    name_len = strlen(array_name) + 1;
    fwrite(&name_len, sizeof(int), 1, fp1);

    /* array name */
    fprintf(fp1, "%s%c", array_name, '\0');

    /* array data */
    fprintf(fp1, "%s", infile);


    /********** Write title (if there is one) **********/
    maptitle = Rast_get_cell_title(infile, "");
    if (strlen(maptitle) >= 1) {

	/** write text element (map title) **/
	strncpy(array_name, "map_title", 31);
	mrows = 1;
	ncols = strlen(maptitle);
	data_format = 5;	/* 0=double  1=float  2=32bit signed int  5=8bit unsigned int(text) */
	data_type = 1;		/* 0=numbers  1=text */

	/* 4 byte data format */
	format_block = endianness * 1000 + data_format * 10 + data_type;
	fwrite(&format_block, sizeof(int), 1, fp1);

	/* 4 byte number of rows & columns */
	fwrite(&mrows, sizeof(int), 1, fp1);
	fwrite(&ncols, sizeof(int), 1, fp1);

	/* 4 byte real/imag flag   0=real vals only */
	fwrite(&realflag, sizeof(int), 1, fp1);

	/* length of array_name+1 */
	name_len = strlen(array_name) + 1;
	fwrite(&name_len, sizeof(int), 1, fp1);

	/* array name */
	fprintf(fp1, "%s%c", array_name, '\0');

	/* array data */
	fprintf(fp1, "%s", maptitle);
    }

    /***** Write bounds *****/
    G_verbose_message("");
    G_verbose_message(_("Using the Current Region settings:"));
    G_verbose_message(_("northern edge=%f"), region.north);
    G_verbose_message(_("southern edge=%f"), region.south);
    G_verbose_message(_("eastern edge=%f"), region.east);
    G_verbose_message(_("western edge=%f"), region.west);
    G_verbose_message(_("nsres=%f"), region.ns_res);
    G_verbose_message(_("ewres=%f"), region.ew_res);
    G_verbose_message(_("rows=%d"), region.rows);
    G_verbose_message(_("cols=%d"), region.cols);
    G_verbose_message("");

    for (i = 0; i < 4; i++) {
	switch (i) {
	case 0:
	    strncpy(array_name, "map_northern_edge", 31);
	    val_d = region.north;
	    break;
	case 1:
	    strncpy(array_name, "map_southern_edge", 31);
	    val_d = region.south;
	    break;
	case 2:
	    strncpy(array_name, "map_eastern_edge", 31);
	    val_d = region.east;
	    break;
	case 3:
	    strncpy(array_name, "map_western_edge", 31);
	    val_d = region.west;
	    break;
	default:
	    fclose(fp1);
	    G_fatal_error("please contact development team");
	    break;
	}

	/** write data element **/
	data_format = 0;	/* 0=double  1=float  2=32bit signed int  5=8bit unsigned int(text) */
	data_type = 0;		/* 0=numbers  1=text */
	mrows = 1;
	ncols = 1;

	/* 4 byte data format */
	format_block = endianness * 1000 + data_format * 10 + data_type;
	fwrite(&format_block, sizeof(int), 1, fp1);
	/* fprintf(stderr, "bounds data format is [%04ld]\n", format_block); */

	/* 4 byte number of rows , 4 byte number of colums */
	fwrite(&mrows, sizeof(int), 1, fp1);
	fwrite(&ncols, sizeof(int), 1, fp1);

	/* 4 byte real/imag flag   0=only real */
	fwrite(&realflag, sizeof(int), 1, fp1);

	/* length of array_name+1 */
	name_len = strlen(array_name) + 1;
	fwrite(&name_len, sizeof(int), 1, fp1);

	/* array name */
	fprintf(fp1, "%s%c", array_name, '\0');

	/* write array data, by increasing column */
	fwrite(&val_d, sizeof(double), 1, fp1);

	/** end of data element **/
    }



    /***** Write map data *****/
    strncpy(array_name, "map_data", 31);

    switch (map_type) {		/* data_format: 0=double  1=float  2=32bit signed int  5=8bit unsigned int (ie text) */

    case CELL_TYPE:
	data_format = 2;
	G_verbose_message(_("Exporting raster as integer values"));
	break;

    case FCELL_TYPE:
	data_format = 1;
	G_verbose_message(_("Exporting raster as floating point values"));
	break;

    case DCELL_TYPE:
	data_format = 0;
	G_verbose_message(_("Exporting raster as double FP values"));
	break;

    default:
	fclose(fp1);
	G_fatal_error("Please contact development team");
	break;
    }

    data_type = 0;		/* 0=numbers  1=text */

    mrows = region.rows;
    ncols = region.cols;

    /* 4 byte data format */
    format_block = (endianness * 1000) + (data_format * 10) + data_type;
    fwrite(&format_block, sizeof(int), 1, fp1);

    G_debug(3, "map data format is [%04d]\n", format_block);

    /* 4 byte number of rows & columns */
    fwrite(&mrows, sizeof(int), 1, fp1);
    fwrite(&ncols, sizeof(int), 1, fp1);

    /* 4 byte real/imag flag   0=only real */
    fwrite(&realflag, sizeof(int), 1, fp1);

    /* length of array_name+1 */
    name_len = strlen(array_name) + 1;
    fwrite(&name_len, sizeof(int), 1, fp1);

    /* array name */
    fprintf(fp1, "%s%c", array_name, '\0');

    /* data array, by increasing column */
    raster =
	G_calloc((Rast_window_rows() + 1) * (Rast_window_cols() + 1),
		 Rast_cell_size(map_type));

    G_debug(1, "mem alloc is %d bytes\n",	/* I think _cols()+1 is unneeded? */
	    Rast_cell_size(map_type) * (Rast_window_rows() +
				       1) * (Rast_window_cols() + 1));

    G_verbose_message(_("Reading in map ... "));

    /* load entire map into memory */
    for (row = 0, ptr = raster; row < mrows; row++,
	 ptr =
	 G_incr_void_ptr(ptr,
			 (Rast_window_cols() + 1) * Rast_cell_size(map_type))) {
	Rast_get_row(fd, ptr, row, map_type);
	G_percent(row, mrows, 2);
    }
    G_percent(row, mrows, 2);	/* finish it off */


    G_verbose_message(_("Writing out map..."));

    /* then write it to disk */
    /* NoGood: fwrite(raster, Rast_cell_size(map_type), mrows*ncols, fp1); */
    for (col = 0; col < ncols; col++) {
	for (row = 0; row < mrows; row++) {

	    ptr = raster;
	    ptr =
		G_incr_void_ptr(ptr,
				(col +
				 row * (ncols +
					1)) * Rast_cell_size(map_type));

	    if (!Rast_is_null_value(ptr, map_type)) {
		if (map_type == CELL_TYPE) {
		    val_i = *((CELL *) ptr);
		    fwrite(&val_i, sizeof(int), 1, fp1);
		}
		else if (map_type == FCELL_TYPE) {
		    val_f = *((FCELL *) ptr);
		    fwrite(&val_f, sizeof(float), 1, fp1);
		}
		else if (map_type == DCELL_TYPE) {
		    val_d = *((DCELL *) ptr);
		    fwrite(&val_d, sizeof(double), 1, fp1);
		}
	    }
	    else {		/* ie if NULL cell -> write IEEE NaN value */
		if (map_type == CELL_TYPE) {
		    val_i = *((CELL *) ptr);	/* int has no NaN value, so use whatever GRASS uses */
		    fwrite(&val_i, sizeof(int), 1, fp1);
		}
		else if (map_type == FCELL_TYPE) {
		    if (endianness)	/* ie big */
			fprintf(fp1, "%c%c%c%c", 0xff, 0xf8, 0, 0);
		    else	/* ie little */
			fprintf(fp1, "%c%c%c%c", 0, 0, 0xf8, 0xff);
		}
		else if (map_type == DCELL_TYPE) {
		    if (endianness)
			fprintf(fp1, "%c%c%c%c%c%c%c%c", 0xff, 0xf8, 0, 0, 0,
				0, 0, 0);
		    else
			fprintf(fp1, "%c%c%c%c%c%c%c%c", 0, 0, 0, 0, 0, 0,
				0xf8, 0xff);
		}
	    }
	}
	G_percent(col, ncols, 2);
    }
    G_percent(col, ncols, 2);	/* finish it off */

    /*** end of data element ***/


    /* done! */
    filesize = G_ftell(fp1);
    fclose(fp1);

    G_verbose_message(_("%ld bytes written to '%s'"), filesize, outfile);

    G_done_msg("");

    G_free(basename);
    G_free(outfile);

    exit(EXIT_SUCCESS);
}
Exemple #23
0
/* DEFINE SAMPLING UNITS MANUALLY */
static void man_unit(int t, int b, int l, int r, char *n1, char *n2, char *n3,
		     double *mx, int fmask)
{
    int i, j, dx, dy, w_w, w_l, u_w, u_l,
	method, l0, t0, randflag = 0, unit_num, num = 0, scales,
	h_d = 1, v_d = 1, itmp, thick, sites, *row_buf, fr, k,
	count = 0, maxsize = 0, nx = 0, ny = 0, numx = 0, numy = 0,
	al = 0, ar = 0, at = 0, ab = 0, au_w = 0, au_l = 0;
    double *ux, *uy;
    FILE *fp;
    double dtmp, ratio, size, intv = 0.0, start[2], cnt = 0, radius = 0.0;
    char *sites_mapset;
    struct Cell_head wind;

    /*  VARIABLES:
       COORDINATES IN THIS ROUTINE ARE IN CELLS

       t    =       top row of sampling frame
       b    =       bottom row of sampling frame
       l    =       left col of sampling frame
       r    =       right col of sampling frame
       n1   =
       n2   =
       n3   =
       start[0]=    row of UL corner of starting pt for strata
       start[1]=    col of UL corner of starting pt for strata
       mx[0]        =       cols of region/width of screen
       mx[1]        =       rows of region/height of screen

     */


    start[0] = 0.0;
    start[1] = 0.0;

    l = (int)((double)(l * mx[0]) + 0.5);
    r = (int)((double)(r * mx[0]) + 0.5);
    t = (int)((double)(t * mx[1]) + 0.5);
    b = (int)((double)(b * mx[1]) + 0.5);
    w_w = r - l;
    w_l = b - t;

    /* draw the sampling frame */

    R_open_driver();
    R_standard_color(D_translate_color("grey"));
    draw_box((int)(l / mx[0] + 0.5), (int)(t / mx[1] + 0.5),
	     (int)(r / mx[0] + 0.5), (int)(b / mx[1] + 0.5), 1);
    R_close_driver();

    /* open the units file for output */

    fp = fopen0("r.le.para/units", "w");
    G_sleep_on_error(0);

    /* get the number of scales */

    do {
	fprintf(stderr,
		"\n    How many different SCALES do you want (1-15)?   ");

	numtrap(1, &dtmp);
	if (dtmp > 15 || dtmp < 1) {
	    fprintf(stderr,
		    "\n    Too many (>15) or too few scales; try again");

	}
    }
    while (dtmp < 1 || dtmp > 15);

    fprintf(fp, "%10d    # of scales\n", (scales = (int)dtmp));


    /* for each scale */

    for (i = 0; i < scales; i++) {
	for (;;) {
	    G_system("clear");

	    radius = 0.0;

	    fprintf(stderr, "\n\n    TYPE IN PARAMETERS FOR SCALE %d:\n",
		    i + 1);


	    /* get the distribution method */

	    fprintf(stderr,
		    "\n    Choose method of sampling unit DISTRIBUTION  \n");
	    fprintf(stderr, "       Random nonoverlapping       1\n");
	    fprintf(stderr, "       Systematic contiguous       2\n");
	    fprintf(stderr, "       Systematic noncontiguous    3\n");
	    fprintf(stderr, "       Stratified random           4\n");
	    fprintf(stderr, "       Centered over sites         5\n");
	    fprintf(stderr, "       Exit to setup option menu   6\n\n");

	    do {
		fprintf(stderr, "                       Which Number?   ");

		numtrap(1, &dtmp);
		if ((method = fabs(dtmp)) > 6 || method < 1) {
		    fprintf(stderr,
			    "\n    Choice must between 1-5; try again");

		}
	    }
	    while (method > 6 || method < 1);

	    if (method == 6)
		return;

	    /* for stratified random distribution,
	       determine the number of strata */

	    if (method == 4) {
	      getstrata:
		fprintf(stderr,
			"\n    Number of strata along the x-axis? (1-60)  ");

		numtrap(1, &dtmp);
		h_d = fabs(dtmp);

		fprintf(stderr,
			"\n    Number of strata along the y-axis? (1-60)  ");

		numtrap(1, &dtmp);
		v_d = fabs(dtmp);

		if (h_d < 1 || v_d < 1 || h_d > 60 || v_d > 60) {
		    fprintf(stderr,
			    "\n    Number must be between 1-60; try again.");

		    goto getstrata;
		}
	    }

	    /* for methods with strata */

	    if (method == 2 || method == 3 || method == 4) {
	      strata:
		fprintf(stderr,
			"\n    Sampling frame row & col for upper left corner of");
		fprintf(stderr,
			" the strata?\n       Rows are numbered down and columns");
		fprintf(stderr,
			" are numbered to the right\n       Enter 1 1 to start in");
		fprintf(stderr, " upper left corner of sampling frame:  ");

		numtrap(2, start);
		start[0] = start[0] - 1.0;
		start[1] = start[1] - 1.0;
		if (start[0] > w_l || start[0] < 0 ||
		    start[1] > w_w || start[1] < 0) {
		    fprintf(stderr,
			    "\n    The starting row and col you entered are outside");
		    fprintf(stderr,
			    " the sampling frame\n       Try again\n");

		    goto strata;
		}
	    }


	    if (method == 4) {

		/* call draw_grid with the left, top, width,
		   length, the number of horizontal and
		   vertical strata, and the starting row
		   and col for the strata */

		draw_grid((int)(l / mx[0] + 0.5), (int)(t / mx[1] + 0.5),
			  (int)(w_w / mx[0] + 0.5), (int)(w_l / mx[1] + 0.5),
			  h_d, v_d, (int)(start[0] / mx[1] + 0.5),
			  (int)(start[1] / mx[0] + 0.5), mx[0], mx[1]);
		if (!G_yes("    Are these strata OK?   ", 1)) {
		    if (G_yes("\n\n    Refresh the screen?   ", 1)) {
			paint_map(n1, n2, n3);
			R_open_driver();
			R_standard_color(D_translate_color("grey"));
			draw_box((int)(l / mx[0] + 0.5),
				 (int)(t / mx[1] + 0.5),
				 (int)(r / mx[0] + 0.5),
				 (int)(b / mx[1] + 0.5), 1);
			R_close_driver();
		    }
		    goto getstrata;
		}
	    }

	    /* if sampling using circles */

	    fprintf(stderr, "\n    Do you want to sample using rectangles");

	    if (!G_yes
		("\n       (including squares) (y) or circles (n)?   ", 1)) {
	      getradius:
		fprintf(stderr,
			"\n    What radius do you want for the circles?  Radius");
		fprintf(stderr,
			"\n       is in pixels; add 0.5 pixels, for the center");
		fprintf(stderr,
			"\n       pixel, to the number of pixels outside the");
		fprintf(stderr,
			"\n       center pixel.  Type a real number with one");
		fprintf(stderr,
			"\n       decimal place ending in .5 (e.g., 4.5):        ");

		numtrap(1, &radius);
		if (radius > 100.0) {
		    fprintf(stderr,
			    "\n    Are you sure that you want such a large");

		    if (!G_yes("\n       radius (> 100 pixels)?   ", 1))
			goto getradius;
		}

		ratio = 1.0;
		u_w = (int)(2 * radius);
		u_l = (int)(2 * radius);

		if (fmask > 0) {
		    count = 0;
		    row_buf = Rast_allocate_buf(CELL_TYPE);
		    fr = Rast_open_old(n1, G_mapset());
		    for (j = t; j < b; j++) {
			Rast_zero_buf(row_buf, CELL_TYPE);
			Rast_get_row(fr, row_buf, j, CELL_TYPE);
			for (k = l; k < r; k++) {
			    if (*(row_buf + k))
				count++;
			}
		    }
		    G_free(row_buf);
		    Rast_close(fr);
		    cnt = (double)(count);
		    if (cnt)
			cnt = sqrt(cnt);
		    else
			cnt = 0;
		}
		else {
		    count = (w_l - (int)(start[0])) * (w_w - (int)(start[1]));
		}
	    }

	    /* if sampling using rectangles/squares */

	    else {

		/* get the width/length ratio */

	      getratio:
		fprintf(stderr,
			"\n    Sampling unit SHAPE (aspect ratio, #cols/#rows) "
			"expressed as real number"
			"\n    (e.g., 10 cols/5 rows = 2.0) for sampling units "
			"of scale %d? ", i + 1);

		numtrap(1, &ratio);
		if (ratio < 0)
		    ratio = -ratio;
		else if (ratio > 25.0)
		    if (!G_yes
			("\n    Are you sure you want such a large ratio?   ",
			 1))
			goto getratio;

		/* determine the recommended maximum size
		   for sampling units */

	      getsize:
		dtmp = (ratio > 1) ? 1 / ratio : ratio;
		dtmp /= (h_d > v_d) ? h_d * h_d : v_d * v_d;

	      tryagain:
		if (method == 1) {

		    if (fmask > 0) {
			count = 0;
			row_buf = Rast_allocate_buf(CELL_TYPE);
			fr = Rast_open_old(n1, G_mapset());
			for (j = t; j < b; j++) {
			    Rast_zero_buf(row_buf, CELL_TYPE);
			    Rast_get_row(fr, row_buf, j, CELL_TYPE);
			    for (k = l; k < r; k++) {
				if (*(row_buf + k))
				    count++;
			    }
			}
			G_free(row_buf);
			Rast_close(fr);
			cnt = (double)(count);
			if (cnt)
			    cnt = sqrt(cnt);
			else
			    cnt = 0;
			maxsize =
			    ((cnt * dtmp / 2) * (cnt * dtmp / 2) >
			     1.0 / dtmp) ? (cnt * dtmp / 2) * (cnt * dtmp /
							       2) : 1.0 /
			    dtmp;
			fprintf(stderr,
				"\n    Recommended maximum SIZE is %d in %d cell total",
				maxsize, count);
			fprintf(stderr, " area\n");

		    }

		    else {
			fprintf(stderr, "\n    Recommended maximum SIZE is");
			fprintf(stderr, " %d in %d pixel total area\n",
				(int)((w_l - (int)(start[0])) * (w_w -
								 (int)(start
								       [1])) *
				      dtmp / 2),
				(w_l - (int)(start[0])) * (w_w -
							   (int)(start[1])));

			count =
			    (w_l - (int)(start[0])) * (w_w - (int)(start[1]));
			maxsize =
			    (int)((w_l - (int)(start[0])) * (w_w -
							     (int)(start[1]))
				  * dtmp / 2);
		    }
		}

		else if (method == 2 || method == 3 || method == 5) {
		    fprintf(stderr,
			    "\n    Recommended maximum SIZE is %d in %d pixel total",
			    (int)((w_l - (int)(start[0])) * (w_w -
							     (int)(start[1]))
				  * dtmp / 2),
			    (w_l - (int)(start[0])) * (w_w -
						       (int)(start[1])));
		    fprintf(stderr, " area\n");

		}

		else if (method == 4) {
		    fprintf(stderr, "\n    Recommended maximum SIZE is");
		    fprintf(stderr, " %d in %d pixel individual",
			    (int)(w_w * w_l * dtmp / 2),
			    ((w_w - (int)(start[1])) / h_d) * ((w_l -
								(int)(start
								      [0])) /
							       v_d));
		    fprintf(stderr, " stratum area\n");

		}

		/* get the unit size, display the calculated
		   size, and ask if it is OK */

		fprintf(stderr,
			"    What size (in pixels) for each sampling unit of scale %d?  ",
			i + 1);

		numtrap(1, &size);
		thick = 1;
		if (size < 15 || ratio < 0.2 || ratio > 5)
		    thick = 0;
		u_w = sqrt(size * ratio);
		u_l = sqrt(size / ratio);
		fprintf(stderr,
			"\n    The nearest size is %d cells wide X %d cells high = %d",
			u_w, u_l, u_w * u_l);
		fprintf(stderr, " cells\n");

		if (!u_w || !u_l) {
		    fprintf(stderr,
			    "\n    0 cells wide or high is not acceptable; try again");

		    goto tryagain;
		}
		if (!G_yes("    Is this SIZE OK?   ", 1))
		    goto getsize;
	    }

	    /* for syst. noncontig. distribution, get
	       the interval between units */

	    if (method == 3) {
		fprintf(stderr,
			"\n    The interval, in pixels, between the units of scale");
		fprintf(stderr, " %d?  ", i + 1);

		numtrap(1, &intv);
	    }

	    /* if the unit dimension + the interval
	       is too large, print a warning and
	       try getting another size */

	    if (u_w + intv > w_w / h_d || u_l + intv > w_l / v_d) {
		fprintf(stderr,
			"\n    Unit size too large for sampling frame; try again\n");

		if (radius)
		    goto getradius;
		else
		    goto getsize;

	    }

	    /* for stratified random distribution,
	       the number of units is the same as
	       the number of strata */

	    if (method == 4)
		num = h_d * v_d;

	    /* for the other distributions, calculate the
	       maximum number of units, then get the
	       number of units */

	    else if (method == 1 || method == 2 || method == 3) {

		if (method == 1) {
		    if (!
			(unit_num =
			 calc_num(w_w, w_l, ratio, u_w, u_l, method, intv,
				  (int)(start[1]), (int)(start[0]), u_w * u_l,
				  count))) {
			fprintf(stderr,
				"\n    Something wrong with sampling unit size, try again\n");

			if (radius)
			    goto getradius;
			else
			    goto getsize;
		    }
		    fprintf(stderr,
			    "\n    Maximum NUMBER of units in scale %d is %d\n",
			    i + 1, unit_num);
		    fprintf(stderr,
			    "    Usually 1/2 of this number can be successfully");
		    fprintf(stderr,
			    " distributed\n    More than 1/2 can sometimes be");
		    fprintf(stderr, " distributed\n");

		}

		else if (method == 2 || method == 3) {
		    numx = floor((double)(w_w - start[1]) / (u_w + intv));
		    numy = floor((double)(w_l - start[0]) / (u_l + intv));
		    if (((w_w -
			  (int)(start[1])) % (numx * (u_w + (int)(intv)))) >=
			u_w)
			numx++;
		    if (((w_l -
			  (int)(start[0])) % (numy * (u_l + (int)(intv)))) >=
			u_l)
			numy++;
		    unit_num = numx * numy;
		    fprintf(stderr,
			    "\n    Maximum NUMBER of units in scale %d is %d as %d",
			    i + 1, unit_num, numy);
		    fprintf(stderr, " rows with %d units per row", numx);

		}

		do {
		    fprintf(stderr,
			    "\n    What NUMBER of sampling units do you want to try");
		    fprintf(stderr, " to use?  ");

		    numtrap(1, &dtmp);

		    if ((num = dtmp) > unit_num || num < 1) {
			fprintf(stderr,
				"\n    %d is greater than the maximum number of",
				num);
			fprintf(stderr, " sampling units; try again\n");

		    }

		    else if (method == 2 || method == 3) {
			fprintf(stderr,
				"\n    How many sampling units do you want per row?  ");

			numtrap(1, &dtmp);
			if ((nx = dtmp) > num) {
			    fprintf(stderr,
				    "\n    Number in each row > number requested; try");
			    fprintf(stderr, " again\n");

			}
			else {
			    if (nx > numx) {
				fprintf(stderr,
					"\n    Can't fit %d units in each row, try",
					nx);
				fprintf(stderr, " again\n");

			    }
			    else {
				if (num % nx)
				    ny = num / nx + 1;
				else
				    ny = num / nx;
				if (ny > numy) {
				    fprintf(stderr,
					    "\n    Can't fit the needed %d rows, try",
					    ny);
				    fprintf(stderr, " again\n");

				}
			    }
			}
		    }
		}
		while (num > unit_num || num < 1 || nx > num || nx > numx ||
		       ny > numy);
	    }

	    /* dynamically allocate storage for arrays to
	       store the upper left corner of sampling
	       units */

	    if (method != 5) {
		ux = G_calloc(num + 1, sizeof(double));
		uy = G_calloc(num + 1, sizeof(double));
	    }

	    else {
		ux = G_calloc(250, sizeof(double));
		uy = G_calloc(250, sizeof(double));
	    }

	    /* calculate the upper left corner of sampling
	       units and store them in arrays ux and uy */

	    if (!calc_unit_loc
		(radius, t, b, l, r, ratio, u_w, u_l, method, intv, num, h_d,
		 v_d, ux, uy, &sites, (int)(start[1]), (int)(start[0]), fmask,
		 nx, mx[0], mx[1]))
		goto last;

	    signal(SIGINT, SIG_DFL);
	    if (method == 5)
		num = sites;

	    /* draw the sampling units on the
	       screen */

	    if (method == 2 || method == 3 || method == 5) {
		R_open_driver();
		R_standard_color(D_translate_color("red"));
		for (j = 0; j < num; j++) {
		    if (radius) {
			draw_circle((int)((double)(ux[j]) / mx[0]),
				    (int)((double)(uy[j]) / mx[1]),
				    (int)((double)(ux[j] + u_w) / mx[0]),
				    (int)((double)(uy[j] + u_l) / mx[1]), 3);
		    }
		    else {
			draw_box((int)((double)(ux[j]) / mx[0]),
				 (int)((double)(uy[j]) / mx[1]),
				 (int)((double)(ux[j] + u_w) / mx[0]),
				 (int)((double)(uy[j] + u_l) / mx[1]), 1);
		    }
		}
		R_close_driver();
	    }

	    if (G_yes("\n    Is this set of sampling units OK?   ", 1))
		break;
	  last:
	    signal(SIGINT, SIG_DFL);
	    if (G_yes("\n    Refresh the screen?   ", 1)) {
		paint_map(n1, n2, n3);
		R_open_driver();
		R_standard_color(D_translate_color("grey"));
		draw_box((int)(l / mx[0]), (int)(t / mx[1]), (int)(r / mx[0]),
			 (int)(b / mx[1]), 1);
		R_close_driver();
	    }
	}

	/* save the sampling unit parameters
	   in r.le.para/units file */

	fprintf(fp, "%10d    # of units of scale %d.\n", num, (i + 1));
	fprintf(fp, "%10d%10d   u_w, u_l of units in scale %d\n", u_w, u_l,
		(i + 1));
	fprintf(fp, "%10.1f             radius of circles in scale %d\n",
		radius, (i + 1));

	for (j = 0; j < num; j++)
	    fprintf(fp, "%10d%10d   left, top of unit[%d]\n", (int)ux[j],
		    (int)uy[j], j + 1);

	if (i < scales - 1 && G_yes("\n\n    Refresh the screen?   ", 1)) {
	    paint_map(n1, n2, n3);
	    R_open_driver();
	    R_standard_color(D_translate_color("grey"));
	    draw_box((int)(l / mx[0]), (int)(t / mx[1]), (int)(r / mx[0]),
		     (int)(b / mx[1]), 1);
	    R_close_driver();
	}
    }

    /* free dynamically allocated memory */

    G_free(ux);
    G_free(uy);
    fclose(fp);
    return;
}
Exemple #24
0
int main(int argc, char *argv[])
{
    struct Cell_head cellhd;	/*region+header info */
    char *mapset;		/*mapset name */
    int nrows, ncols;
    int row, col;
    struct GModule *module;
    struct Option *input, *output;
    struct Option *input1, *input2;
    struct Flag *flag0, *flag1, *flag2;
    struct Flag *flag3, *flag4, *flag5;
    struct History history;	/*metadata */

    /************************************/
    char *name;			/*input raster name */
    char *result;		/*output raster name */

    /*Prepare new names for output files */
    char result0[GNAME_MAX], result1[GNAME_MAX];
    char result2[GNAME_MAX], result3[GNAME_MAX];
    char result4[GNAME_MAX], result5[GNAME_MAX];
    char result6[GNAME_MAX], result7[GNAME_MAX];
    char result8[GNAME_MAX], result9[GNAME_MAX];
    char result10[GNAME_MAX], result11[GNAME_MAX];
    char result12[GNAME_MAX], result13[GNAME_MAX];
    char result14[GNAME_MAX];

    /*File Descriptors */
    int infd[MAXFILES];
    int outfd[MAXFILES];
    char **names, **ptr;
    /* For some strange reason infd[0] cannot be used later */
    /* So nfiles is initialized with nfiles = 1 */
    int nfiles = 1;
    int i = 0, j = 0;
    int radiance = 0;
    void *inrast[MAXFILES];
    DCELL *outrast[MAXFILES];
    RASTER_MAP_TYPE in_data_type[MAXFILES];
    RASTER_MAP_TYPE out_data_type = DCELL_TYPE;	/* 0=numbers  1=text */
    double gain[MAXFILES], offset[MAXFILES];
    double kexo[MAXFILES];
    double doy, sun_elevation;

    /************************************/
    G_gisinit(argv[0]);
    module = G_define_module();
    G_add_keyword(_("imagery"));
    G_add_keyword(_("radiometric conversion"));
    G_add_keyword(_("radiance"));
    G_add_keyword(_("reflectance"));
    G_add_keyword(_("brightness temperature"));
    G_add_keyword(_("satellite"));
    G_add_keyword(_("ASTER"));
    module->description =
	_("Calculates Top of Atmosphere Radiance/Reflectance/Brightness Temperature from ASTER DN.\n");

    /* Define the different options */
    input = G_define_standard_option(G_OPT_R_INPUTS);
    input->description = _("Names of ASTER DN layers (15 layers)");

    input1 = G_define_option();
    input1->key = "dayofyear";
    input1->type = TYPE_DOUBLE;
    input1->required = YES;
    input1->gisprompt = "value";
    input1->description = _("Day of Year of satellite overpass [0-366]");

    input2 = G_define_option();
    input2->key = "sun_elevation";
    input2->type = TYPE_DOUBLE;
    input2->required = YES;
    input2->gisprompt = "value";
    input2->description = _("Sun elevation angle (degrees, < 90.0)");

    output = G_define_standard_option(G_OPT_R_OUTPUT);
    output->description = _("Base name of the output layers (will add .x)");

    /* Define the different flags */
    flag0 = G_define_flag();
    flag0->key = 'r';
    flag0->description = _("Output is radiance (W/m2)");

    flag1 = G_define_flag();
    flag1->key = 'a';
    flag1->description = _("VNIR is High Gain");

    flag2 = G_define_flag();
    flag2->key = 'b';
    flag2->description = _("SWIR is High Gain");

    flag3 = G_define_flag();
    flag3->key = 'c';
    flag3->description = _("VNIR is Low Gain 1");

    flag4 = G_define_flag();
    flag4->key = 'd';
    flag4->description = _("SWIR is Low Gain 1");

    flag5 = G_define_flag();
    flag5->key = 'e';
    flag5->description = _("SWIR is Low Gain 2");

    /********************/
    if (G_parser(argc, argv))
	exit(EXIT_FAILURE);

    names = input->answers;
    ptr = input->answers;
    doy = atof(input1->answer);
    sun_elevation = atof(input2->answer);
    result = output->answer;

    radiance = (flag0->answer);

    /********************/
    /*Prepare the output file names */

    /********************/
    sprintf(result0,"%s%s", result, ".1");
    sprintf(result1,"%s%s", result, ".2");
    sprintf(result2,"%s%s", result, ".3N");
    sprintf(result3,"%s%s", result, ".3B");
    sprintf(result4,"%s%s", result, ".4");
    sprintf(result5,"%s%s", result, ".5");
    sprintf(result6,"%s%s", result, ".6");
    sprintf(result7,"%s%s", result, ".7");
    sprintf(result8,"%s%s", result, ".8");
    sprintf(result9,"%s%s", result, ".9");
    sprintf(result10,"%s%s", result, ".10");
    sprintf(result11,"%s%s", result, ".11");
    sprintf(result12,"%s%s", result, ".12");
    sprintf(result13,"%s%s", result, ".13");
    sprintf(result14,"%s%s", result, ".14");
    /********************/
    /*Prepare radiance boundaries */

    /********************/
    int gain_code = 1;

    for (i = 0; i < MAXFILES; i++) {
	/*0 - High (Not Applicable for band 10-14: TIR) */
	/*1 - Normal */
	/*2 - Low 1(Not Applicable for band 10-14: TIR) */
	/*3 - Low 2(Not Applicable for Band 1-3N/B & 10-14) */
	if (flag1->answer && i <= 3)
	    gain_code = 0;
	if (flag2->answer && i >= 4 && i <= 9)
	    gain_code = 0;
	if (flag3->answer && i <= 3)
	    gain_code = 2;
	if (flag4->answer && i >= 4 && i <= 9)
	    gain_code = 2;
	if (flag5->answer && i >= 4 && i <= 9)
	    gain_code = 3;
	gain[i] = gain_aster(i, gain_code);
	/* Reset to NORMAL GAIN */
	gain_code = 1;
    }

    /********************/
    /*Prepare sun exo-atm irradiance */

    /********************/
    kexo[0] = KEXO1;
    kexo[1] = KEXO2;
    kexo[2] = KEXO3;
    kexo[3] = KEXO3;
    kexo[4] = KEXO4;
    kexo[5] = KEXO5;
    kexo[6] = KEXO6;
    kexo[7] = KEXO7;
    kexo[8] = KEXO8;
    kexo[9] = KEXO9;

    /********************/

    /********************/
    for (; *ptr != NULL; ptr++) {
	if (nfiles > MAXFILES)
	    G_fatal_error(_("Too many input maps. Only %d allowed."),
			  MAXFILES);
	name = *ptr;
	/* Allocate input buffer */
	in_data_type[nfiles-1] = Rast_map_type(name, "");
	/* For some strange reason infd[0] cannot be used later */
	/* So nfiles is initialized with nfiles = 1 */
	infd[nfiles] = Rast_open_old(name, "");

	Rast_get_cellhd(name, "", &cellhd);
	inrast[nfiles-1] = Rast_allocate_buf(in_data_type[nfiles-1]);
	nfiles++;
    }
    nfiles--;
    if (nfiles < MAXFILES) 
	G_fatal_error(_("The input band number should be 15"));

    /***************************************************/
    /* Allocate output buffer, use input map data_type */
    nrows = Rast_window_rows();
    ncols = Rast_window_cols();
    out_data_type = DCELL_TYPE;
    for (i = 0; i < MAXFILES; i++)
	outrast[i] = Rast_allocate_buf(out_data_type);

    outfd[1] = Rast_open_new(result0, 1);
    outfd[2] = Rast_open_new(result1, 1);
    outfd[3] = Rast_open_new(result2, 1);
    outfd[4] = Rast_open_new(result3, 1);
    outfd[5] = Rast_open_new(result4, 1);
    outfd[6] = Rast_open_new(result5, 1);
    outfd[7] = Rast_open_new(result6, 1);
    outfd[8] = Rast_open_new(result7, 1);
    outfd[9] = Rast_open_new(result8, 1);
    outfd[10] = Rast_open_new(result9, 1);
    outfd[11] = Rast_open_new(result10, 1);
    outfd[12] = Rast_open_new(result11, 1);
    outfd[13] = Rast_open_new(result12, 1);
    outfd[14] = Rast_open_new(result13, 1);
    outfd[15] = Rast_open_new(result14, 1);
    /* Process pixels */

    DCELL dout[MAXFILES];
    DCELL d[MAXFILES];

    for (row = 0; row < nrows; row++) {
	G_percent(row, nrows, 2);
	/* read input map */
	for (i = 1; i <= MAXFILES; i++)
	    Rast_get_row(infd[i], inrast[i-1], row, in_data_type[i-1]);

	/*process the data */
	for (col = 0; col < ncols; col++) {
	    for (i = 0; i < MAXFILES; i++) {
		switch (in_data_type[i]) {
		case CELL_TYPE:
		    d[i] = (double)((CELL *) inrast[i])[col];
		    break;
		case FCELL_TYPE:
		    d[i] = (double)((FCELL *) inrast[i])[col];
		    break;
		case DCELL_TYPE:
		    d[i] = (double)((DCELL *) inrast[i])[col];
		    break;
		}
		/* if radiance mode or Thermal band */
		if (radiance || i >= 10) {
		    dout[i] = gain[i] * (d[i] - 1.0);
		}
		/* if reflectance default mode and Not Thermal Band */
		else {
		    dout[i] = gain[i] * (d[i] - 1.0);
		    dout[i] =
			rad2ref_aster(dout[i], doy, sun_elevation, kexo[i]);
		}
		outrast[i][col] = dout[i];
	    }
	}
	for (i = 1; i <= MAXFILES; i++)
	    Rast_put_row(outfd[i], outrast[i-1], out_data_type);
    }
    for (i = 1; i <= MAXFILES; i++) {
	G_free(inrast[i-1]);
	Rast_close(infd[i]);
	G_free(outrast[i-1]);
	Rast_close(outfd[i]);
    }
    exit(EXIT_SUCCESS);
}
Exemple #25
0
int main(int argc, char **argv)
{
    struct Cell_head window;
    RASTER_MAP_TYPE raster_type, mag_raster_type = -1;
    int layer_fd;
    void *raster_row, *ptr;
    int nrows, ncols;
    int aspect_c = -1;
    float aspect_f = -1.0;

    double scale;
    int skip, no_arrow;
    char *mag_map = NULL;
    void *mag_raster_row = NULL, *mag_ptr = NULL;
    double length = -1;
    int mag_fd = -1;
    struct FPRange range;
    double mag_min, mag_max;

    struct GModule *module;
    struct Option *opt1, *opt2, *opt3, *opt4, *opt5,
	*opt6, *opt7, *opt8, *opt9;
    struct Flag *align;

    double t, b, l, r;

    G_gisinit(argv[0]);

    module = G_define_module();
    G_add_keyword(_("display"));
    G_add_keyword(_("raster"));
    module->description =
	_("Draws arrows representing cell aspect direction "
	  "for a raster map containing aspect data.");

    opt1 = G_define_standard_option(G_OPT_R_MAP);
    opt1->description = _("Name of raster aspect map to be displayed");

    opt2 = G_define_option();
    opt2->key = "type";
    opt2->type = TYPE_STRING;
    opt2->required = NO;
    opt2->answer = "grass";
    opt2->options = "grass,compass,agnps,answers";
    opt2->description = _("Type of existing raster aspect map");

    opt3 = G_define_option();
    opt3->key = "arrow_color";
    opt3->type = TYPE_STRING;
    opt3->required = NO;
    opt3->answer = "green";
    opt3->gisprompt = "old_color,color,color";
    opt3->description = _("Color for drawing arrows");
    opt3->guisection = _("Colors");
    
    opt4 = G_define_option();
    opt4->key = "grid_color";
    opt4->type = TYPE_STRING;
    opt4->required = NO;
    opt4->answer = "gray";
    opt4->gisprompt = "old_color,color,color_none";
    opt4->description = _("Color for drawing grid or \"none\"");
    opt4->guisection = _("Colors");

    opt5 = G_define_option();
    opt5->key = "x_color";
    opt5->type = TYPE_STRING;
    opt5->required = NO;
    opt5->answer = DEFAULT_FG_COLOR;
    opt5->gisprompt = "old_color,color,color_none";
    opt5->description = _("Color for drawing X's (null values)");
    opt5->guisection = _("Colors");

    opt6 = G_define_option();
    opt6->key = "unknown_color";
    opt6->type = TYPE_STRING;
    opt6->required = NO;
    opt6->answer = "red";
    opt6->gisprompt = "old_color,color,color_none";
    opt6->description = _("Color for showing unknown information");
    opt6->guisection = _("Colors");

    opt9 = G_define_option();
    opt9->key = "skip";
    opt9->type = TYPE_INTEGER;
    opt9->required = NO;
    opt9->answer = "1";
    opt9->description = _("Draw arrow every Nth grid cell");

    opt7 = G_define_option();
    opt7->key = "magnitude_map";
    opt7->type = TYPE_STRING;
    opt7->required = NO;
    opt7->multiple = NO;
    opt7->gisprompt = "old,cell,raster";
    opt7->description =
	_("Raster map containing values used for arrow length");

    opt8 = G_define_option();
    opt8->key = "scale";
    opt8->type = TYPE_DOUBLE;
    opt8->required = NO;
    opt8->answer = "1.0";
    opt8->description = _("Scale factor for arrows (magnitude map)");

    align = G_define_flag();
    align->key = 'a';
    align->description = _("Align grids with raster cells");


    /* Check command line */
    if (G_parser(argc, argv))
	exit(EXIT_FAILURE);


    layer_name = opt1->answer;

    arrow_color = D_translate_color(opt3->answer);
    x_color = D_translate_color(opt5->answer);
    unknown_color = D_translate_color(opt6->answer);

    if (strcmp("none", opt4->answer) == 0)
	grid_color = -1;
    else
	grid_color = D_translate_color(opt4->answer);


    if (strcmp("grass", opt2->answer) == 0)
	map_type = 1;
    else if (strcmp("agnps", opt2->answer) == 0)
	map_type = 2;
    else if (strcmp("answers", opt2->answer) == 0)
	map_type = 3;
    else if (strcmp("compass", opt2->answer) == 0)
	map_type = 4;


    scale = atof(opt8->answer);
    if (scale <= 0.0)
	G_fatal_error(_("Illegal value for scale factor"));

    skip = atoi(opt9->answer);
    if (skip <= 0)
	G_fatal_error(_("Illegal value for skip factor"));


    if (opt7->answer) {
	if (map_type != 1 && map_type != 4)
	    G_fatal_error(_("Magnitude is only supported for GRASS and compass aspect maps."));

	mag_map = opt7->answer;
    }
    else if (scale != 1.0)
	G_warning(_("Scale option requires magnitude_map"));


    /* Setup driver and check important information */
    if (D_open_driver() != 0)
      	G_fatal_error(_("No graphics device selected. "
			"Use d.mon to select graphics device."));
    
    D_setup(0);

    /* Read in the map window associated with window */
    G_get_window(&window);

    if (align->answer) {
	struct Cell_head wind;

	Rast_get_cellhd(layer_name, "", &wind);

	/* expand window extent by one wind resolution */
	wind.west += wind.ew_res * ((int)((window.west - wind.west) / wind.ew_res) - (window.west < wind.west));
	wind.east += wind.ew_res * ((int)((window.east - wind.east) / wind.ew_res) + (window.east > wind.east));
	wind.south += wind.ns_res * ((int)((window.south - wind.south) / wind.ns_res) - (window.south < wind.south));
	wind.north += wind.ns_res * ((int)((window.north - wind.north) / wind.ns_res) + (window.north > wind.north));

	wind.rows = (wind.north - wind.south) / wind.ns_res;
	wind.cols = (wind.east - wind.west) / wind.ew_res;

	Rast_set_window(&wind);

	nrows = wind.rows;
	ncols = wind.cols;

	t = (wind.north - window.north) * nrows / (wind.north - wind.south);
	b = t + (window.north - window.south) * nrows / (wind.north - wind.south);
	l = (window.west - wind.west) * ncols / (wind.east - wind.west);
	r = l + (window.east - window.west) * ncols / (wind.east - wind.west);
    } else {
        nrows = window.rows;
        ncols = window.cols;

	t = 0;
	b = nrows;
	l = 0;
	r = ncols;
    }

    D_set_src(t, b, l, r);
    D_update_conversions();

    /* figure out arrow scaling if using a magnitude map */
    if (opt7->answer) {
	Rast_init_fp_range(&range);	/* really needed? */
	if (Rast_read_fp_range(mag_map, "", &range) != 1)
	    G_fatal_error(_("Problem reading range file"));
	Rast_get_fp_range_min_max(&range, &mag_min, &mag_max);

	scale *= 1.5 / fabs(mag_max);
	G_debug(3, "scaling=%.2f  rast_max=%.2f", scale, mag_max);
    }

    if (grid_color > 0) {	/* ie not "none" */
	/* Set color */
	D_use_color(grid_color);

	/* Draw vertical grids */
	for (col = 0; col < ncols; col++)
	    D_line_abs(col, 0, col, nrows);

	/* Draw horizontal grids */
	for (row = 0; row < nrows; row++)
	    D_line_abs(0, row, ncols, row);
    }

    /* open the raster map */
    layer_fd = Rast_open_old(layer_name, "");

    raster_type = Rast_get_map_type(layer_fd);

    /* allocate the cell array */
    raster_row = Rast_allocate_buf(raster_type);


    if (opt7->answer) {
	/* open the magnitude raster map */
	mag_fd = Rast_open_old(mag_map, "");

	mag_raster_type = Rast_get_map_type(mag_fd);

	/* allocate the cell array */
	mag_raster_row = Rast_allocate_buf(mag_raster_type);
    }


    /* loop through cells, find value, determine direction (n,s,e,w,ne,se,sw,nw),
       and call appropriate function to draw an arrow on the cell */

    for (row = 0; row < nrows; row++) {
	Rast_get_row(layer_fd, raster_row, row, raster_type);
	ptr = raster_row;

	if (opt7->answer) {
	    Rast_get_row(mag_fd, mag_raster_row, row, mag_raster_type);
	    mag_ptr = mag_raster_row;
	}

	for (col = 0; col < ncols; col++) {

	    if (row % skip != 0)
		no_arrow = TRUE;
	    else
		no_arrow = FALSE;

	    if (col % skip != 0)
		no_arrow = TRUE;

	    /* find aspect direction based on cell value */
	    if (raster_type == CELL_TYPE)
		aspect_f = *((CELL *) ptr);
	    else if (raster_type == FCELL_TYPE)
		aspect_f = *((FCELL *) ptr);
	    else if (raster_type == DCELL_TYPE)
		aspect_f = *((DCELL *) ptr);


	    if (opt7->answer) {

		if (mag_raster_type == CELL_TYPE)
		    length = *((CELL *) mag_ptr);
		else if (mag_raster_type == FCELL_TYPE)
		    length = *((FCELL *) mag_ptr);
		else if (mag_raster_type == DCELL_TYPE)
		    length = *((DCELL *) mag_ptr);

		length *= scale;

		if (Rast_is_null_value(mag_ptr, mag_raster_type)) {
		    G_debug(5, "Invalid arrow length [NULL]. Skipping.");
		    no_arrow = TRUE;
		}
		else if (length <= 0.0) {	/* use fabs() or theta+=180? */
		    G_debug(5, "Illegal arrow length [%.3f]. Skipping.",
			    length);
		    no_arrow = TRUE;
		}
	    }

	    if (no_arrow) {
		ptr = G_incr_void_ptr(ptr, Rast_cell_size(raster_type));
		if (opt7->answer)
		    mag_ptr =
			G_incr_void_ptr(mag_ptr,
					Rast_cell_size(mag_raster_type));
		no_arrow = FALSE;
		continue;
	    }

	    /* treat AGNPS and ANSWERS data like old zero-as-null CELL */
	    /*   TODO: update models */
	    if (map_type == 2 || map_type == 3) {
		if (Rast_is_null_value(ptr, raster_type))
		    aspect_c = 0;
		else
		    aspect_c = (int)(aspect_f + 0.5);
	    }


	    /** Now draw the arrows **/

	    /* case switch for standard GRASS aspect map 
	       measured in degrees counter-clockwise from east */
	    if (map_type == 1) {
		D_use_color(arrow_color);

		if (Rast_is_null_value(ptr, raster_type)) {
		    D_use_color(x_color);
		    draw_x();
		    D_use_color(arrow_color);
		}
		else if (aspect_f >= 0.0 && aspect_f <= 360.0) {
		    if (opt7->answer)
			arrow_mag(aspect_f, length);
		    else
			arrow_360(aspect_f);
		}
		else {
		    D_use_color(unknown_color);
		    unknown_();
		    D_use_color(arrow_color);
		}
	    }


	    /* case switch for AGNPS type aspect map */
	    else if (map_type == 2) {
		D_use_color(arrow_color);
		switch (aspect_c) {
		case 0:
		    D_use_color(x_color);
		    draw_x();
		    D_use_color(arrow_color);
		    break;
		case 1:
		    arrow_n();
		    break;
		case 2:
		    arrow_ne();
		    break;
		case 3:
		    arrow_e();
		    break;
		case 4:
		    arrow_se();
		    break;
		case 5:
		    arrow_s();
		    break;
		case 6:
		    arrow_sw();
		    break;
		case 7:
		    arrow_w();
		    break;
		case 8:
		    arrow_nw();
		    break;
		default:
		    D_use_color(unknown_color);
		    unknown_();
		    D_use_color(arrow_color);
		    break;
		}
	    }


	    /* case switch for ANSWERS type aspect map */
	    else if (map_type == 3) {
		D_use_color(arrow_color);
		if (aspect_c >= 15 && aspect_c <= 360)	/* start at zero? */
		    arrow_360((double)aspect_c);
		else if (aspect_c == 400) {
		    D_use_color(unknown_color);
		    unknown_();
		    D_use_color(arrow_color);
		}
		else {
		    D_use_color(x_color);
		    draw_x();
		    D_use_color(arrow_color);
		}
	    }

	    /* case switch for compass type aspect map
	       measured in degrees clockwise from north */
	    else if (map_type == 4) {
		D_use_color(arrow_color);

		if (Rast_is_null_value(ptr, raster_type)) {
		    D_use_color(x_color);
		    draw_x();
		    D_use_color(arrow_color);
		}
		else if (aspect_f >= 0.0 && aspect_f <= 360.0) {
		    if (opt7->answer)
			arrow_mag(90 - aspect_f, length);
		    else
			arrow_360(90 - aspect_f);
		}
		else {
		    D_use_color(unknown_color);
		    unknown_();
		    D_use_color(arrow_color);
		}
	    }

	    ptr = G_incr_void_ptr(ptr, Rast_cell_size(raster_type));
	    if (opt7->answer)
		mag_ptr =
		    G_incr_void_ptr(mag_ptr, Rast_cell_size(mag_raster_type));
	}
    }

    Rast_close(layer_fd);
    if (opt7->answer)
	Rast_close(mag_fd);

    D_save_command(G_recreate_command());
    D_close_driver();

    exit(EXIT_SUCCESS);
}
Exemple #26
0
int init_vars(int argc, char *argv[])
{
    int r, c;
    int ele_fd, wat_fd, fd = -1;
    int seg_rows, seg_cols, num_cseg_total, num_open_segs, num_open_array_segs;
    double memory_divisor, heap_mem, seg_factor, disk_space;

    /* int page_block, num_cseg; */
    int max_bytes;
    CELL *buf, alt_value, *alt_value_buf, block_value;
    char asp_value;
    DCELL wat_value;
    DCELL dvalue;
    WAT_ALT wa, *wabuf;
    ASP_FLAG af, af_nbr, *afbuf;
    char MASK_flag;
    void *elebuf, *ptr, *watbuf, *watptr;
    int ele_map_type, wat_map_type;
    size_t ele_size, wat_size;
    int ct_dir, r_nbr, c_nbr;

    G_gisinit(argv[0]);
    /* input */
    ele_flag = pit_flag = run_flag = ril_flag = 0;
    /* output */
    wat_flag = asp_flag = bas_flag = seg_flag = haf_flag = tci_flag = 0;
    bas_thres = 0;
    /* shed, unused */
    arm_flag = dis_flag = 0;
    /* RUSLE */
    ob_flag = st_flag = sl_flag = sg_flag = ls_flag = er_flag = 0;
    nxt_avail_pt = 0;
    /* dep_flag = 0; */
    max_length = d_zero = 0.0;
    d_one = 1.0;
    ril_value = -1.0;
    /* dep_slope = 0.0; */
    max_bytes = 0;
    sides = 8;
    mfd = 1;
    c_fac = 5;
    abs_acc = 0;
    ele_scale = 1;
    segs_mb = 300;
    /* scan options */
    for (r = 1; r < argc; r++) {
	if (sscanf(argv[r], "elevation=%s", ele_name) == 1)
	    ele_flag++;
	else if (sscanf(argv[r], "accumulation=%s", wat_name) == 1)
	    wat_flag++;
	else if (sscanf(argv[r], "tci=%s", tci_name) == 1)
	    tci_flag++;
	else if (sscanf(argv[r], "drainage=%s", asp_name) == 1)
	    asp_flag++;
	else if (sscanf(argv[r], "depression=%s", pit_name) == 1)
	    pit_flag++;
	else if (sscanf(argv[r], "threshold=%d", &bas_thres) == 1) ;
	else if (sscanf(argv[r], "max_slope_length=%lf", &max_length) == 1) ;
	else if (sscanf(argv[r], "basin=%s", bas_name) == 1)
	    bas_flag++;
	else if (sscanf(argv[r], "stream=%s", seg_name) == 1)
	    seg_flag++;
	else if (sscanf(argv[r], "half_basin=%s", haf_name) == 1)
	    haf_flag++;
	else if (sscanf(argv[r], "flow=%s", run_name) == 1)
	    run_flag++;
	else if (sscanf(argv[r], "ar=%s", arm_name) == 1)
	    arm_flag++;
	/* slope length
	else if (sscanf(argv[r], "slope_length=%s", sl_name) == 1)
	    sl_flag++; */
	else if (sscanf(argv[r], "slope_steepness=%s", sg_name) == 1)
	    sg_flag++;
	else if (sscanf(argv[r], "length_slope=%s", ls_name) == 1)
	    ls_flag++;
	else if (sscanf(argv[r], "blocking=%s", ob_name) == 1)
	    ob_flag++;
	else if (sscanf(argv[r], "memory=%lf", &segs_mb) == 1) ;
	else if (sscanf(argv[r], "disturbed_land=%s", ril_name) == 1) {
	    if (sscanf(ril_name, "%lf", &ril_value) == 0) {
		ril_value = -1.0;
		ril_flag++;
	    }
	}
	/* slope deposition
	else if (sscanf (argv[r], "sd=%[^\n]", dep_name) == 1) dep_flag++; */
	else if (sscanf(argv[r], "-%d", &sides) == 1) {
	    if (sides != 4)
		usage(argv[0]);
	}
	else if (sscanf(argv[r], "convergence=%d", &c_fac) == 1) ;
	else if (strcmp(argv[r], "-s") == 0)
	    mfd = 0;
	else if (strcmp(argv[r], "-a") == 0)
	    abs_acc = 1;
	else
	    usage(argv[0]);
    }
    /* check options */
    if (mfd == 1 && (c_fac < 1 || c_fac > 10)) {
	G_fatal_error("Convergence factor must be between 1 and 10.");
    }
    if ((ele_flag != 1)
	||
	((arm_flag == 1) &&
	 ((bas_thres <= 0) || ((haf_flag != 1) && (bas_flag != 1))))
	||
	((bas_thres <= 0) &&
	 ((bas_flag == 1) || (seg_flag == 1) || (haf_flag == 1) ||
	  (sl_flag == 1) || (sg_flag == 1) || (ls_flag == 1)))
	)
	usage(argv[0]);
    tot_parts = 4;
    if (sl_flag || sg_flag || ls_flag)
	er_flag = 1;
    /* do RUSLE */
    if (er_flag)
	tot_parts++;
    /* define basins */
    if (seg_flag || bas_flag || haf_flag)
	tot_parts++;

    G_message(_n("SECTION 1 beginning: Initiating Variables. %d section total.", 
        "SECTION 1 beginning: Initiating Variables. %d sections total.", 
        tot_parts),
	      tot_parts);

    this_mapset = G_mapset();
    /* for sd factor
       if (dep_flag)        {
       if (sscanf (dep_name, "%lf", &dep_slope) != 1)       {
       dep_flag = -1;
       }
       }
     */
    G_get_set_window(&window);
    nrows = Rast_window_rows();
    ncols = Rast_window_cols();
    if (max_length <= d_zero)
	max_length = 10 * nrows * window.ns_res + 10 * ncols * window.ew_res;
    if (window.ew_res < window.ns_res)
	half_res = .5 * window.ew_res;
    else
	half_res = .5 * window.ns_res;
    diag = sqrt(window.ew_res * window.ew_res +
		window.ns_res * window.ns_res);
    if (sides == 4)
	diag *= 0.5;

    /* Segment rows and cols: 64 */

    seg_rows = SROW;
    seg_cols = SCOL;
    /* seg_factor * <size in bytes> = segment size in KB */
    seg_factor = seg_rows * seg_rows / 1024.;

    if (segs_mb < 3.0) {
	segs_mb = 3;
	G_warning(_("Maximum memory to be used was smaller than 3 MB,"
	            " set to 3 MB."));
    }

    /* balance segment files */
    /* elevation + accumulation: * 2 */
    memory_divisor = sizeof(WAT_ALT) * 2;
    disk_space = sizeof(WAT_ALT);
    /* aspect and flags: * 4 */
    memory_divisor += sizeof(ASP_FLAG) * 4;
    disk_space += sizeof(ASP_FLAG);
    /* astar_points: / 16 */
    /* ideally only a few but large segments */
    memory_divisor += sizeof(POINT) / 16.;
    disk_space += sizeof(POINT);
    /* heap points: / 4 */
    memory_divisor += sizeof(HEAP_PNT) / 4.;
    disk_space += sizeof(HEAP_PNT);
    /* TCI: as is */
    if (tci_flag) {
	memory_divisor += sizeof(double);
	disk_space += sizeof(double);
    }
    /* RUSLE */
    if (er_flag) {
	/* r_h */
	memory_divisor += 4;
	disk_space += 4;
	/* s_l */
	memory_divisor += 8;
	disk_space += 8;
	/* s_g */
	if (sg_flag) {
	    memory_divisor += 8;
	    disk_space += 8;
	}
	/* l_s */
	if (ls_flag) {
	    memory_divisor += 8;
	    disk_space += 8;
	}
	/* ril */
	if (ril_flag) {
	    memory_divisor += 8;
	    disk_space += 8;
	}
    }
    
    /* KB -> MB */
    memory_divisor = memory_divisor * seg_factor / 1024.;
    disk_space = disk_space * seg_factor / 1024.;
    num_open_segs = segs_mb / memory_divisor;
    heap_mem = num_open_segs * seg_factor * sizeof(HEAP_PNT) / (4. * 1024.);

    G_debug(1, "segs MB: %.0f", segs_mb);
    G_debug(1, "region rows: %d", nrows);
    G_debug(1, "seg rows: %d", seg_rows);
    G_debug(1, "region cols: %d", ncols);
    G_debug(1, "seg cols: %d", seg_cols);

    num_cseg_total = nrows / SROW + 1;
    G_debug(1, "   row segments:\t%d", num_cseg_total);

    num_cseg_total = ncols / SCOL + 1;
    G_debug(1, "column segments:\t%d", num_cseg_total);

    num_cseg_total = (ncols / seg_cols + 1) * (nrows / seg_rows + 1);
    G_debug(1, " total segments:\t%d", num_cseg_total);
    G_debug(1, "  open segments:\t%d", num_open_segs);

    /* nonsense to have more segments open than exist */
    if (num_open_segs > num_cseg_total)
	num_open_segs = num_cseg_total;
    G_debug(1, "  open segments after adjusting:\t%d", num_open_segs);

    disk_space *= num_cseg_total;
    if (disk_space < 1024.0)
	G_verbose_message(_("Will need up to %.2f MB of disk space"), disk_space);
    else
	G_verbose_message(_("Will need up to %.2f GB (%.0f MB) of disk space"),
	           disk_space / 1024.0, disk_space);

    if (er_flag) {
	cseg_open(&r_h, seg_rows, seg_cols, num_open_segs);
	cseg_read_cell(&r_h, ele_name, "");
    }
    
    /* read elevation input and mark NULL/masked cells */

    /* scattered access: alt, watalt, bitflags, asp */
    seg_open(&watalt, nrows, ncols, seg_rows, seg_cols, num_open_segs * 2, sizeof(WAT_ALT));
    seg_open(&aspflag, nrows, ncols, seg_rows, seg_cols, num_open_segs * 4, sizeof(ASP_FLAG));

    if (tci_flag)
	dseg_open(&tci, seg_rows, seg_cols, num_open_segs);

    /* open elevation input */
    ele_fd = Rast_open_old(ele_name, "");

    ele_map_type = Rast_get_map_type(ele_fd);
    ele_size = Rast_cell_size(ele_map_type);
    elebuf = Rast_allocate_buf(ele_map_type);
    afbuf = G_malloc(ncols * sizeof(ASP_FLAG));

    if (ele_map_type == FCELL_TYPE || ele_map_type == DCELL_TYPE)
	ele_scale = 1000; 	/* should be enough to do the trick */

    /* initial flow accumulation */
    if (run_flag) {
	wat_fd = Rast_open_old(run_name, "");

	wat_map_type = Rast_get_map_type(ele_fd);
	wat_size = Rast_cell_size(ele_map_type);
	watbuf = Rast_allocate_buf(ele_map_type);
    }
    else {
	watbuf = watptr = NULL;
	wat_fd = wat_size = wat_map_type = -1;
    }
    wabuf = G_malloc(ncols * sizeof(WAT_ALT));
    alt_value_buf = Rast_allocate_buf(CELL_TYPE);

    /* read elevation input and mark NULL/masked cells */
    G_message("SECTION 1a: Mark masked and NULL cells");
    MASK_flag = 0;
    do_points = (GW_LARGE_INT) nrows * ncols;
    for (r = 0; r < nrows; r++) {
	G_percent(r, nrows, 1);
	Rast_get_row(ele_fd, elebuf, r, ele_map_type);
	ptr = elebuf;

	if (run_flag) {
	    Rast_get_row(wat_fd, watbuf, r, wat_map_type);
	    watptr = watbuf;
	}
	
	for (c = 0; c < ncols; c++) {

	    afbuf[c].flag = 0;
	    afbuf[c].asp = 0;

	    /* check for masked and NULL cells */
	    if (Rast_is_null_value(ptr, ele_map_type)) {
		FLAG_SET(afbuf[c].flag, NULLFLAG);
		FLAG_SET(afbuf[c].flag, INLISTFLAG);
		FLAG_SET(afbuf[c].flag, WORKEDFLAG);
		Rast_set_c_null_value(&alt_value, 1);
		/* flow accumulation */
		Rast_set_d_null_value(&wat_value, 1);
		do_points--;
	    }
	    else {
		if (ele_map_type == CELL_TYPE) {
		    alt_value = *((CELL *)ptr);
		}
		else if (ele_map_type == FCELL_TYPE) {
		    dvalue = *((FCELL *)ptr);
		    dvalue *= ele_scale;
		    alt_value = ele_round(dvalue);
		}
		else if (ele_map_type == DCELL_TYPE) {
		    dvalue = *((DCELL *)ptr);
		    dvalue *= ele_scale;
		    alt_value = ele_round(dvalue);
		}

		/* flow accumulation */
		if (run_flag) {
		    if (Rast_is_null_value(watptr, wat_map_type)) {
			wat_value = 0;    /* ok ? */
		    }
		    else {
			if (wat_map_type == CELL_TYPE) {
			    wat_value = *((CELL *)watptr);
			}
			else if (wat_map_type == FCELL_TYPE) {
			    wat_value = *((FCELL *)watptr);
			}
			else if (wat_map_type == DCELL_TYPE) {
			    wat_value = *((DCELL *)watptr);
			}
		    }
		}
		else {
		    wat_value = 1;
		}
	    }
	    wabuf[c].wat = wat_value;
	    wabuf[c].ele = alt_value;
	    alt_value_buf[c] = alt_value;
	    ptr = G_incr_void_ptr(ptr, ele_size);
	    if (run_flag) {
		watptr = G_incr_void_ptr(watptr, wat_size);
	    }
	}
	seg_put_row(&watalt, (char *) wabuf, r);
	seg_put_row(&aspflag, (char *)afbuf, r);
	
	if (er_flag) {
	    cseg_put_row(&r_h, alt_value_buf, r);
	}
    }
    G_percent(nrows, nrows, 1);    /* finish it */
    Rast_close(ele_fd);
    G_free(wabuf);
    G_free(afbuf);
    
    if (run_flag) {
	Rast_close(wat_fd);
	G_free(watbuf);
    }

    MASK_flag = (do_points < nrows * ncols);
    
    /* do RUSLE */
    if (er_flag) {
	if (ob_flag) {
	    fd = Rast_open_old(ob_name, "");
	    buf = Rast_allocate_c_buf();
	    for (r = 0; r < nrows; r++) {
		G_percent(r, nrows, 1);
		Rast_get_c_row(fd, buf, r);
		for (c = 0; c < ncols; c++) {
		    block_value = buf[c];
		    if (!Rast_is_c_null_value(&block_value) && block_value) {
			seg_get(&aspflag, (char *)&af, r, c);
			FLAG_SET(af.flag, RUSLEBLOCKFLAG);
			seg_put(&aspflag, (char *)&af, r, c);
		    }
		}
	    }
	    G_percent(nrows, nrows, 1);    /* finish it */
	    Rast_close(fd);
	    G_free(buf);
	}

	if (ril_flag) {
	    dseg_open(&ril, seg_rows, seg_cols, num_open_segs);
	    dseg_read_cell(&ril, ril_name, "");
	}
	
	/* dseg_open(&slp, SROW, SCOL, num_open_segs); */

	dseg_open(&s_l, seg_rows, seg_cols, num_open_segs);
	if (sg_flag)
	    dseg_open(&s_g, seg_rows, seg_cols, num_open_segs);
	if (ls_flag)
	    dseg_open(&l_s, seg_rows, seg_cols, num_open_segs);
    }

    G_debug(1, "open segments for A* points");
    /* columns per segment */
    seg_cols = seg_rows * seg_rows;
    num_cseg_total = do_points / seg_cols;
    if (do_points % seg_cols > 0)
	num_cseg_total++;
    /* no need to have more segments open than exist */
    num_open_array_segs = num_open_segs / 16.;
    if (num_open_array_segs > num_cseg_total)
	num_open_array_segs = num_cseg_total;
    if (num_open_array_segs < 1)
	num_open_array_segs = 1;
    
    seg_open(&astar_pts, 1, do_points, 1, seg_cols, num_open_array_segs,
	     sizeof(POINT));

    /* one-based d-ary search_heap with astar_pts */
    G_debug(1, "open segments for A* search heap");
    G_debug(1, "heap memory %.2f MB", heap_mem);
    /* columns per segment */
    /* larger is faster */
    seg_cols = seg_rows * seg_rows;
    num_cseg_total = do_points / seg_cols;
    if (do_points % seg_cols > 0)
	num_cseg_total++;
    /* no need to have more segments open than exist */
    num_open_array_segs = (1 << 20) * heap_mem / (seg_cols * sizeof(HEAP_PNT));
    if (num_open_array_segs > num_cseg_total)
	num_open_array_segs = num_cseg_total;
    if (num_open_array_segs < 2)
	num_open_array_segs = 2;

    G_debug(1, "A* search heap open segments %d, total %d",
            num_open_array_segs, num_cseg_total);
    /* the search heap will not hold more than 5% of all points at any given time ? */
    /* chances are good that the heap will fit into one large segment */
    seg_open(&search_heap, 1, do_points + 1, 1, seg_cols,
	     num_open_array_segs, sizeof(HEAP_PNT));

    G_message(_("SECTION 1b: Determining Offmap Flow."));

    /* heap is empty */
    heap_size = 0;

    if (pit_flag) {
	buf = Rast_allocate_c_buf();
	fd = Rast_open_old(pit_name, "");
    }
    else
	buf = NULL;
    first_astar = first_cum = -1;

    for (r = 0; r < nrows; r++) {
	G_percent(r, nrows, 1);
	if (pit_flag)
	    Rast_get_c_row(fd, buf, r);
	for (c = 0; c < ncols; c++) {
	    seg_get(&aspflag, (char *)&af, r, c);
	    if (!FLAG_GET(af.flag, NULLFLAG)) {
		if (er_flag)
		    dseg_put(&s_l, &half_res, r, c);
		asp_value = af.asp;
		if (r == 0 || c == 0 || r == nrows - 1 ||
		    c == ncols - 1) {
		    /* dseg_get(&wat, &wat_value, r, c); */
		    seg_get(&watalt, (char *)&wa, r, c);
		    wat_value = wa.wat;
		    if (wat_value > 0) {
			wat_value = -wat_value;
			/* dseg_put(&wat, &wat_value, r, c); */
			wa.wat = wat_value;
			seg_put(&watalt, (char *)&wa, r, c);
		    }
		    if (r == 0)
			asp_value = -2;
		    else if (c == 0)
			asp_value = -4;
		    else if (r == nrows - 1)
			asp_value = -6;
		    else if (c == ncols - 1)
			asp_value = -8;
		    /* cseg_get(&alt, &alt_value, r, c); */
		    alt_value = wa.ele;
		    add_pt(r, c, alt_value);
		    FLAG_SET(af.flag, INLISTFLAG);
		    FLAG_SET(af.flag, EDGEFLAG);
		    af.asp = asp_value;
		    seg_put(&aspflag, (char *)&af, r, c);
		}
		else {
		    seg_get(&watalt, (char *)&wa, r, c);
		    for (ct_dir = 0; ct_dir < sides; ct_dir++) {
			/* get r, c (r_nbr, c_nbr) for neighbours */
			r_nbr = r + nextdr[ct_dir];
			c_nbr = c + nextdc[ct_dir];

			seg_get(&aspflag, (char *)&af_nbr, r_nbr, c_nbr);
			if (FLAG_GET(af_nbr.flag, NULLFLAG)) {
			    af.asp = -1 * drain[r - r_nbr + 1][c - c_nbr + 1];
			    add_pt(r, c, wa.ele);
			    FLAG_SET(af.flag, INLISTFLAG);
			    FLAG_SET(af.flag, EDGEFLAG);
			    seg_put(&aspflag, (char *)&af, r, c);
			    wat_value = wa.wat;
			    if (wat_value > 0) {
				wa.wat = -wat_value;
				seg_put(&watalt, (char *)&wa, r, c);
			    }
			    break;
			}
		    }
		}
		/* real depression ? */
		if (pit_flag && asp_value == 0) {
		    if (!Rast_is_c_null_value(&buf[c]) && buf[c] != 0) {

			seg_get(&watalt, (char *)&wa, r, c);
			add_pt(r, c, wa.ele);

			FLAG_SET(af.flag, INLISTFLAG);
			FLAG_SET(af.flag, EDGEFLAG);
			seg_put(&aspflag, (char *)&af, r, c);
			wat_value = wa.wat;
			if (wat_value > 0) {
			    wa.wat = -wat_value;
			    seg_put(&watalt, (char *)&wa, r, c);
			}
		    }
		}

	    }  /* end non-NULL cell */
	}  /* end column */
    }
    G_percent(r, nrows, 1);	/* finish it */

    return 0;
}
Exemple #27
0
/* actual raster band export
 * returns 0 on success
 * -1 on raster data read/write error
 * */
int export_band(GDALDatasetH hMEMDS, int band,
		const char *name, const char *mapset,
		struct Cell_head *cellhead, RASTER_MAP_TYPE maptype,
		double nodataval, int suppress_main_colortable)
{
    struct Colors sGrassColors;
    GDALColorTableH hCT;
    int iColor;
    int bHaveMinMax;
    double dfCellMin;
    double dfCellMax;
    struct FPRange sRange;
    int fd;
    int cols = cellhead->cols;
    int rows = cellhead->rows;
    int ret = 0;
    char value[200];

    /* Open GRASS raster */
    fd = Rast_open_old(name, mapset);

    /* Get raster band  */
    GDALRasterBandH hBand = GDALGetRasterBand(hMEMDS, band);

    if (hBand == NULL) {
	G_warning(_("Unable to get raster band"));
	return -1;
    }

    /* Get min/max values. */
    if (Rast_read_fp_range(name, mapset, &sRange) == -1) {
	bHaveMinMax = FALSE;
    }
    else {
	bHaveMinMax = TRUE;
	Rast_get_fp_range_min_max(&sRange, &dfCellMin, &dfCellMax);
    }

    sprintf(value, "GRASS GIS %s", GRASS_VERSION_NUMBER);
    GDALSetMetadataItem(hBand, "Generated_with", value, NULL);

    /* use default color rules if no color rules are given */
    if (Rast_read_colors(name, mapset, &sGrassColors) >= 0) {
	int maxcolor, i;
	CELL min, max;
	char key[200];
	int rcount;

	Rast_get_c_color_range(&min, &max, &sGrassColors);
	if (bHaveMinMax) {
	    if (max < dfCellMax) {
		maxcolor = max;
	    }
	    else {
		maxcolor = (int)ceil(dfCellMax);
	    }
	    if (maxcolor > GRASS_MAX_COLORS) {
		maxcolor = GRASS_MAX_COLORS;
		G_warning("Too many values, color table cut to %d entries",
			  maxcolor);
	    }
	}
	else {
	    if (max < GRASS_MAX_COLORS) {
		maxcolor = max;
	    }
	    else {
		maxcolor = GRASS_MAX_COLORS;
		G_warning("Too many values, color table set to %d entries",
			  maxcolor);
	    }
	}

	rcount = Rast_colors_count(&sGrassColors);

	G_debug(3, "dfCellMin: %f, dfCellMax: %f, maxcolor: %d", dfCellMin,
		dfCellMax, maxcolor);

	if (!suppress_main_colortable) {
	    hCT = GDALCreateColorTable(GPI_RGB);

	    for (iColor = 0; iColor <= maxcolor; iColor++) {
		int nRed, nGreen, nBlue;
		GDALColorEntry sColor;

		if (Rast_get_c_color(&iColor, &nRed, &nGreen, &nBlue,
				     &sGrassColors)) {
		    sColor.c1 = nRed;
		    sColor.c2 = nGreen;
		    sColor.c3 = nBlue;
		    sColor.c4 = 255;

		    G_debug(3,
			    "Rast_get_c_color: Y, rcount %d, nRed %d, nGreen %d, nBlue %d",
			    rcount, nRed, nGreen, nBlue);
		    GDALSetColorEntry(hCT, iColor, &sColor);
		}
		else {
		    sColor.c1 = 0;
		    sColor.c2 = 0;
		    sColor.c3 = 0;
		    sColor.c4 = 0;

		    G_debug(3,
			    "Rast_get_c_color: N, rcount %d, nRed %d, nGreen %d, nBlue %d",
			    rcount, nRed, nGreen, nBlue);
		    GDALSetColorEntry(hCT, iColor, &sColor);
		}
	    }

	    GDALSetRasterColorTable(hBand, hCT);
	}

	if (rcount > 0) {
	    /* Create metadata entries for color table rules */
	    sprintf(value, "%d", rcount);
	    GDALSetMetadataItem(hBand, "COLOR_TABLE_RULES_COUNT", value,
				NULL);
	}

	/* Add the rules in reverse order */
	/* This can cause a GDAL warning with many rules, something like
	 * Warning 1: Lost metadata writing to GeoTIFF ... too large to fit in tag. */
	for (i = rcount - 1; i >= 0; i--) {
	    DCELL val1, val2;
	    unsigned char r1, g1, b1, r2, g2, b2;

	    Rast_get_fp_color_rule(&val1, &r1, &g1, &b1, &val2, &r2, &g2, &b2,
			       &sGrassColors, i);


	    sprintf(key, "COLOR_TABLE_RULE_RGB_%d", rcount - i - 1);
	    sprintf(value, "%e %e %d %d %d %d %d %d", val1, val2, r1, g1, b1,
		    r2, g2, b2);
	    GDALSetMetadataItem(hBand, key, value, NULL);
	}
    }

    /* Create GRASS raster buffer */
    void *bufer = Rast_allocate_buf(maptype);

    if (bufer == NULL) {
	G_warning(_("Unable to allocate buffer for reading raster map"));
	return -1;
    }

    /* the following routine must be kept identical to exact_checks */

    /* Copy data form GRASS raster to GDAL raster */
    int row, col;
    int n_nulls = 0;

    /* Better use selected GDAL datatype instead of 
     * the best match with GRASS raster map types ? */

    if (maptype == FCELL_TYPE) {

	/* Source datatype understandable by GDAL */
	GDALDataType datatype = GDT_Float32;
	FCELL fnullval = (FCELL) nodataval;

	G_debug(1, "FCELL nodata val: %f", fnullval);

	for (row = 0; row < rows; row++) {

	    Rast_get_row(fd, bufer, row, maptype);
	    for (col = 0; col < cols; col++) {
		if (Rast_is_f_null_value(&((FCELL *) bufer)[col])) {
		    ((FCELL *) bufer)[col] = fnullval;
		    if (n_nulls == 0) {
			GDALSetRasterNoDataValue(hBand, nodataval);
		    }
		    n_nulls++;
		}
	    }

	    if (GDALRasterIO
		(hBand, GF_Write, 0, row, cols, 1, bufer, cols, 1, datatype,
		 0, 0) >= CE_Failure) {
		G_warning(_("Unable to write GDAL raster file"));
		return -1;
	    }
	    G_percent(row + 1, rows, 2);
	}
    }
    else if (maptype == DCELL_TYPE) {

	GDALDataType datatype = GDT_Float64;
	DCELL dnullval = (DCELL) nodataval;

	G_debug(1, "DCELL nodata val: %f", dnullval);

	for (row = 0; row < rows; row++) {

	    Rast_get_row(fd, bufer, row, maptype);
	    for (col = 0; col < cols; col++) {
		if (Rast_is_d_null_value(&((DCELL *) bufer)[col])) {
		    ((DCELL *) bufer)[col] = dnullval;
		    if (n_nulls == 0) {
			GDALSetRasterNoDataValue(hBand, nodataval);
		    }
		    n_nulls++;
		}
	    }

	    if (GDALRasterIO
		(hBand, GF_Write, 0, row, cols, 1, bufer, cols, 1, datatype,
		 0, 0) >= CE_Failure) {
		G_warning(_("Unable to write GDAL raster file"));
		return -1;
	    }
	    G_percent(row + 1, rows, 2);
	}
    }
    else {

	GDALDataType datatype = GDT_Int32;
	CELL inullval = (CELL) nodataval;

	G_debug(1, "CELL nodata val: %d", inullval);

	for (row = 0; row < rows; row++) {

	    Rast_get_row(fd, bufer, row, maptype);
	    for (col = 0; col < cols; col++) {
		if (Rast_is_c_null_value(&((CELL *) bufer)[col])) {
		    ((CELL *) bufer)[col] = inullval;
		    if (n_nulls == 0) {
			GDALSetRasterNoDataValue(hBand, nodataval);
		    }
		    n_nulls++;
		}
	    }

	    if (GDALRasterIO
		(hBand, GF_Write, 0, row, cols, 1, bufer, cols, 1, datatype,
		 0, 0) >= CE_Failure) {
		G_warning(_("Unable to write GDAL raster file"));
		return -1;
	    }
	    G_percent(row + 1, rows, 2);
	}
    }

    Rast_close(fd);

    G_free(bufer);

    return ret;
}
Exemple #28
0
int main(int argc, char *argv[])
{
    int nrows, ncols;
    int row, col;
    char *viflag;		/*Switch for particular index */
    char *desc;
    struct GModule *module;
    struct {
        struct Option *viname, *red, *nir, *green, *blue, *chan5,
            *chan7, *sl_slope, *sl_int, *sl_red, *bits, *output;
    } opt;
    struct History history;	/*metadata */
    struct Colors colors;	/*Color rules */

    char *result;		/*output raster name */
    int infd_redchan, infd_nirchan, infd_greenchan;
    int infd_bluechan, infd_chan5chan, infd_chan7chan;
    int outfd;
    char *bluechan, *greenchan, *redchan, *nirchan, *chan5chan, *chan7chan;
    DCELL *inrast_redchan, *inrast_nirchan, *inrast_greenchan;
    DCELL *inrast_bluechan, *inrast_chan5chan, *inrast_chan7chan;
    DCELL *outrast;
    RASTER_MAP_TYPE data_type_redchan;
    RASTER_MAP_TYPE data_type_nirchan, data_type_greenchan;
    RASTER_MAP_TYPE data_type_bluechan;
    RASTER_MAP_TYPE data_type_chan5chan, data_type_chan7chan;
    DCELL msavip1, msavip2, msavip3, dnbits;
    CELL val1, val2;

    G_gisinit(argv[0]);

    module = G_define_module();
    G_add_keyword(_("imagery"));
    G_add_keyword(_("vegetation index"));
    G_add_keyword(_("biophysical parameters"));
    module->label =
	_("Calculates different types of vegetation indices.");
    module->description = _("Uses red and nir bands mostly, "
			    "and some indices require additional bands.");

    /* Define the different options */
    opt.red = G_define_standard_option(G_OPT_R_INPUT);
    opt.red->key = "red";
    opt.red->label =
	_("Name of input red channel surface reflectance map");
    opt.red->description = _("Range: [0.0;1.0]");

    opt.output = G_define_standard_option(G_OPT_R_OUTPUT);

    opt.viname = G_define_option();
    opt.viname->key = "viname";
    opt.viname->type = TYPE_STRING;
    opt.viname->required = YES;
    opt.viname->description = _("Type of vegetation index");
    desc = NULL;
    G_asprintf(&desc,
	       "arvi;%s;dvi;%s;evi;%s;evi2;%s;gvi;%s;gari;%s;gemi;%s;ipvi;%s;msavi;%s;"
	       "msavi2;%s;ndvi;%s;pvi;%s;savi;%s;sr;%s;vari;%s;wdvi;%s",
	       _("Atmospherically Resistant Vegetation Index"),
	       _("Difference Vegetation Index"),
	       _("Enhanced Vegetation Index"),
	       _("Enhanced Vegetation Index 2"),
	       _("Green Vegetation Index"),
	       _("Green Atmospherically Resistant Vegetation Index"),
	       _("Global Environmental Monitoring Index"),
	       _("Infrared Percentage Vegetation Index"),
	       _("Modified Soil Adjusted Vegetation Index"),
	       _("second Modified Soil Adjusted Vegetation Index"),
	       _("Normalized Difference Vegetation Index"),
	       _("Perpendicular Vegetation Index"),
	       _("Soil Adjusted Vegetation Index"),
	       _("Simple Ratio"),
	       _("Visible Atmospherically Resistant Index"),
	       _("Weighted Difference Vegetation Index"));
    opt.viname->descriptions = desc;
    opt.viname->options = "arvi,dvi,evi,evi2,gvi,gari,gemi,ipvi,msavi,msavi2,ndvi,pvi,savi,sr,vari,wdvi";
    opt.viname->answer = "ndvi";
    opt.viname->key_desc = _("type");

    opt.nir = G_define_standard_option(G_OPT_R_INPUT);
    opt.nir->key = "nir";
    opt.nir->required = NO;
    opt.nir->label =
	_("Name of input nir channel surface reflectance map");
    opt.nir->description = _("Range: [0.0;1.0]");
    opt.nir->guisection = _("Optional inputs");

    opt.green = G_define_standard_option(G_OPT_R_INPUT);
    opt.green->key = "green";
    opt.green->required = NO;
    opt.green->label =
	_("Name of input green channel surface reflectance map");
    opt.green->description = _("Range: [0.0;1.0]");
    opt.green->guisection = _("Optional inputs");

    opt.blue = G_define_standard_option(G_OPT_R_INPUT);
    opt.blue->key = "blue";
    opt.blue->required = NO;
    opt.blue->label =
	_("Name of input blue channel surface reflectance map");
    opt.blue->description = _("Range: [0.0;1.0]");
    opt.blue->guisection = _("Optional inputs");

    opt.chan5 = G_define_standard_option(G_OPT_R_INPUT);
    opt.chan5->key = "band5";
    opt.chan5->required = NO;
    opt.chan5->label =
	_("Name of input 5th channel surface reflectance map");
    opt.chan5->description = _("Range: [0.0;1.0]");
    opt.chan5->guisection = _("Optional inputs");

    opt.chan7 = G_define_standard_option(G_OPT_R_INPUT);
    opt.chan7->key = "band7";
    opt.chan7->required = NO;
    opt.chan7->label =
	_("Name of input 7th channel surface reflectance map");
    opt.chan7->description = _("Range: [0.0;1.0]");
    opt.chan7->guisection = _("Optional inputs");

    opt.sl_slope = G_define_option();
    opt.sl_slope->key = "soil_line_slope";
    opt.sl_slope->type = TYPE_DOUBLE;
    opt.sl_slope->required = NO;
    opt.sl_slope->description = _("Value of the slope of the soil line (MSAVI only)");
    opt.sl_slope->guisection = _("MSAVI settings");

    opt.sl_int = G_define_option();
    opt.sl_int->key = "soil_line_intercept";
    opt.sl_int->type = TYPE_DOUBLE;
    opt.sl_int->required = NO;
    opt.sl_int->description = _("Value of the intercept of the soil line (MSAVI only)");
    opt.sl_int->guisection = _("MSAVI settings");

    opt.sl_red = G_define_option();
    opt.sl_red->key = "soil_noise_reduction";
    opt.sl_red->type = TYPE_DOUBLE;
    opt.sl_red->required = NO;
    opt.sl_red->description = _("Value of the factor of reduction of soil noise (MSAVI only)");
    opt.sl_red->guisection = _("MSAVI settings");

    opt.bits = G_define_option();
    opt.bits->key = "storage_bit";
    opt.bits->type = TYPE_INTEGER;
    opt.bits->required = NO;
    opt.bits->label = _("Maximum bits for digital numbers");
    opt.bits->description = _("If data is in Digital Numbers (i.e. integer type), give the max bits (i.e. 8 for Landsat -> [0-255])");
    opt.bits->options = "7,8,10,16";
    opt.bits->answer = "8";

    if (G_parser(argc, argv))
	exit(EXIT_FAILURE);

    viflag = opt.viname->answer;
    redchan = opt.red->answer;
    nirchan = opt.nir->answer;
    greenchan = opt.green->answer;
    bluechan = opt.blue->answer;
    chan5chan = opt.chan5->answer;
    chan7chan = opt.chan7->answer;
    if(opt.sl_slope->answer)
        msavip1 = atof(opt.sl_slope->answer);
    if(opt.sl_int->answer)
        msavip2 = atof(opt.sl_int->answer);
    if(opt.sl_red->answer)
        msavip3 = atof(opt.sl_red->answer);
    if(opt.bits->answer)
        dnbits = atof(opt.bits->answer);
    result = opt.output->answer;
    G_verbose_message(_("Calculating %s..."), viflag);

    if (!strcasecmp(viflag, "sr") && (!(opt.red->answer) || !(opt.nir->answer)) )
	G_fatal_error(_("sr index requires red and nir maps"));

    if (!strcasecmp(viflag, "ndvi") && (!(opt.red->answer) || !(opt.nir->answer)) )
	G_fatal_error(_("ndvi index requires red and nir maps"));

    if (!strcasecmp(viflag, "ipvi") && (!(opt.red->answer) || !(opt.nir->answer)) )
	G_fatal_error(_("ipvi index requires red and nir maps"));

    if (!strcasecmp(viflag, "dvi") && (!(opt.red->answer) || !(opt.nir->answer)) )
	G_fatal_error(_("dvi index requires red and nir maps"));

    if (!strcasecmp(viflag, "pvi") && (!(opt.red->answer) || !(opt.nir->answer)) )
	G_fatal_error(_("pvi index requires red and nir maps"));

    if (!strcasecmp(viflag, "wdvi") && (!(opt.red->answer) || !(opt.nir->answer)) )
	G_fatal_error(_("wdvi index requires red and nir maps"));

    if (!strcasecmp(viflag, "savi") && (!(opt.red->answer) || !(opt.nir->answer)) )
	G_fatal_error(_("savi index requires red and nir maps"));

    if (!strcasecmp(viflag, "msavi") && (!(opt.red->answer) || !(opt.nir->answer) || 
                                          !(opt.sl_slope->answer) || !(opt.sl_int->answer) || 
                                          !(opt.sl_red->answer)) )
	G_fatal_error(_("msavi index requires red and nir maps, and 3 parameters related to soil line"));

    if (!strcasecmp(viflag, "msavi2") && (!(opt.red->answer) || !(opt.nir->answer)) )
	G_fatal_error(_("msavi2 index requires red and nir maps"));

    if (!strcasecmp(viflag, "gemi") && (!(opt.red->answer) || !(opt.nir->answer)) )
	G_fatal_error(_("gemi index requires red and nir maps"));

    if (!strcasecmp(viflag, "arvi") && (!(opt.red->answer) || !(opt.nir->answer)
                || !(opt.blue->answer)) )
	G_fatal_error(_("arvi index requires blue, red and nir maps"));

    if (!strcasecmp(viflag, "evi") && (!(opt.red->answer) || !(opt.nir->answer)
                || !(opt.blue->answer)) )
	G_fatal_error(_("evi index requires blue, red and nir maps"));

	if (!strcasecmp(viflag, "evi2") && (!(opt.red->answer) || !(opt.nir->answer) ) )
	G_fatal_error(_("evi2 index requires red and nir maps"));
	
    if (!strcasecmp(viflag, "vari") && (!(opt.red->answer) || !(opt.green->answer)
                || !(opt.blue->answer)) )
	G_fatal_error(_("vari index requires blue, green and red maps"));

    if (!strcasecmp(viflag, "gari") && (!(opt.red->answer) || !(opt.nir->answer)
                || !(opt.green->answer) || !(opt.blue->answer)) )
	G_fatal_error(_("gari index requires blue, green, red and nir maps"));

    if (!strcasecmp(viflag, "gvi") && (!(opt.red->answer) || !(opt.nir->answer)
                || !(opt.green->answer) || !(opt.blue->answer)
                || !(opt.chan5->answer) || !(opt.chan7->answer)) )
	G_fatal_error(_("gvi index requires blue, green, red, nir, chan5 and chan7 maps"));

    infd_redchan = Rast_open_old(redchan, "");
    data_type_redchan = Rast_map_type(redchan, "");
    inrast_redchan = Rast_allocate_buf(data_type_redchan);

    if (nirchan) {
        infd_nirchan = Rast_open_old(nirchan, "");
        data_type_nirchan = Rast_map_type(nirchan, "");
        inrast_nirchan = Rast_allocate_buf(data_type_nirchan);
    }

    if (greenchan) {
        infd_greenchan = Rast_open_old(greenchan, "");
        data_type_greenchan = Rast_map_type(greenchan, "");
        inrast_greenchan = Rast_allocate_buf(data_type_greenchan);
    }

    if (bluechan) {
        infd_bluechan = Rast_open_old(bluechan, "");
        data_type_bluechan = Rast_map_type(bluechan, "");
        inrast_bluechan = Rast_allocate_buf(data_type_bluechan);
    }

    if (chan5chan) {
        infd_chan5chan = Rast_open_old(chan5chan, "");
        data_type_chan5chan = Rast_map_type(chan5chan, "");
        inrast_chan5chan = Rast_allocate_buf(data_type_chan5chan);
    }

    if (chan7chan) {
        infd_chan7chan = Rast_open_old(chan7chan, "");
        data_type_chan7chan = Rast_map_type(chan7chan, "");
        inrast_chan7chan = Rast_allocate_buf(data_type_chan7chan);
    }

    nrows = Rast_window_rows();
    ncols = Rast_window_cols();

    /* Create New raster files */
    outfd = Rast_open_new(result, DCELL_TYPE);
    outrast = Rast_allocate_d_buf();

    /* Process pixels */
    for (row = 0; row < nrows; row++)
    {
	DCELL d_bluechan;
	DCELL d_greenchan;
	DCELL d_redchan;
	DCELL d_nirchan;
	DCELL d_chan5chan;
	DCELL d_chan7chan;

	G_percent(row, nrows, 2);

	/* read input maps */
	Rast_get_row(infd_redchan,inrast_redchan,row,data_type_redchan);
	if (nirchan) {
	    Rast_get_row(infd_nirchan,inrast_nirchan,row,data_type_nirchan);
	}
	if (bluechan) {
	    Rast_get_row(infd_bluechan,inrast_bluechan,row,data_type_bluechan);
	}
	if (greenchan) {
	    Rast_get_row(infd_greenchan,inrast_greenchan,row,data_type_greenchan);
	}
	if (chan5chan) {
	    Rast_get_row(infd_chan5chan,inrast_chan5chan,row,data_type_chan5chan);
	}
	if (chan7chan) {
	    Rast_get_row(infd_chan7chan,inrast_chan7chan,row,data_type_chan7chan);
	}
	/* process the data */
	for (col = 0; col < ncols; col++)
	{
	    switch(data_type_redchan){
		    case CELL_TYPE:
			d_redchan   = (double) ((CELL *) inrast_redchan)[col];
			if(opt.bits->answer)
				d_redchan *= 1.0/(pow(2,dnbits)-1);	
			break;
		    case FCELL_TYPE:
			d_redchan   = (double) ((FCELL *) inrast_redchan)[col];
			break;
		    case DCELL_TYPE:
			d_redchan   = ((DCELL *) inrast_redchan)[col];
			break;
	    }
	    if (nirchan) {
		switch(data_type_nirchan){
		    case CELL_TYPE:
			d_nirchan   = (double) ((CELL *) inrast_nirchan)[col];
			if(opt.bits->answer)
				d_nirchan *= 1.0/(pow(2,dnbits)-1);	
			break;
		    case FCELL_TYPE:
			d_nirchan   = (double) ((FCELL *) inrast_nirchan)[col];
			break;
		    case DCELL_TYPE:
			d_nirchan   = ((DCELL *) inrast_nirchan)[col];
			break;
		}
	    }
	    if (greenchan) {
		switch(data_type_greenchan){
		    case CELL_TYPE:
			d_greenchan   = (double) ((CELL *) inrast_greenchan)[col];
			if(opt.bits->answer)
				d_greenchan *= 1.0/(pow(2,dnbits)-1);	
			break;
		    case FCELL_TYPE:
			d_greenchan   = (double) ((FCELL *) inrast_greenchan)[col];
			break;
		    case DCELL_TYPE:
			d_greenchan   = ((DCELL *) inrast_greenchan)[col];
			break;
		}
	    }
	    if (bluechan) {
		switch(data_type_bluechan){
		    case CELL_TYPE:
			d_bluechan   = (double) ((CELL *) inrast_bluechan)[col];
			if(opt.bits->answer)
				d_bluechan *= 1.0/(pow(2,dnbits)-1);	
			break;
		    case FCELL_TYPE:
			d_bluechan   = (double) ((FCELL *) inrast_bluechan)[col];
			break;
		    case DCELL_TYPE:
			d_bluechan   = ((DCELL *) inrast_bluechan)[col];
			break;
		}
	    }
	    if (chan5chan) {
		switch(data_type_chan5chan){
		    case CELL_TYPE:
			d_chan5chan   = (double) ((CELL *) inrast_chan5chan)[col];
			if(opt.bits->answer)
				d_chan5chan *= 1.0/(pow(2,dnbits)-1);	
			break;
		    case FCELL_TYPE:
			d_chan5chan   = (double) ((FCELL *) inrast_chan5chan)[col];
			break;
		    case DCELL_TYPE:
			d_chan5chan   = ((DCELL *) inrast_chan5chan)[col];
			break;
		}
	    }
	    if (chan7chan) {
		switch(data_type_chan7chan){
		    case CELL_TYPE:
			d_chan7chan   = (double) ((CELL *) inrast_chan7chan)[col];
			if(opt.bits->answer)
				d_chan7chan *= 1.0/(pow(2,dnbits)-1);	
			break;
		    case FCELL_TYPE:
			d_chan7chan   = (double) ((FCELL *) inrast_chan7chan)[col];
			break;
		    case DCELL_TYPE:
			d_chan7chan   = ((DCELL *) inrast_chan7chan)[col];
			break;
		}
	    }

	    if (Rast_is_d_null_value(&d_redchan) ||
		((nirchan) && Rast_is_d_null_value(&d_nirchan)) ||
		((greenchan) && Rast_is_d_null_value(&d_greenchan)) ||
		((bluechan) && Rast_is_d_null_value(&d_bluechan)) ||
		((chan5chan) && Rast_is_d_null_value(&d_chan5chan)) ||
		((chan7chan) && Rast_is_d_null_value(&d_chan7chan))) {
		Rast_set_d_null_value(&outrast[col], 1);
	    }
	    else {
		/* calculate simple_ratio        */
		if (!strcasecmp(viflag, "sr"))
		    outrast[col] = s_r(d_redchan, d_nirchan);

		/* calculate ndvi                    */
		if (!strcasecmp(viflag, "ndvi")) {
		    if (d_redchan + d_nirchan < 0.001)
			Rast_set_d_null_value(&outrast[col], 1);
		    else
			outrast[col] = nd_vi(d_redchan, d_nirchan);
		}

		if (!strcasecmp(viflag, "ipvi"))
		    outrast[col] = ip_vi(d_redchan, d_nirchan);

		if (!strcasecmp(viflag, "dvi"))
		    outrast[col] = d_vi(d_redchan, d_nirchan);

		if (!strcasecmp(viflag, "evi"))
		    outrast[col] = e_vi(d_bluechan, d_redchan, d_nirchan);

		if (!strcasecmp(viflag, "evi2"))
		    outrast[col] = e_vi2(d_redchan, d_nirchan);

		if (!strcasecmp(viflag, "pvi"))
		    outrast[col] = p_vi(d_redchan, d_nirchan);

		if (!strcasecmp(viflag, "wdvi"))
		    outrast[col] = wd_vi(d_redchan, d_nirchan);

		if (!strcasecmp(viflag, "savi"))
		    outrast[col] = sa_vi(d_redchan, d_nirchan);

		if (!strcasecmp(viflag, "msavi"))
		    outrast[col] = msa_vi(d_redchan, d_nirchan, msavip1, msavip2, msavip3);

		if (!strcasecmp(viflag, "msavi2"))
		    outrast[col] = msa_vi2(d_redchan, d_nirchan);

		if (!strcasecmp(viflag, "gemi"))
		    outrast[col] = ge_mi(d_redchan, d_nirchan);

		if (!strcasecmp(viflag, "arvi"))
		    outrast[col] = ar_vi(d_redchan, d_nirchan, d_bluechan);

		if (!strcasecmp(viflag, "gvi"))
		    outrast[col] = g_vi(d_bluechan, d_greenchan, d_redchan, d_nirchan, d_chan5chan, d_chan7chan);

		if (!strcasecmp(viflag, "gari"))
		    outrast[col] = ga_ri(d_redchan, d_nirchan, d_bluechan, d_greenchan);

		if (!strcasecmp(viflag, "vari"))
		    outrast[col] = va_ri(d_redchan, d_greenchan, d_bluechan);
	    }
	}
	Rast_put_d_row(outfd, outrast);
    }
    G_percent(1, 1, 1);
      
    G_free(inrast_redchan);
    Rast_close(infd_redchan);
    if (nirchan) {
    	G_free(inrast_nirchan);
    	Rast_close(infd_nirchan);
    }
    if (greenchan) {
	G_free(inrast_greenchan);
	Rast_close(infd_greenchan);
    }
    if (bluechan) {
	G_free(inrast_bluechan);
	Rast_close(infd_bluechan);
    }
    if (chan5chan) {
	G_free(inrast_chan5chan);
	Rast_close(infd_chan5chan);
    }
    if (chan7chan) {
	G_free(inrast_chan7chan);
	Rast_close(infd_chan7chan);
    }

    G_free(outrast);
    Rast_close(outfd);

    if (!strcasecmp(viflag, "ndvi")) {
 	/* apply predefined NDVI color table */
	const char *style = "ndvi";
	if (G_find_color_rule("ndvi")) {
	   Rast_make_fp_colors(&colors, style, -1.0, 1.0);
	} else
	   G_fatal_error(_("Unknown color request '%s'"), style);
    } else {
	/* Color from -1.0 to +1.0 in grey */
	Rast_init_colors(&colors);
	val1 = -1;
	val2 = 1;
	Rast_add_c_color_rule(&val1, 0, 0, 0, &val2, 255, 255, 255, &colors);
    }
    Rast_write_colors(result, G_mapset(), &colors);

    Rast_short_history(result, "raster", &history);
    Rast_command_history(&history);
    Rast_write_history(result, &history);

    exit(EXIT_SUCCESS);
}
Exemple #29
0
static int load_files(void)
{
    void *voidc;
    int rtype;
    register int i, rowoff, row, col, vxoff, vyoff, offset;
    int cnt, fd, size, tsiz, coff;
    int vnum;
    int y_rows, y_cols;
    char *pr, *pg, *pb;
    unsigned char *tr, *tg, *tb, *tset;
    char *mpfilename, *name;
    char *yfiles[MAXIMAGES];
    struct Colors colors;
    int ret;

    size = nrows * ncols;

    pr = G_malloc(size);
    pg = G_malloc(size);
    pb = G_malloc(size);

    tsiz = Rast_window_cols();

    tr = (unsigned char *)G_malloc(tsiz);
    tg = (unsigned char *)G_malloc(tsiz);
    tb = (unsigned char *)G_malloc(tsiz);
    tset = (unsigned char *)G_malloc(tsiz);

    for (cnt = 0; cnt < frames; cnt++) {
	if (cnt > MAXIMAGES) {
	    cnt--;
	    break;
	}

	for (i = 0; i < size; i++)
	    pr[i] = pg[i] = pb[i] = 0;

	for (vnum = 0; vnum < numviews; vnum++) {
	    if (icols == vcols) {
		vxoff = BORDER_W;
		vyoff = (irows == vrows) ? BORDER_W :
		    BORDER_W + vnum * (BORDER_W + vrows);
	    }
	    else if (irows == vrows) {
		vxoff = (icols == vcols) ? BORDER_W :
		    BORDER_W + vnum * (BORDER_W + vcols);
		vyoff = BORDER_W;
	    }
	    else {		/* 4 views */
		/* assumes we want:
		   view1        view2
		   view3        view4   
		 */
		vxoff = vnum % 2 ? BORDER_W : vcols + 2 * BORDER_W;
		vyoff = vnum > 1 ? vrows + 2 * BORDER_W : BORDER_W;
	    }

	    name = vfiles[vnum][cnt];

	    G_message(_("Reading raster map <%s>..."), name);

	    fd = Rast_open_old(name, "");

	    if (Rast_read_colors(name, "", &colors) < 0)
		G_fatal_error(_("Unable to read color table for <%s>"), name);

	    rtype = Rast_get_map_type(fd);
	    voidc = Rast_allocate_buf(rtype);

	    for (row = 0; row < vrows; row++) {
		Rast_get_row(fd, voidc, (int)(row / vscale), rtype);

		rowoff = (vyoff + row) * ncols;
		Rast_lookup_colors(voidc, tr, tg, tb,
				       tset, tsiz, &colors, rtype);

		for (col = 0; col < vcols; col++) {
		    coff = (int)(col / vscale);
		    offset = rowoff + col + vxoff;

		    if (!tset[coff])
			pr[offset] = pg[offset] = pb[offset] = (char)255;
		    else {
			pr[offset] = (char)tr[coff];
			pg[offset] = (char)tg[coff];
			pb[offset] = (char)tb[coff];
		    }
		}
	    }

	    Rast_close(fd);
	}

	yfiles[cnt] = G_tempfile();

#ifdef USE_PPM
	write_ppm(pr, pg, pb, nrows, ncols, &y_rows, &y_cols, yfiles[cnt]);
#else
	write_ycc(pr, pg, pb, nrows, ncols, &y_rows, &y_cols, yfiles[cnt]);
#endif
    }

    mpfilename = G_tempfile();
    write_params(mpfilename, yfiles, outfile, cnt, quality, y_rows, y_cols, 0);

    if (G_verbose() <= G_verbose_min())
	ret = G_spawn(encoder, encoder, mpfilename,
		      SF_REDIRECT_FILE, SF_STDOUT, SF_MODE_OUT, G_DEV_NULL,
		      SF_REDIRECT_FILE, SF_STDERR, SF_MODE_OUT, G_DEV_NULL,
		      NULL);
    else
	ret = G_spawn(encoder, encoder, mpfilename, NULL);

    if (ret != 0)
	G_warning(_("mpeg_encode ERROR"));

    clean_files(mpfilename, yfiles, cnt);

    G_free(voidc);
    G_free(tset);
    G_free(tr);
    G_free(tg);
    G_free(tb);
    G_free(pr);
    G_free(pg);
    G_free(pb);

    return (cnt);
}
Exemple #30
0
/* exact check for each band
 * returns 0 on success
 * -1 if given nodata value was present in data
 * -2 if selected GDAL datatype could not hold all values
 * */
int exact_checks(GDALDataType export_datatype,
		const char *name, const char *mapset,
		struct Cell_head *cellhead, RASTER_MAP_TYPE maptype,
		double nodataval, const char *nodatakey,
		int default_nodataval)
{
    double dfCellMin;
    double dfCellMax;
    int fd;
    int cols = cellhead->cols;
    int rows = cellhead->rows;
    int ret = 0;

    /* Open GRASS raster */
    fd = Rast_open_old(name, mapset);

    /* Create GRASS raster buffer */
    void *bufer = Rast_allocate_buf(maptype);

    if (bufer == NULL) {
	G_warning(_("Unable to allocate buffer for reading raster map"));
	return -1;
    }

    /* the following routine must be kept identical to export_band */

    /* Copy data form GRASS raster to GDAL raster */
    int row, col;
    int n_nulls = 0, nodatavalmatch = 0;

    dfCellMin = TYPE_FLOAT64_MAX;
    dfCellMax = TYPE_FLOAT64_MIN;

    /* Better use selected GDAL datatype instead of 
     * the best match with GRASS raster map types ? */

    if (maptype == FCELL_TYPE) {

	FCELL fnullval = (FCELL) nodataval;

	G_debug(1, "FCELL nodata val: %f", fnullval);

	for (row = 0; row < rows; row++) {

	    Rast_get_row(fd, bufer, row, maptype);
	    for (col = 0; col < cols; col++) {
		if (Rast_is_f_null_value(&((FCELL *) bufer)[col])) {
		    n_nulls++;
		}
		else {
		    if (((FCELL *) bufer)[col] == fnullval) {
			nodatavalmatch = 1;
		    }
		    if (dfCellMin > ((FCELL *) bufer)[col])
			dfCellMin = ((FCELL *) bufer)[col];
		    if (dfCellMax < ((FCELL *) bufer)[col])
			dfCellMax = ((FCELL *) bufer)[col];
		}
	    }
	    G_percent(row + 1, rows, 2);
	}
    }
    else if (maptype == DCELL_TYPE) {

	DCELL dnullval = (DCELL) nodataval;

	G_debug(1, "DCELL nodata val: %f", dnullval);

	for (row = 0; row < rows; row++) {

	    Rast_get_row(fd, bufer, row, maptype);
	    for (col = 0; col < cols; col++) {
		if (Rast_is_d_null_value(&((DCELL *) bufer)[col])) {
		    ((DCELL *) bufer)[col] = dnullval;
		    n_nulls++;
		}
		else {
		    if (((DCELL *) bufer)[col] == dnullval) {
			nodatavalmatch = 1;
		    }
		    if (dfCellMin > ((DCELL *) bufer)[col])
			dfCellMin = ((DCELL *) bufer)[col];
		    if (dfCellMax < ((DCELL *) bufer)[col])
			dfCellMax = ((DCELL *) bufer)[col];
		}
	    }
	    G_percent(row + 1, rows, 2);
	}
    }
    else {

	CELL inullval = (CELL) nodataval;

	G_debug(1, "CELL nodata val: %d", inullval);

	for (row = 0; row < rows; row++) {

	    Rast_get_row(fd, bufer, row, maptype);
	    for (col = 0; col < cols; col++) {
		if (Rast_is_c_null_value(&((CELL *) bufer)[col])) {
		    ((CELL *) bufer)[col] = inullval;
		    n_nulls++;
		}
		else {
		    if (((CELL *) bufer)[col] == inullval) {
			nodatavalmatch = 1;
		    }
		    if (dfCellMin > ((CELL *) bufer)[col])
			dfCellMin = ((CELL *) bufer)[col];
		    if (dfCellMax < ((CELL *) bufer)[col])
			dfCellMax = ((CELL *) bufer)[col];
		}
	    }
	    G_percent(row + 1, rows, 2);
	}
    }
    G_debug(1, "min %g max %g", dfCellMin, dfCellMax);

    /* can the GDAL datatype hold the data range to be exported ? */
    /* f-flag does not override */
    if (exact_range_check(dfCellMin, dfCellMax, export_datatype, name)) {
	G_warning("Raster export results in data loss.");
	ret = -2;
    }
    G_message(_("Using GDAL data type <%s>"), GDALGetDataTypeName(export_datatype));

    /* a default nodata value was used and NULL cells were present */
    if (n_nulls && default_nodataval) {
	if (maptype == CELL_TYPE)
	    G_important_message(_("Input raster map contains cells with NULL-value (no-data). "
				 "The value %d will be used to represent no-data values in the input map. "
				 "You can specify a nodata value with the %s option."),
				(int)nodataval, nodatakey);
	else
	    G_important_message(_("Input raster map contains cells with NULL-value (no-data). "
				 "The value %g will be used to represent no-data values in the input map. "
				 "You can specify a nodata value with the %s option."),
				nodataval, nodatakey);
    }

    /* the nodata value was present in the exported data */
    if (nodatavalmatch && n_nulls) {
	/* default nodataval didn't work */
	if (default_nodataval) {
	    G_warning(_("The default nodata value is present in raster"
			"band <%s> and would lead to data loss. Please specify a "
			"custom nodata value with the %s parameter."),
		      name, nodatakey);
	}
	/* user-specified nodataval didn't work */
	else {
	    G_warning(_("The user given nodata value %g is present in raster"
			"band <%s> and would lead to data loss. Please specify a "
			"different nodata value with the %s parameter."),
		      nodataval, name, nodatakey);
	}
	ret = -1;
    }

    Rast_close(fd);

    G_free(bufer);

    return ret;
}