15

我有 2 个在 .NET 中创建的程序 (.exe)。我们称他们为 Master 和 Worker。Master 启动 1 个或多个 Worker。Worker不会与用户交互,但它是一个 WinForms 应用程序,它接收命令并根据从 Master 接收到的命令运行 WinForms 组件。

我希望 Worker 应用程序完全隐藏运行(当然除了显示在任务管理器中)。我认为我可以使用StartInfo.CreateNoWindowStartInfo.WindowStyle属性来完成此操作,但我仍然在表单中看到 Client.exe 窗口和组件。但是,它不会显示在任务栏中。

   Process process = new Process
      {
          EnableRaisingEvents = true,
          StartInfo =
              {
                  CreateNoWindow = true,
                  WindowStyle = ProcessWindowStyle.Hidden,
                  FileName = "Client.exe",
                  UseShellExecute = false,
                  ErrorDialog = false,
              }
      };

我需要怎么做才能让 Client.exe 运行,但不显示?ㅤㅤㅤㅤㅤ</p>

4

4 回答 4

10

您在我的系统上使用 notepad.exe 可以正常使用CreateNoWindow/ WindowStyle(例如,它被隐藏但在后台运行),所以这可能是 WinForms 应用程序正在做的事情。一些想法:

选项 1:如果您控制 WinForms 工作进程,则可以覆盖Control.SetVisibleCore以始终隐藏表单。如果你不想总是隐藏它,你可以传递一个命令行参数给它,例如/hide这会导致它被隐藏。示例(假设表单已经有代码隐藏):

public partial class MyForm : Form
{
    public MyForm()
    {
        InitializeComponent();
    }

    protected override void SetVisibleCore(bool value)
    {
        // You'd probably want to parse the command line.
        if (Environment.CommandLine.Contains("/hide"))
            base.SetVisibleCore(false);
        else
            base.SetVisibleCore(value);
    }
}

这样,运行就会MyForm.exe产生一个具有可见形式的进程。运行MyForm.exe /hide会导致具有隐藏表单的进程。你可以从你的主进程传递/hide参数,这样运行应用程序的普通用户仍然可以看到它。

选项 2:您可以在应用程序启动后通过执行 P/Invoke 来隐藏应用程序ShowWindow。更多信息在这里。这样做的缺点是您有时会看到工作窗口在隐藏之前闪烁。例子:

class Program
{
    public static void Main(string[] args)
    {
        ProcessStartInfo psi = new ProcessStartInfo()
        {
            FileName = @"C:\windows\system32\notepad.exe",
        };

        Process process = Process.Start(psi);

        // Wait until the process has a main window handle.
        while (process.MainWindowHandle == IntPtr.Zero)
        {
            process.Refresh();
        }

        ShowWindow(process.MainWindowHandle, SW_HIDE);
    }

    const int SW_HIDE = 0;

    [DllImport("user32.dll")]
    static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);
}
于 2010-06-10T04:36:58.370 回答
7

问题在于UseShellExecute = false,将其设置为true,该过程将以隐藏状态启动。使用 shell 启动进程了解如何隐藏应用程序,其中直接UseShellExecute = false启动进程直接启动进程,正如 Chris Schmich 所提到的,您必须处理从客户端应用程序内部隐藏窗口。如果您希望选择手动运行应用程序以进行调试或测试,这可能更可取。

于 2010-06-10T04:54:32.090 回答
0

您必须base.Visibility = Visibility.Hidden;在 Win Form 应用程序构造函数中添加。

于 2014-06-27T06:52:36.803 回答
0

由于我的声誉太低,我只能发布我的答案,无法评论 Chris Schmich 的答案。

在开始进程之前,您可以设置WindowStyle = ProcessWindowStyle.Minimized以避免窗口闪烁。

这是我的代码:

private const int SW_HIDE = 0;

[DllImport("user32.dll")]
private static extern bool ShowWindow(IntPtr hwnd, int nCmdShow);

public int RunWithoutWindow(string exePath)
{
    var startInfo = new ProcessStartInfo(exePath)
    {
        WindowStyle = ProcessWindowStyle.Minimized
    };

    var process = Process.Start(startInfo);

    while (process.MainWindowHandle == IntPtr.Zero)
    {
        process.Refresh();
    }

    ShowWindow(process.MainWindowHandle, SW_HIDE);

    return process.Id;
}

最后感谢 Chris Schmich 提供的好答案,而ProcessWindowStyle.Hidden有时不起作用。

于 2020-05-08T06:37:44.930 回答