// Copyright (c) ppy Pty Ltd . Licensed under the MIT Licence. // See the LICENCE file in the repository root for full licence text. using System.Collections.Generic; using System.Globalization; using osu.Framework.Bindables; using osu.Framework.Configuration; #nullable enable namespace osu.Framework.Localisation { public partial class LocalisationManager { private readonly List locales = new List(); private readonly Bindable configLocale = new Bindable(); private readonly Bindable configPreferUnicode = new BindableBool(); private readonly Bindable currentParameters = new Bindable(new LocalisationParameters(null, false)); public LocalisationManager(FrameworkConfigManager config) { config.BindWith(FrameworkSetting.Locale, configLocale); configLocale.BindValueChanged(updateLocale); config.BindWith(FrameworkSetting.ShowUnicode, configPreferUnicode); configPreferUnicode.BindValueChanged(updateUnicodePreference, true); } public void AddLanguage(string language, ILocalisationStore storage) { locales.Add(new LocaleMapping(language, storage)); configLocale.TriggerChange(); } /// /// Creates an which automatically updates its text according to information provided in . /// /// The . public ILocalisedBindableString GetLocalisedString(LocalisableString original) => new LocalisedBindableString(original, this); private void updateLocale(ValueChangedEvent locale) { if (locales.Count == 0) return; var validLocale = locales.Find(l => l.Name == locale.NewValue); if (validLocale == null) { var culture = string.IsNullOrEmpty(locale.NewValue) ? CultureInfo.CurrentCulture : new CultureInfo(locale.NewValue); for (var c = culture; !EqualityComparer.Default.Equals(c, CultureInfo.InvariantCulture); c = c.Parent) { validLocale = locales.Find(l => l.Name == c.Name); if (validLocale != null) break; } validLocale ??= locales[0]; } ChangeSettings(CreateNewLocalisationParameters(validLocale.Storage, currentParameters.Value.PreferOriginalScript)); } private void updateUnicodePreference(ValueChangedEvent preferUnicode) => ChangeSettings(CreateNewLocalisationParameters(currentParameters.Value.Store, preferUnicode.NewValue)); /// /// Changes the localisation parameters. /// /// The new localisation parameters. protected void ChangeSettings(LocalisationParameters parameters) => currentParameters.Value = parameters; /// /// Creates new . /// /// /// Can be overridden to provide custom parameters for implementations. /// /// The to be used for string lookups and culture-specific formatting. /// Whether to prefer the "original" script of s. /// The resultant . protected virtual LocalisationParameters CreateNewLocalisationParameters(ILocalisationStore? store, bool preferOriginalScript) => new LocalisationParameters(store, preferOriginalScript); private class LocaleMapping { public readonly string Name; public readonly ILocalisationStore Storage; public LocaleMapping(string name, ILocalisationStore storage) { Name = name; Storage = storage; } } } }