兼容win7版应用
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

145 lines
6.6 KiB

using System.Threading.Tasks;
using System.Threading;
using AIK.Models.SystemSettings;
using AIK.Service.IService;
using System;
using System.Collections.Generic;
using System.Globalization;
using System.IO;
using System.Linq;
using System.Text;
using System.Text.Json;
using System.Threading.Tasks;
using System.Windows;
namespace AIK.Service.Service
{
public class LocalizationService : ILocalizationService
{
private const string ASSEMBLY_NAME = "AIK.Assets";
private const string RESOURCE_PATH = "Languages/Strings.{0}.xaml";
private readonly Dictionary<string, ResourceDictionary> _loadedDictionaries = new();
private CultureInfo _currentCulture;
public CultureInfo CurrentCulture => _currentCulture;
public event EventHandler LanguageChanged;
public IEnumerable<CultureInfo> SupportedCultures => new[]
{
new CultureInfo("en"),
new CultureInfo("zh"),
new CultureInfo("es"),
new CultureInfo("pt"),
//new CultureInfo("ru")
};
public IEnumerable<LanguageItems> SupportedLanguages => new[]
{
new LanguageItems { Code = "zh", Name = "中文 (简体)", NativeName = "Chinese", FlagEmoji = "🇨🇳" },
new LanguageItems { Code = "en", Name = "英语", NativeName = "English", FlagEmoji = "🇺🇸" },
new LanguageItems { Code = "pt", Name = "葡萄牙语", NativeName = "Português", FlagEmoji = "🇧🇷" },
new LanguageItems { Code = "es", Name = "西班牙语", NativeName = "Español", FlagEmoji = "🇪🇸" },
new LanguageItems { Code = "pt-BR", Name = "葡萄牙语(巴西)", NativeName = "Português (Brasil)", FlagEmoji = "🇧🇷" },
new LanguageItems { Code = "in", Name = "印度", NativeName = "Indian", FlagEmoji = "🇮🇳" },
new LanguageItems { Code = "fr", Name = "法语", NativeName = "Français", FlagEmoji = "🇫🇷" },
new LanguageItems { Code = "fa", Name = "波斯语", NativeName = "فارسی", FlagEmoji = "🇮🇷" },
new LanguageItems { Code = "he", Name = "希伯来语", NativeName = "עברית", FlagEmoji = "🇮🇱" },
new LanguageItems { Code = "hi", Name = "印地语", NativeName = "हिन्दी", FlagEmoji = "🇮🇳" },
new LanguageItems { Code = "id", Name = "印尼语", NativeName = "Bahasa Indonesia", FlagEmoji = "🇮🇩" },
new LanguageItems { Code = "it", Name = "意大利语", NativeName = "Italiano", FlagEmoji = "🇮🇹" },
new LanguageItems { Code = "ko", Name = "朝鲜语", NativeName = "한국어", FlagEmoji = "🇰🇷" },
new LanguageItems { Code = "pl", Name = "波兰语", NativeName = "Polski", FlagEmoji = "🇵🇱" },
new LanguageItems { Code = "ru", Name = "俄语", NativeName = "Русский", FlagEmoji = "🇷🇺" },
new LanguageItems { Code = "th", Name = "泰语", NativeName = "ไทย", FlagEmoji = "🇹🇭" },
new LanguageItems { Code = "tr", Name = "土耳其语", NativeName = "Türkçe", FlagEmoji = "🇹🇷" },
new LanguageItems { Code = "vi", Name = "越南语", NativeName = "Tiếng Việt", FlagEmoji = "🇻🇳" },
new LanguageItems { Code = "de", Name = "德语", NativeName = "Deutsch", FlagEmoji = "🇩🇪" },
new LanguageItems { Code = "uk", Name = "乌克兰语", NativeName = "Українська", FlagEmoji = "🇺🇦" },
new LanguageItems { Code = "ms", Name = "马来语", NativeName = "Bahasa Melayu", FlagEmoji = "🇲🇾" }
};
public async Task InitializeAsync(string language)
{
// 从设置加载或使用系统默认语言
SetLanguage(language);
}
public void SetLanguage(string cultureCode)
{
try
{
var culture = new CultureInfo(cultureCode);
LoadResourceDictionaryFromAssembly(culture.TwoLetterISOLanguageName);
// 更新线程区域性
CultureInfo.CurrentCulture = culture;
CultureInfo.CurrentUICulture = culture;
// 触发语言更改事件
LanguageChanged?.Invoke(culture, EventArgs.Empty);
}
catch (Exception ex)
{
Console.WriteLine($"切换语言失败: {ex.Message}");
// 回退到中文
LoadResourceDictionaryFromAssembly("zh");
}
}
private void LoadResourceDictionaryFromAssembly(string languageCode)
{
try
{
// 移除现有的语言资源
RemoveExistingLanguageResources();
// 从外部程序集加载资源字典
var resourceUri = GetResourceUri(languageCode);
var resourceDict = new ResourceDictionary { Source = resourceUri };
Application.Current.Resources.MergedDictionaries.Add(resourceDict);
Console.WriteLine($"✅ 成功加载语言资源: {languageCode}");
}
catch (Exception ex)
{
Console.WriteLine($"❌ 加载语言资源失败: {ex.Message}");
// 尝试回退到英语
if (languageCode != "en")
{
LoadResourceDictionaryFromAssembly("en");
}
}
}
private Uri GetResourceUri(string languageCode)
{
// 格式: pack://application:,,,/程序集名称;component/资源路径
return new Uri(
$"pack://application:,,,/{ASSEMBLY_NAME};component/{string.Format(RESOURCE_PATH, languageCode)}",
UriKind.Absolute
);
}
private void RemoveExistingLanguageResources()
{
var dictionariesToRemove = Application.Current.Resources.MergedDictionaries
.Where(d => d.Source?.OriginalString.Contains("Strings.") == true ||
d.Source?.OriginalString.Contains("/Languages/") == true)
.ToList();
foreach (var dict in dictionariesToRemove)
{
Application.Current.Resources.MergedDictionaries.Remove(dict);
}
}
public string GetString(string key)
{
return Application.Current.TryFindResource(key) as string ?? $"[{key}]";
}
public string GetString(string key, CultureInfo culture)
{
throw new NotImplementedException();
}
}
}