Ensure DEB chart path covers full day

This commit is contained in:
2569718930@qq.com
2026-05-17 19:34:42 +08:00
parent 1ab10a9c90
commit 38ac9844c1
2 changed files with 34 additions and 7 deletions
@@ -69,6 +69,15 @@ export function runTests() {
ankaraChartData?.datasets.debSeries.some((point) => point.labelTime === "13:00"),
"Ankara chart should build the DEB original path from MGM hourly data when Open-Meteo hourly is unavailable",
);
assert(
ankaraChartData?.datasets.debSeries.length === 48,
"DEB original path must cover the full 00:00-23:30 chart day even when city hourly data is partial",
);
assert(
ankaraChartData?.datasets.debSeries.some((point) => point.labelTime === "00:00") &&
ankaraChartData?.datasets.debSeries.some((point) => point.labelTime === "23:30"),
"DEB original path must include both start-of-day and end-of-day points",
);
assert(
ankaraChartData?.datasets.calibratedFutureSeries.length,
"Ankara chart should still expose a calibrated path when observation points exist",
+25 -7
View File
@@ -119,6 +119,25 @@ function buildObservationPoints(items: Array<{ time?: string; temp?: number | nu
.filter((point): point is { labelTime: string; x: number; y: number } => point != null);
}
function fillTemperaturePathForFullDay(
times: string[],
values: Array<number | null>,
) {
if (!times.length) return values;
const hasAnyValue = values.some((value) => value != null && Number.isFinite(value));
if (!hasAnyValue) return values;
return times.map((time, index) => {
const value = values[index];
if (value != null && Number.isFinite(value)) return value;
const minute = hmToMinutes(time);
if (minute == null) return null;
const interpolated = interpolateSeriesAtMinutes(times, values, minute);
return interpolated != null && Number.isFinite(interpolated)
? interpolated
: null;
});
}
function clampTemperatureDelta(value: number, min = -4, max = 4) {
return Math.min(Math.max(value, min), max);
}
@@ -408,12 +427,10 @@ export function getTemperatureChartData(
const hh = String(h).padStart(2, "0");
times.push(`${hh}:00`);
temps.push(getHourTemp(h));
if (h < 23) {
const a = getHourTemp(h);
const b = getHourTemp(h + 1);
times.push(`${hh}:30`);
temps.push(a != null && b != null ? Number((a + (b - a) * 0.5).toFixed(1)) : a ?? b);
}
const a = getHourTemp(h);
const b = h < 23 ? getHourTemp(h + 1) : null;
times.push(`${hh}:30`);
temps.push(a != null && b != null ? Number((a + (b - a) * 0.5).toFixed(1)) : a ?? b);
}
const suppressAnkaraMgmObservation = isTurkishMgmCity(detail);
@@ -431,7 +448,8 @@ export function getTemperatureChartData(
const debMax = detail.deb?.prediction;
const offset =
debMax != null && omMax != null ? Number(debMax) - Number(omMax) : 0;
const debTemps = temps.map((temp) =>
const debBaseTemps = fillTemperaturePathForFullDay(times, temps);
const debTemps = debBaseTemps.map((temp) =>
temp != null && Number.isFinite(temp)
? Number((temp + offset).toFixed(1))
: null,