前が反応し、ナビゲーション・ジャンプページを使用してネイティブのナビゲートを反応させるの説明、そして今、私たちは新しいにナビゲートする方法でネイティブのiOSを紹介ネイティブページを反応します。
ネイティブのジャンプは、ネイティブに反応します
- HYReactNativeManager管理クラスを作成します。
HYReactNativeManager.hでRCTBridgeDelegateは、合意を達成し、グローバルブリッジのプロパティを宣言文で宣言
@interface HYReactNativeManager : NSObject<RCTBridgeDelegate>
+ (instancetype)shareInstance;
// 全局唯一的bridge
@property (nonatomic, readonly, strong) RCTBridge *bridge;
@end
例示的な方法は、単一HYReactNativeManager.m、初期化方法、RCTBridgeDelegateプロトコル方法で実装されています。
#import "HYReactNativeManager.h"
@implementation HYReactNativeManager
static HYReactNativeManager *_instance = nil;
+ (instancetype)shareInstance{
if (_instance == nil) {
_instance = [[self alloc] init];
}
return _instance;
}
+ (instancetype)allocWithZone:(struct _NSZone *)zone{
if (_instance == nil) {
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
_instance = [super allocWithZone:zone];
});
}
return _instance;
}
-(instancetype)init{
if (self = [super init]) {
_bridge = [[RCTBridge alloc] initWithDelegate:self launchOptions:nil];
}
return self;
}
#pragma mark - RCTBridgeDelegate
- (NSURL *)sourceURLForBridge:(RCTBridge *)bridge {
# if DEBUG
return [[RCTBundleURLProvider sharedSettings] jsBundleURLForBundleRoot:@"index"
fallbackResource:nil];
# else
return [[NSBundle mainBundle] URLForResource:@"index" withExtension:@"jsbundle"];
#endif
}
@end
- 容器の新しいクラスが便利な作成方法のために、ネイティブのページを反応する、HYReactNativeBaseViewControllerクラスを作成します:
HYReactNativeBaseViewController.h完全なコードは次のとおりです。
#import <UIKit/UIKit.h>
@interface HYReactNativeBaseViewController : UIViewController
/**
传递到React Native的参数
*/
@property (nonatomic, strong) NSDictionary * initialProperty;
/**
React Native界面名称
*/
@property (nonatomic, copy) NSString * pageName;
+ (instancetype)RNPageWithName:(NSString*)pageName initialProperty:(NSDictionary*)initialProperty;
- (instancetype)initWithPageName:(NSString*)pageName initialProperty:(NSDictionary*)initialProperty;
@end
HYReactNativeBaseViewController.m完全なコードは次のとおりです。
#import "HYReactNativeBaseViewController.h"
#import <React/RCTRootView.h>
#import "HYReactNativeManager.h"
@implementation HYReactNativeBaseViewController
+ (instancetype)RNPageWithName:(NSString*)pageName initialProperty:(NSDictionary*)initialProperty{
HYReactNativeBaseViewController *vc = [[HYReactNativeBaseViewController alloc] initWithPageName:pageName initialProperty:initialProperty];
return vc;
}
- (instancetype)initWithPageName:(NSString*)pageName initialProperty:(NSDictionary*)initialProperty{
if(self = [super init]){
self.pageName = pageName;
self.initialProperty = initialProperty;
}
return self;
}
- (void)viewWillAppear:(BOOL)animated{
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:YES];
}
- (void)viewWillDisappear:(BOOL)animated{
[super viewWillDisappear:animated];
[self.navigationController setNavigationBarHidden:NO];
}
-(void)viewDidLoad{
[super viewDidLoad];
RCTRootView *rootView = [[RCTRootView alloc] initWithBridge:[HYReactNativeManager shareInstance].bridge
moduleName:self.pageName
initialProperties:self.initialProperty];
self.view = rootView;
}
@end
- 以下とホームボタンのクリックイベント:
- (void)clickButton:(UIButton*)button{
HYReactNativeBaseViewController *vc = [[HYReactNativeBaseViewController alloc] initWithPageName:@"Navigator" initialProperty:@{}];
[self presentViewController:vc animated:YES completion:nil];
}
二つは、ネイティブにネイティブ戻りに反応します
- HYModuleクラスの作成実装のRCTBridgeModule契約という
HYModule.hコード:
#import <React/RCTBridgeModule.h>
@interface HYModule : NSObject<RCTBridgeModule>
@end
.Mコード:
#import "HYModule.h"
@implementation HYModule
RCT_EXPORT_MODULE()
- (dispatch_queue_t)methodQueue {
return dispatch_get_main_queue();
}
RCT_EXPORT_METHOD(navigateBack){
[[NSNotificationCenter defaultCenter] postNotificationName:@"HYModuleNavigateBack" object:nil];
}
@end
- HYModuleNavigateBackにHYReactNativeBaseViewController.mにイベントリスナーを追加します。
@implementation HYReactNativeBaseViewController
//...省略代码
- (void)dealloc{
[[NSNotificationCenter defaultCenter] removeObserver:self];
}
- (void)navagateBack{
[self.navigationController popViewControllerAnimated:YES];
}
- (void)viewDidLoad{
[super viewDidLoad];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(navagateBack) name:@"HYModuleNavigateBack" object:nil];
RCTRootView *rootView = [[RCTRootView alloc] initWithBridge:[HYReactNativeManager shareInstance].bridge
moduleName:self.pageName
initialProperties:self.initialProperty];
self.view = rootView;
}
@end
RNページでは、輸入HYModules呼び出すとナビゲーションを経由してのページに戻りHYModules.navigateBack()メソッドを呼び出します。
import React, { Component } from 'react';
import {StyleSheet, Image, Text, Button,View, FlatList,TouchableOpacity,NativeModules} from 'react-native';
import { createStackNavigator, createAppContainer } from 'react-navigation'
var REQUEST_URL = "https://movie.douban.com/j/search_subjects?type=movie&tag=%E7%83%AD%E9%97%A8&sort=recommend&page_limit=20&page_start=0"
var HYModules = NativeModules.HYModule
class LogoTitle extends React.Component {
render() {
return (
<Image
source={require('../image/movie.png')}
style={{ width: 30, height: 30 }}
/>
);
}
}
export default class HotMovie extends Component<Props> {
static navigationOptions = {
headerTitle: <LogoTitle />,
headerLeft: (
<Button
onPress={() => HYModules.navigateBack()}
title="首页"
color="#fff"
/>
),
};
_onItemClick(item) {
this.props.navigation.navigate('Details',{itemId:item.id,cover:item.cover,title:item.title})
}
constructor(props){
super(props);
this.state = {
movies:null,
}
this.renderMovie = this.renderMovie.bind(this)
this.fetchData = this.fetchData.bind(this)
}
componentDidMount(){
this.fetchData()
}
fetchData(){
fetch(REQUEST_URL)
.then((response) => response.json())
.then((responseJson) => {
this.setState({
movies:responseJson.subjects
});
})
}
render() {
if (!this.state.movies) {
return this.renderLoadingView();
}
return (
<FlatList
data={this.state.movies}
renderItem={this.renderMovie}
style={styles.list}
keyExtractor={item => item.id}
/>
);
}
renderLoadingView(){
return (
<View style={styles.container}>
<Text>
正在加载...
</Text>
</View>
)
}
renderMovie({item}){
return(
<TouchableOpacity style={styles.item} onPress={() => this._onItemClick(item)}>
<Image source={{url:item.cover}} style={styles.thumbnail}/>
<View style={styles.itemRight}>
<Text>{item.title}</Text>
<Text>{item.rate}</Text>
</View>
</TouchableOpacity>
)
}
}
const styles = StyleSheet.create({
container: {
flex:1,
flexDirection:'row',
alignItems:'center',
justifyContent: 'center',
alignItems: 'center',
},
item:{
marginTop:1,
flexDirection:'row',
alignItems:'center',
justifyContent: 'flex-start',
height:100,
backgroundColor:'lightgray',
paddingLeft:10
},
thumbnail:{
width:53,
height:81,
backgroundColor:'lightgray'
},
itemRight:{
height:100,
justifyContent: 'center',
alignItems:'center',
paddingLeft:10
},
list: {
backgroundColor: "#F5FCFF"
}
});
完全なソースコード:https://github.com/dolacmeng/RNProject/tree/master