Sign in Join

Live chat for Free Pascal, Lazarus, Delphi and every Pascal programmer.

Mailing lists / fpc-pascal / 2021-04

Usage of FieldAddress

8 messages · 2 people · –

Reply by email Subscribe to this list Your subscription

Read-only archive. Use j and k to move between messages.

Ryan Joseph

I'm trying to see fields by name but TObject.FieldAddress doesn't seem to be working. Do I have that correct I should be using FieldAddress to return the pointer of the published property? Some how I can't seem to find an example of FieldAddress on Google....

type
  TSomething = class(TPersistent)
    private
      m_scale: integer;
    published
      property scale: integer read m_scale write m_scale;
  end;

Regards,
Ryan Joseph

Sven Barth
to Ryan Joseph
Ryan Joseph wrote 9 lines
I'm trying to see fields by name but TObject.FieldAddress doesn't seem to be working. Do I have that correct I should be using FieldAddress to return the pointer of the published property? Some how I can't seem to find an example of FieldAddress on Google.... type TSomething = class(TPersistent) private m_scale: integer; published property scale: integer read m_scale write m_scale; end;

FieldAddress only works on published fields. Just like MethodAddress only works on published methods.

For private fields extended RTTI is required which is not yet implemented.

Regards,
Sven

Ryan Joseph
to Sven Barth
Show quoted text 5 lines
On Apr 4, 2021, at 12:10 PM, Sven Barth via fpc-pascal wrote: FieldAddress only works on published fields. Just like MethodAddress only works on published methods. For private fields extended RTTI is required which is not yet implemented.

I don't understand this at all I guess. I thought the properties made them published and I get a "Symbol cannot be published, can be only a class" if I put the field itself in the published section.

Just trying to do this:

PInteger(theClass.FieldAddress('foo'))^ := 10;

Regards,
Ryan Joseph

Sven Barth
to Ryan Joseph
Ryan Joseph wrote 11 lines
> On Apr 4, 2021, at 12:10 PM, Sven Barth via fpc-pascal wrote: > > FieldAddress only works on published fields. Just like MethodAddress only works on published methods. > > For private fields extended RTTI is required which is not yet implemented. I don't understand this at all I guess. I thought the properties made them published and I get a "Symbol cannot be published, can be only a class" if I put the field itself in the published section. Just trying to do this: PInteger(theClass.FieldAddress('foo'))^ := 10;

Only classes or interfaces are supported as published *fields*.

And the visibility of the *property* does not change the visibility of the *field*, after all the property could be provided by a method.

Regards,
Sven

Ryan Joseph
to Sven Barth
Show quoted text 6 lines
On Apr 4, 2021, at 1:07 PM, Sven Barth via fpc-pascal wrote: Only classes or interfaces are supported as published *fields*. And the visibility of the *property* does not change the visibility of the *field*, after all the property could be provided by a method.

I know FPC can deserialize JSON with TJSONDeStreamer so maybe I need to use the RTTI functions in TypInfo.pas?

Regards,
Ryan Joseph

Sven Barth
to Ryan Joseph
Ryan Joseph wrote 8 lines
> On Apr 4, 2021, at 1:07 PM, Sven Barth via fpc-pascal wrote: > > Only classes or interfaces are supported as published *fields*. > > And the visibility of the *property* does not change the visibility of the *field*, after all the property could be provided by a method. > I know FPC can deserialize JSON with TJSONDeStreamer so maybe I need to use the RTTI functions in TypInfo.pas?

The RTTI streaming relies on *published properties* (and published methods for the event handlers).

Regards,
Sven

Ryan Joseph
to Sven Barth
On Apr 4, 2021, at 2:36 PM, Sven Barth via fpc-pascal wrote: The RTTI streaming relies on *published properties* (and published methods for the event handlers).

Sorry Sven, I'm not understand what I'm doing wrong. From original example "scale" is a published property right? So FieldAddress only works on published fields, which are not supported unless they are classes/interfaces.

type
 TSomething = class(TPersistent)
   private
     m_scale: integer;
   published
     property scale: integer read m_scale write m_scale;
 end;

I have used published properties like this for JSON streaming, i.e.:

type
  TVectorObject = class(TPersistent)
    private
      components: array[0..2] of integer;
    published
      property x: integer read components[0] write components[0];
      property y: integer read components[1] write components[1];
      property z: integer read components[2] write components[2];
  end;

which works just fine so I assume I can use the RTTI functions, just not FieldAddress.

Regards,
Ryan Joseph

Sven Barth
to Ryan Joseph

Ryan Joseph via fpc-pascal schrieb am
Mo., 5. Apr. 2021, 05:58:

Show quoted text 36 lines
> On Apr 4, 2021, at 2:36 PM, Sven Barth via fpc-pascal < > wrote: > > The RTTI streaming relies on *published properties* (and published methods for the event handlers). Sorry Sven, I'm not understand what I'm doing wrong. From original example "scale" is a published property right? So FieldAddress only works on published fields, which are not supported unless they are classes/interfaces. type TSomething = class(TPersistent) private m_scale: integer; published property scale: integer read m_scale write m_scale; end; I have used published properties like this for JSON streaming, i.e.: type TVectorObject = class(TPersistent) private components: array[0..2] of integer; published property x: integer read components[0] write components[0]; property y: integer read components[1] write components[1]; property z: integer read components[2] write components[2]; end; which works just fine so I assume I can use the RTTI functions, just not FieldAddress.

Correct. You need to use GetOrdProp and similar from the TypInfo unit or the object oriented variant from the Rtti unit.

Note: you don't need to inherit from TPersistent if you simply want to manually access such properties, setting $M+ before the type (and resetting it afterwards) is enough to enable the published section.

Regards,
Sven