type
TMyEnum = (One, Two, Three);
TMyObject = class
public type
TItems = array[TMyEnum] of String;
private
FItems: TItems;
public
property Items:TItems read FItems write FItems; default; ♠
end;
♠ [dcc32 Error] E2132 Default property must be an array property
There probably is a good reason for this, but I am still annoyed 😛

Well because otherwise it would be an implicit conversion operator, in effect.
Then there is this variation
TMyEnum = (One, Two, Three);
TMyObject = class
public type
TItems = array[TMyEnum] of String;
private
FItems: TItems;
public
property Items[Index:TMyEnum]:String read FItems[Index] write FItems[Index]; default; ♠
end;
♠ [dcc32 Error] E2003 Undeclared identifier: ‘Index’
And if you write a setter and a getter method with an Index parameter? I think read/write methods are required for indexers or array properties.
And that is exactly what I mean when I say the compiler should be able to support more syntax sugar. Obviously the compiler knows what is missing here and should be able to generate the missing code.
Stefan Glienke Well, what if I _wanted_ to return a TItems, not just index into it? The second suggestion from Lars Fosdal could work though.
Asbjørn Heid Then I would not write default behind it?
The default array property should be indexed as an integer value, not an enumeration. The getter/setter signature is fixed to be an “integer” by the compiler intrinsics, I guess.
Stefan Glienke Yeah ok so you want this sugar only to work for “default”, fair enough. I was thinking non-default as well.
A. Bouchez Nope, the index can be any type but you have to write the getter and setter yourself all the time.
A. Bouchez – There is no problem using an enumerated index for a default array propery if you have the get and/or set methods.
TMyEnum = (One, Two, Three);
TMyObject = class
public type
TItems = array[TMyEnum] of String;
private
FItems: TItems;
function GetItems(Index: TMyEnum): String;
procedure SetItems(Index: TMyEnum; const Value: String);
public
property Items[Index:TMyEnum]:String read GetItems write SetItems; default;
end;
My “grind” is that setters and getters that do nothing but
procedure GetItems(Index: TMyEnum):String
begin
Result := FItems[Index];
end;
really should not be required.
Lars Fosdal All getters and setters that don’t do anything but redirect access should be figured out by the compiler imo. The syntax in the property declaration is expressive enough to avoid any ambiguity.
Oh, and then you have this little tidbit:
property One: String index TMyEnum.One read GetItems write SetItems;
which might as well have been
property One: String read FItems[TMyEnum.One] write FItems[TMyEnum.One];
or…
property One: String index FItems[TMyEnum.One]
I just say: inline getter/setter – all cases handled, next.
That isn’t an “array property” it is a property with an array as the type. They’re different things.