/// <summary> /// 初始化<see cref="LanguageResources"/> /// </summary> /// <param name="resourceDirectoryPath">多语言资源文件夹路径</param> /// <param name="resourceType">多语言资源类型</param> public LanguageResources(string resourceDirectoryPath, LanguageResourceTypes resourceType) { this._resourceNames = new List <string>(); this._resourceDirectoryPath = resourceDirectoryPath; this._resourceType = resourceType; // 缓存文件夹下多语言资源名称 this.CacheResourceNames(); }
/// <summary> /// 获取多语言资源内容,失败返回null /// </summary> /// <param name="sourcePath">多语言资源文件路径</param> /// <returns></returns> private string GetResourceContent(string sourcePath) { LanguageResourceTypes resourceType = this._resourceType; switch (resourceType) { case LanguageResourceTypes.Resource: case LanguageResourceTypes.Content: { Uri uri = new Uri(sourcePath, UriKind.RelativeOrAbsolute); StreamResourceInfo srcInfo = null; if (resourceType == LanguageResourceTypes.Resource) { srcInfo = Application.GetResourceStream(uri); } else { srcInfo = Application.GetContentStream(uri); } if (srcInfo != null) { using (var s = srcInfo.Stream) using (var r = new StreamReader(s)) return(r.ReadToEnd()); } } break; case LanguageResourceTypes.File: { if (File.Exists(sourcePath)) { return(File.ReadAllText(sourcePath)); } } break; default: break; }// switch return(null); }
/// <summary> /// 获取所有多语言资源文件路径 /// </summary> /// <returns></returns> private void CacheResourceNames() { LanguageResourceTypes resourceType = this._resourceType; string dirPath = this._resourceDirectoryPath; if (resourceType == LanguageResourceTypes.File) { // 如果是外部文件则直接获取所有文件路径 this._resourceNames = Directory.GetFiles(dirPath, "*.*", SearchOption.TopDirectoryOnly) .Select(p => Path.GetFileName(p)) .ToList(); return; } // 如果是Resource和Content文件则需要从_sourceDefaultDirectoryPath中获取到Assembly和路径,并通过Assembly // 读取对应路径下的资源文件 Regex pathRegex = new Regex(@"^(?<prefix>pack://application:,,,)?(/(?<assemblyName>[^;]+)(;[^;]+){0,2};component)?/(?<path>.*)$", RegexOptions.IgnoreCase); var mh = pathRegex.Match(dirPath); if (!mh.Success) { throw new InvalidOperationException(string.Format("The SourceDefaultDirectoryPath is invalid: [path:{0}]", dirPath)); } Assembly asm = null; var assemblyNameGroup = mh.Groups["assemblyName"]; if (!assemblyNameGroup.Success) { // 没有AssemblyName说明这个路径表示主Assembly asm = Assembly.GetEntryAssembly(); } else { // 通过AssemblyName获取程序集 string assemblyName = assemblyNameGroup.Value; asm = AppDomain.CurrentDomain.GetAssemblies().FirstOrDefault(p => p.GetName().Name == assemblyName); if (asm == null) { throw new InvalidOperationException(string.Format("Can not find resource assembly: [assembly:{0}]", assemblyName)); } } string path = mh.Groups["path"].Value; if (resourceType == LanguageResourceTypes.Content && asm == Assembly.GetEntryAssembly()) { // 当Assembly为WPF工程时,并且资源类型为Content时,必须用AssemblyAssociatedContentFileAttribute // 才能获取资源文件列表 this._resourceNames = asm.GetCustomAttributes(typeof(AssemblyAssociatedContentFileAttribute), true) .Cast <AssemblyAssociatedContentFileAttribute>() .Where(p => p.RelativeContentFilePath.TrimStart('/').StartsWith(path, StringComparison.InvariantCultureIgnoreCase)) .Select(attr => Path.GetFileName(attr.RelativeContentFilePath)) .ToList(); } else { // 当Assembly不是WPF工程时获取资源文件列表需要用GetManifestResourceStream string resName = asm.GetName().Name + ".g.resources"; using (var stream = asm.GetManifestResourceStream(resName)) using (var reader = new ResourceReader(stream)) { this._resourceNames = reader.Cast <DictionaryEntry>() .Where(p => ((string)p.Key).TrimStart('/').StartsWith(path, StringComparison.InvariantCultureIgnoreCase)) .Select(p => Path.GetFileName((string)p.Key)) .ToList(); } }// else }