vue文章列表详情实现
实现Vue文章列表与详情功能
技术栈建议
- Vue 2/3 + Vue Router
- 状态管理:Vuex/Pinia(可选)
- UI库:Element UI/Ant Design Vue(可选)
基础项目结构
src/
├── views/
│ ├── ArticleList.vue # 列表页
│ └── ArticleDetail.vue # 详情页
├── router/
│ └── index.js # 路由配置
├── components/
│ └── ArticleCard.vue # 文章卡片组件
路由配置示例
// router/index.js
const routes = [
{
path: '/articles',
component: () => import('../views/ArticleList.vue')
},
{
path: '/articles/:id',
component: () => import('../views/ArticleDetail.vue'),
props: true
}
]
文章列表实现
<!-- ArticleList.vue -->
<template>
<div class="article-list">
<ArticleCard
v-for="article in articles"
:key="article.id"
:article="article"
@click="goToDetail(article.id)"
/>
</div>
</template>
<script>
export default {
data() {
return {
articles: [
{ id: 1, title: 'Vue基础', excerpt: 'Vue入门教程...' },
{ id: 2, title: 'Vue Router', excerpt: '路由管理指南...' }
]
}
},
methods: {
goToDetail(id) {
this.$router.push(`/articles/${id}`)
}
}
}
</script>
文章详情实现
<!-- ArticleDetail.vue -->
<template>
<div v-if="article">
<h1>{{ article.title }}</h1>
<div class="content">{{ article.content }}</div>
</div>
</template>
<script>
export default {
props: ['id'],
data() {
return {
article: null
}
},
created() {
this.fetchArticle()
},
methods: {
fetchArticle() {
// 模拟API请求
const articles = [
{
id: 1,
title: 'Vue基础',
content: '这里是详细内容...'
}
]
this.article = articles.find(a => a.id === Number(this.id))
}
}
}
</script>
进阶优化方案
API数据获取
// 使用axios示例
import axios from 'axios'
export default {
methods: {
async fetchArticles() {
try {
const res = await axios.get('/api/articles')
this.articles = res.data
} catch (error) {
console.error(error)
}
}
}
}
状态管理(Pinia示例)
// stores/article.js
import { defineStore } from 'pinia'
export const useArticleStore = defineStore('article', {
state: () => ({
articles: [],
currentArticle: null
}),
actions: {
async fetchAll() {
const res = await axios.get('/api/articles')
this.articles = res.data
},
async fetchOne(id) {
const res = await axios.get(`/api/articles/${id}`)
this.currentArticle = res.data
}
}
})
列表分页实现
<template>
<div>
<!-- 列表内容 -->
<el-pagination
@current-change="handlePageChange"
:current-page="currentPage"
:page-size="pageSize"
:total="total"
/>
</div>
</template>
<script>
export default {
data() {
return {
currentPage: 1,
pageSize: 10,
total: 0
}
},
methods: {
handlePageChange(page) {
this.currentPage = page
this.fetchArticles()
},
async fetchArticles() {
const res = await axios.get('/api/articles', {
params: {
page: this.currentPage,
size: this.pageSize
}
})
this.articles = res.data.items
this.total = res.data.total
}
}
}
</script>
样式建议
/* 列表样式 */
.article-list {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));
gap: 20px;
}
/* 详情页样式 */
.article-content {
line-height: 1.6;
max-width: 800px;
margin: 0 auto;
padding: 20px;
}






