从 Delphi 通过命令行启动应用程序后关闭 CMD Window

Closing a CMD Window after launching an application through command line from Delphi

我正在尝试执行以下操作。它有效,但 cmd window 等待 acrobat.exe 在退出前完成执行。我必须使用这种启动方式,因为我打算将来传递某些命令行参数。

cmdLineString := Format('/c ""%s" "%s""',['C:\Program Files (x86)\Adobe\Acrobat 11.0\Acrobat\Acrobat.exe', 'F:\Android-interview\Packt.Android.3.0.Application.Development.Cookbook.Jul.2011.ISBN.1849512949.pdf']);
ShellExecute(Handle, 'open', 'cmd.exe', PChar(CmdLineString), nil, SW_SHOWNORMAL);

有多种方法可以改善这一点:

  1. 不要使用 ShellExecute。这样做很诱人,因为调用起来很简单。但是,它不是很灵活。请改用 CreateProcess
  2. 如果您必须隐藏控制台 window,请将 CREATE_NO_WINDOW 标志传递给 CreateProcess
  3. 也就是说,在这里使用 cmd 没有意义。您不需要创建一个进程来创建另一个进程。这样做实际上使传递论点变得更加困难。直接创建 Acrobat 进程。切掉中间人。

正如 David 所回答的那样,在回答了一些关于 CreateProcess 的其他问题之后,解决方案代码最终如下所示。放在这里是为了像我这样的初学者。想想看这段代码可以做些什么!谢谢,Delphi。

procedure TForm.btnCMDLaunchClick(Sender: TObject);
var
   commandLine: string;
   si: TStartupInfo;
   pi: TProcessInformation;
begin
   commandLine := Format('%s %s',['C:\Program Files (x86)\Adobe\Acrobat 11.0\Acrobat\Acrobat.exe', 'F:\Android-interview\Packt.Android.3.0.Application.Development.Cookbook.Jul.2011.ISBN.1849512949.pdf']);
   UniqueString(commandLine);
   si := Default(TStartupInfo);
   si.cb := sizeof(si);

      if CreateProcess(
        PChar(nil),         //no module name (use command line)
        PChar(commandLine), //Command Line
        nil,                //Process handle not inheritable
        nil,                //Thread handle not inheritable
        False,              //Don't inherit handles
        0,                  //No creation flags
        nil,                //Use parent's environment block
        PChar(nil),         //Use parent's starting directory
        si,                 //Startup Info
        pi                  //Process Info
      ) then begin
       CloseHandle(pi.hProcess);
       CloseHandle(pi.hThread);
      end;
end;