[教程] 通过 Rtti 设置对象的事件响应函数

核心提示:调用 TValue.Make 函数来将事件的响应函数绑定。

示例:我们拿 TTimer 来做例子,我们知道它有一个 OnTimer 事件,但我们又不想引用 TTimer 所在的单元,而我们要修改某个实例的 OnTimer 事件响应函数(感觉好绕是吧?因为只是拿来做例子,反正看不懂就当一切在做梦,什么也没发生就好了)。

下面的代码里,ATimer 是 TTimer 的实例,DoTimer 是 OnTimer 事件的新响应函数。

var
  ATimerClass: TRttiType;
  AOnTimerProp: TRttiProperty;
  AContext: TRttiContext;
  AEvent: TNotifyEvent;
  AMethod: TMethod absolute AEvent;
  V: TValue;
begin
...
//1.找到对应的 TRttiType,当然获取它有N种办法
AContext:=TRttiContext.Create;
ATimerClass:=AContext.GetType(ATimer.ClassType);
//2.将事件绑定到一个临时变量上
AEvent := DoTimer;
//[注意]不要传 @AEvent,编译器优化会优化出错误的结果
TValue.Make(@AMethod, TypeInfo(TNotifyEvent), V);
//3.找到属性定义
AOnTimerProp := ATimerClass.GetProperty('OnTimer');
//4.绑定事件完成
AOnTimerProp.SetValue(ATimer, V);
end;

OK,参考上面的代码实现步骤就可以了,当然如果有更好的方法,欢迎分享给我们。

分享到: