プロセス[メモ帳]を起動し(CreateProcess)、プロセスの起動を待ち(WaitForInputIdle)、プロセスの終了を待つ(WaitForSingleObject) ~Delphiでお手軽プログラミング
ソースコードの記述
Windows11の新しい「メモ帳」はnotepad.exeを起動(プロセスが生成しプロセスIDを取得)すると起動したプロセスとは別のプロセスを起動(別のプロセスID)するので、以下のサンプルソースコードは 古い「メモ帳」でなければ動かないことに注意してください。
Windows11で古い「メモ帳」に切り替えるには
[スタート]⇒[設定]⇒[アプリ]⇒[アプリの詳細設定]⇒[アプリ実行エイリアス] から 「メモ帳」の右側をオフにします。
Delphiを起動し、メニューから「ファイル」⇒「新規作成」⇒「Windows VCLアプリケーション -Delphi(W)」 をクリックする。
TButtonとTMemoをドラッグ&ドロップして配置し、Button1をダブルクリックして以下のソースコードを入力します。
procedure TForm1.Button1Click(Sender: TObject);
var StartupInfo:TStartupInfo;
ProcessInformation:TProcessInformation;
RetVal:Cardinal;
RetValBool:LongBool;
pFileName:PChar;
FileName:String;
begin
Memo1.Lines.Clear;
//メモ帳 の実行ファイル名
FileName:='notepad.exe';
pFileName:=@FileName[1];
ZeroMemory(@StartupInfo,SizeOf(TStartupInfo));
StartupInfo.cb:=SIzeOf(TStartupInfo);
StartupInfo.dwFlags:=STARTF_USESHOWWINDOW;
StartupInfo.wShowWindow:=SW_SHOW;
//プロセスを起動する
RetValBool:=CreateProcess(
nil, pFileName,
nil, nil, False,
NORMAL_PRIORITY_CLASS, nil, nil,
Startupinfo, ProcessInformation
);
if RetValBool=False then
begin
Memo1.Lines.Add( Filename+'の起動に失敗しました('+GetLastError.ToString+')' );
Exit;
end;
//プロセスの起動を待つ
repeat
//指定プロセスがユーザー入力の待機状態になるまで、
//又は指定タイムアウト時間が経過するまで待機する
//戻り値
// 0:待機が正常に行われた
// WAIT_TIMEOUT:タイムアウト時間が経過
// WAIT_FAILED :エラーが発生
RetVal:=WaitForInputIdle(ProcessInformation.hProcess,100);
application.ProcessMessages;
until RetVal<>WAIT_TIMEOUT; //タイムアウト(100ms経過)ならループ
if RetVal=WAIT_FAILED then
begin
Memo1.Lines.Add('起動待ちでエラー('+GetLastError.ToString+')');
CloseHandle(ProcessInformation.hProcess);
CloseHandle(ProcessInformation.hThread);
Exit;
end;
Memo1.Lines.Add(Filename+'が起動しました');
//プロセスの終了を待つ
repeat
//シグナル状態(終了状態)になるか
//タイムアウト間隔が経過するまで待機する
//戻り値
// WAIT_OBJECT_0:オブジェクトがシグナル状態になった
// WAIT_TIMEOUT:タイムアウト時間が経過
// WAIT_FAILED:エラーが発生
RetVal:=WaitForSingleObject(ProcessInformation.hProcess,100);
application.ProcessMessages;
until RetVal<>WAIT_TIMEOUT; //タイムアウト(100ms経過)しただけならループ
if RetVal=WAIT_FAILED then
begin
Memo1.Lines.Add('終了待ちでエラー('+GetLastError.ToString+')');
end
else
begin
Memo1.Lines.Add(Filename+'が終了しました');
end;
CloseHandle(ProcessInformation.hProcess);
CloseHandle(ProcessInformation.hThread);
end;
実行する
実行して「Button1」をクリックするとメモ帳が起動し「notepad.exeが起動しました」と表示され、メモ帳を終了すると「notepad.exeが終了しました」と表示されます。
