ReactNative原生UI组件(mapView reactNative中文网的学习心得)

原生视图都需要被一个RCTViewManager的子类来创建和管理。这些管理器在功能上有些类似“视图控制器”,但它们本质上都是单例 - React Native只会为每个管理器创建一个实例。它们创建原生的视图并提供给RCTUIManager,RCTUIManager则会反过来委托它们在需要的时候去设置和更新视图的属性。RCTViewManager还会代理视图的所有委托,并给JavaScript发回对应的事件。

提供原生视图很简单:

首先创建一个子类
添加RCT_EXPORT_MODULE()标记宏
实现-(UIView *)view方法

#import "RNTMapManager.h"
#import "RCTConvert+Mapkit.h"

@interface RNTMapManager ()<MKMapViewDelegate>

@end

@implementation RNTMapManager
RCT_EXPORT_MODULE();
-(UIView *)view{
    MKMapView *view = [[MKMapView alloc]init];
    view.pitchEnabled=NO;
    view.showsTraffic = YES;
    view.showsUserLocation = YES;
    view.delegate = self;
    return view;
}

MapView.js代码如下:

import React, { Component,PropTypes } from 'react';
import {
    requireNativeComponent
} from 'react-native';
var RNTMap = requireNativeComponent('RNTMap', MapView);

export default class MapView extends Component {
    render() {
        return <RNTMap {...this.props} />;
    }

}

在index.ios.js中引入MapView.js代码如下:

import MapView from './MapView';
class App extends Component{
        return(
            <MapView style={styles.container}
                     showsScale={true}
            />
        );
    }
}
const styles = StyleSheet.create({

    container:{
        flex:1,
        marginTop:20,
    backgroundColor:'red',
    },
}

这时候已经可以看到地图出现了

屏幕快照 2017-07-10 下午5.23.56.png

2.原生像js提供属性,供js操作控制
通过RCT_EXPORT_VIEW_PROPERTY()宏可以向js提供属性
比如
在上面RNTMapManager.m里添加
RCT_EXPORT_VIEW_PROPERTY(showsScale, BOOL)//注意这里的属性名字要和原生的属性名字要一致
然后在index.ios.js的render方法里

render(){
        return(
            <MapView style={styles.container}
                     showsScale={true}
            />
        );
    }

这时候就可以看到左上角出现的比例


屏幕快照 2017-07-10 下午5.39.43.png

3.添加自定义属性
这里稍微复杂一点 实现当我们在JS里改变地图的可视区域的时候,视角会平滑地移动过去
首先通过RCT_CUSTOM_VIEW_PROPERTY添加自定义属性
在RCTMapView.m里面添加自定义属性region

RCT_CUSTOM_VIEW_PROPERTY(region, MKCoordinateRegion, RNTMap){
    [view setRegion:json? [RCTConvert MKCoordinateRegion:json] :defaultView.region animated:YES];
};

然后创建一个RNTMap继承MKMapView
RNTMap.h代码如下(RNTMap.m暂时不需要实现其他代码)


#import <MapKit/MapKit.h>
#import <React/RCTComponent.h>
@interface RNTMap : MKMapView
@property(nonatomic,copy)RCTBubblingEventBlock onChange;
@end

RCTMapManager.m里面的-(UIView *)view替换成下面的

-(UIView *)view{
    MKMapView *view = [[MKMapView alloc]init];
    view.pitchEnabled=NO;
    view.showsTraffic = YES;
    view.showsUserLocation = YES;
    view.delegate = self;
    return view;
}

下面开始写MapView.js代码如下

var RNTMap = requireNativeComponent('RNTMap', MapView);

export default class MapView extends Component {
    render() {
        return <RNTMap {...this.props} />;
    }

}
//这里解决用户要想知道我们的组件有哪些的问题,我们可以创建一个封装组件,并且通过PropTypes来说明这个组件的接口
MapView.PropTypes={
    pitchEnabled:React.PropTypes.bool,
    region:React.PropTypes.shape({
        latitude: React.PropTypes.number.isRequired,
        longitude: React.PropTypes.number.isRequired,
        latitudeDelta: React.PropTypes.number.isRequired,
        longitudeDelta: React.PropTypes.number.isRequired,
    }),
 
}

index.ios.js render代码如下

render(){
        var region = {
            latitude:30.40,
            longitude:120.51,
            latitudeDelta:0.1,
            longitudeDelta:0.1,
        };
        return(
            <MapView style={styles.container}
                     showsScale={true}
                     region={region}
                 
            />
        );
    }

效果如下图(本页的图片都是模拟器 经纬度显示可能不准确):

屏幕快照 2017-07-10 下午5.51.13.png
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

友情链接更多精彩内容