Autor Beitrag
motion
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 295

XP, Linux
D7 Prof
BeitragVerfasst: Sa 19.02.05 18:44 
Ich arbeite mit Form-inheritance und suche nach einer Lösung für folgendes Problem (hier simplifiziert dargestellt):
ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
FormA = class (TForm)
  Edit1 : TEdit;
  ActionDisableControls : TAction;
  F1_Key : TAction;  {Shortcut F1 triggert diese Action}
End;

procedure FormA.ActionDisableControls(Sender: TObject);
begin
  Edit1.enabled:=False;
end;

procedure FormA.F1_Key(Sender: TObject);
begin //Hier liegt meine Frage ...
  ActionDisableControlsExecture(Sender); {Wird F1 gedruckt, wird die Edit1 abgeschaltet, aber nur in der aktuellen Hierarchie-Ebene}
  //wie läßt sich hier die Methode der vererbten Klasse aufrufen?
end;

//------------------

FormB = class(FormA)
  Edit2 : TEdit;
End;

procedure FormB.ActionDisableControls(Sender: TObject);
Begin
  inherited;
  Edit2.enabled:=False; //wird leider nicht ausgeführt
End;


Wie definiere ich in meiner Ursprungsklasse (FormA) einen Methodenaufruf, welcher die gleichnamige Methode am Ende der Vererbungskette definiert?
tommie-lie
ontopic starontopic starontopic starontopic starontopic starofftopic starofftopic starofftopic star
Beiträge: 4373

Ubuntu 7.10 "Gutsy Gibbon"

BeitragVerfasst: Sa 19.02.05 19:17 
Gar nicht, das Vorfahre ist sich doch gar nicht bewusst, was es evtl für Nachfahren der Klasse geben könnte. Ich weiß zwar nicht, was ActionDisableControlsExecture() macht, aber du müsstest wohl in FormB.ActionDisableControls() den Aufruf ebenfalls nochmal für Edit2 machen.

_________________
Your computer is designed to become slower and more unreliable over time, so you have to upgrade. But if you'd like some false hope, I can tell you how to defragment your disk. - Dilbert
motion Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 295

XP, Linux
D7 Prof
BeitragVerfasst: Sa 19.02.05 20:43 
ActionDisablecontrolsExecute(..) ruft einfach das OnExecute Ereignis der Action "ActionDisableControls" auf.

Hmm, dann muss ich etliche Logik wohl doch duplizieren und in die Ableitungen kopieren.

Schade das ...
Phantom1
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 390



BeitragVerfasst: Sa 19.02.05 22:25 
na klar geht das, du musst nur bei der methodendeklaration von ActionDisableControls in der ursprungsklasse virtual dahinter angeben und in den geerbten klassen immer mit override gekennzeichnen, also so hier:

ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
FormA = class (TForm)
  Edit1 : TEdit;
  ActionDisableControls : TAction;
  F1_Key : TAction;  
  procedure ActionDisableControls(Sender: TObject); virtual; // in der ursprungsklasse virtual angeben
End;

procedure FormA.ActionDisableControls(Sender: TObject);
begin
  Edit1.enabled:=False;
end;

procedure FormA.F1_Key(Sender: TObject);
begin 
  ActionDisableControlsExecture(Sender); 
end;

//------------------

FormB = class(FormA)
  Edit2 : TEdit;
  procedure ActionDisableControls(Sender: TObject); override; // und hier override
End;

procedure FormB.ActionDisableControls(Sender: TObject);
Begin
  inherited;
  Edit2.enabled:=False; 
End;
motion Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 295

XP, Linux
D7 Prof
BeitragVerfasst: Sa 19.02.05 22:36 
Cooool!
Das war der Tipp auf den ich gewartet habe.
Ich fahre morgen früh erstmal eine Woche zum Offroaden in Urlaub und werde dann nach meiner Rückkehr übernächste Woche mal die Umsetzung in meinem Projekt proben.

Vielen Dank
motion Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 295

XP, Linux
D7 Prof
BeitragVerfasst: So 20.02.05 00:20 
Hab's doch noch gerade mal geprüft: Ja, funktioniert.

Ausgezeichnet, vielen Dank.

Jetzt kann ich ja beruhigt in den Urlaub abdüsen ...
tommie-lie
ontopic starontopic starontopic starontopic starontopic starofftopic starofftopic starofftopic star
Beiträge: 4373

Ubuntu 7.10 "Gutsy Gibbon"

BeitragVerfasst: So 20.02.05 10:42 
Nur um mich ein bisschen zu verteidigen (;-)), virtuelle Methoden sind nicht das gleiche wie ein Gegenteil von inherited. Bei virtuellen Methoden wird lediglich die Methode der Laufzeit-Instanz aufgerufen, und nicht die der deklarierten Klasse. Bei virtuellen Methoden macht es keinen Unterschied, ob mein Objektzeiger vom Typ FormA oder FormB ist, es wird in beiden Fällen FormB.SoeMethod() aufgerufen. Ein inherit hingegen ist unabhängig von der verwendeten Instanz und funktioniert immer mit dem jeweiligen Vorfahren der deklarierten (!!) Klasse. Das gleiche hätte man mit erstem Code auch schon erreichen können, indem man die Objektvariable vom Typ FormB deklariert hätte, dann wäre ebenfalls FormB.SomeMethod() aufgerufen worden und auch das dort befindliche inherited wäre korrekt durchlaufen worden.
Ein semantisch vollwertiges Gegenteil zu inherited gibt es in der Form nicht.

_________________
Your computer is designed to become slower and more unreliable over time, so you have to upgrade. But if you'd like some false hope, I can tell you how to defragment your disk. - Dilbert
Phantom1
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 390



BeitragVerfasst: So 20.02.05 11:45 
tommie-lie hat folgendes geschrieben:
Nur um mich ein bisschen zu verteidigen (;-)), virtuelle Methoden sind nicht das gleiche wie ein Gegenteil von inherited. Bei virtuellen Methoden wird lediglich die Methode der Laufzeit-Instanz aufgerufen, und nicht die der deklarierten Klasse. Bei virtuellen Methoden macht es keinen Unterschied, ob mein Objektzeiger vom Typ FormA oder FormB ist, es wird in beiden Fällen FormB.SoeMethod() aufgerufen. Ein inherit hingegen ist unabhängig von der verwendeten Instanz und funktioniert immer mit dem jeweiligen Vorfahren der deklarierten (!!) Klasse. Das gleiche hätte man mit erstem Code auch schon erreichen können, indem man die Objektvariable vom Typ FormB deklariert hätte, dann wäre ebenfalls FormB.SomeMethod() aufgerufen worden und auch das dort befindliche inherited wäre korrekt durchlaufen worden.
Ein semantisch vollwertiges Gegenteil zu inherited gibt es in der Form nicht.


Du musst dich nicht verteidigen, ich bin exakt deiner Meinung ->Ein gegenteil zu inherited gibts nicht. Er hat das Problem nur etwas falsch geschildert bzw sich falsch ausgedrückt. Ich hab eigentlich nur vermutet das er auf was ganz anders hinaus will :wink:

mfg