function ExecMenuItemAction(Cmd: Integer;
var Count: Integer; Item: TMenuItem): Boolean;
var
ix: Integer;
begin
Result := false;
ix := 0;
while ix < Item.Count
do
begin
Application.ProcessMessages;
if Cmd = Count
then
begin
Item[ix].Click;
Result := true;
Exit;
end;
if Item.Items[ix].Count > 0
then
ExecMenuItemAction(Cmd,Count,Item.Items[ix]);
Inc(Count);
Inc(ix);
end;
end;
procedure ContextMenuForFile(FileName: TFileName; X, Y: Integer;
Handle: HWND);
var
mPopup: HMENU;
iCmd, iCount: Integer;
mCmdInfo: TCMInvokeCommandInfo;
mPIDL: PItemIDList;
mShellFolder: IShellFolder;
S:
String;
begin
mPIDL := SHGetIDListFromPath(FileName, mShellFolder);
if not Assigned(mPIDL)
then
Exit;
OLECheck(mShellFolder.GetUIObjectOf(
Handle, 1, mPIDL, IID_IContextMenu,
nil,
Pointer(mContextMenu)));
mPopup := CreatePopUpMenu;
if mPopup = 0
then
Exit;
try
OLECheck(mContextMenu.QueryContextMenu(Form1.PopupMenu1.Handle
{mPopup}, 0
{Index}, 0
{idCmdFirst}, 0
{_$7FFF}{idCmdLast}, CMF_NORMAL));
OLECheck(mContextMenu.QueryInterface(IID_IContextMenu2, mContextMenu2));
try
iCmd := Integer(TrackPopupMenuEx(Form1.PopupMenu1.Handle
{mPopup}, TPM_LEFTALIGN
or
TPM_RIGHTBUTTON
or TPM_HORIZONTAL
or TPM_VERTICAL
or TPM_RETURNCMD, X, Y,
Handle,
nil));
// Hint anzeigen
SetLength(S,40);
mContextMenu.GetCommandString(iCmd,GCS_HELPTEXT,
nil,PChar(S),SizeOf(S));
Form1.StatusBar1.Panels[0].Text := S;
// "OnClick" Ereignisse ausführen
if iCmd <> 0
then
begin
FillChar(mCmdInfo, SizeOf(mCmdInfo), 0);
with mCmdInfo
do
begin
cbSize := SizeOf(TCMInvokeCommandInfo);
lpVerb := MakeIntResource(iCmd - 1);
nShow := SW_SHOWNORMAL;
end;
try
if not Succeeded(mContextMenu.InvokeCommand(mCmdInfo))
then
begin
iCount := 1;
ExecMenuItemAction(iCmd,iCount,Form1.PopupMenu1.Items);
end;
except
// nichts tun
end;
end;
finally
mContextMenu :=
nil;
mContextMenu2 :=
nil;
end;
finally
DestroyMenu(mPopup);
end;
end;