2

我是 [Microsoft Windows] 安装程序和Inno Setup的新手,但我需要知道是否可以使用 Inno Setup(或等效程序)在安装过程中自动输入基于 GUI 的 Windows 程序,例如通过单击菜单并选择一个子项目,例如?

我知道AutoItAutoHotkey以及NSIS,但是强烈建议将 Inno Setup 作为软件包程序/安装程序,我也喜欢学习一点 Pascal 编程的想法,以讨价还价;)

任何想法或想法都是最受欢迎的:-)

4

2 回答 2

3

我同意@Deanna,该SendInput功能最适合模拟您可以获得的用户输入。在下面的脚本中,我展示了如何在绝对屏幕位置(以像素为单位)上模拟鼠标点击。例如,我试图通过Help / About Inno Setup菜单项显示 Inno Setup 的 about 框(如果您的屏幕设置与我相同并且 Inno Setup IDE 最大化,它甚至可能会点击该菜单项。所以这里只是鼠标部分(你只能获得有限的功能)。把它作为一个证据,它可以模拟来自 Inno Setup 的用户输入:

[Setup]
AppName=My Program
AppVersion=1.5
DefaultDirName={pf}\My Program
OutputDir=userdocs:Inno Setup Examples Output

[code]
const
  SM_CXSCREEN = 0;
  SM_CYSCREEN = 1;
  INPUT_MOUSE = 0;
  MOUSEEVENTF_MOVE = $0001;
  MOUSEEVENTF_LEFTDOWN = $0002;
  MOUSEEVENTF_LEFTUP = $0004;
  MOUSEEVENTF_RIGHTDOWN = $0008;
  MOUSEEVENTF_RIGHTUP = $0010;
  MOUSEEVENTF_MIDDLEDOWN = $0020;
  MOUSEEVENTF_MIDDLEUP = $0040;
  MOUSEEVENTF_VIRTUALDESK = $4000;
  MOUSEEVENTF_ABSOLUTE = $8000;
type
  TMouseInput = record
    Itype: DWORD;    
    dx: Longint;
    dy: Longint;
    mouseData: DWORD;
    dwFlags: DWORD;
    time: DWORD;
    dwExtraInfo: DWORD;
  end;

function GetSystemMetrics(nIndex: Integer): Integer;
  external 'GetSystemMetrics@user32.dll stdcall';
function SendMouseInput(nInputs: UINT; pInputs: TMouseInput;
  cbSize: Integer): UINT; 
  external 'SendInput@user32.dll stdcall';

function SendMouseClick(Button: TMouseButton; X, Y: Integer): Boolean;
var
  Flags: DWORD;
  Input: TMouseInput;
  ScreenWidth: Integer;
  ScreenHeight: Integer;
begin
  Result := False;
  Flags := MOUSEEVENTF_ABSOLUTE or MOUSEEVENTF_VIRTUALDESK or MOUSEEVENTF_MOVE;
  ScreenWidth := GetSystemMetrics(SM_CXSCREEN);
  ScreenHeight := GetSystemMetrics(SM_CYSCREEN);

  Input.Itype := INPUT_MOUSE;
  Input.dx := Round((X * 65536) / ScreenWidth);
  Input.dy := Round((Y * 65536) / ScreenHeight);
  case Button of
    mbLeft: Input.dwFlags := Flags or MOUSEEVENTF_LEFTDOWN;
    mbRight: Input.dwFlags := Flags or MOUSEEVENTF_RIGHTDOWN;
    mbMiddle: Input.dwFlags := Flags or MOUSEEVENTF_MIDDLEDOWN;
  end;  
  Result := SendMouseInput(1, Input, SizeOf(Input)) = 1;

  if Result then
  begin
    Input.Itype := INPUT_MOUSE;
    Input.dx := Round((X * 65536) / ScreenWidth);
    Input.dy := Round((Y * 65536) / ScreenHeight);
    case Button of
      mbLeft: Input.dwFlags := Flags or MOUSEEVENTF_LEFTUP;
      mbRight: Input.dwFlags := Flags or MOUSEEVENTF_RIGHTUP;
      mbMiddle: Input.dwFlags := Flags or MOUSEEVENTF_MIDDLEUP;
    end;    
    Result := SendMouseInput(1, Input, SizeOf(Input)) = 1;
  end;
end;

procedure InitializeWizard;
begin
  if MsgBox('Are you sure you want to let the installer click ' +
    'somewhere on your screen ? TLama warned you :-)', mbConfirmation, 
    MB_YESNO) = IDYES then
  begin
    if not SendMouseClick(mbLeft, 242, 31) then 
      MsgBox(SysErrorMessage(DLLGetLastError), mbError, mb_Ok);
    if not SendMouseClick(mbLeft, 382, 263) then 
      MsgBox(SysErrorMessage(DLLGetLastError), mbError, mb_Ok);
  end;
end;
于 2013-02-07T12:03:50.100 回答
1

最好的办法是使用SendInput()DLL 中的 API,然后从 Inno Setup 中调用该 API。这将允许您完全控制您可以在该应用程序中手动执行的所有操作。

于 2013-02-07T09:22:10.453 回答