Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Win32/Win64 API (native code) (https://www.delphipraxis.net/17-win32-win64-api-native-code/)
-   -   Delphi ButtonKlick ermitteln und wiedergeben (https://www.delphipraxis.net/50836-buttonklick-ermitteln-und-wiedergeben.html)

VT-DA 1. Aug 2005 18:45


ButtonKlick ermitteln und wiedergeben
 
Hi,

Ich versuche verzweifelt eine Funktion zu erstellen die herausfindet ob ein button geklickt wurde.
Dabei kann ich aber wie sonst keine procedure nehmen weil ich mehrere Buttons habe.
Hier mal meine Funktion an der ich werkelte:

Delphi-Quellcode:
function ButtonClick(Obj: TButton): Integer; stdcall;
var i: Integer;
begin
  for i := Low(ButtonArray) to High(ButtonArray) do
  begin
    if Obj = ButtonArray[i].BHandel then
    begin
      if ButtonArray[i].BHandel.OnClick then
        result := 1
      else
        result := 0;
    end;
  end;
end;
Hier jetzt bei der Funktion sieht man das die Funktion durch eine DLL aufgerufen wird.
ButtonArray ist außerdem ein Dynamisches array wo die Handels gespeichert werden.

Doch zu meinem Problem. In der zeile "if ButtonArray[i].BHandel.OnClick then" sagt er mir das Parameter fehlen. Ich schetze mal das dass Fensterhandel fehlt. Doch ich habe bis jetzt keine möglichkeit gefunden wie ich das Fensterhandel übergeben soll.

Mfg

VT-DA 2. Aug 2005 15:09

Re: ButtonKlick ermitteln und wiedergeben
 
Hi,

Hat niemand ne Idee? :freak:

Mfg

RavenIV 2. Aug 2005 16:27

Re: ButtonKlick ermitteln und wiedergeben
 
Zitat:

Zitat von VT-DA
Doch zu meinem Problem. In der zeile "if ButtonArray[i].BHandel.OnClick then" sagt er mir das Parameter fehlen. Ich schetze mal das dass Fensterhandel fehlt. Doch ich habe bis jetzt keine möglichkeit gefunden wie ich das Fensterhandel übergeben soll.

er will keinen handle haben, sondern einen Sender.
irgendwer muss das onClick-Event ja senden...

ausserdem hat ein TButton die Eigenschaft "Down", vielleicht kannst du diese anstelle von OnClick verwenden.

VT-DA 2. Aug 2005 16:41

Re: ButtonKlick ermitteln und wiedergeben
 
Hi,

Ahh. Okay. Danke. Aber eine Frage hätte ich da noch.
Wie mache ich denn überhaupt einen "Sender"?

Mfg

RavenIV 2. Aug 2005 16:47

Re: ButtonKlick ermitteln und wiedergeben
 
Zitat:

Zitat von VT-DA
Hi,

Ahh. Okay. Danke. Aber eine Frage hätte ich da noch.
Wie mache ich denn überhaupt einen "Sender"?

Mfg

in deinem Falle kannst du als Sender deine Variable "Obj" angeben, da dies ja schon ein TButton ist.

VT-DA 2. Aug 2005 16:54

Re: ButtonKlick ermitteln und wiedergeben
 
Hallo,

Sorry aber ich weiß immer noch nciht wie ich das anstellen soll. :?
Die variable Obj ist ja nur zum überprüfen da.
:gruebel:

Mfg

tigerman33 2. Aug 2005 18:43

Re: ButtonKlick ermitteln und wiedergeben
 
Hi,

Indem du OnClick aufrufst, überprüfst du nicht, ob der Button geklickt wurde. Stattdessen rufst du den Eventhandler für das Klickereignis des Buttons auf. Auf deutsch: OnClick checkt nicht, ob der Button geklickt wurde, sondern befiehlt ihm, sich so zu benehmen als sei das der Fall. Dem Ereignis OnClick gehört per Deklaration
Delphi-Quellcode:
type TNotifyEvent = procedure(Sender: TObject) of object;
der Parameter Sender an. Da steht dann drin, wer das Ereignis ausgelöst hat.

Eine Möglichkeit für dich wäre vielleicht, die Klick-Botschaft des Windows-Kernels abzufangen. Das ist aber (glaub ich) viel Aufwand und wohl auch ein bisschen Overkill. :pale: Vielleicht jemand noch ne bessere Idee?

Khabarakh 2. Aug 2005 18:54

Re: ButtonKlick ermitteln und wiedergeben
 
Wie definierst du überhaupt "wurde geklickt"? Ist die linke Mautaste genau zu dieser Zeit gedrückt oder soll es einfach der zuletzt gedrückte Button o.Ä. sein?

matze.de 2. Aug 2005 19:31

Re: ButtonKlick ermitteln und wiedergeben
 
Also du kannst entweder die WndProc deines Progs überschreiben, das geht dann so:
Delphi-Quellcode:
type
  TForm1 = Class(TForm)
    Button1: TButton;
  Private
    { Private-Deklarationen }
  Public
    { Public-Deklarationen }
    Procedure WndProc(Var Msg: TMessage); Override;
  end;
[...]
implementation
[...]
Procedure TForm1.WndProc(Var Msg: TMessage);
Begin
    If Msg.Msg = WM_COMMAND Then
    Begin
        If Msg.WParamHi = BN_CLICKED Then
        Begin
            If Msg.LParam = Button1.Handle Then
            Begin
                ShowMessage('Button1 wurde gedrückt.');
            End;
        End;
    End;
    Inherited;
End;
Oder du fängst nur die Message WM_COMMAND ab:
Delphi-Quellcode:
type
  TForm1 = Class(TForm)
    Button1: TButton;
  Private
    { Private-Deklarationen }
  Public
    { Public-Deklarationen }
    Procedure OnCommand(Var Msg: TMessage);Message WM_COMMAND;
  end;
[...]
implementation
[...]
Procedure TForm1.OnCommand(Var Msg: TMessage);
Begin
  If Msg.WParamHi = BN_CLICKED Then
  Begin
      If Msg.LParam = Button1.Handle Then
      Begin
        ShowMessage('Button1 wurde gedrückt.');
      End;
  End;
End;
mfg matze

//Edit: Oder du machst es mit nem OnClick :(

Khabarakh 2. Aug 2005 19:42

Re: ButtonKlick ermitteln und wiedergeben
 
VT-DA will aber den Status des Buttons abfragen. Und da frage ich mich eben, wie der Status des "Geklicktseins" definiert ist :gruebel: .

matze.de 2. Aug 2005 19:45

Re: ButtonKlick ermitteln und wiedergeben
 
Hm kapier die Fragestellung dann nicht.. und nicht meckern wegen meinem Quellcode ich bin atm im "Systemnahen Programmieren Feeling"...(Man häts ja auch mit OnClick machen können :mrgreen: )

mfg matze

matze.de 2. Aug 2005 20:18

Re: ButtonKlick ermitteln und wiedergeben
 
Naja, wenn du den Status eines Buttons haben willst, dann probiers mal mit
Delphi-Quellcode:
SendMessage(Button1.Handle, BM_GETSTATE, 0, 0);
Mehr dazu unter:MSDN - BM_GETSTATE

mfg matze

VT-DA 2. Aug 2005 20:58

Re: ButtonKlick ermitteln und wiedergeben
 
Hi,

hmm. Ihr verwirrt mich etwas. :)

@tigerman33
Könntest du mir vielleicht auch nochmal erklären wie ich sowas anwende?
Hab nen bischen rumexperementiert aber der sagt mir das ich Paramater fehlen wenn ich es so mache:

Delphi-Quellcode:
function ButtonClick(Obj: TButton): Integer; stdcall;
var i: Integer;
begin
  for i := Low(ButtonArray) to High(ButtonArray) do
  begin
    if Obj = ButtonArray[i].BHandel then
    begin
      if TNotifyEvent(ButtonArray[i].BHandel) = ButtonArray[i].BHandel then
        result := 1
      else
        result := 0;
    end;
  end;
end;
Dein Typ hab ich dann oben bei den anderen eingefügt...

@Der Rest
Ich möchte einfach nur eine Abfrage machen ob ein bestimmter Button geklickt wurde. Dabei ist aber zu beachten das die Fenster und Buttons variable sind. Das heißt ich kann es, wie ins matze.de's Beispiel, nicht machen weil ich das Fensterhandel ja nicht weiß. Es ist ja wie das Buttonhandel in einem Dynamischen Array gespeichert.

Mfg

VT-DA 3. Aug 2005 13:52

Re: ButtonKlick ermitteln und wiedergeben
 
Hi,

hmm. Ich sitz jetzt schon seit zwei Tagen dran.
Wirklich niemand mehr lust mir zu helfen? :pale:

Mfg

matze.de 3. Aug 2005 14:31

Re: ButtonKlick ermitteln und wiedergeben
 
Wieso lust? Ich kapier die Frage immernoch nicht.....

mfg matze

tigerman33 3. Aug 2005 18:16

Re: ButtonKlick ermitteln und wiedergeben
 
Hi VT-DA

Zitat:

Dein Typ hab ich dann oben bei den anderen eingefügt...
Tja... Das ist leider nicht mein Typ, der gehört zum Lieferumfang von Delphi. Du hast mich auch ein wenig missverstanden. Damit kannst du nicht prüfen, OB der Button gedrückt wurde. Stattdessen erzeugst du quasi einen "künstlichen" Klick. Der Parameter der fehlt, ist der Sender. Funktionieren würde es mit
Delphi-Quellcode:
if OnClick(ButtonArray[i]) = ButtonArray[i].BHandel then ...
Allerdings haut dir dann der Compiler vermutlich irgendwas in der Art von "Eine Prozedur hat keinen Rückgabewert" um die Ohren. Und warum? Weil OnClick (bzw. überhaupt ein TNotifyEvent) nicht dazu da ist, zu überprüfen, ob das entsprechend Event (also hier der Klick) eingetreten ist. Stattdessen ist es dazu gedacht, auf Ereignisse zu reagieren.

Außerdem verstehe ich nicht ganz, wofür du das ButtonArray brauchst. Alles was du damit machst, ist dir aus dem Array wieder den in Obj übergebenen Button rauszusuchen.
Delphi-Quellcode:
if Obj = ButtonArray[i].BHandel then
Warum ersetzt du also nicht die for-Schleife und arbeitest direkt mit dem Parameter Obj? Und weshalb hast du als Rückgabewert einen Integer? Das sieht nämlich eigentlich eher nach einer Boolean aus... :roll:

Matze, die Funktion steht in einer DLL, daher bringt es nichts, die WndProc des Forms zu überschreiben. Denn danach weiß zwar das Form Bescheid, dass ein Button geklickt wurde--die Funktion in der DLL aber immer noch nicht.

Aber irgendwie muss ich auch sagen dass ich nicht so richtig verstehe, wofür du diese Funktion brauchst. Kannst du das nicht irgendwie anders lösen? Erzähl doch einfach mal, was du überhaupt vorhast, vielleicht ergibt sich dann ja noch eine andere Lösung.

VT-DA 3. Aug 2005 19:44

Re: ButtonKlick ermitteln und wiedergeben
 
Hi,

Okay. Ich versuche eine GUI zu machen die auch in anderen Programmiersprachen benutzt werden kann.
Was natürlich bei einer GUi nicht fehlen darf sind Buttons. Naja. Und man muss ja die Buttons auch irgendwie ansprechen. Dazu brauch ich die Funktion.

Ich habe es bei der GUi so gemacht, dass alle Fenster / Buttons etc. in Dynamischen Arrays gespeichert werden weil ich ja nicht weiß wie viele der Anwender braucht.

Edit:
Zitat:

Zitat von tigerman33
Hi VT-DA
Außerdem verstehe ich nicht ganz, wofür du das ButtonArray brauchst. Alles was du damit machst, ist dir aus dem Array wieder den in Obj übergebenen Button rauszusuchen.
Delphi-Quellcode:
if Obj = ButtonArray[i].BHandel then
Warum ersetzt du also nicht die for-Schleife und arbeitest direkt mit dem Parameter Obj? Und weshalb hast du als Rückgabewert einen Integer? Das sieht nämlich eigentlich eher nach einer Boolean aus... :roll:

Ups. Gaanz vergessen :oops: .
Also ich übergebe bei dem Funktionsaufruf noch den Handel mit zur Fehlerkorrektur. Würde ich das nciht machen, und der Handel der dabei übergeben wurde würde falsch sein, dann würde eine Fehlermeldung kommen. Da ich das aber nicht will hab ich das so gemacht.

Ich habe den Funktionsrückgabewert auf Integer gestellt damit es leichter ist für den Benutzer. Somit brauch er nämlich nur prüfen ob o oder 1 zurück kommt.

Mfg

tigerman33 4. Aug 2005 17:05

Re: ButtonKlick ermitteln und wiedergeben
 
Hmmm...also jetzt hast du mich vollkommen verwirrt... :wiejetzt:

Der Sinn der ganzen Sache erschließt sich mir immer noch nicht ganz. Aber ich werd mal da weiterhelfen wo ich kann :)

Zitat:

Ich habe den Funktionsrückgabewert auf Integer gestellt damit es leichter ist für den Benutzer. Somit brauch er nämlich nur prüfen ob o oder 1 zurück kommt.
Aha. Das ist aber doch mit boolean noch einfacher, oder? Dann muss der Benutzer nämlich nur noch prüfen, ob das true oder false ist. Geht bei Delphi sogar mit verkürzter Syntax! Also statt
Delphi-Quellcode:
if ButtonClick(Button) = 1 then ...
reicht sogar
Delphi-Quellcode:
if ButtonClick(Button) then ...
Wenn du eine GUI schreiben willst, dann würde ich den Umweg über die Delphi-Komponenten weglassen. Dann fährst du vermutlich besser, wenn du die von der Windows-API mitgelieferten Komponenten in deiner DLL kapselst. Aber ich verstehe nicht, wozu du das machen willst...sorry :oops:

Vielleicht sollten wir uns mal im Chat treffen, da kann man ein wenig effektiver diskutieren. Außerdem wäre es nicht schlecht, mal ein bisschen mehr von deinem Quellcode zu sehen. Denn wie gesagt: Sinn und Zweck sehe ich leider immer noch nicht. Liefert deine Zielsprache für die du das alles machst denn keine GUI mit?

VT-DA 4. Aug 2005 19:50

Re: ButtonKlick ermitteln und wiedergeben
 
Hi,

Ich würde mich gerne mal mit dir im Chat treffen.
Gibs da einen offizielen Chat oder sowas?

Mfg

tigerman33 5. Aug 2005 12:32

Re: ButtonKlick ermitteln und wiedergeben
 
In DP ist doch ein Chatroom dabei, der würde sich dann ja anbieten. Ich bin unter der Woche meist so ab 16:30 Uhr , 17:00 Uhr online, da check ich dann auch DP immer. Würde dir die Zeit passen? Wenn du deinen online Status nicht versteckt hast, würd ich dann ja sehen ob du da bist. Jetzt am Wochenende weiß ich noch nicht, wann ich online bin. Vermutlich so vormittags irgendwann... :mrgreen: :dancer:

VT-DA 5. Aug 2005 12:37

Re: ButtonKlick ermitteln und wiedergeben
 
Hi,

Du meinst die ShouteBox? :wiejetzt:
Da kann man aber nicht vernünftig chatten.

Mfg

tigerman33 5. Aug 2005 12:43

Re: ButtonKlick ermitteln und wiedergeben
 
Keine Ahnung hab das noch nicht ausprobiert. Aber ich war hier schon mal in so nem komischen Chatroom. Idee wo man sonst hingehen könnte?

VT-DA 5. Aug 2005 12:47

Re: ButtonKlick ermitteln und wiedergeben
 
Hi,

Ja. Vllt kennst du dich ja mit IRC aus?
Naja:
Server: irc.blitzed.org
Port: 6667
Channel: #Delphi

Oder halt hier: http://www.blitzed.org/chat?chan=delphi

Mfg

tigerman33 5. Aug 2005 12:54

Re: ButtonKlick ermitteln und wiedergeben
 
Da bin ich jetzt mal gerade reingegangen

Sharky 5. Aug 2005 13:13

Re: ButtonKlick ermitteln und wiedergeben
 
Zitat:

Zitat von VT-DA
... Du meinst die ShouteBox? ...

Hier ihr.

Nur mal so als Info zum Thema "Chat in der DP"

http://www.sharkys-home.de/dp/chat.jpg

tigerman33 5. Aug 2005 15:49

Re: ButtonKlick ermitteln und wiedergeben
 
Hier wie versprochen der Kram den wir vorhin im Chat besprochen haben. Ich hab noch mal alles was ich an Code vorhin übern Chat gejagt hab zusammengefasst. Aber: untested.

Delphi-Quellcode:
type TMyButton = class(TButton)
      private
        FWasClicked: boolean;
        function GetWasClicked: boolean;
        procedure CNCommand(var Message: TWMCommand); message CN_COMMAND;
      public
        constructor Create(AOwner: TComponent); override;
        property WasClicked: boolean read GetWasClicked write FWasClicked;
      end;

.
. Nicht vergessen, beim Createn anstelle von TButton.Create TMyButton.Create aufzurufen!!
.

constructor TMyButton.Create(AOwner: TComponent);
begin
  inherited;
  WasClicked := false; // Initialisieren
end;

procedure TMyButton.CNCommand(var Message: TWMCommand);
begin
  // Die Methode hier wird immer aufgerufen, wenn Windows eine COMMAND-Botschaft
  // an deinen Button sendet
  if Message.NotifyCode = BN_CLICKED then // Prüfen ob's die richtige Message ist
    WasClicked := true; // Deine Eigenschaft setzen
  inherited;
end;

function TMyButton.GetWasClicked: boolean;
begin
  Result := FWasClicked;
  WasClicked := false; // Wieder resetten
end;

function ButtonClicked(Obj: TMyButton): boolean;
begin
  Result := Obj.WasClicked;
end;

.
.
.

end.
Hoffe das funktioniert jetzt alles. :-D

Khabarakh 5. Aug 2005 15:57

Re: ButtonKlick ermitteln und wiedergeben
 
Es ist schlechter Programmierstil, ein Feld im Getter zu verändern. Und warum überschreibt ihr nicht einfach Click :wink: ?

@VT-DA: Hättest du einmal dein Problem genau beschrieben, hättest du sicher nicht 4 Tage auf die Lösung warten müssen.

VT-DA 5. Aug 2005 15:59

Re: ButtonKlick ermitteln und wiedergeben
 
Hi,

es klappt perfekt. Großen Dank an tigerman33 für seine Hilfe.

Mfg

tigerman33 6. Aug 2005 06:43

Re: ButtonKlick ermitteln und wiedergeben
 
@Khabarakh:
Zitat:

Es ist schlechter Programmierstil, ein Feld im Getter zu verändern.
Hast natürlich Recht. Mea Culpa... :oops:

An Click hab ich gar nicht gedacht. Auf dem Rechner mit dem ich im Netz bin ist kein Delphi = keine RTL-Source. Aber da die Klick-procedure ja sozusagen bloß ein Muster ist, wird es auf Dauer sowieso einfacher sein, die Messagehandler zu überschreiben. Damit lässt sich das ganze "zentraler" handhaben als jede einzelne protected-Methode neu zu implementieren...

Ist letztendlich irgendwann eine Frage des persönlichen Geschmacks, denke ich.

Khabarakh 6. Aug 2005 10:16

Re: ButtonKlick ermitteln und wiedergeben
 
Zitat:

Zitat von tigerman33
Ist letztendlich irgendwann eine Frage des persönlichen Geschmacks, denke ich.

Da gebe ich dir Recht. In meinem aktuellen Projekt überschreibe ich MouseDown, MouseMove, MouseUp, DoMouseWheelDown und DoMouseWheelUp. Stattdessen eine case-Anweisung über 100 Zeilen (+ weitere verschachtelte case-Anweisungen) wäre mir persönlich zu unübersichtlich :wink: .

tigerman33 6. Aug 2005 10:58

Re: ButtonKlick ermitteln und wiedergeben
 
Das hängt immer auch davon ab, was du eigentlich an den betreffenden Stellen vorhast. Wenn in allen Fällen ähnliches Verhalten realisiert werden soll, ist es manchmal doch praktischer den Eventhandler zentral zu überschreiben. Wie immer: alles relativ und im Einzelfall zu sehen. :lol:


Alle Zeitangaben in WEZ +1. Es ist jetzt 07:24 Uhr.

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz