WinForm中直接修改Thread.CurrentThread.CurrentUICulture不会自动刷新已有控件文本,必须手动调用ComponentResourceManager.ApplyResources()递归更新所有控件属性,且资源文件命名(如Resources.zh-CN.resx)、生成配置(Embedded Resource、Public访问修饰符)及键名一致性均需严格匹配文化标识,否则将fallback至默认语言或抛MissingManifestResourceException。

直接改 Thread.CurrentThread.CurrentUICulture 不会刷新已有控件文本,必须重建 UI 或手动重设属性——这是 90% 的“切了语言但没变”问题的根源。
资源文件命名和生成操作必须严格匹配文化标识
Visual Studio 只认标准文化名,比如 Resources.zh-CN.resx、Resources.en-US.resx,写成 Resources_zh.resx 或 Resources.en.resx 就加载失败。常见错误现象是抛 MissingManifestResourceException,或始终 fallback 到默认语言(如总显示中文)。
- 所有资源文件 Build Action 必须设为
Embedded Resource - Access Modifier 要选
Public(否则ResourceManager拿不到) - 主资源文件(如
Resources.resx)是中性资源,不能缺;它和带后缀的文件必须放在同一目录下 - 编译后检查输出目录:
zh-CN\Resources.resources和en-US\Resources.resources应真实存在子文件夹中
WinForms 切换语言后界面不更新?得手动触发重绘
改完 CurrentUICulture 后,已有窗体不会自动响应——ComponentResourceManager.ApplyResources() 是唯一可靠的手动刷新方式,但它依赖设计器生成的资源键名,且不处理嵌套控件(如 ToolStripMenuItem 子项)。
- 推荐封装一个
RefreshLocalizedText()方法,递归遍历控件树,对每个控件调用_rm.ApplyResources(control, control.Name) - 避免在静态构造函数或
Form_Load早期阶段读取资源,此时文化可能还没生效 - 如果控件名变更(如重命名
button1→btnSave),对应资源键也得同步改,否则静默失败 - 别用
this.ApplyResources(null, null)——它只刷当前窗体一级,子控件(如Panel内的Label)不会更新
WPF 中用 GetString() 动态取值要传 culture 参数
WPF 没有内置文化监听机制,{x:Static res:Strings.Title} 是静态引用,改了 CurrentUICulture 完全无效。必须显式传参并兜底 null,否则返回空字符串也不报错。
- 正确写法:
Strings.ResourceManager.GetString("Title", Thread.CurrentThread.CurrentUICulture) - key 区分大小写且禁用空格:
"SaveButton_Text"可以,"savebutton_text"或"Save Button Text"返回null - 绑定场景下,建议把资源字符串封装成 ViewModel 属性,文化变更时触发
INotifyPropertyChanged - 更稳妥的做法仍是重启窗口或重载整个
UserControl,而不是试图局部刷新
别用裸 ResourceManager,.NET Core / .NET 5+ 推荐 Microsoft.Extensions.Localization
手写 ResourceManager 构造容易出错:baseName 写错(漏命名空间)、assembly 传错(误用调用方程序集)、culture 传空都会导致 GetString() 返回 null。强类型资源类(如 Properties.Resources)内部已封装好参数,最稳。
- 类库中尤其注意:
Assembly.GetExecutingAssembly()可能不是资源所在程序集,要用typeof(Resources).Assembly - ASP.NET Core 场景下,
AddLocalization()和UseRequestLocalization()必须在UseRouting()之后、UseEndpoints()之前注册 - resx 里存 HTML 或 JSON 不安全:VS 编辑器会自动转义
&、等字符,合并冲突风险高,运行时解码易失真
最容易被忽略的是:资源键名和控件名的耦合关系——WinForms 设计器生成的资源键是 Form1.button1.Text 这种格式,一旦改名或删控件,对应资源就断了,而且没有任何编译警告。


















