BambooBookView.vue 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487
  1. <script setup>
  2. import { ref, computed, onMounted, inject } from "vue"
  3. import { useRouter } from "vue-router"
  4. import useRollFu from "../rollFu.js"
  5. import { useWindowSize } from "@vueuse/core"
  6. const router = useRouter()
  7. const curState = ref("ye")
  8. const $env = inject("$env")
  9. const { handleScroll } = useRollFu()
  10. const bigViewList = computed(() => {
  11. let resZhu = null
  12. if (curState.value == "ye") {
  13. resZhu = configZhuPu["叶"]
  14. } else if (curState.value == "zhi") {
  15. resZhu = configZhuPu["枝"]
  16. } else if (curState.value == "zhu") {
  17. resZhu = configZhuPu["杆"]
  18. }
  19. const newList = resZhu.map((item) => {
  20. return `${$env.BASE_URL}configMultiMedia/zhupuImages/${
  21. item["图片名称"] ? item["图片名称"] : item["名称"]
  22. }.png`
  23. })
  24. return newList
  25. })
  26. // 画法数据处理
  27. const paintingData = computed(() => {
  28. let resZhu = null
  29. if (curState.value == "ye") {
  30. resZhu = configZhuPu["叶"]
  31. } else if (curState.value == "zhi") {
  32. resZhu = configZhuPu["枝"]
  33. } else if (curState.value == "zhu") {
  34. resZhu = configZhuPu["杆"]
  35. }
  36. const resValue = Object.entries(
  37. resZhu.reduce((groups, item) => {
  38. const category = item["画法"]
  39. if (!groups[category]) {
  40. groups[category] = []
  41. }
  42. groups[category].push(item)
  43. return groups
  44. }, {})
  45. ).map(([key, value]) => ({
  46. category: key,
  47. items: value,
  48. }))
  49. return resValue
  50. })
  51. const rowScroller = ref(null)
  52. const windowHeightDesign = 1080 - 71 - 37 // 设计稿里视口高度。注意要减去上下边栏
  53. const { width: windowWidth, height: windowHeight } = useWindowSize()
  54. const isShowBigView = ref(false)
  55. const isShowOperationTip = ref(true)
  56. const handleWheel = (val) => {
  57. event.preventDefault()
  58. isShowOperationTip.value = false
  59. if (isShowBigView.value) {
  60. return
  61. }
  62. const scrollAmount = 50
  63. // isShowClickTip.value = false
  64. if (val == -1) {
  65. rowScroller.value.scrollLeft -= scrollAmount
  66. } else {
  67. rowScroller.value.scrollLeft += scrollAmount
  68. }
  69. }
  70. // const handleClose = () => {
  71. // setTimeout(() =>{isShowBigView.value = false}, 200)
  72. // }
  73. onMounted(() => {
  74. console.log("paintingData", paintingData.value)
  75. console.log("看看", bigViewList.value)
  76. })
  77. </script>
  78. <template>
  79. <div class="home">
  80. <BtnBack
  81. style="z-index: 2"
  82. @click="router.back()"
  83. />
  84. <div class="left-box">
  85. <div class="title-box-all">
  86. <div class="title-box">
  87. 芥子园画谱
  88. </div>
  89. <div class="zhupu-box">
  90. 竹谱
  91. </div>
  92. </div>
  93. <div class="text">
  94. 《芥子园画传》又称《芥子园画谱》是清代绘画技法图谱,它较系统地介绍了中国画的基本技法。清代文学家李渔曾在南京营造“芥子园”,并支持其婿沈心友及王氏三兄弟(王概、王著、王臬)编绘画谱,故成书出版之时便以此园命名。
  95. </div>
  96. <img
  97. class="zhupu-img"
  98. src="@/assets/images/img_zhupu.png"
  99. alt=""
  100. >
  101. </div>
  102. <div class="right-box">
  103. <!-- 滑动提示 -->
  104. <OperationTip
  105. class="operation-tip"
  106. color="green"
  107. text="向下滑动"
  108. :is-show="isShowOperationTip"
  109. />
  110. <div class="totle-painting-box">
  111. <div class="top">
  112. <img
  113. :style="{ opacity: curState == 'ye' ? 1 : 0 }"
  114. src="@/assets/images/img_ye.png"
  115. alt=""
  116. >
  117. <img
  118. :style="{ opacity: curState == 'zhi' ? 1 : 0 }"
  119. src="@/assets/images/img_zhi.png"
  120. alt=""
  121. >
  122. <img
  123. :style="{ opacity: curState == 'zhu' ? 1 : 0 }"
  124. src="@/assets/images/img_zhu.png"
  125. alt=""
  126. >
  127. </div>
  128. <div class="bottom-btns">
  129. <div
  130. class="btn"
  131. :class="{ btnAc: curState == 'zhu' }"
  132. @click="
  133. () => {
  134. (curState = 'zhu'), (rowScroller.scrollLeft = 0);
  135. }
  136. "
  137. >
  138. </div>
  139. <div
  140. class="btn"
  141. :class="{ btnAc: curState == 'zhi' }"
  142. @click="
  143. () => {
  144. (curState = 'zhi'), (rowScroller.scrollLeft = 0);
  145. }
  146. "
  147. >
  148. </div>
  149. <div
  150. class="btn"
  151. :class="{ btnAc: curState == 'ye' }"
  152. @click="
  153. () => {
  154. (curState = 'ye'), (rowScroller.scrollLeft = 0);
  155. }
  156. "
  157. >
  158. </div>
  159. </div>
  160. </div>
  161. <div
  162. ref="rowScroller"
  163. class="painting-detail-box"
  164. @wheel="($event) => handleScroll($event, (val) => handleWheel(val))"
  165. >
  166. <!-- <OperationTip
  167. v-show="isShowClickTip"
  168. class="operation-tip-click"
  169. :text="'点击查看'"
  170. color="green"
  171. type="click"
  172. @click="() => (isShowClickTip = false)"
  173. /> -->
  174. <div
  175. v-for="(category, index1) in paintingData"
  176. :key="index1"
  177. class="category-box"
  178. >
  179. <div
  180. class="category-title"
  181. :style="{ margin: index1 == 0 ? '0 10px 0 10px' : '' }"
  182. >
  183. {{ category.category }}
  184. </div>
  185. <div
  186. v-for="(item, index2) in category.items"
  187. :key="index2"
  188. class="category-item"
  189. >
  190. <!-- <el-image
  191. class="small-img"
  192. :src="`${$env.BASE_URL}configMultiMedia/zhupuImages/${
  193. item['图片名称'] ? item['图片名称'] : item['名称']
  194. }.png`"
  195. :max-scale="7"
  196. :min-scale="0.2"
  197. :preview-src-list="[`${$env.BASE_URL}configMultiMedia/zhupuImages/${
  198. item['图片名称'] ? item['图片名称'] : item['名称']
  199. }.png`]"
  200. fit="contain"
  201. z-index="100"
  202. :hide-on-click-modal="true"
  203. @close="handleClose"
  204. /> -->
  205. <img
  206. :src="`${$env.BASE_URL}configMultiMedia/zhupuImages/${
  207. item['图片名称'] ? item['图片名称'] : item['名称']
  208. }.png`"
  209. alt=""
  210. >
  211. <div>{{ item["名称"] }}</div>
  212. </div>
  213. </div>
  214. </div>
  215. </div>
  216. </div>
  217. </template>
  218. <style lang="less" scoped>
  219. .home {
  220. width: 100%;
  221. height: 100%;
  222. background: url(@/assets/images/zhupu-bg.png);
  223. background-size: 100% 100%;
  224. // background-position: top left;
  225. position: relative;
  226. > .operation-tip {
  227. position: absolute;
  228. right: calc(30px / v-bind("windowHeightDesign") * v-bind("windowHeight"));
  229. transform: translateX(-50%);
  230. top: 50%;
  231. transform: translateY(-50%);
  232. }
  233. .left-box {
  234. width: 27.3%;
  235. height: 100%;
  236. // background: rgba(255, 0, 0, 0.377);
  237. position: absolute;
  238. left: 0;
  239. top: 0;
  240. .title-box-all {
  241. position: absolute;
  242. font-family: "KingHwa_OldSong";
  243. color: #ffffff;
  244. writing-mode: vertical-lr;
  245. display: flex;
  246. // flex-direction: column;
  247. align-items: center;
  248. left: 3vw;
  249. top: 15vh;
  250. .title-box {
  251. // font-size: 2.8em;
  252. font-size: calc(
  253. 48px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  254. );
  255. line-height: calc(
  256. 56.25px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  257. );
  258. // line-height: 56px;
  259. letter-spacing: 0.3em;
  260. }
  261. .zhupu-box {
  262. // margin-top: 10%;
  263. margin-top: calc(
  264. 20px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  265. );
  266. // font-size: 1.8em;
  267. font-size: calc(
  268. 24px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  269. );
  270. line-height: calc(
  271. 29px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  272. );
  273. // line-height: 28.13px;
  274. letter-spacing: 0.2em;
  275. }
  276. }
  277. .text {
  278. width: 50%;
  279. position: absolute;
  280. top: 50%;
  281. transform: translateY(-50%);
  282. right: 12%;
  283. color: #7b916b;
  284. // opacity: 0.3;
  285. font-size: calc(
  286. 28px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  287. );
  288. line-height: calc(
  289. 38px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  290. );
  291. font-family: "KaiTi";
  292. text-transform: none;
  293. text-align: justified;
  294. text-indent: 2em;
  295. }
  296. .zhupu-img {
  297. width: 55%;
  298. position: absolute;
  299. left: 0;
  300. bottom: 0;
  301. }
  302. }
  303. .right-box {
  304. width: calc(100% - 27.3%);
  305. height: 100%;
  306. // background: rgba(255, 0, 0, 0.281);
  307. position: absolute;
  308. top: 0;
  309. right: 0;
  310. display: flex;
  311. flex-direction: column;
  312. align-items: center;
  313. justify-content: center;
  314. .operation-tip{
  315. position: absolute;
  316. right: calc(30px / v-bind('windowHeightDesign') * v-bind('windowHeight'));
  317. top: 50%;
  318. transform: translateY(-50%);
  319. }
  320. .totle-painting-box {
  321. width: 50%;
  322. height: 60%;
  323. margin-bottom: 5vh;
  324. display: flex;
  325. flex-direction: column;
  326. align-items: center;
  327. justify-content: center;
  328. .top {
  329. width: 100%;
  330. height: calc(
  331. 100% - 60px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  332. );
  333. position: relative;
  334. img {
  335. width: 100%;
  336. height: 100%;
  337. object-fit: contain;
  338. position: absolute;
  339. left: 0;
  340. top: 0;
  341. transition: opacity 1s ease-in-out;
  342. }
  343. }
  344. .bottom-btns {
  345. width: 90%;
  346. display: flex;
  347. justify-content: space-evenly;
  348. .btn {
  349. width: calc(
  350. 60px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  351. );
  352. height: calc(
  353. 60px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  354. );
  355. // font-size: 38px;
  356. font-size: calc(
  357. 38px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  358. );
  359. line-height: calc(
  360. 52px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  361. );
  362. flood-color: #474747;
  363. display: flex;
  364. justify-content: center;
  365. align-items: center;
  366. font-family: "KingHwa_OldSong";
  367. cursor: pointer;
  368. }
  369. .btnAc {
  370. background: url(@/assets/images/zhupu_active.png);
  371. background-size: 100% 100%;
  372. color: #ffffff;
  373. }
  374. }
  375. }
  376. .painting-detail-box {
  377. width: 95%;
  378. height: 25%;
  379. // background: red;
  380. overflow-x: auto;
  381. overflow-y: hidden;
  382. display: flex;
  383. position: relative;
  384. scrollbar-width: none;
  385. .operation-tip-click {
  386. position: absolute;
  387. top: 45%;
  388. left: 10%;
  389. }
  390. &::-webkit-scrollbar {
  391. display: none !important;
  392. }
  393. .category-box {
  394. // display: inline;
  395. // white-space: nowrap;
  396. display: flex;
  397. align-items: flex-start;
  398. img {
  399. width: 20vh;
  400. height: 20vh;
  401. object-fit: contain;
  402. }
  403. > div {
  404. // float: left;
  405. }
  406. .category-title {
  407. display: inline-flex;
  408. writing-mode: vertical-lr;
  409. // letter-spacing: 12px;
  410. letter-spacing: calc(
  411. 12px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  412. );
  413. color: #476446;
  414. background: url(@/assets/images/name-bg.png);
  415. background-size: 100% 100%;
  416. font-family: "KingHwa_OldSong";
  417. // font-size: 20px;
  418. font-size: calc(
  419. 20px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  420. );
  421. // line-height: 48px;
  422. padding: calc(
  423. 10px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  424. );
  425. margin: 0
  426. calc(30px * v-bind("windowHeight") / v-bind("windowHeightDesign")) 0
  427. calc(60px * v-bind("windowHeight") / v-bind("windowHeightDesign"));
  428. // height: 70%;
  429. }
  430. .category-item {
  431. display: flex;
  432. flex-direction: column;
  433. align-items: center;
  434. margin: 0
  435. calc(20px * v-bind("windowHeight") / v-bind("windowHeightDesign")) 0
  436. calc(20px * v-bind("windowHeight") / v-bind("windowHeightDesign"));
  437. .small-img {
  438. width: calc(
  439. 200px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  440. );
  441. height: calc(
  442. 150px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  443. );
  444. }
  445. > div {
  446. margin-top: calc(
  447. 10px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  448. );
  449. color: #7b916b;
  450. font-size: calc(
  451. 20px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  452. );
  453. line-height: calc(
  454. 24px * v-bind("windowHeight") / v-bind("windowHeightDesign")
  455. );
  456. font-family: "KingHwa_OldSong";
  457. }
  458. }
  459. }
  460. }
  461. }
  462. }
  463. </style>