/*C * Original project: Lars Arge, Jeff Chase, Pat Halpin, Laura Toma, Dean * Urban, Jeff Vitter, Rajiv Wickremesinghe 1999 * * GRASS Implementation: Lars Arge, Helena Mitasova, Laura Toma 2002 * * Copyright (c) 2002 Duke University -- Laura Toma * * Copyright (c) 1999-2001 Duke University -- * Laura Toma and Rajiv Wickremesinghe * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * 3. All advertising materials mentioning features or use of this software * must display the following acknowledgement: * This product includes software developed by Duke University * 4. Neither the name of the University nor the names of its contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE TRUSTEES AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE TRUSTEES OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. *C*/ #ifndef _gras2str_H #define _gras2str_H #include #include "option.h" #include "types.h" #include "common.h" #include "nodata.h" /* for TERRAFLOW_INTERNAL_NODATA_VALUE */ /* ---------------------------------------------------------------------- */ /* create and return a STREAM containing the given cell; nodata_count is set to the number of cells that contain nodata */ template AMI_STREAM* cell2stream(char* cellname, elevation_type T_max_value, long* nodata_count) { Rtimer rt; AMI_err ae; elevation_type T_min_value = -T_max_value; rt_start(rt); assert(cellname && nodata_count); *nodata_count = 0; /* create output stream */ AMI_STREAM* str = new AMI_STREAM(); { char * foo; str->name(&foo); *stats << "reading cell file " << cellname << "to stream " << foo << endl; if (opt->verbose) fprintf(stderr, "reading data from %s to stream %s: ", cellname, foo); } char *mapset; mapset = G_find_cell (cellname, ""); if (mapset == NULL) G_fatal_error ("cell file [%s] not found", cellname); /* open map */ int infd; if ( (infd = G_open_cell_old (cellname, mapset)) < 0) G_fatal_error ("Cannot open cell file [%s]", cellname); /* determine map type (CELL/FCELL/DCELL) */ RASTER_MAP_TYPE data_type; data_type = G_raster_map_type(cellname, mapset); /* Allocate input buffer */ void *inrast; inrast = G_allocate_raster_buf(data_type); CELL c; FCELL f; DCELL d; T x; int isnull = 0; for (int i = 0; i< nrows; i++) { /* read input map */ if (G_get_raster_row (infd, inrast, i, data_type) < 0) G_fatal_error ("Could not read from <%s>, row=%d",cellname,i); for (int j=0; j (DCELL)T_max_value) || (d < (DCELL)T_min_value)) { fprintf(stderr, "reading cell file %s at (i=%d,j=%d) value=%.1f\n", cellname, i, j, d); G_fatal_error("value out of range."); } } /* write x to stream */ ae = str->write_item(x); assert(ae == AMI_ERROR_NO_ERROR); } /* for j */ if (opt->verbose) G_percent(i, nrows, 2); }/* for i */ if (opt->verbose) fprintf(stderr, "\n"); /* delete buffers */ G_free(inrast); /* close map files */ G_close_cell (infd); assert(nrows * ncols == str->stream_len()); rt_stop(rt); stats->recordTime("reading cell file", rt); return str; } /* ---------------------------------------------------------------------- */ template void stream2_CELL(AMI_STREAM* str, dimension_type nrows, dimension_type ncols, char* cellname, bool usefcell=false) { Rtimer rt; AMI_err ae; RASTER_MAP_TYPE mtype= (usefcell ? FCELL_TYPE : CELL_TYPE); rt_start(rt); assert(str); assert(str->stream_len() == nrows*ncols); str->seek(0); { char * foo; str->name(&foo); *stats << "writing stream " << foo << " to cell file " << cellname << "\n"; fprintf(stderr, "writing stream %s to cell file %s: ", foo, cellname); } /* open output cell file */ int outfd; if ( (outfd = G_open_raster_new (cellname, mtype)) < 0) { G_fatal_error ("Could not open <%s>", cellname); } /* Allocate output buffer */ unsigned char *outrast; outrast = (unsigned char *)G_allocate_raster_buf(mtype); assert(outrast); T* elt; for (int i=0; i< nrows; i++) { for (int j=0; j< ncols; j++) { /* READ VALUE */ ae = str->read_item(&elt); if (ae != AMI_ERROR_NO_ERROR) { str->sprint(); fprintf(stderr, "reading stream failed at (%d,%d)\n", i,j); G_fatal_error("stream2cell failed"); } /* WRITE VALUE */ if(usefcell){ if (is_nodata(*elt)) { G_set_f_null_value( &( ((FCELL *) outrast)[j]), 1); } else { ((FCELL *) outrast)[j] = (FCELL)(*elt); } }else{ if (is_nodata(*elt)) { G_set_c_null_value( &( ((CELL *) outrast)[j]), 1); } else { ((CELL *) outrast)[j] = (CELL)(*elt); } } } /* for j*/ if (G_put_raster_row (outfd, outrast, mtype) < 0) G_fatal_error ("Cannot write to <%s>",cellname); G_percent(i, nrows, 2); }/* for i */ fprintf(stderr, "\n"); G_free(outrast); G_close_cell (outfd); rt_stop(rt); stats->recordTime("writing cell file", rt); str->seek(0); return; } /* laura: this is identical with stream2_FCELL; did not know how to template ona type --- is that possible? */ /* ---------------------------------------------------------------------- */ template void stream2_CELL(AMI_STREAM *str, dimension_type nrows, dimension_type ncols, FUN fmt, char* cellname) { Rtimer rt; AMI_err ae; assert(str && cellname); /* assert(str->stream_len() == nrows*ncols); */ rt_start(rt); str->seek(0); { char * foo; str->name(&foo); *stats << "writing stream " << foo << "cellfile " << cellname << endl; fprintf(stderr, "writing stream %s to cell file %s: ", foo, cellname); } /* open output cell file */ int outfd; if ( (outfd = G_open_raster_new (cellname, CELL_TYPE)) < 0) { G_fatal_error ("Could not open <%s>", cellname); } /* Allocate output buffer */ unsigned char *outrast; outrast = (unsigned char *)G_allocate_raster_buf(CELL_TYPE); assert(outrast); T* elt; ae = str->read_item(&elt); assert(ae == AMI_ERROR_NO_ERROR || ae == AMI_ERROR_END_OF_STREAM); for (int i=0; i< nrows; i++) { for (int j=0; j< ncols; j++) { if(ae == AMI_ERROR_NO_ERROR && elt->i == i && elt->j == j) { /* WRITE VALUE */ if (is_nodata ( fmt(*elt) )) { G_set_c_null_value( &( ((CELL *) outrast)[j]), 1); } else { ((CELL *) outrast)[j] = (CELL)(fmt(*elt)); } ae = str->read_item(&elt); assert(ae == AMI_ERROR_NO_ERROR || ae == AMI_ERROR_END_OF_STREAM); } else { /* WRITE NODATA */ G_set_c_null_value( &( ((CELL *) outrast)[j]), 1); } } /* for j*/ if (G_put_raster_row (outfd, outrast, CELL_TYPE) < 0) G_fatal_error ("Cannot write to <%s>",cellname); G_percent(i, nrows, 2); }/* for i */ fprintf(stderr,"\n"); G_free(outrast); G_close_cell (outfd); rt_stop(rt); stats->recordTime("writing cell file", rt); str->seek(0); return; } /* ---------------------------------------------------------------------- */ template void stream2_FCELL(AMI_STREAM *str, dimension_type nrows, dimension_type ncols, FUN fmt, char* cellname) { Rtimer rt; AMI_err ae; assert(str && cellname); /* assert(str->stream_len() == nrows*ncols); */ rt_start(rt); str->seek(0); { char * foo; str->name(&foo); *stats << "writing stream " << foo << "cellfile " << cellname << endl; fprintf(stderr, "writing stream %s to cell file %s: ", foo, cellname); } /* open output cell file */ int outfd; if ( (outfd = G_open_raster_new (cellname, FCELL_TYPE)) < 0) { G_fatal_error ("Could not open <%s>", cellname); } /* Allocate output buffer */ unsigned char *outrast; outrast = (unsigned char *)G_allocate_raster_buf(FCELL_TYPE); assert(outrast); T* elt; ae = str->read_item(&elt); assert(ae == AMI_ERROR_NO_ERROR || ae == AMI_ERROR_END_OF_STREAM); for (int i=0; i< nrows; i++) { for (int j=0; j< ncols; j++) { if(ae == AMI_ERROR_NO_ERROR && elt->i == i && elt->j == j) { /* WRITE VALUE */ if (is_nodata ( fmt(*elt) )) { G_set_f_null_value( &( ((FCELL *) outrast)[j]), 1); } else { ((FCELL *) outrast)[j] = (FCELL)(fmt(*elt)); } ae = str->read_item(&elt); assert(ae == AMI_ERROR_NO_ERROR || ae == AMI_ERROR_END_OF_STREAM); } else { /* WRITE NODATA */ G_set_f_null_value( &( ((FCELL *) outrast)[j]), 1); } } /* for j*/ if (G_put_raster_row (outfd, outrast, FCELL_TYPE) < 0) G_fatal_error ("Cannot write to <%s>",cellname); G_percent(i, nrows, 2); }/* for i */ fprintf(stderr, "\n"); G_free(outrast); G_close_cell (outfd); rt_stop(rt); stats->recordTime("writing cell file", rt); str->seek(0); return; } /* ---------------------------------------------------------------------- */ /* outstr is sorted by (i,j); class sweepOutput { public: dimension_type i,j; flowaccumulation_type accu; #ifdef OUTPUT_TCI tci_type tci; #endif }; create an accu cell file, and a tci cell file if OUTPUT_TCI is defined */ template void stream2_FCELL(AMI_STREAM* str, dimension_type nrows, dimension_type ncols, FUN1 fmt1, FUN2 fmt2, char* cellname1, char* cellname2) { Rtimer rt; AMI_err ae; assert(str); #ifndef OUTPUT_TCI /* this function should be used only if tci is wanted as output */ fprintf(stderr, "use this function only if tci is wanted as output\n"); exit(1); #else rt_start(rt); str->seek(0); { char * foo; str->name(&foo); *stats << "writing stream " << foo << "to cell files " << cellname1 << ", " << cellname2 << endl; fprintf(stderr, "writing stream %s to cell files %s, %s: ", foo, cellname1, cellname2); } /* open cell files */ int fd1; if ( (fd1 = G_open_raster_new (cellname1, FCELL_TYPE)) < 0) { G_fatal_error ("Could not open <%s>", cellname1); } int fd2; if ( (fd2 = G_open_raster_new (cellname2, FCELL_TYPE)) < 0) { G_fatal_error ("Could not open <%s>", cellname2); } /* Allocate output buffers */ FCELL *rast1; rast1 = (FCELL*)G_allocate_raster_buf(FCELL_TYPE); assert(rast1); FCELL *rast2; rast2 = (FCELL*)G_allocate_raster_buf(FCELL_TYPE); assert(rast2); T* elt; ae = str->read_item(&elt); assert(ae == AMI_ERROR_NO_ERROR || ae == AMI_ERROR_END_OF_STREAM); for (int i=0; i< nrows; i++) { for (int j=0; j< ncols; j++) { if(ae == AMI_ERROR_NO_ERROR && elt->i == i && elt->j == j) { /* WRITE VALUE */ if (is_nodata(fmt1(*elt))) { G_set_f_null_value(&(rast1[j]), 1); } else { rast1[j] = fmt1(*elt); }; if (is_nodata( fmt2(*elt))) { G_set_f_null_value(&(rast2[j]), 1); } else { rast2[j] = fmt2(*elt); } /* read next value */ ae = str->read_item(&elt); assert(ae == AMI_ERROR_NO_ERROR || ae == AMI_ERROR_END_OF_STREAM); } else { /* WRITE NODATA */ G_set_f_null_value(&(rast1[j]), 1); G_set_f_null_value(&(rast2[j]), 1); } } /* for j*/ if (G_put_raster_row (fd1, rast1, FCELL_TYPE) < 0) G_fatal_error ("Cannot write to <%s>", cellname1); if (G_put_raster_row (fd2, rast2, FCELL_TYPE) < 0) G_fatal_error ("Cannot write to <%s>", cellname2); G_percent(i, nrows, 2); }/* for i */ fprintf(stderr, "\n"); G_free(rast1); G_close_cell (fd1); G_free(rast2); G_close_cell (fd2); rt_stop(rt); stats->recordTime("writing stream to cell files", rt); str->seek(0); return; #endif } #endif