| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260 |
- import React, { useState, useEffect, useRef, useMemo } from 'react'
- import styles from './index.module.scss'
- import Select from 'antd/es/select'
- import Pagination from 'antd/es/pagination'
- import { isMobileFu } from '@/utils/history'
- import store from '@/store'
- import { Swiper, SwiperSlide } from 'swiper/react'
- import 'media-chrome';
- import 'swiper/css'
- import 'swiper/css/effect-coverflow'
- import 'swiper/css/pagination'
- import 'swiper/css/navigation'
- import { EffectCoverflow, Pagination as SwiperPagination, Navigation } from 'swiper/modules'
- function Appreciate({
- style,
- setHidenComplete
- }: {
- style?: React.CSSProperties
- setHidenComplete: (hidenComplete: boolean) => void
- }) {
- const [currentIndex, setCurrentIndex] = useState<number | undefined>(undefined)
- const [isShowInfo, setIsShowInfo] = useState<boolean>(true)
- const [oreData1, setOreData1] = useState(oreData)
- const [searchText, setSearchText] = useState('')
- const [textureFilter, setTextureFilter] = useState('all')
- const [typeFilter, setTypeFilter] = useState('all')
- // 添加分页状态
- const [currentPage, setCurrentPage] = useState(1)
- const pageSize = 12
- const swiperRef = useRef<any>(null);
- const [paginatedData, setPaginatedData] = useState(oreData.slice(0, pageSize))
- const filteredData = useMemo(() => {
- return oreData
- .filter(item => textureFilter === 'all' || item.texture === textureFilter)
- .filter(item => typeFilter === 'all' || item.type === typeFilter)
- .filter(item => item.title.includes(searchText))
- }, [searchText, textureFilter, typeFilter])
- useEffect(() => {
- setOreData1(filteredData)
- // 添加边界检查:如果当前页超出范围,自动跳转到第一页
- if (currentPage > Math.ceil(filteredData.length / pageSize) && filteredData.length > 0) {
- setCurrentPage(1);
- return;
- }
- // 计算当前页数据
- const startIndex = (currentPage - 1) * pageSize
- const endIndex = startIndex + pageSize
- setPaginatedData(filteredData.slice(startIndex, endIndex))
- }, [filteredData, currentPage, pageSize])
- // 缓存文物类别选项
- const typeOptions = useMemo(() => [
- { value: 'all', label: '全部' },
- ...Array.from(new Set(oreData.map(item => item.type))).map(type => ({
- value: type,
- label: type
- }))
- ], []);
- // 缓存质地选项(同理优化)
- const textureOptions = useMemo(() => [
- { value: 'all', label: '全部' },
- ...Array.from(new Set(oreData.map(item => item.texture))).map(texture => ({
- value: texture,
- label: texture
- }))
- ], []);
- return (
- <div className={styles.Appreciate} style={style}>
- <div className='top_A'>
- {isMobileFu() && <div className='txt_A'>文物赏析</div>}
- <div className='search'>
- <input
- type='text'
- value={searchText}
- onChange={e => setSearchText(e.target.value)}
- placeholder='请输入要查找的文字信息'
- />
- <img src={require('@/assets/img/search.png')} alt='' />
- </div>
- <div className='type'>
- <div className='label'>文物类别:</div>
- <Select
- defaultValue={typeFilter}
- options={[
- ...typeOptions
- ]}
- onChange={value => setTypeFilter(value)}
- />
- </div>
- <div className='texture'>
- <div className='label'>质地:</div>
- <Select
- defaultValue={textureFilter}
- options={[
- ...textureOptions
- ]}
- onChange={value => setTextureFilter(value)}
- />
- </div>
- <div className='total'>文物总数:{oreData.length}件</div>
- </div>
- <div className='content'>
- <div className='scroll'>
- {paginatedData.map((item) => (
- <div
- className={`item`}
- key={oreData.indexOf(item)}
- onClick={() => { setCurrentIndex(oreData.indexOf(item)); console.log(oreData.indexOf(item)) }}
- >
- <div className='img'>
- <img
- src={item.img}
- alt=''
- loading='lazy'
- />
- </div>
- <div className='txt'>{item.title}</div>
- </div>
- ))}
- </div>
- </div>
- <div className='page'>
- <Pagination
- defaultCurrent={1}
- total={oreData1.length || 0} // 显示过滤后的总条数
- pageSize={pageSize}
- onChange={(page) => setCurrentPage(page)} // 页码变化时更新currentPage
- />
- </div>
- {currentIndex !== undefined && (oreData[currentIndex].type === '三维' ? (
- <div className='detail'>
- <iframe
- title='文物展示'
- src={oreData[currentIndex]?.modelSrc}
- allow='fullscreen'
- />
- <div className={`info ${isShowInfo ? 'showInfo' : 'hideInfo'}`}>
- <div
- className='arrow'
- onClick={() => {
- isMobileFu() ? setIsShowInfo(true) : setIsShowInfo(false)
- }}
- >
- <img
- src={require(`@/assets/img/${isMobileFu() ? 'up' : 'left'}.png`)}
- alt=''
- />
- </div>
- <div className='content'>
- <div className='title'>{oreData[currentIndex]?.title}</div>
- {/* <div className="time">年代:{oreData[currentIndex]?.year}</div> */}
- <div className='texture'>质地:{oreData[currentIndex]?.texture}</div>
- <div className='size'>尺寸:{oreData[currentIndex]?.size}</div>
- </div>
- <div
- className='arrow arrowR'
- onClick={() => {
- isMobileFu() ? setIsShowInfo(false) : setIsShowInfo(true)
- }}
- >
- <img
- src={require(`@/assets/img/${isMobileFu() ? 'down' : 'right'}.png`)}
- alt=''
- />
- </div>
- </div>
- <div className='close' onClick={() => setCurrentIndex(undefined)}></div>
- {/* <div className='bigger' onClick={handleScrollLeft}></div>
- <div className='smaller' onClick={handleScrollRight}></div> */}
- </div>
- ) : (
- <div className='detail2'>
- <div className='close' onClick={() => setCurrentIndex(undefined)}></div>
- <Swiper
- ref={swiperRef}
- loop={false}
- loopPreventsSliding={false}
- effect={'slide'}
- grabCursor={true}
- centeredSlides={true}
- slidesPerView={'1'}
- coverflowEffect={{
- rotate: 0,
- stretch: 0,
- depth: 0,
- modifier: 1,
- }}
- pagination={{ el: '.swiper-pagination', clickable: true }}
- navigation={{
- prevEl: '.swiper-button-prev.swiper-button-arr-custom',
- nextEl: '.swiper-button-next.swiper-button-arr-custom',
- }}
- modules={[EffectCoverflow, SwiperPagination, Navigation]}
- className='swiper_container'
- onTransitionEnd={(swiper: unknown) => {
- const swiperInternal = swiper as { loopFix: () => void }
- swiperInternal.loopFix()
- }}
- >
- {currentIndex !== undefined && oreData[currentIndex].imgList?.map((item: string, index: number) => (
- <SwiperSlide key={index}>
- <div
- className='itemCard'
- key={index}
- >
- <div className='itemImage'>
- <img
- onClick={() =>
- store.dispatch({
- type: 'layout/lookBigImg',
- payload: {
- url: item,
- show: true
- }
- })
- }
- src={item}
- alt=''
- />
- </div>
- </div>
- </SwiperSlide>
- ))}
- </Swiper>
- {/* 添加左右箭头元素 */}
- <div className="swiper-button-prev swiper-button-arr-custom">
- <img src={require('@/assets/img/left.png')} alt="上一张" />
- </div>
- <div className="swiper-button-next swiper-button-arr-custom">
- <img src={require('@/assets/img/right.png')} alt="下一张" />
- </div>
- <div className="detail2Info">
- <div className="title">{oreData[currentIndex]?.title}</div>
- <div className="text">
- <div className="texture">质地:{oreData[currentIndex]?.texture}</div>
- <div className="size">尺寸:{oreData[currentIndex]?.size}</div>
- </div>
- </div>
- </div>
- ))
- }
- </div >
- )
- }
- const MemoAppreciate = React.memo(Appreciate)
- export default MemoAppreciate
|