This Processing Script is made available under the CC-0 license.
Headwater Catchments
# -*- coding: utf-8 -*-
"""
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************
"""
from pcraster import (
readmap,
setclone,
streamorder,
uniqueid,
nominal,
catchment,
accuflux,
cellarea,
defined,
areamaximum,
ifthen,
boolean,
report
)
from qgis import processing
from qgis.PyQt.QtCore import QCoreApplication
from qgis.PyQt.QtCore import QCoreApplication, QVariant
from qgis.core import (
QgsProcessingAlgorithm,
QgsProcessingParameterRasterLayer,
QgsProcessingParameterCrs,
QgsProcessingParameterNumber,
QgsProcessingParameterRasterDestination)
#from pcraster_tools.processing.algorithm import PCRasterAlgorithm
class HeadWaterCatchmentAlgorithm(QgsProcessingAlgorithm):
INPUT_LDD = 'INPUT1'
INPUT_THRESHOLD_MIN = 'INPUT2'
INPUT_SIZE = 'INPUT3'
OUTPUT_RASTER = 'OUTPUT'
def tr(self, string):
"""
Returns a translatable string with the self.tr() function.
"""
return QCoreApplication.translate('Processing', string)
def createInstance(self):
return HeadWaterCatchmentAlgorithm()
def name(self):
"""
Returns the algorithm name, used for identifying the algorithm. This
string should be fixed for the algorithm, and must not be localised.
The name should be unique within each provider. Names should contain
lowercase alphanumeric characters only and no spaces or other
formatting characters.
"""
return 'headwatercatchment'
def displayName(self):
"""
Returns the translated algorithm name, which should be used for any
user-visible display of the algorithm name.
"""
return self.tr('Headwater Catchment')
def group(self):
"""
Returns the name of the group this algorithm belongs to. This string
should be localised.
"""
return self.tr('PCRaster User Scripts')
def groupId(self):
"""
Returns the unique ID of the group this algorithm belongs to. This
string should be fixed for the algorithm, and must not be localised.
The group id should be unique within each provider. Group id should
contain lowercase alphanumeric characters only and no spaces or other
formatting characters.
"""
return 'pcrasteruser'
def shortHelpString(self):
"""
Returns a localised short helper string for the algorithm. This string
should provide a basic description about what the algorithm does and the
parameters and outputs associated with it..
"""
return self.tr(
"""Calculates Headwater Catchments of a specificied area
Parameters:
* <b>Input Flow Direction Layer (LDD) layer</b> (required) - ldd raster layer
* <b>Input Minimum Strahler Order</b> - integer number of minimum Strahler order to be considered as stream network. Calculated from a raster strahler order
* <b>Input maximum catchment size</b> - size in square kilometers
* <b>Output Headwater Catchments layer</b> (required) - nominal raster layer
"""
)
def initAlgorithm(self, config=None):
"""
Here we define the inputs and output of the algorithm, along
with some other properties.
"""
self.addParameter(
QgsProcessingParameterRasterLayer(
self.INPUT_LDD,
self.tr('LDD layer')
)
)
self.addParameter(
QgsProcessingParameterNumber(
self.INPUT_THRESHOLD_MIN, 'Minimum Strahler Order', type=QgsProcessingParameterNumber.Integer, minValue=1, maxValue=100, defaultValue=4))
self.addParameter(
QgsProcessingParameterNumber(
self.INPUT_SIZE, 'Maximum catchment size (km2)', type=QgsProcessingParameterNumber.Double, minValue=1, maxValue=100, defaultValue=1))
self.addParameter(
QgsProcessingParameterRasterDestination(
self.OUTPUT_RASTER,
self.tr("Output Headwater Catchments Raster Layer")
)
)
def processAlgorithm(self, parameters, context, feedback):
input_ldd = self.parameterAsRasterLayer(parameters, self.INPUT_LDD, context)
input_threshold_min = self.parameterAsInt(parameters, self.INPUT_THRESHOLD_MIN, context)
input_size = self.parameterAsInt(parameters, self.INPUT_SIZE, context)
input_size_sqm = input_size * 1000000
# make sure that a mask (clone) is defined for this tool
setclone(input_ldd.dataProvider().dataSourceUri())
ldd = readmap(input_ldd.dataProvider().dataSourceUri())
# calculate flow accumulation
flow_accumulation = accuflux(ldd,1)
# calculate stream and stream orders based on minimum threshold
strahler = streamorder(ldd)
stream_with_strahler = ifthen(strahler >= input_threshold_min,strahler)
stream = defined(stream_with_strahler)
# define upstream surface area for headwater streams
headwater_catchment_area = ifthen(stream,flow_accumulation * cellarea())
# calculate catchments with max area
headwater_max_catchment_area = ifthen(headwater_catchment_area <= input_size_sqm,headwater_catchment_area)
max_cell = ifthen(headwater_max_catchment_area == areamaximum(headwater_max_catchment_area,strahler),boolean(1))
catchments = catchment(ldd,nominal(uniqueid(max_cell)))
outputFilePath = self.parameterAsOutputLayer(parameters, self.OUTPUT_RASTER, context)
report(catchments,outputFilePath)
results = {}
results[self.OUTPUT_RASTER] = outputFilePath
return results
The script delineates the headwater catchments of a specified maximum size (default 1 km2). This can be useful for identifying areas for water management practices. Headwaters are calculated using a minimum Strahler order threshold, based on a raster Strahler order calculation. If the result shows only zeros, the combination of maximum size and Strahler order threshold did not result headwater catchments.
Great, thank you very much!
Reviewed by gabrieldeluca 6 days, 20 hours ago
This Processing Script is made available under the CC-0 license.