UNPKG

mh-rn-component

Version:

78 lines (77 loc) 2.14 kB
import React, { useEffect, useState, useMemo } from 'react' import { View, Animated, TouchableWithoutFeedback, Easing, StyleSheet } from 'react-native'; type Props = { checked?: boolean onChange: (value: boolean) => void, activeColor?: string inactiveColor?: string size?: number disabled?: boolean type?: string } const Switch = ( { size = 30, checked = false, activeColor = "#0f59a4", inactiveColor = "#dcdee0", ...rest }: Props) => { const move = new Animated.Value(0) const click = () => { rest.onChange(!checked) } const moveInterpolate = move.interpolate({ inputRange: [0, size], outputRange: [inactiveColor, activeColor] }) useEffect(() => { if (checked) { Animated.timing(move, { toValue: size, duration: 300, useNativeDriver: false, easing: Easing.elastic(0.5), }).start(() => { !checked ? move.setValue(0) : move.setValue(size) }) } else { move.setValue(size) Animated.timing(move, { toValue: 0, duration: 300, useNativeDriver: false, easing: Easing.elastic(0.5), }).start(() => { !checked ? move.setValue(0) : move.setValue(size) }) } }, [checked]) return ( <TouchableWithoutFeedback disabled={rest?.disabled} onPress={click}> <Animated.View style={[ styles.switch, { width: size * 2, height: size, borderRadius: size / 2, backgroundColor: moveInterpolate, borderColor: moveInterpolate, }]}> <Animated.View style={{ transform: [{ translateX: move }] }}> <View style={[styles.switch_node, { width: size - 1, height: size - 1, borderRadius: size / 2 }]}></View> </Animated.View> </Animated.View> </TouchableWithoutFeedback> ) } const styles = StyleSheet.create({ switch: { justifyContent: "center", borderWidth: 1, }, switch_node: { backgroundColor: "#fff", } }) // todo 是否需要调整react.memo带来的性能影响,主要用来处理重新渲染 export default React.memo(Switch)