feat: complete Wallonia land cover and terrain sources
This commit is contained in:
@@ -45,6 +45,7 @@ const ANALYTICAL_SOURCE_NAMES = new Set([
|
||||
'agentschap_landbouw_zeevisserij_agricultural_parcels',
|
||||
'dov_soil_map',
|
||||
'digitaal_vlaanderen_dhmv',
|
||||
'spw_terrain',
|
||||
'vmm_flood_hazard',
|
||||
'vmm_vha_bathymetry_profiles',
|
||||
])
|
||||
|
||||
@@ -100,7 +100,7 @@ export function SourceCatalogPanel({
|
||||
const buildingsRegisterDatasets = ready.filter(
|
||||
(dataset) => dataset.source_name === 'digitaal_vlaanderen_buildings_addresses_register',
|
||||
)
|
||||
const dhmvDatasets = ready.filter((dataset) => dataset.source_name === 'digitaal_vlaanderen_dhmv')
|
||||
const dhmvDatasets = ready.filter((dataset) => ['digitaal_vlaanderen_dhmv', 'spw_terrain'].includes(dataset.source_name ?? ''))
|
||||
const floodHazardDatasets = ready.filter((dataset) => dataset.source_name === 'vmm_flood_hazard')
|
||||
const bathymetryProfileDatasets = ready.filter(
|
||||
(dataset) => dataset.source_name === 'vmm_vha_bathymetry_profiles',
|
||||
|
||||
@@ -310,11 +310,11 @@ export function DetectionLab({
|
||||
<p className="ai-quality-guidance">
|
||||
{detectionQualityInterpretation(selectedOperatorProfile?.f1)}
|
||||
</p>
|
||||
{selectedOperatorProfile && !selectedOperatorProfile.nationallyValidated ? (
|
||||
{selectedOperatorProfile && selectedDetectionModel?.nationally_validated !== true ? (
|
||||
<div className="result-state result-state-warning" role="status">
|
||||
<strong>Nog niet nationaal gevalideerd</strong>
|
||||
<p>
|
||||
Dit model is operationeel voor gecontroleerde beeldanalyse, maar de gemeten kwaliteit geldt alleen voor {selectedOperatorProfile.validationScope}.
|
||||
Dit model is operationeel voor gecontroleerde beeldanalyse, maar de gemeten kwaliteit geldt alleen voor {selectedDetectionModel?.validation_scope ?? selectedOperatorProfile.validationScope}.
|
||||
Resultaten elders in Belgie of op zee vereisen lokale referentiedata en QA voordat ze als betrouwbaar kunnen worden vrijgegeven.
|
||||
</p>
|
||||
</div>
|
||||
|
||||
@@ -11,7 +11,6 @@ export interface DetectionOperatorProfile {
|
||||
positiveSampleCount: number
|
||||
maxBackgroundDetections: number
|
||||
validationScope: string
|
||||
nationallyValidated: boolean
|
||||
description: string
|
||||
limitationMessage: string
|
||||
}
|
||||
@@ -30,7 +29,6 @@ export const DETECTION_OPERATOR_PROFILES: DetectionOperatorProfile[] = [
|
||||
positiveSampleCount: 7,
|
||||
maxBackgroundDetections: 0,
|
||||
validationScope: '7 onafhankelijke testgebieden in Mol en de Kempen',
|
||||
nationallyValidated: false,
|
||||
description:
|
||||
'Aanbevolen profiel met een evenwicht tussen gevonden en gemiste kleine gebouwen, opnieuw gemeten over zeven onafhankelijke testgebieden in Mol en de Kempen.',
|
||||
limitationMessage:
|
||||
@@ -49,7 +47,6 @@ export const DETECTION_OPERATOR_PROFILES: DetectionOperatorProfile[] = [
|
||||
positiveSampleCount: 7,
|
||||
maxBackgroundDetections: 0,
|
||||
validationScope: '7 onafhankelijke testgebieden in Mol en de Kempen',
|
||||
nationallyValidated: false,
|
||||
description: 'Voorgaand profiel voor controles waarbij minder foutieve vondsten belangrijker zijn dan maximale dekking.',
|
||||
limitationMessage:
|
||||
'De lege-achtergrondtest is geslaagd. Dit profiel vindt minder onterechte objecten, maar mist meer kleine gebouwen dan het aanbevolen profiel.',
|
||||
@@ -67,7 +64,6 @@ export const DETECTION_OPERATOR_PROFILES: DetectionOperatorProfile[] = [
|
||||
positiveSampleCount: 7,
|
||||
maxBackgroundDetections: 0,
|
||||
validationScope: '7 onafhankelijke testgebieden in Mol en de Kempen',
|
||||
nationallyValidated: false,
|
||||
description: 'Profiel met hoge precisie voor controles waarbij zo weinig mogelijk foutieve vondsten zwaarder wegen dan volledige dekking.',
|
||||
limitationMessage:
|
||||
'Goedgekeurd na de lege-achtergrondtest. Resultaten in dun bebouwde context blijven altijd controlebewijs en geen automatische waarheid.',
|
||||
|
||||
@@ -108,7 +108,7 @@ function productSupportsSelection(product: OnDemandMapProduct, bbox: VectorSelec
|
||||
const scale = selectionAnalysisScale(bbox)
|
||||
if (scale === 'overview') return false
|
||||
const dimensions = selectionDimensions(bbox)
|
||||
if (product.kind === 'dhmv' || product.kind === 'flood_hazard') {
|
||||
if (product.kind === 'dhmv' || product.kind === 'spw_terrain' || product.kind === 'flood_hazard') {
|
||||
return dimensions.areaSquareMetres <= 280_000_000
|
||||
}
|
||||
if (product.kind === 'thematic_raster' || product.kind === 'walous') {
|
||||
@@ -338,7 +338,7 @@ function datasetAvailabilityLabel(
|
||||
): string {
|
||||
const partitionCount = partitions.length
|
||||
const regionalSuffix = partitionCount > 1 ? ` · ${partitionCount} gemeenten` : ''
|
||||
if (dataset.dataset_type === 'raster' && dataset.source_name === 'digitaal_vlaanderen_dhmv') {
|
||||
if (dataset.dataset_type === 'raster' && ['digitaal_vlaanderen_dhmv', 'spw_terrain'].includes(dataset.source_name ?? '')) {
|
||||
const resolution = Number(dataset.source_metadata?.['analysis_resolution_m'])
|
||||
return `${Number.isFinite(resolution) ? `${resolution.toLocaleString('nl-BE')} m` : 'Raster'} hoogtegrid${regionalSuffix}`
|
||||
}
|
||||
@@ -416,7 +416,7 @@ function datasetMatchesTheme(dataset: DatasetCreateResponse, theme: DataTheme):
|
||||
if (dataset.source_name === 'spw_bathymetry') {
|
||||
return theme.id === 'bathymetry'
|
||||
}
|
||||
if (dataset.source_name === 'digitaal_vlaanderen_dhmv') {
|
||||
if (['digitaal_vlaanderen_dhmv', 'spw_terrain'].includes(dataset.source_name ?? '')) {
|
||||
return theme.id === 'elevation'
|
||||
}
|
||||
if (dataset.source_name === 'department_omgeving_thematic_raster') {
|
||||
@@ -444,7 +444,7 @@ function datasetMatchesTheme(dataset: DatasetCreateResponse, theme: DataTheme):
|
||||
function isPartitionedRaster(dataset: DatasetCreateResponse | null | undefined): boolean {
|
||||
return Boolean(
|
||||
dataset?.dataset_type === 'raster'
|
||||
&& ['digitaal_vlaanderen_dhmv', 'vmm_flood_hazard'].includes(dataset.source_name ?? ''),
|
||||
&& ['digitaal_vlaanderen_dhmv', 'spw_terrain', 'vmm_flood_hazard'].includes(dataset.source_name ?? ''),
|
||||
)
|
||||
}
|
||||
|
||||
@@ -544,6 +544,7 @@ function pickThemeDataset(
|
||||
(dataset.source_name === 'spw_walous_land_cover' ? 5_000_000 : 0) +
|
||||
(dataset.source_name === 'digitaal_vlaanderen_buildings_addresses_register' ? 5_000_000 : 0) +
|
||||
(dataset.source_name === 'digitaal_vlaanderen_dhmv' ? 5_000_000 : 0) +
|
||||
(dataset.source_name === 'spw_terrain' ? 5_000_000 : 0) +
|
||||
(dataset.source_name === 'vmm_flood_hazard' ? 5_000_000 : 0) +
|
||||
(dataset.source_name === 'vmm_vha_bathymetry_profiles' ? 5_000_000 : 0) +
|
||||
(dataset.source_name === 'spw_bathymetry' ? 5_100_000 : 0) +
|
||||
@@ -873,6 +874,7 @@ export function MapWorkspace({
|
||||
selectedCoverageZones?.includes('flanders')
|
||||
|| (!selectedCoverageZones && activeScopeProject?.name === FLANDERS_WORKSPACE_PROJECT_NAME),
|
||||
)
|
||||
const walloniaScopeSelected = Boolean(selectedCoverageZones?.includes('wallonia'))
|
||||
const {
|
||||
themeInsights,
|
||||
themeInsightsLoading: themeResultsLoading,
|
||||
@@ -992,6 +994,14 @@ export function MapWorkspace({
|
||||
&& datasetCoversSelectedArea(dataset, selectedMapAreaId, selectedMapArea?.name, regionalScopeSelected),
|
||||
) ?? null
|
||||
}
|
||||
if (walloniaScopeSelected && officialMapProducts.spwTerrain.some((product) => product.configured)) {
|
||||
result.elevation = availableMapDatasets.find(
|
||||
(dataset) =>
|
||||
dataset.source_name === 'spw_terrain'
|
||||
&& datasetProductKey(dataset) === 'spw_mnt_1m_2021_2022'
|
||||
&& datasetCoversSelectedArea(dataset, selectedMapAreaId, selectedMapArea?.name, regionalScopeSelected),
|
||||
) ?? null
|
||||
}
|
||||
if (flandersScopeSelected && officialMapProducts.thematic.length > 0) {
|
||||
for (const product of officialMapProducts.thematic) {
|
||||
if (!result[product.theme]) {
|
||||
@@ -1021,6 +1031,7 @@ export function MapWorkspace({
|
||||
flandersScopeSelected,
|
||||
floodHazardDatasets,
|
||||
officialMapProducts.dhmv.length,
|
||||
officialMapProducts.spwTerrain,
|
||||
officialMapProducts.floodHazard.length,
|
||||
officialMapProducts.grb,
|
||||
officialMapProducts.officialVector,
|
||||
@@ -1032,6 +1043,7 @@ export function MapWorkspace({
|
||||
selectedMapArea?.name,
|
||||
selectedMapAreaId,
|
||||
selectedCoverageZones,
|
||||
walloniaScopeSelected,
|
||||
])
|
||||
const themePartitionMap = useMemo(
|
||||
() =>
|
||||
@@ -1066,6 +1078,7 @@ export function MapWorkspace({
|
||||
effectiveZones?.includes('flanders')
|
||||
|| (!effectiveZones && activeScopeProject?.name === FLANDERS_WORKSPACE_PROJECT_NAME),
|
||||
)
|
||||
const includesWallonia = Boolean(effectiveZones?.includes('wallonia'))
|
||||
if (includesFlanders) {
|
||||
for (const product of officialMapProducts.thematic) {
|
||||
result.push({
|
||||
@@ -1161,6 +1174,21 @@ export function MapWorkspace({
|
||||
coverageZones: ['flanders'],
|
||||
})
|
||||
}
|
||||
const spwTerrainProduct = includesWallonia
|
||||
? officialMapProducts.spwTerrain.find((product) => product.configured)
|
||||
: null
|
||||
if (spwTerrainProduct) {
|
||||
result.push({
|
||||
kind: 'spw_terrain',
|
||||
productKey: spwTerrainProduct.key,
|
||||
displayName: spwTerrainProduct.display_name,
|
||||
theme: 'elevation',
|
||||
availabilityLabel: `${spwTerrainProduct.analysis_resolution_m} m analyse · ${spwTerrainProduct.acquisition_period} · automatisch bij selectie`,
|
||||
attribution: spwTerrainProduct.attribution,
|
||||
limitationMessage: spwTerrainProduct.limitation_message,
|
||||
coverageZones: spwTerrainProduct.coverage_zones,
|
||||
})
|
||||
}
|
||||
const floodProduct = includesFlanders
|
||||
? officialMapProducts.floodHazard.find(
|
||||
(product) => product.key === selectedFloodHazardProductKey,
|
||||
@@ -1319,7 +1347,7 @@ export function MapWorkspace({
|
||||
activeTheme.id === 'elevation' && selectedProjectId
|
||||
? activeThemePartitions.flatMap((dataset) => {
|
||||
const bounds = dataset.source_metadata?.['bbox_epsg4326']
|
||||
return dataset.source_name === 'digitaal_vlaanderen_dhmv'
|
||||
return ['digitaal_vlaanderen_dhmv', 'spw_terrain'].includes(dataset.source_name ?? '')
|
||||
&& Array.isArray(bounds)
|
||||
&& bounds.length === 4
|
||||
? [{
|
||||
@@ -1530,7 +1558,7 @@ export function MapWorkspace({
|
||||
const terrainReliefMetric = activeSupportingMetrics.find((metric) => metric.metric_key === 'relief_m')
|
||||
const populationDensityMetric = activeSupportingMetrics.find((metric) => metric.metric_key === 'population_density_mean_per_ha')
|
||||
const scoreMedianMetric = activeSupportingMetrics.find((metric) => metric.metric_key.endsWith('_median'))
|
||||
const activeSecondaryMetric = activeMetricUnit === 'm TAW'
|
||||
const activeSecondaryMetric = activeMetricUnit === 'm TAW' || activeMetricUnit === 'm DNG'
|
||||
? terrainReliefMetric ? `${terrainReliefMetric.metric_value.toLocaleString('nl-BE', { maximumFractionDigits: 2 })} m reliëf` : null
|
||||
: activeMetricUnit === 'inwoners'
|
||||
? populationDensityMetric ? selectionMetricLabel(populationDensityMetric) : null
|
||||
@@ -1543,7 +1571,7 @@ export function MapWorkspace({
|
||||
: null
|
||||
const activeSecondaryLabel = activeMetricUnit === 'ha'
|
||||
? 'Aandeel selectie'
|
||||
: activeMetricUnit === 'm TAW'
|
||||
: activeMetricUnit === 'm TAW' || activeMetricUnit === 'm DNG'
|
||||
? 'Reliëf'
|
||||
: activeMetricUnit === 'inwoners'
|
||||
? 'Gemiddelde dichtheid'
|
||||
@@ -2301,7 +2329,7 @@ export function MapWorkspace({
|
||||
<p className="error">{officialMapProductsError}</p>
|
||||
) : null}
|
||||
|
||||
{analysisMode === 'current' && activeTheme.id === 'elevation' && officialMapProducts.dhmv.length > 0 ? (
|
||||
{analysisMode === 'current' && activeTheme.id === 'elevation' && flandersScopeSelected && officialMapProducts.dhmv.length > 0 ? (
|
||||
<label className="geo-scope-select">
|
||||
Hoogtemodel
|
||||
<select
|
||||
@@ -2334,6 +2362,9 @@ export function MapWorkspace({
|
||||
<small>DTM meet het maaiveld; DSM bevat ook gebouwen en vegetatie.</small>
|
||||
</label>
|
||||
) : null}
|
||||
{analysisMode === 'current' && activeTheme.id === 'elevation' && walloniaScopeSelected && officialMapProducts.spwTerrain.some((product) => product.configured) ? (
|
||||
<p className="geo-data-notice">SPW MNT 2021-2022 · 1 m bron · 5 m begrensde analyse · hoogte in m DNG.</p>
|
||||
) : null}
|
||||
|
||||
{analysisMode === 'current' && activeTheme.id === 'flood_hazard' && officialMapProducts.floodHazard.length > 0 ? (
|
||||
<label className="geo-scope-select">
|
||||
|
||||
@@ -108,7 +108,7 @@ export function persistedDatasetSupportsSelection(
|
||||
const scale = selectionAnalysisScale(bbox)
|
||||
if (scale === 'overview') return false
|
||||
const dimensions = selectionDimensions(bbox)
|
||||
if (dataset.source_name === 'digitaal_vlaanderen_dhmv' || dataset.source_name === 'vmm_flood_hazard') {
|
||||
if (dataset.source_name === 'digitaal_vlaanderen_dhmv' || dataset.source_name === 'spw_terrain' || dataset.source_name === 'vmm_flood_hazard') {
|
||||
return dimensions.areaSquareMetres <= 280_000_000
|
||||
}
|
||||
if (dataset.source_name === 'department_omgeving_thematic_raster') {
|
||||
|
||||
Reference in New Issue
Block a user