mh-rn-component
Version:
94 lines (92 loc) • 3.12 kB
Flow
import React, { useRef, useEffect, useState } from 'react'
import { View, Text, FlatList } from "react-native"
import type { NativeSyntheticEvent, NativeScrollEvent } from 'react-native';
import { CustomFieldNameType } from "./types"
import { randomBaseId } from "../helpers"
type Props = {
data: any,
columnHeight: number
defaultIndex?: number
columnIndex: number
visibleItemCount: number,
onChange: (value: number | number, index: number, columnIndex: number) => void
customFieldName: CustomFieldNameType,
cascadeLevel?: number
}
const Columns = ({ data, columnHeight, defaultIndex = 0, visibleItemCount, columnIndex, onChange, customFieldName, ...rest }: Props) => {
const customFieldNameValue = customFieldName.value || "value"
const columnRef = useRef<any>(null)
const [curIndex, setCurIndex] = useState<number>(defaultIndex)
const renderColumnItems = (item: any, index: number) => {
const type = typeof (item)
return (
<View style={{ height: columnHeight, justifyContent: "center" }}>
<Text style={{ color: index === curIndex ? "#333" : "#ccc", textAlign: "center" }}>
{type === 'number' || type === 'string' ? item : item[customFieldNameValue]}
</Text>
</View>
)
}
const renderColumns = ({ item, index }: { item: any, index: number }) => {
return (<View style={{ flex: 1 }}>
{renderColumnItems(item, index)}
</View>
)
}
// 占位
const vacancy = () => {
const multiple = (visibleItemCount - 1) / 2
return (
<View style={{ height: columnHeight * multiple }}></View>
)
}
const move = (index: number) => {
columnRef.current?.scrollToIndex({ viewPosition: 0, index: Number(index) })
}
useEffect(() => {
rest.cascadeLevel && setCurIndex(0)
}, [data])
useEffect(() => {
move(curIndex)
//!传数组对象和传数组的区别
onChange(data[curIndex][customFieldNameValue] || data[curIndex], curIndex, columnIndex)
}, [curIndex])
const onScrollEnd = ({
nativeEvent,
}: NativeSyntheticEvent<NativeScrollEvent>) => {
let _index = Number((Number(nativeEvent.contentOffset.y) / columnHeight).toFixed(0))
if (data.length < _index) {
_index = data.length - 1
} else if (_index < 0) {
_index = 0
}
if (data.length > _index && _index >= 0) {
// 节流 只有变化的时候才会调用
if (Math.abs(_index) !== curIndex) {
setCurIndex(Math.abs(_index))
}
}
}
// 自定义key值
const _baseId = randomBaseId()
const customKey = (item: any, index: number): string => {
return `${_baseId}${index}`
}
return (
<FlatList
showsHorizontalScrollIndicator={false}
showsVerticalScrollIndicator={false}
ref={columnRef}
data={data}
renderItem={renderColumns}
ListHeaderComponent={vacancy}
ListFooterComponent={vacancy}
keyExtractor={customKey}
getItemLayout={(data, index) => (
{ length: columnHeight, offset: columnHeight * index, index }
)}
onScrollEndDrag={onScrollEnd}
></FlatList>
)
}
export default Columns