@@ -200,7 +200,7 @@ async function fetchPopulationData() {
200200
201201 for ( let element of document . getElementsByClassName ( "country-item" ) ) {
202202 const population = Object . values ( regions ( populationData . countries [ element . dataset . code ] ) ) . reduce ( ( a , b ) => a + b , 0 ) ;
203- registerTooptip ( element , `<span class="tooltip-title">${ ( population / 1e6 ) . toFixed ( 1 ) } ${ i18n . mioResidents } </span>\n` ) ;
203+ registerTooptip ( element , `<span class="tooltip-title">${ formatPopulation ( population ) } </span>\n` ) ;
204204 }
205205
206206}
@@ -293,18 +293,19 @@ function calculateDayStatistics(fromDate, toDate) {
293293 let holidayPopulationTotal = 0 ;
294294 let nationwideHolidayAnyCountry = false ;
295295 let incompleteData = new Set ( ) ;
296+ let incompleteDataPopulation = 0 ;
296297 const tooltip = [ ] ;
297298
298299 for ( const country of selectedCountries ) {
299300 const { holidays, schoolHolidays} = cachedData [ d . getFullYear ( ) ] [ country ] ;
301+ const countryName = countries . find ( c => c . code === country ) ?. name ;
300302 const regionNames = cachedData . Regions [ country ] . reduce ( ( d , e ) => ( d [ e . code ] = e . name ?. [ 0 ] ?. text , d ) , { } ) ;
301303 const relevant = [ ] ;
302304
303305 // --- Feiertage ---
304306 for ( const h of holidays ) {
305307 if ( inDateRange ( d , h . startDate , h . endDate ) ) relevant . push ( { ...h , type : i18n . publicHoliday } ) ;
306308 }
307- if ( holidays . length === 0 ) incompleteData . add ( country ) ;
308309
309310 // --- Ferien ---
310311 for ( const f of schoolHolidays ) {
@@ -313,7 +314,6 @@ function calculateDayStatistics(fromDate, toDate) {
313314 type : i18n . schoolHoliday
314315 } ) ;
315316 }
316- if ( schoolHolidays . length === 0 || maxDate ( schoolHolidays . map ( f => f . endDate ) ) < d ) incompleteData . add ( country ) ;
317317
318318 // Count population on holiday
319319 const population = regions ( populationData . countries [ country ] ) ;
@@ -355,11 +355,28 @@ function calculateDayStatistics(fromDate, toDate) {
355355 holidayPopulationTotal += holidayPopulation ;
356356 nationwideHolidayAnyCountry |= nationwideHoliday ;
357357
358+
359+ // Check for incomplete data
360+ if ( holidays . length === 0 || schoolHolidays . length === 0 || maxDate ( schoolHolidays . map ( f => f . endDate ) ) < d ) {
361+ incompleteData . add ( countryName ) ;
362+ incompleteDataPopulation += countryPopTotal ;
363+ } else {
364+ // Also check if school holidays are missing completely for any region
365+ let missing = Object . keys ( regions ( populationData . countries [ country ] ) ) . filter ( region => {
366+ const regionHolidays = schoolHolidays . filter ( h => h . nationwide || regions ( h ) ?. map ( s => s . code . split ( "-" ) . slice ( 0 , 2 ) . join ( "-" ) ) . includes ( region ) ) ;
367+ return regionHolidays . length === 0 || maxDate ( regionHolidays . map ( f => f . endDate ) ) < d ;
368+ } ) ;
369+ if ( missing . length > 0 ) {
370+ incompleteData . add ( countryName + " (" + missing . map ( r => regionNames [ r ] ) . join ( ", " ) + ")" )
371+ incompleteDataPopulation += missing . map ( r => population [ r ] ) . reduce ( ( a , b ) => a + b , 0 ) ;
372+ }
373+ }
374+
358375 // infos for tooltip
359376 if ( holidayPopulation > 0 ) {
360377 const c = countries . find ( c => c . code === country ) ;
361378 if ( selectedCountries . length > 1 ) {
362- tooltip . push ( `\n<span class="tooltip-country">${ c . name } : ${ ( holidayPopulation / 1e6 ) . toFixed ( 1 ) } ${ i18n . mioResidents } ( ${ ( 100 * holidayPopulation / countryPopTotal ) . toFixed ( 0 ) } %) </span>` ) ;
379+ tooltip . push ( `\n<span class="tooltip-country">${ c . name } : ${ formatPopulation ( holidayPopulation , countryPopTotal ) } </span>` ) ;
363380 }
364381 for ( const [ label , info ] of Object . entries ( infos ) ) {
365382 if ( info . All || info . Regions . size > 0 ) {
@@ -375,23 +392,20 @@ function calculateDayStatistics(fromDate, toDate) {
375392 // Build tooltip text
376393 let tooltipText = "" ;
377394 if ( holidayPopulationTotal > 0 ) {
378- const summary = `<span class="tooltip-title">${ ( holidayPopulationTotal / 1e6 ) . toFixed ( 1 ) } ${ i18n . mioResidents } ( ${ ( 100 * holidayPopulationTotal / totalPop ) . toFixed ( 0 ) } %) </span>\n` ;
395+ const summary = `<span class="tooltip-title">${ formatPopulation ( holidayPopulationTotal , totalPop ) } </span>\n` ;
379396 tooltipText += summary + tooltip . join ( "\n" ) ;
380397 } else {
381398 tooltipText += `<span class="tooltip-title">${ i18n . noHoliday } </span>` ;
382399 }
383400 if ( incompleteData . size > 0 ) {
384- tooltipText += `\n\n<span class="warning">` + i18n . incompleteData
385- if ( selectedCountries . length > 1 ) {
386- tooltipText += ": " + [ ...incompleteData ] . map ( code => countries . find ( c => c . code === code ) . name ) . join ( ", " )
387- }
388- tooltipText += `</span>` ;
401+ tooltipText += `\n\n<span class="warning warning-title">${ i18n . incompleteData } : ${ formatPopulation ( incompleteDataPopulation , totalPop ) } </span>`
402+ tooltipText += `\n<span class="warning">${ [ ...incompleteData ] . join ( ", " ) } </span>` ;
389403 }
390404
391405 stats [ m ] [ key ] . tooltip = tooltipText ;
392406 stats [ m ] [ key ] . off = nationwideHolidayAnyCountry || d . getDay ( ) === 0 ; // Sunday
393407 stats [ m ] [ key ] . share = holidayPopulationTotal / totalPop ;
394- stats [ m ] [ key ] . incompleteData = incompleteData . size > 0 ;
408+ stats [ m ] [ key ] . incompleteData = incompleteDataPopulation / totalPop >= 0.05 ; // Highlight if error above 5%
395409
396410 }
397411
@@ -491,6 +505,12 @@ function regions(data){
491505 return { ...data . subdivisions , ...data . groups } ;
492506}
493507
508+ function formatPopulation ( number , total = undefined ) {
509+ let result = `${ ( number / 1e6 ) . toFixed ( 1 ) } ${ i18n . mioResidents } `
510+ if ( total !== undefined ) result += ` (${ ( 100 * number / total ) . toFixed ( 0 ) } %)` ;
511+ return result ;
512+ }
513+
494514function inDateRange ( date , startDate , endDate , orAdjacentWeekend = false ) {
495515 const start = new Date ( startDate ) ;
496516 const end = new Date ( endDate ) ;
0 commit comments