3

場合によっては、コマンドラインpowerpnt.exe /sから新しいプログラム (たとえば、コマンド ライン " " でスライドショーとして開くことができる Windows Powerpoint プレゼンテーション) を開き、このプログラムを最大化して、ユーザーが表示および使用できる最初のプログラムとしてデスクトップの前面に表示する必要があります。これは、コマンド プロンプトがアクティブなウィンドウであるため、ユーザーがコマンド プロンプトにコマンドを直接入力すると、デフォルトで発生します。

しかし、問題は、コマンド ラインがバックグラウンド プロセスから実行された場合 (たとえば、Windows タスク シェーデュラーのカスタム Windows サービス アプリケーションから)、これを行う方法です。どちらの場合も、新しいウィンドウは最初のウィンドウとして表示されません。

現時点では、非常に難しいソリューションしか想像できません (コーディングが必要で、タスク スケジューラから使用できないという欠点があります)。

  1. 開いているプログラムのメイン ウィンドウのハンドルを取得して、このウィンドウを操作することができます。たとえば、最大化などです。
  2. コマンド ラインをまったく放棄して、代わりに Windows Office アプリケーションを COM オブジェクトとして操作することもできます。

多分もっと簡単な方法がありますか?

4

2 に答える 2

4

新しいプログラムを呼び出す小さな (GUI 以外の) ランチャー アプリケーションを作成し (それがハード ソリューションと呼ばれていることを知っています)、タスク スケジューラでこのランチャーをスケジュールすることができます。

このランチャー アプリケーションは、de プロセス ( CreateProcess 関数) を作成し、pID からウィンドウ ハンドルを取得する必要があります。ウィンドウ ハンドルを使用すると、SetForegroundWindow を使用して必要なことを実行したり、最大化などのために他の関数を呼び出したりできます。 .

あなたがデルファイにタグを付けたので、その可能性のあるデルファイ実装を投稿しています。

function WindowFromPID(pID: Cardinal; VisibleWindow: Boolean): Cardinal;
type
  TProcData = record
    pID: Cardinal;
    pHandle: Cardinal;

    VisibleWindow: Boolean;
  end;

var 
  wPData: TProcData;

  function EnumProc(Handle: HWND; var pProcData: TProcData): Bool; stdcall;
  var pID: DWORD;
  begin
    Result := True;
    if pProcData.VisibleWindow then
      if not IsWindowVisible(Handle) then
        Exit;

    GetWindowThreadProcessId(Handle, @pID);
    if pID = pProcData.pID then begin
      if GetWindow(Handle, GW_OWNER) = 0 then begin
        pProcData.pHandle := Handle;
        Result := false;
      end;
    end;
  end;
begin
  wPData.pHandle := 0;
  wPData.pID := pID;
  wPData.VisibleWindow := VisibleWindow;

  EnumWindows(@EnumProc, Integer(@wPData));
  while (wPData.pHandle = 0) do begin
    Sleep(50);
    EnumWindows(@EnumProc, Integer(@wPData));
  end;

  Result := wPData.pHandle;
end;

procedure RunAndGetWindowHandle(const FileName, Params: String; const WindowState: Word): Cardinal;
var 
  SUInfo: TStartupInfo;
  CmdLine: String;
  ProcInfo: TProcessInformation
begin
  CmdLine := '"' + Filename + '"' + Params;
  FillChar(SUInfo, SizeOf(SUInfo), #0);
  with SUInfo do begin
    cb := SizeOf(SUInfo);
    dwFlags := StartF_UseShowWindow;
    wShowWindow := WindowState;
  end;

  if not CreateProcess(Nil, PChar(CmdLine), nil, nil, False, Create_New_Console Or Normal_Priority_Class, nil, PChar(ExtractFilePath(Filename)), SUInfo, ProcInfo) then
    raise Exception.Create('Error running process');

  if WaitForSingleObject(ProcInfo.hProcess, 50) <> WAIT_TIMEOUT then
    raise Exception.Create('Error running process!');

  CloseHandle(ProcInfo.hThread);
  while Result = 0 do begin
    Sleep(50);
    Result := WindowFromPID(ProcInfo.dwProcessId, true);
  end;
end;

...

var WindowHandle: Cardinal;
begin
  WindowHandle := RunAndGetWindowHandle("powerpnt.exe", " /s", SW_SHOWNORMAL);
  SetForegroundWindow(WindowHandle);
end;

それがあなたが必要とするものであることを願っています..そうでない場合は申し訳ありません。

よろしくお願いします。

于 2013-01-12T21:49:22.573 に答える
0

必要なプログラムを開くバッチ ファイルを作成し、タスク スケジューラでそれを実行ます。

バッチ ファイルは、ユーザーがコマンド プロンプトにコマンドを直接入力したかのように実行され、目的の結果が得られます。

于 2013-01-12T22:07:49.677 に答える