Skip to content

Implement qswat_populate_gwflow_gis() for GIS-dependent gwflow tables#2

Merged
tadhg-moore merged 3 commits intocopilot/develop-r-package-for-qgis-pluginfrom
copilot/implement-gwflow-tables-in-r
Apr 19, 2026
Merged

Implement qswat_populate_gwflow_gis() for GIS-dependent gwflow tables#2
tadhg-moore merged 3 commits intocopilot/develop-r-package-for-qgis-pluginfrom
copilot/implement-gwflow-tables-in-r

Conversation

Copy link
Copy Markdown

Copilot AI commented Apr 19, 2026

The R package lacked GIS processing capability to populate the spatial gwflow database tables that the Python QGIS plugin generates via GWFlow.run(). This adds qswat_populate_gwflow_gis() using sf and terra to replicate that pipeline end-to-end.

New function: qswat_populate_gwflow_gis()

Accepts a project object plus paths to a conductivity shapefile, aquifer thickness raster, and optionally tile-drain / lake shapefiles. Populates:

Table Source
gwflow_zone Conductivity polygons clipped to basin
gwflow_grid Fishnet cells with elevation, thickness, zone, boundary/active status
gwflow_rivcell sf::st_intersection of streams → length per (cell, channel)
gwflow_lsucell LSU polygon intersection → area per (cell, LSU); when hruorlsu_recharge ≥ 2
gwflow_hrucell HRU polygon intersection → area per (cell, HRU); when hruorlsu_recharge is 1 or 3
gwflow_fpcell Intentionally empty — no floodplain/upslope split in rQSWATPlus
gwflow_rescell gis_water JOIN gwflow_lsucell + optional lake shapefile

Also updates gwflow_base.row_count / col_count.

Key implementation details

  • Fishnet IDs assigned in raster order (left→right, top→bottom) via O(n) column-major-to-row-major conversion — no centroid extraction needed.
  • GLHYMPS auto-detection: if logK_Ferr_ column is present, converts log10(k_intrinsic [m²]) × 100 to hydraulic conductivity in m/day; otherwise accepts any numeric column via conductivity_column.
  • NoData fill uses two focal-mean passes (3×3 then 5×5) to approximate gdal.FillNodata(maxSearchDist=5).
  • Multi-zone cells: zone assigned by mean of intersecting zone IDs, matching Python's groupby('Id').mean().
cfg     <- qswat_read_gwflow_config()
project <- qswat_setup_gwflow(project, gwflow_config = cfg)
project <- qswat_populate_gwflow_gis(
  project           = project,
  gwflow_config     = cfg,
  conductivity_file = "GLHYMPS_basin.shp",   # logK_Ferr_ auto-detected
  thickness_file    = "aquifer_thickness.tif" # cm → m via thickness_scale = 0.01
)

Tests

Eight new tests in test-gwflow.R use synthetic spatial data (1 km² square basin, flat DEM, uniform thickness raster, single GLHYMPS polygon, one stream) to verify grid dimensions, elevation/thickness values, zone K conversion, river/LSU/HRU cell counts, and recharge-mode gating (modes 1, 2, and 3).

Copilot AI and others added 3 commits April 17, 2026 04:07
… population

Agent-Logs-Url: https://github.com/limnotrack/QSWATPlus/sessions/b7944146-d389-458f-8c67-111a1b2723ee

Co-authored-by: tadhg-moore <23136262+tadhg-moore@users.noreply.github.com>
@tadhg-moore tadhg-moore marked this pull request as ready for review April 19, 2026 21:26
@tadhg-moore tadhg-moore merged commit 2e32362 into copilot/develop-r-package-for-qgis-plugin Apr 19, 2026
@tadhg-moore tadhg-moore deleted the copilot/implement-gwflow-tables-in-r branch April 19, 2026 21:26
@tadhg-moore tadhg-moore restored the copilot/implement-gwflow-tables-in-r branch April 19, 2026 22:35
@tadhg-moore
Copy link
Copy Markdown
Collaborator

@copilot can you integrate the new gwflow function with the workflow? So that they are executed if "use_gwflow" is set to True

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants