vue四十七:Vue美团项目之商家详情-左右联动之选中商品分类跳转到对应商品列表
在左侧商品分类点击商品时,右侧自动跳转到对应的商品详情
定义一个点击事件
绑定点击事件
获取商品高度
触发点击事件时改为获取高度偏移量,并滚动
增加选中状态
效果
<style scoped>
.merchant-container >>> .van-nav-bar {
background: none;
}
/*去掉横线*/
.merchant-container >>> .van-hairline--bottom::after {
border: none;
}
/*修改箭头颜色*/
.merchant-container >>> .van-icon {
color: #fff;
}
</style>
<style scoped lang="scss">
.header-group {
background-color: black;
padding: 10px;
display: flex;
margin-top: -46px;
padding-top: 46px;
.logo {
width: 85px;
height: 75px;
}
.merchant-info {
flex: 1;
margin-left: 10px;
color: #fff;
display: flex;
flex-direction: column;
justify-content: space-around;
overflow: hidden;
}
.notice {
text-overflow: ellipsis;
white-space: nowrap;
overflow: hidden;
}
}
.tab-group {
.menu-group {
display: flex;
.category-group {
width: 80px;
text-align: center;
/**/
height: 100%;
overflow: hidden;
.category-list {
overflow: hidden;
li {
height: 50px;
line-height: 50px;
&.active {
background-color: #ccc;
}
}
}
}
.goods-group {
flex: 1;
/**/
margin-left: 10px;
overflow: hidden;
height: 100%;
.category-name {
font-size: 12px;
height: 32px;
line-height: 32px;
}
.goods-item {
display: flex;
/*margin-bottom: 10px;*/
padding-bottom: 10px;
height: 75px;
.thumbnail {
width: 75px;
height: 75px;
}
.goods-info {
flex: 1;
margin-left: 10px;
display: flex;
flex-direction: column;
justify-content: space-around;
.goods-name {
font-size: 16px;
font-weight: 700;
}
.price {
color: #fb4e44;
font-size: 16px;
font-weight: 700;
}
}
}
}
}
}
</style>
<template>
<div class="merchant-container">
<van-nav-bar left-arrow></van-nav-bar>
<div class="header-group">
<img src="https://tse3-mm.cn.bing.net/th/id/OIP.17S875eLr_HDQD8FGwagqQAAAA?w=151&h=201&c=7&o=5&dpr=1.25&pid=1.7"
alt="" class="logo">
<div class="merchant-info">
<div class="delivery-info">
<span>20分钟</span> | <span>3KM</span>
</div>
<div class="notice">
公告公告公告公告公告公告公告公告公告公告公告公告公告公告公告公告公告公告公告公告
</div>
</div>
</div>
<van-tabs class="tab-group" v-model="active">
<van-tab title="点菜">
<div class="menu-group" :style="menuHeightStyle">
<div class="category-group" ref="category">
<ul class="category-list">
<li v-for="(category, index) in categories" :key="category.name"
@click="categoryClick(index)" :class="index==currentIndex?'active':''">
{{ category.name }}
</li>
</ul>
</div>
<div class="goods-group" ref="goods">
<div class="goods-list">
<dl v-for="category in categories" :key="category.name" class="goods-dl">
<dt class="category-name">{{category.name}}</dt>
<dd class="goods-item" v-for="goods in category.goods_list" :key="goods.id">
<img :src="goods.picture" alt="" class="thumbnail">
<div class="goods-info">
<div class="goods-name">{{goods.name}}</div>
<div class="month-sale">月售1份</div>
<div class="price">{{goods.price}}</div>
</div>
</dd>
</dl>
</div>
</div>
</div>
</van-tab>
<van-tab title="评价">
评价页面
</van-tab>
<van-tab title="商家">
商家页面
</van-tab>
</van-tabs>
</div>
</template>
<script type="text/ecmascript-6">
import {NavBar, Tab, Tabs} from 'vant';
import BScroll from "better-scroll"; //先 npm install better-scroll
import kfc from "../data/kfc" // 导入测试数据
export default {
name: "",
data() {
return {
active: 0,
categories: [],
positions: [],
currentIndex: 0
}
},
components: {
[NavBar.name]: NavBar,
[Tab.name]: Tab,
[Tabs.name]: Tabs
},
computed: {
// 定义商家产品页内容体的高度
menuHeightStyle() {
const height = window.innerHeight - 164;
return {
height: height + "px"
}
}
},
mounted() {
const categories = kfc['categories']; // 获取测试数据的categories字段的值
this.categories = categories
// // 获取每条数据的id和name字段
// for (let index = 0; index < categories.length; index++) {
// const category = categories[index];
// this.categories.push({id: category.id, name: category.name})
// }
// 菜单滚动
this.$nextTick(() => {
var menuScroll = new BScroll(this.$refs.category, { // eslint-disable-line no-unused-vars
scrollY: true, // Y,垂直
click: true // 可点击
})
var goodsScroll = new BScroll(this.$refs.goods, { // eslint-disable-line no-unused-vars
scrollY: true, // Y,垂直
click: true // 可点击
})
this.menuScroll = menuScroll;
this.goodsScroll = goodsScroll;
// 获取上平距离顶部的高度,方便跳转
const positions = [0];
let offset = 0;
const dlList = document.getElementsByClassName("goods-dl") // 获取商品列表
// for...in...循环对象
// for...of...循环数组
for (let dl of dlList) {
const height = dl.clientHeight; // 获取商品的高度
offset += height;
positions.push(offset)
}
this.positions = positions;
})
},
methods: {
categoryClick(index) {
const position = this.positions[index];
// 往上滚动,y的值应该为负数
this.goodsScroll.scrollTo(1, -position, 500) // scrollTo滚动到具体位置,具体参见better-scroll官方文档
this.currentIndex = index; // 更新选中的索引
}
}
}
</script>
讨论群:249728408