当前位置: 首页 > news >正文

WPF二合一平板电脑上屏幕旋转时获取屏幕宽高问题

在二合一平板上面,屏幕旋转之后,屏幕的宽高会被改变,如果代码里面有用到屏幕宽高的地方可能会出错。

获取屏幕宽高位置可以通过可以通过如下几种方式获取

/// <summary>/// 获取屏幕大小 /// </summary>public void InitScreenSize(){var primaryScreen = Screen.PrimaryScreen;// 获取主屏幕边界var screenBounds = primaryScreen.Bounds;var  screenWidth = screenBounds.Width;var screenHeight = screenBounds.Height;var screenWidth = SystemParameters.PrimaryScreenWidth;var screenHeight = SystemParameters.PrimaryScreenHeight;var Width = SystemParameters.WorkArea.Width;var Height = SystemParameters.WorkArea.Height;}

现在问题是,如果一开始初始化界面就获取屏幕宽高,正常是1920x1080的,屏幕旋转到竖屏之后就会变成1080x1920了。

如何动态适配呢。可以通过如下SimpleOrientationSensor 方式监听屏幕的旋转变化。

  internal class OrientationManager{#region 监听方向变化private SimpleOrientationSensor simpleSensor;private SimpleOrientation currentOrientation;/// <summary>/// 监听方向变化重启应用/// </summary>public void RegisterOrientationChanged(){try{if (simpleSensor != null){simpleSensor.OrientationChanged -= SimpleSensor_OrientationChanged;}simpleSensor = SimpleOrientationSensor.GetDefault();AnnotatorService.Log.Info($"初始化方向传感器:{simpleSensor != null}");if (simpleSensor != null){currentOrientation = simpleSensor.GetCurrentOrientation();// 订阅方向变化事件simpleSensor.OrientationChanged += SimpleSensor_OrientationChanged;CheckSensorStatus();}}catch (Exception e){AnnotatorService.Log.Error(e);}}public void UnregisterOrientationChanged(){if (simpleSensor != null){simpleSensor.OrientationChanged -= SimpleSensor_OrientationChanged;simpleSensor = null;}}public Action<SimpleOrientation> OnDelayOrientationChanged;private void CheckSensorStatus(){try{// 定期检查传感器状态var timer = new System.Threading.Timer(_ =>{if (simpleSensor != null){var current = simpleSensor.GetCurrentOrientation();var hasChanged = currentOrientation == current;AnnotatorService.Log.Debug($"定时获取传感器当前方向: {current},是否变化:{hasChanged}");}}, null, TimeSpan.FromSeconds(10), TimeSpan.FromSeconds(30));}catch (Exception ex){AnnotatorService.Log.Error($"传感器状态检查失败: {ex.Message}");}}private async void SimpleSensor_OrientationChanged(SimpleOrientationSensor sender, SimpleOrientationSensorOrientationChangedEventArgs args){AnnotatorService.Log.Info($"方向变化:{args.Orientation}");if (currentOrientation == args.Orientation) return;currentOrientation = args.Orientation;if (IsSignificantOrientationChange(currentOrientation)){await Task.Delay(300);OnDelayOrientationChanged?.Invoke(args.Orientation);}return;if (MainWindowManger.MainWindow != null) return;var exePath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "H3CAnnotator.exe");if (File.Exists(exePath)){AnnotatorService.Log.Info($"关闭应用重启");Process.Start(exePath);//方向变化重启}}private bool IsSignificantOrientationChange(SimpleOrientation newOrientation){// 过滤掉不重要的方向变化// 例如:Faceup/Facedown 可能不需要处理switch (newOrientation){case SimpleOrientation.Faceup:case SimpleOrientation.Facedown:return false;default:return true;}}#endregion}

SimpleOrientationSensor 监听之后发现2个问题:

1.在触发方向变化立即获取屏幕宽高错误获取到的还是旋转前的宽高。由于触发旋转变化之后需要等待一会屏幕旋转好了之后再获取才正确。

2.旋转好了之后等待200ms再获取屏幕宽高是正常的,但是这个OrientationChanged 事件存在失效的情况,目前还不清楚为什么有时候用一会就事件没触发了,还未定位到原因。

未来解决在代码里面获取屏幕宽高的获取错误的情况,做了如下处理。

在获取宽高的地方直接调用获取宽高,不要进行首次初始化这类的缓存操作。

建议检测代码里面获取屏幕宽高或者是任务栏宽高,工作区域宽高的位置是否有进行缓存处理,需要都改为实时获取。

获取主屏幕分辨率的过程耗时极短,通常在微秒级别。没有必要缓存,即使上万次获取也是极端。

http://www.hskmm.com/?act=detail&tid=13679

相关文章:

  • 代码中的善意:构建人性化的软件开发文化
  • 超级恶心的题面 [USACO21OPEN] Portals G
  • 如何隐藏一个元素
  • 昆仑通态触摸屏保存参数到内部存储器并读取的方法成都控制器开发提供
  • helloword
  • 使用reCAPTCHA提升WordPress网站安全性 - 指南
  • 软工9.22
  • 在控制台执行可列出所有placeholder样式
  • 今日总结
  • 9/22
  • 对于一门古老东欧玄学的初步研究的简要报告
  • Codeforces 2127 D(图论,组合数学,DFS,分类讨论)
  • Java学习笔记:从三个实验看编程思维的锤炼
  • 题解:AT_arc068_d [ARC068F] Solitaire
  • Codeforces Round 1051 (Div. 2) D1D2题解
  • JSP
  • 每日博客
  • 探展打卡 Serverless,2025 云栖大会来了
  • 从 0 到 1,AI 走进服装店:记住每位顾客的喜好,比你还靠谱
  • STM32HAL 飞快入门(十九):UART 编程(二)—— 中断方式实现收发及局限分析
  • 贪心算法应用:多重背包启发式疑问详解
  • 划重点|云栖大会「AI 原生应用架构论坛」看点梳理
  • 君子如水,心中有火:vivo本心而为30周年
  • Margin 塌陷问题如何解决?触发BFC。BFC的概念和触发条件
  • 9.22
  • 数字统计
  • 火速收藏!2025 云栖大会 AI 中间件议程看点全公开(附免费报名通道)
  • 第二次软工作业——个人项目 - LXJ
  • WinForm引入项目资源文件
  • 第二次作业