App端横屏必须修改原生配置,CSS旋转仅为假横屏;iOS需配置manifest.json的UISupportedInterfaceOrientations,Android需在AndroidManifest.xml中设置screenOrientation;uni.setScreenOrientation在App端基本无效。

App端横屏必须改原生配置,uni-app的CSS旋转只是假横屏
uni-app里用 transform: rotate(90deg) 或 CSS媒体查询模拟横屏,App真机上游戏会卡顿、触摸坐标错乱、键盘弹出异常——因为系统仍认为是竖屏,WebView容器没真正横过来。
真正生效的方式只有一种:修改原生工程配置,让整个App或指定页面强制横屏。iOS和Android处理逻辑不同,不能只靠JS或vue文件控制。
- iOS需在
ios/manifest.json里设置UISupportedInterfaceOrientations,且仅对UIInterfaceOrientationLandscapeLeft和UIInterfaceOrientationLandscapeRight开放 - Android需在
android/app/src/main/AndroidManifest.xml的对应中添加android:screenOrientation="landscape" - 如果只希望游戏页横屏,其他页面保持竖屏,Android可单独为该Activity设 orientation;iOS则需在代码中动态调用
[[UIDevice currentDevice] setValue:@(UIInterfaceOrientationLandscapeRight) forKey:@"orientation"](需原生插件配合)
uni-app的 setScreenOrientation 在App端基本不可用
文档里写的 uni.setScreenOrientation 看似能切横竖屏,但实际在iOS真机几乎无效,在Android部分机型(尤其Android 12+)也会被系统拦截——这是系统级权限限制,uni-app JS层无权绕过。
它只在H5和微信小程序里能跑通,App端调用后既不报错也不生效,容易让人误以为“配置漏了”。别在这上面浪费调试时间。
- 调用后无反应?大概率是平台限制,不是代码写错了
- Android上若开启
android:configChanges="orientation|screenSize",反而会让setScreenOrientation更不可靠 - 想临时切横屏?不如直接跳转到一个独立的、已原生配置为横屏的页面(比如用
uni.navigateTo({ url: '/pages/game/game' }),而/pages/game/game对应的Activity已固定为 landscape)
游戏Canvas适配横屏的关键:避开 uni.getSystemInfo 的陷阱
很多开发者用 uni.getSystemInfo 拿到 screenWidth/screenHeight 后直接当画布尺寸,结果横屏时Canvas被拉伸或裁剪——因为该API返回的是设备物理方向下的值,不是当前屏幕朝向的实际可用尺寸。
正确做法是监听原生横竖屏事件,再读取实时视口尺寸。uni-app目前没暴露标准事件,得靠条件判断:
- Android:在
onShow里用uni.getSystemInfo+ 判断screenWidth > screenHeight(横屏)或反之(竖屏) - iOS:更稳妥的方式是加个定时器轮询
screen.width和screen.height(DOM级),比uni.getSystemInfo更及时 - Canvas初始化时,用
canvas.width = window.innerWidth和canvas.height = window.innerHeight,而不是依赖screenWidth——后者是设备分辨率,前者才是当前渲染区域
横屏游戏里触摸坐标要重映射,event.touches[0].clientX 不是真实坐标
即使原生已强制横屏,WebView内 clientX/clientY 依然按竖屏坐标系上报(尤其iOS WKWebView),导致点击位置偏移。这不是bug,是WebKit对横屏下事件坐标的处理逻辑。
必须手动校正。最简方案:检测横屏后,把X和Y互换,并根据方向做镜像翻转。
- 横屏左(LandscapeLeft):真实X =
event.touches[0].clientY,真实Y =screenHeight - event.touches[0].clientX - 横屏右(LandscapeRight):真实X =
screenWidth - event.touches[0].clientY,真实Y =event.touches[0].clientX - 别信
event.targetTouches或changedTouches的原始值,一律用clientX/clientY做基准再换算
这事没法一劳永逸,每次横竖屏切换都要重新计算映射关系,而且不同iOS版本行为略有差异——上线前务必在iPhone 12~15全系列实机验证。










