前言:
本文给大家讲解,美食杰项目中 实现个人主页的效果,和具体代码。
具体实现思路:
判断是否是本人,获取用户详情信息
关注,取消关注
点击跳转,显示(发布,收藏,粉丝,关注)
判断是否是跳转页,是则显示内容
根据示例图进行渲染
步骤:
1. 展示美食杰菜谱大全效果
美食杰个人主页演示
2. 引入element-ui
点击跳转至 element-ui 中 Tabs 标签页使用方法:https://element.eleme.cn/#/zh-CN/component/tabs
3. 代码
- 个人主页
跳转至(发布,收藏,粉丝,关注)页可以使用 element-ui 中 Tabs 标签的方法。
<template> <div class="box"> <p class="title">欢迎来到我的美食空间</p> <div class="top"> <div class="left"> <img :src="userInfo.avatar" alt="" /> </div> <div class="center"> <p class="one"> {{ userInfo.name }} <!-- v-if="isLogin" 判断是否是本人 --> <span :class="{ action: userInfo.isFollowing }" v-if="isLogin" @click="follow" > {{ userInfo.isFollowing ? "已关注" : "未关注" }}</span > </p> <p class="two"> 个人简介:{{ userInfo.sign ? userInfo.sign : "这个人比较懒,还没有简介" }} </p> <p class="three"> {{ userInfo.createdAt }}加入美食杰<router-link :to="{ name: 'personal' }" v-if="!isLogin" > | 编辑个人资料</router-link > </p> </div> <div class="right"> <p> 关注<span>{{ userInfo.following_len }}</span> </p> <p> 粉丝<span>{{ userInfo.follows_len }}</span> </p> <p> 收藏<span>{{ userInfo.collections_len }}</span> </p> <p> 发布菜谱<span>{{ userInfo.work_menus_len }}</span> </p> </div> </div> <div class="centers"> <router-link :to="{ name: 'works', query: { ...$route.query } }" >作品</router-link > <router-link :to="{ name: 'fans', query: { ...$route.query } }" >粉丝</router-link > <router-link :to="{ name: 'following', query: { ...$route.query } }" >关注</router-link > <router-link :to="{ name: 'collection', query: { ...$route.query } }" >收藏</router-link > </div> <div class="bottom"> <!-- 父传子事件 --> <router-view :activeName="activeName" :info="list"></router-view> </div> </div> </template> <script> import { userInfo, toggleFollowing, getMenus, collection, following, fans, } from "@/connector/api"; // 封装请求接口 const getaxios = { async works(params) { return (await getMenus(params)).data; }, async collection(params) { return (await collection(params)).data; }, async following(params) { return (await following(params)).data; }, async fans(params) { return (await fans(params)).data; }, }; export default { data() { return { // 用户信息 userInfo: [], // 传递参数 activeName: "works", // 是否是本人 isLogin: "", // 用户自己的 list: [], // 用户自己的 用来判断 queen: {}, }; }, watch: { $route: { async handler() { // 获取query值 let { userId } = this.$route.query; // 请求当前用户数据 const { data } = await userInfo({ userId: userId }); // 判断是否是本人如果是则获取本人信息,如果不是则获取用户信息 this.userInfo = userId ? data : this.$store.state.userInfo; // 判断是否是本人 this.isLogin = userId ? true : false; // console.log(this.userInfo); // 传递参数 this.activeName = this.$route.name; this.getaxiose(); }, immediate: true, }, }, mounted() { // 获取用户信息 this.userInfo = this.$store.state.userInfo; // console.log(this.userInfo); }, methods: { // 点击关注 async follow() { const data = await toggleFollowing({ followUserId: this.userInfo.userId, }); // console.log(data.data); // 因为关注后,要更新数据,所以要整体赋值 this.userInfo = data.data; }, // 获取跳转子组件时需要传递的参数 getaxiose() { (async (activeName) => { // 获取跳转子组件时需要传递的参数 let data = await getaxios[this.activeName]({ userId: this.userInfo.userId, }); // 根据 activeName 的值进行赋值 this.queen[activeName] = data.list; // console.log(activeName, this.activeName); // 判断当前的 activeName 是否等于显示的 activeName if (activeName === this.activeName) { // 把值赋值给 list this.list = this.queen[this.activeName]; } // 判断失败则不赋值,直到判断成立为止 // console.log(data); this.queen = {}; })(this.activeName); }, }, }; </script> <style lang="scss" scoped> .box { width: 990px; margin: 0 auto; .title { text-align: center; margin: 30px 0; } .top { width: 100%; background-color: #fff; display: flex; position: relative; img { width: 250px; height: 250px; } .center { margin-left: 20px; p { color: gainsboro; font-size: 14px; padding: 5px 0; margin: 0; } .one { color: #333; font-size: 20px; margin-top: 20px; span { display: inline-block; position: absolute; right: 250px; background-color: red; padding: 5px 10px; border-radius: 5px; color: #fff; } .action { background-color: grey; color: #333; } } .three { a { text-decoration: none; color: gainsboro; } } } .right { width: 160px; display: flex; flex-wrap: wrap; position: absolute; margin: 20px 20px 0 0; right: 0; p { width: 60px; height: 60px; border-radius: 30px; border: 1px solid #333; font-size: 12px; margin: 20px 10px; text-align: center; line-height: 40px; } span { display: block; line-height: 10px; color: red; } } } .centers { margin: 30px 0; a { margin-right: 35px; padding-bottom: 10px; text-decoration: none; color: #333; &.router-link-exact-active { color: red; border-bottom: 1px solid red; } } } } </style>
- 收藏发布页
也可以把发布页和收藏页,分成两个组件来写,在一个组件中需要进行判断,那部分显示,那部分不显示
<template> <div class="box"> <!-- 判断是否有内容 --> <div class="info-empty" v-if="!info.length"> <!-- 判断是否是 发布页 --> <div v-if="activeName == 'works'"> <p>私房菜不要偷偷享用哦~~制作成菜谱与大家分享吧!</p> <router-link to="">发布菜单</router-link> </div> </div> <!-- 判断是否是 收藏页 --> <div class="info-empty" v-if="!info.length"> <div v-if="activeName == 'collection'"> <p>还没有收藏任何的菜谱,去搜自己喜欢的菜谱,收藏起来吧。</p> <router-link to="">菜谱大全</router-link> </div> </div> <div v-if="info.length"> <!-- 使用主页时定义的组件 --> <Roll :menus="info" :id="5"></Roll> </div> </div> </template> <script> import Roll from "@/views/home-page/roll.vue"; export default { components: { Roll }, props: { // 接收数据 activeName activeName: { type: String, default: "fans", }, // 渲染至页面的数据 info: { type: Array, default: () => [], }, }, data() { return { info: "", }; }, mounted() { this.info = this.$store.getters.islogin; }, }; </script> <style lang="scss" scoped> .box { width: 100%; // height: 300px; background-color: #fff; .info-empty { width: 100%; text-align: center; display: block; line-height: 80px; padding: 0 0 20px 0; a { text-decoration: none; padding: 20px 30px; border-radius: 15px; background-color: red; } } } </style>
- 粉丝关注页
也可以把粉丝页和关注页,分成两个组件来写,在一个组件中需要进行判断,那部分显示,那部分不显示
<template> <div class="box"> <!-- 判断是否有信心 --> <div v-if="!info.length"> <!-- 判断是否是 粉丝页 --> <p v-if="activeName == 'fans'" class="activeName"> 还没有被关注哦!多发布菜谱,更容易被找到。 </p> <!-- 判断是否是 关注页 --> <p v-if="activeName == 'following'" class="activeName"> 还没有关注别人哦!可以预览菜谱,找到别人 </p> </div> <ul> <!-- 渲染数据 --> <li v-for="item in info" :key="item._id"> <router-link :to="{ name: 'MyHomepage', query: { userId: item.userId } }" > <img :src="item.avatar" alt="" /> </router-link> <div class="title"> <router-link :to="{ name: 'MyHomepage', query: { userId: item.userId } }" > <p class="name">{{ item.name }}</p> </router-link> <p class="follows"> 粉丝:{{ item.follows_len }} | 关注:{{ item.following_len }} </p> </div> </li> </ul> </div> </template> <script> export default { props: { // 接收数据 activeName activeName: { type: String, default: "fans", }, // 渲染至页面的数据 info: { type: Array, default: () => [], }, }, mounted() { // console.log(this.activeName); }, }; </script> <style lang="scss" scoped> .box { width: 100%; // height: 300px; background-color: #fff; .activeName { width: 100%; text-align: center; padding: 100px 0; } ul { li { display: flex; padding: 10px 0; list-style: none; img { width: 120px; height: 120px; margin-right: 20px; } .name { color: red; } a { text-decoration: none; } } } } </style>
总结:
总结:
以上就是 美食杰项目 中 个人主页的具体实现方法,不懂得也可以在评论区里问我,以后会持续发布一些新的功能,敬请关注。