The following declarations illustrate the use of property overrides.
type
TAncestor = class
...
protected
property Size:
Integer read FSize;
property Text: string read GetText write SetText;
property Color: TColor read FColor write SetColor stored False;
...
end;
type
TDerived = class(TAncestor)
...
protected
property Size write SetSize;
published
property Text;
property Color stored True default clBlue;
...
end;
The override of
Size
adds a write specifier to allow the property to be modified. The overrides of
Text
and
Color
change the visibility of the properties from protected to published.
The property override of
Color
also
specifies that the property should be filed if its value isn't
clBlue
.
A redeclaration of a property that includes a type identifier hides the inherited property rather than overriding it. This
means that a new property is created with the same name as the inherited one. Any property declaration that specifies
a type must be a complete declaration, and must therefore include at least one access specifier.
Whether a property is hidden or overridden in a derived class, property look-up is always static. That is, the declared
(compile-time) type of the variable used to identify an object determines the interpretation of its property identifiers.
Hence, after the following code executes, reading
or assigning a value to
MyObject.Value
invokes
Method1
or
Method2
, even though
MyObject
holds an instance of
TDescendant
.
But you can cast
MyObject
to
TDescendant
to access the descendant class's properties and their access specifiers.
type
TAncestor = class
...
property Value: Integer read Method1 write Method2;
end;
TDescendant = class(TAncestor)
...
property Value: Integer read Method3 write Method4;
end;
var MyObject: TAncestor;
...
MyObject := TDescendant.Create;
155