Identify bank side
Summary :: Usage :: Parameters :: Outputs :: Warnings :: Limitations :: Code sample
Summary
Takes a layer and for each feature identifies which bank side the feature is on. This tool will accept point/line/polygon geometry as input. Optionally exports the vertices of polyline/polygon data.
Usage
Requirement for using this tool:
To use this tool you must have attributed the network with:
This tool takes a point/polyline/polygon dataset and determines which side of the river centreline the features are. You would use this tool for example, to identify which side flood protection assets or bank side features such bank erosion are on. Data snapped to the centreline itself would be invalid for this tool. Bank side is determined as if you are looking downstream.
Valid bank side features can be points, lines or polygons. Ideally such data should not be intersecting the network.
Bank side is determined on a "majority wins" approach, to overcome scenarios where the original data capture of the bank side feature was captured poorly or at a different scale to the river centreline and intersections with the network exist when in reality there are none. Polyline or polygon features are exploded out into their vertices and which side each vertex is to the nearest polyline is determined. If the input data was a point dataset then these are tested as-is. This approach allows for minor crossings of the centreline to be ignored.
Two linear bank features: embankment and reinforcement displayed with their vertices (red points). Note the embankment was poorly
digitised and has a single vertex on the opposite bank. When determining which side of the river a feature is, the side with the most vertices
"wins"; In this example the left side has 8 vertices for the embankment whilst the right side has 1, therefore the majority of this feature
was on the left bank and will be assigned "L" for Left Bank.
Features that are on islands or loops within the river network are tagged "I" for island. In this example
the bank reinforcement is occurring on the right bank of the island but the left side of the channel. To
avoid confusion these features are tagged island.
Features near tributary junctions, when exploded out into their constituent vertices may identify incoming tributaries due their proximity. It is recommended that if your data tends to be located near tributary junctions then you should review the output table to ensure features were assigned the correct bank side. You can quickly identify such features as PerSide is unlikely to be 100%.
This polygon, representing flood storage area, was tagged correctly as being on the Left bank,
but PerSide in the output table returned 75% on left. The reason for this is that the bottom right
vertex was closer to the right side of an incoming tributary.
You can choose to process a subset of your bank side data if a selection exists and you have ticked on Use only selected bank side features.
If a selection exists on the river network this is cleared.
Optionally, if your input bank side layer is either polyline or polygon then by providing an output location and name the vertices are written out as a point dataset tagged with the original site ID. This dataset is purely to help you understand or visualise why RivEX assigned a specific bank side. This dataset is not maintained in the RivEX Settings file.
If RivEX discovers that your input feature has NULL geometry then it will tag it as "N" and set all other output fields to -1.
It is possible for RivEX to fail to identify which bank side a feature is on and tag it as "X" for indeterminate. This can happen under a variety of scenarios, examples are given in the table below:
These 3 crosses represent bridges mapped beyond the limits of the river network. The upper limit of the headwater streams is the nearest location on the polyline to test if the bridge was on the left or right bank side. You cannot test bank side against a single point location, you require a polyline edge to test, hence these feature are tagged "X" for indeterminate. |
|
|
|
|
Optional Tasks
- Join output table field to bank side layer - Tick this on and RivEX will join the output table, permanently transferring the fields to the input bank side layer.
- Add attribute index- Tick this on and RivEX will create an index for the SiteID field in the output Table, this will improve any query/join performance using this field.
- Densify geometry - Tick this on and RivEX will densify the geometry before exploding it out into its constituent vertices. RivEX will insert new vertices into polylines/polygons at 10% steps along the length of the geometry. If your bank side data is a point layer, then densify has no effect. You might want to check this option on if your bank side features are short lines composed of two vertices. Such geometry will likely by identified indeterminate. Inserting more vertices will help resolve this scenario.
A 2-vertex bank feature is identified as indeterminate as one end is identifying a left bank as the closest, the other a right bank on a short tributary. |
Same feature but with densify geometry checked on. With more vertices RivEX is able to correctly identify that the feature is on the LEFT bank |
- Save bank side vertices to Feature Class - If input bank side layer is either polyline or polygon then this option enables. Choose a location and name for the output point dataset and the vertices of the features are written to the Feature Class.
Parameters
Name |
Help |
Data type |
River Network |
The river network used to determine bank side. Any existing selection on the network will be cleared before processing. A network layer with joins will be rejected by this tool. The network needs to be attributed with the RivEX field Loop ID. It is strongly recommended you use a version of your river network stored in a file geodatabase. |
Feature Layer |
Bank side layer |
The bank side features you wish to determine which bank side they are on. This layer can be either point, polyline or polygon geometry. In-memory and Multipoint layers are not accepted as valid input. This layer must be in the same coordinate system as the river network. |
Feature Layer |
Bank side ID field |
A numeric field uniquely identifying the bank feature. This field must contain unique numbers and cannot be the ObjectID field. |
Field |
Use only selected bank features |
Controls if selections are honoured or cleared.
|
Boolean |
Output table name |
The output table name for your bank side data. You do not have control over the location where this table is created, RivEX controls that, but you can decide its name. The table name must be a geodatabase compliant name, so must not have spaces, other unusual characters or start with a number. Output will be stored in fGDB_Sampling.gdb in the RivEX Workspace Output folder. |
String |
Join output table fields to bank side layer |
Optional task that joins the output table fields permanently to the input bank side feature dataset.
|
Boolean |
Add an attribute index to output |
An optional task indicating if RivEX will create an attribute index for the Site ID field in the output table.
If you plan to join or relate data then it is STRONGLY recommended you create attribute indices for the output; an index can significantly speed up query operations. |
Boolean |
Densify geometry |
An optional task indicating RivEX will densify the geometry before exploding it out into its constituent vertices. RivEX will insert new vertices into polylines/polygons at 10% steps along the length of the geometry.
You might want to check this option on if your bank side features are short lines composed of two vertices. Such geometry will likely be identified as indeterminate. Inserting more vertices will help resolve this scenario. |
Boolean |
Save bank side vertices to Feature Class |
This is the full path to a point feature class chosen by the user. If this is set then the vertices extracted from the input geometries are written to this dataset. Only bank side data that is either polyline or polygon offer this export option. This dataset is not maintained by RivEX and output will overwrite datasets of the same name. |
Boolean |
Outputs
The output table can be given a name but you have no control over where it is stored, this would be in the file geodatabase in the output folder ..\RivEX_Workspace\Outputs\fGDB_Sampling.gdb.
The output table contains the following fields:
Field |
Description |
SiteID |
The unique bank side ID. |
BankSide |
A single character identifying which bank side the majority of the feature was on.
|
PolylineID |
The polyline ID that the feature was tested against. If a feature was linear (e.g. an embankment) and tracked alongside multiple polylines, then only the first polyline is reported. |
PerSide |
The percentage that the majority of the features vertices were for the determined side. For example a single point is 100% on one side, a polyline that was composed of 3 vertices but 1 was on the opposite side of the polyline due to poor digitising would return 66% for the side that the other 2 vertices were on. A PerSide of -1 indicates that the point from a point layer for the bank side data intersected the centreline and was not left or right of the line. PerSide is meant to give you a sense of just how much of the feature was on the bank side that RivEX determined. |
NumVert |
The number of vertices the feature was composed of. If you had checked on the densify option then this value includes the extract vertices inserted into the geometry. |
If your bank side data was a polyline or polygon dataset then you have the option to export the vertices of the features to a separate point dataset. You provide a full path to this output Feature Class, but be aware this is not a dataset that is recorded in the RivEX settings file.
The optional output point Feature Class contains a single fields:
Field |
Description |
SiteID |
The ID of the bank side feature that the point came from. For example the bank feature was a polyline numbered 44 and was composed of 12 vertices. You would see in this output Feature Class 12 points each with a site ID value of 44. |
If you have selected the optional processing task, add attribute index, then the SiteID field in the output table will be indexed. An index can significantly speed up query operations such as joins or relates.
Warnings
Features when exploded out into their constituent vertices may identify incoming tributaries due their proximity. It is recommended that if your data tends to be located near tributary junctions then you should review the output table to ensure features were assigned the correct bank side.
A limitation of this tool run in a script is that it only accepts feature classes for the site layer. It will fail with inputs as layers with/without selections. If you need to process data with selections you need to use the tool directly from the toolbox or python console, more details here.
With the release of ArcGIS Pro 3.2.1 a switch control appears on parameters that accept tables\feature classes, do not interact with it! More advice here.
Limitations
- The bank side data cannot be a in-memory layer.
- If bank side data are points then it must be a simple point feature class, multi-point data is not allowed.
- Bank side data must be in the same coordinate system as the river network.
- The bank side layer will be rejected if there is a join on the layer.
Code sample
A minimum code example showing how to call this tool in a python script. This can be run in console or your preferred IDE. If you right click on the tool in the RivEX toolbox and select properties you can view parameter order.
import arcpy
import collections
# Import RivEX toolbox
arcpy.ImportToolbox(r"C:\RivEX_ArcPro\RivEX.atbx")
# Allow overwrite
arcpy.env.overwriteOutput = True
try:
# Input river Feature Class
fcRivers = r"C:\RivEX_ArcPro\Demo_Data\AlaskanNHDSample.shp"
# Linear assets Feature Class
fcAssets = r"C:\RivEX_ArcPro\Demo_Data\LinearAssets.shp"
# The output points FeatureClass
fcPoints = r"c:\Scratch\AssetVertices.shp"
# Run RivEX tool, Identify bank side. We are not joining fields, densifying geometry or adding an index.
res = arcpy.scrBankSide_RivEX(fcRivers, fcAssets, "AssetID", False, "tblBankSide", False, False, False, fcPoints)
# The bank side table, a derived output
tblBankSide = res.getOutput(0)
# Check if points exists
if arcpy.Exists(fcPoints):
# Return a count of number of vertices extracted
res = arcpy.GetCount_management(fcPoints)
n = int(res.getOutput(0))
print("Number of vertices extracted = " + str(n))
# Count number of features on Left and Right bank
lstSide = list()
with arcpy.da.SearchCursor(tblBankSide, "BankSide", "BankSide IN ('L', 'R')") as cursor:
for row in cursor:
lstSide.append(row[0])
co = collections.Counter(lstSide)
print("Number of assets on the left bank = " + str(co['L']))
print("Number of assets on the right bank = " + str(co['R']))
except arcpy.ExecuteError:
print("FAILED to identify bank sides!")