【问题标题】:How to find cause of WPF Window location change?如何查找 WPF 窗口位置更改的原因?
【发布时间】:2016-02-28 18:59:13
【问题描述】:

每当我从休眠状态恢复计算机时,我的Window 的位置似乎会移动到屏幕顶部。我有以下记录我的窗口位置:

        LocationChanged += (sender, args) =>
        {
            Logger.Info($"{Top},{SettingsHelper.Instance.Settings.WindowTop}");
        };

WindowTop 是一个从文件中加载到内存中的属性,该文件跟踪 Window 在关闭之前的最后位置。每当这在启动时打印时,两个值都按预期正确。但是,从休眠状态恢复后,实际值会打印 0,而设置值仍然相同。这消除了加载不正确的设置值的原因。

每当计算机从休眠状态恢复时,我也会尝试重新加载设置:

    private void SystemEvents_PowerModeChanged(object sender, PowerModeChangedEventArgs e)
    {
        if (e.Mode == PowerModes.Resume)
        {   
            LoadUiSettings();
        }
    }

    private void LoadUiSettings()
    {
        Left = SettingsHelper.Instance.Settings.WindowLeft;
        Top = SettingsHelper.Instance.Settings.WindowTop;
    }

这也不能解决问题。但是,当我在加载之前添加MessageBox 时,它会在错误的位置显示Window,然后它会正确加载设置并切换到正确的设置。由于我将窗口从原始位置移开,我可以在恢复时看到它会正确修复位置,然后不知何故,在解锁我的计算机后,它会自行移动到Top = 0。奇怪的是Left 根本没有受到这个问题的困扰。解决方案中这两个属性的所有用法都是相同的。普通 WPF 应用程序不会发生这种情况,所以我不确定如何进一步调查。奇怪的是,如果我只是手动锁定计算机,而不是通过休眠,则不会发生这种情况。

有没有办法找出是什么改变了我的WindowTop 属性?

编辑:我的解决方法是使用SystemEvents.SessionSwitchSessionSwitchReason.SessionUnlock 并从那里调用LoadUiSettings,但这仍然是围绕实际问题的创可贴。我还是想弄清楚是什么原因造成的,并从根本上解决它。

编辑2:如果窗口当前不可见,设置它仍然不会改变实际位置。我暂时覆盖了可见性,然后执行了以下操作:

            while (Math.Abs(Top - SettingsHelper.Instance.Settings.WindowTop) > 0.1)
            {
                Top = SettingsHelper.Instance.Settings.WindowTop;
            }

我看到窗口在等待调整时出现了片刻,然后在它再次消失后,我通过 UI 手动切换可见性,它又在顶部。当它已经在正确的位置时手动切换它不会产生这种行为。

【问题讨论】:

    标签: c# wpf systemevent window-position


    【解决方案1】:

    针对您的具体问题(即找到问题的原因,但不要求解决方案),可以使用以下代码sn-p分析WPFWindow对应@的位置变化找到答案987654322@事件:

    SystemEvents.PowerModeChanged += OnPowerChange;
    
    private void OnPowerChange(object s, PowerModeChangedEventArgs e) 
    {
        switch ( e.Mode ) 
        {
            case PowerModes.Resume:
            // Log the position as it's done in your example
            Logger.Info ("Mode Change: Resume");
            Logger.Info($"{Top},{SettingsHelper.Instance.Settings.WindowTop}");
            break;
            case PowerModes.Suspend:
            Logger.Info ("Mode Change: Suspend");
            Logger.Info($"{Top},{SettingsHelper.Instance.Settings.WindowTop}");
            break;
        }
    }
    

    在找到问题的根本原因(即哪个事件导致Window 错位)后,您可以开发相对简单的修复程序,例如在PowerModes.Resume 事件上重新定位Window

    希望这会有所帮助。

    【讨论】:

    • 不确定您是在我编辑之前还是之后发布的(我假设是在您在我的最新标签之后编辑标签之后),但我提到它在恢复和解锁计算机之间的某个时间会发生变化。我已经有一个解决方法,但我想知道如何在根目录下修复它。
    • 我正在回答您最初的问题。有点不清楚:您是否解决了由休眠引起的窗口错位的实际问题,其次,您是否通过使用我的答案中的代码 sn-p 或您修改后的代码得到了问题的答案:请澄清。最好的问候,
    • 不,我根本没有使用你的sn-p。该问题仍未解决,因为我不知道是什么原因造成的,但我目前确实有一个解决方法。
    猜你喜欢
    • 2010-12-05
    • 2010-12-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-12-29
    • 2012-02-22
    • 1970-01-01
    • 2019-09-28
    相关资源
    最近更新 更多