AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Zurück Delphi-PRAXiS Programmierung allgemein Algorithmen, Datenstrukturen und Klassendesign TPopupMenu Popup überschreiben / DoPopup wird nie aufgerufen
Thema durchsuchen
Ansicht
Themen-Optionen

TPopupMenu Popup überschreiben / DoPopup wird nie aufgerufen

Ein Thema von Glados · begonnen am 19. Okt 2017 · letzter Beitrag vom 21. Okt 2017
Antwort Antwort
Glados
(Gast)

n/a Beiträge
 
#1

AW: TPopupMenu Popup überschreiben / DoPopup wird nie aufgerufen

  Alt 20. Okt 2017, 10:14
Zitat:
Wenn ja, ist diese im interface-Teil nach Menus eingebunden?
War sie nicht

Ich wusste nicht, dass das so sein muss. Danke! Gibt es denn eine Möglichkeit das irgendwie eleganter zu machen? Beispielsweise ohne ein überschriebenes DoPopup?
In procedure TPopupListEx.WndProc(var Message: TMessage); kann ich TPopupListEx(PopupList).PopupMenu auf Nil setzen. Aber umgekehrt beim Enter kann ich kein PopupMenu zuweisen, da ich keinen Sender habe. Deswegen habe ich aktuell die Lösung mit DoPopup. Aber geht das auch ohne?
  Mit Zitat antworten Zitat
Benutzerbild von Uwe Raabe
Uwe Raabe

Registriert seit: 20. Jan 2006
Ort: Lübbecke
11.757 Beiträge
 
Delphi 12 Athens
 
#2

AW: TPopupMenu Popup überschreiben / DoPopup wird nie aufgerufen

  Alt 20. Okt 2017, 12:09
Delphi-Quellcode:
procedure TPopupMenu.Popup(X, Y: Integer);
begin
// TPopupListEx(PopupList).PopupMenu := Sender as TPopupMenu; // wie komme ich hier an den Sender?

  TPopupListEx(PopupList).PopupMenu := Self; // So! Schau mal in den Original-Code von TPopupMenu.Popup...

  inherited;
end;
Du müsstest nur noch erklären, wie du aus PopupList ein TPopupListEx machst. Das geht aus deinem Code-Beispiel nicht hervor.
Uwe Raabe
Certified Delphi Master Developer
Embarcadero MVP
Blog: The Art of Delphi Programming
  Mit Zitat antworten Zitat
Glados
(Gast)

n/a Beiträge
 
#3

AW: TPopupMenu Popup überschreiben / DoPopup wird nie aufgerufen

  Alt 20. Okt 2017, 12:15
Insgesamt sieht das so aus

Delphi-Quellcode:
unit Utils.PopupMenu;

interface

uses
 Vcl.Menus, Winapi.Messages, System.Classes;

type
 TPopupMenu = class(Vcl.Menus.TPopupMenu)

 private
 protected
 public
  procedure Popup(X, Y: Integer); override;
 end;

type
 TPopupListEx = class(Vcl.Menus.TPopupList)

 private
 protected
  procedure WndProc(var Message: TMessage); override;
 public
  PopupMenu: TPopupMenu;
  MenuLoop: Boolean;
 end;

implementation

procedure TPopupMenu.Popup(X, Y: Integer);
begin
 // Wird benötigt, um an anderen Stellen im Code prüfen zu können, WELCHES PopupMenu gerade geöffnet ist
 TPopupListEx(PopupList).PopupMenu := Self;

 inherited;
end;

procedure TPopupListEx.WndProc(var Message: TMessage);
begin
 case message.msg of
  WM_ENTERMENULOOP:
   begin
    MenuLoop := True; // Menu sichtbar
   end;
  WM_EXITMENULOOP:
   begin
    MenuLoop := False; // Menu nicht mehr sichtbar
    TPopupListEx(PopupList).PopupMenu := nil;
   end;
 end;

 inherited WndProc(message);
end;

initialization

Vcl.Menus.PopupList.Free;
Vcl.Menus.PopupList := TPopupListEx.Create;

end.
Stat WndProc > WM_EXITMENULOOP wollte ich eigentlich TPopupMenu > CloseMenu überschreiben aber das ist nicht erlaubt.

Geändert von Glados (21. Okt 2017 um 12:14 Uhr)
  Mit Zitat antworten Zitat
Benutzerbild von Uwe Raabe
Uwe Raabe

Registriert seit: 20. Jan 2006
Ort: Lübbecke
11.757 Beiträge
 
Delphi 12 Athens
 
#4

AW: TPopupMenu Popup überschreiben / DoPopup wird nie aufgerufen

  Alt 20. Okt 2017, 12:27
Nur so 'ne Idee: Du könntest auch in der WndProc auf WM_INITMENUPOPUP (Sent when a drop-down menu or submenu is about to become active.) reagieren und das aktuelle PopupMenu anhand des Handles suchen. Dann sparst du dir die Ableitung von TPopupMenu ganz:

Delphi-Quellcode:
    
 case message.msg of
   WM_INITMENUPOPUP:
   begin
     for I := 0 to Count - 1 do begin
       if TPopupMenu(Items[I]).Handle = TWMInitMenuPopup(Message).MenuPopup then begin
         { sollte nie erreicht werden, wenn ein SubMenu geöffnet wird }
         PopupMenu := TPopupMenu(Items[I]);
         Break;
       end;
     end;
   end;
   WM_ENTERMENULOOP:
   begin
     MenuLoop := True; // Menu sichtbar
   end;
   WM_EXITMENULOOP:
   begin
     MenuLoop := False; // Menu nicht mehr sichtbar
     PopupMenu := nil;
   end;
 end;
Uwe Raabe
Certified Delphi Master Developer
Embarcadero MVP
Blog: The Art of Delphi Programming
  Mit Zitat antworten Zitat
Glados
(Gast)

n/a Beiträge
 
#5

AW: TPopupMenu Popup überschreiben / DoPopup wird nie aufgerufen

  Alt 20. Okt 2017, 12:47
Das ist natürlich die elegantere Lösung.

for I := 0 to Count - 1 do Warum genau denn bis Count-1? Geht man hier einfach auf verdacht bis in einen sehr hohen Bereich?
  Mit Zitat antworten Zitat
Benutzerbild von Uwe Raabe
Uwe Raabe

Registriert seit: 20. Jan 2006
Ort: Lübbecke
11.757 Beiträge
 
Delphi 12 Athens
 
#6

AW: TPopupMenu Popup überschreiben / DoPopup wird nie aufgerufen

  Alt 20. Okt 2017, 12:55
for I := 0 to Count - 1 do Warum genau denn bis Count-1? Geht man hier einfach auf verdacht bis in einen sehr hohen Bereich?
In PopupList registriert sich jede TPopupMenu-Instanz beim Create und meldet sich im Destroy wieder ab. Die aktuelle Anzahl der Einträge einer Liste steht in Count und das erste Element hat den Index 0. Deswegen durchläuft for I := 0 to Count - 1 do die gesamte Liste. Da wir in der Message lediglich das Handle des Menüs bekommen, suchen wir die dazu passende Instanz in der For-Schleife. Sobald diese gefunden ist, bricht das Break die Schleife ab.
Uwe Raabe
Certified Delphi Master Developer
Embarcadero MVP
Blog: The Art of Delphi Programming
  Mit Zitat antworten Zitat
Glados
(Gast)

n/a Beiträge
 
#7

AW: TPopupMenu Popup überschreiben / DoPopup wird nie aufgerufen

  Alt 20. Okt 2017, 13:03
Danke für die Erklärung!
  Mit Zitat antworten Zitat
Antwort Antwort


Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 04:29 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