吉光研途前端代码仓库
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.

360 lines
8.6 KiB

4 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
3 months ago
4 months ago
3 months ago
3 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
4 months ago
3 months ago
4 months ago
3 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
3 months ago
4 months ago
4 months ago
  1. <template>
  2. <view class="page__view">
  3. <view class="bg">
  4. <image class="img" src="@/static/image/bg-index.png" mode="widthFix"></image>
  5. <image class="bg-logo" src="@/static/image/bg-icon.png" mode="widthFix"></image>
  6. </view>
  7. <view class="main">
  8. <view class="flex section header">
  9. <view>
  10. <view class="title">{{ configList.page_index_title }}</view>
  11. <view class="desc">{{ configList.page_index_desc }}</view>
  12. </view>
  13. <view class="flex icon">
  14. <image class="img" :src="configList.config_logo" mode="widthFix"></image>
  15. </view>
  16. </view>
  17. <!-- 搜索栏 -->
  18. <view class="section search">
  19. <uv-search v-model="keyword" :showAction="false" placeholder="输入关键词搜索" placeholderColor="#B2B2B2" bgColor="#FFFFFF" @custom="search" @search="search">
  20. <template #prefix>
  21. <view class="flex search-icon">
  22. <image class="img" src="@/static/image/icon-search.png" mode="widthFix"></image>
  23. </view>
  24. </template>
  25. </uv-search>
  26. </view>
  27. <!-- 轮播图 -->
  28. <view class="section swiper">
  29. <uv-swiper :list="bannerList" keyName="image" indicator indicatorMode="dot" indicatorActiveColor="#FFFFFF" indicatorInactiveColor="#6851A7" height="240rpx"></uv-swiper>
  30. </view>
  31. <view class="section card" v-for="group in list" :key="group.id">
  32. <view class="card-header">
  33. <view class="card-header-title">{{ group.title }}</view>
  34. <image class="card-header-icon" src="@/static/image/icon-triangle-down.png" mode="widthFix"></image>
  35. </view>
  36. <view class="card-content">
  37. <view class="card-item card-row" v-for="item in group.children" :key="item.id">
  38. <view class="flex info">
  39. <image class="info-icon" :src="item.image" mode="widthFix"></image>
  40. <view class="info-label">{{ item.title }}</view>
  41. </view>
  42. <button class="flex btn" @click="jumpToCategory(group.id, item.id, item.title, 'queryThesisList')">
  43. <view>查看</view>
  44. <image class="btn-icon" src="@/static/image/icon-arrow-right.png" mode="widthFix"></image>
  45. </button>
  46. </view>
  47. </view>
  48. </view>
  49. <view class="section card" v-for="group in list2" :key="group.id">
  50. <view class="card-header">
  51. <view class="card-header-title">{{ group.title }}</view>
  52. <image class="card-header-icon" src="@/static/image/icon-triangle-down.png" mode="widthFix"></image>
  53. </view>
  54. <view class="card-content">
  55. <view class="card-box">
  56. <view class="card-item info" v-for="item in group.children" :key="item.id" @click="jumpToCategory(group.id, item.id, item.title, 'queryThesisTwoList')">
  57. <image class="info-icon" :src="item.image" mode="widthFix"></image>
  58. <view class="info-label">{{ item.title }}</view>
  59. </view>
  60. </view>
  61. </view>
  62. </view>
  63. <tabber select="home" />
  64. </view>
  65. </view>
  66. </template>
  67. <script>
  68. import tabber from '@/components/base/tabbar.vue'
  69. export default {
  70. components: {
  71. tabber,
  72. },
  73. data() {
  74. return {
  75. keyword: '',
  76. bannerList: [],
  77. list: [],
  78. list2: [],
  79. }
  80. },
  81. onLoad() {
  82. this.fetchBanner()
  83. this.getData()
  84. },
  85. methods: {
  86. // 获取轮播图
  87. async fetchBanner() {
  88. try {
  89. this.bannerList = (await this.$fetch('queryBannerList', { type: '0' }))?.records // type:0-首页 1-案例 2-服务 3-其他
  90. } catch (err) {
  91. }
  92. },
  93. async fetchCategory(api) {
  94. try {
  95. let parents = (await this.$fetch(api, { pageNo: 1, pageSize: 1000 }))?.records?.filter(item => item.hasChild == '1')
  96. let results = await Promise.allSettled(parents.map(parent => { return this.$fetch(api, { pid: parent.id, pageNo: 1, pageSize: 1000 }) }))
  97. results.forEach((result, index) => {
  98. parents[index].children = result?.value?.records || []
  99. })
  100. return parents
  101. } catch (err) {
  102. return []
  103. }
  104. },
  105. async getData() {
  106. this.list = await this.fetchCategory('queryCategoryThesisList')
  107. this.list2 = await this.fetchCategory('queryCategoryThesisTwoList')
  108. },
  109. search() {
  110. uni.navigateTo({
  111. url: '/pages_order/thesis/search?search=' + this.keyword
  112. })
  113. this.keyword = ''
  114. },
  115. jumpToCategory(categoryOne, categoryTwo, title, api) {
  116. uni.navigateTo({
  117. url: `/pages_order/thesis/search?categoryOne=${categoryOne}&categoryTwo=${categoryTwo}&title=${title}&api=${api}`
  118. })
  119. },
  120. },
  121. }
  122. </script>
  123. <style scoped lang="scss">
  124. .page__view {
  125. /deep/ .tabbar-box {
  126. height: 0;
  127. padding: 0;
  128. }
  129. }
  130. .header {
  131. padding-top: calc(var(--status-bar-height) + 40rpx);
  132. justify-content: space-between;
  133. .title {
  134. font-size: 44rpx;
  135. font-weight: 600;
  136. color: #6851A7;
  137. }
  138. .desc {
  139. font-size: 18rpx;
  140. font-weight: 500;
  141. color: #808080;
  142. }
  143. .icon {
  144. // margin-top: 16rpx;
  145. width: 62rpx;
  146. height: 62rpx;
  147. border: 2rpx solid #A3A2C5;
  148. border-radius: 50%;
  149. overflow: hidden;
  150. .img {
  151. width: 50rpx;
  152. height: auto;
  153. }
  154. }
  155. }
  156. .bg {
  157. width: 100vw;
  158. height: auto;
  159. .img {
  160. width: 100%;
  161. height: auto;
  162. }
  163. &-logo {
  164. position: absolute;
  165. top: 0;
  166. right: 0;
  167. width: 342rpx;
  168. height: auto;
  169. opacity: 0.3;
  170. }
  171. }
  172. .main {
  173. position: absolute;
  174. top: 0;
  175. left: 0;
  176. width: 100vw;
  177. padding-bottom: 182rpx;
  178. box-sizing: border-box;
  179. }
  180. .section {
  181. margin: 0 38rpx 24rpx 38rpx;
  182. }
  183. .search {
  184. width: calc(100% - 38rpx * 2);
  185. height: 48rpx;
  186. background-color: #FFFFFF;
  187. border-radius: 37rpx;
  188. box-sizing: border-box;
  189. display: flex;
  190. align-items: center;
  191. overflow: hidden;
  192. box-shadow: 2rpx 2rpx 9rpx 0 rgba($color: #C5C5C5, $alpha: 0.75);
  193. /deep/ .uv-search__content {
  194. padding: 0;
  195. border: none;
  196. }
  197. /deep/ .uv-search__content__input {
  198. margin-left: 18rpx;
  199. }
  200. &-icon {
  201. padding: 18rpx 10rpx 18rpx 18rpx;
  202. background: rgba($color: #E8DBF3, $alpha: 0.8);
  203. .img {
  204. width: 30rpx;
  205. height: auto;
  206. }
  207. }
  208. }
  209. .swiper {
  210. border-radius: 10rpx;
  211. overflow: hidden;
  212. /deep/ .uv-swiper-indicator__wrapper__dot {
  213. width: 25rpx;
  214. height: 5rpx;
  215. border-radius: 4rpx;
  216. margin: 0 4rpx;
  217. }
  218. /deep/ .uv-swiper-indicator__wrapper__dot--active {
  219. width: 25rpx;
  220. }
  221. }
  222. .card {
  223. width: calc(100% - 38rpx * 2);
  224. box-sizing: border-box;
  225. padding-bottom: 45rpx;
  226. background: linear-gradient(to right, rgba($color: #C8C3FD, $alpha: 0.14), rgba($color: #E2DDFF, $alpha: 0.14));
  227. border-radius: 10rpx;
  228. box-shadow: 4rpx 4rpx 6rpx 0rpx rgba(0,0,0,0.15);
  229. &-header {
  230. display: flex;
  231. align-items: center;
  232. column-gap: 23rpx;
  233. width: 100%;
  234. padding: 25rpx 30rpx 27rpx 30rpx;
  235. box-sizing: border-box;
  236. &-title {
  237. font-size: 34rpx;
  238. font-weight: 700;
  239. color: #4D4D4D;
  240. }
  241. &-icon {
  242. width: 32rpx;
  243. height: auto;
  244. }
  245. }
  246. &-content {
  247. padding: 0 32rpx;
  248. box-sizing: border-box;
  249. }
  250. &-item {
  251. display: flex;
  252. align-items: center;
  253. justify-content: flex-start;
  254. column-gap: 50rpx;
  255. padding: 14rpx 28rpx;
  256. box-sizing: border-box;
  257. background: linear-gradient(to right, rgba($color: #E2DDFF, $alpha: 0.26), rgba($color: #C8C3FD, $alpha: 0.26));
  258. // background: rgba($color: #E2DDFF, $alpha: 0.26);
  259. border-radius: 10rpx;
  260. box-shadow: 4rpx 4rpx 6rpx 0rpx rgba($color: #626266, $alpha: 0.15);
  261. }
  262. .info {
  263. &-icon {
  264. width: 54rpx;
  265. height: auto;
  266. }
  267. &-label {
  268. font-size: 26rpx;
  269. font-weight: 400;
  270. color: #000000;
  271. }
  272. }
  273. &-row {
  274. justify-content: space-between;
  275. padding: 14rpx 30rpx 14rpx 42rpx;
  276. & + & {
  277. margin-top: 28rpx;
  278. }
  279. .info {
  280. column-gap: 35rpx;
  281. }
  282. .btn {
  283. column-gap: 12rpx;
  284. padding: 8rpx 24rpx 8rpx 26rpx;
  285. font-size: 20rpx;
  286. font-weight: 400;
  287. color: #6851A7;
  288. background: #FFFFFF;
  289. border-radius: 20rpx;
  290. &-icon {
  291. width: 22rpx;
  292. height: auto;
  293. }
  294. }
  295. }
  296. &-box {
  297. display: grid;
  298. grid-template-columns: repeat(2, 1fr);
  299. column-gap: 34rpx;
  300. row-gap: 26rpx;
  301. .info {
  302. column-gap: 50rpx;
  303. }
  304. }
  305. }
  306. </style>