整理一下近期开发 React Native App 的经验,以 tips 为主,写下来确保将来不会掉在同样的坑里。能够直接从官方文档查到的我就不写了,这里主要记录我踩到的坑。
技术栈
先说技术栈,我们目前的技术栈主要是:
- React Native v0.74.5,版本受 Expo 限制
- Expo v51.0.38
- NativeWind 用来写样式,蛮舒服的
- Supabase + expo-sqlite + AsyncStorage 用来做各种存储
- expo-apple-authentication + @react-native-google-signin/google-signin 用来 SSO
- expo-av 用来录音
- react-native-sse 用来流式传输
选择 Expo 是因为 React Native 官方推荐,搭起来环境才发现没那么必要……不过配都配好了,就懒得重新搞了。实际用了之后,感觉还不错,大部分功能都更好用,尤其是各种组件比原始组件要好很多。所以推荐大家需要新组建时先看 Expo SDK:docs.expo.dev/versions/latest/sdk/ 大部分都比原生组件好。实在没有再去找其它 React Native 组件。
Expo
Expo 不是必须的,但还是蛮值得使用的。尤其是对 App router 这种基于文件系统的路由体系很熟悉的开发者来说,Expo 很值得。
Expo 提供构建体系 eas,不过免费版每个月只能构建 15 次 iOS,不够用。所以大部分时间还是本地构建。构建之后,无法直接右键安装,但是可以通过 XCode Devices 安装。
使用 Expo 需要注意环境变量和组件配置。因为对 .env 的修改、环境配置(app.json
)、Logo、字体等的配置不一定会实时生效。所以修改这些不受 React Native 控制之后的东西,都先 prebuild + clean cache,然后再打包。或者直接在项目里手动搜索并修改也可以。
NativeWind
NativeWind 让我们可以在 React Native 里使用 TailwindCSS 和 className
,非常舒服,非常推荐。
不过 NativeWind 也有问题。有些组件的 className
不会直接应用在外层容器上,比如 expo-image。而如果不设置 width
、height
的话,<Image>
就不会显示,这会导致我们无法正常使用这个组件。
还有一些组件,它们由多个视觉组件组成,所以样式也需要分层配置,就有一些诸如 containerWrapperStyle
的属性。这样的组件也无法通过 className
来配置样式。所以我们使用的时候还是要多小心。如果组件渲染不符合预期,那么就看看组件如何应用样式。
Expo Image
Expo Image 比起 React Native Image 强很多:
- 支持 WebP
- 支持缓存
- 支持
object-fit
和object-position
填充 - 支持一些我还没有用到的新特性
非常推荐。但是不支持 NativeWind,请大家记得直接操作其 style
属性。
FlashList
<FlashList>
是 Shopify 开发的列表组件,针对大量内容高速滚动做了优化。它提供兼容 <FlatList>
的接口,可以无痛替换,推荐使用。
使用的时候,需要注意滚动方向。比如 Twitter 这种最新的在上面,就是默认滚动;如果是聊天窗口这样最新的在下面,就要 inverted=true
。同时还要注意,inverted=true
之后,Header
Footer
的位置也要对调。
Expo AV
Expo AV 可以用来录音和播放音频。我们用它来实现 STT。将来会尝试原生 STT。
需要注意的点不多,主要就是切换应用时,录音会自动停止,并且无法继续。所以我们需要侦听事件,并且做出相应的处理。
渲染效率
React Native 不支持非常高频的渲染,比如 Streaming output。在网页上没问题,在 RN 里就会报错:too many renderings。所以,我们需要适当缓存数据,减少渲染频率。我目前是 32 token 渲染一次。
将来会尝试用 reanimate 之类的库来渲染文字,看看能否得到更好的效果。
总结
其实最近遇到的问题很多都跟 React 有关,不过考虑到 React 开发者恐怕不会认为这些“问题”是问题,所以还是写一些文档里找不到但是可能会踩到的坑吧。
希望对大家有用,如果大家对 React,React Native,React Native Expo 开发感兴趣、有问题的话,欢迎留言讨论。
欢迎吐槽,共同进步