Delphi如何从resourcestring单元中找到资源名称

时间:2015-03-19 13:15:01

标签: delphi resourcestring

情况是:

unit abc;

interface

resourcestring
  aabbcc = 'my text here';

implementation

end.

从我的应用程序中收到错误代码'aabbcc'。是否可以使用错误代码访问资源名称aabbcc?

2 个答案:

答案 0 :(得分:3)

我想你会要求一个具有以下签名和行为的函数:

function GetNamedResourceString(const Name: string): string;

Assert(GetNamedResourceString('aabbcc') = 'my text here');

资源字符串存储在程序中的字符串表资源中,其中每个字符串都有一个数字索引。您在程序中使用的命名标识符不会在运行时保留在任何位置。因此,没有内置的方法来获取文本'aabbcc'并发现它与之关联的字符串资源。

但是, 是一种在代码中使用Delphi resourcestring标识符并发现其数字ID的方法。将表达式@aabbcc键入到PResStringRec,然后阅读其Identifier字段。查看 System.pas 中的LoadResString,了解RTL如何使用此信息。

您可以使用PResStringRec值在运行时构建TDictionary<string, PResStringRec>,然后使用该字典实现上述假设的GetNamedResourceString函数。

NamedResources := TDictionary<string, PResStringRec>.Create;
NamedResources.Add('aabbcc', PResStringRec(@aabbcc));

function GetNamedResourceString(const Name: string): string;
begin
  Result := LoadResString(NamedResources[Name]);
end;

如果我是为一个真实的项目做这个,我可能会使用预构建脚本来解析输入文件,以从相应的NamedResources.Add声明中自动生成对resourcestring的调用。

答案 1 :(得分:1)

您的resourcestring被编译为字符串表资源。这些由数字标识符标识。编译器在声明的resourcestring实例和数字标识符之间维护一个映射。当您访问resourcestring时,编译器知道数字标识符,并发出使用该标识符的代码。基本上您希望能够从resourcestring的名称和数字标识符进行映射。不幸的是,该映射仅在编译期间存在。它不包含在可执行文件中。

您唯一的另一个希望是编译器为资源字符串生成RTTI信息。但是,它不会这样做,除非我非常错误。

鉴于这些限制,您需要提供自己的机制来在名称和资源字符串之间进行映射。一种可能性是避免使用内置的resourcestring,并通过您自己的机制管理字符串表资源及其标识符。