You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

WPF点击Windows Toast通知按钮后主窗口莫名失焦问题求助

WPF Toast通知激活窗口后焦点丢失问题

我创建了一个.NET 6 WPF应用复现该问题:

public partial class App : Application
{
    protected override void OnStartup(StartupEventArgs e)
    {
        Current.ShutdownMode = ShutdownMode.OnExplicitShutdown;
    }
}

/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();
    }

    private void Button_Click(object sender, RoutedEventArgs e)
    {
        var notifier = new Notifier();

        //Send Toast
        notifier.SendToast();

        //Close MainWindow
        Close();
    }
}

使用Microsoft.Toolkit.Uwp.Notifications NuGet包,通过ToastContentBuilder发送Toast通知:

public class Notifier
{
    public Notifier()
    {
        SubscribeToToastCallback();
    }

    public void SendToast()
    {
        var toastContentBuilder = new ToastContentBuilder();
        toastContentBuilder.AddText("Text").AddButton("Test", ToastActivationType.Foreground, "");
        toastContentBuilder.Show();
    }

    private void SubscribeToToastCallback()
    {
        ToastNotificationManagerCompat.OnActivated += toastArgs =>
        {
            //On Toast button click, Show MainWindow activated
            Application.Current.Dispatcher.BeginInvoke(() =>
            {
                if (Application.Current.MainWindow is null)
                {
                    Application.Current.MainWindow = new MainWindow();
                    Application.Current.MainWindow.ShowActivated = true;
                }
                Application.Current.MainWindow.Show();
            });
        };
    }
}

现象描述

  • 预期流程:点击Toast按钮 → 触发ToastNotificationManagerCompat.OnActivated → 执行主窗口打开代码 → 主窗口在前台显示并保持焦点。
  • 实际流程:点击Toast按钮 → 触发ToastNotificationManagerCompat.OnActivated → 执行主窗口打开代码 → 主窗口在前台显示 → 约0.5秒后主窗口失焦,激活之前打开的应用。
  • 特殊情况:连续复现该场景10次后,点击Toast主体(可交互),主窗口可正常激活;后续即使点击之前导致失焦的按钮,通知也能正常激活窗口。
  • 额外问题:主窗口在此场景下失焦时,未触发基于WA_INACTIVE消息的MainWindow.Deactivated事件,应用无法感知焦点丢失。

已尝试方案

  • 将ToastActivationType.Foreground改为Background,无变化;
  • 尝试Show()/Focus()/Activate()的所有组合,无效;
  • 通过PInvoke调用LockSetForegroundWindow(),也无效;
  • 唯一有效的方法体验极差:主窗口打开后设置Topmost = true,保持1秒(期间Windows尝试夺回焦点),再设置Topmost = false:
MainWindow.Topmost = true;
Task.Delay(1000).ContinueWith((_) => { Dispatcher.Invoke(() => { MainWindow.Topmost = false; }); });

疑问

该现象的原因是什么?是否为Windows在0.5秒后窃取焦点的Bug?有没有比使用Topmost更流畅的解决方案?

环境:Windows 10 x64 Build 19045


内容的提问来源于stack exchange,提问作者nullbody

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.22 19:03:33