最近做项目的需求是先发布h5,后续再开发上线微信小程序版,自然我选择了uniapp多平台打包,过程中也踩了一些坑。本篇文章记录了使用uniapp开发h5的注意事项,及打包成小程序需要兼容改动的内容。
1.需要在pages.json注册页面路由
在uniapp开发h5也要通过pages.json来注册路由,和小程序开发一样。pages数组中第一项表示应用的启动页,参考:https://uniapp.dcloud.io/collocation/pages。路由跳转和小程序一样使用uni.navigateTo。
因为小程序有主包2m大小限制,页面的分包最好也在h5开发时规划出来。
2.分别定义header
页面公共header也是在pages.json里设置的。因为需要针对两个平台分别进行设置,要用到uniapp的条件编译注释:微信小程序 // #ifdef MP-WEIXIN h5 // #ifdef H5 最后都是以// #endif结束。这样uniapp就可以分别进行编译从而实现对不同平台的处理。
h5不需要header,因为已经有了浏览器头部,再设置header就会有两个。这里我们使用"navigationStyle": "custom"来取消h5的额外header。
微信小程序则需要设置header,如果你需要的是常规的纯色header,用navigationBarBackgroundColor设置背景色,navigationBarTextStyle设置文字颜色即可。header的文字会自动取前面页面路由里设置的navigationBarTitleText。
如果需要实现渐变,沉浸式header等设计,使用"navigationStyle": "custom",然后配合uni-nav-bar或者写一个你自己的header组件。
"globalStyle": {
// #ifdef MP-WEIXIN
"navigationBarBackgroundColor": "#fff",
"navigationBarTextStyle": "black",
// #endif
// #ifdef H5
"navigationStyle": "custom"
// #endif
},
3.没有浏览器专用js对象
- 没有浏览器专用的js对象,比如document、xmlhttp、cookie、window、location、navigator、localstorage、websql、indexdb、webgl等对象。
如果你的代码没有直接使用这些,那很可能是引入的三方库使用了这些。如果是后者,去插件市场搜索替代方案。要知道非H5端的js是运行在一个独立的js core或v8下,并不是运行在浏览器里。
从HBuilderX 2.6起,App端新增了renderjs,这是一种运行在视图层的js,vue页面通过renderjs可以操作浏览器对象,进而可以让基于浏览器的库直接在uni-app的App端运行,诸如echart、threejs,详见:renderjs
这一条需要特别注意。如果自己代码或者第三方库使用了这些对象,项目会直接报错白屏。如果h5里一定要用,加上// #ifdef H5条件注释让它只适用于h5。
另一个问题是很多vue的第三方插件也不能用,虽然有个renderjs的方案,在小程序里并不推荐。解决方案是使用uniapp的官方扩展组件uni-ui,或者在官方插件市场里找。注意在h5里使用这些用到了浏览器对象的插件一样需要用renderjs,比如我这篇引入vconsole调试工具时:
4.uni-ui组件使用相对路径图片的问题
在使用uni-list-item等组件时,比如你给缩略图thumb设置为当前页面的相对路径"../../../static/img/icon.png",这样在h5里没问题,运行为小程序时就会发现路径的起始位置不是当前页面,而是从uni_modules开始找,所有组件用到的相对路径图片都会404。
这里我推荐在页面import引入图片,比如:
import iconImg from '../../../static/img/home/icon.png',然后放到data里,最后:thumb="iconImg"
5.uni-ui组件自定义样式问题
这个问题真的很头疼,一些组件内找到的css名,自定义覆盖样式在h5里是正常的,小程序里很多就失效了,检查后发现有的组件的css名在h5里有,在小程序是没有的。而且在页面内使用:deep改样式有的可以有的不行。
最后比较好的解决方案是,给当前页面顶层定一个class名,比如<view class="feedback">,接着在common/uni.css或者别的公共样式里带上页面的class来定义,比如:
/* #ifdef MP-WEIXIN */
.feedback .uni-data-tree {
width: 240rpx;
}
/* #endif */
注意css里也可以用条件编译注释,只不过要用css风格,变成了/* #ifdef MP-WEIXIN */