简体   繁体   English

delphi class 在运行时确定

[英]delphi class determined at runtime

Is there a way in Delphi XE+ to create a function whose result is determined at runtime? Delphi XE+ 中有没有办法创建一个 function,其结果在运行时确定?

For example:例如:

function ARuntimeClass(achoice: integer): ClassType;
begin
   case achoice of
     0: Result := TEdit;
     1: Result := TMemo;
     2: Result := TCheckbox;
     3: Result := TComboBox;
   end;
end;

Then, at runtime:然后,在运行时:

var
  aComponent: TComponent;       
begin
  aComponent := FindComponent('SomeComponent234');
  //then process
  ARuntimeClass(2).Checked := True;
  aComponent := FindComponent('SomeComponent123');
  //then process
  ARuntimeClass(0).Text := 'Chosen';    
end;

I am trying to typecast at runtime.我正在尝试在运行时进行类型转换。

Yes, you can return a class type as a function result, using a metaclass type likeSystem.TClass (represents all class types), Classes.TComponentClass (represents classes derived from TComponent ), TControlClass (represents all classes derived from TControl ), etc. Yes, you can return a class type as a function result, using a metaclass type likeSystem.TClass (represents all class types), Classes.TComponentClass (represents classes derived from TComponent ), TControlClass (represents all classes derived from TControl ), etc .

function ARuntimeClass(achoice: integer): TControlClass;
begin
  case achoice of
    0: Result := TEdit;
    1: Result := TMemo;
    2: Result := TCheckbox;
    3: Result := TComboBox;
  end;
end;

Although, you can simply use aComponent.ClassType() instead to access the object's real metaclass type, you don't need a separate function for that.虽然,您可以简单地使用aComponent.ClassType()来访问对象的真实元类类型,但您不需要单独的 function 。

However, just having access to a metaclass type doesn't actually solve your issue.但是,仅仅访问元类类型并不能真正解决您的问题。 You can't use a metaclass to typecast an object pointer to access any type-specific members.您不能使用元类对 object 指针进行类型转换以访问任何特定于类型的成员。 For what you are attempting, you need to use RTTI instead, eg:对于您正在尝试的内容,您需要 改用 RTTI ,例如:

Using old-style RTTI (pre-D2010):使用旧式 RTTI(D2010 之前):

uses
  ..., TypInfo;

var
  aComponent: TComponent;       
  aProp: PPropInfo;
begin
  aComponent := FindComponent('SomeComponent234');
  //then process
  pProp := GetPropInfo(aComponent, 'Checked');
  if aProp <> nil then SetOrdProp(aComponent, aProp, True);

  aComponent := FindComponent('SomeComponent123');
  //then process
  aProp := GetPropInfo(aComponent, 'Text');
  if aProp = nil then aProp := GetPropInfo(aComponent, 'Caption');
  if aProp <> nil then SetStrProp(aComponent, aProp, 'Chosen');
end;

Using new-style enhanced RTTI (D2010+):使用新型增强型 RTTI (D2010+):

uses
  ..., System.Rtti;

var
  aComponent: TComponent;       
  ctx: TRttiContext;
  rType: TRttiType;
  rProp: TRttiProperty;
begin
  aComponent := FindComponent('SomeComponent234');
  //then process
  rType := ctx.GetType(aComponent.ClassType);
  rProp := rType.GetProperty('Checked');
  if rProp <> nil then rProp.SetValue(aComponent, True);

  aComponent := FindComponent('SomeComponent123');
  //then process
  rType := ctx.GetType(aComponent.ClassType);
  rProp := rType.GetProperty('Text');
  if rProp = nil then rProp := rType.GetProperty('Caption');
  if rProp <> nil then rProp.SetValue(aComponent, 'Chosen');
end;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM