1***@qq.com
1***@qq.com
  • 发布:2026-07-18 13:42
  • 更新:2026-07-18 13:42
  • 阅读:15

AI 写了个 Vue3 页面,我却花了半小时改它的“uni-app 兼容性”——这到底是谁在学谁?

分类:uni-app

我用AI生成商品详情页,结果在iPhone和安卓上各报不同错——这半小时值了

上周接到一个“商品详情页”重构需求,用的uni-app。工期压得紧,我决定赌一把:让AI先写个Vue3版本,我再改成uni-app能跑的。结果AI花10秒生成了一个“完美”页面——轮播图、SKU选择、加购按钮全有,代码干净得像教科书。但我花了整整半小时改兼容性,期间在iPhone 14 Pro Max和一台小米折叠屏上反复测试,白屏、报错、样式崩,一个没落下。

我给了AI一段需求,它给我造了个“浏览器专属”页面

我输入的prompt是:“用Vue3 + Composition API写商品详情页,包含轮播图、SKU选择、加购按钮,数据用mock模拟。”AI立刻吐出代码:、v-model绑定、watch监听SKU变化、onMounted模拟接口请求。结构清晰,逻辑严谨,一眼看去就是“最佳实践”。

但当我把它粘进uni-app项目,直接在微信开发者工具里预览——页面白屏,控制台报错:document is not defined。我盯着屏幕愣了三秒,才反应过来:AI默认跑的是浏览器环境,而uni-app在小程序和App端没有document和window。这个坑,AI永远不会主动告诉我。

半小时里我踩的三个大坑

  1. 轮播图高度设置:一个document.querySelector引发的连锁反应

AI在轮播图组件里写了这样一行:
javascript
document.querySelector('.swiper').style.height = '300px'

在浏览器里没问题,但在uni-app里直接报错。更隐蔽的是,它还在onMounted里用了window.addEventListener('resize')来监听屏幕旋转——这在H5端勉强能用,但一跑到微信小程序端就失效,因为小程序根本没有window对象。

我一开始还想着“能不能保留这个逻辑,只在H5端跑”,但项目要求覆盖小程序和App端。最后只能全部替换:把document.querySelector改成uni.createSelectorQuery(),把window.resize监听换成CSS的vh/vw加rpx组合,或者干脆用onResize生命周期(只在App和H5支持)。

一个真实教训:在小米折叠屏上测试时,轮播图高度设置成固定300px,结果在展开状态下只占屏幕三分之一,缩成一团。用rpx后,宽度按750设计稿换算,高度用宽高比动态计算,才解决。

  1. CSS单位与样式隔离:iPhone上正常,安卓上崩了

AI写的轮播图用了width: 100%和height: 300px。在iPhone 14上看着正常,但在我那台华为折叠屏上,轮播图直接缩成一团——因为不同设备物理像素不同,px不会自动缩放。

更麻烦的是,AI用了全局CSS选择器(比如直接写.swiper),而uni-app在H5端有样式隔离,小程序端又用shadow DOM,全局样式经常失效。我一开始没注意,结果在安卓真机上,轮播图底部的指示器样式全乱了——因为全局样式被隔离,没生效。

最后我把所有px改成rpx,所有全局选择器改成scoped,并且用::v-deep穿透子组件(如果子组件是第三方库)。甚至用条件编译处理端差异:
css
/ #ifdef H5 /
.swiper { height: 400px; }
/ #endif /
/ #ifdef MP-WEIXIN /
.swiper { height: 400rpx; }
/ #endif /

条件编译增加了代码量,但这是保证多端一致性的唯一办法。

  1. 生命周期差异:用户从购物车返回,SKU状态没刷新

AI的SKU选择器用v-for渲染,数据用reactive管理,逻辑上没问题。但它没有处理uni-app特有的“页面生命周期”——比如onShow、onHide。

在Web里,页面切换就是路由跳转,每次进入页面都会重新挂载组件。但小程序里,页面返回时数据可能被缓存,如果不监听onShow,用户从购物车页面返回时,SKU状态不会刷新,导致显示错乱——比如用户之前选了“红色-大号”,返回后页面还显示这个选择,但实际库存可能已经变了。

我补充了uni-app的页面生命周期:
javascript
import { onShow, onHide } from '@dcloudio/uni-app'
onShow(() => {
// 每次页面显示时重新获取SKU库存状态
refreshSkuStatus()
})

同时把原来用watch监听SKU变化改成用computed配合onShow刷新,因为watch在小程序端有时会因作用域问题失效,而computed更稳定。

我是怎么把AI代码“翻译”成uni-app能跑的

既然AI的代码直接不能用,那就把它当“伪代码”来改。我一步步把Web版翻译成uni-app兼容版,主要做了三件事。

第一步:替换所有Web API为uni-app跨端API

把document.querySelector换成uni.createSelectorQuery()。比如动态设置轮播图高度,原来AI写的:
javascript
document.querySelector('.swiper').style.height = '300px'

改成:
javascript
uni.createSelectorQuery().select('.swiper').boundingClientRect(rect => {
// 这里不直接设高度,而是通过data绑定
this.swiperHeight = rect.width * 0.5 // 按宽高比计算
}).exec()

对于window.addEventListener('resize'),我换成了uni-app的onResize生命周期(只在App和H5端支持),或者干脆用CSS的vh/vw加rpx组合实现自适应,避免监听事件。

一个关键发现:不是所有Web API都有uni-app等价物。比如requestAnimationFrame在部分小程序端不支持,我直接改成了setTimeout加帧率控制,虽然性能差一点,但保证多端可用。

第二步:重写CSS,用rpx + scoped + 条件编译

我建了一个mixins文件,把常用尺寸转成rpx:
css
/ 原来AI写的 /
width: 100%;
height: 300px;
/ 改成 /
width: 750rpx; / 按设计稿750px宽度换算 /
height: 400rpx;

对于样式隔离,我把所有全局选择器改成了scoped,并且用::v-deep穿透子组件(如果子组件是第三方库)。更绝的是,我用条件编译处理端差异:
css
/ #ifdef H5 /
.swiper { height: 400px; }
/ #endif /
/ #ifdef MP-WEIXIN /
.swiper { height: 400rpx; }
/ #endif /

一个取舍:条件编译增加了代码量,但这是保证多端一致性的唯一办法。如果项目只做两三个端,可以接受;如果要覆盖全部端,建议直接用rpx统一处理,少用条件编译。

第三步:添加uni-app生命周期钩子

AI的代码只有Vue3的生命周期(onMounted、onUnmounted),我补充了uni-app的页面生命周期:
javascript
import { onShow, onHide } from '@dcloudio/uni-app'
onShow(() => {
// 每次页面显示时重新获取SKU库存状态
refreshSkuStatus()
})

同时,我把原来用watch监听SKU变化改成用computed配合onShow刷新,避免多次重复监听。因为watch在小程序端有时会因作用域问题失效,而computed更稳定。

给想“偷懒”用AI写uni-app的人几条经验

如果你也想用AI生成uni-app代码,这几条经验能帮你省下半小时:

  • 明确告诉AI环境:在prompt里加一句“请生成uni-app兼容的代码,不要使用document、window、CSS的px单位,组件用uni-ui”。虽然AI不一定完全照做,但能减少70%的Web特有代码。
  • 不要信任AI的“多端适配”:AI经常说“本代码兼容多端”,但实际上它只测试了H5。你必须在真机或模拟器上跑一遍小程序端,才能发现隐藏问题。我就是在小米折叠屏上测试时,才发现轮播图高度和样式隔离的问题。
  • 优先用uni-app官方组件:AI喜欢用HTML原生标签(比如、),但在uni-app里应该用、。我改代码时几乎把所有替换成,把换成,并加了mode="widthFix"属性来做图片自适应。
  • 小心AI的“过度封装”:AI可能把轮播图、SKU选择器封装成独立组件,但uni-app的组件通信在跨平台时有坑。比如用provide/inject时,小程序端可能无法正确传递响应式数据,我最后改成了props加emit这种最保守的方式。

最后:AI是“翻译官”,不是“全栈工程师”

这半小时的修改让我意识到:AI写代码的核心优势是“快速生成框架和逻辑”,但它缺乏对“平台差异”的认知。它像是一个精通标准英语的翻译官,但你要把它翻译成方言(uni-app),就必须自己懂方言的语法。

最终,我保留AI生成的数据流逻辑(比如SKU计算、购物车数量管理),但重写了80%的UI层和50%的交互层。项目按时交付了,但我也更加确信:在uni-app这种跨端框架里,经验比代码生成更重要。AI可以帮你写90%的“正确代码”,但剩下的10%平台适配,才是真正区分“能用”和“好用”的关键。

下次再用AI写uni-app页面,我会先想清楚:我是想省时间,还是想找个“代码翻译官”给自己添堵?至少现在,我更愿意自己写骨架,让AI帮我补细节——而不是反过来。

0 关注 分享

要回复文章请先登录注册