title: H5
本篇将介绍 H5 开发的相关内容,包括兼容性、注意事项等。
兼容性
ES5
默认配置下,@babel/preset-env
的 target
配置为:
targets = {
ios: '9',
android: '5'
}
如果需要兼容更低版本的系统,请修改在项目根目录的 babel.config.js
中修改 babel-preset-taro
的配置。(babel-preset-taro
暴露的参数暂时没有文档,详细配置请参考 源码,欢迎贡献文档~)
babel-loader
为了提升编译速度,Taro 给 babel-loader
设置了 external
属性。对于 node_modules
里(除了命名含有 taro
)的依赖,都不经过 babel 编译。babel-loader
配置请看 Github。
因此需要注意以下问题:
@tarojs/components
默认不经 Babel 编译,但3.2.10
之前没有编译出 ES5 包,请更新到3.2.10
及以上版本。- 默认不编译
node_modules
里的依赖,如有兼容性需求,请手动使用 WebpackChain 修改babel-loader
的external
属性。
Android 4.4
兼容安卓 4.4 请确认完成了以下操作:
- Taro 使用
v3.2.15+
版本。 - 使用兼容性组件库(暂时只支持 React)。
- 合理配置
babel-preset-taro
,安装corejs3
。 - 如还是遇到
Promise undefined
的问题,可在index.html
中手动引入一个 Promise 的 polyfill。
React 兼容性组件库
:::note Taro 3.2.4 开始支持 :::
Taro3 的 H5 端组件库基于 Web Components
,使用了 Stencil 框架进行开发。
Stencil 兼容性情况
但移动端对 Web Components
的支持还有一些问题,主要问题如下:
- 安卓 4.4 白屏
- 多行文字截断失效
- 部分安卓机(OPPO、VIVO 居多),样式
visibility
切换失败导致页面白屏
因此,对兼容性要求强烈对开发者,可以使用 React 兼容性组件库代替默认的 Web Components
组件库。它完全基于 React 开发,兼容性良好,但是目前只适配了若干常用的组件,开发者请谨慎选择使用。
使用方法
- 安装兼容性组件库
$ yarn add @tarojs/components-react
- 设置编译配置
h5.useHtmlComponents
```js title=”config/index.js” module.exports = { h5: { useHtmlComponents: true } }
3. 启动编译
```bash
$ taro build --type h5 --watch
贡献流程
由于人力问题,Taro 团队的迭代重心仍在 Web Components
组件库上。也欢迎各位开发者为 React 兼容性组件库添砖加瓦,具体工作是把以 Stencil
语法开发的组件改为 React 语法(Stencil 支持 JSX,因此改造工作量不大)。具体开发流程请看:@tarojs/component-react
lazy-load
Taro-H5 打包时会将页面和组件拆分成独立的文件按需加载,但这么做会导致没有用到的页面和组件依旧会被打包,有一些场景(比如 PWA 等需要严格限制包体大小时)会因此受到一些困扰。
所以我们通过 babel 插件提供了移除懒加载的方法:
```js title=”babel.config.js” {6} module.exports = { presets: [ [‘taro’, { framework: ‘react’, hot: false, ‘dynamic-import-node’: true }] ] }
### dataset
Taro-H5 在 3.3.1+ 版本才支持 `data-*` 设置参数到节点上,如需使用请升级到对应版本。
## 路由
### 路由模式
H5 支持使用 `hash` 路由模式和浏览器 `history` 路由模式,默认使用 `hash` 模式。可以修改 [h5.router.mode](config-detail#h5routermode) 进行配置。
### 路由基准路径 basename
H5 支持设置路由 basename,可以修改 [h5.router.basename](config-detail#h5routerbasename) 进行配置。
### 自定义路由
H5 支持设置自定义的路由影射规则,可以修改 [h5.router.customRoutes](config-detail#h5routercustomroutes) 进行配置。
### 路由守卫
Taro H5 的路由实现基于 [history](https://github.com/remix-run/history) 库,因此支持使用 history 库提供的一系列能力,路由守卫就是其中之一。
当用户返回上一页时,我们可以借助 `history` 的 [Blocking Transitions](https://github.com/remix-run/history/blob/main/docs/blocking-transitions.md) 能力监听返回事件,根据一些判断逻辑(例如弹窗挽留用户)决定是否执行路由返回操作。
```jsx title="history 文档上的例子(例子中的 window.confirm 可以替换为自定义弹窗)"
import { history } from '@tarojs/router'
function Index () {
useEffect(() => {
// Block navigation and register a callback that
// fires when a navigation attempt is blocked.
let unblock = history.block(tx => {
// Navigation was blocked! Let's show a confirmation dialog
// so the user can decide if they actually want to navigate
// away and discard changes they've made in the current page.
let url = tx.location.pathname
if (window.confirm(`Are you sure you want to go to ${url}?`)) {
// Unblock the navigation.
unblock()
// Retry the transition.
tx.retry()
}
})
return () => unblock()
}, [])
return <View />
}
React
使用 React 开发 H5 时需要注意的一些问题。
fast refresh
React 在 H5 Dev 编译模式时默认开启了 fast refresh 功能。
但是当使用了自定义环境变量时会出现以下报错:
或配置了 Webpack devServer
关闭热更新:hot: false
时,会出现以下报错:
:::danger Uncaught ReferenceError: $RefreshSig$ is not defined :::
这都是因为在 dev 环境,Taro 默认做了两件事情:
- 使用
fast-refresh
的 Babel plugin - 把 Webpack 配置的
devServer.hot
设置为 true,会加入fast refresh
的 loader。
而且 fast refresh
的 Babel plugin 和 loader 必须同时启用或关闭。
因此当出现上述报错时,或不希望开启 fast refresh
时,可以通过同时配置 Babel 和 Webpack 进行关闭:
```js title=”config/index.js” {5} const config = { // … h5: { devServer: { hot: false } } }
```js title="babel.config.js" {5}
module.exports = {
presets: [
['taro', {
framework: 'react',
hot: false
}]
]
}
服务端渲染(SSR)
社区 @SyMind 大佬提供了编译 NextJS 应用的插件 tarojs-plugin-platform-nextjs,用于支持 Web 端支持 SSR 能力,可以根据项目需要自行选择。