【问题标题】:How do I exit a WPF application programmatically?如何以编程方式退出 WPF 应用程序?
【发布时间】:2011-02-18 16:57:09
【问题描述】:

应该如何退出应用程序,例如当用户单击“文件”菜单中的“退出”菜单项时?

我试过了:

this.Dispose();
this.Exit();
Application.ShutDown();
Application.Exit();
Application.Dispose();

还有很多。没有任何效果。

【问题讨论】:

    标签: c# .net wpf shutdown


    【解决方案1】:

    要退出您的应用程序,您可以调用

    System.Windows.Application.Current.Shutdown();
    

    Application.Shutdown 方法的文档中所述,您还可以通过指定ShutdownMode 来修改应用程序的关闭行为:

    Windows Presentation Foundation (WPF) 在以下情况下隐式调用Shutdown:

    • 当 ShutdownMode 设置为 OnLastWindowClose 时。
    • 当 ShutdownMode 设置为 OnMainWindowClose 时。
    • 当用户结束会话并且 SessionEnding 事件未处理或未取消处理时。

    还请注意,Application.Current.Shutdown(); 只能从创建 Application 对象的线程调用,即通常是主线程。

    【讨论】:

    • 正如我所指出的,这并不奇怪。在 WPF Application 中是一个静态类。 Application.Current 是对您当前正在运行的应用程序的引用。
    • 在我看来,这有点奇怪,因为乍一看这并不明显,而且它与过去的模型相差得足以让人们望而却步。它当然可以工作,这是完全有道理的。
    • 如果您致电Application.Current.Shutdown();,您的功能将不会立即返回。为此,您还需要致电return;
    • 我用过这个,从一个窗口弹出另一个窗口,在那个窗口的 window_close 事件中,我添加了这段代码。所有窗口都消失了,但程序仍然在弹出窗口创建后运行。
    • @TimothyP No Application 不是静态类。拥有Application.Current 静态成员并不意味着它是静态的。相反,它是一个可以派生的普通类。
    【解决方案2】:

    如果你真的需要它来结束你也可以使用Environment.Exit(),但它一点也不优雅(更像是结束进程)。

    如下使用:

    Environment.Exit(0)
    

    【讨论】:

    • Environment.Exit() 至少需要一个参数,即退出代码。如果您不关心退出代码,请使用Environment.Exit(0)
    • 这个方法实际上关闭了一切。我的应用程序正在运行(表单正在关闭,但进程仍在运行)Application.Current.Shutdown();
    • Environment.Exit 绝对是确保关闭应用程序的正确方法。使用 Application.Current.Shutdown,如果您有将自身推回调度程序的代码,您可以轻松地让应用程序无限期地运行。
    • 等同于 Application.exit(0);
    • 使用Application.Current.Shutdown(); 我的Closing 事件被调用,而我只是想立即关闭我的应用程序。所以Environment.Exit(0); 是更好的选择。
    【解决方案3】:

    由于wuminqi saidApplication.Current.Shutdown(); 是不可逆的,我相信它通常用于在用户注销或关闭 Windows 等时间强制关闭应用程序。

    请在您的主窗口中调用this.close()。这与按 Alt + F4 或窗口上的关闭 [x] 按钮相同。这将导致所有其他拥有的窗口关闭并最终调用Application.Current.Shutdown();,只要关闭操作未被取消。请参阅Closing a Window 上的 MSDN 文档。

    另外,因为this.close() 是可取消的,您可以在关闭事件处理程序中放入保存更改确认对话框。只需为<Window Closing="..."> 创建一个事件处理程序并相应地更改e.Cancel。 (有关如何执行此操作的更多详细信息,请参阅MSDN documentation。)

    【讨论】:

    • +1 我决定使用这个,特别是因为我需要在实际退出应用程序之前保存打开的文件。
    • 这里要注意的重要一点是,艾伦指出了一个非常重要的事实:所有其他拥有的窗口都将被关闭。您必须确保声明所有权。如果您有一个正在运行的窗口,然后您打开另一个窗口但尚未显示它,则在您关闭活动窗口后,隐藏窗口将强制应用程序继续运行。除非您通过其他方式(任务管理器等)关闭该窗口,否则您将有潜在的内存泄漏。我已经测试过了。
    • @B.K.所以在这种情况下会使用 Application.Current.Shutdown() 而不是 this.close() 关闭隐藏的窗口吗?
    【解决方案4】:

    根据需要使用以下任何一种:

    1.

     App.Current.Shutdown();
    OR
     Application.Current.Shutdown();
    

    2.

     App.Current.MainWindow.Close();
    OR
     Application.Current.MainWindow.Close();
    

    以上所有方法都会调用 Window 类的 closing event 并且执行可能会在某个时候停止(因为通常应用程序会像 '你确定吗?' 或'要在关闭前保存数据吗?',在窗口完全关闭之前) p>

    3. 但是如果您想立即在没有任何警告的情况下终止应用程序。在下面使用

       Environment.Exit(0);
    

    【讨论】:

      【解决方案5】:

      这应该可以解决问题:

      Application.Current.Shutdown();
      

      如果您有兴趣,这里有一些我认为有用的附加材料:

      Details on Application.Current

      WPF Application LifeCycle

      【讨论】:

        【解决方案6】:

        我的做法是这样的:

        // Any control that causes the Window.Closing even to trigger.
        private void MenuItemExit_Click(object sender, RoutedEventArgs e)
        {
            this.Close();
        }
        
        // Method to handle the Window.Closing event.
        private void Window_Closing(object sender, CancelEventArgs e)
        {
            var response = MessageBox.Show("Do you really want to exit?", "Exiting...",
                                           MessageBoxButton.YesNo, MessageBoxImage.Exclamation);
            if (response == MessageBoxResult.No)
            {
                e.Cancel = true;
            }
            else
            {
                Application.Current.Shutdown();
            }
        }
        

        我只从主应用程序窗口调用Application.Current.ShutDown(),所有其他窗口使用this.Close()。在我的主窗口中,Window_Closing(...) 处理右上角的x 按钮。如果任何方法需要关闭窗口,Window_Closing(...) 会在用户确认后抓取关闭事件。

        实际上我在主窗口中使用Application.Current.Shutdown() 的原因是我注意到如果出现设计错误并且我没有在应用程序中声明我的一个窗口的父级,如果那个窗口在最后一个活动窗口关闭之前打开而不显示,我留下了一个在后台运行的隐藏窗口。应用程序不会关闭。防止完全内存泄漏的唯一方法是进入任务管理器关闭应用程序。 Application.Current.Shutdown() 保护我免受意外的设计缺陷。

        这是我个人的经验。最后,使用最适合您的场景的东西。这只是另一条信息。

        【讨论】:

          【解决方案7】:

          不应有Application.ShutDown();.Exit() 消息。

          Application 是一个静态类。它不涉及当前的应用程序。 您需要访问当前应用程序,然后像这样将其关闭:

          Application.Current.Shutdown();
          

          【讨论】:

            【解决方案8】:

            另一种方法:

            System.Diagnostics.Process.GetCurrentProcess().Kill();
            

            这将强制终止您的应用程序。它始终有效,即使在多线程应用程序中也是如此。

            注意:请注意不要在另一个线程中丢失未保存的数据。

            【讨论】:

            • 这似乎难以理解:“进程中始终有效”。你能修好它吗?或者至少在这里用 cmets 解释一下你的意思?
            • 这也是部分难以理解的:只关心一个应用程序将数据保存在另一个线程的文件中。你能解决它吗?或者至少在这里用 cmets 解释一下你的意思?
            • 你在用谷歌翻译吗?
            • 不,我没有,我的意思是当应用程序作为多线程运行并且您使用 Process.Kill 时它会起作用,但是像这样的另一种方式。当另一个线程运行时,关闭在多线程应用程序中不起作用正在运行。
            【解决方案9】:

            总之,有几种方法可以做到这一点。

            1) 杀死进程,跳过终结、错误处理等:

            Process.GetCurrentProcess().Kill();
            

            2) 关闭当前应用程序,这可能是正确的方法,因为它调用了退出事件:

            Application.Current.Shutdown();
            

            this.Shutdown();
            

            (当在 App 类的实例中调用时)

            3) 关闭当前应用程序(所有表单都必须提前关闭/完成):

            this.Close(); 
            

            (当在 App 类的实例中调用时)

            4) 退出环境,从而终止应用:

            Environment.Exit(0);
            

            另外,您可能想了解退出状态here

            【讨论】:

            • "Environment.Exit(0);"为我工作。 “System.Windows.Application.Current.Shutdown();”获得最多投票的答案当应用程序试图运行下一个代码行时没有工作。赞成你的。谢谢
            【解决方案10】:
            private void _MenuExit_Click(object sender, RoutedEventArgs e)
            {
               System.Windows.Application.Current.MainWindow.Close();
            }
            
            //Override the onClose method in the Application Main window
            
            protected override void OnClosing(System.ComponentModel.CancelEventArgs e)
            {
                MessageBoxResult result =   MessageBox.Show("Do you really want to close", "",
                                                      MessageBoxButton.OKCancel);
                if (result == MessageBoxResult.Cancel)
                {
                   e.Cancel = true;
                }
                base.OnClosing(e);
            }
            

            【讨论】:

            • 这不是他只想知道如何退出wpf应用的问题。
            【解决方案11】:

            试试

            App.Current.Shutdown();
            

            对我来说

            Application.Current.Shutdown(); 
            

            没用。

            【讨论】:

              【解决方案12】:

              据我了解,Application.Current.Shutdown()也有它的缺点。

              如果您想显示一个确认窗口让用户确认是否退出,Application.Current.Shutdown() 是不可逆的。

              【讨论】:

              • 我不明白这个。但是,我们可以在致电Application.Current.Shutdown() 之前获得用户确认。
              • 我不明白你为什么要确认。太多的确认是一件非常糟糕的事情。有人努力点击打开“文件”菜单,一直向下移动到“文件”菜单的底部,然后单击“退出”,这一事实几乎证实了他们不再希望使用该应用程序。
              • Veer:在我的情况下,确实会出现确认窗口,但是即使您在确认中选择“取消”,主APP也会退出。
              • J-T-S:这个最好是逐案设计。我们的应用,如果有作业在运行,强制退出会造成损坏,所以我们最好在确认对话框中通知他们
              【解决方案13】:

              Caliburn 微香型

              public class CloseAppResult : CancelResult
              {
                  public override void Execute(CoroutineExecutionContext context)
                  {
                      Application.Current.Shutdown();
                      base.Execute(context);
                  }
              }
              
              public class CancelResult : Result
              {
                  public override void Execute(CoroutineExecutionContext context)
                  {
                      OnCompleted(this, new ResultCompletionEventArgs { WasCancelled = true });
                  }
              }
              

              【讨论】:

              • “Caliburn 微风味” 是什么意思?
              • 如何使用 Caliburn Micro 实现它
              【解决方案14】:

              如果您想从另一个没有创建应用程序对象的线程中退出,请使用:System.Windows.Application.Current.Dispatcher.InvokeShutdown()

              【讨论】:

                【解决方案15】:

                App.Current.Shutdown();
                写在你需要的地方。

                【讨论】:

                  【解决方案16】:

                  如果您使用Application.Current.Shutdown() 退出应用程序,如果您从不同的线程调用它,您可能会得到System.InvalidOperationException: 'The calling thread cannot access this object because a different thread owns it.。要解决这个问题,您可以像这样包装调用

                  Application.Current.Dispatcher.Invoke(() => Application.Current.Shutdown());
                  

                  【讨论】:

                    【解决方案17】:

                    Application.Current.ShutdownMode = ShutdownMode.OnExplicitShutdown;

                    【讨论】:

                    • 欢迎来到 SO,Alpha-Lion!此处不鼓励仅使用代码的答案,因为它们无法深入了解问题是如何解决的。请更新您的解决方案,说明您的代码如何解决 OP 的问题 :)
                    【解决方案18】:

                    您可以从 xaml 代码调用预定义的 SystemCommand:

                    Command="SystemCommands.MinimizeWindowCommand"
                    

                    我认为这应该是首选方式...

                    【讨论】:

                    • 最小化 != 退出应用程序。我在该列表中没有看到退出应用程序选项。似乎更多的窗口管理和关闭窗口并不一定意味着关闭应用程序。 msdn.microsoft.com/en-us/library/…
                    猜你喜欢
                    • 2011-10-22
                    • 2023-03-29
                    • 2011-09-13
                    • 2017-12-19
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    相关资源
                    最近更新 更多