diff --git a/src/components/search/index.module.scss b/src/components/search/index.module.scss index 40e27da..07587b6 100644 --- a/src/components/search/index.module.scss +++ b/src/components/search/index.module.scss @@ -15,7 +15,7 @@ width: 100%; input { font-size: 27px; - background: #eee; + background: #f6f7f9; width: 100%; height: 72px; border-radius: 50px; diff --git a/src/components/sideBar/index.module.scss b/src/components/sideBar/index.module.scss index 7329301..cfd3a13 100644 --- a/src/components/sideBar/index.module.scss +++ b/src/components/sideBar/index.module.scss @@ -1,45 +1,54 @@ -.sideBar_main{ - display: flex; +.sideBar_main { + display: flex; + height: 100%; + .sideBar_select { + width: 160px; height: 100%; - .sideBar_select{ - width: 150px; - height: 100%; - background-color: #eaeaea; - border-radius: 0 10px 10px 0; - ::-webkit-scrollbar { - display:none; - width:0; - height:0; - color:transparent; - } - .sideBar_select_title{ - height: 100px; - width: 100%; - font-size: $font_size; - color: #727272; - display: flex; - flex-direction: column; - align-items: center; - justify-content: center; - font-weight: 400; - .title_con{ - width: 74px; - @include common_ellipsis($params:4); - } - - } - .sideBar_select_title_select{ - background-color: #007AFF; - color: #fff; - border-radius: 0px 14px 14px 0px; - } + background-color: #eaeaea; + border-radius: 0 10px 10px 0; + ::-webkit-scrollbar { + display: none; + width: 0; + height: 0; + color: transparent; } - .sideBar_con{ - flex: 1; - .sideBar_con_scroll{ - width: 100%; - height: 100%; - } + .sideBar_select_title { + height: 100px; + width: 100%; + font-size: $font_size; + color: rgba(0, 0, 0, 0.6); + display: flex; + flex-direction: column; + align-items: center; + justify-content: center; + font-weight: 400; + .title_con { + padding: 0 20px; + text-align: center; + // width: 74px; + @include common_ellipsis($params: 4); + } } - -} \ No newline at end of file + .sideBar_select_title_select { + background-color: #007aff; + color: #fff; + border-radius: 0px 14px 14px 0px; + } + } + .sideBar_con { + flex: 1; + min-width: 0; + position: relative; + padding-top: 90px; + .product_class { + width: 100%; + position: absolute; + top: 0; + z-index: 999; + } + .sideBar_con_scroll { + width: 100%; + height: 100%; + } + } +} diff --git a/src/components/sideBar/index.tsx b/src/components/sideBar/index.tsx index d601151..08b150b 100644 --- a/src/components/sideBar/index.tsx +++ b/src/components/sideBar/index.tsx @@ -1,117 +1,126 @@ -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 { 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 + 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, +export default memo( + ({ + list = [], + defaultValue = 0, + height = '100vh', + sideBarOnClick, + children, + heightItem = 100, refresherTriggered = false, selfOnRefresherRefresh, selfOnScrolltolower, hasMore = true, - statusMore = 0 -}: Params) => { - + statusMore = 0, + }: Params) => { let num_half = useRef(0) const [selected, setSelected] = useState(defaultValue) const [tabId, setTabId] = useState('') useEffect(() => { - setSelected(defaultValue) + setSelected(defaultValue) }, [defaultValue]) const init = () => { - const index = list?.findIndex(item => { - return item.id == defaultValue - }) - if(index !== -1) { - computeSelectTab(index) - } + 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 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()) - - } + 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(); - }) + 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 ( - <> - - - { - list?.map((item, index) => { - return( - clickEvent({item, index})} - id={`tab_${item.id}`} - key={item.id} - style={{height:heightItem+'rpx'}} - > - - {item.name} - - - ) - }) - } - - - selfOnScrolltolower?.()} refresherTriggered={refresherTriggered} refresherEnabled={true} selfOnRefresherRefresh={() => selfOnRefresherRefresh?.()}> - {children} - + <> + + + {list?.map((item, index) => { + return ( + clickEvent({ item, index })} + id={`tab_${item.id}`} + key={item.id} + style={{ height: heightItem + 'rpx' }}> + {item.name} + ) + })} + + + + setOpenClass(val)} /> - - + selfOnScrolltolower?.()} + refresherTriggered={refresherTriggered} + refresherEnabled={true} + selfOnRefresherRefresh={() => selfOnRefresherRefresh?.()}> + {children} + + + + ) -}) \ No newline at end of file + }, +) diff --git a/src/pages/index/components/product/index.tsx b/src/pages/index/components/product/index.tsx index ced2691..1c21a1a 100644 --- a/src/pages/index/components/product/index.tsx +++ b/src/pages/index/components/product/index.tsx @@ -1,27 +1,30 @@ -import { Image, View } from "@tarojs/components" -import styles from './index.module.scss' +import { Image, View } from '@tarojs/components' +import styles from './index.module.scss' export default () => { - - return ( - - {new Array(10).fill('').map(item => { - return - - - 230色 - - - 0770#21S单面平纹(食毛) - - 160cm - 110g - - 67.6%棉24%涤纶6.4%氨纶 - 产品描述产品描述产品描述产品描述产品描述 - - - })} - - ) + return ( + + {new Array(10).fill('').map((item) => { + return ( + + + + 230色 + + + + 0770#21S单面平纹(食毛) + + + 160cm + 110g + + 67.6%棉24%涤纶6.4%氨纶 + 产品描述产品描述产品描述产品描述产品描述 + + + ) + })} + + ) } diff --git a/src/pages/index/components/productClass/index.module.scss b/src/pages/index/components/productClass/index.module.scss new file mode 100644 index 0000000..9a969eb --- /dev/null +++ b/src/pages/index/components/productClass/index.module.scss @@ -0,0 +1,114 @@ +.product_class_main_line { + width: 100%; + height: 80px; + position: relative; + display: flex; + align-items: center; + margin-bottom: 20px; + background-color: #fff; + .product_class_scroll { + padding: 0 88px 0 19px; + box-sizing: border-box; + .product_class_list { + white-space: nowrap; + display: flex; + box-sizing: border-box; + .product_class_item { + min-width: 170px; + height: 56px; + background: #f5f5f5; + border-radius: 29px; + display: flex; + align-items: center; + justify-content: center; + font-size: 24px; + color: rgba(0, 0, 0, 0.8); + box-sizing: border-box; + &:nth-last-child(n + 1) { + margin-right: 16px; + } + } + .product_class_item_selected { + border: 1px solid #3c78f4; + color: #3c78f4; + background: #ecf2ff; + } + } + } + .product_class_more { + position: absolute; + right: 0; + top: 0; + width: 88px; + height: 100%; + background-color: #fff; + box-shadow: -7px 0px 7px -5px rgba(0, 0, 0, 0.16); + line-height: 100%; + display: flex; + align-items: center; + .product_class_more_icon { + margin-left: 20px; + display: inline-block; + transform: rotate(90deg); + font-size: 30px; + color: rgba(0, 0, 0, 0.5); + } + } +} + +.product_class_main_block { + width: 100%; + height: 100%; + box-sizing: border-box; + position: relative; + .product_class_block_con { + max-height: 500px; + background-color: #fff; + z-index: 999; + position: relative; + } + .product_class_scroll { + box-sizing: border-box; + max-height: 500px; + padding: 20px 20px 0 20px; + .product_class_list { + display: flex; + flex-wrap: wrap; + box-sizing: border-box; + .product_class_item { + min-width: 167px; + height: 56px; + background: #ecf2ff; + border: 1px solid #3c78f4; + border-radius: 29px; + display: flex; + align-items: center; + justify-content: center; + font-size: 24px; + color: #3c78f4; + margin: 0 6px 20px 6px; + } + } + } + .product_class_close { + font-size: 24px; + color: rgba(0, 0, 0, 0.6); + text-align: center; + padding-bottom: 20px; + .product_class_close_icon { + display: inline-block; + transform: rotate(-90deg); + font-size: 27px; + color: rgba(0, 0, 0, 0.5); + padding: 0 10px; + } + } + .product_class_block_mask { + position: absolute; + top: 0; + height: 100%; + width: 100%; + background-color: rgba(0, 0, 0, 0.5); + z-index: 100; + } +} diff --git a/src/pages/index/components/productClass/index.tsx b/src/pages/index/components/productClass/index.tsx new file mode 100644 index 0000000..47b6dc6 --- /dev/null +++ b/src/pages/index/components/productClass/index.tsx @@ -0,0 +1,114 @@ +import { ScrollView, Text, View } from '@tarojs/components' +import styles from './index.module.scss' +import classnames from 'classnames' +import { useEffect, useMemo, useState } from 'react' + +type Param = { + open: boolean + onOpenClick?: (val: boolean) => void + onSelect?: (val: number) => void +} + +type ParamProduct = Omit & { + defaultSelectIded: number +} + +export default (option: Param) => { + const { open = false, onOpenClick, onSelect } = option + const [defaultSelectIded, setDefaultSelectIded] = useState(-1) + return ( + <> + {open ? ( + onOpenClick?.(val)}> + ) : ( + onOpenClick?.(val)}> + )} + + ) +} + +const ProductClassLine = (option: ParamProduct) => { + const { onOpenClick, defaultSelectIded = -1, onSelect } = option + const [selectInfo, setSelectInfo] = useState({ + selected: -1, //当前选中的id + tabId: '', //需要滚动到的id + }) + + const list = useMemo(() => { + const data = new Array(10).fill('').map((item, index) => { + return { id: index, name: '二级分类' + index } + }) + data.unshift({ id: -1, name: '全部' }) + return data + }, []) + + useEffect(() => { + let data: { item: any; index: number } = {} + list.filter((item, index) => { + if (item.id == defaultSelectIded) { + data = { item, index } + } + }) + clickEvent(data) + }, [defaultSelectIded]) + + const clickEvent = ({ item, index }: { item: any; index: number }) => { + const num = index > 0 ? index - 1 : 0 + setSelectInfo((e) => ({ ...e, tabId: list[num].id.toString(), selected: item.id })) + } + + return ( + + + + {list.map((item, index) => ( + clickEvent({ item, index })}> + {item.name + item.id} + + ))} + + + onOpenClick?.(true)}> + + + + ) +} + +const ProductClassBlock = (option: ParamProduct) => { + const { onOpenClick } = option + const [selectInfo, setSelectInfo] = useState(-1) + const list = useMemo(() => { + const data = new Array(10).fill('').map((item, index) => { + return { id: index, name: '二级分类' + index } + }) + data.unshift({ id: -1, name: '全部' }) + return data + }, []) + + const clickEvent = (item) => { + setSelectInfo(item.id) + } + return ( + + + + + {list.map((item, index) => ( + clickEvent(item)}> + {item.name} + + ))} + + + onOpenClick?.(false)}> + 点击收起 + + + onOpenClick?.(false)}> + + ) +} diff --git a/src/pages/index/index.module.scss b/src/pages/index/index.module.scss index b7b6b43..38e0ce0 100644 --- a/src/pages/index/index.module.scss +++ b/src/pages/index/index.module.scss @@ -1,8 +1,12 @@ .main { - background-color: $color_bg_one; + background-color: #f6f6f6; height: 100vh; display: flex; flex-direction: column; + .header { + background-color: #fff; + padding-bottom: 20px; + } .search { width: 100%; display: flex; @@ -29,5 +33,12 @@ flex: 1; height: 0; margin-top: 20px; + .product_right_con { + position: relative; + .product_class { + position: absolute; + top: 0; + } + } } } diff --git a/src/pages/index/index.tsx b/src/pages/index/index.tsx index 0f3544f..57e68c3 100644 --- a/src/pages/index/index.tsx +++ b/src/pages/index/index.tsx @@ -12,6 +12,7 @@ import Taro, { Events, useDidShow, usePullDownRefresh } from '@tarojs/taro' import { GetProductKindListApi, GetProductListApi } from '@/api/material' import useLogin from '@/use/useLogin' import { dataLoadingStatus } from '@/common/util' +import ProductClass from './components/productClass' export default () => { useLogin() @@ -84,13 +85,14 @@ export default () => { return ( setShowShopCart(!showShopCart)}> - - goLink('/pages/searchList/search')}> - + + + goLink('/pages/searchList/search')}> + + + - - { const router = useRouter() useEffect(() => { if (router?.params.status != undefined && router?.params.status !== '') { - setSearchField((e) => ({ ...e, status: router?.params.status as number })) + setSearchField((e) => ({ ...e, status: router?.params.status as unknown as number })) } else { setSearchField((e) => ({ ...e, status: -1 })) } @@ -200,7 +200,7 @@ export default () => { - +