Silverlight标准本地化是根据微软官方默认支持的本地化方案进行处理。该方案优点:操作简单,需要极少量的后台编码。缺点:(1)只能在编译前调整各个本地化资源文件,(2)Xaml文件中需要本地化的所有控件的显示属性需要通过资源绑定的方式来设置值,在编码阶段不能直接看到最终界面效果。
一、 修改Silverlight宿主Web项目的相关配置
1. 修改Silverlight在宿主页面(aspx)中object元素,添加语言参数:
<param name="uiculture" value="<%=Thread.CurrentThread.CurrentCulture.Name %>" />
同时,需要在对应的aspx中添加对System.Threading命名空间的引用:
<%@ Import Namespace=System.Threading %>
2. 在Web.Config的system.web节点中添加以下子节点:
<globalization culture="auto" uiCulture="auto"/>
二、 更改Silverlight项目的语言支持
1. 编辑Silverlight的csproj文件(在VS中unload项目->Edit project.csproj),在SupportedCultures节点中添加支持的语言代码,多个语言代码间用逗号隔开,如下图:

2. 保存后重新load项目。
三、 添加语言资源文件
1. 在需要本地化的Silverlight项目中添加一个存储本地化资源的文件夹(本例命名CultureFiles)。
2. 添加资源文件支持语言的资源文件,如下:
CultureFile.resx:public;CultureFile.en.resx和CultureFile.zh-CN.resx:no code generation。
资源文件的Name是指给本地化控件绑定的属性名,如LoginID。Value是在各种语言环境下显示的内容值,如zh-CN环境下“登录名”,en环境下“Login ID”。
四、 添加一个包装资源文件的类
1. 在项目中添加一个包装资源文件的类(ResourceManager)
2. 该类公开一个只读的属性,将资源文件的对象公开给Xaml文件调用。内容如下:
五、 Xaml引用语言资源,并绑定控件
1. 在App.xaml中,添加对ResourceManager类的引用,如下图:
同时,需要注意,添加对命名空间的引用:
在需要本地化的Xaml文件中,对控件的显示属性值进行绑定(比如TextBlock的Text属性):Text="{Binding Language.LoginID, Source={StaticResource culture}}" 这样,TextBlock的文本就会根据浏览器的语言环境来显示了。
这种方式的绑定,代码会比较长,如果某个容器控件不需要使用DataContext属性来给子控件绑定数据源,则可以用以下方式简化子空间的绑定代码:(1)将Source={StaticResource culture}部分作为该容器的DataContext的数据源,(2)对应子控件的绑定就变成:Text="{Binding Language.LoginID}",如下图所示:
运行后的效果如下:

一、 修改Silverlight宿主Web项目的相关配置
1. 修改Silverlight在宿主页面(aspx)中object元素,添加语言参数:
<param name="uiculture" value="<%=Thread.CurrentThread.CurrentCulture.Name %>" />
同时,需要在对应的aspx中添加对System.Threading命名空间的引用:
<%@ Import Namespace=System.Threading %>
2. 在Web.Config的system.web节点中添加以下子节点:
<globalization culture="auto" uiCulture="auto"/>
二、 更改Silverlight项目的语言支持
1. 编辑Silverlight的csproj文件(在VS中unload项目->Edit project.csproj),在SupportedCultures节点中添加支持的语言代码,多个语言代码间用逗号隔开,如下图:

2. 保存后重新load项目。
三、 添加语言资源文件
1. 在需要本地化的Silverlight项目中添加一个存储本地化资源的文件夹(本例命名CultureFiles)。
2. 添加资源文件支持语言的资源文件,如下:
CultureFile.resx:public;CultureFile.en.resx和CultureFile.zh-CN.resx:no code generation。
资源文件的Name是指给本地化控件绑定的属性名,如LoginID。Value是在各种语言环境下显示的内容值,如zh-CN环境下“登录名”,en环境下“Login ID”。
四、 添加一个包装资源文件的类
1. 在项目中添加一个包装资源文件的类(ResourceManager)
2. 该类公开一个只读的属性,将资源文件的对象公开给Xaml文件调用。内容如下:

五、 Xaml引用语言资源,并绑定控件
1. 在App.xaml中,添加对ResourceManager类的引用,如下图:

同时,需要注意,添加对命名空间的引用:

在需要本地化的Xaml文件中,对控件的显示属性值进行绑定(比如TextBlock的Text属性):Text="{Binding Language.LoginID, Source={StaticResource culture}}" 这样,TextBlock的文本就会根据浏览器的语言环境来显示了。
这种方式的绑定,代码会比较长,如果某个容器控件不需要使用DataContext属性来给子控件绑定数据源,则可以用以下方式简化子空间的绑定代码:(1)将Source={StaticResource culture}部分作为该容器的DataContext的数据源,(2)对应子控件的绑定就变成:Text="{Binding Language.LoginID}",如下图所示:

运行后的效果如下:

六、一些难点
1.DataGrid的DataGridColumnHeader的国际化资源绑定
在绑定DataGrid的Header属性时,发现用以下代码Header=”{Binding Language.LoginID, Source={StaticResource culture}}”绑定后,运行结果没有按照预期的方式去显示,原因如下:
Silverlight只有FrameworkElement才有数据绑定的上下文支持特性,其对数据绑定和资源的属性级支持通过DependencyProperty 类来实现,并且任何DependencyObject 都可具有 DependencyProperty,但是为可能继承的数据上下文设置值的能力由 FrameworkElement 来实现。换句话说,DependencyObject 不能实现数据绑定,要实现数据绑定,必须从FrameworkElement派生。
Header属性不是DependencyProperty因为 DataGridColumn是DependencyObject,而绑定在 DependencyObjects 上不工作。另外Column本身不是可视元素,不在视觉树上,所以DataGridColumn不可能成为FrameworkElement,也不能实现绑定。
解决方法:通过设置Header的Style,在Style中嵌套一个TextBlock,然后绑定TextBlock的Text属性来实现。代码如下:
<
sdk
:
DataGridTextColumn
Binding
="{
Binding
Score
}">
<
sdk
:
DataGridTextColumn.HeaderStyle
>
<
Style
TargetType
="sdk:DataGridColumnHeader">
<
Setter
Property
="ContentTemplate">
<
Setter.Value
>
<
DataTemplate
>
<
TextBlock
Text
="{
Binding
Language
.Score,
Source
={
StaticResource
culture
}}"></
TextBlock
>
</
DataTemplate
>
</
Setter.Value
>
</
Setter
>
</
Style
>
</
sdk
:
DataGridTextColumn.HeaderStyle
>
</
sdk
:
DataGridTextColumn
>