I am playing around with Interfaces.
unit uMain;
interface
uses
Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics,
Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.StdCtrls;
type
IOrcs = interface
['{89B86797-9F86-48B8-8D0B-01A78C2CA523}']
function Enemies : string;
end;
IHumans = interface
['{D32C39A3-C654-4078-BD5A-0D3793530FB0}']
function Allies : string;
end;
TOrc = class (TInterfacedObject, IOrcs)
function Enemies : string;
end;
THuman = class (TInterfacedObject, IHumans)
function Allies : string;
end;
TElves = class (TInterfacedObject, IHumans,IOrcs)
private
fOrc : IOrcs;
public
constructor Create;
function Enemies : string;
function Allies : string;
property Orc : IOrcs read fOrc implements IOrcs;
end;
TForm1 = class(TForm)
btnHumans: TButton;
btnOrcs: TButton;
ListBox1: TListBox;
btnElves: TButton;
procedure btnHumansClick(Sender: TObject);
procedure btnOrcsClick(Sender: TObject);
procedure btnElvesClick(Sender: TObject);
private
{ Private declarations }
procedure Log ( str : string );
public
{ Public declarations }
end;
var
Form1: TForm1;
implementation
{$R *.dfm}
{ TOrc }
function TOrc.Enemies: string;
begin
Result := 'Our Enemies Humans';
end;
{ THumans }
function THuman.Allies: string;
begin
Result := 'Our Allies Elves';
end;
{ TForm1 }
procedure TForm1.btnElvesClick(Sender: TObject);
var Allied : IHumans;
Horde : IOrcs;
Test : TElves;
begin
Allied := TElves.Create;
Log('IHumans');
Log(Allied.Allies);
Log('IOrcs');
Horde := Allied as IOrcs;
Log(Horde.Enemies);
Log('TElves.Create');
Test := TElves.Create;
Log(test.Allies);
Log(test.Enemies);
end;
procedure TForm1.btnHumansClick(Sender: TObject);
var Allied : IHumans;
begin
Allied := THuman.Create;
Log(Allied.Allies);
end;
procedure TForm1.btnOrcsClick(Sender: TObject);
var Horde : IOrcs;
begin
Horde := TOrc.Create;
Log(Horde.Enemies);
end;
procedure TForm1.Log(str: string);
begin
ListBox1.Items.Add(str);
end;
{ TElves }
function TElves.Allies: string;
begin
Result:='Wood Elves';
end;
constructor TElves.Create;
begin
fOrc := TOrc.Create;
end;
function TElves.Enemies: string;
begin
Result:='Orcs and Dwarwes';
end;
end.
The question here is regarding TElves
.
I have a function Enemies()
, and I have a property Orc
which implements IOrcs
, so I guess that is why the Enemies()
function is called from IOrcs
instead of locally.
If I comment out the property, the local Enemies()
function is called.
I obviously do not understand the use case of this. Maybe I am doing this completely wrong. But when using IInterface
instead of TClass
, is there a way to call the local function?
The method is called from TOrcs because of the implements IOrcs
in:
property Orc : IOrcs read fOrc implements IOrcs;
The implements directive allows you to delegate implementation of an interface to a property in the implementing class.
It mean that the implementation of IOrcs
in your class will use fOrc
TElves = class (TInterfacedObject, IHumans,IOrcs)
private
fOrc : IOrcs;
public
constructor Create;
function Enemies : string;
function Allies : string;
property Orc : IOrcs read fOrc;
end;