program rtti;
uses typinfo;
type
{ TSampleClass }
TSampleClass = class
private
Fi: integer;
procedure SetI(AValue: integer);
public
procedure a;
function b: boolean;
property i: integer read Fi write SetI;
end;
{ TSampleClass }
procedure TSampleClass.SetI(AValue: integer);
begin
if Fi = AValue then Exit;
Fi := AValue;
end;
procedure TSampleClass.a;
begin
writeln('a');
end;
function TSampleClass.b: boolean;
begin
writeln('b');
result := true;
end;
var
SampleClasse: TSampleClass;
info:PTypeInfo;
Data: PTypeData;
begin
SampleClasse := TSampleClass.Create;
info := TypeInfo(SampleClasse);
Data := GetTypeData(info);
Writeln('Type name : ', info^.Name);
Writeln('Type kind : ', GetEnumName(TypeInfo(TTypeKind), Integer(info^.Kind)));
Writeln('Properties count : ', data^.PropCount);
readln;
end.
program rtti;
uses typinfo;
type
{ TSampleClass }
{$M+}
TSampleClass = class
private
function doSomething: string;
published
property Something: string read doSomething;
function somethingElse(Param1, Param2: integer): string;
end;
{$M-}
{ TSampleClass }
TCallFunc = function: string of object;
function TSampleClass.doSomething: string;
begin
result := 'something';
end;
function TSampleClass.somethingElse(Param1, Param2: integer): string;
begin
result := 'somethingElse';
end;
var
SampleClasse: TSampleClass;
info:PTypeInfo;
Data: PTypeData;
propInfo: PPropInfo;
CallFunc : TCallFunc;
r: string;
begin
SampleClasse := TSampleClass.Create;
info := TypeInfo(SampleClasse);
Data := GetTypeData(info);
Writeln('Type name : ', info^.Name);
Writeln('Type kind : ', GetEnumName(TypeInfo(TTypeKind), Integer(info^.Kind)));
Writeln('Properties count : ', data^.PropCount);
propInfo := GetPropInfo(SampleClasse, 'SomeThing');
if assigned(propInfo) then begin
callfunc := TCallFunc(propInfo^.GetProc^);
r := CallFunc();
end;
readln;
end.
Point 1 : how to call something() to get result in r (current code don't work, it end up at callfunc() )Your "Something" was a string property. Not a function.
Your "Something" was a string property. Not a function.
You don't need trunk, nor a redundant {$M+}.
QuoteYour "Something" was a string property. Not a function.
argh you are so right ! what a dumb I made i can use it directly
It has a getProc, so my first attempt was to call it :)
thank you !
I see FPC hasn't implemented an ObjectInvoke (ObjAuto module) (http://docwiki.embarcadero.com/CodeExamples/Rio/en/ObjectInvoke_(Delphi)) yet.Yes that is true. Sven indicated it can take quite some time. At the moment the calls are stubs waiting to be implemented.
At least not like Delphi.
The value: 42
My Object: 21
I see FPC hasn't implemented an ObjectInvoke (ObjAuto module) (http://docwiki.embarcadero.com/CodeExamples/Rio/en/ObjectInvoke_(Delphi)) yet.
At least not like Delphi.
Calling already works as Rtti.Invoke is implemented in 3.2 and newer (though it relies on the FFI library for most systems currently). It's retrieving non-published functions which is not implemented currently.And now try that same example with TMyObject NOT in the same unit and not accessible for the main program.
Invoke(TMethod(@t.DoTest).Code, [t], ccReg, Nil, False, False);
Did you read all of my message? You even quoted it: I stressed that retrieving is the problem currently. As long as you can get a pointer to the function or method you can call it, but you need to roll your own way to get the pointer currently.Ah, you said:
It's retrieving non-published functions which is not implemented currently.So I assumed retrieving public/published functions wouldn't be a problem and wanted to get an example.
Did you read all of my message? You even quoted it: I stressed that retrieving is the problem currently. As long as you can get a pointer to the function or method you can call it, but you need to roll your own way to get the pointer currently.Ah, you said:QuoteIt's retrieving non-published functions which is not implemented currently.So I assumed retrieving public/published functions wouldn't be a problem and wanted to get an example.
But I take it, from your response, you can't get the code-pointer to public functions from an unknown class via RTTI.
(and that was what I was referring to when I said "Getting to a public function is a lot harder.")
B.T.W. If the TMyObject.DoTest is known... just casting it in code would be easier for TS anyway.