diff --git a/public/index.html b/public/index.html index 42b46e7..7e0376a 100644 --- a/public/index.html +++ b/public/index.html @@ -123,13 +123,23 @@ badge.textContent = val + '+'; badge.style.background = getAgeColor(val); } - async function search() { + let lastQuery = ''; + let lastResults = []; + + async function search(force = false) { const query = document.getElementById('q').value.trim(); if (!query) return; const maxAge = parseInt(document.getElementById('maxAge').value, 10); window.history.replaceState({}, '', '?q=' + encodeURIComponent(query) + (maxAge < 21 ? `&maxAge=${maxAge}` : '')); const filmsDiv = document.getElementById('films'); filmsDiv.innerHTML = '
Searching...
'; + + // Si on a déjà cherché ce terme, et pas force, on ne refait pas le fetch + if (!force && lastQuery === query && lastResults.length) { + renderFilms(filterFilmsByMaxAge(lastResults, maxAge)); + return; + } + try { const base = window.location.origin; const response = await fetch(`${base}/search?q=${encodeURIComponent(query)}`); @@ -138,16 +148,8 @@ return; } let films = await response.json(); - if (!Array.isArray(films) || !films.length) { - filmsDiv.innerHTML = 'No results. Try another query.
'; - return; - } - // Filtres sources inutiles (pas de description et/ou pas d'âge) films = films.map(film => { film.results = film.results.filter(r => { - // On considère valide si : - // - summary ou parentsNeedToKnow ou details.summary >= 8 chars - // - ET un âge existe (age, normalizedMarks, marks, details.ageLegal, etc) let hasDescription = (r.summary && r.summary.length >= 8) || (r.parentsNeedToKnow && r.parentsNeedToKnow.length >= 8) || @@ -159,118 +161,133 @@ return film; }).filter(film => film.results.length > 0); - if (isFinite(maxAge)) { - films = films.filter(film => { - const uniqueResults = []; - const seenSources = new Set(); - film.results.forEach(r => { - if (!seenSources.has(r.source)) { - uniqueResults.push(r); - seenSources.add(r.source); - } - }); - const ages = getAllAges(uniqueResults); - if (ages.length === 0) return true; - return Math.max(...ages) <= maxAge; - }); - } - if (!films.length) { - filmsDiv.innerHTML = 'No results for this max age.
'; - return; - } - let html = `Title | -Year | -Information sources | -
---|---|---|
-
-
- ${film.title || 'Unknown title'}
- ${mainImg ? ` |
- ${film.year || 'N/A'} | -`;
- const uniqueResults = [];
- const seenSources = new Set();
- film.results.forEach(r => {
- if (!seenSources.has(r.source)) {
- uniqueResults.push(r);
- seenSources.add(r.source);
- }
- });
- uniqueResults.forEach(r => {
- html += ` `;
- html += ` `;
- });
- html += `${r.source.charAt(0).toUpperCase() + r.source.slice(1)} `; - if (r.link) { - html += ``; - } - if (r.source === 'commonsense') { - html += `Recommended age: ${ageBadge(r.age)} `; - html += `Summary (CSM): ${shortSummary(r.summary || r.parentsNeedToKnow)} `; - if (r.details && r.details.length) { - html += `Details (CSM):
Age(s) (Cinecheck): ${minAge ? ageBadge(minAge) : ''}${r.marks && r.marks.length ? r.marks.join(', ') : '-'} `; - html += `Summary (Cinecheck): ${shortSummary(r.summary)} `; - if (r.details && r.details.length) { - html += `Pictograms (Cinecheck): ${r.details.map(d => d.type).join(', ') || '-'} `; - } - } - else if (r.source === 'filmages') { - html += `Original title (Filmages): ${r.details.titleOriginalPage || r.details.titleOriginal || '-'} `; - html += `Legal age (Filmages): ${ageBadge(r.details.ageLegal)} `; - html += `Suggested age (Filmages): ${ageBadge(r.details.ageSuggested)} `; - html += `Summary (Filmages): ${shortSummary(r.details.summary)} `; - html += `Synthesis (Filmages): ${shortSummary(r.details.synthesis, 100)} `; - if (r.details.indications && r.details.indications.length) { - html += `Indications: ${shortSummary(r.details.indications.join(', '), 100)} `; - } - if (r.details.counterIndications && r.details.counterIndications.length) { - html += `Contra-indications: ${shortSummary(r.details.counterIndications.join(', '), 100)} `; - } - } - else { - html += `Summary: ${shortSummary(r.summary)} `; - html += `Age: ${ageBadge(r.age)} `; - } - html += ` |
Search failed. Check the console.
`; } } + function filterFilmsByMaxAge(films, maxAge) { + if (!isFinite(maxAge)) return films; + return films.filter(film => { + const uniqueResults = []; + const seenSources = new Set(); + film.results.forEach(r => { + if (!seenSources.has(r.source)) { + uniqueResults.push(r); + seenSources.add(r.source); + } + }); + const ages = getAllAges(uniqueResults); + if (ages.length === 0) return true; + return Math.max(...ages) <= maxAge; + }); + } + + // Extraction de la partie rendering pour pouvoir la réutiliser + function renderFilms(films) { + const filmsDiv = document.getElementById('films'); + if (!films.length) { + filmsDiv.innerHTML = 'No results for this max age.
'; + return; + } + let html = `Title | +Year | +Information sources | +
---|---|---|
+
+
+ ${film.title || 'Unknown title'}
+ ${mainImg ? ` |
+ ${film.year || 'N/A'} | +`;
+ const uniqueResults = [];
+ const seenSources = new Set();
+ film.results.forEach(r => {
+ if (!seenSources.has(r.source)) {
+ uniqueResults.push(r);
+ seenSources.add(r.source);
+ }
+ });
+ uniqueResults.forEach(r => {
+ html += ` `;
+ html += ` `;
+ });
+ html += `${r.source.charAt(0).toUpperCase() + r.source.slice(1)} `; + if (r.link) { + html += ``; + } + if (r.source === 'commonsense') { + html += `Recommended age: ${ageBadge(r.age)} `; + html += `Summary (CSM): ${shortSummary(r.summary || r.parentsNeedToKnow)} `; + if (r.details && r.details.length) { + html += `Details (CSM):
Age(s) (Cinecheck): ${minAge ? ageBadge(minAge) : ''}${r.marks && r.marks.length ? r.marks.join(', ') : '-'} `; + html += `Summary (Cinecheck): ${shortSummary(r.summary)} `; + if (r.details && r.details.length) { + html += `Pictograms (Cinecheck): ${r.details.map(d => d.type).join(', ') || '-'} `; + } + } + else if (r.source === 'filmages') { + html += `Original title (Filmages): ${r.details.titleOriginalPage || r.details.titleOriginal || '-'} `; + html += `Legal age (Filmages): ${ageBadge(r.details.ageLegal)} `; + html += `Suggested age (Filmages): ${ageBadge(r.details.ageSuggested)} `; + html += `Summary (Filmages): ${shortSummary(r.details.summary)} `; + html += `Synthesis (Filmages): ${shortSummary(r.details.synthesis, 100)} `; + if (r.details.indications && r.details.indications.length) { + html += `Indications: ${shortSummary(r.details.indications.join(', '), 100)} `; + } + if (r.details.counterIndications && r.details.counterIndications.length) { + html += `Contra-indications: ${shortSummary(r.details.counterIndications.join(', '), 100)} `; + } + } + else { + html += `Summary: ${shortSummary(r.summary)} `; + html += `Age: ${ageBadge(r.age)} `; + } + html += ` |