/**
* @flow
*/
/* eslint react/no-did-mount-set-state: 0 */
import React, { Component } from 'react'
import {
Text,
View,
Animated,
Easing,
StyleSheet,
TouchableOpacity,
} from 'react-native'
const styles = StyleSheet.create({
kbContainer: {
// 必须要有一个背景或者一个border,否则本身高度将不起作用
backgroundColor: 'transparent',
overflow: 'hidden',
},
kb_text_c: {
fontSize: 18,
color: '#181818',
},
})
type Props={
scrollHeight: number,
data: Array,
textStyle: Object,
scrollStyle: Object,
kbContainer: Object,
onChange: ()=>void,
enableAnimation: boolean,
duration:number,
delay:number,
onPress: ()=>void,
}
export default class ScrollVertical extends Component {
static defaultProps = {
enableAnimation: true,
}
constructor(props) {
super(props)
const translateValue = new Animated.ValueXY({ x: 0, y: 0 })
// translateValue.addListener(({ x, y }) => {
// })
this.state = {
translateValue,
// 滚屏高度
scrollHeight: this.props.scrollHeight || 32,
// 滚屏内容
kb_content: [],
// Animated.View 滚动到的 y轴坐标
kb_tempValue: 0,
// 最大偏移量
kb_contentOffsetY: 0,
// 每一次滚动切换之前延迟的时间
delay: this.props.delay || 500,
// 每一次滚动切换的持续时间
duration: this.props.duration || 500,
enableAnimation: true,
}
this.createKbItem = this.createKbItem.bind(this)
}
state: {
translateValue: any,
scrollHeight: number,
kb_content: Array,
kb_tempValue: number,
kb_contentOffsetY: number,
delay: number,
duration: number,
enableAnimation: boolean
}
componentDidMount() {
const content = this.props.data || []
if (content.length !== 0) {
const h = (content.length + 1) * this.state.scrollHeight
this.setState({
kb_content: content.concat(content[0]),
kb_contentOffsetY: h,
})
// 开始动画
// this._startAnimation()
this.startAnimation()
}
}
componentWillReceiveProps(nextProps) {
this.setState({
enableAnimation: nextProps.enableAnimation,
}, () => {
this.startAnimation()
}
)
}
componentWillUnmount() {
if (this.animation) {
clearTimeout(this.animation)
}
if (this.state.translateValue) {
this.state.translateValue.removeAllListeners()
}
}
overStep(name: string, num: number = 13) {
if (name.length > num) {
return `${name.substring(0, num)}...`
}
return name
}
createKbItem(kbItem, index) {
return (
this.props.onPress(kbItem.content)}
>
{this.overStep(kbItem.title)}
)
}
startAnimation = () => {
if (this.state.enableAnimation) {
if (!this.animation) {
this.animation = setTimeout(() => {
this.animation = null
this.startAnimationSeamless()
}, this.state.delay)
}
}
}
startAnimationSeamless = () => {
this.state.kb_tempValue -= this.state.scrollHeight
if (this.props.onChange) {
const index = Math.abs(this.state.kb_tempValue) / (this.state.scrollHeight)
this.props.onChange(index < this.state.kb_content.length - 1 ? index : 0)
}
Animated.sequence([
// Animated.delay(this.state.delay),
Animated.timing(
this.state.translateValue,
{
isInteraction: false,
toValue: { x: 0, y: this.state.kb_tempValue },
duration: this.state.duration, // 动画持续的时间(单位是毫秒),默认为500
easing: Easing.linear,
}
),
])
.start(() => {
// 无缝切换
if (this.state.kb_tempValue - this.state.scrollHeight === -this.state.kb_contentOffsetY) {
// 快速拉回到初始状态
this.state.translateValue.setValue({ x: 0, y: 0 })
this.state.kb_tempValue = 0
}
this.startAnimation()
})
}
props: Props
render() {
return (
{
this.state.kb_content.length !== 0 ?
{this.state.kb_content.map(this.createKbItem)}
: null
}
)
}
}
引入
import ScrollVertical from './ScrollVertical'
const dataArray = [
{
title: '保险全场五折',
content: '保险全场五折,你买不了吃亏买不了上当嗷嗷嗷',
},
{
title: '打到骨折',
content: '骨折甩卖,全场骨折甩卖',
},
]
let arrayContent = [{ title: '', content: '' }]
if (dataArray && dataArray.length > 0) {
arrayContent = []
for (const item of dataArray) {
arrayContent.push({ title: item.title, content: item.content })
}
}
{
this.index = index
})}
onPress={(value: string) => {
this.setModalVisible(value)
}}
enableAnimation
data={arrayContent}
delay={2500}
duration={1000}
scrollHeight={34}
scrollStyle={{ alignItems: 'flex-start' }}
textStyle={{ fontSize: 14, color: '#000' }}
/>