如果还不知道rn通信机制就来看这篇文章

551 阅读2分钟

前言

rn通信机制,作为一个rn的开发者不能不知道。rn作为一个JavaScript跨端框架,他与原生native之间的交互是必不可少的。对比于之前的混合模式hybrid,rn中js代码构建的界面完全是基于原生组件,而hybrid则是通过利用UIwebview作为界面,向webview请求加载特殊URL的方式来调用原生功能。 rn使用JavaScriptCore框架提供的js运行环境,通过执行特殊的js脚本来传递数据,完成Object-C和js代码之间的交互。

一、模块配置映射

当我们想要在js端去调用native的功能的时候,我们需要知道我们要调用的是哪个模块里的哪个方法,需要传什么参数。

graph TD
调用native桥 --> 桥对应的模块方法参数 --> 模块配置映射

模块配置表生成

模块配置映射由rn在加载的时候生成,所有注册并且符合规范的模块都会被导出。生成模块数据类 RCTModuleData,和模块的moduleID。 模块数据中,当前模块中所有的模块方法会通过Object-C运行时被导出,生成模块方法类RCTModuleMethod和MethodID。 该对象里缓存了原生方法 与 js方法的对应关系以及模块的实例。这些执行完后会生成一份模块配置表。其中包括了模块名,js方法,常量参数,ModuleID,MethodID。 这个配置表最终会注册到js端,生成对应的js模块对象和方法。

rn 模块配置映射表.png

二、通信流程

js会维护一个MessageQueue。当调用模块的方法时,调用会被解析为模块名 moduleName,methodName,param,将着三部分传个messageQueue,通过模块配置表解析为 ModuleID 和 MethodID. MessageQueue是一个很重要的模块,所起的作用 与 原生代码中的RCTBridge类似,提供了将模块方法调用与模块通信数据相互转换的功能。

rn 桥通信图.png

如果调用参数包含了回调函数,MessageQueue会将参数params中的回调函数缓存在本地,并生成一个callbackID来代替。 最终js调用以ModuleID、MethodID、params的形式缓存起来,传给Native,值得注意的是这里不是js模块主动将数据传给Native的,而是由Native模块主动调用MessageQueue接口,获取MQ中的缓存消息数据。

js模块与Native模块之间的数据是以序列化成JSON类型来传递的,而native模块方法的参数必须使用native的类型,因此,需要进行类型处理转换。

native 调 js js端也会生成一份本地模块配置localModules,native通过enqueue-JSCall直接调用js模块方法。也是通过ModuleID,MethodID调用。 rn提供了js模块中对于native模块时间的监听处理,在js端注册事件相应函数,通过native端事件监听处理。