[Delphi3] Sender : TObject ?

Hi,
ich habe mehrere Button, bei einem Klick mit der rechten Maustaste öffnet sich ein Popup. Jetzt möchte ich je nach Button verschiedene Aktionen durchführen. Wie kann ich im Eventhandler den Sender überprüfen?

procedure TForm1.Clear1Click(Sender: TObject);
begin
if TEdit(sender) = Button_a then

Versuchs mal mit der Tag-Eigenschaft. Ordne jedem Button einen unterschiedlichen Tag zu und frag ihn dann ab.

Beispiel:
if TComponent(Sender).Tag = 1 then
begin
Variante1;
end
else if TComponent(Sender).Tag = 2 then
begin
Variante2;
end;
Gruß

[Bei dieser Antwort wurde das Vollzitat nachträglich automatisiert entfernt]

Was Helmut geschrieben hat funktioniert auch, aber es geht auch anderst:

if (sender as TButton).Caption = ‚Button1‘ then…

du kannst natürlich auch andere Eigenschaften als Caption verwenden, da müsste eigentlich alles gehn. das AS bedeutet Delphi soll annehmen der Sender sei ein TButton. Soll’s ein BitBtn sein muss es dann halt heissen

if (sender as TBitBtn).caption =…

Ist sender kein solches Objekt gibt’s ne Exception. Du kannst aber vorher per
if (sender is TBitBtn) then…
prüfen, ob’s ein solches Objekt ist und darauf reagieren…

Timo

Danke!
Erstmal großes Lob für die schnelle Hilfe. Leider ist Sender vom Typ MenuItem, wie ich herausgefunden habe. Das ist natürlich bei allen Buttons gleich. Deshalb werde ich das Popupmenu kopieren und ziiiiiemlich viele Eventhandler schreiben. :frowning:
Danke trotzdem! Chris

Nicht so schnell aufgeben!
Tja, jetzt wird mir langsam klar, was Du eigentlich machen willst… Stimmt es, dass Du auf mehreren Buttons das gleiche Menü einblenden willst, aber je nachdem welcher Button es war in den Menüpunkten verschiedene Aktionen auslösen?

Das geht z.B. mit folgendem Trick ganz einfach:
Wird das Menü geöffnet erhält es als Sender den Button. Wenn Du den irgendwie speicherst, z.B. in einer private-Variablen im Formular oder sonstwo (kannst ein Popup-Menu-Abkömmling schreiben, der das automatsich macht) kannst Du bei einem Menüaufruf darauf zurückgreifen!

Timo

Hi Timo,
hmm…das Problem hast du richtig erkannt :smile:
Allerdings kann man im OnPopup-Event schon nicht mehr auf die Button zugreifen. Aber die Idee ist nicht schlecht. Ich werde jetzt solange basteln, bis es funktioniert! Chris

Allerdings kann man im OnPopup-Event schon nicht mehr auf die
Button zugreifen.

Hi Chrissi,

das stimmt. Angenommen Du hast vier Buttons (Button1 … Button4) und ein Popupmenü (PopupMenu1234). Weil zu jedem Button das gleiche PopupMenü, nämlich PopupMenu1234 erscheinen soll, hast Du das PopupMenu-Property jedes Buttons im Objektinspektor auf „PopupMenu1234“ gesetzt. Tatsache ist nun, daß in dem „OnPopup“-Event von PopupMenu1234 als „Sender“ nicht etwa der jeweilige Button erscheint, sondern bloß das jeweilige PopupMenü, in diesem Fall also PopupMenu1234. Du willst aber wissen, von welchem der vier Buttons das PopupMenü aufgerufen wurde. Dieses Problem kannst Du ganz simpel lösen, und zwar so.

1.: Deklariere im Formular eine neue TObject-Variable, z. B. „PMCallObj: TObject“ (gehört in den PRIVATE-Teil). 2.: Selektiere alle vier Buttons gleichzeitig, und erzeuge den Eventhandler für das „OnMouseDown“-Ereignis. In die MouseDown-Prozedur schreibst Du eine einzige kleine aber feine Zeile, und zwar „PMCallObj := Sender“. Was auch immer der „Sender“ ist – er wird erstmal „dauerhaft“ abgespeichert und steht dadurch für eine Abfrage im OnPopup-Event zur Verfügung.

Das war’s schon. Du kannst jetzt innerhalb des OnPopup-Events den Button einfach anhand der PMCallObj-Variable identifizieren:

IF PMCallObj IS TButton THEN
 begin
 IF TButton(PMCallObj)=Button1 THEN ...
 IF TButton(PMCallObj)=Button2 THEN ...
 IF TButton(PMCallObj)=Button3 THEN ...
 IF TButton(PMCallObj)=Button4 THEN ...
 end;

Wenn feststeht, daß nur Buttons als Sender in Frage kommen, kannst Du das äußere IF…THEN… auch weglassen.

Eleganter ist es, wenn Du das Tag-Property für jeden der vier Buttons auf einen unterschiedlichen Wert setzt, z. B. 1, 2, 3 und 4. Dann kannst Du nämlich schreiben:

IF PMCallObj IS TComponent THEN
 begin
 CASE TComponent(PMCallObj).Tag OF
 1: ...; { PopupMenü wurde von Button 1 aus aufgerufen }
 2: ...; { PopupMenü wurde von Button 2 aus aufgerufen } 
 3: ...; { PopupMenü wurde von Button 3 aus aufgerufen }
 4: ...; { PopupMenü wurde von Button 4 aus aufgerufen }
 END
 end

Genau für diese Zwecke ist übrigens das Tag-Property gedacht. Die letzte Methode hat aber noch einen weiteren Vorteil. Wenn du außerdem noch ein Bild hat („ChrissiImage“ vom Typ „TImage“), von dem aus ebenfalls das PopupMenu1234 aufgerufen werden soll, brauchst Du dessen Tag-Property bloß z. B. auf 5 zu setzen und die CASE-Anweisung um einen weiteren Punkt „5: …“ zu ergänzen:

IF PMCallObj IS TComponent THEN
 begin
 CASE TComponent(PMCallObj).Tag OF
 1: ...; { PopupMenü wurde von Button 1 aus aufgerufen }
 2: ...; { PopupMenü wurde von Button 2 aus aufgerufen } 
 3: ...; { PopupMenü wurde von Button 3 aus aufgerufen }
 4: ...; { PopupMenü wurde von Button 4 aus aufgerufen }
 5: ...; { PopupMenü wurde von ChrissiImage aus a. }
 END
 end

Daß dies funktioniert, liegt daran, daß ein Objekt der Klasse „TButton“ immer auch ein Objekt der Klasse „TComponent“ ist, und das gleiche gilt auch für alle „TImage“-Objekte, denn sowohl TButton als auch TImage sind (indirekt) von TComponent abgeleitet. TComponent ist gerade die Klasse, ab der es ein Tag-Property gibt.

Ich hoffe, ich konnte Dir helfen.

Mit freundlichem Gruß
Martin