React Native(iOS):加载javascript之前的RCTEventEmitter



我在应用程序中实现信标时遇到问题。我正在使用库react-native-beacons-manager,但我认为这是一个普遍的"问题"。

问题是,当我杀死我的应用程序(这对重现问题很重要),并且我离信标越来越近时,iOS会触发一个事件regionDidEnter,该事件被用本机代码编写的文件捕获,然后使用RCTEventEmitter:[self sendEventWithName:@"regionDidEnter" body:event];的方法发送到javascript

问题是这个事件是在javascript完全加载之前触发的,所以我的监听器:

// component.js
Beacons.BeaconsEventEmitter.addListener('regionDidEnter', b => {
//code
});

没有接到电话。

事件顺序:

[BeaconsDemo] Did finish launching enter
[BeaconsDemo] Did finish launching After jsBundleURLForBundleRoot
[BeaconsDemo] Did finish launching After RCTRootView alloc
[BeaconsDemo] Did finish launching After UIWindow alloc
[BeaconsDemo] Did finish launching After makeKeyAndVisible
[BeaconsDemo] Did finish launching end
--iOS send the event and it is caught by RNiBeacon but it has no listeners yet--
[BeaconsDemo] no listeners in RnIBeacon.m
--Register
[BeaconsDemo] regionDidExit
-- First line of javascript --
[BeaconsDemo] start observing
[BeaconsDemo] requestAlwaysAuth

有什么办法处理这种情况吗?是否有任何方式或方法可以通过RCTEventEmitter发送事件,等待加载javascript?

感谢

在为iOS或Android编写本机信标应用程序时也存在此一般问题。解决方案是,您必须设置"挂钩",以启用信标监控,并在每个平台的适当位置添加事件侦听器(或在本机代码中调用的委托/通知回调):

iOS:AppDelegate.didFinishLanching(options: )

安卓系统:Application.onCreate()

关键是,在这些方法返回之前,必须完成此设置。

同样的规则也适用于ReactNative。ReactNative的诀窍是,默认情况下,JavaScript不会在这些事件上运行——它只在屏幕启动时运行,这会设置挂钩太晚,以至于当你的应用程序被终止时,上述功能无法工作。要实现这一点,你需要弹出你的应用程序,这样你就可以在上面的回调中设置一些自定义的本地代码。

两种选择:

  1. 本机实现信标检测(最简单,但需要基于每个平台的本机编码)
  2. 在上面的本机回调中添加本机代码,该回调在iOS上启动RCTBridge,并启动一个视图,该视图执行触发我们的JavaScript代码以设置信标检测的代码。在Android上,等效的方法是构建一个新的ReactRootView和ReactNativeInstanceManager,以触发您的JavaScript代码来设置信标检测

我还没有亲自测试选项2,看看它是否能很快设置挂钩。如果它有效,它肯定会比原生解决方案更难,但允许您将信标检测逻辑保留在JavaScript中。

(https://github.com/MacKentoch/react-native-beacons-manager/issues/50)

我已经分叉了@newoceaninfosys的分叉,并添加了"错过信标"方法。查看我最近的3次提交,了解如何复制它。(https://github.com/iamandiradu/react-native-beacons-manager)通过在您的didMount函数中添加以下内容来使用它:

if (Platform.OS === 'ios') { // iOS cold start listener this.beaconMissedListener = Beacons.BeaconsEventEmitter.addListener( 'onMissedBeacon', data => { if (data) { this._beaconListener(data); } }, ); Beacons.getMissedBeacon(); }

这将检索"丢失"的数据,因为事件的触发速度比侦听器快。

(React Native(iOS):加载javascript之前的RCTEventEmitter)

希望这能帮助到别人。:)

最新更新