如何继承资源文件(resx)

Fue*_*led 10 c# inheritance resx resource-files

想象一下,你正在开发一个由数百个程序集组成的.Net 4.0项目,每个程序集都有自己的资源文件(.resx)用于本地化.通过使用ResXFileCodeGenerator(创建"ResourceFile.Designer.cs"文件)自动生成的类,从C#访问本地化字符串:string test = ResourceFile.TestString;

每个程序集都有特定于它的本地化字符串,但是有些字符串对所有程序集都是通用的.您告诉自己,在"父"资源文件中使用这些"公共字符串"会很好,如果资源键在"本地"资源文件中不可用,代码将在该文件中回退.然后你说"嘿!继承可以在这里工作." 事实上,在自动生成的设计器文件中执行类似的操作确实有效: internal class ResourceFile : ParentResourceFile 也就是说,仍然可以使用ResourceFile未定义但定义的字符串.ParentResourceFileResourceFile.StringInParentFile

但是设计器文件标题中的某些内容会让您感到麻烦:" 对此文件的更改可能会导致错误的行为,如果重新生成代码,则会丢失. "另外,您知道在自动生成的设计器文件中播放是不受欢迎的.所以你来到这里,你问:

  • ResXFileCodeGenerator何时生成/重新生成设计器类?
  • 有没有办法关闭那个自动生成?
  • 我们是否必须放弃ResXFileCodeGenerator的优点并实现我们自己的ResourceManager处理?

你说"谢谢你".

Fue*_*led 6

在对该问题进行了一段时间的调查之后,我已经找到了解决方法:不继续对资源文件本身进行继承,而是对需要访问"父"资源的类进行继承.

您只需要有一个基类,其项目包含"主"资源文件,并将该资源文件的CustomTool属性设置为PublicResXFileCodeGenerator("公共"部分很重要,因为它将创建一个public类,而不是一个类internal).一个限制是PublicResXFileCodeGenerator只能从VS2008开始提供(此CodeProject 文章可能会有所帮助).

然后,在需要访问"主"资源的类中,只需从基类继承并访问如下资源:

public class ChildClass : BaseClass
{
    string test = BaseClass.BaseResourceFile.TestString; // a common resource
    string localResource = ResourceFile.OtherString;     // a local resource
}
Run Code Online (Sandbox Code Playgroud)

此解决方案的一个缺点是您必须显式引用BaseResourceFile来访问那里定义的资源; 没有回退到父类,就像在Resource类之间直接进行继承一样.

对于后代,我会回答我自己的问题:

  • ResXFileCodeGenerator何时生成/重新生成设计器类?

    每当添加/删除/修改资源时.

  • 有没有办法关闭那个自动生成?

    没有.无论如何,没有自动生成的"代码生成器"工具将毫无用处,你不觉得吗?

  • 我们是否必须放弃ResXFileCodeGenerator的优点并实现我们自己的ResourceManager处理?

    不,见上面的答案.

我们还考虑使用"链接"文件(来自"添加现有项目"对话框,使用"添加为链接"选项)实现解决方案,其中一个父资源文件将链接到我们的所有程序集,但由于我们的程序集已经从一个基类,继承方式似乎要好得多.

我不太愿意接受我自己的答案,所以如果有人想出一个更好的解决方案或改进我的解决方案,我很乐意接受.也就是说,如果有人关心的话.