After Width: | Height: | Size: 79 KiB |
After Width: | Height: | Size: 62 KiB |
After Width: | Height: | Size: 69 KiB |
After Width: | Height: | Size: 65 KiB |
After Width: | Height: | Size: 58 KiB |
After Width: | Height: | Size: 62 KiB |
After Width: | Height: | Size: 75 KiB |
After Width: | Height: | Size: 79 KiB |
After Width: | Height: | Size: 603 KiB |
After Width: | Height: | Size: 247 KiB |
After Width: | Height: | Size: 58 KiB |
After Width: | Height: | Size: 530 KiB |
After Width: | Height: | Size: 379 KiB |
@ -0,0 +1,182 @@
|
|||||||
|
<template>
|
||||||
|
<div class="notice-board">
|
||||||
|
<h2 class="notice-title">公告栏</h2>
|
||||||
|
<div class="notice-list">
|
||||||
|
<!-- 左箭头按钮 -->
|
||||||
|
<button class="arrow-button left-arrow" @click="prevImage">←</button>
|
||||||
|
<div class="notice-item">
|
||||||
|
<img
|
||||||
|
:src="images[currentIndex].src"
|
||||||
|
:alt="images[currentIndex].alt"
|
||||||
|
class="notice-image"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<!-- 右箭头按钮 -->
|
||||||
|
<button class="arrow-button right-arrow" @click="nextImage">→</button>
|
||||||
|
</div>
|
||||||
|
<!-- 圆形按钮 -->
|
||||||
|
<div class="indicator-container">
|
||||||
|
<button
|
||||||
|
v-for="(image, index) in images"
|
||||||
|
:key="index"
|
||||||
|
class="indicator-button"
|
||||||
|
:class="{ active: currentIndex === index }"
|
||||||
|
@click="goToImage(index)"
|
||||||
|
></button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
import { ref, onMounted, onUnmounted } from 'vue';
|
||||||
|
|
||||||
|
export default {
|
||||||
|
name: 'NoticeBoard',
|
||||||
|
setup() {
|
||||||
|
const images = ref([
|
||||||
|
{ src: require('@/assets/whu1.jpg'), alt: '公告图片1' },
|
||||||
|
{ src: require('@/assets/whu2.jpg'), alt: '公告图片2' },
|
||||||
|
{ src: require('@/assets/whu3.jpg'), alt: '公告图片3' },
|
||||||
|
{ src: require('@/assets/whu4.jpg'), alt: '公告图片4' },
|
||||||
|
{ src: require('@/assets/whu5.jpg'), alt: '公告图片5' },
|
||||||
|
]);
|
||||||
|
|
||||||
|
const currentIndex = ref(0);
|
||||||
|
|
||||||
|
// 切换到下一张图片
|
||||||
|
const nextImage = () => {
|
||||||
|
currentIndex.value = (currentIndex.value + 1) % images.value.length;
|
||||||
|
};
|
||||||
|
|
||||||
|
// 切换到上一张图片
|
||||||
|
const prevImage = () => {
|
||||||
|
currentIndex.value =
|
||||||
|
(currentIndex.value - 1 + images.value.length) % images.value.length;
|
||||||
|
};
|
||||||
|
|
||||||
|
// 跳转到指定图片
|
||||||
|
const goToImage = (index) => {
|
||||||
|
currentIndex.value = index;
|
||||||
|
};
|
||||||
|
|
||||||
|
// 定时器
|
||||||
|
let interval = null;
|
||||||
|
|
||||||
|
onMounted(() => {
|
||||||
|
// 初始化定时器
|
||||||
|
interval = setInterval(nextImage, 5000);
|
||||||
|
});
|
||||||
|
|
||||||
|
onUnmounted(() => {
|
||||||
|
// 清除定时器
|
||||||
|
clearInterval(interval);
|
||||||
|
});
|
||||||
|
|
||||||
|
return {
|
||||||
|
images,
|
||||||
|
currentIndex,
|
||||||
|
nextImage,
|
||||||
|
prevImage,
|
||||||
|
goToImage,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.notice-board {
|
||||||
|
position: relative;
|
||||||
|
background-color: #5aa76f;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: flex-start; /* 顶部对齐 */
|
||||||
|
width: 500px; /* 固定宽度 */
|
||||||
|
height: 350px; /* 固定高度 */
|
||||||
|
overflow: hidden; /* 防止图片溢出 */
|
||||||
|
padding: 10px; /* 内边距 */
|
||||||
|
box-sizing: border-box; /* 包括内边距在宽高内 */
|
||||||
|
}
|
||||||
|
|
||||||
|
.notice-title {
|
||||||
|
font-size: 24px;
|
||||||
|
color: white;
|
||||||
|
text-align: center;
|
||||||
|
margin: 0; /* 去掉默认外边距 */
|
||||||
|
padding-bottom: 10px; /* 与图片保持间距 */
|
||||||
|
}
|
||||||
|
|
||||||
|
.notice-list {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
position: relative;
|
||||||
|
width: 100%;
|
||||||
|
height: calc(100% - 60px); /* 除去标题和指示器的高度 */
|
||||||
|
}
|
||||||
|
|
||||||
|
.notice-item {
|
||||||
|
text-align: center;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.notice-image {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
object-fit: cover; /* 让图片适应公告栏 */
|
||||||
|
border-radius: 8px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.arrow-button {
|
||||||
|
position: absolute;
|
||||||
|
top: 50%;
|
||||||
|
transform: translateY(-50%);
|
||||||
|
background-color: rgba(255, 255, 255, 0.7);
|
||||||
|
border: none;
|
||||||
|
border-radius: 50%;
|
||||||
|
width: 40px;
|
||||||
|
height: 40px;
|
||||||
|
font-size: 20px;
|
||||||
|
cursor: pointer;
|
||||||
|
z-index: 10;
|
||||||
|
}
|
||||||
|
|
||||||
|
.left-arrow {
|
||||||
|
left: 10px; /* 左侧按钮距离公告栏左边缘 10px */
|
||||||
|
}
|
||||||
|
|
||||||
|
.right-arrow {
|
||||||
|
right: 10px; /* 右侧按钮距离公告栏右边缘 10px */
|
||||||
|
}
|
||||||
|
|
||||||
|
.arrow-button:hover {
|
||||||
|
background-color: rgba(255, 255, 255, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
.indicator-container {
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
margin-top: 10px;
|
||||||
|
gap: 8px; /* 按钮之间的间距 */
|
||||||
|
}
|
||||||
|
|
||||||
|
.indicator-button {
|
||||||
|
width: 12px;
|
||||||
|
height: 12px;
|
||||||
|
border: none;
|
||||||
|
border-radius: 50%;
|
||||||
|
background-color: rgba(255, 255, 255, 0.5);
|
||||||
|
cursor: pointer;
|
||||||
|
transition: background-color 0.3s;
|
||||||
|
}
|
||||||
|
|
||||||
|
.indicator-button.active {
|
||||||
|
background-color: rgba(255, 255, 255, 1); /* 高亮当前按钮 */
|
||||||
|
}
|
||||||
|
|
||||||
|
.indicator-button:hover {
|
||||||
|
background-color: rgba(255, 255, 255, 0.8);
|
||||||
|
}
|
||||||
|
</style>
|
@ -0,0 +1,222 @@
|
|||||||
|
<template>
|
||||||
|
<div class="post-page-container">
|
||||||
|
<!-- 左侧分类按钮 -->
|
||||||
|
<div class="category-buttons">
|
||||||
|
<button
|
||||||
|
v-for="(category, index) in categories"
|
||||||
|
:key="index"
|
||||||
|
class="category-button"
|
||||||
|
:class="{ active: selectedCategory === category }"
|
||||||
|
@click="selectCategory(category)"
|
||||||
|
>
|
||||||
|
{{ category }}
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- 右侧帖子列表 -->
|
||||||
|
<div class="post-list">
|
||||||
|
<div
|
||||||
|
v-for="(post, index) in filteredPosts"
|
||||||
|
:key="index"
|
||||||
|
class="post-item"
|
||||||
|
@click="goToPostDetail(post.id)"
|
||||||
|
>
|
||||||
|
<div class="post-header">
|
||||||
|
<img :src="post.avatar" :alt="头像" class="post-avatar" />
|
||||||
|
<h3 class="post-title">{{ post.title }}</h3>
|
||||||
|
</div>
|
||||||
|
<p class="post-summary">{{ post.summary }}</p>
|
||||||
|
<div class="post-stats">
|
||||||
|
<span>热度 {{ post.likes }}</span>
|
||||||
|
<span>评论 {{ post.comments }}</span>
|
||||||
|
<span>赞 {{ post.favorites }}</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
import { ref } from 'vue';
|
||||||
|
|
||||||
|
export default {
|
||||||
|
name: 'PostPage',
|
||||||
|
setup() {
|
||||||
|
const categories = ref(['全部', '学习', '娱乐', '二手交易']);
|
||||||
|
const selectedCategory = ref('全部');
|
||||||
|
const posts = ref([
|
||||||
|
{
|
||||||
|
id: 1,
|
||||||
|
category: '学习',
|
||||||
|
title: '如何高效学习?',
|
||||||
|
summary: '分享一些学习技巧...',
|
||||||
|
avatar: require('@/assets/default-avatar/boy_1.png'),
|
||||||
|
likes: 1200,
|
||||||
|
comments: 10,
|
||||||
|
favorites: 100,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 2,
|
||||||
|
category: '娱乐',
|
||||||
|
title: '最近的热门电影推荐',
|
||||||
|
summary: '看看这些电影吧...',
|
||||||
|
avatar: require('@/assets/default-avatar/girl_1.png'),
|
||||||
|
likes: 800,
|
||||||
|
comments: 5,
|
||||||
|
favorites: 50,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 3,
|
||||||
|
category: '二手交易',
|
||||||
|
title: '出售二手书籍',
|
||||||
|
summary: '价格优惠,欢迎咨询...',
|
||||||
|
avatar: require('@/assets/default-avatar/boy_2.png'),
|
||||||
|
likes: 300,
|
||||||
|
comments: 2,
|
||||||
|
favorites: 20,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 4,
|
||||||
|
category: '学习',
|
||||||
|
title: '考研经验分享',
|
||||||
|
summary: '考研路上的一些心得...',
|
||||||
|
avatar: require('@/assets/default-avatar/girl_3.png'),
|
||||||
|
likes: 1500,
|
||||||
|
comments: 20,
|
||||||
|
favorites: 200,
|
||||||
|
},
|
||||||
|
]);
|
||||||
|
|
||||||
|
const filteredPosts = ref(posts.value);
|
||||||
|
|
||||||
|
const selectCategory = (category) => {
|
||||||
|
selectedCategory.value = category;
|
||||||
|
filteredPosts.value =
|
||||||
|
category === '全部'
|
||||||
|
? posts.value
|
||||||
|
: posts.value.filter((post) => post.category === category);
|
||||||
|
};
|
||||||
|
|
||||||
|
const goToPostDetail = (postId) => {
|
||||||
|
const url = `/post/${postId}`;
|
||||||
|
console.log('Opening URL:', url);
|
||||||
|
window.open(`/post/${postId}`, '_blank');
|
||||||
|
};
|
||||||
|
|
||||||
|
return {
|
||||||
|
categories,
|
||||||
|
selectedCategory,
|
||||||
|
filteredPosts,
|
||||||
|
selectCategory,
|
||||||
|
goToPostDetail,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
/* 页面整体布局 */
|
||||||
|
.post-page-container {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: row;
|
||||||
|
align-items: flex-start;
|
||||||
|
padding: 20px;
|
||||||
|
box-sizing: border-box;
|
||||||
|
gap: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 左侧分类按钮样式 */
|
||||||
|
.category-buttons {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: 0;
|
||||||
|
width: 200px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.category-button {
|
||||||
|
padding: 10px 20px;
|
||||||
|
font-size: 14px;
|
||||||
|
border: 1px solid #ccc;
|
||||||
|
border-bottom: none;
|
||||||
|
background-color: #f9f9f9;
|
||||||
|
cursor: pointer;
|
||||||
|
transition: background-color 0.3s, color 0.3s;
|
||||||
|
}
|
||||||
|
|
||||||
|
.category-button:last-child {
|
||||||
|
border-bottom: 1px solid #ccc;
|
||||||
|
}
|
||||||
|
|
||||||
|
.category-button.active {
|
||||||
|
background-color: #5aa76f;
|
||||||
|
color: white;
|
||||||
|
border-color: #5aa76f;
|
||||||
|
}
|
||||||
|
|
||||||
|
.category-button:hover {
|
||||||
|
background-color: #e0e0e0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 右侧帖子列表样式 */
|
||||||
|
.post-list {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: repeat(2, 1fr);
|
||||||
|
gap: 20px;
|
||||||
|
flex: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
.post-item {
|
||||||
|
position: relative; /* 设置为相对定位 */
|
||||||
|
width: 300px;
|
||||||
|
height: 150px;
|
||||||
|
padding: 15px;
|
||||||
|
border: 1px solid #ccc;
|
||||||
|
border-radius: 8px;
|
||||||
|
background-color: #ffffff;
|
||||||
|
cursor: pointer;
|
||||||
|
transition: box-shadow 0.3s;
|
||||||
|
}
|
||||||
|
|
||||||
|
.post-item:hover {
|
||||||
|
box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 帖子头部样式 */
|
||||||
|
.post-header {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 10px;
|
||||||
|
margin-bottom: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.post-avatar {
|
||||||
|
width: 40px;
|
||||||
|
height: 40px;
|
||||||
|
border-radius: 50%; /* 设置为圆形 */
|
||||||
|
object-fit: cover; /* 确保图片按比例填充 */
|
||||||
|
}
|
||||||
|
|
||||||
|
.post-title {
|
||||||
|
font-size: 18px;
|
||||||
|
font-weight: bold;
|
||||||
|
margin: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 帖子摘要样式 */
|
||||||
|
.post-summary {
|
||||||
|
font-size: 14px;
|
||||||
|
color: #666;
|
||||||
|
margin-bottom: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 帖子统计信息样式 */
|
||||||
|
.post-stats {
|
||||||
|
display: flex;
|
||||||
|
gap: 15px; /* 图标之间的间距 */
|
||||||
|
font-size: 12px;
|
||||||
|
color: #999;
|
||||||
|
position: absolute; /* 绝对定位 */
|
||||||
|
bottom: 10px; /* 距离卡片底部 10px */
|
||||||
|
left: 15px; /* 距离卡片左侧 15px */
|
||||||
|
}
|
||||||
|
</style>
|
@ -1,4 +1,8 @@
|
|||||||
import { createApp } from 'vue'
|
import { createApp } from 'vue';
|
||||||
import App from './App.vue'
|
import App from './App.vue';
|
||||||
|
import router from './router'; // 确保引入了 router
|
||||||
|
|
||||||
createApp(App).mount('#app')
|
const app = createApp(App);
|
||||||
|
|
||||||
|
app.use(router); // 注册 vue-router
|
||||||
|
app.mount('#app');
|