Delphi - TValue for pointer and back

I am struggling with a simple piece of code and even this is simple, I cannot find a solution for this. Partly I have an event called so

OnReadMessageParameter(Self, aName, aTypeInfo, pointer(@aValue), [psIsTValue]);

      

The important parameter is aValue, which is of type TValue . When it's called aValue.IsObject it's true. I assigned my procedure to this event in order to process data from it:

.DoOnReadMessageParameter(Sender: TROMessage; const aName: string;
  aTypeInfo: PTypeInfo; const DataRef: pointer; Attributes: TParamAttributes);

      

Now what is my problem, I tried several ways to convert the DataRef to a TValue element:

var val: tvalue;

tvalue.Make(@DataRef^,TypeInfo(TValue),val);
or another attempt
val := TValue(@DataRef^);

      

but the IsObject property is false. It must be something really simple that I am missing. Any idea?

+3


source to share


2 answers


If aValue is a TValue, @aValue is a pointer to the TValue structure, not the value it wraps. A better option would be to make the OnReadMessageParameter event its own DataRef, typical of the TValue itself, rather than an untyped pointer.

However, if you cannot control this, you need to cast the DataRef to the pointer to TValue and then read it -



type
  PValue = ^TValue;
var
  val: TValue;
begin
  val := PValue(DataRef)^;

      

+5


source


If you can't manage DoOnReadMessageParameter

, but you know you DataRef

will always be a pointer to TValue

, then:

type
   PValue = ^TValue;

procedure [someclass].DoOnReadMessageParameter(Sender: TROMessage; const aName: string; 
       aTypeInfo: PTypeInfo; const DataRef : pointer; Attributes: TParamAttributes);

var
   HaveObject : boolean;

begin
   HaveObject := PValue(DataRef).IsObject;
   //...
end;

      


Assuming you are in control DoOnReadMessageParameter

and not the event OnReadMessageParameter

:

type
   PValue = ^TValue;

procedure [someclass].DoOnReadMessageParameter(Sender: TROMessage; const aName: string; 
       aTypeInfo: PTypeInfo; const DataRef : PValue; Attributes: TParamAttributes);

var
   HaveObject : boolean;

begin
   HaveObject := DataRef.IsObject;
   //...
end;

      




If you have control over both:

OnReadMessageParameter(Self, aName, aTypeInfo, aValue, [psIsTValue]);

procedure [someclass].DoOnReadMessageParameter(Sender: TROMessage; const aName: string; 
       aTypeInfo: PTypeInfo; const DataRef : TValue; Attributes: TParamAttributes);

      


Finally, if it DataRef

can point to anything, you're out of luck since you don't have type information with which to create TValue instances.

+2


source







All Articles