127 lines
4.0 KiB
TypeScript
127 lines
4.0 KiB
TypeScript
import { ScrollView, View } from '@tarojs/components'
|
|
import React, { memo, ReactNode, useEffect, useRef, useState } from 'react'
|
|
import styles from './index.module.scss'
|
|
import classnames from 'classnames'
|
|
import Taro, { useReady } from '@tarojs/taro'
|
|
import InfiniteScroll, { StatusParam } from '../infiniteScroll'
|
|
import LoadingCard from '../loadingCard'
|
|
import ProductClass from '@/pages/index/components/productClass'
|
|
|
|
type Params = {
|
|
list?: any[]
|
|
defaultValue?: number | string
|
|
children?: ReactNode
|
|
height?: string
|
|
heightItem?: number
|
|
sideBarOnClick?: (val: any) => void
|
|
refresherTriggered?: true | false
|
|
selfOnRefresherRefresh?: () => void
|
|
selfOnScrolltolower?: () => void
|
|
hasMore?: true | false
|
|
statusMore?: StatusParam
|
|
}
|
|
|
|
export default memo(
|
|
({
|
|
list = [],
|
|
defaultValue = 0,
|
|
height = '100vh',
|
|
sideBarOnClick,
|
|
children,
|
|
heightItem = 100,
|
|
refresherTriggered = false,
|
|
selfOnRefresherRefresh,
|
|
selfOnScrolltolower,
|
|
hasMore = true,
|
|
statusMore = 0,
|
|
}: Params) => {
|
|
let num_half = useRef(0)
|
|
|
|
const [selected, setSelected] = useState(defaultValue)
|
|
const [tabId, setTabId] = useState('')
|
|
|
|
useEffect(() => {
|
|
setSelected(defaultValue)
|
|
}, [defaultValue])
|
|
|
|
const init = () => {
|
|
const index = list?.findIndex((item) => {
|
|
return item.id == defaultValue
|
|
})
|
|
if (index !== -1) {
|
|
computeSelectTab(index)
|
|
}
|
|
}
|
|
|
|
const clickEvent = ({ item, index }: { item; index: number }) => {
|
|
setSelected(item.id)
|
|
sideBarOnClick?.(item)
|
|
computeSelectTab(index)
|
|
}
|
|
|
|
const computeSelectTab = (index) => {
|
|
if (index + 1 > num_half.current) {
|
|
let num = index + 1 - num_half.current
|
|
setTabId(list[num].id.toString())
|
|
} else {
|
|
setTabId(list[0].id.toString())
|
|
}
|
|
}
|
|
|
|
useReady(() => {
|
|
Taro.nextTick(() => {
|
|
let query = Taro.createSelectorQuery()
|
|
query
|
|
.select('.side_bar_select')
|
|
.boundingClientRect((rect) => {
|
|
console.log('rect::', rect)
|
|
let clientHeight = rect.height
|
|
let clientWidth = rect.width
|
|
let ratio = 750 / clientWidth
|
|
let height = clientHeight * ratio
|
|
num_half.current = Math.ceil(height / 2 / heightItem)
|
|
init()
|
|
})
|
|
.exec()
|
|
})
|
|
})
|
|
|
|
const [openClass, setOpenClass] = useState(false)
|
|
|
|
return (
|
|
<>
|
|
<View className={classnames(styles.sideBar_main, 'side_bar_select')}>
|
|
<ScrollView scrollWithAnimation={true} style={{ height }} className={styles.sideBar_select} scrollY scrollIntoView={`tab_${tabId}`}>
|
|
{list?.map((item, index) => {
|
|
return (
|
|
<View
|
|
className={classnames(styles.sideBar_select_title, { [styles.sideBar_select_title_select]: selected == item.id })}
|
|
onClick={() => clickEvent({ item, index })}
|
|
id={`tab_${item.id}`}
|
|
key={item.id}
|
|
style={{ height: heightItem + 'rpx' }}>
|
|
<View className={styles.title_con}>{item.name}</View>
|
|
</View>
|
|
)
|
|
})}
|
|
</ScrollView>
|
|
<View className={styles.sideBar_con}>
|
|
<View className={styles.product_class} style={{ height: openClass ? '100%' : '' }}>
|
|
<ProductClass open={openClass} onOpenClick={(val) => setOpenClass(val)} />
|
|
</View>
|
|
<InfiniteScroll
|
|
statusMore={statusMore}
|
|
hasMore={hasMore}
|
|
selfonScrollToLower={() => selfOnScrolltolower?.()}
|
|
refresherTriggered={refresherTriggered}
|
|
refresherEnabled={true}
|
|
selfOnRefresherRefresh={() => selfOnRefresherRefresh?.()}>
|
|
{children}
|
|
</InfiniteScroll>
|
|
</View>
|
|
</View>
|
|
</>
|
|
)
|
|
},
|
|
)
|