3

我可以使用 FileSaveDialog1.Dialog.QueryInterface 创建一个按钮,如下所示。您如何设置和处理 OnPushButton 单击事件,以便我可以响应按钮单击?

procedure TForm1.FileSaveDialog1Execute(Sender: TObject);
const
  dwVisualGroup1ID: DWORD = 1900;
var
  c: IFileDialogCustomize;
  d: IFileDialogControlEvents;
begin
  if FileSaveDialog1.Dialog.QueryInterface(IFileDialogCustomize, c) = S_OK then
  begin
    // Add a Advanced Button
    c.AddPushButton(dwVisualGroup1ID, 'Advanced');
    c.MakeProminent(dwVisualGroup1ID);
    // Setup the PushButton Click event?

  end;
4

2 回答 2

9

以下在 XE2 中对我来说很好用:

type
  TMyFileDialogEvents = class(TInterfacedObject, IFileDialogEvents, IFileDialogControlEvents)
  public
    { IFileDialogEvents }
    function OnFileOk(const pfd: IFileDialog): HResult; stdcall;
    function OnFolderChanging(const pfd: IFileDialog;
      const psiFolder: IShellItem): HResult; stdcall;
    function OnFolderChange(const pfd: IFileDialog): HResult; stdcall;
    function OnSelectionChange(const pfd: IFileDialog): HResult; stdcall;
    function OnShareViolation(const pfd: IFileDialog; const psi: IShellItem;
      out pResponse: DWORD): HResult; stdcall;
    function OnTypeChange(const pfd: IFileDialog): HResult; stdcall;
    function OnOverwrite(const pfd: IFileDialog; const psi: IShellItem;
      out pResponse: DWORD): HResult; stdcall;
    { IFileDialogControlEvents }
    function OnItemSelected(const pfdc: IFileDialogCustomize; dwIDCtl: DWORD;
      dwIDItem: DWORD): HResult; stdcall;
    function OnButtonClicked(const pfdc: IFileDialogCustomize;
      dwIDCtl: DWORD): HResult; stdcall;
    function OnCheckButtonToggled(const pfdc: IFileDialogCustomize;
      dwIDCtl: DWORD; bChecked: BOOL): HResult; stdcall;
    function OnControlActivating(const pfdc: IFileDialogCustomize;
      dwIDCtl: DWORD): HResult; stdcall;
  end;

const 
  dwVisualGroup1ID: DWORD = 1900; 

function TMyFileDialogEvents.OnFileOk(const pfd: IFileDialog): HResult;
begin
  Result := E_NOTIMPL;
end;

function TMyFileDialogEvents.OnFolderChange(const pfd: IFileDialog): HResult;
begin
  Result := E_NOTIMPL;
end;

function TMyFileDialogEvents.OnFolderChanging(const pfd: IFileDialog;
  const psiFolder: IShellItem): HResult;
begin
  Result := E_NOTIMPL;
end;

function TMyFileDialogEvents.OnOverwrite(const pfd: IFileDialog;
  const psi: IShellItem; out pResponse: DWORD): HResult;
begin
  Result := E_NOTIMPL;
end;

function TMyFileDialogEvents.OnSelectionChange(const pfd: IFileDialog): HResult;
begin
  Result := E_NOTIMPL;
end;

function TMyFileDialogEvents.OnShareViolation(const pfd: IFileDialog;
  const psi: IShellItem; out pResponse: DWORD): HResult;
begin
  Result := E_NOTIMPL;
end;

function TMyFileDialogEvents.OnTypeChange(const pfd: IFileDialog): HResult;
begin
  Result := E_NOTIMPL;
end;

function TMyFileDialogEvents.OnItemSelected(const pfdc: IFileDialogCustomize; dwIDCtl: DWORD; dwIDItem: DWORD): HResult;
begin
  Result := E_NOTIMPL;
end;

function TMyFileDialogEvents.OnButtonClicked(const pfdc: IFileDialogCustomize; dwIDCtl: DWORD): HResult;
begin
  if dwIDCtl = dwVisualGroup1ID then begin
    // ...
    Result := S_OK;
  end else begin
    Result := E_NOTIMPL;
  end;
end;

function TMyFileDialogEvents.OnCheckButtonToggled(const pfdc: IFileDialogCustomize; dwIDCtl: DWORD; bChecked: BOOL): HResult;
begin
  Result := E_NOTIMPL;
end;

function TMyFileDialogEvents.OnControlActivating(const pfdc: IFileDialogCustomize; dwIDCtl: DWORD): HResult;
begin
  Result := E_NOTIMPL;
end;

.

var
  FileDialog: IFileDialog = nil;
  MyEvents: IFileDialogEvents = nil; 
  MyEventsCookie: DWORD = 0;

procedure TForm1.FileSaveDialog1Execute(Sender: TObject); 
var 
  c: IFileDialogCustomize; 
  d: IFileDialogEvents; 
  cookie: DWORD;
begin 
  if Supports(FileSaveDialog1.Dialog, IFileDialogCustomize, c) then 
  begin 
    // Add a Advanced Button 
    c.AddPushButton(dwVisualGroup1ID, 'Advanced'); 
    c.MakeProminent(dwVisualGroup1ID); 

    // Setup the PushButton Click event 
    d := TMyFileDialogEvents.Create; 
    if Succeeded(FileSaveDialog1.Dialog.Advise(d, cookie)) then
    begin
      FileDialog := FileSaveDialog1.Dialog
      MyEvents := d;
      MyEventsCookie := cookie;
    end;
  end; 
end;

procedure TForm1.Button1Click(Sender: TObject); 
var
  Ok: Boolean;
begin
  FileDialog := nil;
  MyEvents := nil; 
  MyEventsCookie := 0;

  try
    Ok := FileSaveDialog1.Execute;
  finally
    if (FileDialog <> nil) and (MyEventsCookie <> 0) then
      FileDialog.Unadvise(MyEventsCookie);
    FileDialog := nil;
    MyEvents := nil; 
    MyEventsCookie := 0;
  end;

  if Ok then ...
end;
于 2012-06-04T23:09:48.340 回答
2

您需要实现 IFileDialogControlEvents。然后调用 IFileDialog.Advise 传递您的 IFileDialogControlEvents 接口。单击按钮时将调用您的 IFileDialogControlEvents.OnButtonClicked 方法。

于 2012-06-04T22:06:02.243 回答