SuperMap iTablet定制分为原生和JavaScript两部分。
原生包含App图标和启动页,需要在App编译前改动;JavaScript部分包含App内部界面与功能的定制,由iTalbet/configs/config.json文件配置。
环境搭建
搭建React Native环境
搭建React Naïve环境,参考https://reactnative.cn/docs/getting-started/。
react-native: v0.57.4。
node: 不高于v12.10.0。
若首次拷贝项目,需要备份nodemodules,然后npm install后,把nodemodules重新拷贝进iTalbet目录下。
调试
(1).iOS版
AppDelegate.m设置调试IP,摇晃移动设备“-Debug JS Remotely”打开调试。
+(RCTRootView *)loadBunle:(NSDictionary *)launchOptions {
...
if ([fileMgr fileExistsAtPath:jsBundlePath isDirectory:&isDir]) {
jsCodeLocation = [NSURL URLWithString:jsBundlePath];
} else {
#if DEBUG
// 有线调试
//[[RCTBundleURLProvider sharedSettings] setJsLocation:@"localhost"];
//无线调试,保持电脑和移动设备在同一WIFI下,下面为电脑的IP
[[RCTBundleURLProvider sharedSettings] setJsLocation:@"10.10.65.195"];
#endif
jsCodeLocation = [[RCTBundleURLProvider sharedSettings] jsBundleURLForBundleRoot:@"index" fallbackResource:nil];
}
...
}
(2).Android版
数据线连接调试
adb reverse tcp:8081 tcp:8081
输入IP + Port无线调试
adb shell input keyevent 82 - Dev Settings - Debug server host & port for device
打开调试界面
adb shell input keyevent 82 - Debug JS Remotely
App图标和启动页
App图标和启动页需要在原生代码中修改。
Android
图标设置文件:AndroidManifest.xml“MyProject/android/app/src/main/AndroidManifest.xml”。
<application>
android:icon="App图标文件路径"
</application>
启动页设置文件:“ /layout/launch_screen.xml”。
iOS
图标设置文件:Images.xcassets。
启动页设置文件:launchScreen.storyboard。
配置文件结构
Config文件结构表
字段名称 | 字段解释 | 字段类型 | 可选参数 | 是否必填 |
---|---|---|---|---|
name | App标题 | String | 是 | |
alias | App简称,用于内部部分内容 | String | 是 | |
version | config版本号 | String | 是 | |
language | 默认语言 | String | CN, EN | 否 |
about | 关于的配置 | Object | isShow:boolean,//是否显示 url:String,//关于的html链接 |
否 |
login | 登录的方式 | Array | [“Online”, “iPortal”] | 否 |
tabModules | App Tabs中的界面配置 | Array | [“Home”,“Friend”,”Find”, “Mine”,Exmaple, ...] //Example为定制界面 |
是 |
mapModules | 地图功能模块的配置 | Array | [见表2] | 是 |
infoServer | 消息服务 | Object | “url”: //消息服务下载文件地址 “fileName”://消息服务下载文件名称 |
若tabsModules包含Friend则是,反之否 |
mineModules | 我的 功能配置 | Array | {“key”:”IMPORT”},//导入 {“key”:”MY_SERVICE”},//服务 {“key”:”DATA”},//数据 {“key”:”MARK”},//标注 {“key”:”MAP”},//地图 {“key”:”SCENE”},//场景 {“key”:”BASE_MAP”},//底图 {“key”:”SYMBOL”},//符号 {“key”:”TEMPLATE”},//模板 {“key:””MyColor”},//色带 |
是 |
首页模块定制mapModules
字段名称 | 字段解释 | 字段类型 | 可选参数 | 是否必填 |
---|---|---|---|---|
key | 键值,用于判断类型 | String | 是 | |
functionModules | 地图右侧功能模块 | Array | startModule 二维地图 开始 start3DModule 三维地图 开始 addModule 添加 styleModule 风格 toolModule 工具 shareModule 二维分享 share3DModule 三维分享 fly3DModule 三维旅行轨迹 tool3DModule 三维工具 arAIAssistant AI助手 navigationModule 导航 themeModule 专题 collectionModule 采集 editModule 编辑 plotModule 标绘 analysisModule 分析 incrementModule 增量路网 |
否 |
example | 示例地图信息 | Object | {"checkUrl” //检查下载数据信息 "nickname” //检测下载的数据信息 "type” //下载数据的类型 "url" //下载数据的路径 "example": { // 示范数据 EN: { //系统语言关联的数据 name, // 示例数据名称 mapName, // 默认地图名称 }, DEFAULT: [//可为数组或者对象,第一个为默认示范数据 { name, mapName,},], JA: { //可为数组或者对象,第一个为默认示范数据 name, mapName, }, }, } |
否 |
tabModules | 地图底部Tabs | Array | // MapTabs.MapView(地图)和 MapTabs.Sence(三维场景)需要在排第一位 // MapTabs 普通地图: [ MapTabs.MapView, //二维地图界面 MapTabs.LayerManager,//二维图层管理界面 MapTabs.LayerAttribute,//二维属性界面 MapTabs.LayerAttribute, /二维地图设置界面 ] 三维地图: [ MapTabs.Scene, // 场景界面 MapTabs.Layer3D, // 三维图层管理界面 MapTabs.Attribute3D, // 三维属性界面 MapTabs.Settings3D // 三维场景设置界面 ] |
否(二三维默认包含) |
headerButtons | 地图导航栏右侧按钮 | Array | [// 自定义按钮 { key, image, action, }, // App默认按钮 'audio', 'undo' 'search', 'share' ] |
否 |
// iTalbet/configs/mapModules/MapExample.js
import { ConstOnline, MapTabs } from '../../src/constants'
import { getThemeAssets } from '../../src/assets'
import { Module } from '../../src/class'
import {
startModule,
addModule,
markModule,
toolModule,
shareModule,
} from '../../src/containers/workspace/components/ToolBar/modules'
// import { functionExample } from '../map
'
export default class MapExample extends Module {
constructor () {
super({
key: 'MapExample', // key值唯一
// 下载的地图示例数据(可选)
example: { // 数据可为数组或对象,当前语言对应数据是数组是,第一个为默认数据,并提示下载
DEFAULT: { // 默认数据,若当前语言没有指定示范数据,默认使用DEFAULT
name: '湖北',
mapName: 'LandBuild',
},
EN: [ // 英文数据名称
{
name: 'PrecipitationOfUSA',
mapName: 'LosAngeles',
},
{
name: 'LosAngles',
mapName: 'LosAngles',
},
],
},
// 配置地图右侧工具栏(可选)
functionModules: [
startModule,
addModule,
markModule,
toolModule,
shareModule,
],
// 配置地图底部Tab栏(可选) MapTabs.MapView(地图)和 MapTabs.Sence(三维场景)需要在排第一位
// tabModules: [MapTabs.MapView, MapTabs.LayerManager, MapTabs.LayerAttribute, MapTabs.MapSetting]
})
}
// 首页模块数据
getChunk = language => {
return this.createChunk(language, {
key: 'MapExample',
// 根据语言获取地图模块名称
title: language === 'CN' ? '示例模块' : 'Example',
// 模块图片
moduleImage: getThemeAssets().nav.icon_map_theme,
// 点击时模块高亮图片
moduleImageTouch: getThemeAssets().nav.icon_map_theme_touch,
// 默认地图名称
defaultMapName: GLOBAL.language === 'CN' ? 'LandBuild' : 'PrecipitationOfUSA',
// 地图默认底图数据
baseMapSource: {...ConstOnline.Google},
// 地图默认底图当前显示的地图
baseMapIndex: 3,
licenceType: 0x04,
})
}
}
// iTalbet/configs/mapModules/index.js
// 入口文件
/** App自带模块 **/
import * as AppModule from '../../src/customModule/mapModules'
/** 自定义模块 **/
// import MapExample from './MapExample'
/** export顺序为首页模块显示顺序 **/
export default [
AppModule.MapEditConfig,
AppModule.Map3DConfig,
AppModule.MapCollectionConfig,
AppModule.MapARConfig,
AppModule.MapNavigationConfig,
// 自定义模块
// new MapExample,
AppModule.MapThemeConfig,
AppModule.MapPlottingConfig,
AppModule.MapAnalystConfig,
]
首页tabModules定制
// iTablet/configs/tabModules/Example.js
import React, { Component } from 'react'
import { View } from 'react-native'
import { connect } from 'react-redux'
import TabContainer from '../../src/containers/tabs/TabContainer'
import { getThemeAssets } from '../../src/assets'
class Example extends Component {
props: {
language: string, // redux存放中的当前语言
navigation: Object, // TabNavigator导航
device: Object, // redux存放设备信息
}
constructor(props) {
super(props)
}
static getTitle = language => {
return language === 'CN' ? 'Map Tab示例' : 'Map Tab Example'
}
render() {
// TabContainer为首页Tab的界面容器,具体Props参照Container组件
return (
<TabContainer
ref={ref => (this.container = ref)}
hideInBackground={false}
showFullInMap={true}
headerProps={{ // Header属性,具体参照Header组件
title: this.getTitle(),
withoutBack: true,
}}
navigation={this.props.navigation}
>
<View style={{flex: 1}} />
</TabContainer>
)
}
}
const mapDispatchToProps = {}
const mapStateToProps = state => ({
device: state.device.toJS().device,
language: state.setting.toJS().language,
})
// 链接Redux,获取持久化/全局动态数据
const MyExample = connect(
mapStateToProps,
mapDispatchToProps,
)(Example)
// 固定格式
export default {
key: 'Example',
getTitle: MyExample.getTitle, // 根据系统语言获取Title
Screen: MyExample, // 自定义Tab界面
image: getThemeAssets().tabBar.tab_discover, // Tab未点击图片
selectedImage: getThemeAssets().tabBar.tab_discover_selected,
// Tab高亮图片
}
// iTablet/configs/tabModules/index.js
// 入口文件
/** export顺序为首页Tabs显示顺序, 默认第一个为Home **/
export default [
AppTabs.Friend,
AppTabs.Find,
// Example,
AppTabs.Mine,
]
地图右侧FunctionToolbar定制
// iTablet/configs/mapFunctionModules/index.js
// 入口文件
import functionExample from './FunctionExample'
// 获取自定义模块
function getModule (type, params = {}) {
let module = {}
if (type === 'FunctionExample') {
module = functionExample()
}
return module
}
export default {
getModule,
}
export {
functionExample,
}
// iTablet/configs/mapFunctionModules/FUnctionExample/index.js
import ToolbarModule from '../../../src/containers/workspace/components/ToolBar/modules/ToolbarModule'
import { ToolbarType } from '../../../src/constants'
import CustomFunctionModule from '../../../src/class/CustomFunctionModule'
import FunctionData from './FunctionData'
import FunctionAction from './FunctionAction'
class FunctionExample extends CustomFunctionModule {
constructor (props) {
super(props)
this.setTypes(FunctionExampleTypes) // 用于检测Type是否可用,避免与系统自带类型冲突
}
getToolbarSize = () => {}
action = () => {
// 注册当前模块数据到ToolbarModule中
this.setModuleData(this.type)
const params = ToolbarModule.getParams()
// 获取显示的数据
const _data = FunctionData.getData(this.type, params)
// Toolbar 内容弹出框的类型
const containerType = ToolbarType.table
// 获取内容弹出框的尺寸,自定义尺寸需要复写getToolbarSize方法
const data = ToolbarModule.getToolbarSize(containerType, {})
// 显示全屏
params.showFullMap && params.showFullMap(true)
// 弹出Toolbar并设置类型和内容
params.setToolbarVisible(true, this.type, {
containerType,
isFullScreen: true,
...data,
..._data,
})
}
}
export default function () {
return new FunctionExample({
type: 'FunctionExample',
title: '示例',
size: 'large',
image: require('../../../src/assets/function/icon_function_start.png'),
getData: FunctionData.getData, // 当前Function模块获取数据的方法
actions: FunctionAction, // 当前Function模块所有事件
})
}
/**
* 地图右侧功能基础类
*/
import ToolbarModule from '../containers/workspace/components/ToolBar/modules/ToolbarModule'
export default class FunctionModule {
constructor(props) {
this.props = props || {}
this.type = this.props.type // 类型
this.key = this.props.title
this.title = this.props.title || '' // 图标下的文字
this.size = this.props.size // large | normal(默认) 显示的图标大小
this.image = this.props.image // 图标
// 模块相关数据
this.getData = this.props.getData
this.getMenuData = this.props.getMenuData
// 整合默认事件和自定义事件
this.actions = Object(this.props.actions || {}, Actions)
}
/**
* 自定义高度
* @param type
* @param orientation 横竖屏方向
* @param additional 补充数据,自行定义
*/
getToolbarSize = (type, orientation, additional) => {
// let height = 0,
// column = -1,
// row = -1
// return { height, column, row }
}
/**
* 存放当前数据到ToolbarModule
* @param type
*/
setModuleData = (type = this.type) => {
ToolbarModule.setData({
type,
getData: this.getData,
actions: this.actions,
getToolbarSize: this.getToolbarSize,
})
}
/**
* 启动模块事件
* @param type
*/
action = type => {
this.setModuleData(type)
this.props.action && this.props.action()
}
/**
* 添加模块事件
* @param _actions
*/
addActions = (_actions = {}) => {
this.actions = Object(this.actions || {}, _actions)
}
}
/** 模块相关默认事件 **/
const Actions = {
/********** ToolbarBottomButtons事件 **********/
commit: () => {}, // 提交
menu: () => {}, // 屏幕中间的指滑菜单
showMenuBox: () => {}, // 指滑菜单和内容框交替显示
showAttribute: () => {}, // 显示属性
undo: () => {}, // 地图撤销
redo: () => {}, // 地图重做
close: () => {}, // 关闭Toolbar
toolbarBack: () => {}, // Toolbar界面回退
/********** ToolbarContentView事件 **********/
listSelectableAction: () => {}, // Toolbar SelectList类型点击事件
listAction: () => {}, // Toolbar List类型点击事件
/********** 地图事件 **********/
geometrySelected: () => {}, // 地图对象选择事件
}
常用组件
常用组件引用路径 import { 组件 } from ‘src/component’ // src/component改为对应的相对路径。
Container
界面容器,自带Header导航栏。
// 属性
props: {
style?: StyleSheet, // 自定义内容样式
children: any, // Component自带属性,子组件
header?: any, // 自定义导航栏
bottomBar?: any, // 自定义底部栏
withoutHeader?: boolean, // 设置没有导航栏
headerProps?: Object, // 导航栏属性(参照Header.js)
bottomProps?: Object, // {type: 'fix'} 底部栏和内容是同一级的,若不是fix,则底部栏是压盖在内容上的
navigation: Object, // react-navigation的导航
initWithLoading?: boolean, // 初始化显示加载
dialogInfo?: boolean, // 加载的文字
scrollable?: boolean, // 内容是ScrollView或者View
showFullInMap?: boolean, // 横屏时,地图上层界面是否显示半屏
blankOpacity?: Number, // 横屏时,半屏遮罩透明度
hideInBackground?: boolean, // 在mapview和map3d中,StackNavigator中有新页面时是否隐藏本页面
orientation?: String, // redux中的实时横竖屏数据
onOverlayPress?: () => {}, // 横屏时,半屏遮罩点击事件
isOverlayBefore?: boolean, // 横屏是,遮罩的位置,true为左,反之为右
}
// 默认属性
static defaultProps = {
orientation:
Dimensions.get('screen').height > Dimensions.get('screen').width
? 'PORTRAIT'
: 'LANDSCAPE',
withoutHeader: false,
sideMenu: false,
initWithLoading: false,
scrollable: false,
showFullInMap: false, //是否在mapview和map3d中显示全屏页面,默认半屏
blankOpacity: 0, //透明半屏的透明度
hideInBackground: true, //在mapview和map3d中,StackNavigator中有新页面时是否隐藏本页面
isOverlayBefore: true,
}
Header
导航栏。
// 属性
props: {
header?: any, // 自定义Header
headerStyle?: StyleSheet, // 自定义Header Style
withoutBack?: boolean, // 是否有返回按钮
backBtnType?: string, // 返回按钮类型(white, gray)
backAction?: any, // 返回事件
title?: string, // 标题
subTitle?: string, // 副标题
subTitleStyle?: StyleSheet, // 副标题样式
headerViewStyle?: StyleSheet, // Header Style
headerLeftStyle?: StyleSheet, // Header左边View样式
headerRightStyle?: StyleSheet, // Header右边View样式
headerTitleViewStyle?: StyleSheet, // Header中间Title View样式
headerTitleStyle?: StyleSheet, // Header标题样式
headerLeft?: any, // Header左端组件,可为Array
headerRight?: any, // Header右端组件,可为Array
opacity?: number, // 透明度
activeOpacity?: number, // 返回键点击透明度
type?: string, // default | float:浮动Header | floatNoTitle:浮动无title,透明背景 | fix:固定顶部,绝对定位
navigation?: any, // navigation
count?: any, // 消息提示数量
darkBackBtn?: boolean, // 黑色透明背景,返回按钮
headerCenter?: any, // 自定义Header中间View
backImg?: any, // 返回按钮图片
statusVisible?: boolean, // 状态栏是否可见
}
// 默认属性
static defaultProps = {
title: '',
withoutBack: false,
backBtnType: 'gray',
opacity: 1,
activeOpacity: 0.2,
type: 'default',
headerViewStyle: styles.navigationHeader,
headerLeftStyle: styles.headerLeftView,
headerTitleViewStyle: styles.headerTitleView,
headerTitleStyle: styles.headerTitle,
subTitleStyle: styles.subTitle,
count: 0,
darkBackBtn: false,
headerCenter: null,
}
BubblePane
气泡提示框,点击则消失。
<BubblePane ref={ref => (GLOBAL.bubblePane = ref)} maxSize={1} />
// 属性
props: {
maxSize?: number, // 最大显示气泡消息个数,默认3
}
/**
* 添加气泡提示
* @param bubble 气泡数据
* { title, type }
* @param position Pane位置
* {top, bottom, left, right}
*/
GLOBAL.bubblePane.addBubble(bubble = {}, position)
/** 清除气泡提示 **/
GLOBAL.bubblePane.clear({})
/** 清空并重置位置 **/
GLOBAL.bubblePane.reset({})
SearchBar
搜索框。
// 属性
props: {
onBlur?: () => {}, // 失去焦点事件
onFocus?: () => {}, // 获得焦点事件
onClear?: () => {}, // 清除文字
onSubmitEditing?: () => {}, // 提交
defaultValue: string, // 默认值
editable: string, // 是否可编辑
placeholder: string, // 占位符
isFocused?: string, // 是否获得焦点
keyboardAppearance?: string, // 键盘样式
returnKeyType?: string, // Android上确定按钮文字
returnKeyLabel?: string, // 键盘返回按钮文字
blurOnSubmit?: string, // 是否提交失去焦点
}
// 默认属性
static defaultProps = {
isFocused: false,
keyboardAppearance: 'default',
returnKeyType: 'search',
returnKeyLabel: '搜索',
blurOnSubmit: true,
}
<SearchBar
ref={ref => (this.searchBar = ref)}
defaultValue={this.state.defaultValue}
onSubmitEditing={async searchKey => {}}
placeholder={'请输入搜索关键字'}
/>
MTBtn
图片按钮,可搭配文字。
// 属性
props: {
image: any, // 未点击时图片
selectedImage?: any, // 点击时图片
size?: string, // 图片文字大小
title?: string, // 文字
onPress: () => {}, // 点击事件
textStyle?: any, // 自定义文字样式
textColor?: string, // 自定义文字颜色
imageStyle?: any, // 自定义图片样式
style?: any, // 自定义按钮样式
selected?: boolean, // 是否被选中
selectMode?: string, // normal: 选择 | 非选择状态 // flash:按下和松开
activeOpacity?: number, // 点击按钮透明度 0 - 1
separator?: number, // 图片和文字的间距
onPressIn?: () => {}, // 按下时的事件
onPressOut?: () => {}, // 松开时的事件
}
// 默认属性
static defaultProps = {
activeOpacity: 1,
size: 'normal',
selected: false,
selectMode: 'normal',
}
// Size的类型
MTBtn.Size = {
LARGE: 'large',
NORMAL: 'normal',
SMALL: 'small',
}
// 示例
<MTBtn
key={'undo'}
title={getLanguage(this.props.language).Map_Attribute.ATTRIBUTE_UNDO}
style={styles.button}
textColor={!this.state.canBeUndo && color.contentColorGray}
image={
this.state.canBeUndo
? getThemeAssets().publicAssets.icon_undo
: getPublicAssets().attribute.icon_undo_disable
}
imageStyle={styles.headerBtn}
onPress={() => this.setAttributeHistory('undo')}
/>
Input
输入框,当有值时,显示清除按钮。
// 属性,参照React Native TextInput
props: {
accessible?: boolean,
accessibilityLabel?: string,
showClear?: boolean, // 显示清除按钮
isKeyboardAvoiding?: boolean, // 是否使用KeyboardAvoidingView键盘
behavior?: string, // ReactNative KeyboardAvoidingView
style?: Object, // Input样式
inputStyle?: Object, // 自定义输入框样式
placeholder?: string, // 占位符
value?: string, // 输入框值
defaultValue?: string, // 输入框默认值
keyboardAppearance?: string, // 键盘颜色
returnKeyType?: string, // 返回键类型
placeholderTextColor?: string, // 占位符颜色
keyboardType?: string, // 弹出键盘类型
textContentType?: string, // iOS输入内容类型,eg:password
secureTextEntry?: boolean, // 密码
onChangeText?: () => {}, // 输入回调
onClear?: () => {}, // 自定义清除事件
}
static defaultProps = {
label: '',
keyboardAppearance: 'dark',
returnKeyType: 'done',
keyboardType: 'default',
placeholder: '',
placeholderTextColor: color.themePlaceHolder,
showClear: false,
isKeyboardAvoiding: false,
secureTextEntry: false,
}
Row
多类型行,文本+(输入框,单选框,数字,文字按钮)。
props: {
style?: Object, // 自定义Row样式
titleStyle?: Object, // 左侧文字样式
customRightStyle?: Object, // 右侧内容样式
title: string, // 左侧文字
defaultValue?: any, // 默认值
customRightView?: any, // 自定义右侧内容
type?: string, // Row.Type
inputType?: string, // Row.InputType
value?: any, // 值
radioArr?: Array, // 单选框组[{title, value}]
radioColumn?: number, // 单选框组列数
separatorHeight?: number, // 单选框行间隔
minValue?: number, // CHOOSE_NUMBER 最小值
maxValue?: number, // CHOOSE_NUMBER 最大值
commonDifference?: number, // CHOOSE_NUMBER 公差,值之间差值
times?: number, // CHOOSE_NUMBER 倍数
unit?: string, // CHOOSE_NUMBER 单位
getValue?: () => {}, // 获取值的回调
disable?: boolean, // 是否可操作
}
Row.Type = {
INPUT: 'input', // 普通输入框
INPUT_WRAP: 'input_wrap', // 含删除输入框Input
RADIO: 'radio', // 一个单选框
RADIO_GROUP: 'radio_group', // 多个单选框
CHOOSE_NUMBER: 'choose_number', // 含数字增减按钮
CHOOSE_COLOR: 'choose_color', // 色板
TEXT_BTN: 'text_btn', // 文字按钮
}
// 输入框内容,键盘类型
Row.InputType = {
NUMERIC: 'numeric', // 数字键盘
DEFAULT: 'default', // 默认
}
// 示例
<Row
style={{ marginTop: scaleSize(30) }}
customRightStyle={styles.customRightStyle}
key={'名称'}
disable={this.state.isEdit}
defaultValue={this.state.name}
type={Row.Type.INPUT_WRAP}
title={getLanguage(global.language).Map_Attribute.NAME}
getValue={this.getInputValue}
/>
<Row
style={{ marginTop: scaleSize(15) }}
customRightStyle={styles.customRightStyle}
key={'别名'}
disable={this.state.isEdit}
defaultValue={this.state.caption}
type={Row.Type.INPUT_WRAP}
title={getLanguage(global.language).Map_Attribute.ALIAS}
getValue={this.getInputValue}
/>
<Row
style={{ marginTop: scaleSize(30) }}
key={'类型'}
type={Row.Type.RADIO_GROUP}
title={getLanguage(global.language).Map_Attribute.TYPE}
defaultValue={this.state.type}
disable={this.state.isEdit}
customRightView={
<TouchableOpacity
style={{
flexDirection: 'row',
justifyContent: 'space-between',
alignItems: 'center',
}}
onPress={
this.state.isEdit
? null
: () => {
Keyboard.dismiss()
this.popModal && this.popModal.setVisible(true)
}
}
>
<Text style={{ fontSize: scaleSize(24), color: color.gray }}>
{this.state.currentPopData
? this.state.currentPopData.key
: null}
</Text>
<Image
source={require('../../../../assets/Mine/mine_my_arrow.png')}
style={{ height: scaleSize(28), width: scaleSize(28) }}
/>
</TouchableOpacity>
}
/>
<Row
style={{ marginTop: scaleSize(15) }}
key={'必填'}
type={Row.Type.RADIO_GROUP}
title={getLanguage(global.language).Map_Attribute.REQUIRED}
disable={this.state.isEdit}
defaultValue={this.state.isRequired}
radioArr={[
{ title: getLanguage(global.language).Prompt.YES, value: true },
{ title: getLanguage(global.language).Prompt.NO, value: false },
]}
radioColumn={2}
getValue={this.getType}
/>
SurfaceView
画板(eg:圆选裁剪,框选裁剪),并获取点位置。
props: {
style: Object,
type: string, // ShapeType
orientation: string, // 横竖屏
}
// 显隐SurfaceView
show = isShow => {
// ...
}
// 获取点位置
getResult = () => {
switch (this.props.type) {
case ShapeType.CIRCLE:
return [this.state.startPoint, this.state.endPoint]
case ShapeType.RECTANGLE:
default:
return [
this.state.startPoint,
{ x: this.state.startPoint.x, y: this.state.endPoint.y },
this.state.endPoint,
{ x: this.state.endPoint.x, y: this.state.startPoint.y },
]
}
}
const ShapeType = {
RECTANGLE: 'RECTANGLE',
CIRCLE: 'CIRCLE',
}
TableList
表格列表。Table类型根据orientation限制行或列,PORTRAIT时列固定,行自适应;LANDSCAPE时行固定,列自适应。scrollTable类型始终固定列数。
props: {
data: Array, // 数据
lineSeparator?: number, // 行间距
style?: Object, // 表格样式
cellStyle?: Object, // Cell样式
rowStyle?: Object, // 行样式
renderCell: () => {}, // 自定义Cell, 必填
type?: string, // normal 固定 | scroll 滚动
device?: string, // 设备信息
isAutoType?: Boolean, // 是否根据个数,自适应滚动或固定表格
column?: number, // 列数
numberOfRows?: number, // 行数限制
}
static defaultProps = {
data: [],
column: 2,
numberOfRows: 6,
type: 'table', // normal | scroll
lineSeparator: 5,
isAutoType: true,
}
// 示例
_renderItem = ({ item, rowIndex, cellIndex }) => {
return (
<MTBtn
key={rowIndex + '-' + cellIndex}
title={item.title}
textColor={item.disable ? '#A0A0A0' : color.font_color_white}
textStyle={{ fontSize: setSpText(20) }}
image={item.image}
background={item.background}
onPress={() => {
!item.disable && this.itemAction(item)
}}
/>
)
}
<TableList
data={this.props.data}
column={this.props.column}
numberOfRows={this.props.row}
type={this.props.containerType}
renderCell={this._renderItem}
device={this.props.device}
/>
Progress / PieProgress
条形/圆形进度条。
static propTypes = { ...View.propTypes,
//当前进度
progress?: PropTypes.number,
//second progress进度
buffer?: PropTypes.number,
//进度条颜色
progressColor?: PropTypes.string,
//buffer进度条颜色
bufferColor?: PropTypes.string,
//进度动画时长
progressAniDuration?: PropTypes.number,
//buffer动画时长
bufferAniDuration?: PropTypes.number,
}
static defaultProps = {
//进度条颜色
progressColor: 'yellow',
//buffer进度条颜色
bufferColor: 'rgba(255,0,0,0.7)',
//进度条动画时长
progressAniDuration: 300,
//buffer进度条动画时长
bufferAniDuration: 300,
}
CheckBox
复选框。
props: {
onChange: () => {}, // 选中/取消的回调
style?: Object,
imgStyle?: Object,
disable?: boolean,
checked?: boolean,
}
static defaultProps = {
disable: false,
}
MenuDialog
界面中间指滑菜单:触摸屏幕,白色框体上下滑动,松手或者点击菜单选项,为选中操作。触摸范围:父类组件全屏。
// MenuDialog属性
props: {
data: Array, // 数据
selectKey?: '', // 当前选中的key
viewableItems?: number, // 可见范围item的数量,默认为3
autoSelect?: boolean, // 松手自动选择
onSelect?: () => {}, // 选中item的回调
device: Object, // 设备信息
}
// MenuDialog使用方法
<MenuDialog
data={this.state.data}
selectKey={this.props.selectKey}
autoSelect={true}
device={this.props.device}
onSelect={item => {
this.setState({
selectKey: item.selectKey,
selectName: item.selectName || item.key,
})
}}
/>
// MenuDialog数据格式
data = [
{
key: 'test',
action: () => {}, // 点击事件
selectKey: 'test', // 菜单Item文字
},
]
FingerMenu
固定的指滑菜单,上下滚动菜单,中间蓝色部分为选中项。
// 属性
props: {
data: Array, // 数据[{ key 显示Title, icon 图标, highLightIcon 选中的图标 }]
initialKey: string, // 初始数据
selectKey?: '', // 当前选中的key
viewableItems?: number, // 可见范围item的数量,单数
autoSelect?: boolean, // 松手自动选择
onSelect?: () => {}, // 选中item的回调
onScroll?: () => {}, // 滚动选中item的回调
onScrollEnd?: () => {}, // 滚动结束的回调
onDragEnd?: () => {}, // 手指拖动结束的回调
rowHeight?: number, // 行高
style?: Object,
}
static defaultProps = {
data: [],
initialKey: '',
viewableItems: 5,
rowHeight: ITEM_HEIGHT,
}
// 示例
<FingerMenu
ref={ref => (this.fingerMenu = ref)}
data={this.props.popData}
initialKey={
(this.props.currentPopData && this.props.currentPopData.key) ||
(this.props.popData.length > 0 && this.props.popData[0].key)
}
/>
// 数据格式
data = [
{
key: 'test',
icon: 图标,
highLightIcon: 选中的图标,
},
]
PopModalList
底部弹出列表。
finger类型:对FingerMenu封装,多了“取消”、“确定”两个按钮。
mutil类型:多选列表。
const LIST_TYPE = {
FINGER: 'finger', // 指滑单选列表
MULTI: 'multi', // 复选框多选列表
}
props: {
language?: String, // 语言,用于根据当前语言设置按钮Title
type?: String, // LIST_TYPE
confirm: () => {}, // 自定义确定事件
cancel: () => {}, // 自定义取消事件
confirmTitle?: String, // 自定义确定Title
cancelTitle?: String, // 自定义取消Title
popData: Array, // 数据[{ key 显示Title, icon 图标, highLightIcon 选中的图标 }]
currentPopData: Object, // 当前选中对象,用户初始化选中对象
}
static defaultProps = {
type: LIST_TYPE.FINGER, // finger, multi
}
// 示例
<PopModalList
ref={ref => (this.popModal = ref)}
language={this.props.language}
popData={this.state.popData}
currentPopData={this.state.currentPopData}
confirm={data => {}}
/>
data = [
{
key: 'test',
icon: 图标,
highLightIcon: 选中的图标,
},
]
LinkageList
二级联动菜单,支持改变左右列表宽度。
props: {
language: String,
data: Array, // 菜单数据
titles: Array, //左右侧标题
onLeftPress?: () => {}, //左侧点击
onRightPress?: () => {}, //右侧点击
styles?: Object, //样式
adjustmentWidth?: boolean,
isMultiple: boolean, //是否是多选
}
static defaultProps = {
adjustmentWidth: false,
}
// 数据格式
data = [
{
title: alias,
server: udbPath,
engineType: EngineType.UDB,
data: [{title: '111', parentTitle: alias}], // 右侧列表数据
},
]
// 示例
<LinkageList
ref={ref => (this.linkageList = ref)}
language={this.props.language}
adjustmentWidth={true}
data={this.props.userUdbAndDs}
titles={[
getLanguage(this.props.language).Analyst_Labels.DATA_SOURCE,
getLanguage(this.props.language).Analyst_Labels.DATA_SET,
]}
onRightPress={this.listRightAction}
/>
MediaPager
多媒体浏览组件,支持视频和图片翻页阅览。
props: {
data: Array,
isModal: boolean, // 是否使用Model作为容器
withBackBtn: boolean, // 左上角是否有返回按钮
backHide?: boolean, //
defaultIndex: number,
}
static defaultProps = {
isModal: false,
withBackBtn: false,
defaultIndex: 0,
data: [],
backHide: true,
}
// 数据格式
data = [
{uri: ''} // 根据uri后缀区分视频还是图片
]
<MediaPager
ref={ref => (this.mediaViewer = ref)}
data={this.state.paths}
withBackBtn
isModal
/>
// 显示隐藏MediaPager,index为默认显示第几个
setVisible = (visible = !this.state.visible, index = 0)