四零语境前端代码仓库
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

691 lines
16 KiB

1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
  1. <template>
  2. <view class="container">
  3. <view class="header">
  4. <view class="header-bg">
  5. <image
  6. src="/static/会员背景.png"
  7. class="header-img"
  8. mode="scaleToFill"
  9. />
  10. <text class="header-title">会员中心</text>
  11. </view>
  12. <view class="header-content">
  13. <view class="zuanshi">
  14. <image
  15. src="/static/会员钻石.png"
  16. mode="scaleToFill"
  17. class="zuanshi-img"
  18. />
  19. </view>
  20. <view v-if="!isMember" class="noVip-container">
  21. <image
  22. src="/static/VIP.png"
  23. mode="aspectFit"
  24. class="VIP-img"
  25. />
  26. <text class="intro" >共19项会员特权 | 3 项年VIP专属特权</text>
  27. <view class="border" ></view>
  28. <view class="info" >
  29. <view class="avatar-box">
  30. <image
  31. :src="userInfo.avatar"
  32. mode="aspectFill"
  33. class="avatar"
  34. />
  35. <text class="name">{{userInfo.name}}</text>
  36. </view>
  37. <uv-button :text="isLogin ? '立即开通' : '前往登陆'"
  38. @click="goRecharge"
  39. type="primary"
  40. :customStyle="{
  41. width: '160rpx',
  42. height: '60rpx',
  43. borderRadius: '198rpx',
  44. backgroundColor: '#06DADC',
  45. color: '#fff',
  46. fontSize: '28rpx',
  47. fontWeight: '500',
  48. lineHeight: '60rpx',
  49. letterSpacing: '0%',
  50. verticalAlign: 'middle',
  51. }" />
  52. </view>
  53. </view>
  54. <view v-else>
  55. <!-- 代码加在这里 -->
  56. <view class="vip-container " >
  57. <view class="avatar-box ">
  58. <image
  59. :src="userInfo.avatar"
  60. mode="aspectFill"
  61. class="avatar"
  62. />
  63. <text class="name">{{userInfo.name}}</text>
  64. <text class="time">{{memberInfo[0].endTime.split(' ')[0]}}</text>
  65. </view>
  66. <view class="border" ></view>
  67. <view class="project">{{ memberInfo[0].memberTitle }}</view>
  68. <text class="res-time">{{ '预计剩余学习' + $utils.calculateDateDifference(memberInfo[0].endTime.split(' ')[0]) + '天'}}</text>
  69. </view>
  70. </view>
  71. </view>
  72. </view>
  73. <!-- 会员权益 -->
  74. <view class="benefits-section" v-if="!isMember">
  75. <view class="benefits-title">会员权益</view>
  76. <view class="benefits-list">
  77. <!-- 碎片学习 系统掌握 -->
  78. <view class="benefit-item">
  79. <view class="benefit-content">
  80. <view class="benefit-title">碎片学习 系统掌握</view>
  81. <view class="benefit-desc">根据薄弱点智能推荐每节课3-5分钟碎片化完成系统学习</view>
  82. </view>
  83. <view class="benefit-icon">
  84. <image src="/static/会员图片1.png" mode="aspectFit"></image>
  85. </view>
  86. </view>
  87. <!-- 匹配水平 -->
  88. <view class="benefit-item">
  89. <view class="benefit-content">
  90. <view class="benefit-title">匹配水平</view>
  91. <view class="benefit-desc">依据水平精准推课不做无用功快速提升</view>
  92. </view>
  93. <view class="benefit-icon">
  94. <image src="/static/会员图片2.png" mode="aspectFit"></image>
  95. </view>
  96. </view>
  97. <!-- 科学闭环测 讲练结合 -->
  98. <view class="benefit-item">
  99. <view class="benefit-content">
  100. <view class="benefit-title">科学闭环测 讲练结合</view>
  101. <view class="benefit-desc">精心设计科学的学习流程 测试-讲解-练习-检验知识掌握更牢固</view>
  102. </view>
  103. <view class="benefit-icon">
  104. <image src="/static/会员图片3.png" mode="aspectFit"></image>
  105. </view>
  106. </view>
  107. </view>
  108. </view>
  109. <!-- 以下内容为成为会员才能看到的 -->
  110. <!-- 学习计划 -->
  111. <view class="study-plan-section" v-else>
  112. <view class="section-title">学习计划</view>
  113. <view class="plan-books">
  114. <view
  115. v-for="(book, index) in studyPlanBooks"
  116. :key="index"
  117. class="plan-book-item"
  118. @click="goBookDetail(book.book.id)"
  119. :class="{ 'active-book': index === 1 }"
  120. >
  121. <view class="plan-book-cover">
  122. <image :src="book.book.booksImg" mode="aspectFill"></image>
  123. <!-- 学习中标识 -->
  124. <view v-if="index === 1" class="studying-badge">
  125. <view class="studying-icon"/>
  126. <text>学习中</text>
  127. </view>
  128. </view>
  129. <view class="plan-book-info">
  130. <text class="plan-book-title" :class="{ 'highlight-title': index === 1 }">{{ book.book.booksName }}</text>
  131. <view class="plan-book-meta" >
  132. <text class="plan-book-grade" :class="{ 'highlight-title': index === 1 }">{{ book.book.categoryName }}/</text>
  133. <image v-if="index !== 1" src="/static/播放图标.png" class="plan-book-duration-icon" />
  134. <image v-else src="/static/播放图标高亮.png" class="plan-book-duration-icon" />
  135. <text class="plan-book-duration" :class="{ 'highlight-title': index === 1 }">{{ book.book.duration }}</text>
  136. </view>
  137. </view>
  138. </view>
  139. </view>
  140. </view>
  141. <!-- 学习推荐 -->
  142. <view class="study-recommend-section" v-if="isMember">
  143. <view class="section-header" @click="goRecommend">
  144. <text class="section-title">学习推荐</text>
  145. <view class="section-more">
  146. <text>更多</text>
  147. <uv-icon name="arrow-right" size="14" color="#8B8B8B"></uv-icon>
  148. </view>
  149. </view>
  150. <view class="recommend-grid">
  151. <view
  152. v-for="(book, index) in recommendBooks"
  153. :key="index"
  154. @click="goBookDetail(book.id)"
  155. class="recommend-grid-item"
  156. >
  157. <view class="recommend-grid-cover">
  158. <image :src="book.booksImg" mode="aspectFill"></image>
  159. </view>
  160. <view class="recommend-grid-info">
  161. <text class="recommend-grid-title">{{ book.booksName }}</text>
  162. <view class="recommend-grid-meta">
  163. <text class="recommend-grid-grade">{{ book.categoryName }}/</text>
  164. <image src="/static/播放图标.png" class="recommend-grid-duration-icon" />
  165. <text class="recommend-grid-duration">{{ book.duration }}</text>
  166. </view>
  167. </view>
  168. </view>
  169. </view>
  170. </view>
  171. </view>
  172. </template>
  173. <script>
  174. export default{
  175. data() {
  176. return {
  177. isLogin: uni.getStorageSync('token') ? true : false,
  178. memberInfo: [],
  179. userInfo: {
  180. name: '战斗世界',
  181. avatar: '/static/默认头像.png'
  182. },
  183. // 学习计划书籍数据
  184. studyPlanBooks: [
  185. ],
  186. // 学习推荐书籍数据
  187. recommendBooks: [
  188. ]
  189. }
  190. },
  191. computed: {
  192. isMember() {
  193. return this.memberInfo.length > 0
  194. }
  195. },
  196. methods: {
  197. // 跳转学习推荐
  198. goRecommend() {
  199. uni.navigateTo({
  200. url: '/subPages/home/search'
  201. })
  202. },
  203. // 跳转书籍详情
  204. goBookDetail(bookId) {
  205. uni.navigateTo({
  206. url: `/subPages/home/directory?id=${bookId}`
  207. })
  208. },
  209. goRecharge() {
  210. if (!this.isLogin) {
  211. uni.navigateTo({
  212. url: '/subPages/login/login'
  213. })
  214. return
  215. }
  216. uni.navigateTo({
  217. url: '/subPages/member/recharge'
  218. })
  219. },
  220. // 获取会员信息
  221. async getUserMemberInfo() {
  222. const memberRes = await this.$api.member.getUserMemberInfo()
  223. if (memberRes.code === 200) {
  224. this.memberInfo = [...memberRes.result]
  225. }
  226. },
  227. // 获取用户信息
  228. async getUserInfo() {
  229. const userRes = await this.$api.login.getUserInfo()
  230. if (userRes.code === 200) {
  231. this.userInfo = userRes.result
  232. }
  233. },
  234. // 获取3个学习计划书籍
  235. async getStudyPlanBook() {
  236. const bookRes = await this.$api.book.stand({
  237. pageNo: 1,
  238. pageSize: 3
  239. })
  240. if (bookRes.code === 200) {
  241. const oneBook = bookRes.result.records[1]
  242. const twoBook = bookRes.result.records[0]
  243. const threeBook = bookRes.result.records[2]
  244. this.studyPlanBooks = [oneBook, twoBook, threeBook]
  245. }
  246. },
  247. async getRecommendBook() {
  248. const bookRes = await this.$api.book.list({
  249. pageNo: 1,
  250. pageSize: 6,
  251. member: 1
  252. }, false)
  253. if (bookRes.code === 200) {
  254. this.recommendBooks = bookRes.result.records
  255. }
  256. },
  257. },
  258. async onShow() {
  259. // 如果登录了就查询会员情况 如果没有登录就不查询
  260. if (uni.getStorageSync('token')) {
  261. this.isLogin = true
  262. Promise.all([this.getUserMemberInfo(), this.getUserInfo(), this.getStudyPlanBook(), this.getRecommendBook()])
  263. }else {
  264. this.isLogin = false
  265. this.userInfo = {
  266. name: '登录后查看会员情况',
  267. avatar: '/static/默认头像.png'
  268. }
  269. }
  270. }
  271. }
  272. </script>
  273. <style lang="scss" scoped>
  274. .container {
  275. min-height: 100%;
  276. padding-bottom: 50rpx;
  277. }
  278. .header{
  279. width: 100%;
  280. .header-bg{
  281. position: relative;
  282. width: 100%;
  283. height: 400rpx;
  284. // background: red;
  285. .header-img{
  286. width: 100%;
  287. height: 400rpx;
  288. }
  289. .header-title{
  290. font-size: 32rpx;
  291. color: black;
  292. position: absolute;
  293. top: 100rpx;
  294. font-weight: 500;
  295. left: 50%;
  296. transform: translateX(-50%);
  297. }
  298. }
  299. .header-content{
  300. margin: 0 18rpx;
  301. margin-top: -150rpx;
  302. // height: 256rpx;
  303. border-radius: 32rpx;
  304. border-width: 2rpx;
  305. padding: 40rpx;
  306. background: linear-gradient(180deg, #DEFFFF 0%, #FBFEFF 22.65%, #F0FBFF 100%);
  307. border: 2rpx solid #06DADC12;
  308. display: flex;
  309. flex-direction: column;
  310. gap: 28rpx;
  311. position: relative;
  312. .vip-container{
  313. padding: 20rpx 0;
  314. display: flex;
  315. flex-direction: column;
  316. gap: 18rpx;
  317. .project{
  318. font-size: 36rpx;
  319. color: #191919;
  320. line-height: 1.4;
  321. font-weight: 500;
  322. }
  323. .res-time{
  324. color: $primary-color;
  325. font-size: 24rpx;
  326. line-height: 36rpx;
  327. }
  328. }
  329. .noVip-container{
  330. display: flex;
  331. flex-direction: column;
  332. // align-items: center;
  333. // justify-content: center;
  334. gap: 28rpx;
  335. }
  336. .zuanshi{
  337. position: absolute;
  338. width: 190rpx;
  339. height: 190rpx;
  340. top: -80rpx;
  341. right: 0;
  342. .zuanshi-img{
  343. width: 190rpx;
  344. height: 190rpx;
  345. }
  346. }
  347. .VIP-img{
  348. width: 80rpx;
  349. height: 50rpx;
  350. }
  351. .border{
  352. width: 100%;
  353. // height: 2rpx;
  354. border: 2rpx solid;
  355. border-image-source: linear-gradient(90deg, rgba(228, 255, 255, 0) 0%, #C3EFEF 50.48%, rgba(228, 255, 255, 0) 100%);
  356. border-image-slice: 1;
  357. }
  358. .intro{
  359. font-size: 28rpx;
  360. line-height: 36rpx;
  361. letter-spacing: 0%;
  362. vertical-align: middle;
  363. color: #09B1B3;
  364. }
  365. .info{
  366. display: flex;
  367. justify-content: space-between;
  368. align-items: center;
  369. }
  370. .avatar-box{
  371. display: flex;
  372. align-items: center;
  373. gap: 16rpx;
  374. .name{
  375. font-weight: 600;
  376. font-size: 36rpx;
  377. line-height: 44rpx;
  378. letter-spacing: 0%;
  379. vertical-align: middle;
  380. color: #252545;
  381. }
  382. .avatar{
  383. width: 60rpx;
  384. height: 60rpx;
  385. border-radius: 50%;
  386. }
  387. .time{
  388. font-size: 30rpx;
  389. color: #8B8B8B;
  390. line-height: 36rpx;
  391. }
  392. }
  393. }
  394. }
  395. /* 立即开通会员按钮样式 */
  396. .member-button-section {
  397. margin: 40rpx 50rpx;
  398. }
  399. /* 会员权益样式 */
  400. .benefits-section {
  401. margin-top: 40rpx;
  402. padding: 0 30rpx;
  403. }
  404. .benefits-title {
  405. font-size: 36rpx;
  406. font-weight: bold;
  407. color: #191919;
  408. margin-bottom: 32rpx;
  409. }
  410. .benefits-list {
  411. display: flex;
  412. flex-direction: column;
  413. gap: 32rpx;
  414. }
  415. .benefit-item {
  416. background: #F8F8F8;
  417. border: 1px solid #FFFFFF;
  418. border-radius: 48rpx;
  419. padding: 27rpx 40rpx;
  420. display: flex;
  421. align-items: center;
  422. justify-content: space-between;
  423. }
  424. .benefit-content {
  425. flex: 1;
  426. margin-right: 40rpx;
  427. }
  428. .benefit-title {
  429. font-size: 32rpx;
  430. font-weight: 600;
  431. color: #333;
  432. margin-bottom: 16rpx;
  433. }
  434. .benefit-desc {
  435. font-size: 24rpx;
  436. color: #09B1B3;
  437. line-height: 36rpx;
  438. }
  439. .benefit-icon {
  440. width: 152rpx;
  441. height: 152rpx;
  442. // flex-shrink: 0;
  443. }
  444. .benefit-icon image {
  445. width: 100%;
  446. height: 100%;
  447. }
  448. /* 学习计划样式 */
  449. .study-plan-section {
  450. margin-top: 40rpx;
  451. padding: 0 30rpx;
  452. }
  453. .section-title {
  454. font-size: 36rpx;
  455. font-weight: 500;
  456. color: #191919;
  457. margin-bottom: 32rpx;
  458. }
  459. .plan-books {
  460. display: flex;
  461. justify-content: center;
  462. align-items: flex-end;
  463. gap: 78rpx;
  464. padding: 20rpx 0;
  465. }
  466. .plan-book-item {
  467. display: flex;
  468. flex-direction: column;
  469. align-items: center;
  470. transition: all 0.3s ease;
  471. &.active-book {
  472. transform: scale(1.15);
  473. .plan-book-cover {
  474. // box-shadow: 0 8rpx 24rpx rgba(6, 218, 220, 0.3);
  475. }
  476. }
  477. }
  478. .plan-book-cover {
  479. width: 172rpx;
  480. height: 230rpx;
  481. border-radius: 16rpx;
  482. overflow: hidden;
  483. margin-bottom: 16rpx;
  484. position: relative;
  485. box-shadow: 0px 4px 4px 0px #C0BCBA75;
  486. image {
  487. width: 100%;
  488. height: 100%;
  489. }
  490. .studying-badge {
  491. position: absolute;
  492. bottom: 0rpx;
  493. right: 0rpx;
  494. background: #00000099;
  495. color: #fff;
  496. padding: 6rpx 10rpx;
  497. border-radius: 20rpx;
  498. font-size: 18rpx;
  499. display: flex;
  500. align-items: center;
  501. justify-content: center;
  502. gap: 6rpx;
  503. .studying-icon{
  504. width: 10rpx;
  505. height: 10rpx;
  506. background: $primary-color;
  507. border-radius: 50%;
  508. }
  509. }
  510. }
  511. .plan-book-info {
  512. text-align: center;
  513. .plan-book-title {
  514. font-size: 28rpx;
  515. font-weight: 700;
  516. color: #333;
  517. margin-bottom: 8rpx;
  518. display: block;
  519. &.highlight-title {
  520. color: $primary-color;
  521. }
  522. }
  523. .plan-book-meta {
  524. display: flex;
  525. align-items: center;
  526. justify-content: center;
  527. gap: 8rpx;
  528. .plan-book-duration-icon {
  529. width: 20rpx;
  530. height: 20rpx;
  531. }
  532. .plan-book-grade {
  533. font-size: 24rpx;
  534. color: #999;
  535. &.highlight-title {
  536. color: $primary-color;
  537. }
  538. }
  539. .plan-book-duration {
  540. font-size: 24rpx;
  541. color: #999;
  542. &.highlight-title {
  543. color: $primary-color;
  544. }
  545. }
  546. }
  547. }
  548. /* 学习推荐样式 */
  549. .study-recommend-section {
  550. margin-top: 40rpx;
  551. padding: 0 30rpx;
  552. }
  553. .section-header {
  554. display: flex;
  555. align-items: center;
  556. justify-content: space-between;
  557. margin-bottom: 24rpx;
  558. .section-more {
  559. display: flex;
  560. align-items: center;
  561. gap: 4rpx;
  562. text {
  563. font-size: 24rpx;
  564. color: #8B8B8B;
  565. }
  566. }
  567. }
  568. .recommend-grid {
  569. display: flex;
  570. flex-wrap: wrap;
  571. gap: 32rpx;
  572. .recommend-grid-item {
  573. width: 208rpx;
  574. display: flex;
  575. flex-direction: column;
  576. .recommend-grid-cover {
  577. box-shadow: 0px 4px 4px 0px #C0BCBA75;
  578. width: 100%;
  579. height: 278rpx;
  580. border-radius: 16rpx;
  581. overflow: hidden;
  582. margin-bottom: 16rpx;
  583. image {
  584. width: 100%;
  585. height: 100%;
  586. }
  587. }
  588. .recommend-grid-info {
  589. padding: 6rpx;
  590. .recommend-grid-title {
  591. font-size: 28rpx;
  592. font-weight: 700;
  593. color: #333;
  594. margin-bottom: 14rpx;
  595. overflow: hidden;
  596. text-overflow: ellipsis;
  597. white-space: nowrap;
  598. }
  599. .recommend-grid-meta {
  600. display: flex;
  601. align-items: center;
  602. .recommend-grid-duration-icon {
  603. width: 24rpx;
  604. height: 24rpx;
  605. margin-right: 12rpx;
  606. }
  607. .recommend-grid-grade {
  608. font-size: 24rpx;
  609. color: #999;
  610. margin-right: 8rpx;
  611. }
  612. .recommend-grid-duration {
  613. font-size: 24rpx;
  614. color: #999;
  615. }
  616. }
  617. }
  618. }
  619. }
  620. </style>