C# App_LocalResources实现多语言
介绍
如果您创建的网页将由使用不同语言的用户阅读,则必须为这些读者提供用他们自己的语言查看网页的方法。一种方法是分别用各语言重新创建页面,但这种方法可能需要大量工作量、容易出错并且在更改原始页时很难维护。 ASP.NET 为您提供了一种方法,使用这种方法创建网页可以根据浏览器的首选语言设置或用户显式选择的语言获取内容和其他数据。内容和其他数据指的就是资源,此类数据可以存储在资源文件中。
参考:App_GlobalResources、App_LocalResources (理论篇)
App_GlobalResources是全局资源文件夹,主要存放一些所有页面都需要用到的信息。App_LocalResources是本地资源文件夹,主要存放的是该页面所要用到的字符串和信息。
具体使用,参考:asp.net mvc5 多语言应用、区域性名称和标识符
添加资源文件
在web项目中,右键 添加ASP.NET文件夹,添加App_LocalResources文件夹,再添加资源文件。
若资源文件命名为Order.resx
在cshtml中引用方式为:
@using xxx.App_LocalResources
<div>@Order.baggage</div>
运行报错:未能找到任何适合于指定的区域性或非特定区域性的资源。请确保在编译时已将“Ninject.MVC.App_LocalResources.Order.resources”正确嵌入或链接到程序集“Ninject.MVC”,或者确保所有需要的附属程序集都可加载并已进行了完全签名。
解决方法:将资源文件的 属性->生成操作 改为”嵌入的资源”。
改为
多语言实现
1、资源文件准备
将Order.resx 复制一份,修改为英文的Order.en.resx,(也可以是Order.en-US.resx)并将中文改为对应的英文。
若这里没有designer.cs 则看下 他的访问修饰符是否是public。同时注意:属性->生成操作 改为”嵌入的资源”。
再添加一个 繁体中文的资源文件:Order.zh-HK.resx 不要简写为Order.HK.resx
最后这里只能有一个Order.cs文件
2、 创建一个过滤器
using System; using System.Collections.Generic; using System.Globalization; using System.Linq; using System.Threading; using System.Web; using System.Web.Mvc; namespace MultiMVCWebApp.Filters { /// <summary> /// 本地化,翻译 /// </summary> [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method)] public class LocalizationAttribute : ActionFilterAttribute { public override void OnActionExecuting(ActionExecutingContext filterContext) { if (filterContext.RouteData.Values["lang"] != null && !string.IsNullOrWhiteSpace(filterContext.RouteData.Values["lang"].ToString())) { ///从路由数据(url)里设置语言 var lang = filterContext.RouteData.Values["lang"].ToString(); Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(lang); } else { ///从cookie里读取语言设置 var cookie = filterContext.HttpContext.Request.Cookies["ShaunXu.MvcLocalization.CurrentUICulture"]; var langHeader = string.Empty; if (cookie != null) { ///根据cookie设置语言 langHeader = cookie.Value; Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(langHeader); } else { ///如果读取cookie失败则设置默认语言 langHeader = filterContext.HttpContext.Request.UserLanguages[0]; Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(langHeader); } ///把语言值设置到路由值里 filterContext.RouteData.Values["lang"] = langHeader; } /// 把设置保存进cookie HttpCookie _cookie = new HttpCookie("ShaunXu.MvcLocalization.CurrentUICulture", Thread.CurrentThread.CurrentUICulture.Name); _cookie.Expires = DateTime.Now.AddYears(1); filterContext.HttpContext.Response.SetCookie(_cookie); base.OnActionExecuting(filterContext); } } }
3、 创建一个控制器
在控制器上 添加属性[Localization]
4、 配置 路由
//添加路由节点 语言 lang routes.MapRoute("DefaultLocalized", "{lang}/{controller}/{action}/{id}", //new { controller = "Book", action = "Index", id = UrlParameter.Optional }, new { lang = @"\w{2}" }); new { controller = "Book", action = "Index", id = UrlParameter.Optional }); //lang不用約束為2個字母 routes.MapRoute( name: "Default", url: "{controller}/{action}/{id}", defaults: new { controller = "Book", action = "Index", id = UrlParameter.Optional } );
5、cshtml页面
@using Ninject.MVC.App_LocalResources
@Order.baggage<br />
@Order.name
6、运行
http://localhost:52058/zh/book/index
http://localhost:52058/en/book/index
http://localhost:52058/zh-HK/book/index