在Visual Studio C#中更改资源文件的CodeGenerator

时间:2015-12-17 16:34:24

标签: c# visual-studio-2015 resx

在我的VS2015项目中,我正在使用资源文件来跟踪我的文本和相应的翻译。文本保存在resx文件中,对于主resx文件,会自动创建相应的.designer.cs文件,通过属性公开文本。

我现在的问题是我必须修改.desginer.cs中生成的代码以获得一些额外的功能。当然,这只有在我修改VS用来生成代码的模板时才有意义 - 但我该怎么办呢?

我注意到我可以为我的主resx文件指定一个'自定义工具',该文件当前设置为'PublicResXFileCodeGenerator':

我对自动代码生成做了一些研究,但是找不到它的基本教程,但只有一些复杂的例子可以追溯到VS2008。 不幸的是,我仍然不知道这个'PublicResXFileCodeGenerator'来自哪里,所以我可以用它作为我自己开始的方法的基础。我也不知道我自己的模板是否会是一个.rgt文件,我必须把它放在哪里(我在一个例子中看到了那些rgt文件,但却找不到它们被分配/使用的位置)。

有人可以推荐一种方法来修改我的.Designer.cs的自动代码生成吗?

谢谢!

2 个答案:

答案 0 :(得分:1)

在做了一点研究后,我对this MSDN article进行了解释,解释了如何实现“自定义工具”或“单文件生成器”。其中一部分是发生器需要注册为COM组件,这听起来对我不太有吸引力(我是否必须在每个队友的计算机上注册它以使其在系统上运行?)。

作为替代方案,我决定创建一个简单的控制台应用程序,它将'SourceFile','DestinationFile'和'NameSpace'作为参数。这个小应用程序将能够为我生成.designer.cs。

将工具添加到TFS并从我的资源项目的“预构建事件命令行”调用它应该是小菜一碟。

从TFS中检出.designer.cs(或添加它)shoudl并不是什么大问题(所以我被告知)。

使用System.Resources.ResXResourceReader时,通过RESX文件进行迭代非常方便。

最后这不是一个非常好的解决方法,但我仍然比我迄今为止找到的其他解决方案更喜欢它: - /

答案 1 :(得分:1)

我这样做的方法是删除MyResource.resx文件的自定义工具属性,使其不再生成任何内容,然后创建生成MyResource.Designer.cs类的T4模板。

所以你的解决方案结构看起来像:

enter image description here

您可以将结构基于常规生成的设计器文件,或者只是按照自己的方式使用它。

您需要以某种方式加载资源文件。以下是使用ResXResourceReader的示例(不幸的是,这是在System.Windows.Forms程序集中),并且在T4模板标头中将hostspecific设置为true,因此您可以访问相对路径上的文件:

string fileName = this.Host.ResolvePath("MyResource.resx");
ResXResourceReader reader = new ResXResourceReader(fileName);

// This lets you access the comment. If set to false the DictionaryEntry's
// value will simply be the resource value.
reader.UseResXDataNodes = true;

foreach (DictionaryEntry resource in reader)
{
    ResXDataNode node = (ResXDataNode)resource.Value;

    string key = (string)resource.Key;
    string value = (string)node.GetValue((ITypeResolutionService)null);
    string comment = node.Comment;
}

作为替代方案,您可以选择仍然生成常规MyResource.Designer.cs并枚举资源集(taken from this answer):

ResourceSet resourceSet = MyResource.ResourceManager
    .GetResourceSet(CultureInfo.CurrentUICulture, true, true);
foreach (DictionaryEntry entry in resourceSet)
{
    string resourceKey = entry.Key.ToString();
    object resource = entry.Value;
}

我的代码在构建时以及保存模板时重新生成,这对我来说已经足够了。它使用变体of this answer构建。请注意,批处理文件确实运行TextTransform.exe以生成T4并在基于visual studio版本的部分硬编码路径中找到此exe,但如果您愿意,可以在批处理文件中找出该版本。

不是一个完美的解决方案,但可能是运行外部自定义可执行文件以生成代码的替代方法。这至少不需要为任何人的开发环境提供任何额外的先决条件。