Spaces:
Running
Running
| import { useMemo, useRef } from "react"; | |
| const LANGUAGE_FAMILIES = { | |
| "Indo-European": { | |
| Germanic: ["english", "german", "dutch", "danish", "swedish", "icelandic"], | |
| Romance: [ | |
| "french", | |
| "spanish", | |
| "italian", | |
| "portuguese", | |
| "romanian", | |
| "catalan", | |
| "galician", | |
| ], | |
| Slavic: [ | |
| "russian", | |
| "polish", | |
| "czech", | |
| "slovak", | |
| "ukrainian", | |
| "bulgarian", | |
| "slovenian", | |
| "serbian", | |
| "croatian", | |
| ], | |
| Baltic: ["lithuanian", "latvian"], | |
| "Indo-Iranian": [ | |
| "persian", | |
| "hindi", | |
| "bengali", | |
| "gujarati", | |
| "nepali", | |
| "marathi", | |
| "indic", | |
| ], | |
| Greek: ["greek"], | |
| Armenian: ["armenian"], | |
| }, | |
| "Sino-Tibetan": ["chinese", "mandarin", "taiwanese"], | |
| Afroasiatic: [ | |
| "arabic", | |
| "hebrew", | |
| "darija", // Variante de l'arabe | |
| ], | |
| Austronesian: [ | |
| "indonesian", | |
| "malay", | |
| "filipino", | |
| "singlish", // Créole basé sur l'anglais mais avec influence malaise | |
| ], | |
| "Niger-Congo": ["swahili", "yoruba"], | |
| Dravidian: ["tamil", "telugu", "kannada", "malayalam"], | |
| Austroasiatic: ["vietnamese"], | |
| "Kra-Dai": ["thai"], | |
| Japonic: [ | |
| "japanese", | |
| "日本語", // Japonais en caractères japonais | |
| ], | |
| Koreanic: ["korean"], | |
| Uralic: ["hungarian", "finnish", "estonian"], | |
| Turkic: ["turkish", "azerbaijani", "uzbek", "kazakh"], | |
| "Language Isolate": [ | |
| "basque", // Langue isolée, pas de famille connue | |
| ], | |
| "Other Languages": [], // Will catch any language not in other families | |
| }; | |
| const FAMILY_ORDER = [ | |
| "Indo-European", // Plus grande famille en Europe et Asie du Sud | |
| "Sino-Tibetan", // Deuxième plus grande famille en Asie | |
| "Afroasiatic", // Principale famille en Afrique du Nord et Moyen-Orient | |
| "Austronesian", // Principale famille en Asie du Sud-Est insulaire | |
| "Niger-Congo", // Plus grande famille en Afrique subsaharienne | |
| "Dravidian", // Principale famille en Inde du Sud | |
| "Austroasiatic", // Importante en Asie du Sud-Est continentale | |
| "Kra-Dai", // Famille du thaï | |
| "Japonic", // Japonais | |
| "Koreanic", // Coréen | |
| "Uralic", // Famille finno-ougrienne | |
| "Turkic", // Famille des langues turciques | |
| "Language Isolate", // Langues isolées | |
| "Other Languages", // Autres langues non classifiées | |
| ]; | |
| const findLanguageFamily = (language) => { | |
| for (const [family, content] of Object.entries(LANGUAGE_FAMILIES)) { | |
| if (family === "Indo-European") { | |
| // Cas spécial pour l'Indo-Européen qui a des sous-familles | |
| for (const [subFamily, languages] of Object.entries(content)) { | |
| if (languages.includes(language.toLowerCase())) { | |
| return { family, subFamily }; | |
| } | |
| } | |
| } else if (content.includes(language.toLowerCase())) { | |
| return { family, subFamily: language }; | |
| } | |
| } | |
| return { family: "Other Languages", subFamily: language }; | |
| }; | |
| export const useLanguageStats = (leaderboards, filteredLeaderboards) => { | |
| const statsRef = useRef(null); | |
| const languagesRef = useRef(null); | |
| // Reset stats when leaderboards or filteredLeaderboards change | |
| if (leaderboards && filteredLeaderboards) { | |
| // Calculate unique languages from all leaderboards | |
| const langMap = new Map(); | |
| const langFamilyMap = new Map(); | |
| leaderboards.forEach((board) => { | |
| board.tags?.forEach((tag) => { | |
| if (tag.toLowerCase().startsWith("language:")) { | |
| const lang = tag.split(":")[1].toLowerCase(); | |
| langMap.set(lang, (langMap.get(lang) || 0) + 1); | |
| const { family } = findLanguageFamily(lang); | |
| langFamilyMap.set(family, (langFamilyMap.get(family) || 0) + 1); | |
| } | |
| }); | |
| }); | |
| const langArray = Array.from(langMap.entries()).map(([lang, count]) => { | |
| const { family } = findLanguageFamily(lang); | |
| return [lang, count, family]; | |
| }); | |
| languagesRef.current = langArray | |
| .sort((a, b) => { | |
| const familyA = a[2]; | |
| const familyB = b[2]; | |
| const orderA = FAMILY_ORDER.indexOf(familyA); | |
| const orderB = FAMILY_ORDER.indexOf(familyB); | |
| if (orderA !== orderB) { | |
| return orderA - orderB; | |
| } | |
| // Sort alphabetically by language name instead of by count | |
| return a[0].localeCompare(b[0]); | |
| }) | |
| .map(([lang]) => lang); | |
| // Calculate stats based on filtered leaderboards | |
| statsRef.current = new Map(); | |
| languagesRef.current.forEach((lang) => { | |
| const count = filteredLeaderboards.filter((board) => | |
| board.tags?.some( | |
| (tag) => tag.toLowerCase() === `language:${lang.toLowerCase()}` | |
| ) | |
| ).length; | |
| statsRef.current.set(lang, count); | |
| }); | |
| } | |
| return { | |
| languages: languagesRef.current, | |
| languageStats: statsRef.current, | |
| LANGUAGE_FAMILIES, | |
| findLanguageFamily, | |
| }; | |
| }; | |