【问题标题】:Windows Screens.AllScreens does not update after switching the main display切换主显示后 Windows Screens.AllScreens 不更新
【发布时间】:2018-03-17 11:17:14
【问题描述】:

Windows Screens.AllScreens 在切换主显示后不会更新。

我正在尝试使用具有小屏幕 (800/480) 和外接显示器 (1920/1080) 的仪器来操作多显示器设置。外接显示器必须始终为主屏幕。我需要在小型显示器上执行某些任务,例如更改方向 (DMDO_180/DMDO_DEFAULT)。并触发触摸屏校准 (tabcal.exe)。这两个操作都要求执行操作的屏幕是主显示器。

我有更改显示的代码,但是当屏幕更改时,它不会反映在 Screen.AllScreens 中。当 AllScreen 未更新时,我的任务将失败,因为主屏幕不正确。

我注意到 Screen 对象确实会在上下文切换时更新,但我需要强制它发生。我看过Screen.AllScreen is not giving the correct monitor count。它提到“我查看了源代码(记住我们可以使用 MS Symbol 服务器做到这一点)。AllScreens 使用非托管 API 在第一次访问时获取屏幕,然后将结果存储在静态变量供以后使用。 这样做的结果是,如果程序运行时监视器的数量发生了变化;那么 Screen.AllScreens 将不会接受更改。" 这并不完全正确。我已经挂钩了窗口加载事件,如果我在触发之前设置断点并更改主屏幕,当触发 AllScreens 对象更新并显示正确的主屏幕的事件。

我尝试模仿这种行为的一个例子是触发我的应用程序代码和我在互联网上找到的使用 DEVMODE 结构来操纵显示的代码之间的事件,但两者之间的触发事件不会更新AllScreens 对象。

执行此操作的代码有数千行,因此我将根据要求发布。

我正在使用 VS2015、C#、WPF。

如何强制 AllScreens 使用非托管 API 进行更新?

【问题讨论】:

  • “切换”非常模糊。试试看,订阅 SystemEvents.DisplaySettingsChanging 事件。如果您“切换”时它没有触发,那么您确实不会获得不同的 AllScreens 属性值。如果这是 hacky,那么您必须自己发送 WM_DISPLAYCHANGE 消息。
  • 我已添加到我的主窗口:
  • 谢谢你的作品。我执行 PostMessage((IntPtr)HWND_BROADCAST, WM_DISPLAYCHANGE, UIntPtr.Zero, IntPtr.Zero);并等待 IntPtr hwndSourceHook(IntPtr hwnd, int msg, IntPtr wParam, IntPtr lParam, ref bool handler) 中的 WM_DISPLAYCHANGE 向我的信号量发出信号。
  • 发送消息,这使得使用 SendMessageTimeout() 而不是 PostMessage() 合适。

标签: c# wpf visual-studio-2015


【解决方案1】:

Microsoft.Win32.SystemEvents.DisplaySettingsChanged 似乎在主显示开关上被触发。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-11-27
    • 1970-01-01
    • 2011-12-24
    • 2015-11-05
    相关资源
    最近更新 更多