![]() |
Menu funktionalität ohne MainMenu
Hallo Zusammen!
Ich möchte die Funktionalität eines MainMenus ohne das Menu haben. Bedeutet... Ich definieren &Aufrufen &Nichtaufruf &Sonderfunktion CooleFunktion STRG+C Wenn keines der MDI-Childs auf Alt-A, Alt-N, Alt-S reagiert hat, möchte ich die Funktionen die hinter meinen Menüpunkten stehen aufrufen... Das Ganze aber bitte ohne das ein MainMenu dargestellt wird... Ich brauche also kein Keypreview.... sondern ein Shortcut/Accelerator wurde nicht verwendet Aufruf... Jemand ne Idee hierfür? Mavarik |
AW: Menu funktionalität ohne MainMenu
TActionList?
MfG Dalai |
AW: Menu funktionalität ohne MainMenu
Liste der Anhänge anzeigen (Anzahl: 1)
Ich verwende hier ein TApplicationEvent-Object in der Mainform. Mit der folgenden Abfrage kann ich die Shortcuts aus dem Main-Manu verwenden und die Alt+Buchstabe-Abfrage machen, um z.B. den entsprechenden Menübandeintrag (Alt+S für "Start") anzeigen zu lassen. Gleichzeitig wird sichergestellt, dass bestimmte Alt (+Strg)-Kombinationen von den üblichen Objekten (z.T. TEdit für "@-Zeichen", das man normalerweise mit Alt+Strg+E aufruft) verarbeitet werden können.
Delphi-Quellcode:
Beispiel für eine Anwendung im anliegenden Screenshot: Mainmenu ist in Form, wird aber nicht angezeigt (Stattdessen arbeite ich mit eigenen Menübändern, nutze aber die Menüeinstellungen des Mainmenus, für die der User auch benutzerdefinierte Einstellungen vornehmen kann, um so z.B. eigene Shortcuts festzulegen).
procedure Tfrm_Main.AppEvents1ShortCut(var Msg: TWMKey; var Handled: Boolean);
begin //Shortcut für mein nicht angezeigtes MainMenu? Handled := Menu1.IsShortCut(Msg); //Shortcut bzw. Key kam nicht aus dieser Form, daher hier keine weitere Prüfung //und statt dessen Verarbeitung in anderer Form (z.B. MDI) if Application.ActiveFormHandle <> self.handle then exit; if not handled then begin // Alt+Strg gedrückt? if (Getkeystate (VK_MENU) shr 15 <> 0) and (Getkeystate (VK_Control) <> 0) then begin if (msg.CharCode in [69,81]) then begin // @ und €-Zeichen wurden gedrückt Handled := false; exit; end; end; end; if not handled then begin // Tasten Alt+Buchstaben (A-Z) gedrückt? if Getkeystate (VK_MENU) shr 15 <> 0 then begin if (msg.CharCode in [65..90]) or (msg.CharCode.ToString = '186') then begin handled := True; sleep (10); // Tatsächliche Verarbeitung in der Form-KeyUp-Prozedur FormKeyup(NIL, msg.CharCode, [ssAlt]); end; end; end; end; |
AW: Menu funktionalität ohne MainMenu
In jedem Buch alla "Wie diskutiere ich richtig" steht gleich am Anfang der Tipp: vereinbaren sie zuerst ein gemeinsames Glossar, so dass die Wörter für beide das gleiche bedeuten. Sonst reden sie evtl. aneignender vorbei.
Was meinst du mit "Menu funktionalität ohne MainMenu". Du hast kein Menü oder willst du nicht ein Menü aufklappen? |
AW: Menu funktionalität ohne MainMenu
Komisch, die anderen drei (Dalai, Harry und ich) haben die Frage verstanden. Vielleicht liegts doch an Dir? ;-)
|
AW: Menu funktionalität ohne MainMenu
@Dejan Vu
Und jetzt? |
AW: Menu funktionalität ohne MainMenu
Und jetzt könntest Du deinen Beitrag überdenken. Ne wahr? ;-)
|
AW: Menu funktionalität ohne MainMenu
Alternativ könnte man auch einfach zum Thema zurück kommen. :roll:
|
AW: Menu funktionalität ohne MainMenu
Zitat:
So hab ich es jedenfalls verstanden. |
AW: Menu funktionalität ohne MainMenu
Du könntest das mit RegisterHotkey / WM_HOTKEY machen. Wobei ich nicht weiß, ob diese Hotkeys dann nicht evtl. durch die MDI-Childs verwendeten, gemergeten Menü-Hotkeys übersteuern.
|
AW: Menu funktionalität ohne MainMenu
Danke für die Antworten...
HotKey nach dem Motto STRG+F2 sind kein Thema sondern eher z.B. Alt+A Wenn ich in "Meinem Menu" Alt-A drin stehen habe, soll das natürlich nur ausgelöst werden, wenn nicht ein anderes (MDI-Child) Fenster nicht auch ALT+A benutzt um zum Beinspiel einen Button "@Aufrufen" aus zu lösen. Ich muss also wissen ob der Accelerator schon "verbraucht" ist. |
AW: Menu funktionalität ohne MainMenu
Zitat:
Bei einem MDI-Form ist das ActiveFormHandle immer das Form...?!? |
AW: Menu funktionalität ohne MainMenu
Das wäre vielleicht ein Ansatz, als Basis habe ich ein mit der "MDI-Anwendung" erstelltes Standardprojekt verwendet. Umgebogen wird Strg+V. Ist ein MDI-Child aktiv, wird der Tastendruck wieder an dieses per PostMessage weitergeleitet.
Delphi-Quellcode:
procedure FormCreate(Sender: TObject);
procedure FormDestroy(Sender: TObject); private { Private-Deklarationen } const VK_V = $56; // "V" var idVK_V : Integer; procedure WMHotKey(var Msg: TWMHotKey); message WM_HOTKEY; // Implementation procedure TMainForm.FormCreate(Sender: TObject); const MOD_CONTROL = 2; begin idVK_V := GlobalAddAtom('Control+V'); RegisterHotKey(Handle, idVK_V, MOD_CONTROL, VK_V); end; procedure TMainForm.FormDestroy(Sender: TObject); begin UnregisterHotKey(Handle, idVK_V); GlobalDeleteAtom(idVK_V); end; procedure TMainForm.WMHotKey(var Msg: TWMHotKey); begin if Msg.HotKey = idVK_V then begin if ActiveMDIChild <> nil then begin PostMessage(ActiveMDIChild.Handle, WM_KEYDOWN, VK_CONTROL, 0); PostMessage(ActiveMDIChild.Handle, WM_KEYDOWN, VK_V, 0); PostMessage(ActiveMDIChild.Handle, WM_KEYUP, VK_CONTROL, 0); PostMessage(ActiveMDIChild.Handle, WM_KEYUP, VK_V, 0); end else Showmessage('Strg+V'); end; end; |
AW: Menu funktionalität ohne MainMenu
Zitat:
@Mavarick: Was meinst du dazu? |
AW: Menu funktionalität ohne MainMenu
Zitat:
Was ist ein ein Child Fenster einen La&bel mit Focus Control auf ein TEdit hat... Kommt der Alt+B noch durch? Was fatal wäre! [Edit] Jo und so ist es auch... Eine ActionList klaut alle Tasten... @Union Aufwendig.. Muss ich mir auch näher anschauen... [EDIT] Leider falsche Reigenfolge.. bzw.. Selbst wenn ein MDI-Child active ist aber die Taste "nicht gebrauchen" kann... Wird diese ja ans Menu weitergeleitet... |
AW: Menu funktionalität ohne MainMenu
Zitat:
MfG Dalai |
AW: Menu funktionalität ohne MainMenu
Zitat:
|
AW: Menu funktionalität ohne MainMenu
Zitat:
|
AW: Menu funktionalität ohne MainMenu
Und wieso alle offnen MDIChilds durchsuchen? Das
![]() Man kann natürlich auch Funktionen über ein Interface zur Verfügung stellen:
Delphi-Quellcode:
und dann ganz simpel abfragen
IPrintable = interface
[{GUID}] function CanPrint : Boolean; procedure DoPrint; end;
Delphi-Quellcode:
procedure TMainForm.PrintActionExecute(Sender:TObject);
var LPrintable : IPrintable; begin if Supports( ActiveMDIChild, IPrintable, LPrintable ) then LPrintable.DoPrint; end; procedure TMainForm.PrintActionExecute(Sender:TObject); var LPrintable : IPrintable; begin TAction( Sender ).Enabled := Supports( ActiveMDIChild, IPrintable, LPrintable ) and LPrintable.CanPrint; end; |
AW: Menu funktionalität ohne MainMenu
Eine weitere Alternative ist das Versenden einer Nachricht
Delphi-Quellcode:
die von der Action verschickt wird
unit UserCommand;
interface uses System.Messaging; type {$SCOPEDENUMS ON} TUserCommand = ( Print, Save, SaveAs ); TUserCommandMessage = class( TMessage ) private FCommand: TUserCommand; FIsQuery: Boolean; FHandled: Boolean; public constructor Create( ACommand : TUserCommand; AIsQuery : Boolean = False ); property Command: TUserCommand read FCommand; property IsQuery: Boolean read FIsQuery; property Handled: Boolean read FHandled write FHandled; end; implementation { TUserCommandMessage } constructor TUserCommandMessage.Create(ACommand: TUserCommand; AIsQuery: Boolean); begin inherited Create; FCommand := ACommand; FIsQuery := AIsQuery; FHandled := False; end; end.
Delphi-Quellcode:
und von den Empfängern entsprechend behandelt wird
procedure TMainForm.FilePrint1Execute( Sender: TObject );
begin TMessageManager.DefaultManager.SendMessage( Self, TUserCommandMessage.Create( TUserCommand.Print ), True ); end; procedure TMainForm.FilePrint1Update( Sender: TObject ); var LCmd: TUserCommandMessage; begin LCmd := TUserCommandMessage.Create( TUserCommand.Print, True ); try TMessageManager.DefaultManager.SendMessage( Self, LCmd, False ); TAction( Sender ).Enabled := LCmd.Handled; finally LCmd.Free; end; end;
Delphi-Quellcode:
Das geht dann ohne Interfaces ... :)
procedure TMDIChild.AfterConstruction;
begin inherited; TMessageManager.DefaultManager.SubscribeToMessage( TUserCommandMessage, HandleUserCommand ); end; procedure TMDIChild.BeforeDestruction; begin TMessageManager.DefaultManager.UnSubscribe( TUserCommandMessage, HandleUserCommand ); inherited; end; procedure TMDIChild.HandleUserCommand( const Sender: TObject; const M: TMessage ); var LCmd: TUserCommandMessage absolute M; begin if not Self.Active then Exit; case LCmd.Command of TUserCommand.Print: if LCmd.IsQuery then LCmd.Handled := ( Memo1.Text <> '' ); else // Dokument drucken TUserCommand.Save: ; TUserCommand.SaveAs: ; end; end; |
AW: Menu funktionalität ohne MainMenu
Zitat:
|
AW: Menu funktionalität ohne MainMenu
Zitat:
Die Abfrage auf ActiveFormHandle erfolgt, weil ich im Hauptformular neben MDI-Fenstern auch noch normale Formulare habe, welche auch einen modalen Fokus haben können (das sind Einstellflächen als Alternative zu modalen Dialogen, aber eben innerhalb der Form). Dann sollen natürlich Shortcuts nicht ausgeführt werden können (daher dann Exit). Habe hier übrigens beim rüber kopieren aus meinem Source die Abfrage auf das Formhandle versehentlich hinter die IsShortCut-Abfrage kopiert, richtig muss es aber so lauten:
Delphi-Quellcode:
Jedenfalls funktioniert hier die Nutzung von Actions, Shortcuts (aus ActionList oder dem unsichtbaren Mainmenu), Tastaturabfragen für Form, MDI, integrierte Forms usw. wie gewünscht.
procedure THauptformular.ApplicationEvents1ShortCut(var Msg: TWMKey;
var Handled: Boolean); begin if Application.ActiveFormHandle <> self.handle then exit; handled := MainMenu1.IsShortCut(Msg); ... |
Alle Zeitangaben in WEZ +1. Es ist jetzt 20:39 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