游戏详情
react-native-modal-layer
What's TOC?
项目地址:https://github.com/horou-dsk/react-native-modal-layer
npm:https://www.npmjs.com/package/react-native-modal-layer
在app开发中通常都会遇到弹窗开发的需求,但在RN中无论是自带的 Modal 以及第三方库都会存在或多或少的问题和不方便的地方。
比如官方的Modal不能覆盖状态栏以及麻烦的配置和可复用性以及弹出效果和样式的定制。
所以笔者为了解决这些痛点开发了一个自认为比较好用和方便的rn弹窗组件, 纯JS实现。
先看示例:
快速使用
首先在App 根组件上面使用 ModalLayers 包裹你的应用, 如下:
注意:ModalLayers标签只能在写在应用入口App.js文件里面,包裹您的整个路由页面。之后就可使用ModalLayerFactory类里面的方法创建弹窗,在任意页面弹出了。
const App = () => {
return (
<Fragment>
<StatusBar barStyle="dark-content" translucent={true} backgroundColor={'transparent'} />
<ModalLayers> {/*包裹您的整个应用, 该标签只能写在您应用的入口App.js里面,写一次即可。*/}
<Page1 />
</ModalLayers>
</Fragment>
);
};
接下来你就可以在任意地方使用 ModalLayerFactory.create(options)
创建弹窗了,不过笔者建议最好是在 componentDidMount
函数中创建, 创建弹窗示例代码如下:
class Layer extends Component {
render() {
return (
<View style={{width: 200, height: 200, alignItems: 'center', justifyContent: 'center', borderRadius: 5, backgroundColor: '#fff'}}>
<Text style={{fontSize: 30, color: '#000'}}>弹窗内容</Text>
</View>
);
}
}
class Page1 extends Component {
layer: ModalLayerController
componentDidMount(): void {
// 在此创建弹窗,使用一个变量接收, Layer为你需要创建的弹窗组件
this.layer = ModalLayerFactory.create(Layer)
/**
* 也可使用这种方式创建
* 两者的区别在于options配置的位置不同以及参数传递方式不同
*
this.layer = ModalLayerFactory.create({
component: <Layer />
})
*/
}
componentWillUnmount(): void {
// 建议在此删除弹窗对象,因为弹窗都是在应用全局创建的,在析构函数删除弹窗可减少不必要的内存使用
ModalLayerFactory.delete(this.layer) // or ModalLayerFactory.delete([this.layer])
}
render() {
return (
<View style={{justifyContent: 'center', alignItems: 'center', flex: 1}}>
{/*在此调用layer的show方法即可显示弹窗*/}
<Button onPress={() => this.layer.show()} title={'Open Layer'} />
</View>
);
}
}
就这样,效果图1的弹窗就创建好了,该组件基本的使用就是这些了。
完整代码:
import React, {Component, Fragment} from 'react';
import {
Button,
StatusBar, View, Text, Easing
} from 'react-native';
import {
ModalLayerController,
ModalLayerFactory,
ModalLayers
} from "react-native-modal-layer";
class Layer extends Component {
render() {
return (
<View style={{width: 200, height: 200, alignItems: 'center', justifyContent: 'center', borderRadius: 5, backgroundColor: '#fff'}}>
<Text style={{fontSize: 30, color: '#000'}}>弹窗内容</Text>
</View>
);
}
}
class Page1 extends Component {
layer: ModalLayerController
componentDidMount(): void {
this.layer = ModalLayerFactory.create(Layer)
}
componentWillUnmount(): void {
ModalLayerFactory.delete(this.layer) // or ModalLayerFactory.delete([this.layer])
}
render() {
return (
<View style={{justifyContent: 'center', alignItems: 'center', flex: 1}}>
<Button onPress={() => this.layer.show()} title={'Open Layer'} />
</View>
);
}
}
const App = () => {
return (
<Fragment>
<StatusBar barStyle="dark-content" translucent={true} backgroundColor={'transparent'} />
<ModalLayers>
<Page1 />
</ModalLayers>
</Fragment>
);
};
export default App;
更多配置
CreateModalOptions
Prop | Type | Default | Description |
---|---|---|---|
component | Component or Function | null | 要创建成为的弹窗组件 |
boxStyle | ViewStyle | {} | 弹窗容器的样式 |
act | Function | ModalLayerAnimated.SCALE | 弹窗弹出时动画的方向 |
showEasing | Easing | Easing.elastic(1) | 弹窗弹出时的缓动效果 |
hideEasing | Easing | null | 弹窗隐藏时的缓动效果 |
key | String | Random | 弹窗的key值,可通过ModalLayerFactory.getLayer(key) 来获取弹窗对象 |
showDuration | Number | 400 | 弹窗的显示动画时间,单位:ms |
hideDuration | Number | 200 | 弹窗的隐藏动画时间,单位:ms |
backHandle | Function | null | ModalLayerFactory.back() 会触发该方法 |
shade | Boolean | true | 弹窗背景遮罩 |
shadePress | Function | null | 弹窗背景遮罩的点击事件 |
zIndex | Number | 1 | 弹窗的层级 |
示例
this.layer = ModalLayerFactory.create({
component: <Layer />,
boxStyle: {position: 'absolute', bottom: 0},
act: ModalLayerAnimated.TRANSLATE_Y,
hideEasing: Easing.bezier(0.215, 0.61, 0.355, 1),
showEasing: Easing.bezier(0.215, 0.61, 0.355, 1),
key: 'MyLayer'
})
如果使用的是 ModalLayerFactory.create(Layer)
这种方式创建弹窗的话,配置是写在Layer类中的静态属性modalLayerOptions
中
如:
class Layer extends Component {
static modalLayerOptions: CreateModalOptions = {
boxStyle: {position: 'absolute', bottom: 0},
act: ModalLayerAnimated.TRANSLATE_Y,
hideEasing: Easing.bezier(0.215, 0.61, 0.355, 1),
showEasing: Easing.bezier(0.215, 0.61, 0.355, 1),
key: 'MyLayer'
}
render() {
return (
<View style={{width: screenWidth, height: screenHeight / 2, alignItems: 'center', justifyContent: 'center', borderRadius: 5, backgroundColor: '#fff'}}>
<Text style={{fontSize: 30, color: '#000'}}>弹窗内容</Text>
</View>
);
}
}
效果图
传参
在多数情况下,可能需要向弹窗组件传递不同的参数显示不同的内容
该组件有两种传参方式
通过
ModalLayerFactory.create({component: <Layer />})
方式创建的弹窗传参方式如下// 弹窗的component更改为函数,函数返回要生成的弹窗组件,函数参数为要传入的参数 this.layer = ModalLayerFactory.create({ component: (title) => <Layer title={title} />, ...options }) //调用显示弹窗的函数里面传入参数 this.layer.show('弹窗标题-测试')
如果是通过
ModalLayerFactory.create(Layer)
的方式创建的弹窗,传参方式有所改变//该方式只需更改 show 方法调用,传入一个对象,对象的key值为要传入参数的key值 this.layer.show({title: '弹窗标题-测试'})
Layer组件的接收方式与 React 的 props 是一样的
class Layer extends Component<{title: string}> {
render() {
//接收参数
const {title} = this.props
return (
<View style={{width: screenWidth, height: screenHeight / 2, alignItems: 'center', justifyContent: 'center', borderRadius: 5, backgroundColor: '#fff'}}>
<Text style={{fontSize: 30, color: '#000'}}>{title}</Text>
</View>
);
}
}
效果图
推荐:使用 hooks
更新: 现推荐使用react hooks 方式创建使用弹窗,更加方便
使用方式:
file: useLayer.ts
import React, { useEffect, useState } from 'react'
import { ModalLayerController, ModalLayerFactory } from 'react-native-modal-layer'
export function useLayer(Layer: React.ElementType) {
const [layer, setLayer] = useState<ModalLayerController>()
useEffect(() => {
setLayer(ModalLayerFactory.create(Layer))
return () => {
if (layer) ModalLayerFactory.delete(layer)
}
}, [])
return layer
}
之后只需在需要使用弹层的页面这样写,就可以使用了:
function Page() {
const layer = useLayer(Layer) // Layer 为你定义的弹层页面
return (
<View style={{justifyContent: 'center', alignItems: 'center', flex: 1}}>
<Button onPress={() => layer.show()} title={'Open Layer'} />
</View>
)
}
我日你妈
草拟
fuck
holy shit
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了, 在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
在此弹窗组件的大部分用法就是这些了,还有一些其他的接口和功能都可通过源码和d.ts文件查看,这里就不一一介绍了,
最后欢迎大家积极提出 issue 帮助改进该组件,谢谢!
用户评论 3 条