2016-08-26 3 views
0

Как я могу создать во время выполнения визуальный компонент как дочерний элемент формы, используя в конечном итоге RTTI? Все, что я получил это TValue экземпляр ...Создание времени выполнения компонентов Delphi Firemonkey из строки

t := (ctx.FindType(Edit1.Text) as TRttiInstanceType); 
inst:= t.GetMethod('Create').Invoke(t.MetaclassType,[Form1]); 

Спасибо!

ответ

1

Чисто RTTI подход с использованием TRttiMethod.Invoke() будет выглядеть примерно так:

var 
    ctx: TRttiContext; 
    t: TRttiInstanceType; 
    m: TRttiMethod; 
    params: TArray<TRttiParameter>; 
    v: TValue; 
    inst: TControl; 
begin 
    t := ctx.FindType(Edit1.Text) as TRttiInstanceType; 
    if t = nil then Exit; 
    if not t.MetaclassType.InheritsFrom(TControl) then Exit; 
    for m in t.GetMethods('Create') do 
    begin 
    if not m.IsConstructor then Continue; 
    params := m.GetParameters; 
    if Length(params) <> 1 then Continue; 
    if params[0].ParamType.Handle <> TypeInfo(TComponent) then Continue; 
    v := m.Invoke(t.MetaclassType, [TComponent(Form1)]); 
    inst := v.AsType<TControl>(); 
    // or: inst := TControl(v.AsObject); 
    Break; 
    end; 
    inst.Parent := ...; 
    ... 
end; 

гораздо более простой подход, который не использует TRttiMethod.Invoke() будет выглядеть следующим образом:

type 
    // TControlClass is defined in VCL, but not in FMX 
    TControlClass = class of TControl; 

var 
    ctx: TRttiContext; 
    t: TRttiInstanceType; 
    inst: TControl; 
begin 
    t := ctx.FindType(Edit1.Text) as TRttiInstanceType; 
    if t = nil then Exit; 
    if not t.MetaclassType.InheritsFrom(TControl) then Exit; 
    inst := TControlClass(t.MetaclassType).Create(Form4); 
    inst.Parent := ...; 
    //... 
end; 
+0

Большое спасибо, что сделал трюк, но что, если мне нужно установить свойство Text элемента управления? –

+1

'Text' - это публичное свойство' TTextControl', которое происходит от 'TControl'. Таким образом, либо создавайте тип 'inst' to' TTextControl' для прямого доступа к «Тексту», либо используйте RTTI для получения «TRttiProperty» для «Text», а затем вызывайте 'TRttiProperty.SetValue()'. –

+0

Хорошо! Я поеду с первым вариантом! Благодаря! –

Смежные вопросы