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.

279 lines
8.8 KiB

9 months ago
8 months ago
9 months ago
8 months ago
9 months ago
8 months ago
9 months ago
8 months ago
8 months ago
8 months ago
8 months ago
9 months ago
8 months ago
8 months ago
8 months ago
9 months ago
8 months ago
9 months ago
8 months ago
8 months ago
9 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
9 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
8 months ago
9 months ago
8 months ago
9 months ago
8 months ago
9 months ago
8 months ago
8 months ago
8 months ago
9 months ago
  1. <template>
  2. <div class="main">
  3. <div class="mainContent" v-for="article in displayedData">
  4. <div class="blogs" v-if="article.blogtitle">
  5. <a-badge-ribbon :text=article.typename color="black">
  6. <a-card hoverable>
  7. <h2>{{ article.blogtitle }}</h2>
  8. <div class="tag-group">
  9. <a-tag color="#E6E6FA">
  10. <template #icon>
  11. <component :is=iconComponents.RiLiLined />
  12. </template>
  13. {{ article.create_at }}
  14. </a-tag>
  15. <a-tag color="#6495ED">
  16. <template #icon>
  17. <component :is=iconComponents.YanJingLined />
  18. </template>
  19. {{ 111 }}
  20. </a-tag>
  21. <a-tag color="#B0C4DE">
  22. <template #icon>
  23. <component :is=iconComponents.XieZiLined />
  24. </template>
  25. 字数{{ article.wordcount }}
  26. </a-tag>
  27. <a-tag color="#20B2AA">
  28. <template #icon>
  29. <component :is=iconComponents.YueDuLined />
  30. </template>
  31. 阅读时长{{ article.blogcontent?.length }}
  32. </a-tag>
  33. </div>
  34. <div class="blog-content">
  35. <div>
  36. <a-image :preview="false" :width="200" :src=article.imglink />
  37. </div>
  38. <div class="text-container">
  39. {{ article.blogcontent }}
  40. </div>
  41. </div>
  42. <div class="read-button">
  43. <a-button type="primary" shape="round" @click="readMoreBlog(article.id)">阅读全文</a-button>
  44. </div>
  45. <hr class="custom-line">
  46. <div>
  47. <a-tag :color=randomColor() v-for="label in JSON.parse(article.labelnames)">{{ label
  48. }}</a-tag>
  49. </div>
  50. </a-card>
  51. </a-badge-ribbon>
  52. </div>
  53. <div class="diarys" v-else>
  54. <a-badge-ribbon :text=article.typename color="black">
  55. <a-card hoverable>
  56. <h2>{{ article.diarytitle }}</h2>
  57. <div class="tag-group">
  58. <a-tag color="#E6E6FA">
  59. <template #icon>
  60. <component :is=iconComponents.RiLiLined />
  61. </template>
  62. {{ article.create_at }}
  63. </a-tag>
  64. <a-tag color="#6495ED">
  65. <template #icon>
  66. <component :is=iconComponents.YanJingLined />
  67. </template>
  68. {{ 1111 }}
  69. </a-tag>
  70. <a-tag color="#B0C4DE">
  71. <template #icon>
  72. <component :is=iconComponents.XieZiLined />
  73. </template>
  74. 字数{{ article.wordcount }}
  75. </a-tag>
  76. <a-tag color="#20B2AA">
  77. <template #icon>
  78. <component :is=iconComponents.YueDuLined />
  79. </template>
  80. 阅读时长{{ 111 }}
  81. </a-tag>
  82. </div>
  83. <div class="blog-content">
  84. <div>
  85. <a-image :preview="false" :width="1000" :height="500" :src=article.imglink />
  86. </div>
  87. </div>
  88. <div class="read-button">
  89. <a-button type="primary" shape="round" @click="readMoreDiary(article.id)">阅读全文</a-button>
  90. </div>
  91. </a-card>
  92. </a-badge-ribbon>
  93. </div>
  94. </div>
  95. <div class="loadbutton" v-if="showLoadMoreButton">
  96. <a-button @click="loadMore" class="ripple-button" :loading="loading" type="primary">
  97. {{ loading ? '加载中...' : '加载更多' }}
  98. </a-button>
  99. </div>
  100. <div class="is-null" v-if="homepageStore.isEmpty">
  101. <a-card hoverable>
  102. <a-empty description="没有数据" />
  103. </a-card>
  104. </div>
  105. </div>
  106. </template>
  107. <script setup lang='ts'>
  108. import { onMounted, ref, watch } from 'vue';
  109. import type { homePageInterface } from '@/api';
  110. import iconComponents from "@/assets/index"
  111. import { get } from '@/tools/request';
  112. import router from '@/router';
  113. import { homePageStore } from '@/stores';
  114. const homepageStore = homePageStore();
  115. const randomColor = () => {
  116. const labelColor = ref(["processing", "success", "error", "warning", "magenta", "red", "volcano", "orange", "gold", "lime", "green", "cyan", "blue", "geekblue", "purple"])
  117. return labelColor.value[Math.floor(Math.random() * labelColor.value.length)];
  118. }
  119. const readMoreBlog = (id: any) => {
  120. router.push(`/blog/${id}`)
  121. }
  122. const readMoreDiary = (id: any) => {
  123. router.push(`/diary/${id}`)
  124. }
  125. // const homepagelist = ref<homePageInterface[]>([])
  126. const displayedData = ref<any[]>([]); // 存储当前显示的部分数据
  127. const itemsPerPage = 10; // 每次加载的条目数
  128. let currentIndex = 0; // 当前显示数据的索引位置
  129. const showNextBatch = () => {
  130. const end = currentIndex + itemsPerPage;
  131. displayedData.value = homepageStore.homepagelist.slice(0, end);
  132. currentIndex = end;
  133. // 控制加载更多按钮的显示与隐藏
  134. showLoadMoreButton.value = currentIndex < homepageStore.homepagelist.length;
  135. };
  136. // 加载更多按钮的显示与隐藏
  137. const showLoadMoreButton = ref<boolean>(true);
  138. // 点击加载更多按钮时触发加载下一批数据
  139. const loading = ref(false)
  140. const loadMore = () => {
  141. loading.value = true
  142. setTimeout(() => {
  143. loading.value = false
  144. showNextBatch();
  145. }, 1500)
  146. };
  147. // const homePageList = async () => {
  148. // await get(
  149. // "/statistics/homepage"
  150. // ).then(response => {
  151. // homepagelist.value = response.data.data
  152. // showNextBatch();
  153. // })
  154. // }
  155. onMounted(() => {
  156. // homePageList()
  157. homepageStore.fetchHomePageList();
  158. })
  159. watch(() => homepageStore.homepagelist, () => {
  160. // 当 homepagelist 更新时,重新显示第一页数据
  161. currentIndex = 0;
  162. showNextBatch();
  163. },);
  164. </script>
  165. <style scoped>
  166. .main {
  167. width: 45%;
  168. margin: 0 24px;
  169. }
  170. .main h2 {
  171. text-align: center;
  172. }
  173. .main .tag-group {
  174. display: flex;
  175. justify-content: center;
  176. }
  177. .main .tag-group>* {
  178. color: black;
  179. margin: 0 12px;
  180. }
  181. .main .blog-content {
  182. display: flex;
  183. margin: 48px;
  184. }
  185. .main .blog-content>:first-child {
  186. padding: 4px;
  187. border: 2px solid #ccc;
  188. display: inline-block;
  189. border-radius: 10px;
  190. box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1);
  191. }
  192. .main .blog-content>:nth-child(2) {
  193. overflow: hidden;
  194. text-overflow: ellipsis;
  195. white-space: pre-wrap;
  196. /* 防止文本换行 */
  197. }
  198. .main .read-button {
  199. display: flex;
  200. justify-content: center;
  201. }
  202. .main .read-button button {
  203. color: #fff;
  204. border: none;
  205. cursor: pointer;
  206. background-color: #007bff;
  207. /* 初始背景颜色 */
  208. animation: colorChange 3s infinite alternate;
  209. /* 添加颜色变化的动画 */
  210. }
  211. .mainContent .blogs,
  212. .mainContent .diarys {
  213. margin: 0 0 24px 0;
  214. }
  215. .custom-line {
  216. border: 0;
  217. height: 1px;
  218. background: #d9d6d6;
  219. margin: 48px 0 24px 0;
  220. }
  221. @keyframes colorChange {
  222. 0% {
  223. background-color: #007bff;
  224. /* 初始颜色 */
  225. }
  226. 50% {
  227. background-color: #ff7e5f;
  228. /* 中间颜色 */
  229. }
  230. 100% {
  231. background-color: #feb47b;
  232. /* 结束颜色 */
  233. }
  234. }
  235. .main .text-container {
  236. text-overflow: ellipsis;
  237. display: -webkit-box;
  238. -webkit-box-orient: vertical;
  239. -webkit-line-clamp: 6;
  240. word-wrap: break-word;
  241. overflow-wrap: break-word;
  242. line-height: 2;
  243. margin-left: 24px;
  244. }
  245. .loadbutton {
  246. display: flex;
  247. justify-content: right;
  248. margin-bottom: 24px;
  249. }
  250. </style>