diff --git a/static/js/weather-table.js b/static/js/weather-table.js index 81e5330..b4c1308 100644 --- a/static/js/weather-table.js +++ b/static/js/weather-table.js @@ -7,29 +7,75 @@ const WeatherTable = { return; } - const allData = [...historyData, ...forecastData]; - const sortedData = allData.sort((a, b) => new Date(a.date_time) - new Date(b.date_time)); + const showPastEl = document.getElementById('showPastForecast'); + const nowTs = Date.now(); + const future3hTs = nowTs + 3 * 60 * 60 * 1000; + const showPast = !!(showPastEl && showPastEl.checked); + const displayedForecast = forecastData.filter(item => { + const t = new Date(item.date_time).getTime(); + const isFuture3h = t > nowTs && t <= future3hTs; + const isPast = t <= nowTs; + return isFuture3h || (showPast && isPast); + }); + const taggedHistory = historyData.map(item => ({ ...item, __source: '实测' })); + const taggedForecast = displayedForecast.map(item => ({ ...item, __source: '预报' })); + const allData = [...taggedHistory, ...taggedForecast]; + const hasForecast = taggedForecast.length > 0; + const sortedData = allData.sort((a, b) => new Date(b.date_time) - new Date(a.date_time)); const tableBody = document.getElementById('tableBody'); if (!tableBody) return; tableBody.innerHTML = ''; + // 动态表头:在有预报时加入“降水概率 (%)” + const headerRow = document.getElementById('tableHeader'); + if (headerRow) { + headerRow.innerHTML = ''; + const addTh = (text) => { + const th = document.createElement('th'); + th.textContent = text; + headerRow.appendChild(th); + }; + ['时间','温度 (°C)','湿度 (%)','气压 (hPa)','风速 (m/s)','风向 (°)','雨量 (mm)'].forEach(addTh); + if (hasForecast) addTh('降水概率 (%)'); + ['光照 (lux)','紫外线'].forEach(addTh); + } + const fmt = (v, digits) => (v === null || v === undefined || v === '' || isNaN(Number(v))) ? '' : Number(v).toFixed(digits); sortedData.forEach(row => { const tr = document.createElement('tr'); - tr.innerHTML = ` - ${row.date_time || ''} - ${fmt(row.temperature, 1)} - ${fmt(row.humidity, 1)} - ${fmt(row.pressure, 1)} - ${fmt(row.wind_speed, 1)} - ${fmt(row.wind_direction, 0)} - ${fmt(row.rainfall, 2)} - ${fmt(row.light, 0)} - ${fmt(row.uv, 1)} - `; + const isForecast = row.__source === '预报'; + if (isForecast) { + tr.style.backgroundColor = 'rgba(255, 165, 0, 0.08)'; + } + const issuedBadge = (() => { + if (!isForecast) return ''; + const lead = (typeof row.lead_hours === 'number' && row.lead_hours >= 0) ? ` +${row.lead_hours}h` : ''; + const issued = row.issued_at ? new Date(String(row.issued_at).replace(' ', 'T')) : null; + const issuedStr = issued ? `${String(issued.getHours()).padStart(2,'0')}:${String(issued.getMinutes()).padStart(2,'0')}` : '-'; + return `(发布: ${issuedStr}${lead})`; + })(); + const timeCell = `${row.date_time || ''}${isForecast ? ' [预报]' : ''}${isForecast ? `
${issuedBadge}` : ''}`; + const columns = [ + `${timeCell}`, + `${fmt(row.temperature, 1)}`, + `${fmt(row.humidity, 1)}`, + `${fmt(row.pressure, 1)}`, + `${fmt(row.wind_speed, 1)}`, + `${fmt(row.wind_direction, 0)}`, + `${fmt(row.rainfall, 2)}` + ]; + if (hasForecast) { + const val = isForecast && row.precip_prob !== null && row.precip_prob !== undefined ? row.precip_prob : '-'; + columns.push(`${val}`); + } + columns.push( + `${fmt(row.light, 0)}`, + `${fmt(row.uv, 1)}` + ); + tr.innerHTML = columns.join(''); tableBody.appendChild(tr); }); diff --git a/templates/index.html b/templates/index.html index c7c8620..2e92ca3 100644 --- a/templates/index.html +++ b/templates/index.html @@ -534,7 +534,7 @@