Vue实现左右菜单联动实现代码

本文介绍了Vue实现左右菜单联动实现代码吗,分享给大家,也给自己留个笔记,具体如下:

Github

源码传送门: Rain120/vue-study

之前在外卖软件上看到这个左右联动的效果,觉得很有意思,所以就尝试使用 Vue 来实现,将这个联动抽离成为一个单独的组件,废话少说,先来一张效果图。

这个组件分为两个部分,1、左菜单;2、右菜单。 左菜单的 DOM 结构

<scroll
 class="left-menu"
 :data="leftMenu"
 ref="leftMenu">
 <div class="left-menu-container">
 <ul>
  <li
  class="left-item"
  ref="leftItem"
  :class="{'current': currentIndex === index}"
  @click="selectLeft(index, $event)"
  v-for="(item, index) in leftMenu"
  :key="index">
  <p class="text">{{item}}</p>
  </li>
 </ul>
 </div>
</scroll>

右菜单的 DOM 结构

<scroll
 class="right-menu"
 :data="rightMenu"
 ref="rightMenu"
 @scroll="scrollHeight"
 :listenScroll="true"
 :probeType="3">
 <div class="right-menu-container">
 <ul>
  <li class="right-item" ref="rightItem" v-for="(items, i) in rightMenu" :key="i">
  <div class="data-wrapper">
   <div class="title">{{items.title}}</div>
   <div class="data" v-for="(item, j) in items.data" :key="j">{{item}}</div>
  </div>
  </li>
 </ul>
 </div>
</scroll>

这里是为了做 demo ,所以在数据上只是单纯捏造。

当然因为这是个子组件,我们将通过父组件传递 props ,所以定义 props

props: {
 leftMenu: {
 required: true,
 type: Array,
 default () {
  return []
 }
 },
 rightMenu: {
 required: true,
 type: Array,
 default () {
  return []
 }
 },
}

在这个业务场景中,我们的实现方式是根据右边菜单滚动的高度来计算左边菜单的位置,当然左边菜单也可以通过点击来确定右边菜单需要滚动多高的距离,那么我们如何获得该容器滚动的距离呢? 之前一直在使用better-scroll,通过阅读文档,我们知道它有有 scroll 事件,我们可以通过监听这个事件来获取滚动的 pos

if (this.listenScroll) {
 let me = this
 this.scroll.on('scroll', (pos) => {
 me.$emit('scroll', pos)
 })
}

所以我们在右边菜单的 scroll 组件上监听scroll事件

@scroll="scrollHeight"

method

scrollHeight (pos) {
 console.log(pos);
 this.scrollY = Math.abs(Math.round(pos.y))
},

我们将监听得到的pos打出来看看

我们可以看到控制台打出了当前滚动的pos信息,因为在移动端开发时,坐标轴和我们数学中的坐标轴相反,所以上滑时y轴的值是负数

所以我们要得到每一块 li 的高度,我们可以通过拿到他们的 DOM

 _calculateHeight() {
 let lis = this.$refs.rightItem;
 let height = 0
 this.rightHeight.push(height)
 Array.prototype.slice.call(lis).forEach(li => {
 height += li.clientHeight
 this.rightHeight.push(height)
 })
console.log(this.rightHeight)
}

我们在 created 这个 hook 之后调用这个计算高度的函数

 _calculateHeight() {
 let lis = this.$refs.rightItem;
 let height = 0
 this.rightHeight.push(height)
 Array.prototype.slice.call(lis).forEach(li => {
 height += li.clientHeight
 this.rightHeight.push(height)
 })
 console.log(this.rightHeight)
}

当用户在滚动时,我们需要计算当前滚动距离实在那个区间内,并拿到他的 index

computed: {
 currentIndex () {
 const { scrollY, rightHeight } = this
 const index = rightHeight.findIndex((height, index) => {
  return scrollY >= rightHeight[index] && scrollY < rightHeight[index + 1]
 })
 return index > 0 ? index : 0
 }
}

所以当前应该是左边菜单 index = 1 的菜单项 active 以上是左边菜单根据右边菜单的滑动联动的实现,用户也可以通过点击左边菜单来实现右边菜单的联动,此时,我们给菜单项加上 click事件

@click="selectLeft(index, $event)"

这里加上 $event 是为了区分原生点击事件还是[better-scroll]((https://ustbhuangyi.github.io/better-scroll/doc/zh-hans/#better-scroll 是什么)派发的事件

selectLeft (index, event) {
 if (!event._constructed) {
 return
 }
 let rightItem = this.$refs.rightItem
 let el = rightItem[index]
 this.$refs.rightMenu.scrollToElement(el, 300)
},

到这里我们就基本上完成了这些需求了

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • vue.js与element-ui实现菜单树形结构的解决方法

    由于业务需要,要求实现树形菜单,且菜单数据由后台返回,在网上找了几篇文章,看下来总算有了解决办法. 场景:根据业务要求,需要实现活动的树形菜单,菜单数据由后台返回,最后的效果图如下: 后台返回的数据格式是这个样子的: data=[{ pID:'1',//父ID name:'目录一', menuID:'m1',//本身ID isContent:false//判断是否是目录 }, { pID:'1', name:'目录二', menuID:'m2', isContent:false }, { pID

  • vue实现底部菜单功能

    具体代码如下所示: <template> <div class="mui-row"> <div class="mui-col-xs-12 mui-row nav"> <div class="mui-col-xs-4" @tap="tab1=1;tab2=1;tab3=1"> <router-link to="/recommend" ><img

  • Vue实现侧边菜单栏手风琴效果实例代码

    效果图如下所示: <template> <div class="asideBox"> <aside> <ul class="asideMenu"> <li v-for="(item,index) in menuList"> <div class="oneMenu" @click="showToggle(item,index)"> <

  • Vue.js 实现微信公众号菜单编辑器功能(一)

    学习一段时间Vue.js,于是想尝试着做一个像微信平台里那样的菜单编辑器,在这里分享下 具体样式代码查看项目github 创建一个vue实例 <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> <script src="https://cdn.bootcss.com/vue/2.5.9/vue.js"&g

  • vue2.0使用v-for循环制作多级嵌套菜单栏

    使用v-for循环生成一个多级嵌套菜单栏,只要你学会了这个方法,几乎所有的菜单栏都可以实现了. 方法 <div class="level-one" v-if="obj.level == 1" v-for="obj in bar1"><a>{{obj.title}}</a> <div class="level-two" v-if="obj1.parentId == obj.id

  • Vue实现自定义下拉菜单功能

    先看例子,后面有对用到的知识点的总结 效果图: 实现代码如下: <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>组件练习</title> <link rel="stylesheet" type="text/css" href="component.c

  • Vue在页面右上角实现可悬浮/隐藏的系统菜单

    这是个大多数网站很常见的功能,点击页面右上角头像显示一个悬浮菜单,点击页面其他位置或再次点击头像则菜单隐藏. 作为一个jQuery前端攻城狮实现这个功能可以说是很easy了,但是对只刚粗看了一遍vue文档的菜鸟来说,坑还是要亲自踩过才算圆满. 知识点 组件及组件间通信 计算属性 正文 1. 父组件 这里暂时只涉及系统菜单这一个功能,因此路由暂未涉及. 基本思路是:通过props将showCancel这个Boolean值传递到子组件,对父子组件分别绑定事件,来控制这个系统菜单的显示状态.其中在父组

  • vuejs 切换导航条高亮(路由菜单高亮)的方法示例

    我的GitHub前端经验总结,喜欢的话请点star:Thanks.: https://github.com/liangfengbo/frontend-develop vuejs导航条高亮我的做法: 用一个数组存导航条,用v-for循环它,这样可以减少代码,二可以使用它的下标来判断高亮,三还可以获取后端的导航信息来遍历 重点是在:routerLink(index, path)函数,传入当前点击的下标,自定义一个下标,判断是否相等就用三元符号判断多给一个高亮样式 如何解决刷新就不高亮或第一个高亮了,

  • Vue.js 实现微信公众号菜单编辑器功能(二)

    Vue.js 实现微信公众号菜单编辑器功能(一)上一篇菜单的点击和添加菜单功能已经在模版实现了,接下来实现菜单的编辑功能 实现菜单删除方法 在vue实例中添加删除菜单方法,根据选中的菜单级别和索引来删除. methods: { //删除菜单 delMenu:function(){ //删除主菜单 if(this.selectedMenuLevel()==1&&confirm('删除后菜单下设置的子菜单也将被删除')){ if(this.selectedMenuIndex===0){ thi

  • Vue实现左右菜单联动实现代码

    本文介绍了Vue实现左右菜单联动实现代码吗,分享给大家,也给自己留个笔记,具体如下: Github 源码传送门: Rain120/vue-study 之前在外卖软件上看到这个左右联动的效果,觉得很有意思,所以就尝试使用 Vue 来实现,将这个联动抽离成为一个单独的组件,废话少说,先来一张效果图. 这个组件分为两个部分,1.左菜单:2.右菜单. 左菜单的 DOM 结构 <scroll class="left-menu" :data="leftMenu" ref=

  • Vue 递归多级菜单的实例代码

    考虑以下菜单数据: [ { name: "About", path: "/about", children: [ { name: "About US", path: "/about/us" }, { name: "About Comp", path: "/about/company", children: [ { name: "About Comp A", path:

  • vue实现伸缩菜单功能

    本文实例为大家分享了vue实现伸缩菜单的具体代码,供大家参考,具体内容如下 先看效果: 点击图片按钮可调整菜单宽度 伸缩后 页面结构一共分为三部分,加上一个伸缩按钮,在你的项目对应的部分都加上class名. 我这里定义的分别是box.left.mid.resize(按钮类名) html 页面结构划分完成之后,完善一下样式(直接复制,菜单类名换成你的) /*拖拽区div样式*/ .resize {     cursor: col-resize;     position: relative;  

  • vue element 生成无线级左侧菜单的实现代码

    首先来总结element ui 官方文档的左侧菜单结构,带有el-submenu为子级节点,el-menu-item表示没有下级.当然,菜单不能写死,因为菜单也许不止两级,所以我们需要递归来实现.根据当前节点是否有下级去判断,如果有下级,则继续调用子级,直到没有下级为止,下面我贴上左侧菜单所有的代码: 请求数据格式 [ { name: "首页", id: -1, icon: "el-icon-picture-outline-round", url: "/i

  • vue实现导航菜单和编辑文本的示例代码

    导航菜单实例 <div id="main"> <!-- 激活的菜单样式为 active 类 --> <!-- 为了阻止链接在点击时跳转,我们使用了 "prevent" 修饰符 (preventDefault 的简称). --> <nav v-bind:class="active" v-on:click.prevent> <!-- 当菜单上的链接被点击时,我们调用了 makeActive 方法,

  • Vue + Element UI 实现权限管理系统之菜单功能实现代码

    目录 菜单功能实现 菜单接口封装 菜单管理界面 测试效果 源码下载 菜单功能实现 菜单接口封装 菜单管理是一个对菜单树结构的增删改查操作. 提供一个菜单查询接口,查询整颗菜单树形结构. http/modules/menu.js 添加findMenuTree 接口. import axios from '../axios' /* * 菜单管理模块 */ // 保存 export const save = (data) => { return axios({ url: '/menu/save', m

  • vue+elementui+vuex+sessionStorage实现历史标签菜单的示例代码

    一般是有左侧菜单后,然后要在页面上部分添加历史标签菜单需求. 借鉴其他项目,以及网上功能加以组合调整实现 按照标签实现方式步骤来(大致思路): 1,写一个tagNav标签组件 2,在路由文件上每个路由组件都添加meta属性 meta:{title:'组件中文名'} 3,在store的mutation.js文件中写标签的添加/删除方法以及在方法中更新sessionStorage数据 4,在主页面上添加组件以及router-view外层添加keep-alive组件,我这边是main.vue为登录后主

  • vue2.0的contextmenu右键弹出菜单的实例代码

    整理文档,搜刮出一个vue2.0的contextmenu右键弹出菜单的实例代码,稍微整理精简一下做下分享. 1.事情对象 <!DOCTYPE html> <html> <head> <title></title> <meta charset="utf-8"> <script src="http://unpkg.com/vue/dist/vue.js"></script>

  • vue实现树形菜单效果

    本文实例为大家分享了vue实现树形菜单效果展示的具体代码,供大家参考,具体内容如下 <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>vue</title> <meta name="viewport" content="width=device-width, initial-scale=1.0">

  • Vue实现商品分类菜单数量提示功能

    如上所示,这篇我们将商品分类菜单显示数量的提示完善,是软件更加易于使用. 好先让我回顾一下上节课的内容,Goods组件,数量提示功能最终需要在Goods组件内显示. <template> <div class="goods"> <div class="menu-wrapper" ref="menuScroll"> <ul> <!--专场--> <li class="men

随机推荐