taro生命周期 | 填坑系列

2020-05-254459

Taro-V2.0.5-页面生命周期

Taro-V2.0.5-入口文件生命周期

结论

  1. 生命周期函数里哪些可以 setState ?什么时候 setState 合适?
    • 可以 setState
      • componentWillMount
        • (虽然这个函数可以,但建议尽量不要在这个函数中执行 setState,如果可以改成在 componentDidMount 执行就尽量放在 componentDidMount 中)
      • componentDidMount
      • componentDidUpdate
      • componentWillReceiveProps
    • 不可以 setState
      • componentWillUnmount
      • shouldComponentUpdate
      • componentWillUpdate
  2. taro 在正常加载页面前,会先把定义在 src/app.jsx 中的 tabBar 页面以及页面包含组件的 render 函数都跑一遍
    • 如上图《Taro-V2.0.5-入口文件生命周期》
    • ps:这个执行顺序也是乱的,不确定是哪个页面先,哪个页面后,有时甚至先执行组件的 render ,不确定是不是 bug,暂时没发现有什么问题,如下图:
  3. 微信小程序生命周期与 taro 生命周期的对应关系
  4. 适合使用 async 的生命周期函数要满足这两个条件:
    1. 要在 render 函数之后执行
    2. Taro(React)不关心这个生命周期函数的返回值

Why?

对于第一个结论

可以 setState 的生命周期函数:

  1. componentWillMount
    • componentWillMount 是在 render 之前的,如果在这个生命周期函数中执行 setState 会有以下两种情况:
      • 同步执行:
        • 对于同步执行的情况,相当于在 render 前修改 state 的值,这样写实际上跟直接在 constructor 直接修改 state 的定义是一样的效果
          • 如下图:在 constructor 定义的 state 值是:“我在 constructor 中定义了 txt 的值”,然后在 componentWillMount 上同步修改了 state 的值,改成:“我在 componentWillMount 中 同步 修改了 txt 的值”,在 render 时就直接用了修改后的值
      • 异步执行:(放在请求的回调函数中)
        • 对于异步执行的情况,相当于在页面在“运行中”时,触发了“状态(state)改变”的情况
    • 页面只挂载一次,在 componentWillMountsetState 会更新 state 一次,而且会和 constructor 里的初始化 state 合并执行,一定程度上是一次意义不大的 setState,所以虽然在 componentWillMount 中可以执行 setState,但个人认为是一种反模式,不建议这样做
  2. componentDidMount
    • 页面在“运行中”时,触发了“状态(state)改变”的情况
  3. componentDidUpdate
    • 页面在“运行中”时,触发了“状态(state)改变”的情况
  4. componentWillReceiveProps
    • 页面在“运行中”时,触发了“状态(state)改变”的情况

不可以 setState 的生命周期函数:

  1. componentWillUnmount
    • 页面都要卸载了,在 componentWillUnmount 中执行 setState 不会更新 state,不生效并且没有意义
  2. shouldComponentUpdate
    • shouldComponentUpdate 里调用 setState 会再次触发这个函数,然后在函数中又触发 setState,然后再次触发这个函数,从而死循环
  3. componentWillUpdate
    • componentWillUpdate 里调用 setState 会再次触发这个函数,然后在函数中又触发 setState,然后再次触发这个函数,从而死循环

》》》》》》》》》》》》》》》》》》

对于第四个结论

参考:React中的async/await生命周期函数

src/app.jsx 中,componentWillMountcomponentDidMountcomponentDidShow 都是在 render 之前,所有如果在这些生命周期函数中加 async 是不会阻断程序去执行 render 的,如下图所示:

同样,如果是在页面上,componentWillMount 是在 render 之前,也会出现以上情况。

另外,如果在 React 关系返回值的生命周期函数中用 async 会有问题:

async shouldComponentUpdate() {
    return false; //实际上不会这么写,应该根据state和prop计算出false或者true
}

表面上看,shouldComponentUpdate 返回的是 false ,组件不会被重新渲染,其实,因为函数声明为 async ,所以每次返回的是一个 Promise.resolve(false) ,一个 Promise 对象被转化为 bool 类型,绝对是 true,所以实际上在React看来 shouldComponentUpdate 返回的永远是 true

吴勤发

芦苇科技web前端开发工程师、COO

擅长网站建设、公众号开发、微信小程序开发、小游戏、公众号开发,专注于前端框架、服务端渲染、SEO技术、交互设计、图像绘制、数据分析等研究,有兴趣的小伙伴来撩撩我们~ web@talkmoney.cn

访问 https://www.luweitech.cn/ 了解更多

分享
点赞2
打赏
上一篇:代理工具Fiddler -调试与替换接口状态
下一篇:vscode 快捷使用篇