Boring changes
This commit is contained in:
parent
cfaf58dfba
commit
920119ff48
32 changed files with 912 additions and 88 deletions
|
|
@ -57,6 +57,14 @@ import {
|
|||
isTenureFeatureName,
|
||||
isTenureFilterName,
|
||||
} from './tenure-filter';
|
||||
import {
|
||||
COUNCIL_FILTER_NAME,
|
||||
createCouncilFilterKey,
|
||||
getCouncilFeatureName,
|
||||
getCouncilWindow,
|
||||
isCouncilFeatureName,
|
||||
isCouncilFilterName,
|
||||
} from './council-filter';
|
||||
import {
|
||||
POI_DISTANCE_FILTER_NAME,
|
||||
TRANSPORT_DISTANCE_FILTER_NAME,
|
||||
|
|
@ -77,6 +85,7 @@ import {
|
|||
colorOpacityToPercent,
|
||||
normalizeColorOpacity,
|
||||
} from './color-opacity';
|
||||
import { DEFAULT_LISTINGS_MODE, LISTINGS_MODES, type ListingsMode } from './listings';
|
||||
|
||||
const POI_NONE_PARAM = '__none';
|
||||
const CRIME_TYPES_NONE_PARAM = '__none';
|
||||
|
|
@ -94,6 +103,8 @@ export interface UrlState {
|
|||
crimeTypes?: Set<string>;
|
||||
basemap: BasemapId;
|
||||
colorOpacity: number;
|
||||
/** Which slice of the live for-sale listings to render (new-build only, etc.). */
|
||||
listings: ListingsMode;
|
||||
tab: 'properties' | 'area';
|
||||
travelTime?: TravelTimeInitial;
|
||||
postcode?: string;
|
||||
|
|
@ -109,6 +120,7 @@ function parseFilters(params: URLSearchParams): FeatureFilters {
|
|||
const ethnicityParams = params.getAll('ethnicity');
|
||||
const qualificationParams = params.getAll('qualification');
|
||||
const tenureParams = params.getAll('tenure');
|
||||
const councilParams = params.getAll('council');
|
||||
const amenityDistanceParams = params.getAll('amenityDistance');
|
||||
const transportDistanceParams = params.getAll('transportDistance');
|
||||
const amenityCount2KmParams = params.getAll('amenityCount2km');
|
||||
|
|
@ -122,6 +134,7 @@ function parseFilters(params: URLSearchParams): FeatureFilters {
|
|||
ethnicityParams.length === 0 &&
|
||||
qualificationParams.length === 0 &&
|
||||
tenureParams.length === 0 &&
|
||||
councilParams.length === 0 &&
|
||||
amenityDistanceParams.length === 0 &&
|
||||
transportDistanceParams.length === 0 &&
|
||||
amenityCount2KmParams.length === 0 &&
|
||||
|
|
@ -243,6 +256,20 @@ function parseFilters(params: URLSearchParams): FeatureFilters {
|
|||
filters[createTenureFilterKey(featureName, index)] = [min, max];
|
||||
});
|
||||
|
||||
councilParams.forEach((entry, index) => {
|
||||
const parts = entry.split(':');
|
||||
if (parts.length < 3) return;
|
||||
const featureName = parts.slice(0, -2).join(':');
|
||||
const min = Number(parts[parts.length - 2]);
|
||||
const max = Number(parts[parts.length - 1]);
|
||||
// getCouncilWindow recognises all three pill columns, incl. the shared
|
||||
// "% Social rent" (which isCouncilFeatureName excludes from bare folding).
|
||||
if (getCouncilWindow(featureName) == null || isNaN(min) || isNaN(max)) {
|
||||
return;
|
||||
}
|
||||
filters[createCouncilFilterKey(featureName, index)] = [min, max];
|
||||
});
|
||||
|
||||
const parsePoiParams = (entries: string[], filterName: PoiFilterName, startIndex: number) => {
|
||||
entries.forEach((entry, index) => {
|
||||
const parts = entry.split(':');
|
||||
|
|
@ -295,6 +322,7 @@ export function parseUrlState(): UrlState {
|
|||
overlays: new Set(DEFAULT_OVERLAY_IDS),
|
||||
basemap: 'standard',
|
||||
colorOpacity: DEFAULT_COLOR_OPACITY,
|
||||
listings: DEFAULT_LISTINGS_MODE,
|
||||
tab: 'area',
|
||||
};
|
||||
|
||||
|
|
@ -363,6 +391,13 @@ export function parseUrlState(): UrlState {
|
|||
}
|
||||
}
|
||||
|
||||
// Listings mode: which slice of the for-sale listings is shown. Absent means
|
||||
// the default ('all'); an explicit value survives a reload.
|
||||
const listings = params.get('listings');
|
||||
if (listings && (LISTINGS_MODES as readonly string[]).includes(listings)) {
|
||||
result.listings = listings as ListingsMode;
|
||||
}
|
||||
|
||||
// Tab: full name
|
||||
const tab = params.get('tab');
|
||||
if (tab === 'properties' || tab === 'area') {
|
||||
|
|
@ -436,7 +471,8 @@ export function stateToParams(
|
|||
basemap?: BasemapId,
|
||||
selectedCrimeTypes?: Set<string>,
|
||||
selectedPostcode?: string,
|
||||
colorOpacity?: number
|
||||
colorOpacity?: number,
|
||||
listingsMode?: ListingsMode
|
||||
): URLSearchParams {
|
||||
const params = new URLSearchParams();
|
||||
|
||||
|
|
@ -500,6 +536,15 @@ export function stateToParams(
|
|||
continue;
|
||||
}
|
||||
|
||||
// After tenure: a "Council housing:" key never matches isTenureFilterName,
|
||||
// and a bare "% Social rent" is handled by the tenure branch above.
|
||||
const councilFeatureName = getCouncilFeatureName(name);
|
||||
if (councilFeatureName && isCouncilFilterName(name)) {
|
||||
const [min, max] = value as [number, number];
|
||||
params.append('council', `${councilFeatureName}:${min}:${max}`);
|
||||
continue;
|
||||
}
|
||||
|
||||
const amenityDistanceFeatureName = getPoiDistanceFeatureName(name);
|
||||
if (amenityDistanceFeatureName && isPoiDistanceFilterName(name)) {
|
||||
const [min, max] = value as [number, number];
|
||||
|
|
@ -577,6 +622,12 @@ export function stateToParams(
|
|||
}
|
||||
}
|
||||
|
||||
// Emit the listings mode only when it deviates from the default, matching the
|
||||
// "only serialize non-default" convention above (keeps default URLs clean).
|
||||
if (listingsMode && listingsMode !== DEFAULT_LISTINGS_MODE) {
|
||||
params.set('listings', listingsMode);
|
||||
}
|
||||
|
||||
// Travel time: repeated `tt` params
|
||||
if (travelTimeEntries) {
|
||||
for (const entry of dedupeTravelTimeEntries(travelTimeEntries)) {
|
||||
|
|
@ -612,6 +663,7 @@ export function summarizeParams(queryString: string): string {
|
|||
const ethnicityParams = params.getAll('ethnicity');
|
||||
const qualificationParams = params.getAll('qualification');
|
||||
const tenureParams = params.getAll('tenure');
|
||||
const councilParams = params.getAll('council');
|
||||
const amenityDistanceParams = params.getAll('amenityDistance');
|
||||
const transportDistanceParams = params.getAll('transportDistance');
|
||||
const amenityCount2KmParams = params.getAll('amenityCount2km');
|
||||
|
|
@ -625,6 +677,7 @@ export function summarizeParams(queryString: string): string {
|
|||
ethnicityParams.length > 0 ||
|
||||
qualificationParams.length > 0 ||
|
||||
tenureParams.length > 0 ||
|
||||
councilParams.length > 0 ||
|
||||
amenityDistanceParams.length > 0 ||
|
||||
transportDistanceParams.length > 0 ||
|
||||
amenityCount2KmParams.length > 0 ||
|
||||
|
|
@ -640,6 +693,7 @@ export function summarizeParams(queryString: string): string {
|
|||
if (isEthnicityFeatureName(name)) return ETHNICITIES_FILTER_NAME;
|
||||
if (isQualificationFeatureName(name)) return QUALIFICATIONS_FILTER_NAME;
|
||||
if (isTenureFeatureName(name)) return TENURE_FILTER_NAME;
|
||||
if (isCouncilFeatureName(name)) return COUNCIL_FILTER_NAME;
|
||||
const poiFilterName = getPoiFilterName(name);
|
||||
if (poiFilterName) return poiFilterName;
|
||||
return name;
|
||||
|
|
@ -667,6 +721,9 @@ export function summarizeParams(queryString: string): string {
|
|||
for (let i = 0; i < tenureParams.length; i++) {
|
||||
filterNames.push(TENURE_FILTER_NAME);
|
||||
}
|
||||
for (let i = 0; i < councilParams.length; i++) {
|
||||
filterNames.push(COUNCIL_FILTER_NAME);
|
||||
}
|
||||
for (let i = 0; i < amenityDistanceParams.length; i++) {
|
||||
filterNames.push(POI_DISTANCE_FILTER_NAME);
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue