- For an interactive online version click here:
+ For an interactive online version click here:
"""
diff --git a/docs/user_guide/wflow_model_setup.rst b/docs/user_guide/wflow_model_setup.rst
index 0edfed7e..c308eab5 100644
--- a/docs/user_guide/wflow_model_setup.rst
+++ b/docs/user_guide/wflow_model_setup.rst
@@ -53,9 +53,7 @@ a specific method see its documentation.
* - :py:func:`~WflowModel.setup_soilmaps`
- This component derives several (layered) soil parameters based on a database with physical soil properties using available point-scale (pedo)transfer functions (PTFs) from literature with upscaling rulesto ensure flux matching across scales.
* - :py:func:`~WflowModel.setup_rootzoneclim`
- - This component derives an estimate of the rooting depth from hydroclimatic data (as an alternative from the look-up table). The method can be applied for current conditions and future climate change conditions.
- * - :py:func:`~WflowModel.setup_hydrodem`
- - This component adds a hydrologically conditioned elevation (hydrodem) map for river and/or land local-inertial routing.
+ - This component derives an estimate of the rooting depth from hydroclimatic data (as an alternative from the look-up table). The method can be applied for current conditions and future climate change conditions.
* - :py:func:`~WflowModel.setup_outlets`
- This method sets the default gauge map based on basin outlets.
* - :py:func:`~WflowModel.setup_gauges`
diff --git a/hydromt_wflow/wflow.py b/hydromt_wflow/wflow.py
index fc46fcb2..2014f3e1 100644
--- a/hydromt_wflow/wflow.py
+++ b/hydromt_wflow/wflow.py
@@ -772,7 +772,7 @@ def setup_lulcmaps(
This component derives several wflow maps are derived based on landuse-
landcover (LULC) data.
- Currently, ``lulc_fn`` can be set to the "vito", "globcover"
+ Currently, ``lulc_fn`` can be set to the "vito", "globcover", "esa_worldcover"
or "corine", fo which lookup tables are constructed to convert lulc classses to
model parameters based on literature. The data is remapped at its original
resolution and then resampled to the model resolution using the average
@@ -1506,6 +1506,7 @@ def setup_reservoirs(
if np.all(np.isin(resattributes, gdf_org.columns)):
intbl_reservoirs = gdf_org[resattributes]
reservoir_accuracy = None
+ reservoir_timeseries = None
# else compute
else:
(
@@ -2385,6 +2386,12 @@ def write_staticmaps(self):
ds_out.rio.write_transform(self.staticmaps.raster.transform, inplace=True)
ds_out.raster.set_spatial_dims()
+ # Remove FillValue Nan for x_dim, y_dim
+ encoding = dict()
+ for v in [ds_out.raster.x_dim, ds_out.raster.y_dim]:
+ ds_out[v].attrs.pop("_FillValue", None)
+ encoding[v] = {"_FillValue": None}
+
# filename
fn_default = join(self.root, "staticmaps.nc")
fn = self.get_config("input.path_static", abs_path=True, fallback=fn_default)
@@ -2403,7 +2410,7 @@ def write_staticmaps(self):
# nodata is required for all but boolean fields
if ds_out[v].dtype != "bool":
ds_out[v] = ds_out[v].where(mask, ds_out[v].raster.nodata)
- ds_out.to_netcdf(fn)
+ ds_out.to_netcdf(fn, encoding=encoding)
# self.write_staticmaps_pcr()
def read_staticmaps_pcr(self, crs=4326, **kwargs):
@@ -2665,10 +2672,11 @@ def write_forcing(
v: {"zlib": True, "dtype": "float32", "chunksizes": chunksizes}
for v in ds.data_vars.keys()
}
- # make sure no _FillValue is written to the time dimension
+ # make sure no _FillValue is written to the time / x_dim / y_dim dimension
# For several forcing files add common units attributes to time
- ds["time"].attrs.pop("_FillValue", None)
- encoding["time"] = {"_FillValue": None}
+ for v in ["time", ds.raster.x_dim, ds.raster.y_dim]:
+ ds[v].attrs.pop("_FillValue", None)
+ encoding[v] = {"_FillValue": None}
# Check if all sub-folders in fn_out exists and if not create them
if not isdir(dirname(fn_out)):
@@ -2894,11 +2902,20 @@ def basins(self):
"""Returns a basin(s) geometry as a geopandas.GeoDataFrame."""
if "basins" in self.staticgeoms:
gdf = self.staticgeoms["basins"]
- else:
- gdf = flw.basin_shape(
- self.staticmaps, self.flwdir, basin_name=self._MAPS["basins"]
+ elif self._MAPS["basins"] in self.staticmaps:
+ gdf = (
+ self.staticmaps[self._MAPS["basins"]]
+ .raster.vectorize()
+ .set_index("value")
+ .sort_index()
)
+ gdf.index.name = self._MAPS["basins"]
self.set_staticgeoms(gdf, name="basins")
+ else:
+ self.logger.warning(
+ f"Basin map {self._MAPS['basins']} not found in staticmaps."
+ )
+ gdf = None
return gdf
@property
@@ -2974,7 +2991,7 @@ def clip_staticmaps(
)
ds_staticmaps.coords["mask"] = ds_staticmaps.raster.geometry_mask(geom)
ds_staticmaps[basins_name] = ds_staticmaps[basins_name].where(
- ds_staticmaps["mask"], self.staticmaps[basins_name].raster.nodata
+ ds_staticmaps.coords["mask"], self.staticmaps[basins_name].raster.nodata
)
ds_staticmaps[basins_name].attrs.update(
_FillValue=self.staticmaps[basins_name].raster.nodata
@@ -3001,10 +3018,16 @@ def clip_staticmaps(
# self.rivers
# now staticgeoms links to geoms which does not exist in every hydromt version
# remove when updating wflow to new objects
- basins = flw.basin_shape(
- self.staticmaps, self.flwdir, basin_name=self._MAPS["basins"]
+ # Basin shape
+ basins = (
+ self.staticmaps[basins_name]
+ .raster.vectorize()
+ .set_index("value")
+ .sort_index()
)
+ basins.index.name = basins_name
self.set_staticgeoms(basins, name="basins")
+
rivmsk = self.staticmaps[self._MAPS["rivmsk"]].values != 0
# Check if there are river cells in the model before continuing
if np.any(rivmsk):