index.tsx 6.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238
  1. import React, { useCallback, useEffect, useRef, useState } from 'react'
  2. import styles from './index.module.scss'
  3. import BaseImg from '@/components/BaseImg'
  4. import { baseURL, myData } from '@/utils/http'
  5. import useLoding from '@/components/ownUse/useLoding'
  6. import CatVideo from '@/components/CatVideo'
  7. import A6PanoVideo from './A6PanoVideo'
  8. import classNames from 'classnames'
  9. import { domDelOwnFu } from '@/utils/utilsSome'
  10. import FloorBtn from '@/components/FloorBtn'
  11. import NextPage from '@/components/NextPage'
  12. import EndVideo from '@/components/EndVideo'
  13. import history from '@/utils/history'
  14. function A6xian() {
  15. // 过度动画
  16. const [cutVideoShow, setCutVideoShow] = useState(false)
  17. // 点击 跳下一个章节
  18. const [lastVideo, setLastVideo] = useState(false)
  19. // 点击继续
  20. const btnStart = useCallback(() => {
  21. setCutVideoShow(true)
  22. }, [])
  23. // 过度动画播放完毕或者点击跳过
  24. const cutEndFu = useCallback(() => {
  25. setCutVideoShow(false)
  26. }, [])
  27. // 先加载背景图 序列帧等 在加载视频
  28. const { imgNow, imgNumFu } = useLoding(3)
  29. // 点击升仙
  30. const [xianShow, setXianShow] = useState(window.location.href.includes('t=xian') ? true : false)
  31. // 滚动
  32. const [isFlag, setIsFlag] = useState(false)
  33. const xianRef = useRef<HTMLDivElement>(null)
  34. // 监听3S没有操作
  35. const [action, setAction] = useState(false)
  36. const actionRef = useRef(-1)
  37. const actionFu = useCallback(
  38. (val?: boolean) => {
  39. if (xianShow || val) {
  40. setAction(false)
  41. clearTimeout(actionRef.current)
  42. actionRef.current = window.setTimeout(() => {
  43. setAction(true)
  44. }, 3000)
  45. }
  46. },
  47. [xianShow]
  48. )
  49. const actionMoveRef = useRef(-1)
  50. useEffect(() => {
  51. if (xianShow) {
  52. clearInterval(actionMoveRef.current)
  53. if (action) {
  54. actionMoveRef.current = window.setInterval(() => {
  55. if (xianRef.current) {
  56. const nowMove = xianRef.current.scrollLeft
  57. xianRef.current.scrollLeft = nowMove + 2
  58. if (xianRef.current.scrollLeft >= 2988) xianRef.current.scrollLeft = 0
  59. }
  60. }, 50)
  61. }
  62. }
  63. }, [action, xianShow])
  64. const mousemoveFu = useCallback(
  65. (ev: any, flag?: boolean) => {
  66. if (xianRef.current) {
  67. if (flag && !isFlag) {
  68. actionFu()
  69. const nowMove = xianRef.current.scrollLeft
  70. // 滚轮
  71. let num = 50
  72. if (ev.deltaY < 0) num = -num
  73. xianRef.current.scrollLeft = nowMove + num
  74. } else if (isFlag) {
  75. actionFu()
  76. const nowMove = xianRef.current.scrollLeft
  77. // 鼠标按住移动
  78. xianRef.current.scrollLeft = nowMove - ev.movementX
  79. }
  80. }
  81. },
  82. [actionFu, isFlag]
  83. )
  84. const videoRef = useRef<HTMLVideoElement>(null)
  85. useEffect(() => {
  86. if (window.location.href.includes('t=xian')) {
  87. setTimeout(() => {
  88. if (videoRef.current) videoRef.current.play()
  89. }, 100)
  90. }
  91. }, [])
  92. // 二级的静态图
  93. const [erImg, setErImg] = useState(false)
  94. return (
  95. <div className={styles.A6xian}>
  96. {/* 初始静态图 */}
  97. <BaseImg
  98. hidden={window.location.href.includes('t=xian')}
  99. isShow={cutVideoShow}
  100. iconSrc={`${baseURL}xianJu/mulu.png`}
  101. parentFu={() => setErImg(true)}
  102. bgImg={`${baseURL}${myData.xianJu.bgImg}`}
  103. imgNow={imgNow}
  104. imgNumFu={imgNumFu}
  105. num={70}
  106. bird='xianJu'
  107. />
  108. {/* 二级静态图 */}
  109. <div
  110. className='A6erImg'
  111. style={{ opacity: erImg ? '1' : '0', pointerEvents: erImg ? 'auto' : 'none' }}
  112. >
  113. <img src={baseURL + 'xianJu/bg.jpg'} alt='' />
  114. <NextPage
  115. clickSon={() => {
  116. domDelOwnFu('.A6erImg')
  117. btnStart()
  118. }}
  119. txt='开始冥想'
  120. />
  121. {/* 右下角按钮 */}
  122. <FloorBtn />
  123. </div>
  124. {/* 过度动画页面 */}
  125. {imgNow ? (
  126. <CatVideo
  127. isShow={cutVideoShow}
  128. src={baseURL + myData.xianJu.videos[0]}
  129. parentFu={() => cutEndFu()}
  130. />
  131. ) : null}
  132. {/* 全景视频 */}
  133. {imgNow && !window.location.href.includes('t=xian') ? (
  134. <div className={classNames('pvBox', cutVideoShow ? '' : 'pvBoxShow')}>
  135. <A6PanoVideo />
  136. <div
  137. className='pvBtn'
  138. onClick={() => {
  139. domDelOwnFu('.pvBox')
  140. setXianShow(true)
  141. setTimeout(() => {
  142. if (videoRef.current) videoRef.current.play()
  143. }, 100)
  144. // 开启滚动动画
  145. actionFu(true)
  146. }}
  147. >
  148. 升仙之途
  149. </div>
  150. <FloorBtn />
  151. </div>
  152. ) : null}
  153. {/* 点击升仙之途 出来的长 滚动 页面 */}
  154. {imgNow || window.location.href.includes('t=xian') ? (
  155. <div
  156. onTouchStart={() => actionFu()}
  157. onClick={() => actionFu()}
  158. className='A6XimgBox'
  159. style={{ opacity: xianShow ? '1' : '0', pointerEvents: xianShow ? 'auto' : 'none' }}
  160. >
  161. <div
  162. className='A6XimgBoxSon'
  163. style={{ cursor: isFlag ? 'move' : 'default' }}
  164. ref={xianRef}
  165. onMouseDown={() => setIsFlag(true)}
  166. onMouseUp={() => setIsFlag(false)}
  167. onMouseLeave={() => setIsFlag(false)}
  168. onMouseMove={e => mousemoveFu(e)}
  169. onWheel={e => mousemoveFu(e, true)}
  170. >
  171. <video
  172. ref={videoRef}
  173. playsInline
  174. muted
  175. webkit-playsinline='true'
  176. x5-video-player-type='h5'
  177. loop={true}
  178. >
  179. <source type='video/mp4' src={`${baseURL}xianJu/chang.mp4`} />
  180. Your browser does not support the video tag.
  181. </video>
  182. </div>
  183. {/* 跳到下一章 */}
  184. <NextPage clickSon={() => setLastVideo(true)} txt='结束冥想' />
  185. {/* 右下角按钮 */}
  186. <FloorBtn />
  187. {/* 底部按钮 */}
  188. <div className='A6XimgBoxBtn'>
  189. <div onClick={() => history.push('/xian?t=xian')}>卜千秋墓中的升仙图</div>
  190. <div onClick={() => history.push('/yun?t=xian')}>四神云气图</div>
  191. </div>
  192. </div>
  193. ) : null}
  194. {/* 最后的视频 */}
  195. <EndVideo
  196. lastVideo={lastVideo}
  197. src={baseURL + 'xianJu/end.mp4'}
  198. path='/end'
  199. delDom='.A22Pano'
  200. />
  201. </div>
  202. )
  203. }
  204. const MemoA6xian = React.memo(A6xian)
  205. export default MemoA6xian