Script for property getter/setter

Suppose I have an Entity with a two properties, for example Revenue (boolean) and Amount (Double). I would like to display Amount as positive and store as negative numbers if Revenue is false (i.e. Cost). To achieve this I would write a property Getter and a Setter:

function TMyEntity.GetAmount: Double
begin
   if FRevenue then
      result := FAmount
   else
      result := FAmount * -1;
end;

function TMyEntity.SetAmount(AValue: Double);
begin
   if FRevenue then
      FAmount := AValue
   else
      FAmount := AValue * -1;
end;

I suppose this should work, but how can I achieve this by scripting so that I do not manually have to update the entity every time I update the model and (re-)create the unit? Is there an example somewhere?

These documentation topics show how to create a new procedure and new function in a class, using customization scripts:

Alternatively, you can also directly create a Delphi using and add those methods in a class helper for TMyEntity.

Thanks! That works but I'm now stuck on the last step.

I succeed in creating a private function and procedure GetAmount and SetAmount but how do I change this line (by script) in the generated class:

property Amount: Nullable<Double> read FAmount write FAmount;

to point to my new getter/setter methods:

property Amount: Nullable<Double> read GetAmount write SetAmount;

I am trying something like that results in a scripting error:

procedure OnColumnGenerated(Args: TColumnGeneratedArgs);
begin
   if Args.Prop.Name = 'Amount' then
   begin        
      Args.Getter = GetAmount; 
   end;
end;

Please ignore the last question. Through some trial and error I managed to solve the issue. I answer it here to create an example that may of use for someone else in the future.

I first create the getter and setter:

procedure OnClassGenerated(Args: TClassGeneratedArgs);
var
  Func: TCodeMemberMethod; 
  Proc: TCodeMemberMethod;
begin
   Func := Args.CodeType.AddFunction('GetAmount', 'Double', mvPrivate);                       
   Func.AddSnippet('if FCategory = 0 then');  
   Func.AddSnippet('   result := FAmount');
   Func.AddSnippet('else');
   Func.AddSnippet('   result := FAmount * -1;'); 
        
    Proc := Args.CodeType.AddProcedure('SetAmount', mvPrivate);
    Proc.AddParameter('Value', 'Double').Modifier := pmNone
    Proc.AddSnippet('if FCategory = 0 then');  
    Proc.AddSnippet('   FAmount := Value');
    Proc.AddSnippet('else');
    Proc.AddSnippet('   FAmount := Value * -1;');            
end;                                              

Note the .Modifier := pmNone, pmVar is not allowed for property setter

I then modify the property line in the class as:

procedure OnColumnGenerated(Args: TColumnGeneratedArgs);
begin
   if Args.CodeType.Name = 'TMyEntity' then
   begin
      if Args.Prop.Name = 'Amount' then
      begin        
         Args.Prop.ReadMember := 'GetAmount';    
         Args.Prop.WriteMember := 'SetAmount'; 
      end;
   end;
end;

This results in the desired code:

Property Amount: Double read GetAmount write SetAmount;

Note the Args.CodeType.Name = 'TMyEntity'!, otherwise property 'Amount' will be changed for all classes! Which happened to me.... ;-)

1 Like

This topic was automatically closed 24 hours after the last reply. New replies are no longer allowed.