最近在公司做一個 RN 項目, 其中因為對接了一些友盟推送等功能,于是需要和原生通信數(shù)據(jù),于是上網(wǎng)查了下,這類資料在網(wǎng)上已經(jīng)有許多了,在這就做個整理,也為自己加深印象
首先 RN 與 IOS 通信,在原生端需創(chuàng)建一個bridge ,并遵守<RCTBridgeModule>協(xié)議
#import <React/RCTBridgeModule.h>
@interface PushModule : NSObject<RCTBridgeModule>
其次,在@implementation中導(dǎo)出 Module,這里,當(dāng)導(dǎo)出 module,也就是RCT_EXPORT_MODULE()之后,RN 中引用這個 module,就會自動創(chuàng)建一個對象,IOS 原生這邊不要額外 alloc 或者 new 一個新對象
@implementation PushModule
RCT_EXPORT_MODULE()
然后 有幾種通信方式
- 定義導(dǎo)出的方法名
RCT_EXPORT_METHOD(pushEvent:(NSString *)event callback:(RCTResponseSenderBlock)callback){
NSLog(@"----對React Native提供調(diào)用方法,Callback---%@",event);
NSString *callbackData = @"原生數(shù)據(jù)被RN調(diào)用"; //準(zhǔn)備回調(diào)回去的數(shù)據(jù)
callback(@[[NSNull null],callbackData]);
}
定義一個方法后,RN 就可通過NativeModules獲取到對于 Module后調(diào)用相應(yīng)方法,event是 RN 傳給 IOS 的值,IOS 這邊可通過 callback 這個 block 回調(diào)給 RN 數(shù)據(jù)
callBackEvent (){
NativeModules.PushModule.pushEvent(('RN->原生的數(shù)據(jù)'),(error, events) => {
if (error) {
console.log(error);
}else {
alert(events)
}
})
}
- promise實現(xiàn)的回調(diào)函數(shù)
這種,原生這邊區(qū)別不是很大, 但回調(diào) block 得使用特定的
static RCTPromiseResolveBlock _resolve;//成功回調(diào)
static RCTPromiseRejectBlock _reject;//失敗回調(diào)
RCT_REMAP_METHOD(pushPromisesEvent,
resolver:(RCTPromiseResolveBlock)resolve
rejecter:(RCTPromiseRejectBlock)reject){
_resolve = resolve;
_reject = reject;
}
//異步回調(diào)函數(shù)
+(void) handleResult:(id)result{
//原生Promises數(shù)據(jù)被RN調(diào)用
if ([result isEqualToString:@"獲取數(shù)據(jù)成功"]) {
_resolve(@[result]);
}else{
//返回錯誤信息
NSError *error=[NSError errorWithDomain:result code:101 userInfo:nil];
_reject(@"no_events", @"There were no events", error);
}
}
RN 調(diào)用方法
NativeModules.PushModule.pushPromisesEvent().then((events)=>{
alert(events+1111)
}).catch((e)=>{
// alert(e)
console.log("錯誤信息------"+e);
})
}
- 還有一種就是通知模式, 與前兩者不同,IOS 原生 module 不僅要遵守協(xié)議,還要繼承RCTEventEmitter類
#import <React/RCTEventEmitter.h>
#import <React/RCTBridgeModule.h>
@interface PushModule : RCTEventEmitter<RCTBridgeModule>
在 .m 的實現(xiàn)中有幾個繼承方法需要實現(xiàn)
//IOS 回傳給 RN 的通知方法
- (NSArray*)supportedEvents{
return @[@"Notice_name"]
}
- (void)startObserving
{
[PushTool sharedPushTool].isReady = YES;
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(notice:)
name:@"event-notice"
object:nil];
}
-(void)notice:(NSNotification*)notification
{
NSDictionary*obj = notification.object;
[self sendEventWithName:@"Notice_name" body:obj];
}
在 RN 這邊添加監(jiān)聽
var module = new NativeEventEmitter(NativeModules.PushModule)
module.addListener('Notice_name',(data)=>this.message(data));
之前 IOS 也可以和安卓那邊統(tǒng)一,使用DeviceEventEmitter來添加監(jiān)聽,但先好像已經(jīng)被遺棄