diff --git a/src/components/player/atoms/settings/CaptionsView.tsx b/src/components/player/atoms/settings/CaptionsView.tsx index 1c6365ef..41acf04d 100644 --- a/src/components/player/atoms/settings/CaptionsView.tsx +++ b/src/components/player/atoms/settings/CaptionsView.tsx @@ -260,6 +260,7 @@ export function CaptionOption(props: CaptionOptionProps) { // Hook to filter and sort subtitle list with search export function useSubtitleList(subs: CaptionListItem[], searchQuery: string) { const { t: translate } = useTranslation(); + const appLanguage = useLanguageStore((s) => s.language); const unknownChoice = translate("player.menus.subtitles.unknownLanguage"); return useMemo(() => { const input = subs.map((t) => ({ @@ -267,7 +268,10 @@ export function useSubtitleList(subs: CaptionListItem[], searchQuery: string) { languageName: getPrettyLanguageNameFromLocale(t.language) ?? unknownChoice, })); - const sorted = sortLangCodes(input.map((t) => t.language)); + const sorted = sortLangCodes( + input.map((t) => t.language), + appLanguage, + ); let results = input.sort((a, b) => { return sorted.indexOf(a.language) - sorted.indexOf(b.language); }); @@ -283,7 +287,7 @@ export function useSubtitleList(subs: CaptionListItem[], searchQuery: string) { } return results; - }, [subs, searchQuery, unknownChoice]); + }, [subs, searchQuery, unknownChoice, appLanguage]); } export function CustomCaptionOption() { @@ -529,8 +533,12 @@ export function CaptionsView({ // Sort with app language first, then alphabetically return sortedGroups.sort((a, b) => { // App language always comes first - if (a.language === appLanguage) return -1; - if (b.language === appLanguage) return 1; + const isALang = + a.language === appLanguage || a.language.startsWith(`${appLanguage}-`); + const isBLang = + b.language === appLanguage || b.language.startsWith(`${appLanguage}-`); + if (isALang && !isBLang) return -1; + if (!isALang && isBLang) return 1; // Then sort alphabetically return a.languageName.localeCompare(b.languageName); diff --git a/src/pages/parts/settings/PreferencesPart.tsx b/src/pages/parts/settings/PreferencesPart.tsx index 36d34eb0..09873e5e 100644 --- a/src/pages/parts/settings/PreferencesPart.tsx +++ b/src/pages/parts/settings/PreferencesPart.tsx @@ -47,7 +47,10 @@ export function PreferencesPart(props: { const { t } = useTranslation(); const { showModal } = useOverlayStack(); const [isSourceListExpanded, setIsSourceListExpanded] = useState(false); - const sorted = sortLangCodes(appLanguageOptions.map((item) => item.code)); + const sorted = sortLangCodes( + appLanguageOptions.map((item) => item.code), + props.language, + ); const allowAutoplay = isAutoplayAllowed(); diff --git a/src/utils/language.ts b/src/utils/language.ts index 326e15be..e6946744 100644 --- a/src/utils/language.ts +++ b/src/utils/language.ts @@ -123,16 +123,21 @@ export function getPrettyLanguageNameFromLocale(locale: string): string | null { /** * Sort locale codes by occurrence, rest on alphabetical order * @param langCodes list language codes to sort + * @param appLanguage optional app language to prioritize * @returns sorted version of inputted list */ -export function sortLangCodes(langCodes: string[]) { - const languagesOrder = [...languageOrder].reverse(); // Reverse is necessary, not sure why +export function sortLangCodes(langCodes: string[], appLanguage?: string) { + const languagesOrder = [...languageOrder]; + if (appLanguage && !languagesOrder.includes(appLanguage)) { + languagesOrder.unshift(appLanguage); + } + const reversedOrder = [...languagesOrder].reverse(); // Reverse is necessary, not sure why const results = langCodes.sort((a, b) => { - const langOrderA = languagesOrder.findIndex( + const langOrderA = reversedOrder.findIndex( (v) => a.startsWith(`${v}-`) || a === v, ); - const langOrderB = languagesOrder.findIndex( + const langOrderB = reversedOrder.findIndex( (v) => b.startsWith(`${v}-`) || b === v, ); if (langOrderA !== -1 || langOrderB !== -1) return langOrderB - langOrderA;