Adil-U / Adil

Harvard
0 stars 0 forks source link

Scrollable scrollview #1

Open Adil-U opened 2 years ago

Adil-U commented 2 years ago

https://user-images.githubusercontent.com/68853548/146137631-88f2a962-2712-40ef-94e6-2a0c36de490a.mp4

Реализация довольна простая Есть ScrollView Есть state activeIndex, setActiveIndex Внутри ScrollView в функцию onMomentumScrollEnd устанавливаем активный индекс через state onMomentumScrollEnd={ev => { setActiveIndex(Math.floor(ev.nativeEvent.contentOffset.x / 60)) }} (где 60 ширина элемента а Натив контент оффсет х расположение элемента по оси х) При это также есть функции на нажатие стрелок это scrollToEnd и scrollToIndex где index === 0 Отображение стрелок зависит от активного индекса если индекс меньше трёх то стрелка вправо и соответственно наоборот

Adil-U commented 2 years ago

import React from 'react' import { View, StyleSheet, Image, ScrollView, TouchableOpacity } from 'react-native' import PropTypes from 'prop-types' import { MaterialIcons } from '@expo/vector-icons' import { LinearGradient } from 'expo-linear-gradient'

import THEME from '../../shared/theme'

const AvatarList = ({ arr, choosed, setChoosed }) => { const ScrollRef = React.useRef() const [activeIndex, setActiveIndex] = React.useState(0)

const scrollToTop = index => { // eslint-disable-next-line no-unused-expressions ScrollRef.current?.scrollTo({ x: index, animated: true }) }

return (

{ setActiveIndex(Math.floor(ev.nativeEvent.contentOffset.x / 60)) }} > {arr.map(item => { return ( setChoosed(item)} > ) })} {activeIndex < 3 ? ( { ScrollRef.current.scrollToEnd() setActiveIndex(10) }} > ) : ( { scrollToTop(0) setActiveIndex(0) }} > )}

) }

const styles = StyleSheet.create({ container: { paddingLeft: 24 }, list: { paddingRight: 24, flexDirection: 'row' }, avatarsContainer: { marginTop: 24 }, avatarActive: { width: 64, height: 64, borderWidth: 3, borderColor: THEME.COLOR_WHITE, borderRadius: 8, backgroundColor: THEME.COLOR_MAIN, marginRight: 16 }, avatarNoActive: { width: 64, height: 64, borderWidth: 3, borderColor: THEME.COLOR_GRAY_OPACITY_4, borderRadius: 8, backgroundColor: '#484848', marginRight: 16 }, img: { width: 60, height: 60, borderRadius: 10, bottom: 3 }, arrowContainer: { position: 'absolute', left: '90%', top: '0%', zIndex: 30 }, arrowBackContainer: { position: 'absolute', top: '0%', zIndex: 30 }, gradient: { right: 20, width: 88, height: 65, borderRadius: 10 }, arrow: { alignItems: 'center', top: '19%' } })

AvatarList.propTypes = { arr: PropTypes.arrayOf(PropTypes.object).isRequired, choosed: PropTypes.shape().isRequired, setChoosed: PropTypes.func.isRequired }

export default AvatarList