БлогNot. C# Windows Forms: запускаем и завершаем внешние приложения

C# Windows Forms: запускаем и завершаем внешние приложения

Формально проблема несложна - подключив к проекту пространство имён

using System.Diagnostics;

мы можем запускать внешние приложения кодом вида

 Process p = Process.Start("notepad.exe");

(в данном случае файл находится в одной из прописанных в системной переменной Path папок, поэтому указываем только имя исполняемого файла) и завершать его строкой

 p.CloseMainWindow();

Увы, это не решает как минимум следующих проблем:

  • метод CloseMainWindow не гарантирует, что приложение действительно закрыто или что процесс завершился, а лишь информирует, что отправлено сообщение закрытия основному окну процесса;
  • одноимённых процессов может быть несколько или не быть вовсе;
  • имя процесса (оно видно, например, на вкладке "Подробности" Диспетчера задач Windows 10) может отличаться от имени исполняемого файла (например, для стандартного калькулятора запускается процесс CalculatorApp, а имя файла calc.exe, хотя обычно имя процесса - это имя исполняемого файла без расширения, то есть, notepad для notepad.exe);
  • процесс может просто запускать другой процесс с другим идентификатором, а сам завершаться, как делает тот же Калькулятор;
  • процесс может быть закрыт независимо от работы приложения, пока оно остаётся запущенным, при этом он должен удаляться из списка запущенных нами процессов (установить EnableRaisingEvents = true и обработку события Exited);
  • по неизвестным причинам MainWindowHandle у процесса может оказываться нулём и тогда CloseMainWindow не срабатывает, а завершить процесс программно можно разве что через Kill (принудительное завершение без сохранения данных);
  • вызов Kill тоже может порождать исключения, например, если не хватает прав или система не успевает обработать завершение;
  • во всех случаях имеет смысл подождать закрытия окна методом WaitForExit;
  • при массовом закрытии процессов в цикле отсутствие паузы между закрытиями может стать причиной ошибок, таких как System.ComponentModel.Win32Exception, например, если процесс еще не завершился, а мы пытаемся его принудительно убить или послать ему закрытие.

В прилагаем проекте мы пытаемся учесть все эти моменты с помощью нескольких методов:

  • void process_Run (string filePath, string appName) - создаёт процесс вызовом process_Start, создаёт объект processInfo для процесса и заносит объект в список List <ProcessInfo> processes;
  • Process process_Start (String filePath) - открывает и возвращает процесс или null;
  • void process_End (ProcessInfo process) - для закрытия процесса, информация о котором сохранена в объекте пользовательского класса ProcessInfo, содержащего свойства string FilePath, string AppName, Process Process;
  • void process_Stop (String appName) - ищет последний по времени запуска процесс с именем appName и вызывает для него process_End. Отдельно отслеживается ситуация, когда процесс не был нами запущен и не попал в наш список (например, был запущен до старта программы).

Эти методы применяются для открытия и закрытия произвольного количества стандартных приложений Калькулятор, Блокнот и Paint по принципу:

process_Run ("calc.exe", "CalculatorApp");
process_Run ("notepad.exe", "notepad");
//...
process_Stop("CalculatorApp");
process_Stop("notepad");

Методы выводят текстовые сообщения в многострочное поле textBox1, занимающее основную часть окна.

При выходе из приложения через меню Файл - Выход закрываются те экземпляры указанных приложений, которые мы открывали.

Существенно, что экземпляров Калькулятора к моменту выхода через меню в нашем списке уже не окажется, так как calc.exe запускает CalculatorApp.exe, который, в свою очередь, его завершает. Но для большинства приложений (в том числе для двух других тестовых) этой проблемы не возникает. Зато через меню Файл - Имя приложения - Стоп можно закрыть и те экземпляры приложений, которые мы не запускали, без вылета, если закрытие не удаётся (например, для экземпляра Калькулятора, часто запускаемого системой и болтающегося в процессах - у пользователя нет возможности его закрыть иначе, как сняв через Диспетчер задач с правами администратора).

Вывод - подход работает для "обычных" приложений, не ведущих себя так, как Калькулятор Windows.

скриншот окна приложения
скриншот окна приложения

 Скачать проект C# Windows Forms в архиве .zip, развернуть в новую папку (Visual Studio 2019 и выше) (13 Кб)

13.01.2026, 00:10 [287 просмотров]


теги: программирование c# список учебное windows

К этой статье пока нет комментариев, Ваш будет первым