//=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- // Creates an LSDChiTools from an LSDRaster //=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- void LSDChiTools::create(LSDIndexRaster& ThisRaster) { NRows = ThisRaster.get_NRows(); NCols = ThisRaster.get_NCols(); XMinimum = ThisRaster.get_XMinimum(); YMinimum = ThisRaster.get_YMinimum(); DataResolution = ThisRaster.get_DataResolution(); NoDataValue = ThisRaster.get_NoDataValue(); GeoReferencingStrings = ThisRaster.get_GeoReferencingStrings(); }
//=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- // // Create function that reads from an index raster // //=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- void LSDRasterInfo::create(LSDIndexRaster& IRaster) { ///Number of rows. NRows = IRaster.get_NRows(); NCols = IRaster.get_NCols(); XMinimum = IRaster.get_XMinimum(); YMinimum = IRaster.get_YMinimum(); DataResolution = IRaster.get_DataResolution(); NoDataValue = IRaster.get_NoDataValue(); GeoReferencingStrings = IRaster.get_GeoReferencingStrings(); }
//=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-= // this appends the channel onto an index raster. Used to test where the channel is. // // SMM 2012 // //=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-= void LSDIndexChannel::append_index_channel_to_index_raster(LSDIndexRaster& old_raster) { int n_nodes_in_channel = int(NodeSequence.size()); cout << "NRows: " << NRows << " NCols: " << NCols << endl; Array2D<int> Channel_array= old_raster.get_RasterData(); for(int i = 0; i<n_nodes_in_channel; i++) { //cout << "row: " << RowSequence[i] << " col: " << ColSequence[i] << endl; Channel_array[RowSequence[i]][ColSequence[i]]= 1; } LSDIndexRaster Channel_loc(NRows,NCols, XMinimum, YMinimum, DataResolution, NoDataValue, Channel_array,GeoReferencingStrings); old_raster = Channel_loc; }
int main (int nNumberofArgs,char *argv[]) { //Test for correct input arguments if (nNumberofArgs!=3) { cout << "FATAL ERROR: wrong number inputs. The program needs the path name and the file name" << endl; exit(EXIT_SUCCESS); } string path_name = argv[1]; // make sure there is a slash on the end of the file string lchar = path_name.substr(path_name.length()-2,1); string slash = "/"; if (lchar != slash) { cout << "You forgot the frontslash at the end of the path. Appending." << endl; path_name = path_name+slash; } string f_name = argv[2]; cout << "\nYou are running the write junctions driver." << endl <<"IMPORTANT: this has been updated to load an ENVI DEM, whith extension .bil" << endl <<"You can convert your DEM to this file format using gdal_translate, with -of ENVI" << endl <<"See documentation at: http://www.geos.ed.ac.uk/~smudd/LSDTT_docs/html/gdal_notes.html" << endl << endl; cout << "The path is: " << path_name << " and the filename is: " << f_name << endl; string full_name = path_name+f_name; ifstream file_info_in; file_info_in.open(full_name.c_str()); if( file_info_in.fail() ) { cout << "\nFATAL ERROR: the header file \"" << full_name << "\" doesn't exist" << endl; exit(EXIT_FAILURE); } string DEM_name; string fill_ext = "_fill"; file_info_in >> DEM_name; int junction_number; float pruning_threshold; int threshold; float A_0; int minimum_segment_length; float sigma; float start_movern; float d_movern; float Minimum_Slope; int n_movern; int target_nodes; int n_iterations; float fraction_dchi_for_variation; float vertical_interval; float horizontal_interval; float area_thin_frac; int target_skip; file_info_in >> Minimum_Slope >> threshold >> junction_number >> pruning_threshold >> A_0 >> minimum_segment_length >> sigma >> start_movern >> d_movern >> n_movern >> target_nodes >> n_iterations >> fraction_dchi_for_variation >> vertical_interval >> horizontal_interval >> area_thin_frac >> target_skip; cout << "Paramters of this run: " << endl << "junction number: " << junction_number << endl << "pruning_threshold: " << pruning_threshold << endl << "threshold: " << threshold << endl << "A_0: " << A_0 << endl << "minimum_segment_length: " << minimum_segment_length << endl << "sigma: " << sigma << endl << "start_movern " << start_movern << endl << "d_movern: " << d_movern << endl << "n_movern: " << n_movern << endl << "target_nodes: " << target_nodes << endl << "n_iterarions: " << n_iterations << endl << "fraction_dchi_for_variation: " << fraction_dchi_for_variation << endl << "vertical interval: " << vertical_interval << endl << "horizontal interval: " << horizontal_interval << endl << "area thinning fraction for SA analysis: " << area_thin_frac << endl << "target_skip is: " << target_skip << endl; string jn_name = itoa(junction_number); string uscore = "_"; jn_name = uscore+jn_name; file_info_in.close(); string DEM_f_name = path_name+DEM_name+fill_ext; string DEM_bil_extension = "bil"; // set no flux boundary conditions vector<string> boundary_conditions(4); boundary_conditions[0] = "No"; boundary_conditions[1] = "no flux"; boundary_conditions[2] = "no flux"; boundary_conditions[3] = "No flux"; // load the filled DEM LSDRaster filled_topo_test((path_name+DEM_name+fill_ext), DEM_bil_extension); // get a flow info object LSDFlowInfo FlowInfo(boundary_conditions,filled_topo_test); // calcualte the distance from outlet LSDRaster DistanceFromOutlet = FlowInfo.distance_from_outlet(); LSDIndexRaster ContributingPixels = FlowInfo.write_NContributingNodes_to_LSDIndexRaster(); // get the sources vector<int> sources; sources = FlowInfo.get_sources_index_threshold(ContributingPixels, threshold); // now get the junction network LSDJunctionNetwork ChanNetwork(sources, FlowInfo); // now get a junction and look for the longest channel upstream cout << "creating main stem" << endl; LSDIndexChannel main_stem = ChanNetwork.generate_longest_index_channel_in_basin(junction_number, FlowInfo, DistanceFromOutlet); cout << "got main stem channel, with n_nodes " << main_stem.get_n_nodes_in_channel() << endl; string Basin_name = "_basin"; LSDIndexRaster BasinArray = ChanNetwork.extract_basin_from_junction(junction_number,junction_number,FlowInfo); BasinArray.write_raster((path_name+DEM_name+Basin_name+jn_name),DEM_bil_extension); // now get the best fit m over n for all the tributaries int organization_switch = 1; int pruning_switch = 1; LSDIndexChannelTree ChannelTree(FlowInfo, ChanNetwork, junction_number, organization_switch, DistanceFromOutlet, pruning_switch, pruning_threshold); // print a file that can be ingested bt the chi fitting algorithm string Chan_fname = "_ChanNet"; string Chan_ext = ".chan"; string Chan_for_chi_ingestion_fname = path_name+DEM_name+Chan_fname+jn_name+Chan_ext; ChannelTree.print_LSDChannels_for_chi_network_ingestion(FlowInfo, filled_topo_test, DistanceFromOutlet, Chan_for_chi_ingestion_fname); ChannelTree.convert_chan_file_for_ArcMap_ingestion(Chan_for_chi_ingestion_fname); }
int main (int nNumberofArgs,char *argv[]) { //Test for correct input arguments if (nNumberofArgs!=7) { cout << "FATAL ERROR: wrong number of inputs. The program needs the path (with trailing slash), the filename prefix, window radius, "; cout << "basin order, a switch to use or exclude floodplains and a switch to write rasters if desired." << endl; exit(EXIT_SUCCESS); } //load input arguments string path = argv[1]; string filename = argv[2]; float window_radius = atof(argv[3]); //6 int BasinOrder = atoi(argv[4]); //2 int FloodplainSwitch = atoi(argv[5]); int WriteRasters = atoi(argv[6]); //0 (do not write rasters) or 1 (write rasters) //set boundary conditions vector<string> BoundaryConditions(4, "No Flux"); //load dem LSDRaster DEM((path+filename+"_dem"), "flt"); //Fill float MinSlope = 0.0001; LSDRaster FilledDEM = DEM.fill(MinSlope); //surface fitting vector<int> raster_selection; raster_selection.push_back(0); raster_selection.push_back(1); //slope raster_selection.push_back(1); //aspect raster_selection.push_back(1); //curvature raster_selection.push_back(1); //plan curvature raster_selection.push_back(0); raster_selection.push_back(0); raster_selection.push_back(0); vector<LSDRaster> Surfaces = FilledDEM.calculate_polyfit_surface_metrics(window_radius, raster_selection); LSDRaster slope = Surfaces[1]; LSDRaster aspect = Surfaces[2]; cout << "\nGetting drainage network and basins\n" << endl; // get a flow info object LSDFlowInfo FlowInfo(BoundaryConditions,FilledDEM); //get stream net from channel heads vector<int> sources = FlowInfo.Ingest_Channel_Heads((path+filename+"_dem_CH"), "flt"); //swap to csv? LSDJunctionNetwork ChanNetwork(sources, FlowInfo); LSDIndexRaster StreamNetwork = ChanNetwork.StreamOrderArray_to_LSDIndexRaster(); //load floodplain and merge with the channel network if required, otherwise the //floodplain mask will only contain the channel data LSDIndexRaster ChannelAndFloodplain; if (FloodplainSwitch == 1){ LSDIndexRaster Floodplains((path+filename+"_FloodPlain"), "flt"); ChannelAndFloodplain = StreamNetwork.MergeChannelWithFloodplain(Floodplains); } else{ ChannelAndFloodplain = StreamNetwork; } //Extract basins based on input stream order vector< int > basin_junctions = ChanNetwork.ExtractBasinJunctionOrder(BasinOrder, FlowInfo); LSDIndexRaster Basin_Raster = ChanNetwork.extract_basins_from_junction_vector(basin_junctions, FlowInfo); cout << "\nExtracting hilltops and hilltop curvature" << endl; // extract hilltops - no critical slope filtering is performed here LSDRaster hilltops = ChanNetwork.ExtractRidges(FlowInfo); //get hilltop curvature using filter to remove positive curvatures LSDRaster cht_raster = FilledDEM.get_hilltop_curvature(Surfaces[3], hilltops); LSDRaster CHT = FilledDEM.remove_positive_hilltop_curvature(cht_raster); //get d infinity flowdirection and flow area Array2D<float> dinf = FilledDEM.D_inf_FlowDir(); LSDRaster dinf_rast = FilledDEM.LSDRasterTemplate(dinf); LSDRaster DinfArea = FilledDEM.D_inf_units(); cout << "Starting hilltop flow routing\n" << endl; //start of Hilltop flow routing string prefix = (path+filename+"_dreich_"); //set a path to write the hillslope length data to, based on the input path and filename given by the user // these params do not need changed during normal use of the HFR algorithm bool print_paths_switch = false; int thinning = 1; string trace_path = ""; bool basin_filter_switch = false; vector<int> Target_Basin_Vector; //run HFR vector< Array2D<float> > HFR_Arrays = FlowInfo.HilltopFlowRouting(FilledDEM, hilltops, slope, ChannelAndFloodplain, aspect, prefix, Basin_Raster, Surfaces[4], print_paths_switch, thinning, trace_path, basin_filter_switch, Target_Basin_Vector); LSDRaster HFR_LH = hilltops.LSDRasterTemplate(HFR_Arrays[1]); LSDRaster HFR_Slope = hilltops.LSDRasterTemplate(HFR_Arrays[2]); LSDRaster relief = hilltops.LSDRasterTemplate(HFR_Arrays[3]); //end of HFR //create lsdbasin objects in a loop over each junction number vector< LSDBasin > Basins; //slope area plotting parameters - these defaults are usually fine float log_bin_width = 0.1; int SplineResolution = 10000; int bin_threshold = 0; float CriticalSlope = 1.2; //this needs modified to generate proper E*R* data cout << "\nCreating each LSDBasin" << endl; //loop over each basin, generating an LSDBasin object which contains that basin's measurements for (int w = 0; w < int(basin_junctions.size()); ++w){ cout << (w+1) << " / " << basin_junctions.size() << endl; LSDBasin Basin(basin_junctions[w], FlowInfo, ChanNetwork); Basin.set_FlowLength(StreamNetwork, FlowInfo); Basin.set_DrainageDensity(); Basin.set_all_HillslopeLengths(FlowInfo, HFR_LH, slope, DinfArea, log_bin_width, SplineResolution, bin_threshold); Basin.set_SlopeMean(FlowInfo, slope); Basin.set_AspectMean(FlowInfo, aspect); Basin.set_ElevationMean(FlowInfo, FilledDEM); Basin.set_ReliefMean(FlowInfo, relief); Basin.set_CHTMean(FlowInfo, CHT); Basin.set_EStar_RStar(CriticalSlope); Basins.push_back(Basin); } //create a filestream to write the output data // use the input arguments to generate a path and filename for the output file ofstream WriteData; stringstream ss; ss << path << filename << "_dreich_PaperData.txt"; WriteData.open(ss.str().c_str()); //write headers WriteData << "BasinID HFR_mean HFR_median HFR_stddev HFR_stderr HFR_Nvalues HFR_range HFR_min HFR_max SA_binned_LH SA_Spline_LH LH_Density Area Basin_Slope_mean Basin_Slope_median Basin_Slope_stddev Basin_Slope_stderr Basin_Slope_Nvalues Basin_Slope_range Basin_Slope_min Basin_Slope_max Basin_elev_mean Basin_elev_median Basin_elev_stddev Basin_elev_stderr Basin_elev_Nvalues Basin_elev_Range Basin_elev_min Basin_elev_max Aspect_mean CHT_mean CHT_median CHT_stddev CHT_stderr CHT_Nvalues CHT_range CHT_min CHT_max EStar RStar HT_Slope_mean HT_Slope_median HT_Slope_stddev HT_Slope_stderr HT_Slope_Nvalues HT_Slope_range HT_Slope_min HT_Slope_max HT_relief_mean HT_relief_median HT_relief_stddev HT_relief_stderr HT_relief_Nvalues HT_relief_range HT_relief_min HT_relief_max" << endl; cout << "\nWriting data to file\n" << endl; //write all data to the opened file, ensuring that there are data points to be written in each basin for (int q = 0; q < int(Basins.size()); ++q){ // only work where we have data points if (Basins[q].CalculateNumDataPoints(FlowInfo, HFR_LH) != 0 && Basins[q].CalculateNumDataPoints(FlowInfo, slope) != 0 && Basins[q].CalculateNumDataPoints(FlowInfo, FilledDEM) != 0 && Basins[q].CalculateNumDataPoints(FlowInfo, CHT) != 0 && Basins[q].CalculateNumDataPoints(FlowInfo, HFR_Slope) != 0 && Basins[q].CalculateNumDataPoints(FlowInfo, relief) != 0){ // BasinID WriteData << Basins[q].get_Junction()<< " "; //HFR WriteData << Basins[q].get_HillslopeLength_HFR() << " " << Basins[q].CalculateBasinMedian(FlowInfo, HFR_LH) << " " << Basins[q].CalculateBasinStdDev(FlowInfo, HFR_LH) << " " << Basins[q].CalculateBasinStdError(FlowInfo, HFR_LH) << " " << Basins[q].CalculateNumDataPoints(FlowInfo, HFR_LH) << " " << Basins[q].CalculateBasinRange(FlowInfo, HFR_LH) << " " << Basins[q].CalculateBasinMin(FlowInfo, HFR_LH) << " " << Basins[q].CalculateBasinMax(FlowInfo, HFR_LH)<< " "; //SA_Bins WriteData << Basins[q].get_HillslopeLength_Binned()<< " "; //SA_Spline WriteData << Basins[q].get_HillslopeLength_Spline()<< " "; //Density WriteData << Basins[q].get_HillslopeLength_Density()<< " "; //Area WriteData << Basins[q].get_Area()<< " "; //Slope_Basin WriteData << Basins[q].get_SlopeMean() << " " << Basins[q].CalculateBasinMedian(FlowInfo, slope) << " " << Basins[q].CalculateBasinStdDev(FlowInfo, slope) << " " << Basins[q].CalculateBasinStdError(FlowInfo, slope) << " " << Basins[q].CalculateNumDataPoints(FlowInfo, slope) << " " << Basins[q].CalculateBasinRange(FlowInfo, slope) << " " << Basins[q].CalculateBasinMin(FlowInfo, slope) << " " << Basins[q].CalculateBasinMax(FlowInfo, slope)<< " "; //Elev_Basin WriteData << Basins[q].get_ElevationMean() << " " << Basins[q].CalculateBasinMedian(FlowInfo, FilledDEM) << " " << Basins[q].CalculateBasinStdDev(FlowInfo, FilledDEM) << " " << Basins[q].CalculateBasinStdError(FlowInfo, FilledDEM) << " " << Basins[q].CalculateNumDataPoints(FlowInfo, FilledDEM) << " " << Basins[q].CalculateBasinRange(FlowInfo, FilledDEM) << " " << Basins[q].CalculateBasinMin(FlowInfo, FilledDEM) << " " << Basins[q].CalculateBasinMax(FlowInfo, FilledDEM)<< " "; //Aspect_Basin WriteData << Basins[q].get_AspectMean()<< " "; //CHT WriteData << Basins[q].get_CHTMean() << " " << Basins[q].CalculateBasinMedian(FlowInfo, CHT) << " " << Basins[q].CalculateBasinStdDev(FlowInfo, CHT) << " " << Basins[q].CalculateBasinStdError(FlowInfo, CHT) << " " << Basins[q].CalculateNumDataPoints(FlowInfo, CHT) << " " << Basins[q].CalculateBasinRange(FlowInfo, CHT) << " " << Basins[q].CalculateBasinMin(FlowInfo, CHT) << " " << Basins[q].CalculateBasinMax(FlowInfo, CHT) << " "; //EStar WriteData << Basins[q].get_EStar()<< " "; //RStar WriteData << Basins[q].get_RStar()<< " "; //Slope_mean WriteData << Basins[q].CalculateBasinMean(FlowInfo, HFR_Slope) << " " << Basins[q].CalculateBasinMedian(FlowInfo, HFR_Slope) << " " << Basins[q].CalculateBasinStdDev(FlowInfo, HFR_Slope) << " " << Basins[q].CalculateBasinStdError(FlowInfo, HFR_Slope) << " " << Basins[q].CalculateNumDataPoints(FlowInfo, HFR_Slope) << " " << Basins[q].CalculateBasinRange(FlowInfo, HFR_Slope) << " " << Basins[q].CalculateBasinMin(FlowInfo, HFR_Slope) << " " << Basins[q].CalculateBasinMax(FlowInfo, HFR_Slope)<< " "; //Relief_mean WriteData << Basins[q].get_ReliefMean() << " " << Basins[q].CalculateBasinMedian(FlowInfo, relief) << " " << Basins[q].CalculateBasinStdDev(FlowInfo, relief) << " " << Basins[q].CalculateBasinStdError(FlowInfo, relief) << " " << Basins[q].CalculateNumDataPoints(FlowInfo, relief) << " " << Basins[q].CalculateBasinRange(FlowInfo, relief) << " " << Basins[q].CalculateBasinMin(FlowInfo, relief) << " " << Basins[q].CalculateBasinMax(FlowInfo, relief)<< "\n"; } } // close the output file WriteData.close(); //if the user requests the raster to be written, write the rasters if (WriteRasters == 1){ cout << "Writing Rasters\n" << endl; // FilledDEM.write_raster((path+filename+"_Fill"), "flt"); Surfaces[1].write_raster((path+filename+"_dreich_Slope"),"flt"); //Surfaces[2].write_raster((path+filename+"_Aspect"),"flt"); //Surfaces[3].write_raster((path+filename+"_Curvature"),"flt"); //StreamNetwork.write_raster((path+filename+"_STNET"), "flt"); //Basin_Raster.write_raster((path+filename+"_Basins"), "flt"); CHT.write_raster((path+filename+"_dreich_CHT"),"flt"); HFR_LH.write_raster((path+filename+"_dreich_HFR_LH"),"flt"); HFR_Slope.write_raster((path+filename+"_dreich_HFR_SLP"),"flt"); relief.write_raster((path+filename+"_dreich_Relief"),"flt"); //perform a hillshade //LSDRaster Hillshade = FilledDEM.hillshade(45.0,315.0,1.0); //Hillshade.write_raster((path+filename+"_HS"),"flt"); } }
int main (int nNumberofArgs,char *argv[]) { //Test for correct input arguments if (nNumberofArgs!=3) { cout << "FATAL ERROR: wrong number inputs. The program needs the path name and the file name" << endl; exit(EXIT_SUCCESS); } string path_name = argv[1]; string f_name = argv[2]; cout << "The path is: " << path_name << " and the filename is: " << f_name << endl; string full_name = path_name+f_name; ifstream file_info_in; file_info_in.open(full_name.c_str()); if( file_info_in.fail() ) { cout << "\nFATAL ERROR: the header file \"" << full_name << "\" doesn't exist" << endl; exit(EXIT_FAILURE); } string DEM_name; string fill_ext = "_fill"; file_info_in >> DEM_name; int threshold; float Minimum_Slope; float curv_threshold; float minimum_catchment_area; file_info_in >> Minimum_Slope >> threshold >> curv_threshold >> minimum_catchment_area; // get some file names string DEM_f_name = path_name+DEM_name+fill_ext; string DEM_flt_extension = "bil"; // load the DEM LSDRaster topo_test((path_name+DEM_name), DEM_flt_extension); LSDRasterSpectral SpectralRaster(topo_test); // int FilterType = 2; // float FLow = 0.01; // float FHigh = 0.1; // LSDRaster topo_test_filtered = SpectralRaster.fftw2D_filter(FilterType, FLow, FHigh); LSDRaster topo_test_wiener = SpectralRaster.fftw2D_wiener(); int border_width = 100; // topo_test_filtered = topo_test_filtered.border_with_nodata(border_width); topo_test_wiener = topo_test_wiener.border_with_nodata(border_width); // Set the no flux boundary conditions vector<string> boundary_conditions(4); boundary_conditions[0] = "No"; boundary_conditions[1] = "no flux"; boundary_conditions[2] = "no flux"; boundary_conditions[3] = "No flux"; // get the filled file cout << "Filling the DEM" << endl; // LSDRaster filled_topo_test = topo_test_filtered.fill(Minimum_Slope); LSDRaster filled_topo_test = topo_test_wiener.fill(Minimum_Slope); filled_topo_test.write_raster((DEM_f_name),DEM_flt_extension); //get a FlowInfo object LSDFlowInfo FlowInfo(boundary_conditions,filled_topo_test); LSDIndexRaster ContributingPixels = FlowInfo.write_NContributingNodes_to_LSDIndexRaster(); vector<int> sources; sources = FlowInfo.get_sources_index_threshold(ContributingPixels, threshold); // now get the junction network LSDJunctionNetwork ChanNetwork(sources, FlowInfo); // Get the valleys using the contour curvature int surface_fitting_window_radius = 7; int surface_fitting_window_radius_LW = 25; vector<LSDRaster> surface_fitting, surface_fitting_LW; LSDRaster tan_curvature; LSDRaster tan_curvature_LW; string curv_name = "_tan_curv"; vector<int> raster_selection(8, 0); raster_selection[6] = 1; surface_fitting = topo_test_wiener.calculate_polyfit_surface_metrics(surface_fitting_window_radius, raster_selection); surface_fitting_LW = topo_test_wiener.calculate_polyfit_surface_metrics(surface_fitting_window_radius_LW, raster_selection); for(int i = 0; i<int(raster_selection.size()); ++i) { if(raster_selection[i]==1) { tan_curvature = surface_fitting[i]; tan_curvature.write_raster((path_name+DEM_name+curv_name), DEM_flt_extension); tan_curvature_LW = surface_fitting[i]; tan_curvature_LW.write_raster((path_name+DEM_name+curv_name+"_LW"), DEM_flt_extension); } } string CH_name = "_CH_Pelletier"; Array2D<float> topography = filled_topo_test.get_RasterData(); Array2D<float> curvature = tan_curvature.get_RasterData(); Array2D<float> curvature_LW = tan_curvature_LW.get_RasterData(); cout << "\tLocating channel heads..." << endl; vector<int> ChannelHeadNodes = ChanNetwork.calculate_pelletier_channel_heads_DTM(FlowInfo, topography, curv_threshold, curvature,curvature_LW); // Now filter out false positives along channel according to a threshold // catchment area cout << "\tFiltering out false positives..." << endl; LSDJunctionNetwork ChanNetworkNew(ChannelHeadNodes, FlowInfo); vector<int> ChannelHeadNodesFilt; int count = 0; for(int i = 0; i<int(ChannelHeadNodes.size()); ++i) { int upstream_junc = ChanNetworkNew.get_Junction_of_Node(ChannelHeadNodes[i], FlowInfo); int test_node = ChanNetworkNew.get_penultimate_node_from_stream_link(upstream_junc, FlowInfo); float catchment_area = float(FlowInfo.retrieve_contributing_pixels_of_node(test_node)) * FlowInfo.get_DataResolution(); if (catchment_area >= minimum_catchment_area) ChannelHeadNodesFilt.push_back(ChannelHeadNodes[i]); else ++count; } cout << "\t...removed " << count << " nodes out of " << ChannelHeadNodes.size() << endl; FlowInfo.print_vector_of_nodeindices_to_csv_file(ChannelHeadNodesFilt,(path_name+DEM_name+CH_name)); //LSDIndexRaster Channel_heads_raster = FlowInfo.write_NodeIndexVector_to_LSDIndexRaster(ChannelHeadNodesFilt); //Channel_heads_raster.write_raster((path_name+DEM_name+CH_name),DEM_flt_extension); //create a channel network based on these channel heads LSDJunctionNetwork NewChanNetwork(ChannelHeadNodesFilt, FlowInfo); LSDIndexRaster SOArrayNew = NewChanNetwork.StreamOrderArray_to_LSDIndexRaster(); string SO_name_new = "_SO_Pelletier"; SOArrayNew.write_raster((path_name+DEM_name+SO_name_new),DEM_flt_extension); }