Where are the Delphi Attributes Real World Examples?

后端 未结 3 1815
刺人心
刺人心 2021-02-04 08:45

I know by TMS Aurelius that we can use the \"new\" 2010 attributes feature to serialize database table fields into object properties at run-time, for example, and I am not an ex

3条回答
  •  暖寄归人
    2021-02-04 09:20

    If you want to declare you own attribute, you can do it like this:

    type
      TDisplayLabelAttribute = class(TCustomAttribute)
      private
        FText: string;
      public
        constructor Create(const aText: string);
        property Text: string read FText write FText;
      end;
    

    An attribute is a regular class, that has the TCustomAttribute as its ancestor. You implement it as usual:

    implementation
    
    constructor TDisplayLabelAttribute.Create(const aText: string);
    begin
      FText := aText;
    end;
    

    Now the attribute is declared and implemented, you can just use it:

    [DisplayLabel('My Class')]
    TMyClass = class
    end;
    

    So now you have an attribute declared and implemented and you have used it to add a display label to some class. The final phase is to use that attribute, since you have a class decorated with it. The code that uses the attribute does not resides in the attribute nor the decorated class, it is implemented in the service layer that will use the decoration.

    Let's say we have a class that returns a possible display label for a class:

    type
      TArtifactInspector = class
      public
        class function DisplayLabelFor(aClass: TClass): string;
      end;
    

    That method will inspect a class and return its display label, given it exists. Otherwise it returns an empty string:

    implementation
    
    uses
      Rtti;
    
    class function TArtifactInspector.DisplayLabelFor(aClass: TClass): string;
    var
      rttiContext: TRttiContext;
      rttiType: TRttiType;
      attribute: TCustomAttribute;
    begin
      rttiContext := TRttiContext.Create;
      try
        rttiType := rttiContext.GetType(aClass);
        for attribute in rttiType.GetAttributes do
          if attribute is TDisplayLabelAttribute then
            Exit(TDisplayLabelAttribute(attribute).Text);
        Result := '';
      finally
        rttiContext.Free;
      end; // try to recover and return the DisplayLabel
    end;
    

提交回复
热议问题